doc: design: rewrite state space in terms of "swap types"
The current "boot states" description doesn't make sense and shouldn't
be used.
For one thing, with three possible pending states, two possible
confirmed states, and two image slots each with a combined (pending,
confirmed) state, the total number of boot states is 36, but the
document says there are "four possible states".
For another, the actual bits on flash map to the "boot states" in a
way that is carefully designed to ensure that only those 4 are the
"outcome" of a boot.
The fact that this map does not cover the entire space of what is
being presented as the "logical" states of the device is a strong
indication that the pending/confirmed state space is a bad choice, not
connected with the actual operation of the bootloader.
A state space that is better for describing how the bootloader behaves
is given the by the enumeration of "swap types" which appear under
each of the tables in the "IMAGE TRAILERS" section, as well as the
bootloader code itself.
To help fix the description of the bootloader' operation, rewrite the
"boot states" portions of the design document, deleting the
pending/confirmed "states" and replacing them with swap types.
There is still more work to do here:
- There is still an "important caveat" to describing things in
terms of swap types, which means it's not quite right.
- It's strange to say that "none" is a swap type.
- This doesn't provide a clean explanation for how mcuboot handles an
interrupted swap.
But it's another step.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
diff --git a/doc/design.txt b/doc/design.txt
index f4f907e..8894304 100644
--- a/doc/design.txt
+++ b/doc/design.txt
@@ -141,78 +141,58 @@
rest of the document describes its behavior when configured to swap images
during an upgrade.
-*** BOOT STATES
+*** BOOT SWAP TYPES
-Logically, you can think of a pair of values associated with each image slot:
-pending and confirmed. On startup, the boot loader determines the state of the
-device by inspecting each pair of values. These values have the following
-meanings:
+When the device first boots under normal circumstances, there is an up-to-date
+firmware image in slot 0, which mcuboot can validate and then chain-load. In
+this case, no image swaps are necessary. During device upgrades, however, new
+candidate images are present in slot 1, which mcuboot must swap into slot 0
+before booting as discussed above.
-* pending: Indicates whether the image should be used on the next reboot; can
- hold one of three values:
- " " (unset): Don't use image on next boot
- "T" (temporary): Use image on next boot; absent subsequent confirm command,
- revert to original image on second reboot.
- "P" (permanent): Use image on next boot and all subsequent boots
+Upgrading an old image with a new one by swapping can be a two-step process. In
+this process, mcuboot performs a "test" swap of image data in flash and boots
+the new image. The new image can then update the contents of flash at runtime
+to mark itself "OK", and mcuboot will then still choose to run it during the
+next boot. When this happens, the swap is made "permanent". If this doesn't
+happen, mcuboot will perform a "revert" swap during the next boot by swapping
+the images back into their original locations, and attempting to boot the old
+image.
-* confirmed: always use image unless excluded by a test image.
+Depending on the use case, the first swap can also be made permanent directly.
+In this case, mcuboot will never attempt to revert the images on the next reset.
-In English, when the user wants to run the secondary image, they set the
-pending flag for the second slot and reboot the device. On startup, the boot
-loader will swap the two images in flash, clear the secondary slot's pending
-flag, and run the newly-copied image in slot 0. If the user set the pending
-flag to "temporary," then this is only a temporary state; if the device reboots
-again, the boot loader swaps the images back to their original slots and boots
-into the original image. If the user doesn't want to revert to the original
-state, they can make the current state permanent by setting the confirmed flag
-in slot 0.
+Test swaps are supported to provide a rollback mechanism to prevent devices
+from becoming "bricked" by bad firmware. If the device crashes immediately
+upon booting a new (bad) image, mcuboot will revert to the old (working) image
+at the next device reset, rather than booting the bad image again. This allows
+device firmware to make test swaps permanent only after performing a self-test
+routine.
-Switching to an alternate image is a two-step process (set + confirm) to
-prevent a device from becoming "bricked" by bad firmware. If the device
-crashes immediately upon booting the second image, the boot loader reverts to
-the working image, rather than repeatedly rebooting into the bad image.
+On startup, mcuboot inspects the contents of flash to decide which of these
+"swap types" to perform; this decision determines how it proceeds.
-Alternatively, if the user is confident that the second image is good, they can
-set and confirm in a single action by setting the pending flag to "permanent."
+The possible swap types, and their meanings, are:
-The following set of tables illustrate the four possible states that the device
-can be in:
+- BOOT_SWAP_TYPE_NONE: The "usual" or "no upgrade" case; attempt to boot the
+ contents of slot 0.
- | slot-0 | slot-1 |
- ---------------+--------+--------|
- pending | | |
- confirmed | X | |
- ---------------+--------+--------'
- Image 0 confirmed; |
- No change on reboot |
- ---------------------------------'
+- BOOT_SWAP_TYPE_TEST: Boot the contents of slot 1 by swapping images. Unless
+ the swap is made permanent, revert back on the next boot.
- | slot-0 | slot-1 |
- ---------------+--------+--------|
- pending | | T |
- confirmed | X | |
- ---------------+--------+--------'
- Image 0 confirmed; |
- Test image 1 on next reboot |
- ---------------------------------'
+- BOOT_SWAP_TYPE_PERM: Permanently swap images, and boot the upgraded image
+ firmware.
- | slot-0 | slot-1 |
- ---------------+--------+--------|
- pending | | P |
- confirmed | X | |
- ---------------+--------+--------'
- Image 0 confirmed; |
- Use image 1 permanently on boot |
- ---------------------------------'
+- BOOT_SWAP_TYPE_REVERT: A previous test swap was not made permanent; swap back
+ to the old image whose data are now in slot 1. If the old image marks itself
+ "OK" when it boots, the next boot will have swap type BOOT_SWAP_TYPE_NONE.
- | slot-0 | slot-1 |
- ---------------+--------+--------|
- pending | | |
- confirmed | | X |
- ---------------+--------+--------'
- Testing image 0; |
- Revert to image 1 on next reboot |
- ---------------------------------'
+- BOOT_SWAP_TYPE_FAIL: Swap failed because image to be run is not valid.
+
+- BOOT_SWAP_TYPE_PANIC: Swapping encountered an unrecoverable error.
+
+The "swap type" is a high-level representation of the outcome of the
+boot. Subsequent sections describe how mcuboot determines the swap type from
+the bit-level contents of flash.
*** IMAGE TRAILER
@@ -281,18 +261,15 @@
*** IMAGE TRAILERS
-At startup, the boot loader determines which of the above four states the
-device is in by inspecting the image trailers. When using the term "image
-trailers" what is meant is the aggregate information provided by both image
-slot's trailers.
+At startup, the boot loader determines the boot swap type by inspecting the
+image trailers. When using the term "image trailers" what is meant is the
+aggregate information provided by both image slot's trailers.
The image trailers records are structured around the limitations imposed by flash
hardware. As a consequence, they do not have a very intuitive design, and it
is difficult to get a sense of the state of the device just by looking at the
-image trailers. It is better to map all the possible trailer states to the four
-states described above via a set of tables. These tables are reproduced below.
-In these tables, the "pending" and "confirmed" flags are shown for illustrative
-purposes; they are not actually present in the image trailers.
+image trailers. It is better to map all the possible trailer states to the swap
+types described above via a set of tables. These tables are reproduced below.
Note: An important caveat about the tables described below is that they must
be evaluated in the order presented here. Lower state numbers must have a
@@ -306,10 +283,7 @@
image-ok | Any | Unset |
copy-done | Any | Any |
-----------------+--------+--------'
- pending | | T |
- confirmed | X | |
- -----------------+--------+--------'
- swap: test |
+ result: BOOT_SWAP_TYPE_TEST |
-----------------------------------'
@@ -320,10 +294,7 @@
image-ok | Any | 0x01 |
copy-done | Any | Any |
-----------------+--------+--------'
- pending | | P |
- confirmed | X | |
- -----------------+--------+--------'
- swap: permanent |
+ result: BOOT_SWAP_TYPE_PERM |
-----------------------------------'
@@ -334,17 +305,13 @@
image-ok | 0xff | Any |
copy-done | 0x01 | Any |
-----------------+--------+--------'
- pending | | |
- confirmed | | X |
- -----------------+--------+--------'
- swap: revert (test image running) |
+ result: BOOT_SWAP_TYPE_REVERT |
-----------------------------------'
+Any of the above three states results in mcuboot attempting to swap images.
-Those three states described above are explicity tested for and result in a
-swap decision by the bootloader. If the existing values in the the image trailers
-are not one of those previously described the bootloader will assume no swap
-operation is to be performed which is illustrated by state IV.
+Otherwise, mcuboot does not attempt to swap images, resulting in one of the
+other three swap types, as illustrated by State IV.
State IV
@@ -354,24 +321,22 @@
image-ok | Any | Any |
copy-done | Any | Any |
-----------------+--------+--------'
- pending | | |
- confirmed | X | |
- -----------------+--------+--------'
- swap: none |
+ result: BOOT_SWAP_TYPE_NONE, |
+ BOOT_SWAP_TYPE_FAIL, or |
+ BOOT_SWAP_TYPE_PANIC |
-----------------------------------'
+In State IV, when no errors occur, mcuboot will attempt to boot the contents of
+slot 0 directly, and the result is BOOT_SWAP_TYPE_NONE. If the image in slot 0
+is not valid, the result is BOOT_SWAP_TYPE_FAIL. If a fatal error occurs during
+boot, the result is BOOT_SWAP_TYPE_PANIC. If the result is either
+BOOT_SWAP_TYPE_FAIL or BOOT_SWAP_TYPE_PANIC, mcuboot hangs rather than booting
+an invalid or compromised image.
-Note: An important caveat to be mentioned here is, that due to the physical
-limitations of the storage and another possible failure, two extra "states"
-were added specifically to signal a failure in the boot process.
-
-1. One of them is a result of any device read/write error, called panic and
- will result in the bootloader hanging without booting the image in slot 0.
-
-2. Another state was added specifically to handle the situation in which a swap
- was requested and the image in slot 1 fails to validate, due to hashing
- or signing error. This state behaves as state IV with the extra action of
- marking the image in slot 0 as confirmed.
+Note: An important caveat to the above is the result when a swap is requested
+ and the image in slot 1 fails to validate, due to a hashing or signing
+ error. This state behaves as State IV with the extra action of marking
+ the image in slot 0 as "OK", to prevent further attempts to swap.
*** HIGH-LEVEL OPERATION