source: rtems/cpukit/rtems/src/msg.c @ 3235ad9

4.104.114.84.95
Last change on this file since 3235ad9 was 3235ad9, checked in by Joel Sherrill <joel.sherrill@…>, on 08/23/95 at 19:30:23

Support for variable length names added to Object Handler. This supports
both fixed length "raw" names and strings from the API's point of view.

Both inline and macro implementations were tested.

  • Property mode set to 100644
File size: 21.9 KB
Line 
1/*
2 *  Message Queue Manager
3 *
4 *
5 *  COPYRIGHT (c) 1989, 1990, 1991, 1992, 1993, 1994.
6 *  On-Line Applications Research Corporation (OAR).
7 *  All rights assigned to U.S. Government, 1994.
8 *
9 *  This material may be reproduced by or for the U.S. Government pursuant
10 *  to the copyright license under the clause at DFARS 252.227-7013.  This
11 *  notice must appear in all copies of this file and its derivatives.
12 *
13 *  $Id$
14 */
15
16#include <rtems/system.h>
17#include <rtems/attr.h>
18#include <rtems/chain.h>
19#include <rtems/config.h>
20#include <rtems/isr.h>
21#include <rtems/message.h>
22#include <rtems/object.h>
23#include <rtems/options.h>
24#include <rtems/states.h>
25#include <rtems/support.h>
26#include <rtems/thread.h>
27#include <rtems/wkspace.h>
28#include <rtems/mpci.h>
29
30/*PAGE
31 *
32 *  _Message_queue_Manager_initialization
33 *
34 *  This routine initializes all message queue manager related
35 *  data structures.
36 *
37 *  Input parameters:
38 *    maximum_message_queues - number of message queues to initialize
39 *
40 *  Output parameters:  NONE
41 */
42
43void _Message_queue_Manager_initialization(
44  unsigned32 maximum_message_queues
45)
46{
47  _Objects_Initialize_information(
48    &_Message_queue_Information,
49    OBJECTS_RTEMS_MESSAGE_QUEUES,
50    TRUE,
51    maximum_message_queues,
52    sizeof( Message_queue_Control ),
53    FALSE,
54    RTEMS_MAXIMUM_NAME_LENGTH
55  );
56}
57
58/*PAGE
59 *
60 *  _Message_queue_Allocate
61 *
62 *  Allocate a message queue and the space for its messages
63 */
64
65Message_queue_Control *_Message_queue_Allocate (
66  unsigned32          count,
67  unsigned32          max_message_size
68)
69{
70    Message_queue_Control *mq = 0;
71    unsigned32 message_buffering_required;
72    unsigned32 allocated_message_size;
73
74    mq = \
75      (Message_queue_Control *)_Objects_Allocate(&_Message_queue_Information);
76
77    if (mq == 0)
78        goto failed;
79
80    mq->maximum_message_size = max_message_size;
81
82    /*
83     * round size up to multiple of a ptr for chain init
84     */
85   
86    allocated_message_size = max_message_size;
87    if (allocated_message_size & (sizeof(unsigned32) - 1)) {
88        allocated_message_size += sizeof(unsigned32);
89        allocated_message_size &= ~(sizeof(unsigned32) - 1);
90    }
91   
92    message_buffering_required =
93      count * (allocated_message_size + sizeof(Message_queue_Buffer_control));
94 
95    mq->message_buffers =
96      (Message_queue_Buffer *) _Workspace_Allocate(message_buffering_required);
97
98    if (mq->message_buffers == 0)
99        goto failed;
100 
101    _Chain_Initialize
102      (&mq->Inactive_messages,
103      mq->message_buffers,
104      count,
105      allocated_message_size + sizeof(Message_queue_Buffer_control)
106    );
107    return mq;
108
109failed:
110    if (mq)
111        _Message_queue_Free(mq);
112    return (Message_queue_Control *) 0;
113}
114
115/*PAGE
116 *
117 *  rtems_message_queue_create
118 *
119 *  This directive creates a message queue by allocating and initializing
120 *  a message queue data structure.
121 *
122 *  Input parameters:
123 *    name          - user defined queue name
124 *    count         - maximum message and reserved buffer count
125 *    max_message_size - maximum size of each message
126 *    attribute_set - process method
127 *    id            - pointer to queue
128 *
129 *  Output parameters:
130 *    id                - queue id
131 *    RTEMS_SUCCESSFUL - if successful
132 *    error code        - if unsuccessful
133 */
134
135rtems_status_code rtems_message_queue_create(
136  rtems_name          name,
137  unsigned32          count,
138  unsigned32          max_message_size,
139  rtems_attribute     attribute_set,
140  Objects_Id         *id
141)
142{
143  register Message_queue_Control *the_message_queue;
144
145  if ( !rtems_is_name_valid( name ) )
146    return ( RTEMS_INVALID_NAME );
147
148  if ( _Attributes_Is_global( attribute_set ) &&
149       !_Configuration_Is_multiprocessing() )
150    return( RTEMS_MP_NOT_CONFIGURED );
151
152  if (count == 0)
153      return RTEMS_INVALID_NUMBER;
154
155  if (max_message_size == 0)
156      return RTEMS_INVALID_SIZE;
157
158#if 1
159  /*
160   * I am not 100% sure this should be an error.
161   * It seems reasonable to create a que with a large max size,
162   * and then just send smaller msgs from remote (or all) nodes.
163   */
164 
165  if ( _Attributes_Is_global( attribute_set ) &&
166       _Configuration_MPCI_table &&
167       (_Configuration_MPCI_table->maximum_packet_size < max_message_size))
168  {
169      return RTEMS_INVALID_SIZE;
170  }
171#endif
172       
173  _Thread_Disable_dispatch();              /* protects object pointer */
174
175  the_message_queue = _Message_queue_Allocate(count, max_message_size);
176
177  if ( !the_message_queue ) {
178    _Thread_Enable_dispatch();
179    return( RTEMS_TOO_MANY );
180  }
181
182  if ( _Attributes_Is_global( attribute_set ) &&
183       !( _Objects_MP_Open( &_Message_queue_Information, name,
184                            the_message_queue->Object.id, FALSE ) ) ) {
185    _Message_queue_Free( the_message_queue );
186    _Thread_Enable_dispatch();
187    return RTEMS_TOO_MANY;
188  }
189
190  the_message_queue->maximum_pending_messages = count;
191
192  the_message_queue->attribute_set = attribute_set;
193  the_message_queue->number_of_pending_messages = 0;
194
195  _Chain_Initialize_empty( &the_message_queue->Pending_messages );
196
197  _Thread_queue_Initialize( &the_message_queue->Wait_queue, attribute_set,
198                            STATES_WAITING_FOR_MESSAGE );
199
200  _Objects_Open(
201    &_Message_queue_Information,
202    &the_message_queue->Object,
203    &name
204  );
205
206  *id = the_message_queue->Object.id;
207
208  if ( _Attributes_Is_global( attribute_set ) )
209    _Message_queue_MP_Send_process_packet(
210      MESSAGE_QUEUE_MP_ANNOUNCE_CREATE,
211      the_message_queue->Object.id,
212      name,
213      0
214    );
215
216  _Thread_Enable_dispatch();
217  return( RTEMS_SUCCESSFUL );
218}
219
220/*PAGE
221 *
222 *  rtems_message_queue_ident
223 *
224 *  This directive returns the system ID associated with
225 *  the message queue name.
226 *
227 *  Input parameters:
228 *    name - user defined message queue name
229 *    node - node(s) to be searched
230 *    id   - pointer to message queue id
231 *
232 *  Output parameters:
233 *    *id               - message queue id
234 *    RTEMS_SUCCESSFUL - if successful
235 *    error code        - if unsuccessful
236 */
237
238rtems_status_code rtems_message_queue_ident(
239  rtems_name    name,
240  unsigned32    node,
241  Objects_Id   *id
242)
243{
244  return _Objects_Name_to_id(
245    &_Message_queue_Information,
246    &name,
247    node,
248    id
249  );
250}
251
252/*PAGE
253 *
254 *  rtems_message_queue_delete
255 *
256 *  This directive allows a thread to delete the message queue specified
257 *  by the given queue identifier.
258 *
259 *  Input parameters:
260 *    id - queue id
261 *
262 *  Output parameters:
263 *    RTEMS_SUCCESSFUL - if successful
264 *    error code        - if unsuccessful
265 */
266
267rtems_status_code rtems_message_queue_delete(
268  Objects_Id id
269)
270{
271  register Message_queue_Control *the_message_queue;
272  Objects_Locations               location;
273
274  the_message_queue = _Message_queue_Get( id, &location );
275  switch ( location ) {
276    case OBJECTS_ERROR:
277      return( RTEMS_INVALID_ID );
278    case OBJECTS_REMOTE:
279      _Thread_Dispatch();
280      return( RTEMS_ILLEGAL_ON_REMOTE_OBJECT );
281    case OBJECTS_LOCAL:
282      _Objects_Close( &_Message_queue_Information,
283                      &the_message_queue->Object );
284
285      if ( the_message_queue->number_of_pending_messages != 0 )
286        (void) _Message_queue_Flush_support( the_message_queue );
287      else
288        _Thread_queue_Flush(
289          &the_message_queue->Wait_queue,
290          _Message_queue_MP_Send_object_was_deleted
291        );
292
293      _Message_queue_Free( the_message_queue );
294
295      if ( _Attributes_Is_global( the_message_queue->attribute_set ) ) {
296        _Objects_MP_Close(
297          &_Message_queue_Information,
298          the_message_queue->Object.id
299        );
300
301        _Message_queue_MP_Send_process_packet(
302          MESSAGE_QUEUE_MP_ANNOUNCE_DELETE,
303          the_message_queue->Object.id,
304          0,                                 /* Not used */
305          0
306        );
307      }
308
309      _Thread_Enable_dispatch();
310      return( RTEMS_SUCCESSFUL );
311  }
312
313  return( RTEMS_INTERNAL_ERROR );   /* unreached - only to remove warnings */
314}
315
316/*PAGE
317 *
318 *  rtems_message_queue_send
319 *
320 *  This routine implements the directives q_send.  It sends a
321 *  message to the specified message queue.
322 *
323 *  Input parameters:
324 *    id     - pointer to message queue
325 *    buffer - pointer to message buffer
326 *
327 *  Output parameters:
328 *    RTEMS_SUCCESSFUL - if successful
329 *    error code        - if unsuccessful
330 */
331
332rtems_status_code rtems_message_queue_send(
333  Objects_Id            id,
334  void                 *buffer,
335  unsigned32            size
336)
337{
338  return _Message_queue_Submit(id, buffer, size, MESSAGE_QUEUE_SEND_REQUEST);
339}
340
341/*PAGE
342 *
343 *  rtems_message_queue_urgent
344 *
345 *  This routine implements the directives q_urgent.  It urgents a
346 *  message to the specified message queue.
347 *
348 *  Input parameters:
349 *    id     - pointer to message queue
350 *    buffer - pointer to message buffer
351 *
352 *  Output parameters:
353 *    RTEMS_SUCCESSFUL - if successful
354 *    error code - if unsuccessful
355 */
356
357rtems_status_code rtems_message_queue_urgent(
358  Objects_Id            id,
359  void                 *buffer,
360  unsigned32            size
361)
362{
363  return _Message_queue_Submit(id, buffer, size, MESSAGE_QUEUE_URGENT_REQUEST);
364}
365
366/*PAGE
367 *
368 *  rtems_message_queue_broadcast
369 *
370 *  This directive sends a message for every thread waiting on the queue
371 *  designated by id.
372 *
373 *  Input parameters:
374 *    id     - pointer to message queue
375 *    buffer - pointer to message buffer
376 *    count  - pointer to area to store number of threads made ready
377 *
378 *  Output parameters:
379 *    count             - number of threads made ready
380 *    RTEMS_SUCCESSFUL - if successful
381 *    error code        - if unsuccessful
382 */
383
384rtems_status_code rtems_message_queue_broadcast(
385  Objects_Id            id,
386  void                 *buffer,
387  unsigned32            size,
388  unsigned32           *count
389)
390{
391  register Message_queue_Control *the_message_queue;
392  Objects_Locations               location;
393  Thread_Control                 *the_thread;
394  unsigned32                      number_broadcasted;
395
396  the_message_queue = _Message_queue_Get( id, &location );
397  switch ( location ) {
398    case OBJECTS_ERROR:
399      return( RTEMS_INVALID_ID );
400    case OBJECTS_REMOTE:
401      _Thread_Executing->Wait.return_argument = count;
402
403      return
404        _Message_queue_MP_Send_request_packet(
405          MESSAGE_QUEUE_MP_BROADCAST_REQUEST,
406          id,
407          buffer,
408          &size,
409          0,                               /* option_set not used */
410          MPCI_DEFAULT_TIMEOUT
411        );
412
413    case OBJECTS_LOCAL:
414    {
415      Thread_Wait_information *waitp;
416      unsigned32 constrained_size;
417
418      number_broadcasted = 0;
419      while ( (the_thread =
420                 _Thread_queue_Dequeue(&the_message_queue->Wait_queue)) ) {
421        waitp = &the_thread->Wait;
422        number_broadcasted += 1;
423
424        constrained_size = size;
425        if (size > the_message_queue->maximum_message_size)
426            constrained_size = the_message_queue->maximum_message_size;
427
428        _Message_queue_Copy_buffer(buffer,
429                                   waitp->return_argument,
430                                   constrained_size);
431
432        *waitp->Extra.message_size_p = constrained_size;
433       
434        if ( !_Objects_Is_local_id( the_thread->Object.id ) ) {
435          the_thread->receive_packet->return_code = RTEMS_SUCCESSFUL;
436
437          _Message_queue_MP_Send_response_packet(
438            MESSAGE_QUEUE_MP_RECEIVE_RESPONSE,
439            id,
440            the_thread
441          );
442        }
443      }
444      _Thread_Enable_dispatch();
445      *count = number_broadcasted;
446      return( RTEMS_SUCCESSFUL );
447    }
448
449    default:
450      return RTEMS_INTERNAL_ERROR;
451  }
452}
453
454/*PAGE
455 *
456 *  rtems_message_queue_receive
457 *
458 *  This directive dequeues a message from the designated message queue
459 *  and copies it into the requesting thread's buffer.
460 *
461 *  Input parameters:
462 *    id         - queue id
463 *    buffer     - pointer to message buffer
464 *    option_set - options on receive
465 *    timeout    - number of ticks to wait
466 *
467 *  Output parameters:
468 *    RTEMS_SUCCESSFUL - if successful
469 *    error code        - if unsuccessful
470 */
471
472rtems_status_code rtems_message_queue_receive(
473  Objects_Id            id,
474  void                 *buffer,
475  unsigned32           *size_p,
476  unsigned32            option_set,
477  rtems_interval        timeout
478)
479{
480  register Message_queue_Control *the_message_queue;
481  Objects_Locations               location;
482
483  the_message_queue = _Message_queue_Get( id, &location );
484  switch ( location ) {
485
486    case OBJECTS_ERROR:
487      return( RTEMS_INVALID_ID );
488
489    case OBJECTS_REMOTE:
490      _Thread_Executing->Wait.return_argument = buffer;
491     
492      return _Message_queue_MP_Send_request_packet(
493          MESSAGE_QUEUE_MP_RECEIVE_REQUEST,
494          id,
495          buffer,
496          size_p,
497          option_set,
498          timeout
499        );
500
501    case OBJECTS_LOCAL:
502      if ( ! _Message_queue_Seize(the_message_queue,
503                                  option_set,
504                                  buffer,
505                                  size_p))
506      {
507        _Thread_queue_Enqueue( &the_message_queue->Wait_queue, timeout );
508      }
509      _Thread_Enable_dispatch();
510      return _Thread_Executing->Wait.return_code;
511  }
512
513  return( RTEMS_INTERNAL_ERROR );   /* unreached - only to remove warnings */
514}
515
516/*PAGE
517 *
518 *  rtems_message_queue_flush
519 *
520 *  This directive removes all pending messages from a queue and returns
521 *  the number of messages removed.  If no messages were present then
522 *  a count of zero is returned.
523 *
524 *  Input parameters:
525 *    id    - queue id
526 *    count - return area for count
527 *
528 *  Output parameters:
529 *    count             - number of messages removed ( 0 = empty queue )
530 *    RTEMS_SUCCESSFUL - if successful
531 *    error code        - if unsuccessful
532 */
533
534rtems_status_code rtems_message_queue_flush(
535  Objects_Id  id,
536  unsigned32 *count
537)
538{
539  register Message_queue_Control *the_message_queue;
540  Objects_Locations               location;
541
542  the_message_queue = _Message_queue_Get( id, &location );
543  switch ( location ) {
544    case OBJECTS_ERROR:
545      return( RTEMS_INVALID_ID );
546    case OBJECTS_REMOTE:
547      _Thread_Executing->Wait.return_argument = count;
548
549      return
550        _Message_queue_MP_Send_request_packet(
551          MESSAGE_QUEUE_MP_FLUSH_REQUEST,
552          id,
553          0,                               /* buffer not used */
554          0,                               /* size_p */
555          0,                               /* option_set not used */
556          MPCI_DEFAULT_TIMEOUT
557        );
558
559    case OBJECTS_LOCAL:
560      if ( the_message_queue->number_of_pending_messages != 0 )
561        *count = _Message_queue_Flush_support( the_message_queue );
562      else
563        *count = 0;
564      _Thread_Enable_dispatch();
565      return( RTEMS_SUCCESSFUL );
566  }
567
568  return( RTEMS_INTERNAL_ERROR );   /* unreached - only to remove warnings */
569}
570
571/*PAGE
572 *
573 *  _Message_queue_Seize
574 *
575 *  This kernel routine dequeues a message, copies the message buffer to
576 *  a given destination buffer, and frees the message buffer to the
577 *  inactive message pool.
578 *
579 *  Input parameters:
580 *    the_message_queue - pointer to message queue
581 *    option_set        - options on receive
582 *    the_buffer        - pointer to message buffer to be filled
583 *
584 *  Output parameters:
585 *    TRUE  - if message received or RTEMS_NO_WAIT and no message
586 *    FALSE - if thread is to block
587 *
588 *  NOTE: Dependent on BUFFER_LENGTH
589 *
590 *  INTERRUPT LATENCY:
591 *    available
592 *    wait
593 */
594
595boolean _Message_queue_Seize(
596  Message_queue_Control  *the_message_queue,
597  rtems_option            option_set,
598  void                   *buffer,
599  unsigned32             *size_p
600)
601{
602  ISR_Level                     level;
603  Message_queue_Buffer_control *the_message;
604  Thread_Control               *executing;
605
606  executing = _Thread_Executing;
607  executing->Wait.return_code = RTEMS_SUCCESSFUL;
608  _ISR_Disable( level );
609  if ( the_message_queue->number_of_pending_messages != 0 ) {
610    the_message_queue->number_of_pending_messages -= 1;
611
612    the_message = _Message_queue_Get_pending_message( the_message_queue );
613    _ISR_Enable( level );
614    *size_p = the_message->Contents.size;
615    _Message_queue_Copy_buffer( the_message->Contents.buffer, buffer, *size_p );
616    _Message_queue_Free_message_buffer(the_message_queue, the_message );
617    return( TRUE );
618  }
619
620  if ( _Options_Is_no_wait( option_set ) ) {
621    _ISR_Enable( level );
622    executing->Wait.return_code = RTEMS_UNSATISFIED;
623    return( TRUE );
624  }
625
626  the_message_queue->Wait_queue.sync = TRUE;
627  executing->Wait.queue              = &the_message_queue->Wait_queue;
628  executing->Wait.id                 = the_message_queue->Object.id;
629  executing->Wait.option_set         = option_set;
630  executing->Wait.return_argument    = (unsigned32 *)buffer;
631  executing->Wait.Extra.message_size_p = size_p;
632  _ISR_Enable( level );
633  return FALSE;
634}
635
636/*PAGE
637 *
638 *  _Message_queue_Flush_support
639 *
640 *  This message manager routine removes all messages from a message queue
641 *  and returns them to the inactive message pool.
642 *
643 *  Input parameters:
644 *    the_message_queue - pointer to message queue
645 *
646 *  Output parameters:
647 *    returns - number of messages placed on inactive chain
648 *
649 *  INTERRUPT LATENCY:
650 *    only case
651 */
652
653unsigned32 _Message_queue_Flush_support(
654  Message_queue_Control *the_message_queue
655)
656{
657  ISR_Level   level;
658  Chain_Node *inactive_first;
659  Chain_Node *message_queue_first;
660  Chain_Node *message_queue_last;
661  unsigned32  count;
662
663  _ISR_Disable( level );
664    inactive_first      = the_message_queue->Inactive_messages.first;
665    message_queue_first = the_message_queue->Pending_messages.first;
666    message_queue_last  = the_message_queue->Pending_messages.last;
667
668    the_message_queue->Inactive_messages.first = message_queue_first;
669    message_queue_last->next = inactive_first;
670    inactive_first->previous = message_queue_last;
671    message_queue_first->previous          =
672               _Chain_Head( &the_message_queue->Inactive_messages );
673
674    _Chain_Initialize_empty( &the_message_queue->Pending_messages );
675
676    count = the_message_queue->number_of_pending_messages;
677    the_message_queue->number_of_pending_messages = 0;
678  _ISR_Enable( level );
679  return count;
680}
681
682/*PAGE
683 *
684 *  _Message_queue_Submit
685 *
686 *  This routine implements the directives q_send and q_urgent.  It
687 *  processes a message that is to be submitted to the designated
688 *  message queue.  The message will either be processed as a send
689 *  send message which it will be inserted at the rear of the queue
690 *  or it will be processed as an urgent message which will be inserted
691 *  at the front of the queue.
692 *
693 *  Input parameters:
694 *    id          - pointer to message queue
695 *    buffer      - pointer to message buffer
696 *    size        - size in bytes of message to send
697 *    submit_type - send or urgent message
698 *
699 *  Output parameters:
700 *    RTEMS_SUCCESSFUL - if successful
701 *    error code       - if unsuccessful
702 */
703
704rtems_status_code _Message_queue_Submit(
705  Objects_Id                  id,
706  void                       *buffer,
707  unsigned32                  size,
708  Message_queue_Submit_types  submit_type
709)
710{
711  register Message_queue_Control *the_message_queue;
712  Objects_Locations               location;
713  Thread_Control                 *the_thread;
714  Message_queue_Buffer_control   *the_message;
715
716  the_message_queue = _Message_queue_Get( id, &location );
717  switch ( location )
718  {
719    case OBJECTS_ERROR:
720      return( RTEMS_INVALID_ID );
721
722    case OBJECTS_REMOTE:
723      switch ( submit_type ) {
724        case MESSAGE_QUEUE_SEND_REQUEST:
725          return
726            _Message_queue_MP_Send_request_packet(
727              MESSAGE_QUEUE_MP_SEND_REQUEST,
728              id,
729              buffer,
730              &size,
731              0,                               /* option_set */
732              MPCI_DEFAULT_TIMEOUT
733            );
734
735        case MESSAGE_QUEUE_URGENT_REQUEST:
736          return
737            _Message_queue_MP_Send_request_packet(
738              MESSAGE_QUEUE_MP_URGENT_REQUEST,
739              id,
740              buffer,
741              &size,
742              0,                               /* option_set */
743              MPCI_DEFAULT_TIMEOUT
744            );
745      }
746
747    case OBJECTS_LOCAL:
748      if (size > the_message_queue->maximum_message_size)
749      {
750          _Thread_Enable_dispatch();
751          return RTEMS_INVALID_SIZE;
752      }
753
754      /*
755       * Is there a thread currently waiting on this message queue?
756       */
757     
758      the_thread = _Thread_queue_Dequeue( &the_message_queue->Wait_queue );
759      if ( the_thread )
760      {
761        _Message_queue_Copy_buffer(
762          buffer,
763          the_thread->Wait.return_argument,
764          size
765        );
766        *the_thread->Wait.Extra.message_size_p = size;
767       
768        if ( !_Objects_Is_local_id( the_thread->Object.id ) ) {
769          the_thread->receive_packet->return_code = RTEMS_SUCCESSFUL;
770
771          _Message_queue_MP_Send_response_packet(
772            MESSAGE_QUEUE_MP_RECEIVE_RESPONSE,
773            id,
774            the_thread
775          );
776
777        }
778        _Thread_Enable_dispatch();
779        return( RTEMS_SUCCESSFUL );
780      }
781
782      /*
783       * No one waiting on this one currently.
784       * Allocate a message buffer and store it away
785       */
786
787      if ( the_message_queue->number_of_pending_messages ==
788           the_message_queue->maximum_pending_messages ) {
789        _Thread_Enable_dispatch();
790        return( RTEMS_TOO_MANY );
791      }
792
793      the_message = _Message_queue_Allocate_message_buffer(the_message_queue);
794      if ( the_message == 0) {
795        _Thread_Enable_dispatch();
796        return( RTEMS_UNSATISFIED );
797      }
798
799      _Message_queue_Copy_buffer( buffer, the_message->Contents.buffer, size );
800      the_message->Contents.size = size;
801     
802      the_message_queue->number_of_pending_messages += 1;
803
804      switch ( submit_type ) {
805        case MESSAGE_QUEUE_SEND_REQUEST:
806          _Message_queue_Append( the_message_queue, the_message );
807          break;
808        case MESSAGE_QUEUE_URGENT_REQUEST:
809          _Message_queue_Prepend( the_message_queue, the_message );
810          break;
811      }
812
813      _Thread_Enable_dispatch();
814      return( RTEMS_SUCCESSFUL );
815         
816    default:
817      return RTEMS_INTERNAL_ERROR;       /* And they were such nice boys, too! */
818  }
819}
Note: See TracBrowser for help on using the repository browser.