From a5d112167500ce3bdc796ca488330398b35a7e76 Mon Sep 17 00:00:00 2001 From: Gregor Haas Date: Thu, 27 Feb 2020 14:08:53 -0500 Subject: [PATCH] lots of changes, some project restructuring and a new experiment --- c8_remote/CMakeLists.txt | 3 +- c8_remote/include/bootrom_type.h | 11 ++ c8_remote/include/crypto_host.h | 14 ++ c8_remote/include/experiments.h | 3 + c8_remote/include/payload.h | 3 +- c8_remote/lib/CMakeLists.txt | 9 +- c8_remote/lib/crypto/aes_sw_host.c | 78 ++++++++ .../src/aes_sw.c => crypto/aes_sw_impl.c} | 88 --------- c8_remote/lib/experiments/aes_sw.c | 178 +++++++++++------- c8_remote/lib/payload/CMakeLists.txt | 11 +- c8_remote/lib/payload/include/crypto_dev.h | 13 ++ c8_remote/lib/payload/src/aes_sw_bern.c | 83 ++++++++ c8_remote/lib/payload/src/aes_sw_corr.c | 54 ++++++ c8_remote/main.c | 82 ++++++-- c8_remote/src/payload.c | 11 +- 15 files changed, 455 insertions(+), 186 deletions(-) create mode 100644 c8_remote/include/crypto_host.h create mode 100644 c8_remote/lib/crypto/aes_sw_host.c rename c8_remote/lib/{payload/src/aes_sw.c => crypto/aes_sw_impl.c} (58%) create mode 100644 c8_remote/lib/payload/include/crypto_dev.h create mode 100644 c8_remote/lib/payload/src/aes_sw_bern.c create mode 100644 c8_remote/lib/payload/src/aes_sw_corr.c diff --git a/c8_remote/CMakeLists.txt b/c8_remote/CMakeLists.txt index 6e72146..62a6b47 100644 --- a/c8_remote/CMakeLists.txt +++ b/c8_remote/CMakeLists.txt @@ -7,4 +7,5 @@ set(CMAKE_C_FLAGS "-g -Wall") include_directories(include) add_executable(checkm8_remote main.c src/usb_helpers.c src/exploit.c src/payload.c src/command.c) -target_link_libraries(checkm8_remote usb-1.0 pthread udev m payload experiments) \ No newline at end of file +target_link_libraries(checkm8_remote usb-1.0 pthread udev m) +target_link_libraries(checkm8_remote payload experiments crypto_host) \ No newline at end of file diff --git a/c8_remote/include/bootrom_type.h b/c8_remote/include/bootrom_type.h index a0770f1..7bbf3dc 100644 --- a/c8_remote/include/bootrom_type.h +++ b/c8_remote/include/bootrom_type.h @@ -30,4 +30,15 @@ struct bern_data struct event ev_done; } __attribute__ ((packed)); +#define N_CORR_ENTRIES 1024*256 + +struct corr_data +{ + struct event ev_cont; + + int num_cutoff; + unsigned char msg[16]; + unsigned char data[N_CORR_ENTRIES]; +}; + #endif //CHECKM8_TOOL_BOOTROM_TYPE_H diff --git a/c8_remote/include/crypto_host.h b/c8_remote/include/crypto_host.h new file mode 100644 index 0000000..a167f82 --- /dev/null +++ b/c8_remote/include/crypto_host.h @@ -0,0 +1,14 @@ +#ifndef CHECKM8_TOOL_CRYPTO_HOST_H +#define CHECKM8_TOOL_CRYPTO_HOST_H + +#include "bootrom_type.h" + +void expand_key(unsigned char key[16], unsigned char key_sched[176], + int n, struct aes_constants *c); + +void aes128_encrypt_ecb(unsigned char *msg, unsigned int msg_len, + unsigned char key_sched[176], struct aes_constants *c); + +struct aes_constants *get_constants(); + +#endif //CHECKM8_TOOL_CRYPTO_HOST_H diff --git a/c8_remote/include/experiments.h b/c8_remote/include/experiments.h index a542776..72e206a 100644 --- a/c8_remote/include/experiments.h +++ b/c8_remote/include/experiments.h @@ -8,6 +8,9 @@ DEV_PTR_T setup_bern_exp(struct pwned_device *dev); struct bern_data *get_bern_exp_data(struct pwned_device *dev, DEV_PTR_T async_buf); +DEV_PTR_T setup_corr_exp(struct pwned_device *dev, unsigned char *init_key); +struct corr_data *get_corr_exp_data(struct pwned_device *dev, DEV_PTR_T async_buf); + /* System */ void usb_task_exit(struct pwned_device *dev); diff --git a/c8_remote/include/payload.h b/c8_remote/include/payload.h index a18046e..09d2b1b 100644 --- a/c8_remote/include/payload.h +++ b/c8_remote/include/payload.h @@ -6,7 +6,8 @@ typedef enum { PAYLOAD_AES_BUSY, - PAYLOAD_AES_SW, + PAYLOAD_AES_SW_BERN, + PAYLOAD_AES_SW_CORR, PAYLOAD_CACHELIB, PAYLOAD_EXIT_USB_TASK, PAYLOAD_FLOPPYSLEEP, diff --git a/c8_remote/lib/CMakeLists.txt b/c8_remote/lib/CMakeLists.txt index 85aad8c..7b9100f 100644 --- a/c8_remote/lib/CMakeLists.txt +++ b/c8_remote/lib/CMakeLists.txt @@ -1,6 +1,7 @@ set(PL_NAMES aes_busy - aes_sw + aes_sw_bern + aes_sw_corr cachelib exit_usb_task floppysleep @@ -17,6 +18,7 @@ foreach(TARGET ${PL_TARGETS}) list(APPEND PL_BIN "${CMAKE_CURRENT_BINARY_DIR}/payload/bin/${TARGET}.bin") endforeach(TARGET) +set(CMAKE_C_FLAGS "-g -Wall") add_subdirectory(${CMAKE_CURRENT_LIST_DIR}/payload) file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/lib_cfiles) @@ -37,4 +39,7 @@ add_custom_command(TARGET payload POST_BUILD ${CMAKE_CURRENT_BINARY_DIR}/lib_cfiles ${CMAKE_SOURCE_DIR}/c8_remote/include) -add_library(experiments experiments/aes_sw.c experiments/system.c experiments/power.c) \ No newline at end of file +add_library(experiments experiments/aes_sw.c + experiments/system.c + experiments/power.c) +add_library(crypto_host crypto/aes_sw_impl.c crypto/aes_sw_host.c) \ No newline at end of file diff --git a/c8_remote/lib/crypto/aes_sw_host.c b/c8_remote/lib/crypto/aes_sw_host.c new file mode 100644 index 0000000..4caa57e --- /dev/null +++ b/c8_remote/lib/crypto/aes_sw_host.c @@ -0,0 +1,78 @@ +#include +#include + +#include "bootrom_type.h" + +static const unsigned char sbox[256] = + { + 0x63, 0x7c, 0x77, 0x7b, 0xf2, 0x6b, 0x6f, 0xc5, 0x30, 0x01, 0x67, 0x2b, 0xfe, 0xd7, 0xab, 0x76, + 0xca, 0x82, 0xc9, 0x7d, 0xfa, 0x59, 0x47, 0xf0, 0xad, 0xd4, 0xa2, 0xaf, 0x9c, 0xa4, 0x72, 0xc0, + 0xb7, 0xfd, 0x93, 0x26, 0x36, 0x3f, 0xf7, 0xcc, 0x34, 0xa5, 0xe5, 0xf1, 0x71, 0xd8, 0x31, 0x15, + 0x04, 0xc7, 0x23, 0xc3, 0x18, 0x96, 0x05, 0x9a, 0x07, 0x12, 0x80, 0xe2, 0xeb, 0x27, 0xb2, 0x75, + 0x09, 0x83, 0x2c, 0x1a, 0x1b, 0x6e, 0x5a, 0xa0, 0x52, 0x3b, 0xd6, 0xb3, 0x29, 0xe3, 0x2f, 0x84, + 0x53, 0xd1, 0x00, 0xed, 0x20, 0xfc, 0xb1, 0x5b, 0x6a, 0xcb, 0xbe, 0x39, 0x4a, 0x4c, 0x58, 0xcf, + 0xd0, 0xef, 0xaa, 0xfb, 0x43, 0x4d, 0x33, 0x85, 0x45, 0xf9, 0x02, 0x7f, 0x50, 0x3c, 0x9f, 0xa8, + 0x51, 0xa3, 0x40, 0x8f, 0x92, 0x9d, 0x38, 0xf5, 0xbc, 0xb6, 0xda, 0x21, 0x10, 0xff, 0xf3, 0xd2, + 0xcd, 0x0c, 0x13, 0xec, 0x5f, 0x97, 0x44, 0x17, 0xc4, 0xa7, 0x7e, 0x3d, 0x64, 0x5d, 0x19, 0x73, + 0x60, 0x81, 0x4f, 0xdc, 0x22, 0x2a, 0x90, 0x88, 0x46, 0xee, 0xb8, 0x14, 0xde, 0x5e, 0x0b, 0xdb, + 0xe0, 0x32, 0x3a, 0x0a, 0x49, 0x06, 0x24, 0x5c, 0xc2, 0xd3, 0xac, 0x62, 0x91, 0x95, 0xe4, 0x79, + 0xe7, 0xc8, 0x37, 0x6d, 0x8d, 0xd5, 0x4e, 0xa9, 0x6c, 0x56, 0xf4, 0xea, 0x65, 0x7a, 0xae, 0x08, + 0xba, 0x78, 0x25, 0x2e, 0x1c, 0xa6, 0xb4, 0xc6, 0xe8, 0xdd, 0x74, 0x1f, 0x4b, 0xbd, 0x8b, 0x8a, + 0x70, 0x3e, 0xb5, 0x66, 0x48, 0x03, 0xf6, 0x0e, 0x61, 0x35, 0x57, 0xb9, 0x86, 0xc1, 0x1d, 0x9e, + 0xe1, 0xf8, 0x98, 0x11, 0x69, 0xd9, 0x8e, 0x94, 0x9b, 0x1e, 0x87, 0xe9, 0xce, 0x55, 0x28, 0xdf, + 0x8c, 0xa1, 0x89, 0x0d, 0xbf, 0xe6, 0x42, 0x68, 0x41, 0x99, 0x2d, 0x0f, 0xb0, 0x54, 0xbb, 0x16 + }; + +static const unsigned char rc_lookup[11] = {0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80, 0x1b, 0x36, 0x6c}; + +static const unsigned char mul2_lookup[256] = + { + 0x00, 0x02, 0x04, 0x06, 0x08, 0x0a, 0x0c, 0x0e, 0x10, 0x12, 0x14, 0x16, 0x18, 0x1a, 0x1c, 0x1e, + 0x20, 0x22, 0x24, 0x26, 0x28, 0x2a, 0x2c, 0x2e, 0x30, 0x32, 0x34, 0x36, 0x38, 0x3a, 0x3c, 0x3e, + 0x40, 0x42, 0x44, 0x46, 0x48, 0x4a, 0x4c, 0x4e, 0x50, 0x52, 0x54, 0x56, 0x58, 0x5a, 0x5c, 0x5e, + 0x60, 0x62, 0x64, 0x66, 0x68, 0x6a, 0x6c, 0x6e, 0x70, 0x72, 0x74, 0x76, 0x78, 0x7a, 0x7c, 0x7e, + 0x80, 0x82, 0x84, 0x86, 0x88, 0x8a, 0x8c, 0x8e, 0x90, 0x92, 0x94, 0x96, 0x98, 0x9a, 0x9c, 0x9e, + 0xa0, 0xa2, 0xa4, 0xa6, 0xa8, 0xaa, 0xac, 0xae, 0xb0, 0xb2, 0xb4, 0xb6, 0xb8, 0xba, 0xbc, 0xbe, + 0xc0, 0xc2, 0xc4, 0xc6, 0xc8, 0xca, 0xcc, 0xce, 0xd0, 0xd2, 0xd4, 0xd6, 0xd8, 0xda, 0xdc, 0xde, + 0xe0, 0xe2, 0xe4, 0xe6, 0xe8, 0xea, 0xec, 0xee, 0xf0, 0xf2, 0xf4, 0xf6, 0xf8, 0xfa, 0xfc, 0xfe, + 0x1b, 0x19, 0x1f, 0x1d, 0x13, 0x11, 0x17, 0x15, 0x0b, 0x09, 0x0f, 0x0d, 0x03, 0x01, 0x07, 0x05, + 0x3b, 0x39, 0x3f, 0x3d, 0x33, 0x31, 0x37, 0x35, 0x2b, 0x29, 0x2f, 0x2d, 0x23, 0x21, 0x27, 0x25, + 0x5b, 0x59, 0x5f, 0x5d, 0x53, 0x51, 0x57, 0x55, 0x4b, 0x49, 0x4f, 0x4d, 0x43, 0x41, 0x47, 0x45, + 0x7b, 0x79, 0x7f, 0x7d, 0x73, 0x71, 0x77, 0x75, 0x6b, 0x69, 0x6f, 0x6d, 0x63, 0x61, 0x67, 0x65, + 0x9b, 0x99, 0x9f, 0x9d, 0x93, 0x91, 0x97, 0x95, 0x8b, 0x89, 0x8f, 0x8d, 0x83, 0x81, 0x87, 0x85, + 0xbb, 0xb9, 0xbf, 0xbd, 0xb3, 0xb1, 0xb7, 0xb5, 0xab, 0xa9, 0xaf, 0xad, 0xa3, 0xa1, 0xa7, 0xa5, + 0xdb, 0xd9, 0xdf, 0xdd, 0xd3, 0xd1, 0xd7, 0xd5, 0xcb, 0xc9, 0xcf, 0xcd, 0xc3, 0xc1, 0xc7, 0xc5, + 0xfb, 0xf9, 0xff, 0xfd, 0xf3, 0xf1, 0xf7, 0xf5, 0xeb, 0xe9, 0xef, 0xed, 0xe3, 0xe1, 0xe7, 0xe5 + }; + +static const unsigned char mul3_lookup[256] = + { + 0x00, 0x03, 0x06, 0x05, 0x0c, 0x0f, 0x0a, 0x09, 0x18, 0x1b, 0x1e, 0x1d, 0x14, 0x17, 0x12, 0x11, + 0x30, 0x33, 0x36, 0x35, 0x3c, 0x3f, 0x3a, 0x39, 0x28, 0x2b, 0x2e, 0x2d, 0x24, 0x27, 0x22, 0x21, + 0x60, 0x63, 0x66, 0x65, 0x6c, 0x6f, 0x6a, 0x69, 0x78, 0x7b, 0x7e, 0x7d, 0x74, 0x77, 0x72, 0x71, + 0x50, 0x53, 0x56, 0x55, 0x5c, 0x5f, 0x5a, 0x59, 0x48, 0x4b, 0x4e, 0x4d, 0x44, 0x47, 0x42, 0x41, + 0xc0, 0xc3, 0xc6, 0xc5, 0xcc, 0xcf, 0xca, 0xc9, 0xd8, 0xdb, 0xde, 0xdd, 0xd4, 0xd7, 0xd2, 0xd1, + 0xf0, 0xf3, 0xf6, 0xf5, 0xfc, 0xff, 0xfa, 0xf9, 0xe8, 0xeb, 0xee, 0xed, 0xe4, 0xe7, 0xe2, 0xe1, + 0xa0, 0xa3, 0xa6, 0xa5, 0xac, 0xaf, 0xaa, 0xa9, 0xb8, 0xbb, 0xbe, 0xbd, 0xb4, 0xb7, 0xb2, 0xb1, + 0x90, 0x93, 0x96, 0x95, 0x9c, 0x9f, 0x9a, 0x99, 0x88, 0x8b, 0x8e, 0x8d, 0x84, 0x87, 0x82, 0x81, + 0x9b, 0x98, 0x9d, 0x9e, 0x97, 0x94, 0x91, 0x92, 0x83, 0x80, 0x85, 0x86, 0x8f, 0x8c, 0x89, 0x8a, + 0xab, 0xa8, 0xad, 0xae, 0xa7, 0xa4, 0xa1, 0xa2, 0xb3, 0xb0, 0xb5, 0xb6, 0xbf, 0xbc, 0xb9, 0xba, + 0xfb, 0xf8, 0xfd, 0xfe, 0xf7, 0xf4, 0xf1, 0xf2, 0xe3, 0xe0, 0xe5, 0xe6, 0xef, 0xec, 0xe9, 0xea, + 0xcb, 0xc8, 0xcd, 0xce, 0xc7, 0xc4, 0xc1, 0xc2, 0xd3, 0xd0, 0xd5, 0xd6, 0xdf, 0xdc, 0xd9, 0xda, + 0x5b, 0x58, 0x5d, 0x5e, 0x57, 0x54, 0x51, 0x52, 0x43, 0x40, 0x45, 0x46, 0x4f, 0x4c, 0x49, 0x4a, + 0x6b, 0x68, 0x6d, 0x6e, 0x67, 0x64, 0x61, 0x62, 0x73, 0x70, 0x75, 0x76, 0x7f, 0x7c, 0x79, 0x7a, + 0x3b, 0x38, 0x3d, 0x3e, 0x37, 0x34, 0x31, 0x32, 0x23, 0x20, 0x25, 0x26, 0x2f, 0x2c, 0x29, 0x2a, + 0x0b, 0x08, 0x0d, 0x0e, 0x07, 0x04, 0x01, 0x02, 0x13, 0x10, 0x15, 0x16, 0x1f, 0x1c, 0x19, 0x1a + }; + +struct aes_constants *get_constants() +{ + struct aes_constants *res = malloc(sizeof(struct aes_constants)); + + memcpy(res->sbox, sbox, sizeof(sbox)); + memcpy(res->rc_lookup, rc_lookup, sizeof(rc_lookup)); + memcpy(res->mul2, mul2_lookup, sizeof(mul2_lookup)); + memcpy(res->mul3, mul3_lookup, sizeof(mul3_lookup)); + + return res; +} \ No newline at end of file diff --git a/c8_remote/lib/payload/src/aes_sw.c b/c8_remote/lib/crypto/aes_sw_impl.c similarity index 58% rename from c8_remote/lib/payload/src/aes_sw.c rename to c8_remote/lib/crypto/aes_sw_impl.c index 3fc2bb7..5eed39b 100644 --- a/c8_remote/lib/payload/src/aes_sw.c +++ b/c8_remote/lib/crypto/aes_sw_impl.c @@ -1,8 +1,5 @@ -#include "bootrom_func.h" #include "bootrom_type.h" -#include "cacheutil.h" -PAYLOAD_SECTION void sub_bytes(unsigned char block[16], struct aes_constants *c) { int i; @@ -15,7 +12,6 @@ void sub_bytes(unsigned char block[16], struct aes_constants *c) } } -PAYLOAD_SECTION void shift_rows(unsigned char block[16]) { unsigned char temp1, temp2; @@ -40,7 +36,6 @@ void shift_rows(unsigned char block[16]) block[0x7] = temp1; } -PAYLOAD_SECTION void mix_cols(unsigned char block[16], struct aes_constants *c) { unsigned char r0, r1, r2, r3; @@ -61,7 +56,6 @@ void mix_cols(unsigned char block[16], struct aes_constants *c) } } -PAYLOAD_SECTION void add_key(unsigned char block[16], unsigned char key[16]) { int i; @@ -71,7 +65,6 @@ void add_key(unsigned char block[16], unsigned char key[16]) } } -PAYLOAD_SECTION void expand_key(unsigned char key[16], unsigned char key_sched[176], int n, struct aes_constants *c) { @@ -110,7 +103,6 @@ void expand_key(unsigned char key[16], unsigned char key_sched[176], int n, } } -PAYLOAD_SECTION void aes128_encrypt_ecb(unsigned char *msg, unsigned int msg_len, unsigned char key_sched[176], struct aes_constants *c) { @@ -135,84 +127,4 @@ void aes128_encrypt_ecb(unsigned char *msg, unsigned int msg_len, shift_rows(block); add_key(block, &key_sched[16 * (j + 1)]); } -} - -PAYLOAD_SECTION -uint64_t entry_sync(unsigned char *msg, unsigned int msg_len, unsigned char key[16], - struct aes_constants *c) -{ - unsigned long long start = 0; - unsigned char key_sched[176]; - expand_key(key, key_sched, 11, c); - - start = get_ticks(); - aes128_encrypt_ecb(msg, msg_len, key, c); - return get_ticks() - start; -} - -PAYLOAD_SECTION -void entry_async(uint64_t *base) -{ - int i, j, iter_count = 0; - unsigned long long start = 0; - struct event *usb_event = ADDR_USB_EVENT; - - unsigned char msg_old[16]; - unsigned char key_sched[176]; - double timing; - - // get initial params - unsigned char *msg = (unsigned char *) base[0]; - unsigned int msg_len = (unsigned int) base[1]; - unsigned char *key = (unsigned char *) base[2]; - struct aes_constants *c = (struct aes_constants *) base[3]; - - expand_key(key, key_sched, 11, c); - - // initialize events and buffers - struct bern_data *data = (struct bern_data *) base; - event_new(&data->ev_data, 1, 0); - event_new(&data->ev_done, 1, 0); - - data->count = 0; - for(i = 0; i < 16; i++) - { - for(j = 0; j < 256; j++) - { - data->t[i][j] = 0; - data->tsq[i][j] = 0; - data->tnum[i][j] = 0; - } - } - - while(1) - { - // randomly generate a new msg based on the old one - for(i = 0; i < 16; i++) - msg_old[i] = msg[i]; - - // encrypt it and measure time - start = get_ticks(); - aes128_encrypt_ecb(msg, msg_len, key_sched, c); - timing = (double) (get_ticks() - start); - - // update counters - for(i = 0; i < 16; i++) - { - data->t[i][msg_old[i]] += timing; - data->tsq[i][msg_old[i]] += (timing * timing); - data->tnum[i][msg_old[i]] += 1; - - data->count++; - data->ttotal += timing; - } - - // check if host has requested data - iter_count++; - if(iter_count % 100000 == 0) - { - if(event_try(&data->ev_data, 1)) - event_wait(&data->ev_done); - } - } } \ No newline at end of file diff --git a/c8_remote/lib/experiments/aes_sw.c b/c8_remote/lib/experiments/aes_sw.c index f52c2ed..f94826b 100644 --- a/c8_remote/lib/experiments/aes_sw.c +++ b/c8_remote/lib/experiments/aes_sw.c @@ -8,78 +8,13 @@ #include "bootrom_addr.h" #include "usb_helpers.h" #include "command.h" - -static unsigned char sbox[256] = - { - 0x63, 0x7c, 0x77, 0x7b, 0xf2, 0x6b, 0x6f, 0xc5, 0x30, 0x01, 0x67, 0x2b, 0xfe, 0xd7, 0xab, 0x76, - 0xca, 0x82, 0xc9, 0x7d, 0xfa, 0x59, 0x47, 0xf0, 0xad, 0xd4, 0xa2, 0xaf, 0x9c, 0xa4, 0x72, 0xc0, - 0xb7, 0xfd, 0x93, 0x26, 0x36, 0x3f, 0xf7, 0xcc, 0x34, 0xa5, 0xe5, 0xf1, 0x71, 0xd8, 0x31, 0x15, - 0x04, 0xc7, 0x23, 0xc3, 0x18, 0x96, 0x05, 0x9a, 0x07, 0x12, 0x80, 0xe2, 0xeb, 0x27, 0xb2, 0x75, - 0x09, 0x83, 0x2c, 0x1a, 0x1b, 0x6e, 0x5a, 0xa0, 0x52, 0x3b, 0xd6, 0xb3, 0x29, 0xe3, 0x2f, 0x84, - 0x53, 0xd1, 0x00, 0xed, 0x20, 0xfc, 0xb1, 0x5b, 0x6a, 0xcb, 0xbe, 0x39, 0x4a, 0x4c, 0x58, 0xcf, - 0xd0, 0xef, 0xaa, 0xfb, 0x43, 0x4d, 0x33, 0x85, 0x45, 0xf9, 0x02, 0x7f, 0x50, 0x3c, 0x9f, 0xa8, - 0x51, 0xa3, 0x40, 0x8f, 0x92, 0x9d, 0x38, 0xf5, 0xbc, 0xb6, 0xda, 0x21, 0x10, 0xff, 0xf3, 0xd2, - 0xcd, 0x0c, 0x13, 0xec, 0x5f, 0x97, 0x44, 0x17, 0xc4, 0xa7, 0x7e, 0x3d, 0x64, 0x5d, 0x19, 0x73, - 0x60, 0x81, 0x4f, 0xdc, 0x22, 0x2a, 0x90, 0x88, 0x46, 0xee, 0xb8, 0x14, 0xde, 0x5e, 0x0b, 0xdb, - 0xe0, 0x32, 0x3a, 0x0a, 0x49, 0x06, 0x24, 0x5c, 0xc2, 0xd3, 0xac, 0x62, 0x91, 0x95, 0xe4, 0x79, - 0xe7, 0xc8, 0x37, 0x6d, 0x8d, 0xd5, 0x4e, 0xa9, 0x6c, 0x56, 0xf4, 0xea, 0x65, 0x7a, 0xae, 0x08, - 0xba, 0x78, 0x25, 0x2e, 0x1c, 0xa6, 0xb4, 0xc6, 0xe8, 0xdd, 0x74, 0x1f, 0x4b, 0xbd, 0x8b, 0x8a, - 0x70, 0x3e, 0xb5, 0x66, 0x48, 0x03, 0xf6, 0x0e, 0x61, 0x35, 0x57, 0xb9, 0x86, 0xc1, 0x1d, 0x9e, - 0xe1, 0xf8, 0x98, 0x11, 0x69, 0xd9, 0x8e, 0x94, 0x9b, 0x1e, 0x87, 0xe9, 0xce, 0x55, 0x28, 0xdf, - 0x8c, 0xa1, 0x89, 0x0d, 0xbf, 0xe6, 0x42, 0x68, 0x41, 0x99, 0x2d, 0x0f, 0xb0, 0x54, 0xbb, 0x16 - }; - -static unsigned char rc_lookup[11] = {0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80, 0x1b, 0x36, 0x6c}; - -static unsigned char mul2_lookup[256] = - { - 0x00, 0x02, 0x04, 0x06, 0x08, 0x0a, 0x0c, 0x0e, 0x10, 0x12, 0x14, 0x16, 0x18, 0x1a, 0x1c, 0x1e, - 0x20, 0x22, 0x24, 0x26, 0x28, 0x2a, 0x2c, 0x2e, 0x30, 0x32, 0x34, 0x36, 0x38, 0x3a, 0x3c, 0x3e, - 0x40, 0x42, 0x44, 0x46, 0x48, 0x4a, 0x4c, 0x4e, 0x50, 0x52, 0x54, 0x56, 0x58, 0x5a, 0x5c, 0x5e, - 0x60, 0x62, 0x64, 0x66, 0x68, 0x6a, 0x6c, 0x6e, 0x70, 0x72, 0x74, 0x76, 0x78, 0x7a, 0x7c, 0x7e, - 0x80, 0x82, 0x84, 0x86, 0x88, 0x8a, 0x8c, 0x8e, 0x90, 0x92, 0x94, 0x96, 0x98, 0x9a, 0x9c, 0x9e, - 0xa0, 0xa2, 0xa4, 0xa6, 0xa8, 0xaa, 0xac, 0xae, 0xb0, 0xb2, 0xb4, 0xb6, 0xb8, 0xba, 0xbc, 0xbe, - 0xc0, 0xc2, 0xc4, 0xc6, 0xc8, 0xca, 0xcc, 0xce, 0xd0, 0xd2, 0xd4, 0xd6, 0xd8, 0xda, 0xdc, 0xde, - 0xe0, 0xe2, 0xe4, 0xe6, 0xe8, 0xea, 0xec, 0xee, 0xf0, 0xf2, 0xf4, 0xf6, 0xf8, 0xfa, 0xfc, 0xfe, - 0x1b, 0x19, 0x1f, 0x1d, 0x13, 0x11, 0x17, 0x15, 0x0b, 0x09, 0x0f, 0x0d, 0x03, 0x01, 0x07, 0x05, - 0x3b, 0x39, 0x3f, 0x3d, 0x33, 0x31, 0x37, 0x35, 0x2b, 0x29, 0x2f, 0x2d, 0x23, 0x21, 0x27, 0x25, - 0x5b, 0x59, 0x5f, 0x5d, 0x53, 0x51, 0x57, 0x55, 0x4b, 0x49, 0x4f, 0x4d, 0x43, 0x41, 0x47, 0x45, - 0x7b, 0x79, 0x7f, 0x7d, 0x73, 0x71, 0x77, 0x75, 0x6b, 0x69, 0x6f, 0x6d, 0x63, 0x61, 0x67, 0x65, - 0x9b, 0x99, 0x9f, 0x9d, 0x93, 0x91, 0x97, 0x95, 0x8b, 0x89, 0x8f, 0x8d, 0x83, 0x81, 0x87, 0x85, - 0xbb, 0xb9, 0xbf, 0xbd, 0xb3, 0xb1, 0xb7, 0xb5, 0xab, 0xa9, 0xaf, 0xad, 0xa3, 0xa1, 0xa7, 0xa5, - 0xdb, 0xd9, 0xdf, 0xdd, 0xd3, 0xd1, 0xd7, 0xd5, 0xcb, 0xc9, 0xcf, 0xcd, 0xc3, 0xc1, 0xc7, 0xc5, - 0xfb, 0xf9, 0xff, 0xfd, 0xf3, 0xf1, 0xf7, 0xf5, 0xeb, 0xe9, 0xef, 0xed, 0xe3, 0xe1, 0xe7, 0xe5 - }; - -static unsigned char mul3_lookup[256] = - { - 0x00, 0x03, 0x06, 0x05, 0x0c, 0x0f, 0x0a, 0x09, 0x18, 0x1b, 0x1e, 0x1d, 0x14, 0x17, 0x12, 0x11, - 0x30, 0x33, 0x36, 0x35, 0x3c, 0x3f, 0x3a, 0x39, 0x28, 0x2b, 0x2e, 0x2d, 0x24, 0x27, 0x22, 0x21, - 0x60, 0x63, 0x66, 0x65, 0x6c, 0x6f, 0x6a, 0x69, 0x78, 0x7b, 0x7e, 0x7d, 0x74, 0x77, 0x72, 0x71, - 0x50, 0x53, 0x56, 0x55, 0x5c, 0x5f, 0x5a, 0x59, 0x48, 0x4b, 0x4e, 0x4d, 0x44, 0x47, 0x42, 0x41, - 0xc0, 0xc3, 0xc6, 0xc5, 0xcc, 0xcf, 0xca, 0xc9, 0xd8, 0xdb, 0xde, 0xdd, 0xd4, 0xd7, 0xd2, 0xd1, - 0xf0, 0xf3, 0xf6, 0xf5, 0xfc, 0xff, 0xfa, 0xf9, 0xe8, 0xeb, 0xee, 0xed, 0xe4, 0xe7, 0xe2, 0xe1, - 0xa0, 0xa3, 0xa6, 0xa5, 0xac, 0xaf, 0xaa, 0xa9, 0xb8, 0xbb, 0xbe, 0xbd, 0xb4, 0xb7, 0xb2, 0xb1, - 0x90, 0x93, 0x96, 0x95, 0x9c, 0x9f, 0x9a, 0x99, 0x88, 0x8b, 0x8e, 0x8d, 0x84, 0x87, 0x82, 0x81, - 0x9b, 0x98, 0x9d, 0x9e, 0x97, 0x94, 0x91, 0x92, 0x83, 0x80, 0x85, 0x86, 0x8f, 0x8c, 0x89, 0x8a, - 0xab, 0xa8, 0xad, 0xae, 0xa7, 0xa4, 0xa1, 0xa2, 0xb3, 0xb0, 0xb5, 0xb6, 0xbf, 0xbc, 0xb9, 0xba, - 0xfb, 0xf8, 0xfd, 0xfe, 0xf7, 0xf4, 0xf1, 0xf2, 0xe3, 0xe0, 0xe5, 0xe6, 0xef, 0xec, 0xe9, 0xea, - 0xcb, 0xc8, 0xcd, 0xce, 0xc7, 0xc4, 0xc1, 0xc2, 0xd3, 0xd0, 0xd5, 0xd6, 0xdf, 0xdc, 0xd9, 0xda, - 0x5b, 0x58, 0x5d, 0x5e, 0x57, 0x54, 0x51, 0x52, 0x43, 0x40, 0x45, 0x46, 0x4f, 0x4c, 0x49, 0x4a, - 0x6b, 0x68, 0x6d, 0x6e, 0x67, 0x64, 0x61, 0x62, 0x73, 0x70, 0x75, 0x76, 0x7f, 0x7c, 0x79, 0x7a, - 0x3b, 0x38, 0x3d, 0x3e, 0x37, 0x34, 0x31, 0x32, 0x23, 0x20, 0x25, 0x26, 0x2f, 0x2c, 0x29, 0x2a, - 0x0b, 0x08, 0x0d, 0x0e, 0x07, 0x04, 0x01, 0x02, 0x13, 0x10, 0x15, 0x16, 0x1f, 0x1c, 0x19, 0x1a - }; +#include "crypto_host.h" DEV_PTR_T install_aes_data(struct pwned_device *dev) { int close; DEV_PTR_T res; - struct aes_constants *constants = malloc(sizeof(struct aes_constants)); - memcpy(constants->sbox, sbox, sizeof(sbox)); - memcpy(constants->rc_lookup, rc_lookup, sizeof(rc_lookup)); - memcpy(constants->mul2, mul2_lookup, sizeof(mul2_lookup)); - memcpy(constants->mul3, mul3_lookup, sizeof(mul3_lookup)); + struct aes_constants *constants = get_constants(); if(is_device_session_open(dev)) close = 0; else @@ -157,7 +92,7 @@ DEV_PTR_T setup_bern_exp(struct pwned_device *dev) return DEV_PTR_NULL; } - if(IS_CHECKM8_FAIL(install_payload(dev, PAYLOAD_AES_SW, SRAM))) + if(IS_CHECKM8_FAIL(install_payload(dev, PAYLOAD_AES_SW_BERN, SRAM))) { printf("failed to install aes payload\n"); return DEV_PTR_NULL; @@ -172,10 +107,10 @@ DEV_PTR_T setup_bern_exp(struct pwned_device *dev) } free_dev_cmd_resp(resp); - addr_async_buf = setup_payload_async(dev, PAYLOAD_AES_SW, + addr_async_buf = setup_payload_async(dev, PAYLOAD_AES_SW_BERN, sizeof(struct bern_data), 4, addr_data, 16, addr_key, addr_constants); - run_payload_async(dev, PAYLOAD_AES_SW); + run_payload_async(dev, PAYLOAD_AES_SW_BERN); if(IS_CHECKM8_FAIL(close_device_session(dev))) { @@ -236,5 +171,108 @@ struct bern_data *get_bern_exp_data(struct pwned_device *dev, DEV_PTR_T async_bu return NULL; } + return res; +} + +DEV_PTR_T setup_corr_exp(struct pwned_device *dev, unsigned char *init_key) +{ + DEV_PTR_T addr_key, addr_async_buf, addr_constants; + struct dev_cmd_resp *resp; + + if(IS_CHECKM8_FAIL(open_device_session(dev))) + { + printf("failed to open device session\n"); + return DEV_PTR_NULL; + } + + addr_constants = install_aes_data(dev); + if(addr_constants == DEV_PTR_NULL) + { + printf("failed to install aes constants\n"); + return DEV_PTR_NULL; + } + + addr_key = install_data(dev, SRAM, init_key, 16); + if(addr_key == DEV_PTR_NULL) + { + printf("failed to install aes key\n"); + return DEV_PTR_NULL; + } + + if(IS_CHECKM8_FAIL(install_payload(dev, PAYLOAD_SYNC, SRAM))) + { + printf("failed to install sync payload\n"); + return DEV_PTR_NULL; + } + + if(IS_CHECKM8_FAIL(install_payload(dev, PAYLOAD_AES_SW_CORR, SRAM))) + { + printf("failed to install aes payload\n"); + return DEV_PTR_NULL; + } + + resp = execute_payload(dev, PAYLOAD_SYNC, 0, 0); + if(IS_CHECKM8_FAIL(resp->ret)) + { + printf("failed to execute sync payload\n"); + free_dev_cmd_resp(resp); + return DEV_PTR_NULL; + } + free_dev_cmd_resp(resp); + + addr_async_buf = setup_payload_async(dev, PAYLOAD_AES_SW_CORR, + sizeof(struct corr_data), + 2, addr_key, addr_constants); + run_payload_async(dev, PAYLOAD_AES_SW_CORR); + + if(IS_CHECKM8_FAIL(close_device_session(dev))) + { + printf("failed to close device session\n"); + return DEV_PTR_NULL; + } + + return addr_async_buf; +} + +struct corr_data *get_corr_exp_data(struct pwned_device *dev, DEV_PTR_T async_buf) +{ + struct dev_cmd_resp *resp; + struct corr_data *res; + + if(IS_CHECKM8_FAIL(open_device_session(dev))) + { + printf("failed to open device session\n"); + return NULL; + } + + resp = read_gadget(dev, async_buf, sizeof(struct corr_data)); + if(IS_CHECKM8_FAIL(resp->ret)) + { + printf("failed to get data from device\n"); + free_dev_cmd_resp(resp); + return NULL; + } + + res = (struct corr_data *) resp->data; + free(resp); + + resp = execute_gadget(dev, ADDR_EVENT_NOTIFY, 0, 1, + async_buf + offsetof(struct corr_data, ev_cont)); + if(IS_CHECKM8_FAIL(resp->ret)) + { + printf("failed to signal data continue\n"); + free(res); + free_dev_cmd_resp(resp); + return NULL; + } + + free_dev_cmd_resp(resp); + if(IS_CHECKM8_FAIL(close_device_session(dev))) + { + printf("failed to close device session\n"); + free(res); + return NULL; + } + return res; } \ No newline at end of file diff --git a/c8_remote/lib/payload/CMakeLists.txt b/c8_remote/lib/payload/CMakeLists.txt index 2d09bab..1d1ab91 100644 --- a/c8_remote/lib/payload/CMakeLists.txt +++ b/c8_remote/lib/payload/CMakeLists.txt @@ -6,14 +6,16 @@ if(${CMAKE_HOST_SYSTEM_PROCESSOR} STREQUAL "x86_64") set(CMAKE_C_COMPILER /usr/bin/aarch64-linux-gnu-gcc) set(CMAKE_ASM_COMPILER /usr/bin/aarch64-linux-gnu-as) set(CMAKE_OBJCOPY /usr/bin/aarch64-linux-gnu-objcopy) + set(CMAKE_RANLIB /usr/bin/aarch64-linux-gnu-ranlib) elseif(${CMAKE_HOST_SYSTEM_PROCESSOR} STREQUAL "armv7l") # raspberry pi set(CMAKE_C_COMPILER /opt/cross/bin/aarch64-linux-gcc) set(CMAKE_ASM_COMPILER /opt/cross/bin/aarch64-linux-as) set(CMAKE_OBJCOPY /opt/cross/bin/aarch64-linux-objcopy) + set(CMAKE_RANLIB /opt/cross/bin/aarch64-linux-ranlib) endif() -set(CMAKE_C_FLAGS "-nostdlib -O -Wl,--gc-sections") +set(CMAKE_C_FLAGS "-nostdlib -O") file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/bin) foreach(NAME ${PL_NAMES}) @@ -34,4 +36,9 @@ foreach(NAME ${PL_NAMES}) ARGS -O binary -j .text -j .payload_text ${CMAKE_CURRENT_BINARY_DIR}/payload_${NAME} ${CMAKE_CURRENT_BINARY_DIR}/bin/payload_${NAME}.bin) -endforeach(NAME) \ No newline at end of file +endforeach(NAME) + +add_library(crypto_dev ../crypto/aes_sw_impl.c) + +target_link_libraries(payload_aes_sw_bern crypto_dev) +target_link_libraries(payload_aes_sw_corr crypto_dev) \ No newline at end of file diff --git a/c8_remote/lib/payload/include/crypto_dev.h b/c8_remote/lib/payload/include/crypto_dev.h new file mode 100644 index 0000000..936febe --- /dev/null +++ b/c8_remote/lib/payload/include/crypto_dev.h @@ -0,0 +1,13 @@ +#ifndef CHECKM8_TOOL_CRYPTO_H +#define CHECKM8_TOOL_CRYPTO_H + +#include "bootrom_type.h" + +void expand_key(unsigned char key[16], unsigned char key_sched[176], + int n, struct aes_constants *c); + +void aes128_encrypt_ecb(unsigned char *msg, unsigned int msg_len, + unsigned char key_sched[176], struct aes_constants *c); + + +#endif //CHECKM8_TOOL_CRYPTO_H diff --git a/c8_remote/lib/payload/src/aes_sw_bern.c b/c8_remote/lib/payload/src/aes_sw_bern.c new file mode 100644 index 0000000..1ab1f31 --- /dev/null +++ b/c8_remote/lib/payload/src/aes_sw_bern.c @@ -0,0 +1,83 @@ +#include "bootrom_func.h" +#include "bootrom_type.h" +#include "cacheutil.h" +#include "crypto_dev.h" + +PAYLOAD_SECTION +uint64_t entry_sync(unsigned char *msg, unsigned int msg_len, unsigned char key[16], + struct aes_constants *c) +{ + unsigned long long start = 0; + unsigned char key_sched[176]; + expand_key(key, key_sched, 11, c); + + start = get_ticks(); + aes128_encrypt_ecb(msg, msg_len, key, c); + return get_ticks() - start; +} + +PAYLOAD_SECTION +void entry_async(uint64_t *base) +{ + int i, j, iter_count = 0; + unsigned long long start = 0; + + unsigned char msg_old[16]; + unsigned char key_sched[176]; + double timing; + + // get initial params + unsigned char *msg = (unsigned char *) base[0]; + unsigned int msg_len = (unsigned int) base[1]; + unsigned char *key = (unsigned char *) base[2]; + struct aes_constants *c = (struct aes_constants *) base[3]; + + expand_key(key, key_sched, 11, c); + + // initialize events and buffers + struct bern_data *data = (struct bern_data *) base; + event_new(&data->ev_data, 1, 0); + event_new(&data->ev_done, 1, 0); + + data->count = 0; + for(i = 0; i < 16; i++) + { + for(j = 0; j < 256; j++) + { + data->t[i][j] = 0; + data->tsq[i][j] = 0; + data->tnum[i][j] = 0; + } + } + + while(1) + { + // randomly generate a new msg based on the old one + for(i = 0; i < 16; i++) + msg_old[i] = msg[i]; + + // encrypt it and measure time + start = get_ticks(); + aes128_encrypt_ecb(msg, msg_len, key_sched, c); + timing = (double) (get_ticks() - start); + + // update counters + for(i = 0; i < 16; i++) + { + data->t[i][msg_old[i]] += timing; + data->tsq[i][msg_old[i]] += (timing * timing); + data->tnum[i][msg_old[i]] += 1; + + data->count++; + data->ttotal += timing; + } + + // check if host has requested data + iter_count++; + if(iter_count % 100000 == 0) + { + if(event_try(&data->ev_data, 1)) + event_wait(&data->ev_done); + } + } +} \ No newline at end of file diff --git a/c8_remote/lib/payload/src/aes_sw_corr.c b/c8_remote/lib/payload/src/aes_sw_corr.c new file mode 100644 index 0000000..9e81942 --- /dev/null +++ b/c8_remote/lib/payload/src/aes_sw_corr.c @@ -0,0 +1,54 @@ +#include "bootrom_func.h" +#include "dev_util.h" +#include "crypto_dev.h" + +PAYLOAD_SECTION +void entry_sync() +{ + +} + +PAYLOAD_SECTION +void entry_async(uint64_t *base) +{ + int i; + unsigned char key_sched[176]; + unsigned long long start, timing; + + unsigned char *key = (unsigned char *) base[0]; + struct aes_constants *c = (struct aes_constants *) base[1]; + + struct corr_data *data = (struct corr_data *) base; + event_new(&data->ev_cont, 1, 0); + + expand_key(key, key_sched, 11, c); + for(i = 0; i < 16; i++) + data->msg[i] = 0; + + while(1) + { + // reset data state + data->num_cutoff = 0; + for(i = 0; i < N_CORR_ENTRIES; i++) + { + data->data[i] = 0; + } + + // collect new data + i = 0; + while(i < N_CORR_ENTRIES) + { + start = get_ticks(); + aes128_encrypt_ecb(data->msg, 16, key_sched, c); + timing = get_ticks() - start; + + if(timing < 256) + data->data[i++] = (unsigned char) timing; + else + data->num_cutoff++; + } + + event_wait(&data->ev_cont); + } + +} \ No newline at end of file diff --git a/c8_remote/main.c b/c8_remote/main.c index f94cd8b..7cb7c77 100644 --- a/c8_remote/main.c +++ b/c8_remote/main.c @@ -6,11 +6,11 @@ #include #include -#include "command.h" #include "payload.h" #include "usb_helpers.h" #include "bootrom_type.h" #include "experiments.h" +#include "crypto_host.h" #ifdef CHECKM8_LOGGING @@ -95,10 +95,69 @@ void record_bern_data(struct bern_data *data) fclose(outfile); } +void run_corr_exp(struct pwned_device *dev, char *fname) +{ + int i; + FILE *outfile; + DEV_PTR_T addr_async_buf; + + struct aes_constants *c = get_constants(); + struct corr_data *data; + + unsigned char msg[16]; + unsigned char key[16]; + unsigned char key_sched[176]; + + for(i = 0; i < 16; i++) + { + msg[i] = 0; + key[i] = 0x1; + } + + expand_key(key, key_sched, 11, c); + + outfile = fopen(fname, "wb"); + if(outfile == NULL) + { + printf("failed to open outfile\n"); + return; + } + + addr_async_buf = setup_corr_exp(dev, key); + printf("got async buf ptr %llx\n", addr_async_buf); + if(addr_async_buf == DEV_PTR_NULL)return; + + while(1) + { + data = get_corr_exp_data(dev, addr_async_buf); + + for(i = 0; i < N_CORR_ENTRIES; i++) + { + fwrite(msg, 1, sizeof(msg), outfile); + fwrite("\x00", 1, 1, outfile); + fwrite(&data->data[i], 1, 1, outfile); + fwrite("\x00", 1, 1, outfile); + + aes128_encrypt_ecb(msg, 16, key_sched, c); + } + + fflush(outfile); + for(i = 0; i < 16; i++) + { + if(msg[i] != data->msg[i]) + { + printf("aes error! message mismatch\n"); + free(data); + return; + } + } + + free(data); + } +} + int main() { - DEV_PTR_T addr_async_buf; - struct bern_data *data; struct pwned_device *dev = exploit_device(); if(dev == NULL || dev->status == DEV_NORMAL) @@ -110,22 +169,7 @@ int main() fix_heap(dev); demote_device(dev); - addr_async_buf = setup_bern_exp(dev); - printf("got async buf ptr %llx\n", addr_async_buf); - if(addr_async_buf == DEV_PTR_NULL) - { - return -1; - } - - while(1) - { - sleep(60); - - data = get_bern_exp_data(dev, addr_async_buf); - record_bern_data(data); - free(data); - } - + run_corr_exp(dev, "test.out"); free_device(dev); } diff --git a/c8_remote/src/payload.c b/c8_remote/src/payload.c index a055ada..6eb0f4d 100644 --- a/c8_remote/src/payload.c +++ b/c8_remote/src/payload.c @@ -45,9 +45,14 @@ struct payload *get_payload(PAYLOAD_T p) len = PAYLOAD_AES_BUSY_SZ; break; - case PAYLOAD_AES_SW: - pl = payload_aes_sw; - len = PAYLOAD_AES_SW_SZ; + case PAYLOAD_AES_SW_BERN: + pl = payload_aes_sw_bern; + len = PAYLOAD_AES_SW_BERN_SZ; + break; + + case PAYLOAD_AES_SW_CORR: + pl = payload_aes_sw_corr; + len = PAYLOAD_AES_SW_CORR_SZ; break; case PAYLOAD_CACHELIB: