static int mbx_wait_until(MBX *mbx, int *fravbs, RTIME time, RT_TASK *rt_current) { unsigned long flags; flags = rt_global_save_flags_and_cli(); if (!(*fravbs)) { void *retp; rt_current->blocked_on = (void *)mbx; mbx->waiting_task = rt_current; if ((rt_current->resume_time = time) > rt_smp_time_h[rtai_cpuid()]) { rt_current->state |= (RT_SCHED_MBXSUSP | RT_SCHED_DELAYED); rem_ready_current(rt_current); enq_timed_task(rt_current); rt_schedule(); } if (unlikely((retp = rt_current->blocked_on) != NULL)) { mbx->waiting_task = NULL; rt_global_restore_flags(flags); return likely(retp > RTP_HIGERR) ? RTE_TIMOUT : (retp == RTP_UNBLKD ? RTE_UNBLKD : RTE_OBJREM); } } rt_global_restore_flags(flags); return 0; }
RTAI_SYSCALL_MODE int _rt_bits_wait(BITS *bits, int testfun, unsigned long testmasks, int exitfun, unsigned long exitmasks, unsigned long *resulting_mask, int space) { RT_TASK *rt_current; unsigned long flags, mask = 0; int retval; CHECK_BITS_MAGIC(bits); flags = rt_global_save_flags_and_cli(); if (!test_fun[testfun](bits, testmasks)) { void *retpnt; long bits_test[2]; rt_current = RT_CURRENT; TEST_BUF(rt_current, bits_test); TEST_FUN(rt_current) = testfun; TEST_MASK(rt_current) = testmasks; rt_current->state |= RT_SCHED_SEMAPHORE; rem_ready_current(rt_current); enqueue_blocked(rt_current, &bits->queue, 1); rt_schedule(); if (unlikely((retpnt = rt_current->blocked_on) != NULL)) { if (likely(retpnt != RTP_OBJREM)) { dequeue_blocked(rt_current); retval = RTE_UNBLKD; } else { rt_current->prio_passed_to = NULL; retval = RTE_OBJREM; } goto retmask; } } retval = 0; mask = bits->mask; exec_fun[exitfun](bits, exitmasks); retmask: rt_global_restore_flags(flags); if (resulting_mask) { if (space) { *resulting_mask = mask; } else { rt_copy_to_user(resulting_mask, &mask, sizeof(mask)); } } return retval; }
RTAI_SYSCALL_MODE int rt_wait_signal(RT_TASK *sigtask, RT_TASK *task) { unsigned long flags; if (sigtask->rt_signals != NULL) { flags = rt_global_save_flags_and_cli(); if (!sigtask->suspdepth++) { sigtask->state |= RT_SCHED_SIGSUSP; rem_ready_current(sigtask); if (task->pstate > 0 && !(--task->pstate) && (task->state &= ~RT_SCHED_SIGSUSP) == RT_SCHED_READY) { enq_ready_task(task); } rt_schedule(); } rt_global_restore_flags(flags); return sigtask->retval; } return 0; }
static int mbx_wait(MBX *mbx, int *fravbs, RT_TASK *rt_current) { unsigned long flags; flags = rt_global_save_flags_and_cli(); if (!(*fravbs)) { unsigned long retval; rt_current->state |= RT_SCHED_MBXSUSP; rem_ready_current(rt_current); rt_current->blocked_on = (void *)mbx; mbx->waiting_task = rt_current; rt_schedule(); if (unlikely(retval = (unsigned long)rt_current->blocked_on)) { mbx->waiting_task = NULL; rt_global_restore_flags(flags); return retval; } } rt_global_restore_flags(flags); return 0; }