90 |
if (ipc_tqueue_empty (& send_port->waiting_threads) == false) |
if (ipc_tqueue_empty (& send_port->waiting_threads) == false) |
91 |
{ |
{ |
92 |
struct thread *thread; |
struct thread *thread; |
93 |
|
SPL_T spl; |
94 |
|
|
95 |
thread = ipc_tqueue_dequeue (& send_port->waiting_threads); |
thread = ipc_tqueue_dequeue (& send_port->waiting_threads); |
96 |
|
|
97 |
|
spl = SPLOFF (); |
98 |
thread_lock (thread); |
thread_lock (thread); |
99 |
|
|
100 |
/* If there's not room for the message we continue to the |
/* If there's not room for the message we continue to the |
104 |
{ |
{ |
105 |
thread->ipc_result = MSG_RCV_TOO_SMALL; |
thread->ipc_result = MSG_RCV_TOO_SMALL; |
106 |
thread_unlock (thread); |
thread_unlock (thread); |
107 |
|
SPLON (spl); |
108 |
|
|
109 |
thread_interrupt (thread); |
thread_interrupt (thread); |
110 |
goto retry_waiting_thread; |
goto retry_waiting_thread; |
113 |
thread->ipc_result = MSG_SUCCESS; |
thread->ipc_result = MSG_SUCCESS; |
114 |
thread->ipc_kmsg = ikm; |
thread->ipc_kmsg = ikm; |
115 |
thread_unlock (thread); |
thread_unlock (thread); |
116 |
|
SPLON (spl); |
117 |
|
|
118 |
thread_lock_unlock (& send_port->lock); |
thread_lock_unlock (& send_port->lock); |
119 |
|
|
169 |
kern_return_t kr; |
kern_return_t kr; |
170 |
bool intratask_p; |
bool intratask_p; |
171 |
|
|
172 |
#if 1 |
#if 0 |
173 |
trace_printf ("options %d sname %d ssize %d rname %d rsize %d", |
trace_printf ("options %d sname %d ssize %d rname %d rsize %d", |
174 |
options, send_name, send_size, recv_name, recv_size); |
options, send_name, send_size, recv_name, recv_size); |
175 |
#endif |
#endif |
183 |
|
|
184 |
kr = ipc_object_lookup (object, recv_name, &entry); |
kr = ipc_object_lookup (object, recv_name, &entry); |
185 |
if (kr != KERN_SUCCESS) |
if (kr != KERN_SUCCESS) |
186 |
return kr; |
{ |
187 |
|
ipc_object_unlock (object); |
188 |
|
return kr; |
189 |
|
} |
190 |
|
|
191 |
if (! (entry->ie_bits & RTMK_PORT_TYPE_RECEIVE)) |
if (! (entry->ie_bits & RTMK_PORT_TYPE_RECEIVE)) |
192 |
{ |
{ |
333 |
else if (ipc_tqueue_empty (&port->waiting_threads) == false) |
else if (ipc_tqueue_empty (&port->waiting_threads) == false) |
334 |
{ |
{ |
335 |
bool succeeded; |
bool succeeded; |
336 |
|
SPL_T spl; |
337 |
|
|
338 |
/* We have to update the lock from read to write. */ |
/* We have to update the lock from read to write. */ |
339 |
|
|
344 |
|
|
345 |
retry_waiting_thread: |
retry_waiting_thread: |
346 |
target = ipc_tqueue_dequeue (&port->waiting_threads); |
target = ipc_tqueue_dequeue (&port->waiting_threads); |
347 |
|
spl = SPLOFF (); |
348 |
thread_lock (target); |
thread_lock (target); |
349 |
|
|
350 |
/* If there's not room for the message we continue to the |
/* If there's not room for the message we continue to the |
355 |
thread->ipc_result = MSG_RCV_TOO_SMALL; |
thread->ipc_result = MSG_RCV_TOO_SMALL; |
356 |
|
|
357 |
thread_unlock (thread); |
thread_unlock (thread); |
358 |
|
SPLON (spl); |
359 |
thread_interrupt (thread); |
thread_interrupt (thread); |
360 |
|
|
361 |
if (! ipc_tqueue_empty (&port->waiting_threads)) |
if (! ipc_tqueue_empty (&port->waiting_threads)) |
368 |
target->ipc_result = KERN_SUCCESS; |
target->ipc_result = KERN_SUCCESS; |
369 |
target->ipc_kmsg = kmsg; |
target->ipc_kmsg = kmsg; |
370 |
thread_unlock (target); |
thread_unlock (target); |
371 |
|
SPLON (spl); |
372 |
|
|
373 |
thread_lock_unlock (&port->lock); |
thread_lock_unlock (&port->lock); |
374 |
ipc_object_unlock (object); |
ipc_object_unlock (object); |