kernel: sched: Make k_sleep() similar to POSIX equivalent

This commit introduces k_sleep() return value, which provides
information about actual sleep time. If the returned value is
not-zero, the thread slept shorter than requested, which is
only possible if the thread has been woken up by k_wakeup() call.

Signed-off-by: Piotr Zięcik <piotr.ziecik@nordicsemi.no>
This commit is contained in:
Piotr Zięcik 2018-10-25 17:45:08 +02:00 committed by Carles Cufí
commit 7700eb2a15
2 changed files with 17 additions and 10 deletions

View file

@ -787,9 +787,11 @@ void k_thread_system_pool_assign(struct k_thread *thread);
*
* @param duration Number of milliseconds to sleep.
*
* @return N/A
* @return Zero if the requested time has elapsed or the number of milliseconds
* left to sleep, if thread was woken up by \ref k_wakeup call.
*
*/
__syscall void k_sleep(s32_t duration);
__syscall s32_t k_sleep(s32_t duration);
/**
* @brief Cause the current thread to busy wait.

View file

@ -793,13 +793,11 @@ void _impl_k_yield(void)
Z_SYSCALL_HANDLER0_SIMPLE_VOID(k_yield);
#endif
void _impl_k_sleep(s32_t duration)
s32_t _impl_k_sleep(s32_t duration)
{
#ifdef CONFIG_MULTITHREADING
/* volatile to guarantee that irq_lock() is executed after ticks is
* populated
*/
volatile s32_t ticks;
u32_t expected_wakeup_time;
s32_t ticks;
unsigned int key;
__ASSERT(!_is_in_isr(), "");
@ -810,17 +808,25 @@ void _impl_k_sleep(s32_t duration)
/* wait of 0 ms is treated as a 'yield' */
if (duration == 0) {
k_yield();
return;
return 0;
}
ticks = _TICK_ALIGN + _ms_to_ticks(duration);
expected_wakeup_time = ticks + z_tick_get_32();
key = irq_lock();
_remove_thread_from_ready_q(_current);
_add_thread_timeout(_current, ticks);
(void)_Swap(key);
ticks = expected_wakeup_time - z_tick_get_32();
if (ticks > 0) {
return __ticks_to_ms(ticks);
}
#endif
return 0;
}
#ifdef CONFIG_USERSPACE
@ -831,9 +837,8 @@ Z_SYSCALL_HANDLER(k_sleep, duration)
*/
Z_OOPS(Z_SYSCALL_VERIFY_MSG(duration != K_FOREVER,
"sleeping forever not allowed"));
_impl_k_sleep(duration);
return 0;
return _impl_k_sleep(duration);
}
#endif