Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 0 additions & 2 deletions EXAMPLES.md
Original file line number Diff line number Diff line change
Expand Up @@ -67,8 +67,6 @@ Options:
Parse UEFI Capsule information from binary file
--dump <DUMP>
Dump extracted UX capsule bitmap image to a file
--h2o-capsule <H2O_CAPSULE>
Parse UEFI Capsule information from binary file
--dump-ec-flash <DUMP_EC_FLASH>
Dump EC flash contents
--flash-ec <FLASH_EC>
Expand Down
11 changes: 4 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -133,14 +133,11 @@ On UEFI and FreeBSD raw port I/O is used - on Linux this can also be used as a f
- [x] CCG5 PD (11th Gen TigerLake) (`--pd-bin`)
- [x] CCG6 PD (Intel systems, Framework Desktop) (`--pd-bin`)
- [x] CCG8 PD (AMD Laptops) (`--pd-bin`)
- [x] H2O BIOS Capsule (`--h2o-capsule`)
- [x] BIOS Version
- [x] EC Version
- [x] CCG5/CCG6/CCG8 PD Version
- [x] UEFI Capsule (`--capsule`)
- [x] Parse metadata from capsule binary
- [x] Determine type (GUID) of capsule binary
- [x] Extract bitmap image from winux capsule to file
- [x] Determine type (GUID) of capsule binary
- [x] Extract embedded BIOS, EC, and PD versions
- [x] Extract bitmap image from winux capsule to file
- [x] Fallback to raw H2O BIOS files without capsule header
- [x] Get firmware version from system (`--versions`)
- [x] BIOS
- [x] EC
Expand Down
48 changes: 34 additions & 14 deletions framework_lib/src/capsule_content.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

use crate::alloc::string::ToString;
use alloc::string::String;
use alloc::vec::Vec;
use core::convert::TryInto;

use crate::ccgx::binary::{CCG5_PD_LEN, CCG6_PD_LEN, CCG8_PD_LEN};
Expand Down Expand Up @@ -51,19 +52,38 @@ pub fn find_ec_in_bios_cap(data: &[u8]) -> Option<&[u8]> {
}

pub fn find_pd_in_bios_cap(data: &[u8]) -> Option<&[u8]> {
// Just search for the first couple of bytes in PD binaries
// TODO: There's a second one but unless the capsule is bad, we can assume
// they're the same version
let ccg5_needle = &[0x00, 0x20, 0x00, 0x20, 0x11, 0x00];
let ccg6_needle = &[0x00, 0x40, 0x00, 0x20, 0x11, 0x00];
let ccg8_needle = &[0x00, 0x80, 0x00, 0x20, 0xAD, 0x0C];
if let Some(found_pd1) = util::find_sequence(data, ccg5_needle) {
Some(&data[found_pd1..found_pd1 + CCG5_PD_LEN])
} else if let Some(found_pd1) = util::find_sequence(data, ccg6_needle) {
Some(&data[found_pd1..found_pd1 + CCG6_PD_LEN])
} else if let Some(found_pd1) = util::find_sequence(data, ccg8_needle) {
Some(&data[found_pd1..found_pd1 + CCG8_PD_LEN])
} else {
None
find_all_pds_in_bios_cap(data).into_iter().next()
}

/// PD binary signatures and their corresponding lengths
const CCG5_NEEDLE: &[u8] = &[0x00, 0x20, 0x00, 0x20, 0x11, 0x00];
const CCG6_NEEDLE: &[u8] = &[0x00, 0x40, 0x00, 0x20, 0x11, 0x00];
const CCG8_NEEDLE: &[u8] = &[0x00, 0x80, 0x00, 0x20, 0xAD, 0x0C];

/// Find all PD firmware binaries embedded in a BIOS capsule
pub fn find_all_pds_in_bios_cap(data: &[u8]) -> Vec<&[u8]> {
let mut results = Vec::new();

// Search for CCG5 PDs
for offset in util::find_all_sequences(data, CCG5_NEEDLE) {
if offset + CCG5_PD_LEN <= data.len() {
results.push(&data[offset..offset + CCG5_PD_LEN]);
}
}

// Search for CCG6 PDs
for offset in util::find_all_sequences(data, CCG6_NEEDLE) {
if offset + CCG6_PD_LEN <= data.len() {
results.push(&data[offset..offset + CCG6_PD_LEN]);
}
}

// Search for CCG8 PDs
for offset in util::find_all_sequences(data, CCG8_NEEDLE) {
if offset + CCG8_PD_LEN <= data.len() {
results.push(&data[offset..offset + CCG8_PD_LEN]);
}
}

results
}
7 changes: 0 additions & 7 deletions framework_lib/src/commandline/clap_std.rs
Original file line number Diff line number Diff line change
Expand Up @@ -161,10 +161,6 @@ struct ClapCli {
#[arg(long)]
dump: Option<std::path::PathBuf>,

/// Parse UEFI Capsule information from binary file
#[arg(long)]
h2o_capsule: Option<std::path::PathBuf>,

/// Dump EC flash contents
#[arg(long)]
dump_ec_flash: Option<std::path::PathBuf>,
Expand Down Expand Up @@ -671,9 +667,6 @@ pub fn parse(args: &[String]) -> Cli {
.capsule
.map(|x| x.into_os_string().into_string().unwrap()),
dump: args.dump.map(|x| x.into_os_string().into_string().unwrap()),
h2o_capsule: args
.h2o_capsule
.map(|x| x.into_os_string().into_string().unwrap()),
dump_ec_flash: args
.dump_ec_flash
.map(|x| x.into_os_string().into_string().unwrap()),
Expand Down
Loading
Loading