1e1051a39Sopenharmony_ci/* 2e1051a39Sopenharmony_ci * Copyright 2001-2021 The OpenSSL Project Authors. All Rights Reserved. 3e1051a39Sopenharmony_ci * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved 4e1051a39Sopenharmony_ci * 5e1051a39Sopenharmony_ci * Licensed under the Apache License 2.0 (the "License"). You may not use 6e1051a39Sopenharmony_ci * this file except in compliance with the License. You can obtain a copy 7e1051a39Sopenharmony_ci * in the file LICENSE in the source distribution or at 8e1051a39Sopenharmony_ci * https://www.openssl.org/source/license.html 9e1051a39Sopenharmony_ci */ 10e1051a39Sopenharmony_ci 11e1051a39Sopenharmony_ci/* 12e1051a39Sopenharmony_ci * ECDSA low level APIs are deprecated for public use, but still ok for 13e1051a39Sopenharmony_ci * internal use. 14e1051a39Sopenharmony_ci */ 15e1051a39Sopenharmony_ci#include "internal/deprecated.h" 16e1051a39Sopenharmony_ci 17e1051a39Sopenharmony_ci#include <limits.h> 18e1051a39Sopenharmony_ci 19e1051a39Sopenharmony_ci#include <openssl/err.h> 20e1051a39Sopenharmony_ci#include <openssl/obj_mac.h> 21e1051a39Sopenharmony_ci#include "ec_local.h" 22e1051a39Sopenharmony_ci 23e1051a39Sopenharmony_ciconst EC_METHOD *EC_GFp_nist_method(void) 24e1051a39Sopenharmony_ci{ 25e1051a39Sopenharmony_ci static const EC_METHOD ret = { 26e1051a39Sopenharmony_ci EC_FLAGS_DEFAULT_OCT, 27e1051a39Sopenharmony_ci NID_X9_62_prime_field, 28e1051a39Sopenharmony_ci ossl_ec_GFp_simple_group_init, 29e1051a39Sopenharmony_ci ossl_ec_GFp_simple_group_finish, 30e1051a39Sopenharmony_ci ossl_ec_GFp_simple_group_clear_finish, 31e1051a39Sopenharmony_ci ossl_ec_GFp_nist_group_copy, 32e1051a39Sopenharmony_ci ossl_ec_GFp_nist_group_set_curve, 33e1051a39Sopenharmony_ci ossl_ec_GFp_simple_group_get_curve, 34e1051a39Sopenharmony_ci ossl_ec_GFp_simple_group_get_degree, 35e1051a39Sopenharmony_ci ossl_ec_group_simple_order_bits, 36e1051a39Sopenharmony_ci ossl_ec_GFp_simple_group_check_discriminant, 37e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_init, 38e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_finish, 39e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_clear_finish, 40e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_copy, 41e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_set_to_infinity, 42e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_set_affine_coordinates, 43e1051a39Sopenharmony_ci ossl_ec_GFp_simple_point_get_affine_coordinates, 44e1051a39Sopenharmony_ci 0, 0, 0, 45e1051a39Sopenharmony_ci ossl_ec_GFp_simple_add, 46e1051a39Sopenharmony_ci ossl_ec_GFp_simple_dbl, 47e1051a39Sopenharmony_ci ossl_ec_GFp_simple_invert, 48e1051a39Sopenharmony_ci ossl_ec_GFp_simple_is_at_infinity, 49e1051a39Sopenharmony_ci ossl_ec_GFp_simple_is_on_curve, 50e1051a39Sopenharmony_ci ossl_ec_GFp_simple_cmp, 51e1051a39Sopenharmony_ci ossl_ec_GFp_simple_make_affine, 52e1051a39Sopenharmony_ci ossl_ec_GFp_simple_points_make_affine, 53e1051a39Sopenharmony_ci 0 /* mul */ , 54e1051a39Sopenharmony_ci 0 /* precompute_mult */ , 55e1051a39Sopenharmony_ci 0 /* have_precompute_mult */ , 56e1051a39Sopenharmony_ci ossl_ec_GFp_nist_field_mul, 57e1051a39Sopenharmony_ci ossl_ec_GFp_nist_field_sqr, 58e1051a39Sopenharmony_ci 0 /* field_div */ , 59e1051a39Sopenharmony_ci ossl_ec_GFp_simple_field_inv, 60e1051a39Sopenharmony_ci 0 /* field_encode */ , 61e1051a39Sopenharmony_ci 0 /* field_decode */ , 62e1051a39Sopenharmony_ci 0, /* field_set_to_one */ 63e1051a39Sopenharmony_ci ossl_ec_key_simple_priv2oct, 64e1051a39Sopenharmony_ci ossl_ec_key_simple_oct2priv, 65e1051a39Sopenharmony_ci 0, /* set private */ 66e1051a39Sopenharmony_ci ossl_ec_key_simple_generate_key, 67e1051a39Sopenharmony_ci ossl_ec_key_simple_check_key, 68e1051a39Sopenharmony_ci ossl_ec_key_simple_generate_public_key, 69e1051a39Sopenharmony_ci 0, /* keycopy */ 70e1051a39Sopenharmony_ci 0, /* keyfinish */ 71e1051a39Sopenharmony_ci ossl_ecdh_simple_compute_key, 72e1051a39Sopenharmony_ci ossl_ecdsa_simple_sign_setup, 73e1051a39Sopenharmony_ci ossl_ecdsa_simple_sign_sig, 74e1051a39Sopenharmony_ci ossl_ecdsa_simple_verify_sig, 75e1051a39Sopenharmony_ci 0, /* field_inverse_mod_ord */ 76e1051a39Sopenharmony_ci ossl_ec_GFp_simple_blind_coordinates, 77e1051a39Sopenharmony_ci ossl_ec_GFp_simple_ladder_pre, 78e1051a39Sopenharmony_ci ossl_ec_GFp_simple_ladder_step, 79e1051a39Sopenharmony_ci ossl_ec_GFp_simple_ladder_post 80e1051a39Sopenharmony_ci }; 81e1051a39Sopenharmony_ci 82e1051a39Sopenharmony_ci return &ret; 83e1051a39Sopenharmony_ci} 84e1051a39Sopenharmony_ci 85e1051a39Sopenharmony_ciint ossl_ec_GFp_nist_group_copy(EC_GROUP *dest, const EC_GROUP *src) 86e1051a39Sopenharmony_ci{ 87e1051a39Sopenharmony_ci dest->field_mod_func = src->field_mod_func; 88e1051a39Sopenharmony_ci 89e1051a39Sopenharmony_ci return ossl_ec_GFp_simple_group_copy(dest, src); 90e1051a39Sopenharmony_ci} 91e1051a39Sopenharmony_ci 92e1051a39Sopenharmony_ciint ossl_ec_GFp_nist_group_set_curve(EC_GROUP *group, const BIGNUM *p, 93e1051a39Sopenharmony_ci const BIGNUM *a, const BIGNUM *b, 94e1051a39Sopenharmony_ci BN_CTX *ctx) 95e1051a39Sopenharmony_ci{ 96e1051a39Sopenharmony_ci int ret = 0; 97e1051a39Sopenharmony_ci BN_CTX *new_ctx = NULL; 98e1051a39Sopenharmony_ci 99e1051a39Sopenharmony_ci if (ctx == NULL) 100e1051a39Sopenharmony_ci if ((ctx = new_ctx = BN_CTX_new_ex(group->libctx)) == NULL) 101e1051a39Sopenharmony_ci return 0; 102e1051a39Sopenharmony_ci 103e1051a39Sopenharmony_ci BN_CTX_start(ctx); 104e1051a39Sopenharmony_ci 105e1051a39Sopenharmony_ci if (BN_ucmp(BN_get0_nist_prime_192(), p) == 0) 106e1051a39Sopenharmony_ci group->field_mod_func = BN_nist_mod_192; 107e1051a39Sopenharmony_ci else if (BN_ucmp(BN_get0_nist_prime_224(), p) == 0) 108e1051a39Sopenharmony_ci group->field_mod_func = BN_nist_mod_224; 109e1051a39Sopenharmony_ci else if (BN_ucmp(BN_get0_nist_prime_256(), p) == 0) 110e1051a39Sopenharmony_ci group->field_mod_func = BN_nist_mod_256; 111e1051a39Sopenharmony_ci else if (BN_ucmp(BN_get0_nist_prime_384(), p) == 0) 112e1051a39Sopenharmony_ci group->field_mod_func = BN_nist_mod_384; 113e1051a39Sopenharmony_ci else if (BN_ucmp(BN_get0_nist_prime_521(), p) == 0) 114e1051a39Sopenharmony_ci group->field_mod_func = BN_nist_mod_521; 115e1051a39Sopenharmony_ci else { 116e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_EC, EC_R_NOT_A_NIST_PRIME); 117e1051a39Sopenharmony_ci goto err; 118e1051a39Sopenharmony_ci } 119e1051a39Sopenharmony_ci 120e1051a39Sopenharmony_ci ret = ossl_ec_GFp_simple_group_set_curve(group, p, a, b, ctx); 121e1051a39Sopenharmony_ci 122e1051a39Sopenharmony_ci err: 123e1051a39Sopenharmony_ci BN_CTX_end(ctx); 124e1051a39Sopenharmony_ci BN_CTX_free(new_ctx); 125e1051a39Sopenharmony_ci return ret; 126e1051a39Sopenharmony_ci} 127e1051a39Sopenharmony_ci 128e1051a39Sopenharmony_ciint ossl_ec_GFp_nist_field_mul(const EC_GROUP *group, BIGNUM *r, const BIGNUM *a, 129e1051a39Sopenharmony_ci const BIGNUM *b, BN_CTX *ctx) 130e1051a39Sopenharmony_ci{ 131e1051a39Sopenharmony_ci int ret = 0; 132e1051a39Sopenharmony_ci BN_CTX *ctx_new = NULL; 133e1051a39Sopenharmony_ci 134e1051a39Sopenharmony_ci if (!group || !r || !a || !b) { 135e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_EC, ERR_R_PASSED_NULL_PARAMETER); 136e1051a39Sopenharmony_ci goto err; 137e1051a39Sopenharmony_ci } 138e1051a39Sopenharmony_ci if (!ctx) 139e1051a39Sopenharmony_ci if ((ctx_new = ctx = BN_CTX_new_ex(group->libctx)) == NULL) 140e1051a39Sopenharmony_ci goto err; 141e1051a39Sopenharmony_ci 142e1051a39Sopenharmony_ci if (!BN_mul(r, a, b, ctx)) 143e1051a39Sopenharmony_ci goto err; 144e1051a39Sopenharmony_ci if (!group->field_mod_func(r, r, group->field, ctx)) 145e1051a39Sopenharmony_ci goto err; 146e1051a39Sopenharmony_ci 147e1051a39Sopenharmony_ci ret = 1; 148e1051a39Sopenharmony_ci err: 149e1051a39Sopenharmony_ci BN_CTX_free(ctx_new); 150e1051a39Sopenharmony_ci return ret; 151e1051a39Sopenharmony_ci} 152e1051a39Sopenharmony_ci 153e1051a39Sopenharmony_ciint ossl_ec_GFp_nist_field_sqr(const EC_GROUP *group, BIGNUM *r, const BIGNUM *a, 154e1051a39Sopenharmony_ci BN_CTX *ctx) 155e1051a39Sopenharmony_ci{ 156e1051a39Sopenharmony_ci int ret = 0; 157e1051a39Sopenharmony_ci BN_CTX *ctx_new = NULL; 158e1051a39Sopenharmony_ci 159e1051a39Sopenharmony_ci if (!group || !r || !a) { 160e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_EC, EC_R_PASSED_NULL_PARAMETER); 161e1051a39Sopenharmony_ci goto err; 162e1051a39Sopenharmony_ci } 163e1051a39Sopenharmony_ci if (!ctx) 164e1051a39Sopenharmony_ci if ((ctx_new = ctx = BN_CTX_new_ex(group->libctx)) == NULL) 165e1051a39Sopenharmony_ci goto err; 166e1051a39Sopenharmony_ci 167e1051a39Sopenharmony_ci if (!BN_sqr(r, a, ctx)) 168e1051a39Sopenharmony_ci goto err; 169e1051a39Sopenharmony_ci if (!group->field_mod_func(r, r, group->field, ctx)) 170e1051a39Sopenharmony_ci goto err; 171e1051a39Sopenharmony_ci 172e1051a39Sopenharmony_ci ret = 1; 173e1051a39Sopenharmony_ci err: 174e1051a39Sopenharmony_ci BN_CTX_free(ctx_new); 175e1051a39Sopenharmony_ci return ret; 176e1051a39Sopenharmony_ci} 177