diff --git a/fido2/extensions/extensions.c b/fido2/extensions/extensions.c new file mode 100644 index 0000000..9fe1d94 --- /dev/null +++ b/fido2/extensions/extensions.c @@ -0,0 +1,59 @@ +#include +#include "extensions.h" +#include "u2f.h" +#include "wallet.h" + +#include "log.h" + +int16_t extend_u2f(struct u2f_request_apdu* req, uint32_t len) +{ + + struct u2f_authenticate_request * auth = (struct u2f_authenticate_request *) req->payload; + uint16_t rcode; + + if (req->ins == U2F_AUTHENTICATE) + { + if (req->p1 == U2F_AUTHENTICATE_CHECK) + { + + if (is_wallet_device((uint8_t *) &auth->kh, auth->khl)) // Pin requests + { + rcode = U2F_SW_CONDITIONS_NOT_SATISFIED; + } + else + { + rcode = U2F_SW_WRONG_DATA; + } + printf1(TAG_WALLET,"Ignoring U2F request\n"); + goto end; + } + else + { + if ( ! is_wallet_device((uint8_t *) &auth->kh, auth->khl)) // Pin requests + { + rcode = U2F_SW_WRONG_PAYLOAD; + printf1(TAG_WALLET,"Ignoring U2F request\n"); + goto end; + } + rcode = bridge_u2f_to_wallet(auth->chal, auth->app, auth->khl, (uint8_t*)&auth->kh); + } + } + else if (req->ins == U2F_VERSION) + { + printf1(TAG_U2F, "U2F_VERSION\n"); + if (len) + { + rcode = U2F_SW_WRONG_LENGTH; + } + else + { + rcode = u2f_version(); + } + } + else + { + rcode = U2F_SW_INS_NOT_SUPPORTED; + } +end: + return rcode; +} diff --git a/fido2/extensions/extensions.h b/fido2/extensions/extensions.h new file mode 100644 index 0000000..ebeca7e --- /dev/null +++ b/fido2/extensions/extensions.h @@ -0,0 +1,8 @@ + +#ifndef EXTENSIONS_H_ +#define EXTENSIONS_H_ +#include "u2f.h" + +int16_t extend_u2f(struct u2f_request_apdu* req, uint32_t len); + +#endif /* EXTENSIONS_H_ */ diff --git a/fido2/wallet.c b/fido2/extensions/wallet.c similarity index 100% rename from fido2/wallet.c rename to fido2/extensions/wallet.c diff --git a/fido2/wallet.h b/fido2/extensions/wallet.h similarity index 100% rename from fido2/wallet.h rename to fido2/extensions/wallet.h diff --git a/fido2/u2f.c b/fido2/u2f.c index 5f8b51e..861fc3f 100644 --- a/fido2/u2f.c +++ b/fido2/u2f.c @@ -9,7 +9,6 @@ // void u2f_response_writeback(uint8_t * buf, uint8_t len); static int16_t u2f_register(struct u2f_register_request * req); -static int16_t u2f_version(); static int16_t u2f_authenticate(struct u2f_authenticate_request * req, uint8_t control); int8_t u2f_response_writeback(const uint8_t * buf, uint16_t len); void u2f_reset_response(); @@ -18,7 +17,7 @@ static CTAP_RESPONSE * _u2f_resp = NULL; void u2f_request(struct u2f_request_apdu* req, CTAP_RESPONSE * resp) { - uint16_t rcode; + uint16_t rcode = 0; uint64_t t1,t2; uint32_t len = ((req->LC3) | ((uint32_t)req->LC2 << 8) | ((uint32_t)req->LC1 << 16)); uint8_t byte; @@ -31,101 +30,58 @@ void u2f_request(struct u2f_request_apdu* req, CTAP_RESPONSE * resp) rcode = U2F_SW_CLASS_NOT_SUPPORTED; goto end; } -#if defined(BRIDGE_TO_WALLET) || defined(IS_BOOTLOADER) - struct u2f_authenticate_request * auth = (struct u2f_authenticate_request *) req->payload; - - - if (req->ins == U2F_AUTHENTICATE) - { - if (req->p1 == U2F_AUTHENTICATE_CHECK) - { - - - if (is_wallet_device((uint8_t *) &auth->kh, auth->khl)) // Pin requests - { - rcode = U2F_SW_CONDITIONS_NOT_SATISFIED; - } - else - { - rcode = U2F_SW_WRONG_DATA; - } - printf1(TAG_WALLET,"Ignoring U2F request\n"); - goto end; - } - else - { - if ( ! is_wallet_device((uint8_t *) &auth->kh, auth->khl)) // Pin requests - { - rcode = U2F_SW_WRONG_PAYLOAD; - printf1(TAG_WALLET,"Ignoring U2F request\n"); - goto end; - } - rcode = bridge_u2f_to_wallet(auth->chal, auth->app, auth->khl, (uint8_t*)&auth->kh); - } - } - else if (req->ins == U2F_VERSION) - { - printf1(TAG_U2F, "U2F_VERSION\n"); - if (len) - { - rcode = U2F_SW_WRONG_LENGTH; - } - else - { - rcode = u2f_version(); - } - } - else - { - rcode = U2F_SW_INS_NOT_SUPPORTED; - } - -#else - switch(req->ins) - { - case U2F_REGISTER: - printf1(TAG_U2F, "U2F_REGISTER\n"); - if (len != 64) - { - rcode = U2F_SW_WRONG_LENGTH; - } - else - { - t1 = millis(); - rcode = u2f_register((struct u2f_register_request*)req->payload); - t2 = millis(); - printf1(TAG_TIME,"u2f_register time: %d ms\n", t2-t1); - } - break; - case U2F_AUTHENTICATE: - printf1(TAG_U2F, "U2F_AUTHENTICATE\n"); - t1 = millis(); - rcode = u2f_authenticate((struct u2f_authenticate_request*)req->payload, req->p1); - t2 = millis(); - printf1(TAG_TIME,"u2f_authenticate time: %d ms\n", t2-t1); - break; - case U2F_VERSION: - printf1(TAG_U2F, "U2F_VERSION\n"); - if (len) - { - rcode = U2F_SW_WRONG_LENGTH; - } - else - { - rcode = u2f_version(); - } - break; - case U2F_VENDOR_FIRST: - case U2F_VENDOR_LAST: - printf1(TAG_U2F, "U2F_VENDOR\n"); - rcode = U2F_SW_NO_ERROR; - break; - default: - printf1(TAG_ERR, "Error, unknown U2F command\n"); - rcode = U2F_SW_INS_NOT_SUPPORTED; - break; - } +#ifdef ENABLE_U2F_EXTENSIONS + rcode = extend_u2f(req, len); #endif + if (rcode != U2F_SW_NO_ERROR) // If the extension didn't do anything... + { +#ifdef ENABLE_U2F + switch(req->ins) + { + case U2F_REGISTER: + printf1(TAG_U2F, "U2F_REGISTER\n"); + if (len != 64) + { + rcode = U2F_SW_WRONG_LENGTH; + } + else + { + t1 = millis(); + rcode = u2f_register((struct u2f_register_request*)req->payload); + t2 = millis(); + printf1(TAG_TIME,"u2f_register time: %d ms\n", t2-t1); + } + break; + case U2F_AUTHENTICATE: + printf1(TAG_U2F, "U2F_AUTHENTICATE\n"); + t1 = millis(); + rcode = u2f_authenticate((struct u2f_authenticate_request*)req->payload, req->p1); + t2 = millis(); + printf1(TAG_TIME,"u2f_authenticate time: %d ms\n", t2-t1); + break; + case U2F_VERSION: + printf1(TAG_U2F, "U2F_VERSION\n"); + if (len) + { + rcode = U2F_SW_WRONG_LENGTH; + } + else + { + rcode = u2f_version(); + } + break; + case U2F_VENDOR_FIRST: + case U2F_VENDOR_LAST: + printf1(TAG_U2F, "U2F_VENDOR\n"); + rcode = U2F_SW_NO_ERROR; + break; + default: + printf1(TAG_ERR, "Error, unknown U2F command\n"); + rcode = U2F_SW_INS_NOT_SUPPORTED; + break; + } +#endif + } end: if (rcode != U2F_SW_NO_ERROR) @@ -329,7 +285,7 @@ static int16_t u2f_register(struct u2f_register_request * req) return U2F_SW_NO_ERROR; } -static int16_t u2f_version() +int16_t u2f_version() { const char version[] = "U2F_V2"; u2f_response_writeback((uint8_t*)version, sizeof(version)-1); diff --git a/fido2/u2f.h b/fido2/u2f.h index beb5f1b..74eb512 100644 --- a/fido2/u2f.h +++ b/fido2/u2f.h @@ -96,11 +96,7 @@ void u2f_request(struct u2f_request_apdu* req, CTAP_RESPONSE * resp); int8_t u2f_response_writeback(const uint8_t * buf, uint16_t len); void u2f_reset_response(); - -////////////////////////////////////////////////////////////////// -/* Platform specific functions that must be implemented by user */ -////////////////////////////////////////////////////////////////// - +int16_t u2f_version(); #endif /* U2F_H_ */