From eadb0dbb1d07e7f54ec72abe08f3c95ce5765843 Mon Sep 17 00:00:00 2001 From: George Hotz Date: Tue, 10 Dec 2019 08:14:30 -0800 Subject: [PATCH] security upgrades (#397) * security upgrades * Gated DFU entry from debug console as well --- board/bootstub.c | 10 ++++++++++ board/main.c | 13 ++++++++----- board/spi_flasher.h | 5 +++++ crypto/sign.py | 6 ++++++ 4 files changed, 29 insertions(+), 5 deletions(-) diff --git a/board/bootstub.c b/board/bootstub.c index ac75c9c072ec5f..1521b5324030d0 100644 --- a/board/bootstub.c +++ b/board/bootstub.c @@ -1,5 +1,8 @@ #define BOOTSTUB +#define VERS_TAG 0x53524556 +#define MIN_VERSION 2 + #include "config.h" #include "obj/gitversion.h" @@ -90,6 +93,13 @@ int main(void) { uint8_t digest[SHA_DIGEST_SIZE]; SHA_hash(&_app_start[1], len-4, digest); + // verify version, last bytes in the signed area + uint32_t vers[2] = {0}; + memcpy(&vers, ((void*)&_app_start[0]) + len - sizeof(vers), sizeof(vers)); + if (vers[0] != VERS_TAG || vers[1] < MIN_VERSION) { + goto fail; + } + // verify RSA signature if (RSA_verify(&release_rsa_key, ((void*)&_app_start[0]) + len, RSANUMBYTES, digest, SHA_DIGEST_SIZE)) { goto good; diff --git a/board/main.c b/board/main.c index 2b6c78a94a82a7..dd4edb33d1e6c7 100644 --- a/board/main.c +++ b/board/main.c @@ -72,11 +72,14 @@ void debug_ring_callback(uart_ring *ring) { while (getc(ring, &rcv)) { (void)putc(ring, rcv); // misra-c2012-17.7: cast to void is ok: debug function - // jump to DFU flash - if (rcv == 'z') { - enter_bootloader_mode = ENTER_BOOTLOADER_MAGIC; - NVIC_SystemReset(); - } + // only allow bootloader entry on debug builds + #ifdef ALLOW_DEBUG + // jump to DFU flash + if (rcv == 'z') { + enter_bootloader_mode = ENTER_BOOTLOADER_MAGIC; + NVIC_SystemReset(); + } + #endif // normal reset if (rcv == 'x') { diff --git a/board/spi_flasher.h b/board/spi_flasher.h index 3fe15961c8cf9f..fbdbab8a61e0cf 100644 --- a/board/spi_flasher.h +++ b/board/spi_flasher.h @@ -65,7 +65,12 @@ int usb_cb_control_msg(USB_Setup_TypeDef *setup, uint8_t *resp, bool hardwired) // so it's blocked over wifi switch (setup->b.wValue.w) { case 0: + #ifdef ALLOW_DEBUG if (hardwired) { + #else + // no more bootstub on UNO + if (hardwired && hw_type != HW_TYPE_UNO) { + #endif puts("-> entering bootloader\n"); enter_bootloader_mode = ENTER_BOOTLOADER_MAGIC; NVIC_SystemReset(); diff --git a/crypto/sign.py b/crypto/sign.py index 0f1ce030815b6d..8cbe6f4195f1c6 100755 --- a/crypto/sign.py +++ b/crypto/sign.py @@ -6,6 +6,9 @@ from Crypto.PublicKey import RSA import binascii +# increment this to make new hardware not run old versions +VERSION = 2 + rsa = RSA.importKey(open(sys.argv[3]).read()) with open(sys.argv[1], "rb") as f: @@ -15,6 +18,9 @@ with open(sys.argv[2], "wb") as f: if os.getenv("SETLEN") is not None: + # add the version at the end + dat += b"VERS" + struct.pack("I", VERSION) + # add the length at the beginning x = struct.pack("I", len(dat)) + dat[4:] # mock signature of dat[4:] dd = hashlib.sha1(dat[4:]).digest()