Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions drivers/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -383,7 +383,7 @@ pub const Clock_Device = struct {
- `sleep_us(time_us)` - Sleep for N microseconds (polls if no custom sleep)
- `sleep_ms(time_ms)` - Sleep for N milliseconds
- `make_timeout(duration)` - Create deadline from current time + duration
- `is_reached(absolute_time)` - Check if time point has passed
- `Timeout.is_reached()` - Check if time point has passed

**Usage Example**:
```zig
Expand All @@ -394,7 +394,7 @@ const timeout = clock.make_timeout(mdf.time.Duration.from_ms(100));
// Poll with timeout
while (!is_ready()) {
if (clock.is_reached(timeout)) {
if (timeout.is_reached()) {
return error.Timeout;
}
}
Expand Down
49 changes: 29 additions & 20 deletions drivers/base/Clock_Device.zig
Original file line number Diff line number Diff line change
Expand Up @@ -18,18 +18,32 @@ ptr: *anyopaque,
/// Virtual table for the digital i/o functions.
vtable: *const VTable,

/// API
pub fn is_reached(td: Clock_Device, time: mdf.time.Absolute) bool {
/// Object created by make_timeout to perform to hold
/// a duration.
pub const Timeout = struct {
clock: Clock_Device,
time: mdf.time.Absolute,

pub fn is_reached(self: @This()) bool {
return self.clock.is_reached(self.time);
}

pub fn diff(self: @This()) mdf.time.Duration {
return self.time.diff(self.clock.get_time_since_boot());
}
};

fn is_reached(td: Clock_Device, time: mdf.time.Absolute) bool {
const now = td.get_time_since_boot();
return time.is_reached_by(now);
}

pub fn make_timeout(td: Clock_Device, timeout: mdf.time.Duration) mdf.time.Absolute {
return @as(mdf.time.Absolute, @enumFromInt(td.get_time_since_boot().to_us() + timeout.to_us()));
}

pub fn make_timeout_us(td: Clock_Device, timeout_us: u64) mdf.time.Absolute {
return @as(mdf.time.Absolute, @enumFromInt(td.get_time_since_boot().to_us() + timeout_us));
/// API
pub fn make_timeout(td: Clock_Device, timeout: mdf.time.Duration) Timeout {
return .{
.clock = td,
.time = td.get_time_since_boot().add_duration(timeout),
};
}

pub fn sleep_ms(td: Clock_Device, time_ms: u32) void {
Expand All @@ -44,8 +58,8 @@ pub fn sleep_us(td: Clock_Device, time_us: u64) void {
}

// Otherwise, fall back to polling
const end_time = td.make_timeout_us(time_us);
while (!td.is_reached(end_time)) {}
const end_time = td.make_timeout(.from_us(time_us));
while (!end_time.is_reached()) {}
}

/// VTable methods
Expand Down Expand Up @@ -116,17 +130,12 @@ test Test_Device {
ttd.elapse_time(2);
try std.testing.expectEqual(2, td.get_time_since_boot().to_us());

try std.testing.expect(!td.is_reached(@enumFromInt(4)));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are these assertions deleted?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I did remove is_reached from the public interface. There is now test around the Timeout which is the new public interface.

ttd.elapse_time(2);
try std.testing.expect(td.is_reached(@enumFromInt(4)));

// Timeouts
try std.testing.expectEqual(
54,
@intFromEnum(td.make_timeout(mdf.time.Duration.from_us(50))),
);
ttd.elapse_time(50);
try std.testing.expectEqual(104, @intFromEnum(td.make_timeout_us(50)));
const timeout = td.make_timeout(.from_us(50));
ttd.elapse_time(40);
try std.testing.expectEqual(mdf.time.Duration.from_us(10), timeout.diff());
ttd.elapse_time(10);
try std.testing.expect(timeout.is_reached());

try std.testing.expectEqual(0, ttd.get_total_sleep_time());
td.sleep_ms(1000);
Expand Down
9 changes: 4 additions & 5 deletions drivers/led/ws2812.zig
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ pub fn WS2812(options: struct {

dev: options.Datagram_Device,
clock_dev: options.Clock_Device,
next_write_time: ?mdf.time.Absolute = null,
next_write_time: ?mdf.base.Clock_Device.Timeout = null,
buffer: [buffer_size]u8 = undefined,

/// Initializes the driver.
Expand All @@ -36,9 +36,8 @@ pub fn WS2812(options: struct {

// ensures that a reset takes place between writes
if (self.next_write_time) |next_write_time| {
const now = self.clock_dev.get_time_since_boot();
if (!next_write_time.is_reached_by(now)) {
self.clock_dev.sleep_us(next_write_time.diff(now).to_us());
if (!next_write_time.is_reached()) {
self.clock_dev.sleep_us(next_write_time.diff().to_us());
}
}

Expand All @@ -63,7 +62,7 @@ pub fn WS2812(options: struct {

try self.dev.write(self.buffer[0..i]);

self.next_write_time = self.clock_dev.make_timeout_us(300);
self.next_write_time = self.clock_dev.make_timeout(.from_us(300));
}
};
}
Expand Down
Loading