From 7fdc6a2c1b5799221f5d89d5f935cfe7dad4ccd2 Mon Sep 17 00:00:00 2001 From: Brian Cully Date: Sun, 11 Aug 2019 19:01:34 -0400 Subject: Move usb controller stuff to usb directory. --- .cargo/config | 2 - .gitignore | 2 +- Cargo.lock | 449 --------------------------------------------------- Cargo.toml | 36 ----- Makefile | 55 ------- find-serial-port | 16 -- src/dotstar.rs | 42 ----- src/logger.rs | 139 ---------------- src/macros.rs | 15 -- src/main.rs | 196 ---------------------- src/rtc.rs | 75 --------- usb/.cargo/config | 2 + usb/Cargo.lock | 437 +++++++++++++++++++++++++++++++++++++++++++++++++ usb/Cargo.toml | 36 +++++ usb/Makefile | 55 +++++++ usb/find-serial-port | 16 ++ usb/src/dotstar.rs | 42 +++++ usb/src/logger.rs | 139 ++++++++++++++++ usb/src/macros.rs | 15 ++ usb/src/main.rs | 196 ++++++++++++++++++++++ usb/src/rtc.rs | 75 +++++++++ 21 files changed, 1014 insertions(+), 1026 deletions(-) delete mode 100644 .cargo/config delete mode 100644 Cargo.lock delete mode 100644 Cargo.toml delete mode 100644 Makefile delete mode 100755 find-serial-port delete mode 100644 src/dotstar.rs delete mode 100644 src/logger.rs delete mode 100644 src/macros.rs delete mode 100644 src/main.rs delete mode 100644 src/rtc.rs create mode 100644 usb/.cargo/config create mode 100644 usb/Cargo.lock create mode 100644 usb/Cargo.toml create mode 100644 usb/Makefile create mode 100755 usb/find-serial-port create mode 100644 usb/src/dotstar.rs create mode 100644 usb/src/logger.rs create mode 100644 usb/src/macros.rs create mode 100644 usb/src/main.rs create mode 100644 usb/src/rtc.rs diff --git a/.cargo/config b/.cargo/config deleted file mode 100644 index b10f29d..0000000 --- a/.cargo/config +++ /dev/null @@ -1,2 +0,0 @@ -[build] -target = "thumbv6m-none-eabi" diff --git a/.gitignore b/.gitignore index 27bca1e..976120a 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,4 @@ *.bin *.uf2 -/target +*/target **/*.rs.bk diff --git a/Cargo.lock b/Cargo.lock deleted file mode 100644 index c881d30..0000000 --- a/Cargo.lock +++ /dev/null @@ -1,449 +0,0 @@ -# This file is automatically @generated by Cargo. -# It is not intended for manual editing. -[[package]] -name = "aligned" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "aligned" -version = "0.3.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "as-slice 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "apa102-spi" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "as-slice" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)", - "stable_deref_trait 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "atsamd-hal" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "atsamd21e18a 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "bitfield 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "paste 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "atsamd-hal" -version = "0.6.0" -source = "git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a#53f8d846e40715c8592d171d9a57b66ee303207a" -dependencies = [ - "atsamd21e18a 0.5.0 (git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a)", - "bitfield 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "paste 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "atsamd-usb-host" -version = "0.1.0" -source = "git+https://github.com/bjc/atsamd-usb-host.git?rev=385efdf53fa3fe38591f22d01edf75d3087c2326#385efdf53fa3fe38591f22d01edf75d3087c2326" -dependencies = [ - "atsamd-hal 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", - "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", - "starb 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "usb-host 0.1.0 (git+https://github.com/bjc/usb-host.git?rev=b0be48424e81384de3280b5a5ac521d694b82e15)", -] - -[[package]] -name = "atsamd21e18a" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "atsamd21e18a" -version = "0.5.0" -source = "git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a#53f8d846e40715c8592d171d9a57b66ee303207a" -dependencies = [ - "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", - "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "bare-metal" -version = "0.2.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "bitfield" -version = "0.13.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "bleusb" -version = "0.1.0" -dependencies = [ - "apa102-spi 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "atsamd-usb-host 0.1.0 (git+https://github.com/bjc/atsamd-usb-host.git?rev=385efdf53fa3fe38591f22d01edf75d3087c2326)", - "bootkbd 0.1.0 (git+https://github.com/bjc/bootkbd.git?rev=49827fce5adbaf636b893919f31c0dbd97bb3eb4)", - "clint 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", - "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", - "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "smart-leds 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "starb 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "trinket_m0 0.4.0 (git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a)", - "usb-host 0.1.0 (git+https://github.com/bjc/usb-host.git?rev=b0be48424e81384de3280b5a5ac521d694b82e15)", -] - -[[package]] -name = "bootkbd" -version = "0.1.0" -source = "git+https://github.com/bjc/bootkbd.git?rev=49827fce5adbaf636b893919f31c0dbd97bb3eb4#49827fce5adbaf636b893919f31c0dbd97bb3eb4" -dependencies = [ - "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", - "usb-host 0.1.0 (git+https://github.com/bjc/usb-host.git?rev=b0be48424e81384de3280b5a5ac521d694b82e15)", -] - -[[package]] -name = "cfg-if" -version = "0.1.9" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "clint" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "cortex-m" -version = "0.5.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "aligned 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", - "volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "cortex-m" -version = "0.6.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "aligned 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", - "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", - "volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "cortex-m-rt" -version = "0.6.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cortex-m-rt-macros 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "cortex-m-rt-macros" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", - "rand 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)", - "syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "embedded-hal" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "generic-array" -version = "0.12.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "log" -version = "0.4.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "nb" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "paste" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "paste-impl 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "proc-macro-hack 0.5.8 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "paste-impl" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro-hack 0.5.8 (registry+https://github.com/rust-lang/crates.io-index)", - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", - "syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "proc-macro-hack" -version = "0.5.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", - "syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "proc-macro2" -version = "0.4.30" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "quote" -version = "0.6.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "r0" -version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "rand" -version = "0.5.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rand_core" -version = "0.3.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "rand_core 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rand_core" -version = "0.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "rgb" -version = "0.8.13" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "rustc_version" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "semver" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "semver-parser" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "smart-leds" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "smart-leds-trait" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "rgb 0.8.13 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "stable_deref_trait" -version = "1.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "starb" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "syn" -version = "0.15.42" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "trinket_m0" -version = "0.4.0" -source = "git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a#53f8d846e40715c8592d171d9a57b66ee303207a" -dependencies = [ - "atsamd-hal 0.6.0 (git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a)", - "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", - "cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", - "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "typenum" -version = "1.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "unicode-xid" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "usb-host" -version = "0.1.0" -source = "git+https://github.com/bjc/usb-host.git?rev=b0be48424e81384de3280b5a5ac521d694b82e15#b0be48424e81384de3280b5a5ac521d694b82e15" - -[[package]] -name = "vcell" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "void" -version = "1.0.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "volatile-register" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[metadata] -"checksum aligned 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d39da9b88ae1a81c03c9c082b8db83f1d0e93914126041962af61034ab44c4a5" -"checksum aligned 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d3a316c7ea8e1e9ece54862c992def5a7ac14de9f5832b69d71760680efeeefa" -"checksum apa102-spi 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "244c305e53cabeadfce23409fe24bfcedaa20166aa3f16f6c4ab256302158fd5" -"checksum as-slice 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "293dac66b274fab06f95e7efb05ec439a6b70136081ea522d270bc351ae5bb27" -"checksum atsamd-hal 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9affce3b8d443195536c0b398a55a152cc962366c24824ea833bb22afd49b3d6" -"checksum atsamd-hal 0.6.0 (git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a)" = "" -"checksum atsamd-usb-host 0.1.0 (git+https://github.com/bjc/atsamd-usb-host.git?rev=385efdf53fa3fe38591f22d01edf75d3087c2326)" = "" -"checksum atsamd21e18a 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "139787a30d118dd09a2e9570f5404cf582b70afe9b53dd1194239f9be382b897" -"checksum atsamd21e18a 0.5.0 (git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a)" = "" -"checksum bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)" = "a3caf393d93b2d453e80638d0674597020cef3382ada454faacd43d1a55a735a" -"checksum bitfield 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)" = "46afbd2983a5d5a7bd740ccb198caf5b82f45c40c09c0eed36052d91cb92e719" -"checksum bootkbd 0.1.0 (git+https://github.com/bjc/bootkbd.git?rev=49827fce5adbaf636b893919f31c0dbd97bb3eb4)" = "" -"checksum cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "b486ce3ccf7ffd79fdeb678eac06a9e6c09fc88d33836340becb8fffe87c5e33" -"checksum clint 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "200296af81a4cbe7da52afd9e5c35b7782eca865678caf2280251b777c9c37aa" -"checksum cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)" = "3c0b159a1e8306949579de3698c841dba58058197b65c60807194e4fa1e7a554" -"checksum cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "f3c18719fdc57db65668bfc977db9a0fa1a41d718c5d9cd4f652c9d4b0e0956a" -"checksum cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)" = "17805910e3ecf029bdbfcc42b7384d9e3d9e5626153fa810002c1ef9839338ac" -"checksum cortex-m-rt-macros 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "d7ae692573e0acccb1579fef1abf5a5bf1d2f3f0149a22b16870ec9309aee25f" -"checksum embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "ee4908a155094da7723c2d60d617b820061e3b4efcc3d9e293d206a5a76c170b" -"checksum generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)" = "c68f0274ae0e023facc3c97b2e00f076be70e254bc851d972503b328db79b2ec" -"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7" -"checksum nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "b1411551beb3c11dedfb0a90a0fa256b47d28b9ec2cdff34c25a2fa59e45dbdc" -"checksum paste 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "1f4a4a1c555c6505821f9d58b8779d0f630a6b7e4e1be24ba718610acf01fa79" -"checksum paste-impl 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "26e796e623b8b257215f27e6c80a5478856cae305f5b59810ff9acdaa34570e6" -"checksum proc-macro-hack 0.5.8 (registry+https://github.com/rust-lang/crates.io-index)" = "982a35d1194084ba319d65c4a68d24ca28f5fdb5b8bc20899e4eef8641ea5178" -"checksum proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)" = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759" -"checksum quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)" = "6ce23b6b870e8f94f81fb0a363d65d86675884b34a09043c81e5562f11c1f8e1" -"checksum r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e2a38df5b15c8d5c7e8654189744d8e396bddc18ad48041a500ce52d6948941f" -"checksum rand 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c618c47cd3ebd209790115ab837de41425723956ad3ce2e6a7f09890947cacb9" -"checksum rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6fdeb83b075e8266dcc8762c22776f6877a63111121f5f8c7411e5be7eed4b" -"checksum rand_core 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9c33a3c44ca05fa6f1807d8e6743f3824e8509beca625669633be0acbdf509dc" -"checksum rgb 0.8.13 (registry+https://github.com/rust-lang/crates.io-index)" = "4f089652ca87f5a82a62935ec6172a534066c7b97be003cc8f702ee9a7a59c92" -"checksum rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a" -"checksum semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403" -"checksum semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" -"checksum smart-leds 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ab0a30e934e60850bfc020d4c2727cc8a3635371f6af2cb3f55f36f0134ed080" -"checksum smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fef18e60d41a6fde19e640cd7590c03fb27aa23146bf60e4da85028d7410cee7" -"checksum stable_deref_trait 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "dba1a27d3efae4351c8051072d619e3ade2820635c3958d826bfea39d59b54c8" -"checksum starb 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "36de9f301031f2a692afe144c8a757950d2b60b7fbf447055b8e19a9c232fb2c" -"checksum syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)" = "eadc09306ca51a40555dd6fc2b415538e9e18bc9f870e47b1a524a79fe2dcf5e" -"checksum trinket_m0 0.4.0 (git+https://github.com/atsamd-rs/atsamd.git?rev=53f8d846e40715c8592d171d9a57b66ee303207a)" = "" -"checksum typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "612d636f949607bdf9b123b4a6f6d966dedf3ff669f7f045890d3a4a73948169" -"checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" -"checksum usb-host 0.1.0 (git+https://github.com/bjc/usb-host.git?rev=b0be48424e81384de3280b5a5ac521d694b82e15)" = "" -"checksum vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "45c297f0afb6928cd08ab1ff9d95e99392595ea25ae1b5ecf822ff8764e57a0d" -"checksum void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "6a02e4885ed3bc0f2de90ea6dd45ebcbb66dacffe03547fadbb0eeae2770887d" -"checksum volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "0d67cb4616d99b940db1d6bd28844ff97108b498a6ca850e5b6191a532063286" diff --git a/Cargo.toml b/Cargo.toml deleted file mode 100644 index d5535a9..0000000 --- a/Cargo.toml +++ /dev/null @@ -1,36 +0,0 @@ -[package] -name = "bleusb" -description = "Send boot keyboard reports over I²C." -version = "0.1.0" -authors = ["Brian Cully "] -edition = "2018" -license = "GPL-3.0-or-later" -repository = "https://github.com/bjc/bleusb.git" - -[dependencies] -embedded-hal = "0.2" -trinket_m0 = "0.4" -log = "0.4" -starb = "0.1" -clint = "0.2" -nb = "0.1" -cortex-m = "0.6" -cortex-m-rt = "0.6" -smart-leds-trait = "0.2" -smart-leds = "0.2" -apa102-spi = "0.2" -usb-host = "0.1" -bootkbd = "0.1" -atsamd-usb-host = { git = "https://github.com/bjc/atsamd-usb-host.git", rev = "385efdf53fa3fe38591f22d01edf75d3087c2326" } -# atsamd-usb-host = { path = "../usbh/atsamd-usb-host" } - -[patch.crates-io] -bootkbd = { git = "https://github.com/bjc/bootkbd.git", rev = "49827fce5adbaf636b893919f31c0dbd97bb3eb4" } -usb-host = { git = "https://github.com/bjc/usb-host.git", rev = "b0be48424e81384de3280b5a5ac521d694b82e15" } -trinket_m0 = { git = "https://github.com/atsamd-rs/atsamd.git", rev = "53f8d846e40715c8592d171d9a57b66ee303207a" } -# trinket_m0 = { path = "../usbh/atsamd/boards/trinket_m0" } -# bootkbd = { path = "../usbh/bootkbd" } -# usb-host = { path = "../usbh/usb-host" } - -[features] -default = ["atsamd-usb-host/samd21e18a"] diff --git a/Makefile b/Makefile deleted file mode 100644 index 6d420d1..0000000 --- a/Makefile +++ /dev/null @@ -1,55 +0,0 @@ -# How to compile the examples. -APP = bleusb -RELEASE = debug -TARGET = thumbv6m-none-eabi - -# VID and PID of device to flash firmware to. -USBVID = 239a -USBPID = '001e|801e' - -BOSSAC = bossac -OFFSET = 0x2000 - -OBJCOPY = arm-none-eabi-objcopy - -TARGETDIR = target/$(TARGET) -OUTDIR = $(TARGETDIR)/$(RELEASE) - -CARGOFLAGS = --target thumbv6m-none-eabi - -.PHONY: all clean cargo-build $(OUTDIR)/$(APP) - -all: $(OUTDIR)/$(APP) - -clean: - rm -f $(APP).uf2 - rm -f $(APP).bin - cargo clean - -test: - cargo test - -cargo-build: - cargo rustc $(CARGOFLAGS) -- -C link-arg=-Tlink.x - -$(OUTDIR)/$(APP): cargo-build - -flash: $(APP).bin - feather-cmd r - sleep 2 - feather-cmd dfu - sleep 2 - $(BOSSAC) -R -e -w -v -o$(OFFSET) -p`./find-serial-port $(USBVID) $(USBPID)` $< - -qemu: $(OUTDIR)/$(APP) - qemu-system-arm -d in_asm,int,exec,cpu,guest_errors,unimp -pidfile qemu.pid -cpu cortex-m0 -machine lm3s6965evb -nographic -semihosting-config enable=on,target=native -s -S -kernel $< - -gdb: $(OUTDIR)/$(APP) - gdb-multiarch -ex "target remote localhost:1234" -ex "break main" -ex "continue" $< - -%.bin: $(OUTDIR)/% - $(OBJCOPY) -O binary $< $@ - -# Requires https://github.com/sajattack/uf2conv-rs.git -%.uf2: %.bin - uf2conv-rs $< --base $(OFFSET) --output $@ diff --git a/find-serial-port b/find-serial-port deleted file mode 100755 index 62e2c0c..0000000 --- a/find-serial-port +++ /dev/null @@ -1,16 +0,0 @@ -#!/bin/sh - -if [ $# -ne 2 ]; then - echo "Usage: $0 vid pid" >&2 - exit 1 -fi - -prefix=/dev/serial/by-id - -for dev in `ls $prefix`; do - if [ `udevadm info -q property --name $prefix/$dev | egrep -i "ID_VENDOR_ID=($1)|ID_MODEL_ID=($2)" | wc -l` -eq 2 ]; then - echo `readlink -f $prefix/$dev` - exit 0 - fi -done -exit 2 diff --git a/src/dotstar.rs b/src/dotstar.rs deleted file mode 100644 index 8e930d0..0000000 --- a/src/dotstar.rs +++ /dev/null @@ -1,42 +0,0 @@ -use trinket_m0::{ - clock::GenericClockController, - gpio::{self, Floating, Input}, - prelude::*, - sercom::{self, PadPin, SPIMaster1}, - PM, SERCOM1, -}; - -use apa102_spi::Apa102; - -pub fn new( - sercom: SERCOM1, - miso: gpio::Pa31>, - mosi: gpio::Pa0>, - sck: gpio::Pa1>, - port: &mut gpio::Port, - pm: &mut PM, - clocks: &mut GenericClockController, -) -> Apa102< - SPIMaster1< - sercom::Sercom1Pad3>, - sercom::Sercom1Pad0>, - sercom::Sercom1Pad1>, - >, -> { - let gclk = clocks.gclk0(); - let miso = miso.into_pad(port); - let mosi = mosi.into_pad(port); - let sck = sck.into_pad(port); - let spi = SPIMaster1::new( - &clocks - .sercom1_core(&gclk) - .expect("setting up sercom1 clock"), - 3.mhz(), - apa102_spi::MODE, - sercom, - pm, - (miso, mosi, sck), - ); - - Apa102::new(spi) -} diff --git a/src/logger.rs b/src/logger.rs deleted file mode 100644 index be9d391..0000000 --- a/src/logger.rs +++ /dev/null @@ -1,139 +0,0 @@ -use crate::rtc; -use starb::{Reader, RingBuffer, Writer}; - -use core::cell::UnsafeCell; -use core::fmt::{self, Write}; -use embedded_hal::{digital::v2::OutputPin, serial}; -use log::{Metadata, Record}; -use trinket_m0::{ - gpio::{Pa6, Pa7, PfD}, - sercom::{Sercom0Pad2, Sercom0Pad3, UART0}, -}; - -static mut UART0: usize = 0; - -struct JoinedRingBuffer<'a> { - lbr: Reader<'a, u8>, - lbw: Writer<'a, u8>, -} - -impl<'a> JoinedRingBuffer<'a> { - const fn new(rb: &'a RingBuffer) -> Self { - let (lbr, lbw) = rb.split(); - Self { lbr: lbr, lbw: lbw } - } -} - -impl fmt::Write for JoinedRingBuffer<'_> { - fn write_str(&mut self, s: &str) -> Result<(), fmt::Error> { - for b in s.bytes() { - if let Err(_) = self.lbw.unshift(b) { - // Ignore buffer full errors for logging. - return Ok(()); - } - } - Ok(()) - } -} - -static mut LB: RingBuffer = RingBuffer::::new(0); -static mut JRB: JoinedRingBuffer = unsafe { JoinedRingBuffer::new(&LB) }; - -// The UART isn't necessarily Sync, so wrap it in something that -// is. As long as flush() is only called from one thread, we're fine, -// but this is a guarantee that the logger module doesn't make. -pub struct WriteWrapper { - w: W, -} -impl WriteWrapper -where - W: serial::Write, -{ - pub fn new(writer: W) -> Self { - Self { w: writer } - } -} -unsafe impl Sync for WriteWrapper {} - -pub struct SerialLogger { - writer: UnsafeCell>, - led: UnsafeCell, -} - -impl SerialLogger -where - W: serial::Write, - L: OutputPin + Send + Sync, -{ - pub fn new(writer: WriteWrapper, led: L) -> Self { - // Stash this for unsafe usage in case there's an issue with - // the rest of the logging. - unsafe { UART0 = core::mem::transmute(&writer.w) }; - Self { - writer: UnsafeCell::new(writer), - led: UnsafeCell::new(led), - } - } -} -unsafe impl Send for SerialLogger {} -unsafe impl Sync for SerialLogger {} - -impl log::Log for SerialLogger -where - W: serial::Write, - L: OutputPin + Send + Sync, -{ - fn enabled(&self, metadata: &Metadata) -> bool { - metadata.level() <= log::max_level() - } - - fn log(&self, record: &Record) { - if !self.enabled(record.metadata()) { - return; - } - - let jrb = unsafe { &mut JRB }; - write!( - jrb, - "[{}] {} {} -- {}\r\n", - rtc::millis(), - record.level(), - record.target(), - record.args() - ) - .ok(); - } - - fn flush(&self) { - // Unsafe due to mutable static. We can only deal with the - // tail position of the buffer here to keep things safe. - let jrb = unsafe { &mut JRB }; - if jrb.lbr.is_empty() { - return; - } - - let led = unsafe { &mut (*self.led.get()) }; - let writer = unsafe { &mut (*self.writer.get()) }; - - led.set_high().ok(); - while let Some(b) = jrb.lbr.shift() { - nb::block!(writer.w.write(b)).ok(); - } - led.set_low().ok(); - } -} - -// Write to the UART right now, instead of putting it on a ring -// buffer. This function is a huge hack, and only useful for debugging -// either before the main loop starts or if the ring buffer is broken. -pub unsafe fn write_fmt_now(args: fmt::Arguments, nl: bool) { - if UART0 == 0 { - return; - } - let uart: &mut UART0>, Sercom0Pad2>, (), ()> = - core::mem::transmute(UART0); - fmt::write(uart, args).expect("writing fmt now to uart"); - if nl { - uart.write_str("\r\n").expect("writing nl now to uart"); - } -} diff --git a/src/macros.rs b/src/macros.rs deleted file mode 100644 index 46d2d07..0000000 --- a/src/macros.rs +++ /dev/null @@ -1,15 +0,0 @@ -#[macro_export] -macro_rules! logln_now { - ($($arg:tt)*) => { - unsafe {crate::logger::write_fmt_now(format_args!($($arg)*), true);} - }; - (_) => {}; -} - -#[macro_export] -macro_rules! log_now { - ($($arg:tt)*) => { - unsafe {crate::logger::write_fmt_now(format_args!($($arg)*), false);} - }; - (_) => {}; -} diff --git a/src/main.rs b/src/main.rs deleted file mode 100644 index a7cfd8a..0000000 --- a/src/main.rs +++ /dev/null @@ -1,196 +0,0 @@ -//! Take USB keyboard reports and echo them over I²C. - -#![no_std] -#![no_main] - -mod dotstar; -mod logger; -mod macros; -mod rtc; - -use atsamd_usb_host::SAMDHost; -use bootkbd::BootKeyboard; -use clint::HandlerArray; -use core::mem; -use core::panic::PanicInfo; -use cortex_m::asm::wfi; -use cortex_m_rt::{entry, exception, ExceptionFrame}; -use embedded_hal::{blocking::i2c::Write, digital::v2::OutputPin}; -use log::{info, LevelFilter}; -use smart_leds::colors; -use smart_leds_trait::SmartLedsWrite; -use trinket_m0::{ - self as hal, - clock::GenericClockController, - gpio::{OpenDrain, Output, Pa10, Pa6, Pa7, PfD}, - sercom, - target_device::{interrupt, Interrupt}, - time::*, - CorePeripherals, Peripherals, -}; -use usb_host::Driver; - -// A very unsafe copy of an LED to turn on when things go really, really wrong. -static mut LED: usize = 0; - -// I²C address to send keyboard reports to. -const NRF_WIREADDR: u8 = 4; - -// Interrupt handler table. -static HANDLERS: HandlerArray = HandlerArray::new(); - -#[entry] -fn main() -> ! { - let mut cp = CorePeripherals::take().expect("taking core peripherals"); - let mut dp = Peripherals::take().expect("taking device peripherals"); - - let mut clocks = GenericClockController::with_internal_32kosc( - dp.GCLK, - &mut dp.PM, - &mut dp.SYSCTRL, - &mut dp.NVMCTRL, - ); - - let mut pins = hal::Pins::new(dp.PORT); - - let uart = hal::uart( - &mut clocks, - 115_200.hz(), - dp.SERCOM0, - &mut cp.NVIC, - &mut dp.PM, - pins.d3, - pins.d4, - &mut pins.port, - ); - - let mut i2c_master = hal::i2c_master( - &mut clocks, - 400_000.hz(), - dp.SERCOM2, - &mut dp.PM, - pins.d0, - pins.d2, - &mut pins.port, - ); - - let mut red_led = pins.d13.into_open_drain_output(&mut pins.port); - red_led.set_low().expect("turning off red LED"); - unsafe { LED = mem::transmute(&red_led) } - - let mut dotstar = dotstar::new( - dp.SERCOM1, - pins.swdio, - pins.dotstar_di, - pins.dotstar_ci, - &mut pins.port, - &mut dp.PM, - &mut clocks, - ); - let black = [colors::BLACK]; - dotstar - .write(black.iter().cloned()) - .expect("turning off dotstar"); - - // We do the transmute because, while all the underlying data is - // static, we're unable to get a referecence to the UART or LED - // until run-time. Another option would be to use Option in the - // SerialLogger definition, but that requires a check every time - // they might be used. - let uart_wrapped = logger::WriteWrapper::new(uart); - let logger = logger::SerialLogger::new(uart_wrapped, red_led); - - // Wow, would I love to not be annotating this type. - let logger_ref: &'static logger::SerialLogger< - sercom::UART0>, sercom::Sercom0Pad2>, (), ()>, - Pa10>, - > = unsafe { mem::transmute(&logger) }; - unsafe { log::set_logger_racy(logger_ref).expect("couldn't set logger") }; - log::set_max_level(LevelFilter::Info); - - let mut rtc_handler = rtc::setup(dp.RTC, &mut clocks); - - let (mut usb_host, mut usb_handler) = SAMDHost::new( - dp.USB, - pins.usb_sof, - pins.usb_dm, - pins.usb_dp, - Some(pins.usb_host_enable), - &mut pins.port, - &mut clocks, - &mut dp.PM, - &rtc::millis, - ); - - let mut bootkbd = BootKeyboard::new(|addr, buf| { - info!("{}: {:?}", addr, buf); - let hdr: [u8; 2] = [I2CMessageType::Keyboard as u8, buf.len() as u8]; - i2c_master.write(NRF_WIREADDR, &hdr).ok(); - i2c_master.write(NRF_WIREADDR, &buf).ok(); - }); - let mut drivers: [&mut dyn Driver; 1] = [&mut bootkbd]; - - HANDLERS.with_overrides(|hs| { - hs.register(0, &mut rtc_handler); - unsafe { cp.NVIC.set_priority(Interrupt::USB, 0) }; - cp.NVIC.enable(Interrupt::RTC); - - hs.register(1, &mut usb_handler); - unsafe { cp.NVIC.set_priority(Interrupt::USB, 1) }; - cp.NVIC.enable(Interrupt::USB); - - info!("Bootstrap complete."); - - loop { - usb_host.task(&mut drivers[..]); - wfi() - } - }); - unreachable!(); -} - -#[allow(unused)] -#[repr(u8)] -enum I2CMessageType { - Debug = 0x00, - Keyboard = 0x01, - Invalid = 0xff, -} - -#[panic_handler] -fn panic_handler(pi: &PanicInfo) -> ! { - let red_led: &mut Pa10> = unsafe { mem::transmute(LED) }; - red_led.set_high().ok(); - - logln_now!("~~~ PANIC ~~~"); - logln_now!("{}", pi); - logln_now!("flushing log"); - loop { - log::logger().flush(); - wfi() - } -} - -#[exception] -fn HardFault(ef: &ExceptionFrame) -> ! { - let red_led: &mut Pa10> = unsafe { mem::transmute(LED) }; - red_led.set_high().ok(); - - log::logger().flush(); - logln_now!("!!! Hard Fault - ef: {:?} !!!", ef); - logln_now!("flushing log"); - loop { - log::logger().flush(); - wfi() - } -} - -#[interrupt] -fn RTC() { - HANDLERS.call(0); -} - -#[interrupt] -fn USB() { - HANDLERS.call(1); -} diff --git a/src/rtc.rs b/src/rtc.rs deleted file mode 100644 index fa7b347..0000000 --- a/src/rtc.rs +++ /dev/null @@ -1,75 +0,0 @@ -use core::sync::atomic::{AtomicUsize, Ordering}; -use log; -use trinket_m0::{clock::GenericClockController, RTC}; - -struct Clock(AtomicUsize); -impl Clock { - const fn new() -> Self { - Self(AtomicUsize::new(0)) - } - - fn set(&self, millis: usize) { - self.0.store(millis, Ordering::SeqCst) - } - - // Slightly less than 1ms, due to using a 32,768Hz clock, we can't - // hit exactly 1ms, so we shoot for a bit under. - fn millis(&self) -> usize { - self.0.load(Ordering::SeqCst) - } -} - -static CLOCK: Clock = Clock::new(); - -// Set to run every ~500µs. This has been loosely calibrated from a -// nrf52 clock running Arduino and a Linux host. -static COUNTER: u32 = 13; - -pub fn setup(mut rtc: RTC, clocks: &mut GenericClockController) -> impl FnMut() { - let rtc_clock = &clocks.gclk1(); - clocks.rtc(&rtc_clock); - - rtc.mode0().ctrl.write(|w| w.swrst().set_bit()); - while rtc.mode0().status.read().syncbusy().bit_is_set() {} - - rtc.mode0().ctrl.write(|w| { - w.mode().count32(); - - // Neither the prescaler nor matchlr values seem to work. Not - // sure why. - //w.prescaler().div1024(); - w.matchclr().set_bit() // Reset on match for periodic - }); - - rtc.mode0().comp[0].write(|w| unsafe { w.bits(COUNTER) }); - rtc.mode0().intflag.write(|w| w.cmp0().set_bit()); - rtc.mode0().intenset.write(|w| w.cmp0().set_bit()); - - // Enable the RTC and wait for sync. - rtc.mode0().ctrl.write(|w| w.enable().set_bit()); - while rtc.mode0().status.read().syncbusy().bit_is_set() {} - - move || handler(&mut rtc) -} - -pub fn millis() -> usize { - CLOCK.millis() -} - -fn handler(rtc: &mut RTC) { - // FIXME: matchclr doesn't seem to work to reset the counter? - rtc.mode0().count.write(|w| unsafe { w.bits(0) }); - rtc.mode0().intflag.write(|w| w.cmp0().set_bit()); - - static mut TICKS: usize = 0; - static mut ADD: bool = false; - unsafe { - if ADD { - TICKS += 1; - CLOCK.set(TICKS); - } - ADD = !ADD; - - log::logger().flush(); - } -} diff --git a/usb/.cargo/config b/usb/.cargo/config new file mode 100644 index 0000000..b10f29d --- /dev/null +++ b/usb/.cargo/config @@ -0,0 +1,2 @@ +[build] +target = "thumbv6m-none-eabi" diff --git a/usb/Cargo.lock b/usb/Cargo.lock new file mode 100644 index 0000000..99b87a9 --- /dev/null +++ b/usb/Cargo.lock @@ -0,0 +1,437 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +[[package]] +name = "aligned" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "aligned" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "as-slice 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "apa102-spi" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", + "smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "as-slice" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)", + "stable_deref_trait 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "atsamd-hal" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "atsamd21e18a 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", + "bitfield 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", + "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", + "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", + "paste 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "atsamd-hal" +version = "0.6.0" +dependencies = [ + "atsamd21e18a 0.5.0", + "bitfield 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", + "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", + "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", + "paste 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "atsamd-usb-host" +version = "0.1.0" +dependencies = [ + "atsamd-hal 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", + "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", + "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", + "starb 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "usb-host 0.1.1", +] + +[[package]] +name = "atsamd21e18a" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", + "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "atsamd21e18a" +version = "0.5.0" +dependencies = [ + "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", + "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "bare-metal" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "bitfield" +version = "0.13.2" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "bleusb" +version = "0.1.0" +dependencies = [ + "apa102-spi 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", + "atsamd-usb-host 0.1.0", + "bootkbd 0.2.0", + "clint 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", + "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", + "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", + "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", + "smart-leds 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", + "smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", + "starb 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "trinket_m0 0.4.0", + "usb-host 0.1.1", +] + +[[package]] +name = "bootkbd" +version = "0.2.0" +dependencies = [ + "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", + "usb-host 0.1.1", +] + +[[package]] +name = "cfg-if" +version = "0.1.9" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "clint" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "cortex-m" +version = "0.5.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "aligned 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", + "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)", + "volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "cortex-m" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "aligned 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", + "bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)", + "volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "cortex-m-rt" +version = "0.6.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "cortex-m-rt-macros 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "cortex-m-rt-macros" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", + "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", + "rand 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)", + "syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "embedded-hal" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", + "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "generic-array" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "log" +version = "0.4.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "nb" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "paste" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "paste-impl 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "proc-macro-hack 0.5.8 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "paste-impl" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "proc-macro-hack 0.5.8 (registry+https://github.com/rust-lang/crates.io-index)", + "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", + "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", + "syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "proc-macro-hack" +version = "0.5.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", + "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", + "syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "proc-macro2" +version = "0.4.30" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "quote" +version = "0.6.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "r0" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "rand" +version = "0.5.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "rand_core" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "rand_core 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "rand_core" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "rgb" +version = "0.8.13" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "rustc_version" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "semver" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "semver-parser" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "smart-leds" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "smart-leds-trait" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "rgb 0.8.13 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "stable_deref_trait" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "starb" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "syn" +version = "0.15.42" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)", + "quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)", + "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "trinket_m0" +version = "0.4.0" +dependencies = [ + "atsamd-hal 0.6.0", + "cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)", + "cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)", + "embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", + "nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "typenum" +version = "1.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "unicode-xid" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "usb-host" +version = "0.1.1" + +[[package]] +name = "vcell" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "void" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "volatile-register" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[metadata] +"checksum aligned 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d39da9b88ae1a81c03c9c082b8db83f1d0e93914126041962af61034ab44c4a5" +"checksum aligned 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d3a316c7ea8e1e9ece54862c992def5a7ac14de9f5832b69d71760680efeeefa" +"checksum apa102-spi 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "244c305e53cabeadfce23409fe24bfcedaa20166aa3f16f6c4ab256302158fd5" +"checksum as-slice 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "293dac66b274fab06f95e7efb05ec439a6b70136081ea522d270bc351ae5bb27" +"checksum atsamd-hal 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9affce3b8d443195536c0b398a55a152cc962366c24824ea833bb22afd49b3d6" +"checksum atsamd21e18a 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "139787a30d118dd09a2e9570f5404cf582b70afe9b53dd1194239f9be382b897" +"checksum bare-metal 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)" = "a3caf393d93b2d453e80638d0674597020cef3382ada454faacd43d1a55a735a" +"checksum bitfield 0.13.2 (registry+https://github.com/rust-lang/crates.io-index)" = "46afbd2983a5d5a7bd740ccb198caf5b82f45c40c09c0eed36052d91cb92e719" +"checksum cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "b486ce3ccf7ffd79fdeb678eac06a9e6c09fc88d33836340becb8fffe87c5e33" +"checksum clint 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "200296af81a4cbe7da52afd9e5c35b7782eca865678caf2280251b777c9c37aa" +"checksum cortex-m 0.5.10 (registry+https://github.com/rust-lang/crates.io-index)" = "3c0b159a1e8306949579de3698c841dba58058197b65c60807194e4fa1e7a554" +"checksum cortex-m 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "f3c18719fdc57db65668bfc977db9a0fa1a41d718c5d9cd4f652c9d4b0e0956a" +"checksum cortex-m-rt 0.6.10 (registry+https://github.com/rust-lang/crates.io-index)" = "17805910e3ecf029bdbfcc42b7384d9e3d9e5626153fa810002c1ef9839338ac" +"checksum cortex-m-rt-macros 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "d7ae692573e0acccb1579fef1abf5a5bf1d2f3f0149a22b16870ec9309aee25f" +"checksum embedded-hal 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "ee4908a155094da7723c2d60d617b820061e3b4efcc3d9e293d206a5a76c170b" +"checksum generic-array 0.12.3 (registry+https://github.com/rust-lang/crates.io-index)" = "c68f0274ae0e023facc3c97b2e00f076be70e254bc851d972503b328db79b2ec" +"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7" +"checksum nb 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "b1411551beb3c11dedfb0a90a0fa256b47d28b9ec2cdff34c25a2fa59e45dbdc" +"checksum paste 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "1f4a4a1c555c6505821f9d58b8779d0f630a6b7e4e1be24ba718610acf01fa79" +"checksum paste-impl 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "26e796e623b8b257215f27e6c80a5478856cae305f5b59810ff9acdaa34570e6" +"checksum proc-macro-hack 0.5.8 (registry+https://github.com/rust-lang/crates.io-index)" = "982a35d1194084ba319d65c4a68d24ca28f5fdb5b8bc20899e4eef8641ea5178" +"checksum proc-macro2 0.4.30 (registry+https://github.com/rust-lang/crates.io-index)" = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759" +"checksum quote 0.6.13 (registry+https://github.com/rust-lang/crates.io-index)" = "6ce23b6b870e8f94f81fb0a363d65d86675884b34a09043c81e5562f11c1f8e1" +"checksum r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e2a38df5b15c8d5c7e8654189744d8e396bddc18ad48041a500ce52d6948941f" +"checksum rand 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c618c47cd3ebd209790115ab837de41425723956ad3ce2e6a7f09890947cacb9" +"checksum rand_core 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6fdeb83b075e8266dcc8762c22776f6877a63111121f5f8c7411e5be7eed4b" +"checksum rand_core 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9c33a3c44ca05fa6f1807d8e6743f3824e8509beca625669633be0acbdf509dc" +"checksum rgb 0.8.13 (registry+https://github.com/rust-lang/crates.io-index)" = "4f089652ca87f5a82a62935ec6172a534066c7b97be003cc8f702ee9a7a59c92" +"checksum rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a" +"checksum semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403" +"checksum semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" +"checksum smart-leds 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ab0a30e934e60850bfc020d4c2727cc8a3635371f6af2cb3f55f36f0134ed080" +"checksum smart-leds-trait 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fef18e60d41a6fde19e640cd7590c03fb27aa23146bf60e4da85028d7410cee7" +"checksum stable_deref_trait 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "dba1a27d3efae4351c8051072d619e3ade2820635c3958d826bfea39d59b54c8" +"checksum starb 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "36de9f301031f2a692afe144c8a757950d2b60b7fbf447055b8e19a9c232fb2c" +"checksum syn 0.15.42 (registry+https://github.com/rust-lang/crates.io-index)" = "eadc09306ca51a40555dd6fc2b415538e9e18bc9f870e47b1a524a79fe2dcf5e" +"checksum typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "612d636f949607bdf9b123b4a6f6d966dedf3ff669f7f045890d3a4a73948169" +"checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" +"checksum vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "45c297f0afb6928cd08ab1ff9d95e99392595ea25ae1b5ecf822ff8764e57a0d" +"checksum void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "6a02e4885ed3bc0f2de90ea6dd45ebcbb66dacffe03547fadbb0eeae2770887d" +"checksum volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "0d67cb4616d99b940db1d6bd28844ff97108b498a6ca850e5b6191a532063286" diff --git a/usb/Cargo.toml b/usb/Cargo.toml new file mode 100644 index 0000000..a1978dd --- /dev/null +++ b/usb/Cargo.toml @@ -0,0 +1,36 @@ +[package] +name = "bleusb" +description = "Send boot keyboard reports over I²C." +version = "0.1.0" +authors = ["Brian Cully "] +edition = "2018" +license = "GPL-3.0-or-later" +repository = "https://github.com/bjc/bleusb.git" + +[dependencies] +embedded-hal = "0.2" +trinket_m0 = "0.4" +log = "0.4" +starb = "0.1" +clint = "0.2" +nb = "0.1" +cortex-m = "0.6" +cortex-m-rt = "0.6" +smart-leds-trait = "0.2" +smart-leds = "0.2" +apa102-spi = "0.2" +usb-host = "0.1" +bootkbd = "0.2" +#atsamd-usb-host = { git = "https://github.com/bjc/atsamd-usb-host.git", rev = "385efdf53fa3fe38591f22d01edf75d3087c2326" } +atsamd-usb-host = { path = "../../usbh/atsamd-usb-host" } + +[patch.crates-io] +#bootkbd = { git = "https://github.com/bjc/bootkbd.git", rev = "49827fce5adbaf636b893919f31c0dbd97bb3eb4" } +#usb-host = { git = "https://github.com/bjc/usb-host.git", rev = "b0be48424e81384de3280b5a5ac521d694b82e15" } +#trinket_m0 = { git = "https://github.com/atsamd-rs/atsamd.git", rev = "53f8d846e40715c8592d171d9a57b66ee303207a" } +trinket_m0 = { path = "../../usbh/atsamd/boards/trinket_m0" } +bootkbd = { path = "../../usbh/bootkbd" } +usb-host = { path = "../../usbh/usb-host" } + +[features] +default = ["atsamd-usb-host/samd21e18a"] diff --git a/usb/Makefile b/usb/Makefile new file mode 100644 index 0000000..6d420d1 --- /dev/null +++ b/usb/Makefile @@ -0,0 +1,55 @@ +# How to compile the examples. +APP = bleusb +RELEASE = debug +TARGET = thumbv6m-none-eabi + +# VID and PID of device to flash firmware to. +USBVID = 239a +USBPID = '001e|801e' + +BOSSAC = bossac +OFFSET = 0x2000 + +OBJCOPY = arm-none-eabi-objcopy + +TARGETDIR = target/$(TARGET) +OUTDIR = $(TARGETDIR)/$(RELEASE) + +CARGOFLAGS = --target thumbv6m-none-eabi + +.PHONY: all clean cargo-build $(OUTDIR)/$(APP) + +all: $(OUTDIR)/$(APP) + +clean: + rm -f $(APP).uf2 + rm -f $(APP).bin + cargo clean + +test: + cargo test + +cargo-build: + cargo rustc $(CARGOFLAGS) -- -C link-arg=-Tlink.x + +$(OUTDIR)/$(APP): cargo-build + +flash: $(APP).bin + feather-cmd r + sleep 2 + feather-cmd dfu + sleep 2 + $(BOSSAC) -R -e -w -v -o$(OFFSET) -p`./find-serial-port $(USBVID) $(USBPID)` $< + +qemu: $(OUTDIR)/$(APP) + qemu-system-arm -d in_asm,int,exec,cpu,guest_errors,unimp -pidfile qemu.pid -cpu cortex-m0 -machine lm3s6965evb -nographic -semihosting-config enable=on,target=native -s -S -kernel $< + +gdb: $(OUTDIR)/$(APP) + gdb-multiarch -ex "target remote localhost:1234" -ex "break main" -ex "continue" $< + +%.bin: $(OUTDIR)/% + $(OBJCOPY) -O binary $< $@ + +# Requires https://github.com/sajattack/uf2conv-rs.git +%.uf2: %.bin + uf2conv-rs $< --base $(OFFSET) --output $@ diff --git a/usb/find-serial-port b/usb/find-serial-port new file mode 100755 index 0000000..62e2c0c --- /dev/null +++ b/usb/find-serial-port @@ -0,0 +1,16 @@ +#!/bin/sh + +if [ $# -ne 2 ]; then + echo "Usage: $0 vid pid" >&2 + exit 1 +fi + +prefix=/dev/serial/by-id + +for dev in `ls $prefix`; do + if [ `udevadm info -q property --name $prefix/$dev | egrep -i "ID_VENDOR_ID=($1)|ID_MODEL_ID=($2)" | wc -l` -eq 2 ]; then + echo `readlink -f $prefix/$dev` + exit 0 + fi +done +exit 2 diff --git a/usb/src/dotstar.rs b/usb/src/dotstar.rs new file mode 100644 index 0000000..8e930d0 --- /dev/null +++ b/usb/src/dotstar.rs @@ -0,0 +1,42 @@ +use trinket_m0::{ + clock::GenericClockController, + gpio::{self, Floating, Input}, + prelude::*, + sercom::{self, PadPin, SPIMaster1}, + PM, SERCOM1, +}; + +use apa102_spi::Apa102; + +pub fn new( + sercom: SERCOM1, + miso: gpio::Pa31>, + mosi: gpio::Pa0>, + sck: gpio::Pa1>, + port: &mut gpio::Port, + pm: &mut PM, + clocks: &mut GenericClockController, +) -> Apa102< + SPIMaster1< + sercom::Sercom1Pad3>, + sercom::Sercom1Pad0>, + sercom::Sercom1Pad1>, + >, +> { + let gclk = clocks.gclk0(); + let miso = miso.into_pad(port); + let mosi = mosi.into_pad(port); + let sck = sck.into_pad(port); + let spi = SPIMaster1::new( + &clocks + .sercom1_core(&gclk) + .expect("setting up sercom1 clock"), + 3.mhz(), + apa102_spi::MODE, + sercom, + pm, + (miso, mosi, sck), + ); + + Apa102::new(spi) +} diff --git a/usb/src/logger.rs b/usb/src/logger.rs new file mode 100644 index 0000000..be9d391 --- /dev/null +++ b/usb/src/logger.rs @@ -0,0 +1,139 @@ +use crate::rtc; +use starb::{Reader, RingBuffer, Writer}; + +use core::cell::UnsafeCell; +use core::fmt::{self, Write}; +use embedded_hal::{digital::v2::OutputPin, serial}; +use log::{Metadata, Record}; +use trinket_m0::{ + gpio::{Pa6, Pa7, PfD}, + sercom::{Sercom0Pad2, Sercom0Pad3, UART0}, +}; + +static mut UART0: usize = 0; + +struct JoinedRingBuffer<'a> { + lbr: Reader<'a, u8>, + lbw: Writer<'a, u8>, +} + +impl<'a> JoinedRingBuffer<'a> { + const fn new(rb: &'a RingBuffer) -> Self { + let (lbr, lbw) = rb.split(); + Self { lbr: lbr, lbw: lbw } + } +} + +impl fmt::Write for JoinedRingBuffer<'_> { + fn write_str(&mut self, s: &str) -> Result<(), fmt::Error> { + for b in s.bytes() { + if let Err(_) = self.lbw.unshift(b) { + // Ignore buffer full errors for logging. + return Ok(()); + } + } + Ok(()) + } +} + +static mut LB: RingBuffer = RingBuffer::::new(0); +static mut JRB: JoinedRingBuffer = unsafe { JoinedRingBuffer::new(&LB) }; + +// The UART isn't necessarily Sync, so wrap it in something that +// is. As long as flush() is only called from one thread, we're fine, +// but this is a guarantee that the logger module doesn't make. +pub struct WriteWrapper { + w: W, +} +impl WriteWrapper +where + W: serial::Write, +{ + pub fn new(writer: W) -> Self { + Self { w: writer } + } +} +unsafe impl Sync for WriteWrapper {} + +pub struct SerialLogger { + writer: UnsafeCell>, + led: UnsafeCell, +} + +impl SerialLogger +where + W: serial::Write, + L: OutputPin + Send + Sync, +{ + pub fn new(writer: WriteWrapper, led: L) -> Self { + // Stash this for unsafe usage in case there's an issue with + // the rest of the logging. + unsafe { UART0 = core::mem::transmute(&writer.w) }; + Self { + writer: UnsafeCell::new(writer), + led: UnsafeCell::new(led), + } + } +} +unsafe impl Send for SerialLogger {} +unsafe impl Sync for SerialLogger {} + +impl log::Log for SerialLogger +where + W: serial::Write, + L: OutputPin + Send + Sync, +{ + fn enabled(&self, metadata: &Metadata) -> bool { + metadata.level() <= log::max_level() + } + + fn log(&self, record: &Record) { + if !self.enabled(record.metadata()) { + return; + } + + let jrb = unsafe { &mut JRB }; + write!( + jrb, + "[{}] {} {} -- {}\r\n", + rtc::millis(), + record.level(), + record.target(), + record.args() + ) + .ok(); + } + + fn flush(&self) { + // Unsafe due to mutable static. We can only deal with the + // tail position of the buffer here to keep things safe. + let jrb = unsafe { &mut JRB }; + if jrb.lbr.is_empty() { + return; + } + + let led = unsafe { &mut (*self.led.get()) }; + let writer = unsafe { &mut (*self.writer.get()) }; + + led.set_high().ok(); + while let Some(b) = jrb.lbr.shift() { + nb::block!(writer.w.write(b)).ok(); + } + led.set_low().ok(); + } +} + +// Write to the UART right now, instead of putting it on a ring +// buffer. This function is a huge hack, and only useful for debugging +// either before the main loop starts or if the ring buffer is broken. +pub unsafe fn write_fmt_now(args: fmt::Arguments, nl: bool) { + if UART0 == 0 { + return; + } + let uart: &mut UART0>, Sercom0Pad2>, (), ()> = + core::mem::transmute(UART0); + fmt::write(uart, args).expect("writing fmt now to uart"); + if nl { + uart.write_str("\r\n").expect("writing nl now to uart"); + } +} diff --git a/usb/src/macros.rs b/usb/src/macros.rs new file mode 100644 index 0000000..46d2d07 --- /dev/null +++ b/usb/src/macros.rs @@ -0,0 +1,15 @@ +#[macro_export] +macro_rules! logln_now { + ($($arg:tt)*) => { + unsafe {crate::logger::write_fmt_now(format_args!($($arg)*), true);} + }; + (_) => {}; +} + +#[macro_export] +macro_rules! log_now { + ($($arg:tt)*) => { + unsafe {crate::logger::write_fmt_now(format_args!($($arg)*), false);} + }; + (_) => {}; +} diff --git a/usb/src/main.rs b/usb/src/main.rs new file mode 100644 index 0000000..36e4d1e --- /dev/null +++ b/usb/src/main.rs @@ -0,0 +1,196 @@ +//! Take USB keyboard reports and echo them over I²C. + +#![no_std] +#![no_main] + +mod dotstar; +mod logger; +mod macros; +mod rtc; + +use atsamd_usb_host::SAMDHost; +use bootkbd::BootKeyboard; +use clint::HandlerArray; +use core::mem; +use core::panic::PanicInfo; +use cortex_m::asm::wfi; +use cortex_m_rt::{entry, exception, ExceptionFrame}; +use embedded_hal::{blocking::i2c::Write, digital::v2::OutputPin}; +use log::{info, LevelFilter}; +use smart_leds::colors; +use smart_leds_trait::SmartLedsWrite; +use trinket_m0::{ + self as hal, + clock::GenericClockController, + gpio::{OpenDrain, Output, Pa10, Pa6, Pa7, PfD}, + sercom, + target_device::{interrupt, Interrupt}, + time::*, + CorePeripherals, Peripherals, +}; +use usb_host::Driver; + +// A very unsafe copy of an LED to turn on when things go really, really wrong. +static mut LED: usize = 0; + +// I²C address to send keyboard reports to. +const NRF_WIREADDR: u8 = 4; + +// Interrupt handler table. +static HANDLERS: HandlerArray = HandlerArray::new(); + +#[entry] +fn main() -> ! { + let mut cp = CorePeripherals::take().expect("taking core peripherals"); + let mut dp = Peripherals::take().expect("taking device peripherals"); + + let mut clocks = GenericClockController::with_internal_32kosc( + dp.GCLK, + &mut dp.PM, + &mut dp.SYSCTRL, + &mut dp.NVMCTRL, + ); + + let mut pins = hal::Pins::new(dp.PORT); + + let uart = hal::uart( + &mut clocks, + 115_200.hz(), + dp.SERCOM0, + &mut cp.NVIC, + &mut dp.PM, + pins.d3, + pins.d4, + &mut pins.port, + ); + + let mut i2c_master = hal::i2c_master( + &mut clocks, + 400_000.hz(), + dp.SERCOM2, + &mut dp.PM, + pins.d0, + pins.d2, + &mut pins.port, + ); + + let mut red_led = pins.d13.into_open_drain_output(&mut pins.port); + red_led.set_low().expect("turning off red LED"); + unsafe { LED = mem::transmute(&red_led) } + + let mut dotstar = dotstar::new( + dp.SERCOM1, + pins.swdio, + pins.dotstar_di, + pins.dotstar_ci, + &mut pins.port, + &mut dp.PM, + &mut clocks, + ); + let black = [colors::BLACK]; + dotstar + .write(black.iter().cloned()) + .expect("turning off dotstar"); + + // We do the transmute because, while all the underlying data is + // static, we're unable to get a referecence to the UART or LED + // until run-time. Another option would be to use Option in the + // SerialLogger definition, but that requires a check every time + // they might be used. + let uart_wrapped = logger::WriteWrapper::new(uart); + let logger = logger::SerialLogger::new(uart_wrapped, red_led); + + // Wow, would I love to not be annotating this type. + let logger_ref: &'static logger::SerialLogger< + sercom::UART0>, sercom::Sercom0Pad2>, (), ()>, + Pa10>, + > = unsafe { mem::transmute(&logger) }; + unsafe { log::set_logger_racy(logger_ref).expect("couldn't set logger") }; + log::set_max_level(LevelFilter::Trace); + + let mut rtc_handler = rtc::setup(dp.RTC, &mut clocks); + + let (mut usb_host, mut usb_handler) = SAMDHost::new( + dp.USB, + pins.usb_sof, + pins.usb_dm, + pins.usb_dp, + Some(pins.usb_host_enable), + &mut pins.port, + &mut clocks, + &mut dp.PM, + &rtc::millis, + ); + + let mut bootkbd = BootKeyboard::new(|addr, buf| { + info!("{}: {:?}", addr, buf); + let hdr: [u8; 2] = [I2CMessageType::Keyboard as u8, buf.len() as u8]; + i2c_master.write(NRF_WIREADDR, &hdr).ok(); + i2c_master.write(NRF_WIREADDR, &buf).ok(); + }); + let mut drivers: [&mut dyn Driver; 1] = [&mut bootkbd]; + + HANDLERS.with_overrides(|hs| { + hs.register(0, &mut rtc_handler); + unsafe { cp.NVIC.set_priority(Interrupt::USB, 0) }; + cp.NVIC.enable(Interrupt::RTC); + + hs.register(1, &mut usb_handler); + unsafe { cp.NVIC.set_priority(Interrupt::USB, 1) }; + cp.NVIC.enable(Interrupt::USB); + + info!("Bootstrap complete."); + + loop { + usb_host.task(&mut drivers[..]); + wfi() + } + }); + unreachable!(); +} + +#[allow(unused)] +#[repr(u8)] +enum I2CMessageType { + Debug = 0x00, + Keyboard = 0x01, + Invalid = 0xff, +} + +#[panic_handler] +fn panic_handler(pi: &PanicInfo) -> ! { + let red_led: &mut Pa10> = unsafe { mem::transmute(LED) }; + red_led.set_high().ok(); + + logln_now!("~~~ PANIC ~~~"); + logln_now!("{}", pi); + logln_now!("flushing log"); + loop { + log::logger().flush(); + wfi() + } +} + +#[exception] +fn HardFault(ef: &ExceptionFrame) -> ! { + let red_led: &mut Pa10> = unsafe { mem::transmute(LED) }; + red_led.set_high().ok(); + + log::logger().flush(); + logln_now!("!!! Hard Fault - ef: {:?} !!!", ef); + logln_now!("flushing log"); + loop { + log::logger().flush(); + wfi() + } +} + +#[interrupt] +fn RTC() { + HANDLERS.call(0); +} + +#[interrupt] +fn USB() { + HANDLERS.call(1); +} diff --git a/usb/src/rtc.rs b/usb/src/rtc.rs new file mode 100644 index 0000000..fa7b347 --- /dev/null +++ b/usb/src/rtc.rs @@ -0,0 +1,75 @@ +use core::sync::atomic::{AtomicUsize, Ordering}; +use log; +use trinket_m0::{clock::GenericClockController, RTC}; + +struct Clock(AtomicUsize); +impl Clock { + const fn new() -> Self { + Self(AtomicUsize::new(0)) + } + + fn set(&self, millis: usize) { + self.0.store(millis, Ordering::SeqCst) + } + + // Slightly less than 1ms, due to using a 32,768Hz clock, we can't + // hit exactly 1ms, so we shoot for a bit under. + fn millis(&self) -> usize { + self.0.load(Ordering::SeqCst) + } +} + +static CLOCK: Clock = Clock::new(); + +// Set to run every ~500µs. This has been loosely calibrated from a +// nrf52 clock running Arduino and a Linux host. +static COUNTER: u32 = 13; + +pub fn setup(mut rtc: RTC, clocks: &mut GenericClockController) -> impl FnMut() { + let rtc_clock = &clocks.gclk1(); + clocks.rtc(&rtc_clock); + + rtc.mode0().ctrl.write(|w| w.swrst().set_bit()); + while rtc.mode0().status.read().syncbusy().bit_is_set() {} + + rtc.mode0().ctrl.write(|w| { + w.mode().count32(); + + // Neither the prescaler nor matchlr values seem to work. Not + // sure why. + //w.prescaler().div1024(); + w.matchclr().set_bit() // Reset on match for periodic + }); + + rtc.mode0().comp[0].write(|w| unsafe { w.bits(COUNTER) }); + rtc.mode0().intflag.write(|w| w.cmp0().set_bit()); + rtc.mode0().intenset.write(|w| w.cmp0().set_bit()); + + // Enable the RTC and wait for sync. + rtc.mode0().ctrl.write(|w| w.enable().set_bit()); + while rtc.mode0().status.read().syncbusy().bit_is_set() {} + + move || handler(&mut rtc) +} + +pub fn millis() -> usize { + CLOCK.millis() +} + +fn handler(rtc: &mut RTC) { + // FIXME: matchclr doesn't seem to work to reset the counter? + rtc.mode0().count.write(|w| unsafe { w.bits(0) }); + rtc.mode0().intflag.write(|w| w.cmp0().set_bit()); + + static mut TICKS: usize = 0; + static mut ADD: bool = false; + unsafe { + if ADD { + TICKS += 1; + CLOCK.set(TICKS); + } + ADD = !ADD; + + log::logger().flush(); + } +} -- cgit v1.2.3