diff options
author | jaseg <git@jaseg.de> | 2021-03-24 14:17:28 +0100 |
---|---|---|
committer | jaseg <git@jaseg.de> | 2021-03-24 14:17:28 +0100 |
commit | dbb264c68d658e5c851c0b3926f5465196e486df (patch) | |
tree | 1c03c543bbb01e29533480ebbe6df1ed407b18f5 /fw/src | |
parent | 4fcc3337e21089b50a1034fa05c69d4bd7b84640 (diff) | |
download | secure-hid-dbb264c68d658e5c851c0b3926f5465196e486df.tar.gz secure-hid-dbb264c68d658e5c851c0b3926f5465196e486df.tar.bz2 secure-hid-dbb264c68d658e5c851c0b3926f5465196e486df.zip |
Make keyboard emulation for debug work
Diffstat (limited to 'fw/src')
-rw-r--r-- | fw/src/demo.c | 204 |
1 files changed, 174 insertions, 30 deletions
diff --git a/fw/src/demo.c b/fw/src/demo.c index 69f8e8e..5ceecec 100644 --- a/fw/src/demo.c +++ b/fw/src/demo.c @@ -191,9 +191,12 @@ static void gpio_setup(void) /* Mode button */
gpio_mode_setup(GPIOE, GPIO_MODE_INPUT, GPIO_PUPD_PULLUP, GPIO15);
+ /* Test button */
+ gpio_mode_setup(GPIOB, GPIO_MODE_INPUT, GPIO_PUPD_PULLUP, GPIO10);
+
/* Speaker */
- gpio_mode_setup(GPIOB, GPIO_MODE_OUTPUT, GPIO_PUPD_NONE, GPIO10);
- gpio_set(GPIOB, GPIO10);
+ //gpio_mode_setup(GPIOB, GPIO_MODE_OUTPUT, GPIO_PUPD_NONE, GPIO10);
+ //gpio_set(GPIOB, GPIO10);
/* USB OTG FS phy outputs */
gpio_mode_setup(GPIOA, GPIO_MODE_AF, GPIO_PUPD_NONE, GPIO11 | GPIO12);
@@ -222,7 +225,7 @@ void pairing_input(uint8_t modbyte, uint8_t keycode); void pairing_parse_report(struct hid_report *buf, uint8_t len);
/* Minimum number of bytes of handshake hash to confirm during pairing */
-#define MIN_PAIRING_SEQUENCE_LENGTH 4
+#define MIN_PAIRING_SEQUENCE_LENGTH 1
int pairing_check(struct NoiseState *st, const char *buf) {
//LOG_PRINTF("Checking pairing\n");
@@ -439,6 +442,12 @@ struct dma_usart_file debug_out_s = { struct dma_usart_file *debug_out = &debug_out_s;
/* FIXME start unsafe debug code */
+bool debug_emulate_pairing_input(char c);
+bool debug_fill_report_from_ascii(char c, struct hid_report *out);
+bool debug_send_encrypted_emulated_report(char c);
+bool debug_enqueue_emulated_input(char c);
+
+/* Feed keyboard input from debug UART into keyboard subsystem */
void usart1_isr(void) {
if (USART1_SR & USART_SR_ORE) { /* Overrun handling */
LOG_PRINTF("USART1 data register overrun\n");
@@ -448,30 +457,126 @@ void usart1_isr(void) { }
uint8_t data = USART1_DR; /* This automatically acknowledges the IRQ */
+
+ LOG_PRINTF(" %02x ", data);
+ if (data == '\r')
+ LOG_PRINTF("\n");
+
+ if (noise_state.handshake_state == HANDSHAKE_DONE_UNKNOWN_HOST) {
+ if (!debug_emulate_pairing_input(data)) {
+ LOG_PRINTF("Error emulating pairing input\n");
+ }
+
+ } else {
+ if (!debug_enqueue_emulated_input(data)) {
+ LOG_PRINTF("Error enqueueing emulated keystroke\n");
+ }
+ }
+}
+
+size_t debug_keystroke_queue_wptr = 0;
+size_t debug_keystroke_queue_rptr = 0;
+#define ARRAY_LENGTH(x) (sizeof(x) / sizeof((x)[0]))
+char debug_keystroke_queue[64];
+
+bool debug_enqueue_emulated_input(char c) {
+ size_t next_wptr = (debug_keystroke_queue_wptr + 1) % ARRAY_LENGTH(debug_keystroke_queue);
+
+ if (next_wptr == debug_keystroke_queue_rptr)
+ return false; /* overflow */
+
+ debug_keystroke_queue[debug_keystroke_queue_wptr] = c;
+ debug_keystroke_queue_wptr = next_wptr;
+ return true;
+}
+
+int debug_dequeue_emulated_input() {
+ if (debug_keystroke_queue_rptr == debug_keystroke_queue_wptr) {
+ return -1; /* queue empty */
+ }
+
+ int rc = debug_keystroke_queue[debug_keystroke_queue_rptr];
+ debug_keystroke_queue_rptr = (debug_keystroke_queue_rptr + 1) % ARRAY_LENGTH(debug_keystroke_queue);
+ return (unsigned char)rc; /* cast into range 0-255 */
+}
+
+/* Lookup ASCII char and fill in corresponding HID keycode in HID report.
+ *
+ * Returns true if char was found in keycode mapping.
+ */
+bool debug_fill_report_from_ascii(char c, struct hid_report *out) {
+ memset(out, 0, sizeof(out));
+
for (size_t i=0; keycode_mapping[i].kc != KEY_NONE; i++) {
- struct hid_report report = {0};
- if (keycode_mapping[i].ch[0] == data)
- report.modifiers = 0;
- else if (keycode_mapping[i].ch[1] == data)
- report.modifiers = MOD_LSHIFT;
+ if (keycode_mapping[i].ch[0] == c)
+ out->modifiers = 0;
+ else if (keycode_mapping[i].ch[1] == c)
+ out->modifiers = MOD_LSHIFT;
else continue;
- report.keycodes[0] = keycode_mapping[i].kc;
- pairing_parse_report(&report, 8);
- break;
+ out->keycodes[0] = keycode_mapping[i].kc;
+ return true;
}
- LOG_PRINTF(" %02x ", data);
- if (data == 0x7f) {
- struct hid_report report = {.modifiers=0, .keycodes={KEY_BACKSPACE, 0}};
- pairing_parse_report(&report, 8);
- } else if (data == '\r') {
- struct hid_report report = {.modifiers=0, .keycodes={KEY_ENTER, 0}};
- pairing_parse_report(&report, 8);
- LOG_PRINTF("\n");
+
+ if (c == 0x7f) {
+ out->modifiers = 0;
+ out->keycodes[0] = KEY_BACKSPACE;
+ return true;
+
+ } else if (c == '\r') {
+ out->modifiers = 0;
+ out->keycodes[0] = KEY_ENTER;
+ return true;
+ }
+
+ return false; /* not found */
+}
+
+/* Returns true on success */
+bool debug_emulate_pairing_input(char c) {
+ struct hid_report report;
+ if (!debug_fill_report_from_ascii(c, &report)) {
+ return false;
}
- struct hid_report report = {0};
+ /* Emulate key press input */
+ pairing_parse_report(&report, 8);
+
+ /* key release */
+ memset(&report, 0, sizeof(report));
pairing_parse_report(&report, 8);
+
+ return true;
+}
+
+/* Returns true on success */
+bool debug_send_encrypted_emulated_report(char c) {
+ struct hid_report_packet pkt = {
+ .type = REPORT_KEYBOARD,
+ .report = {
+ .len = 8,
+ .report = {0}
+ }
+ };
+
+ /* key press */
+ if (!debug_fill_report_from_ascii(c, &pkt.report.report))
+ return false;
+
+ if (send_encrypted_message(&noise_state, (uint8_t *)&pkt, sizeof(pkt))) {
+ LOG_PRINTF("Error sending emulated HID report packet\n");
+ return false;
+ }
+
+ /* key release */
+ memset(&pkt.report.report, 0, sizeof(struct hid_report));
+
+ if (send_encrypted_message(&noise_state, (uint8_t *)&pkt, sizeof(pkt))) {
+ LOG_PRINTF("Error sending emulated HID report packet\n");
+ return false;
+ }
+
+ return true;
}
/* end unsafe debug code */
@@ -605,25 +710,64 @@ int main(void) int spk_inc = 1;
gpio_clear(GPIOA, GPIO6);
gpio_clear(GPIOA, GPIO7);
- gpio_clear(GPIOB, GPIO10);
+ //gpio_clear(GPIOB, GPIO10);
- int last_btn_st = 0;
- int debounce_ctr = 0;
+ int last_btn_st_mode = 0;
+ int last_btn_st_test = 0;
+ int debounce_ctr_mode = 0;
+ int debounce_ctr_test = 0;
int mode_debug = 0;
#define DEBOUNCE_IVL 1000
gpio_set(GPIOE, GPIO13);
gpio_clear(GPIOE, GPIO14);
+ int dbg_keyem_ctr = 0;
+#define DBG_KEYEM_IVL 100
+
while (23) {
delay(1);
- if (debounce_ctr > 0) {
- debounce_ctr -= 1;
+ if (dbg_keyem_ctr <= 0) {
+ int rc = debug_dequeue_emulated_input();
+ if (rc >= 0) {
+ dbg_keyem_ctr = DBG_KEYEM_IVL;
+ if (!debug_send_encrypted_emulated_report((char) rc)) {
+ LOG_PRINTF("Error sending emulated keyboard input\n");
+ } else {
+ LOG_PRINTF("Sent emulated keypress %02x\n", (unsigned char)rc);
+ }
+ }
+ } else {
+ dbg_keyem_ctr -= 1;
+ }
+
+ if (debounce_ctr_test > 0) {
+ debounce_ctr_test -= 1;
+ } else {
+ if (!gpio_get(GPIOB, GPIO10)) {
+ if (last_btn_st_test) {
+ debounce_ctr_test = DEBOUNCE_IVL;
+
+ const char *s = "unicorn\r";
+ for (size_t i=0; i<8; i++) {
+ if (!debug_enqueue_emulated_input(s[i])) {
+ LOG_PRINTF("Error enqueuing emulated test input\n");
+ }
+ }
+ }
+ last_btn_st_test = 0;
+ } else {
+ last_btn_st_test = 1;
+ }
+ }
+
+ if (debounce_ctr_mode > 0) {
+ debounce_ctr_mode -= 1;
} else {
- if (gpio_get(GPIOE, GPIO15)) {
- if (!last_btn_st) {
- debounce_ctr = DEBOUNCE_IVL;
+ if (!gpio_get(GPIOE, GPIO15)) {
+ if (last_btn_st_mode) {
+ debounce_ctr_mode = DEBOUNCE_IVL;
mode_debug = !mode_debug;
@@ -637,10 +781,10 @@ int main(void) }
}
- last_btn_st = 1;
+ last_btn_st_mode = 0;
} else {
- last_btn_st = 0;
+ last_btn_st_mode = 1;
}
}
|