diff --git a/Cargo.toml b/Cargo.toml index 83bdd54..29207db 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -19,6 +19,10 @@ members = [ name = "vpicc" required-features = ["vpicc"] +[[example]] +name = "usbip" +required-features = ["apdu-dispatch"] + [dependencies] heapless = "0.7" heapless-bytes = "0.3" @@ -53,6 +57,9 @@ ron = "0.8" serde_cbor = "0.11" hex = { version = "0.4", features = ["serde"] } +# usbip +trussed-usbip = { git = "https://github.com/trussed-dev/pc-usbip-runner", default-features = false, features = ["ccid"], rev = "f3a680ca4c9a1411838ae0774f1713f79d4c2979" } + [features] default = [] std = [] diff --git a/Makefile b/Makefile index ec61357..3f5d117 100644 --- a/Makefile +++ b/Makefile @@ -73,3 +73,11 @@ clean: cargo clean cd fuzz && cargo clean && rm -rf corpus rm -f fuzz_coverage.html + +.PHONY: example-vpicc +example-vpicc: + cargo run --example vpicc --features vpicc,rsa4096-gen + +.PHONY: example-usbip +example-usbip: + cargo run --example usbip --features virt,rsa4096-gen,apdu-dispatch diff --git a/examples/usbip.rs b/examples/usbip.rs new file mode 100644 index 0000000..07c5a27 --- /dev/null +++ b/examples/usbip.rs @@ -0,0 +1,63 @@ +// Copyright (C) 2022 Nitrokey GmbH +// SPDX-License-Identifier: CC0-1.0 + +//! USB/IP runner for opcard. +//! Run with cargo run --example --features apdu-dispatch (and optionally rsa4096-gen) + +use trussed::virt::{self, Ram, UserInterface}; +use trussed::{ClientImplementation, Platform}; +use trussed_usbip::ClientBuilder; + +use opcard::virt::dispatch::{self, Dispatch}; + +type VirtClient = + ClientImplementation, dispatch::Dispatch>; + +const MANUFACTURER: &str = "Nitrokey"; +const PRODUCT: &str = "Nitrokey 3"; +const VID: u16 = 0x20a0; +const PID: u16 = 0x42b2; + +struct OpcardApp { + opcard: opcard::Card, +} + +impl trussed_usbip::Apps for OpcardApp { + type Data = (); + fn new>(builder: &B, _data: ()) -> Self { + OpcardApp { + opcard: opcard::Card::new( + builder.build("opcard", dispatch::BACKENDS), + opcard::Options::default(), + ), + } + } + + fn with_ccid_apps( + &mut self, + f: impl FnOnce(&mut [&mut dyn apdu_dispatch::App<7609, 7609>]) -> T, + ) -> T { + f(&mut [&mut self.opcard]) + } +} + +fn main() { + env_logger::init(); + + let options = trussed_usbip::Options { + manufacturer: Some(MANUFACTURER.to_owned()), + product: Some(PRODUCT.to_owned()), + serial_number: Some("TEST".into()), + vid: VID, + pid: PID, + }; + trussed_usbip::Builder::new(virt::Ram::default(), options) + .dispatch(Dispatch::new()) + .init_platform(move |platform| { + let ui: Box = + Box::new(UserInterface::new()); + platform.user_interface().set_inner(ui); + }) + .build::() + .exec(|_platform| {}); +} diff --git a/src/virt.rs b/src/virt.rs index 309a75f..1c8631f 100644 --- a/src/virt.rs +++ b/src/virt.rs @@ -3,7 +3,8 @@ //! Virtual trussed client (mostly for testing) -mod dispatch { +/// Implementation of ExtensionDispatch for a virtual implementation of opcard +pub mod dispatch { use trussed::{ api::{reply, request, Reply, Request}, @@ -27,15 +28,21 @@ mod dispatch { BackendId::Core, ]; + /// Id for the ExtensionDispatch implementation #[derive(Debug, Clone, Copy)] pub enum Backend { + /// trussed-auth Auth, + /// trussed-rsa-alloc #[cfg(feature = "rsa")] Rsa, } + /// Extensions used by opcard + /// Used for the ExtensionDispatch implementation #[derive(Debug, Clone, Copy)] pub enum Extension { + /// trussed-auth Auth, } @@ -71,12 +78,14 @@ mod dispatch { } impl Dispatch { + /// Create a new dispatch using the internal filesystem pub fn new() -> Self { Self { auth: AuthBackend::new(Location::Internal), } } + /// Create a new dispatch using the internal filesystem and a key derived from hardware parameters pub fn with_hw_key(hw_key: Bytes) -> Self { Self { auth: AuthBackend::with_hw_key(Location::Internal, hw_key),