diff --git a/fido2/ctap.c b/fido2/ctap.c index 553b20e..ecdff80 100644 --- a/fido2/ctap.c +++ b/fido2/ctap.c @@ -1536,7 +1536,7 @@ static void ctap_state_init() ctap_reset_rk(); } -void ctap_init(int init_pin) +void ctap_init() { crypto_ecc256_init(); @@ -1591,7 +1591,7 @@ void ctap_init(int init_pin) exit(1); } - if (init_pin) + if (! device_is_nfc()) { crypto_ecc256_make_key_pair(KEY_AGREEMENT_PUB, KEY_AGREEMENT_PRIV); } diff --git a/fido2/ctap.h b/fido2/ctap.h index a6db27d..a3a8783 100644 --- a/fido2/ctap.h +++ b/fido2/ctap.h @@ -267,7 +267,7 @@ uint8_t ctap_request(uint8_t * pkt_raw, int length, CTAP_RESPONSE * resp); int ctap_encode_der_sig(uint8_t const * const in_sigbuf, uint8_t * const out_sigder); // Run ctap related power-up procedures (init pinToken, generate shared secret) -void ctap_init(int init_pin); +void ctap_init(); // Resets state between different accesses of different applications void ctap_reset_state(); diff --git a/targets/stm32l432/src/ams.c b/targets/stm32l432/src/ams.c index 7b2438a..335758f 100644 --- a/targets/stm32l432/src/ams.c +++ b/targets/stm32l432/src/ams.c @@ -6,6 +6,7 @@ #include "log.h" #include "util.h" #include "device.h" +#include "nfc.h" static void flush_rx() { @@ -269,11 +270,8 @@ void ams_print_int1(uint8_t int0) #endif } - -bool ams_init() +void ams_init() { - uint8_t block[4]; - LL_GPIO_SetPinMode(SOLO_AMS_CS_PORT,SOLO_AMS_CS_PIN,LL_GPIO_MODE_OUTPUT); LL_GPIO_SetOutputPin(SOLO_AMS_CS_PORT,SOLO_AMS_CS_PIN); @@ -284,85 +282,85 @@ bool ams_init() // delay(10); SELECT(); - delay(2); + delay(1); +} - // Needs to be disabled for passive operation - if (0) - // if (1) +void ams_configure() +{ + // Should not be used during passive operation. + uint8_t block[4]; + + // check connection + uint8_t productType = ams_read_reg(AMS_REG_PRODUCT_TYPE); + if (productType != 0x14) { - // check connection - uint8_t productType = ams_read_reg(AMS_REG_PRODUCT_TYPE); - if (productType != 0x14) - { - printf1(TAG_NFC, "Have wrong product type [0x%02x]. AMS3956 connection error.\n", productType); - return false; - } + printf1(TAG_ERR, "Have wrong product type [0x%02x]. AMS3956 connection error.\n", productType); + } - printf1(TAG_NFC,"AMS3956 product type 0x%02x.\n", productType); + printf1(TAG_NFC,"AMS3956 product type 0x%02x.\n", productType); - ams_read_eeprom_block(AMS_CONFIG_UID_ADDR, block); - printf1(TAG_NFC,"UID: 3F 14 02 - "); dump_hex1(TAG_NFC,block,4); + ams_read_eeprom_block(AMS_CONFIG_UID_ADDR, block); + printf1(TAG_NFC,"UID: 3F 14 02 - "); dump_hex1(TAG_NFC,block,4); + + ams_read_eeprom_block(AMS_CONFIG_BLOCK0_ADDR, block); + printf1(TAG_NFC,"conf0: "); dump_hex1(TAG_NFC,block,4); + + uint8_t sense1 = 0x44; + uint8_t sense2 = 0x00; + uint8_t selr = 0x20; // SAK + + if(block[0] != sense1 || block[1] != sense2 || block[2] != selr) + { + printf1(TAG_NFC,"Writing config block 0\r\n"); + block[0] = sense1; + block[1] = sense2; + block[2] = selr; + block[3] = 0x00; + + ams_write_eeprom_block(AMS_CONFIG_BLOCK0_ADDR, block); + UNSELECT(); + delay(10); + SELECT(); + delay(10); ams_read_eeprom_block(AMS_CONFIG_BLOCK0_ADDR, block); printf1(TAG_NFC,"conf0: "); dump_hex1(TAG_NFC,block,4); - - uint8_t sense1 = 0x44; - uint8_t sense2 = 0x00; - uint8_t selr = 0x20; // SAK - - if(block[0] != sense1 || block[1] != sense2 || block[2] != selr) - { - printf1(TAG_NFC,"Writing config block 0\r\n"); - block[0] = sense1; - block[1] = sense2; - block[2] = selr; - block[3] = 0x00; - - ams_write_eeprom_block(AMS_CONFIG_BLOCK0_ADDR, block); - UNSELECT(); - delay(10); - SELECT(); - delay(10); - - ams_read_eeprom_block(AMS_CONFIG_BLOCK0_ADDR, block); - printf1(TAG_NFC,"conf0: "); dump_hex1(TAG_NFC,block,4); - } - - ams_read_eeprom_block(AMS_CONFIG_BLOCK1_ADDR, block); - printf1(TAG_NFC,"conf1: "); dump_hex1(TAG_NFC,block,4); - - uint8_t ic_cfg1 = AMS_CFG1_OUTPUT_RESISTANCE_100 | AMS_CFG1_VOLTAGE_LEVEL_2V0; - uint8_t ic_cfg2 = AMS_CFG2_TUN_MOD; - - if (block[0] != ic_cfg1 || block[1] != ic_cfg2) - { - - printf1(TAG_NFC,"Writing config block 1\r\n"); - - ams_write_reg(AMS_REG_IC_CONF1,ic_cfg1); - ams_write_reg(AMS_REG_IC_CONF2,ic_cfg2); - - // set IC_CFG1 - block[0] = ic_cfg1; - - // set IC_CFG2 - block[1] = ic_cfg2; - - // mask interrupt bits - block[2] = 0x80; - block[3] = 0; - - ams_write_eeprom_block(AMS_CONFIG_BLOCK1_ADDR, block); - - UNSELECT(); - delay(10); - SELECT(); - delay(10); - - ams_read_eeprom_block(0x7F, block); - printf1(TAG_NFC,"conf1: "); dump_hex1(TAG_NFC,block,4); - } } - return true; + ams_read_eeprom_block(AMS_CONFIG_BLOCK1_ADDR, block); + printf1(TAG_NFC,"conf1: "); dump_hex1(TAG_NFC,block,4); + + uint8_t ic_cfg1 = AMS_CFG1_OUTPUT_RESISTANCE_100 | AMS_CFG1_VOLTAGE_LEVEL_2V0; + uint8_t ic_cfg2 = AMS_CFG2_TUN_MOD; + + if (block[0] != ic_cfg1 || block[1] != ic_cfg2) + { + + printf1(TAG_NFC,"Writing config block 1\r\n"); + + ams_write_reg(AMS_REG_IC_CONF1,ic_cfg1); + ams_write_reg(AMS_REG_IC_CONF2,ic_cfg2); + + // set IC_CFG1 + block[0] = ic_cfg1; + + // set IC_CFG2 + block[1] = ic_cfg2; + + // mask interrupt bits + block[2] = 0x80; + block[3] = 0; + + ams_write_eeprom_block(AMS_CONFIG_BLOCK1_ADDR, block); + + UNSELECT(); + delay(10); + SELECT(); + delay(10); + + ams_read_eeprom_block(0x7F, block); + printf1(TAG_NFC,"conf1: "); dump_hex1(TAG_NFC,block,4); + } + + } diff --git a/targets/stm32l432/src/ams.h b/targets/stm32l432/src/ams.h index d8e3cad..ef701bf 100644 --- a/targets/stm32l432/src/ams.h +++ b/targets/stm32l432/src/ams.h @@ -39,7 +39,8 @@ typedef union #define SELECT() LL_GPIO_ResetOutputPin(SOLO_AMS_CS_PORT,SOLO_AMS_CS_PIN) #define UNSELECT() LL_GPIO_SetOutputPin(SOLO_AMS_CS_PORT,SOLO_AMS_CS_PIN) -bool ams_init(); +void ams_init(); +void ams_configure(); void ams_read_buffer(uint8_t * data, int len); void ams_write_buffer(uint8_t * data, int len); diff --git a/targets/stm32l432/src/app.h b/targets/stm32l432/src/app.h index 5753d14..8570d24 100644 --- a/targets/stm32l432/src/app.h +++ b/targets/stm32l432/src/app.h @@ -30,7 +30,7 @@ // #define DISABLE_CTAPHID_WINK // #define DISABLE_CTAPHID_CBOR -// #define ENABLE_SERIAL_PRINTING +#define ENABLE_SERIAL_PRINTING #if defined(SOLO_HACKER) #define SOLO_PRODUCT_NAME "Solo Hacker " SOLO_VERSION diff --git a/targets/stm32l432/src/device.c b/targets/stm32l432/src/device.c index 7562c75..d65b7f8 100644 --- a/targets/stm32l432/src/device.c +++ b/targets/stm32l432/src/device.c @@ -60,7 +60,7 @@ void TIM6_DAC_IRQHandler() } #ifndef IS_BOOTLOADER // NFC sending WTX if needs - if (haveNFC) + if (device_is_nfc()) { WTX_timer_exec(); } @@ -113,26 +113,32 @@ void device_init() hw_init(LOW_FREQUENCY); isLowFreq = 1; - printf1(TAG_NFC,"PWR->CR1: %04x\r\n", LL_PWR_GetRegulVoltageScaling()); + haveNFC = nfc_init(); - // hw_init(HIGH_FREQUENCY); - // isLowFreq = 0; + if (haveNFC) + { + printf1(TAG_NFC, "Have NFC\r\n"); + } + else + { + printf1(TAG_NFC, "Have NO NFC\r\n"); + hw_init(HIGH_FREQUENCY); + + isLowFreq = 0; + } usbhid_init(); ctaphid_init(); - ctap_init( 0 ); + ctap_init( !haveNFC ); -#ifndef IS_BOOTLOADER #if BOOT_TO_DFU flash_option_bytes_init(1); #else flash_option_bytes_init(0); #endif - printf1(TAG_GEN,"init nfc\n"); - haveNFC = nfc_init(); -#endif + } @@ -430,7 +436,7 @@ void device_manage() } #endif #ifndef IS_BOOTLOADER - if(haveNFC) + // if(device_is_nfc()) nfc_loop(); #endif } diff --git a/targets/stm32l432/src/init.c b/targets/stm32l432/src/init.c index 4834e5d..3e704ea 100644 --- a/targets/stm32l432/src/init.c +++ b/targets/stm32l432/src/init.c @@ -808,6 +808,8 @@ void init_debug_uart(void) /* Peripheral clock enable */ LL_APB2_GRP1_EnableClock(LL_APB2_GRP1_PERIPH_USART1); + + LL_USART_DeInit(USART1); /**USART1 GPIO Configuration PB6 ------> USART1_TX PB7 ------> USART1_RX diff --git a/targets/stm32l432/src/nfc.c b/targets/stm32l432/src/nfc.c index dc66235..ab0ddf3 100644 --- a/targets/stm32l432/src/nfc.c +++ b/targets/stm32l432/src/nfc.c @@ -57,8 +57,23 @@ void nfc_state_init() bool nfc_init() { + uint32_t t1; nfc_state_init(); - return ams_init(); + ams_init(); + + // Detect if we are powered by NFC field by listening for a message for + // first 25 ms. + t1 = millis(); + while ((millis() - t1) < 25) + { + if (nfc_loop() > 0) + return 1; + } + + // Under USB power. Configure AMS chip. + ams_configure(); + + return 0; } void process_int0(uint8_t int0) @@ -699,88 +714,86 @@ void nfc_process_block(uint8_t * buf, unsigned int len) } } -void nfc_loop() +int nfc_loop() { uint8_t buf[32]; AMS_DEVICE ams; int len = 0; - if (1) + read_reg_block(&ams); + uint8_t state = AMS_STATE_MASK & ams.regs.rfid_status; + + if (state != AMS_STATE_SELECTED && state != AMS_STATE_SELECTEDX) { - read_reg_block(&ams); - uint8_t state = AMS_STATE_MASK & ams.regs.rfid_status; + // delay(1); // sleep ? + return 0; + } - if (state != AMS_STATE_SELECTED && state != AMS_STATE_SELECTEDX) - { - // delay(1); // sleep ? - return; - } + if (ams.regs.rfid_status) + { + // if (state != AMS_STATE_SENSE) + // printf1(TAG_NFC," %s x%02x\r\n", ams_get_state_string(ams.regs.rfid_status), state); + } + if (ams.regs.int0 & AMS_INT_INIT) + { + nfc_state_init(); + } + if (ams.regs.int1) + { + // ams_print_int1(ams.regs.int1); + } - if (ams.regs.rfid_status) + if ((ams.regs.int0 & AMS_INT_RXE)) + { + if (ams.regs.buffer_status2) { - // if (state != AMS_STATE_SENSE) - // printf1(TAG_NFC," %s x%02x\r\n", ams_get_state_string(ams.regs.rfid_status), state); - } - if (ams.regs.int0 & AMS_INT_INIT) - { - nfc_state_init(); - } - if (ams.regs.int1) - { - // ams_print_int1(ams.regs.int1); - } - - if ((ams.regs.int0 & AMS_INT_RXE)) - { - if (ams.regs.buffer_status2) + if (ams.regs.buffer_status2 & AMS_BUF_INVALID) { - if (ams.regs.buffer_status2 & AMS_BUF_INVALID) - { - printf1(TAG_NFC,"Buffer being updated!\r\n"); - } - else - { - len = ams.regs.buffer_status2 & AMS_BUF_LEN_MASK; - ams_read_buffer(buf, len); - } + printf1(TAG_NFC,"Buffer being updated!\r\n"); + } + else + { + len = ams.regs.buffer_status2 & AMS_BUF_LEN_MASK; + ams_read_buffer(buf, len); } } + } - if (len) + if (len) + { + + // ISO 14443-3 + switch(buf[0]) { + case NFC_CMD_REQA: + printf1(TAG_NFC, "NFC_CMD_REQA\r\n"); + break; + case NFC_CMD_WUPA: + printf1(TAG_NFC, "NFC_CMD_WUPA\r\n"); + break; + case NFC_CMD_HLTA: + printf1(TAG_NFC, "HLTA/Halt\r\n"); + break; + case NFC_CMD_RATS: - // ISO 14443-3 - switch(buf[0]) - { - case NFC_CMD_REQA: - printf1(TAG_NFC, "NFC_CMD_REQA\r\n"); - break; - case NFC_CMD_WUPA: - printf1(TAG_NFC, "NFC_CMD_WUPA\r\n"); - break; - case NFC_CMD_HLTA: - printf1(TAG_NFC, "HLTA/Halt\r\n"); - break; - case NFC_CMD_RATS: + answer_rats(buf[1]); - answer_rats(buf[1]); + NFC_STATE.block_num = 1; + clear_ibuf(); + WTX_clear(); + break; + default: - NFC_STATE.block_num = 1; - clear_ibuf(); - WTX_clear(); - break; - default: - - // ISO 14443-4 - nfc_process_block(buf,len); + // ISO 14443-4 + nfc_process_block(buf,len); - break; - } - + break; } } + return len; + } diff --git a/targets/stm32l432/src/nfc.h b/targets/stm32l432/src/nfc.h index 2388018..a8627a2 100644 --- a/targets/stm32l432/src/nfc.h +++ b/targets/stm32l432/src/nfc.h @@ -5,7 +5,9 @@ #include #include "apdu.h" -void nfc_loop(); +// Return number of bytes read if any. +int nfc_loop(); + bool nfc_init(); typedef struct