Skip to content

Commit 8249c7a

Browse files
committed
Construct PspSoftFuseChain bitfield from serde input and/or serialize to serde.
Fixes <#235>.
1 parent f059912 commit 8249c7a

File tree

2 files changed

+43
-5
lines changed

2 files changed

+43
-5
lines changed

ahib-config/src/lib.rs

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use amd_efs::flash::Location;
88
use amd_efs::{
99
AddressMode, ComboDirectoryEntryFilter, EfhBulldozerSpiMode,
1010
EfhEspiConfiguration, EfhNaplesSpiMode, EfhRomeSpiMode,
11-
ProcessorGeneration,
11+
ProcessorGeneration, PspSoftFuseChain,
1212
};
1313
use amd_efs::{
1414
BhdDirectoryEntry, BhdDirectoryEntryRegionType, BhdDirectoryEntryType,
@@ -30,6 +30,8 @@ pub enum Error {
3030
Io(std::io::Error),
3131
#[error("image too big")]
3232
ImageTooBig,
33+
#[error("psp entry source {0} unknown")]
34+
PspEntrySourceUnknown(PspDirectoryEntryType),
3335
}
3436

3537
impl From<amd_efs::Error> for Error {
@@ -106,11 +108,46 @@ impl TryFromSerdeDirectoryEntryWithContext<SerdePspDirectoryEntry>
106108
}
107109
}
108110

111+
// See <https://github.com/serde-rs/serde/issues/1799>
112+
#[derive(Clone, serde::Serialize, serde::Deserialize, schemars::JsonSchema)]
113+
#[serde(rename = "SerdePspEntrySourceValue")]
114+
#[serde(deny_unknown_fields)]
115+
pub enum SerdePspEntrySourceValue {
116+
PspSoftFuseChain(PspSoftFuseChain),
117+
#[serde(default)]
118+
Raw(u64),
119+
}
120+
121+
impl SerdePspEntrySourceValue {
122+
pub fn from_u64(value: u64, typ: PspDirectoryEntryType) -> Result<Self> {
123+
match typ {
124+
PspDirectoryEntryType::PspSoftFuseChain => {
125+
Ok(Self::PspSoftFuseChain(PspSoftFuseChain::from(value)))
126+
}
127+
_ => Err(Error::PspEntrySourceUnknown(typ)),
128+
}
129+
}
130+
131+
pub fn to_u64(
132+
&self,
133+
typ_or_err: std::result::Result<PspDirectoryEntryType, amd_efs::Error>,
134+
) -> Result<u64> {
135+
let typ = typ_or_err.unwrap();
136+
match typ {
137+
PspDirectoryEntryType::PspSoftFuseChain => match self {
138+
Self::PspSoftFuseChain(x) => Ok(u64::from(*x)),
139+
_ => Err(Error::PspEntrySourceUnknown(typ)),
140+
},
141+
_ => Err(Error::PspEntrySourceUnknown(typ)),
142+
}
143+
}
144+
}
145+
109146
#[derive(Clone, serde::Serialize, serde::Deserialize, schemars::JsonSchema)]
110147
#[serde(rename = "PspEntrySource")]
111148
#[serde(deny_unknown_fields)]
112149
pub enum SerdePspEntrySource {
113-
Value(u64),
150+
Value(SerdePspEntrySourceValue),
114151
BlobFile(PathBuf),
115152
SecondLevelDirectory(SerdePspDirectory),
116153
}

src/main.rs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ use amd_efs::{
66
ProcessorGeneration, PspDirectory, PspDirectoryEntry,
77
PspDirectoryEntryType, PspDirectoryHeader, ValueOrLocation,
88
};
9+
use amd_host_image_builder_config::SerdePspEntrySourceValue;
910
use amd_host_image_builder_config::{
1011
Error, Result, SerdeBhdDirectory, SerdeBhdDirectoryEntry,
1112
SerdeBhdDirectoryEntryAttrs, SerdeBhdDirectoryEntryBlob,
@@ -622,7 +623,7 @@ fn dump_psp_directory<T: FlashRead + FlashWrite>(
622623
// TODO: Handle the other variant (PspComboDirectory)
623624
let mut blob_dump_filenames = HashSet::<PathBuf>::new();
624625
SerdePspDirectoryVariant::PspDirectory(SerdePspDirectory {
625-
entries: psp_directory.entries().map_while(|e| {
626+
entries: psp_directory.entries().map_while(|e| -> Option<SerdePspEntry> {
626627
if let Ok(typ) = e.typ_or_err() {
627628
match typ {
628629
PspDirectoryEntryType::SecondLevelDirectory => {
@@ -684,7 +685,7 @@ fn dump_psp_directory<T: FlashRead + FlashWrite>(
684685
}
685686
None => {
686687
let value = e.value().unwrap();
687-
SerdePspEntrySource::Value(value)
688+
SerdePspEntrySource::Value(SerdePspEntrySourceValue::from_u64(value, typ).expect("known psp entry type"))
688689
}
689690
},
690691
target: SerdePspDirectoryEntry {
@@ -1096,7 +1097,7 @@ fn prepare_psp_directory_contents(
10961097
SerdePspEntrySource::Value(x) => {
10971098
// FIXME: assert!(blob_slot_settings.is_none()); fails for some reason
10981099
// DirectoryRelativeOffset is the one that can always be overridden
1099-
raw_entry.set_source(AddressMode::DirectoryRelativeOffset, ValueOrLocation::Value(x)).unwrap();
1100+
raw_entry.set_source(AddressMode::DirectoryRelativeOffset, ValueOrLocation::Value(x.to_u64(raw_entry.typ_or_err()).unwrap())).unwrap();
11001101
vec![(raw_entry, None, None)]
11011102
}
11021103
SerdePspEntrySource::BlobFile(

0 commit comments

Comments
 (0)