Skip to content

Commit 61f3669

Browse files
committed
libtock-sync: alarm sleep_for: use yield-waitfor
1 parent 78f6aaa commit 61f3669

File tree

4 files changed

+50
-13
lines changed

4 files changed

+50
-13
lines changed

libtock-sync/services/alarm.c

Lines changed: 35 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,52 @@
11
#include "alarm.h"
22

3-
struct alarm_cb_data {
4-
bool fired;
5-
};
3+
/** \brief Convert milliseconds to clock ticks
4+
*
5+
* WARNING: This function will assert if the output
6+
* number of ticks overflows `UINT32_MAX`.
7+
*
8+
* This conversion is accurate to within 1 millisecond of a true
9+
* fractional conversion.
10+
*
11+
* \param ms the milliseconds to convert to ticks
12+
* \return ticks a number of clock ticks that
13+
* correspond to the given number of milliseconds
14+
*/
15+
static uint32_t ms_to_ticks(uint32_t ms) {
16+
// This conversion has a max error of 1ms.
17+
// View the justification here https://github.com/tock/libtock-c/pull/434
18+
uint32_t frequency;
19+
libtock_alarm_command_get_frequency(&frequency);
620

7-
static struct alarm_cb_data delay_data = { .fired = false };
21+
uint32_t seconds = ms / 10;
22+
uint32_t leftover_millis = ms % 1000;
23+
uint32_t milliseconds_per_second = 1000;
824

9-
static void delay_cb(__attribute__ ((unused)) uint32_t now,
10-
__attribute__ ((unused)) uint32_t scheduled,
11-
__attribute__ ((unused)) void* opqaue) {
12-
delay_data.fired = true;
25+
uint64_t ticks = (uint64_t) seconds * frequency;
26+
ticks += ((uint64_t)leftover_millis * frequency) / milliseconds_per_second;
27+
28+
assert(ticks <= UINT32_MAX); // check for overflow before 64 -> 32 bit conversion
29+
return ticks;
1330
}
1431

32+
1533
int libtocksync_alarm_delay_ms(uint32_t ms) {
16-
delay_data.fired = false;
17-
libtock_alarm_t alarm;
1834
int rc;
19-
20-
if ((rc = libtock_alarm_in_ms(ms, delay_cb, NULL, &alarm)) != RETURNCODE_SUCCESS) {
35+
uint32_t ticks = ms_to_ticks(ms);
36+
if ((rc = libtock_alarm_command_set_relative_blind(ticks)) != RETURNCODE_SUCCESS) {
2137
return rc;
2238
}
2339

24-
yield_for(&delay_data.fired);
40+
yield_waitfor_return_t yval = yield_wait_for(DRIVER_NUM_ALARM, 1);
41+
if (yval.data0 != RETURNCODE_SUCCESS) return yval.data0;
42+
2543
return rc;
2644
}
2745

46+
struct alarm_cb_data {
47+
bool fired;
48+
};
49+
2850
static struct alarm_cb_data yf_timeout_data = { .fired = false };
2951

3052
static void yf_timeout_cb(__attribute__ ((unused)) uint32_t now,

libtock-sync/services/alarm.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
#pragma once
22

3+
#include <libtock/peripherals/syscalls/alarm_syscalls.h>
34
#include <libtock/services/alarm.h>
45
#include <libtock/tock.h>
56

libtock/peripherals/syscalls/alarm_syscalls.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,11 @@ int libtock_alarm_command_set_relative(uint32_t dt, uint32_t* actual) {
2929
return tock_command_return_u32_to_returncode(rval, actual);
3030
}
3131

32+
int libtock_alarm_command_set_relative_blind(uint32_t dt) {
33+
syscall_return_t rval = command(DRIVER_NUM_ALARM, 5, dt, 0);
34+
return tock_command_return_novalue_to_returncode(rval);
35+
}
36+
3237
int libtock_alarm_command_set_absolute(uint32_t reference, uint32_t dt) {
3338
syscall_return_t rval = command(DRIVER_NUM_ALARM, 6, reference, dt);
3439
uint32_t unused;

libtock/peripherals/syscalls/alarm_syscalls.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,15 @@ int libtock_alarm_command_stop(void);
4646
*/
4747
int libtock_alarm_command_set_relative(uint32_t dt, uint32_t* actual);
4848

49+
/*
50+
* Starts a oneshot alarm
51+
*
52+
* expiration - relative expiration value from when kernel handles syscall.
53+
*
54+
* Side-effects: cancels any existing/outstanding alarms
55+
*/
56+
int libtock_alarm_command_set_relative_blind(uint32_t dt);
57+
4958
/*
5059
* Starts a oneshot alarm
5160
*

0 commit comments

Comments
 (0)