serial: split out --root process, don't wait for reboot, update usage text

We need to wait for atfwd_daemon to startup before sending any AT
commands, and I can't think of a way to reliably do that within rust.
So, instead of trying to switch the device to command mode before
executing a command, require the user to run the "--root" step
beforehand, and then start executing AT commands.
This commit is contained in:
Will Greenberg
2024-08-02 18:14:44 -07:00
committed by Cooper Quintin
parent d6fb54afb3
commit 65e1cd4967
+26 -34
View File
@@ -20,7 +20,6 @@
//! Err(e) => panic!("Failed to initialize libusb: {0}", e), //! Err(e) => panic!("Failed to initialize libusb: {0}", e),
//! ```` //! ````
use std::str; use std::str;
use std::thread::sleep;
use std::time::Duration; use std::time::Duration;
use rusb::{Context, DeviceHandle, UsbContext}; use rusb::{Context, DeviceHandle, UsbContext};
@@ -28,19 +27,21 @@ use rusb::{Context, DeviceHandle, UsbContext};
fn main() { fn main() {
let args: Vec<String> = std::env::args().collect(); let args: Vec<String> = std::env::args().collect();
if args.len() < 2 { if args.len() != 2 {
println!("usage: {0} <command>", args[0]); println!("usage: {0} [<command> | --root]", args[0]);
return; return;
} }
match Context::new() { match Context::new() {
Ok(mut context) => match open_orbic(&mut context) { Ok(mut context) => {
Some(mut handle) => { if args[1] == "--root" {
if &args[1] != "--root" { enable_command_mode(&mut context);
send_command(&mut handle, &args[1]) } else {
match open_orbic(&mut context) {
Some(mut handle) => send_command(&mut handle, &args[1]),
None => panic!("No Orbic device found"),
} }
} }
None => panic!("No Orbic device found"),
}, },
Err(e) => panic!("Failed to initialize libusb: {0}", e), Err(e) => panic!("Failed to initialize libusb: {0}", e),
} }
@@ -78,30 +79,33 @@ fn send_command<T: UsbContext>(handle: &mut DeviceHandle<T>, command: &str) {
.expect("Failed to read response"); .expect("Failed to read response");
let responsestr = str::from_utf8(&response).expect("Failed to parse response"); let responsestr = str::from_utf8(&response).expect("Failed to parse response");
if !responsestr.starts_with("\r\nOK\r\n") { if !responsestr.contains("\r\nOK\r\n") {
println!("Received unexpected response{0}", responsestr) println!("Received unexpected response{0}", responsestr);
std::process::exit(1);
} }
} }
/// Send a command to switch the device into generic mode, exposing serial /// Send a command to switch the device into generic mode, exposing serial
/// ///
/// If the device reboots while the command is still executing you may get a pipe error here, not sure what to do about this race condition. /// If the device reboots while the command is still executing you may get a pipe error here, not sure what to do about this race condition.
fn switch_device<T: UsbContext>(handle: &mut DeviceHandle<T>) { fn enable_command_mode<T: UsbContext>(context: &mut T) {
let timeout = Duration::from_secs(1); let timeout = Duration::from_secs(1);
match open_device(context, 0x05c6, 0xf626) {
if let Err(e) = handle.write_control(0x40, 0xa0, 0, 0, &[], timeout) { Some(handle) => {
// If the device reboots while the command is still executing we if let Err(e) = handle.write_control(0x40, 0xa0, 0, 0, &[], timeout) {
// may get a pipe error here // If the device reboots while the command is still executing we
if e == rusb::Error::Pipe { // may get a pipe error here
return; if e == rusb::Error::Pipe {
} return;
panic!("Failed to send device switch control request: {0}", e) }
panic!("Failed to send device switch control request: {0}", e)
}
},
None => panic!("No Orbic device detected"),
} }
} }
/// Get a handle and contet for the orbic device /// Get a handle and contet for the orbic device
///
/// If the device isn't already in command mode this function will call swtich_device to switch it into command mode
fn open_orbic<T: UsbContext>(context: &mut T) -> Option<DeviceHandle<T>> { fn open_orbic<T: UsbContext>(context: &mut T) -> Option<DeviceHandle<T>> {
// Device after initial mode switch // Device after initial mode switch
if let Some(handle) = open_device(context, 0x05c6, 0xf601) { if let Some(handle) = open_device(context, 0x05c6, 0xf601) {
@@ -113,19 +117,7 @@ fn open_orbic<T: UsbContext>(context: &mut T) -> Option<DeviceHandle<T>> {
return Some(handle); return Some(handle);
} }
// Device in out-of-the-box state, need to switch to diag mode None
match open_device(context, 0x05c6, 0xf626) {
Some(mut handle) => switch_device(&mut handle),
None => panic!("No Orbic device detected"),
}
for _ in 1..10 {
if let Some(handle) = open_device(context, 0x05c6, 0xf601) {
return Some(handle);
}
sleep(Duration::from_secs(10))
}
panic!("No Orbic device detected")
} }
/// Generic function to open a USB device /// Generic function to open a USB device