From 12f2cdeafba2b030e8bf8e6c81ba757ec4cd6e48 Mon Sep 17 00:00:00 2001 From: Simo Sorce Date: Tue, 5 Sep 2023 17:50:42 -0400 Subject: [PATCH] Change Key Generation to take a URI Drop passing in individual separate parameters for Label or CKA_ID, rely on URI to provide those (object/id) and also use it to select which token to generate the key on. Signed-off-by: Simo Sorce revert this Signed-off-by: Simo Sorce --- src/keymgmt.c | 90 ++++++++++++++++++++----------------------------- src/provider.h | 3 +- tests/tfork.c | 40 ++++++++++++++++++---- tests/tgenkey.c | 70 ++++++++++++++++++++++++++------------ 4 files changed, 119 insertions(+), 84 deletions(-) diff --git a/src/keymgmt.c b/src/keymgmt.c index e1b11ea9..d1ccb18a 100644 --- a/src/keymgmt.c +++ b/src/keymgmt.c @@ -107,9 +107,7 @@ struct key_generator { CK_KEY_TYPE type; - char *label; - CK_BYTE *id; - CK_ULONG id_len; + P11PROV_URI *uri; CK_MECHANISM mechanism; @@ -205,22 +203,23 @@ static int p11prov_common_gen_set_params(void *genctx, return RET_OSSL_OK; } - p = OSSL_PARAM_locate_const(params, P11PROV_PARAM_KEY_LABEL); + p = OSSL_PARAM_locate_const(params, P11PROV_PARAM_URI); if (p) { - ret = OSSL_PARAM_get_utf8_string(p, &ctx->label, 0); - if (ret != RET_OSSL_OK) { - return ret; + if (p->data_type != OSSL_PARAM_UTF8_STRING) { + return RET_OSSL_ERR; } - } - p = OSSL_PARAM_locate_const(params, P11PROV_PARAM_KEY_ID); - if (p) { - size_t id_len; - ret = OSSL_PARAM_get_octet_string(p, (void **)&ctx->id, 0, &id_len); - if (ret != RET_OSSL_OK) { - return ret; + if (!p->data || p->data_size == 0) { + return RET_OSSL_ERR; + } + if (ctx->uri) { + p11prov_uri_free(ctx->uri); + } + ctx->uri = p11prov_parse_uri(ctx->provctx, (const char *)p->data); + if (!ctx->uri) { + return RET_OSSL_ERR; } - ctx->id_len = id_len; } + switch (ctx->type) { case CKK_RSA: p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_RSA_BITS); @@ -343,17 +342,21 @@ static void *p11prov_common_gen(struct key_generator *ctx, { CK_SLOT_ID slotid = CK_UNAVAILABLE_INFORMATION; CK_BYTE id[16]; - CK_BYTE_PTR id_ptr; - CK_ULONG id_len; CK_OBJECT_HANDLE privkey; CK_OBJECT_HANDLE pubkey; P11PROV_SESSION *session = NULL; CK_SESSION_HANDLE sh; P11PROV_OBJ *key = NULL; + CK_ATTRIBUTE cka_id = { 0 }; + CK_ATTRIBUTE label = { 0 }; CK_RV ret; - /* FIXME: how do we get a URI to select the right slot ? */ - ret = p11prov_get_session(ctx->provctx, &slotid, NULL, NULL, + if (ctx->uri) { + cka_id = p11prov_uri_get_id(ctx->uri); + label = p11prov_uri_get_label(ctx->uri); + } + + ret = p11prov_get_session(ctx->provctx, &slotid, NULL, ctx->uri, ctx->mechanism.mechanism, NULL, NULL, true, true, &session); if (ret != CKR_OK) { @@ -368,36 +371,25 @@ static void *p11prov_common_gen(struct key_generator *ctx, sh = p11prov_session_handle(session); - if (ctx->id_len != 0) { - id_ptr = ctx->id; - id_len = ctx->id_len; - } else { + if (cka_id.ulValueLen == 0) { /* generate unique id for the key */ ret = p11prov_GenerateRandom(ctx->provctx, sh, id, sizeof(id)); if (ret != CKR_OK) { p11prov_return_session(session); return NULL; } - id_ptr = id; - id_len = 16; + cka_id.type = CKA_ID; + cka_id.pValue = id; + cka_id.ulValueLen = 16; } - pubkey_template[pubtsize].type = CKA_ID; - pubkey_template[pubtsize].pValue = id_ptr; - pubkey_template[pubtsize].ulValueLen = id_len; + pubkey_template[pubtsize] = cka_id; pubtsize++; - privkey_template[privtsize].type = CKA_ID; - privkey_template[privtsize].pValue = id_ptr; - privkey_template[privtsize].ulValueLen = id_len; + privkey_template[privtsize] = cka_id; privtsize++; - if (ctx->label) { - CK_ULONG len = strlen(ctx->label); - pubkey_template[pubtsize].type = CKA_LABEL; - pubkey_template[pubtsize].pValue = ctx->label; - pubkey_template[pubtsize].ulValueLen = len; + if (label.ulValueLen != 0) { + pubkey_template[pubtsize] = label; pubtsize++; - privkey_template[privtsize].type = CKA_LABEL; - privkey_template[privtsize].pValue = ctx->label; - privkey_template[privtsize].ulValueLen = len; + privkey_template[privtsize] = label; privtsize++; } @@ -425,12 +417,8 @@ static void p11prov_common_gen_cleanup(void *genctx) P11PROV_debug("common gen_cleanup %p", genctx); - if (ctx->label) { - OPENSSL_free(ctx->label); - } - if (ctx->id) { - OPENSSL_clear_free(ctx->id, ctx->id_len); - } + p11prov_uri_free(ctx->uri); + if (ctx->type == CKK_RSA) { if (ctx->data.rsa.allowed_types_size) { OPENSSL_free(ctx->data.rsa.allowed_types); @@ -536,8 +524,7 @@ static const OSSL_PARAM *p11prov_rsa_gen_settable_params(void *genctx, void *provctx) { static OSSL_PARAM p11prov_rsa_params[] = { - OSSL_PARAM_utf8_string(P11PROV_PARAM_KEY_LABEL, NULL, 0), - OSSL_PARAM_octet_string(P11PROV_PARAM_KEY_ID, NULL, 0), + OSSL_PARAM_utf8_string(P11PROV_PARAM_URI, NULL, 0), OSSL_PARAM_size_t(OSSL_PKEY_PARAM_RSA_BITS, NULL), OSSL_PARAM_size_t(OSSL_PKEY_PARAM_RSA_PRIMES, NULL), OSSL_PARAM_BN(OSSL_PKEY_PARAM_RSA_E, NULL, 0), @@ -952,8 +939,7 @@ static const OSSL_PARAM *p11prov_rsapss_gen_settable_params(void *genctx, void *provctx) { static OSSL_PARAM p11prov_rsapss_params[] = { - OSSL_PARAM_utf8_string(P11PROV_PARAM_KEY_LABEL, NULL, 0), - OSSL_PARAM_octet_string(P11PROV_PARAM_KEY_ID, NULL, 0), + OSSL_PARAM_utf8_string(P11PROV_PARAM_URI, NULL, 0), OSSL_PARAM_size_t(OSSL_PKEY_PARAM_RSA_BITS, NULL), OSSL_PARAM_size_t(OSSL_PKEY_PARAM_RSA_PRIMES, NULL), OSSL_PARAM_BN(OSSL_PKEY_PARAM_RSA_E, NULL, 0), @@ -1071,8 +1057,7 @@ static const OSSL_PARAM *p11prov_ec_gen_settable_params(void *genctx, void *provctx) { static OSSL_PARAM p11prov_ec_params[] = { - OSSL_PARAM_utf8_string(P11PROV_PARAM_KEY_LABEL, NULL, 0), - OSSL_PARAM_octet_string(P11PROV_PARAM_KEY_ID, NULL, 0), + OSSL_PARAM_utf8_string(P11PROV_PARAM_URI, NULL, 0), OSSL_PARAM_utf8_string(OSSL_PKEY_PARAM_GROUP_NAME, NULL, 0), OSSL_PARAM_END, }; @@ -1499,8 +1484,7 @@ static const OSSL_PARAM *p11prov_ed_gen_settable_params(void *genctx, void *provctx) { static OSSL_PARAM p11prov_ed_params[] = { - OSSL_PARAM_utf8_string(P11PROV_PARAM_KEY_LABEL, NULL, 0), - OSSL_PARAM_octet_string(P11PROV_PARAM_KEY_ID, NULL, 0), + OSSL_PARAM_utf8_string(P11PROV_PARAM_URI, NULL, 0), OSSL_PARAM_END, }; return p11prov_ed_params; diff --git a/src/provider.h b/src/provider.h index e6cb896a..38f3df4f 100644 --- a/src/provider.h +++ b/src/provider.h @@ -57,8 +57,7 @@ #define P11PROV_NAMES_RAND "PKCS11-RAND" #define P11PROV_DESCS_RAND "PKCS11 Random Generator" -#define P11PROV_PARAM_KEY_LABEL "pkcs11_key_label" -#define P11PROV_PARAM_KEY_ID "pkcs11_key_id" +#define P11PROV_PARAM_URI "pkcs11_uri" #define P11PROV_PARAM_SLOT_ID "pkcs11_slot_id" typedef struct p11prov_ctx P11PROV_CTX; diff --git a/tests/tfork.c b/tests/tfork.c index 963a50ef..8b2003fb 100644 --- a/tests/tfork.c +++ b/tests/tfork.c @@ -24,12 +24,33 @@ fflush(stderr); \ } while (0) +static void hexify(char *out, unsigned char *byte, size_t len) +{ + char c[2], s; + + for (size_t i = 0; i < len; i++) { + out[i * 3] = '%'; + c[0] = byte[i] >> 4; + c[1] = byte[i] & 0x0f; + for (int j = 0; j < 2; j++) { + if (c[j] < 0x0A) { + s = '0'; + } else { + s = 'a' - 10; + } + out[i * 3 + 1 + j] = c[j] + s; + } + } + out[len * 3] = '\0'; +} + static EVP_PKEY *gen_key(void) { - char label[] = "##########: Fork Test Key"; unsigned char id[16]; + char idhex[16 * 3 + 1]; + char *uri; size_t rsa_bits = 3072; - OSSL_PARAM params[5]; + OSSL_PARAM params[3]; EVP_PKEY_CTX *ctx; EVP_PKEY *key = NULL; int miniid; @@ -42,13 +63,17 @@ static EVP_PKEY *gen_key(void) exit(EXIT_FAILURE); } + hexify(idhex, id, 16); miniid = (id[0] << 24) + (id[1] << 16) + (id[2] << 8) + id[3]; - snprintf(label, 10, "%08x", miniid); + ret = asprintf(&uri, "pkcs11:object=Fork-Test-%08x;id=%s", miniid, idhex); + if (ret == -1) { + fprintf(stderr, "Failed to allocate uri\n"); + exit(EXIT_FAILURE); + } - params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_key_label", label, 0); - params[1] = OSSL_PARAM_construct_octet_string("pkcs11_key_id", id, 16); - params[2] = OSSL_PARAM_construct_size_t("rsa_keygen_bits", &rsa_bits); - params[3] = OSSL_PARAM_construct_end(); + params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_uri", uri, 0); + params[1] = OSSL_PARAM_construct_size_t("rsa_keygen_bits", &rsa_bits); + params[2] = OSSL_PARAM_construct_end(); ctx = EVP_PKEY_CTX_new_from_name(NULL, "RSA", "provider=pkcs11"); if (ctx == NULL) { @@ -71,6 +96,7 @@ static EVP_PKEY *gen_key(void) exit(EXIT_FAILURE); } + free(uri); return key; } diff --git a/tests/tgenkey.c b/tests/tgenkey.c index dde7884e..22d26f98 100644 --- a/tests/tgenkey.c +++ b/tests/tgenkey.c @@ -115,8 +115,8 @@ static void check_keys(OSSL_STORE_CTX *store, const char *key_type) EVP_PKEY_free(pubkey); } -static void gen_keys(const char *key_type, const char *label, unsigned char *id, - const char *idhex, const OSSL_PARAM *params) +static void gen_keys(const char *key_type, const char *label, const char *idhex, + const OSSL_PARAM *params) { EVP_PKEY_CTX *ctx; EVP_PKEY *key = NULL; @@ -125,6 +125,8 @@ static void gen_keys(const char *key_type, const char *label, unsigned char *id, OSSL_STORE_SEARCH *search; int ret; + fprintf(stdout, "Generate %s\n", key_type); + ctx = EVP_PKEY_CTX_new_from_name(NULL, key_type, "provider=pkcs11"); if (ctx == NULL) { fprintf(stderr, "Failed to init PKEY context\n"); @@ -151,6 +153,8 @@ static void gen_keys(const char *key_type, const char *label, unsigned char *id, ctx = NULL; /* now try to search by id */ + fprintf(stdout, "Search by ID\n"); + ret = asprintf(&uri, "pkcs11:id=%s", idhex); if (ret == -1) { fprintf(stderr, "Failed to allocate uri\n"); @@ -169,6 +173,8 @@ static void gen_keys(const char *key_type, const char *label, unsigned char *id, OSSL_STORE_close(store); /* now make sure we can filter by label */ + fprintf(stdout, "Search by Label\n"); + store = OSSL_STORE_open("pkcs11:", NULL, NULL, NULL, NULL); if (store == NULL) { fprintf(stderr, "Failed to open pkcs11 store\n"); @@ -197,8 +203,10 @@ int main(int argc, char *argv[]) char *label; unsigned char id[16]; char idhex[16 * 3 + 1]; + char *uri; size_t rsa_bits = 3072; - OSSL_PARAM params[5]; + OSSL_PARAM params[4]; + int miniid; int ret; /* RSA */ @@ -207,19 +215,25 @@ int main(int argc, char *argv[]) fprintf(stderr, "Failed to set generate key id\n"); exit(EXIT_FAILURE); } + miniid = (id[0] << 24) + (id[1] << 16) + (id[2] << 8) + id[3]; + ret = asprintf(&label, "Test-RSA-gen-%08x", miniid); + if (ret == -1) { + fprintf(stderr, "Failed to make label"); + exit(EXIT_FAILURE); + } hexify(idhex, id, 16); - ret = asprintf(&label, "Test RSA gen [%.9s]", idhex); + ret = asprintf(&uri, "pkcs11:object=%s;id=%s", label, idhex); if (ret == -1) { fprintf(stderr, "Failed to make label"); exit(EXIT_FAILURE); } - params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_key_label", label, 0); - params[1] = OSSL_PARAM_construct_octet_string("pkcs11_key_id", id, 16); - params[2] = OSSL_PARAM_construct_size_t("rsa_keygen_bits", &rsa_bits); - params[3] = OSSL_PARAM_construct_end(); + params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_uri", uri, 0); + params[1] = OSSL_PARAM_construct_size_t("rsa_keygen_bits", &rsa_bits); + params[2] = OSSL_PARAM_construct_end(); - gen_keys("RSA", label, id, idhex, params); + gen_keys("RSA", label, idhex, params); free(label); + free(uri); /* RSA-PSS */ ret = RAND_bytes(id, 16); @@ -227,21 +241,27 @@ int main(int argc, char *argv[]) fprintf(stderr, "Failed to set generate key id\n"); exit(EXIT_FAILURE); } + miniid = (id[0] << 24) + (id[1] << 16) + (id[2] << 8) + id[3]; + ret = asprintf(&label, "Test-RSA-PSS-gen-%08x", miniid); + if (ret == -1) { + fprintf(stderr, "Failed to make label"); + exit(EXIT_FAILURE); + } hexify(idhex, id, 16); - ret = asprintf(&label, "Test RSA-PSS gen [%.9s]", idhex); + ret = asprintf(&uri, "pkcs11:object=%s;id=%s", label, idhex); if (ret == -1) { fprintf(stderr, "Failed to make label"); exit(EXIT_FAILURE); } - params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_key_label", label, 0); - params[1] = OSSL_PARAM_construct_octet_string("pkcs11_key_id", id, 16); - params[2] = OSSL_PARAM_construct_size_t("rsa_keygen_bits", &rsa_bits); - params[3] = OSSL_PARAM_construct_utf8_string("rsa_pss_keygen_md", + params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_uri", uri, 0); + params[1] = OSSL_PARAM_construct_size_t("rsa_keygen_bits", &rsa_bits); + params[2] = OSSL_PARAM_construct_utf8_string("rsa_pss_keygen_md", (char *)"SHA256", 0); - params[4] = OSSL_PARAM_construct_end(); + params[3] = OSSL_PARAM_construct_end(); - gen_keys("RSA-PSS", label, id, idhex, params); + gen_keys("RSA-PSS", label, idhex, params); free(label); + free(uri); /* EC */ ret = RAND_bytes(id, 16); @@ -249,20 +269,26 @@ int main(int argc, char *argv[]) fprintf(stderr, "Failed to set generate key id\n"); exit(EXIT_FAILURE); } + miniid = (id[0] << 24) + (id[1] << 16) + (id[2] << 8) + id[3]; + ret = asprintf(&label, "Test-EC-gen-%08x", miniid); + if (ret == -1) { + fprintf(stderr, "Failed to make label"); + exit(EXIT_FAILURE); + } hexify(idhex, id, 16); - ret = asprintf(&label, "Test EC gen [%.9s]", idhex); + ret = asprintf(&uri, "pkcs11:object=%s;id=%s", label, idhex); if (ret == -1) { fprintf(stderr, "Failed to make label"); exit(EXIT_FAILURE); } - params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_key_label", label, 0); - params[1] = OSSL_PARAM_construct_octet_string("pkcs11_key_id", id, 16); - params[2] = OSSL_PARAM_construct_utf8_string("ec_paramgen_curve", + params[0] = OSSL_PARAM_construct_utf8_string("pkcs11_uri", uri, 0); + params[1] = OSSL_PARAM_construct_utf8_string("ec_paramgen_curve", (char *)"P-256", 0); - params[3] = OSSL_PARAM_construct_end(); + params[2] = OSSL_PARAM_construct_end(); - gen_keys("EC", label, id, idhex, params); + gen_keys("EC", label, idhex, params); free(label); + free(uri); fprintf(stderr, "ALL A-OK!"); exit(EXIT_SUCCESS);