Skip to content

Commit cad75f7

Browse files
committed
Use model-specific scripts if found
Prioritize model-specific scripts over embedded flash logic. Allows using scripts and external drivers/apps for flashing systems with coreboot and 76ec. Signed-off-by: Tim Crawford <[email protected]>
1 parent 83d9398 commit cad75f7

File tree

3 files changed

+100
-41
lines changed

3 files changed

+100
-41
lines changed

src/app/bios.rs

Lines changed: 42 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ use std::uefi::reset::ResetType;
1515
use std::vars::{get_boot_item, get_boot_order, set_boot_item, set_boot_order};
1616

1717
use super::{
18-
Component, FIRMWARECAP, FIRMWAREDIR, FIRMWARENSH, FIRMWAREROM, H2OFFT, IFLASHV, UEFIFLASH,
19-
UefiMapper, cmos, pci_mcfg, shell,
18+
Component, FIRMWARECAP, FIRMWAREDIR, FIRMWARENSH, FIRMWAREROM, H2OFFT, IFLASHV,
19+
MODEL_FIRMWARE_NSH, UEFIFLASH, UefiMapper, cmos, pci_mcfg, shell,
2020
};
2121

2222
fn copy_region(
@@ -245,7 +245,46 @@ impl Component for BiosComponent {
245245
}
246246

247247
fn flash(&self) -> Result<()> {
248-
if let Some((mut spi, _hsfsts_ctl)) = self.spi() {
248+
if find(MODEL_FIRMWARE_NSH).is_ok() {
249+
find(FIRMWARENSH)?;
250+
251+
let mut boot_options: Vec<(u16, Vec<u8>)> = vec![];
252+
253+
let order = get_boot_order();
254+
if order.is_ok() {
255+
println!("Preserving boot order");
256+
for num in order.clone().unwrap() {
257+
if let Ok(item) = get_boot_item(num) {
258+
boot_options.push((num, item));
259+
} else {
260+
println!("Failed to read Boot{:>04X}", num);
261+
}
262+
}
263+
} else {
264+
println!("Failed to preserve boot order");
265+
}
266+
267+
let cmd = format!("{} {} bios flash", FIRMWARENSH, FIRMWAREDIR);
268+
let status = shell(&cmd)?;
269+
270+
if let Ok(order) = order {
271+
if set_boot_order(&order).is_ok() {
272+
for (num, data) in boot_options {
273+
if set_boot_item(num, &data).is_err() {
274+
println!("Failed to write Boot{:>04X}", num);
275+
}
276+
}
277+
println!("Restored boot order");
278+
} else {
279+
println!("Failed to restore boot order");
280+
}
281+
}
282+
283+
if status != 0 {
284+
println!("{} Flash Error: {}", self.name(), status);
285+
return Err(Status::DEVICE_ERROR);
286+
}
287+
} else if let Some((mut spi, _hsfsts_ctl)) = self.spi() {
249288
// Read new data
250289
let mut new;
251290
{

src/app/ec.rs

Lines changed: 54 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,8 @@ use std::{
1616
};
1717

1818
use super::{
19-
Component, EC2ROM, ECROM, ECTAG, FIRMWAREDIR, FIRMWARENSH, pci_read, shell, sideband::Sideband,
19+
Component, EC2ROM, ECROM, ECTAG, FIRMWAREDIR, FIRMWARENSH, MODEL_EC_NSH, pci_read, shell,
20+
sideband::Sideband,
2021
};
2122

2223
pub struct UefiTimeout {
@@ -767,49 +768,64 @@ impl Component for EcComponent {
767768
println!("file version: {:?}", str::from_utf8(firmware.version));
768769
}
769770

770-
let result = match &self.ec {
771-
EcKind::Pang(_pmc, _system_version) => {
772-
find(FIRMWARENSH)?;
773-
let command = if self.master { "ec" } else { "ec2" };
774-
let status = shell(&format!(
775-
"{} {} {} flash",
776-
FIRMWARENSH, FIRMWAREDIR, command
777-
))?;
778-
if status == 0 {
779-
Ok(())
780-
} else {
781-
println!("{} Flash Error: {}", self.name(), status);
782-
Err(Status::DEVICE_ERROR)
783-
}
771+
let result = if find(MODEL_EC_NSH).is_ok() {
772+
find(FIRMWARENSH)?;
773+
let command = if self.master { "ec" } else { "ec2" };
774+
let status = shell(&format!(
775+
"{} {} {} flash",
776+
FIRMWARENSH, FIRMWAREDIR, command
777+
))?;
778+
if status == 0 {
779+
Ok(())
780+
} else {
781+
println!("{} Flash Error: {}", self.name(), status);
782+
Err(Status::DEVICE_ERROR)
784783
}
785-
EcKind::System76(_ec, _pmc) => {
786-
// System76 EC requires reset to load new firmware
787-
requires_reset = true;
788-
789-
// Flash main ROM
790-
match unsafe { flash(&firmware_data, SpiTarget::Main) } {
791-
Ok(()) => Ok(()),
792-
Err(err) => {
793-
println!("{} Flash Error: {:X?}", self.name(), err);
784+
} else {
785+
match &self.ec {
786+
EcKind::Pang(_pmc, _system_version) => {
787+
find(FIRMWARENSH)?;
788+
let command = if self.master { "ec" } else { "ec2" };
789+
let status = shell(&format!(
790+
"{} {} {} flash",
791+
FIRMWARENSH, FIRMWAREDIR, command
792+
))?;
793+
if status == 0 {
794+
Ok(())
795+
} else {
796+
println!("{} Flash Error: {}", self.name(), status);
794797
Err(Status::DEVICE_ERROR)
795798
}
796799
}
797-
}
798-
EcKind::Legacy(_ec) => {
799-
requires_reset = true;
800-
801-
// Use open source flashing code
802-
match unsafe { flash_legacy(&firmware_data) } {
803-
Ok(()) => Ok(()),
804-
Err(err) => {
805-
println!("{} Flash Error: {:X?}", self.name(), err);
806-
Err(Status::DEVICE_ERROR)
800+
EcKind::System76(_ec, _pmc) => {
801+
// System76 EC requires reset to load new firmware
802+
requires_reset = true;
803+
804+
// Flash main ROM
805+
match unsafe { flash(&firmware_data, SpiTarget::Main) } {
806+
Ok(()) => Ok(()),
807+
Err(err) => {
808+
println!("{} Flash Error: {:X?}", self.name(), err);
809+
Err(Status::DEVICE_ERROR)
810+
}
807811
}
808812
}
809-
}
810-
EcKind::Unknown => {
811-
println!("{} Failed to flash EcKind::Unknown", self.name());
812-
Err(Status::DEVICE_ERROR)
813+
EcKind::Legacy(_ec) => {
814+
requires_reset = true;
815+
816+
// Use open source flashing code
817+
match unsafe { flash_legacy(&firmware_data) } {
818+
Ok(()) => Ok(()),
819+
Err(err) => {
820+
println!("{} Flash Error: {:X?}", self.name(), err);
821+
Err(Status::DEVICE_ERROR)
822+
}
823+
}
824+
}
825+
EcKind::Unknown => {
826+
println!("{} Failed to flash EcKind::Unknown", self.name());
827+
Err(Status::DEVICE_ERROR)
828+
}
813829
}
814830
};
815831

src/app/mod.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,10 @@ static SPLASHBMP: &str = concat!("\\", env!("BASEDIR"), "\\res\\splash.bmp");
4949
static UEFIFLASH: &str = concat!("\\", env!("BASEDIR"), "\\firmware\\uefiflash.efi");
5050
static UEFIFLASHTAG: &str = concat!("\\", env!("BASEDIR"), "\\firmware\\uefiflash.tag");
5151

52+
// Model-specific flash scripts
53+
static MODEL_FIRMWARE_NSH: &str = concat!("\\", env!("BASEDIR"), "\\firmware\\firmware.nsh");
54+
static MODEL_EC_NSH: &str = concat!("\\", env!("BASEDIR"), "\\firmware\\ec.nsh");
55+
5256
fn shell(cmd: &str) -> Result<usize> {
5357
exec_path(
5458
SHELLEFI,

0 commit comments

Comments
 (0)