Skip to content

Commit

Permalink
Merge pull request #68 from Skyler84/skyler/HMAC
Browse files Browse the repository at this point in the history
HMAC: Add tildagon HMAC module
  • Loading branch information
MatthewWilkes committed May 31, 2024
2 parents efd1975 + 08e6e2f commit 7400fdb
Show file tree
Hide file tree
Showing 8 changed files with 168 additions and 9 deletions.
64 changes: 64 additions & 0 deletions burn_mac.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
#!/usr/bin/python

import hashlib
import esptool, espefuse
import os, hmac, time


def burn_hmac_key(key_to_use=1, port=None, do_not_confirm=False):
# This is the master secret and should be kept secret
# Initialise it from the environment variable
MASTER_SECRET = os.environ["MASTER_SECRET"]

# Fix this in the code to the sha256sum of the master secret
MASTER_HASH='59a61bdad01d1074a37bc6ee2ae4bac0a424fc2fcfcbdfd0c386d1fdac0d5c7e'

# PLEASE PLEASE PLEASE DO NOT REMOVE THIS CHECK
# IF YOU FLASH THE WRONG SECRET TO THE DEVICE IT CAN NEVER BE UNDONE
if hashlib.sha256(MASTER_SECRET.encode()).hexdigest() != MASTER_HASH:
print("Master secret does not match")
raise Exception("Master secret does not match")

esp=esptool.get_default_connected_device(esptool.get_port_list(), port=port, connect_attempts=1, initial_baud=115200)
mac_address = esp.read_mac("BASE_MAC")
mac_str = '-'.join([f"{b:02X}" for b in mac_address])

print("MAC Address:", mac_str)

COMBINED_SECRET = MASTER_SECRET + mac_str

HMAC_KEY = hashlib.sha256(COMBINED_SECRET.encode()).digest()

test_mac = hmac.digest(HMAC_KEY, b"test", "sha256")
print(test_mac.hex())

efuses, operations = espefuse.get_efuses(esp, do_not_confirm=do_not_confirm)
class Args:
name_value_pairs = {}
args = Args()
args.name_value_pairs[f"KEY_PURPOSE_{key_to_use}"] = 8
args.name_value_pairs[f"BLOCK_KEY{key_to_use}"] = HMAC_KEY
args.name_value_pairs[f"RD_DIS"] = (1<<(key_to_use))
# args.name_value_pairs[f"WR_DIS"] = (1<<(23+key_to_use))
print(operations.burn_efuse)
operations.burn_efuse(esp, efuses, args)


if __name__ == "__main__":
_in = input("Burn in a loop? (y/N): ")
loop=False
if _in.lower() == "y":
loop = True
print("Burning fuses on loop. Press Ctrl+C to stop")
else:
print("Burning single fuse, waiting for device.")
while(True):
ports = esptool.get_port_list()
if not ports:
time.sleep(1)
continue
burn_hmac_key(do_not_confirm=loop)
while esptool.get_port_list():
time.sleep(1)
if not loop:
break
6 changes: 6 additions & 0 deletions drivers/micropython.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,9 @@ include(${CMAKE_CURRENT_LIST_DIR}/tildagon_power/tildagon_power.cmake)

# Add OTA helpers
include(${CMAKE_CURRENT_LIST_DIR}/ota/micropython.cmake)

# Add Tildagon module
include(${CMAKE_CURRENT_LIST_DIR}/tildagon/micropython.cmake)

# Add HMAC driver
include(${CMAKE_CURRENT_LIST_DIR}/tildagon_hmac/micropython.cmake)
16 changes: 16 additions & 0 deletions drivers/tildagon/micropython.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# Create an INTERFACE library for our C module.
add_library(usermod_tildagon INTERFACE)

# Add our source files to the lib
target_sources(usermod_tildagon INTERFACE
${CMAKE_CURRENT_LIST_DIR}/tildagon.c
)

# Add the current directory as an include directory.
target_include_directories(usermod_tildagon INTERFACE
${CMAKE_CURRENT_LIST_DIR}
)

# Link our INTERFACE library to the usermod target.
target_link_libraries(usermod_tildagon INTERFACE usermod_tildagon_hmac)
target_link_libraries(usermod INTERFACE usermod_tildagon)
13 changes: 4 additions & 9 deletions drivers/tildagon_py.c → drivers/tildagon/tildagon.c
Original file line number Diff line number Diff line change
@@ -1,17 +1,14 @@
#include "py/builtin.h"
#include "py/runtime.h"

#if MICROPY_PY_TILDAGON
// #include "tildagon_hmac/tildagon_hmac.h"

extern const mp_obj_module_t tildagon_hmac_module;

// info()
static mp_obj_t py_tildagon_info(void) {
return MP_OBJ_NEW_SMALL_INT(42);
}
MP_DEFINE_CONST_FUN_OBJ_0(tildagon_info_obj, py_tildagon_info);

