The keyhash should be able to have any size up to the maximum allowed
size of 32, but the assert was not allowing images created with newt to
be accepted as valid (newt currently uses only 4 bytes for keyhash).
Signed-off-by: Fabio Utzig <utzig@apache.org>
Signed-off-by: David Brown <david.brown@linaro.org>
When starting a swap upgrade, the total size of data to be swapped is
calculated only at the beginning and saved to the trailer. This avoids
having to use complicated heuristics to find the total swap size, which
might depend on data that was already moved. When resuming a swap, the
size is found in the trailer and used.
Also includes some small comment fixes and refactors.
Signed-off-by: Fabio Utzig <utzig@apache.org>
Signed-off-by: David Brown <david.brown@linaro.org>
The local variable 'size' is actually the offset of the end, and not the
size. Rename it to reflect this reality.
Signed-off-by: David Brown <david.brown@linaro.org>
Clarify the name of the TLV field to more fully describe the signature
type.
Signed-off-by: Marko Kiiskila <marko@runtime.io>
Signed-off-by: David Brown <david.brown@linaro.org>
Since we are changing the image header format, there is no reason to
continue to support the old PKCS#1 v1.5 signatures. Remove the
definitions, and conditional complication related to this, and only
support the newer PSS signatures.
Signed-off-by: Marko Kiiskila <marko@runtime.io>
Signed-off-by: David Brown <david.brown@linaro.org>
Since we've changed the meaning of several fields in the header, bump
the header to a new magic number. The fields that are still present are
in the same place, but all of the signature and TLV information is moved
into the TLV itself, which is still immediately after the image.
As of this commit, this defines the new image header/TLV format used for
1.0.
Based on work by Marko Kiiskila <marko@runtime.io>
Signed-off-by: Marko Kiiskila <marko@runtime.io>
Signed-off-by: David Brown <david.brown@linaro.org>
To allow the signatures to be replaced, move the size of the TLV into a
small "info" header at the start of the TLV.
Note that this causes image swapping to lose robustness. This is fixed
by a later commit.
Based on work by Marko Kiiskila <marko@runtime.io>
Signed-off-by: Marko Kiiskila <marko@runtime.io>
Signed-off-by: David Brown <david.brown@linaro.org>
JIRA: MCUB-65
Remove the key_id field from the image header. There are two problems
with this field. First, it is only an integer offset, and so causes an
unnecessarily tight coupling between the particular keys built into the
bootloader, and the key that is used to sign. Second, it makes the
key_id part of the image header, which is included in the signature.
This makes it impossible to later sign the image with a different
signature.
Instead of the key-id, add a TLV KEYHASH entry. This will hold the
SHA256 of the public key that the signature is against. Each signature
placed in the TLV should be preceeded by this entry to indicate the
public key used.
The signature check will check each signature, and if the KEYHASH is
known and the signature type is supported, it will be checked. As long
as at least one signature is considered valid, the image will be
considered signed. This also allows the image to be signed with
multiple signatures to support having different devices with possibly
different keys compiled into the bootloaders.
Based on work by Marko Kiiskila <marko@runtime.io>
Signed-off-by: Marko Kiiskila <marko@runtime.io>
Signed-off-by: David Brown <david.brown@linaro.org>
In preparation for moving the signature related values out of the main
image header and into the TLV, renumber the existing TLV values to be
grouped together better.
The SHA256 is moved into the first group, at 0x10, and the signature
values themselves are moved to start with 0x20.
This change is the first in a series of changes toward the new v1.0
image format. The intermediate results are all internally consistent
(meaning that the simulator, and the builtin imgtool.py will all work
together), but until all patches are applied, the image format is not
valid with any external tools.
Based on work by Marko Kiiskila <marko@runtime.io>.
Signed-off-by: Marko Kiiskila <marko@runtime.io>
Signed-off-by: David Brown <david.brown@linaro.org>
The comment for BOOT_SWAP_TYPE_NONE says "Just boot whatever is in
slot 0". That's not correct: if configured to do so (and this the
strongly recommended configuration), mcuboot will first
cryptographically validate the contents of slot 0 before booting it.
Fix the comment to be more accurate.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Adjust alignment and add missing leading zero to
IMAGE_F_PKCS1_PSS_RSA2048_SHA256. This needed some comment changes to
keep things 80 column clean.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
This enables mynewt to use mcuboot as a remote repository, which is only
required when using newtmgr to manage images. Since mcuboot has slightly
changed the trailer format, newtmgr built against the bundled mynewt
bootloader writes the magic and flags to the wrong location.
To build a mynewt app the wants to run with mcuboot as the bootloader
and requires newtmgr one needs to change the app's pkg.yml dependencies
as follows:
- - boot/bootutil
+ - "@mcuboot/boot/bootutil"
Signed-off-by: Fabio Utzig <utzig@apache.org>
When image is slot 1 had bad signature, the swap would fail and
try to write image_ok in slot 0 which if that was already a
permanent image would cause a overwrite in flash.
Fix warning/error when slot 0 validation is not enabled.
Signed-off-by: Fabio Utzig <utzig@apache.org>
After a swap operation is finished trailer control flags are written
according to the type of swap that was performed. The function names
that execute those operations were renamed to explicity reflect what
they do, and all "less deterministic" behaviors, of the type
"if flash is not set, set it", were removed.
Signed-off-by: Fabio Utzig <utzig@apache.org>
This adds handling of the copy_done bit while evaluation a swap state.
Since copy_done is only ever written when a swap finishes, it can be
safely assumed that if copy_done is not set no swap was ever performed
and the image was written directly to flash, and thus no revert is run.
Signed-off-by: Fabio Utzig <utzig@apache.org>
This reworks much of the code, as well as tables, handling swap
state to make them simpler. Only states that require an actual
swap to be performed, perm/test/revert are checked for and acted
upon. Other possible states try to default to no operation
performed.
One extra state, BOOT_SWAP_TYPE_PANIC, was added to differentiate
between "soft" errors and unrecoverable ones (as flash read/write
errors).
Non well defined state changes after swap failures, as described
in MCUB-59 were also clean up.
This should also fix situations as described in MCUB-63, where
images generated using imgtool (magic + image_ok set) are written
to slot 0 and cause an incorrect "revert".
Signed-off-by: Fabio Utzig <utzig@apache.org>
The MCUBOOT_VALIDATE_SLOT0 feature only verifies the signature when
there is no swapping happening. The assumption was that if there is a
swap being done, the code will verify the signature of slot 1 before
doing the slot.
However, either due to bugs, or intentional trickery, it may be possible
to confuse the code into continuing a swap operation. If the data is
modified before this, the bootloader can be tricked into booting the
resulting image in slot 0 without having verified the signature.
Fix this by always verifying slot 0's signature before booting it.
JIRA: MCUB-64
Signed-off-by: David Brown <david.brown@linaro.org>
This implements changes according to MCUB-14, easing the process
of making external apps parse and read/write the trailer.
Signed-off-by: Fabio Utzig <utzig@apache.org>
For mynewt flash map only accepts values for slot 0 and 1. This
code was trying to read the image header on the scratch area using
the same interface and was segfaulting when slot0 and slot1 had
similarly sized images.
Signed-off-by: Fabio Utzig <utzig@apache.org>
This error was catched by Coverity and it happens when a fail occurs
opening a flash map handle, which is not checked by the close
routine.
Right now this only affects Zephyr, but extra checking was added
assuming that in a future Mynewt implementation close could actually
be changed to do something.
Signed-off-by: Fabio Utzig <utzig@apache.org>
Use flash_device_base() in the boot code to compute a real address,
given the offset returned by boot_go().
Provide an implementation on mynewt that preserves existing
behavior. If mynewt needs to support devices with nonzero flash base
addresses, this can be migrated to the core OS.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Similarly, it's confusing whether br_flash_id is a flash device ID or
a flash area ID. Make this unambiguous.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
The boot response returns a flash offset, not a flash address. This is
causing confusion and leading to crashes on some platforms which don't
have flash at address 0.
Rename the field to make it more clear what its purpose is; future
patches can start fixing up usages.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Add a typedef which lets us use flash_sector or flash_area to contain
the sectors within the boot_data global. When
MCUBOOT_USE_FLASH_AREA_GET_SECTORS is defined, this is struct
flash_sector.
Also add struct boot_loader_state accessors to handle this case, and
make the appropriate changes to where the sectors are allocated to use
the new typedef.
Finally, ensure MCUBOOT_USE_FLASH_AREA_GET_SECTORS is defined in the
Zephyr Makefile, since flash_area_get_sectors() is already provided
there.
This lets mcuboot users convert to the new flash API gradually.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Move helpers which are needed for using flash_area_to_sectors() to the
end of file. This is just to keep things clean when we add support for
flash_area_get_sectors().
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Keep both image areas and the scratch area open while we are
bootloading. This fixes up a hack and will make it easier to use
flash_area_get_sectors() later.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Add abstractions for calculating the starting offset of a sector from
the beginning of its image, and the starting offset of an image slot
from the beginning of its flash device.
Using this tweaks a check in boot_swap_sectors(), but doesn't change
its outcome.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Add an abstraction for initializing bootloader state for a particular
flash area.
For now, we preserve some existing hacky behavior related to the
scratch area. This will get cleaned up more later in the series.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Taking the opportunity to move some signed integers over to unsigned
size_t as we go. (Depending on compiler settings, signed / unsigned
comparisons can generate warnings, so it's nice to use the signedness
we mean when possible).
Having boot_img_set_num_sectors() is just an intermediate step; this
gets cleaned up as we go forward.
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
This begins some preparatory work to using flash_area_get_sectors() in
loader.c. Subsequent commits will add and use additional accessors for
the contents of this struct.
Making the struct contents opaque will allow it to contain struct
flash_area or struct flash_sector values in its sectors field. This
will allow use of either flash_area_get_sectors() or the
now-deprecated flash_area_to_sectors().
Signed-off-by: Marti Bolivar <marti.bolivar@linaro.org>
Allow the size of bignums in mbed TLS to be configured larger than
needed for RSA2048. This will waste memory holding the large numbers,
but will still work.
The PKCS#1 standards, which define RSA signatures, are currently at
version 2.2. Starting in v2.1, the standard defines a new signature
method RSA-PSS, which has a stronger security proof than the signature
method used in earlier versions. The standard recommends that RSA-PSS
be used in new designs, instead of the older algorithm.
This patch implements RSA-PSS verification for a specific set of
parameters:
- RSA-2048
- SHA256 for both the message digest and the internal hash
- 32-byte salt
- 2047 bit message
Although RSA-PSS supports other parameters, due to size constraints,
this verificatino code only supports these specific parameters, and
signatures with other parameters will be considered invalid.
To encourage the use of the more secure algorithm, the default build
configuration is RSA-PSS. BOOTUTIL_RSA_PKCS1_15 needs to be defined in
order to support the older signature algorithm.