3 * - By John Hodge (thePowersGang)
11 #include <threads_int.h>
17 * \fn int Proc_SendMessage(Uint *Err, Uint Dest, int Length, void *Data)
18 * \brief Send an IPC message
19 * \param Err Pointer to the errno variable
20 * \param Dest Destination Thread
21 * \param Length Length of the message
22 * \param Data Message data
24 int Proc_SendMessage(Uint *Err, Uint Dest, int Length, void *Data)
29 ENTER("pErr iDest iLength pData", Err, Dest, Length, Data);
31 if(Length <= 0 || !Data) {
36 // TODO: Check message length against global/per-thread maximums
37 // TODO: Restrict queue length
40 thread = Threads_GetThread( Dest );
43 if(!thread) LEAVE_RET('i', -1);
46 SHORTLOCK( &thread->IsLocked );
48 // Check if thread is still alive
49 if(thread->Status == THREAD_STAT_DEAD) {
50 SHORTREL( &thread->IsLocked );
55 msg = malloc( sizeof(tMsg)+Length );
57 msg->Source = Proc_GetCurThread()->TID;
59 memcpy(msg->Data, Data, Length);
61 // If there are already messages
62 if(thread->LastMessage) {
63 thread->LastMessage->Next = msg;
64 thread->LastMessage = msg;
66 thread->Messages = msg;
67 thread->LastMessage = msg;
70 SHORTREL(&thread->IsLocked);
73 LOG("Waking %p (%i %s)", thread, thread->TID, thread->ThreadName);
74 Threads_PostEvent( thread, THREAD_EVENT_IPCMSG );
80 * \fn int Proc_GetMessage(Uint *Err, Uint *Source, void *Buffer)
81 * \brief Gets a message
82 * \param Err Pointer to \a errno
83 * \param Source Where to put the source TID
84 * \param Buffer Buffer to place the message data (set to NULL to just get message length)
85 * \return Message length
87 int Proc_GetMessage(Uint *Err, Uint *Source, void *Buffer)
91 tThread *cur = Proc_GetCurThread();
93 ENTER("pSource pBuffer", Source, Buffer);
95 // Check if queue has any items
101 SHORTLOCK( &cur->IsLocked );
104 *Source = cur->Messages->Source;
105 LOG("*Source = %i", *Source);
108 // Get message length
110 ret = cur->Messages->Length;
111 SHORTREL( &cur->IsLocked );
117 if(Buffer != GETMSG_IGNORE)
119 if( !CheckMem( Buffer, cur->Messages->Length ) )
121 LOG("Invalid buffer");
123 SHORTREL( &cur->IsLocked );
127 LOG("Copied to buffer");
128 memcpy(Buffer, cur->Messages->Data, cur->Messages->Length);
130 ret = cur->Messages->Length;
134 cur->Messages = cur->Messages->Next;
135 if(cur->Messages == NULL) cur->LastMessage = NULL;
137 SHORTREL( &cur->IsLocked );
139 free(tmp); // Free outside of lock