Add board-info command support in Secure Download Mode (#838)

* Cut off the write_bin part from original #832

* Changelog entry

* Akela missed...

* Dumb

* Address reviews
This commit is contained in:
Kirill Mikhailov 2025-04-10 11:50:31 +02:00 committed by GitHub
parent 37f28f6ba0
commit fd795df7b5
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 44 additions and 15 deletions

View File

@ -234,6 +234,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Make the default flashing frequency target specific (#389)
- Add note about permissions on Linux (#391)
- Add a diagnostic to tell the user about the partition table format (#397)
- Add `board-info` command support in Secure Download Mode (#838)
### Fixed

View File

@ -575,17 +575,21 @@ pub fn parse_chip_rev(chip_rev: &str) -> Result<u16> {
/// Print information about a chip
pub fn print_board_info(flasher: &mut Flasher) -> Result<()> {
let info = flasher.device_info()?;
print!("Chip type: {}", info.chip);
if let Some((major, minor)) = info.revision {
println!(" (revision v{major}.{minor})");
} else {
println!();
}
println!("Crystal frequency: {}", info.crystal_frequency);
println!("Flash size: {}", info.flash_size);
println!("Features: {}", info.features.join(", "));
println!("MAC address: {}", info.mac_address);
if let Some(mac) = info.mac_address {
println!("MAC address: {}", mac);
}
Ok(())
}

View File

@ -124,6 +124,7 @@ pub struct Connection {
decoder: SlipDecoder,
after_operation: ResetAfterOperation,
before_operation: ResetBeforeOperation,
pub(crate) secure_download_mode: bool,
}
impl Connection {
@ -139,6 +140,7 @@ impl Connection {
decoder: SlipDecoder::new(),
after_operation,
before_operation,
secure_download_mode: false,
}
}
@ -449,6 +451,7 @@ impl Connection {
// - https://docs.espressif.com/projects/esptool/en/latest/esp32/advanced-topics/serial-protocol.html?highlight=md5#response-packet
// - https://docs.espressif.com/projects/esptool/en/latest/esp32/advanced-topics/serial-protocol.html?highlight=md5#status-bytes
// - https://docs.espressif.com/projects/esptool/en/latest/esp32/advanced-topics/serial-protocol.html?highlight=md5#verifying-uploaded-data
let status_len = if response.len() == 10 || response.len() == 26 {
2
} else {
@ -483,8 +486,8 @@ impl Connection {
return_op: response[1],
return_length: u16::from_le_bytes(response[2..][..2].try_into().unwrap()),
value,
error: response[response.len() - status_len],
status: response[response.len() - status_len + 1],
error: response[response.len() - status_len + 1],
status: response[response.len() - status_len],
};
Ok(Some(header))
@ -524,11 +527,10 @@ impl Connection {
pub fn command(&mut self, command: Command<'_>) -> Result<CommandResponseValue, Error> {
let ty = command.command_type();
self.write_command(command).for_command(ty)?;
for _ in 0..100 {
match self.read_response().for_command(ty)? {
Some(response) if response.return_op == ty as u8 => {
return if response.error != 0 {
return if response.status != 0 {
let _error = self.flush();
Err(Error::RomError(RomError::new(
command.command_type(),

View File

@ -634,7 +634,7 @@ pub struct DeviceInfo {
/// Device features
pub features: Vec<String>,
/// MAC address
pub mac_address: String,
pub mac_address: Option<String>,
}
/// Connect to and flash a target device
@ -710,14 +710,19 @@ impl Flasher {
return Ok(flasher);
}
// Load flash stub if enabled
if use_stub {
info!("Using flash stub");
flasher.load_stub()?;
if !flasher.connection.secure_download_mode {
// Load flash stub if enabled.
if use_stub {
info!("Using flash stub");
flasher.load_stub()?;
}
// Flash size autodetection doesn't work in Secure Download Mode.
flasher.spi_autodetect()?;
} else if use_stub {
warn!("Stub is not supported in Secure Download Mode, setting --no-stub");
flasher.use_stub = false;
}
flasher.spi_autodetect()?;
// Now that we have established a connection and detected the chip and flash
// size, we can set the baud rate of the connection to the configured value.
if let Some(baud) = speed {
@ -985,14 +990,21 @@ impl Flasher {
let chip = self.chip();
let target = chip.into_target();
let revision = Some(target.chip_revision(self.connection())?);
// chip_revision reads from efuse, which is not possible in Secure Download Mode
let revision = (!self.connection.secure_download_mode)
.then(|| target.chip_revision(self.connection()))
.transpose()?;
let crystal_frequency = target.crystal_freq(self.connection())?;
let features = target
.chip_features(self.connection())?
.iter()
.map(|s| s.to_string())
.collect::<Vec<_>>();
let mac_address = target.mac_address(self.connection())?;
let mac_address = (!self.connection.secure_download_mode)
.then(|| target.mac_address(self.connection()))
.transpose()?;
let info = DeviceInfo {
chip,
@ -1099,13 +1111,23 @@ impl Flasher {
segments: &[Segment<'_>],
mut progress: Option<&mut dyn ProgressCallbacks>,
) -> Result<(), Error> {
if self.connection.secure_download_mode {
return Err(Error::UnsupportedFeature {
chip: self.chip,
feature: "writing binaries in Secure Download Mode currently".into(),
});
}
let mut target = self
.chip
.flash_target(self.spi_params, self.use_stub, false, false);
target.begin(&mut self.connection).flashing()?;
for segment in segments {
target.write_segment(&mut self.connection, segment.borrow(), &mut progress)?;
}
target.finish(&mut self.connection, true).flashing()?;
Ok(())