aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/libs/openssl/crypto/ec/ecdh_ossl.c
diff options
context:
space:
mode:
authorDevtools Arcadia <arcadia-devtools@yandex-team.ru>2022-02-07 18:08:42 +0300
committerDevtools Arcadia <arcadia-devtools@mous.vla.yp-c.yandex.net>2022-02-07 18:08:42 +0300
commit1110808a9d39d4b808aef724c861a2e1a38d2a69 (patch)
treee26c9fed0de5d9873cce7e00bc214573dc2195b7 /contrib/libs/openssl/crypto/ec/ecdh_ossl.c
downloadydb-1110808a9d39d4b808aef724c861a2e1a38d2a69.tar.gz
intermediate changes
ref:cde9a383711a11544ce7e107a78147fb96cc4029
Diffstat (limited to 'contrib/libs/openssl/crypto/ec/ecdh_ossl.c')
-rw-r--r--contrib/libs/openssl/crypto/ec/ecdh_ossl.c120
1 files changed, 120 insertions, 0 deletions
diff --git a/contrib/libs/openssl/crypto/ec/ecdh_ossl.c b/contrib/libs/openssl/crypto/ec/ecdh_ossl.c
new file mode 100644
index 0000000000..0be00d43da
--- /dev/null
+++ b/contrib/libs/openssl/crypto/ec/ecdh_ossl.c
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2002-2019 The OpenSSL Project Authors. All Rights Reserved.
+ * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved
+ *
+ * Licensed under the OpenSSL license (the "License"). You may not use
+ * this file except in compliance with the License. You can obtain a copy
+ * in the file LICENSE in the source distribution or at
+ * https://www.openssl.org/source/license.html
+ */
+
+#include <string.h>
+#include <limits.h>
+
+#include "internal/cryptlib.h"
+
+#include <openssl/err.h>
+#include <openssl/bn.h>
+#include <openssl/objects.h>
+#include <openssl/ec.h>
+#include "ec_local.h"
+
+int ossl_ecdh_compute_key(unsigned char **psec, size_t *pseclen,
+ const EC_POINT *pub_key, const EC_KEY *ecdh)
+{
+ if (ecdh->group->meth->ecdh_compute_key == NULL) {
+ ECerr(EC_F_OSSL_ECDH_COMPUTE_KEY, EC_R_CURVE_DOES_NOT_SUPPORT_ECDH);
+ return 0;
+ }
+
+ return ecdh->group->meth->ecdh_compute_key(psec, pseclen, pub_key, ecdh);
+}
+
+/*-
+ * This implementation is based on the following primitives in the IEEE 1363 standard:
+ * - ECKAS-DH1
+ * - ECSVDP-DH
+ */
+int ecdh_simple_compute_key(unsigned char **pout, size_t *poutlen,
+ const EC_POINT *pub_key, const EC_KEY *ecdh)
+{
+ BN_CTX *ctx;
+ EC_POINT *tmp = NULL;
+ BIGNUM *x = NULL;
+ const BIGNUM *priv_key;
+ const EC_GROUP *group;
+ int ret = 0;
+ size_t buflen, len;
+ unsigned char *buf = NULL;
+
+ if ((ctx = BN_CTX_new()) == NULL)
+ goto err;
+ BN_CTX_start(ctx);
+ x = BN_CTX_get(ctx);
+ if (x == NULL) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, ERR_R_MALLOC_FAILURE);
+ goto err;
+ }
+
+ priv_key = EC_KEY_get0_private_key(ecdh);
+ if (priv_key == NULL) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, EC_R_MISSING_PRIVATE_KEY);
+ goto err;
+ }
+
+ group = EC_KEY_get0_group(ecdh);
+
+ if (EC_KEY_get_flags(ecdh) & EC_FLAG_COFACTOR_ECDH) {
+ if (!EC_GROUP_get_cofactor(group, x, NULL) ||
+ !BN_mul(x, x, priv_key, ctx)) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, ERR_R_MALLOC_FAILURE);
+ goto err;
+ }
+ priv_key = x;
+ }
+
+ if ((tmp = EC_POINT_new(group)) == NULL) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, ERR_R_MALLOC_FAILURE);
+ goto err;
+ }
+
+ if (!EC_POINT_mul(group, tmp, NULL, pub_key, priv_key, ctx)) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, EC_R_POINT_ARITHMETIC_FAILURE);
+ goto err;
+ }
+
+ if (!EC_POINT_get_affine_coordinates(group, tmp, x, NULL, ctx)) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, EC_R_POINT_ARITHMETIC_FAILURE);
+ goto err;
+ }
+
+ buflen = (EC_GROUP_get_degree(group) + 7) / 8;
+ len = BN_num_bytes(x);
+ if (len > buflen) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, ERR_R_INTERNAL_ERROR);
+ goto err;
+ }
+ if ((buf = OPENSSL_malloc(buflen)) == NULL) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, ERR_R_MALLOC_FAILURE);
+ goto err;
+ }
+
+ memset(buf, 0, buflen - len);
+ if (len != (size_t)BN_bn2bin(x, buf + buflen - len)) {
+ ECerr(EC_F_ECDH_SIMPLE_COMPUTE_KEY, ERR_R_BN_LIB);
+ goto err;
+ }
+
+ *pout = buf;
+ *poutlen = buflen;
+ buf = NULL;
+
+ ret = 1;
+
+ err:
+ EC_POINT_clear_free(tmp);
+ BN_CTX_end(ctx);
+ BN_CTX_free(ctx);
+ OPENSSL_free(buf);
+ return ret;
+}