Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*  Diffie-Hellman Key Agreement Method [RFC2631]
0003  *
0004  * Copyright (c) 2016, Intel Corporation
0005  * Authors: Salvatore Benedetto <salvatore.benedetto@intel.com>
0006  */
0007 
0008 #include <linux/fips.h>
0009 #include <linux/module.h>
0010 #include <crypto/internal/kpp.h>
0011 #include <crypto/kpp.h>
0012 #include <crypto/dh.h>
0013 #include <crypto/rng.h>
0014 #include <linux/mpi.h>
0015 
0016 struct dh_ctx {
0017     MPI p;  /* Value is guaranteed to be set. */
0018     MPI g;  /* Value is guaranteed to be set. */
0019     MPI xa; /* Value is guaranteed to be set. */
0020 };
0021 
0022 static void dh_clear_ctx(struct dh_ctx *ctx)
0023 {
0024     mpi_free(ctx->p);
0025     mpi_free(ctx->g);
0026     mpi_free(ctx->xa);
0027     memset(ctx, 0, sizeof(*ctx));
0028 }
0029 
0030 /*
0031  * If base is g we compute the public key
0032  *  ya = g^xa mod p; [RFC2631 sec 2.1.1]
0033  * else if base if the counterpart public key we compute the shared secret
0034  *  ZZ = yb^xa mod p; [RFC2631 sec 2.1.1]
0035  */
0036 static int _compute_val(const struct dh_ctx *ctx, MPI base, MPI val)
0037 {
0038     /* val = base^xa mod p */
0039     return mpi_powm(val, base, ctx->xa, ctx->p);
0040 }
0041 
0042 static inline struct dh_ctx *dh_get_ctx(struct crypto_kpp *tfm)
0043 {
0044     return kpp_tfm_ctx(tfm);
0045 }
0046 
0047 static int dh_check_params_length(unsigned int p_len)
0048 {
0049     if (fips_enabled)
0050         return (p_len < 2048) ? -EINVAL : 0;
0051 
0052     return (p_len < 1536) ? -EINVAL : 0;
0053 }
0054 
0055 static int dh_set_params(struct dh_ctx *ctx, struct dh *params)
0056 {
0057     if (dh_check_params_length(params->p_size << 3))
0058         return -EINVAL;
0059 
0060     ctx->p = mpi_read_raw_data(params->p, params->p_size);
0061     if (!ctx->p)
0062         return -EINVAL;
0063 
0064     ctx->g = mpi_read_raw_data(params->g, params->g_size);
0065     if (!ctx->g)
0066         return -EINVAL;
0067 
0068     return 0;
0069 }
0070 
0071 static int dh_set_secret(struct crypto_kpp *tfm, const void *buf,
0072              unsigned int len)
0073 {
0074     struct dh_ctx *ctx = dh_get_ctx(tfm);
0075     struct dh params;
0076 
0077     /* Free the old MPI key if any */
0078     dh_clear_ctx(ctx);
0079 
0080     if (crypto_dh_decode_key(buf, len, &params) < 0)
0081         goto err_clear_ctx;
0082 
0083     if (dh_set_params(ctx, &params) < 0)
0084         goto err_clear_ctx;
0085 
0086     ctx->xa = mpi_read_raw_data(params.key, params.key_size);
0087     if (!ctx->xa)
0088         goto err_clear_ctx;
0089 
0090     return 0;
0091 
0092 err_clear_ctx:
0093     dh_clear_ctx(ctx);
0094     return -EINVAL;
0095 }
0096 
0097 /*
0098  * SP800-56A public key verification:
0099  *
0100  * * For the safe-prime groups in FIPS mode, Q can be computed
0101  *   trivially from P and a full validation according to SP800-56A
0102  *   section 5.6.2.3.1 is performed.
0103  *
0104  * * For all other sets of group parameters, only a partial validation
0105  *   according to SP800-56A section 5.6.2.3.2 is performed.
0106  */
0107 static int dh_is_pubkey_valid(struct dh_ctx *ctx, MPI y)
0108 {
0109     if (unlikely(!ctx->p))
0110         return -EINVAL;
0111 
0112     /*
0113      * Step 1: Verify that 2 <= y <= p - 2.
0114      *
0115      * The upper limit check is actually y < p instead of y < p - 1
0116      * in order to save one mpi_sub_ui() invocation here. Note that
0117      * p - 1 is the non-trivial element of the subgroup of order 2 and
0118      * thus, the check on y^q below would fail if y == p - 1.
0119      */
0120     if (mpi_cmp_ui(y, 1) < 1 || mpi_cmp(y, ctx->p) >= 0)
0121         return -EINVAL;
0122 
0123     /*
0124      * Step 2: Verify that 1 = y^q mod p
0125      *
0126      * For the safe-prime groups q = (p - 1)/2.
0127      */
0128     if (fips_enabled) {
0129         MPI val, q;
0130         int ret;
0131 
0132         val = mpi_alloc(0);
0133         if (!val)
0134             return -ENOMEM;
0135 
0136         q = mpi_alloc(mpi_get_nlimbs(ctx->p));
0137         if (!q) {
0138             mpi_free(val);
0139             return -ENOMEM;
0140         }
0141 
0142         /*
0143          * ->p is odd, so no need to explicitly subtract one
0144          * from it before shifting to the right.
0145          */
0146         mpi_rshift(q, ctx->p, 1);
0147 
0148         ret = mpi_powm(val, y, q, ctx->p);
0149         mpi_free(q);
0150         if (ret) {
0151             mpi_free(val);
0152             return ret;
0153         }
0154 
0155         ret = mpi_cmp_ui(val, 1);
0156 
0157         mpi_free(val);
0158 
0159         if (ret != 0)
0160             return -EINVAL;
0161     }
0162 
0163     return 0;
0164 }
0165 
0166 static int dh_compute_value(struct kpp_request *req)
0167 {
0168     struct crypto_kpp *tfm = crypto_kpp_reqtfm(req);
0169     struct dh_ctx *ctx = dh_get_ctx(tfm);
0170     MPI base, val = mpi_alloc(0);
0171     int ret = 0;
0172     int sign;
0173 
0174     if (!val)
0175         return -ENOMEM;
0176 
0177     if (unlikely(!ctx->xa)) {
0178         ret = -EINVAL;
0179         goto err_free_val;
0180     }
0181 
0182     if (req->src) {
0183         base = mpi_read_raw_from_sgl(req->src, req->src_len);
0184         if (!base) {
0185             ret = -EINVAL;
0186             goto err_free_val;
0187         }
0188         ret = dh_is_pubkey_valid(ctx, base);
0189         if (ret)
0190             goto err_free_base;
0191     } else {
0192         base = ctx->g;
0193     }
0194 
0195     ret = _compute_val(ctx, base, val);
0196     if (ret)
0197         goto err_free_base;
0198 
0199     if (fips_enabled) {
0200         /* SP800-56A rev3 5.7.1.1 check: Validation of shared secret */
0201         if (req->src) {
0202             MPI pone;
0203 
0204             /* z <= 1 */
0205             if (mpi_cmp_ui(val, 1) < 1) {
0206                 ret = -EBADMSG;
0207                 goto err_free_base;
0208             }
0209 
0210             /* z == p - 1 */
0211             pone = mpi_alloc(0);
0212 
0213             if (!pone) {
0214                 ret = -ENOMEM;
0215                 goto err_free_base;
0216             }
0217 
0218             ret = mpi_sub_ui(pone, ctx->p, 1);
0219             if (!ret && !mpi_cmp(pone, val))
0220                 ret = -EBADMSG;
0221 
0222             mpi_free(pone);
0223 
0224             if (ret)
0225                 goto err_free_base;
0226 
0227         /* SP800-56A rev 3 5.6.2.1.3 key check */
0228         } else {
0229             if (dh_is_pubkey_valid(ctx, val)) {
0230                 ret = -EAGAIN;
0231                 goto err_free_val;
0232             }
0233         }
0234     }
0235 
0236     ret = mpi_write_to_sgl(val, req->dst, req->dst_len, &sign);
0237     if (ret)
0238         goto err_free_base;
0239 
0240     if (sign < 0)
0241         ret = -EBADMSG;
0242 err_free_base:
0243     if (req->src)
0244         mpi_free(base);
0245 err_free_val:
0246     mpi_free(val);
0247     return ret;
0248 }
0249 
0250 static unsigned int dh_max_size(struct crypto_kpp *tfm)
0251 {
0252     struct dh_ctx *ctx = dh_get_ctx(tfm);
0253 
0254     return mpi_get_size(ctx->p);
0255 }
0256 
0257 static void dh_exit_tfm(struct crypto_kpp *tfm)
0258 {
0259     struct dh_ctx *ctx = dh_get_ctx(tfm);
0260 
0261     dh_clear_ctx(ctx);
0262 }
0263 
0264 static struct kpp_alg dh = {
0265     .set_secret = dh_set_secret,
0266     .generate_public_key = dh_compute_value,
0267     .compute_shared_secret = dh_compute_value,
0268     .max_size = dh_max_size,
0269     .exit = dh_exit_tfm,
0270     .base = {
0271         .cra_name = "dh",
0272         .cra_driver_name = "dh-generic",
0273         .cra_priority = 100,
0274         .cra_module = THIS_MODULE,
0275         .cra_ctxsize = sizeof(struct dh_ctx),
0276     },
0277 };
0278 
0279 
0280 struct dh_safe_prime {
0281     unsigned int max_strength;
0282     unsigned int p_size;
0283     const char *p;
0284 };
0285 
0286 static const char safe_prime_g[]  = { 2 };
0287 
0288 struct dh_safe_prime_instance_ctx {
0289     struct crypto_kpp_spawn dh_spawn;
0290     const struct dh_safe_prime *safe_prime;
0291 };
0292 
0293 struct dh_safe_prime_tfm_ctx {
0294     struct crypto_kpp *dh_tfm;
0295 };
0296 
0297 static void dh_safe_prime_free_instance(struct kpp_instance *inst)
0298 {
0299     struct dh_safe_prime_instance_ctx *ctx = kpp_instance_ctx(inst);
0300 
0301     crypto_drop_kpp(&ctx->dh_spawn);
0302     kfree(inst);
0303 }
0304 
0305 static inline struct dh_safe_prime_instance_ctx *dh_safe_prime_instance_ctx(
0306     struct crypto_kpp *tfm)
0307 {
0308     return kpp_instance_ctx(kpp_alg_instance(tfm));
0309 }
0310 
0311 static int dh_safe_prime_init_tfm(struct crypto_kpp *tfm)
0312 {
0313     struct dh_safe_prime_instance_ctx *inst_ctx =
0314         dh_safe_prime_instance_ctx(tfm);
0315     struct dh_safe_prime_tfm_ctx *tfm_ctx = kpp_tfm_ctx(tfm);
0316 
0317     tfm_ctx->dh_tfm = crypto_spawn_kpp(&inst_ctx->dh_spawn);
0318     if (IS_ERR(tfm_ctx->dh_tfm))
0319         return PTR_ERR(tfm_ctx->dh_tfm);
0320 
0321     return 0;
0322 }
0323 
0324 static void dh_safe_prime_exit_tfm(struct crypto_kpp *tfm)
0325 {
0326     struct dh_safe_prime_tfm_ctx *tfm_ctx = kpp_tfm_ctx(tfm);
0327 
0328     crypto_free_kpp(tfm_ctx->dh_tfm);
0329 }
0330 
0331 static u64 __add_u64_to_be(__be64 *dst, unsigned int n, u64 val)
0332 {
0333     unsigned int i;
0334 
0335     for (i = n; val && i > 0; --i) {
0336         u64 tmp = be64_to_cpu(dst[i - 1]);
0337 
0338         tmp += val;
0339         val = tmp >= val ? 0 : 1;
0340         dst[i - 1] = cpu_to_be64(tmp);
0341     }
0342 
0343     return val;
0344 }
0345 
0346 static void *dh_safe_prime_gen_privkey(const struct dh_safe_prime *safe_prime,
0347                        unsigned int *key_size)
0348 {
0349     unsigned int n, oversampling_size;
0350     __be64 *key;
0351     int err;
0352     u64 h, o;
0353 
0354     /*
0355      * Generate a private key following NIST SP800-56Ar3,
0356      * sec. 5.6.1.1.1 and 5.6.1.1.3 resp..
0357      *
0358      * 5.6.1.1.1: choose key length N such that
0359      * 2 * ->max_strength <= N <= log2(q) + 1 = ->p_size * 8 - 1
0360      * with q = (p - 1) / 2 for the safe-prime groups.
0361      * Choose the lower bound's next power of two for N in order to
0362      * avoid excessively large private keys while still
0363      * maintaining some extra reserve beyond the bare minimum in
0364      * most cases. Note that for each entry in safe_prime_groups[],
0365      * the following holds for such N:
0366      * - N >= 256, in particular it is a multiple of 2^6 = 64
0367      *   bits and
0368      * - N < log2(q) + 1, i.e. N respects the upper bound.
0369      */
0370     n = roundup_pow_of_two(2 * safe_prime->max_strength);
0371     WARN_ON_ONCE(n & ((1u << 6) - 1));
0372     n >>= 6; /* Convert N into units of u64. */
0373 
0374     /*
0375      * Reserve one extra u64 to hold the extra random bits
0376      * required as per 5.6.1.1.3.
0377      */
0378     oversampling_size = (n + 1) * sizeof(__be64);
0379     key = kmalloc(oversampling_size, GFP_KERNEL);
0380     if (!key)
0381         return ERR_PTR(-ENOMEM);
0382 
0383     /*
0384      * 5.6.1.1.3, step 3 (and implicitly step 4): obtain N + 64
0385      * random bits and interpret them as a big endian integer.
0386      */
0387     err = -EFAULT;
0388     if (crypto_get_default_rng())
0389         goto out_err;
0390 
0391     err = crypto_rng_get_bytes(crypto_default_rng, (u8 *)key,
0392                    oversampling_size);
0393     crypto_put_default_rng();
0394     if (err)
0395         goto out_err;
0396 
0397     /*
0398      * 5.6.1.1.3, step 5 is implicit: 2^N < q and thus,
0399      * M = min(2^N, q) = 2^N.
0400      *
0401      * For step 6, calculate
0402      * key = (key[] mod (M - 1)) + 1 = (key[] mod (2^N - 1)) + 1.
0403      *
0404      * In order to avoid expensive divisions, note that
0405      * 2^N mod (2^N - 1) = 1 and thus, for any integer h,
0406      * 2^N * h mod (2^N - 1) = h mod (2^N - 1) always holds.
0407      * The big endian integer key[] composed of n + 1 64bit words
0408      * may be written as key[] = h * 2^N + l, with h = key[0]
0409      * representing the 64 most significant bits and l
0410      * corresponding to the remaining 2^N bits. With the remark
0411      * from above,
0412      * h * 2^N + l mod (2^N - 1) = l + h mod (2^N - 1).
0413      * As both, l and h are less than 2^N, their sum after
0414      * this first reduction is guaranteed to be <= 2^(N + 1) - 2.
0415      * Or equivalently, that their sum can again be written as
0416      * h' * 2^N + l' with h' now either zero or one and if one,
0417      * then l' <= 2^N - 2. Thus, all bits at positions >= N will
0418      * be zero after a second reduction:
0419      * h' * 2^N + l' mod (2^N - 1) = l' + h' mod (2^N - 1).
0420      * At this point, it is still possible that
0421      * l' + h' = 2^N - 1, i.e. that l' + h' mod (2^N - 1)
0422      * is zero. This condition will be detected below by means of
0423      * the final increment overflowing in this case.
0424      */
0425     h = be64_to_cpu(key[0]);
0426     h = __add_u64_to_be(key + 1, n, h);
0427     h = __add_u64_to_be(key + 1, n, h);
0428     WARN_ON_ONCE(h);
0429 
0430     /* Increment to obtain the final result. */
0431     o = __add_u64_to_be(key + 1, n, 1);
0432     /*
0433      * The overflow bit o from the increment is either zero or
0434      * one. If zero, key[1:n] holds the final result in big-endian
0435      * order. If one, key[1:n] is zero now, but needs to be set to
0436      * one, c.f. above.
0437      */
0438     if (o)
0439         key[n] = cpu_to_be64(1);
0440 
0441     /* n is in units of u64, convert to bytes. */
0442     *key_size = n << 3;
0443     /* Strip the leading extra __be64, which is (virtually) zero by now. */
0444     memmove(key, &key[1], *key_size);
0445 
0446     return key;
0447 
0448 out_err:
0449     kfree_sensitive(key);
0450     return ERR_PTR(err);
0451 }
0452 
0453 static int dh_safe_prime_set_secret(struct crypto_kpp *tfm, const void *buffer,
0454                     unsigned int len)
0455 {
0456     struct dh_safe_prime_instance_ctx *inst_ctx =
0457         dh_safe_prime_instance_ctx(tfm);
0458     struct dh_safe_prime_tfm_ctx *tfm_ctx = kpp_tfm_ctx(tfm);
0459     struct dh params = {};
0460     void *buf = NULL, *key = NULL;
0461     unsigned int buf_size;
0462     int err;
0463 
0464     if (buffer) {
0465         err = __crypto_dh_decode_key(buffer, len, &params);
0466         if (err)
0467             return err;
0468         if (params.p_size || params.g_size)
0469             return -EINVAL;
0470     }
0471 
0472     params.p = inst_ctx->safe_prime->p;
0473     params.p_size = inst_ctx->safe_prime->p_size;
0474     params.g = safe_prime_g;
0475     params.g_size = sizeof(safe_prime_g);
0476 
0477     if (!params.key_size) {
0478         key = dh_safe_prime_gen_privkey(inst_ctx->safe_prime,
0479                         &params.key_size);
0480         if (IS_ERR(key))
0481             return PTR_ERR(key);
0482         params.key = key;
0483     }
0484 
0485     buf_size = crypto_dh_key_len(&params);
0486     buf = kmalloc(buf_size, GFP_KERNEL);
0487     if (!buf) {
0488         err = -ENOMEM;
0489         goto out;
0490     }
0491 
0492     err = crypto_dh_encode_key(buf, buf_size, &params);
0493     if (err)
0494         goto out;
0495 
0496     err = crypto_kpp_set_secret(tfm_ctx->dh_tfm, buf, buf_size);
0497 out:
0498     kfree_sensitive(buf);
0499     kfree_sensitive(key);
0500     return err;
0501 }
0502 
0503 static void dh_safe_prime_complete_req(struct crypto_async_request *dh_req,
0504                        int err)
0505 {
0506     struct kpp_request *req = dh_req->data;
0507 
0508     kpp_request_complete(req, err);
0509 }
0510 
0511 static struct kpp_request *dh_safe_prime_prepare_dh_req(struct kpp_request *req)
0512 {
0513     struct dh_safe_prime_tfm_ctx *tfm_ctx =
0514         kpp_tfm_ctx(crypto_kpp_reqtfm(req));
0515     struct kpp_request *dh_req = kpp_request_ctx(req);
0516 
0517     kpp_request_set_tfm(dh_req, tfm_ctx->dh_tfm);
0518     kpp_request_set_callback(dh_req, req->base.flags,
0519                  dh_safe_prime_complete_req, req);
0520 
0521     kpp_request_set_input(dh_req, req->src, req->src_len);
0522     kpp_request_set_output(dh_req, req->dst, req->dst_len);
0523 
0524     return dh_req;
0525 }
0526 
0527 static int dh_safe_prime_generate_public_key(struct kpp_request *req)
0528 {
0529     struct kpp_request *dh_req = dh_safe_prime_prepare_dh_req(req);
0530 
0531     return crypto_kpp_generate_public_key(dh_req);
0532 }
0533 
0534 static int dh_safe_prime_compute_shared_secret(struct kpp_request *req)
0535 {
0536     struct kpp_request *dh_req = dh_safe_prime_prepare_dh_req(req);
0537 
0538     return crypto_kpp_compute_shared_secret(dh_req);
0539 }
0540 
0541 static unsigned int dh_safe_prime_max_size(struct crypto_kpp *tfm)
0542 {
0543     struct dh_safe_prime_tfm_ctx *tfm_ctx = kpp_tfm_ctx(tfm);
0544 
0545     return crypto_kpp_maxsize(tfm_ctx->dh_tfm);
0546 }
0547 
0548 static int __maybe_unused __dh_safe_prime_create(
0549     struct crypto_template *tmpl, struct rtattr **tb,
0550     const struct dh_safe_prime *safe_prime)
0551 {
0552     struct kpp_instance *inst;
0553     struct dh_safe_prime_instance_ctx *ctx;
0554     const char *dh_name;
0555     struct kpp_alg *dh_alg;
0556     u32 mask;
0557     int err;
0558 
0559     err = crypto_check_attr_type(tb, CRYPTO_ALG_TYPE_KPP, &mask);
0560     if (err)
0561         return err;
0562 
0563     dh_name = crypto_attr_alg_name(tb[1]);
0564     if (IS_ERR(dh_name))
0565         return PTR_ERR(dh_name);
0566 
0567     inst = kzalloc(sizeof(*inst) + sizeof(*ctx), GFP_KERNEL);
0568     if (!inst)
0569         return -ENOMEM;
0570 
0571     ctx = kpp_instance_ctx(inst);
0572 
0573     err = crypto_grab_kpp(&ctx->dh_spawn, kpp_crypto_instance(inst),
0574                   dh_name, 0, mask);
0575     if (err)
0576         goto err_free_inst;
0577 
0578     err = -EINVAL;
0579     dh_alg = crypto_spawn_kpp_alg(&ctx->dh_spawn);
0580     if (strcmp(dh_alg->base.cra_name, "dh"))
0581         goto err_free_inst;
0582 
0583     ctx->safe_prime = safe_prime;
0584 
0585     err = crypto_inst_setname(kpp_crypto_instance(inst),
0586                   tmpl->name, &dh_alg->base);
0587     if (err)
0588         goto err_free_inst;
0589 
0590     inst->alg.set_secret = dh_safe_prime_set_secret;
0591     inst->alg.generate_public_key = dh_safe_prime_generate_public_key;
0592     inst->alg.compute_shared_secret = dh_safe_prime_compute_shared_secret;
0593     inst->alg.max_size = dh_safe_prime_max_size;
0594     inst->alg.init = dh_safe_prime_init_tfm;
0595     inst->alg.exit = dh_safe_prime_exit_tfm;
0596     inst->alg.reqsize = sizeof(struct kpp_request) + dh_alg->reqsize;
0597     inst->alg.base.cra_priority = dh_alg->base.cra_priority;
0598     inst->alg.base.cra_module = THIS_MODULE;
0599     inst->alg.base.cra_ctxsize = sizeof(struct dh_safe_prime_tfm_ctx);
0600 
0601     inst->free = dh_safe_prime_free_instance;
0602 
0603     err = kpp_register_instance(tmpl, inst);
0604     if (err)
0605         goto err_free_inst;
0606 
0607     return 0;
0608 
0609 err_free_inst:
0610     dh_safe_prime_free_instance(inst);
0611 
0612     return err;
0613 }
0614 
0615 #ifdef CONFIG_CRYPTO_DH_RFC7919_GROUPS
0616 
0617 static const struct dh_safe_prime ffdhe2048_prime = {
0618     .max_strength = 112,
0619     .p_size = 256,
0620     .p =
0621     "\xff\xff\xff\xff\xff\xff\xff\xff\xad\xf8\x54\x58\xa2\xbb\x4a\x9a"
0622     "\xaf\xdc\x56\x20\x27\x3d\x3c\xf1\xd8\xb9\xc5\x83\xce\x2d\x36\x95"
0623     "\xa9\xe1\x36\x41\x14\x64\x33\xfb\xcc\x93\x9d\xce\x24\x9b\x3e\xf9"
0624     "\x7d\x2f\xe3\x63\x63\x0c\x75\xd8\xf6\x81\xb2\x02\xae\xc4\x61\x7a"
0625     "\xd3\xdf\x1e\xd5\xd5\xfd\x65\x61\x24\x33\xf5\x1f\x5f\x06\x6e\xd0"
0626     "\x85\x63\x65\x55\x3d\xed\x1a\xf3\xb5\x57\x13\x5e\x7f\x57\xc9\x35"
0627     "\x98\x4f\x0c\x70\xe0\xe6\x8b\x77\xe2\xa6\x89\xda\xf3\xef\xe8\x72"
0628     "\x1d\xf1\x58\xa1\x36\xad\xe7\x35\x30\xac\xca\x4f\x48\x3a\x79\x7a"
0629     "\xbc\x0a\xb1\x82\xb3\x24\xfb\x61\xd1\x08\xa9\x4b\xb2\xc8\xe3\xfb"
0630     "\xb9\x6a\xda\xb7\x60\xd7\xf4\x68\x1d\x4f\x42\xa3\xde\x39\x4d\xf4"
0631     "\xae\x56\xed\xe7\x63\x72\xbb\x19\x0b\x07\xa7\xc8\xee\x0a\x6d\x70"
0632     "\x9e\x02\xfc\xe1\xcd\xf7\xe2\xec\xc0\x34\x04\xcd\x28\x34\x2f\x61"
0633     "\x91\x72\xfe\x9c\xe9\x85\x83\xff\x8e\x4f\x12\x32\xee\xf2\x81\x83"
0634     "\xc3\xfe\x3b\x1b\x4c\x6f\xad\x73\x3b\xb5\xfc\xbc\x2e\xc2\x20\x05"
0635     "\xc5\x8e\xf1\x83\x7d\x16\x83\xb2\xc6\xf3\x4a\x26\xc1\xb2\xef\xfa"
0636     "\x88\x6b\x42\x38\x61\x28\x5c\x97\xff\xff\xff\xff\xff\xff\xff\xff",
0637 };
0638 
0639 static const struct dh_safe_prime ffdhe3072_prime = {
0640     .max_strength = 128,
0641     .p_size = 384,
0642     .p =
0643     "\xff\xff\xff\xff\xff\xff\xff\xff\xad\xf8\x54\x58\xa2\xbb\x4a\x9a"
0644     "\xaf\xdc\x56\x20\x27\x3d\x3c\xf1\xd8\xb9\xc5\x83\xce\x2d\x36\x95"
0645     "\xa9\xe1\x36\x41\x14\x64\x33\xfb\xcc\x93\x9d\xce\x24\x9b\x3e\xf9"
0646     "\x7d\x2f\xe3\x63\x63\x0c\x75\xd8\xf6\x81\xb2\x02\xae\xc4\x61\x7a"
0647     "\xd3\xdf\x1e\xd5\xd5\xfd\x65\x61\x24\x33\xf5\x1f\x5f\x06\x6e\xd0"
0648     "\x85\x63\x65\x55\x3d\xed\x1a\xf3\xb5\x57\x13\x5e\x7f\x57\xc9\x35"
0649     "\x98\x4f\x0c\x70\xe0\xe6\x8b\x77\xe2\xa6\x89\xda\xf3\xef\xe8\x72"
0650     "\x1d\xf1\x58\xa1\x36\xad\xe7\x35\x30\xac\xca\x4f\x48\x3a\x79\x7a"
0651     "\xbc\x0a\xb1\x82\xb3\x24\xfb\x61\xd1\x08\xa9\x4b\xb2\xc8\xe3\xfb"
0652     "\xb9\x6a\xda\xb7\x60\xd7\xf4\x68\x1d\x4f\x42\xa3\xde\x39\x4d\xf4"
0653     "\xae\x56\xed\xe7\x63\x72\xbb\x19\x0b\x07\xa7\xc8\xee\x0a\x6d\x70"
0654     "\x9e\x02\xfc\xe1\xcd\xf7\xe2\xec\xc0\x34\x04\xcd\x28\x34\x2f\x61"
0655     "\x91\x72\xfe\x9c\xe9\x85\x83\xff\x8e\x4f\x12\x32\xee\xf2\x81\x83"
0656     "\xc3\xfe\x3b\x1b\x4c\x6f\xad\x73\x3b\xb5\xfc\xbc\x2e\xc2\x20\x05"
0657     "\xc5\x8e\xf1\x83\x7d\x16\x83\xb2\xc6\xf3\x4a\x26\xc1\xb2\xef\xfa"
0658     "\x88\x6b\x42\x38\x61\x1f\xcf\xdc\xde\x35\x5b\x3b\x65\x19\x03\x5b"
0659     "\xbc\x34\xf4\xde\xf9\x9c\x02\x38\x61\xb4\x6f\xc9\xd6\xe6\xc9\x07"
0660     "\x7a\xd9\x1d\x26\x91\xf7\xf7\xee\x59\x8c\xb0\xfa\xc1\x86\xd9\x1c"
0661     "\xae\xfe\x13\x09\x85\x13\x92\x70\xb4\x13\x0c\x93\xbc\x43\x79\x44"
0662     "\xf4\xfd\x44\x52\xe2\xd7\x4d\xd3\x64\xf2\xe2\x1e\x71\xf5\x4b\xff"
0663     "\x5c\xae\x82\xab\x9c\x9d\xf6\x9e\xe8\x6d\x2b\xc5\x22\x36\x3a\x0d"
0664     "\xab\xc5\x21\x97\x9b\x0d\xea\xda\x1d\xbf\x9a\x42\xd5\xc4\x48\x4e"
0665     "\x0a\xbc\xd0\x6b\xfa\x53\xdd\xef\x3c\x1b\x20\xee\x3f\xd5\x9d\x7c"
0666     "\x25\xe4\x1d\x2b\x66\xc6\x2e\x37\xff\xff\xff\xff\xff\xff\xff\xff",
0667 };
0668 
0669 static const struct dh_safe_prime ffdhe4096_prime = {
0670     .max_strength = 152,
0671     .p_size = 512,
0672     .p =
0673     "\xff\xff\xff\xff\xff\xff\xff\xff\xad\xf8\x54\x58\xa2\xbb\x4a\x9a"
0674     "\xaf\xdc\x56\x20\x27\x3d\x3c\xf1\xd8\xb9\xc5\x83\xce\x2d\x36\x95"
0675     "\xa9\xe1\x36\x41\x14\x64\x33\xfb\xcc\x93\x9d\xce\x24\x9b\x3e\xf9"
0676     "\x7d\x2f\xe3\x63\x63\x0c\x75\xd8\xf6\x81\xb2\x02\xae\xc4\x61\x7a"
0677     "\xd3\xdf\x1e\xd5\xd5\xfd\x65\x61\x24\x33\xf5\x1f\x5f\x06\x6e\xd0"
0678     "\x85\x63\x65\x55\x3d\xed\x1a\xf3\xb5\x57\x13\x5e\x7f\x57\xc9\x35"
0679     "\x98\x4f\x0c\x70\xe0\xe6\x8b\x77\xe2\xa6\x89\xda\xf3\xef\xe8\x72"
0680     "\x1d\xf1\x58\xa1\x36\xad\xe7\x35\x30\xac\xca\x4f\x48\x3a\x79\x7a"
0681     "\xbc\x0a\xb1\x82\xb3\x24\xfb\x61\xd1\x08\xa9\x4b\xb2\xc8\xe3\xfb"
0682     "\xb9\x6a\xda\xb7\x60\xd7\xf4\x68\x1d\x4f\x42\xa3\xde\x39\x4d\xf4"
0683     "\xae\x56\xed\xe7\x63\x72\xbb\x19\x0b\x07\xa7\xc8\xee\x0a\x6d\x70"
0684     "\x9e\x02\xfc\xe1\xcd\xf7\xe2\xec\xc0\x34\x04\xcd\x28\x34\x2f\x61"
0685     "\x91\x72\xfe\x9c\xe9\x85\x83\xff\x8e\x4f\x12\x32\xee\xf2\x81\x83"
0686     "\xc3\xfe\x3b\x1b\x4c\x6f\xad\x73\x3b\xb5\xfc\xbc\x2e\xc2\x20\x05"
0687     "\xc5\x8e\xf1\x83\x7d\x16\x83\xb2\xc6\xf3\x4a\x26\xc1\xb2\xef\xfa"
0688     "\x88\x6b\x42\x38\x61\x1f\xcf\xdc\xde\x35\x5b\x3b\x65\x19\x03\x5b"
0689     "\xbc\x34\xf4\xde\xf9\x9c\x02\x38\x61\xb4\x6f\xc9\xd6\xe6\xc9\x07"
0690     "\x7a\xd9\x1d\x26\x91\xf7\xf7\xee\x59\x8c\xb0\xfa\xc1\x86\xd9\x1c"
0691     "\xae\xfe\x13\x09\x85\x13\x92\x70\xb4\x13\x0c\x93\xbc\x43\x79\x44"
0692     "\xf4\xfd\x44\x52\xe2\xd7\x4d\xd3\x64\xf2\xe2\x1e\x71\xf5\x4b\xff"
0693     "\x5c\xae\x82\xab\x9c\x9d\xf6\x9e\xe8\x6d\x2b\xc5\x22\x36\x3a\x0d"
0694     "\xab\xc5\x21\x97\x9b\x0d\xea\xda\x1d\xbf\x9a\x42\xd5\xc4\x48\x4e"
0695     "\x0a\xbc\xd0\x6b\xfa\x53\xdd\xef\x3c\x1b\x20\xee\x3f\xd5\x9d\x7c"
0696     "\x25\xe4\x1d\x2b\x66\x9e\x1e\xf1\x6e\x6f\x52\xc3\x16\x4d\xf4\xfb"
0697     "\x79\x30\xe9\xe4\xe5\x88\x57\xb6\xac\x7d\x5f\x42\xd6\x9f\x6d\x18"
0698     "\x77\x63\xcf\x1d\x55\x03\x40\x04\x87\xf5\x5b\xa5\x7e\x31\xcc\x7a"
0699     "\x71\x35\xc8\x86\xef\xb4\x31\x8a\xed\x6a\x1e\x01\x2d\x9e\x68\x32"
0700     "\xa9\x07\x60\x0a\x91\x81\x30\xc4\x6d\xc7\x78\xf9\x71\xad\x00\x38"
0701     "\x09\x29\x99\xa3\x33\xcb\x8b\x7a\x1a\x1d\xb9\x3d\x71\x40\x00\x3c"
0702     "\x2a\x4e\xce\xa9\xf9\x8d\x0a\xcc\x0a\x82\x91\xcd\xce\xc9\x7d\xcf"
0703     "\x8e\xc9\xb5\x5a\x7f\x88\xa4\x6b\x4d\xb5\xa8\x51\xf4\x41\x82\xe1"
0704     "\xc6\x8a\x00\x7e\x5e\x65\x5f\x6a\xff\xff\xff\xff\xff\xff\xff\xff",
0705 };
0706 
0707 static const struct dh_safe_prime ffdhe6144_prime = {
0708     .max_strength = 176,
0709     .p_size = 768,
0710     .p =
0711     "\xff\xff\xff\xff\xff\xff\xff\xff\xad\xf8\x54\x58\xa2\xbb\x4a\x9a"
0712     "\xaf\xdc\x56\x20\x27\x3d\x3c\xf1\xd8\xb9\xc5\x83\xce\x2d\x36\x95"
0713     "\xa9\xe1\x36\x41\x14\x64\x33\xfb\xcc\x93\x9d\xce\x24\x9b\x3e\xf9"
0714     "\x7d\x2f\xe3\x63\x63\x0c\x75\xd8\xf6\x81\xb2\x02\xae\xc4\x61\x7a"
0715     "\xd3\xdf\x1e\xd5\xd5\xfd\x65\x61\x24\x33\xf5\x1f\x5f\x06\x6e\xd0"
0716     "\x85\x63\x65\x55\x3d\xed\x1a\xf3\xb5\x57\x13\x5e\x7f\x57\xc9\x35"
0717     "\x98\x4f\x0c\x70\xe0\xe6\x8b\x77\xe2\xa6\x89\xda\xf3\xef\xe8\x72"
0718     "\x1d\xf1\x58\xa1\x36\xad\xe7\x35\x30\xac\xca\x4f\x48\x3a\x79\x7a"
0719     "\xbc\x0a\xb1\x82\xb3\x24\xfb\x61\xd1\x08\xa9\x4b\xb2\xc8\xe3\xfb"
0720     "\xb9\x6a\xda\xb7\x60\xd7\xf4\x68\x1d\x4f\x42\xa3\xde\x39\x4d\xf4"
0721     "\xae\x56\xed\xe7\x63\x72\xbb\x19\x0b\x07\xa7\xc8\xee\x0a\x6d\x70"
0722     "\x9e\x02\xfc\xe1\xcd\xf7\xe2\xec\xc0\x34\x04\xcd\x28\x34\x2f\x61"
0723     "\x91\x72\xfe\x9c\xe9\x85\x83\xff\x8e\x4f\x12\x32\xee\xf2\x81\x83"
0724     "\xc3\xfe\x3b\x1b\x4c\x6f\xad\x73\x3b\xb5\xfc\xbc\x2e\xc2\x20\x05"
0725     "\xc5\x8e\xf1\x83\x7d\x16\x83\xb2\xc6\xf3\x4a\x26\xc1\xb2\xef\xfa"
0726     "\x88\x6b\x42\x38\x61\x1f\xcf\xdc\xde\x35\x5b\x3b\x65\x19\x03\x5b"
0727     "\xbc\x34\xf4\xde\xf9\x9c\x02\x38\x61\xb4\x6f\xc9\xd6\xe6\xc9\x07"
0728     "\x7a\xd9\x1d\x26\x91\xf7\xf7\xee\x59\x8c\xb0\xfa\xc1\x86\xd9\x1c"
0729     "\xae\xfe\x13\x09\x85\x13\x92\x70\xb4\x13\x0c\x93\xbc\x43\x79\x44"
0730     "\xf4\xfd\x44\x52\xe2\xd7\x4d\xd3\x64\xf2\xe2\x1e\x71\xf5\x4b\xff"
0731     "\x5c\xae\x82\xab\x9c\x9d\xf6\x9e\xe8\x6d\x2b\xc5\x22\x36\x3a\x0d"
0732     "\xab\xc5\x21\x97\x9b\x0d\xea\xda\x1d\xbf\x9a\x42\xd5\xc4\x48\x4e"
0733     "\x0a\xbc\xd0\x6b\xfa\x53\xdd\xef\x3c\x1b\x20\xee\x3f\xd5\x9d\x7c"
0734     "\x25\xe4\x1d\x2b\x66\x9e\x1e\xf1\x6e\x6f\x52\xc3\x16\x4d\xf4\xfb"
0735     "\x79\x30\xe9\xe4\xe5\x88\x57\xb6\xac\x7d\x5f\x42\xd6\x9f\x6d\x18"
0736     "\x77\x63\xcf\x1d\x55\x03\x40\x04\x87\xf5\x5b\xa5\x7e\x31\xcc\x7a"
0737     "\x71\x35\xc8\x86\xef\xb4\x31\x8a\xed\x6a\x1e\x01\x2d\x9e\x68\x32"
0738     "\xa9\x07\x60\x0a\x91\x81\x30\xc4\x6d\xc7\x78\xf9\x71\xad\x00\x38"
0739     "\x09\x29\x99\xa3\x33\xcb\x8b\x7a\x1a\x1d\xb9\x3d\x71\x40\x00\x3c"
0740     "\x2a\x4e\xce\xa9\xf9\x8d\x0a\xcc\x0a\x82\x91\xcd\xce\xc9\x7d\xcf"
0741     "\x8e\xc9\xb5\x5a\x7f\x88\xa4\x6b\x4d\xb5\xa8\x51\xf4\x41\x82\xe1"
0742     "\xc6\x8a\x00\x7e\x5e\x0d\xd9\x02\x0b\xfd\x64\xb6\x45\x03\x6c\x7a"
0743     "\x4e\x67\x7d\x2c\x38\x53\x2a\x3a\x23\xba\x44\x42\xca\xf5\x3e\xa6"
0744     "\x3b\xb4\x54\x32\x9b\x76\x24\xc8\x91\x7b\xdd\x64\xb1\xc0\xfd\x4c"
0745     "\xb3\x8e\x8c\x33\x4c\x70\x1c\x3a\xcd\xad\x06\x57\xfc\xcf\xec\x71"
0746     "\x9b\x1f\x5c\x3e\x4e\x46\x04\x1f\x38\x81\x47\xfb\x4c\xfd\xb4\x77"
0747     "\xa5\x24\x71\xf7\xa9\xa9\x69\x10\xb8\x55\x32\x2e\xdb\x63\x40\xd8"
0748     "\xa0\x0e\xf0\x92\x35\x05\x11\xe3\x0a\xbe\xc1\xff\xf9\xe3\xa2\x6e"
0749     "\x7f\xb2\x9f\x8c\x18\x30\x23\xc3\x58\x7e\x38\xda\x00\x77\xd9\xb4"
0750     "\x76\x3e\x4e\x4b\x94\xb2\xbb\xc1\x94\xc6\x65\x1e\x77\xca\xf9\x92"
0751     "\xee\xaa\xc0\x23\x2a\x28\x1b\xf6\xb3\xa7\x39\xc1\x22\x61\x16\x82"
0752     "\x0a\xe8\xdb\x58\x47\xa6\x7c\xbe\xf9\xc9\x09\x1b\x46\x2d\x53\x8c"
0753     "\xd7\x2b\x03\x74\x6a\xe7\x7f\x5e\x62\x29\x2c\x31\x15\x62\xa8\x46"
0754     "\x50\x5d\xc8\x2d\xb8\x54\x33\x8a\xe4\x9f\x52\x35\xc9\x5b\x91\x17"
0755     "\x8c\xcf\x2d\xd5\xca\xce\xf4\x03\xec\x9d\x18\x10\xc6\x27\x2b\x04"
0756     "\x5b\x3b\x71\xf9\xdc\x6b\x80\xd6\x3f\xdd\x4a\x8e\x9a\xdb\x1e\x69"
0757     "\x62\xa6\x95\x26\xd4\x31\x61\xc1\xa4\x1d\x57\x0d\x79\x38\xda\xd4"
0758     "\xa4\x0e\x32\x9c\xd0\xe4\x0e\x65\xff\xff\xff\xff\xff\xff\xff\xff",
0759 };
0760 
0761 static const struct dh_safe_prime ffdhe8192_prime = {
0762     .max_strength = 200,
0763     .p_size = 1024,
0764     .p =
0765     "\xff\xff\xff\xff\xff\xff\xff\xff\xad\xf8\x54\x58\xa2\xbb\x4a\x9a"
0766     "\xaf\xdc\x56\x20\x27\x3d\x3c\xf1\xd8\xb9\xc5\x83\xce\x2d\x36\x95"
0767     "\xa9\xe1\x36\x41\x14\x64\x33\xfb\xcc\x93\x9d\xce\x24\x9b\x3e\xf9"
0768     "\x7d\x2f\xe3\x63\x63\x0c\x75\xd8\xf6\x81\xb2\x02\xae\xc4\x61\x7a"
0769     "\xd3\xdf\x1e\xd5\xd5\xfd\x65\x61\x24\x33\xf5\x1f\x5f\x06\x6e\xd0"
0770     "\x85\x63\x65\x55\x3d\xed\x1a\xf3\xb5\x57\x13\x5e\x7f\x57\xc9\x35"
0771     "\x98\x4f\x0c\x70\xe0\xe6\x8b\x77\xe2\xa6\x89\xda\xf3\xef\xe8\x72"
0772     "\x1d\xf1\x58\xa1\x36\xad\xe7\x35\x30\xac\xca\x4f\x48\x3a\x79\x7a"
0773     "\xbc\x0a\xb1\x82\xb3\x24\xfb\x61\xd1\x08\xa9\x4b\xb2\xc8\xe3\xfb"
0774     "\xb9\x6a\xda\xb7\x60\xd7\xf4\x68\x1d\x4f\x42\xa3\xde\x39\x4d\xf4"
0775     "\xae\x56\xed\xe7\x63\x72\xbb\x19\x0b\x07\xa7\xc8\xee\x0a\x6d\x70"
0776     "\x9e\x02\xfc\xe1\xcd\xf7\xe2\xec\xc0\x34\x04\xcd\x28\x34\x2f\x61"
0777     "\x91\x72\xfe\x9c\xe9\x85\x83\xff\x8e\x4f\x12\x32\xee\xf2\x81\x83"
0778     "\xc3\xfe\x3b\x1b\x4c\x6f\xad\x73\x3b\xb5\xfc\xbc\x2e\xc2\x20\x05"
0779     "\xc5\x8e\xf1\x83\x7d\x16\x83\xb2\xc6\xf3\x4a\x26\xc1\xb2\xef\xfa"
0780     "\x88\x6b\x42\x38\x61\x1f\xcf\xdc\xde\x35\x5b\x3b\x65\x19\x03\x5b"
0781     "\xbc\x34\xf4\xde\xf9\x9c\x02\x38\x61\xb4\x6f\xc9\xd6\xe6\xc9\x07"
0782     "\x7a\xd9\x1d\x26\x91\xf7\xf7\xee\x59\x8c\xb0\xfa\xc1\x86\xd9\x1c"
0783     "\xae\xfe\x13\x09\x85\x13\x92\x70\xb4\x13\x0c\x93\xbc\x43\x79\x44"
0784     "\xf4\xfd\x44\x52\xe2\xd7\x4d\xd3\x64\xf2\xe2\x1e\x71\xf5\x4b\xff"
0785     "\x5c\xae\x82\xab\x9c\x9d\xf6\x9e\xe8\x6d\x2b\xc5\x22\x36\x3a\x0d"
0786     "\xab\xc5\x21\x97\x9b\x0d\xea\xda\x1d\xbf\x9a\x42\xd5\xc4\x48\x4e"
0787     "\x0a\xbc\xd0\x6b\xfa\x53\xdd\xef\x3c\x1b\x20\xee\x3f\xd5\x9d\x7c"
0788     "\x25\xe4\x1d\x2b\x66\x9e\x1e\xf1\x6e\x6f\x52\xc3\x16\x4d\xf4\xfb"
0789     "\x79\x30\xe9\xe4\xe5\x88\x57\xb6\xac\x7d\x5f\x42\xd6\x9f\x6d\x18"
0790     "\x77\x63\xcf\x1d\x55\x03\x40\x04\x87\xf5\x5b\xa5\x7e\x31\xcc\x7a"
0791     "\x71\x35\xc8\x86\xef\xb4\x31\x8a\xed\x6a\x1e\x01\x2d\x9e\x68\x32"
0792     "\xa9\x07\x60\x0a\x91\x81\x30\xc4\x6d\xc7\x78\xf9\x71\xad\x00\x38"
0793     "\x09\x29\x99\xa3\x33\xcb\x8b\x7a\x1a\x1d\xb9\x3d\x71\x40\x00\x3c"
0794     "\x2a\x4e\xce\xa9\xf9\x8d\x0a\xcc\x0a\x82\x91\xcd\xce\xc9\x7d\xcf"
0795     "\x8e\xc9\xb5\x5a\x7f\x88\xa4\x6b\x4d\xb5\xa8\x51\xf4\x41\x82\xe1"
0796     "\xc6\x8a\x00\x7e\x5e\x0d\xd9\x02\x0b\xfd\x64\xb6\x45\x03\x6c\x7a"
0797     "\x4e\x67\x7d\x2c\x38\x53\x2a\x3a\x23\xba\x44\x42\xca\xf5\x3e\xa6"
0798     "\x3b\xb4\x54\x32\x9b\x76\x24\xc8\x91\x7b\xdd\x64\xb1\xc0\xfd\x4c"
0799     "\xb3\x8e\x8c\x33\x4c\x70\x1c\x3a\xcd\xad\x06\x57\xfc\xcf\xec\x71"
0800     "\x9b\x1f\x5c\x3e\x4e\x46\x04\x1f\x38\x81\x47\xfb\x4c\xfd\xb4\x77"
0801     "\xa5\x24\x71\xf7\xa9\xa9\x69\x10\xb8\x55\x32\x2e\xdb\x63\x40\xd8"
0802     "\xa0\x0e\xf0\x92\x35\x05\x11\xe3\x0a\xbe\xc1\xff\xf9\xe3\xa2\x6e"
0803     "\x7f\xb2\x9f\x8c\x18\x30\x23\xc3\x58\x7e\x38\xda\x00\x77\xd9\xb4"
0804     "\x76\x3e\x4e\x4b\x94\xb2\xbb\xc1\x94\xc6\x65\x1e\x77\xca\xf9\x92"
0805     "\xee\xaa\xc0\x23\x2a\x28\x1b\xf6\xb3\xa7\x39\xc1\x22\x61\x16\x82"
0806     "\x0a\xe8\xdb\x58\x47\xa6\x7c\xbe\xf9\xc9\x09\x1b\x46\x2d\x53\x8c"
0807     "\xd7\x2b\x03\x74\x6a\xe7\x7f\x5e\x62\x29\x2c\x31\x15\x62\xa8\x46"
0808     "\x50\x5d\xc8\x2d\xb8\x54\x33\x8a\xe4\x9f\x52\x35\xc9\x5b\x91\x17"
0809     "\x8c\xcf\x2d\xd5\xca\xce\xf4\x03\xec\x9d\x18\x10\xc6\x27\x2b\x04"
0810     "\x5b\x3b\x71\xf9\xdc\x6b\x80\xd6\x3f\xdd\x4a\x8e\x9a\xdb\x1e\x69"
0811     "\x62\xa6\x95\x26\xd4\x31\x61\xc1\xa4\x1d\x57\x0d\x79\x38\xda\xd4"
0812     "\xa4\x0e\x32\x9c\xcf\xf4\x6a\xaa\x36\xad\x00\x4c\xf6\x00\xc8\x38"
0813     "\x1e\x42\x5a\x31\xd9\x51\xae\x64\xfd\xb2\x3f\xce\xc9\x50\x9d\x43"
0814     "\x68\x7f\xeb\x69\xed\xd1\xcc\x5e\x0b\x8c\xc3\xbd\xf6\x4b\x10\xef"
0815     "\x86\xb6\x31\x42\xa3\xab\x88\x29\x55\x5b\x2f\x74\x7c\x93\x26\x65"
0816     "\xcb\x2c\x0f\x1c\xc0\x1b\xd7\x02\x29\x38\x88\x39\xd2\xaf\x05\xe4"
0817     "\x54\x50\x4a\xc7\x8b\x75\x82\x82\x28\x46\xc0\xba\x35\xc3\x5f\x5c"
0818     "\x59\x16\x0c\xc0\x46\xfd\x82\x51\x54\x1f\xc6\x8c\x9c\x86\xb0\x22"
0819     "\xbb\x70\x99\x87\x6a\x46\x0e\x74\x51\xa8\xa9\x31\x09\x70\x3f\xee"
0820     "\x1c\x21\x7e\x6c\x38\x26\xe5\x2c\x51\xaa\x69\x1e\x0e\x42\x3c\xfc"
0821     "\x99\xe9\xe3\x16\x50\xc1\x21\x7b\x62\x48\x16\xcd\xad\x9a\x95\xf9"
0822     "\xd5\xb8\x01\x94\x88\xd9\xc0\xa0\xa1\xfe\x30\x75\xa5\x77\xe2\x31"
0823     "\x83\xf8\x1d\x4a\x3f\x2f\xa4\x57\x1e\xfc\x8c\xe0\xba\x8a\x4f\xe8"
0824     "\xb6\x85\x5d\xfe\x72\xb0\xa6\x6e\xde\xd2\xfb\xab\xfb\xe5\x8a\x30"
0825     "\xfa\xfa\xbe\x1c\x5d\x71\xa8\x7e\x2f\x74\x1e\xf8\xc1\xfe\x86\xfe"
0826     "\xa6\xbb\xfd\xe5\x30\x67\x7f\x0d\x97\xd1\x1d\x49\xf7\xa8\x44\x3d"
0827     "\x08\x22\xe5\x06\xa9\xf4\x61\x4e\x01\x1e\x2a\x94\x83\x8f\xf8\x8c"
0828     "\xd6\x8c\x8b\xb7\xc5\xc6\x42\x4c\xff\xff\xff\xff\xff\xff\xff\xff",
0829 };
0830 
0831 static int dh_ffdhe2048_create(struct crypto_template *tmpl,
0832                    struct rtattr **tb)
0833 {
0834     return  __dh_safe_prime_create(tmpl, tb, &ffdhe2048_prime);
0835 }
0836 
0837 static int dh_ffdhe3072_create(struct crypto_template *tmpl,
0838                    struct rtattr **tb)
0839 {
0840     return  __dh_safe_prime_create(tmpl, tb, &ffdhe3072_prime);
0841 }
0842 
0843 static int dh_ffdhe4096_create(struct crypto_template *tmpl,
0844                    struct rtattr **tb)
0845 {
0846     return  __dh_safe_prime_create(tmpl, tb, &ffdhe4096_prime);
0847 }
0848 
0849 static int dh_ffdhe6144_create(struct crypto_template *tmpl,
0850                    struct rtattr **tb)
0851 {
0852     return  __dh_safe_prime_create(tmpl, tb, &ffdhe6144_prime);
0853 }
0854 
0855 static int dh_ffdhe8192_create(struct crypto_template *tmpl,
0856                    struct rtattr **tb)
0857 {
0858     return  __dh_safe_prime_create(tmpl, tb, &ffdhe8192_prime);
0859 }
0860 
0861 static struct crypto_template crypto_ffdhe_templates[] = {
0862     {
0863         .name = "ffdhe2048",
0864         .create = dh_ffdhe2048_create,
0865         .module = THIS_MODULE,
0866     },
0867     {
0868         .name = "ffdhe3072",
0869         .create = dh_ffdhe3072_create,
0870         .module = THIS_MODULE,
0871     },
0872     {
0873         .name = "ffdhe4096",
0874         .create = dh_ffdhe4096_create,
0875         .module = THIS_MODULE,
0876     },
0877     {
0878         .name = "ffdhe6144",
0879         .create = dh_ffdhe6144_create,
0880         .module = THIS_MODULE,
0881     },
0882     {
0883         .name = "ffdhe8192",
0884         .create = dh_ffdhe8192_create,
0885         .module = THIS_MODULE,
0886     },
0887 };
0888 
0889 #else /* ! CONFIG_CRYPTO_DH_RFC7919_GROUPS */
0890 
0891 static struct crypto_template crypto_ffdhe_templates[] = {};
0892 
0893 #endif /* CONFIG_CRYPTO_DH_RFC7919_GROUPS */
0894 
0895 
0896 static int dh_init(void)
0897 {
0898     int err;
0899 
0900     err = crypto_register_kpp(&dh);
0901     if (err)
0902         return err;
0903 
0904     err = crypto_register_templates(crypto_ffdhe_templates,
0905                     ARRAY_SIZE(crypto_ffdhe_templates));
0906     if (err) {
0907         crypto_unregister_kpp(&dh);
0908         return err;
0909     }
0910 
0911     return 0;
0912 }
0913 
0914 static void dh_exit(void)
0915 {
0916     crypto_unregister_templates(crypto_ffdhe_templates,
0917                     ARRAY_SIZE(crypto_ffdhe_templates));
0918     crypto_unregister_kpp(&dh);
0919 }
0920 
0921 subsys_initcall(dh_init);
0922 module_exit(dh_exit);
0923 MODULE_ALIAS_CRYPTO("dh");
0924 MODULE_LICENSE("GPL");
0925 MODULE_DESCRIPTION("DH generic algorithm");