Rewrite the driver in Rust; move the testbench tools out
The repository is now only the HPCS 6500 driver: a Rust library (serial transport, every protocol command, block parsing, USBPcap captures, a simulated instrument) and the hpcs6500 CLI with the flags of the former hpcs6500.py, plus dump/capture for reverse engineering. The lamp station, lamp export, TM-30, label printer and LED calibration move to B4L/lamp-testbench. Golden tests pin the Rust output to the Python driver's: parsed values bit-exact, report text, CSV and number formatting. The Python driver is at tag python-final.
This commit is contained in:
1 parent
3ac7cd243b
commit
54242da04b
79 files changed
+23340
-3246
No files matched your search
@@ -0,0 +1,52 @@
|
||||
use std::fmt::Write;
|
||||
|
||||
/// Everything that can go wrong talking to the instrument.
|
||||
#[derive(Debug, thiserror::Error)]
|
||||
pub enum Error {
|
||||
#[error("serial port: {0}")]
|
||||
Serial(#[from] serialport::Error),
|
||||
#[error("I/O: {0}")]
|
||||
Io(#[from] std::io::Error),
|
||||
/// A write command was not acknowledged with `8C <cmd>`.
|
||||
#[error("no acknowledge for command 0x{cmd:02X} (got {got})")]
|
||||
NoAck { cmd: u8, got: String },
|
||||
/// A read command answered with an unexpected header.
|
||||
#[error("bad response to command 0x{cmd:02X} (got {got})")]
|
||||
BadResponse { cmd: u8, got: String },
|
||||
/// A data block ended early.
|
||||
#[error("{what} short ({got}/{want} bytes)")]
|
||||
Short {
|
||||
what: &'static str,
|
||||
got: usize,
|
||||
want: usize,
|
||||
},
|
||||
#[error("timeout waiting for measurement data")]
|
||||
Timeout,
|
||||
/// The cancel flag (Ctrl+C) was raised during a wait.
|
||||
#[error("cancelled")]
|
||||
Cancelled,
|
||||
#[error("HPCS 6500 not found (no serial port with VID 0483 / PID 5741)")]
|
||||
NotFound,
|
||||
#[error("pcap: {0}")]
|
||||
Pcap(String),
|
||||
}
|
||||
|
||||
pub type Result<T, E = Error> = std::result::Result<T, E>;
|
||||
|
||||
/// `8c 13 0f` style hex for error messages, `(nothing)` when empty.
|
||||
pub(crate) fn hex(b: &[u8]) -> String {
|
||||
if b.is_empty() {
|
||||
return "nothing".into();
|
||||
}
|
||||
let mut s = String::new();
|
||||
for (i, x) in b.iter().take(24).enumerate() {
|
||||
if i > 0 {
|
||||
s.push(' ');
|
||||
}
|
||||
let _ = write!(s, "{x:02x}");
|
||||
}
|
||||
if b.len() > 24 {
|
||||
let _ = write!(s, " ... ({} bytes)", b.len());
|
||||
}
|
||||
s
|
||||
}
|
||||
Reference in new issue
Block a user