static const mp_rom_map_elem_t mp_module_tildagon_globals_table[] = {
{ MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR_tildagon) },
{ MP_ROM_QSTR(MP_QSTR_I2C), MP_ROM_PTR(&tildagon_info_obj) },
{ MP_ROM_QSTR(MP_QSTR_HMAC), MP_ROM_PTR(&tildagon_hmac_module) },
};
static MP_DEFINE_CONST_DICT(mp_module_tildagon_globals, mp_module_tildagon_globals_table);

Expand All @@ -21,5 +18,3 @@ const mp_obj_module_t mp_module_tildagon = {
};

MP_REGISTER_MODULE(MP_QSTR_tildagon, mp_module_tildagon);

#endif
15 changes: 15 additions & 0 deletions drivers/tildagon_hmac/micropython.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Create an INTERFACE library for our C module.
add_library(usermod_tildagon_hmac INTERFACE)

# Add our source files to the lib
target_sources(usermod_tildagon_hmac INTERFACE
${CMAKE_CURRENT_LIST_DIR}/tildagon_hmac.c
)

# Add the current directory as an include directory.
target_include_directories(usermod_tildagon_hmac INTERFACE
${CMAKE_CURRENT_LIST_DIR}
)

# Link our INTERFACE library to the usermod target.
target_link_libraries(usermod INTERFACE usermod_tildagon_hmac)
40 changes: 40 additions & 0 deletions drivers/tildagon_hmac/tildagon_hmac.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
#include "tildagon_hmac.h"
#include "esp_hmac.h"

#include "py/runtime.h"

static mp_obj_t tildagon_hmac_digest(mp_obj_t key_slot, mp_obj_t msg) {
uint8_t hmac[32];
hmac_key_id_t key_id = mp_obj_get_int(key_slot);

mp_buffer_info_t bufinfo;
mp_get_buffer_raise(msg, &bufinfo, MP_BUFFER_READ);

esp_err_t err = esp_hmac_calculate(key_id, bufinfo.buf, bufinfo.len, hmac);

if (err == ESP_FAIL) {
mp_raise_msg(&mp_type_Exception, "HMAC key not provisioned!");
}

return mp_obj_new_bytes(hmac, 32);
}

static MP_DEFINE_CONST_FUN_OBJ_2(tildagon_hmac_digest_obj, tildagon_hmac_digest);

static const mp_rom_map_elem_t tildagon_hmac_globals_table[] = {
{ MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR_HMAC)},
{ MP_ROM_QSTR(MP_QSTR_digest), MP_ROM_PTR(&tildagon_hmac_digest_obj) },
{ MP_ROM_QSTR(MP_QSTR_HMAC_KEY0), MP_ROM_INT(HMAC_KEY0)},
{ MP_ROM_QSTR(MP_QSTR_HMAC_KEY1), MP_ROM_INT(HMAC_KEY1)},
{ MP_ROM_QSTR(MP_QSTR_HMAC_KEY2), MP_ROM_INT(HMAC_KEY2)},
{ MP_ROM_QSTR(MP_QSTR_HMAC_KEY3), MP_ROM_INT(HMAC_KEY3)},
{ MP_ROM_QSTR(MP_QSTR_HMAC_KEY4), MP_ROM_INT(HMAC_KEY4)},
{ MP_ROM_QSTR(MP_QSTR_HMAC_KEY5), MP_ROM_INT(HMAC_KEY5)},
};

static MP_DEFINE_CONST_DICT(tildagon_hmac_globals, tildagon_hmac_globals_table);

const mp_obj_module_t tildagon_hmac_module = {
.base = { &mp_type_module },
.globals = (mp_obj_dict_t *)&tildagon_hmac_globals,
};
8 changes: 8 additions & 0 deletions drivers/tildagon_hmac/tildagon_hmac.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
#ifndef _TILDAGON_HMAC_H_
#define _TILDAGON_HMAC_H_

#include "py/runtime.h"

extern const mp_obj_module_t tildagon_hmac_module;

#endif // _TILDAGON_HMAC_H_
15 changes: 15 additions & 0 deletions sim/fakes/tildagon/HMAC.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import hmac

def digest(key_slot, msg):
key = bytes(32)
if key_slot == HMAC_KEY0:
key = b'\x96\xd6I\x0c\x8f\x81\x0f\xc1\x95a\xe2K\xef\xa5xT~\x8d\xcd\xa7~\xd9H\x0b\xdc\xf2\x9dD\xd3\xd3>Y'
return hmac.digest(key, msg, "sha256")


HMAC_KEY0 = 0
HMAC_KEY1 = 1
HMAC_KEY2 = 2
HMAC_KEY3 = 3
HMAC_KEY4 = 4
HMAC_KEY5 = 5

0 comments on commit 7400fdb

Please sign in to comment.