ctap: Add support for the CTAP driver
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
diff --git a/src/ctap.rs b/src/ctap.rs
new file mode 100644
index 0000000..ac09120
--- /dev/null
+++ b/src/ctap.rs
@@ -0,0 +1,110 @@
+use crate::callback::CallbackSubscription;
+use crate::callback::Consumer;
+use crate::result::TockResult;
+use crate::syscalls;
+use core::marker::PhantomData;
+use libtock_core::shared_memory::SharedMemory;
+
+const DRIVER_NUMBER: usize = 0x40004;
+
+pub const RECV_BUFFER_SIZE: usize = 64;
+pub const SEND_BUFFER_SIZE: usize = 64;
+
+mod command_nr {
+ pub const SEND_DATA: usize = 0;
+ pub const ALLOW_RECEIVE: usize = 1;
+}
+
+mod subscribe_nr {
+ pub const SUBSCRIBE_CALLBACK: usize = 0;
+}
+
+mod allow_nr {
+ pub const RECV: usize = 0;
+ pub const SEND: usize = 1;
+}
+
+#[non_exhaustive]
+pub struct CtapDriverFactory;
+
+impl CtapDriverFactory {
+ pub fn init_driver(&mut self) -> TockResult<CtapDriver> {
+ let ctap = CtapDriver {
+ lifetime: PhantomData,
+ };
+ Ok(ctap)
+ }
+}
+
+struct CtapEventConsumer;
+
+impl<CB: FnMut(usize, usize)> Consumer<CB> for CtapEventConsumer {
+ fn consume(callback: &mut CB, sent: usize, _: usize, _: usize) {
+ callback(sent, 0);
+ }
+}
+
+pub struct CtapRecvBuffer {
+ buffer: [u8; RECV_BUFFER_SIZE],
+}
+
+impl Default for CtapRecvBuffer {
+ fn default() -> Self {
+ CtapRecvBuffer {
+ buffer: [0; RECV_BUFFER_SIZE],
+ }
+ }
+}
+
+pub struct CtapSendBuffer {
+ pub buffer: [u8; SEND_BUFFER_SIZE],
+}
+
+impl CtapSendBuffer {
+ pub fn new(buf: [u8; SEND_BUFFER_SIZE]) -> Self {
+ CtapSendBuffer { buffer: buf }
+ }
+}
+
+impl Default for CtapSendBuffer {
+ fn default() -> Self {
+ CtapSendBuffer {
+ buffer: [0; SEND_BUFFER_SIZE],
+ }
+ }
+}
+
+pub struct CtapDriver<'a> {
+ lifetime: PhantomData<&'a ()>,
+}
+
+impl<'a> CtapDriver<'a> {
+ pub fn init_recv_buffer(&self, buffer: &'a mut CtapRecvBuffer) -> TockResult<SharedMemory> {
+ syscalls::allow(DRIVER_NUMBER, allow_nr::RECV, &mut buffer.buffer).map_err(Into::into)
+ }
+
+ pub fn init_send_buffer(&self, buffer: &'a mut CtapSendBuffer) -> TockResult<SharedMemory> {
+ syscalls::allow(DRIVER_NUMBER, allow_nr::SEND, &mut buffer.buffer).map_err(Into::into)
+ }
+
+ pub fn subscribe<CB: FnMut(usize, usize)>(
+ &self,
+ callback: &'a mut CB,
+ ) -> TockResult<CallbackSubscription> {
+ syscalls::subscribe::<CtapEventConsumer, _>(
+ DRIVER_NUMBER,
+ subscribe_nr::SUBSCRIBE_CALLBACK,
+ callback,
+ )
+ .map_err(Into::into)
+ }
+ pub fn send_data(&self) -> TockResult<()> {
+ syscalls::command(DRIVER_NUMBER, command_nr::SEND_DATA, 0, 0)?;
+ Ok(())
+ }
+
+ pub fn allow_receive(&self) -> TockResult<()> {
+ syscalls::command(DRIVER_NUMBER, command_nr::ALLOW_RECEIVE, 0, 0)?;
+ Ok(())
+ }
+}
diff --git a/src/drivers.rs b/src/drivers.rs
index bd7f45b..9b74a28 100644
--- a/src/drivers.rs
+++ b/src/drivers.rs
@@ -1,6 +1,7 @@
use crate::adc::AdcDriverFactory;
use crate::buttons::ButtonsDriverFactory;
use crate::console::ConsoleDriver;
+use crate::ctap::CtapDriverFactory;
use crate::gpio::GpioDriverFactory;
use crate::hmac::HmacDriverFactory;
use crate::leds::LedsDriverFactory;
@@ -21,6 +22,7 @@
#[non_exhaustive]
pub struct Drivers {
pub console: ConsoleDriver,
+ pub ctap: CtapDriverFactory,
pub leds: LedsDriverFactory,
pub timer: DriverContext,
pub gpio: GpioDriverFactory,
@@ -68,6 +70,7 @@
ble_scanning: BleScanningDriverFactory,
buttons: ButtonsDriverFactory,
console: ConsoleDriver,
+ ctap: CtapDriverFactory,
leds: LedsDriverFactory,
timer: DriverContext {
active_timer: Cell::new(None),
diff --git a/src/lib.rs b/src/lib.rs
index eb13b94..96d2720 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -5,6 +5,7 @@
pub mod ble_parser;
pub mod buttons;
pub mod console;
+pub mod ctap;
pub mod debug;
pub mod drivers;
pub mod electronics;