From 9bf58fe335f0cb305382ae08c6bf1cce390bff78 Mon Sep 17 00:00:00 2001 From: Adam Goodman Date: Mon, 16 Nov 2015 16:54:21 -0500 Subject: [PATCH 001/107] YKCS11: On OS X, use @loader_path rather than @executable_path for dylib paths --- mac.mk | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/mac.mk b/mac.mk index 94549e7..04cfd64 100644 --- a/mac.mk +++ b/mac.mk @@ -63,14 +63,14 @@ doit: PKG_CONFIG_PATH=$(PWD)/tmp/root/lib/pkgconfig ./configure --prefix=$(PWD)/tmp/root && \ make install $(CHECK) && \ chmod u+w $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib && \ - install_name_tool -id @executable_path/../lib/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib && \ - install_name_tool -id @executable_path/../lib/libykpiv.1.dylib $(PWD)/tmp/root/lib/libykpiv.1.dylib && \ - install_name_tool -id @executable_path/../lib/libykcs11.1.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ - install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @executable_path/../lib/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libykpiv.1.dylib && \ - install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @executable_path/../lib/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ - install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @executable_path/../lib/libcrypto.1.0.0.dylib $(PWD)/tmp/root/bin/yubico-piv-tool && \ - install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @executable_path/../lib/libykpiv.1.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ - install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @executable_path/../lib/libykpiv.1.dylib $(PWD)/tmp/root/bin/yubico-piv-tool ; \ + install_name_tool -id @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib && \ + install_name_tool -id @loader_path/libykpiv.1.dylib $(PWD)/tmp/root/lib/libykpiv.1.dylib && \ + install_name_tool -id @loader_path/libykcs11.1.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ + install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libykpiv.1.dylib && \ + install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ + install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/bin/yubico-piv-tool && \ + install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @loader_path/libykpiv.1.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ + install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @loader_path/libykpiv.1.dylib $(PWD)/tmp/root/bin/yubico-piv-tool ; \ if otool -L $(PWD)/tmp/root/lib/*.dylib $(PWD)/tmp/root/bin/* | grep '$(PWD)/tmp/root' | grep -q compatibility; then \ echo "something is incorrectly linked!"; \ exit 1; \ From 87b461be99c6c47451bf27933651d150b7073cdc Mon Sep 17 00:00:00 2001 From: Adam Goodman Date: Wed, 18 Nov 2015 10:24:18 -0500 Subject: [PATCH 002/107] except, continue using @executable_path for yubico-piv-tool itself --- mac.mk | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/mac.mk b/mac.mk index 04cfd64..be456b2 100644 --- a/mac.mk +++ b/mac.mk @@ -68,9 +68,9 @@ doit: install_name_tool -id @loader_path/libykcs11.1.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libykpiv.1.dylib && \ install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ - install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/bin/yubico-piv-tool && \ + install_name_tool -change $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib @executable_path/../lib/libcrypto.1.0.0.dylib $(PWD)/tmp/root/bin/yubico-piv-tool && \ install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @loader_path/libykpiv.1.dylib $(PWD)/tmp/root/lib/libykcs11.1.dylib && \ - install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @loader_path/libykpiv.1.dylib $(PWD)/tmp/root/bin/yubico-piv-tool ; \ + install_name_tool -change $(PWD)/tmp/root/lib/libykpiv.1.dylib @executable_path/../lib/libykpiv.1.dylib $(PWD)/tmp/root/bin/yubico-piv-tool ; \ if otool -L $(PWD)/tmp/root/lib/*.dylib $(PWD)/tmp/root/bin/* | grep '$(PWD)/tmp/root' | grep -q compatibility; then \ echo "something is incorrectly linked!"; \ exit 1; \ From b11dcfd14bfc49b2273798a28295dda1eea9cf5e Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Mon, 9 Nov 2015 14:40:34 +0100 Subject: [PATCH 003/107] YKCS11: accept EC keys that are 1 byte shorter. --- ykcs11/objects.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index b18fee4..fa3ed8c 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -1150,12 +1150,13 @@ CK_RV check_create_ec_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, has_params == CK_FALSE) return CKR_TEMPLATE_INCOMPLETE; - if (*value_len != 32) + if (*value_len == 32 || *value_len == 31) { + if (ec_params_len != 10 || memcmp(ec_params, PRIME256V1, ec_params_len) != 0) + return CKR_ATTRIBUTE_VALUE_INVALID; + } + else /*if () TODO: P384*/ return CKR_ATTRIBUTE_VALUE_INVALID; - if (*value_len == 32 && (ec_params_len != 10 || memcmp(ec_params, PRIME256V1, ec_params_len)) != 0) - return CKR_TEMPLATE_INCONSISTENT; - return CKR_OK; } From b6d42388564aef647ba9a820718a3df8d499a555 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 11 Nov 2015 16:39:34 +0100 Subject: [PATCH 004/107] Initial work on doing padding internally --- lib/ykpiv.c | 82 +++++++++++++++++++++++++++++++++++++++++++++++++++-- lib/ykpiv.h | 8 ++++++ 2 files changed, 87 insertions(+), 3 deletions(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index 51aeb5d..348c13c 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -5,15 +5,15 @@ * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are * met: - * + * * * Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. - * + * * * Redistributions in binary form must reproduce the above * copyright notice, this list of conditions and the following * disclaimer in the documentation and/or other materials provided * with the distribution. - * + * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR @@ -781,3 +781,79 @@ ykpiv_rc ykpiv_save_object(ykpiv_state *state, int object_id, return YKPIV_GENERIC_ERROR; } } + +ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, unsigned char algorithm, + const unsigned char *p, size_t p_len, + const unsigned char *q, size_t q_len, + const unsigned char *dp, size_t dp_len, + const unsigned char *dq, size_t dq_len, + const unsigned char *qinv, size_t qinv_len, + const unsigned char *ec_data, unsigned char ec_data_len, + const unsigned char pin_policy, const unsigned char touch_policy) { + + /*unsigned char key_data[1024]; + unsigned char *in_ptr = key_data; + unsigned char templ[] = {0, YKPIV_INS_IMPORT_KEY, 0, key}; + unsigned char data[256]; + unsigned long recv_len = sizeof(data); + unsigned elem_len; + int sw; + const unsigned char *params[5]; + unsigned char n_params; + int i; + int param_tag; + + if (state == NULL) + return YKPIV_GENERIC_ERROR; + + if (key != YKPIV_KEY_AUTHENTICATION && + key != YKPIV_KEY_SIGNATURE && + key != YKPIV_KEY_KEYMGM && + key != YKPIV_KEY_CARDAUTH) { + return YKPIV_KEY_ERROR; + } + + if (pin_policy != YKPIV_PINPOLICY_NEVER && + pin_policy != YKPIV_PINPOLICY_ONCE && + pin_policy != YKPIV_PINPOLICY_ALWAYS) + return YKPIV_GENERIC_ERROR; + + if (touch_policy != YKPIV_TOUCHPOLICY_NEVER && + touch_policy != YKPIV_TOUCHPOLICY_ALWAYS) + return YKPIV_GENERIC_ERROR; + + if (algorithm == YKPIV_ALGO_RSA1024 || algorithm == YKPIV_ALGO_RSA2048) { + + if (algorithm == YKPIV_ALGO_RSA1024) + elem_len = 64; + if (algorithm == YKPIV_ALGO_RSA2048) + elem_len = 128; + + params[0] = p; + params[1] = q; + params[2] = dp; + params[3] = dq; + params[4] = qinv; + param_tag = 0x00; + n_params = 5; + } + else if (algorithm == YKPIV_ALGO_ECCP256 || algorithm == YKPIV_ALGO_ECCP384) { + if (algorithm == YKPIV_ALGO_ECCP256) + elem_len = 32; + if (algorithm == YKPIV_ALGO_ECCP384) + elem_len = 48; + + params[0] = ec_data; + param_tag = + n_params = 1; + } + else + return YKPIV_ALGORITHM_ERROR; + + for (i = 0; i < n_params; i++) { + + }*/ + + return YKPIV_OK; + +} diff --git a/lib/ykpiv.h b/lib/ykpiv.h index ffbee83..17ee85e 100644 --- a/lib/ykpiv.h +++ b/lib/ykpiv.h @@ -91,6 +91,14 @@ extern "C" const unsigned char touch); ykpiv_rc ykpiv_save_object(ykpiv_state *state, int object_id, unsigned char *indata, size_t len); + ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, unsigned char algorithm, + const unsigned char *p, size_t p_len, + const unsigned char *q, size_t q_len, + const unsigned char *dp, size_t dp_len, + const unsigned char *dq, size_t dq_len, + const unsigned char *qinv, size_t qinv_len, + const unsigned char *ec_data, unsigned char ec_data_len, + const unsigned char pin_policy, const unsigned char touch_policy); #define YKPIV_ALGO_3DES 0x03 #define YKPIV_ALGO_RSA1024 0x06 From 9b16e208073978b29c7254c411eb862f3787e755 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 19 Nov 2015 18:27:48 +0100 Subject: [PATCH 005/107] Export ykpiv_import_private_key globally. --- lib/ykpiv.map | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/ykpiv.map b/lib/ykpiv.map index c647a5a..fb2efb1 100644 --- a/lib/ykpiv.map +++ b/lib/ykpiv.map @@ -60,4 +60,5 @@ YKPIV_1.1.0 global: ykpiv_set_mgmkey2; ykpiv_list_readers; + ykpiv_import_private_key; } YKPIV_0.1.0; From 62692805784878755bd6068dc95b62e7b47a27f3 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 19 Nov 2015 18:29:26 +0100 Subject: [PATCH 006/107] Add import private key to libykpiv. --- lib/ykpiv.c | 71 +++++++++++++++++++++++++++++++++++++++++++---------- lib/ykpiv.h | 2 ++ 2 files changed, 60 insertions(+), 13 deletions(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index 348c13c..6a8a7f7 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -783,22 +783,24 @@ ykpiv_rc ykpiv_save_object(ykpiv_state *state, int object_id, } ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, unsigned char algorithm, - const unsigned char *p, size_t p_len, - const unsigned char *q, size_t q_len, - const unsigned char *dp, size_t dp_len, - const unsigned char *dq, size_t dq_len, - const unsigned char *qinv, size_t qinv_len, - const unsigned char *ec_data, unsigned char ec_data_len, + const unsigned char *p, size_t p_len, + const unsigned char *q, size_t q_len, + const unsigned char *dp, size_t dp_len, + const unsigned char *dq, size_t dq_len, + const unsigned char *qinv, size_t qinv_len, + const unsigned char *ec_data, unsigned char ec_data_len, const unsigned char pin_policy, const unsigned char touch_policy) { - /*unsigned char key_data[1024]; + unsigned char key_data[1024]; unsigned char *in_ptr = key_data; - unsigned char templ[] = {0, YKPIV_INS_IMPORT_KEY, 0, key}; + unsigned char templ[] = {0, YKPIV_INS_IMPORT_KEY, algorithm, key}; unsigned char data[256]; unsigned long recv_len = sizeof(data); unsigned elem_len; int sw; const unsigned char *params[5]; + size_t lens[5]; + size_t padding; unsigned char n_params; int i; int param_tag; @@ -813,12 +815,14 @@ ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, u return YKPIV_KEY_ERROR; } - if (pin_policy != YKPIV_PINPOLICY_NEVER && + if (pin_policy != YKPIV_PINPOLICY_DEFAULT && + pin_policy != YKPIV_PINPOLICY_NEVER && pin_policy != YKPIV_PINPOLICY_ONCE && pin_policy != YKPIV_PINPOLICY_ALWAYS) return YKPIV_GENERIC_ERROR; - if (touch_policy != YKPIV_TOUCHPOLICY_NEVER && + if (touch_policy != YKPIV_TOUCHPOLICY_DEFAULT && + touch_policy != YKPIV_TOUCHPOLICY_NEVER && touch_policy != YKPIV_TOUCHPOLICY_ALWAYS) return YKPIV_GENERIC_ERROR; @@ -829,12 +833,22 @@ ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, u if (algorithm == YKPIV_ALGO_RSA2048) elem_len = 128; + if (p == NULL || q == NULL || dp == NULL || + dq == NULL || qinv == NULL) + return YKPIV_GENERIC_ERROR; + params[0] = p; + lens[0] = p_len; params[1] = q; + lens[1] = q_len; params[2] = dp; + lens[2] = dp_len; params[3] = dq; + lens[3] = dq_len; params[4] = qinv; - param_tag = 0x00; + lens[4] = qinv_len; + param_tag = 0x01; + n_params = 5; } else if (algorithm == YKPIV_ALGO_ECCP256 || algorithm == YKPIV_ALGO_ECCP384) { @@ -843,16 +857,47 @@ ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, u if (algorithm == YKPIV_ALGO_ECCP384) elem_len = 48; + if (ec_data == NULL) + return YKPIV_GENERIC_ERROR; + params[0] = ec_data; - param_tag = + lens[0] = ec_data_len; + param_tag = 0x06; n_params = 1; } else return YKPIV_ALGORITHM_ERROR; for (i = 0; i < n_params; i++) { + *in_ptr++ = param_tag + i; + in_ptr += set_length(in_ptr, elem_len); + padding = elem_len - lens[i]; + memset(in_ptr, 0, padding); + in_ptr += padding; + memcpy(in_ptr, params[i], lens[i]); + in_ptr += lens[i]; + } - }*/ + if (pin_policy != YKPIV_PINPOLICY_DEFAULT) { + *in_ptr++ = YKPIV_PINPOLICY_TAG; + *in_ptr++ = 0x01; + *in_ptr++ = pin_policy; + } + + if (touch_policy != YKPIV_TOUCHPOLICY_DEFAULT) { + *in_ptr++ = YKPIV_TOUCHPOLICY_TAG; + *in_ptr++ = 0x01; + *in_ptr++ = touch_policy; + } + + if (ykpiv_transfer_data(state, templ, key_data, in_ptr - key_data, data, &recv_len, &sw) != YKPIV_OK) + return YKPIV_GENERIC_ERROR; + printf("IMPORTING %x, %d\n", sw, n_params); + if (sw == 0x6982) + return YKPIV_AUTHENTICATION_ERROR; + + if (sw != 0x9000) + return YKPIV_GENERIC_ERROR; return YKPIV_OK; diff --git a/lib/ykpiv.h b/lib/ykpiv.h index 17ee85e..16b92a2 100644 --- a/lib/ykpiv.h +++ b/lib/ykpiv.h @@ -163,11 +163,13 @@ extern "C" #define YKPIV_INS_SET_PIN_RETRIES 0xfa #define YKPIV_PINPOLICY_TAG 0xaa +#define YKPIV_PINPOLICY_DEFAULT 0 #define YKPIV_PINPOLICY_NEVER 1 #define YKPIV_PINPOLICY_ONCE 2 #define YKPIV_PINPOLICY_ALWAYS 3 #define YKPIV_TOUCHPOLICY_TAG 0xab +#define YKPIV_TOUCHPOLICY_DEFAULT 0 #define YKPIV_TOUCHPOLICY_NEVER 1 #define YKPIV_TOUCHPOLICY_ALWAYS 2 From 8e3314ab426eef75b17951ab0e94d3efb52d0479 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 19 Nov 2015 18:30:08 +0100 Subject: [PATCH 007/107] Switch ykcs11 to use private key import from libykpiv. --- ykcs11/objects.c | 30 +++++----- ykcs11/objects.h | 8 ++- ykcs11/pkcs11t.h | 3 +- ykcs11/token_vendors.c | 130 +++++++++++++++++++---------------------- ykcs11/token_vendors.h | 10 +++- ykcs11/ykcs11.c | 39 ++++++++++--- 6 files changed, 120 insertions(+), 100 deletions(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index fa3ed8c..aaf3fa7 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -1161,8 +1161,12 @@ CK_RV check_create_ec_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, } CK_RV check_create_rsa_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, - CK_BYTE_PTR *p, CK_BYTE_PTR *q, CK_BYTE_PTR *dp, - CK_BYTE_PTR *dq, CK_BYTE_PTR *qinv, CK_ULONG_PTR value_len, CK_ULONG_PTR vendor_defined) { + CK_BYTE_PTR *p, CK_ULONG_PTR p_len, + CK_BYTE_PTR *q, CK_ULONG_PTR q_len, + CK_BYTE_PTR *dp, CK_ULONG_PTR dp_len, + CK_BYTE_PTR *dq, CK_ULONG_PTR dq_len, + CK_BYTE_PTR *qinv, CK_ULONG_PTR qinv_len, + CK_ULONG_PTR vendor_defined) { CK_ULONG i; CK_BBOOL has_id = CK_FALSE; @@ -1172,11 +1176,6 @@ CK_RV check_create_rsa_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, CK_BBOOL has_dp = CK_FALSE; CK_BBOOL has_dq = CK_FALSE; CK_BBOOL has_qinv = CK_FALSE; - CK_ULONG p_len = 0; - CK_ULONG q_len = 0; - CK_ULONG dp_len = 0; - CK_ULONG dq_len = 0; - CK_ULONG qinv_len = 0; *vendor_defined = 0; @@ -1211,35 +1210,35 @@ CK_RV check_create_rsa_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, case CKA_PRIME_1: has_p = CK_TRUE; *p = (CK_BYTE_PTR)templ[i].pValue; - p_len = templ[i].ulValueLen; + *p_len = templ[i].ulValueLen; break; case CKA_PRIME_2: has_q = CK_TRUE; *q = (CK_BYTE_PTR)templ[i].pValue; - q_len = templ[i].ulValueLen; + *q_len = templ[i].ulValueLen; break; case CKA_EXPONENT_1: has_dp = CK_TRUE; *dp = (CK_BYTE_PTR)templ[i].pValue; - dp_len = templ[i].ulValueLen; + *dp_len = templ[i].ulValueLen; break; case CKA_EXPONENT_2: has_dq = CK_TRUE; *dq = (CK_BYTE_PTR)templ[i].pValue; - dq_len = templ[i].ulValueLen; + *dq_len = templ[i].ulValueLen; break; case CKA_COEFFICIENT: has_qinv = CK_TRUE; *qinv = (CK_BYTE_PTR)templ[i].pValue; - qinv_len = templ[i].ulValueLen; + *qinv_len = templ[i].ulValueLen; break; @@ -1270,13 +1269,12 @@ CK_RV check_create_rsa_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, has_qinv == CK_FALSE) return CKR_TEMPLATE_INCOMPLETE; - if (p_len != 64 && p_len != 128) + if (*p_len != 64 && *p_len != 128) return CKR_ATTRIBUTE_VALUE_INVALID; - *value_len = p_len; - if (q_len != p_len || dp_len != p_len || - dq_len != p_len || qinv_len != p_len) + if (*q_len != *p_len || *dp_len > *p_len || + *dq_len > *p_len || *qinv_len > *p_len) return CKR_ATTRIBUTE_VALUE_INVALID; return CKR_OK; diff --git a/ykcs11/objects.h b/ykcs11/objects.h index be9db19..0780503 100644 --- a/ykcs11/objects.h +++ b/ykcs11/objects.h @@ -18,8 +18,12 @@ CK_RV check_create_cert(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, CK_RV check_create_ec_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, CK_BYTE_PTR *value, CK_ULONG_PTR value_len, CK_ULONG_PTR vendor_defined); CK_RV check_create_rsa_key(CK_ATTRIBUTE_PTR templ, CK_ULONG n, CK_BYTE_PTR id, - CK_BYTE_PTR *p, CK_BYTE_PTR *q, CK_BYTE_PTR *dp, - CK_BYTE_PTR *dq, CK_BYTE_PTR *qinv, CK_ULONG_PTR value_len, CK_ULONG_PTR vendor_defined); + CK_BYTE_PTR *p, CK_ULONG_PTR p_len, + CK_BYTE_PTR *q, CK_ULONG_PTR q_len, + CK_BYTE_PTR *dp, CK_ULONG_PTR dp_len, + CK_BYTE_PTR *dq, CK_ULONG_PTR dq_len, + CK_BYTE_PTR *qinv, CK_ULONG_PTR qinv_len, + CK_ULONG_PTR vendor_defined); CK_RV check_delete_cert(CK_OBJECT_HANDLE hObject, CK_BYTE_PTR id); #endif diff --git a/ykcs11/pkcs11t.h b/ykcs11/pkcs11t.h index d357092..4e0569c 100644 --- a/ykcs11/pkcs11t.h +++ b/ykcs11/pkcs11t.h @@ -1190,6 +1190,7 @@ typedef CK_EXTRACT_PARAMS CK_PTR CK_EXTRACT_PARAMS_PTR; #define CKA_TOUCH_ALWAYS 0x00000001U #define CKA_PIN_ONCE 0x00000002U #define CKA_PIN_ALWAYS 0x00000004U - +#define CKA_PIN_NEVER 0x00000008U +#define CKA_TOUCH_NEVER 0x00000016U #endif diff --git a/ykcs11/token_vendors.c b/ykcs11/token_vendors.c index 25db6d7..b5bbfd8 100644 --- a/ykcs11/token_vendors.c +++ b/ykcs11/token_vendors.c @@ -176,85 +176,73 @@ static CK_RV COMMON_token_import_cert(ykpiv_state *state, CK_ULONG cert_id, CK_B return CKR_OK; } -CK_RV COMMON_token_import_private_key(ykpiv_state *state, CK_BYTE key_id, CK_BYTE_PTR p, CK_BYTE_PTR q, - CK_BYTE_PTR dp, CK_BYTE_PTR dq, CK_BYTE_PTR qinv, - CK_BYTE_PTR ec_data, CK_ULONG elem_len, CK_ULONG vendor_defined) { +CK_RV COMMON_token_import_private_key(ykpiv_state *state, CK_BYTE key_id, + CK_BYTE_PTR p, CK_ULONG p_len, + CK_BYTE_PTR q, CK_ULONG q_len, + CK_BYTE_PTR dp, CK_ULONG dp_len, + CK_BYTE_PTR dq, CK_ULONG dq_len, + CK_BYTE_PTR qinv, CK_ULONG qinv_len, + CK_BYTE_PTR ec_data, CK_ULONG ec_data_len, + CK_ULONG vendor_defined) { - unsigned char key_data[1024]; - unsigned char *in_ptr = key_data; - unsigned char templ[] = {0, YKPIV_INS_IMPORT_KEY, 0, key_id}; - unsigned char data[0xff]; - unsigned long recv_len = sizeof(data); - int sw; + CK_BYTE pin_policy; + CK_BYTE touch_policy; + CK_BYTE algo; + ykpiv_rc rc; - if (elem_len == 128) // TODO: add a flag to check algo type ? - templ[2] = YKPIV_ALGO_RSA2048; - else if (elem_len == 64) - templ[2] = YKPIV_ALGO_RSA1024; - else if(elem_len == 32) - templ[2] = YKPIV_ALGO_ECCP256; - - if (templ[2] == YKPIV_ALGO_RSA1024 ||templ[2] == YKPIV_ALGO_RSA2048) { - *in_ptr++ = 0x01; - in_ptr += set_length(in_ptr, elem_len); - memcpy(in_ptr, p, (size_t)(elem_len)); - in_ptr += elem_len; - - *in_ptr++ = 0x02; - in_ptr += set_length(in_ptr, elem_len); - memcpy(in_ptr, q, (size_t)(elem_len)); - in_ptr += elem_len; - - *in_ptr++ = 0x03; - in_ptr += set_length(in_ptr, elem_len); - memcpy(in_ptr, dp, (size_t)(elem_len)); - in_ptr += elem_len; - - *in_ptr++ = 0x04; - in_ptr += set_length(in_ptr, elem_len); - memcpy(in_ptr, dq, (size_t)(elem_len)); - in_ptr += elem_len; - - *in_ptr++ = 0x05; - in_ptr += set_length(in_ptr, elem_len); - memcpy(in_ptr, qinv, (size_t)(elem_len)); - in_ptr += elem_len; + if (p == NULL) { + if (ec_data_len == 32 || ec_data_len == 31) + algo = YKPIV_ALGO_ECCP256; + else + algo = YKPIV_ALGO_ECCP384; } - else if (templ[2] == YKPIV_ALGO_ECCP256) { - *in_ptr++ = 0x06; - in_ptr += set_length(in_ptr, elem_len); - memcpy(in_ptr, ec_data, (size_t)(elem_len)); - in_ptr += elem_len; + else if (ec_data == NULL) { + if (p_len == 64) + algo = YKPIV_ALGO_RSA1024; + else + algo = YKPIV_ALGO_RSA2048; } - - // PIN policy and touch - if (vendor_defined != 0) { - if (vendor_defined & CKA_PIN_ONCE) { - *in_ptr++ = YKPIV_PINPOLICY_TAG; - *in_ptr++ = 0x01; - *in_ptr++ = YKPIV_PINPOLICY_ONCE; - } - else if (vendor_defined & CKA_PIN_ALWAYS) { - *in_ptr++ = YKPIV_PINPOLICY_TAG; - *in_ptr++ = 0x01; - *in_ptr++ = YKPIV_PINPOLICY_ALWAYS; - } - - if (vendor_defined & CKA_TOUCH_ALWAYS) { - *in_ptr++ = YKPIV_TOUCHPOLICY_TAG; - *in_ptr++ = 0x01; - *in_ptr++ = YKPIV_TOUCHPOLICY_ALWAYS; - } - } - - if (ykpiv_transfer_data(state, templ, key_data, in_ptr - key_data, data, &recv_len, &sw) != YKPIV_OK) + else return CKR_FUNCTION_FAILED; - if (sw != 0x9000) - return CKR_DEVICE_ERROR; + pin_policy = YKPIV_PINPOLICY_DEFAULT; + touch_policy = YKPIV_TOUCHPOLICY_DEFAULT; + if (vendor_defined != 0) { + if (vendor_defined & CKA_PIN_ONCE) { + pin_policy = YKPIV_PINPOLICY_ONCE; + } + else if (vendor_defined & CKA_PIN_ALWAYS) { + pin_policy = YKPIV_PINPOLICY_ALWAYS; + } + else if (vendor_defined & CKA_PIN_NEVER) { + pin_policy = YKPIV_PINPOLICY_NEVER; + } + else + return CKR_ATTRIBUTE_VALUE_INVALID; - return CKR_OK; + if (vendor_defined & CKA_TOUCH_ALWAYS) { + touch_policy = YKPIV_TOUCHPOLICY_ALWAYS; + } + else if (vendor_defined & CKA_TOUCH_NEVER) { + touch_policy = YKPIV_TOUCHPOLICY_NEVER; + } + else + return CKR_ATTRIBUTE_VALUE_INVALID; + } + rc = ykpiv_import_private_key(state, key_id, algo, + p, p_len, + q, q_len, + dp, dp_len, + dq, dq_len, + qinv, qinv_len, + ec_data, ec_data_len, + pin_policy, touch_policy); + + if (rc != YKPIV_OK) + return CKR_FUNCTION_FAILED; + + return CKR_OK; } CK_RV COMMON_token_delete_cert(ykpiv_state *state, CK_ULONG cert_id) { diff --git a/ykcs11/token_vendors.h b/ykcs11/token_vendors.h index 3b57209..e091124 100644 --- a/ykcs11/token_vendors.h +++ b/ykcs11/token_vendors.h @@ -23,8 +23,14 @@ typedef CK_RV (*get_t_raw_certificate_f)(ykpiv_state *, piv_obj_id_t, CK_BYTE_PT typedef CK_RV (*t_login_f)(ykpiv_state *, CK_USER_TYPE, CK_UTF8CHAR_PTR, CK_ULONG); typedef CK_RV (*t_generate_key_f)(ykpiv_state *, CK_BBOOL, CK_BYTE, CK_ULONG, CK_ULONG); typedef CK_RV (*t_import_cert_f)(ykpiv_state *, CK_ULONG, CK_BYTE_PTR); -typedef CK_RV (*t_import_private_key_f)(ykpiv_state *, CK_BYTE, CK_BYTE_PTR, CK_BYTE_PTR, CK_BYTE_PTR, - CK_BYTE_PTR, CK_BYTE_PTR, CK_BYTE_PTR, CK_ULONG, CK_ULONG); +typedef CK_RV (*t_import_private_key_f)(ykpiv_state *, CK_BYTE, + CK_BYTE_PTR, CK_ULONG, + CK_BYTE_PTR, CK_ULONG, + CK_BYTE_PTR, CK_ULONG, + CK_BYTE_PTR, CK_ULONG, + CK_BYTE_PTR, CK_ULONG, + CK_BYTE_PTR, CK_ULONG, + CK_ULONG); typedef CK_RV (*t_delete_cert_f)(ykpiv_state *, CK_ULONG); // TODO: replace all the common calls with functions defined in .c that use libykpiv diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index 739df2b..37c7fbd 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -858,6 +858,13 @@ CK_DEFINE_FUNCTION(CK_RV, C_CreateObject)( CK_BYTE_PTR dp; CK_BYTE_PTR dq; CK_BYTE_PTR qinv; + CK_ULONG p_len; + CK_ULONG q_len; + CK_ULONG dp_len; + CK_ULONG dq_len; + CK_ULONG qinv_len; + CK_BYTE_PTR ec_data; + CK_ULONG ec_data_len; CK_ULONG vendor_defined; token_vendor_t token; CK_BBOOL is_new; @@ -980,11 +987,17 @@ CK_DEFINE_FUNCTION(CK_RV, C_CreateObject)( // Try to parse the key as EC is_rsa = CK_FALSE; - rv = check_create_ec_key(pTemplate, ulCount, &id, &value, &value_len, &vendor_defined); + rv = check_create_ec_key(pTemplate, ulCount, &id, &ec_data, &ec_data_len, &vendor_defined); if (rv != CKR_OK) { // Try to parse the key as RSA is_rsa = CK_TRUE; - rv = check_create_rsa_key(pTemplate, ulCount, &id, &p, &q, &dp, &dq, &qinv, &value_len, &vendor_defined); + rv = check_create_rsa_key(pTemplate, ulCount, &id, + &p, &p_len, + &q, &q_len, + &dp, &dp_len, + &dq, &dq_len, + &qinv, &qinv_len, + &vendor_defined); if (rv != CKR_OK) { DBG("Private key template not valid"); return rv; @@ -997,9 +1010,14 @@ CK_DEFINE_FUNCTION(CK_RV, C_CreateObject)( if (is_rsa == CK_TRUE) { DBG("Key is RSA"); - rv = token.token_import_private_key(piv_state, piv_2_ykpiv(object), p, q, dp, dq, qinv, - NULL, - value_len, vendor_defined); + rv = token.token_import_private_key(piv_state, piv_2_ykpiv(object), + p, p_len, + q, q_len, + dp, dp_len, + dq, dq_len, + qinv, qinv_len, + NULL, 0, + vendor_defined); if (rv != CKR_OK) { DBG("Unable to import RSA private key"); return rv; @@ -1007,9 +1025,14 @@ CK_DEFINE_FUNCTION(CK_RV, C_CreateObject)( } else { DBG("Key is ECDSA"); - rv = token.token_import_private_key(piv_state, piv_2_ykpiv(object), NULL, NULL, NULL, NULL, NULL, - value, - value_len, vendor_defined); + rv = token.token_import_private_key(piv_state, piv_2_ykpiv(object), + NULL, 0, + NULL, 0, + NULL, 0, + NULL, 0, + NULL, 0, + ec_data, ec_data_len, + vendor_defined); if (rv != CKR_OK) { DBG("Unable to import ECDSA private key"); return rv; From e39b203d66c4bc64fca1bd14e30d541230518e13 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 11:45:35 +0100 Subject: [PATCH 008/107] Remove leftover print. --- lib/ykpiv.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index 6a8a7f7..abf2b7e 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -892,7 +892,7 @@ ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, u if (ykpiv_transfer_data(state, templ, key_data, in_ptr - key_data, data, &recv_len, &sw) != YKPIV_OK) return YKPIV_GENERIC_ERROR; - printf("IMPORTING %x, %d\n", sw, n_params); + if (sw == 0x6982) return YKPIV_AUTHENTICATION_ERROR; From abc94bc62aa936ca83b779af2275d41fd305799f Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 11:49:30 +0100 Subject: [PATCH 009/107] Refactor yubico-piv-tool to use import_private_key from libykpiv. --- tool/util.c | 11 +-- tool/util.h | 2 +- tool/yubico-piv-tool.c | 181 +++++++++++++++++++++-------------------- 3 files changed, 100 insertions(+), 94 deletions(-) diff --git a/tool/util.c b/tool/util.c index 17c4b12..9ab2801 100644 --- a/tool/util.c +++ b/tool/util.c @@ -291,15 +291,16 @@ int key_to_object_id(int key) { return object; } -bool set_component_with_len(unsigned char **in_ptr, const BIGNUM *bn, int element_len) { +bool set_component(unsigned char *in_ptr, const BIGNUM *bn, int element_len) { int real_len = BN_num_bytes(bn); - *in_ptr += set_length(*in_ptr, element_len); + if(real_len > element_len) { return false; } - memset(*in_ptr, 0, (size_t)(element_len - real_len)); - *in_ptr += element_len - real_len; - *in_ptr += BN_bn2bin(bn, *in_ptr); + memset(in_ptr, 0, (size_t)(element_len - real_len)); + in_ptr += element_len - real_len; + BN_bn2bin(bn, in_ptr); + return true; } diff --git a/tool/util.h b/tool/util.h index f6d984d..21bb843 100644 --- a/tool/util.h +++ b/tool/util.h @@ -46,7 +46,7 @@ unsigned char get_algorithm(EVP_PKEY*); FILE *open_file(const char*, int); int get_object_id(enum enum_slot slot); int key_to_object_id(int key); -bool set_component_with_len(unsigned char**, const BIGNUM*, int); +bool set_component(unsigned char *in_ptr, const BIGNUM *bn, int element_len); bool prepare_rsa_signature(const unsigned char*, unsigned int, unsigned char*, unsigned int*, int); bool read_pw(const char*, char*, size_t, int); diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 01a6690..8a943eb 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -316,14 +316,15 @@ static bool set_pin_retries(ykpiv_state *state, int pin_retries, int puk_retries } static bool import_key(ykpiv_state *state, enum enum_key_format key_format, - const char *input_file_name, const char *slot, char *password, - enum enum_pin_policy pin_policy, enum enum_touch_policy touch_policy) { + const char *input_file_name, const char *slot, char *password, + enum enum_pin_policy pin_policy, enum enum_touch_policy touch_policy) { int key = 0; FILE *input_file = NULL; EVP_PKEY *private_key = NULL; PKCS12 *p12 = NULL; X509 *cert = NULL; bool ret = false; + ykpiv_rc rc = YKPIV_GENERIC_ERROR; sscanf(slot, "%2x", &key); @@ -360,119 +361,123 @@ static bool import_key(ykpiv_state *state, enum enum_key_format key_format, { unsigned char algorithm = get_algorithm(private_key); + unsigned char pp = YKPIV_PINPOLICY_DEFAULT; + unsigned char tp = YKPIV_TOUCHPOLICY_DEFAULT; + if(algorithm == 0) { goto import_out; } - { - unsigned char data[0xff]; - unsigned long recv_len = sizeof(data); - unsigned char in_data[1024]; - unsigned char *in_ptr = in_data; - unsigned char templ[] = {0, YKPIV_INS_IMPORT_KEY, algorithm, key}; - int sw; - if(YKPIV_IS_RSA(algorithm)) { - RSA *rsa_private_key = EVP_PKEY_get1_RSA(private_key); - unsigned char e[4]; - unsigned char *e_ptr = e; - int element_len = 128; - if(algorithm == YKPIV_ALGO_RSA1024) { - element_len = 64; - } - if((set_component_with_len(&e_ptr, rsa_private_key->e, 3) == false) || - !(e[1] == 0x01 && e[2] == 0x00 && e[3] == 0x01)) { - fprintf(stderr, "Invalid public exponent for import (only 0x10001 supported)\n"); - goto import_out; - } + if(pin_policy != pin_policy__NULL) { + pp = get_pin_policy(pin_policy); + } - *in_ptr++ = 0x01; - if(set_component_with_len(&in_ptr, rsa_private_key->p, element_len) == false) { - fprintf(stderr, "Failed setting p component.\n"); - goto import_out; - } + if(touch_policy != touch_policy__NULL) { + tp = get_touch_policy(touch_policy); + } - *in_ptr++ = 0x02; - if(set_component_with_len(&in_ptr, rsa_private_key->q, element_len) == false) { - fprintf(stderr, "Failed setting q component.\n"); - goto import_out; - } + if(YKPIV_IS_RSA(algorithm)) { + RSA *rsa_private_key = EVP_PKEY_get1_RSA(private_key); + unsigned char e[4]; + unsigned char p[128]; + unsigned char q[128]; + unsigned char dmp1[128]; + unsigned char dmq1[128]; + unsigned char iqmp[128]; - *in_ptr++ = 0x03; - if(set_component_with_len(&in_ptr, rsa_private_key->dmp1, element_len) == false) { - fprintf(stderr, "Failed setting dmp1 component.\n"); - goto import_out; - } - - *in_ptr++ = 0x04; - if(set_component_with_len(&in_ptr, rsa_private_key->dmq1, element_len) == false) { - fprintf(stderr, "Failed setting dmq1 component.\n"); - goto import_out; - } - - *in_ptr++ = 0x05; - if(set_component_with_len(&in_ptr, rsa_private_key->iqmp, element_len) == false) { - fprintf(stderr, "Failed setting iqmp component.\n"); - goto import_out; - } - } else if(YKPIV_IS_EC(algorithm)) { - EC_KEY *ec = EVP_PKEY_get1_EC_KEY(private_key); - const BIGNUM *s = EC_KEY_get0_private_key(ec); - int element_len = 32; - - if(algorithm == YKPIV_ALGO_ECCP384) { - element_len = 48; - } - - *in_ptr++ = 0x06; - if(set_component_with_len(&in_ptr, s, element_len) == false) { - fprintf(stderr, "Failed setting ec private key.\n"); - goto import_out; - } + int element_len = 128; + if(algorithm == YKPIV_ALGO_RSA1024) { + element_len = 64; } - if(pin_policy != pin_policy__NULL) { - *in_ptr++ = YKPIV_PINPOLICY_TAG; - *in_ptr++ = 1; - *in_ptr++ = get_pin_policy(pin_policy); - } - if(touch_policy != touch_policy__NULL) { - *in_ptr++ = YKPIV_TOUCHPOLICY_TAG; - *in_ptr++ = 1; - *in_ptr++ = get_touch_policy(touch_policy); + if((set_component(e, rsa_private_key->e, 3) == false) || + !(e[0] == 0x01 && e[1] == 0x00 && e[2] == 0x01)) { + fprintf(stderr, "Invalid public exponent for import (only 0x10001 supported)\n"); + goto import_out; } - if(ykpiv_transfer_data(state, templ, in_data, in_ptr - in_data, data, - &recv_len, &sw) != YKPIV_OK) { - return false; - } else if(sw == 0x6a80) { - fprintf(stderr, "Failed import."); - if(pin_policy != pin_policy__NULL) { - fprintf(stderr, "Maybe pin-policy is not supported on this key?\n"); - } else if(touch_policy != touch_policy__NULL) { - fprintf(stderr, "Maybe touch-policy is not supported on this key?\n"); - } else { - fprintf(stderr, "Maybe algorithm is not supported on this key?\n"); - } - } else if(sw != 0x9000) { - fprintf(stderr, "Failed import command with code %x.\n", sw); - } else { - ret = true; + if(set_component(p, rsa_private_key->p, element_len) == false) { + fprintf(stderr, "Failed setting p component.\n"); + goto import_out; } + + if(set_component(q, rsa_private_key->q, element_len) == false) { + fprintf(stderr, "Failed setting q component.\n"); + goto import_out; + } + + if(set_component(dmp1, rsa_private_key->dmp1, element_len) == false) { + fprintf(stderr, "Failed setting dmp1 component.\n"); + goto import_out; + } + + if(set_component(dmq1, rsa_private_key->dmq1, element_len) == false) { + fprintf(stderr, "Failed setting dmq1 component.\n"); + goto import_out; + } + + if(set_component(iqmp, rsa_private_key->iqmp, element_len) == false) { + fprintf(stderr, "Failed setting iqmp component.\n"); + goto import_out; + } + + rc = ykpiv_import_private_key(state, key, algorithm, + p, element_len, + q, element_len, + dmp1, element_len, + dmq1, element_len, + iqmp, element_len, + NULL, 0, + pp, tp); + } + else if(YKPIV_IS_EC(algorithm)) { + EC_KEY *ec = EVP_PKEY_get1_EC_KEY(private_key); + const BIGNUM *s = EC_KEY_get0_private_key(ec); + unsigned char s_ptr[48]; + + int element_len = 32; + if(algorithm == YKPIV_ALGO_ECCP384) { + element_len = 48; + } + + if(set_component(s_ptr, s, element_len) == false) { + fprintf(stderr, "Failed setting ec private key.\n"); + goto import_out; + } + + ret = true; + rc = ykpiv_import_private_key(state, key, algorithm, + NULL, 0, + NULL, 0, + NULL, 0, + NULL, 0, + NULL, 0, + s_ptr, element_len, + pp, tp); + } + + if(rc != YKPIV_OK) { + ret = false; } } + import_out: if(private_key) { EVP_PKEY_free(private_key); } + if(p12) { PKCS12_free(p12); } + if(cert) { X509_free(cert); } + if(input_file != stdin) { fclose(input_file); } + return ret; } From 113c3e0b98f898ecb8fde7cbd7519ec84d4f1b6f Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 12:03:02 +0100 Subject: [PATCH 010/107] Whitespace cleanup. --- tool/yubico-piv-tool.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 8a943eb..d19eb3b 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -5,15 +5,15 @@ * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are * met: - * + * * * Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. - * + * * * Redistributions in binary form must reproduce the above * copyright notice, this list of conditions and the following * disclaimer in the documentation and/or other materials provided * with the distribution. - * + * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR @@ -694,7 +694,7 @@ static bool request_certificate(ykpiv_state *state, enum enum_key_format key_for memcpy(digest, oid, oid_len); /* XXX: this should probably use X509_REQ_digest() but that's buggy */ if(!ASN1_item_digest(ASN1_ITEM_rptr(X509_REQ_INFO), md, req->req_info, - digest + oid_len, &digest_len)) { + digest + oid_len, &digest_len)) { fprintf(stderr, "Failed doing digest of request.\n"); goto request_out; } @@ -861,7 +861,7 @@ static bool selfsign_certificate(ykpiv_state *state, enum enum_key_format key_fo memcpy(digest, oid, oid_len); /* XXX: this should probably use X509_digest() but that looks buggy */ if(!ASN1_item_digest(ASN1_ITEM_rptr(X509_CINF), md, x509->cert_info, - digest + oid_len, &digest_len)) { + digest + oid_len, &digest_len)) { fprintf(stderr, "Failed doing digest of certificate.\n"); goto selfsign_out; } @@ -1793,7 +1793,7 @@ int main(int argc, char *argv[]) { break; case action_arg_reset: if(reset(state) == false) { - fprintf(stderr, "Reset failed, are pincodes blocked?\n"); + fprintf(stderr, "Reset failed, are pincodes blocked?\n"); ret = EXIT_FAILURE; } else { fprintf(stderr, "Successfully reset the application.\n"); From ed38b96fe4e5e55098337e027541220bde389fb3 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Fri, 20 Nov 2015 08:53:39 +0100 Subject: [PATCH 011/107] raise buffer sizes and remove a miss-leading error --- lib/ykpiv.c | 2 +- tool/yubico-piv-tool.c | 8 ++------ 2 files changed, 3 insertions(+), 7 deletions(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index abf2b7e..427ce89 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -751,7 +751,7 @@ ykpiv_rc ykpiv_fetch_object(ykpiv_state *state, int object_id, ykpiv_rc ykpiv_save_object(ykpiv_state *state, int object_id, unsigned char *indata, size_t len) { - unsigned char data[2048]; + unsigned char data[3072]; unsigned char *dataptr = data; unsigned char templ[] = {0, YKPIV_INS_PUT_DATA, 0x3f, 0xff}; int sw; diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index d19eb3b..f0052f6 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -541,15 +541,11 @@ static bool import_cert(ykpiv_state *state, enum enum_key_format cert_format, } { - unsigned char certdata[2100]; + unsigned char certdata[3072]; unsigned char *certptr = certdata; int object = get_object_id(slot); ykpiv_rc res; - if(cert_len > 2048) { - fprintf(stderr, "Certificate to large, maximum 2048 bytes (was %d bytes).\n", cert_len); - goto import_cert_out; - } *certptr++ = 0x70; certptr += set_length(certptr, cert_len); if (compress) { @@ -1024,7 +1020,7 @@ static bool read_certificate(ykpiv_state *state, enum enum_slot slot, enum enum_key_format key_format, const char *output_file_name) { FILE *output_file; int object = get_object_id(slot); - unsigned char data[2048]; + unsigned char data[3072]; const unsigned char *ptr = data; unsigned long len = sizeof(data); int cert_len; From fe56e288d96b83ea4e83dc34f6f42320ced64eba Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 12:48:45 +0100 Subject: [PATCH 012/107] Bump libtool version. --- configure.ac | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/configure.ac b/configure.ac index 9b6c506..408fab5 100644 --- a/configure.ac +++ b/configure.ac @@ -34,9 +34,9 @@ AC_CONFIG_MACRO_DIR([m4]) # Interfaces changed/added/removed: CURRENT++ REVISION=0 # Interfaces added: AGE++ # Interfaces removed: AGE=0 -AC_SUBST([LT_CURRENT], 2) -AC_SUBST([LT_REVISION], 1) -AC_SUBST([LT_AGE], 1) +AC_SUBST([LT_CURRENT], 3) +AC_SUBST([LT_REVISION], 0) +AC_SUBST([LT_AGE], 2) AM_INIT_AUTOMAKE([-Wall -Werror foreign]) AM_SILENT_RULES([yes]) From 3b81112aeb3f87d3351301ef70d422be03ea0832 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 14:34:05 +0100 Subject: [PATCH 013/107] Change behavior of yubico-piv-tool -a status. Status only prints information from populated slots. Additionally, it is possible to explicitly choose a single slot and only print information reagarding it. --- tool/yubico-piv-tool.c | 29 ++++++++++++++++++++++------- 1 file changed, 22 insertions(+), 7 deletions(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index f0052f6..8989667 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1168,6 +1168,7 @@ out: static void print_cert_info(ykpiv_state *state, enum enum_slot slot, const EVP_MD *md, FILE *output) { int object = get_object_id(slot); + int slot_name; unsigned char data[2048]; const unsigned char *ptr = data; unsigned long len = sizeof(data); @@ -1177,10 +1178,18 @@ static void print_cert_info(ykpiv_state *state, enum enum_slot slot, const EVP_M BIO *bio = NULL; if(ykpiv_fetch_object(state, object, data, &len) != YKPIV_OK) { - fprintf(output, "No data available.\n"); return; } + if (slot == slot_arg_9a) + slot_name = 0x9a; + else if (slot >= slot_arg_9c && slot <= slot_arg_9e) + slot_name = 0x9b + slot; + else + slot_name = 0x82 + (slot - slot_arg_82); + + fprintf(output, "Slot %x:\t", slot_name); + if(*ptr++ == 0x70) { unsigned int md_len = sizeof(data); ASN1_TIME *not_before, *not_after; @@ -1267,10 +1276,12 @@ cert_out: } static bool status(ykpiv_state *state, enum enum_hash hash, - const char *output_file_name) { + enum enum_slot slot, + const char *output_file_name) { const EVP_MD *md; unsigned char chuid[2048]; long unsigned len = sizeof(chuid); + int i; FILE *output_file = open_file(output_file_name, OUTPUT); if(!output_file) { return false; @@ -1288,14 +1299,18 @@ static bool status(ykpiv_state *state, enum enum_hash hash, dump_hex(chuid, len, output_file, false); } - fprintf(output_file, "Slot 9a:\t"); - print_cert_info(state, slot_arg_9a, md, output_file); - fprintf(output_file, "Slot 9c:\t"); + if (slot == slot__NULL) + for (i = 0; i < 24; i++) { + print_cert_info(state, i, md, output_file); + } + else + print_cert_info(state, slot, md, output_file); + /*fprintf(output_file, "Slot 9c:\t"); print_cert_info(state, slot_arg_9c, md, output_file); fprintf(output_file, "Slot 9d:\t"); print_cert_info(state, slot_arg_9d, md, output_file); fprintf(output_file, "Slot 9e:\t"); - print_cert_info(state, slot_arg_9e, md, output_file); + print_cert_info(state, slot_arg_9e, md, output_file);*/ { int tries; @@ -1877,7 +1892,7 @@ int main(int argc, char *argv[]) { } break; case action_arg_status: - if(status(state, args_info.hash_arg, args_info.output_arg) == false) { + if(status(state, args_info.hash_arg, args_info.slot_arg, args_info.output_arg) == false) { ret = EXIT_FAILURE; } break; From 4849e494be36adadcc97a07ea99e5dae911bcd64 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 15:38:11 +0100 Subject: [PATCH 014/107] Add retired key definitions to libykpiv. Include retired keys in import_key's check. --- lib/ykpiv.c | 8 ++++---- lib/ykpiv.h | 20 ++++++++++++++++++++ tool/yubico-piv-tool.c | 3 ++- 3 files changed, 26 insertions(+), 5 deletions(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index 427ce89..7936ee2 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -808,10 +808,10 @@ ykpiv_rc ykpiv_import_private_key(ykpiv_state *state, const unsigned char key, u if (state == NULL) return YKPIV_GENERIC_ERROR; - if (key != YKPIV_KEY_AUTHENTICATION && - key != YKPIV_KEY_SIGNATURE && - key != YKPIV_KEY_KEYMGM && - key != YKPIV_KEY_CARDAUTH) { + if (key == YKPIV_KEY_CARDMGM || + key < YKPIV_KEY_RETIRED1 || + (key > YKPIV_KEY_RETIRED20 && key < YKPIV_KEY_AUTHENTICATION) || + key > YKPIV_KEY_CARDAUTH) { return YKPIV_KEY_ERROR; } diff --git a/lib/ykpiv.h b/lib/ykpiv.h index 16b92a2..a868966 100644 --- a/lib/ykpiv.h +++ b/lib/ykpiv.h @@ -111,6 +111,26 @@ extern "C" #define YKPIV_KEY_SIGNATURE 0x9c #define YKPIV_KEY_KEYMGM 0x9d #define YKPIV_KEY_CARDAUTH 0x9e +#define YKPIV_KEY_RETIRED1 0x82 +#define YKPIV_KEY_RETIRED2 0x83 +#define YKPIV_KEY_RETIRED3 0x84 +#define YKPIV_KEY_RETIRED4 0x85 +#define YKPIV_KEY_RETIRED5 0x86 +#define YKPIV_KEY_RETIRED6 0x87 +#define YKPIV_KEY_RETIRED7 0x88 +#define YKPIV_KEY_RETIRED8 0x89 +#define YKPIV_KEY_RETIRED9 0x8a +#define YKPIV_KEY_RETIRED10 0x8b +#define YKPIV_KEY_RETIRED11 0x8c +#define YKPIV_KEY_RETIRED12 0x8d +#define YKPIV_KEY_RETIRED13 0x8e +#define YKPIV_KEY_RETIRED14 0x8f +#define YKPIV_KEY_RETIRED15 0x90 +#define YKPIV_KEY_RETIRED16 0x91 +#define YKPIV_KEY_RETIRED17 0x92 +#define YKPIV_KEY_RETIRED18 0x93 +#define YKPIV_KEY_RETIRED19 0x94 +#define YKPIV_KEY_RETIRED20 0x95 #define YKPIV_OBJ_CAPABILITY 0x5fc107 #define YKPIV_OBJ_CHUID 0x5fc102 diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 8989667..fb521b9 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -445,7 +445,6 @@ static bool import_key(ykpiv_state *state, enum enum_key_format key_format, goto import_out; } - ret = true; rc = ykpiv_import_private_key(state, key, algorithm, NULL, 0, NULL, 0, @@ -456,6 +455,7 @@ static bool import_key(ykpiv_state *state, enum enum_key_format key_format, pp, tp); } + ret = true; if(rc != YKPIV_OK) { ret = false; } @@ -1822,6 +1822,7 @@ int main(int argc, char *argv[]) { case action_arg_importMINUS_key: if(import_key(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_orig, args_info.password_arg, args_info.pin_policy_arg, args_info.touch_policy_arg) == false) { + fprintf(stderr, "Unable to import private key\n"); ret = EXIT_FAILURE; } else { fprintf(stderr, "Successfully imported a new private key.\n"); From 11a7d11e4826831e71a13fde95850deaab43311b Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 20 Nov 2015 17:39:33 +0100 Subject: [PATCH 015/107] Start adding retired keys to ykcs11. --- ykcs11/obj_types.h | 137 +++++++++++++++++++++------------- ykcs11/objects.c | 182 +++++++++++++++++++++++++++++++++++++-------- 2 files changed, 237 insertions(+), 82 deletions(-) diff --git a/ykcs11/obj_types.h b/ykcs11/obj_types.h index ca4fc09..d54b8bf 100644 --- a/ykcs11/obj_types.h +++ b/ykcs11/obj_types.h @@ -11,6 +11,26 @@ typedef enum { PIV_DATA_OBJ_X509_CARD_AUTH, // Certificate for card authentication PIV_DATA_OBJ_X509_DS, // Certificate for digital signature PIV_DATA_OBJ_X509_KM, // Certificate for key management + PIV_DATA_OBJ_X509_RETIRED_1, // Certificate for retired key 1 + PIV_DATA_OBJ_X509_RETIRED_2, // Certificate for retired key 2 + PIV_DATA_OBJ_X509_RETIRED_3, // Certificate for retired key 3 + PIV_DATA_OBJ_X509_RETIRED_4, // Certificate for retired key 4 + PIV_DATA_OBJ_X509_RETIRED_5, // Certificate for retired key 5 + PIV_DATA_OBJ_X509_RETIRED_6, // Certificate for retired key 6 + PIV_DATA_OBJ_X509_RETIRED_7, // Certificate for retired key 7 + PIV_DATA_OBJ_X509_RETIRED_8, // Certificate for retired key 8 + PIV_DATA_OBJ_X509_RETIRED_9, // Certificate for retired key 9 + PIV_DATA_OBJ_X509_RETIRED_10, // Certificate for retired key 10 + PIV_DATA_OBJ_X509_RETIRED_11, // Certificate for retired key 11 + PIV_DATA_OBJ_X509_RETIRED_12, // Certificate for retired key 12 + PIV_DATA_OBJ_X509_RETIRED_13, // Certificate for retired key 13 + PIV_DATA_OBJ_X509_RETIRED_14, // Certificate for retired key 14 + PIV_DATA_OBJ_X509_RETIRED_15, // Certificate for retired key 15 + PIV_DATA_OBJ_X509_RETIRED_16, // Certificate for retired key 16 + PIV_DATA_OBJ_X509_RETIRED_17, // Certificate for retired key 17 + PIV_DATA_OBJ_X509_RETIRED_18, // Certificate for retired key 18 + PIV_DATA_OBJ_X509_RETIRED_19, // Certificate for retired key 19 + PIV_DATA_OBJ_X509_RETIRED_20, // Certificate for retired key 20 PIV_DATA_OBJ_CCC, // Card capability container PIV_DATA_OBJ_CHUI, // Cardholder unique id PIV_DATA_OBJ_CHF, // Cardholder fingerprints @@ -19,73 +39,88 @@ typedef enum { PIV_DATA_OBJ_PI, // Cardholder printed information PIV_DATA_OBJ_DISCOVERY, // Discovery object PIV_DATA_OBJ_HISTORY, // History object - PIV_DATA_OBJ_RETIRED_X509_1, // Retired certificate for KM 1 - PIV_DATA_OBJ_RETIRED_X509_2, // Retired certificate for KM 2 - PIV_DATA_OBJ_RETIRED_X509_3, // Retired certificate for KM 3 - PIV_DATA_OBJ_RETIRED_X509_4, // Retired certificate for KM 4 - PIV_DATA_OBJ_RETIRED_X509_5, // Retired certificate for KM 5 - PIV_DATA_OBJ_RETIRED_X509_6, // Retired certificate for KM 6 - PIV_DATA_OBJ_RETIRED_X509_7, // Retired certificate for KM 7 - PIV_DATA_OBJ_RETIRED_X509_8, // Retired certificate for KM 8 - PIV_DATA_OBJ_RETIRED_X509_9, // Retired certificate for KM 9 - PIV_DATA_OBJ_RETIRED_X509_10, // Retired certificate for KM 10 - PIV_DATA_OBJ_RETIRED_X509_11, // Retired certificate for KM 11 - PIV_DATA_OBJ_RETIRED_X509_12, // Retired certificate for KM 12 - PIV_DATA_OBJ_RETIRED_X509_13, // Retired certificate for KM 13 - PIV_DATA_OBJ_RETIRED_X509_14, // Retired certificate for KM 14 - PIV_DATA_OBJ_RETIRED_X509_15, // Retired certificate for KM 15 - PIV_DATA_OBJ_RETIRED_X509_16, // Retired certificate for KM 16 - PIV_DATA_OBJ_RETIRED_X509_17, // Retired certificate for KM 17 - PIV_DATA_OBJ_RETIRED_X509_18, // Retired certificate for KM 18 - PIV_DATA_OBJ_RETIRED_X509_19, // Retired certificate for KM 19 - PIV_DATA_OBJ_RETIRED_X509_20, // Retired certificate for KM 20 PIV_DATA_OBJ_IRIS_IMAGE, // Cardholder iris images PIV_DATA_OBJ_BITGT, // Biometric information templates group template PIV_DATA_OBJ_SM_SIGNER, // Secure messaging signer PIV_DATA_OBJ_PC_REF_DATA, // Pairing code reference data -/* PIV_DATA_OBJ_9B03, // NON-STANDARD TODO: remove? - PIV_DATA_OBJ_9A06, // NON-STANDARD - PIV_DATA_OBJ_9C06, // NON-STANDARD - PIV_DATA_OBJ_9D06, // NON-STANDARD - PIV_DATA_OBJ_9E06, // NON-STANDARD - PIV_DATA_OBJ_8206, // NON-STANDARD - PIV_DATA_OBJ_8306, // NON-STANDARD - PIV_DATA_OBJ_8406, // NON-STANDARD - PIV_DATA_OBJ_8506, // NON-STANDARD - PIV_DATA_OBJ_8606, // NON-STANDARD - PIV_DATA_OBJ_8706, // NON-STANDARD - PIV_DATA_OBJ_8806, // NON-STANDARD - PIV_DATA_OBJ_8906, // NON-STANDARD - PIV_DATA_OBJ_8A06, // NON-STANDARD - PIV_DATA_OBJ_8B06, // NON-STANDARD - PIV_DATA_OBJ_8C06, // NON-STANDARD - PIV_DATA_OBJ_8D06, // NON-STANDARD - PIV_DATA_OBJ_8E06, // NON-STANDARD - PIV_DATA_OBJ_8F06, // NON-STANDARD - PIV_DATA_OBJ_9006, // NON-STANDARD - PIV_DATA_OBJ_9106, // NON-STANDARD - PIV_DATA_OBJ_9206, // NON-STANDARD - PIV_DATA_OBJ_9306, // NON-STANDARD - PIV_DATA_OBJ_9406, // NON-STANDARD - PIV_DATA_OBJ_9506, // NON-STANDARD*/ PIV_DATA_OBJ_LAST, PIV_CERT_OBJ_X509_PIV_AUTH, // PIV authentication PIV_CERT_OBJ_X509_CARD_AUTH, // Certificate for card authentication PIV_CERT_OBJ_X509_DS, // Certificate for digital signature PIV_CERT_OBJ_X509_KM, // Certificate for key management + PIV_CERT_OBJ_X509_RETIRED_1, // Certificate for retired key 1 + PIV_CERT_OBJ_X509_RETIRED_2, // Certificate for retired key 2 + PIV_CERT_OBJ_X509_RETIRED_3, // Certificate for retired key 3 + PIV_CERT_OBJ_X509_RETIRED_4, // Certificate for retired key 4 + PIV_CERT_OBJ_X509_RETIRED_5, // Certificate for retired key 5 + PIV_CERT_OBJ_X509_RETIRED_6, // Certificate for retired key 6 + PIV_CERT_OBJ_X509_RETIRED_7, // Certificate for retired key 7 + PIV_CERT_OBJ_X509_RETIRED_8, // Certificate for retired key 8 + PIV_CERT_OBJ_X509_RETIRED_9, // Certificate for retired key 9 + PIV_CERT_OBJ_X509_RETIRED_10, // Certificate for retired key 10 + PIV_CERT_OBJ_X509_RETIRED_11, // Certificate for retired key 11 + PIV_CERT_OBJ_X509_RETIRED_12, // Certificate for retired key 12 + PIV_CERT_OBJ_X509_RETIRED_13, // Certificate for retired key 13 + PIV_CERT_OBJ_X509_RETIRED_14, // Certificate for retired key 14 + PIV_CERT_OBJ_X509_RETIRED_15, // Certificate for retired key 15 + PIV_CERT_OBJ_X509_RETIRED_16, // Certificate for retired key 16 + PIV_CERT_OBJ_X509_RETIRED_17, // Certificate for retired key 17 + PIV_CERT_OBJ_X509_RETIRED_18, // Certificate for retired key 18 + PIV_CERT_OBJ_X509_RETIRED_19, // Certificate for retired key 19 + PIV_CERT_OBJ_X509_RETIRED_20, // Certificate for retired key 20 PIV_CERT_OBJ_LAST, PIV_PVTK_OBJ_PIV_AUTH, // Private key for PIV authentication - PIV_PVTK_OBJ_CARD_AUTH, // Private Key for card authentication - PIV_PVTK_OBJ_DS, // Private Key for digital signature - PIV_PVTK_OBJ_KM, // Private Key for key management + PIV_PVTK_OBJ_CARD_AUTH, // Private key for card authentication + PIV_PVTK_OBJ_DS, // Private key for digital signature + PIV_PVTK_OBJ_KM, // Private key for key management + PIV_PVTK_OBJ_RETIRED_1, // Private key for retired key 1 + PIV_PVTK_OBJ_RETIRED_2, // Private key for retired key 2 + PIV_PVTK_OBJ_RETIRED_3, // Private key for retired key 3 + PIV_PVTK_OBJ_RETIRED_4, // Private key for retired key 4 + PIV_PVTK_OBJ_RETIRED_5, // Private key for retired key 5 + PIV_PVTK_OBJ_RETIRED_6, // Private key for retired key 6 + PIV_PVTK_OBJ_RETIRED_7, // Private key for retired key 7 + PIV_PVTK_OBJ_RETIRED_8, // Private key for retired key 8 + PIV_PVTK_OBJ_RETIRED_9, // Private key for retired key 9 + PIV_PVTK_OBJ_RETIRED_10, // Private key for retired key 10 + PIV_PVTK_OBJ_RETIRED_11, // Private key for retired key 11 + PIV_PVTK_OBJ_RETIRED_12, // Private key for retired key 12 + PIV_PVTK_OBJ_RETIRED_13, // Private key for retired key 13 + PIV_PVTK_OBJ_RETIRED_14, // Private key for retired key 14 + PIV_PVTK_OBJ_RETIRED_15, // Private key for retired key 15 + PIV_PVTK_OBJ_RETIRED_16, // Private key for retired key 16 + PIV_PVTK_OBJ_RETIRED_17, // Private key for retired key 17 + PIV_PVTK_OBJ_RETIRED_18, // Private key for retired key 18 + PIV_PVTK_OBJ_RETIRED_19, // Private key for retired key 19 + PIV_PVTK_OBJ_RETIRED_20, // Private key for retired key 20 PIV_PVTK_OBJ_LAST, PIV_PUBK_OBJ_PIV_AUTH, // Public key for PIV authentication - PIV_PUBK_OBJ_CARD_AUTH, // Public Key for card authentication - PIV_PUBK_OBJ_DS, // Public Key for digital signature - PIV_PUBK_OBJ_KM, // Public Key for key management + PIV_PUBK_OBJ_CARD_AUTH, // Public key for card authentication + PIV_PUBK_OBJ_DS, // Public key for digital signature + PIV_PUBK_OBJ_KM, // Public key for key management + PIV_PUBK_OBJ_RETIRED_1, // Public key for retired key 1 + PIV_PUBK_OBJ_RETIRED_2, // Public key for retired key 2 + PIV_PUBK_OBJ_RETIRED_3, // Public key for retired key 3 + PIV_PUBK_OBJ_RETIRED_4, // Public key for retired key 4 + PIV_PUBK_OBJ_RETIRED_5, // Public key for retired key 5 + PIV_PUBK_OBJ_RETIRED_6, // Public key for retired key 6 + PIV_PUBK_OBJ_RETIRED_7, // Public key for retired key 7 + PIV_PUBK_OBJ_RETIRED_8, // Public key for retired key 8 + PIV_PUBK_OBJ_RETIRED_9, // Public key for retired key 9 + PIV_PUBK_OBJ_RETIRED_10, // Public key for retired key 10 + PIV_PUBK_OBJ_RETIRED_11, // Public key for retired key 11 + PIV_PUBK_OBJ_RETIRED_12, // Public key for retired key 12 + PIV_PUBK_OBJ_RETIRED_13, // Public key for retired key 13 + PIV_PUBK_OBJ_RETIRED_14, // Public key for retired key 14 + PIV_PUBK_OBJ_RETIRED_15, // Public key for retired key 15 + PIV_PUBK_OBJ_RETIRED_16, // Public key for retired key 16 + PIV_PUBK_OBJ_RETIRED_17, // Public key for retired key 17 + PIV_PUBK_OBJ_RETIRED_18, // Public key for retired key 18 + PIV_PUBK_OBJ_RETIRED_19, // Public key for retired key 19 + PIV_PUBK_OBJ_RETIRED_20, // Public key for retired key 20 PIV_PUBK_OBJ_LAST } piv_obj_id_t; diff --git a/ykcs11/objects.c b/ykcs11/objects.c index aaf3fa7..ee27983 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -24,34 +24,34 @@ static piv_obj_t piv_objects[] = { {PIV_DATA_OBJ_X509_CARD_AUTH, 1, 0, 0, "X.509 Certificate for Card Authentication", 0, 0, get_doa, 1}, {PIV_DATA_OBJ_X509_DS, 1, 0, 0, "X.509 Certificate for Digital Signature", 0, 0, get_doa, 2}, {PIV_DATA_OBJ_X509_KM, 1, 0, 0, "X.509 Certificate for Key Management", 0, 0, get_doa, 3}, - {PIV_DATA_OBJ_CCC, 1, 0, 0, "Card Capability Container", 0, 0, get_doa, 4}, - {PIV_DATA_OBJ_CHUI, 1, 0, 0, "Card Holder Unique Identifier", 0, 0, get_doa, 5}, - {PIV_DATA_OBJ_CHF, 1, 1, 0, "Card Holder Fingerprints", 0, 0, get_doa, 6}, - {PIV_DATA_OBJ_SEC_OBJ, 1, 0, 0, "Security Object", 0, 0, get_doa, 7}, - {PIV_DATA_OBJ_CHFI, 1, 1, 0, "Cardholder Facial Images", 0, 0, get_doa, 8}, - {PIV_DATA_OBJ_PI, 1, 1, 0, "Printed Information", 0, 0, get_doa, 9}, - {PIV_DATA_OBJ_DISCOVERY, 1, 0, 0, "Discovery Object", 0, 0, get_doa, 10}, - {PIV_DATA_OBJ_HISTORY, 1, 0, 0, "Key History Object", 0, 0, get_doa, 11}, - {PIV_DATA_OBJ_RETIRED_X509_1, 1, 0, 0, "Retired X.509 Certificate for Key Management 1", 0, 0, get_doa, 12}, - {PIV_DATA_OBJ_RETIRED_X509_2, 1, 0, 0, "Retired X.509 Certificate for Key Management 2", 0, 0, get_doa, 13}, - {PIV_DATA_OBJ_RETIRED_X509_3, 1, 0, 0, "Retired X.509 Certificate for Key Management 3", 0, 0, get_doa, 14}, - {PIV_DATA_OBJ_RETIRED_X509_4, 1, 0, 0, "Retired X.509 Certificate for Key Management 4", 0, 0, get_doa, 15}, - {PIV_DATA_OBJ_RETIRED_X509_5, 1, 0, 0, "Retired X.509 Certificate for Key Management 5", 0, 0, get_doa, 16}, - {PIV_DATA_OBJ_RETIRED_X509_6, 1, 0, 0, "Retired X.509 Certificate for Key Management 6", 0, 0, get_doa, 17}, - {PIV_DATA_OBJ_RETIRED_X509_7, 1, 0, 0, "Retired X.509 Certificate for Key Management 7", 0, 0, get_doa, 18}, - {PIV_DATA_OBJ_RETIRED_X509_8, 1, 0, 0, "Retired X.509 Certificate for Key Management 8", 0, 0, get_doa, 19}, - {PIV_DATA_OBJ_RETIRED_X509_9, 1, 0, 0, "Retired X.509 Certificate for Key Management 9", 0, 0, get_doa, 20}, - {PIV_DATA_OBJ_RETIRED_X509_10, 1, 0, 0, "Retired X.509 Certificate for Key Management 10", 0, 0, get_doa, 21}, - {PIV_DATA_OBJ_RETIRED_X509_11, 1, 0, 0, "Retired X.509 Certificate for Key Management 11", 0, 0, get_doa, 22}, - {PIV_DATA_OBJ_RETIRED_X509_12, 1, 0, 0, "Retired X.509 Certificate for Key Management 12", 0, 0, get_doa, 23}, - {PIV_DATA_OBJ_RETIRED_X509_13, 1, 0, 0, "Retired X.509 Certificate for Key Management 13", 0, 0, get_doa, 24}, - {PIV_DATA_OBJ_RETIRED_X509_14, 1, 0, 0, "Retired X.509 Certificate for Key Management 14", 0, 0, get_doa, 25}, - {PIV_DATA_OBJ_RETIRED_X509_15, 1, 0, 0, "Retired X.509 Certificate for Key Management 15", 0, 0, get_doa, 26}, - {PIV_DATA_OBJ_RETIRED_X509_16, 1, 0, 0, "Retired X.509 Certificate for Key Management 16", 0, 0, get_doa, 27}, - {PIV_DATA_OBJ_RETIRED_X509_17, 1, 0, 0, "Retired X.509 Certificate for Key Management 17", 0, 0, get_doa, 28}, - {PIV_DATA_OBJ_RETIRED_X509_18, 1, 0, 0, "Retired X.509 Certificate for Key Management 18", 0, 0, get_doa, 29}, - {PIV_DATA_OBJ_RETIRED_X509_19, 1, 0, 0, "Retired X.509 Certificate for Key Management 19", 0, 0, get_doa, 30}, - {PIV_DATA_OBJ_RETIRED_X509_20, 1, 0, 0, "Retired X.509 Certificate for Key Management 20", 0, 0, get_doa, 31}, + {PIV_DATA_OBJ_X509_RETIRED_1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_doa, 4}, + {PIV_DATA_OBJ_X509_RETIRED_2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_doa, 5}, + {PIV_DATA_OBJ_X509_RETIRED_3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_doa, 6}, + {PIV_DATA_OBJ_X509_RETIRED_4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_doa, 7}, + {PIV_DATA_OBJ_X509_RETIRED_5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_doa, 8}, + {PIV_DATA_OBJ_X509_RETIRED_6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_doa, 9}, + {PIV_DATA_OBJ_X509_RETIRED_7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_doa, 10}, + {PIV_DATA_OBJ_X509_RETIRED_8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_doa, 11}, + {PIV_DATA_OBJ_X509_RETIRED_9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_doa, 12}, + {PIV_DATA_OBJ_X509_RETIRED_10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_doa, 13}, + {PIV_DATA_OBJ_X509_RETIRED_11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_doa, 14}, + {PIV_DATA_OBJ_X509_RETIRED_12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_doa, 15}, + {PIV_DATA_OBJ_X509_RETIRED_13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_doa, 16}, + {PIV_DATA_OBJ_X509_RETIRED_14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_doa, 17}, + {PIV_DATA_OBJ_X509_RETIRED_15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_doa, 18}, + {PIV_DATA_OBJ_X509_RETIRED_16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_doa, 19}, + {PIV_DATA_OBJ_X509_RETIRED_17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_doa, 20}, + {PIV_DATA_OBJ_X509_RETIRED_18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_doa, 21}, + {PIV_DATA_OBJ_X509_RETIRED_19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_doa, 22}, + {PIV_DATA_OBJ_X509_RETIRED_20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_doa, 23}, + {PIV_DATA_OBJ_CCC, 1, 0, 0, "Card Capability Container", 0, 0, get_doa, 24}, + {PIV_DATA_OBJ_CHUI, 1, 0, 0, "Card Holder Unique Identifier", 0, 0, get_doa, 25}, + {PIV_DATA_OBJ_CHF, 1, 1, 0, "Card Holder Fingerprints", 0, 0, get_doa, 26}, + {PIV_DATA_OBJ_SEC_OBJ, 1, 0, 0, "Security Object", 0, 0, get_doa, 27}, + {PIV_DATA_OBJ_CHFI, 1, 1, 0, "Cardholder Facial Images", 0, 0, get_doa, 28}, + {PIV_DATA_OBJ_PI, 1, 1, 0, "Printed Information", 0, 0, get_doa, 29}, + {PIV_DATA_OBJ_DISCOVERY, 1, 0, 0, "Discovery Object", 0, 0, get_doa, 30}, + {PIV_DATA_OBJ_HISTORY, 1, 0, 0, "Key History Object", 0, 0, get_doa, 31}, {PIV_DATA_OBJ_IRIS_IMAGE, 1, 1, 0, "Cardholder Iris Images", 0, 0, get_doa, 32}, {PIV_DATA_OBJ_BITGT, 1, 0, 0, "Biometric Information Templates Group Template", 0, 0, get_doa, 33}, {PIV_DATA_OBJ_SM_SIGNER, 1, 0, 0, "Secure Messaging Certificate Signer", 0, 0, get_doa, 34}, @@ -62,19 +62,79 @@ static piv_obj_t piv_objects[] = { {PIV_CERT_OBJ_X509_CARD_AUTH, 1, 0, 0, "X.509 Certificate for Card Authentication", 0, 0, get_coa, 1}, {PIV_CERT_OBJ_X509_DS, 1, 0, 0, "X.509 Certificate for Digital Signature", 0, 0, get_coa, 2}, {PIV_CERT_OBJ_X509_KM, 1, 0, 0, "X.509 Certificate for Key Management", 0, 0, get_coa, 3}, - {PIV_CERT_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 4}, + {PIV_CERT_OBJ_X509_RETIRED_1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_coa, 4}, + {PIV_CERT_OBJ_X509_RETIRED_2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_coa, 5}, + {PIV_CERT_OBJ_X509_RETIRED_3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_coa, 6}, + {PIV_CERT_OBJ_X509_RETIRED_4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_coa, 7}, + {PIV_CERT_OBJ_X509_RETIRED_5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_coa, 8}, + {PIV_CERT_OBJ_X509_RETIRED_6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_coa, 9}, + {PIV_CERT_OBJ_X509_RETIRED_7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_coa, 10}, + {PIV_CERT_OBJ_X509_RETIRED_8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_coa, 11}, + {PIV_CERT_OBJ_X509_RETIRED_9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_coa, 12}, + {PIV_CERT_OBJ_X509_RETIRED_10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_coa, 13}, + {PIV_CERT_OBJ_X509_RETIRED_11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_coa, 14}, + {PIV_CERT_OBJ_X509_RETIRED_12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_coa, 15}, + {PIV_CERT_OBJ_X509_RETIRED_13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_coa, 16}, + {PIV_CERT_OBJ_X509_RETIRED_14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_coa, 17}, + {PIV_CERT_OBJ_X509_RETIRED_15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_coa, 18}, + {PIV_CERT_OBJ_X509_RETIRED_16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_coa, 19}, + {PIV_CERT_OBJ_X509_RETIRED_17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_coa, 20}, + {PIV_CERT_OBJ_X509_RETIRED_18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_coa, 21}, + {PIV_CERT_OBJ_X509_RETIRED_19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_coa, 22}, + {PIV_CERT_OBJ_X509_RETIRED_20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_coa, 23}, + {PIV_CERT_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24}, {PIV_PVTK_OBJ_PIV_AUTH, 1, 1, 0, "Private key for PIV Authentication", 0, 0, get_proa, 0}, // 9a {PIV_PVTK_OBJ_CARD_AUTH, 1, 0, 0, "Private key for Card Authentication", 0, 0, get_proa, 1}, // 9e {PIV_PVTK_OBJ_DS, 1, 1, 0, "Private key for Digital Signature", 0, 0, get_proa, 2}, // 9c {PIV_PVTK_OBJ_KM, 1, 1, 0, "Private key for Key Management", 0, 0, get_proa, 3}, // 9d - {PIV_PVTK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 4}, + {PIV_PVTK_OBJ_RETIRED_1, 1, 1, 0, "Private key for retired key 1", 0, 0, get_proa, 4}, + {PIV_PVTK_OBJ_RETIRED_2, 1, 1, 0, "Private key for retired key 2", 0, 0, get_proa, 5}, + {PIV_PVTK_OBJ_RETIRED_3, 1, 1, 0, "Private key for retired key 3", 0, 0, get_proa, 6}, + {PIV_PVTK_OBJ_RETIRED_4, 1, 1, 0, "Private key for retired key 4", 0, 0, get_proa, 7}, + {PIV_PVTK_OBJ_RETIRED_5, 1, 1, 0, "Private key for retired key 5", 0, 0, get_proa, 8}, + {PIV_PVTK_OBJ_RETIRED_6, 1, 1, 0, "Private key for retired key 6", 0, 0, get_proa, 9}, + {PIV_PVTK_OBJ_RETIRED_7, 1, 1, 0, "Private key for retired key 7", 0, 0, get_proa, 10}, + {PIV_PVTK_OBJ_RETIRED_8, 1, 1, 0, "Private key for retired key 8", 0, 0, get_proa, 11}, + {PIV_PVTK_OBJ_RETIRED_9, 1, 1, 0, "Private key for retired key 9", 0, 0, get_proa, 12}, + {PIV_PVTK_OBJ_RETIRED_10, 1, 1, 0, "Private key for retired key 10", 0, 0, get_proa, 13}, + {PIV_PVTK_OBJ_RETIRED_11, 1, 1, 0, "Private key for retired key 11", 0, 0, get_proa, 14}, + {PIV_PVTK_OBJ_RETIRED_12, 1, 1, 0, "Private key for retired key 12", 0, 0, get_proa, 15}, + {PIV_PVTK_OBJ_RETIRED_13, 1, 1, 0, "Private key for retired key 13", 0, 0, get_proa, 16}, + {PIV_PVTK_OBJ_RETIRED_14, 1, 1, 0, "Private key for retired key 14", 0, 0, get_proa, 17}, + {PIV_PVTK_OBJ_RETIRED_15, 1, 1, 0, "Private key for retired key 15", 0, 0, get_proa, 18}, + {PIV_PVTK_OBJ_RETIRED_16, 1, 1, 0, "Private key for retired key 16", 0, 0, get_proa, 19}, + {PIV_PVTK_OBJ_RETIRED_17, 1, 1, 0, "Private key for retired key 17", 0, 0, get_proa, 20}, + {PIV_PVTK_OBJ_RETIRED_18, 1, 1, 0, "Private key for retired key 18", 0, 0, get_proa, 21}, + {PIV_PVTK_OBJ_RETIRED_19, 1, 1, 0, "Private key for retired key 19", 0, 0, get_proa, 22}, + {PIV_PVTK_OBJ_RETIRED_20, 1, 1, 0, "Private key for retired key 20", 0, 0, get_proa, 23}, + {PIV_PVTK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24}, {PIV_PUBK_OBJ_PIV_AUTH, 1, 0, 0, "Public key for PIV Authentication", 0, 0, get_puoa, 0}, {PIV_PUBK_OBJ_CARD_AUTH, 1, 0, 0, "Public key for Card Authentication", 0, 0, get_puoa, 1}, {PIV_PUBK_OBJ_DS, 1, 0, 0, "Public key for Digital Signature", 0, 0, get_puoa, 2}, {PIV_PUBK_OBJ_KM, 1, 0, 0, "Public key for Key Management", 0, 0, get_puoa, 3}, - {PIV_PUBK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 4} + {PIV_PUBK_OBJ_RETIRED_1, 1, 0, 0, "Public key for retired key 1", 0, 0, get_puoa, 4}, + {PIV_PUBK_OBJ_RETIRED_2, 1, 0, 0, "Public key for retired key 2", 0, 0, get_puoa, 5}, + {PIV_PUBK_OBJ_RETIRED_3, 1, 0, 0, "Public key for retired key 3", 0, 0, get_puoa, 6}, + {PIV_PUBK_OBJ_RETIRED_4, 1, 0, 0, "Public key for retired key 4", 0, 0, get_puoa, 7}, + {PIV_PUBK_OBJ_RETIRED_5, 1, 0, 0, "Public key for retired key 5", 0, 0, get_puoa, 8}, + {PIV_PUBK_OBJ_RETIRED_6, 1, 0, 0, "Public key for retired key 6", 0, 0, get_puoa, 9}, + {PIV_PUBK_OBJ_RETIRED_7, 1, 0, 0, "Public key for retired key 7", 0, 0, get_puoa, 10}, + {PIV_PUBK_OBJ_RETIRED_8, 1, 0, 0, "Public key for retired key 8", 0, 0, get_puoa, 11}, + {PIV_PUBK_OBJ_RETIRED_9, 1, 0, 0, "Public key for retired key 9", 0, 0, get_puoa, 12}, + {PIV_PUBK_OBJ_RETIRED_10, 1, 0, 0, "Public key for retired key 10", 0, 0, get_puoa, 13}, + {PIV_PUBK_OBJ_RETIRED_11, 1, 0, 0, "Public key for retired key 11", 0, 0, get_puoa, 14}, + {PIV_PUBK_OBJ_RETIRED_12, 1, 0, 0, "Public key for retired key 12", 0, 0, get_puoa, 15}, + {PIV_PUBK_OBJ_RETIRED_13, 1, 0, 0, "Public key for retired key 13", 0, 0, get_puoa, 16}, + {PIV_PUBK_OBJ_RETIRED_14, 1, 0, 0, "Public key for retired key 14", 0, 0, get_puoa, 17}, + {PIV_PUBK_OBJ_RETIRED_15, 1, 0, 0, "Public key for retired key 15", 0, 0, get_puoa, 18}, + {PIV_PUBK_OBJ_RETIRED_16, 1, 0, 0, "Public key for retired key 16", 0, 0, get_puoa, 19}, + {PIV_PUBK_OBJ_RETIRED_17, 1, 0, 0, "Public key for retired key 17", 0, 0, get_puoa, 20}, + {PIV_PUBK_OBJ_RETIRED_18, 1, 0, 0, "Public key for retired key 18", 0, 0, get_puoa, 21}, + {PIV_PUBK_OBJ_RETIRED_19, 1, 0, 0, "Public key for retired key 19", 0, 0, get_puoa, 22}, + {PIV_PUBK_OBJ_RETIRED_20, 1, 0, 0, "Public key for retired key 20", 0, 0, get_puoa, 23}, + {PIV_PUBK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24} }; static piv_data_obj_t data_objects[] = { @@ -119,6 +179,26 @@ static piv_data_obj_t data_objects[] = { }; static piv_cert_obj_t cert_objects[] = { + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, + {NULL}, {NULL}, {NULL}, {NULL}, @@ -131,10 +211,50 @@ static piv_pvtk_obj_t pvtkey_objects[] = { {1, 1, 0, 0, 0}, {1, 1, 0, 0, 0}, {1, 1, 0, 0, 1}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, + {1, 1, 0, 0, 0}, {1, 1, 0, 0, 0} }; static piv_pubk_obj_t pubkey_objects[] = { + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, + {NULL, 1, 1, 0, 0}, {NULL, 1, 1, 0, 0}, {NULL, 1, 1, 0, 0}, {NULL, 1, 1, 0, 0}, From 7de6ab14502ef983efdc09aed90da18781d52eae Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Mon, 23 Nov 2015 16:29:17 +0100 Subject: [PATCH 016/107] Add OIDs for retired keys and rearrange. --- ykcs11/objects.c | 73 ++++++++++++++++++++++++------------------------ 1 file changed, 36 insertions(+), 37 deletions(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index ee27983..6f7f865 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -138,43 +138,42 @@ static piv_obj_t piv_objects[] = { }; static piv_data_obj_t data_objects[] = { - {"2.16.840.1.101.3.7.2.1.1", 3, "\x5F\xC1\x05", "\x01\x01"}, - {"2.16.840.1.101.3.7.2.5.0", 3, "\x5F\xC1\x01", "\x05\x00"}, - {"2.16.840.1.101.3.7.2.1.0", 3, "\x5F\xC1\x0A", "\x01\x00"}, - {"2.16.840.1.101.3.7.2.1.2", 3, "\x5F\xC1\x0B", "\x01\x02"}, - {"2.16.840.1.101.3.7.1.219.0", 3, "\x5F\xC1\x07", "\xDB\x00"}, - {"2.16.840.1.101.3.7.2.48.0", 3, "\x5F\xC1\x02", "\x30\x00"}, - {"2.16.840.1.101.3.7.2.96.16", 3, "\x5F\xC1\x03", "\x60\x10"}, - {"2.16.840.1.101.3.7.2.144.0", 3, "\x5F\xC1\x06", "\x90\x00"}, - {"2.16.840.1.101.3.7.2.96.48", 3, "\x5F\xC1\x08", "\x60\x30"}, - {"2.16.840.1.101.3.7.2.48.1", 3, "\x5F\xC1\x09", "\x30\x01"}, - {"2.16.840.1.101.3.7.2.96.80", 1, "\x7E", "\x60\x50"}, - {"2.16.840.1.101.3.7.2.96.96", 3, "\x5F\xC1\x0C", "\x60\x60"}, - -/* 800-73-3, 21 new objects, 20 history certificates */ - {"2.16.840.1.101.3.7.2.16.1", 3, "\x5F\xC1\x0D", "\x10\x01"}, - {"2.16.840.1.101.3.7.2.16.2", 3, "\x5F\xC1\x0E", "\x10\x02"}, - {"2.16.840.1.101.3.7.2.16.3", 3, "\x5F\xC1\x0F", "\x10\x03"}, - {"2.16.840.1.101.3.7.2.16.4", 3, "\x5F\xC1\x10", "\x10\x04"}, - {"2.16.840.1.101.3.7.2.16.5", 3, "\x5F\xC1\x11", "\x10\x05"}, - {"2.16.840.1.101.3.7.2.16.7", 3, "\x5F\xC1\x13", "\x10\x07"}, - {"2.16.840.1.101.3.7.2.16.8", 3, "\x5F\xC1\x14", "\x10\x08"}, - {"2.16.840.1.101.3.7.2.16.9", 3, "\x5F\xC1\x15", "\x10\x09"}, - {"2.16.840.1.101.3.7.2.16.10", 3, "\x5F\xC1\x16", "\x10\x0A"}, - {"2.16.840.1.101.3.7.2.16.11", 3, "\x5F\xC1\x17", "\x10\x0B"}, - {"2.16.840.1.101.3.7.2.16.12", 3, "\x5F\xC1\x18", "\x10\x0C"}, - {"2.16.840.1.101.3.7.2.16.13", 3, "\x5F\xC1\x19", "\x10\x0D"}, - {"2.16.840.1.101.3.7.2.16.14", 3, "\x5F\xC1\x1A", "\x10\x0E"}, - {"2.16.840.1.101.3.7.2.16.15", 3, "\x5F\xC1\x1B", "\x10\x0F"}, - {"2.16.840.1.101.3.7.2.16.16", 3, "\x5F\xC1\x1C", "\x10\x10"}, - {"2.16.840.1.101.3.7.2.16.17", 3, "\x5F\xC1\x1D", "\x10\x11"}, - {"2.16.840.1.101.3.7.2.16.18", 3, "\x5F\xC1\x1E", "\x10\x12"}, - {"2.16.840.1.101.3.7.2.16.19", 3, "\x5F\xC1\x1F", "\x10\x13"}, - {"2.16.840.1.101.3.7.2.16.20", 3, "\x5F\xC1\x20", "\x10\x14"}, - {"2.16.840.1.101.3.7.2.16.21", 3, "\x5F\xC1\x21", "\x10\x15"}, - {"2.16.840.1.101.3.7.2.16.22", 2, "\x7F\x61", "\x10\x16"}, - {"2.16.840.1.101.3.7.2.16.23", 3, "\x5F\xC1\x22", "\x10\x17"}, - {"2.16.840.1.101.3.7.2.16.24", 3, "\x5F\xC1\x23", "\x10\x18"}, + {"2.16.840.1.101.3.7.2.1.1", 3, "\x5F\xC1\x05", "\x01\x01"}, // PIV Authentication + {"2.16.840.1.101.3.7.2.5.0", 3, "\x5F\xC1\x01", "\x05\x00"}, // Card Authentication + {"2.16.840.1.101.3.7.2.1.0", 3, "\x5F\xC1\x0A", "\x01\x00"}, // Digital Signature + {"2.16.840.1.101.3.7.2.1.2", 3, "\x5F\xC1\x0B", "\x01\x02"}, // Key Management + {"2.16.840.1.101.3.7.2.16.1", 3, "\x5F\xC1\x0D", "\x10\x01"}, // Retired Key 1 + {"2.16.840.1.101.3.7.2.16.2", 3, "\x5F\xC1\x0E", "\x10\x02"}, // Retired Key 2 + {"2.16.840.1.101.3.7.2.16.3", 3, "\x5F\xC1\x0F", "\x10\x03"}, // Retired Key 3 + {"2.16.840.1.101.3.7.2.16.4", 3, "\x5F\xC1\x10", "\x10\x04"}, // Retired Key 4 + {"2.16.840.1.101.3.7.2.16.5", 3, "\x5F\xC1\x11", "\x10\x05"}, // Retired Key 5 + {"2.16.840.1.101.3.7.2.16.6", 3, "\x5F\xC1\x12", "\x10\x06"}, // Retired Key 6 + {"2.16.840.1.101.3.7.2.16.7", 3, "\x5F\xC1\x13", "\x10\x07"}, // Retired Key 7 + {"2.16.840.1.101.3.7.2.16.8", 3, "\x5F\xC1\x14", "\x10\x08"}, // Retired Key 8 + {"2.16.840.1.101.3.7.2.16.9", 3, "\x5F\xC1\x15", "\x10\x09"}, // Retired Key 9 + {"2.16.840.1.101.3.7.2.16.10", 3, "\x5F\xC1\x16", "\x10\x0A"}, // Retired Key 10 + {"2.16.840.1.101.3.7.2.16.11", 3, "\x5F\xC1\x17", "\x10\x0B"}, // Retired Key 11 + {"2.16.840.1.101.3.7.2.16.12", 3, "\x5F\xC1\x18", "\x10\x0C"}, // Retired Key 12 + {"2.16.840.1.101.3.7.2.16.13", 3, "\x5F\xC1\x19", "\x10\x0D"}, // Retired Key 13 + {"2.16.840.1.101.3.7.2.16.14", 3, "\x5F\xC1\x1A", "\x10\x0E"}, // Retired Key 14 + {"2.16.840.1.101.3.7.2.16.15", 3, "\x5F\xC1\x1B", "\x10\x0F"}, // Retired Key 15 + {"2.16.840.1.101.3.7.2.16.16", 3, "\x5F\xC1\x1C", "\x10\x10"}, // Retired Key 16 + {"2.16.840.1.101.3.7.2.16.17", 3, "\x5F\xC1\x1D", "\x10\x11"}, // Retired Key 17 + {"2.16.840.1.101.3.7.2.16.18", 3, "\x5F\xC1\x1E", "\x10\x12"}, // Retired Key 18 + {"2.16.840.1.101.3.7.2.16.19", 3, "\x5F\xC1\x1F", "\x10\x13"}, // Retired Key 19 + {"2.16.840.1.101.3.7.2.16.20", 3, "\x5F\xC1\x20", "\x10\x14"}, // Retired Key 20 + {"2.16.840.1.101.3.7.1.219.0", 3, "\x5F\xC1\x07", "\xDB\x00"}, // CCC + {"2.16.840.1.101.3.7.2.48.0", 3, "\x5F\xC1\x02", "\x30\x00"}, // CHUID + {"2.16.840.1.101.3.7.2.96.16", 3, "\x5F\xC1\x03", "\x60\x10"}, // CHFP + {"2.16.840.1.101.3.7.2.144.0", 3, "\x5F\xC1\x06", "\x90\x00"}, // Security Object + {"2.16.840.1.101.3.7.2.96.48", 3, "\x5F\xC1\x08", "\x60\x30"}, // CHFI + {"2.16.840.1.101.3.7.2.48.1", 3, "\x5F\xC1\x09", "\x30\x01"}, // Printed Information + {"2.16.840.1.101.3.7.2.96.80", 1, "\x7E", "\x60\x50"}, // Discovery Object + {"2.16.840.1.101.3.7.2.96.96", 3, "\x5F\xC1\x0C", "\x60\x60"}, // Key History Object + {"2.16.840.1.101.3.7.2.16.21", 3, "\x5F\xC1\x21", "\x10\x15"}, // CHII + {"2.16.840.1.101.3.7.2.16.22", 2, "\x7F\x61", "\x10\x16"}, // Biometric Information + {"2.16.840.1.101.3.7.2.16.23", 3, "\x5F\xC1\x22", "\x10\x17"}, // Secure Messaging Certificate Signer + {"2.16.840.1.101.3.7.2.16.24", 3, "\x5F\xC1\x23", "\x10\x18"}, // Pairing Code Reference Data Container {"", 0, "", ""} }; From c16aaaa7d0051468cedeaa9a4cce30a754925f5b Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 11:05:21 +0100 Subject: [PATCH 017/107] Add retired keys in more places. --- ykcs11/obj_types.h | 160 ++++++++++++------------ ykcs11/objects.c | 281 ++++++++++++++++++++++++++++++------------ ykcs11/yubico_token.c | 18 ++- 3 files changed, 295 insertions(+), 164 deletions(-) diff --git a/ykcs11/obj_types.h b/ykcs11/obj_types.h index d54b8bf..f4267ba 100644 --- a/ykcs11/obj_types.h +++ b/ykcs11/obj_types.h @@ -11,26 +11,26 @@ typedef enum { PIV_DATA_OBJ_X509_CARD_AUTH, // Certificate for card authentication PIV_DATA_OBJ_X509_DS, // Certificate for digital signature PIV_DATA_OBJ_X509_KM, // Certificate for key management - PIV_DATA_OBJ_X509_RETIRED_1, // Certificate for retired key 1 - PIV_DATA_OBJ_X509_RETIRED_2, // Certificate for retired key 2 - PIV_DATA_OBJ_X509_RETIRED_3, // Certificate for retired key 3 - PIV_DATA_OBJ_X509_RETIRED_4, // Certificate for retired key 4 - PIV_DATA_OBJ_X509_RETIRED_5, // Certificate for retired key 5 - PIV_DATA_OBJ_X509_RETIRED_6, // Certificate for retired key 6 - PIV_DATA_OBJ_X509_RETIRED_7, // Certificate for retired key 7 - PIV_DATA_OBJ_X509_RETIRED_8, // Certificate for retired key 8 - PIV_DATA_OBJ_X509_RETIRED_9, // Certificate for retired key 9 - PIV_DATA_OBJ_X509_RETIRED_10, // Certificate for retired key 10 - PIV_DATA_OBJ_X509_RETIRED_11, // Certificate for retired key 11 - PIV_DATA_OBJ_X509_RETIRED_12, // Certificate for retired key 12 - PIV_DATA_OBJ_X509_RETIRED_13, // Certificate for retired key 13 - PIV_DATA_OBJ_X509_RETIRED_14, // Certificate for retired key 14 - PIV_DATA_OBJ_X509_RETIRED_15, // Certificate for retired key 15 - PIV_DATA_OBJ_X509_RETIRED_16, // Certificate for retired key 16 - PIV_DATA_OBJ_X509_RETIRED_17, // Certificate for retired key 17 - PIV_DATA_OBJ_X509_RETIRED_18, // Certificate for retired key 18 - PIV_DATA_OBJ_X509_RETIRED_19, // Certificate for retired key 19 - PIV_DATA_OBJ_X509_RETIRED_20, // Certificate for retired key 20 + PIV_DATA_OBJ_X509_RETIRED1, // Certificate for retired key 1 + PIV_DATA_OBJ_X509_RETIRED2, // Certificate for retired key 2 + PIV_DATA_OBJ_X509_RETIRED3, // Certificate for retired key 3 + PIV_DATA_OBJ_X509_RETIRED4, // Certificate for retired key 4 + PIV_DATA_OBJ_X509_RETIRED5, // Certificate for retired key 5 + PIV_DATA_OBJ_X509_RETIRED6, // Certificate for retired key 6 + PIV_DATA_OBJ_X509_RETIRED7, // Certificate for retired key 7 + PIV_DATA_OBJ_X509_RETIRED8, // Certificate for retired key 8 + PIV_DATA_OBJ_X509_RETIRED9, // Certificate for retired key 9 + PIV_DATA_OBJ_X509_RETIRED10, // Certificate for retired key 10 + PIV_DATA_OBJ_X509_RETIRED11, // Certificate for retired key 11 + PIV_DATA_OBJ_X509_RETIRED12, // Certificate for retired key 12 + PIV_DATA_OBJ_X509_RETIRED13, // Certificate for retired key 13 + PIV_DATA_OBJ_X509_RETIRED14, // Certificate for retired key 14 + PIV_DATA_OBJ_X509_RETIRED15, // Certificate for retired key 15 + PIV_DATA_OBJ_X509_RETIRED16, // Certificate for retired key 16 + PIV_DATA_OBJ_X509_RETIRED17, // Certificate for retired key 17 + PIV_DATA_OBJ_X509_RETIRED18, // Certificate for retired key 18 + PIV_DATA_OBJ_X509_RETIRED19, // Certificate for retired key 19 + PIV_DATA_OBJ_X509_RETIRED20, // Certificate for retired key 20 PIV_DATA_OBJ_CCC, // Card capability container PIV_DATA_OBJ_CHUI, // Cardholder unique id PIV_DATA_OBJ_CHF, // Cardholder fingerprints @@ -49,78 +49,78 @@ typedef enum { PIV_CERT_OBJ_X509_CARD_AUTH, // Certificate for card authentication PIV_CERT_OBJ_X509_DS, // Certificate for digital signature PIV_CERT_OBJ_X509_KM, // Certificate for key management - PIV_CERT_OBJ_X509_RETIRED_1, // Certificate for retired key 1 - PIV_CERT_OBJ_X509_RETIRED_2, // Certificate for retired key 2 - PIV_CERT_OBJ_X509_RETIRED_3, // Certificate for retired key 3 - PIV_CERT_OBJ_X509_RETIRED_4, // Certificate for retired key 4 - PIV_CERT_OBJ_X509_RETIRED_5, // Certificate for retired key 5 - PIV_CERT_OBJ_X509_RETIRED_6, // Certificate for retired key 6 - PIV_CERT_OBJ_X509_RETIRED_7, // Certificate for retired key 7 - PIV_CERT_OBJ_X509_RETIRED_8, // Certificate for retired key 8 - PIV_CERT_OBJ_X509_RETIRED_9, // Certificate for retired key 9 - PIV_CERT_OBJ_X509_RETIRED_10, // Certificate for retired key 10 - PIV_CERT_OBJ_X509_RETIRED_11, // Certificate for retired key 11 - PIV_CERT_OBJ_X509_RETIRED_12, // Certificate for retired key 12 - PIV_CERT_OBJ_X509_RETIRED_13, // Certificate for retired key 13 - PIV_CERT_OBJ_X509_RETIRED_14, // Certificate for retired key 14 - PIV_CERT_OBJ_X509_RETIRED_15, // Certificate for retired key 15 - PIV_CERT_OBJ_X509_RETIRED_16, // Certificate for retired key 16 - PIV_CERT_OBJ_X509_RETIRED_17, // Certificate for retired key 17 - PIV_CERT_OBJ_X509_RETIRED_18, // Certificate for retired key 18 - PIV_CERT_OBJ_X509_RETIRED_19, // Certificate for retired key 19 - PIV_CERT_OBJ_X509_RETIRED_20, // Certificate for retired key 20 + PIV_CERT_OBJ_X509_RETIRED1, // Certificate for retired key 1 + PIV_CERT_OBJ_X509_RETIRED2, // Certificate for retired key 2 + PIV_CERT_OBJ_X509_RETIRED3, // Certificate for retired key 3 + PIV_CERT_OBJ_X509_RETIRED4, // Certificate for retired key 4 + PIV_CERT_OBJ_X509_RETIRED5, // Certificate for retired key 5 + PIV_CERT_OBJ_X509_RETIRED6, // Certificate for retired key 6 + PIV_CERT_OBJ_X509_RETIRED7, // Certificate for retired key 7 + PIV_CERT_OBJ_X509_RETIRED8, // Certificate for retired key 8 + PIV_CERT_OBJ_X509_RETIRED9, // Certificate for retired key 9 + PIV_CERT_OBJ_X509_RETIRED10, // Certificate for retired key 10 + PIV_CERT_OBJ_X509_RETIRED11, // Certificate for retired key 11 + PIV_CERT_OBJ_X509_RETIRED12, // Certificate for retired key 12 + PIV_CERT_OBJ_X509_RETIRED13, // Certificate for retired key 13 + PIV_CERT_OBJ_X509_RETIRED14, // Certificate for retired key 14 + PIV_CERT_OBJ_X509_RETIRED15, // Certificate for retired key 15 + PIV_CERT_OBJ_X509_RETIRED16, // Certificate for retired key 16 + PIV_CERT_OBJ_X509_RETIRED17, // Certificate for retired key 17 + PIV_CERT_OBJ_X509_RETIRED18, // Certificate for retired key 18 + PIV_CERT_OBJ_X509_RETIRED19, // Certificate for retired key 19 + PIV_CERT_OBJ_X509_RETIRED20, // Certificate for retired key 20 PIV_CERT_OBJ_LAST, PIV_PVTK_OBJ_PIV_AUTH, // Private key for PIV authentication PIV_PVTK_OBJ_CARD_AUTH, // Private key for card authentication PIV_PVTK_OBJ_DS, // Private key for digital signature PIV_PVTK_OBJ_KM, // Private key for key management - PIV_PVTK_OBJ_RETIRED_1, // Private key for retired key 1 - PIV_PVTK_OBJ_RETIRED_2, // Private key for retired key 2 - PIV_PVTK_OBJ_RETIRED_3, // Private key for retired key 3 - PIV_PVTK_OBJ_RETIRED_4, // Private key for retired key 4 - PIV_PVTK_OBJ_RETIRED_5, // Private key for retired key 5 - PIV_PVTK_OBJ_RETIRED_6, // Private key for retired key 6 - PIV_PVTK_OBJ_RETIRED_7, // Private key for retired key 7 - PIV_PVTK_OBJ_RETIRED_8, // Private key for retired key 8 - PIV_PVTK_OBJ_RETIRED_9, // Private key for retired key 9 - PIV_PVTK_OBJ_RETIRED_10, // Private key for retired key 10 - PIV_PVTK_OBJ_RETIRED_11, // Private key for retired key 11 - PIV_PVTK_OBJ_RETIRED_12, // Private key for retired key 12 - PIV_PVTK_OBJ_RETIRED_13, // Private key for retired key 13 - PIV_PVTK_OBJ_RETIRED_14, // Private key for retired key 14 - PIV_PVTK_OBJ_RETIRED_15, // Private key for retired key 15 - PIV_PVTK_OBJ_RETIRED_16, // Private key for retired key 16 - PIV_PVTK_OBJ_RETIRED_17, // Private key for retired key 17 - PIV_PVTK_OBJ_RETIRED_18, // Private key for retired key 18 - PIV_PVTK_OBJ_RETIRED_19, // Private key for retired key 19 - PIV_PVTK_OBJ_RETIRED_20, // Private key for retired key 20 + PIV_PVTK_OBJ_RETIRED1, // Private key for retired key 1 + PIV_PVTK_OBJ_RETIRED2, // Private key for retired key 2 + PIV_PVTK_OBJ_RETIRED3, // Private key for retired key 3 + PIV_PVTK_OBJ_RETIRED4, // Private key for retired key 4 + PIV_PVTK_OBJ_RETIRED5, // Private key for retired key 5 + PIV_PVTK_OBJ_RETIRED6, // Private key for retired key 6 + PIV_PVTK_OBJ_RETIRED7, // Private key for retired key 7 + PIV_PVTK_OBJ_RETIRED8, // Private key for retired key 8 + PIV_PVTK_OBJ_RETIRED9, // Private key for retired key 9 + PIV_PVTK_OBJ_RETIRED10, // Private key for retired key 10 + PIV_PVTK_OBJ_RETIRED11, // Private key for retired key 11 + PIV_PVTK_OBJ_RETIRED12, // Private key for retired key 12 + PIV_PVTK_OBJ_RETIRED13, // Private key for retired key 13 + PIV_PVTK_OBJ_RETIRED14, // Private key for retired key 14 + PIV_PVTK_OBJ_RETIRED15, // Private key for retired key 15 + PIV_PVTK_OBJ_RETIRED16, // Private key for retired key 16 + PIV_PVTK_OBJ_RETIRED17, // Private key for retired key 17 + PIV_PVTK_OBJ_RETIRED18, // Private key for retired key 18 + PIV_PVTK_OBJ_RETIRED19, // Private key for retired key 19 + PIV_PVTK_OBJ_RETIRED20, // Private key for retired key 20 PIV_PVTK_OBJ_LAST, PIV_PUBK_OBJ_PIV_AUTH, // Public key for PIV authentication PIV_PUBK_OBJ_CARD_AUTH, // Public key for card authentication PIV_PUBK_OBJ_DS, // Public key for digital signature PIV_PUBK_OBJ_KM, // Public key for key management - PIV_PUBK_OBJ_RETIRED_1, // Public key for retired key 1 - PIV_PUBK_OBJ_RETIRED_2, // Public key for retired key 2 - PIV_PUBK_OBJ_RETIRED_3, // Public key for retired key 3 - PIV_PUBK_OBJ_RETIRED_4, // Public key for retired key 4 - PIV_PUBK_OBJ_RETIRED_5, // Public key for retired key 5 - PIV_PUBK_OBJ_RETIRED_6, // Public key for retired key 6 - PIV_PUBK_OBJ_RETIRED_7, // Public key for retired key 7 - PIV_PUBK_OBJ_RETIRED_8, // Public key for retired key 8 - PIV_PUBK_OBJ_RETIRED_9, // Public key for retired key 9 - PIV_PUBK_OBJ_RETIRED_10, // Public key for retired key 10 - PIV_PUBK_OBJ_RETIRED_11, // Public key for retired key 11 - PIV_PUBK_OBJ_RETIRED_12, // Public key for retired key 12 - PIV_PUBK_OBJ_RETIRED_13, // Public key for retired key 13 - PIV_PUBK_OBJ_RETIRED_14, // Public key for retired key 14 - PIV_PUBK_OBJ_RETIRED_15, // Public key for retired key 15 - PIV_PUBK_OBJ_RETIRED_16, // Public key for retired key 16 - PIV_PUBK_OBJ_RETIRED_17, // Public key for retired key 17 - PIV_PUBK_OBJ_RETIRED_18, // Public key for retired key 18 - PIV_PUBK_OBJ_RETIRED_19, // Public key for retired key 19 - PIV_PUBK_OBJ_RETIRED_20, // Public key for retired key 20 + PIV_PUBK_OBJ_RETIRED1, // Public key for retired key 1 + PIV_PUBK_OBJ_RETIRED2, // Public key for retired key 2 + PIV_PUBK_OBJ_RETIRED3, // Public key for retired key 3 + PIV_PUBK_OBJ_RETIRED4, // Public key for retired key 4 + PIV_PUBK_OBJ_RETIRED5, // Public key for retired key 5 + PIV_PUBK_OBJ_RETIRED6, // Public key for retired key 6 + PIV_PUBK_OBJ_RETIRED7, // Public key for retired key 7 + PIV_PUBK_OBJ_RETIRED8, // Public key for retired key 8 + PIV_PUBK_OBJ_RETIRED9, // Public key for retired key 9 + PIV_PUBK_OBJ_RETIRED10, // Public key for retired key 10 + PIV_PUBK_OBJ_RETIRED11, // Public key for retired key 11 + PIV_PUBK_OBJ_RETIRED12, // Public key for retired key 12 + PIV_PUBK_OBJ_RETIRED13, // Public key for retired key 13 + PIV_PUBK_OBJ_RETIRED14, // Public key for retired key 14 + PIV_PUBK_OBJ_RETIRED15, // Public key for retired key 15 + PIV_PUBK_OBJ_RETIRED16, // Public key for retired key 16 + PIV_PUBK_OBJ_RETIRED17, // Public key for retired key 17 + PIV_PUBK_OBJ_RETIRED18, // Public key for retired key 18 + PIV_PUBK_OBJ_RETIRED19, // Public key for retired key 19 + PIV_PUBK_OBJ_RETIRED20, // Public key for retired key 20 PIV_PUBK_OBJ_LAST } piv_obj_id_t; diff --git a/ykcs11/objects.c b/ykcs11/objects.c index 6f7f865..4d15ecf 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -24,26 +24,26 @@ static piv_obj_t piv_objects[] = { {PIV_DATA_OBJ_X509_CARD_AUTH, 1, 0, 0, "X.509 Certificate for Card Authentication", 0, 0, get_doa, 1}, {PIV_DATA_OBJ_X509_DS, 1, 0, 0, "X.509 Certificate for Digital Signature", 0, 0, get_doa, 2}, {PIV_DATA_OBJ_X509_KM, 1, 0, 0, "X.509 Certificate for Key Management", 0, 0, get_doa, 3}, - {PIV_DATA_OBJ_X509_RETIRED_1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_doa, 4}, - {PIV_DATA_OBJ_X509_RETIRED_2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_doa, 5}, - {PIV_DATA_OBJ_X509_RETIRED_3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_doa, 6}, - {PIV_DATA_OBJ_X509_RETIRED_4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_doa, 7}, - {PIV_DATA_OBJ_X509_RETIRED_5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_doa, 8}, - {PIV_DATA_OBJ_X509_RETIRED_6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_doa, 9}, - {PIV_DATA_OBJ_X509_RETIRED_7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_doa, 10}, - {PIV_DATA_OBJ_X509_RETIRED_8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_doa, 11}, - {PIV_DATA_OBJ_X509_RETIRED_9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_doa, 12}, - {PIV_DATA_OBJ_X509_RETIRED_10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_doa, 13}, - {PIV_DATA_OBJ_X509_RETIRED_11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_doa, 14}, - {PIV_DATA_OBJ_X509_RETIRED_12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_doa, 15}, - {PIV_DATA_OBJ_X509_RETIRED_13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_doa, 16}, - {PIV_DATA_OBJ_X509_RETIRED_14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_doa, 17}, - {PIV_DATA_OBJ_X509_RETIRED_15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_doa, 18}, - {PIV_DATA_OBJ_X509_RETIRED_16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_doa, 19}, - {PIV_DATA_OBJ_X509_RETIRED_17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_doa, 20}, - {PIV_DATA_OBJ_X509_RETIRED_18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_doa, 21}, - {PIV_DATA_OBJ_X509_RETIRED_19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_doa, 22}, - {PIV_DATA_OBJ_X509_RETIRED_20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_doa, 23}, + {PIV_DATA_OBJ_X509_RETIRED1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_doa, 4}, + {PIV_DATA_OBJ_X509_RETIRED2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_doa, 5}, + {PIV_DATA_OBJ_X509_RETIRED3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_doa, 6}, + {PIV_DATA_OBJ_X509_RETIRED4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_doa, 7}, + {PIV_DATA_OBJ_X509_RETIRED5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_doa, 8}, + {PIV_DATA_OBJ_X509_RETIRED6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_doa, 9}, + {PIV_DATA_OBJ_X509_RETIRED7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_doa, 10}, + {PIV_DATA_OBJ_X509_RETIRED8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_doa, 11}, + {PIV_DATA_OBJ_X509_RETIRED9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_doa, 12}, + {PIV_DATA_OBJ_X509_RETIRED10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_doa, 13}, + {PIV_DATA_OBJ_X509_RETIRED11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_doa, 14}, + {PIV_DATA_OBJ_X509_RETIRED12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_doa, 15}, + {PIV_DATA_OBJ_X509_RETIRED13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_doa, 16}, + {PIV_DATA_OBJ_X509_RETIRED14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_doa, 17}, + {PIV_DATA_OBJ_X509_RETIRED15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_doa, 18}, + {PIV_DATA_OBJ_X509_RETIRED16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_doa, 19}, + {PIV_DATA_OBJ_X509_RETIRED17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_doa, 20}, + {PIV_DATA_OBJ_X509_RETIRED18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_doa, 21}, + {PIV_DATA_OBJ_X509_RETIRED19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_doa, 22}, + {PIV_DATA_OBJ_X509_RETIRED20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_doa, 23}, {PIV_DATA_OBJ_CCC, 1, 0, 0, "Card Capability Container", 0, 0, get_doa, 24}, {PIV_DATA_OBJ_CHUI, 1, 0, 0, "Card Holder Unique Identifier", 0, 0, get_doa, 25}, {PIV_DATA_OBJ_CHF, 1, 1, 0, "Card Holder Fingerprints", 0, 0, get_doa, 26}, @@ -62,78 +62,78 @@ static piv_obj_t piv_objects[] = { {PIV_CERT_OBJ_X509_CARD_AUTH, 1, 0, 0, "X.509 Certificate for Card Authentication", 0, 0, get_coa, 1}, {PIV_CERT_OBJ_X509_DS, 1, 0, 0, "X.509 Certificate for Digital Signature", 0, 0, get_coa, 2}, {PIV_CERT_OBJ_X509_KM, 1, 0, 0, "X.509 Certificate for Key Management", 0, 0, get_coa, 3}, - {PIV_CERT_OBJ_X509_RETIRED_1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_coa, 4}, - {PIV_CERT_OBJ_X509_RETIRED_2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_coa, 5}, - {PIV_CERT_OBJ_X509_RETIRED_3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_coa, 6}, - {PIV_CERT_OBJ_X509_RETIRED_4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_coa, 7}, - {PIV_CERT_OBJ_X509_RETIRED_5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_coa, 8}, - {PIV_CERT_OBJ_X509_RETIRED_6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_coa, 9}, - {PIV_CERT_OBJ_X509_RETIRED_7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_coa, 10}, - {PIV_CERT_OBJ_X509_RETIRED_8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_coa, 11}, - {PIV_CERT_OBJ_X509_RETIRED_9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_coa, 12}, - {PIV_CERT_OBJ_X509_RETIRED_10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_coa, 13}, - {PIV_CERT_OBJ_X509_RETIRED_11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_coa, 14}, - {PIV_CERT_OBJ_X509_RETIRED_12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_coa, 15}, - {PIV_CERT_OBJ_X509_RETIRED_13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_coa, 16}, - {PIV_CERT_OBJ_X509_RETIRED_14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_coa, 17}, - {PIV_CERT_OBJ_X509_RETIRED_15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_coa, 18}, - {PIV_CERT_OBJ_X509_RETIRED_16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_coa, 19}, - {PIV_CERT_OBJ_X509_RETIRED_17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_coa, 20}, - {PIV_CERT_OBJ_X509_RETIRED_18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_coa, 21}, - {PIV_CERT_OBJ_X509_RETIRED_19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_coa, 22}, - {PIV_CERT_OBJ_X509_RETIRED_20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_coa, 23}, + {PIV_CERT_OBJ_X509_RETIRED1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_coa, 4}, + {PIV_CERT_OBJ_X509_RETIRED2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_coa, 5}, + {PIV_CERT_OBJ_X509_RETIRED3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_coa, 6}, + {PIV_CERT_OBJ_X509_RETIRED4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_coa, 7}, + {PIV_CERT_OBJ_X509_RETIRED5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_coa, 8}, + {PIV_CERT_OBJ_X509_RETIRED6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_coa, 9}, + {PIV_CERT_OBJ_X509_RETIRED7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_coa, 10}, + {PIV_CERT_OBJ_X509_RETIRED8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_coa, 11}, + {PIV_CERT_OBJ_X509_RETIRED9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_coa, 12}, + {PIV_CERT_OBJ_X509_RETIRED10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_coa, 13}, + {PIV_CERT_OBJ_X509_RETIRED11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_coa, 14}, + {PIV_CERT_OBJ_X509_RETIRED12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_coa, 15}, + {PIV_CERT_OBJ_X509_RETIRED13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_coa, 16}, + {PIV_CERT_OBJ_X509_RETIRED14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_coa, 17}, + {PIV_CERT_OBJ_X509_RETIRED15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_coa, 18}, + {PIV_CERT_OBJ_X509_RETIRED16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_coa, 19}, + {PIV_CERT_OBJ_X509_RETIRED17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_coa, 20}, + {PIV_CERT_OBJ_X509_RETIRED18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_coa, 21}, + {PIV_CERT_OBJ_X509_RETIRED19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_coa, 22}, + {PIV_CERT_OBJ_X509_RETIRED20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_coa, 23}, {PIV_CERT_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24}, {PIV_PVTK_OBJ_PIV_AUTH, 1, 1, 0, "Private key for PIV Authentication", 0, 0, get_proa, 0}, // 9a {PIV_PVTK_OBJ_CARD_AUTH, 1, 0, 0, "Private key for Card Authentication", 0, 0, get_proa, 1}, // 9e {PIV_PVTK_OBJ_DS, 1, 1, 0, "Private key for Digital Signature", 0, 0, get_proa, 2}, // 9c {PIV_PVTK_OBJ_KM, 1, 1, 0, "Private key for Key Management", 0, 0, get_proa, 3}, // 9d - {PIV_PVTK_OBJ_RETIRED_1, 1, 1, 0, "Private key for retired key 1", 0, 0, get_proa, 4}, - {PIV_PVTK_OBJ_RETIRED_2, 1, 1, 0, "Private key for retired key 2", 0, 0, get_proa, 5}, - {PIV_PVTK_OBJ_RETIRED_3, 1, 1, 0, "Private key for retired key 3", 0, 0, get_proa, 6}, - {PIV_PVTK_OBJ_RETIRED_4, 1, 1, 0, "Private key for retired key 4", 0, 0, get_proa, 7}, - {PIV_PVTK_OBJ_RETIRED_5, 1, 1, 0, "Private key for retired key 5", 0, 0, get_proa, 8}, - {PIV_PVTK_OBJ_RETIRED_6, 1, 1, 0, "Private key for retired key 6", 0, 0, get_proa, 9}, - {PIV_PVTK_OBJ_RETIRED_7, 1, 1, 0, "Private key for retired key 7", 0, 0, get_proa, 10}, - {PIV_PVTK_OBJ_RETIRED_8, 1, 1, 0, "Private key for retired key 8", 0, 0, get_proa, 11}, - {PIV_PVTK_OBJ_RETIRED_9, 1, 1, 0, "Private key for retired key 9", 0, 0, get_proa, 12}, - {PIV_PVTK_OBJ_RETIRED_10, 1, 1, 0, "Private key for retired key 10", 0, 0, get_proa, 13}, - {PIV_PVTK_OBJ_RETIRED_11, 1, 1, 0, "Private key for retired key 11", 0, 0, get_proa, 14}, - {PIV_PVTK_OBJ_RETIRED_12, 1, 1, 0, "Private key for retired key 12", 0, 0, get_proa, 15}, - {PIV_PVTK_OBJ_RETIRED_13, 1, 1, 0, "Private key for retired key 13", 0, 0, get_proa, 16}, - {PIV_PVTK_OBJ_RETIRED_14, 1, 1, 0, "Private key for retired key 14", 0, 0, get_proa, 17}, - {PIV_PVTK_OBJ_RETIRED_15, 1, 1, 0, "Private key for retired key 15", 0, 0, get_proa, 18}, - {PIV_PVTK_OBJ_RETIRED_16, 1, 1, 0, "Private key for retired key 16", 0, 0, get_proa, 19}, - {PIV_PVTK_OBJ_RETIRED_17, 1, 1, 0, "Private key for retired key 17", 0, 0, get_proa, 20}, - {PIV_PVTK_OBJ_RETIRED_18, 1, 1, 0, "Private key for retired key 18", 0, 0, get_proa, 21}, - {PIV_PVTK_OBJ_RETIRED_19, 1, 1, 0, "Private key for retired key 19", 0, 0, get_proa, 22}, - {PIV_PVTK_OBJ_RETIRED_20, 1, 1, 0, "Private key for retired key 20", 0, 0, get_proa, 23}, + {PIV_PVTK_OBJ_RETIRED1, 1, 1, 0, "Private key for retired key 1", 0, 0, get_proa, 4}, + {PIV_PVTK_OBJ_RETIRED2, 1, 1, 0, "Private key for retired key 2", 0, 0, get_proa, 5}, + {PIV_PVTK_OBJ_RETIRED3, 1, 1, 0, "Private key for retired key 3", 0, 0, get_proa, 6}, + {PIV_PVTK_OBJ_RETIRED4, 1, 1, 0, "Private key for retired key 4", 0, 0, get_proa, 7}, + {PIV_PVTK_OBJ_RETIRED5, 1, 1, 0, "Private key for retired key 5", 0, 0, get_proa, 8}, + {PIV_PVTK_OBJ_RETIRED6, 1, 1, 0, "Private key for retired key 6", 0, 0, get_proa, 9}, + {PIV_PVTK_OBJ_RETIRED7, 1, 1, 0, "Private key for retired key 7", 0, 0, get_proa, 10}, + {PIV_PVTK_OBJ_RETIRED8, 1, 1, 0, "Private key for retired key 8", 0, 0, get_proa, 11}, + {PIV_PVTK_OBJ_RETIRED9, 1, 1, 0, "Private key for retired key 9", 0, 0, get_proa, 12}, + {PIV_PVTK_OBJ_RETIRED10, 1, 1, 0, "Private key for retired key 10", 0, 0, get_proa, 13}, + {PIV_PVTK_OBJ_RETIRED11, 1, 1, 0, "Private key for retired key 11", 0, 0, get_proa, 14}, + {PIV_PVTK_OBJ_RETIRED12, 1, 1, 0, "Private key for retired key 12", 0, 0, get_proa, 15}, + {PIV_PVTK_OBJ_RETIRED13, 1, 1, 0, "Private key for retired key 13", 0, 0, get_proa, 16}, + {PIV_PVTK_OBJ_RETIRED14, 1, 1, 0, "Private key for retired key 14", 0, 0, get_proa, 17}, + {PIV_PVTK_OBJ_RETIRED15, 1, 1, 0, "Private key for retired key 15", 0, 0, get_proa, 18}, + {PIV_PVTK_OBJ_RETIRED16, 1, 1, 0, "Private key for retired key 16", 0, 0, get_proa, 19}, + {PIV_PVTK_OBJ_RETIRED17, 1, 1, 0, "Private key for retired key 17", 0, 0, get_proa, 20}, + {PIV_PVTK_OBJ_RETIRED18, 1, 1, 0, "Private key for retired key 18", 0, 0, get_proa, 21}, + {PIV_PVTK_OBJ_RETIRED19, 1, 1, 0, "Private key for retired key 19", 0, 0, get_proa, 22}, + {PIV_PVTK_OBJ_RETIRED20, 1, 1, 0, "Private key for retired key 20", 0, 0, get_proa, 23}, {PIV_PVTK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24}, {PIV_PUBK_OBJ_PIV_AUTH, 1, 0, 0, "Public key for PIV Authentication", 0, 0, get_puoa, 0}, {PIV_PUBK_OBJ_CARD_AUTH, 1, 0, 0, "Public key for Card Authentication", 0, 0, get_puoa, 1}, {PIV_PUBK_OBJ_DS, 1, 0, 0, "Public key for Digital Signature", 0, 0, get_puoa, 2}, {PIV_PUBK_OBJ_KM, 1, 0, 0, "Public key for Key Management", 0, 0, get_puoa, 3}, - {PIV_PUBK_OBJ_RETIRED_1, 1, 0, 0, "Public key for retired key 1", 0, 0, get_puoa, 4}, - {PIV_PUBK_OBJ_RETIRED_2, 1, 0, 0, "Public key for retired key 2", 0, 0, get_puoa, 5}, - {PIV_PUBK_OBJ_RETIRED_3, 1, 0, 0, "Public key for retired key 3", 0, 0, get_puoa, 6}, - {PIV_PUBK_OBJ_RETIRED_4, 1, 0, 0, "Public key for retired key 4", 0, 0, get_puoa, 7}, - {PIV_PUBK_OBJ_RETIRED_5, 1, 0, 0, "Public key for retired key 5", 0, 0, get_puoa, 8}, - {PIV_PUBK_OBJ_RETIRED_6, 1, 0, 0, "Public key for retired key 6", 0, 0, get_puoa, 9}, - {PIV_PUBK_OBJ_RETIRED_7, 1, 0, 0, "Public key for retired key 7", 0, 0, get_puoa, 10}, - {PIV_PUBK_OBJ_RETIRED_8, 1, 0, 0, "Public key for retired key 8", 0, 0, get_puoa, 11}, - {PIV_PUBK_OBJ_RETIRED_9, 1, 0, 0, "Public key for retired key 9", 0, 0, get_puoa, 12}, - {PIV_PUBK_OBJ_RETIRED_10, 1, 0, 0, "Public key for retired key 10", 0, 0, get_puoa, 13}, - {PIV_PUBK_OBJ_RETIRED_11, 1, 0, 0, "Public key for retired key 11", 0, 0, get_puoa, 14}, - {PIV_PUBK_OBJ_RETIRED_12, 1, 0, 0, "Public key for retired key 12", 0, 0, get_puoa, 15}, - {PIV_PUBK_OBJ_RETIRED_13, 1, 0, 0, "Public key for retired key 13", 0, 0, get_puoa, 16}, - {PIV_PUBK_OBJ_RETIRED_14, 1, 0, 0, "Public key for retired key 14", 0, 0, get_puoa, 17}, - {PIV_PUBK_OBJ_RETIRED_15, 1, 0, 0, "Public key for retired key 15", 0, 0, get_puoa, 18}, - {PIV_PUBK_OBJ_RETIRED_16, 1, 0, 0, "Public key for retired key 16", 0, 0, get_puoa, 19}, - {PIV_PUBK_OBJ_RETIRED_17, 1, 0, 0, "Public key for retired key 17", 0, 0, get_puoa, 20}, - {PIV_PUBK_OBJ_RETIRED_18, 1, 0, 0, "Public key for retired key 18", 0, 0, get_puoa, 21}, - {PIV_PUBK_OBJ_RETIRED_19, 1, 0, 0, "Public key for retired key 19", 0, 0, get_puoa, 22}, - {PIV_PUBK_OBJ_RETIRED_20, 1, 0, 0, "Public key for retired key 20", 0, 0, get_puoa, 23}, + {PIV_PUBK_OBJ_RETIRED1, 1, 0, 0, "Public key for retired key 1", 0, 0, get_puoa, 4}, + {PIV_PUBK_OBJ_RETIRED2, 1, 0, 0, "Public key for retired key 2", 0, 0, get_puoa, 5}, + {PIV_PUBK_OBJ_RETIRED3, 1, 0, 0, "Public key for retired key 3", 0, 0, get_puoa, 6}, + {PIV_PUBK_OBJ_RETIRED4, 1, 0, 0, "Public key for retired key 4", 0, 0, get_puoa, 7}, + {PIV_PUBK_OBJ_RETIRED5, 1, 0, 0, "Public key for retired key 5", 0, 0, get_puoa, 8}, + {PIV_PUBK_OBJ_RETIRED6, 1, 0, 0, "Public key for retired key 6", 0, 0, get_puoa, 9}, + {PIV_PUBK_OBJ_RETIRED7, 1, 0, 0, "Public key for retired key 7", 0, 0, get_puoa, 10}, + {PIV_PUBK_OBJ_RETIRED8, 1, 0, 0, "Public key for retired key 8", 0, 0, get_puoa, 11}, + {PIV_PUBK_OBJ_RETIRED9, 1, 0, 0, "Public key for retired key 9", 0, 0, get_puoa, 12}, + {PIV_PUBK_OBJ_RETIRED10, 1, 0, 0, "Public key for retired key 10", 0, 0, get_puoa, 13}, + {PIV_PUBK_OBJ_RETIRED11, 1, 0, 0, "Public key for retired key 11", 0, 0, get_puoa, 14}, + {PIV_PUBK_OBJ_RETIRED12, 1, 0, 0, "Public key for retired key 12", 0, 0, get_puoa, 15}, + {PIV_PUBK_OBJ_RETIRED13, 1, 0, 0, "Public key for retired key 13", 0, 0, get_puoa, 16}, + {PIV_PUBK_OBJ_RETIRED14, 1, 0, 0, "Public key for retired key 14", 0, 0, get_puoa, 17}, + {PIV_PUBK_OBJ_RETIRED15, 1, 0, 0, "Public key for retired key 15", 0, 0, get_puoa, 18}, + {PIV_PUBK_OBJ_RETIRED16, 1, 0, 0, "Public key for retired key 16", 0, 0, get_puoa, 19}, + {PIV_PUBK_OBJ_RETIRED17, 1, 0, 0, "Public key for retired key 17", 0, 0, get_puoa, 20}, + {PIV_PUBK_OBJ_RETIRED18, 1, 0, 0, "Public key for retired key 18", 0, 0, get_puoa, 21}, + {PIV_PUBK_OBJ_RETIRED19, 1, 0, 0, "Public key for retired key 19", 0, 0, get_puoa, 22}, + {PIV_PUBK_OBJ_RETIRED20, 1, 0, 0, "Public key for retired key 20", 0, 0, get_puoa, 23}, {PIV_PUBK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24} }; @@ -1002,7 +1002,6 @@ CK_RV get_puoa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { } CK_ULONG piv_2_ykpiv(piv_obj_id_t id) { - // TODO: add retired keys switch(id) { case PIV_CERT_OBJ_X509_PIV_AUTH: return YKPIV_OBJ_AUTHENTICATION; @@ -1016,6 +1015,66 @@ CK_ULONG piv_2_ykpiv(piv_obj_id_t id) { case PIV_CERT_OBJ_X509_KM: return YKPIV_OBJ_KEY_MANAGEMENT; + case PIV_CERT_OBJ_X509_RETIRED1: + return YKPIV_OBJ_RETIRED1; + + case PIV_CERT_OBJ_X509_RETIRED2: + return YKPIV_OBJ_RETIRED2; + + case PIV_CERT_OBJ_X509_RETIRED3: + return YKPIV_OBJ_RETIRED3; + + case PIV_CERT_OBJ_X509_RETIRED4: + return YKPIV_OBJ_RETIRED4; + + case PIV_CERT_OBJ_X509_RETIRED5: + return YKPIV_OBJ_RETIRED5; + + case PIV_CERT_OBJ_X509_RETIRED6: + return YKPIV_OBJ_RETIRED6; + + case PIV_CERT_OBJ_X509_RETIRED7: + return YKPIV_OBJ_RETIRED7; + + case PIV_CERT_OBJ_X509_RETIRED8: + return YKPIV_OBJ_RETIRED8; + + case PIV_CERT_OBJ_X509_RETIRED9: + return YKPIV_OBJ_RETIRED9; + + case PIV_CERT_OBJ_X509_RETIRED10: + return YKPIV_OBJ_RETIRED10; + + case PIV_CERT_OBJ_X509_RETIRED11: + return YKPIV_OBJ_RETIRED11; + + case PIV_CERT_OBJ_X509_RETIRED12: + return YKPIV_OBJ_RETIRED12; + + case PIV_CERT_OBJ_X509_RETIRED13: + return YKPIV_OBJ_RETIRED13; + + case PIV_CERT_OBJ_X509_RETIRED14: + return YKPIV_OBJ_RETIRED14; + + case PIV_CERT_OBJ_X509_RETIRED15: + return YKPIV_OBJ_RETIRED15; + + case PIV_CERT_OBJ_X509_RETIRED16: + return YKPIV_OBJ_RETIRED16; + + case PIV_CERT_OBJ_X509_RETIRED17: + return YKPIV_OBJ_RETIRED17; + + case PIV_CERT_OBJ_X509_RETIRED18: + return YKPIV_OBJ_RETIRED18; + + case PIV_CERT_OBJ_X509_RETIRED19: + return YKPIV_OBJ_RETIRED19; + + case PIV_CERT_OBJ_X509_RETIRED20: + return YKPIV_OBJ_RETIRED20; + case PIV_PVTK_OBJ_PIV_AUTH: return YKPIV_KEY_AUTHENTICATION; @@ -1028,6 +1087,66 @@ CK_ULONG piv_2_ykpiv(piv_obj_id_t id) { case PIV_PVTK_OBJ_KM: return YKPIV_KEY_KEYMGM; + case PIV_PVTK_OBJ_RETIRED1: + return YKPIV_KEY_RETIRED1; + + case PIV_PVTK_OBJ_RETIRED2: + return YKPIV_KEY_RETIRED2; + + case PIV_PVTK_OBJ_RETIRED3: + return YKPIV_KEY_RETIRED3; + + case PIV_PVTK_OBJ_RETIRED4: + return YKPIV_KEY_RETIRED4; + + case PIV_PVTK_OBJ_RETIRED5: + return YKPIV_KEY_RETIRED5; + + case PIV_PVTK_OBJ_RETIRED6: + return YKPIV_KEY_RETIRED6; + + case PIV_PVTK_OBJ_RETIRED7: + return YKPIV_KEY_RETIRED7; + + case PIV_PVTK_OBJ_RETIRED8: + return YKPIV_KEY_RETIRED8; + + case PIV_PVTK_OBJ_RETIRED9: + return YKPIV_KEY_RETIRED9; + + case PIV_PVTK_OBJ_RETIRED10: + return YKPIV_KEY_RETIRED10; + + case PIV_PVTK_OBJ_RETIRED11: + return YKPIV_KEY_RETIRED11; + + case PIV_PVTK_OBJ_RETIRED12: + return YKPIV_KEY_RETIRED12; + + case PIV_PVTK_OBJ_RETIRED13: + return YKPIV_KEY_RETIRED13; + + case PIV_PVTK_OBJ_RETIRED14: + return YKPIV_KEY_RETIRED14; + + case PIV_PVTK_OBJ_RETIRED15: + return YKPIV_KEY_RETIRED15; + + case PIV_PVTK_OBJ_RETIRED16: + return YKPIV_KEY_RETIRED16; + + case PIV_PVTK_OBJ_RETIRED17: + return YKPIV_KEY_RETIRED17; + + case PIV_PVTK_OBJ_RETIRED18: + return YKPIV_KEY_RETIRED18; + + case PIV_PVTK_OBJ_RETIRED19: + return YKPIV_KEY_RETIRED19; + + case PIV_PVTK_OBJ_RETIRED20: + return YKPIV_KEY_RETIRED20; + default: return 0ul; } diff --git a/ykcs11/yubico_token.c b/ykcs11/yubico_token.c index 7210a29..f562203 100644 --- a/ykcs11/yubico_token.c +++ b/ykcs11/yubico_token.c @@ -228,9 +228,10 @@ static CK_RV get_objects(ykpiv_state *state, CK_BBOOL num_only, CK_BYTE buf[2048]; CK_ULONG buf_len; - piv_obj_id_t certs[4]; // TODO: this can be > 4 if there are retired keys - piv_obj_id_t pvtkeys[4]; - piv_obj_id_t pubkeys[4]; + piv_obj_id_t certs[24]; + piv_obj_id_t pvtkeys[24]; + piv_obj_id_t pubkeys[24]; + CK_ULONG i; CK_ULONG n_cert = 0; if (state == NULL || len == NULL_PTR) @@ -275,6 +276,17 @@ static CK_RV get_objects(ykpiv_state *state, CK_BBOOL num_only, DBG("Found KMK cert (9d)"); } + for (i = 0; i < 20; i++) { + buf_len = sizeof(buf); + if (ykpiv_fetch_object(state, YKPIV_OBJ_RETIRED1 + i, buf, &buf_len) == YKPIV_OK) { + certs[n_cert] = PIV_CERT_OBJ_X509_RETIRED1 + i; + pvtkeys[n_cert] = PIV_PVTK_OBJ_RETIRED1 + i; + pubkeys[n_cert] = PIV_PUBK_OBJ_RETIRED1 + i; + n_cert++; + DBG("Found RETIRED cert (%lx)", 0x82 + i); + } + } + DBG("The total number of objects for this token is %lu", (n_cert * 3) + token_objects_num); if (num_only == CK_TRUE) { From 2d7b8fadc959b41d2dc0ec339d1d3fafc400e4e8 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 11:12:56 +0100 Subject: [PATCH 018/107] Capitalize. --- ykcs11/objects.c | 160 +++++++++++++++++++++++------------------------ 1 file changed, 80 insertions(+), 80 deletions(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index 4d15ecf..6dc080b 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -24,26 +24,26 @@ static piv_obj_t piv_objects[] = { {PIV_DATA_OBJ_X509_CARD_AUTH, 1, 0, 0, "X.509 Certificate for Card Authentication", 0, 0, get_doa, 1}, {PIV_DATA_OBJ_X509_DS, 1, 0, 0, "X.509 Certificate for Digital Signature", 0, 0, get_doa, 2}, {PIV_DATA_OBJ_X509_KM, 1, 0, 0, "X.509 Certificate for Key Management", 0, 0, get_doa, 3}, - {PIV_DATA_OBJ_X509_RETIRED1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_doa, 4}, - {PIV_DATA_OBJ_X509_RETIRED2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_doa, 5}, - {PIV_DATA_OBJ_X509_RETIRED3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_doa, 6}, - {PIV_DATA_OBJ_X509_RETIRED4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_doa, 7}, - {PIV_DATA_OBJ_X509_RETIRED5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_doa, 8}, - {PIV_DATA_OBJ_X509_RETIRED6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_doa, 9}, - {PIV_DATA_OBJ_X509_RETIRED7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_doa, 10}, - {PIV_DATA_OBJ_X509_RETIRED8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_doa, 11}, - {PIV_DATA_OBJ_X509_RETIRED9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_doa, 12}, - {PIV_DATA_OBJ_X509_RETIRED10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_doa, 13}, - {PIV_DATA_OBJ_X509_RETIRED11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_doa, 14}, - {PIV_DATA_OBJ_X509_RETIRED12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_doa, 15}, - {PIV_DATA_OBJ_X509_RETIRED13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_doa, 16}, - {PIV_DATA_OBJ_X509_RETIRED14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_doa, 17}, - {PIV_DATA_OBJ_X509_RETIRED15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_doa, 18}, - {PIV_DATA_OBJ_X509_RETIRED16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_doa, 19}, - {PIV_DATA_OBJ_X509_RETIRED17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_doa, 20}, - {PIV_DATA_OBJ_X509_RETIRED18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_doa, 21}, - {PIV_DATA_OBJ_X509_RETIRED19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_doa, 22}, - {PIV_DATA_OBJ_X509_RETIRED20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_doa, 23}, + {PIV_DATA_OBJ_X509_RETIRED1, 1, 0, 0, "X.509 Certificate for Retired Key 1", 0, 0, get_doa, 4}, + {PIV_DATA_OBJ_X509_RETIRED2, 1, 0, 0, "X.509 Certificate for Retired Key 2", 0, 0, get_doa, 5}, + {PIV_DATA_OBJ_X509_RETIRED3, 1, 0, 0, "X.509 Certificate for Retired Key 3", 0, 0, get_doa, 6}, + {PIV_DATA_OBJ_X509_RETIRED4, 1, 0, 0, "X.509 Certificate for Retired Key 4", 0, 0, get_doa, 7}, + {PIV_DATA_OBJ_X509_RETIRED5, 1, 0, 0, "X.509 Certificate for Retired Key 5", 0, 0, get_doa, 8}, + {PIV_DATA_OBJ_X509_RETIRED6, 1, 0, 0, "X.509 Certificate for Retired Key 6", 0, 0, get_doa, 9}, + {PIV_DATA_OBJ_X509_RETIRED7, 1, 0, 0, "X.509 Certificate for Retired Key 7", 0, 0, get_doa, 10}, + {PIV_DATA_OBJ_X509_RETIRED8, 1, 0, 0, "X.509 Certificate for Retired Key 8", 0, 0, get_doa, 11}, + {PIV_DATA_OBJ_X509_RETIRED9, 1, 0, 0, "X.509 Certificate for Retired Key 9", 0, 0, get_doa, 12}, + {PIV_DATA_OBJ_X509_RETIRED10, 1, 0, 0, "X.509 Certificate for Retired Key 10", 0, 0, get_doa, 13}, + {PIV_DATA_OBJ_X509_RETIRED11, 1, 0, 0, "X.509 Certificate for Retired Key 11", 0, 0, get_doa, 14}, + {PIV_DATA_OBJ_X509_RETIRED12, 1, 0, 0, "X.509 Certificate for Retired Key 12", 0, 0, get_doa, 15}, + {PIV_DATA_OBJ_X509_RETIRED13, 1, 0, 0, "X.509 Certificate for Retired Key 13", 0, 0, get_doa, 16}, + {PIV_DATA_OBJ_X509_RETIRED14, 1, 0, 0, "X.509 Certificate for Retired Key 14", 0, 0, get_doa, 17}, + {PIV_DATA_OBJ_X509_RETIRED15, 1, 0, 0, "X.509 Certificate for Retired Key 15", 0, 0, get_doa, 18}, + {PIV_DATA_OBJ_X509_RETIRED16, 1, 0, 0, "X.509 Certificate for Retired Key 16", 0, 0, get_doa, 19}, + {PIV_DATA_OBJ_X509_RETIRED17, 1, 0, 0, "X.509 Certificate for Retired Key 17", 0, 0, get_doa, 20}, + {PIV_DATA_OBJ_X509_RETIRED18, 1, 0, 0, "X.509 Certificate for Retired Key 18", 0, 0, get_doa, 21}, + {PIV_DATA_OBJ_X509_RETIRED19, 1, 0, 0, "X.509 Certificate for Retired Key 19", 0, 0, get_doa, 22}, + {PIV_DATA_OBJ_X509_RETIRED20, 1, 0, 0, "X.509 Certificate for Retired Key 20", 0, 0, get_doa, 23}, {PIV_DATA_OBJ_CCC, 1, 0, 0, "Card Capability Container", 0, 0, get_doa, 24}, {PIV_DATA_OBJ_CHUI, 1, 0, 0, "Card Holder Unique Identifier", 0, 0, get_doa, 25}, {PIV_DATA_OBJ_CHF, 1, 1, 0, "Card Holder Fingerprints", 0, 0, get_doa, 26}, @@ -62,78 +62,78 @@ static piv_obj_t piv_objects[] = { {PIV_CERT_OBJ_X509_CARD_AUTH, 1, 0, 0, "X.509 Certificate for Card Authentication", 0, 0, get_coa, 1}, {PIV_CERT_OBJ_X509_DS, 1, 0, 0, "X.509 Certificate for Digital Signature", 0, 0, get_coa, 2}, {PIV_CERT_OBJ_X509_KM, 1, 0, 0, "X.509 Certificate for Key Management", 0, 0, get_coa, 3}, - {PIV_CERT_OBJ_X509_RETIRED1, 1, 0, 0, "X.509 Certificate for retired key 1", 0, 0, get_coa, 4}, - {PIV_CERT_OBJ_X509_RETIRED2, 1, 0, 0, "X.509 Certificate for retired key 2", 0, 0, get_coa, 5}, - {PIV_CERT_OBJ_X509_RETIRED3, 1, 0, 0, "X.509 Certificate for retired key 3", 0, 0, get_coa, 6}, - {PIV_CERT_OBJ_X509_RETIRED4, 1, 0, 0, "X.509 Certificate for retired key 4", 0, 0, get_coa, 7}, - {PIV_CERT_OBJ_X509_RETIRED5, 1, 0, 0, "X.509 Certificate for retired key 5", 0, 0, get_coa, 8}, - {PIV_CERT_OBJ_X509_RETIRED6, 1, 0, 0, "X.509 Certificate for retired key 6", 0, 0, get_coa, 9}, - {PIV_CERT_OBJ_X509_RETIRED7, 1, 0, 0, "X.509 Certificate for retired key 7", 0, 0, get_coa, 10}, - {PIV_CERT_OBJ_X509_RETIRED8, 1, 0, 0, "X.509 Certificate for retired key 8", 0, 0, get_coa, 11}, - {PIV_CERT_OBJ_X509_RETIRED9, 1, 0, 0, "X.509 Certificate for retired key 9", 0, 0, get_coa, 12}, - {PIV_CERT_OBJ_X509_RETIRED10, 1, 0, 0, "X.509 Certificate for retired key 10", 0, 0, get_coa, 13}, - {PIV_CERT_OBJ_X509_RETIRED11, 1, 0, 0, "X.509 Certificate for retired key 11", 0, 0, get_coa, 14}, - {PIV_CERT_OBJ_X509_RETIRED12, 1, 0, 0, "X.509 Certificate for retired key 12", 0, 0, get_coa, 15}, - {PIV_CERT_OBJ_X509_RETIRED13, 1, 0, 0, "X.509 Certificate for retired key 13", 0, 0, get_coa, 16}, - {PIV_CERT_OBJ_X509_RETIRED14, 1, 0, 0, "X.509 Certificate for retired key 14", 0, 0, get_coa, 17}, - {PIV_CERT_OBJ_X509_RETIRED15, 1, 0, 0, "X.509 Certificate for retired key 15", 0, 0, get_coa, 18}, - {PIV_CERT_OBJ_X509_RETIRED16, 1, 0, 0, "X.509 Certificate for retired key 16", 0, 0, get_coa, 19}, - {PIV_CERT_OBJ_X509_RETIRED17, 1, 0, 0, "X.509 Certificate for retired key 17", 0, 0, get_coa, 20}, - {PIV_CERT_OBJ_X509_RETIRED18, 1, 0, 0, "X.509 Certificate for retired key 18", 0, 0, get_coa, 21}, - {PIV_CERT_OBJ_X509_RETIRED19, 1, 0, 0, "X.509 Certificate for retired key 19", 0, 0, get_coa, 22}, - {PIV_CERT_OBJ_X509_RETIRED20, 1, 0, 0, "X.509 Certificate for retired key 20", 0, 0, get_coa, 23}, + {PIV_CERT_OBJ_X509_RETIRED1, 1, 0, 0, "X.509 Certificate for Retired Key 1", 0, 0, get_coa, 4}, + {PIV_CERT_OBJ_X509_RETIRED2, 1, 0, 0, "X.509 Certificate for Retired Key 2", 0, 0, get_coa, 5}, + {PIV_CERT_OBJ_X509_RETIRED3, 1, 0, 0, "X.509 Certificate for Retired Key 3", 0, 0, get_coa, 6}, + {PIV_CERT_OBJ_X509_RETIRED4, 1, 0, 0, "X.509 Certificate for Retired Key 4", 0, 0, get_coa, 7}, + {PIV_CERT_OBJ_X509_RETIRED5, 1, 0, 0, "X.509 Certificate for Retired Key 5", 0, 0, get_coa, 8}, + {PIV_CERT_OBJ_X509_RETIRED6, 1, 0, 0, "X.509 Certificate for Retired Key 6", 0, 0, get_coa, 9}, + {PIV_CERT_OBJ_X509_RETIRED7, 1, 0, 0, "X.509 Certificate for Retired Key 7", 0, 0, get_coa, 10}, + {PIV_CERT_OBJ_X509_RETIRED8, 1, 0, 0, "X.509 Certificate for Retired Key 8", 0, 0, get_coa, 11}, + {PIV_CERT_OBJ_X509_RETIRED9, 1, 0, 0, "X.509 Certificate for Retired Key 9", 0, 0, get_coa, 12}, + {PIV_CERT_OBJ_X509_RETIRED10, 1, 0, 0, "X.509 Certificate for Retired Key 10", 0, 0, get_coa, 13}, + {PIV_CERT_OBJ_X509_RETIRED11, 1, 0, 0, "X.509 Certificate for Retired Key 11", 0, 0, get_coa, 14}, + {PIV_CERT_OBJ_X509_RETIRED12, 1, 0, 0, "X.509 Certificate for Retired Key 12", 0, 0, get_coa, 15}, + {PIV_CERT_OBJ_X509_RETIRED13, 1, 0, 0, "X.509 Certificate for Retired Key 13", 0, 0, get_coa, 16}, + {PIV_CERT_OBJ_X509_RETIRED14, 1, 0, 0, "X.509 Certificate for Retired Key 14", 0, 0, get_coa, 17}, + {PIV_CERT_OBJ_X509_RETIRED15, 1, 0, 0, "X.509 Certificate for Retired Key 15", 0, 0, get_coa, 18}, + {PIV_CERT_OBJ_X509_RETIRED16, 1, 0, 0, "X.509 Certificate for Retired Key 16", 0, 0, get_coa, 19}, + {PIV_CERT_OBJ_X509_RETIRED17, 1, 0, 0, "X.509 Certificate for Retired Key 17", 0, 0, get_coa, 20}, + {PIV_CERT_OBJ_X509_RETIRED18, 1, 0, 0, "X.509 Certificate for Retired Key 18", 0, 0, get_coa, 21}, + {PIV_CERT_OBJ_X509_RETIRED19, 1, 0, 0, "X.509 Certificate for Retired Key 19", 0, 0, get_coa, 22}, + {PIV_CERT_OBJ_X509_RETIRED20, 1, 0, 0, "X.509 Certificate for Retired Key 20", 0, 0, get_coa, 23}, {PIV_CERT_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24}, {PIV_PVTK_OBJ_PIV_AUTH, 1, 1, 0, "Private key for PIV Authentication", 0, 0, get_proa, 0}, // 9a {PIV_PVTK_OBJ_CARD_AUTH, 1, 0, 0, "Private key for Card Authentication", 0, 0, get_proa, 1}, // 9e {PIV_PVTK_OBJ_DS, 1, 1, 0, "Private key for Digital Signature", 0, 0, get_proa, 2}, // 9c {PIV_PVTK_OBJ_KM, 1, 1, 0, "Private key for Key Management", 0, 0, get_proa, 3}, // 9d - {PIV_PVTK_OBJ_RETIRED1, 1, 1, 0, "Private key for retired key 1", 0, 0, get_proa, 4}, - {PIV_PVTK_OBJ_RETIRED2, 1, 1, 0, "Private key for retired key 2", 0, 0, get_proa, 5}, - {PIV_PVTK_OBJ_RETIRED3, 1, 1, 0, "Private key for retired key 3", 0, 0, get_proa, 6}, - {PIV_PVTK_OBJ_RETIRED4, 1, 1, 0, "Private key for retired key 4", 0, 0, get_proa, 7}, - {PIV_PVTK_OBJ_RETIRED5, 1, 1, 0, "Private key for retired key 5", 0, 0, get_proa, 8}, - {PIV_PVTK_OBJ_RETIRED6, 1, 1, 0, "Private key for retired key 6", 0, 0, get_proa, 9}, - {PIV_PVTK_OBJ_RETIRED7, 1, 1, 0, "Private key for retired key 7", 0, 0, get_proa, 10}, - {PIV_PVTK_OBJ_RETIRED8, 1, 1, 0, "Private key for retired key 8", 0, 0, get_proa, 11}, - {PIV_PVTK_OBJ_RETIRED9, 1, 1, 0, "Private key for retired key 9", 0, 0, get_proa, 12}, - {PIV_PVTK_OBJ_RETIRED10, 1, 1, 0, "Private key for retired key 10", 0, 0, get_proa, 13}, - {PIV_PVTK_OBJ_RETIRED11, 1, 1, 0, "Private key for retired key 11", 0, 0, get_proa, 14}, - {PIV_PVTK_OBJ_RETIRED12, 1, 1, 0, "Private key for retired key 12", 0, 0, get_proa, 15}, - {PIV_PVTK_OBJ_RETIRED13, 1, 1, 0, "Private key for retired key 13", 0, 0, get_proa, 16}, - {PIV_PVTK_OBJ_RETIRED14, 1, 1, 0, "Private key for retired key 14", 0, 0, get_proa, 17}, - {PIV_PVTK_OBJ_RETIRED15, 1, 1, 0, "Private key for retired key 15", 0, 0, get_proa, 18}, - {PIV_PVTK_OBJ_RETIRED16, 1, 1, 0, "Private key for retired key 16", 0, 0, get_proa, 19}, - {PIV_PVTK_OBJ_RETIRED17, 1, 1, 0, "Private key for retired key 17", 0, 0, get_proa, 20}, - {PIV_PVTK_OBJ_RETIRED18, 1, 1, 0, "Private key for retired key 18", 0, 0, get_proa, 21}, - {PIV_PVTK_OBJ_RETIRED19, 1, 1, 0, "Private key for retired key 19", 0, 0, get_proa, 22}, - {PIV_PVTK_OBJ_RETIRED20, 1, 1, 0, "Private key for retired key 20", 0, 0, get_proa, 23}, + {PIV_PVTK_OBJ_RETIRED1, 1, 1, 0, "Private key for Retired Key 1", 0, 0, get_proa, 4}, + {PIV_PVTK_OBJ_RETIRED2, 1, 1, 0, "Private key for Retired Key 2", 0, 0, get_proa, 5}, + {PIV_PVTK_OBJ_RETIRED3, 1, 1, 0, "Private key for Retired Key 3", 0, 0, get_proa, 6}, + {PIV_PVTK_OBJ_RETIRED4, 1, 1, 0, "Private key for Retired Key 4", 0, 0, get_proa, 7}, + {PIV_PVTK_OBJ_RETIRED5, 1, 1, 0, "Private key for Retired Key 5", 0, 0, get_proa, 8}, + {PIV_PVTK_OBJ_RETIRED6, 1, 1, 0, "Private key for Retired Key 6", 0, 0, get_proa, 9}, + {PIV_PVTK_OBJ_RETIRED7, 1, 1, 0, "Private key for Retired Key 7", 0, 0, get_proa, 10}, + {PIV_PVTK_OBJ_RETIRED8, 1, 1, 0, "Private key for Retired Key 8", 0, 0, get_proa, 11}, + {PIV_PVTK_OBJ_RETIRED9, 1, 1, 0, "Private key for Retired Key 9", 0, 0, get_proa, 12}, + {PIV_PVTK_OBJ_RETIRED10, 1, 1, 0, "Private key forRretired Key 10", 0, 0, get_proa, 13}, + {PIV_PVTK_OBJ_RETIRED11, 1, 1, 0, "Private key forRretired Key 11", 0, 0, get_proa, 14}, + {PIV_PVTK_OBJ_RETIRED12, 1, 1, 0, "Private key forRretired Key 12", 0, 0, get_proa, 15}, + {PIV_PVTK_OBJ_RETIRED13, 1, 1, 0, "Private key forRretired Key 13", 0, 0, get_proa, 16}, + {PIV_PVTK_OBJ_RETIRED14, 1, 1, 0, "Private key forRretired Key 14", 0, 0, get_proa, 17}, + {PIV_PVTK_OBJ_RETIRED15, 1, 1, 0, "Private key forRretired Key 15", 0, 0, get_proa, 18}, + {PIV_PVTK_OBJ_RETIRED16, 1, 1, 0, "Private key forRretired Key 16", 0, 0, get_proa, 19}, + {PIV_PVTK_OBJ_RETIRED17, 1, 1, 0, "Private key forRretired Key 17", 0, 0, get_proa, 20}, + {PIV_PVTK_OBJ_RETIRED18, 1, 1, 0, "Private key forRretired Key 18", 0, 0, get_proa, 21}, + {PIV_PVTK_OBJ_RETIRED19, 1, 1, 0, "Private key forRretired Key 19", 0, 0, get_proa, 22}, + {PIV_PVTK_OBJ_RETIRED20, 1, 1, 0, "Private key forRretired Key 20", 0, 0, get_proa, 23}, {PIV_PVTK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24}, {PIV_PUBK_OBJ_PIV_AUTH, 1, 0, 0, "Public key for PIV Authentication", 0, 0, get_puoa, 0}, {PIV_PUBK_OBJ_CARD_AUTH, 1, 0, 0, "Public key for Card Authentication", 0, 0, get_puoa, 1}, {PIV_PUBK_OBJ_DS, 1, 0, 0, "Public key for Digital Signature", 0, 0, get_puoa, 2}, {PIV_PUBK_OBJ_KM, 1, 0, 0, "Public key for Key Management", 0, 0, get_puoa, 3}, - {PIV_PUBK_OBJ_RETIRED1, 1, 0, 0, "Public key for retired key 1", 0, 0, get_puoa, 4}, - {PIV_PUBK_OBJ_RETIRED2, 1, 0, 0, "Public key for retired key 2", 0, 0, get_puoa, 5}, - {PIV_PUBK_OBJ_RETIRED3, 1, 0, 0, "Public key for retired key 3", 0, 0, get_puoa, 6}, - {PIV_PUBK_OBJ_RETIRED4, 1, 0, 0, "Public key for retired key 4", 0, 0, get_puoa, 7}, - {PIV_PUBK_OBJ_RETIRED5, 1, 0, 0, "Public key for retired key 5", 0, 0, get_puoa, 8}, - {PIV_PUBK_OBJ_RETIRED6, 1, 0, 0, "Public key for retired key 6", 0, 0, get_puoa, 9}, - {PIV_PUBK_OBJ_RETIRED7, 1, 0, 0, "Public key for retired key 7", 0, 0, get_puoa, 10}, - {PIV_PUBK_OBJ_RETIRED8, 1, 0, 0, "Public key for retired key 8", 0, 0, get_puoa, 11}, - {PIV_PUBK_OBJ_RETIRED9, 1, 0, 0, "Public key for retired key 9", 0, 0, get_puoa, 12}, - {PIV_PUBK_OBJ_RETIRED10, 1, 0, 0, "Public key for retired key 10", 0, 0, get_puoa, 13}, - {PIV_PUBK_OBJ_RETIRED11, 1, 0, 0, "Public key for retired key 11", 0, 0, get_puoa, 14}, - {PIV_PUBK_OBJ_RETIRED12, 1, 0, 0, "Public key for retired key 12", 0, 0, get_puoa, 15}, - {PIV_PUBK_OBJ_RETIRED13, 1, 0, 0, "Public key for retired key 13", 0, 0, get_puoa, 16}, - {PIV_PUBK_OBJ_RETIRED14, 1, 0, 0, "Public key for retired key 14", 0, 0, get_puoa, 17}, - {PIV_PUBK_OBJ_RETIRED15, 1, 0, 0, "Public key for retired key 15", 0, 0, get_puoa, 18}, - {PIV_PUBK_OBJ_RETIRED16, 1, 0, 0, "Public key for retired key 16", 0, 0, get_puoa, 19}, - {PIV_PUBK_OBJ_RETIRED17, 1, 0, 0, "Public key for retired key 17", 0, 0, get_puoa, 20}, - {PIV_PUBK_OBJ_RETIRED18, 1, 0, 0, "Public key for retired key 18", 0, 0, get_puoa, 21}, - {PIV_PUBK_OBJ_RETIRED19, 1, 0, 0, "Public key for retired key 19", 0, 0, get_puoa, 22}, - {PIV_PUBK_OBJ_RETIRED20, 1, 0, 0, "Public key for retired key 20", 0, 0, get_puoa, 23}, + {PIV_PUBK_OBJ_RETIRED1, 1, 0, 0, "Public key for Retired Key 1", 0, 0, get_puoa, 4}, + {PIV_PUBK_OBJ_RETIRED2, 1, 0, 0, "Public key for Retired Key 2", 0, 0, get_puoa, 5}, + {PIV_PUBK_OBJ_RETIRED3, 1, 0, 0, "Public key for Retired Key 3", 0, 0, get_puoa, 6}, + {PIV_PUBK_OBJ_RETIRED4, 1, 0, 0, "Public key for Retired Key 4", 0, 0, get_puoa, 7}, + {PIV_PUBK_OBJ_RETIRED5, 1, 0, 0, "Public key for Retired Key 5", 0, 0, get_puoa, 8}, + {PIV_PUBK_OBJ_RETIRED6, 1, 0, 0, "Public key for Retired Key 6", 0, 0, get_puoa, 9}, + {PIV_PUBK_OBJ_RETIRED7, 1, 0, 0, "Public key for Retired Key 7", 0, 0, get_puoa, 10}, + {PIV_PUBK_OBJ_RETIRED8, 1, 0, 0, "Public key for Retired Key 8", 0, 0, get_puoa, 11}, + {PIV_PUBK_OBJ_RETIRED9, 1, 0, 0, "Public key for Retired Key 9", 0, 0, get_puoa, 12}, + {PIV_PUBK_OBJ_RETIRED10, 1, 0, 0, "Public key for Retired Key 10", 0, 0, get_puoa, 13}, + {PIV_PUBK_OBJ_RETIRED11, 1, 0, 0, "Public key for Retired Key 11", 0, 0, get_puoa, 14}, + {PIV_PUBK_OBJ_RETIRED12, 1, 0, 0, "Public key for Retired Key 12", 0, 0, get_puoa, 15}, + {PIV_PUBK_OBJ_RETIRED13, 1, 0, 0, "Public key for Retired Key 13", 0, 0, get_puoa, 16}, + {PIV_PUBK_OBJ_RETIRED14, 1, 0, 0, "Public key for Retired Key 14", 0, 0, get_puoa, 17}, + {PIV_PUBK_OBJ_RETIRED15, 1, 0, 0, "Public key for Retired Key 15", 0, 0, get_puoa, 18}, + {PIV_PUBK_OBJ_RETIRED16, 1, 0, 0, "Public key for Retired Key 16", 0, 0, get_puoa, 19}, + {PIV_PUBK_OBJ_RETIRED17, 1, 0, 0, "Public key for Retired Key 17", 0, 0, get_puoa, 20}, + {PIV_PUBK_OBJ_RETIRED18, 1, 0, 0, "Public key for Retired Key 18", 0, 0, get_puoa, 21}, + {PIV_PUBK_OBJ_RETIRED19, 1, 0, 0, "Public key for Retired Key 19", 0, 0, get_puoa, 22}, + {PIV_PUBK_OBJ_RETIRED20, 1, 0, 0, "Public key for Retired Key 20", 0, 0, get_puoa, 23}, {PIV_PUBK_OBJ_LAST, 1, 0, 0, "", 0, 0, NULL, 24} }; From d00150ac05a871815a008dcfbeb05e376e163b6f Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 13:01:32 +0100 Subject: [PATCH 019/107] Add retired keys to Find operations. --- ykcs11/yubico_token.c | 103 +++++++++++++++++++++++++----------------- 1 file changed, 61 insertions(+), 42 deletions(-) diff --git a/ykcs11/yubico_token.c b/ykcs11/yubico_token.c index f562203..15da5e0 100644 --- a/ykcs11/yubico_token.c +++ b/ykcs11/yubico_token.c @@ -69,40 +69,41 @@ static const piv_obj_id_t token_objects[] = { // TODO: is there a way to get thi PIV_DATA_OBJ_X509_CARD_AUTH, // Certificate for card authentication PIV_DATA_OBJ_X509_DS, // Certificate for digital signature PIV_DATA_OBJ_X509_KM, // Certificate for key management + PIV_DATA_OBJ_X509_RETIRED1, // Certificate for retired key 1 + PIV_DATA_OBJ_X509_RETIRED2, // Certificate for retired key 2 + PIV_DATA_OBJ_X509_RETIRED3, // Certificate for retired key 3 + PIV_DATA_OBJ_X509_RETIRED4, // Certificate for retired key 4 + PIV_DATA_OBJ_X509_RETIRED5, // Certificate for retired key 5 + PIV_DATA_OBJ_X509_RETIRED6, // Certificate for retired key 6 + PIV_DATA_OBJ_X509_RETIRED7, // Certificate for retired key 7 + PIV_DATA_OBJ_X509_RETIRED8, // Certificate for retired key 8 + PIV_DATA_OBJ_X509_RETIRED9, // Certificate for retired key 9 + PIV_DATA_OBJ_X509_RETIRED10, // Certificate for retired key 10 + PIV_DATA_OBJ_X509_RETIRED11, // Certificate for retired key 11 + PIV_DATA_OBJ_X509_RETIRED12, // Certificate for retired key 12 + PIV_DATA_OBJ_X509_RETIRED13, // Certificate for retired key 13 + PIV_DATA_OBJ_X509_RETIRED14, // Certificate for retired key 14 + PIV_DATA_OBJ_X509_RETIRED15, // Certificate for retired key 15 + PIV_DATA_OBJ_X509_RETIRED16, // Certificate for retired key 16 + PIV_DATA_OBJ_X509_RETIRED17, // Certificate for retired key 17 + PIV_DATA_OBJ_X509_RETIRED18, // Certificate for retired key 18 + PIV_DATA_OBJ_X509_RETIRED19, // Certificate for retired key 19 + PIV_DATA_OBJ_X509_RETIRED20, // Certificate for retired key 20 PIV_DATA_OBJ_CCC, // Card capability container PIV_DATA_OBJ_CHUI, // Cardholder unique id PIV_DATA_OBJ_CHF, // Cardholder fingerprints PIV_DATA_OBJ_SEC_OBJ, // Security object PIV_DATA_OBJ_CHFI, // Cardholder facial images - //PIV_DATA_OBJ_PI, // Cardholder printed information - //PIV_DATA_OBJ_DISCOVERY, // Discovery object - //PIV_DATA_OBJ_HISTORY, // History object -/* PIV_DATA_OBJ_RETIRED_X509_1, // Retired certificate for KM 1 - PIV_DATA_OBJ_RETIRED_X509_2, // Retired certificate for KM 2 - PIV_DATA_OBJ_RETIRED_X509_3, // Retired certificate for KM 3 - PIV_DATA_OBJ_RETIRED_X509_4, // Retired certificate for KM 4 - PIV_DATA_OBJ_RETIRED_X509_5, // Retired certificate for KM 5 - PIV_DATA_OBJ_RETIRED_X509_6, // Retired certificate for KM 6 - PIV_DATA_OBJ_RETIRED_X509_7, // Retired certificate for KM 7 - PIV_DATA_OBJ_RETIRED_X509_8, // Retired certificate for KM 8 - PIV_DATA_OBJ_RETIRED_X509_9, // Retired certificate for KM 9 - PIV_DATA_OBJ_RETIRED_X509_10, // Retired certificate for KM 10 - PIV_DATA_OBJ_RETIRED_X509_11, // Retired certificate for KM 11 - PIV_DATA_OBJ_RETIRED_X509_12, // Retired certificate for KM 12 - PIV_DATA_OBJ_RETIRED_X509_13, // Retired certificate for KM 13 - PIV_DATA_OBJ_RETIRED_X509_14, // Retired certificate for KM 14 - PIV_DATA_OBJ_RETIRED_X509_15, // Retired certificate for KM 15 - PIV_DATA_OBJ_RETIRED_X509_16, // Retired certificate for KM 16 - PIV_DATA_OBJ_RETIRED_X509_17, // Retired certificate for KM 17 - PIV_DATA_OBJ_RETIRED_X509_18, // Retired certificate for KM 18 - PIV_DATA_OBJ_RETIRED_X509_19, // Retired certificate for KM 19 - PIV_DATA_OBJ_RETIRED_X509_20, // Retired certificate for KM 20*/ - //PIV_DATA_OBJ_IRIS_IMAGE, // Cardholder iris images - //PIV_DATA_OBJ_BITGT, // Biometric information templates group template - //PIV_DATA_OBJ_SM_SIGNER, // Secure messaging signer - //PIV_DATA_OBJ_PC_REF_DATA, // Pairing code reference data + //PIV_DATA_OBJ_PI, // Cardholder printed information + //PIV_DATA_OBJ_DISCOVERY, // Discovery object + //PIV_DATA_OBJ_HISTORY, // History object + //PIV_DATA_OBJ_IRIS_IMAGE, // Cardholder iris images + //PIV_DATA_OBJ_BITGT, // Biometric information templates group template + //PIV_DATA_OBJ_SM_SIGNER, // Secure messaging signer + //PIV_DATA_OBJ_PC_REF_DATA, // Pairing code reference data }; -static const CK_ULONG token_objects_num = sizeof(token_objects) / sizeof(piv_obj_id_t); +static const CK_ULONG neo_token_objects_num = sizeof(token_objects) / sizeof(piv_obj_id_t) - 20; +static const CK_ULONG yk4_token_objects_num = sizeof(token_objects) / sizeof(piv_obj_id_t); CK_RV YUBICO_get_token_label(CK_UTF8CHAR_PTR str, CK_ULONG len) { @@ -225,14 +226,16 @@ CK_RV YUBICO_get_token_mechanism_info(CK_MECHANISM_TYPE mec, CK_MECHANISM_INFO_P static CK_RV get_objects(ykpiv_state *state, CK_BBOOL num_only, piv_obj_id_t *obj, CK_ULONG_PTR len, CK_ULONG_PTR num_certs) { - CK_BYTE buf[2048]; - CK_ULONG buf_len; + CK_BYTE buf[2048]; + CK_ULONG buf_len; + CK_BYTE major; + CK_ULONG i; piv_obj_id_t certs[24]; piv_obj_id_t pvtkeys[24]; piv_obj_id_t pubkeys[24]; - CK_ULONG i; - CK_ULONG n_cert = 0; + CK_ULONG n_cert = 0; + CK_ULONG token_objects_num = neo_token_objects_num; if (state == NULL || len == NULL_PTR) return CKR_ARGUMENTS_BAD; @@ -240,6 +243,11 @@ static CK_RV get_objects(ykpiv_state *state, CK_BBOOL num_only, if (num_only == CK_FALSE && obj == NULL) return CKR_ARGUMENTS_BAD; + if (ykpiv_get_version(state, (char *) buf, sizeof(buf)) != YKPIV_OK) + return CKR_FUNCTION_FAILED; + + major = buf[0] - '0'; + buf_len = sizeof(buf); if (ykpiv_fetch_object(state, YKPIV_OBJ_AUTHENTICATION, buf, &buf_len) == YKPIV_OK) { certs[n_cert] = PIV_CERT_OBJ_X509_PIV_AUTH; @@ -276,15 +284,18 @@ static CK_RV get_objects(ykpiv_state *state, CK_BBOOL num_only, DBG("Found KMK cert (9d)"); } - for (i = 0; i < 20; i++) { - buf_len = sizeof(buf); - if (ykpiv_fetch_object(state, YKPIV_OBJ_RETIRED1 + i, buf, &buf_len) == YKPIV_OK) { - certs[n_cert] = PIV_CERT_OBJ_X509_RETIRED1 + i; - pvtkeys[n_cert] = PIV_PVTK_OBJ_RETIRED1 + i; - pubkeys[n_cert] = PIV_PUBK_OBJ_RETIRED1 + i; - n_cert++; - DBG("Found RETIRED cert (%lx)", 0x82 + i); + if (major >= 4) { + for (i = 0; i < 20; i++) { + buf_len = sizeof(buf); + if (ykpiv_fetch_object(state, YKPIV_OBJ_RETIRED1 + i, buf, &buf_len) == YKPIV_OK) { + certs[n_cert] = PIV_CERT_OBJ_X509_RETIRED1 + i; + pvtkeys[n_cert] = PIV_PVTK_OBJ_RETIRED1 + i; + pubkeys[n_cert] = PIV_PUBK_OBJ_RETIRED1 + i; + n_cert++; + DBG("Found RETIRED cert (%lx)", 0x82 + i); + } } + token_objects_num = yk4_token_objects_num; } DBG("The total number of objects for this token is %lu", (n_cert * 3) + token_objects_num); @@ -301,8 +312,16 @@ static CK_RV get_objects(ykpiv_state *state, CK_BBOOL num_only, if (*len < (n_cert * 3) + token_objects_num) return CKR_BUFFER_TOO_SMALL; - // Copy mandatory data objects - memcpy(obj, token_objects, token_objects_num * sizeof(piv_obj_id_t)); + // Copy data objects + if (major >= 4) { + // YK4: just copy all the objects + memcpy(obj, token_objects, token_objects_num * sizeof(piv_obj_id_t)); + } + else { + // NEO: remove retired keys + memcpy(obj, token_objects, 4 * sizeof(piv_obj_id_t)); + memcpy(obj + 4, token_objects + 24, (neo_token_objects_num - 4) * sizeof(piv_obj_id_t)); + } // Copy certificates if (n_cert > 0) { From 71dde91fe2d329e0319048e275efab8b3f2112b7 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 13:03:18 +0100 Subject: [PATCH 020/107] Fix some comments. --- ykcs11/obj_types.h | 48 +++++++++++++++++++++---------------------- ykcs11/yubico_token.c | 46 ++++++++++++++++++++--------------------- 2 files changed, 47 insertions(+), 47 deletions(-) diff --git a/ykcs11/obj_types.h b/ykcs11/obj_types.h index f4267ba..f861123 100644 --- a/ykcs11/obj_types.h +++ b/ykcs11/obj_types.h @@ -8,29 +8,29 @@ // TODO: this is mostly from OpenSC, how to give credit? typedef enum { PIV_DATA_OBJ_X509_PIV_AUTH = 0, // PIV authentication - PIV_DATA_OBJ_X509_CARD_AUTH, // Certificate for card authentication - PIV_DATA_OBJ_X509_DS, // Certificate for digital signature - PIV_DATA_OBJ_X509_KM, // Certificate for key management - PIV_DATA_OBJ_X509_RETIRED1, // Certificate for retired key 1 - PIV_DATA_OBJ_X509_RETIRED2, // Certificate for retired key 2 - PIV_DATA_OBJ_X509_RETIRED3, // Certificate for retired key 3 - PIV_DATA_OBJ_X509_RETIRED4, // Certificate for retired key 4 - PIV_DATA_OBJ_X509_RETIRED5, // Certificate for retired key 5 - PIV_DATA_OBJ_X509_RETIRED6, // Certificate for retired key 6 - PIV_DATA_OBJ_X509_RETIRED7, // Certificate for retired key 7 - PIV_DATA_OBJ_X509_RETIRED8, // Certificate for retired key 8 - PIV_DATA_OBJ_X509_RETIRED9, // Certificate for retired key 9 - PIV_DATA_OBJ_X509_RETIRED10, // Certificate for retired key 10 - PIV_DATA_OBJ_X509_RETIRED11, // Certificate for retired key 11 - PIV_DATA_OBJ_X509_RETIRED12, // Certificate for retired key 12 - PIV_DATA_OBJ_X509_RETIRED13, // Certificate for retired key 13 - PIV_DATA_OBJ_X509_RETIRED14, // Certificate for retired key 14 - PIV_DATA_OBJ_X509_RETIRED15, // Certificate for retired key 15 - PIV_DATA_OBJ_X509_RETIRED16, // Certificate for retired key 16 - PIV_DATA_OBJ_X509_RETIRED17, // Certificate for retired key 17 - PIV_DATA_OBJ_X509_RETIRED18, // Certificate for retired key 18 - PIV_DATA_OBJ_X509_RETIRED19, // Certificate for retired key 19 - PIV_DATA_OBJ_X509_RETIRED20, // Certificate for retired key 20 + PIV_DATA_OBJ_X509_CARD_AUTH, // Card authentication + PIV_DATA_OBJ_X509_DS, // Digital signature + PIV_DATA_OBJ_X509_KM, // Key management + PIV_DATA_OBJ_X509_RETIRED1, // Retired key 1 + PIV_DATA_OBJ_X509_RETIRED2, // Retired key 2 + PIV_DATA_OBJ_X509_RETIRED3, // Retired key 3 + PIV_DATA_OBJ_X509_RETIRED4, // Retired key 4 + PIV_DATA_OBJ_X509_RETIRED5, // Retired key 5 + PIV_DATA_OBJ_X509_RETIRED6, // Retired key 6 + PIV_DATA_OBJ_X509_RETIRED7, // Retired key 7 + PIV_DATA_OBJ_X509_RETIRED8, // Retired key 8 + PIV_DATA_OBJ_X509_RETIRED9, // Retired key 9 + PIV_DATA_OBJ_X509_RETIRED10, // Retired key 10 + PIV_DATA_OBJ_X509_RETIRED11, // Retired key 11 + PIV_DATA_OBJ_X509_RETIRED12, // Retired key 12 + PIV_DATA_OBJ_X509_RETIRED13, // Retired key 13 + PIV_DATA_OBJ_X509_RETIRED14, // Retired key 14 + PIV_DATA_OBJ_X509_RETIRED15, // Retired key 15 + PIV_DATA_OBJ_X509_RETIRED16, // Retired key 16 + PIV_DATA_OBJ_X509_RETIRED17, // Retired key 17 + PIV_DATA_OBJ_X509_RETIRED18, // Retired key 18 + PIV_DATA_OBJ_X509_RETIRED19, // Retired key 19 + PIV_DATA_OBJ_X509_RETIRED20, // Retired key 20 PIV_DATA_OBJ_CCC, // Card capability container PIV_DATA_OBJ_CHUI, // Cardholder unique id PIV_DATA_OBJ_CHF, // Cardholder fingerprints @@ -45,7 +45,7 @@ typedef enum { PIV_DATA_OBJ_PC_REF_DATA, // Pairing code reference data PIV_DATA_OBJ_LAST, - PIV_CERT_OBJ_X509_PIV_AUTH, // PIV authentication + PIV_CERT_OBJ_X509_PIV_AUTH, // Certificate for PIV authentication PIV_CERT_OBJ_X509_CARD_AUTH, // Certificate for card authentication PIV_CERT_OBJ_X509_DS, // Certificate for digital signature PIV_CERT_OBJ_X509_KM, // Certificate for key management diff --git a/ykcs11/yubico_token.c b/ykcs11/yubico_token.c index 15da5e0..b8cf730 100644 --- a/ykcs11/yubico_token.c +++ b/ykcs11/yubico_token.c @@ -66,29 +66,29 @@ static const CK_MECHANISM_INFO token_mechanism_infos[] = { // KEEP ALIGNED WITH static const piv_obj_id_t token_objects[] = { // TODO: is there a way to get this from the token? PIV_DATA_OBJ_X509_PIV_AUTH, // PIV authentication - PIV_DATA_OBJ_X509_CARD_AUTH, // Certificate for card authentication - PIV_DATA_OBJ_X509_DS, // Certificate for digital signature - PIV_DATA_OBJ_X509_KM, // Certificate for key management - PIV_DATA_OBJ_X509_RETIRED1, // Certificate for retired key 1 - PIV_DATA_OBJ_X509_RETIRED2, // Certificate for retired key 2 - PIV_DATA_OBJ_X509_RETIRED3, // Certificate for retired key 3 - PIV_DATA_OBJ_X509_RETIRED4, // Certificate for retired key 4 - PIV_DATA_OBJ_X509_RETIRED5, // Certificate for retired key 5 - PIV_DATA_OBJ_X509_RETIRED6, // Certificate for retired key 6 - PIV_DATA_OBJ_X509_RETIRED7, // Certificate for retired key 7 - PIV_DATA_OBJ_X509_RETIRED8, // Certificate for retired key 8 - PIV_DATA_OBJ_X509_RETIRED9, // Certificate for retired key 9 - PIV_DATA_OBJ_X509_RETIRED10, // Certificate for retired key 10 - PIV_DATA_OBJ_X509_RETIRED11, // Certificate for retired key 11 - PIV_DATA_OBJ_X509_RETIRED12, // Certificate for retired key 12 - PIV_DATA_OBJ_X509_RETIRED13, // Certificate for retired key 13 - PIV_DATA_OBJ_X509_RETIRED14, // Certificate for retired key 14 - PIV_DATA_OBJ_X509_RETIRED15, // Certificate for retired key 15 - PIV_DATA_OBJ_X509_RETIRED16, // Certificate for retired key 16 - PIV_DATA_OBJ_X509_RETIRED17, // Certificate for retired key 17 - PIV_DATA_OBJ_X509_RETIRED18, // Certificate for retired key 18 - PIV_DATA_OBJ_X509_RETIRED19, // Certificate for retired key 19 - PIV_DATA_OBJ_X509_RETIRED20, // Certificate for retired key 20 + PIV_DATA_OBJ_X509_CARD_AUTH, // card authentication + PIV_DATA_OBJ_X509_DS, // digital signature + PIV_DATA_OBJ_X509_KM, // key management + PIV_DATA_OBJ_X509_RETIRED1, // Retired key 1 + PIV_DATA_OBJ_X509_RETIRED2, // Retired key 2 + PIV_DATA_OBJ_X509_RETIRED3, // Retired key 3 + PIV_DATA_OBJ_X509_RETIRED4, // Retired key 4 + PIV_DATA_OBJ_X509_RETIRED5, // Retired key 5 + PIV_DATA_OBJ_X509_RETIRED6, // Retired key 6 + PIV_DATA_OBJ_X509_RETIRED7, // Retired key 7 + PIV_DATA_OBJ_X509_RETIRED8, // Retired key 8 + PIV_DATA_OBJ_X509_RETIRED9, // Retired key 9 + PIV_DATA_OBJ_X509_RETIRED10, // Retired key 10 + PIV_DATA_OBJ_X509_RETIRED11, // Retired key 11 + PIV_DATA_OBJ_X509_RETIRED12, // Retired key 12 + PIV_DATA_OBJ_X509_RETIRED13, // Retired key 13 + PIV_DATA_OBJ_X509_RETIRED14, // Retired key 14 + PIV_DATA_OBJ_X509_RETIRED15, // Retired key 15 + PIV_DATA_OBJ_X509_RETIRED16, // Retired key 16 + PIV_DATA_OBJ_X509_RETIRED17, // Retired key 17 + PIV_DATA_OBJ_X509_RETIRED18, // Retired key 18 + PIV_DATA_OBJ_X509_RETIRED19, // Retired key 19 + PIV_DATA_OBJ_X509_RETIRED20, // Retired key 20 PIV_DATA_OBJ_CCC, // Card capability container PIV_DATA_OBJ_CHUI, // Cardholder unique id PIV_DATA_OBJ_CHF, // Cardholder fingerprints From e236803bb142d862b781fc54bebf7bbe2dfbbed5 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 13:13:14 +0100 Subject: [PATCH 021/107] Whitespace fix. --- ykcs11/utils.c | 1 + 1 file changed, 1 insertion(+) diff --git a/ykcs11/utils.c b/ykcs11/utils.c index dd90a67..6402530 100644 --- a/ykcs11/utils.c +++ b/ykcs11/utils.c @@ -114,6 +114,7 @@ CK_RV create_token(ykpiv_state *state, CK_BYTE_PTR p, ykcs11_slot_t *slot) { if (ykpiv_connect(state, (char *)p) != YKPIV_OK) return CKR_FUNCTION_FAILED; + memset(t_info->model, ' ', sizeof(t_info->model)); if(token.get_token_model(state, t_info->model, sizeof(t_info->model)) != CKR_OK) return CKR_FUNCTION_FAILED; From 8bf407e33031dbd2d9866a05d32889be86b25531 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 14:06:37 +0100 Subject: [PATCH 022/107] YKCS11: report correct version. --- ykcs11/token_vendors.h | 2 +- ykcs11/utils.c | 30 +++++++++++++++++------------- ykcs11/yubico_token.c | 30 ++++++++---------------------- ykcs11/yubico_token.h | 2 +- 4 files changed, 27 insertions(+), 37 deletions(-) diff --git a/ykcs11/token_vendors.h b/ykcs11/token_vendors.h index e091124..a9be63d 100644 --- a/ykcs11/token_vendors.h +++ b/ykcs11/token_vendors.h @@ -10,7 +10,7 @@ typedef CK_RV (*get_t_label_f)(CK_UTF8CHAR_PTR, CK_ULONG); typedef CK_RV (*get_t_manufacturer_f)(CK_UTF8CHAR_PTR, CK_ULONG); typedef CK_RV (*get_t_model_f)(ykpiv_state *, CK_UTF8CHAR_PTR, CK_ULONG); typedef CK_RV (*get_t_flags_f)(CK_FLAGS_PTR); -typedef CK_RV (*get_t_version_f)(CK_UTF8CHAR_PTR, CK_ULONG, CK_VERSION_PTR); +typedef CK_RV (*get_t_version_f)(ykpiv_state *, CK_VERSION_PTR); typedef CK_RV (*get_t_serial_f)(CK_CHAR_PTR, CK_ULONG); typedef CK_RV (*get_t_mechanisms_num_f)(CK_ULONG_PTR); typedef CK_RV (*get_t_mechanism_list_f)(CK_MECHANISM_TYPE_PTR, CK_ULONG); diff --git a/ykcs11/utils.c b/ykcs11/utils.c index 6402530..c647bf9 100644 --- a/ykcs11/utils.c +++ b/ykcs11/utils.c @@ -92,7 +92,7 @@ failure: CK_RV create_token(ykpiv_state *state, CK_BYTE_PTR p, ykcs11_slot_t *slot) { - token_vendor_t token; + token_vendor_t token; CK_TOKEN_INFO_PTR t_info; slot->token = malloc(sizeof(ykcs11_token_t)); // TODO: free @@ -116,16 +116,21 @@ CK_RV create_token(ykpiv_state *state, CK_BYTE_PTR p, ykcs11_slot_t *slot) { return CKR_FUNCTION_FAILED; memset(t_info->model, ' ', sizeof(t_info->model)); - if(token.get_token_model(state, t_info->model, sizeof(t_info->model)) != CKR_OK) + if(token.get_token_model(state, t_info->model, sizeof(t_info->model)) != CKR_OK) { + ykpiv_disconnect(state); return CKR_FUNCTION_FAILED; - ykpiv_disconnect(state); + } memset(t_info->serialNumber, ' ', sizeof(t_info->serialNumber)); - if(token.get_token_serial(t_info->serialNumber, sizeof(t_info->serialNumber)) != CKR_OK) + if(token.get_token_serial(t_info->serialNumber, sizeof(t_info->serialNumber)) != CKR_OK) { + ykpiv_disconnect(state); return CKR_FUNCTION_FAILED; + } - if (token.get_token_flags(&t_info->flags) != CKR_OK) + if (token.get_token_flags(&t_info->flags) != CKR_OK) { + ykpiv_disconnect(state); return CKR_FUNCTION_FAILED; + } t_info->ulMaxSessionCount = CK_UNAVAILABLE_INFORMATION; @@ -147,20 +152,19 @@ CK_RV create_token(ykpiv_state *state, CK_BYTE_PTR p, ykcs11_slot_t *slot) { t_info->ulFreePrivateMemory = CK_UNAVAILABLE_INFORMATION; - //ykpiv_get_version(piv_state, buf, sizeof(buf)); - //if (token_vendor.get_token_version(buf, strlen(buf), &ver) != CKR_OK) // TODO: fix this - // return CKR_FUNCTION_FAILED; - - //t_info->hardwareVersion = ver; // version number of hardware // TODO: fix - - //t_info->firmwareVersion = ver; // version number of firmware // TODO: fix + // Ignore hardware version, report firmware version + if (token.get_token_version(state, &t_info->firmwareVersion) != CKR_OK) { + ykpiv_disconnect(state); + return CKR_FUNCTION_FAILED; + } memset(t_info->utcTime, ' ', sizeof(t_info->utcTime)); // No clock present, clear - // TODO: also get token objects here? (and destroy on failure) slot->token->objects = NULL; slot->token->n_objects = 0; + ykpiv_disconnect(state); + return CKR_OK; } diff --git a/ykcs11/yubico_token.c b/ykcs11/yubico_token.c index b8cf730..4e89c85 100644 --- a/ykcs11/yubico_token.c +++ b/ykcs11/yubico_token.c @@ -153,32 +153,18 @@ CK_RV YUBICO_get_token_flags(CK_FLAGS_PTR flags) { } -CK_RV YUBICO_get_token_version(CK_UTF8CHAR_PTR v_str, CK_ULONG len, CK_VERSION_PTR version) { +CK_RV YUBICO_get_token_version(ykpiv_state *state, CK_VERSION_PTR version) { - CK_VERSION v = {0, 0}; - unsigned int i = 0; + char buf[16]; - while (i < len && v_str[i] != '.') { - v.major *= 10; - v.major += v_str[i++] - '0'; - } + if (version == NULL) + return CKR_ARGUMENTS_BAD; - i++; + if (ykpiv_get_version(state, buf, sizeof(buf)) != YKPIV_OK) + return CKR_FUNCTION_FAILED; - while (i < len && v_str[i] != '.') { - v.minor *= 10; - v.minor += v_str[i++] - '0'; - } - - i++; - - while (i < len && v_str[i] != '.') { - v.minor *= 10; - v.minor += v_str[i++] - '0'; - } - - version->major = v.major; - version->minor = v.minor; + version->major = (buf[0] - '0'); + version->minor = (buf[2] - '0') * 100 + (buf[4] - '0'); return CKR_OK; } diff --git a/ykcs11/yubico_token.h b/ykcs11/yubico_token.h index e95c8e3..b725123 100644 --- a/ykcs11/yubico_token.h +++ b/ykcs11/yubico_token.h @@ -10,7 +10,7 @@ CK_RV YUBICO_get_token_manufacturer(CK_UTF8CHAR_PTR str, CK_ULONG len); CK_RV YUBICO_get_token_model(ykpiv_state *state, CK_UTF8CHAR_PTR str, CK_ULONG len); CK_RV YUBICO_get_token_flags(CK_FLAGS_PTR flags); CK_RV YUBICO_get_token_serial(CK_CHAR_PTR str, CK_ULONG len); -CK_RV YUBICO_get_token_version(CK_UTF8CHAR_PTR v_str, CK_ULONG v_str_len, CK_VERSION_PTR version); +CK_RV YUBICO_get_token_version(ykpiv_state *state, CK_VERSION_PTR version); CK_RV YUBICO_get_token_mechanisms_num(CK_ULONG_PTR num); CK_RV YUBICO_get_token_mechanism_list(CK_MECHANISM_TYPE_PTR mec, CK_ULONG num); CK_RV YUBICO_get_token_mechanism_info(CK_MECHANISM_TYPE mec, CK_MECHANISM_INFO_PTR info); From c0dfbb73774c00b8ab000411c65051bea9e44060 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 14:29:38 +0100 Subject: [PATCH 023/107] Whitelist retired key IDs. --- ykcs11/utils.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ykcs11/utils.c b/ykcs11/utils.c index c647bf9..b350b97 100644 --- a/ykcs11/utils.c +++ b/ykcs11/utils.c @@ -175,8 +175,8 @@ void destroy_token(ykcs11_slot_t *slot) { CK_BBOOL is_valid_key_id(CK_BYTE id) { - // Valid ids are 0, 1, 2, 3 - if (id > 3) + // Valid ids are [0, 23] aka [0x00, 0x17] + if (id > 23) return CK_FALSE; return CK_TRUE; From cc8cb59f8c7885e743fd88c6a89a4d9b7ab5cd4d Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 15:30:35 +0100 Subject: [PATCH 024/107] Added infrastructure for hardware tests. --- configure.ac | 22 ++++++++++++++++++---- ykcs11/tests/ykcs11_tests.c | 37 +++++++++++++++++++++++++++++++------ 2 files changed, 49 insertions(+), 10 deletions(-) diff --git a/configure.ac b/configure.ac index 408fab5..19c4936 100644 --- a/configure.ac +++ b/configure.ac @@ -52,8 +52,6 @@ PKG_PROG_PKG_CONFIG PKG_CHECK_MODULES(OPENSSL, libcrypto) -#PKG_CHECK_MODULES([LIBNSPR], [nspr], [], []) - gl_LD_VERSION_SCRIPT gl_VALGRIND_TESTS @@ -190,10 +188,24 @@ AC_ARG_ENABLE([ykcs11-debug], AS_IF([test "x$enable_ykcs11_debug" != xno], [AC_DEFINE([YKCS11_DBG], [1], [Regular debug flag]) - AC_DEFINE([YKCS11_DINOUT], [1], [Function accessed/left debug flag])], + AC_DEFINE([YKCS11_DINOUT], [1], [Function accessed/left debug flag]) + ykcs11_debug="ENABLED"], [true], [AC_DEFINE([YKCS11_DBG], [0], [Regular debug flag]) - AC_DEFINE([YKCS11_DINOUT], [0], [Function accessed/left debug flag])]) + AC_DEFINE([YKCS11_DINOUT], [0], [Function accessed/left debug flag]) + ykcs11_debug="DISABLED"]) + +AC_ARG_ENABLE([hardware-tests], + [AS_HELP_STRING([--enable-hardware-tests], + [enables tests that require a YubiKey to be plugged in])], + [enable_hardware_tests="$enableval"], + [enable_hardware_tests="no"]) + +AS_IF([test "x$enable_hardware_tests" != xno], + [AC_DEFINE([HW_TESTS], [1], [Flag for hardware tests]) + hw_tests="ENABLED"], + [true], + [hw_tests="DISABLED"]) AC_SUBST(YKPIV_VERSION_MAJOR, `echo $PACKAGE_VERSION | sed 's/\(.*\)\..*\..*/\1/g'`) AC_SUBST(YKPIV_VERSION_MINOR, `echo $PACKAGE_VERSION | sed 's/.*\.\(.*\)\..*/\1/g'`) @@ -238,4 +250,6 @@ AC_MSG_NOTICE([summary of build options: Mac PCSC LIBS: ${PCSC_MACOSX_LIBS} + YKCS11 debug: ${ykcs11_debug} + Hardware tests: ${hw_tests} ]) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 3013d5b..208c0d8 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -8,22 +8,29 @@ #define CRYPTOKI_VERSION_MAJ 2 #define CRYPTOKI_VERSION_MIN 40 +static void get_functions(CK_FUNCTION_LIST_PTR_PTR funcs) { -static void lib_info() { + if (C_GetFunctionList(funcs) != CKR_OK) { + fprintf(stderr, "Get function list failed\n"); + exit(EXIT_FAILURE); + } + +} + +static void test_lib_info() { CK_INFO info; CK_FUNCTION_LIST_PTR funcs; - if (C_GetFunctionList(&funcs) != CKR_OK) { - fprintf(stderr, "Get function list failed\n"); - exit(EXIT_FAILURE); - } + get_functions(&funcs); + if (funcs->C_GetInfo(&info) != CKR_OK) { fprintf(stderr, "GetInfo failed\n"); exit(EXIT_FAILURE); } + if (strcmp(info.manufacturerID, MANUFACTURER_ID) != 0) { fprintf(stderr, "unexpected manufacturer ID %s\n", info.manufacturerID); exit(EXIT_FAILURE); @@ -48,9 +55,27 @@ static void lib_info() { } +static void test_initalize() { + + CK_FUNCTION_LIST_PTR funcs; + + get_functions(&funcs); + + if (funcs->C_Initialize(NULL) != CKR_OK) + exit(EXIT_FAILURE); + + if (funcs->C_Finalize(NULL) != CKR_OK) + exit(EXIT_FAILURE); + +} + int main(void) { - lib_info(); + test_lib_info(); + +#ifdef HW_TESTS + test_initalize(); +#endif return EXIT_SUCCESS; From 56415dbc2d52f02eec60daa2804224bc4dac6afb Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 16:50:27 +0100 Subject: [PATCH 025/107] Whitespace fix. --- ykcs11/tests/ykcs11_tests.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 208c0d8..d32d932 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -24,13 +24,11 @@ static void test_lib_info() { get_functions(&funcs); - if (funcs->C_GetInfo(&info) != CKR_OK) { fprintf(stderr, "GetInfo failed\n"); exit(EXIT_FAILURE); } - if (strcmp(info.manufacturerID, MANUFACTURER_ID) != 0) { fprintf(stderr, "unexpected manufacturer ID %s\n", info.manufacturerID); exit(EXIT_FAILURE); From 0f1b05494a9269b3323a88741d1f2e2c41666866 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 16:52:31 +0100 Subject: [PATCH 026/107] Add/fix some prints for tests. --- ykcs11/tests/ykcs11_tests.c | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index d32d932..2db0a36 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -30,24 +30,24 @@ static void test_lib_info() { } if (strcmp(info.manufacturerID, MANUFACTURER_ID) != 0) { - fprintf(stderr, "unexpected manufacturer ID %s\n", info.manufacturerID); + fprintf(stderr, "Unexpected manufacturer ID %s\n", info.manufacturerID); exit(EXIT_FAILURE); } if (info.cryptokiVersion.major != CRYPTOKI_VERSION_MAJ || info.cryptokiVersion.minor != CRYPTOKI_VERSION_MIN ) { - fprintf(stderr, "unexpected Cryptoki version %d.%d\n", info.cryptokiVersion.major, info.cryptokiVersion.minor); + fprintf(stderr, "Unexpected Cryptoki version %d.%d\n", info.cryptokiVersion.major, info.cryptokiVersion.minor); exit(EXIT_FAILURE); } if (info.libraryVersion.major != YKCS11_VERSION_MAJOR || info.libraryVersion.minor != ((YKCS11_VERSION_MINOR * 100) + YKCS11_VERSION_PATCH )) { - fprintf(stderr, "unexpected YKCS11 version %d.%d\n", info.libraryVersion.major, info.libraryVersion.minor); + fprintf(stderr, "Unexpected YKCS11 version %d.%d\n", info.libraryVersion.major, info.libraryVersion.minor); exit(EXIT_FAILURE); } if (strcmp(info.libraryDescription, YKCS11_DESCRIPTION) != 0) { - fprintf(stderr, "unexpected description %s\n", info.libraryDescription); + fprintf(stderr, "Unexpected description %s\n", info.libraryDescription); exit(EXIT_FAILURE); } @@ -59,11 +59,15 @@ static void test_initalize() { get_functions(&funcs); - if (funcs->C_Initialize(NULL) != CKR_OK) + if (funcs->C_Initialize(NULL) != CKR_OK) { + fprintf(stderr, "Unable to initialize YKCS11\n"); exit(EXIT_FAILURE); + } - if (funcs->C_Finalize(NULL) != CKR_OK) + if (funcs->C_Finalize(NULL) != CKR_OK) { + fprintf(stderr, "Unable to finalize YKCS11\n"); exit(EXIT_FAILURE); + } } From 262f5f4771977719eb9d2eda3a0ac39bc43e668a Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 16:56:17 +0100 Subject: [PATCH 027/107] Make ykcs11 functions pointer global to all tests. --- ykcs11/tests/ykcs11_tests.c | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 2db0a36..f644b7c 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -2,12 +2,15 @@ #include #include +#include #define MANUFACTURER_ID "Yubico (www.yubico.com)" #define YKCS11_DESCRIPTION "PKCS#11 PIV Library (SP-800-73)" #define CRYPTOKI_VERSION_MAJ 2 #define CRYPTOKI_VERSION_MIN 40 +CK_FUNCTION_LIST_PTR funcs; + static void get_functions(CK_FUNCTION_LIST_PTR_PTR funcs) { if (C_GetFunctionList(funcs) != CKR_OK) { @@ -20,9 +23,6 @@ static void get_functions(CK_FUNCTION_LIST_PTR_PTR funcs) { static void test_lib_info() { CK_INFO info; - CK_FUNCTION_LIST_PTR funcs; - - get_functions(&funcs); if (funcs->C_GetInfo(&info) != CKR_OK) { fprintf(stderr, "GetInfo failed\n"); @@ -55,10 +55,6 @@ static void test_lib_info() { static void test_initalize() { - CK_FUNCTION_LIST_PTR funcs; - - get_functions(&funcs); - if (funcs->C_Initialize(NULL) != CKR_OK) { fprintf(stderr, "Unable to initialize YKCS11\n"); exit(EXIT_FAILURE); @@ -71,12 +67,25 @@ static void test_initalize() { } +static void test_token_info() { + + CK_TOKEN_INFO info; + + assert(funcs->C_GetTokenInfo(0, &info) == CKR_OK); + /*fprintf + }*/ + +} + int main(void) { + get_functions(&funcs); + test_lib_info(); #ifdef HW_TESTS test_initalize(); + test_token_info(); #endif return EXIT_SUCCESS; From 523ab1d3650a08cad0189bf85e0898b72c5bd399 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Tue, 24 Nov 2015 18:56:36 +0100 Subject: [PATCH 028/107] More YKCS11 tests. --- ykcs11/tests/ykcs11_tests.c | 102 ++++++++++++++++++++++-------------- 1 file changed, 62 insertions(+), 40 deletions(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index f644b7c..0bd4408 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -2,15 +2,23 @@ #include #include -#include - -#define MANUFACTURER_ID "Yubico (www.yubico.com)" -#define YKCS11_DESCRIPTION "PKCS#11 PIV Library (SP-800-73)" -#define CRYPTOKI_VERSION_MAJ 2 -#define CRYPTOKI_VERSION_MIN 40 CK_FUNCTION_LIST_PTR funcs; +#define asrt(c, e, m) _asrt(__LINE__, c, e, m); + +static void _asrt(int line, CK_ULONG check, CK_ULONG expected, CK_CHAR_PTR msg) { + + if (check == expected) + return; + + fprintf(stderr, "<%s>:%d check failed with value %lu (0x%lx), expected %lu (0x%lx)\n", + msg, line, check, check, expected, expected); + + exit(EXIT_FAILURE); + +} + static void get_functions(CK_FUNCTION_LIST_PTR_PTR funcs) { if (C_GetFunctionList(funcs) != CKR_OK) { @@ -22,58 +30,72 @@ static void get_functions(CK_FUNCTION_LIST_PTR_PTR funcs) { static void test_lib_info() { + const CK_CHAR_PTR MANUFACTURER_ID = "Yubico (www.yubico.com)"; + const CK_CHAR_PTR YKCS11_DESCRIPTION = "PKCS#11 PIV Library (SP-800-73)"; + const CK_ULONG CRYPTOKI_VERSION_MAJ = 2; + const CK_ULONG CRYPTOKI_VERSION_MIN = 40; + + CK_INFO info; - if (funcs->C_GetInfo(&info) != CKR_OK) { - fprintf(stderr, "GetInfo failed\n"); - exit(EXIT_FAILURE); - } + asrt(funcs->C_GetInfo(&info), CKR_OK, "GET_INFO"); - if (strcmp(info.manufacturerID, MANUFACTURER_ID) != 0) { - fprintf(stderr, "Unexpected manufacturer ID %s\n", info.manufacturerID); - exit(EXIT_FAILURE); - } + asrt(strcmp(info.manufacturerID, MANUFACTURER_ID), 0, "MANUFACTURER"); - if (info.cryptokiVersion.major != CRYPTOKI_VERSION_MAJ || - info.cryptokiVersion.minor != CRYPTOKI_VERSION_MIN ) { - fprintf(stderr, "Unexpected Cryptoki version %d.%d\n", info.cryptokiVersion.major, info.cryptokiVersion.minor); - exit(EXIT_FAILURE); - } + asrt(info.cryptokiVersion.major, CRYPTOKI_VERSION_MAJ, "CK_MAJ"); + asrt(info.cryptokiVersion.minor, CRYPTOKI_VERSION_MIN, "CK_MIN"); - if (info.libraryVersion.major != YKCS11_VERSION_MAJOR || - info.libraryVersion.minor != ((YKCS11_VERSION_MINOR * 100) + YKCS11_VERSION_PATCH )) { - fprintf(stderr, "Unexpected YKCS11 version %d.%d\n", info.libraryVersion.major, info.libraryVersion.minor); - exit(EXIT_FAILURE); - } - - if (strcmp(info.libraryDescription, YKCS11_DESCRIPTION) != 0) { - fprintf(stderr, "Unexpected description %s\n", info.libraryDescription); - exit(EXIT_FAILURE); - } + asrt(info.libraryVersion.major, YKCS11_VERSION_MAJOR, "LIB_MAJ"); + asrt(info.libraryVersion.minor, ((YKCS11_VERSION_MINOR * 100) + YKCS11_VERSION_PATCH ), "LIB_MIN"); + asrt(strcmp(info.libraryDescription, YKCS11_DESCRIPTION), 0, "LIB_DESC"); } static void test_initalize() { - if (funcs->C_Initialize(NULL) != CKR_OK) { - fprintf(stderr, "Unable to initialize YKCS11\n"); - exit(EXIT_FAILURE); - } + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); - if (funcs->C_Finalize(NULL) != CKR_OK) { - fprintf(stderr, "Unable to finalize YKCS11\n"); - exit(EXIT_FAILURE); - } + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); } static void test_token_info() { + const CK_CHAR_PTR TOKEN_LABEL = "YubiKey PIV"; + const CK_CHAR_PTR TOKEN_MODEL = "YubiKey "; // Skip last 3 characters (version dependent) + const CK_CHAR_PTR TOKEN_SERIAL = "1234"; + const CK_FLAGS TOKEN_FLAGS = CKF_RNG | CKF_LOGIN_REQUIRED | CKF_USER_PIN_INITIALIZED | CKF_TOKEN_INITIALIZED; + const CK_VERSION HW = {0, 0}; + const CK_CHAR_PTR TOKEN_TIME = " "; CK_TOKEN_INFO info; - assert(funcs->C_GetTokenInfo(0, &info) == CKR_OK); - /*fprintf - }*/ + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); + + asrt(funcs->C_GetTokenInfo(0, &info), CKR_OK, "GetTokeninfo"); + asrt(strncmp(info.label, TOKEN_LABEL, strlen(TOKEN_LABEL)), 0, "TOKEN_LABEL"); + // Skip manufacturer id (not used) + asrt(strncmp(info.model, TOKEN_MODEL, strlen(TOKEN_MODEL)), 0, "TOKEN_MODEL"); + asrt(strncmp(info.serialNumber, TOKEN_SERIAL, strlen(TOKEN_SERIAL)), 0, "SERIAL_NUMBER"); + asrt(info.flags, TOKEN_FLAGS, "TOKEN_FLAGS"); + asrt(info.ulMaxSessionCount, CK_UNAVAILABLE_INFORMATION, "MAX_SESSION_COUNT"); + asrt(info.ulSessionCount, CK_UNAVAILABLE_INFORMATION, "SESSION_COUNT"); + asrt(info.ulMaxRwSessionCount, CK_UNAVAILABLE_INFORMATION, "MAX_RW_SESSION_COUNT"); + asrt(info.ulRwSessionCount, CK_UNAVAILABLE_INFORMATION, "RW_SESSION_COUNT"); + asrt(info.ulMaxPinLen, 8, "MAX_PIN_LEN"); + asrt(info.ulMinPinLen, 6, "MIN_PIN_LEN"); + asrt(info.ulTotalPublicMemory, CK_UNAVAILABLE_INFORMATION, "TOTAL_PUB_MEM"); + asrt(info.ulFreePublicMemory, CK_UNAVAILABLE_INFORMATION, "FREE_PUB_MEM"); + asrt(info.ulTotalPrivateMemory, CK_UNAVAILABLE_INFORMATION, "TOTAL_PVT_MEM"); + asrt(info.ulFreePrivateMemory, CK_UNAVAILABLE_INFORMATION, "FREE_PVT_MEM"); + asrt(info.hardwareVersion.major, HW.major, "HW_MAJ"); + asrt(info.hardwareVersion.minor, HW.minor, "HW_MIN"); + + if (info.firmwareVersion.major != 4 && info.firmwareVersion.major != 0) + asrt(info.firmwareVersion.major, 4, "FW_MAJ"); + + asrt(strcmp(info.utcTime, TOKEN_TIME), 0, "TOKEN_TIME"); + + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); } From 60a3186d1daebd22d8fd798c78e4172ff6c9bcce Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Wed, 25 Nov 2015 11:08:32 +0100 Subject: [PATCH 029/107] add short doc on android code signing fixes #20 --- doc/Android_code_signing.adoc | 59 +++++++++++++++++++++++++++++++++++ 1 file changed, 59 insertions(+) create mode 100644 doc/Android_code_signing.adoc diff --git a/doc/Android_code_signing.adoc b/doc/Android_code_signing.adoc new file mode 100644 index 0000000..a5774e3 --- /dev/null +++ b/doc/Android_code_signing.adoc @@ -0,0 +1,59 @@ +Load and use Android code signing certificate +--------------------------------------------- + +This is a step-by-step guide on how to load and use an android code signing +key and certificate. + +Prerequisites +------------- + +* a YubiKey with the PIV application +* the yubico-piv-tool software +* the OpenSC software +* jarsigner and keytool from the JDK (openjdk 8 used here) + +Steps +----- + +1. Import the key and cert, do a or b +a. Import the key and cert (PEM format) in slot 9a: + + $ yubico-piv-tool -s 9a -a import-key -i key.pem + $ yubico-piv-tool -s 9a -a import-certificate -i cert.pem + +b. Import the key and cert (PKCS12 format) in slot 9a: + + $ yubico-piv-tool -s 9a -a import-key -a import-cert -i key.p12 -K PKCS12 + +2. Create a java pkcs11 configuration file: + + cat > /tmp/pkcs11_java.cfg + name = OpenSC-PKCS11 + description = SunPKCS11 via OpenSC + library = /usr/lib/x86_64-linux-gnu/opensc-pkcs11.so + slotListIndex = 1 + +3. Check that keytool can see the key: + + $ keytool -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg -keystore NONE -storetype PKCS11 -list + Enter keystore password: + + Keystore type: PKCS11 + Keystore provider: SunPKCS11-OpenSC-PKCS11 + + Your keystore contains 1 entry + + Certificate for PIV Authentication, PrivateKeyEntry, + Certificate fingerprint (SHA1): 26:D7:CB:71:6D:42:3C:AB:58:69:E0:9D:F0:16:DF:84:7E:1C:5A:9A ++ +Password here is the PIN of the key (default 123456). + +4. Sign the apk with jarsigner: + + $ jarsigner -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg -keystore NONE -storetype PKCS11 app.apk "Certificate for PIV Authentication" + Enter Passphrase for keystore: + jar signed. + +5. Verify the signature with jarsigner: + + $ jarsigner -verify app.apk From 5a75c0383ed15eee7a555b2ea1d2415b67726b25 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Wed, 25 Nov 2015 11:11:03 +0100 Subject: [PATCH 030/107] shorten very long lines --- doc/Android_code_signing.adoc | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/doc/Android_code_signing.adoc b/doc/Android_code_signing.adoc index a5774e3..74648ed 100644 --- a/doc/Android_code_signing.adoc +++ b/doc/Android_code_signing.adoc @@ -35,7 +35,8 @@ b. Import the key and cert (PKCS12 format) in slot 9a: 3. Check that keytool can see the key: - $ keytool -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg -keystore NONE -storetype PKCS11 -list + $ keytool -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg \ + -keystore NONE -storetype PKCS11 -list Enter keystore password: Keystore type: PKCS11 @@ -50,7 +51,8 @@ Password here is the PIN of the key (default 123456). 4. Sign the apk with jarsigner: - $ jarsigner -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg -keystore NONE -storetype PKCS11 app.apk "Certificate for PIV Authentication" + $ jarsigner -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg \ + -keystore NONE -storetype PKCS11 app.apk "Certificate for PIV Authentication" Enter Passphrase for keystore: jar signed. From 7f826f3aabb155c2d993836d7b62e2840ab46058 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Wed, 25 Nov 2015 11:13:07 +0100 Subject: [PATCH 031/107] bind together what should be one block --- doc/Android_code_signing.adoc | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/doc/Android_code_signing.adoc b/doc/Android_code_signing.adoc index 74648ed..d5f8b75 100644 --- a/doc/Android_code_signing.adoc +++ b/doc/Android_code_signing.adoc @@ -38,12 +38,12 @@ b. Import the key and cert (PKCS12 format) in slot 9a: $ keytool -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg \ -keystore NONE -storetype PKCS11 -list Enter keystore password: - ++ Keystore type: PKCS11 Keystore provider: SunPKCS11-OpenSC-PKCS11 - ++ Your keystore contains 1 entry - ++ Certificate for PIV Authentication, PrivateKeyEntry, Certificate fingerprint (SHA1): 26:D7:CB:71:6D:42:3C:AB:58:69:E0:9D:F0:16:DF:84:7E:1C:5A:9A + From e4a2b6c3deef55bafda10cdb24c723f93ed4d7c5 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Wed, 25 Nov 2015 11:13:43 +0100 Subject: [PATCH 032/107] wording on list points --- doc/Android_code_signing.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/Android_code_signing.adoc b/doc/Android_code_signing.adoc index d5f8b75..067cf29 100644 --- a/doc/Android_code_signing.adoc +++ b/doc/Android_code_signing.adoc @@ -15,7 +15,7 @@ Prerequisites Steps ----- -1. Import the key and cert, do a or b +1. Import the key and cert, do one of the below: a. Import the key and cert (PEM format) in slot 9a: $ yubico-piv-tool -s 9a -a import-key -i key.pem From 856cf03009b08d2f6e8d665ce37c7483d2f7811f Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Wed, 25 Nov 2015 12:52:52 +0100 Subject: [PATCH 033/107] formatting of blocks --- doc/Android_code_signing.adoc | 30 +++++++++++++++++++++--------- 1 file changed, 21 insertions(+), 9 deletions(-) diff --git a/doc/Android_code_signing.adoc b/doc/Android_code_signing.adoc index 067cf29..80fefbb 100644 --- a/doc/Android_code_signing.adoc +++ b/doc/Android_code_signing.adoc @@ -17,45 +17,57 @@ Steps 1. Import the key and cert, do one of the below: a. Import the key and cert (PEM format) in slot 9a: - ++ +---- $ yubico-piv-tool -s 9a -a import-key -i key.pem $ yubico-piv-tool -s 9a -a import-certificate -i cert.pem +---- b. Import the key and cert (PKCS12 format) in slot 9a: - ++ +---- $ yubico-piv-tool -s 9a -a import-key -a import-cert -i key.p12 -K PKCS12 +---- 2. Create a java pkcs11 configuration file: - ++ +---- cat > /tmp/pkcs11_java.cfg name = OpenSC-PKCS11 description = SunPKCS11 via OpenSC library = /usr/lib/x86_64-linux-gnu/opensc-pkcs11.so slotListIndex = 1 +---- 3. Check that keytool can see the key: - ++ +---- $ keytool -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg \ -keystore NONE -storetype PKCS11 -list Enter keystore password: -+ + Keystore type: PKCS11 Keystore provider: SunPKCS11-OpenSC-PKCS11 -+ + Your keystore contains 1 entry -+ + Certificate for PIV Authentication, PrivateKeyEntry, Certificate fingerprint (SHA1): 26:D7:CB:71:6D:42:3C:AB:58:69:E0:9D:F0:16:DF:84:7E:1C:5A:9A +---- + Password here is the PIN of the key (default 123456). 4. Sign the apk with jarsigner: - ++ +---- $ jarsigner -providerClass sun.security.pkcs11.SunPKCS11 -providerArg /tmp/pkcs11_java.cfg \ -keystore NONE -storetype PKCS11 app.apk "Certificate for PIV Authentication" Enter Passphrase for keystore: jar signed. +---- 5. Verify the signature with jarsigner: - ++ +---- $ jarsigner -verify app.apk +---- From 6f8541b438d6bea881aa9254825b7b89bc44b414 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Wed, 25 Nov 2015 12:57:21 +0100 Subject: [PATCH 034/107] openjdk -> OpenJDK --- doc/Android_code_signing.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/Android_code_signing.adoc b/doc/Android_code_signing.adoc index 80fefbb..1826b67 100644 --- a/doc/Android_code_signing.adoc +++ b/doc/Android_code_signing.adoc @@ -10,7 +10,7 @@ Prerequisites * a YubiKey with the PIV application * the yubico-piv-tool software * the OpenSC software -* jarsigner and keytool from the JDK (openjdk 8 used here) +* jarsigner and keytool from the JDK (OpenJDK 8 used here) Steps ----- From 8566e50f0c872e651b1431df7c4232989b0e8281 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 10:59:24 +0100 Subject: [PATCH 035/107] Typo --- ykcs11/ykcs11.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index 37c7fbd..7f03027 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -479,7 +479,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_OpenSession)( } if ((flags & CKF_SERIAL_SESSION) == 0) { - DBG("Open session called without CKF_SERIAL_SESSION set"); // Reuired by spes + DBG("Open session called without CKF_SERIAL_SESSION set"); // Required by specs return CKR_SESSION_PARALLEL_NOT_SUPPORTED; } From a0d4e9b887a6aa29911abc885091b758bee4bd1a Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 11:09:03 +0100 Subject: [PATCH 036/107] YKCS11: test mechanisms. --- ykcs11/tests/ykcs11_tests.c | 71 +++++++++++++++++++++++++++++++++++++ 1 file changed, 71 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 0bd4408..7cee7b9 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -99,6 +99,76 @@ static void test_token_info() { } +static void test_mechanism_list_and_info() { + + CK_MECHANISM_TYPE_PTR mechs; + CK_ULONG n_mechs; + CK_MECHANISM_INFO info; + CK_ULONG i; + + static const CK_MECHANISM_TYPE token_mechanisms[] = { + CKM_RSA_PKCS_KEY_PAIR_GEN, + CKM_RSA_PKCS, + CKM_RSA_PKCS_PSS, + CKM_RSA_X_509, + CKM_SHA1_RSA_PKCS, + CKM_SHA256_RSA_PKCS, + CKM_SHA384_RSA_PKCS, + CKM_SHA512_RSA_PKCS, + CKM_SHA1_RSA_PKCS_PSS, + CKM_SHA256_RSA_PKCS_PSS, + CKM_SHA384_RSA_PKCS_PSS, + CKM_SHA512_RSA_PKCS_PSS, + CKM_EC_KEY_PAIR_GEN, + CKM_ECDSA, + CKM_ECDSA_SHA1, + CKM_ECDSA_SHA256, + CKM_SHA_1, + CKM_SHA256, + CKM_SHA384, + CKM_SHA512 + }; + + static const CK_MECHANISM_INFO token_mechanism_infos[] = { // KEEP ALIGNED WITH token_mechanisms + {1024, 2048, CKF_HW | CKF_GENERATE_KEY_PAIR}, + {1024, 2048, CKF_HW | CKF_DECRYPT | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_DECRYPT | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {1024, 2048, CKF_HW | CKF_SIGN}, + {256, 384, CKF_HW | CKF_GENERATE_KEY_PAIR}, + {256, 384, CKF_HW | CKF_SIGN}, + {256, 384, CKF_HW | CKF_SIGN}, + {256, 384, CKF_HW | CKF_SIGN}, + {0, 0, CKF_DIGEST}, + {0, 0, CKF_DIGEST}, + {0, 0, CKF_DIGEST}, + {0, 0, CKF_DIGEST} +}; + + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); + + asrt(funcs->C_GetMechanismList(0, NULL, &n_mechs), CKR_OK, "GetMechanismList"); + + mechs = malloc(n_mechs * sizeof(CK_MECHANISM_TYPE)); + asrt(funcs->C_GetMechanismList(0, mechs, &n_mechs), CKR_OK, "GetMechanismList"); + + asrt(memcmp(token_mechanisms, mechs, sizeof(token_mechanisms)), 0, "CHECK MECHS"); + + for (i = 0; i < n_mechs; i++) { + asrt(funcs->C_GetMechanismInfo(0, mechs[i], &info), CKR_OK, "GET MECH INFO"); + asrt(memcmp(token_mechanism_infos + i, &info, sizeof(CK_MECHANISM_INFO)), 0, "CHECK MECH INFO"); + } + + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); +} + int main(void) { get_functions(&funcs); @@ -108,6 +178,7 @@ int main(void) { #ifdef HW_TESTS test_initalize(); test_token_info(); + test_mechanism_list_and_info(); #endif return EXIT_SUCCESS; From 67646399823d7c68ed0f628611f49d3c6bfcd80b Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 11:10:19 +0100 Subject: [PATCH 037/107] YKCS11: test session. --- ykcs11/tests/ykcs11_tests.c | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 7cee7b9..6aaafe0 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -169,6 +169,25 @@ static void test_mechanism_list_and_info() { asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); } +static void test_session() { + + CK_SESSION_HANDLE session; + + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); + + asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); + asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); + + asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession2"); + asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); + + asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession3"); + asrt(funcs->C_CloseAllSessions(0), CKR_OK, "CloseAllSessions"); + + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); + +} + int main(void) { get_functions(&funcs); @@ -179,6 +198,7 @@ int main(void) { test_initalize(); test_token_info(); test_mechanism_list_and_info(); + test_session(); #endif return EXIT_SUCCESS; From a5387c12e7894ece011ebdd864c2a471d14e2355 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 15:44:11 +0100 Subject: [PATCH 038/107] YKCS11: Add more to session tests. --- ykcs11/tests/ykcs11_tests.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 6aaafe0..a08ac72 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -172,6 +172,7 @@ static void test_mechanism_list_and_info() { static void test_session() { CK_SESSION_HANDLE session; + CK_SESSION_INFO info; asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); @@ -179,6 +180,10 @@ static void test_session() { asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession2"); + asrt(funcs->C_GetSessionInfo(session, &info), CKR_OK, "GetSessionInfo"); + asrt(info.state, CKS_RW_PUBLIC_SESSION, "CHECK STATE"); + asrt(info.flags, CKF_SERIAL_SESSION | CKF_RW_SESSION, "CHECK FLAGS"); + asrt(info.ulDeviceError, 0, "CHECK DEVICE ERROR"); asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession3"); From ab92c9007196f28a6aa5a323625750a78dbe0bfb Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 15:46:10 +0100 Subject: [PATCH 039/107] Report disabled hw test in the logfile of the test. --- ykcs11/tests/ykcs11_tests.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index a08ac72..331a7a8 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -204,6 +204,8 @@ int main(void) { test_token_info(); test_mechanism_list_and_info(); test_session(); +#else + fprintf(stderr, "HARDWARE TESTS DISABLED!, skipping...\n"); #endif return EXIT_SUCCESS; From ef813171836d13d5fc626cb7729024e2eb24cbf4 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 16:10:41 +0100 Subject: [PATCH 040/107] YKCS11: Test logins. --- ykcs11/tests/ykcs11_tests.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 331a7a8..d052c80 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -193,6 +193,27 @@ static void test_session() { } +static void test_login() { + + CK_SESSION_HANDLE session; + CK_SESSION_INFO info; + + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); + + asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); + + asrt(funcs->C_Login(session, CKU_USER, "123456", 8), CKR_OK, "Login USER"); + asrt(funcs->C_Logout(session), CKR_OK, "Loout USER"); + + asrt(funcs->C_Login(session, CKU_SO, "010203040506070801020304050607080102030405060708", 48), CKR_OK, "Login SO"); + asrt(funcs->C_Logout(session), CKR_OK, "Logout SO"); + + asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); + + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); + +} + int main(void) { get_functions(&funcs); @@ -204,6 +225,7 @@ int main(void) { test_token_info(); test_mechanism_list_and_info(); test_session(); + test_login(); #else fprintf(stderr, "HARDWARE TESTS DISABLED!, skipping...\n"); #endif From 59faa09c7a76e7585a8b04d9c016e9562cc9f95a Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Wed, 25 Nov 2015 17:43:21 +0100 Subject: [PATCH 041/107] YKCS11: started test on key import and signatures. --- ykcs11/tests/ykcs11_tests.c | 84 ++++++++++++++++++++++++++++++++++++- 1 file changed, 83 insertions(+), 1 deletion(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index d052c80..990300b 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -3,6 +3,10 @@ #include +#include +#include +#include + CK_FUNCTION_LIST_PTR funcs; #define asrt(c, e, m) _asrt(__LINE__, c, e, m); @@ -203,7 +207,7 @@ static void test_login() { asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); asrt(funcs->C_Login(session, CKU_USER, "123456", 8), CKR_OK, "Login USER"); - asrt(funcs->C_Logout(session), CKR_OK, "Loout USER"); + asrt(funcs->C_Logout(session), CKR_OK, "Logout USER"); asrt(funcs->C_Login(session, CKU_SO, "010203040506070801020304050607080102030405060708", 48), CKR_OK, "Login SO"); asrt(funcs->C_Logout(session), CKR_OK, "Logout SO"); @@ -214,6 +218,83 @@ static void test_login() { } +// Import a newly generated P256 pvt key and a certificate +// to every slot and use the key to sign some data +static void test_import_and_sign_100() { + + EC_KEY *k1; + EC_KEY *k2; + EC_POINT *ecp1; + EC_POINT *ecp2; + BIGNUM *bn1; + BIGNUM *bn2; + char pk1[32]; + char pk2[32]; + X509 *cert1; + X509 *cert2; + CK_BYTE i; + CK_BYTE some_data[] = "0123456789012345678901"; + + + CK_ULONG class = CKO_PRIVATE_KEY; + CK_ULONG kt = CKK_ECDSA; + CK_BYTE id = 0; + CK_BYTE params[] = {0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x03, 0x01, 0x07}; + CK_BYTE value[32]; + + CK_ATTRIBUTE publicKeyTemplate[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &kt, sizeof(kt)}, + {CKA_ID, &id, sizeof(id)}, + {CKA_EC_PARAMS, ¶ms, sizeof(params)}, + {CKA_VALUE, value, sizeof(value)} + }; + + CK_OBJECT_HANDLE obj; + + CK_SESSION_HANDLE session; + + k1 = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1); + k2 = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1); + + if (k1 == NULL || k2 == NULL) + exit(EXIT_FAILURE); + + cert1 = X509_new(); + + if (cert1 == NULL) + exit(EXIT_FAILURE); + + asrt(EC_KEY_generate_key(k1), 1, "GENERATE K1"); + asrt(EC_KEY_generate_key(k2), 1, "GENERATE K2"); + + bn1 = EC_KEY_get0_private_key(k1); + bn2 = EC_KEY_get0_private_key(k2); + + asrt(BN_bn2bin(bn1, pk1), 32, "EXTRACT PK1"); + asrt(BN_bn2bin(bn2, pk2), 32, "EXTRACT PK2"); + + /*ecp1 = EC_KEY_get0_public_key(k1); + ecp2 = EC_KEY_get0_public_key(k2); + + if (ecp1 == NULL || ecp2 == NULL) + exit(EXIT_FAILURE);*/ + + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); + asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); + asrt(funcs->C_Login(session, CKU_SO, "010203040506070801020304050607080102030405060708", 48), CKR_OK, "Login SO"); + + asrt(funcs->C_CreateObject(session, publicKeyTemplate, 5, &obj), CKR_OK, "IMPORT KEY"); + + asrt(funcs->C_Logout(session), CKR_OK, "Logout SO"); + asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); + + //for (i = 0; i < 100f; i++) { + + //} +} + int main(void) { get_functions(&funcs); @@ -226,6 +307,7 @@ int main(void) { test_mechanism_list_and_info(); test_session(); test_login(); + test_import_and_sign_100(); #else fprintf(stderr, "HARDWARE TESTS DISABLED!, skipping...\n"); #endif From 8b0ed073d332fa139e0994ff5b414c928c4c0a9c Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 10:06:26 +0100 Subject: [PATCH 042/107] YKCS11: Return the object handler after importing certs/keys. --- ykcs11/ykcs11.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index 7f03027..4013cfd 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -1038,6 +1038,9 @@ CK_DEFINE_FUNCTION(CK_RV, C_CreateObject)( return rv; } } + + *phObject = PIV_PVTK_OBJ_PIV_AUTH + id; + break; default: From 721ad03e35082ccc488805a76aeac2aec75512c3 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 10:10:14 +0100 Subject: [PATCH 043/107] Fix parameter check in SignInit. --- ykcs11/ykcs11.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index 4013cfd..d7234e2 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -1653,8 +1653,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_SignInit)( return CKR_OPERATION_ACTIVE; } - if (pMechanism == NULL_PTR || - hKey == NULL_PTR) + if (pMechanism == NULL_PTR) return CKR_ARGUMENTS_BAD; DBG("Trying to sign some data with mechanism %lu and key %lu", pMechanism->mechanism, hKey); From 968348a4c209f2dd638cf61b1cfbef96561f883c Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 13:41:56 +0100 Subject: [PATCH 044/107] YKCS11: use memcpy. --- ykcs11/objects.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index 6dc080b..c471f73 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -404,7 +404,7 @@ CK_RV get_doa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_OBJECT_ID: // TODO: how about just storing the OID in DER ? DBG("OID"); - strcpy((char *)tmp, data_objects[piv_objects[obj].sub_id].oid); + memcpy((char *)tmp, data_objects[piv_objects[obj].sub_id].oid, sizeof(tmp)); asn1_encode_oid(tmp, tmp, &len); data = tmp; break; From 0a93217dbc5fe2bae1d37fef0f34b94053ce080e Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 14:01:56 +0100 Subject: [PATCH 045/107] Minor fix. --- tool/yubico-piv-tool.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index fb521b9..01ad5d5 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -71,7 +71,7 @@ static void print_version(ykpiv_state *state, const char *output_file_name) { char version[7]; FILE *output_file = open_file(output_file_name, OUTPUT); if(!output_file) { - fprintf(stderr, "Failed opening output_file_name\n"); + return; } if(ykpiv_get_version(state, version, sizeof(version)) == YKPIV_OK) { @@ -1101,6 +1101,9 @@ static bool sign_file(ykpiv_state *state, const char *input, const char *output, output_file = open_file(output, OUTPUT); if(!output_file) { + if(input_file && input_file != stdin) { + fclose(input_file); + } return false; } From 669997b2dc6f041a026784b21506b78c31f9b66c Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 14:06:10 +0100 Subject: [PATCH 046/107] Minor fix. --- ykcs11/utils.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ykcs11/utils.c b/ykcs11/utils.c index b350b97..6cc729b 100644 --- a/ykcs11/utils.c +++ b/ykcs11/utils.c @@ -49,7 +49,7 @@ CK_RV parse_readers(ykpiv_state *state, const CK_BYTE_PTR readers, const CK_ULON memset(slots[*n_slots].info.slotDescription, ' ', sizeof(slots[*n_slots].info.slotDescription)); s = slots[*n_slots].info.slotDescription; l = sizeof(slots[*n_slots].info.slotDescription); - strncpy((char *)s, (char*)p, l); + memcpy((char *)s, (char*)p, l); memset(slots[*n_slots].info.manufacturerID, ' ', sizeof(slots[*n_slots].info.manufacturerID)); s = slots[*n_slots].info.manufacturerID; From 4e8f818e82aa80e59903aef7c24e7fa739f818ad Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 14:21:18 +0100 Subject: [PATCH 047/107] YKCS11: add more tests. --- ykcs11/tests/ykcs11_tests.c | 194 ++++++++++++++++++++++++++++-------- 1 file changed, 151 insertions(+), 43 deletions(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 990300b..0f95887 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -6,6 +6,15 @@ #include #include #include +#include + +void dump_hex(const unsigned char *buf, unsigned int len, FILE *output, int space) { + unsigned int i; + for (i = 0; i < len; i++) { + fprintf(output, "%02x%s", buf[i], space == 1 ? " " : ""); + } + fprintf(output, "\n"); +} CK_FUNCTION_LIST_PTR funcs; @@ -206,7 +215,7 @@ static void test_login() { asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); - asrt(funcs->C_Login(session, CKU_USER, "123456", 8), CKR_OK, "Login USER"); + asrt(funcs->C_Login(session, CKU_USER, "123456", 6), CKR_OK, "Login USER"); asrt(funcs->C_Logout(session), CKR_OK, "Logout USER"); asrt(funcs->C_Login(session, CKU_SO, "010203040506070801020304050607080102030405060708", 48), CKR_OK, "Login SO"); @@ -220,79 +229,178 @@ static void test_login() { // Import a newly generated P256 pvt key and a certificate // to every slot and use the key to sign some data -static void test_import_and_sign_100() { +static void test_import_and_sign_all_10() { - EC_KEY *k1; - EC_KEY *k2; - EC_POINT *ecp1; - EC_POINT *ecp2; - BIGNUM *bn1; - BIGNUM *bn2; - char pk1[32]; - char pk2[32]; - X509 *cert1; - X509 *cert2; - CK_BYTE i; - CK_BYTE some_data[] = "0123456789012345678901"; + EVP_PKEY *evp; + EC_KEY *eck; + const EC_POINT *ecp; + const BIGNUM *bn; + char pvt[32]; + X509 *cert; + ASN1_TIME *tm; + CK_BYTE i, j; + CK_BYTE some_data[32]; + CK_ULONG class_k = CKO_PRIVATE_KEY; + CK_ULONG class_c = CKO_CERTIFICATE; + CK_ULONG kt = CKK_ECDSA; + CK_BYTE id = 0; + CK_BYTE params[] = {0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x03, 0x01, 0x07}; + CK_BYTE sig[64]; + CK_ULONG recv_len; + CK_BYTE value_c[3100]; + CK_ULONG cert_len; + CK_BYTE der_encoded[80]; + CK_BYTE_PTR der_ptr; + CK_BYTE_PTR r_ptr; + CK_BYTE_PTR s_ptr; + CK_ULONG r_len; + CK_ULONG s_len; - CK_ULONG class = CKO_PRIVATE_KEY; - CK_ULONG kt = CKK_ECDSA; - CK_BYTE id = 0; - CK_BYTE params[] = {0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x03, 0x01, 0x07}; - CK_BYTE value[32]; + unsigned char *p; - CK_ATTRIBUTE publicKeyTemplate[] = { - {CKA_CLASS, &class, sizeof(class)}, + CK_ATTRIBUTE privateKeyTemplate[] = { + {CKA_CLASS, &class_k, sizeof(class_k)}, {CKA_KEY_TYPE, &kt, sizeof(kt)}, {CKA_ID, &id, sizeof(id)}, {CKA_EC_PARAMS, ¶ms, sizeof(params)}, - {CKA_VALUE, value, sizeof(value)} + {CKA_VALUE, pvt, sizeof(pvt)} }; - CK_OBJECT_HANDLE obj; + CK_ATTRIBUTE publicKeyTemplate[] = { + {CKA_CLASS, &class_c, sizeof(class_c)}, + {CKA_ID, &id, sizeof(id)}, + {CKA_VALUE, value_c, sizeof(value_c)} + }; + CK_OBJECT_HANDLE obj[24]; CK_SESSION_HANDLE session; + CK_MECHANISM mech = {CKM_ECDSA, NULL}; - k1 = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1); - k2 = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1); + evp = EVP_PKEY_new(); - if (k1 == NULL || k2 == NULL) + if (evp == NULL) exit(EXIT_FAILURE); - cert1 = X509_new(); + eck = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1); - if (cert1 == NULL) + if (eck == NULL) exit(EXIT_FAILURE); - asrt(EC_KEY_generate_key(k1), 1, "GENERATE K1"); - asrt(EC_KEY_generate_key(k2), 1, "GENERATE K2"); + asrt(EC_KEY_generate_key(eck), 1, "GENERATE ECK"); - bn1 = EC_KEY_get0_private_key(k1); - bn2 = EC_KEY_get0_private_key(k2); + bn = EC_KEY_get0_private_key(eck); - asrt(BN_bn2bin(bn1, pk1), 32, "EXTRACT PK1"); - asrt(BN_bn2bin(bn2, pk2), 32, "EXTRACT PK2"); + asrt(BN_bn2bin(bn, pvt), 32, "EXTRACT PVT"); - /*ecp1 = EC_KEY_get0_public_key(k1); - ecp2 = EC_KEY_get0_public_key(k2); + if (EVP_PKEY_set1_EC_KEY(evp, eck) == 0) + exit(EXIT_FAILURE); - if (ecp1 == NULL || ecp2 == NULL) - exit(EXIT_FAILURE);*/ + cert = X509_new(); + + if (cert == NULL) + exit(EXIT_FAILURE); + + if (X509_set_pubkey(cert, evp) == 0) + exit(EXIT_FAILURE); + + tm = ASN1_TIME_new(); + if (tm == NULL) + exit(EXIT_FAILURE); + + ASN1_TIME_set_string(tm, "000001010000Z"); + X509_set_notBefore(cert, tm); + X509_set_notAfter(cert, tm); + + cert->sig_alg->algorithm = OBJ_nid2obj(8); + cert->cert_info->signature->algorithm = OBJ_nid2obj(8); + + ASN1_BIT_STRING_set_bit(cert->signature, 8, 1); + ASN1_BIT_STRING_set(cert->signature, "\x00", 1); + + p = value_c; + if ((cert_len = (CK_ULONG) i2d_X509(cert, &p)) == 0 || cert_len > sizeof(value_c)) + exit(EXIT_FAILURE); + + publicKeyTemplate[2].ulValueLen = cert_len; asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); asrt(funcs->C_Login(session, CKU_SO, "010203040506070801020304050607080102030405060708", 48), CKR_OK, "Login SO"); - asrt(funcs->C_CreateObject(session, publicKeyTemplate, 5, &obj), CKR_OK, "IMPORT KEY"); + for (i = 0; i < 24; i++) { + id = i; + asrt(funcs->C_CreateObject(session, publicKeyTemplate, 3, obj + i), CKR_OK, "IMPORT CERT"); + asrt(funcs->C_CreateObject(session, privateKeyTemplate, 5, obj + i), CKR_OK, "IMPORT KEY"); + } asrt(funcs->C_Logout(session), CKR_OK, "Logout SO"); + + for (i = 0; i < 24; i++) { + for (j = 0; j < 10; j++) { + + if(RAND_pseudo_bytes(some_data, sizeof(some_data)) == -1) + exit(EXIT_FAILURE); + + asrt(funcs->C_Login(session, CKU_USER, "123456", 6), CKR_OK, "Login USER"); + asrt(funcs->C_SignInit(session, &mech, obj[i]), CKR_OK, "SignInit"); + + recv_len = sizeof(sig); + asrt(funcs->C_Sign(session, some_data, sizeof(some_data), sig, &recv_len), CKR_OK, "Sign"); + + r_len = 32; + s_len = 32; + + der_ptr = der_encoded; + *der_ptr++ = 0x30; + *der_ptr++ = 0xff; // placeholder, fix below + + r_ptr = sig; + + *der_ptr++ = 0x02; + *der_ptr++ = r_len; + if (*r_ptr >= 0x80) { + *(der_ptr - 1) = *(der_ptr - 1) + 1; + *der_ptr++ = 0x00; + } + else if (*r_ptr == 0x00 && *(r_ptr + 1) < 0x80) { + r_len--; + *(der_ptr - 1) = *(der_ptr - 1) - 1; + r_ptr++; + } + memcpy(der_ptr, r_ptr, r_len); + der_ptr+= r_len; + + s_ptr = sig + 32; + + *der_ptr++ = 0x02; + *der_ptr++ = s_len; + if (*s_ptr >= 0x80) { + *(der_ptr - 1) = *(der_ptr - 1) + 1; + *der_ptr++ = 0x00; + } + else if (*s_ptr == 0x00 && *(s_ptr + 1) < 0x80) { + s_len--; + *(der_ptr - 1) = *(der_ptr - 1) - 1; + s_ptr++; + } + memcpy(der_ptr, s_ptr, s_len); + der_ptr+= s_len; + + der_encoded[1] = der_ptr - der_encoded - 2; + + dump_hex(der_encoded, der_encoded[1] + 2, stderr, 1); + + asrt(ECDSA_verify(0, some_data, sizeof(some_data), der_encoded, der_encoded[1] + 2, eck), 1, "ECDSA VERIFICATION"); + + } + } + + asrt(funcs->C_Logout(session), CKR_OK, "Logout USER"); + asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); - //for (i = 0; i < 100f; i++) { - - //} } int main(void) { @@ -307,7 +415,7 @@ int main(void) { test_mechanism_list_and_info(); test_session(); test_login(); - test_import_and_sign_100(); + test_import_and_sign_all_10(); #else fprintf(stderr, "HARDWARE TESTS DISABLED!, skipping...\n"); #endif From 72a5137e9d69e9d8381f21031d87eef3c1039078 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 15:43:24 +0100 Subject: [PATCH 048/107] More memcpy. --- ykcs11/utils.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/ykcs11/utils.c b/ykcs11/utils.c index 6cc729b..11968eb 100644 --- a/ykcs11/utils.c +++ b/ykcs11/utils.c @@ -29,16 +29,16 @@ CK_RV parse_readers(ykpiv_state *state, const CK_BYTE_PTR readers, const CK_ULON for (i = 0; i < len; i++) if (readers[i] == '\0' && i != len - 1) { - slots[*n_slots].vid = get_vendor_id(p); + slots[*n_slots].vid = get_vendor_id((char *)p); if (slots[*n_slots].vid == UNKNOWN) { // TODO: distinguish between tokenless and unsupported? // Unknown slot, just save what info we have memset(&slots[*n_slots].info, 0, sizeof(CK_SLOT_INFO)); memset(slots[*n_slots].info.slotDescription, ' ', sizeof(slots[*n_slots].info.slotDescription)); - if (strlen(p) <= sizeof(slots[*n_slots].info.slotDescription)) - strncpy(slots[*n_slots].info.slotDescription, p, strlen(p)); + if (strlen((char *)p) <= sizeof(slots[*n_slots].info.slotDescription)) + memcpy(slots[*n_slots].info.slotDescription, p, strlen((char *)p)); else - strncpy(slots[*n_slots].info.slotDescription, p, sizeof(slots[*n_slots].info.slotDescription)); + memcpy(slots[*n_slots].info.slotDescription, p, sizeof(slots[*n_slots].info.slotDescription)); } else { // Supported slot From e949618ec2941ae74cf4ba1a132298d8d0455ac9 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 27 Nov 2015 17:13:54 +0100 Subject: [PATCH 049/107] YKCS11: started adding RSA test. --- ykcs11/tests/ykcs11_tests.c | 193 ++++++++++++++++++++++++++++++++++++ 1 file changed, 193 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 0f95887..f81e153 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -3,6 +3,7 @@ #include +#include #include #include #include @@ -403,6 +404,197 @@ static void test_import_and_sign_all_10() { } +// Import a newly generated RSA1024 pvt key and a certificate +// to every slot and use the key to sign some data +static void test_import_and_sign_all_10_RSA() { + + EVP_PKEY *evp; + RSA *rsak; + X509 *cert; + ASN1_TIME *tm; + CK_BYTE i, j; + CK_BYTE some_data[32]; + CK_BYTE e[] = {0x01, 0x00, 0x01}; + CK_BYTE p[64]; + CK_BYTE q[64]; + CK_BYTE dp[64]; + CK_BYTE dq[64]; + CK_BYTE qinv[64]; + BIGNUM *e_bn; + CK_ULONG class_k = CKO_PRIVATE_KEY; + CK_ULONG class_c = CKO_CERTIFICATE; + CK_ULONG kt = CKK_RSA; + CK_BYTE id = 0; + CK_BYTE sig[64]; + CK_ULONG recv_len; + CK_BYTE value_c[3100]; + CK_ULONG cert_len; + CK_BYTE der_encoded[80]; + CK_BYTE_PTR der_ptr; + CK_BYTE_PTR r_ptr; + CK_BYTE_PTR s_ptr; + CK_ULONG r_len; + CK_ULONG s_len; + + unsigned char *px; + + CK_ATTRIBUTE privateKeyTemplate[] = { + {CKA_CLASS, &class_k, sizeof(class_k)}, + {CKA_KEY_TYPE, &kt, sizeof(kt)}, + {CKA_ID, &id, sizeof(id)}, + {CKA_PUBLIC_EXPONENT, e, sizeof(e)}, + {CKA_PRIME_1, p, sizeof(p)}, + {CKA_PRIME_2, q, sizeof(q)}, + {CKA_EXPONENT_1, dp, sizeof(dp)}, + {CKA_EXPONENT_2, dq, sizeof(dq)}, + {CKA_COEFFICIENT, qinv, sizeof(qinv)} + }; + + CK_ATTRIBUTE publicKeyTemplate[] = { + {CKA_CLASS, &class_c, sizeof(class_c)}, + {CKA_ID, &id, sizeof(id)}, + {CKA_VALUE, value_c, sizeof(value_c)} + }; + + CK_OBJECT_HANDLE obj[24]; + CK_SESSION_HANDLE session; + CK_MECHANISM mech = {CKM_RSA_PKCS, NULL}; + + evp = EVP_PKEY_new(); + + if (evp == NULL) + exit(EXIT_FAILURE); + + rsak = RSA_new(); + + if (rsak == NULL) + exit(EXIT_FAILURE); + + e_bn = BN_bin2bn(e, 3, NULL); + + if (e_bn == NULL) + exit(EXIT_FAILURE); + + asrt(RSA_generate_key_ex(rsak, 1024, e_bn, NULL), 1, "GENERATE RSAK"); + + asrt(BN_bn2bin(rsak->p, p), 64, "GET P"); + asrt(BN_bn2bin(rsak->q, q), 64, "GET Q"); + asrt(BN_bn2bin(rsak->dmp1, dp), 64, "GET DP"); + asrt(BN_bn2bin(rsak->dmq1, dp), 64, "GET DQ"); + asrt(BN_bn2bin(rsak->iqmp, qinv), 64, "GET QINV"); + + + + if (EVP_PKEY_set1_RSA(evp, rsak) == 0) + exit(EXIT_FAILURE); + + cert = X509_new(); + + if (cert == NULL) + exit(EXIT_FAILURE); + + if (X509_set_pubkey(cert, evp) == 0) + exit(EXIT_FAILURE); + + tm = ASN1_TIME_new(); + if (tm == NULL) + exit(EXIT_FAILURE); + + ASN1_TIME_set_string(tm, "000001010000Z"); + X509_set_notBefore(cert, tm); + X509_set_notAfter(cert, tm); + + cert->sig_alg->algorithm = OBJ_nid2obj(8); + cert->cert_info->signature->algorithm = OBJ_nid2obj(8); + + ASN1_BIT_STRING_set_bit(cert->signature, 8, 1); + ASN1_BIT_STRING_set(cert->signature, "\x00", 1); + + px = value_c; + if ((cert_len = (CK_ULONG) i2d_X509(cert, &px)) == 0 || cert_len > sizeof(value_c)) + exit(EXIT_FAILURE); + + publicKeyTemplate[2].ulValueLen = cert_len; + + asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); + asrt(funcs->C_OpenSession(0, CKF_SERIAL_SESSION | CKF_RW_SESSION, NULL, NULL, &session), CKR_OK, "OpenSession1"); + asrt(funcs->C_Login(session, CKU_SO, "010203040506070801020304050607080102030405060708", 48), CKR_OK, "Login SO"); + + for (i = 0; i < 24; i++) { + id = i; + asrt(funcs->C_CreateObject(session, publicKeyTemplate, 3, obj + i), CKR_OK, "IMPORT CERT"); + asrt(funcs->C_CreateObject(session, privateKeyTemplate, 9, obj + i), CKR_OK, "IMPORT KEY"); + } + + asrt(funcs->C_Logout(session), CKR_OK, "Logout SO"); + + for (i = 0; i < 24; i++) { + for (j = 0; j < 10; j++) { + + if(RAND_pseudo_bytes(some_data, sizeof(some_data)) == -1) + exit(EXIT_FAILURE); + + asrt(funcs->C_Login(session, CKU_USER, "123456", 6), CKR_OK, "Login USER"); + asrt(funcs->C_SignInit(session, &mech, obj[i]), CKR_OK, "SignInit"); + + recv_len = sizeof(sig); + asrt(funcs->C_Sign(session, some_data, sizeof(some_data), sig, &recv_len), CKR_OK, "Sign"); + + /* r_len = 32; */ + /* s_len = 32; */ + + /* der_ptr = der_encoded; */ + /* *der_ptr++ = 0x30; */ + /* *der_ptr++ = 0xff; // placeholder, fix below */ + + /* r_ptr = sig; */ + + /* *der_ptr++ = 0x02; */ + /* *der_ptr++ = r_len; */ + /* if (*r_ptr >= 0x80) { */ + /* *(der_ptr - 1) = *(der_ptr - 1) + 1; */ + /* *der_ptr++ = 0x00; */ + /* } */ + /* else if (*r_ptr == 0x00 && *(r_ptr + 1) < 0x80) { */ + /* r_len--; */ + /* *(der_ptr - 1) = *(der_ptr - 1) - 1; */ + /* r_ptr++; */ + /* } */ + /* memcpy(der_ptr, r_ptr, r_len); */ + /* der_ptr+= r_len; */ + + /* s_ptr = sig + 32; */ + + /* *der_ptr++ = 0x02; */ + /* *der_ptr++ = s_len; */ + /* if (*s_ptr >= 0x80) { */ + /* *(der_ptr - 1) = *(der_ptr - 1) + 1; */ + /* *der_ptr++ = 0x00; */ + /* } */ + /* else if (*s_ptr == 0x00 && *(s_ptr + 1) < 0x80) { */ + /* s_len--; */ + /* *(der_ptr - 1) = *(der_ptr - 1) - 1; */ + /* s_ptr++; */ + /* } */ + /* memcpy(der_ptr, s_ptr, s_len); */ + /* der_ptr+= s_len; */ + + /* der_encoded[1] = der_ptr - der_encoded - 2; */ + + /* dump_hex(der_encoded, der_encoded[1] + 2, stderr, 1); */ + + /* asrt(ECDSA_verify(0, some_data, sizeof(some_data), der_encoded, der_encoded[1] + 2, eck), 1, "ECDSA VERIFICATION"); */ + + } + } + + asrt(funcs->C_Logout(session), CKR_OK, "Logout USER"); + + asrt(funcs->C_CloseSession(session), CKR_OK, "CloseSession"); + asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); + +} + int main(void) { get_functions(&funcs); @@ -416,6 +608,7 @@ int main(void) { test_session(); test_login(); test_import_and_sign_all_10(); + test_import_and_sign_all_10_RSA(); #else fprintf(stderr, "HARDWARE TESTS DISABLED!, skipping...\n"); #endif From 9d4ff79dd67a42e57b2eced26aa23ad3481eb70a Mon Sep 17 00:00:00 2001 From: denisenkom Date: Tue, 1 Dec 2015 13:26:33 -0500 Subject: [PATCH 050/107] Update ykcs11.c According to PKCS11 spec CKR_SESSION_READ_ONLY_EXISTS should only be returned by C_Login when SO user is logging in. From spec: If the application calling C_Login has a R/O session open with the token, then it will be unable to log the SO into a session (see [PKCS11-UG] for further details). An attempt to do this will result in the error code CKR_SESSION_READ_ONLY_EXISTS. --- ykcs11/ykcs11.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index d7234e2..cbb56b1 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -731,8 +731,8 @@ CK_DEFINE_FUNCTION(CK_RV, C_Login)( return CKR_SESSION_HANDLE_INVALID; } - if ((session.info.flags & CKF_RW_SESSION) == 0) { // TODO: make macros for these? - DBG("Tried to log-in to a read-only session"); + if (userType == CKU_SO && (session.info.flags & CKF_RW_SESSION) == 0) { // TODO: make macros for these? + DBG("Tried to log-in SO user to a read-only session"); return CKR_SESSION_READ_ONLY_EXISTS; } From 1a533ea0dcd02809ad503c2d354f7b7f1e2ca208 Mon Sep 17 00:00:00 2001 From: Mikhail Denisenko Date: Tue, 1 Dec 2015 16:24:38 -0500 Subject: [PATCH 051/107] Fixed bug #39 C_Login fails with CKR_PIN_INCORRECT when pin and pinLen are valid but pin is not null terminated --- ykcs11/token_vendors.c | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/ykcs11/token_vendors.c b/ykcs11/token_vendors.c index b5bbfd8..debcf50 100644 --- a/ykcs11/token_vendors.c +++ b/ykcs11/token_vendors.c @@ -12,12 +12,23 @@ static CK_RV COMMON_token_login(ykpiv_state *state, CK_USER_TYPE user, CK_UTF8CH int tries = 0; // TODO: this is effectively disregarded, should we add a better value in ykpiv_verify? unsigned char key[24]; size_t key_len = sizeof(key); + unsigned char *term_pin; if (user == CKU_USER) { - if (ykpiv_verify(state, (char *)pin, &tries) != YKPIV_OK) { + // add null termination for the pin + term_pin = malloc(pin_len + 1); + if (term_pin == NULL) { + return CKR_HOST_MEMORY; + } + memcpy(term_pin, pin, pin_len); + term_pin[pin_len] = 0; + + if (ykpiv_verify(state, (char *)term_pin, &tries) != YKPIV_OK) { + free(term_pin); DBG("Failed to login"); return CKR_PIN_INCORRECT; } + free(term_pin); } else if (user == CKU_SO) { if(ykpiv_hex_decode((char *)pin, pin_len, key, &key_len) != YKPIV_OK) { From 36972ebc6fba9671f05de27f1e668596ba1db027 Mon Sep 17 00:00:00 2001 From: Mikhail Denisenko Date: Tue, 1 Dec 2015 16:45:09 -0500 Subject: [PATCH 052/107] Securely dispose of pin copy --- ykcs11/token_vendors.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/ykcs11/token_vendors.c b/ykcs11/token_vendors.c index debcf50..9cb33b6 100644 --- a/ykcs11/token_vendors.c +++ b/ykcs11/token_vendors.c @@ -13,6 +13,7 @@ static CK_RV COMMON_token_login(ykpiv_state *state, CK_USER_TYPE user, CK_UTF8CH unsigned char key[24]; size_t key_len = sizeof(key); unsigned char *term_pin; + ykpiv_rc res; if (user == CKU_USER) { // add null termination for the pin @@ -23,12 +24,15 @@ static CK_RV COMMON_token_login(ykpiv_state *state, CK_USER_TYPE user, CK_UTF8CH memcpy(term_pin, pin, pin_len); term_pin[pin_len] = 0; - if (ykpiv_verify(state, (char *)term_pin, &tries) != YKPIV_OK) { - free(term_pin); + res = ykpiv_verify(state, (char *)term_pin, &tries); + + OPENSSL_cleanse(term_pin, pin_len); + free(term_pin); + + if (res != YKPIV_OK) { DBG("Failed to login"); return CKR_PIN_INCORRECT; } - free(term_pin); } else if (user == CKU_SO) { if(ykpiv_hex_decode((char *)pin, pin_len, key, &key_len) != YKPIV_OK) { From 70e181a860f7bcfb53e92342f34e464b87d15fbe Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 3 Dec 2015 08:01:07 +0100 Subject: [PATCH 053/107] add a new action set-ccc change aroudn so set_chuid() becomes set_dataobject() and a bit more generic fixes #33 --- tool/cmdline.ggo | 2 +- tool/yubico-piv-tool.c | 46 ++++++++++++++++++++++++++++++++++-------- 2 files changed, 39 insertions(+), 9 deletions(-) diff --git a/tool/cmdline.ggo b/tool/cmdline.ggo index 4d9ab43..5252868 100644 --- a/tool/cmdline.ggo +++ b/tool/cmdline.ggo @@ -32,7 +32,7 @@ option "action" a "Action to take" values="version","generate","set-mgm-key", "reset","pin-retries","import-key","import-certificate","set-chuid", "request-certificate","verify-pin","change-pin","change-puk","unblock-pin", "selfsign-certificate","delete-certificate","read-certificate","status", - "test-signature","test-decipher","list-readers" enum multiple + "test-signature","test-decipher","list-readers","set-ccc" enum multiple text " Multiple actions may be given at once and will be executed in order for example --action=verify-pin --action=request-certificate\n" diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 01ad5d5..8809690 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -63,6 +63,17 @@ unsigned const char chuid_tmpl[] = { }; #define CHUID_GUID_OFFS 29 +unsigned const char ccc_tmpl[] = { + 0xf0, 0x15, 0xa0, 0x00, 0x00, 0x01, 0x16, 0xff, 0x02, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf1, 0x01, 0x21, + 0xf2, 0x01, 0x21, 0xf3, 0x00, 0xf4, 0x01, 0x00, 0xf5, 0x01, 0x10, 0xf6, 0x00, + 0xf7, 0x00, 0xfa, 0x00, 0xfb, 0x00, 0xfc, 0x00, 0xfd, 0x00, 0xfe, 0x00 +}; +#define CCC_ID_OFFS 9 + +#define CHUID 0 +#define CCC 1 + #define MAX_OID_LEN 19 #define KEY_LEN 24 @@ -588,20 +599,36 @@ import_cert_out: return ret; } -static bool set_chuid(ykpiv_state *state, int verbose) { - unsigned char chuid[sizeof(chuid_tmpl)]; +static bool set_dataobject(ykpiv_state *state, int verbose, int type) { + unsigned char obj[1024]; ykpiv_rc res; + size_t offs, rand_len, len; + const unsigned char *tmpl; + int id; - memcpy(chuid, chuid_tmpl, sizeof(chuid)); - if(RAND_pseudo_bytes(chuid + CHUID_GUID_OFFS, 0x10) == -1) { + if(type == CHUID) { + offs = CHUID_GUID_OFFS; + len = sizeof(chuid_tmpl); + rand_len = 0x10; + tmpl = chuid_tmpl; + id = YKPIV_OBJ_CHUID; + } else { + offs = CCC_ID_OFFS; + rand_len = 0xe; + len = sizeof(ccc_tmpl); + tmpl = ccc_tmpl; + id = YKPIV_OBJ_CAPABILITY; + } + memcpy(obj, tmpl, len); + if(RAND_pseudo_bytes(obj + offs, rand_len) == -1) { fprintf(stderr, "error: no randomness.\n"); return false; } if(verbose) { - fprintf(stderr, "Setting the CHUID to: "); - dump_hex(chuid, sizeof(chuid), stderr, true); + fprintf(stderr, "Setting the %s to: ", type == CHUID ? "CHUID" : "CCC"); + dump_hex(obj, len, stderr, true); } - if((res = ykpiv_save_object(state, YKPIV_OBJ_CHUID, chuid, sizeof(chuid))) != YKPIV_OK) { + if((res = ykpiv_save_object(state, id, obj, len)) != YKPIV_OK) { fprintf(stderr, "Failed communicating with device: %s\n", ykpiv_strerror(res)); return false; } @@ -1668,6 +1695,7 @@ int main(int argc, char *argv[]) { case action_arg_verifyMINUS_pin: case action_arg_setMINUS_mgmMINUS_key: case action_arg_setMINUS_chuid: + case action_arg_setMINUS_ccc: case action_arg_version: case action_arg_reset: case action_arg_status: @@ -1698,6 +1726,7 @@ int main(int argc, char *argv[]) { case action_arg_importMINUS_key: case action_arg_importMINUS_certificate: case action_arg_setMINUS_chuid: + case action_arg_setMINUS_ccc: case action_arg_deleteMINUS_certificate: if(verbosity) { fprintf(stderr, "Authenticating since action '%s' needs that.\n", cmdline_parser_action_values[action]); @@ -1838,8 +1867,9 @@ int main(int argc, char *argv[]) { fprintf(stderr, "Successfully imported a new certificate.\n"); } break; + case action_arg_setMINUS_ccc: case action_arg_setMINUS_chuid: - if(set_chuid(state, verbosity) == false) { + if(set_dataobject(state, verbosity, action == action_arg_setMINUS_chuid ? CHUID : CCC) == false) { ret = EXIT_FAILURE; } else { fprintf(stderr, "Successfully set new CHUID.\n"); From baae5fa464b7338cac1edd450f702b101596c862 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 3 Dec 2015 14:53:10 +0100 Subject: [PATCH 054/107] difference between CHUID and CCC in success message. --- tool/yubico-piv-tool.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 8809690..97c386e 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1872,7 +1872,7 @@ int main(int argc, char *argv[]) { if(set_dataobject(state, verbosity, action == action_arg_setMINUS_chuid ? CHUID : CCC) == false) { ret = EXIT_FAILURE; } else { - fprintf(stderr, "Successfully set new CHUID.\n"); + fprintf(stderr, "Successfully set new %s.\n", action == action_arg_setMINUS_chuid ? "CHUID" : "CCC"); } break; case action_arg_requestMINUS_certificate: From ebdb9f7f5fd45b00d46d49e3ab86024f8baf0556 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 3 Dec 2015 10:10:38 -0800 Subject: [PATCH 055/107] YKCS11: Fix RSA2048 key generation template. --- ykcs11/token_vendors.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ykcs11/token_vendors.c b/ykcs11/token_vendors.c index 9cb33b6..2f2ad7d 100644 --- a/ykcs11/token_vendors.c +++ b/ykcs11/token_vendors.c @@ -73,7 +73,7 @@ static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, switch(key_len) { case 2048: if (rsa == CK_TRUE) - in_data[4] = YKPIV_ALGO_RSA2048; + *in_ptr++ = YKPIV_ALGO_RSA2048; else return CKR_FUNCTION_FAILED; From 94cd489efd6d123773a6d075e61016fe9806580f Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 3 Dec 2015 10:24:02 -0800 Subject: [PATCH 056/107] YKCS11: allow key generation for retired keys slots. --- tool/util.c | 68 +++++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 64 insertions(+), 4 deletions(-) diff --git a/tool/util.c b/tool/util.c index 9ab2801..d330daa 100644 --- a/tool/util.c +++ b/tool/util.c @@ -273,18 +273,78 @@ int key_to_object_id(int key) { int object; switch(key) { - case 0x9a: + case YKPIV_KEY_AUTHENTICATION: object = YKPIV_OBJ_AUTHENTICATION; break; - case 0x9c: + case YKPIV_KEY_CARDMGM: object = YKPIV_OBJ_SIGNATURE; break; - case 0x9d: + case YKPIV_KEY_KEYMGM: object = YKPIV_OBJ_KEY_MANAGEMENT; break; - case 0x9e: + case YKPIV_KEY_CARDAUTH: object = YKPIV_OBJ_CARD_AUTH; break; + case YKPIV_KEY_RETIRED1: + object = YKPIV_OBJ_RETIRED1; + break; + case YKPIV_KEY_RETIRED2: + object = YKPIV_OBJ_RETIRED2; + break; + case YKPIV_KEY_RETIRED3: + object = YKPIV_OBJ_RETIRED3; + break; + case YKPIV_KEY_RETIRED4: + object = YKPIV_OBJ_RETIRED4; + break; + case YKPIV_KEY_RETIRED5: + object = YKPIV_OBJ_RETIRED5; + break; + case YKPIV_KEY_RETIRED6: + object = YKPIV_OBJ_RETIRED6; + break; + case YKPIV_KEY_RETIRED7: + object = YKPIV_OBJ_RETIRED7; + break; + case YKPIV_KEY_RETIRED8: + object = YKPIV_OBJ_RETIRED8; + break; + case YKPIV_KEY_RETIRED9: + object = YKPIV_OBJ_RETIRED9; + break; + case YKPIV_KEY_RETIRED10: + object = YKPIV_OBJ_RETIRED10; + break; + case YKPIV_KEY_RETIRED11: + object = YKPIV_OBJ_RETIRED11; + break; + case YKPIV_KEY_RETIRED12: + object = YKPIV_OBJ_RETIRED12; + break; + case YKPIV_KEY_RETIRED13: + object = YKPIV_OBJ_RETIRED13; + break; + case YKPIV_KEY_RETIRED14: + object = YKPIV_OBJ_RETIRED14; + break; + case YKPIV_KEY_RETIRED15: + object = YKPIV_OBJ_RETIRED15; + break; + case YKPIV_KEY_RETIRED16: + object = YKPIV_OBJ_RETIRED16; + break; + case YKPIV_KEY_RETIRED17: + object = YKPIV_OBJ_RETIRED17; + break; + case YKPIV_KEY_RETIRED18: + object = YKPIV_OBJ_RETIRED18; + break; + case YKPIV_KEY_RETIRED19: + object = YKPIV_OBJ_RETIRED19; + break; + case YKPIV_KEY_RETIRED20: + object = YKPIV_OBJ_RETIRED20; + break; default: object = 0; } From bfda53303ced4c5303f0a6859b4c98e872108849 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 3 Dec 2015 10:47:49 -0800 Subject: [PATCH 057/107] YKCS11: update cert buffer size. --- ykcs11/token_vendors.c | 4 ++-- ykcs11/ykcs11.c | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/ykcs11/token_vendors.c b/ykcs11/token_vendors.c index 2f2ad7d..aa50ad2 100644 --- a/ykcs11/token_vendors.c +++ b/ykcs11/token_vendors.c @@ -158,7 +158,7 @@ static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, static CK_RV COMMON_token_import_cert(ykpiv_state *state, CK_ULONG cert_id, CK_BYTE_PTR in) { - unsigned char certdata[2100]; + unsigned char certdata[3072]; unsigned char *certptr; CK_ULONG cert_len; @@ -168,7 +168,7 @@ static CK_RV COMMON_token_import_cert(ykpiv_state *state, CK_ULONG cert_id, CK_B if ((rv = do_check_cert(in, &cert_len)) != CKR_OK) return rv; - if (cert_len > 2100) + if (cert_len > 3072) return CKR_FUNCTION_FAILED; certptr = certdata; diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index cbb56b1..e0e4497 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -438,7 +438,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_OpenSession)( CK_RV rv; piv_obj_id_t *cert_ids; CK_ULONG i; - CK_BYTE cert_data[2100]; // Max cert value for ykpiv + CK_BYTE cert_data[3072]; // Max cert value for ykpiv CK_ULONG cert_len = sizeof(cert_data); DIN; // TODO: pApplication and Notify @@ -2115,7 +2115,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_GenerateKeyPair)( CK_ULONG pvtk_id; CK_ULONG pubk_id; piv_obj_id_t *obj_ptr; - CK_BYTE cert_data[2100]; + CK_BYTE cert_data[3072]; CK_ULONG cert_len; DIN; From 8297815622e7464f454e9faa43cf1bc8e384e55c Mon Sep 17 00:00:00 2001 From: Mikhail Denisenko Date: Thu, 3 Dec 2015 18:04:44 -0500 Subject: [PATCH 058/107] Return CKR_ATTRIBUTE_TYPE_INVALID instead of CKR_FUNCTION_FAILED on unsupported attributes. This result works better with Java IaikPkcs11 wrapper, and possibly others. --- ykcs11/objects.c | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index c471f73..9e62342 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -493,15 +493,15 @@ CK_RV get_coa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_ISSUER: DBG("ISSUER TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_SERIAL_NUMBER: DBG("SERIAL NUMBER TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_SUBJECT: DBG("SUBJECT TODO"); // Required - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_ID: DBG("ID"); @@ -512,11 +512,11 @@ CK_RV get_coa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_START_DATE: DBG("START DATE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_END_DATE: DBG("END DATE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_MODIFIABLE: DBG("MODIFIABLE"); @@ -596,7 +596,7 @@ CK_RV get_proa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_SUBJECT: DBG("SUBJECT TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_ID: DBG("ID"); @@ -607,7 +607,7 @@ CK_RV get_proa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_SENSITIVE: DBG("SENSITIVE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_DECRYPT: DBG("DECRYPT"); // Default empy @@ -632,7 +632,7 @@ CK_RV get_proa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_SIGN_RECOVER: DBG("SIGN RECOVER TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_DERIVE: DBG("DERIVE"); // Default false @@ -643,11 +643,11 @@ CK_RV get_proa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_START_DATE: DBG("START DATE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_END_DATE: DBG("END DATE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_MODULUS: DBG("MODULUS"); @@ -747,7 +747,7 @@ CK_RV get_proa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { /* case CKA_EXTRACTABLE: */ case CKA_LOCAL: DBG("LOCAL TODO"); // Required - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; /* case CKA_NEVER_EXTRACTABLE: */ /*case CKA_ALWAYS_SENSITIVE:*/ @@ -838,7 +838,7 @@ CK_RV get_puoa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_SUBJECT: DBG("SUBJECT TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_ID: DBG("ID"); @@ -877,11 +877,11 @@ CK_RV get_puoa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_START_DATE: DBG("START DATE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_END_DATE: DBG("END DATE TODO"); // Default empty - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_EC_POINT: DBG("EC_POINT"); @@ -969,7 +969,7 @@ CK_RV get_puoa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { case CKA_LOCAL: DBG("LOCAL TODO"); // Required - return CKR_FUNCTION_FAILED; + return CKR_ATTRIBUTE_TYPE_INVALID; case CKA_MODIFIABLE: DBG("MODIFIABLE"); From ebbb00206808c5e62acee9ce34f14dfe8cf5264e Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 09:24:04 +0100 Subject: [PATCH 059/107] don't overfill the buffer on cert import --- tool/yubico-piv-tool.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 97c386e..d8851f9 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -557,6 +557,11 @@ static bool import_cert(ykpiv_state *state, enum enum_key_format cert_format, int object = get_object_id(slot); ykpiv_rc res; + if(4 + cert_len + 5 > 3072) { /* 4 is prefix size, 5 is postfix size */ + fprintf(stderr, "Certificate is to large to fit in buffer.\n"); + goto import_cert_out; + } + *certptr++ = 0x70; certptr += set_length(certptr, cert_len); if (compress) { From 75f9ccd06484f0e8cd98a90c19371222cc677bb7 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 09:36:54 +0100 Subject: [PATCH 060/107] add Android code signing doc for dist --- Makefile.am | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Makefile.am b/Makefile.am index b4f185c..5cecf0d 100644 --- a/Makefile.am +++ b/Makefile.am @@ -31,7 +31,8 @@ ACLOCAL_AMFLAGS = -I m4 EXTRA_DIST = windows.mk mac.mk tool/tests/basic.sh tools/fasc.pl -EXTRA_DIST += doc/Certificate_Authority.adoc doc/OS_X_code_signing.adoc doc/SSH_with_PIV_and_PKCS11.adoc doc/Windows_certificate.adoc doc/YKCS11_release_notes.adoc doc/YubiKey_PIV_introduction.adoc +EXTRA_DIST += doc/Android_code_signing.adoc doc/Certificate_Authority.adoc doc/OS_X_code_signing.adoc doc/SSH_with_PIV_and_PKCS11.adoc doc/Windows_certificate.adoc doc/YKCS11_release_notes.adoc doc/YubiKey_PIV_introduction.adoc + if ENABLE_COV cov-reset: From dcdc42ad4c578ea53a635dd737d46a565314bb78 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 09:02:45 +0100 Subject: [PATCH 061/107] bump openssl to 1.0.1q for windows and mac builds --- mac.mk | 2 +- windows.mk | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/mac.mk b/mac.mk index be456b2..2f0f70f 100644 --- a/mac.mk +++ b/mac.mk @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. PACKAGE=yubico-piv-tool -OPENSSLVERSION=1.0.1p +OPENSSLVERSION=1.0.1q all: usage mac diff --git a/windows.mk b/windows.mk index af2de79..8b88736 100644 --- a/windows.mk +++ b/windows.mk @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. PACKAGE=yubico-piv-tool -OPENSSLVERSION=1.0.1p +OPENSSLVERSION=1.0.1q all: usage 32bit 64bit From 16be345e8ba073d34c2ffd89959fc283652cfcaa Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 09:14:09 +0100 Subject: [PATCH 062/107] next version is 1.2.0, also NEWS for it --- NEWS | 16 +++++++++++++++- configure.ac | 2 +- 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/NEWS b/NEWS index cb3ff65..514a262 100644 --- a/NEWS +++ b/NEWS @@ -1,6 +1,20 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- -* Version 1.1.3 (unreleased) +* Version 1.2.0 (released 2015-12-07) + +** On OSX use @loader_path instead of @executable_path for ykcs11. + +** Add ykpiv_import_private_key to libykpiv. + +** Raise buffer sizes to support bigger objects. + +** Change behavior of action status, only list populated slots. + +** Add retired keys to ykcs11. + +** In ykcs11 support login with non null terminated pin. + +** Add a new action set-ccc to yubico-piv-tool to set the CCC. * Version 1.1.2 (released 2015-11-13) diff --git a/configure.ac b/configure.ac index 19c4936..39e71a5 100644 --- a/configure.ac +++ b/configure.ac @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -AC_INIT([yubico-piv-tool], [1.1.3]) +AC_INIT([yubico-piv-tool], [1.2.0]) AC_CONFIG_AUX_DIR([build-aux]) AC_CONFIG_MACRO_DIR([m4]) From 337931fae741c85dc74aea32b0d92850239580c6 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 09:41:07 +0100 Subject: [PATCH 063/107] bump versions --- NEWS | 2 ++ configure.ac | 4 ++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/NEWS b/NEWS index 514a262..30e1f8c 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,7 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- +* Version 1.2.1 (unreleased) + * Version 1.2.0 (released 2015-12-07) ** On OSX use @loader_path instead of @executable_path for ykcs11. diff --git a/configure.ac b/configure.ac index 39e71a5..6ce490c 100644 --- a/configure.ac +++ b/configure.ac @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -AC_INIT([yubico-piv-tool], [1.2.0]) +AC_INIT([yubico-piv-tool], [1.2.1]) AC_CONFIG_AUX_DIR([build-aux]) AC_CONFIG_MACRO_DIR([m4]) @@ -35,7 +35,7 @@ AC_CONFIG_MACRO_DIR([m4]) # Interfaces added: AGE++ # Interfaces removed: AGE=0 AC_SUBST([LT_CURRENT], 3) -AC_SUBST([LT_REVISION], 0) +AC_SUBST([LT_REVISION], 1) AC_SUBST([LT_AGE], 2) AM_INIT_AUTOMAKE([-Wall -Werror foreign]) From a03181757d001f3ca0cb2186b9c744f3b6053c7e Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 12:08:50 +0100 Subject: [PATCH 064/107] change around windows layout, include libssl, drop all pkgconfig --- windows.mk | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/windows.mk b/windows.mk index 8b88736..56ad45f 100644 --- a/windows.mk +++ b/windows.mk @@ -53,17 +53,14 @@ doit: rm -rf $(PWD)/tmp$(ARCH)/root/ssl/ && \ rm $(PWD)/tmp$(ARCH)/root/bin/openssl.exe && \ rm $(PWD)/tmp$(ARCH)/root/bin/c_rehash && \ - rm $(PWD)/tmp$(ARCH)/root/bin/ssleay32.dll && \ rm -rf $(PWD)/tmp$(ARCH)/root/lib/engines/ && \ - rm -rf $(PWD)/tmp$(ARCH)/root/lib/libssl* && \ - rm $(PWD)/tmp$(ARCH)/root/lib/pkgconfig/libssl.pc && \ - rm $(PWD)/tmp$(ARCH)/root/lib/pkgconfig/openssl.pc && \ cd .. && \ cp ../$(PACKAGE)-$(VERSION).tar.gz . && \ tar xfa $(PACKAGE)-$(VERSION).tar.gz && \ cd $(PACKAGE)-$(VERSION)/ && \ CC=$(HOST)-gcc PKG_CONFIG_PATH=$(PWD)/tmp$(ARCH)/root/lib/pkgconfig lt_cv_deplibs_check_method=pass_all ./configure --host=$(HOST) --build=x86_64-unknown-linux-gnu --prefix=$(PWD)/tmp$(ARCH)/root LDFLAGS=-L$(PWD)/tmp$(ARCH)/root/lib CPPFLAGS=-I$(PWD)/tmp$(ARCH)/root/include && \ make install $(CHECK) && \ + rm -rf $(PWD)/tmp$(ARCH)/root/lib/pkgconfig/ && \ cp COPYING $(PWD)/tmp$(ARCH)/root/licenses/$(PACKAGE).txt && \ cd .. && \ cd root && \ From 6f6490f023aaf5b7d11c39e5e4f61312e048db73 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 12:22:42 +0100 Subject: [PATCH 065/107] add cflags for mac build --- mac.mk | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/mac.mk b/mac.mk index 2f0f70f..49f853f 100644 --- a/mac.mk +++ b/mac.mk @@ -27,6 +27,7 @@ PACKAGE=yubico-piv-tool OPENSSLVERSION=1.0.1q +CFLAGS="-mmacosx-version-min=10.6" all: usage mac @@ -47,7 +48,7 @@ doit: curl -L -O "https://www.openssl.org/source/openssl-$(OPENSSLVERSION).tar.gz" && \ tar xfz openssl-$(OPENSSLVERSION).tar.gz && \ cd openssl-$(OPENSSLVERSION) && \ - ./Configure darwin64-x86_64-cc shared no-ssl2 no-ssl3 no-engines --prefix=$(PWD)/tmp/root && \ + ./Configure darwin64-x86_64-cc shared no-ssl2 no-ssl3 no-engines --prefix=$(PWD)/tmp/root $(CFLAGS) && \ make all install_sw && \ cp LICENSE $(PWD)/tmp$(ARCH)/root/licenses/openssl.txt && \ rm -rf $(PWD)/tmp/root/ssl/ && \ @@ -60,7 +61,7 @@ doit: cp ../$(PACKAGE)-$(VERSION).tar.gz . && \ tar xfz $(PACKAGE)-$(VERSION).tar.gz && \ cd $(PACKAGE)-$(VERSION)/ && \ - PKG_CONFIG_PATH=$(PWD)/tmp/root/lib/pkgconfig ./configure --prefix=$(PWD)/tmp/root && \ + CFLAGS=$(CFLAGS) PKG_CONFIG_PATH=$(PWD)/tmp/root/lib/pkgconfig ./configure --prefix=$(PWD)/tmp/root && \ make install $(CHECK) && \ chmod u+w $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib && \ install_name_tool -id @loader_path/libcrypto.1.0.0.dylib $(PWD)/tmp/root/lib/libcrypto.1.0.0.dylib && \ From a1d60073759e43da5f4141bc5d2fc988522505ff Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 7 Dec 2015 19:53:43 +0100 Subject: [PATCH 066/107] increase buffer sizes when building the status view otherwise data buffer will be to small after loading a big certificate --- tool/yubico-piv-tool.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index d8851f9..f04b6e0 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1204,7 +1204,7 @@ static void print_cert_info(ykpiv_state *state, enum enum_slot slot, const EVP_M FILE *output) { int object = get_object_id(slot); int slot_name; - unsigned char data[2048]; + unsigned char data[3072]; const unsigned char *ptr = data; unsigned long len = sizeof(data); int cert_len; @@ -1314,7 +1314,7 @@ static bool status(ykpiv_state *state, enum enum_hash hash, enum enum_slot slot, const char *output_file_name) { const EVP_MD *md; - unsigned char chuid[2048]; + unsigned char chuid[3072]; long unsigned len = sizeof(chuid); int i; FILE *output_file = open_file(output_file_name, OUTPUT); From 895e6216b158f73c99c68423a5ea4a87ec9082bf Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 8 Dec 2015 10:38:01 +0100 Subject: [PATCH 067/107] NEWS for 1.2.1 --- NEWS | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/NEWS b/NEWS index 30e1f8c..900e88d 100644 --- a/NEWS +++ b/NEWS @@ -1,6 +1,8 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- -* Version 1.2.1 (unreleased) +* Version 1.2.1 (released 2015-12-08) + +** Fix issue with big certificates and status. * Version 1.2.0 (released 2015-12-07) From 1f1b61bcf9cf62b25a84611fe2d54dbee66de81e Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 8 Dec 2015 13:20:56 +0100 Subject: [PATCH 068/107] bump versions to 1.2.2 --- NEWS | 2 ++ configure.ac | 4 ++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/NEWS b/NEWS index 900e88d..4604aaa 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,7 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- +* Version 1.2.2 (unreleased) + * Version 1.2.1 (released 2015-12-08) ** Fix issue with big certificates and status. diff --git a/configure.ac b/configure.ac index 6ce490c..f8e7a46 100644 --- a/configure.ac +++ b/configure.ac @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -AC_INIT([yubico-piv-tool], [1.2.1]) +AC_INIT([yubico-piv-tool], [1.2.2]) AC_CONFIG_AUX_DIR([build-aux]) AC_CONFIG_MACRO_DIR([m4]) @@ -35,7 +35,7 @@ AC_CONFIG_MACRO_DIR([m4]) # Interfaces added: AGE++ # Interfaces removed: AGE=0 AC_SUBST([LT_CURRENT], 3) -AC_SUBST([LT_REVISION], 1) +AC_SUBST([LT_REVISION], 2) AC_SUBST([LT_AGE], 2) AM_INIT_AUTOMAKE([-Wall -Werror foreign]) From b784f0ea8da53ac8db5ecd749f21582d6c70c9cd Mon Sep 17 00:00:00 2001 From: Jakub Jelen Date: Tue, 8 Dec 2015 13:27:04 +0100 Subject: [PATCH 069/107] Get rid of warnings about unused functions when running without HW_TESTS --- ykcs11/tests/ykcs11_tests.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index f81e153..00d165e 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -65,6 +65,7 @@ static void test_lib_info() { asrt(strcmp(info.libraryDescription, YKCS11_DESCRIPTION), 0, "LIB_DESC"); } +#ifdef HW_TESTS static void test_initalize() { asrt(funcs->C_Initialize(NULL), CKR_OK, "INITIALIZE"); @@ -594,6 +595,7 @@ static void test_import_and_sign_all_10_RSA() { asrt(funcs->C_Finalize(NULL), CKR_OK, "FINALIZE"); } +#endif int main(void) { From e7d53ceb4540899b98ec3f0c3f5afbcaed376680 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 8 Dec 2015 14:12:29 +0100 Subject: [PATCH 070/107] fix an old overflow bug we need to do 8 - new_len, not 16 - new_len which overflows the indata buffer --- tool/yubico-piv-tool.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index f04b6e0..d2b3383 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1013,7 +1013,7 @@ static bool change_pin(ykpiv_state *state, enum enum_action action, const char * } memcpy(indata + 8, new_pin, new_len); if(new_len < 8) { - memset(indata + 8 + new_len, 0xff, 16 - new_len); + memset(indata + 8 + new_len, 0xff, 8 - new_len); } if(ykpiv_transfer_data(state, templ, indata, sizeof(indata), data, &recv_len, &sw) != YKPIV_OK) { return false; From 98c0b34699c71398336b78bc78af77364b039aad Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 8 Dec 2015 14:13:38 +0100 Subject: [PATCH 071/107] NEWS for 1.2.2 --- NEWS | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/NEWS b/NEWS index 4604aaa..f015353 100644 --- a/NEWS +++ b/NEWS @@ -1,6 +1,8 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- -* Version 1.2.2 (unreleased) +* Version 1.2.2 (released 2015-12-08) + +** Fix old buffer overflow in change-pin functionality. * Version 1.2.1 (released 2015-12-08) From 3e920d11b3656467ffcc8df52ece226018a55c50 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 8 Dec 2015 14:22:39 +0100 Subject: [PATCH 072/107] bump next version to 1.2.3 --- NEWS | 2 ++ configure.ac | 4 ++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/NEWS b/NEWS index f015353..2fced7c 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,7 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- +* Version 1.2.3 (unreleased) + * Version 1.2.2 (released 2015-12-08) ** Fix old buffer overflow in change-pin functionality. diff --git a/configure.ac b/configure.ac index f8e7a46..7b9592e 100644 --- a/configure.ac +++ b/configure.ac @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -AC_INIT([yubico-piv-tool], [1.2.2]) +AC_INIT([yubico-piv-tool], [1.2.3]) AC_CONFIG_AUX_DIR([build-aux]) AC_CONFIG_MACRO_DIR([m4]) @@ -35,7 +35,7 @@ AC_CONFIG_MACRO_DIR([m4]) # Interfaces added: AGE++ # Interfaces removed: AGE=0 AC_SUBST([LT_CURRENT], 3) -AC_SUBST([LT_REVISION], 2) +AC_SUBST([LT_REVISION], 3) AC_SUBST([LT_AGE], 2) AM_INIT_AUTOMAKE([-Wall -Werror foreign]) From 5a60faf7791d4c4401a36fd90c952ab692d6e9b1 Mon Sep 17 00:00:00 2001 From: Mikhail Denisenko Date: Wed, 9 Dec 2015 13:13:24 -0500 Subject: [PATCH 073/107] Fixed extraction of RSA modulus and exponent --- ykcs11/objects.c | 22 +++++++++++++--------- ykcs11/openssl_utils.c | 33 ++++++++++++++++++++++++++++++--- ykcs11/openssl_utils.h | 3 ++- 3 files changed, 45 insertions(+), 13 deletions(-) diff --git a/ykcs11/objects.c b/ykcs11/objects.c index 9e62342..c94af52 100644 --- a/ykcs11/objects.c +++ b/ykcs11/objects.c @@ -340,8 +340,12 @@ static CK_ULONG get_modulus_bits(EVP_PKEY *key) { return do_get_rsa_modulus_length(key); } -static CK_ULONG get_public_exponent(EVP_PKEY *key) { - return do_get_public_exponent(key); +static CK_RV get_public_exponent(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len) { + return do_get_public_exponent(key, data, len); +} + +static CK_RV get_modulus(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len) { + return do_get_modulus(key, data, len); } static CK_RV get_public_key(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len) { @@ -727,10 +731,9 @@ CK_RV get_proa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { if (ul_tmp != CKK_RSA) return CKR_ATTRIBUTE_VALUE_INVALID; - ul_tmp = get_public_exponent(pubkey_objects[piv_objects[obj].sub_id].data); // Getting the info from the pubk - if (ul_tmp == 0) + if (get_public_exponent(pubkey_objects[piv_objects[obj].sub_id].data, b_tmp, &len) != CKR_OK) return CKR_FUNCTION_FAILED; - data = (CK_BYTE_PTR) &ul_tmp; + data = b_tmp; break; /* case CKA_PRIVATE_EXPONENT: */ @@ -928,7 +931,7 @@ CK_RV get_puoa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { if (ul_tmp != CKK_RSA) return CKR_ATTRIBUTE_VALUE_INVALID; - if (get_public_key(pubkey_objects[piv_objects[obj].sub_id].data, b_tmp, &len) != CKR_OK) + if (get_modulus(pubkey_objects[piv_objects[obj].sub_id].data, b_tmp, &len) != CKR_OK) return CKR_FUNCTION_FAILED; data = b_tmp; break; @@ -961,10 +964,9 @@ CK_RV get_puoa(CK_OBJECT_HANDLE obj, CK_ATTRIBUTE_PTR template) { if (ul_tmp != CKK_RSA) return CKR_ATTRIBUTE_VALUE_INVALID; - ul_tmp = get_public_exponent(pubkey_objects[piv_objects[obj].sub_id].data); // Getting the info from the pubk - if (ul_tmp == 0) + if (get_public_exponent(pubkey_objects[piv_objects[obj].sub_id].data, b_tmp, &len) != CKR_OK) return CKR_FUNCTION_FAILED; - data = (CK_BYTE_PTR) &ul_tmp; + data = b_tmp; break; case CKA_LOCAL: @@ -1301,6 +1303,8 @@ CK_RV check_create_cert(CK_ATTRIBUTE_PTR templ, CK_ULONG n, case CKA_TOKEN: case CKA_LABEL: case CKA_SUBJECT: + case CKA_ISSUER: + case CKA_CERTIFICATE_TYPE: // Ignore other attributes break; diff --git a/ykcs11/openssl_utils.c b/ykcs11/openssl_utils.c index 353c29f..43a4550 100644 --- a/ykcs11/openssl_utils.c +++ b/ykcs11/openssl_utils.c @@ -317,16 +317,43 @@ CK_ULONG do_get_rsa_modulus_length(EVP_PKEY *key) { } -CK_ULONG do_get_public_exponent(EVP_PKEY *key) { +CK_RV do_get_modulus(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len) { + RSA *rsa; + + rsa = EVP_PKEY_get1_RSA(key); + if (rsa == NULL) + return CKR_FUNCTION_FAILED; + + if ((CK_ULONG)BN_num_bytes(rsa->n) > *len) { + RSA_free(rsa); + rsa = NULL; + return CKR_BUFFER_TOO_SMALL; + } + + *len = (CK_ULONG)BN_bn2bin(rsa->n, data); + + RSA_free(rsa); + rsa = NULL; + + return CKR_OK; +} + +CK_RV do_get_public_exponent(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len) { CK_ULONG e = 0; RSA *rsa; rsa = EVP_PKEY_get1_RSA(key); if (rsa == NULL) - return 0; + return CKR_FUNCTION_FAILED; - BN_bn2bin(rsa->e, (unsigned char *)&e); + if ((CK_ULONG)BN_num_bytes(rsa->e) > *len) { + RSA_free(rsa); + rsa = NULL; + return CKR_BUFFER_TOO_SMALL; + } + + *len = (CK_ULONG)BN_bn2bin(rsa->e, data); RSA_free(rsa); rsa = NULL; diff --git a/ykcs11/openssl_utils.h b/ykcs11/openssl_utils.h index 35461a5..8281be3 100644 --- a/ykcs11/openssl_utils.h +++ b/ykcs11/openssl_utils.h @@ -20,8 +20,9 @@ CK_RV do_delete_cert(X509 **cert); CK_RV do_store_pubk(X509 *cert, EVP_PKEY **key); CK_KEY_TYPE do_get_key_type(EVP_PKEY *key); CK_ULONG do_get_rsa_modulus_length(EVP_PKEY *key); -CK_ULONG do_get_public_exponent(EVP_PKEY *key); +CK_RV do_get_public_exponent(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len); CK_RV do_get_public_key(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len); +CK_RV do_get_modulus(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len); CK_RV do_encode_rsa_public_key(CK_BYTE_PTR data, CK_ULONG len, RSA **key); CK_RV do_get_curve_parameters(EVP_PKEY *key, CK_BYTE_PTR data, CK_ULONG_PTR len); CK_RV do_delete_pubk(EVP_PKEY **key); From 6042a2140eda42ee642904ac25b708edc85828b7 Mon Sep 17 00:00:00 2001 From: Mikhail Denisenko Date: Thu, 10 Dec 2015 17:31:22 -0500 Subject: [PATCH 074/107] Implemented C_SetPIN --- lib/ykpiv.c | 62 ++++++++++++++++++++++++++++++++++++++++++ lib/ykpiv.h | 10 +++++++ lib/ykpiv.map | 8 ++++++ tool/yubico-piv-tool.c | 48 ++++++++++++++------------------ ykcs11/token_vendors.c | 1 + ykcs11/token_vendors.h | 2 ++ ykcs11/ykcs11.c | 32 +++++++++++++++++++++- ykcs11/yubico_token.c | 22 +++++++++++++++ ykcs11/yubico_token.h | 2 ++ 9 files changed, 159 insertions(+), 28 deletions(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index 7936ee2..25ebb5d 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -716,6 +716,68 @@ ykpiv_rc ykpiv_verify(ykpiv_state *state, const char *pin, int *tries) { } } +#define CHREF_ACT_CHANGE_PIN 0 +#define CHREF_ACT_UNBLOCK_PIN 1 +#define CHREF_ACT_CHANGE_PUK 2 + +static ykpiv_rc _change_pin_internal(ykpiv_state *state, int action, const char * current_pin, size_t current_pin_len, const char * new_pin, size_t new_pin_len, int *tries) { + int sw; + unsigned char templ[] = {0, YKPIV_INS_CHANGE_REFERENCE, 0, 0x80}; + unsigned char indata[0x10]; + unsigned char data[0xff]; + unsigned long recv_len = sizeof(data); + ykpiv_rc res; + if (current_pin_len > 8) { + return YKPIV_SIZE_ERROR; + } + if (new_pin_len > 8) { + return YKPIV_SIZE_ERROR; + } + if(action == CHREF_ACT_UNBLOCK_PIN) { + templ[1] = YKPIV_INS_RESET_RETRY; + } + else if(action == CHREF_ACT_CHANGE_PUK) { + templ[3] = 0x81; + } + memcpy(indata, current_pin, current_pin_len); + if(current_pin_len < 8) { + memset(indata + current_pin_len, 0xff, 8 - current_pin_len); + } + memcpy(indata + 8, new_pin, new_pin_len); + if(new_pin_len < 8) { + memset(indata + 8 + new_pin_len, 0xff, 8 - new_pin_len); + } + res = ykpiv_transfer_data(state, templ, indata, sizeof(indata), data, &recv_len, &sw); + if(res != YKPIV_OK) { + return res; + } else if(sw != 0x9000) { + if((sw >> 8) == 0x63) { + *tries = sw & 0xf; + return YKPIV_WRONG_PIN; + } else if(sw == 0x6983) { + return YKPIV_PIN_LOCKED; + } else { + if(state->verbose) { + fprintf(stderr, "Failed changing pin, token response code: %x.\n", sw); + } + return YKPIV_GENERIC_ERROR; + } + } + return YKPIV_OK; +} + +ykpiv_rc ykpiv_change_pin(ykpiv_state *state, const char * current_pin, size_t current_pin_len, const char * new_pin, size_t new_pin_len, int *tries) { + return _change_pin_internal(state, CHREF_ACT_CHANGE_PIN, current_pin, current_pin_len, new_pin, new_pin_len, tries); +} + +ykpiv_rc ykpiv_change_puk(ykpiv_state *state, const char * current_puk, size_t current_puk_len, const char * new_puk, size_t new_puk_len, int *tries) { + return _change_pin_internal(state, CHREF_ACT_CHANGE_PUK, current_puk, current_puk_len, new_puk, new_puk_len, tries); +} + +ykpiv_rc ykpiv_unblock_pin(ykpiv_state *state, const char * puk, size_t puk_len, const char * new_pin, size_t new_pin_len, int *tries) { + return _change_pin_internal(state, CHREF_ACT_CHANGE_PUK, puk, puk_len, new_pin, new_pin_len, tries); +} + ykpiv_rc ykpiv_fetch_object(ykpiv_state *state, int object_id, unsigned char *data, unsigned long *len) { int sw; diff --git a/lib/ykpiv.h b/lib/ykpiv.h index a868966..a89a827 100644 --- a/lib/ykpiv.h +++ b/lib/ykpiv.h @@ -57,6 +57,7 @@ extern "C" YKPIV_WRONG_PIN = -10, YKPIV_INVALID_OBJECT = -11, YKPIV_ALGORITHM_ERROR = -12, + YKPIV_PIN_LOCKED = -13, } ykpiv_rc; const char *ykpiv_strerror(ykpiv_rc err); @@ -85,6 +86,15 @@ extern "C" unsigned char algorithm, unsigned char key); ykpiv_rc ykpiv_get_version(ykpiv_state *state, char *version, size_t len); ykpiv_rc ykpiv_verify(ykpiv_state *state, const char *pin, int *tries); + ykpiv_rc ykpiv_change_pin(ykpiv_state *state, const char * current_pin, size_t current_pin_len, + const char * new_pin, size_t new_pin_len, + int *tries); + ykpiv_rc ykpiv_change_puk(ykpiv_state *state, const char * current_puk, size_t current_puk_len, + const char * new_puk, size_t new_puk_len, + int *tries); + ykpiv_rc ykpiv_unblock_pin(ykpiv_state *state, const char * puk, size_t puk_len, + const char * new_pin, size_t new_pin_len, + int *tries); ykpiv_rc ykpiv_fetch_object(ykpiv_state *state, int object_id, unsigned char *data, unsigned long *len); ykpiv_rc ykpiv_set_mgmkey2(ykpiv_state *state, const unsigned char *new_key, diff --git a/lib/ykpiv.map b/lib/ykpiv.map index fb2efb1..309cbf3 100644 --- a/lib/ykpiv.map +++ b/lib/ykpiv.map @@ -62,3 +62,11 @@ global: ykpiv_list_readers; ykpiv_import_private_key; } YKPIV_0.1.0; + +YKPIV_1.2.1 +{ +global: + ykpiv_change_pin; + ykpiv_change_puk; + ykpiv_unblock_pin; +} YKPIV_1.1.0; diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index d2b3383..0c00a59 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -969,17 +969,16 @@ static bool verify_pin(ykpiv_state *state, const char *pin) { * since they're very similar in what data they use. */ static bool change_pin(ykpiv_state *state, enum enum_action action, const char *pin, const char *new_pin) { - unsigned char templ[] = {0, YKPIV_INS_CHANGE_REFERENCE, 0, 0x80}; - unsigned char indata[0x10]; - unsigned char data[0xff]; - unsigned long recv_len = sizeof(data); char pinbuf[9] = {0}; char new_pinbuf[9] = {0}; const char *name = action == action_arg_changeMINUS_pin ? "pin" : "puk"; const char *new_name = action == action_arg_changeMINUS_puk ? "new puk" : "new pin"; - int sw; + int (*op)(ykpiv_state *state, const char * puk, size_t puk_len, + const char * new_pin, size_t new_pin_len, int *tries) = ykpiv_change_pin; size_t pin_len; size_t new_len; + int tries; + ykpiv_rc res; if(!pin) { if (!read_pw(name, pinbuf, sizeof(pinbuf), false)) { @@ -1002,38 +1001,33 @@ static bool change_pin(ykpiv_state *state, enum enum_action action, const char * } if(action == action_arg_unblockMINUS_pin) { - templ[1] = YKPIV_INS_RESET_RETRY; + op = ykpiv_unblock_pin; } else if(action == action_arg_changeMINUS_puk) { - templ[3] = 0x81; + op = ykpiv_change_puk; } - memcpy(indata, pin, pin_len); - if(pin_len < 8) { - memset(indata + pin_len, 0xff, 8 - pin_len); - } - memcpy(indata + 8, new_pin, new_len); - if(new_len < 8) { - memset(indata + 8 + new_len, 0xff, 8 - new_len); - } - if(ykpiv_transfer_data(state, templ, indata, sizeof(indata), data, &recv_len, &sw) != YKPIV_OK) { - return false; - } else if(sw != 0x9000) { - if((sw >> 8) == 0x63) { - int tries = sw & 0xf; + res = op(state, pin, pin_len, new_pin, new_len, &tries); + switch (res) { + case YKPIV_OK: + return true; + + case YKPIV_WRONG_PIN: fprintf(stderr, "Failed verifying %s code, now %d tries left before blocked.\n", - name, tries); - } else if(sw == 0x6983) { + name, tries); + return false; + + case YKPIV_PIN_LOCKED: if(action == action_arg_changeMINUS_pin) { fprintf(stderr, "The pin code is blocked, use the unblock-pin action to unblock it.\n"); } else { fprintf(stderr, "The puk code is blocked, you will have to reinitialize the application.\n"); } - } else { - fprintf(stderr, "Failed changing/unblocking code, error: %x\n", sw); - } - return false; + return false; + + default: + fprintf(stderr, "Failed changing/unblocking code, error: %x\n", res); + return false; } - return true; } static bool delete_certificate(ykpiv_state *state, enum enum_slot slot) { diff --git a/ykcs11/token_vendors.c b/ykcs11/token_vendors.c index aa50ad2..9cda842 100644 --- a/ykcs11/token_vendors.c +++ b/ykcs11/token_vendors.c @@ -290,6 +290,7 @@ token_vendor_t get_token_vendor(vendor_id_t vid) { v.token_import_cert = COMMON_token_import_cert; v.token_import_private_key = COMMON_token_import_private_key; v.token_delete_cert = COMMON_token_delete_cert; + v.token_change_pin = YUBICO_token_change_pin; break; case UNKNOWN: diff --git a/ykcs11/token_vendors.h b/ykcs11/token_vendors.h index a9be63d..528b2c5 100644 --- a/ykcs11/token_vendors.h +++ b/ykcs11/token_vendors.h @@ -18,6 +18,7 @@ typedef CK_RV (*get_t_mechanism_info_f)(CK_MECHANISM_TYPE, CK_MECHANISM_INFO_PTR typedef CK_RV (*get_t_objects_num_f)(ykpiv_state *, CK_ULONG_PTR, CK_ULONG_PTR); typedef CK_RV (*get_t_object_list_f)(ykpiv_state *, piv_obj_id_t *, CK_ULONG); typedef CK_RV (*get_t_raw_certificate_f)(ykpiv_state *, piv_obj_id_t, CK_BYTE_PTR, CK_ULONG_PTR); +typedef CK_RV (*t_change_pin_f)(ykpiv_state *, CK_USER_TYPE, CK_UTF8CHAR_PTR, CK_ULONG, CK_UTF8CHAR_PTR, CK_ULONG); // Common token functions below typedef CK_RV (*t_login_f)(ykpiv_state *, CK_USER_TYPE, CK_UTF8CHAR_PTR, CK_ULONG); @@ -53,6 +54,7 @@ typedef struct { t_import_cert_f token_import_cert; t_import_private_key_f token_import_private_key; t_delete_cert_f token_delete_cert; + t_change_pin_f token_change_pin; } token_vendor_t; token_vendor_t get_token_vendor(vendor_id_t vid); diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index e0e4497..23e290d 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -421,7 +421,36 @@ CK_DEFINE_FUNCTION(CK_RV, C_SetPIN)( ) { DIN; - DBG("TODO!!!"); + CK_RV rv; + token_vendor_t token; + + if (piv_state == NULL) { + DBG("libykpiv is not initialized or already finalized"); + return CKR_CRYPTOKI_NOT_INITIALIZED; + } + + if (session.handle == CK_INVALID_HANDLE) { + DBG("User called SetPIN on closed session"); + return CKR_SESSION_CLOSED; + } + + if (hSession != YKCS11_SESSION_ID) { + DBG("Unknown session %lu", hSession); + return CKR_SESSION_HANDLE_INVALID; + } + + CK_USER_TYPE user_type = CKU_USER; + if (session.info.state == CKS_RW_SO_FUNCTIONS) { + user_type = CKU_SO; + } + + token = get_token_vendor(session.slot->token->vid); + rv = token.token_change_pin(piv_state, user_type, pOldPin, ulOldLen, pNewPin, ulNewLen); + if (rv != CKR_OK) { + DBG("Pin change failed %lx", rv); + return rv; + } + DOUT; return CKR_OK; } @@ -979,6 +1008,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_CreateObject)( DBG("Unable to store certificate data"); return CKR_FUNCTION_FAILED; } + *phObject = cert_id; break; diff --git a/ykcs11/yubico_token.c b/ykcs11/yubico_token.c index 4e89c85..a85a26a 100644 --- a/ykcs11/yubico_token.c +++ b/ykcs11/yubico_token.c @@ -334,3 +334,25 @@ CK_RV YUBICO_get_token_raw_certificate(ykpiv_state *state, piv_obj_id_t obj, CK_ return CKR_OK; } + +CK_RV YUBICO_token_change_pin(ykpiv_state *state, CK_USER_TYPE user_type, CK_UTF8CHAR_PTR pOldPin, CK_ULONG ulOldLen, CK_UTF8CHAR_PTR pNewPin, CK_ULONG ulNewLen) { + int tries; + ykpiv_rc res; + if (user_type != CKU_USER) { + DBG("TODO implement other users pin change"); + return CKR_FUNCTION_FAILED; + } + res = ykpiv_change_pin(state, pOldPin, ulOldLen, pNewPin, ulNewLen, &tries); + switch (res) { + case YKPIV_OK: + return CKR_OK; + case YKPIV_SIZE_ERROR: + return CKR_PIN_LEN_RANGE; + case YKPIV_WRONG_PIN: + return CKR_PIN_INCORRECT; + case YKPIV_PIN_LOCKED: + return CKR_PIN_LOCKED; + default: + return CKR_FUNCTION_FAILED; + } +} diff --git a/ykcs11/yubico_token.h b/ykcs11/yubico_token.h index b725123..37f90a2 100644 --- a/ykcs11/yubico_token.h +++ b/ykcs11/yubico_token.h @@ -17,5 +17,7 @@ CK_RV YUBICO_get_token_mechanism_info(CK_MECHANISM_TYPE mec, CK_MECHANISM_INFO_P CK_RV YUBICO_get_token_objects_num(ykpiv_state *state, CK_ULONG_PTR num, CK_ULONG_PTR num_certs); CK_RV YUBICO_get_token_object_list(ykpiv_state *state, piv_obj_id_t *obj, CK_ULONG num); CK_RV YUBICO_get_token_raw_certificate(ykpiv_state *state, piv_obj_id_t obj, CK_BYTE_PTR data, CK_ULONG_PTR len); +CK_RV YUBICO_token_change_pin(ykpiv_state *state, CK_USER_TYPE user_type, CK_UTF8CHAR_PTR pOldPin, CK_ULONG ulOldLen, + CK_UTF8CHAR_PTR pNewPin, CK_ULONG ulNewLen); #endif From f3520c44c523e525319ad5d9cad3307fa69fbd80 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 11 Dec 2015 12:17:08 -0800 Subject: [PATCH 075/107] Fixup ykpiv exports and untabify. --- lib/ykpiv.map | 44 ++++++++++++++++++++++---------------------- 1 file changed, 22 insertions(+), 22 deletions(-) diff --git a/lib/ykpiv.map b/lib/ykpiv.map index 309cbf3..f4e621c 100644 --- a/lib/ykpiv.map +++ b/lib/ykpiv.map @@ -28,42 +28,42 @@ YKPIV_0.1.0 { global: - ykpiv_check_version; - ykpiv_strerror_name; - ykpiv_strerror; - ykpiv_init; - ykpiv_done; - ykpiv_connect; - ykpiv_disconnect; - ykpiv_transfer_data; - ykpiv_authenticate; - ykpiv_set_mgmkey; - ykpiv_sign_data; - ykpiv_get_version; - ykpiv_verify; - ykpiv_fetch_object; - ykpiv_save_object; - ykpiv_hex_decode; + ykpiv_check_version; + ykpiv_strerror_name; + ykpiv_strerror; + ykpiv_init; + ykpiv_done; + ykpiv_connect; + ykpiv_disconnect; + ykpiv_transfer_data; + ykpiv_authenticate; + ykpiv_set_mgmkey; + ykpiv_sign_data; + ykpiv_get_version; + ykpiv_verify; + ykpiv_fetch_object; + ykpiv_save_object; + ykpiv_hex_decode; local: - *; + *; }; YKPIV_0.2.0 { global: - ykpiv_decipher_data; + ykpiv_decipher_data; } YKPIV_0.1.0; YKPIV_1.1.0 { global: - ykpiv_set_mgmkey2; - ykpiv_list_readers; + ykpiv_set_mgmkey2; + ykpiv_list_readers; ykpiv_import_private_key; -} YKPIV_0.1.0; +} YKPIV_0.2.0; -YKPIV_1.2.1 +YKPIV_1.2.3 { global: ykpiv_change_pin; From 63b8b43bef5fe44f1154f96e0f8fe6c435fd5173 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Fri, 11 Dec 2015 12:14:48 -0800 Subject: [PATCH 076/107] Bump LT version. --- configure.ac | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/configure.ac b/configure.ac index 7b9592e..d84086a 100644 --- a/configure.ac +++ b/configure.ac @@ -34,9 +34,9 @@ AC_CONFIG_MACRO_DIR([m4]) # Interfaces changed/added/removed: CURRENT++ REVISION=0 # Interfaces added: AGE++ # Interfaces removed: AGE=0 -AC_SUBST([LT_CURRENT], 3) -AC_SUBST([LT_REVISION], 3) -AC_SUBST([LT_AGE], 2) +AC_SUBST([LT_CURRENT], 4) +AC_SUBST([LT_REVISION], 0) +AC_SUBST([LT_AGE], 3) AM_INIT_AUTOMAKE([-Wall -Werror foreign]) AM_SILENT_RULES([yes]) From a4ee5725b862544f9469119067a42bdcc667010c Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 14 Dec 2015 10:55:32 +0100 Subject: [PATCH 077/107] add generic write and read object actions for the tool this take in/out hex dump of the data --- tool/cmdline.ggo | 4 +- tool/yubico-piv-tool.c | 95 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 98 insertions(+), 1 deletion(-) diff --git a/tool/cmdline.ggo b/tool/cmdline.ggo index 5252868..33b968b 100644 --- a/tool/cmdline.ggo +++ b/tool/cmdline.ggo @@ -32,7 +32,8 @@ option "action" a "Action to take" values="version","generate","set-mgm-key", "reset","pin-retries","import-key","import-certificate","set-chuid", "request-certificate","verify-pin","change-pin","change-puk","unblock-pin", "selfsign-certificate","delete-certificate","read-certificate","status", - "test-signature","test-decipher","list-readers","set-ccc" enum multiple + "test-signature","test-decipher","list-readers","set-ccc","write-object", + "read-object" enum multiple text " Multiple actions may be given at once and will be executed in order for example --action=verify-pin --action=request-certificate\n" @@ -60,4 +61,5 @@ option "pin" P "Pin/puk code for verification" string optional option "new-pin" N "New pin/puk code for changing" string optional dependon="pin" option "pin-policy" - "Set pin policy for action generate or import-key" values="never","once","always" enum optional option "touch-policy" - "Set touch policy for action generate, import-key or set-mgm-key" values="never","always" enum optional +option "id" - "Id of object for write/get" int optional option "sign" - "Sign data" flag off hidden diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 0c00a59..ab3caef 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1644,6 +1644,82 @@ static bool list_readers(ykpiv_state *state) { return true; } +static bool write_object(ykpiv_state *state, int id, + const char *input_file_name, int verbosity) { + bool ret = false; + FILE *input_file = NULL; + unsigned char data[3072]; + char raw_data[3072 * 2]; + size_t len = sizeof(data); + size_t raw_len = sizeof(raw_data); + ykpiv_rc res; + + input_file = open_file(input_file_name, INPUT); + if(!input_file) { + return false; + } + + if(isatty(fileno(input_file))) { + fprintf(stderr, "Please paste the data...\n"); + } + + raw_len = fread(raw_data, 1, raw_len, input_file); + if(raw_len == 0) { + fprintf(stderr, "Failed reading data\n"); + goto write_out; + } + if(raw_data[raw_len - 1] == '\n') { + raw_len -= 1; + } + + if(ykpiv_hex_decode(raw_data, raw_len, data, &len) != YKPIV_OK) { + fprintf(stderr, "Failed decoding data\n"); + goto write_out; + } + + if(verbosity) { + fprintf(stderr, "Writing %lu bytes of data to object %x.\n", len, id); + } + + if((res = ykpiv_save_object(state, id, data, len)) != YKPIV_OK) { + fprintf(stderr, "Failed writing data to device: %s\n", ykpiv_strerror(res)); + } else { + ret = true; + } + +write_out: + if(input_file != stdin) { + fclose(input_file); + } + return ret; +} + +static bool read_object(ykpiv_state *state, int id, const char *output_file_name) { + FILE *output_file = NULL; + unsigned char data[3072]; + size_t len = sizeof(data); + bool ret = false; + + output_file = open_file(output_file_name, OUTPUT); + if(!output_file) { + return false; + } + + if(ykpiv_fetch_object(state, id, data, &len) != YKPIV_OK) { + fprintf(stderr, "Failed fetching object.\n"); + goto read_out; + } + + dump_hex(data, len, output_file, false); + ret = true; + +read_out: + if(output_file != stdout) { + fclose(output_file); + } + return ret; +} + int main(int argc, char *argv[]) { struct gengetopt_args_info args_info; ykpiv_state *state; @@ -1688,6 +1764,14 @@ int main(int argc, char *argv[]) { return EXIT_FAILURE; } break; + case action_arg_writeMINUS_object: + case action_arg_readMINUS_object: + if(!args_info.id_given) { + fprintf(stderr, "The '%s' action needs the --id argument.\n", + cmdline_parser_action_values[action]); + return EXIT_FAILURE; + } + break; case action_arg_changeMINUS_pin: case action_arg_changeMINUS_puk: case action_arg_unblockMINUS_pin: @@ -1727,6 +1811,7 @@ int main(int argc, char *argv[]) { case action_arg_setMINUS_chuid: case action_arg_setMINUS_ccc: case action_arg_deleteMINUS_certificate: + case action_arg_writeMINUS_object: if(verbosity) { fprintf(stderr, "Authenticating since action '%s' needs that.\n", cmdline_parser_action_values[action]); } @@ -1745,6 +1830,7 @@ int main(int argc, char *argv[]) { case action_arg_testMINUS_signature: case action_arg_testMINUS_decipher: case action_arg_listMINUS_readers: + case action_arg_readMINUS_object: case action__NULL: default: if(verbosity) { @@ -1945,6 +2031,15 @@ int main(int argc, char *argv[]) { if(list_readers(state) == false) { ret = EXIT_FAILURE; } + case action_arg_writeMINUS_object: + if(write_object(state, args_info.id_arg, args_info.input_arg, verbosity) == false) { + ret = EXIT_FAILURE; + } + break; + case action_arg_readMINUS_object: + if(read_object(state, args_info.id_arg, args_info.output_arg) == false) { + ret = EXIT_FAILURE; + } break; case action__NULL: default: From d3b271cd9ea644da766550a12e1ea02203046581 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 14 Dec 2015 12:22:13 +0100 Subject: [PATCH 078/107] next version will be 1.3.0 since new interfaces where added also fixup map file to show 1.2.0 correctly --- NEWS | 2 +- configure.ac | 2 +- lib/ykpiv.map | 11 ++++++++--- 3 files changed, 10 insertions(+), 5 deletions(-) diff --git a/NEWS b/NEWS index 2fced7c..fdf94b2 100644 --- a/NEWS +++ b/NEWS @@ -1,6 +1,6 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- -* Version 1.2.3 (unreleased) +* Version 1.3.0 (unreleased) * Version 1.2.2 (released 2015-12-08) diff --git a/configure.ac b/configure.ac index d84086a..29a8b19 100644 --- a/configure.ac +++ b/configure.ac @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -AC_INIT([yubico-piv-tool], [1.2.3]) +AC_INIT([yubico-piv-tool], [1.3.0]) AC_CONFIG_AUX_DIR([build-aux]) AC_CONFIG_MACRO_DIR([m4]) diff --git a/lib/ykpiv.map b/lib/ykpiv.map index f4e621c..7c71de8 100644 --- a/lib/ykpiv.map +++ b/lib/ykpiv.map @@ -60,13 +60,18 @@ YKPIV_1.1.0 global: ykpiv_set_mgmkey2; ykpiv_list_readers; - ykpiv_import_private_key; } YKPIV_0.2.0; -YKPIV_1.2.3 +YKPIV_1.2.0 +{ +global: + ykpiv_import_private_key; +} YKPIV_1.1.0; + +YKPIV_1.3.0 { global: ykpiv_change_pin; ykpiv_change_puk; ykpiv_unblock_pin; -} YKPIV_1.1.0; +} YKPIV_1.2.0; From 35c449e37416ec09b5df4608a183f53a358b6629 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 14 Dec 2015 12:48:28 +0100 Subject: [PATCH 079/107] change multiplication of minor to 10 so we don't overflow possibly temporary fix.. --- ykcs11/tests/ykcs11_tests.c | 2 +- ykcs11/ykcs11.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/ykcs11/tests/ykcs11_tests.c b/ykcs11/tests/ykcs11_tests.c index 00d165e..8495456 100644 --- a/ykcs11/tests/ykcs11_tests.c +++ b/ykcs11/tests/ykcs11_tests.c @@ -60,7 +60,7 @@ static void test_lib_info() { asrt(info.cryptokiVersion.minor, CRYPTOKI_VERSION_MIN, "CK_MIN"); asrt(info.libraryVersion.major, YKCS11_VERSION_MAJOR, "LIB_MAJ"); - asrt(info.libraryVersion.minor, ((YKCS11_VERSION_MINOR * 100) + YKCS11_VERSION_PATCH ), "LIB_MIN"); + asrt(info.libraryVersion.minor, ((YKCS11_VERSION_MINOR * 10) + YKCS11_VERSION_PATCH ), "LIB_MIN"); asrt(strcmp(info.libraryDescription, YKCS11_DESCRIPTION), 0, "LIB_DESC"); } diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index 23e290d..e4c5aae 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -114,7 +114,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetInfo)( CK_INFO_PTR pInfo ) { - CK_VERSION ver = {YKCS11_VERSION_MAJOR, (YKCS11_VERSION_MINOR * 100) + YKCS11_VERSION_PATCH}; + CK_VERSION ver = {YKCS11_VERSION_MAJOR, (YKCS11_VERSION_MINOR * 10) + YKCS11_VERSION_PATCH}; DIN; From fc4443aca7fec0ef86bc834208ba4073b8aa2345 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 14 Dec 2015 12:52:34 +0100 Subject: [PATCH 080/107] add configure.ac as a dependency of the yubico-piv-tool binary since if version number changes it should be rebuilt relates #53 --- tool/Makefile.am | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/tool/Makefile.am b/tool/Makefile.am index 3a9c760..5f4c73a 100644 --- a/tool/Makefile.am +++ b/tool/Makefile.am @@ -32,7 +32,7 @@ AM_CPPFLAGS = $(OPENSSL_CFLAGS) AM_CPPFLAGS += -I$(top_srcdir)/lib -I$(top_builddir)/lib bin_PROGRAMS = yubico-piv-tool -yubico_piv_tool_SOURCES = yubico-piv-tool.c yubico-piv-tool.h2m +yubico_piv_tool_SOURCES = yubico-piv-tool.c yubico-piv-tool.h2m $(top_srcdir)/configure.ac yubico_piv_tool_LDADD = $(OPENSSL_LIBS) ../lib/libykpiv.la yubico_piv_tool_LDADD += libpiv_cmd.la libpiv_util.la @@ -54,8 +54,7 @@ MAINTAINERCLEANFILES = $(BUILT_SOURCES) dist_man_MANS = yubico-piv-tool.1 MAINTAINERCLEANFILES += $(dist_man_MANS) -yubico-piv-tool.1: $(yubico_piv_tool_SOURCES) \ - $(top_srcdir)/configure.ac +yubico-piv-tool.1: $(yubico_piv_tool_SOURCES) $(HELP2MAN) --no-info \ --name="Yubico PIV tool" \ --include=$(srcdir)/yubico-piv-tool.h2m \ From 1c2d98b16d78a68a3aa5c02d6e0441e31beb8f19 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 14 Dec 2015 12:54:25 +0100 Subject: [PATCH 081/107] use top_builddir for relations between dirs --- tool/Makefile.am | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/Makefile.am b/tool/Makefile.am index 5f4c73a..aee15e8 100644 --- a/tool/Makefile.am +++ b/tool/Makefile.am @@ -33,7 +33,7 @@ AM_CPPFLAGS += -I$(top_srcdir)/lib -I$(top_builddir)/lib bin_PROGRAMS = yubico-piv-tool yubico_piv_tool_SOURCES = yubico-piv-tool.c yubico-piv-tool.h2m $(top_srcdir)/configure.ac -yubico_piv_tool_LDADD = $(OPENSSL_LIBS) ../lib/libykpiv.la +yubico_piv_tool_LDADD = $(OPENSSL_LIBS) $(top_builddir)/lib/libykpiv.la yubico_piv_tool_LDADD += libpiv_cmd.la libpiv_util.la noinst_LTLIBRARIES = libpiv_cmd.la libpiv_util.la From 24d9569f6579dcc1e3f1ee595c862e2be4afc5e8 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 15 Dec 2015 09:23:04 +0100 Subject: [PATCH 082/107] more work on automake dependencies to rebuild things correctly relates #53 --- tool/Makefile.am | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tool/Makefile.am b/tool/Makefile.am index aee15e8..b815bbb 100644 --- a/tool/Makefile.am +++ b/tool/Makefile.am @@ -32,7 +32,7 @@ AM_CPPFLAGS = $(OPENSSL_CFLAGS) AM_CPPFLAGS += -I$(top_srcdir)/lib -I$(top_builddir)/lib bin_PROGRAMS = yubico-piv-tool -yubico_piv_tool_SOURCES = yubico-piv-tool.c yubico-piv-tool.h2m $(top_srcdir)/configure.ac +yubico_piv_tool_SOURCES = yubico-piv-tool.c yubico-piv-tool.h2m yubico_piv_tool_LDADD = $(OPENSSL_LIBS) $(top_builddir)/lib/libykpiv.la yubico_piv_tool_LDADD += libpiv_cmd.la libpiv_util.la @@ -43,7 +43,7 @@ libpiv_cmd_la_CFLAGS = libpiv_util_la_SOURCES = util.c util.h libpiv_util_la_LIBADD = $(OPENSSL_LIBS) -cmdline.c cmdline.h: cmdline.ggo Makefile.am +cmdline.c cmdline.h: cmdline.ggo Makefile.am $(top_srcdir)/configure.ac $(GENGETOPT) --input $^ BUILT_SOURCES = cmdline.c cmdline.h @@ -54,7 +54,7 @@ MAINTAINERCLEANFILES = $(BUILT_SOURCES) dist_man_MANS = yubico-piv-tool.1 MAINTAINERCLEANFILES += $(dist_man_MANS) -yubico-piv-tool.1: $(yubico_piv_tool_SOURCES) +yubico-piv-tool.1: $(yubico_piv_tool_SOURCES) $(libpiv_cmd_la_SOURCES) $(HELP2MAN) --no-info \ --name="Yubico PIV tool" \ --include=$(srcdir)/yubico-piv-tool.h2m \ From e71c3b5337fada0638828df98e7210f3f663237e Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 15 Dec 2015 09:28:42 +0100 Subject: [PATCH 083/107] util depends on stdbool --- tool/util.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/tool/util.h b/tool/util.h index 21bb843..2dc893e 100644 --- a/tool/util.h +++ b/tool/util.h @@ -31,6 +31,8 @@ #ifndef YUBICO_PIV_TOOL_INTERNAL_H #define YUBICO_PIV_TOOL_INTERNAL_H +#include + #include #include "cmdline.h" From 30cc13aaff789b11c7d166d061276d35877a9944 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 15 Dec 2015 10:22:11 +0100 Subject: [PATCH 084/107] add format for read/write object as hex/base64/binary relates #31 --- tool/cmdline.ggo | 3 +- tool/util.c | 76 +++++++++++++++++++++++++++++++++++++++--- tool/util.h | 2 ++ tool/yubico-piv-tool.c | 27 ++++++--------- 4 files changed, 85 insertions(+), 23 deletions(-) diff --git a/tool/cmdline.ggo b/tool/cmdline.ggo index 33b968b..03e61c9 100644 --- a/tool/cmdline.ggo +++ b/tool/cmdline.ggo @@ -61,5 +61,6 @@ option "pin" P "Pin/puk code for verification" string optional option "new-pin" N "New pin/puk code for changing" string optional dependon="pin" option "pin-policy" - "Set pin policy for action generate or import-key" values="never","once","always" enum optional option "touch-policy" - "Set touch policy for action generate, import-key or set-mgm-key" values="never","always" enum optional -option "id" - "Id of object for write/get" int optional +option "id" - "Id of object for write/read object" int optional +option "format" f "Format of data for write/read object" values="hex","base64","binary" enum optional default="hex" option "sign" - "Sign data" flag off hidden diff --git a/tool/util.c b/tool/util.c index d330daa..56a9588 100644 --- a/tool/util.c +++ b/tool/util.c @@ -148,12 +148,78 @@ parse_err: return NULL; } -void dump_hex(const unsigned char *buf, unsigned int len, FILE *output, bool space) { - unsigned int i; - for (i = 0; i < len; i++) { - fprintf(output, "%02x%s", buf[i], space == true ? " " : ""); +size_t read_data(unsigned char *buf, size_t len, FILE* input, enum enum_format format) { + char raw_buf[3072 * 2]; + size_t raw_len = sizeof(raw_buf); + raw_len = fread(raw_buf, 1, raw_len, input); + switch(format) { + case format_arg_hex: + if(raw_buf[raw_len - 1] == '\n') { + raw_len -= 1; + } + if(ykpiv_hex_decode(raw_buf, raw_len, buf, &len) != YKPIV_OK) { + return 0; + } + return len; + case format_arg_base64: + { + int read; + BIO *b64 = BIO_new(BIO_f_base64()); + BIO *bio = BIO_new_mem_buf(raw_buf, raw_len); + BIO_push(b64, bio); + read = BIO_read(b64, buf, len); + BIO_free_all(b64); + if(read <= 0) { + return 0; + } else { + return (size_t)read; + } + } + break; + case format_arg_binary: + if(raw_len > len) { + return 0; + } + memcpy(buf, raw_buf, raw_len); + return raw_len; + case format__NULL: + default: + return 0; } - fprintf(output, "\n"); +} + +void dump_data(const unsigned char *buf, unsigned int len, FILE *output, bool space, enum enum_format format) { + switch(format) { + case format_arg_hex: + { + unsigned int i; + for (i = 0; i < len; i++) { + fprintf(output, "%02x%s", buf[i], space == true ? " " : ""); + } + fprintf(output, "\n"); + } + return; + case format_arg_base64: + { + BIO *b64 = BIO_new(BIO_f_base64()); + BIO *bio = BIO_new_fp(output, BIO_NOCLOSE); + BIO_push(b64, bio); + BIO_write(b64, buf, (int)len); + BIO_flush(b64); + BIO_free_all(b64); + } + return; + case format_arg_binary: + fwrite(buf, 1, len, output); + return; + case format__NULL: + default: + return; + } +} + +void dump_hex(const unsigned char *buf, unsigned int len, FILE *output, bool space) { + dump_data(buf, len, output, space, format_arg_hex); } int get_length(const unsigned char *buffer, int *len) { diff --git a/tool/util.h b/tool/util.h index 21bb843..8b2b728 100644 --- a/tool/util.h +++ b/tool/util.h @@ -38,6 +38,8 @@ #define INPUT 1 #define OUTPUT 2 +size_t read_data(unsigned char*, size_t, FILE*, enum enum_format); +void dump_data(unsigned const char*, unsigned int, FILE*, bool, enum enum_format); void dump_hex(unsigned const char*, unsigned int, FILE*, bool); int set_length(unsigned char*, int); int get_length(const unsigned char*, int*); diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index ab3caef..40b71c3 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1645,13 +1645,11 @@ static bool list_readers(ykpiv_state *state) { } static bool write_object(ykpiv_state *state, int id, - const char *input_file_name, int verbosity) { + const char *input_file_name, int verbosity, enum enum_format format) { bool ret = false; FILE *input_file = NULL; unsigned char data[3072]; - char raw_data[3072 * 2]; size_t len = sizeof(data); - size_t raw_len = sizeof(raw_data); ykpiv_rc res; input_file = open_file(input_file_name, INPUT); @@ -1663,19 +1661,11 @@ static bool write_object(ykpiv_state *state, int id, fprintf(stderr, "Please paste the data...\n"); } - raw_len = fread(raw_data, 1, raw_len, input_file); - if(raw_len == 0) { + len = read_data(data, len, input_file, format); + if(len == 0) { fprintf(stderr, "Failed reading data\n"); goto write_out; } - if(raw_data[raw_len - 1] == '\n') { - raw_len -= 1; - } - - if(ykpiv_hex_decode(raw_data, raw_len, data, &len) != YKPIV_OK) { - fprintf(stderr, "Failed decoding data\n"); - goto write_out; - } if(verbosity) { fprintf(stderr, "Writing %lu bytes of data to object %x.\n", len, id); @@ -1694,7 +1684,8 @@ write_out: return ret; } -static bool read_object(ykpiv_state *state, int id, const char *output_file_name) { +static bool read_object(ykpiv_state *state, int id, const char *output_file_name, + enum enum_format format) { FILE *output_file = NULL; unsigned char data[3072]; size_t len = sizeof(data); @@ -1710,7 +1701,7 @@ static bool read_object(ykpiv_state *state, int id, const char *output_file_name goto read_out; } - dump_hex(data, len, output_file, false); + dump_data(data, len, output_file, false, format); ret = true; read_out: @@ -2032,12 +2023,14 @@ int main(int argc, char *argv[]) { ret = EXIT_FAILURE; } case action_arg_writeMINUS_object: - if(write_object(state, args_info.id_arg, args_info.input_arg, verbosity) == false) { + if(write_object(state, args_info.id_arg, args_info.input_arg, verbosity, + args_info.format_arg) == false) { ret = EXIT_FAILURE; } break; case action_arg_readMINUS_object: - if(read_object(state, args_info.id_arg, args_info.output_arg) == false) { + if(read_object(state, args_info.id_arg, args_info.output_arg, + args_info.format_arg) == false) { ret = EXIT_FAILURE; } break; From a143c6d67dd9c864c245c149045845f4a3494d09 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 15 Dec 2015 10:27:54 +0100 Subject: [PATCH 085/107] remove the util function dump_hex() in favor of dump_data() --- tool/util.c | 4 ---- tool/util.h | 1 - tool/yubico-piv-tool.c | 20 ++++++++++---------- ykcs11/ykcs11.c | 8 ++++---- 4 files changed, 14 insertions(+), 19 deletions(-) diff --git a/tool/util.c b/tool/util.c index 56a9588..aeb40c2 100644 --- a/tool/util.c +++ b/tool/util.c @@ -218,10 +218,6 @@ void dump_data(const unsigned char *buf, unsigned int len, FILE *output, bool sp } } -void dump_hex(const unsigned char *buf, unsigned int len, FILE *output, bool space) { - dump_data(buf, len, output, space, format_arg_hex); -} - int get_length(const unsigned char *buffer, int *len) { if(buffer[0] < 0x81) { *len = buffer[0]; diff --git a/tool/util.h b/tool/util.h index 8b2b728..e045b07 100644 --- a/tool/util.h +++ b/tool/util.h @@ -40,7 +40,6 @@ size_t read_data(unsigned char*, size_t, FILE*, enum enum_format); void dump_data(unsigned const char*, unsigned int, FILE*, bool, enum enum_format); -void dump_hex(unsigned const char*, unsigned int, FILE*, bool); int set_length(unsigned char*, int); int get_length(const unsigned char*, int*); X509_NAME *parse_name(const char*); diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 40b71c3..9ee73ee 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -631,7 +631,7 @@ static bool set_dataobject(ykpiv_state *state, int verbose, int type) { } if(verbose) { fprintf(stderr, "Setting the %s to: ", type == CHUID ? "CHUID" : "CCC"); - dump_hex(obj, len, stderr, true); + dump_data(obj, len, stderr, true, format_arg_hex); } if((res = ykpiv_save_object(state, id, obj, len)) != YKPIV_OK) { fprintf(stderr, "Failed communicating with device: %s\n", ykpiv_strerror(res)); @@ -1157,7 +1157,7 @@ static bool sign_file(ykpiv_state *state, const char *input, const char *output, if(verbosity) { fprintf(stderr, "file hashed as: "); - dump_hex(hashed, hash_len, stderr, true); + dump_data(hashed, hash_len, stderr, true, format_arg_hex); } EVP_MD_CTX_destroy(mdctx); } @@ -1176,7 +1176,7 @@ static bool sign_file(ykpiv_state *state, const char *input, const char *output, if(verbosity) { fprintf(stderr, "file signed as: "); - dump_hex(buf, len, stderr, true); + dump_data(buf, len, stderr, true, format_arg_hex); } fwrite(buf, 1, len, output_file); ret = true; @@ -1276,7 +1276,7 @@ static void print_cert_info(ykpiv_state *state, enum enum_slot slot, const EVP_M fprintf(output, "\n"); X509_digest(x509, md, data, &md_len); fprintf(output, "\tFingerprint:\t"); - dump_hex(data, md_len, output, false); + dump_data(data, md_len, output, false, format_arg_hex); bio = BIO_new_fp(output, BIO_NOCLOSE | BIO_FP_TEXT); not_before = X509_get_notBefore(x509); @@ -1325,7 +1325,7 @@ static bool status(ykpiv_state *state, enum enum_hash hash, if(ykpiv_fetch_object(state, YKPIV_OBJ_CHUID, chuid, &len) != YKPIV_OK) { fprintf(output_file, "No data available\n"); } else { - dump_hex(chuid, len, output_file, false); + dump_data(chuid, len, output_file, false, format_arg_hex); } if (slot == slot__NULL) @@ -1405,7 +1405,7 @@ static bool test_signature(ykpiv_state *state, enum enum_slot slot, EVP_DigestFinal_ex(mdctx, data, &data_len); if(verbose) { fprintf(stderr, "Test data hashes as: "); - dump_hex(data, data_len, stderr, true); + dump_data(data, data_len, stderr, true, format_arg_hex); } } @@ -1561,9 +1561,9 @@ static bool test_decipher(ykpiv_state *state, enum enum_slot slot, if(len == sizeof(secret)) { if(verbose) { fprintf(stderr, "Generated nonce: "); - dump_hex(secret, sizeof(secret), stderr, true); + dump_data(secret, sizeof(secret), stderr, true, format_arg_hex); fprintf(stderr, "Decrypted nonce: "); - dump_hex(secret2, sizeof(secret2), stderr, true); + dump_data(secret2, sizeof(secret2), stderr, true, format_arg_hex); } if(memcmp(secret, secret2, sizeof(secret)) == 0) { fprintf(stderr, "Successfully performed RSA decryption!\n"); @@ -1603,9 +1603,9 @@ static bool test_decipher(ykpiv_state *state, enum enum_slot slot, } if(verbose) { fprintf(stderr, "ECDH host generated: "); - dump_hex(secret, len, stderr, true); + dump_data(secret, len, stderr, true, format_arg_hex); fprintf(stderr, "ECDH card generated: "); - dump_hex(secret2, len, stderr, true); + dump_data(secret2, len, stderr, true, format_arg_hex); } if(memcmp(secret, secret2, key_len) == 0) { fprintf(stderr, "Successfully performed ECDH exchange with card.\n"); diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index 23e290d..fa4458e 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -1840,7 +1840,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_Sign)( DBG("Sending %lu bytes to sign", ulDataLen); #if YKCS11_DBG == 1 - dump_hex(pData, ulDataLen, stderr, CK_TRUE); + dump_data(pData, ulDataLen, stderr, CK_TRUE, format_arg_hex); #endif if (is_hashed_mechanism(op_info.mechanism.mechanism) == CK_TRUE) { @@ -1882,7 +1882,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_Sign)( DBG("Using key %lx", op_info.op.sign.key_id); DBG("After padding and transformation there are %lu bytes", op_info.buf_len); #if YKCS11_DBG == 1 - dump_hex(op_info.buf, op_info.buf_len, stderr, CK_TRUE); + dump_data(op_info.buf, op_info.buf_len, stderr, CK_TRUE, format_arg_hex); #endif *pulSignatureLen = sizeof(op_info.buf); @@ -1903,7 +1903,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_Sign)( DBG("Got %lu bytes back", *pulSignatureLen); #if YKCS11_DBG == 1 - dump_hex(pSignature, *pulSignatureLen, stderr, CK_TRUE); + dump_data(pSignature, *pulSignatureLen, stderr, CK_TRUE, format_arg_hex); #endif if (!is_RSA_mechanism(op_info.mechanism.mechanism)) { @@ -1913,7 +1913,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_Sign)( DBG("After removing DER encoding %lu", *pulSignatureLen); #if YKCS11_DBG == 1 - dump_hex(pSignature, *pulSignatureLen, stderr, CK_TRUE); + dump_data(pSignature, *pulSignatureLen, stderr, CK_TRUE, format_arg_hex); #endif } From c89387e8fccbee73c8f76e56a836663cdcb3c369 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Tue, 15 Dec 2015 10:43:29 +0100 Subject: [PATCH 086/107] add libykpiv as a dependency for libpiv_util --- tool/Makefile.am | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/Makefile.am b/tool/Makefile.am index 3a9c760..0aebf99 100644 --- a/tool/Makefile.am +++ b/tool/Makefile.am @@ -41,7 +41,7 @@ libpiv_cmd_la_SOURCES = cmdline.ggo cmdline.c cmdline.h libpiv_cmd_la_CFLAGS = libpiv_util_la_SOURCES = util.c util.h -libpiv_util_la_LIBADD = $(OPENSSL_LIBS) +libpiv_util_la_LIBADD = $(top_builddir)/lib/libykpiv.la $(OPENSSL_LIBS) cmdline.c cmdline.h: cmdline.ggo Makefile.am $(GENGETOPT) --input $^ From e2f8ad21aa13d1860e4e3bfc35284f95a42f0979 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 17 Dec 2015 09:27:20 +0100 Subject: [PATCH 087/107] add a simple test case for the dump/read data functions --- .gitignore | 4 ++++ tool/tests/Makefile.am | 3 ++- tool/tests/test_inout.c | 53 +++++++++++++++++++++++++++++++++++++++++ 3 files changed, 59 insertions(+), 1 deletion(-) create mode 100644 tool/tests/test_inout.c diff --git a/.gitignore b/.gitignore index 8ca8bbd..f9e3e3d 100644 --- a/.gitignore +++ b/.gitignore @@ -73,6 +73,10 @@ tool/tests/parse_name tool/tests/parse_name.log tool/tests/parse_name.o tool/tests/parse_name.trs +tool/tests/test_inout +tool/tests/test_inout.log +tool/tests/test_inout.o +tool/tests/test_inout.trs coverage/ lib/error.gcno lib/version.gcno diff --git a/tool/tests/Makefile.am b/tool/tests/Makefile.am index 7148d1d..7c1ac31 100644 --- a/tool/tests/Makefile.am +++ b/tool/tests/Makefile.am @@ -37,8 +37,9 @@ AM_CPPFLAGS += $(OPENSSL_CFLAGS) AM_LDFLAGS = -no-install parse_name_LDADD = ../libpiv_util.la $(OPENSSL_LIBS) +test_inout_LDADD = ../libpiv_util.la -check_PROGRAMS = parse_name +check_PROGRAMS = parse_name test_inout TESTS = basic.sh $(check_PROGRAMS) if ENABLE_COV diff --git a/tool/tests/test_inout.c b/tool/tests/test_inout.c new file mode 100644 index 0000000..6a62906 --- /dev/null +++ b/tool/tests/test_inout.c @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2015 Yubico AB + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +#include +#include +#include + +#include "util.h" + +static void test_inout(enum enum_format format) { + unsigned char buf[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08}; + unsigned char buf2[sizeof(buf)]; + FILE *tmp = tmpfile(); + + dump_data(buf, sizeof(buf), tmp, false, format); + rewind(tmp); + read_data(buf2, sizeof(buf2), tmp, format); + assert(memcmp(buf, buf2, sizeof(buf)) == 0); +} + +int main(void) { + test_inout(format_arg_base64); + test_inout(format_arg_hex); + test_inout(format_arg_binary); + exit(0); +} From 3f874dd147e1a4d638a53b6d0d38019115eaca52 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 17 Dec 2015 09:54:52 +0100 Subject: [PATCH 088/107] don't use tmpfile(), it's broken on windows --- tool/tests/test_inout.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/tool/tests/test_inout.c b/tool/tests/test_inout.c index 6a62906..4e05679 100644 --- a/tool/tests/test_inout.c +++ b/tool/tests/test_inout.c @@ -35,14 +35,18 @@ #include "util.h" static void test_inout(enum enum_format format) { - unsigned char buf[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08}; + const unsigned char buf[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08}; unsigned char buf2[sizeof(buf)]; - FILE *tmp = tmpfile(); + char filename[] = "/tmp/pivtool_test_XXXXXX"; + int fd = mkstemp(filename); + FILE *tmp = fdopen(fd, "r+"); dump_data(buf, sizeof(buf), tmp, false, format); rewind(tmp); read_data(buf2, sizeof(buf2), tmp, format); assert(memcmp(buf, buf2, sizeof(buf)) == 0); + fclose(tmp); + remove(filename); } int main(void) { From 73585f241643ebb4ddfe1fd79386563d030a34db Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 17 Dec 2015 09:55:20 +0100 Subject: [PATCH 089/107] use unsigned long for len --- tool/yubico-piv-tool.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 9ee73ee..3410134 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1688,7 +1688,7 @@ static bool read_object(ykpiv_state *state, int id, const char *output_file_name enum enum_format format) { FILE *output_file = NULL; unsigned char data[3072]; - size_t len = sizeof(data); + unsigned long len = sizeof(data); bool ret = false; output_file = open_file(output_file_name, OUTPUT); From d8bda22cdd9659d583269432df61c9788326d698 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 17 Dec 2015 10:18:01 +0100 Subject: [PATCH 090/107] rework inout test to use pipes for emulating files --- tool/tests/test_inout.c | 22 ++++++++++++++-------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/tool/tests/test_inout.c b/tool/tests/test_inout.c index 4e05679..50a5ed2 100644 --- a/tool/tests/test_inout.c +++ b/tool/tests/test_inout.c @@ -31,22 +31,28 @@ #include #include #include +#include #include "util.h" +#ifdef _WIN32 +#define pipe(fds) _pipe(fds,4096, 0) +#endif + static void test_inout(enum enum_format format) { const unsigned char buf[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08}; unsigned char buf2[sizeof(buf)]; - char filename[] = "/tmp/pivtool_test_XXXXXX"; - int fd = mkstemp(filename); - FILE *tmp = fdopen(fd, "r+"); + int pipefd[2]; + FILE *tmp1, *tmp2; - dump_data(buf, sizeof(buf), tmp, false, format); - rewind(tmp); - read_data(buf2, sizeof(buf2), tmp, format); + assert(pipe(pipefd) == 0); + tmp1 = fdopen(pipefd[1], "w"); + dump_data(buf, sizeof(buf), tmp1, false, format); + fclose(tmp1); + tmp2 = fdopen(pipefd[0], "r"); + read_data(buf2, sizeof(buf2), tmp2, format); assert(memcmp(buf, buf2, sizeof(buf)) == 0); - fclose(tmp); - remove(filename); + fclose(tmp2); } int main(void) { From ab68b53b5c525a11e57f278661edff1976c70108 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Thu, 17 Dec 2015 13:26:53 +0100 Subject: [PATCH 091/107] rework dump_data() to keep an internal buffer and only fprintf() once --- tool/util.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/tool/util.c b/tool/util.c index aeb40c2..9e3b675 100644 --- a/tool/util.c +++ b/tool/util.c @@ -192,11 +192,17 @@ void dump_data(const unsigned char *buf, unsigned int len, FILE *output, bool sp switch(format) { case format_arg_hex: { + char tmp[3072 * 3 + 1]; unsigned int i; - for (i = 0; i < len; i++) { - fprintf(output, "%02x%s", buf[i], space == true ? " " : ""); + int step = 2; + if(space) step += 1; + if(len > 3072) { + return; } - fprintf(output, "\n"); + for (i = 0; i < len; i++) { + sprintf(tmp + i * step, "%02x%s", buf[i], space == true ? " " : ""); + } + fprintf(output, "%s\n", tmp); } return; case format_arg_base64: From ecfc71fab061aad9d11e6f0d94ba35694098fed5 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 24 Dec 2015 10:50:05 +0100 Subject: [PATCH 092/107] Print CCC with status action. Relates to #57. --- tool/yubico-piv-tool.c | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 3410134..0d266f5 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1308,8 +1308,8 @@ static bool status(ykpiv_state *state, enum enum_hash hash, enum enum_slot slot, const char *output_file_name) { const EVP_MD *md; - unsigned char chuid[3072]; - long unsigned len = sizeof(chuid); + unsigned char buf[3072]; + long unsigned len = sizeof(buf); int i; FILE *output_file = open_file(output_file_name, OUTPUT); if(!output_file) { @@ -1322,10 +1322,18 @@ static bool status(ykpiv_state *state, enum enum_hash hash, } fprintf(output_file, "CHUID:\t"); - if(ykpiv_fetch_object(state, YKPIV_OBJ_CHUID, chuid, &len) != YKPIV_OK) { + if(ykpiv_fetch_object(state, YKPIV_OBJ_CHUID, buf, &len) != YKPIV_OK) { fprintf(output_file, "No data available\n"); } else { - dump_data(chuid, len, output_file, false, format_arg_hex); + dump_data(buf, len, output_file, false, format_arg_hex); + } + + len = sizeof(buf); + fprintf(output_file, "CCC:\t"); + if(ykpiv_fetch_object(state, YKPIV_OBJ_CAPABILITY, buf, &len) != YKPIV_OK) { + fprintf(output_file, "No data available\n"); + } else { + dump_data(buf, len, output_file, false, format_arg_hex); } if (slot == slot__NULL) From b08de955970c5cd544c740990fb68f496fedb814 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Thu, 24 Dec 2015 10:50:36 +0100 Subject: [PATCH 093/107] Remove some clutter. --- tool/yubico-piv-tool.c | 6 ------ 1 file changed, 6 deletions(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 0d266f5..ae048e2 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -1342,12 +1342,6 @@ static bool status(ykpiv_state *state, enum enum_hash hash, } else print_cert_info(state, slot, md, output_file); - /*fprintf(output_file, "Slot 9c:\t"); - print_cert_info(state, slot_arg_9c, md, output_file); - fprintf(output_file, "Slot 9d:\t"); - print_cert_info(state, slot_arg_9d, md, output_file); - fprintf(output_file, "Slot 9e:\t"); - print_cert_info(state, slot_arg_9e, md, output_file);*/ { int tries; From 8d29845b51c7768ab77157f2a9818eb1acf4cbeb Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Mon, 11 Jan 2016 12:44:43 +0100 Subject: [PATCH 094/107] Remove unnecessary fields from ykpiv_state. --- lib/internal.h | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/lib/internal.h b/lib/internal.h index 4ceafc3..4395347 100644 --- a/lib/internal.h +++ b/lib/internal.h @@ -46,12 +46,9 @@ #define MAX_READERS 16 struct ykpiv_state { - SCARDCONTEXT context; - SCARDHANDLE card; - unsigned long n_readers; - char readers[MAX_READERS][READER_LEN]; - unsigned long tot_readers_len; - int verbose; + SCARDCONTEXT context; + SCARDHANDLE card; + int verbose; }; union u_APDU { From 018821e99df04c9511b7962a54b2db355050706b Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Mon, 11 Jan 2016 12:45:09 +0100 Subject: [PATCH 095/107] Addresses #59, ykcs11 still has issues on Win64. --- ykcs11/pkcs11.h | 8 ++++++++ ykcs11/pkcs11t.h | 12 ++++++++---- 2 files changed, 16 insertions(+), 4 deletions(-) diff --git a/ykcs11/pkcs11.h b/ykcs11/pkcs11.h index 3d7e166..53b8df4 100644 --- a/ykcs11/pkcs11.h +++ b/ykcs11/pkcs11.h @@ -239,6 +239,9 @@ extern "C" { #define __PASTE(x,y) x##y +#if defined _WIN32 || _WIN64 +#pragma pack(push, cryptoki, 1) +#endif /* packing defines */ //#include "pkcs11p.h" // TODO: msc specific? @@ -309,6 +312,11 @@ struct CK_FUNCTION_LIST { /* unpack */ //#include "pkcs11u.h" // TODO: msc specific? +#if defined _WIN32 || _WIN64 +#pragma pack(pop, cryptoki) +#endif + + #ifdef __cplusplus } #endif diff --git a/ykcs11/pkcs11t.h b/ykcs11/pkcs11t.h index 4e0569c..e24b372 100644 --- a/ykcs11/pkcs11t.h +++ b/ykcs11/pkcs11t.h @@ -108,7 +108,9 @@ typedef CK_VOID_PTR CK_PTR CK_VOID_PTR_PTR; /* pack */ -//#include "pkcs11p.h" // TODO: msc specific? +#if defined _WIN32 || _WIN64 +#pragma pack(push, cryptoki, 1) +#endif typedef struct CK_VERSION { CK_BYTE major; /* integer portion of version number */ @@ -1182,9 +1184,6 @@ typedef CK_EXTRACT_PARAMS CK_PTR CK_EXTRACT_PARAMS_PTR; #define CKA_NETSCAPE_DB 0xD5A0DB00UL #define CKA_NETSCAPE_TRUST 0x80000001UL -/* undo packing */ -//#include "pkcs11u.h" // TODO: msc specific? - // YUBICO specific attributes #define CKA_TOUCH_PIN_DEFAULT 0x00000000U #define CKA_TOUCH_ALWAYS 0x00000001U @@ -1193,4 +1192,9 @@ typedef CK_EXTRACT_PARAMS CK_PTR CK_EXTRACT_PARAMS_PTR; #define CKA_PIN_NEVER 0x00000008U #define CKA_TOUCH_NEVER 0x00000016U +/* undo packing */ +#if defined _WIN32 || _WIN64 +#pragma pack(pop, cryptoki) +#endif + #endif From 58766ac403590f26763d651c36c7318ad3808f30 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Mon, 11 Jan 2016 12:49:15 +0100 Subject: [PATCH 096/107] Whitespace fix. --- ykcs11/pkcs11t.h | 32 ++++++++++++++++---------------- 1 file changed, 16 insertions(+), 16 deletions(-) diff --git a/ykcs11/pkcs11t.h b/ykcs11/pkcs11t.h index e24b372..92d7678 100644 --- a/ykcs11/pkcs11t.h +++ b/ykcs11/pkcs11t.h @@ -1165,24 +1165,24 @@ typedef CK_EXTRACT_PARAMS CK_PTR CK_EXTRACT_PARAMS_PTR; * PKCS #11 interface. Most of these are place holders for other mechanism * and will change in the future. */ -#define CKM_NETSCAPE_PBE_KEY_GEN 0x80000001UL -#define CKM_NETSCAPE_PBE_SHA1_DES_CBC 0x80000002UL -#define CKM_NETSCAPE_PBE_SHA1_TRIPLE_DES_CBC 0x80000003UL -#define CKM_NETSCAPE_PBE_SHA1_40_BIT_RC2_CBC 0x80000004UL -#define CKM_NETSCAPE_PBE_SHA1_128_BIT_RC2_CBC 0x80000005UL -#define CKM_NETSCAPE_PBE_SHA1_40_BIT_RC4 0x80000006UL -#define CKM_NETSCAPE_PBE_SHA1_128_BIT_RC4 0x80000007UL -#define CKM_NETSCAPE_PBE_SHA1_FAULTY_3DES_CBC 0x80000008UL -#define CKM_NETSCAPE_PBE_SHA1_HMAC_KEY_GEN 0x80000009UL -#define CKM_NETSCAPE_PBE_MD5_HMAC_KEY_GEN 0x8000000aUL -#define CKM_NETSCAPE_PBE_MD2_HMAC_KEY_GEN 0x8000000bUL -#define CKM_TLS_MASTER_KEY_DERIVE 0x80000371UL -#define CKM_TLS_KEY_AND_MAC_DERIVE 0x80000372UL -#define CKM_TLS_PRF_GENERAL 0x80000373UL +#define CKM_NETSCAPE_PBE_KEY_GEN 0x80000001UL +#define CKM_NETSCAPE_PBE_SHA1_DES_CBC 0x80000002UL +#define CKM_NETSCAPE_PBE_SHA1_TRIPLE_DES_CBC 0x80000003UL +#define CKM_NETSCAPE_PBE_SHA1_40_BIT_RC2_CBC 0x80000004UL +#define CKM_NETSCAPE_PBE_SHA1_128_BIT_RC2_CBC 0x80000005UL +#define CKM_NETSCAPE_PBE_SHA1_40_BIT_RC4 0x80000006UL +#define CKM_NETSCAPE_PBE_SHA1_128_BIT_RC4 0x80000007UL +#define CKM_NETSCAPE_PBE_SHA1_FAULTY_3DES_CBC 0x80000008UL +#define CKM_NETSCAPE_PBE_SHA1_HMAC_KEY_GEN 0x80000009UL +#define CKM_NETSCAPE_PBE_MD5_HMAC_KEY_GEN 0x8000000aUL +#define CKM_NETSCAPE_PBE_MD2_HMAC_KEY_GEN 0x8000000bUL +#define CKM_TLS_MASTER_KEY_DERIVE 0x80000371UL +#define CKM_TLS_KEY_AND_MAC_DERIVE 0x80000372UL +#define CKM_TLS_PRF_GENERAL 0x80000373UL /* define used to pass in the database key for DSA private keys */ -#define CKA_NETSCAPE_DB 0xD5A0DB00UL -#define CKA_NETSCAPE_TRUST 0x80000001UL +#define CKA_NETSCAPE_DB 0xD5A0DB00UL +#define CKA_NETSCAPE_TRUST 0x80000001UL // YUBICO specific attributes #define CKA_TOUCH_PIN_DEFAULT 0x00000000U From 39f5dbd11950250e76dea68226cde6f0b1fd6918 Mon Sep 17 00:00:00 2001 From: Alessio Di Mauro Date: Mon, 11 Jan 2016 12:49:58 +0100 Subject: [PATCH 097/107] Typo. --- lib/ykpiv.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ykpiv.c b/lib/ykpiv.c index 25ebb5d..1a76965 100644 --- a/lib/ykpiv.c +++ b/lib/ykpiv.c @@ -258,7 +258,7 @@ ykpiv_rc ykpiv_transfer_data(ykpiv_state *state, const unsigned char *templ, rc = SCardBeginTransaction(state->card); if(rc != SCARD_S_SUCCESS) { if(state->verbose) { - fprintf(stderr, "error: Failed to being pcsc transaction, rc=%08lx\n", rc); + fprintf(stderr, "error: Failed to begin pcsc transaction, rc=%08lx\n", rc); } return YKPIV_PCSC_ERROR; } From 47cb761a7e2646bbd38c05e7306b39728e960715 Mon Sep 17 00:00:00 2001 From: Mikhail Denisenko Date: Wed, 13 Jan 2016 17:33:39 -0500 Subject: [PATCH 098/107] Fix bugs windows --- ykcs11/utils.c | 2 +- ykcs11/ykcs11.c | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/ykcs11/utils.c b/ykcs11/utils.c index 11968eb..7053456 100644 --- a/ykcs11/utils.c +++ b/ykcs11/utils.c @@ -76,7 +76,7 @@ CK_RV parse_readers(ykpiv_state *state, const CK_BYTE_PTR readers, const CK_ULON } } (*n_slots)++; - p += i + 1; + p = readers + i + 1; } return CKR_OK; diff --git a/ykcs11/ykcs11.c b/ykcs11/ykcs11.c index b710ca7..19fd60b 100644 --- a/ykcs11/ykcs11.c +++ b/ykcs11/ykcs11.c @@ -51,7 +51,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_Initialize)( ) { CK_BYTE readers[2048]; - CK_ULONG len = sizeof(readers); + size_t len = sizeof(readers); DIN; @@ -536,6 +536,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_OpenSession)( session.info.state = CKS_RO_PUBLIC_SESSION; // Nobody has logged in, default RW session } + session.info.slotID = slotID; session.info.flags = flags; session.info.ulDeviceError = 0; From 98f843e7e7fb698b1aea919b9d490504a5fd24ca Mon Sep 17 00:00:00 2001 From: Matt Moyer Date: Wed, 10 Feb 2016 17:30:05 -0600 Subject: [PATCH 099/107] Add a --valid-days parameter to yubico-piv-tool. Allows the expiration date (notAfter) value of self signed certificates to be configured. --- tool/cmdline.ggo | 1 + tool/yubico-piv-tool.c | 6 +++--- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/tool/cmdline.ggo b/tool/cmdline.ggo index 03e61c9..30dc8c6 100644 --- a/tool/cmdline.ggo +++ b/tool/cmdline.ggo @@ -57,6 +57,7 @@ option "subject" S "The subject to use for certificate request" string optional text " The subject must be written as: /CN=host.example.com/OU=test/O=example.com/\n" +option "valid-days" - "Time (in days) until the self-signed certificate expires" int optional default="365" option "pin" P "Pin/puk code for verification" string optional option "new-pin" N "New pin/puk code for changing" string optional dependon="pin" option "pin-policy" - "Set pin policy for action generate or import-key" values="never","once","always" enum optional diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index ae048e2..2e471ec 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -781,7 +781,7 @@ request_out: static bool selfsign_certificate(ykpiv_state *state, enum enum_key_format key_format, const char *input_file_name, const char *slot, char *subject, enum enum_hash hash, - const char *output_file_name) { + const int validDays, const char *output_file_name) { FILE *input_file = NULL; FILE *output_file = NULL; bool ret = false; @@ -855,7 +855,7 @@ static bool selfsign_certificate(ykpiv_state *state, enum enum_key_format key_fo fprintf(stderr, "Failed to set certificate notBefore.\n"); goto selfsign_out; } - if(!X509_gmtime_adj(X509_get_notAfter(x509), 31536000L)) { + if(!X509_gmtime_adj(X509_get_notAfter(x509), 60L * 60L * 24L * validDays)) { fprintf(stderr, "Failed to set certificate notAfter.\n"); goto selfsign_out; } @@ -1986,7 +1986,7 @@ int main(int argc, char *argv[]) { case action_arg_selfsignMINUS_certificate: if(selfsign_certificate(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_orig, args_info.subject_arg, args_info.hash_arg, - args_info.output_arg) == false) { + args_info.valid_days_arg, args_info.output_arg) == false) { ret = EXIT_FAILURE; } else { fprintf(stderr, "Successfully generated a new self signed certificate.\n"); From f91cf3379a8062b37254c544681fcb762c4267e1 Mon Sep 17 00:00:00 2001 From: Matt Moyer Date: Wed, 10 Feb 2016 17:40:12 -0600 Subject: [PATCH 100/107] Add a --serial parameter to yubico-piv-tool. Allows the serial number of self signed certificates to be configured. --- tool/cmdline.ggo | 1 + tool/yubico-piv-tool.c | 7 ++++--- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/tool/cmdline.ggo b/tool/cmdline.ggo index 30dc8c6..a8f618f 100644 --- a/tool/cmdline.ggo +++ b/tool/cmdline.ggo @@ -57,6 +57,7 @@ option "subject" S "The subject to use for certificate request" string optional text " The subject must be written as: /CN=host.example.com/OU=test/O=example.com/\n" +option "serial" - "Serial number of the self-signed certificate" int optional default="1" option "valid-days" - "Time (in days) until the self-signed certificate expires" int optional default="365" option "pin" P "Pin/puk code for verification" string optional option "new-pin" N "New pin/puk code for changing" string optional dependon="pin" diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 2e471ec..4917763 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -781,7 +781,7 @@ request_out: static bool selfsign_certificate(ykpiv_state *state, enum enum_key_format key_format, const char *input_file_name, const char *slot, char *subject, enum enum_hash hash, - const int validDays, const char *output_file_name) { + const int serial, const int validDays, const char *output_file_name) { FILE *input_file = NULL; FILE *output_file = NULL; bool ret = false; @@ -847,7 +847,7 @@ static bool selfsign_certificate(ykpiv_state *state, enum enum_key_format key_fo fprintf(stderr, "Failed to set the certificate public key.\n"); goto selfsign_out; } - if(!ASN1_INTEGER_set(X509_get_serialNumber(x509), 1)) { + if(!ASN1_INTEGER_set(X509_get_serialNumber(x509), serial)) { fprintf(stderr, "Failed to set certificate serial.\n"); goto selfsign_out; } @@ -1986,7 +1986,8 @@ int main(int argc, char *argv[]) { case action_arg_selfsignMINUS_certificate: if(selfsign_certificate(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_orig, args_info.subject_arg, args_info.hash_arg, - args_info.valid_days_arg, args_info.output_arg) == false) { + args_info.serial_arg, args_info.valid_days_arg, + args_info.output_arg) == false) { ret = EXIT_FAILURE; } else { fprintf(stderr, "Successfully generated a new self signed certificate.\n"); From d39b697d49b10b0eb0227003ec346ff8206286a2 Mon Sep 17 00:00:00 2001 From: Matt Moyer Date: Fri, 12 Feb 2016 09:01:12 -0600 Subject: [PATCH 101/107] Drop const from these these int parameters. --- tool/yubico-piv-tool.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index 4917763..d8ce0b1 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -781,7 +781,7 @@ request_out: static bool selfsign_certificate(ykpiv_state *state, enum enum_key_format key_format, const char *input_file_name, const char *slot, char *subject, enum enum_hash hash, - const int serial, const int validDays, const char *output_file_name) { + int serial, int validDays, const char *output_file_name) { FILE *input_file = NULL; FILE *output_file = NULL; bool ret = false; From a233ff53aebcb577e3ad3c11567100181d8a6c38 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 15 Feb 2016 08:42:35 +0100 Subject: [PATCH 102/107] if the password supplied for PKCS12 doesn't verify ask for a new one or if it's NULL and the mac doesn't verify with that either.. fixes #66 --- tool/yubico-piv-tool.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index ae048e2..75aa669 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -355,11 +355,19 @@ static bool import_key(ykpiv_state *state, enum enum_key_format key_format, goto import_out; } } else if(key_format == key_format_arg_PKCS12) { + char pwbuf[128]; p12 = d2i_PKCS12_fp(input_file, NULL); if(!p12) { fprintf(stderr, "Failed to load PKCS12 from file.\n"); goto import_out; } + if(!PKCS12_verify_mac(p12, password, password ? strlen(password) : 0)) { + if(!read_pw("PKCS12 Password", pwbuf, sizeof(pwbuf), false)) { + fprintf(stderr, "Failed to get password.\n"); + return false; + } + password = pwbuf; + } if(PKCS12_parse(p12, password, &private_key, &cert, NULL) == 0) { fprintf(stderr, "Failed to parse PKCS12 structure. (wrong password?)\n"); goto import_out; From 53667a22b0a9b31943232f726a5976e0d5d239a3 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 15 Feb 2016 08:59:39 +0100 Subject: [PATCH 103/107] Move asking for PKCS12 password outside of import_key() also restructure a bit when deciding to do authentication relates #66 --- tool/yubico-piv-tool.c | 95 +++++++++++++++++++++++------------------- 1 file changed, 52 insertions(+), 43 deletions(-) diff --git a/tool/yubico-piv-tool.c b/tool/yubico-piv-tool.c index e8b90d0..a151782 100644 --- a/tool/yubico-piv-tool.c +++ b/tool/yubico-piv-tool.c @@ -355,19 +355,11 @@ static bool import_key(ykpiv_state *state, enum enum_key_format key_format, goto import_out; } } else if(key_format == key_format_arg_PKCS12) { - char pwbuf[128]; p12 = d2i_PKCS12_fp(input_file, NULL); if(!p12) { fprintf(stderr, "Failed to load PKCS12 from file.\n"); goto import_out; } - if(!PKCS12_verify_mac(p12, password, password ? strlen(password) : 0)) { - if(!read_pw("PKCS12 Password", pwbuf, sizeof(pwbuf), false)) { - fprintf(stderr, "Failed to get password.\n"); - return false; - } - password = pwbuf; - } if(PKCS12_parse(p12, password, &private_key, &cert, NULL) == 0) { fprintf(stderr, "Failed to parse PKCS12 structure. (wrong password?)\n"); goto import_out; @@ -1728,12 +1720,16 @@ int main(int argc, char *argv[]) { enum enum_action action; unsigned int i; int ret = EXIT_SUCCESS; + bool authed = false; + char pwbuf[128]; + char *password; if(cmdline_parser(argc, argv, &args_info) != 0) { return EXIT_FAILURE; } verbosity = args_info.verbose_arg + (int)args_info.verbose_given; + password = args_info.password_arg; for(i = 0; i < args_info.action_given; i++) { action = *(args_info.action_arg + i); @@ -1801,22 +1797,60 @@ int main(int argc, char *argv[]) { } for(i = 0; i < args_info.action_given; i++) { - bool needs_auth = false; action = *(args_info.action_arg + i); switch(action) { + case action_arg_importMINUS_key: + case action_arg_importMINUS_certificate: + if(args_info.key_format_arg == key_format_arg_PKCS12 && !password) { + if(verbosity) { + fprintf(stderr, "Asking for password since '%s' needs it.\n", cmdline_parser_action_values[action]); + } + if(!read_pw("Password", pwbuf, sizeof(pwbuf), false)) { + fprintf(stderr, "Failed to get password.\n"); + return false; + } + password = pwbuf; + } case action_arg_generate: case action_arg_setMINUS_mgmMINUS_key: case action_arg_pinMINUS_retries: - case action_arg_importMINUS_key: - case action_arg_importMINUS_certificate: case action_arg_setMINUS_chuid: case action_arg_setMINUS_ccc: case action_arg_deleteMINUS_certificate: case action_arg_writeMINUS_object: - if(verbosity) { - fprintf(stderr, "Authenticating since action '%s' needs that.\n", cmdline_parser_action_values[action]); + if(!authed) { + unsigned char key[KEY_LEN]; + size_t key_len = sizeof(key); + char keybuf[KEY_LEN*2+1]; + char *key_ptr = args_info.key_arg; + if(verbosity) { + fprintf(stderr, "Authenticating since action '%s' needs that.\n", cmdline_parser_action_values[action]); + } + if(args_info.key_given && args_info.key_orig == NULL) { + if(!read_pw("management key", keybuf, sizeof(keybuf), false)) { + fprintf(stderr, "Failed to read management key from stdin,\n"); + return EXIT_FAILURE; + } + key_ptr = keybuf; + } + if(ykpiv_hex_decode(key_ptr, strlen(key_ptr), key, &key_len) != YKPIV_OK) { + fprintf(stderr, "Failed decoding key!\n"); + return EXIT_FAILURE; + } + + if(ykpiv_authenticate(state, key) != YKPIV_OK) { + fprintf(stderr, "Failed authentication with the application.\n"); + return EXIT_FAILURE; + } + if(verbosity) { + fprintf(stderr, "Successful application authentication.\n"); + } + authed = true; + } else { + if(verbosity) { + fprintf(stderr, "Skipping authentication for '%s' since it's already done.\n", cmdline_parser_action_values[action]); + } } - needs_auth = true; break; case action_arg_version: case action_arg_reset: @@ -1837,39 +1871,14 @@ int main(int argc, char *argv[]) { if(verbosity) { fprintf(stderr, "Action '%s' does not need authentication.\n", cmdline_parser_action_values[action]); } - continue; - } - if(needs_auth) { - unsigned char key[KEY_LEN]; - size_t key_len = sizeof(key); - char keybuf[KEY_LEN*2+1]; - char *key_ptr = args_info.key_arg; - if(args_info.key_given && args_info.key_orig == NULL) { - if(!read_pw("management key", keybuf, sizeof(keybuf), false)) { - fprintf(stderr, "Failed to read management key from stdin,\n"); - return EXIT_FAILURE; - } - key_ptr = keybuf; - } - if(ykpiv_hex_decode(key_ptr, strlen(key_ptr), key, &key_len) != YKPIV_OK) { - fprintf(stderr, "Failed decoding key!\n"); - return EXIT_FAILURE; - } - - if(ykpiv_authenticate(state, key) != YKPIV_OK) { - fprintf(stderr, "Failed authentication with the application.\n"); - return EXIT_FAILURE; - } - if(verbosity) { - fprintf(stderr, "Successful application authentication.\n"); - } - break; } } + /* openssl setup.. */ OpenSSL_add_all_algorithms(); + for(i = 0; i < args_info.action_given; i++) { char new_keybuf[KEY_LEN*2+1] = {0}; char *new_mgm_key = args_info.new_key_arg; @@ -1938,7 +1947,7 @@ int main(int argc, char *argv[]) { } break; case action_arg_importMINUS_key: - if(import_key(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_orig, args_info.password_arg, + if(import_key(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_orig, password, args_info.pin_policy_arg, args_info.touch_policy_arg) == false) { fprintf(stderr, "Unable to import private key\n"); ret = EXIT_FAILURE; @@ -1947,7 +1956,7 @@ int main(int argc, char *argv[]) { } break; case action_arg_importMINUS_certificate: - if(import_cert(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_arg, args_info.password_arg) == false) { + if(import_cert(state, args_info.key_format_arg, args_info.input_arg, args_info.slot_arg, password) == false) { ret = EXIT_FAILURE; } else { fprintf(stderr, "Successfully imported a new certificate.\n"); From 90f23029e1cb817ceb201567d6a7874fa9f60fb5 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Mon, 15 Feb 2016 09:29:05 +0100 Subject: [PATCH 104/107] make step unsigned in dump_data() since it's muliplied with another unsigned int --- tool/util.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tool/util.c b/tool/util.c index 9e3b675..700b5e5 100644 --- a/tool/util.c +++ b/tool/util.c @@ -194,7 +194,7 @@ void dump_data(const unsigned char *buf, unsigned int len, FILE *output, bool sp { char tmp[3072 * 3 + 1]; unsigned int i; - int step = 2; + unsigned int step = 2; if(space) step += 1; if(len > 3072) { return; From d6014ce575140f841402323365c5b350092fab22 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Fri, 19 Feb 2016 12:30:13 +0100 Subject: [PATCH 105/107] NEWS for 1.3.0 --- NEWS | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/NEWS b/NEWS index fdf94b2..54972ba 100644 --- a/NEWS +++ b/NEWS @@ -1,6 +1,23 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- -* Version 1.3.0 (unreleased) +* Version 1.3.0 (released 2016-02-19) + +** Fixed extraction of RSA modulus and exponent for pkcs11. + +** Implemented C_SetPIN for pkcs11. + +** Add generic write and read object actions for the tool. +Supports hex/binary/base64 formats + +** Add ykpiv_change_pin(), ykpiv_change_puk() and ykpiv_unblock_pin() + +** Print CCC with status action. + +** Address bugs with pkcs11 on windows. + +** Add --valid-days and --serial to tool for selfsign-certificate action. + +** Ask for password for pkcs12 if none is given. * Version 1.2.2 (released 2015-12-08) From f51c42f2d88552779481e382d7b7937c376709d3 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Fri, 19 Feb 2016 12:40:18 +0100 Subject: [PATCH 106/107] bump version to 1.3.1 --- NEWS | 2 ++ configure.ac | 4 ++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/NEWS b/NEWS index 54972ba..d52ed2f 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,7 @@ yubico-piv-tool NEWS -- History of user-visible changes. -*- outline -*- +* Version 1.3.1 (unreleased) + * Version 1.3.0 (released 2016-02-19) ** Fixed extraction of RSA modulus and exponent for pkcs11. diff --git a/configure.ac b/configure.ac index 29a8b19..52795cc 100644 --- a/configure.ac +++ b/configure.ac @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -AC_INIT([yubico-piv-tool], [1.3.0]) +AC_INIT([yubico-piv-tool], [1.3.1]) AC_CONFIG_AUX_DIR([build-aux]) AC_CONFIG_MACRO_DIR([m4]) @@ -35,7 +35,7 @@ AC_CONFIG_MACRO_DIR([m4]) # Interfaces added: AGE++ # Interfaces removed: AGE=0 AC_SUBST([LT_CURRENT], 4) -AC_SUBST([LT_REVISION], 0) +AC_SUBST([LT_REVISION], 1) AC_SUBST([LT_AGE], 3) AM_INIT_AUTOMAKE([-Wall -Werror foreign]) From d52b8bd3efb179f20b5ee5f3bc36c05a6ec29fc7 Mon Sep 17 00:00:00 2001 From: Klas Lindfors Date: Fri, 19 Feb 2016 12:40:23 +0100 Subject: [PATCH 107/107] bump openssl to 1.0.1r --- mac.mk | 2 +- windows.mk | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/mac.mk b/mac.mk index 49f853f..7e99eb4 100644 --- a/mac.mk +++ b/mac.mk @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. PACKAGE=yubico-piv-tool -OPENSSLVERSION=1.0.1q +OPENSSLVERSION=1.0.1r CFLAGS="-mmacosx-version-min=10.6" all: usage mac diff --git a/windows.mk b/windows.mk index 56ad45f..9612f98 100644 --- a/windows.mk +++ b/windows.mk @@ -26,7 +26,7 @@ # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. PACKAGE=yubico-piv-tool -OPENSSLVERSION=1.0.1q +OPENSSLVERSION=1.0.1r all: usage 32bit 64bit