EVP_KEYMGMT-DH
名稱
EVP_PKEY-DH、EVP_PKEY-DHX、EVP_KEYMGMT-DH、EVP_KEYMGMT-DHX - EVP_PKEY DH 和 DHX 金鑰類型和演算法支援
說明
對於 DH FFC 金鑰協定,可以使用兩類網域參數:「安全」網域參數與已核准命名安全質數群組相關聯,以及「FIPS186 類型」網域參數類別。FIPS186 類型網域參數應僅用於與無法升級以使用已核准安全質數群組的現有應用程式向後相容。
請參閱 EVP_PKEY-FFC(7) 以取得有關 FFC 金鑰的更多資訊。
DH 金鑰類型使用 PKCS#3 格式,會儲存 p 和 g,但不會儲存 q 值。DHX 金鑰類型使用 X9.42 格式,會儲存 q 的值,且必須用於 FIPS186-4。如果需要金鑰驗證,使用者應注意與 FIPS186-4 類型參數相關的細微差別,如 "DH 金鑰驗證" 中所述。
DH 和 DHX 網域參數
除了所有 FFC 金鑰類型都應支援的常見 FCC 參數外(請參閱 EVP_PKEY-FFC(7) 中的「FFC 參數」),DHX 和 DH 金鑰類型實作還支援下列內容:
- "群組" (OSSL_PKEY_PARAM_GROUP_NAME) <UTF8 字串>
-
設定或取得將 DH 或 DHX 命名安全質數群組與 p、q 和 g 的已知值關聯的字串。
OpenSSL 的預設和 FIPS 提供者可以使用下列值:「ffdhe2048」、「ffdhe3072」、「ffdhe4096」、「ffdhe6144」、「ffdhe8192」、「modp_2048」、「modp_3072」、「modp_4096」、「modp_6144」、「modp_8192」。
OpenSSL 的預設提供者還可以額外使用下列值:「modp_1536」、「dh_1024_160」、「dh_2048_224」、「dh_2048_256」。
可以輕鬆驗證 DH/DHX 命名群組,因為這些參數是眾所周知的。對於僅傳輸 p 和 g 的通訊協定,也可以擷取 q 的值。
DH 和 DHX 其他參數
- "編碼公鑰" (OSSL_PKEY_PARAM_ENCODED_PUBLIC_KEY) <八位元組字串>
-
用於取得和設定 TLS 協定的金鑰交換訊息中所使用的 DH 公開金鑰編碼。請參閱 EVP_PKEY_set1_encoded_public_key() 和 EVP_PKEY_get1_encoded_public_key()。
DH 額外網域參數
- "safeprime-generator" (OSSL_PKEY_PARAM_DH_GENERATOR) <整數>
-
用於使用舊的安全質數產生器程式碼產生 DH 安全質數。預設值為 2。建議改用已命名安全質數群組,如果需要網域參數驗證。
FIPS 不允許隨機產生的安全質數,因此為 OpenSSL FIPS 提供者設定此值時,反而會根據 p 的大小選擇已命名安全質數群組。
DH 和 DHX 網域參數 / 金鑰產生參數
除了所有 FFC 金鑰類型都應支援的常見 FFC 金鑰產生參數(請參閱 EVP_PKEY-FFC(7) 中的「FFC 金鑰產生參數」)外,DH 和 DHX 金鑰類型實作支援下列參數
- "type" (OSSL_PKEY_PARAM_FFC_TYPE) <UTF8 字串>
-
設定參數產生類型。對於 DH,有效值為
- "fips186_4"
- "default"
- "fips186_2"
-
這些值在 EVP_PKEY-FFC(7) 中的「FFC 金鑰產生參數」 中有說明
- "group"
-
這指定將使用「pbits」類型選擇已命名安全質數名稱。
- "generator"
-
安全質數產生器。請參閱上方的「safeprime-generator」類型。這僅對 DH 金鑰有效。
- "pbits" (OSSL_PKEY_PARAM_FFC_PBITS) <無符號整數>
-
設定質數 'p' 的大小(以位元為單位)。
對於「fips186_4」,這必須是 2048。對於「fips186_2」,這必須是 1024。對於「group」,這可以是 2048、3072、4096、6144 或 8192 中的任何一個。
- "priv_len" (OSSL_PKEY_PARAM_DH_PRIV_LEN) <整數>
-
設定產生私密金鑰最大長度的選用值。如果未設定,則使用的預設值是 BN_num_bits(q)) 的最大值。可以設定的最小值是 2 * s。其中 s 是金鑰的安全強度,對於金鑰大小 2048、3072、4096、6144 和 8192,其值分別為 112、128、152、176 和 200。
DH 金鑰驗證
對於非已命名群組的 DHX,FIPS186-4 標準規定,用於 FFC 參數產生的值也需要用於參數驗證。這表示可能需要儲存種子、pcounter 和 gindex 或 hindex 的選用 FFC 網域參數值,以供驗證用途。對於 DHX,種子和 pcounter 可以儲存在 ASN1 資料中(但 gindex 或 hindex 無法儲存)。建議改用已命名安全質數群組。
對於 DH 金鑰,EVP_PKEY_param_check(3) 的行為如下:OpenSSL FIPS 提供者會測試參數是否為已核准的安全質數群組,或 FFC 參數是否符合 SP800-56Ar3 中定義的 FIPS186-4 網域參數有效性保證。OpenSSL 預設提供者使用較簡單的檢查,允許沒有 q 值以維持向後相容性。
對於 DH 金鑰,EVP_PKEY_param_check_quick(3) 等同於 EVP_PKEY_param_check(3)。
對於 DH 金鑰,EVP_PKEY_public_check(3) 符合 SP800-56Ar3 FFC 完整公鑰驗證。
對於 DH 金鑰,EVP_PKEY_public_check_quick(3) 符合 SP800-56Ar3 FFC 部分公鑰驗證,前提是 DH 金鑰為核准的命名安全質數群組,否則與 EVP_PKEY_public_check(3) 相同。
對於 DH 金鑰,EVP_PKEY_private_check(3) 根據 SP800-56Ar3 測試私鑰是否在正確範圍內。OpenSSL FIPS 提供者需要設定 q 的值(請注意,這是針對命名安全質數群組設定的)。為了向後相容性,OpenSSL 預設提供者只需要設定 p。
對於 DH 金鑰,EVP_PKEY_pairwise_check(3) 符合 SP800-56Ar3 成對一致性的所有者保證。
範例
可以透過呼叫來取得 EVP_PKEY 內容
EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new_from_name(NULL, "DH", NULL);
可以透過呼叫來使用命名安全質數群組產生 DH 金鑰
int priv_len = 2 * 112;
OSSL_PARAM params[3];
EVP_PKEY *pkey = NULL;
EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new_from_name(NULL, "DH", NULL);
params[0] = OSSL_PARAM_construct_utf8_string("group", "ffdhe2048", 0);
/* "priv_len" is optional */
params[1] = OSSL_PARAM_construct_int("priv_len", &priv_len);
params[2] = OSSL_PARAM_construct_end();
EVP_PKEY_keygen_init(pctx);
EVP_PKEY_CTX_set_params(pctx, params);
EVP_PKEY_generate(pctx, &pkey);
...
EVP_PKEY_free(pkey);
EVP_PKEY_CTX_free(pctx);
可以透過呼叫來根據 FIPS186-4 產生 DHX 域參數
int gindex = 2;
unsigned int pbits = 2048;
unsigned int qbits = 256;
OSSL_PARAM params[6];
EVP_PKEY *param_key = NULL;
EVP_PKEY_CTX *pctx = NULL;
pctx = EVP_PKEY_CTX_new_from_name(NULL, "DHX", NULL);
EVP_PKEY_paramgen_init(pctx);
params[0] = OSSL_PARAM_construct_uint("pbits", &pbits);
params[1] = OSSL_PARAM_construct_uint("qbits", &qbits);
params[2] = OSSL_PARAM_construct_int("gindex", &gindex);
params[3] = OSSL_PARAM_construct_utf8_string("type", "fips186_4", 0);
params[4] = OSSL_PARAM_construct_utf8_string("digest", "SHA256", 0);
params[5] = OSSL_PARAM_construct_end();
EVP_PKEY_CTX_set_params(pctx, params);
EVP_PKEY_generate(pctx, ¶m_key);
EVP_PKEY_print_params(bio_out, param_key, 0, NULL);
...
EVP_PKEY_free(param_key);
EVP_PKEY_CTX_free(pctx);
可以透過呼叫來使用域參數產生 DH 金鑰
EVP_PKEY *key = NULL;
EVP_PKEY_CTX *gctx = EVP_PKEY_CTX_new_from_pkey(NULL, param_key, NULL);
EVP_PKEY_keygen_init(gctx);
EVP_PKEY_generate(gctx, &key);
EVP_PKEY_print_private(bio_out, key, 0, NULL);
...
EVP_PKEY_free(key);
EVP_PKEY_CTX_free(gctx);
若要驗證從 PEM 或 DER 資料解碼的 FIPS186-4 DHX 域參數,可能需要將產生期間使用的其他值設定到金鑰中。
EVP_PKEY_todata()、OSSL_PARAM_merge() 和 EVP_PKEY_fromdata() 可用於在實際驗證之前將這些參數新增到原始金鑰或域參數。在實際程式碼中,應該檢查回傳值。
EVP_PKEY *received_domp = ...; /* parameters received and decoded */
unsigned char *seed = ...; /* and additional parameters received */
size_t seedlen = ...; /* by other means, required */
int gindex = ...; /* for the validation */
int pcounter = ...;
int hindex = ...;
OSSL_PARAM extra_params[4];
OSSL_PARAM *domain_params = NULL;
OSSL_PARAM *merged_params = NULL;
EVP_PKEY_CTX *ctx = NULL, *validate_ctx = NULL;
EVP_PKEY *complete_domp = NULL;
EVP_PKEY_todata(received_domp, OSSL_KEYMGMT_SELECT_DOMAIN_PARAMETERS,
&domain_params);
extra_params[0] = OSSL_PARAM_construct_octet_string("seed", seed, seedlen);
/*
* NOTE: For unverifiable g use "hindex" instead of "gindex"
* extra_params[1] = OSSL_PARAM_construct_int("hindex", &hindex);
*/
extra_params[1] = OSSL_PARAM_construct_int("gindex", &gindex);
extra_params[2] = OSSL_PARAM_construct_int("pcounter", &pcounter);
extra_params[3] = OSSL_PARAM_construct_end();
merged_params = OSSL_PARAM_merge(domain_params, extra_params);
ctx = EVP_PKEY_CTX_new_from_name(NULL, "DHX", NULL);
EVP_PKEY_fromdata_init(ctx);
EVP_PKEY_fromdata(ctx, &complete_domp, OSSL_KEYMGMT_SELECT_ALL,
merged_params);
validate_ctx = EVP_PKEY_CTX_new_from_pkey(NULL, complete_domp, NULL);
if (EVP_PKEY_param_check(validate_ctx) > 0)
/* validation_passed(); */
else
/* validation_failed(); */
OSSL_PARAM_free(domain_params);
OSSL_PARAM_free(merged_params);
EVP_PKEY_CTX_free(ctx);
EVP_PKEY_CTX_free(validate_ctx);
EVP_PKEY_free(complete_domp);
符合
- RFC 7919(TLS ffdhe 命名安全質數群組)
- RFC 3526(IKE modp 命名安全質數群組)
- RFC 5114(其他 DH 命名群組,包括「dh_1024_160」、「dh_2048_224」和「dh_2048_256」)。
SP800-56Ar3 的下列章節
- 5.5.1.1 FFC 域參數選取/產生
- 附錄 D:FFC 安全質數群組
FIPS186-4 的下列章節
- A.1.1.2 使用核准的雜湊函數產生可能的質數 p 和 q。
- A.2.3 產生正規產生器 g。
- A.2.1 產生器 g 的不可驗證產生。
另請參閱
EVP_PKEY-FFC(7)、EVP_KEYEXCH-DH(7) EVP_PKEY(3)、provider-keymgmt(7)、EVP_KEYMGMT(3)、OSSL_PROVIDER-default(7)、OSSL_PROVIDER-FIPS(7)
版權
版權所有 2020-2021 OpenSSL 專案作者。保留所有權利。
依據 Apache 授權 2.0(「授權」)授權。您不得使用此檔案,除非符合授權規定。您可以在原始程式碼散佈中的 LICENSE 檔案中取得一份副本,或於 https://www.openssl.org/source/license.html 取得。