@@ -629,7 +629,7 @@ boot_check_header_erased(struct boot_loader_state *state, int slot)
629629#if (BOOT_IMAGE_NUMBER > 1 ) || \
630630 defined(MCUBOOT_DIRECT_XIP ) || \
631631 defined(MCUBOOT_RAM_LOAD ) || \
632- ( defined(MCUBOOT_OVERWRITE_ONLY ) && defined( MCUBOOT_DOWNGRADE_PREVENTION ) )
632+ defined(MCUBOOT_DOWNGRADE_PREVENTION )
633633/**
634634 * Compare image version numbers not including the build number
635635 *
@@ -1438,6 +1438,8 @@ boot_swap_image(struct boot_loader_state *state, struct boot_status *bs)
14381438 boot_status_fails );
14391439 }
14401440#endif
1441+ rc = BOOT_HOOK_CALL (boot_copy_region_post_hook , 0 , BOOT_CURR_IMG (state ),
1442+ BOOT_IMG_AREA (state , BOOT_PRIMARY_SLOT ), size );
14411443
14421444 return 0 ;
14431445}
@@ -2012,6 +2014,60 @@ boot_update_hw_rollback_protection(struct boot_loader_state *state)
20122014#endif
20132015}
20142016
2017+ /**
2018+ * Checks test swap downgrade prevention conditions.
2019+ *
2020+ * Function called only for swap upgrades test run. It may prevent
2021+ * swap if slot 1 image has <= version number or < security counter
2022+ *
2023+ * @param state Boot loader status information.
2024+ *
2025+ * @return 0 - image can be swapped, -1 downgrade prevention
2026+ */
2027+ static int
2028+ check_downgrade_prevention (struct boot_loader_state * state )
2029+ {
2030+ #if defined(MCUBOOT_DOWNGRADE_PREVENTION ) && \
2031+ (defined(MCUBOOT_SWAP_USING_MOVE ) || defined(MCUBOOT_SWAP_USING_SCRATCH ))
2032+ uint32_t security_counter [2 ];
2033+ int rc ;
2034+
2035+ if (MCUBOOT_DOWNGRADE_PREVENTION_SECURITY_COUNTER ) {
2036+ /* If there was security no counter in slot 0, allow swap */
2037+ rc = bootutil_get_img_security_cnt (& (BOOT_IMG (state , 0 ).hdr ),
2038+ BOOT_IMG (state , 0 ).area ,
2039+ & security_counter [0 ]);
2040+ if (rc != 0 ) {
2041+ return 0 ;
2042+ }
2043+ /* If there is no security counter in slot 1, or it's lower than
2044+ * that of slot 0, prevent downgrade */
2045+ rc = bootutil_get_img_security_cnt (& (BOOT_IMG (state , 1 ).hdr ),
2046+ BOOT_IMG (state , 1 ).area ,
2047+ & security_counter [1 ]);
2048+ if (rc != 0 || security_counter [0 ] > security_counter [1 ]) {
2049+ rc = -1 ;
2050+ }
2051+ }
2052+ else {
2053+ rc = boot_version_cmp (& boot_img_hdr (state , BOOT_SECONDARY_SLOT )-> ih_ver ,
2054+ & boot_img_hdr (state , BOOT_PRIMARY_SLOT )-> ih_ver );
2055+ }
2056+ if (rc < 0 ) {
2057+ /* Image in slot 0 prevents downgrade, delete image in slot 1 */
2058+ BOOT_LOG_INF ("Image in slot 1 erased due to downgrade prevention" );
2059+ flash_area_erase (BOOT_IMG (state , 1 ).area , 0 ,
2060+ flash_area_get_size (BOOT_IMG (state , 1 ).area ));
2061+ } else {
2062+ rc = 0 ;
2063+ }
2064+ return rc ;
2065+ #else
2066+ (void )state ;
2067+ return 0 ;
2068+ #endif
2069+ }
2070+
20152071fih_int
20162072context_boot_go (struct boot_loader_state * state , struct boot_rsp * rsp )
20172073{
@@ -2140,7 +2196,13 @@ context_boot_go(struct boot_loader_state *state, struct boot_rsp *rsp)
21402196 case BOOT_SWAP_TYPE_NONE :
21412197 break ;
21422198
2143- case BOOT_SWAP_TYPE_TEST : /* fallthrough */
2199+ case BOOT_SWAP_TYPE_TEST :
2200+ if (check_downgrade_prevention (state ) != 0 ) {
2201+ /* Downgrade prevented */
2202+ BOOT_SWAP_TYPE (state ) = BOOT_SWAP_TYPE_NONE ;
2203+ break ;
2204+ }
2205+ /* fallthrough */
21442206 case BOOT_SWAP_TYPE_PERM : /* fallthrough */
21452207 case BOOT_SWAP_TYPE_REVERT :
21462208 rc = BOOT_HOOK_CALL (boot_perform_update_hook , BOOT_HOOK_REGULAR ,
0 commit comments