YKCS11: added support for touch and PIN policy during generate.
This commit is contained in:
+6
-2
@@ -420,7 +420,7 @@ CK_RV check_pubkey_template(op_info_t *op_info, CK_ATTRIBUTE_PTR templ, CK_ULONG
|
|||||||
|
|
||||||
default:
|
default:
|
||||||
DBG(("Invalid attribute %lx in public key template", templ[i].type));
|
DBG(("Invalid attribute %lx in public key template", templ[i].type));
|
||||||
return CKR_ATTRIBUTE_VALUE_INVALID;
|
return CKR_ATTRIBUTE_TYPE_INVALID;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -433,6 +433,7 @@ CK_RV check_pvtkey_template(op_info_t *op_info, CK_ATTRIBUTE_PTR templ, CK_ULONG
|
|||||||
CK_ULONG i;
|
CK_ULONG i;
|
||||||
|
|
||||||
op_info->op.gen.rsa = is_RSA_mechanism(op_info->mechanism.mechanism);
|
op_info->op.gen.rsa = is_RSA_mechanism(op_info->mechanism.mechanism);
|
||||||
|
op_info->op.gen.vendor_defined = 0;
|
||||||
|
|
||||||
for (i = 0; i < n; i++) {
|
for (i = 0; i < n; i++) {
|
||||||
switch (templ[i].type) {
|
switch (templ[i].type) {
|
||||||
@@ -473,6 +474,9 @@ CK_RV check_pvtkey_template(op_info_t *op_info, CK_ATTRIBUTE_PTR templ, CK_ULONG
|
|||||||
op_info->op.gen.key_id = PIV_PVTK_OBJ_PIV_AUTH + *((CK_BYTE_PTR)templ[i].pValue);
|
op_info->op.gen.key_id = PIV_PVTK_OBJ_PIV_AUTH + *((CK_BYTE_PTR)templ[i].pValue);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case CKA_VENDOR_DEFINED:
|
||||||
|
op_info->op.gen.vendor_defined = (*((CK_ULONG_PTR)templ[i].pValue));
|
||||||
|
|
||||||
case CKA_SENSITIVE:
|
case CKA_SENSITIVE:
|
||||||
case CKA_DECRYPT:
|
case CKA_DECRYPT:
|
||||||
case CKA_UNWRAP:
|
case CKA_UNWRAP:
|
||||||
@@ -485,7 +489,7 @@ CK_RV check_pvtkey_template(op_info_t *op_info, CK_ATTRIBUTE_PTR templ, CK_ULONG
|
|||||||
|
|
||||||
default:
|
default:
|
||||||
DBG(("Invalid attribute %lx in private key template", templ[i].type));
|
DBG(("Invalid attribute %lx in private key template", templ[i].type));
|
||||||
return CKR_ATTRIBUTE_VALUE_INVALID;
|
return CKR_ATTRIBUTE_TYPE_INVALID;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+34
-10
@@ -31,9 +31,11 @@ static CK_RV COMMON_token_login(ykpiv_state *state, CK_USER_TYPE user, CK_UTF8CH
|
|||||||
return CKR_OK;
|
return CKR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, CK_BYTE key, CK_ULONG key_len) {
|
static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa,
|
||||||
|
CK_BYTE key, CK_ULONG key_len, CK_ULONG vendor_defined) {
|
||||||
// TODO: make a function in ykpiv for this
|
// TODO: make a function in ykpiv for this
|
||||||
unsigned char in_data[5];
|
unsigned char in_data[11];
|
||||||
|
unsigned char *in_ptr = in_data;
|
||||||
unsigned char data[1024];
|
unsigned char data[1024];
|
||||||
unsigned char templ[] = {0, YKPIV_INS_GENERATE_ASYMMERTRIC, 0, 0};
|
unsigned char templ[] = {0, YKPIV_INS_GENERATE_ASYMMERTRIC, 0, 0};
|
||||||
unsigned char *certptr;
|
unsigned char *certptr;
|
||||||
@@ -45,10 +47,10 @@ static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, CK_BYTE
|
|||||||
|
|
||||||
templ[3] = key;
|
templ[3] = key;
|
||||||
|
|
||||||
in_data[0] = 0xac;
|
*in_ptr++ = 0xac;
|
||||||
in_data[1] = 3;
|
*in_ptr++ = 3;
|
||||||
in_data[2] = 0x80;
|
*in_ptr++ = 0x80;
|
||||||
in_data[3] = 1;
|
*in_ptr++ = 1;
|
||||||
|
|
||||||
switch(key_len) {
|
switch(key_len) {
|
||||||
case 2048:
|
case 2048:
|
||||||
@@ -61,7 +63,7 @@ static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, CK_BYTE
|
|||||||
|
|
||||||
case 1024:
|
case 1024:
|
||||||
if (rsa == CK_TRUE)
|
if (rsa == CK_TRUE)
|
||||||
in_data[4] = YKPIV_ALGO_RSA1024;
|
*in_ptr++ = YKPIV_ALGO_RSA1024;
|
||||||
else
|
else
|
||||||
return CKR_FUNCTION_FAILED;
|
return CKR_FUNCTION_FAILED;
|
||||||
|
|
||||||
@@ -69,7 +71,7 @@ static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, CK_BYTE
|
|||||||
|
|
||||||
case 256:
|
case 256:
|
||||||
if (rsa == CK_FALSE)
|
if (rsa == CK_FALSE)
|
||||||
in_data[4] = YKPIV_ALGO_ECCP256;
|
*in_ptr++ = YKPIV_ALGO_ECCP256;
|
||||||
else
|
else
|
||||||
return CKR_FUNCTION_FAILED;
|
return CKR_FUNCTION_FAILED;
|
||||||
|
|
||||||
@@ -78,8 +80,30 @@ static CK_RV COMMON_token_generate_key(ykpiv_state *state, CK_BBOOL rsa, CK_BYTE
|
|||||||
default:
|
default:
|
||||||
return CKR_FUNCTION_FAILED;
|
return CKR_FUNCTION_FAILED;
|
||||||
}
|
}
|
||||||
//DBG(("Generating key %x with algorithm %u and length %lu", templ[3], in_data[4], key_len));
|
// PIN policy and touch
|
||||||
if(ykpiv_transfer_data(state, templ, in_data, sizeof(in_data), data, &recv_len, &sw) != YKPIV_OK ||
|
if (vendor_defined != 0) {
|
||||||
|
if (vendor_defined & CKA_PIN_ONCE) {
|
||||||
|
in_data[1] += 3;
|
||||||
|
*in_ptr++ = YKPIV_PINPOLICY_TAG;
|
||||||
|
*in_ptr++ = 0x01;
|
||||||
|
*in_ptr++ = YKPIV_PINPOLICY_ONCE;
|
||||||
|
}
|
||||||
|
else if (vendor_defined & CKA_PIN_ALWAYS) {
|
||||||
|
in_data[1] += 3;
|
||||||
|
*in_ptr++ = YKPIV_PINPOLICY_TAG;
|
||||||
|
*in_ptr++ = 0x01;
|
||||||
|
*in_ptr++ = YKPIV_PINPOLICY_ALWAYS;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (vendor_defined & CKA_TOUCH_ALWAYS) {
|
||||||
|
in_data[1] += 3;
|
||||||
|
*in_ptr++ = YKPIV_TOUCHPOLICY_TAG;
|
||||||
|
*in_ptr++ = 0x01;
|
||||||
|
*in_ptr++ = YKPIV_TOUCHPOLICY_ALWAYS;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(ykpiv_transfer_data(state, templ, in_data, in_ptr - in_data, data, &recv_len, &sw) != YKPIV_OK ||
|
||||||
sw != 0x9000)
|
sw != 0x9000)
|
||||||
return CKR_DEVICE_ERROR;
|
return CKR_DEVICE_ERROR;
|
||||||
|
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ typedef CK_RV (*get_t_raw_certificate_f)(ykpiv_state *, piv_obj_id_t, CK_BYTE_PT
|
|||||||
|
|
||||||
// Common token functions below
|
// Common token functions below
|
||||||
typedef CK_RV (*t_login_f)(ykpiv_state *, CK_USER_TYPE, CK_UTF8CHAR_PTR, CK_ULONG);
|
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);
|
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_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,
|
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);
|
CK_BYTE_PTR, CK_BYTE_PTR, CK_BYTE_PTR, CK_ULONG, CK_ULONG);
|
||||||
|
|||||||
+1
-1
@@ -2053,7 +2053,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_GenerateKeyPair)(
|
|||||||
|
|
||||||
token = get_token_vendor(session.slot->token->vid);
|
token = get_token_vendor(session.slot->token->vid);
|
||||||
|
|
||||||
if ((rv = token.token_generate_key(piv_state, op_info.op.gen.rsa, piv_2_ykpiv(op_info.op.gen.key_id), op_info.op.gen.key_len)) != CKR_OK) {
|
if ((rv = token.token_generate_key(piv_state, op_info.op.gen.rsa, piv_2_ykpiv(op_info.op.gen.key_id), op_info.op.gen.key_len, op_info.op.gen.vendor_defined)) != CKR_OK) {
|
||||||
DBG(("Unable to generate key pair"));
|
DBG(("Unable to generate key pair"));
|
||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|||||||
+4
-4
@@ -28,7 +28,6 @@ typedef struct {
|
|||||||
ykcs11_slot_t *slot;
|
ykcs11_slot_t *slot;
|
||||||
} ykcs11_session_t;
|
} ykcs11_session_t;
|
||||||
|
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
YKCS11_NOOP,
|
YKCS11_NOOP,
|
||||||
YKCS11_GEN,
|
YKCS11_GEN,
|
||||||
@@ -38,9 +37,10 @@ typedef enum {
|
|||||||
} ykcs11_op_type_t;
|
} ykcs11_op_type_t;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
CK_BBOOL rsa; // RSA or EC key
|
CK_BBOOL rsa; // RSA or EC key
|
||||||
CK_BYTE key_id; // Key id
|
CK_BYTE key_id; // Key id
|
||||||
CK_ULONG key_len; // Length in bits
|
CK_ULONG key_len; // Length in bits
|
||||||
|
CK_ULONG vendor_defined; // Additional parameters (touch and PIN policy)
|
||||||
} gen_info_t;
|
} gen_info_t;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
|
|||||||
Reference in New Issue
Block a user