Skip to content

Commit cfa8e42

Browse files
committed
sim: Fix largest image computation for swap-move and swap-offset
For the swap-move and swap-offset strategies, the computation of the largest image size was not taking taking into account the padding that is needed when using those strategies. Due to this limitation, the simulator is currently using hardcoded image sizes, smaller than the maximum possible size, when running tests for the swap-move or swap-offset strategies. This commit fixes the maximum image size computation for those strategies. Signed-off-by: Thomas Altenbach <[email protected]>
1 parent 3589fb9 commit cfa8e42

File tree

1 file changed

+71
-55
lines changed

1 file changed

+71
-55
lines changed

sim/src/image.rs

Lines changed: 71 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -234,21 +234,21 @@ impl ImagesBuilder {
234234

235235
let (primaries,upgrades) = if img_manipulation == ImageManipulation::CorruptHigherVersionImage && !higher_version_corrupted {
236236
higher_version_corrupted = true;
237-
let prim = install_image(&mut flash, &self.areadesc, &slots[0],
238-
maximal(42784), &ram, &*dep, ImageManipulation::None, Some(0), false);
237+
let prim = install_image(&mut flash, &self.areadesc, &slots, 0,
238+
maximal(42784), &ram, &*dep, ImageManipulation::None, Some(0));
239239
let upgr = match deps.depends[image_num] {
240240
DepType::NoUpgrade => install_no_image(),
241-
_ => install_image(&mut flash, &self.areadesc, &slots[1],
242-
maximal(46928), &ram, &*dep, ImageManipulation::BadSignature, Some(0), true)
241+
_ => install_image(&mut flash, &self.areadesc, &slots, 1,
242+
maximal(46928), &ram, &*dep, ImageManipulation::BadSignature, Some(0))
243243
};
244244
(prim, upgr)
245245
} else {
246-
let prim = install_image(&mut flash, &self.areadesc, &slots[0],
247-
maximal(42784), &ram, &*dep, img_manipulation, Some(0), false);
246+
let prim = install_image(&mut flash, &self.areadesc, &slots, 0,
247+
maximal(42784), &ram, &*dep, img_manipulation, Some(0));
248248
let upgr = match deps.depends[image_num] {
249249
DepType::NoUpgrade => install_no_image(),
250-
_ => install_image(&mut flash, &self.areadesc, &slots[1],
251-
maximal(46928), &ram, &*dep, img_manipulation, Some(0), true)
250+
_ => install_image(&mut flash, &self.areadesc, &slots, 1,
251+
maximal(46928), &ram, &*dep, img_manipulation, Some(0))
252252
};
253253
(prim, upgr)
254254
};
@@ -298,10 +298,10 @@ impl ImagesBuilder {
298298
let ram = self.ram.clone(); // TODO: Avoid this clone.
299299
let images = self.slots.into_iter().enumerate().map(|(image_num, slots)| {
300300
let dep = BoringDep::new(image_num, &NO_DEPS);
301-
let primaries = install_image(&mut bad_flash, &self.areadesc, &slots[0],
302-
maximal(32784), &ram, &dep, ImageManipulation::None, Some(0), false);
303-
let upgrades = install_image(&mut bad_flash, &self.areadesc, &slots[1],
304-
maximal(41928), &ram, &dep, ImageManipulation::BadSignature, Some(0), true);
301+
let primaries = install_image(&mut bad_flash, &self.areadesc, &slots, 0,
302+
maximal(32784), &ram, &dep, ImageManipulation::None, Some(0));
303+
let upgrades = install_image(&mut bad_flash, &self.areadesc, &slots, 1,
304+
maximal(41928), &ram, &dep, ImageManipulation::BadSignature, Some(0));
305305
OneImage {
306306
slots,
307307
primaries,
@@ -321,10 +321,10 @@ impl ImagesBuilder {
321321
let ram = self.ram.clone(); // TODO: Avoid this clone.
322322
let images = self.slots.into_iter().enumerate().map(|(image_num, slots)| {
323323
let dep = BoringDep::new(image_num, &NO_DEPS);
324-
let primaries = install_image(&mut bad_flash, &self.areadesc, &slots[0],
325-
maximal(32784), &ram, &dep, ImageManipulation::None, Some(0), false);
326-
let upgrades = install_image(&mut bad_flash, &self.areadesc, &slots[1],
327-
ImageSize::Oversized, &ram, &dep, ImageManipulation::None, Some(0), true);
324+
let primaries = install_image(&mut bad_flash, &self.areadesc, &slots, 0,
325+
maximal(32784), &ram, &dep, ImageManipulation::None, Some(0));
326+
let upgrades = install_image(&mut bad_flash, &self.areadesc, &slots, 1,
327+
ImageSize::Oversized, &ram, &dep, ImageManipulation::None, Some(0));
328328
OneImage {
329329
slots,
330330
primaries,
@@ -344,8 +344,8 @@ impl ImagesBuilder {
344344
let ram = self.ram.clone(); // TODO: Avoid this clone.
345345
let images = self.slots.into_iter().enumerate().map(|(image_num, slots)| {
346346
let dep = BoringDep::new(image_num, &NO_DEPS);
347-
let primaries = install_image(&mut flash, &self.areadesc, &slots[0],
348-
maximal(32784), &ram, &dep,ImageManipulation::None, Some(0), false);
347+
let primaries = install_image(&mut flash, &self.areadesc, &slots, 0,
348+
maximal(32784), &ram, &dep,ImageManipulation::None, Some(0));
349349
let upgrades = install_no_image();
350350
OneImage {
351351
slots,
@@ -367,8 +367,8 @@ impl ImagesBuilder {
367367
let images = self.slots.into_iter().enumerate().map(|(image_num, slots)| {
368368
let dep = BoringDep::new(image_num, &NO_DEPS);
369369
let primaries = install_no_image();
370-
let upgrades = install_image(&mut flash, &self.areadesc, &slots[1],
371-
maximal(32784), &ram, &dep, ImageManipulation::None, Some(0), true);
370+
let upgrades = install_image(&mut flash, &self.areadesc, &slots, 1,
371+
maximal(32784), &ram, &dep, ImageManipulation::None, Some(0));
372372
OneImage {
373373
slots,
374374
primaries,
@@ -389,8 +389,8 @@ impl ImagesBuilder {
389389
let images = self.slots.into_iter().enumerate().map(|(image_num, slots)| {
390390
let dep = BoringDep::new(image_num, &NO_DEPS);
391391
let primaries = install_no_image();
392-
let upgrades = install_image(&mut flash, &self.areadesc, &slots[1],
393-
ImageSize::Oversized, &ram, &dep, ImageManipulation::None, Some(0), true);
392+
let upgrades = install_image(&mut flash, &self.areadesc, &slots, 1,
393+
ImageSize::Oversized, &ram, &dep, ImageManipulation::None, Some(0));
394394
OneImage {
395395
slots,
396396
primaries,
@@ -411,10 +411,10 @@ impl ImagesBuilder {
411411
let ram = self.ram.clone(); // TODO: Avoid this clone.
412412
let images = self.slots.into_iter().enumerate().map(|(image_num, slots)| {
413413
let dep = BoringDep::new(image_num, &NO_DEPS);
414-
let primaries = install_image(&mut flash, &self.areadesc, &slots[0],
415-
maximal(32784), &ram, &dep, ImageManipulation::None, security_cnt, false);
416-
let upgrades = install_image(&mut flash, &self.areadesc, &slots[1],
417-
maximal(41928), &ram, &dep, ImageManipulation::None, security_cnt.map(|v| v + 1), true);
414+
let primaries = install_image(&mut flash, &self.areadesc, &slots, 0,
415+
maximal(32784), &ram, &dep, ImageManipulation::None, security_cnt);
416+
let upgrades = install_image(&mut flash, &self.areadesc, &slots, 1,
417+
maximal(41928), &ram, &dep, ImageManipulation::None, security_cnt.map(|v| v + 1));
418418
OneImage {
419419
slots,
420420
primaries,
@@ -1819,19 +1819,52 @@ fn image_largest_trailer(dev: &dyn Flash, areadesc: &AreaDesc, slot: &SlotInfo)
18191819
trailer
18201820
}
18211821

1822+
// Computes the padding required in the primary or secondary slot to be able to perform an upgrade.
1823+
// This is needed only for the swap-move and swap-offset upgrade strategies.
1824+
fn required_slot_padding(dev: &dyn Flash) -> usize {
1825+
let mut required_padding = 0;
1826+
1827+
if Caps::SwapUsingMove.present() || Caps::SwapUsingOffset.present() {
1828+
// Assumes equally-sized sectors
1829+
let sector_size = dev.sector_iter().next().unwrap().size;
1830+
1831+
required_padding = sector_size;
1832+
};
1833+
1834+
required_padding
1835+
}
1836+
1837+
// Computes the largest possible firmware image size, not including the header and TLV area.
1838+
fn compute_largest_image_size(dev: &dyn Flash, areadesc: &AreaDesc, slots: &[SlotInfo],
1839+
slot_ind: usize, hdr_size: usize, tlv: &dyn ManifestGen) -> usize {
1840+
let slot_len = if Caps::SwapUsingOffset.present() {
1841+
slots[1].len
1842+
} else {
1843+
slots[0].len
1844+
};
1845+
1846+
let trailer = image_largest_trailer(dev, areadesc, &slots[slot_ind]);
1847+
let padding = required_slot_padding(dev);
1848+
let tlv_len = tlv.estimate_size();
1849+
info!("slot: 0x{:x}, HDR: 0x{:x}, trailer: 0x{:x}, tlv_len: 0x{:x}, padding: 0x{:x}",
1850+
slot_len, hdr_size, trailer, tlv_len, padding);
1851+
1852+
slot_len - hdr_size - trailer - tlv_len - padding
1853+
}
1854+
18221855
/// Install a "program" into the given image. This fakes the image header, or at least all of the
18231856
/// fields used by the given code. Returns a copy of the image that was written.
1824-
fn install_image(flash: &mut SimMultiFlash, areadesc: &AreaDesc, slot: &SlotInfo, len: ImageSize,
1825-
ram: &RamData,
1826-
deps: &dyn Depender, img_manipulation: ImageManipulation, security_counter:Option<u32>, secondary_slot:bool) -> ImageData {
1857+
fn install_image(flash: &mut SimMultiFlash, areadesc: &AreaDesc, slots: &[SlotInfo],
1858+
slot_ind: usize, len: ImageSize, ram: &RamData,
1859+
deps: &dyn Depender, img_manipulation: ImageManipulation, security_counter:Option<u32>) -> ImageData {
1860+
let slot = &slots[slot_ind];
18271861
let mut offset = slot.base_off;
1828-
let slot_len = slot.len;
18291862
let dev_id = slot.dev_id;
18301863
let dev = flash.get_mut(&dev_id).unwrap();
18311864

18321865
let mut tlv: Box<dyn ManifestGen> = Box::new(make_tlv());
18331866

1834-
if Caps::SwapUsingOffset.present() && secondary_slot {
1867+
if Caps::SwapUsingOffset.present() && slot_ind == 1 {
18351868
let sector_size = dev.sector_iter().next().unwrap().size as usize;
18361869
offset += sector_size;
18371870
}
@@ -1863,30 +1896,13 @@ fn install_image(flash: &mut SimMultiFlash, areadesc: &AreaDesc, slot: &SlotInfo
18631896

18641897
let len = match len {
18651898
ImageSize::Given(size) => size,
1866-
ImageSize::Largest => {
1867-
let trailer = image_largest_trailer(dev, &areadesc, &slot);
1868-
let tlv_len = tlv.estimate_size();
1869-
info!("slot: 0x{:x}, HDR: 0x{:x}, trailer: 0x{:x}",
1870-
slot_len, HDR_SIZE, trailer);
1871-
slot_len - HDR_SIZE - trailer - tlv_len
1872-
},
1899+
ImageSize::Largest => compute_largest_image_size(dev, areadesc, slots, slot_ind,
1900+
HDR_SIZE, tlv.as_ref()),
18731901
ImageSize::Oversized => {
1874-
let trailer = image_largest_trailer(dev, &areadesc, &slot);
1875-
let tlv_len = tlv.estimate_size();
1876-
let mut sector_offset = 0;
1877-
1878-
if Caps::SwapUsingOffset.present() && secondary_slot {
1879-
// This accounts for when both slots have the same size, it will not work where
1880-
// the second slot is one sector larger than the primary
1881-
sector_offset = dev.sector_iter().next().unwrap().size as usize;
1882-
}
1883-
1884-
info!("slot: 0x{:x}, HDR: 0x{:x}, trailer: 0x{:x}",
1885-
slot_len, HDR_SIZE, trailer);
1886-
1887-
slot_len - HDR_SIZE - trailer - tlv_len - sector_offset + dev.align()
1902+
let largest_img_sz = compute_largest_image_size(dev, areadesc, slots, slot_ind,
1903+
HDR_SIZE, tlv.as_ref());
1904+
largest_img_sz + dev.align()
18881905
}
1889-
18901906
};
18911907

18921908
// Generate a boot header. Note that the size doesn't include the header.
@@ -1995,7 +2011,7 @@ fn install_image(flash: &mut SimMultiFlash, areadesc: &AreaDesc, slot: &SlotInfo
19952011

19962012
enc_copy = Some(enc);
19972013

1998-
dev.erase(offset, slot_len).unwrap();
2014+
dev.erase(offset, slot.len).unwrap();
19992015
} else {
20002016
enc_copy = None;
20012017
}
@@ -2020,7 +2036,7 @@ fn install_image(flash: &mut SimMultiFlash, areadesc: &AreaDesc, slot: &SlotInfo
20202036
let enc_copy: Option<Vec<u8>>;
20212037

20222038
if is_encrypted {
2023-
dev.erase(offset, slot_len).unwrap();
2039+
dev.erase(offset, slot.len).unwrap();
20242040

20252041
dev.write(offset, &encbuf).unwrap();
20262042

0 commit comments

Comments
 (0)