diff options
Diffstat (limited to 'crypto')
-rw-r--r-- | crypto/dh/dh_pmeth.c | 43 | ||||
-rw-r--r-- | crypto/evp/ctrl_params_translate.c | 104 | ||||
-rw-r--r-- | crypto/evp/dh_support.c | 29 | ||||
-rw-r--r-- | crypto/evp/p_lib.c | 33 | ||||
-rw-r--r-- | crypto/ffc/ffc_dh.c | 4 |
5 files changed, 124 insertions, 89 deletions
diff --git a/crypto/dh/dh_pmeth.c b/crypto/dh/dh_pmeth.c index affe40a53c..78d46aba22 100644 --- a/crypto/dh/dh_pmeth.c +++ b/crypto/dh/dh_pmeth.c @@ -35,7 +35,6 @@ typedef struct { int pad; /* message digest used for parameter generation */ const EVP_MD *md; - int rfc5114_param; int param_nid; /* Keygen callback info */ int gentmp[2]; @@ -98,7 +97,6 @@ static int pkey_dh_copy(EVP_PKEY_CTX *dst, const EVP_PKEY_CTX *src) dctx->paramgen_type = sctx->paramgen_type; dctx->pad = sctx->pad; dctx->md = sctx->md; - dctx->rfc5114_param = sctx->rfc5114_param; dctx->param_nid = sctx->param_nid; dctx->kdf_type = sctx->kdf_type; @@ -156,11 +154,11 @@ static int pkey_dh_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2) case EVP_PKEY_CTRL_DH_RFC5114: if (p1 < 1 || p1 > 3 || dctx->param_nid != NID_undef) return -2; - dctx->rfc5114_param = p1; + dctx->param_nid = p1; return 1; case EVP_PKEY_CTRL_DH_NID: - if (p1 <= 0 || dctx->rfc5114_param != 0) + if (p1 <= 0 || dctx->param_nid != NID_undef) return -2; dctx->param_nid = p1; return 1; @@ -233,11 +231,12 @@ static int pkey_dh_ctrl_str(EVP_PKEY_CTX *ctx, } if (strcmp(type, "dh_rfc5114") == 0) { DH_PKEY_CTX *dctx = ctx->data; - int len; - len = atoi(value); - if (len < 0 || len > 3) + int id; + + id = atoi(value); + if (id < 0 || id > 3) return -2; - dctx->rfc5114_param = len; + dctx->param_nid = id; return 1; } if (strcmp(type, "dh_param") == 0) { @@ -331,36 +330,16 @@ static int pkey_dh_paramgen(EVP_PKEY_CTX *ctx, /* * Look for a safe prime group for key establishment. Which uses * either RFC_3526 (modp_XXXX) or RFC_7919 (ffdheXXXX). + * RFC_5114 is also handled here for param_nid = (1..3) */ if (dctx->param_nid != NID_undef) { + int type = dctx->param_nid <= 3 ? EVP_PKEY_DHX : EVP_PKEY_DH; + if ((dh = DH_new_by_nid(dctx->param_nid)) == NULL) return 0; - EVP_PKEY_assign(pkey, EVP_PKEY_DH, dh); - return 1; - } - -#ifndef FIPS_MODULE - if (dctx->rfc5114_param) { - switch (dctx->rfc5114_param) { - case 1: - dh = DH_get_1024_160(); - break; - - case 2: - dh = DH_get_2048_224(); - break; - - case 3: - dh = DH_get_2048_256(); - break; - - default: - return -2; - } - EVP_PKEY_assign(pkey, EVP_PKEY_DHX, dh); + EVP_PKEY_assign(pkey, type, dh); return 1; } -#endif /* FIPS_MODULE */ if (ctx->pkey_gencb != NULL) { pcb = BN_GENCB_new(); diff --git a/crypto/evp/ctrl_params_translate.c b/crypto/evp/ctrl_params_translate.c index 8f4ffd3bc4..f48e723c33 100644 --- a/crypto/evp/ctrl_params_translate.c +++ b/crypto/evp/ctrl_params_translate.c @@ -977,7 +977,7 @@ static int fix_oid(enum state state, return ret; } -/* EVP_PKEY_CTRL_DH_NID, ...??? */ +/* EVP_PKEY_CTRL_DH_NID */ static int fix_dh_nid(enum state state, const struct translation_st *translation, struct translation_ctx_st *ctx) @@ -987,7 +987,7 @@ static int fix_dh_nid(enum state state, if ((ret = default_check(state, translation, ctx)) <= 0) return ret; - /* This is currently only settable */ + /* This is only settable */ if (ctx->action_type != SET) return 0; @@ -997,16 +997,30 @@ static int fix_dh_nid(enum state state, ctx->p1 = 0; } - if ((ret = default_fixup_args(state, translation, ctx)) <= 0) + return default_fixup_args(state, translation, ctx); +} + +/* EVP_PKEY_CTRL_DH_RFC5114 */ +static int fix_dh_nid5114(enum state state, + const struct translation_st *translation, + struct translation_ctx_st *ctx) +{ + int ret; + + if ((ret = default_check(state, translation, ctx)) <= 0) return ret; - if (state == PRE_PARAMS_TO_CTRL) { - ctx->p1 = - ossl_ffc_named_group_get_uid(ossl_ffc_name_to_dh_named_group(ctx->p2)); - ctx->p2 = NULL; + /* This is only settable */ + if (ctx->action_type != SET) + return 0; + + if (state == PRE_CTRL_STR_TO_PARAMS) { + ctx->p2 = (char *)ossl_ffc_named_group_get_name + (ossl_ffc_uid_to_dh_named_group(atoi(ctx->p2))); + ctx->p1 = 0; } - return ret; + return default_fixup_args(state, translation, ctx); } /* EVP_PKEY_CTRL_DH_PARAMGEN_TYPE */ @@ -1019,24 +1033,16 @@ static int fix_dh_paramgen_type(enum state state, if ((ret = default_check(state, translation, ctx)) <= 0) return ret; - /* This is currently only settable */ + /* This is only settable */ if (ctx->action_type != SET) return 0; - if (state == PRE_CTRL_TO_PARAMS) { - ctx->p2 = (char *)ossl_dh_gen_type_id2name(ctx->p1); - ctx->p1 = 0; - } - - if ((ret = default_fixup_args(state, translation, ctx)) <= 0) - return ret; - - if (state == PRE_PARAMS_TO_CTRL) { - ctx->p1 = ossl_dh_gen_type_name2id(ctx->p2); - ctx->p2 = NULL; + if (state == PRE_CTRL_STR_TO_PARAMS) { + ctx->p2 = (char *)ossl_dh_gen_type_id2name(atoi(ctx->p2)); + ctx->p1 = strlen(ctx->p2); } - return ret; + return default_fixup_args(state, translation, ctx); } /* EVP_PKEY_CTRL_EC_PARAM_ENC */ @@ -1927,35 +1933,47 @@ static const struct translation_st evp_pkey_ctx_translations[] = { EVP_PKEY_CTRL_GET_DH_KDF_OID, NULL, NULL, OSSL_KDF_PARAM_CEK_ALG, OSSL_PARAM_UTF8_STRING, fix_oid }, - { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_DERIVE, - EVP_PKEY_CTRL_DH_PAD, "dh_pad", NULL, - OSSL_EXCHANGE_PARAM_PAD, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, + /* DHX Keygen Parameters that are shared with DH */ + { SET, EVP_PKEY_DHX, 0, EVP_PKEY_OP_PARAMGEN, + EVP_PKEY_CTRL_DH_PARAMGEN_TYPE, "dh_paramgen_type", NULL, + OSSL_PKEY_PARAM_FFC_TYPE, OSSL_PARAM_UTF8_STRING, fix_dh_paramgen_type }, + { SET, EVP_PKEY_DHX, 0, EVP_PKEY_OP_PARAMGEN, + EVP_PKEY_CTRL_DH_PARAMGEN_PRIME_LEN, "dh_paramgen_prime_len", NULL, + OSSL_PKEY_PARAM_FFC_PBITS, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, + { SET, EVP_PKEY_DHX, 0, EVP_PKEY_OP_PARAMGEN | EVP_PKEY_OP_KEYGEN, + EVP_PKEY_CTRL_DH_NID, "dh_param", NULL, + OSSL_PKEY_PARAM_GROUP_NAME, OSSL_PARAM_UTF8_STRING, NULL }, + { SET, EVP_PKEY_DHX, 0, EVP_PKEY_OP_PARAMGEN | EVP_PKEY_OP_KEYGEN, + EVP_PKEY_CTRL_DH_RFC5114, "dh_rfc5114", NULL, + OSSL_PKEY_PARAM_GROUP_NAME, OSSL_PARAM_UTF8_STRING, fix_dh_nid5114 }, + /* DH Keygen Parameters that are shared with DHX */ + { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, + EVP_PKEY_CTRL_DH_PARAMGEN_TYPE, "dh_paramgen_type", NULL, + OSSL_PKEY_PARAM_FFC_TYPE, OSSL_PARAM_UTF8_STRING, fix_dh_paramgen_type }, + { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, + EVP_PKEY_CTRL_DH_PARAMGEN_PRIME_LEN, "dh_paramgen_prime_len", NULL, + OSSL_PKEY_PARAM_FFC_PBITS, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN | EVP_PKEY_OP_KEYGEN, EVP_PKEY_CTRL_DH_NID, "dh_param", NULL, OSSL_PKEY_PARAM_GROUP_NAME, OSSL_PARAM_UTF8_STRING, fix_dh_nid }, - { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, - EVP_PKEY_CTRL_DH_PARAMGEN_PRIME_LEN, NULL, NULL, - OSSL_PKEY_PARAM_FFC_PBITS, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, - { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, - EVP_PKEY_CTRL_DH_PARAMGEN_SUBPRIME_LEN, "dh_paramgen_subprime_len", NULL, - OSSL_PKEY_PARAM_FFC_QBITS, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, + { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN | EVP_PKEY_OP_KEYGEN, + EVP_PKEY_CTRL_DH_RFC5114, "dh_rfc5114", NULL, + OSSL_PKEY_PARAM_GROUP_NAME, OSSL_PARAM_UTF8_STRING, fix_dh_nid5114 }, + + /* DH specific Keygen Parameters */ { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, EVP_PKEY_CTRL_DH_PARAMGEN_GENERATOR, "dh_paramgen_generator", NULL, OSSL_PKEY_PARAM_DH_GENERATOR, OSSL_PARAM_INTEGER, NULL }, - { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, - EVP_PKEY_CTRL_DH_PARAMGEN_TYPE, "dh_paramgen_type", NULL, - OSSL_PKEY_PARAM_FFC_TYPE, OSSL_PARAM_UTF8_STRING, fix_dh_paramgen_type }, - /* - * This is know to be incorrect, will be fixed and enabled when the - * underlying code is corrected. - * Until then, we simply don't support it here. - */ -#if 0 - { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_PARAMGEN, - EVP_PKEY_CTRL_DH_RFC5114, "dh_rfc5114", NULL, - OSSL_PKEY_PARAM_GROUP_NAME, OSSL_PARAM_INTEGER, NULL }, -#endif + + /* DHX specific Keygen Parameters */ + { SET, EVP_PKEY_DHX, 0, EVP_PKEY_OP_PARAMGEN, + EVP_PKEY_CTRL_DH_PARAMGEN_SUBPRIME_LEN, "dh_paramgen_subprime_len", NULL, + OSSL_PKEY_PARAM_FFC_QBITS, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, + + { SET, EVP_PKEY_DH, 0, EVP_PKEY_OP_DERIVE, + EVP_PKEY_CTRL_DH_PAD, "dh_pad", NULL, + OSSL_EXCHANGE_PARAM_PAD, OSSL_PARAM_UNSIGNED_INTEGER, NULL }, /*- * DSA diff --git a/crypto/evp/dh_support.c b/crypto/evp/dh_support.c index 7e0256bd00..87296ffbee 100644 --- a/crypto/evp/dh_support.c +++ b/crypto/evp/dh_support.c @@ -15,14 +15,25 @@ typedef struct dh_name2id_st{ const char *name; int id; + int type; } DH_GENTYPE_NAME2ID; -static const DH_GENTYPE_NAME2ID dhtype2id[]= +/* Indicates that the paramgen_type can be used for either DH or DHX */ +#define TYPE_ANY -1 +#ifndef OPENSSL_NO_DH +# define TYPE_DH DH_FLAG_TYPE_DH +# define TYPE_DHX DH_FLAG_TYPE_DHX +#else +# define TYPE_DH 0 +# define TYPE_DHX 0 +#endif + +static const DH_GENTYPE_NAME2ID dhtype2id[] = { - { "fips186_4", DH_PARAMGEN_TYPE_FIPS_186_4 }, - { "fips186_2", DH_PARAMGEN_TYPE_FIPS_186_2 }, - { "group", DH_PARAMGEN_TYPE_GROUP }, - { "generator", DH_PARAMGEN_TYPE_GENERATOR } + { "group", DH_PARAMGEN_TYPE_GROUP, TYPE_ANY }, + { "generator", DH_PARAMGEN_TYPE_GENERATOR, TYPE_DH }, + { "fips186_4", DH_PARAMGEN_TYPE_FIPS_186_4, TYPE_DHX }, + { "fips186_2", DH_PARAMGEN_TYPE_FIPS_186_2, TYPE_DHX }, }; const char *ossl_dh_gen_type_id2name(int id) @@ -36,13 +47,17 @@ const char *ossl_dh_gen_type_id2name(int id) return NULL; } -int ossl_dh_gen_type_name2id(const char *name) +#ifndef OPENSSL_NO_DH +int ossl_dh_gen_type_name2id(const char *name, int type) { size_t i; for (i = 0; i < OSSL_NELEM(dhtype2id); ++i) { - if (strcmp(dhtype2id[i].name, name) == 0) + if ((dhtype2id[i].type == TYPE_ANY + || type == dhtype2id[i].type) + && strcmp(dhtype2id[i].name, name) == 0) return dhtype2id[i].id; } return -1; } +#endif diff --git a/crypto/evp/p_lib.c b/crypto/evp/p_lib.c index daa0f617d8..3af7e17bee 100644 --- a/crypto/evp/p_lib.c +++ b/crypto/evp/p_lib.c @@ -890,13 +890,38 @@ IMPLEMENT_ECX_VARIANT(ED448) # if !defined(OPENSSL_NO_DH) && !defined(OPENSSL_NO_DEPRECATED_3_0) -int EVP_PKEY_set1_DH(EVP_PKEY *pkey, DH *key) +int EVP_PKEY_set1_DH(EVP_PKEY *pkey, DH *dhkey) { - int type = DH_get0_q(key) == NULL ? EVP_PKEY_DH : EVP_PKEY_DHX; - int ret = EVP_PKEY_assign(pkey, type, key); + int ret, type; + + /* + * ossl_dh_is_named_safe_prime_group() returns 1 for named safe prime groups + * related to ffdhe and modp (which cache q = (p - 1) / 2), + * and returns 0 for all other dh parameter generation types including + * RFC5114 named groups. + * + * The EVP_PKEY_DH type is used for dh parameter generation types: + * - named safe prime groups related to ffdhe and modp + * - safe prime generator + * + * The type EVP_PKEY_DHX is used for dh parameter generation types + * - fips186-4 and fips186-2 + * - rfc5114 named groups. + * + * The EVP_PKEY_DH type is used to save PKCS#3 data than can be stored + * without a q value. + * The EVP_PKEY_DHX type is used to save X9.42 data that requires the + * q value to be stored. + */ + if (ossl_dh_is_named_safe_prime_group(dhkey)) + type = EVP_PKEY_DH; + else + type = DH_get0_q(dhkey) == NULL ? EVP_PKEY_DH : EVP_PKEY_DHX; + + ret = EVP_PKEY_assign(pkey, type, dhkey); if (ret) - DH_up_ref(key); + DH_up_ref(dhkey); return ret; } diff --git a/crypto/ffc/ffc_dh.c b/crypto/ffc/ffc_dh.c index 17888e9291..e9f597c46c 100644 --- a/crypto/ffc/ffc_dh.c +++ b/crypto/ffc/ffc_dh.c @@ -113,9 +113,7 @@ const DH_NAMED_GROUP *ossl_ffc_numbers_to_dh_named_group(const BIGNUM *p, if (BN_cmp(p, dh_named_groups[i].p) == 0 && BN_cmp(g, dh_named_groups[i].g) == 0 /* Verify q is correct if it exists */ - && ((q != NULL && BN_cmp(q, dh_named_groups[i].q) == 0) - /* Do not match RFC 5114 groups without q */ - || (q == NULL && dh_named_groups[i].uid > 3))) + && (q == NULL || BN_cmp(q, dh_named_groups[i].q) == 0)) return &dh_named_groups[i]; } return NULL; |