@@ -234,20 +234,20 @@ impl ImagesBuilder {
234
234
235
235
let ( primaries, upgrades) = if img_manipulation == ImageManipulation :: CorruptHigherVersionImage && !higher_version_corrupted {
236
236
higher_version_corrupted = true ;
237
- let prim = install_image ( & mut flash, & slots[ 0 ] ,
237
+ let prim = install_image ( & mut flash, & self . areadesc , & slots[ 0 ] ,
238
238
maximal ( 42784 ) , & ram, & * dep, ImageManipulation :: None , Some ( 0 ) , false ) ;
239
239
let upgr = match deps. depends [ image_num] {
240
240
DepType :: NoUpgrade => install_no_image ( ) ,
241
- _ => install_image ( & mut flash, & slots[ 1 ] ,
241
+ _ => install_image ( & mut flash, & self . areadesc , & slots[ 1 ] ,
242
242
maximal ( 46928 ) , & ram, & * dep, ImageManipulation :: BadSignature , Some ( 0 ) , true )
243
243
} ;
244
244
( prim, upgr)
245
245
} else {
246
- let prim = install_image ( & mut flash, & slots[ 0 ] ,
246
+ let prim = install_image ( & mut flash, & self . areadesc , & slots[ 0 ] ,
247
247
maximal ( 42784 ) , & ram, & * dep, img_manipulation, Some ( 0 ) , false ) ;
248
248
let upgr = match deps. depends [ image_num] {
249
249
DepType :: NoUpgrade => install_no_image ( ) ,
250
- _ => install_image ( & mut flash, & slots[ 1 ] ,
250
+ _ => install_image ( & mut flash, & self . areadesc , & slots[ 1 ] ,
251
251
maximal ( 46928 ) , & ram, & * dep, img_manipulation, Some ( 0 ) , true )
252
252
} ;
253
253
( prim, upgr)
@@ -298,9 +298,9 @@ impl ImagesBuilder {
298
298
let ram = self . ram . clone ( ) ; // TODO: Avoid this clone.
299
299
let images = self . slots . into_iter ( ) . enumerate ( ) . map ( |( image_num, slots) | {
300
300
let dep = BoringDep :: new ( image_num, & NO_DEPS ) ;
301
- let primaries = install_image ( & mut bad_flash, & slots[ 0 ] ,
301
+ let primaries = install_image ( & mut bad_flash, & self . areadesc , & slots[ 0 ] ,
302
302
maximal ( 32784 ) , & ram, & dep, ImageManipulation :: None , Some ( 0 ) , false ) ;
303
- let upgrades = install_image ( & mut bad_flash, & slots[ 1 ] ,
303
+ let upgrades = install_image ( & mut bad_flash, & self . areadesc , & slots[ 1 ] ,
304
304
maximal ( 41928 ) , & ram, & dep, ImageManipulation :: BadSignature , Some ( 0 ) , true ) ;
305
305
OneImage {
306
306
slots,
@@ -321,9 +321,9 @@ impl ImagesBuilder {
321
321
let ram = self . ram . clone ( ) ; // TODO: Avoid this clone.
322
322
let images = self . slots . into_iter ( ) . enumerate ( ) . map ( |( image_num, slots) | {
323
323
let dep = BoringDep :: new ( image_num, & NO_DEPS ) ;
324
- let primaries = install_image ( & mut bad_flash, & slots[ 0 ] ,
324
+ let primaries = install_image ( & mut bad_flash, & self . areadesc , & slots[ 0 ] ,
325
325
maximal ( 32784 ) , & ram, & dep, ImageManipulation :: None , Some ( 0 ) , false ) ;
326
- let upgrades = install_image ( & mut bad_flash, & slots[ 1 ] ,
326
+ let upgrades = install_image ( & mut bad_flash, & self . areadesc , & slots[ 1 ] ,
327
327
ImageSize :: Oversized , & ram, & dep, ImageManipulation :: None , Some ( 0 ) , true ) ;
328
328
OneImage {
329
329
slots,
@@ -344,7 +344,7 @@ impl ImagesBuilder {
344
344
let ram = self . ram . clone ( ) ; // TODO: Avoid this clone.
345
345
let images = self . slots . into_iter ( ) . enumerate ( ) . map ( |( image_num, slots) | {
346
346
let dep = BoringDep :: new ( image_num, & NO_DEPS ) ;
347
- let primaries = install_image ( & mut flash, & slots[ 0 ] ,
347
+ let primaries = install_image ( & mut flash, & self . areadesc , & slots[ 0 ] ,
348
348
maximal ( 32784 ) , & ram, & dep, ImageManipulation :: None , Some ( 0 ) , false ) ;
349
349
let upgrades = install_no_image ( ) ;
350
350
OneImage {
@@ -367,7 +367,7 @@ impl ImagesBuilder {
367
367
let images = self . slots . into_iter ( ) . enumerate ( ) . map ( |( image_num, slots) | {
368
368
let dep = BoringDep :: new ( image_num, & NO_DEPS ) ;
369
369
let primaries = install_no_image ( ) ;
370
- let upgrades = install_image ( & mut flash, & slots[ 1 ] ,
370
+ let upgrades = install_image ( & mut flash, & self . areadesc , & slots[ 1 ] ,
371
371
maximal ( 32784 ) , & ram, & dep, ImageManipulation :: None , Some ( 0 ) , true ) ;
372
372
OneImage {
373
373
slots,
@@ -389,7 +389,7 @@ impl ImagesBuilder {
389
389
let images = self . slots . into_iter ( ) . enumerate ( ) . map ( |( image_num, slots) | {
390
390
let dep = BoringDep :: new ( image_num, & NO_DEPS ) ;
391
391
let primaries = install_no_image ( ) ;
392
- let upgrades = install_image ( & mut flash, & slots[ 1 ] ,
392
+ let upgrades = install_image ( & mut flash, & self . areadesc , & slots[ 1 ] ,
393
393
ImageSize :: Oversized , & ram, & dep, ImageManipulation :: None , Some ( 0 ) , true ) ;
394
394
OneImage {
395
395
slots,
@@ -411,9 +411,9 @@ impl ImagesBuilder {
411
411
let ram = self . ram . clone ( ) ; // TODO: Avoid this clone.
412
412
let images = self . slots . into_iter ( ) . enumerate ( ) . map ( |( image_num, slots) | {
413
413
let dep = BoringDep :: new ( image_num, & NO_DEPS ) ;
414
- let primaries = install_image ( & mut flash, & slots[ 0 ] ,
414
+ let primaries = install_image ( & mut flash, & self . areadesc , & slots[ 0 ] ,
415
415
maximal ( 32784 ) , & ram, & dep, ImageManipulation :: None , security_cnt, false ) ;
416
- let upgrades = install_image ( & mut flash, & slots[ 1 ] ,
416
+ let upgrades = install_image ( & mut flash, & self . areadesc , & slots[ 1 ] ,
417
417
maximal ( 41928 ) , & ram, & dep, ImageManipulation :: None , security_cnt. map ( |v| v + 1 ) , true ) ;
418
418
OneImage {
419
419
slots,
@@ -1754,20 +1754,54 @@ enum ImageSize {
1754
1754
Oversized ,
1755
1755
}
1756
1756
1757
- #[ cfg( not( feature = "max-align-32" ) ) ]
1758
- fn tralier_estimation ( dev : & dyn Flash ) -> usize {
1759
- c:: boot_trailer_sz ( dev. align ( ) as u32 ) as usize
1760
- }
1757
+ /// Estimate the number of bytes in each slot that must be reserved for the trailer when
1758
+ /// swap-scratch is used.
1759
+ fn estimate_swap_scratch_trailer_size ( dev : & dyn Flash , areadesc : & AreaDesc , slot : & SlotInfo ) -> usize {
1760
+ // Compute the minimal size that must be allocated to the trailer, without considering the
1761
+ // trailer in the sratch area.
1762
+ let mut trailer_sz = c:: boot_trailer_sz ( dev. align ( ) as u32 ) as usize ;
1763
+
1764
+ // If the trailer is not a multiple of the sector size, the last sector that can hold firmware
1765
+ // data also contains the trailer or a part of it. Let's compute the size of the part of the
1766
+ // trailer that is in the last firmware sector.
1767
+ let mut trailer_sz_in_fw_sector = trailer_sz;
1768
+
1769
+ let flash_id = match slot. index {
1770
+ 0 => FlashId :: Image0 ,
1771
+ 1 => FlashId :: Image1 ,
1772
+ _ => panic ! ( "Invalid slot index" ) ,
1773
+ } ;
1761
1774
1762
- #[ cfg( feature = "max-align-32" ) ]
1763
- fn tralier_estimation ( dev : & dyn Flash ) -> usize {
1775
+ let slot_sectors = areadesc. get_area_sectors ( flash_id) . unwrap ( ) ;
1764
1776
1765
- let sector_size = dev. sector_iter ( ) . next ( ) . unwrap ( ) . size as u32 ;
1777
+ for sector in slot_sectors. iter ( ) . rev ( ) {
1778
+ let sector_sz = sector. size as usize ;
1779
+
1780
+ if sector_sz > trailer_sz_in_fw_sector {
1781
+ break ;
1782
+ }
1783
+
1784
+ trailer_sz_in_fw_sector -= sector_sz;
1785
+ }
1786
+
1787
+ // If the trailer is not a multiple of the sector size, when the last sector containing firmware
1788
+ // data will be copied to the scratch area, it must be ensured enough space is left to write the
1789
+ // scratch trailer.
1790
+ if trailer_sz_in_fw_sector != 0 {
1791
+ // The scratch contains a single boot status entry
1792
+ let boot_status_entry_sz = 3 * dev. align ( ) ;
1793
+ let trailer_info_sz = trailer_sz - c:: boot_status_sz ( dev. align ( ) as u32 ) as usize ;
1794
+ let scratch_trailer_sz = boot_status_entry_sz + trailer_info_sz;
1795
+
1796
+ if scratch_trailer_sz > trailer_sz_in_fw_sector {
1797
+ trailer_sz += scratch_trailer_sz - trailer_sz_in_fw_sector;
1798
+ }
1799
+ }
1766
1800
1767
- align_up ( c :: boot_trailer_sz ( dev . align ( ) as u32 ) , sector_size ) as usize
1801
+ trailer_sz
1768
1802
}
1769
1803
1770
- fn image_largest_trailer ( dev : & dyn Flash ) -> usize {
1804
+ fn image_largest_trailer ( dev : & dyn Flash , areadesc : & AreaDesc , slot : & SlotInfo ) -> usize {
1771
1805
// Using the header size we know, the trailer size, and the slot size, we can compute
1772
1806
// the largest image possible.
1773
1807
let trailer = if Caps :: OverwriteUpgrade . present ( ) {
@@ -1778,7 +1812,7 @@ fn image_largest_trailer(dev: &dyn Flash) -> usize {
1778
1812
let sector_size = dev. sector_iter ( ) . next ( ) . unwrap ( ) . size as u32 ;
1779
1813
align_up ( c:: boot_trailer_sz ( dev. align ( ) as u32 ) , sector_size) as usize
1780
1814
} else if Caps :: SwapUsingScratch . present ( ) {
1781
- tralier_estimation ( dev)
1815
+ estimate_swap_scratch_trailer_size ( dev, areadesc , slot )
1782
1816
} else {
1783
1817
panic ! ( "The maximum image size can't be calculated." )
1784
1818
} ;
@@ -1788,7 +1822,7 @@ fn image_largest_trailer(dev: &dyn Flash) -> usize {
1788
1822
1789
1823
/// Install a "program" into the given image. This fakes the image header, or at least all of the
1790
1824
/// fields used by the given code. Returns a copy of the image that was written.
1791
- fn install_image ( flash : & mut SimMultiFlash , slot : & SlotInfo , len : ImageSize ,
1825
+ fn install_image ( flash : & mut SimMultiFlash , areadesc : & AreaDesc , slot : & SlotInfo , len : ImageSize ,
1792
1826
ram : & RamData ,
1793
1827
deps : & dyn Depender , img_manipulation : ImageManipulation , security_counter : Option < u32 > , secondary_slot : bool ) -> ImageData {
1794
1828
let mut offset = slot. base_off ;
@@ -1831,14 +1865,14 @@ fn install_image(flash: &mut SimMultiFlash, slot: &SlotInfo, len: ImageSize,
1831
1865
let len = match len {
1832
1866
ImageSize :: Given ( size) => size,
1833
1867
ImageSize :: Largest => {
1834
- let trailer = image_largest_trailer ( dev) ;
1868
+ let trailer = image_largest_trailer ( dev, & areadesc , & slot ) ;
1835
1869
let tlv_len = tlv. estimate_size ( ) ;
1836
1870
info ! ( "slot: 0x{:x}, HDR: 0x{:x}, trailer: 0x{:x}" ,
1837
1871
slot_len, HDR_SIZE , trailer) ;
1838
1872
slot_len - HDR_SIZE - trailer - tlv_len
1839
1873
} ,
1840
1874
ImageSize :: Oversized => {
1841
- let trailer = image_largest_trailer ( dev) ;
1875
+ let trailer = image_largest_trailer ( dev, & areadesc , & slot ) ;
1842
1876
let tlv_len = tlv. estimate_size ( ) ;
1843
1877
let mut sector_offset = 0 ;
1844
1878
0 commit comments