summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorjaseg <git@jaseg.net>2018-11-14 22:47:04 +0900
committerjaseg <git@jaseg.net>2018-11-14 22:47:04 +0900
commiteb481f1cda0a6eae1aa0486acb637f985cddcc2f (patch)
treec6082d8d5e8809e7d590b4f5d0e9d2de2700451b /src
parent66f9e82c5ca313fb90edff6a9d1956c02c973934 (diff)
downloadsecure-hid-eb481f1cda0a6eae1aa0486acb637f985cddcc2f.tar.gz
secure-hid-eb481f1cda0a6eae1aa0486acb637f985cddcc2f.tar.bz2
secure-hid-eb481f1cda0a6eae1aa0486acb637f985cddcc2f.zip
known device/sram data persistence working
Diffstat (limited to 'src')
-rw-r--r--src/demo.c23
-rw-r--r--src/noise.c24
-rw-r--r--src/noise.h4
3 files changed, 39 insertions, 12 deletions
diff --git a/src/demo.c b/src/demo.c
index ad73cff..05875b8 100644
--- a/src/demo.c
+++ b/src/demo.c
@@ -38,6 +38,7 @@
#include <libopencm3/stm32/timer.h>
#include <libopencm3/stm32/otg_hs.h>
#include <libopencm3/stm32/otg_fs.h>
+#include <libopencm3/stm32/pwr.h>
#include <libopencm3/stm32/dma.h>
#include <libopencm3/cm3/nvic.h>
#include <libopencmsis/core_cm3.h>
@@ -56,7 +57,9 @@
static struct NoiseState noise_state;
-static uint8_t remote_key_reference[CURVE25519_KEY_LEN];
+static uint8_t remote_key_reference[BLAKE2S_HASH_SIZE] __attribute__((section(".backup_sram")));
+static uint8_t local_key[CURVE25519_KEY_LEN] __attribute__((section(".backup_sram")));
+static uint8_t identity_key_valid __attribute__((section(".backup_sram"))) = 0;
void _fini(void);
@@ -81,6 +84,9 @@ static void clock_setup(void) {
rcc_periph_clock_enable(RCC_DMA2);
rcc_periph_clock_enable(RCC_DMA1);
+ rcc_periph_clock_enable(RCC_PWR);
+ rcc_periph_clock_enable(RCC_BKPSRAM);
+
rcc_periph_clock_enable(RCC_RNG);
}
@@ -413,6 +419,8 @@ int main(void)
{
clock_setup();
gpio_setup();
+ pwr_disable_backup_domain_write_protect();
+ PWR_CSR |= PWR_CSR_BRE; /* Enable backup SRAM battery power regulator */
/* provides time_curr_us to usbh_poll function */
tim6_setup();
@@ -447,12 +455,17 @@ int main(void)
LOG_PRINTF("Initializing RNG...\n");
rand_init();
- noise_state_init(&noise_state, remote_key_reference);
+ noise_state_init(&noise_state, remote_key_reference, local_key);
/* FIXME load remote key from backup memory */
/* FIXME only run this on first boot and persist key in backup sram. Allow reset via jumper-triggered factory reset function. */
- LOG_PRINTF("Generating identity key...\n");
- if (generate_identity_key(&noise_state))
- LOG_PRINTF("Error generating identiy key\n");
+ if (!identity_key_valid) {
+ LOG_PRINTF("Generating identity key...\n");
+ if (generate_identity_key(&noise_state)) {
+ LOG_PRINTF("Error generating identiy key\n");
+ } else {
+ identity_key_valid = 1;
+ }
+ }
int poll_ctr = 0;
while (23) {
diff --git a/src/noise.c b/src/noise.c
index a30d338..7a969c3 100644
--- a/src/noise.c
+++ b/src/noise.c
@@ -3,6 +3,9 @@
#include "noise.h"
#include "packet_interface.h"
+#include "rand_stm32.h"
+
+#include "crypto/noise-c/src/crypto/blake2/blake2s.h"
#define HANDLE_NOISE_ERROR(x, msg) do { \
@@ -20,12 +23,13 @@ volatile uint8_t host_packet_buf[MAX_HOST_PACKET_SIZE];
volatile int host_packet_length = 0;
-void noise_state_init(struct NoiseState *st, uint8_t *remote_key_reference) {
+void noise_state_init(struct NoiseState *st, uint8_t *remote_key_reference, uint8_t *local_key) {
st->handshake_state = HANDSHAKE_UNINITIALIZED;
st->handshake = NULL;
st->tx_cipher = NULL;
st->rx_cipher = NULL;
st->remote_key_reference = remote_key_reference;
+ st->local_key = local_key;
st->failed_handshakes = 0;
}
@@ -51,7 +55,7 @@ int start_protocol_handshake(struct NoiseState *st) {
HANDLE_NOISE_ERROR(noise_handshakestate_new_by_name(&handshake, "Noise_XX_25519_ChaChaPoly_BLAKE2s", NOISE_ROLE_RESPONDER), "instantiating handshake pattern");
NoiseDHState *dh = noise_handshakestate_get_local_keypair_dh(handshake);
- HANDLE_NOISE_ERROR(noise_dhstate_set_keypair_private(dh, st->local_key, sizeof(st->local_key)), "loading local private keys");
+ HANDLE_NOISE_ERROR(noise_dhstate_set_keypair_private(dh, st->local_key, CURVE25519_KEY_LEN), "loading local private keys");
HANDLE_NOISE_ERROR(noise_handshakestate_start(handshake), "starting handshake");
@@ -74,7 +78,7 @@ int generate_identity_key(struct NoiseState *st) {
uint8_t unused[CURVE25519_KEY_LEN]; /* the noise api is a bit bad here. */
memset(st->local_key, 0, sizeof(st->local_key));
- HANDLE_NOISE_ERROR(noise_dhstate_get_keypair(dh, st->local_key, sizeof(st->local_key), unused, sizeof(unused)), "saving key pair");
+ HANDLE_NOISE_ERROR(noise_dhstate_get_keypair(dh, st->local_key, CURVE25519_KEY_LEN, unused, sizeof(unused)), "saving key pair");
return 0;
errout:
@@ -146,7 +150,14 @@ int try_continue_noise_handshake(struct NoiseState *st, uint8_t *buf, size_t len
HANDLE_NOISE_ERROR(noise_dhstate_get_public_key(remote_dh, st->remote_key, sizeof(st->remote_key)), "getting remote pubkey");
- if (!memcmp(st->remote_key, st->remote_key_reference, sizeof(st->remote_key))) { /* keys match */
+ /* TODO support list of known remote hosts here instead of just one */
+ uint8_t remote_fp[BLAKE2S_HASH_SIZE];
+ BLAKE2s_context_t bc;
+ BLAKE2s_reset(&bc);
+ BLAKE2s_update(&bc, st->remote_key, sizeof(st->remote_key));
+ BLAKE2s_finish(&bc, remote_fp);
+
+ if (!memcmp(remote_fp, st->remote_key_reference, sizeof(remote_fp))) { /* keys match */
uint8_t response = REPORT_PAIRING_SUCCESS;
if (send_encrypted_message(st, &response, sizeof(response)))
LOG_PRINTF("Error sending pairing response packet\n");
@@ -177,7 +188,10 @@ errout:
}
void persist_remote_key(struct NoiseState *st) {
- memcpy(st->remote_key_reference, st->remote_key, sizeof(st->remote_key));
+ BLAKE2s_context_t bc;
+ BLAKE2s_reset(&bc);
+ BLAKE2s_update(&bc, st->remote_key, sizeof(st->remote_key));
+ BLAKE2s_finish(&bc, st->remote_key_reference);
st->handshake_state = HANDSHAKE_DONE_KNOWN_HOST;
}
diff --git a/src/noise.h b/src/noise.h
index a4c1e6e..92acdcf 100644
--- a/src/noise.h
+++ b/src/noise.h
@@ -30,7 +30,7 @@ struct NoiseState {
NoiseHandshakeState *handshake;
enum handshake_state handshake_state;
NoiseCipherState *tx_cipher, *rx_cipher;
- uint8_t local_key[CURVE25519_KEY_LEN];
+ uint8_t *local_key;
uint8_t remote_key[CURVE25519_KEY_LEN];
uint8_t *remote_key_reference;
uint8_t handshake_hash[BLAKE2S_HASH_SIZE];
@@ -39,7 +39,7 @@ struct NoiseState {
void uninit_handshake(struct NoiseState *st, enum handshake_state new_state);
-void noise_state_init(struct NoiseState *st, uint8_t *remote_key_reference);
+void noise_state_init(struct NoiseState *st, uint8_t *remote_key_reference, uint8_t *local_key);
void persist_remote_key(struct NoiseState *st);
int start_protocol_handshake(struct NoiseState *st);
int reset_protocol_handshake(struct NoiseState *st);