Adding DEK to private keys.
Signed-off-by: Pol Henarejos <pol.henarejos@cttc.es>
This commit is contained in:
@@ -136,9 +136,10 @@ file_t file_entries[] = {
|
|||||||
/* 49 */ { .fid = EF_PB_DEC, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_R_WP },
|
/* 49 */ { .fid = EF_PB_DEC, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_R_WP },
|
||||||
/* 50 */ { .fid = EF_PB_AUT, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_R_WP },
|
/* 50 */ { .fid = EF_PB_AUT, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_R_WP },
|
||||||
/* 51 */ { .fid = EF_PW_PRIV, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_R_WP },
|
/* 51 */ { .fid = EF_PW_PRIV, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_R_WP },
|
||||||
|
/* 52 */ { .fid = EF_DEK, .parent = 0, .name = NULL, .type = FILE_TYPE_INTERNAL_EF | FILE_DATA_FLASH, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_NONE },
|
||||||
|
|
||||||
/* 52 */ { .fid = 0x0000, .parent = 0, .name = openpgp_aid, .type = FILE_TYPE_WORKING_EF, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_RO },
|
/* 53 */ { .fid = 0x0000, .parent = 0, .name = openpgp_aid, .type = FILE_TYPE_WORKING_EF, .data = NULL, .ef_structure = FILE_EF_TRANSPARENT, .acl = ACL_RO },
|
||||||
/* 53 */ { .fid = 0x0000, .parent = 0xff, .name = NULL, .type = FILE_TYPE_UNKNOWN, .data = NULL, .ef_structure = 0, .acl = ACL_NONE } //end
|
/* 54 */ { .fid = 0x0000, .parent = 0xff, .name = NULL, .type = FILE_TYPE_UNKNOWN, .data = NULL, .ef_structure = 0, .acl = ACL_NONE } //end
|
||||||
};
|
};
|
||||||
|
|
||||||
const file_t *MF = &file_entries[0];
|
const file_t *MF = &file_entries[0];
|
||||||
|
|||||||
@@ -34,6 +34,7 @@
|
|||||||
#define EF_PB_SIG 0x10d4
|
#define EF_PB_SIG 0x10d4
|
||||||
#define EF_PB_DEC 0x10d5
|
#define EF_PB_DEC 0x10d5
|
||||||
#define EF_PB_AUT 0x10d6
|
#define EF_PB_AUT 0x10d6
|
||||||
|
#define EF_DEK 0x1099
|
||||||
|
|
||||||
#define EF_EXT_HEADER 0x004d //C
|
#define EF_EXT_HEADER 0x004d //C
|
||||||
#define EF_FULL_AID 0x004f //S
|
#define EF_FULL_AID 0x004f //S
|
||||||
|
|||||||
@@ -30,7 +30,9 @@
|
|||||||
bool has_pw1 = false;
|
bool has_pw1 = false;
|
||||||
bool has_pw2 = false;
|
bool has_pw2 = false;
|
||||||
bool has_pw3 = false;
|
bool has_pw3 = false;
|
||||||
|
uint8_t session_pw1[32];
|
||||||
uint8_t session_pw3[32];
|
uint8_t session_pw3[32];
|
||||||
|
static uint8_t dek[IV_SIZE+32];
|
||||||
|
|
||||||
uint8_t openpgp_aid[] = {
|
uint8_t openpgp_aid[] = {
|
||||||
6,
|
6,
|
||||||
@@ -186,9 +188,72 @@ void scan_files() {
|
|||||||
flash_write_data_to_file(ef, def, sizeof(def));
|
flash_write_data_to_file(ef, def, sizeof(def));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if ((ef = search_by_fid(EF_DEK, NULL, SPECIFY_ANY))) {
|
||||||
|
if (!ef->data) {
|
||||||
|
TU_LOG1("DEK is empty\r\n");
|
||||||
|
const uint8_t def1[6] = { 0x31,0x32,0x33,0x34,0x35,0x36 };
|
||||||
|
const uint8_t def3[8] = { 0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38 };
|
||||||
|
|
||||||
|
uint8_t def[IV_SIZE+32+32];
|
||||||
|
const uint8_t *dek = random_bytes_get(IV_SIZE+32);
|
||||||
|
memcpy(def, dek, IV_SIZE+32);
|
||||||
|
memcpy(def+IV_SIZE+32, dek+IV_SIZE, 32);
|
||||||
|
hash_multi(def1, sizeof(def1), session_pw1);
|
||||||
|
aes_encrypt_cfb_256(session_pw1, def, def+IV_SIZE, 32);
|
||||||
|
memset(session_pw1, 0, sizeof(session_pw1));
|
||||||
|
|
||||||
|
hash_multi(def3, sizeof(def3), session_pw3);
|
||||||
|
aes_encrypt_cfb_256(session_pw3, def, def+IV_SIZE+32, 32);
|
||||||
|
memset(session_pw1, 0, sizeof(session_pw1));
|
||||||
|
flash_write_data_to_file(ef, def, sizeof(def));
|
||||||
|
}
|
||||||
|
}
|
||||||
low_flash_available();
|
low_flash_available();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int load_dek() {
|
||||||
|
if (!has_pw1 && !has_pw2 && !has_pw3)
|
||||||
|
return CCID_NO_LOGIN;
|
||||||
|
file_t *tf = search_by_fid(EF_DEK, NULL, SPECIFY_EF);
|
||||||
|
if (!tf)
|
||||||
|
return CCID_ERR_FILE_NOT_FOUND;
|
||||||
|
int r = CCID_OK;
|
||||||
|
if (has_pw1 || has_pw2) {
|
||||||
|
memcpy(dek, file_read(tf->data+sizeof(uint16_t)), IV_SIZE+32);
|
||||||
|
r = aes_decrypt_cfb_256(session_pw1, dek, dek+IV_SIZE, 32);
|
||||||
|
}
|
||||||
|
else if (has_pw3) {
|
||||||
|
memcpy(dek, file_read(tf->data+sizeof(uint16_t)), IV_SIZE);
|
||||||
|
memcpy(dek+IV_SIZE, file_read(tf->data+sizeof(uint16_t)+IV_SIZE+32), 32);
|
||||||
|
r = aes_decrypt_cfb_256(session_pw3, dek, dek+IV_SIZE, 32);
|
||||||
|
}
|
||||||
|
if (r != 0)
|
||||||
|
return CCID_EXEC_ERROR;
|
||||||
|
return CCID_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
void release_dek() {
|
||||||
|
memset(dek, 0, sizeof(dek));
|
||||||
|
}
|
||||||
|
|
||||||
|
int dek_encrypt(uint8_t *data, size_t len) {
|
||||||
|
int r;
|
||||||
|
if ((r = load_dek()) != CCID_OK)
|
||||||
|
return r;
|
||||||
|
r = aes_encrypt_cfb_256(dek+IV_SIZE, dek, data, len);
|
||||||
|
release_dek();
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
int dek_decrypt(uint8_t *data, size_t len) {
|
||||||
|
int r;
|
||||||
|
if ((r = load_dek()) != CCID_OK)
|
||||||
|
return r;
|
||||||
|
r = aes_decrypt_cfb_256(dek+IV_SIZE, dek, data, len);
|
||||||
|
release_dek();
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
void init_openpgp() {
|
void init_openpgp() {
|
||||||
isUserAuthenticated = false;
|
isUserAuthenticated = false;
|
||||||
has_pw1 = has_pw3 = false;
|
has_pw1 = has_pw3 = false;
|
||||||
@@ -707,6 +772,7 @@ int check_pin(const file_t *pin, const uint8_t *data, size_t len) {
|
|||||||
has_pw1 = true;
|
has_pw1 = true;
|
||||||
else
|
else
|
||||||
has_pw2 = true;
|
has_pw2 = true;
|
||||||
|
hash_multi(data, len, session_pw1);
|
||||||
}
|
}
|
||||||
else if (pin->fid == EF_PW3) {
|
else if (pin->fid == EF_PW3) {
|
||||||
has_pw3 = true;
|
has_pw3 = true;
|
||||||
@@ -869,6 +935,10 @@ int store_keys(void *key_ctx, int type, uint16_t key_id) {
|
|||||||
key_size = 32;
|
key_size = 32;
|
||||||
memcpy(kdata, key_ctx, key_size);
|
memcpy(kdata, key_ctx, key_size);
|
||||||
}
|
}
|
||||||
|
r = dek_encrypt(kdata, key_size);
|
||||||
|
if (r != CCID_OK) {
|
||||||
|
return r;
|
||||||
|
}
|
||||||
//r = aes_encrypt_cfb_256(file_read(pw3->data+2), session_pw3, kdata, key_size);
|
//r = aes_encrypt_cfb_256(file_read(pw3->data+2), session_pw3, kdata, key_size);
|
||||||
//if (r != CCID_OK)
|
//if (r != CCID_OK)
|
||||||
// return r;
|
// return r;
|
||||||
@@ -883,15 +953,10 @@ int load_private_key_rsa(mbedtls_rsa_context *ctx, file_t *fkey) {
|
|||||||
//wait_button();
|
//wait_button();
|
||||||
int key_size = file_read_uint16(fkey->data);
|
int key_size = file_read_uint16(fkey->data);
|
||||||
uint8_t kdata[4096/8];
|
uint8_t kdata[4096/8];
|
||||||
//if (!has_pw3)
|
|
||||||
// return CCID_NO_LOGIN;
|
|
||||||
//file_t *pw3 = search_by_fid(EF_PW3, NULL, SPECIFY_EF);
|
|
||||||
//if (!pw3)
|
|
||||||
// return CCID_ERR_FILE_NOT_FOUND;
|
|
||||||
memcpy(kdata, file_read(fkey->data+2), key_size);
|
memcpy(kdata, file_read(fkey->data+2), key_size);
|
||||||
//int r = aes_decrypt_cfb_256(file_read(pw3->data+2), session_pw3, kdata, key_size);
|
if (dek_decrypt(kdata, key_size) != 0) {
|
||||||
//if (r != CCID_OK)
|
return SW_EXEC_ERROR();
|
||||||
// return r;
|
}
|
||||||
if (mbedtls_mpi_read_binary(&ctx->P, kdata, key_size/2) != 0) {
|
if (mbedtls_mpi_read_binary(&ctx->P, kdata, key_size/2) != 0) {
|
||||||
mbedtls_rsa_free(ctx);
|
mbedtls_rsa_free(ctx);
|
||||||
return CCID_WRONG_DATA;
|
return CCID_WRONG_DATA;
|
||||||
@@ -924,6 +989,9 @@ int load_private_key_ecdsa(mbedtls_ecdsa_context *ctx, file_t *fkey) {
|
|||||||
int key_size = file_read_uint16(fkey->data);
|
int key_size = file_read_uint16(fkey->data);
|
||||||
uint8_t kdata[67]; //Worst case, 521 bit + 1byte
|
uint8_t kdata[67]; //Worst case, 521 bit + 1byte
|
||||||
memcpy(kdata, file_read(fkey->data+2), key_size);
|
memcpy(kdata, file_read(fkey->data+2), key_size);
|
||||||
|
if (dek_decrypt(kdata, key_size) != 0) {
|
||||||
|
return SW_EXEC_ERROR();
|
||||||
|
}
|
||||||
mbedtls_ecp_group_id gid = kdata[0];
|
mbedtls_ecp_group_id gid = kdata[0];
|
||||||
int r = mbedtls_ecp_read_key(gid, ctx, kdata+1, key_size-1);
|
int r = mbedtls_ecp_read_key(gid, ctx, kdata+1, key_size-1);
|
||||||
if (r != 0) {
|
if (r != 0) {
|
||||||
@@ -1241,6 +1309,9 @@ static int cmd_pso() {
|
|||||||
if (len != 2*key_size-1)
|
if (len != 2*key_size-1)
|
||||||
return SW_WRONG_LENGTH();
|
return SW_WRONG_LENGTH();
|
||||||
memcpy(kdata, file_read(ef->data+2), key_size);
|
memcpy(kdata, file_read(ef->data+2), key_size);
|
||||||
|
if (dek_decrypt(kdata, key_size) != 0) {
|
||||||
|
return SW_EXEC_ERROR();
|
||||||
|
}
|
||||||
mbedtls_ecdh_init(&ctx);
|
mbedtls_ecdh_init(&ctx);
|
||||||
mbedtls_ecp_group_id gid = kdata[0];
|
mbedtls_ecp_group_id gid = kdata[0];
|
||||||
r = mbedtls_ecdh_setup(&ctx, gid);
|
r = mbedtls_ecdh_setup(&ctx, gid);
|
||||||
|
|||||||
Reference in New Issue
Block a user