mirror of
https://github.com/guanzhi/GmSSL.git
synced 2026-05-06 16:36:16 +08:00
sm2 test vector
This commit is contained in:
4
Makefile
4
Makefile
@@ -4,7 +4,7 @@
|
||||
## Makefile for OpenSSL
|
||||
##
|
||||
|
||||
VERSION=1.0.2d
|
||||
VERSION=1.0.2d-fips
|
||||
MAJOR=1
|
||||
MINOR=0.2
|
||||
SHLIB_VERSION_NUMBER=1.0.0
|
||||
@@ -151,7 +151,7 @@ SDIRS= \
|
||||
buffer bio stack lhash rand err \
|
||||
evp asn1 pem x509 x509v3 conf txt_db pkcs7 pkcs12 comp ocsp ui krb5 \
|
||||
cms pqueue ts srp cmac \
|
||||
sm3 sms4 zuc cpk ecies sm2
|
||||
sm2 sm3 sms4 ecies zuc
|
||||
|
||||
# keep in mind that the above list is adjusted by ./Configure
|
||||
# according to no-xxx arguments...
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
## Makefile for OpenSSL
|
||||
##
|
||||
|
||||
VERSION=1.0.2d
|
||||
VERSION=1.0.2d-fips
|
||||
MAJOR=1
|
||||
MINOR=0.2
|
||||
SHLIB_VERSION_NUMBER=1.0.0
|
||||
@@ -67,9 +67,9 @@ EX_LIBS=
|
||||
EXE_EXT=
|
||||
ARFLAGS=
|
||||
AR= ar $(ARFLAGS) r
|
||||
RANLIB= /opt/local/bin/ranlib
|
||||
RANLIB= /usr/bin/ranlib
|
||||
NM= nm
|
||||
PERL= /opt/local/bin/perl5
|
||||
PERL= /usr/bin/perl
|
||||
TAR= tar
|
||||
TARFLAGS= --no-recursion
|
||||
MAKEDEPPROG=makedepend
|
||||
@@ -151,7 +151,7 @@ SDIRS= \
|
||||
buffer bio stack lhash rand err \
|
||||
evp asn1 pem x509 x509v3 conf txt_db pkcs7 pkcs12 comp ocsp ui krb5 \
|
||||
cms pqueue ts srp cmac \
|
||||
sm3 sms4 zuc cpk ecies sm2
|
||||
sm2 sm3 sms4 ecies
|
||||
|
||||
# keep in mind that the above list is adjusted by ./Configure
|
||||
# according to no-xxx arguments...
|
||||
|
||||
@@ -149,7 +149,7 @@ SDIRS= \
|
||||
buffer bio stack lhash rand err \
|
||||
evp asn1 pem x509 x509v3 conf txt_db pkcs7 pkcs12 comp ocsp ui krb5 \
|
||||
cms pqueue ts jpake srp store cmac \
|
||||
sm3 sms4 zuc cpk ecies sm2
|
||||
sm2 sm3 sms4 ecies zuc
|
||||
|
||||
# keep in mind that the above list is adjusted by ./Configure
|
||||
# according to no-xxx arguments...
|
||||
|
||||
@@ -0,0 +1,6 @@
|
||||
/*
|
||||
*
|
||||
* gmssl cpkparam
|
||||
*/
|
||||
|
||||
|
||||
|
||||
BIN
apps/openssl
BIN
apps/openssl
Binary file not shown.
69
apps/sm2.c
69
apps/sm2.c
@@ -1,69 +0,0 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <libgen.h>
|
||||
#include <openssl/evp.h>
|
||||
#include <openssl/ecdsa.h>
|
||||
#include <openssl/objects.h>
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
char *prog = basename(argv[0]);
|
||||
EC_GROUP *ec_group = NULL;
|
||||
EC_KEY *ec_key = NULL;
|
||||
BN_CTX *ctx = BN_CTX_new();
|
||||
const char *id = "Alice@YAHOO.COM";
|
||||
unsigned char za[32];
|
||||
BIGNUM *k = NULL;
|
||||
BIGNUM *x = NULL;
|
||||
ECDSA_SIG *sig = NULL;
|
||||
unsigned char dgst[20] = "abc";
|
||||
int ret;
|
||||
|
||||
if (!(ec_group = EC_GROUP_new_by_curve_name(NID_sm2t257v1))) {
|
||||
fprintf(stderr, "%s: no such curve\n", prog);
|
||||
return -1;
|
||||
}
|
||||
if (!(ec_key = EC_KEY_new_by_curve_name(NID_sm2p256v1))) {
|
||||
fprintf(stderr, "%s: %s %d\n", prog, __FUNCTION__, __LINE__);
|
||||
return -1;
|
||||
}
|
||||
if (!EC_KEY_generate_key(ec_key)) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
if ((ret = EC_KEY_compute_za(za, EVP_sha256(), id, strlen(id), ec_key)) < 0) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
printf("Za length = %d\n", ret);
|
||||
|
||||
if (!(sig = ECDSA_do_sign(dgst, sizeof(dgst), ec_key))) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
if ((ret = ECDSA_do_verify(dgst, sizeof(dgst), sig, ec_key)) < 0) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
printf("result = %d\n", ret);
|
||||
|
||||
if (!ECDSA_sign_setup(ec_key, ctx, &k, &x)) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
if (!(sig = ECDSA_do_sign_ex(dgst, sizeof(dgst), k, x, ec_key))) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
if ((ret = ECDSA_do_verify(dgst, sizeof(dgst), sig, ec_key)) < 0) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
return -1;
|
||||
}
|
||||
printf("result = %d\n", ret);
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -1,7 +1,3 @@
|
||||
|
||||
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
@@ -54,17 +50,21 @@ int CBCMAC_CTX_copy(CBCMAC_CTX *to, const CBCMAC_CTX *from)
|
||||
int CBCMAC_Init(CBCMAC_CTX *ctx, const void *key, size_t keylen,
|
||||
const EVP_CIPHER *cipher, ENGINE *impl)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CBCMAC_Update(CBCMAC_CTX *ctx, const void *data, size_t datalen)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CBCMAC_Final(CBCMAC_CTX *ctx, unsigned char *out, size_t *outlen)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CBCMAC_resume(CBCMAC_CTX *ctx)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -48,7 +48,11 @@
|
||||
* ====================================================================
|
||||
*
|
||||
*/
|
||||
|
||||
/* Note:
|
||||
* 1. CBC-MAC should be only used for fixed-length message
|
||||
* 2. the message length should be multiple of block size
|
||||
* 3. the implementation do not add padding
|
||||
*/
|
||||
#ifndef HEADER_CBCMAC_H
|
||||
#define HEADER_CBCMAC_H
|
||||
|
||||
|
||||
@@ -1224,11 +1224,25 @@ void ERR_load_EC_strings(void);
|
||||
# define EC_F_PKEY_EC_SIGN 218
|
||||
|
||||
# ifndef OPENSSL_NO_GMSSL
|
||||
# define EC_F_PKEY_EC_ENCRYPT 300
|
||||
# define EC_F_PKEY_EC_DECRYPT 301
|
||||
# define EC_F_PKEY_SM2_SIGN 302
|
||||
# define EC_F_PKEY_SM2_ENCRYPT 303
|
||||
# define EC_F_PKEY_SM2_DECRYPT 304
|
||||
# define EC_F_PKEY_EC_ENCRYPT 300
|
||||
# define EC_F_PKEY_EC_DECRYPT 301
|
||||
# define EC_F_PKEY_SM2_INIT 302
|
||||
# define EC_F_PKEY_SM2_COPY 303
|
||||
# define EC_F_PKEY_SM2_CLEANUP 304
|
||||
# define EC_F_PKEY_SM2_PARAMGEN 305
|
||||
# define EC_F_PKEY_SM2_KEYGEN 306
|
||||
# define EC_F_PKEY_SM2_SIGN 307
|
||||
# define EC_F_PKEY_SM2_VERIFY 308
|
||||
# define EC_F_PKEY_SM2_SIGNCTX_INIT 309
|
||||
# define EC_F_PKEY_SM2_SIGNCTX 310
|
||||
# define EC_F_PKEY_SM2_VERIFYCTX_INIT 311
|
||||
# define EC_F_PKEY_SM2_VERIFYCTX 312
|
||||
# define EC_F_PKEY_SM2_ENCRYPT 313
|
||||
# define EC_F_PKEY_SM2_DECRYPT 314
|
||||
# define EC_F_PKEY_SM2_DERIVE_INIT 315
|
||||
# define EC_F_PKEY_SM2_DERIVE 316
|
||||
# define EC_F_PKEY_SM2_CTRL 317
|
||||
# define EC_F_PKEY_SM2_CTRL_STR 318
|
||||
# endif
|
||||
|
||||
/* Reason codes. */
|
||||
|
||||
@@ -625,7 +625,97 @@ static int pkey_sm2_verify(EVP_PKEY_CTX *ctx,
|
||||
return SM2_verify(type, dgst, dgstlen, sig, siglen, ec_key);
|
||||
}
|
||||
|
||||
static int pkey_sm2_encrypt(EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen,
|
||||
static int pkey_sm2_signctx_init(EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx)
|
||||
{
|
||||
int ret = 0;
|
||||
EC_PKEY_CTX *ec_ctx = ctx->data;
|
||||
EC_KEY *ec_key = ctx->pkey->pkey.ec;
|
||||
const EVP_MD *md = EVP_sm3();
|
||||
unsigned char zid[EVP_MAX_MD_SIZE];
|
||||
unsigned int zidlen;
|
||||
|
||||
if (!SM2_compute_id_digest(md, zid, &zidlen, ec_key)) {
|
||||
ECerr(EC_F_PKEY_SM2_SIGNCTX_INIT, ERR_R_SM2_LIB);
|
||||
return 0;
|
||||
}
|
||||
if (!mctx->update(mctx, zid, zidlen)) {
|
||||
ECerr(EC_F_PKEY_SM2_SIGNCTX_INIT, ERR_R_EVP_LIB);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int pkey_sm2_signctx(EVP_PKEY_CTX *ctx,
|
||||
unsigned char *sig, size_t *siglen, EVP_MD_CTX *mctx)
|
||||
{
|
||||
EC_PKEY_CTX *ec_ctx = ctx->data;
|
||||
EC_KEY *ec_key = ctx->pkey->pkey.ec;
|
||||
unsigned char dgst[EVP_MAX_MD_SIZE];
|
||||
unsigned int dgstlen;
|
||||
int type = NID_undef;
|
||||
|
||||
if (!sig) {
|
||||
*siglen = SM2_signature_size(ec_key);
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (*siglen < (size_t)SM2_signature_size(ec_key)) {
|
||||
ECerr(EC_F_PKEY_SM2_SIGNCTX, EC_R_BUFFER_TOO_SMALL);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!EVP_DigestFinal_ex(mctx, dgst, &dgstlen)) {
|
||||
ECerr(EC_F_PKEY_SM2_SIGNCTX, ERR_R_EVP_LIB);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return SM2_sign(type, dgst, dgstlen, sig, &siglen, ec_key);
|
||||
}
|
||||
|
||||
static int pkey_sm2_verifyctx_init(EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx)
|
||||
{
|
||||
int ret = 0;
|
||||
EC_PKEY_CTX *ec_ctx = ctx->data;
|
||||
EC_KEY *ec_key = ctx->pkey->pkey.ec;
|
||||
const EVP_MD *md = EVP_sm3();
|
||||
unsigned char zid[EVP_MAX_MD_SIZE];
|
||||
unsigned int zidlen;
|
||||
|
||||
// FIXME: we need to get md from somewhere
|
||||
|
||||
if (!SM2_compute_id_digest(md, zid, &zidlen, ec_key)) {
|
||||
goto end;
|
||||
}
|
||||
if (!mctx->update(mctx, zid, zidlen)) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
ret = 1;
|
||||
end:
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pkey_sm2_verifyctx(EVP_PKEY_CTX *ctx,
|
||||
const unsigned char *sig, int siglen, EVP_MD_CTX *mctx)
|
||||
{
|
||||
EC_PKEY_CTX *ec_ctx = ctx->data;
|
||||
EC_KEY *ec_key = ctx->pkey->pkey.ec;
|
||||
int type = ec_ctx->md ? EVP_MD_type(ec_ctx->md) : NID_sm3;
|
||||
|
||||
/*
|
||||
if (!EVP_DigestFinal_ex(mctx, dgst, &dgstlen)) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
return SM2_verify(type, dgst, dgstlen, sig, siglen, ec_key);
|
||||
*/
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pkey_sm2_encrypt(EVP_PKEY_CTX *ctx,
|
||||
unsigned char *out, size_t *outlen,
|
||||
const unsigned char *in, size_t inlen)
|
||||
{
|
||||
EC_PKEY_CTX *ec_ctx = ctx->data;
|
||||
@@ -641,7 +731,8 @@ static int pkey_sm2_encrypt(EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outle
|
||||
return SM2_encrypt(kdf_md, mac_md, point_form, in, inlen, out, outlen, ec_key);
|
||||
}
|
||||
|
||||
static int pkey_sm2_decrypt(EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen,
|
||||
static int pkey_sm2_decrypt(EVP_PKEY_CTX *ctx,
|
||||
unsigned char *out, size_t *outlen,
|
||||
const unsigned char *in, size_t inlen)
|
||||
{
|
||||
EC_PKEY_CTX *ec_ctx = ctx->data;
|
||||
@@ -654,7 +745,8 @@ static int pkey_sm2_decrypt(EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outle
|
||||
kdf_md = EVP_sm3();
|
||||
mac_md = EVP_sm3();
|
||||
|
||||
return SM2_decrypt(kdf_md, mac_md, point_form, in, inlen, out, outlen, ec_key);
|
||||
return SM2_decrypt(kdf_md, mac_md, point_form,
|
||||
in, inlen, out, outlen, ec_key);
|
||||
}
|
||||
|
||||
static int pkey_sm2_ctrl_digestinit(EVP_PKEY_CTX *pk_ctx, EVP_MD_CTX *md_ctx)
|
||||
@@ -679,7 +771,7 @@ static int pkey_sm2_ctrl_digestinit(EVP_PKEY_CTX *pk_ctx, EVP_MD_CTX *md_ctx)
|
||||
*/
|
||||
|
||||
//FIXME: check this function
|
||||
if (!SM2_compute_id_digest(zid, &zidlen, md, ec_key)) {
|
||||
if (!SM2_compute_id_digest(md, zid, &zidlen, ec_key)) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
return 0;
|
||||
}
|
||||
@@ -706,6 +798,16 @@ end:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int pkey_sm2_derive_init(EVP_PKEY_CTX *ctx)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pkey_sm2_derive(EVP_PKEY_CTX *ctx, unsigned char *key, size_t *keylen)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pkey_sm2_ctrl(EVP_PKEY_CTX *pk_ctx, int type, int p1, void *p2)
|
||||
{
|
||||
switch (type) {
|
||||
@@ -720,34 +822,30 @@ static int pkey_sm2_ctrl(EVP_PKEY_CTX *pk_ctx, int type, int p1, void *p2)
|
||||
|
||||
const EVP_PKEY_METHOD sm2_pkey_meth = {
|
||||
EVP_PKEY_SM2,
|
||||
0, /* flags */
|
||||
0,
|
||||
pkey_ec_init,
|
||||
pkey_ec_copy,
|
||||
pkey_ec_cleanup,
|
||||
0, /* paramgen_init */
|
||||
pkey_ec_paramgen,
|
||||
0, /* keygen_init */
|
||||
pkey_sm2_keygen,
|
||||
0, /* sign_init */
|
||||
pkey_sm2_sign,
|
||||
0, /* verify_init */
|
||||
pkey_sm2_verify,
|
||||
0, /* verify_recover_init */
|
||||
0, /* verify_recover */
|
||||
0, /* signctx_init */
|
||||
0, /* signctx */
|
||||
0, /* verifyctx_init */
|
||||
0, /* verifyctx */
|
||||
0, /* encrypt_init */
|
||||
pkey_sm2_encrypt,
|
||||
0, /* decrypt_init */
|
||||
pkey_sm2_decrypt,
|
||||
0, /* derive_init */
|
||||
#ifndef OPENSSL_NO_ECDH
|
||||
pkey_ec_kdf_derive,
|
||||
#else
|
||||
0,
|
||||
#endif
|
||||
pkey_ec_paramgen,
|
||||
0,
|
||||
pkey_sm2_keygen,
|
||||
0,
|
||||
pkey_sm2_sign,
|
||||
0,
|
||||
pkey_sm2_verify,
|
||||
0,
|
||||
0,
|
||||
pkey_sm2_signctx_init,
|
||||
pkey_sm2_signctx,
|
||||
pkey_sm2_verifyctx_init,
|
||||
pkey_sm2_verifyctx,
|
||||
0,
|
||||
pkey_sm2_encrypt,
|
||||
0,
|
||||
pkey_sm2_decrypt,
|
||||
pkey_sm2_derive_init,
|
||||
pkey_sm2_derive,
|
||||
pkey_sm2_ctrl,
|
||||
pkey_ec_ctrl_str
|
||||
};
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -177,7 +177,7 @@ void OpenSSL_add_all_ciphers(void)
|
||||
#endif
|
||||
|
||||
#ifndef OPENSSL_NO_ZUC
|
||||
EVP_add_cipher(EVP_zuc());
|
||||
EVP_add_cipher(EVP_zuc());
|
||||
#endif
|
||||
|
||||
#ifndef OPENSSL_NO_AES
|
||||
|
||||
@@ -219,8 +219,8 @@ int EVP_DigestInit_ex(EVP_MD_CTX *ctx, const EVP_MD *type, ENGINE *impl)
|
||||
if (!(ctx->flags & EVP_MD_CTX_FLAG_NO_INIT) && type->ctx_size) {
|
||||
ctx->update = type->update;
|
||||
ctx->md_data = OPENSSL_malloc(type->ctx_size);
|
||||
//fprintf(stderr, "%s %d\n", __FILE__, __LINE__);
|
||||
if (ctx->md_data == NULL) {
|
||||
fprintf(stderr, "%s %d\n", __FILE__, __LINE__);
|
||||
EVPerr(EVP_F_EVP_DIGESTINIT_EX, ERR_R_MALLOC_FAILURE);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -23,6 +23,11 @@ static int zuc_do_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* FIXME:
|
||||
* evp_enc.c assert block_size in {1, 8, 16}, 4 not ok!
|
||||
*/
|
||||
static const EVP_CIPHER zuc_cipher = {
|
||||
NID_zuc, /* nid */
|
||||
4, /* block_size */
|
||||
|
||||
@@ -210,6 +210,9 @@ int EVP_CipherInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
|
||||
#endif
|
||||
/* we assume block size is a power of 2 in *cryptUpdate */
|
||||
OPENSSL_assert(ctx->cipher->block_size == 1
|
||||
#ifndef OPENSSL_NO_GMSSL
|
||||
|| ctx->cipher->block_size == 4
|
||||
#endif
|
||||
|| ctx->cipher->block_size == 8
|
||||
|| ctx->cipher->block_size == 16);
|
||||
|
||||
|
||||
@@ -17,9 +17,8 @@ TEST=sm2test.c
|
||||
APPS=
|
||||
|
||||
LIB=$(TOP)/libcrypto.a
|
||||
LIBSRC= sm2_lib.c sm2_err.c sm2_sign.c sm2_enc.c sm2_kap.c
|
||||
|
||||
LIBOBJ= sm2_lib.o sm2_err.o sm2_sign.o sm2_enc.o sm2_kap.o
|
||||
LIBSRC= sm2_lib.c sm2_asn1.c sm2_err.c sm2_sign.c sm2_enc.c sm2_kap.c
|
||||
LIBOBJ= sm2_lib.o sm2_asn1.o sm2_err.o sm2_sign.o sm2_enc.o sm2_kap.o
|
||||
|
||||
SRC= $(LIBSRC)
|
||||
|
||||
|
||||
@@ -67,10 +67,16 @@ extern "C" {
|
||||
|
||||
|
||||
#define SM2_MAX_ID_BITS 65535
|
||||
#define SM2_MAX_ID_LENGTH 8191
|
||||
#define SM2_MAX_ID_LENGTH (SM2_MAX_ID_BITS/8)
|
||||
#define SM2_DEFAULT_ID "1234567812345678"
|
||||
#define SM2_DEFAULT_POINT_CONVERSION_FORM POINT_CONVERSION_UNCOMPRESSED
|
||||
|
||||
|
||||
char *SM2_get0_id(EC_KEY *ec_key);
|
||||
int SM2_set_id(EC_KEY *ec_key, const char *id);
|
||||
int SM2_compute_id_digest(const EVP_MD *md, unsigned char *dgst,
|
||||
unsigned int *dgstlen, EC_KEY *ec_key);
|
||||
|
||||
|
||||
typedef struct sm2_ciphertext_value_st {
|
||||
EC_POINT *ephem_point;
|
||||
@@ -80,13 +86,6 @@ typedef struct sm2_ciphertext_value_st {
|
||||
unsigned int mactag_size;
|
||||
} SM2_CIPHERTEXT_VALUE;
|
||||
|
||||
|
||||
char *SM2_get_id(EC_KEY *ec_key);
|
||||
int SM2_set_id(EC_KEY *ec_key, const char *id);
|
||||
int SM2_compute_id_digest(unsigned char *dgst, unsigned int *dgstlen,
|
||||
const EVP_MD *md, EC_KEY *ec_key);
|
||||
|
||||
|
||||
int SM2_CIPHERTEXT_VALUE_size(const EC_GROUP *ec_group,
|
||||
point_conversion_form_t point_form, size_t mlen,
|
||||
const EVP_MD *mac_md);
|
||||
@@ -97,13 +96,19 @@ int SM2_CIPHERTEXT_VALUE_encode(const SM2_CIPHERTEXT_VALUE *cv,
|
||||
SM2_CIPHERTEXT_VALUE *SM2_CIPHERTEXT_VALUE_decode(const EC_GROUP *ec_group,
|
||||
point_conversion_form_t point_form, const EVP_MD *mac_md,
|
||||
const unsigned char *buf, size_t buflen);
|
||||
int i2d_SM2_CIPHERTEXT_VALUE(const SM2_CIPHERTEXT_VALUE *c, unsigned char **out);
|
||||
SM2_CIPHERTEXT_VALUE *d2i_SM2_CIPHERTEXT_VALUE(SM2_CIPHERTEXT_VALUE **c,
|
||||
const unsigned char **in, long len);
|
||||
int SM2_CIPHERTEXT_VALUE_print(BIO *out, const EC_GROUP *ec_group,
|
||||
const SM2_CIPHERTEXT_VALUE *cv, int indent, unsigned long flags);
|
||||
|
||||
/* FIXME: we should provide optional return value */
|
||||
SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
const unsigned char *in, size_t inlen, EC_KEY *ec_key);
|
||||
int SM2_do_decrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
const SM2_CIPHERTEXT_VALUE *cv, unsigned char *out, size_t *outlen,
|
||||
EC_KEY *ec_key);
|
||||
|
||||
int SM2_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
point_conversion_form_t point_form,
|
||||
const unsigned char *in, size_t inlen,
|
||||
@@ -114,6 +119,12 @@ int SM2_decrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
unsigned char *out, size_t *outlen, EC_KEY *ec_key);
|
||||
|
||||
|
||||
|
||||
|
||||
int SM2_compute_message_digest(const EVP_MD *id_md, const EVP_MD *msg_md,
|
||||
const void *msg, size_t msglen, unsigned char *dgst,
|
||||
unsigned int *dgstlen, EC_KEY *ec_key);
|
||||
|
||||
#define SM2_signature_size(ec_key) ECDSA_size(ec_key)
|
||||
int SM2_sign_setup(EC_KEY *ec_key, BN_CTX *ctx, BIGNUM **a, BIGNUM **b);
|
||||
ECDSA_SIG *SM2_do_sign_ex(const unsigned char *dgst, int dgstlen,
|
||||
@@ -127,6 +138,9 @@ int SM2_sign_ex(int type, const unsigned char *dgst, int dgstlen,
|
||||
const BIGNUM *k, const BIGNUM *x, EC_KEY *ec_key);
|
||||
int SM2_sign(int type, const unsigned char *dgst, int dgstlen,
|
||||
unsigned char *sig, unsigned int *siglen, EC_KEY *eckey);
|
||||
#define SM2_VERIFY_SUCCESS 1
|
||||
#define SM2_VERIFY_FAILED 0
|
||||
#define SM2_VERIFY_INNER_ERROR -1
|
||||
int SM2_verify(int type, const unsigned char *dgst, int dgstlen,
|
||||
const unsigned char *sig, int siglen, EC_KEY *ec_key);
|
||||
|
||||
@@ -165,13 +179,13 @@ typedef struct sm2_kap_ctx_st {
|
||||
|
||||
|
||||
|
||||
int SM2_KAP_CTX_init_ex(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
int SM2_KAP_CTX_init(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
EC_KEY *remote_pubkey, int is_initiator, int do_checksum);
|
||||
void SM2_KAP_CTX_cleanup(SM2_KAP_CTX *ctx);
|
||||
int SM2_KAP_prepare(SM2_KAP_CTX *ctx, unsigned char *ephem_point,
|
||||
size_t ephem_point_len);
|
||||
size_t *ephem_point_len);
|
||||
int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_ephem_point,
|
||||
size_t remote_ephem_point_len, unsigned char *key, size_t *keylen,
|
||||
size_t remote_ephem_point_len, unsigned char *key, size_t keylen,
|
||||
unsigned char *checksum, size_t *checksumlen);
|
||||
int SM2_KAP_final_check(SM2_KAP_CTX *ctx, const unsigned char *checksum,
|
||||
size_t checksumlen);
|
||||
|
||||
@@ -1,41 +1,130 @@
|
||||
/* crypto/sm2/sm2_asn1.c */
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2007 - 2016 The GmSSL Project. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
*
|
||||
* 3. All advertising materials mentioning features or use of this
|
||||
* software must display the following acknowledgment:
|
||||
* "This product includes software developed by the GmSSL Project.
|
||||
* (http://gmssl.org/)"
|
||||
*
|
||||
* 4. The name "GmSSL Project" must not be used to endorse or promote
|
||||
* products derived from this software without prior written
|
||||
* permission. For written permission, please contact
|
||||
* guanzhi1980@gmail.com.
|
||||
*
|
||||
* 5. Products derived from this software may not be called "GmSSL"
|
||||
* nor may "GmSSL" appear in their names without prior written
|
||||
* permission of the GmSSL Project.
|
||||
*
|
||||
* 6. Redistributions of any form whatsoever must retain the following
|
||||
* acknowledgment:
|
||||
* "This product includes software developed by the GmSSL Project
|
||||
* (http://gmssl.org/)"
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE GmSSL PROJECT ``AS IS'' AND ANY
|
||||
* EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE GmSSL PROJECT OR
|
||||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
|
||||
* OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
* ====================================================================
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include <string.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/asn1.h>
|
||||
#include <openssl/asn1t.h>
|
||||
#include <openssl/objects.h>
|
||||
#include <openssl/obj_mac.h>
|
||||
#include <openssl/sm2.h>
|
||||
|
||||
/*
|
||||
* from GM/T 0009-2012
|
||||
* "SM2 Cryptography Algorithm Application Specification"
|
||||
*
|
||||
SM2PrivateKey ::= INTEGER
|
||||
|
||||
SM2PublicKey ::= BIT STRING
|
||||
|
||||
SM2CiphertextValue ::= SEQUENCE {
|
||||
XCoordinate INTEGER,
|
||||
YCoordinate INTEGER,
|
||||
Hash OCTET STRING SIZE(32),
|
||||
Ciphertext OCTET STRING
|
||||
}
|
||||
SM2PrivateKey ::= INTEGER
|
||||
|
||||
SM2Signature ::= SEQUENCE {
|
||||
R INTEGER,
|
||||
S INTEGER,
|
||||
}
|
||||
SM2PublicKey ::= BIT STRING
|
||||
|
||||
SM2EnvelopedKey ::= SEQUENCE {
|
||||
symAlgID AlgorithmIdentifier,
|
||||
symEncryptedKey SM2CiphertextValue,
|
||||
sm2PublicKey SM2PublicKey,
|
||||
sm2EncryptedPrivateKey BIT STRING
|
||||
}
|
||||
SM2CiphertextValue ::= SEQUENCE {
|
||||
XCoordinate INTEGER,
|
||||
YCoordinate INTEGER,
|
||||
Hash OCTET STRING SIZE(32),
|
||||
Ciphertext OCTET STRING
|
||||
}
|
||||
|
||||
ZID = SM3(nbits(ID)||ID||a||b||xG||yG||xA||yA)
|
||||
|
||||
Default ID = "1234567812345678"
|
||||
SM2Signature ::= SEQUENCE {
|
||||
R INTEGER,
|
||||
S INTEGER,
|
||||
}
|
||||
|
||||
SM2EnvelopedKey ::= SEQUENCE {
|
||||
symAlgID AlgorithmIdentifier,
|
||||
symEncryptedKey SM2CiphertextValue,
|
||||
sm2PublicKey SM2PublicKey,
|
||||
sm2EncryptedPrivateKey BIT STRING
|
||||
}
|
||||
|
||||
ZID = SM3(nbits(ID)||ID||a||b||xG||yG||xA||yA)
|
||||
|
||||
Default ID = "1234567812345678"
|
||||
|
||||
*/
|
||||
|
||||
typedef struct SM2CiphertextValue_st {
|
||||
ASN1_INTEGER *xCoordinate;
|
||||
ASN1_INTEGER *yCoordinate;
|
||||
ASN1_OCTET_STRING *hash;
|
||||
ASN1_OCTET_STRING *ciphertext;
|
||||
} SM2CiphertextValue;
|
||||
|
||||
ASN1_SEQUENCE(SM2CiphertextValue) = {
|
||||
ASN1_SIMPLE(SM2CiphertextValue, xCoordinate, ASN1_INTEGER),
|
||||
ASN1_SIMPLE(SM2CiphertextValue, yCoordinate, ASN1_INTEGER),
|
||||
ASN1_SIMPLE(SM2CiphertextValue, hash, ASN1_OCTET_STRING),
|
||||
ASN1_SIMPLE(SM2CiphertextValue, ciphertext, ASN1_OCTET_STRING),
|
||||
} ASN1_SEQUENCE_END(SM2CiphertextValue)
|
||||
IMPLEMENT_ASN1_FUNCTIONS(SM2CiphertextValue)
|
||||
IMPLEMENT_ASN1_DUP_FUNCTION(SM2CiphertextValue)
|
||||
|
||||
|
||||
int i2d_SM2_CIPHERTEXT_VALUE(const SM2_CIPHERTEXT_VALUE *c, unsigned char **out)
|
||||
{
|
||||
SM2CiphertextValue *asn1 = NULL;
|
||||
|
||||
/*
|
||||
asn1 = SM2CiphertextValue_new();
|
||||
|
||||
asn1->xCoordinate = BN_to_ASN1_INTEGER(x, NULL);
|
||||
asn1->yCoordinate = BN_to_ASN1_INTEGER(y, NULL);
|
||||
*/
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
SM2_CIPHERTEXT_VALUE *d2i_SM2_CIPHERTEXT_VALUE(SM2_CIPHERTEXT_VALUE **c,
|
||||
const unsigned char **in, long len)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
@@ -330,7 +330,9 @@ SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
goto end;
|
||||
}
|
||||
nbytes = (EC_GROUP_get_degree(ec_group) + 7) / 8;
|
||||
OPENSSL_assert(nbytes == BN_num_bytes(n));
|
||||
|
||||
|
||||
//OPENSSL_assert(nbytes == BN_num_bytes(n));
|
||||
|
||||
#if 0
|
||||
/* check sm2 curve and md is 256 bits */
|
||||
@@ -345,6 +347,7 @@ SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
do {
|
||||
BN_rand_range(k, n);
|
||||
} while (BN_is_zero(k));
|
||||
|
||||
|
||||
/* A2: C1 = [k]G = (x1, y1) */
|
||||
if (!EC_POINT_mul(ec_group, cv->ephem_point, k, NULL, NULL, bn_ctx)) {
|
||||
@@ -358,7 +361,7 @@ SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
if (EC_POINT_is_at_infinity(ec_group, point)) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
|
||||
/* A4: compute ECDH [k]P_B = (x2, y2) */
|
||||
if (!EC_POINT_mul(ec_group, point, NULL, pub_key, k, bn_ctx)) {
|
||||
goto end;
|
||||
@@ -368,11 +371,10 @@ SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
goto end;
|
||||
}
|
||||
OPENSSL_assert(len == nbytes * 2 + 1);
|
||||
|
||||
|
||||
/* A5: t = KDF(x2 || y2, klen) */
|
||||
kdf(buf + 1, len - 1, cv->ciphertext, &cv->ciphertext_size);
|
||||
|
||||
|
||||
for (i = 0; i < cv->ciphertext_size; i++) {
|
||||
if (cv->ciphertext[i]) {
|
||||
break;
|
||||
@@ -391,7 +393,7 @@ SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
for (i = 0; i < inlen; i++) {
|
||||
cv->ciphertext[i] ^= in[i];
|
||||
}
|
||||
|
||||
|
||||
/* A7: C3 = Hash(x2 || M || y2) */
|
||||
if (!EVP_DigestInit_ex(md_ctx, mac_md, NULL)) {
|
||||
goto end;
|
||||
@@ -409,6 +411,7 @@ SM2_CIPHERTEXT_VALUE *SM2_do_encrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
goto end;
|
||||
}
|
||||
|
||||
|
||||
ok = 1;
|
||||
|
||||
end:
|
||||
@@ -525,7 +528,7 @@ int SM2_do_decrypt(const EVP_MD *kdf_md, const EVP_MD *mac_md,
|
||||
goto end;
|
||||
}
|
||||
nbytes = (EC_GROUP_get_degree(ec_group) + 7) / 8;
|
||||
OPENSSL_assert(nbytes == BN_num_bytes(n));
|
||||
//OPENSSL_assert(nbytes == BN_num_bytes(n));
|
||||
|
||||
#if 0
|
||||
/* check sm2 curve and md is 256 bits */
|
||||
|
||||
@@ -90,16 +90,16 @@ static ERR_STRING_DATA SM2_str_functs[] = {
|
||||
};
|
||||
|
||||
static ERR_STRING_DATA SM2_str_reasons[] = {
|
||||
{ERR_REASON(SM2_R_BAD_DATA), "bad data"},
|
||||
{ERR_REASON(SM2_R_UNKNOWN_CIPHER_TYPE), "unknown cipher type"},
|
||||
{ERR_REASON(SM2_R_ENCRYPT_FAILED), "encrypt failed"},
|
||||
{ERR_REASON(SM2_R_DECRYPT_FAILED), "decrypt failed"},
|
||||
{ERR_REASON(SM2_R_UNKNOWN_MAC_TYPE), "unknown MAC type"},
|
||||
{ERR_REASON(SM2_R_GEN_MAC_FAILED), "MAC generation failed"},
|
||||
{ERR_REASON(SM2_R_VERIFY_MAC_FAILED), "MAC verification failed"},
|
||||
{ERR_REASON(SM2_R_ECDH_FAILED), "ECDH failed"},
|
||||
{ERR_REASON(SM2_R_BUFFER_TOO_SMALL), "buffer too small"},
|
||||
{ERR_REASON(SM2_R_SM2_KAP_NOT_INITED), "KAP not inited"},
|
||||
{ERR_REASON(SM2_R_BAD_DATA), "bad data"},
|
||||
{ERR_REASON(SM2_R_UNKNOWN_CIPHER_TYPE), "unknown cipher type"},
|
||||
{ERR_REASON(SM2_R_ENCRYPT_FAILED), "encrypt failed"},
|
||||
{ERR_REASON(SM2_R_DECRYPT_FAILED), "decrypt failed"},
|
||||
{ERR_REASON(SM2_R_UNKNOWN_MAC_TYPE), "unknown MAC type"},
|
||||
{ERR_REASON(SM2_R_GEN_MAC_FAILED), "MAC generation failed"},
|
||||
{ERR_REASON(SM2_R_VERIFY_MAC_FAILED), "MAC verification failed"},
|
||||
{ERR_REASON(SM2_R_ECDH_FAILED), "ECDH failed"},
|
||||
{ERR_REASON(SM2_R_BUFFER_TOO_SMALL), "buffer too small"},
|
||||
{ERR_REASON(SM2_R_SM2_KAP_NOT_INITED), "KAP not inited"},
|
||||
{ERR_REASON(SM2_R_RANDOM_NUMBER_GENERATION_FAILED), "random number generation failed"},
|
||||
{0,NULL}
|
||||
};
|
||||
|
||||
@@ -53,7 +53,7 @@
|
||||
#include <openssl/kdf.h>
|
||||
#include "sm2.h"
|
||||
|
||||
int SM2_KAP_CTX_init_ex(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
int SM2_KAP_CTX_init(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
EC_KEY *remote_pubkey, int is_initiator, int do_checksum)
|
||||
{
|
||||
int ret = 0;
|
||||
@@ -64,7 +64,7 @@ int SM2_KAP_CTX_init_ex(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
ctx->id_dgst_md = EVP_sm3();
|
||||
ctx->kdf_md = EVP_sm3();
|
||||
ctx->checksum_md = EVP_sm3();
|
||||
ctx->point_form = POINT_CONVERSION_COMPRESSED;
|
||||
ctx->point_form = SM2_DEFAULT_POINT_CONVERSION_FORM;
|
||||
|
||||
if (!(ctx->kdf = KDF_get_x9_63(ctx->kdf_md))) {
|
||||
SM2err(SM2_F_SM2_KAP_CTX_INIT, 0);
|
||||
@@ -80,8 +80,8 @@ int SM2_KAP_CTX_init_ex(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!SM2_compute_id_digest(ctx->id_dgst, &ctx->id_dgstlen,
|
||||
ctx->id_dgst_md, ec_key)) {
|
||||
if (!SM2_compute_id_digest(ctx->id_dgst_md, ctx->id_dgst,
|
||||
&ctx->id_dgstlen, ec_key)) {
|
||||
SM2err(SM2_F_SM2_KAP_CTX_INIT, 0);
|
||||
goto end;
|
||||
}
|
||||
@@ -91,8 +91,8 @@ int SM2_KAP_CTX_init_ex(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!SM2_compute_id_digest(ctx->remote_id_dgst, &ctx->remote_id_dgstlen,
|
||||
ctx->id_dgst_md, remote_pubkey)) {
|
||||
if (!SM2_compute_id_digest(ctx->id_dgst_md, ctx->remote_id_dgst,
|
||||
&ctx->remote_id_dgstlen, remote_pubkey)) {
|
||||
SM2err(SM2_F_SM2_KAP_CTX_INIT, 0);
|
||||
goto end;
|
||||
}
|
||||
@@ -118,7 +118,7 @@ int SM2_KAP_CTX_init_ex(SM2_KAP_CTX *ctx, EC_KEY *ec_key,
|
||||
goto end;
|
||||
}
|
||||
|
||||
w = (EC_GROUP_get_degree(ctx->group) + 1)/2 - 1;
|
||||
w = (BN_num_bits(ctx->order) + 1)/2 - 1;
|
||||
|
||||
if (!BN_one(ctx->two_pow_w)) {
|
||||
SM2err(SM2_F_SM2_KAP_CTX_INIT, ERR_R_BN_LIB);
|
||||
@@ -155,8 +155,10 @@ void SM2_KAP_CTX_cleanup(SM2_KAP_CTX *ctx)
|
||||
memset(ctx, 0, sizeof(*ctx));
|
||||
}
|
||||
|
||||
|
||||
/* FIXME: ephem_point_len should be both input and output */
|
||||
int SM2_KAP_prepare(SM2_KAP_CTX *ctx, unsigned char *ephem_point,
|
||||
size_t ephem_point_len)
|
||||
size_t *ephem_point_len)
|
||||
{
|
||||
int ret = 0;
|
||||
const BIGNUM *prikey;
|
||||
@@ -191,11 +193,13 @@ int SM2_KAP_prepare(SM2_KAP_CTX *ctx, unsigned char *ephem_point,
|
||||
|
||||
} while (BN_is_zero(r));
|
||||
|
||||
|
||||
if (!EC_POINT_mul(ctx->group, ctx->point, r, NULL, NULL, ctx->bn_ctx)) {
|
||||
SM2err(SM2_F_SM2_KAP_PREPARE, ERR_R_EC_LIB);
|
||||
goto end;
|
||||
}
|
||||
|
||||
|
||||
if (EC_METHOD_get_field_type(EC_GROUP_method_of(ctx->group)) == NID_X9_62_prime_field) {
|
||||
if (!EC_POINT_get_affine_coordinates_GFp(ctx->group, ctx->point, x, NULL, ctx->bn_ctx)) {
|
||||
SM2err(SM2_F_SM2_KAP_PREPARE, ERR_R_EC_LIB);
|
||||
@@ -252,11 +256,13 @@ int SM2_KAP_prepare(SM2_KAP_CTX *ctx, unsigned char *ephem_point,
|
||||
|
||||
/* encode R = (x, y) for output and local buffer */
|
||||
|
||||
// FIXME: ret is size_t and ret is the output length
|
||||
ret = EC_POINT_point2oct(ctx->group, ctx->point, ctx->point_form,
|
||||
ephem_point, ephem_point_len, ctx->bn_ctx);
|
||||
ephem_point, *ephem_point_len, ctx->bn_ctx);
|
||||
|
||||
memcpy(ctx->pt_buf, ephem_point, ret);
|
||||
|
||||
*ephem_point_len = ret;
|
||||
ret = 1;
|
||||
|
||||
end:
|
||||
if (h) BN_free(h);
|
||||
@@ -267,19 +273,21 @@ end:
|
||||
}
|
||||
|
||||
int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
size_t remote_point_len, unsigned char *key, size_t *keylen,
|
||||
size_t remote_point_len, unsigned char *key, size_t keylen,
|
||||
unsigned char *checksum, size_t *checksumlen)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
EVP_MD_CTX md_ctx;
|
||||
BIGNUM *x = NULL;
|
||||
unsigned char share_pt_buf[1 + (OPENSSL_ECC_MAX_FIELD_BITS+7)/4 + EVP_MAX_MD_SIZE * 2];
|
||||
unsigned char remote_pt_buf[1 + (OPENSSL_ECC_MAX_FIELD_BITS+7)/4];
|
||||
unsigned char share_pt_buf[1 + (OPENSSL_ECC_MAX_FIELD_BITS+7)/4 + EVP_MAX_MD_SIZE * 2 + 100];
|
||||
unsigned char remote_pt_buf[1 + (OPENSSL_ECC_MAX_FIELD_BITS+7)/4 + 111];
|
||||
unsigned char dgst[EVP_MAX_MD_SIZE];
|
||||
unsigned int dgstlen;
|
||||
unsigned int len, bnlen;
|
||||
size_t klen = keylen;
|
||||
|
||||
|
||||
EVP_MD_CTX_init(&md_ctx);
|
||||
|
||||
if (!(x = BN_new())) {
|
||||
@@ -329,14 +337,16 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_BN_LIB);
|
||||
goto end;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
if (!BN_mod_mul(x, x, ctx->t, ctx->order, ctx->bn_ctx)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_BN_LIB);
|
||||
goto end;
|
||||
}
|
||||
*/
|
||||
|
||||
/* U = ht * (P + x * R), check U != O */
|
||||
|
||||
|
||||
if (!EC_POINT_mul(ctx->group, ctx->point, NULL, ctx->point, x, ctx->bn_ctx)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EC_LIB);
|
||||
goto end;
|
||||
@@ -352,8 +362,8 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EC_LIB);
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!EC_POINT_is_at_infinity(ctx->group, ctx->point)) {
|
||||
|
||||
if (EC_POINT_is_at_infinity(ctx->group, ctx->point)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, 0);
|
||||
goto end;
|
||||
}
|
||||
@@ -380,12 +390,13 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
|
||||
/* key = KDF(xu, yu, ZA, ZB) */
|
||||
|
||||
if (!ctx->kdf(share_pt_buf, len, key, keylen)) {
|
||||
|
||||
if (!ctx->kdf(share_pt_buf + 1, len - 1, key, &klen)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, 0);
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!ctx->do_checksum) {
|
||||
if (ctx->do_checksum) {
|
||||
|
||||
/* generate checksum S1 or SB start with 0x02
|
||||
* S1 = SB = Hash(0x02, yu, Hash(xu, ZA, ZB, x1, y1, x2, y2))
|
||||
@@ -403,7 +414,8 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
}
|
||||
|
||||
if (ctx->is_initiator) {
|
||||
|
||||
|
||||
/* update ZA,ZB,x1,y1,x2,y2 */
|
||||
if (!EVP_DigestUpdate(&md_ctx, ctx->id_dgst, ctx->id_dgstlen)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
goto end;
|
||||
@@ -422,6 +434,7 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
if (!EVP_DigestUpdate(&md_ctx, ctx->remote_id_dgst, ctx->remote_id_dgstlen)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
goto end;
|
||||
@@ -444,6 +457,8 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
goto end;
|
||||
}
|
||||
/* now dgst == H(xu,ZA,ZB,x1,y1,x2,y2)
|
||||
*/
|
||||
|
||||
/* S1 = SB = Hash(0x02, yu, dgst) */
|
||||
|
||||
@@ -452,7 +467,7 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!EVP_DigestUpdate(&md_ctx, "\0x02", 1)) {
|
||||
if (!EVP_DigestUpdate(&md_ctx, "\x02", 1)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
goto end;
|
||||
}
|
||||
@@ -473,6 +488,7 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
goto end;
|
||||
}
|
||||
|
||||
} else {
|
||||
if (!EVP_DigestFinal_ex(&md_ctx, checksum, &len)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
@@ -490,7 +506,7 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!EVP_DigestUpdate(&md_ctx, "\0x03", 1)) {
|
||||
if (!EVP_DigestUpdate(&md_ctx, "\x03", 1)) {
|
||||
SM2err(SM2_F_SM2_KAP_COMPUTE_KEY, ERR_R_EVP_LIB);
|
||||
goto end;
|
||||
}
|
||||
@@ -519,6 +535,7 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
ret = 1;
|
||||
@@ -526,7 +543,7 @@ int SM2_KAP_compute_key(SM2_KAP_CTX *ctx, const unsigned char *remote_point,
|
||||
end:
|
||||
EVP_MD_CTX_cleanup(&md_ctx);
|
||||
if (x) BN_free(x);
|
||||
return 0;
|
||||
return ret;
|
||||
}
|
||||
|
||||
int SM2_KAP_final_check(SM2_KAP_CTX *ctx, const unsigned char *checksum,
|
||||
|
||||
@@ -65,14 +65,16 @@
|
||||
#define EC_MAX_NBYTES ((OPENSSL_ECC_MAX_FIELD_BITS + 7)/8)
|
||||
|
||||
|
||||
#define SM2_DEFAULT_ID "1234567812345678"
|
||||
|
||||
static void *sm2_data_dup(void *data) {
|
||||
return OPENSSL_strdup((const char *)data);
|
||||
if (data)
|
||||
return OPENSSL_strdup((const char *)data);
|
||||
else return NULL;
|
||||
}
|
||||
|
||||
static void sm2_data_free(void *data) {
|
||||
return OPENSSL_free(data);
|
||||
if (data)
|
||||
OPENSSL_free(data);
|
||||
}
|
||||
|
||||
int SM2_set_id(EC_KEY *ec_key, const char *id)
|
||||
@@ -80,28 +82,33 @@ int SM2_set_id(EC_KEY *ec_key, const char *id)
|
||||
char *pid;
|
||||
|
||||
if (strlen(id) > SM2_MAX_ID_LENGTH) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if ((pid = EC_KEY_get_key_method_data(ec_key, sm2_data_dup,
|
||||
sm2_data_free, sm2_data_free)) != NULL) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(pid = OPENSSL_strdup(id))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!EC_KEY_insert_key_method_data(ec_key, pid, sm2_data_dup,
|
||||
if (EC_KEY_insert_key_method_data(ec_key, pid, sm2_data_dup,
|
||||
sm2_data_free, sm2_data_free)) {
|
||||
OPENSSL_free(pid);
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
//ERR_print_errors_fp(stderr);
|
||||
//OPENSSL_free(pid);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
char *SM2_get_id(EC_KEY *ec_key)
|
||||
char *SM2_get0_id(EC_KEY *ec_key)
|
||||
{
|
||||
return (char *)EC_KEY_get_key_method_data(ec_key, sm2_data_dup,
|
||||
sm2_data_free, sm2_data_free);
|
||||
@@ -110,12 +117,12 @@ char *SM2_get_id(EC_KEY *ec_key)
|
||||
/*
|
||||
* pkdata = a || b || G.x || G.y || P.x || P.y
|
||||
*/
|
||||
static int sm2_get_public_key_data(unsigned char *buf, EC_KEY *ec_key)
|
||||
int sm2_get_public_key_data(unsigned char *buf, EC_KEY *ec_key)
|
||||
{
|
||||
int ret = -1;
|
||||
const EC_GROUP *ec_group = EC_KEY_get0_group(ec_key);
|
||||
const EC_POINT *point;
|
||||
int nbytes = (EC_GROUP_get_degree(ec_group) + 7) / 8;
|
||||
int nbytes;
|
||||
unsigned char oct[EC_MAX_NBYTES * 2 + 1];
|
||||
BN_CTX *bn_ctx = NULL;
|
||||
BIGNUM *p = NULL;
|
||||
@@ -123,12 +130,12 @@ static int sm2_get_public_key_data(unsigned char *buf, EC_KEY *ec_key)
|
||||
BIGNUM *y = NULL;
|
||||
size_t len;
|
||||
|
||||
OPENSSL_assert(ec_key);
|
||||
OPENSSL_assert(nbytes == 256/8);
|
||||
|
||||
if (!buf) {
|
||||
return (nbytes * 6);
|
||||
unsigned char *pbuf = buf;
|
||||
|
||||
if (!ec_key || !buf) {
|
||||
return 0;
|
||||
}
|
||||
nbytes = (EC_GROUP_get_degree(EC_KEY_get0_group(ec_key)) + 7)/8;
|
||||
bzero(buf, nbytes * 6);
|
||||
|
||||
bn_ctx = BN_CTX_new();
|
||||
@@ -139,44 +146,54 @@ static int sm2_get_public_key_data(unsigned char *buf, EC_KEY *ec_key)
|
||||
goto err;
|
||||
}
|
||||
|
||||
/* get curve coefficients a, b */
|
||||
if (!EC_GROUP_get_curve_GFp(ec_group, p, x, y, bn_ctx)) {
|
||||
goto err;
|
||||
if (EC_METHOD_get_field_type(EC_GROUP_method_of(ec_group)) == NID_X9_62_prime_field) {
|
||||
if (!EC_GROUP_get_curve_GFp(ec_group, p, x, y, bn_ctx)) {
|
||||
SM2err(SM2_F_SM2_KAP_PREPARE, ERR_R_EC_LIB);
|
||||
goto err;
|
||||
}
|
||||
} else {
|
||||
if (!EC_GROUP_get_curve_GF2m(ec_group, p, x, y, bn_ctx)) {
|
||||
SM2err(SM2_F_SM2_KAP_PREPARE, ERR_R_EC_LIB);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
buf += nbytes;
|
||||
if (!BN_bn2bin(x, buf - BN_num_bytes(x))) {
|
||||
goto err;
|
||||
}
|
||||
BN_bn2bin(x, buf - BN_num_bytes(x));
|
||||
buf += nbytes;
|
||||
if (!BN_bn2bin(y, buf - BN_num_bytes(y))) {
|
||||
goto err;
|
||||
}
|
||||
BN_bn2bin(y, buf - BN_num_bytes(y));
|
||||
|
||||
/* get curve generator coordinates */
|
||||
if (!(point = EC_GROUP_get0_generator(ec_group))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
if (!(len = EC_POINT_point2oct(ec_group, point,
|
||||
POINT_CONVERSION_UNCOMPRESSED, oct, sizeof(oct), bn_ctx))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
OPENSSL_assert(len == 32 * 2 + 1);
|
||||
//OPENSSL_assert(len == 32 * 2 + 1);
|
||||
memcpy(buf, oct + 1, len - 1);
|
||||
buf += len - 1;
|
||||
|
||||
/* get pub_key coorindates */
|
||||
if (!(point = EC_KEY_get0_public_key(ec_key))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
if (!(len = EC_POINT_point2oct(ec_group, point,
|
||||
POINT_CONVERSION_UNCOMPRESSED, oct, sizeof(oct), bn_ctx))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
OPENSSL_assert(len == 32 * 2 + 1);
|
||||
//OPENSSL_assert(len == 32 * 2 + 1);
|
||||
memcpy(buf, oct + 1, len - 1);
|
||||
buf += len - 1;
|
||||
|
||||
ret = (nbytes * 6);
|
||||
|
||||
err:
|
||||
if (bn_ctx) BN_CTX_free(bn_ctx);
|
||||
if (p) BN_free(p);
|
||||
@@ -187,42 +204,53 @@ err:
|
||||
}
|
||||
|
||||
//TODO: review this function again.
|
||||
int SM2_compute_id_digest(unsigned char *dgst, unsigned int *dgstlen,
|
||||
const EVP_MD *md, EC_KEY *ec_key)
|
||||
int SM2_compute_id_digest(const EVP_MD *md, unsigned char *dgst,
|
||||
unsigned int *dgstlen, EC_KEY *ec_key)
|
||||
{
|
||||
int ret = 0;
|
||||
EVP_MD_CTX *md_ctx = NULL;
|
||||
unsigned char pkdata[EC_MAX_NBYTES * 6];
|
||||
uint16_t idbits;
|
||||
unsigned char idbits[2];
|
||||
int pkdatalen;
|
||||
char *id = NULL;
|
||||
char *id;
|
||||
|
||||
if ((pkdatalen = sm2_get_public_key_data(pkdata, ec_key)) < 0) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!(id = SM2_get_id(ec_key))) {
|
||||
id = SM2_DEFAULT_ID;
|
||||
if (!(id = SM2_get0_id(ec_key))) {
|
||||
id = SM2_DEFAULT_ID;
|
||||
}
|
||||
|
||||
idbits = strlen(id) * 8;
|
||||
|
||||
idbits[0] = ((strlen(id) * 8) >> 8) % 256;
|
||||
idbits[1] = (strlen(id) * 8) % 256;
|
||||
|
||||
|
||||
if (!(md_ctx = EVP_MD_CTX_create())) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
if (!EVP_DigestInit_ex(md_ctx, md, NULL)) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
ERR_print_errors_fp(stderr);
|
||||
goto err;
|
||||
}
|
||||
if (!EVP_DigestUpdate(md_ctx, &idbits, sizeof(idbits))) {
|
||||
if (!EVP_DigestUpdate(md_ctx, idbits, sizeof(idbits))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
if (!EVP_DigestUpdate(md_ctx, id, strlen(id))) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
if (!EVP_DigestUpdate(md_ctx, pkdata, pkdatalen)) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
if (!EVP_DigestFinal(md_ctx, dgst, dgstlen)) {
|
||||
if (!EVP_DigestFinal_ex(md_ctx, dgst, dgstlen)) {
|
||||
fprintf(stderr, "error: %s %d\n", __FILE__, __LINE__);
|
||||
goto err;
|
||||
}
|
||||
|
||||
@@ -233,3 +261,40 @@ err:
|
||||
return ret;
|
||||
}
|
||||
|
||||
int SM2_compute_message_digest(const EVP_MD *id_md, const EVP_MD *msg_md,
|
||||
const void *msg, size_t msglen, unsigned char *dgst,
|
||||
unsigned int *dgstlen, EC_KEY *ec_key)
|
||||
{
|
||||
int ret = 0;
|
||||
EVP_MD_CTX md_ctx;
|
||||
unsigned char buf[EVP_MAX_MD_SIZE];
|
||||
unsigned int len;
|
||||
|
||||
EVP_MD_CTX_init(&md_ctx);
|
||||
|
||||
if (!EVP_DigestInit_ex(&md_ctx, msg_md, NULL)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!SM2_compute_id_digest(id_md, buf, &len, ec_key)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!EVP_DigestUpdate(&md_ctx, buf, len)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!EVP_DigestUpdate(&md_ctx, msg, msglen)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!EVP_DigestFinal_ex(&md_ctx, dgst, &dgstlen)) {
|
||||
goto err;
|
||||
}
|
||||
|
||||
ret = 1;
|
||||
err:
|
||||
EVP_MD_CTX_cleanup(&md_ctx);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* crypto/sm2/sm2_locl.h */
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2015 The GmSSL Project. All rights reserved.
|
||||
* Copyright (c) 2015-2016 The GmSSL Project. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@@ -58,15 +58,16 @@
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct sm2_data_st {
|
||||
int (*init)(EC_KEY *);
|
||||
ENGINE *engine;
|
||||
int flags;
|
||||
const ECDSA_METHOD *sign_meth;
|
||||
const ECDH_METHOD *kap_meth; /* FIXME: SM2 KAP is different from ECDH */
|
||||
CRYPTO_EX_DATA ex_data;
|
||||
} SM2_DATA;
|
||||
|
||||
struct sm2sign_method {
|
||||
const char *name;
|
||||
SM2_SIG *(*sm2_do_sign)(const unsigned char *dgst, int dgstlen);
|
||||
int (*sm2_sign_setup)(void);
|
||||
int (*sm2_do_verify)(void);
|
||||
int flag;
|
||||
void *app_data;
|
||||
};
|
||||
SM2_DATA *sm2_check(EC_KEY *eckey);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
@@ -58,7 +58,6 @@
|
||||
#include <openssl/rand.h>
|
||||
#include <openssl/sm2.h>
|
||||
|
||||
//FIXME: ECDSAerr()
|
||||
|
||||
/* k in [1, n-1], (x, y) = kG */
|
||||
static int sm2_sign_setup(EC_KEY *ec_key, BN_CTX *ctx_in, BIGNUM **kp, BIGNUM **xp)
|
||||
@@ -69,7 +68,7 @@ static int sm2_sign_setup(EC_KEY *ec_key, BN_CTX *ctx_in, BIGNUM **kp, BIGNUM **
|
||||
BIGNUM *k = NULL;
|
||||
BIGNUM *x = NULL;
|
||||
BIGNUM *order = NULL;
|
||||
EC_POINT *point=NULL;
|
||||
EC_POINT *point = NULL;
|
||||
|
||||
if (ec_key == NULL || (ec_group = EC_KEY_get0_group(ec_key)) == NULL) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_SIGN_SETUP, ERR_R_PASSED_NULL_PARAMETER);
|
||||
@@ -89,7 +88,6 @@ static int sm2_sign_setup(EC_KEY *ec_key, BN_CTX *ctx_in, BIGNUM **kp, BIGNUM **
|
||||
k = BN_new();
|
||||
x = BN_new();
|
||||
order = BN_new();
|
||||
|
||||
if (!k || !x || !order) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_SIGN_SETUP, ERR_R_MALLOC_FAILURE);
|
||||
goto err;
|
||||
@@ -133,7 +131,8 @@ static int sm2_sign_setup(EC_KEY *ec_key, BN_CTX *ctx_in, BIGNUM **kp, BIGNUM **
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//FIXME: do we need this?
|
||||
if (!BN_nnmod(x, x, order, ctx)) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_SIGN_SETUP, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
@@ -206,17 +205,22 @@ static ECDSA_SIG *sm2_do_sign(const unsigned char *dgst, int dgst_len,
|
||||
|
||||
/* convert dgst to e */
|
||||
i = BN_num_bits(order);
|
||||
#if 0
|
||||
if (8 * dgst_len > i) {
|
||||
dgst_len = (i + 7)/8;
|
||||
}
|
||||
#endif
|
||||
if (!BN_bin2bn(dgst, dgst_len, e)) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
|
||||
#if 0
|
||||
if ((8 * dgst_len > i) && !BN_rshift(e, e, 8 - (i & 0x7))) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
#endif
|
||||
|
||||
do {
|
||||
/* use or compute k and (kG).x */
|
||||
@@ -234,11 +238,14 @@ static ECDSA_SIG *sm2_do_sign(const unsigned char *dgst, int dgst_len,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* r = e + x (mod n) */
|
||||
if (!BN_mod_add(ret->r, ret->r, e, order, ctx)) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
|
||||
|
||||
if (!BN_mod_add(bn, ret->r, ck, order, ctx)) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
@@ -266,6 +273,7 @@ static ECDSA_SIG *sm2_do_sign(const unsigned char *dgst, int dgst_len,
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!BN_mod_mul(bn, ret->r, priv_key, order, ctx)) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
@@ -309,7 +317,7 @@ err:
|
||||
int sm2_do_verify(const unsigned char *dgst, int dgstlen,
|
||||
const ECDSA_SIG *sig, EC_KEY *ec_key)
|
||||
{
|
||||
int ret = -1;
|
||||
int ret = SM2_VERIFY_INNER_ERROR;
|
||||
const EC_GROUP *ec_group;
|
||||
const EC_POINT *pub_key;
|
||||
EC_POINT *point = NULL;
|
||||
@@ -366,17 +374,21 @@ int sm2_do_verify(const unsigned char *dgst, int dgstlen,
|
||||
|
||||
/* convert digest to e */
|
||||
i = BN_num_bits(order);
|
||||
#if 0
|
||||
if (8 * dgstlen > i) {
|
||||
dgstlen = (i + 7)/8;
|
||||
}
|
||||
#endif
|
||||
if (!BN_bin2bn(dgst, dgstlen, e)) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
#if 0
|
||||
if ((8 * dgstlen > i) && !BN_rshift(e, e, 8 - (i & 0x7))) {
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* compute (x, y) = sG + tP, P is pub_key */
|
||||
if (!(point = EC_POINT_new(ec_group))) {
|
||||
@@ -408,8 +420,12 @@ int sm2_do_verify(const unsigned char *dgst, int dgstlen,
|
||||
ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
|
||||
goto err;
|
||||
}
|
||||
ret = (BN_ucmp(t, sig->r) == 0);
|
||||
|
||||
if (BN_ucmp(t, sig->r) == 0) {
|
||||
ret = SM2_VERIFY_SUCCESS;
|
||||
} else {
|
||||
ret = SM2_VERIFY_FAILED;
|
||||
}
|
||||
|
||||
err:
|
||||
if (point) EC_POINT_free(point);
|
||||
if (order) BN_free(order);
|
||||
|
||||
1276
crypto/sm2/sm2test.c
1276
crypto/sm2/sm2test.c
File diff suppressed because it is too large
Load Diff
@@ -209,6 +209,7 @@ void ZUC_set_key(ZUC_KEY *key, const unsigned char *k, const unsigned char *iv)
|
||||
|
||||
void ZUC_encrypt(ZUC_KEY *key, size_t inlen, const unsigned char *in, unsigned char *out)
|
||||
{
|
||||
#if 0
|
||||
uint32_t word;
|
||||
int n = key->buf_index;
|
||||
|
||||
@@ -244,5 +245,6 @@ void ZUC_encrypt(ZUC_KEY *key, size_t inlen, const unsigned char *in, unsigned c
|
||||
|
||||
key->buf_index = n;
|
||||
return;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
72
demos/gmssl/sm2.c
Normal file
72
demos/gmssl/sm2.c
Normal file
@@ -0,0 +1,72 @@
|
||||
/* demo/gmssl/sm2.c */
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2015-2016 The GmSSL Project. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
*
|
||||
* 3. All advertising materials mentioning features or use of this
|
||||
* software must display the following acknowledgment:
|
||||
* "This product includes software developed by the GmSSL Project.
|
||||
* (http://gmssl.org/)"
|
||||
*
|
||||
* 4. The name "GmSSL Project" must not be used to endorse or promote
|
||||
* products derived from this software without prior written
|
||||
* permission. For written permission, please contact
|
||||
* guanzhi1980@gmail.com.
|
||||
*
|
||||
* 5. Products derived from this software may not be called "GmSSL"
|
||||
* nor may "GmSSL" appear in their names without prior written
|
||||
* permission of the GmSSL Project.
|
||||
*
|
||||
* 6. Redistributions of any form whatsoever must retain the following
|
||||
* acknowledgment:
|
||||
* "This product includes software developed by the GmSSL Project
|
||||
* (http://gmssl.org/)"
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE GmSSL PROJECT ``AS IS'' AND ANY
|
||||
* EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE GmSSL PROJECT OR
|
||||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
|
||||
* OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
* ====================================================================
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <strings.h>
|
||||
#include <openssl/ec.h>
|
||||
#include <openssl/bn.h>
|
||||
#include <openssl/evp.h>
|
||||
#include <openssl/rand.h>
|
||||
#include <openssl/engine.h>
|
||||
#include <openssl/sm2.h>
|
||||
|
||||
|
||||
int main()
|
||||
{
|
||||
ENGINE *engine = NULL;
|
||||
EVP_PKEY_CTX *pkctx;
|
||||
|
||||
|
||||
pkctx = EVP_PKEY_CTX_new_id(id, engine);
|
||||
}
|
||||
|
||||
|
||||
111
demos/gmssl/sms4enc.c
Normal file
111
demos/gmssl/sms4enc.c
Normal file
@@ -0,0 +1,111 @@
|
||||
/* demo/gmssl/sms4enc.c */
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2014 - 2016 The GmSSL Project. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
*
|
||||
* 3. All advertising materials mentioning features or use of this
|
||||
* software must display the following acknowledgment:
|
||||
* "This product includes software developed by the GmSSL Project.
|
||||
* (http://gmssl.org/)"
|
||||
*
|
||||
* 4. The name "GmSSL Project" must not be used to endorse or promote
|
||||
* products derived from this software without prior written
|
||||
* permission. For written permission, please contact
|
||||
* guanzhi1980@gmail.com.
|
||||
*
|
||||
* 5. Products derived from this software may not be called "GmSSL"
|
||||
* nor may "GmSSL" appear in their names without prior written
|
||||
* permission of the GmSSL Project.
|
||||
*
|
||||
* 6. Redistributions of any form whatsoever must retain the following
|
||||
* acknowledgment:
|
||||
* "This product includes software developed by the GmSSL Project
|
||||
* (http://gmssl.org/)"
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE GmSSL PROJECT ``AS IS'' AND ANY
|
||||
* EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE GmSSL PROJECT OR
|
||||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
|
||||
* OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
* ====================================================================
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <openssl/evp.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/hmac.h>
|
||||
#include <openssl/rand.h>
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int ret = -1;
|
||||
FILE *fp = stdin;
|
||||
unsigned char key[32];
|
||||
unsigned char buf[1024];
|
||||
int len;
|
||||
const EVP_MD *md;
|
||||
HMAC_CTX hmctx;
|
||||
unsigned char mac[EVP_MAX_MD_SIZE];
|
||||
unsigned int maclen, i;
|
||||
|
||||
if (argc == 2) {
|
||||
if (!(fp = fopen(argv[1], "r"))) {
|
||||
fprintf(stderr, "open file %s failed\n", argv[1]);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
HMAC_CTX_init(&hmctx);
|
||||
|
||||
RAND_bytes(key, sizeof(key));
|
||||
|
||||
OpenSSL_add_all_digests();
|
||||
if (!(md = EVP_get_digestbyname("sm3"))) {
|
||||
ERR_print_errors_fp(stderr);
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (!EVP_DigestSignInit()) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
while ((len = fread(buf, 1, sizeof(buf), fp))) {
|
||||
EVP_DigestSignUpdate(&hmctx, buf, len);
|
||||
}
|
||||
|
||||
if (!EVP_DigestSignFinal()) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
for (i = 0; i < maclen; i++) {
|
||||
printf("%02x", mac[i]);
|
||||
}
|
||||
printf("\n");
|
||||
ret = 0;
|
||||
|
||||
end:
|
||||
fclose(fp);
|
||||
EVP_cleanup();
|
||||
return ret;
|
||||
}
|
||||
|
||||
Binary file not shown.
1
include/openssl/cbcmac.h
Symbolic link
1
include/openssl/cbcmac.h
Symbolic link
@@ -0,0 +1 @@
|
||||
../../crypto/cbcmac/cbcmac.h
|
||||
1
include/openssl/ffx.h
Symbolic link
1
include/openssl/ffx.h
Symbolic link
@@ -0,0 +1 @@
|
||||
../../crypto/ffx/ffx.h
|
||||
54
test/p
Normal file
54
test/p
Normal file
@@ -0,0 +1,54 @@
|
||||
#!/bin/sh
|
||||
|
||||
testsrc=testenc
|
||||
test=./p
|
||||
cmd="../util/shlib_wrap.sh ../apps/openssl"
|
||||
|
||||
cat $testsrc >$test;
|
||||
|
||||
echo cat
|
||||
$cmd enc < $test > $test.cipher
|
||||
$cmd enc < $test.cipher >$test.clear
|
||||
cmp $test $test.clear
|
||||
if [ $? != 0 ]
|
||||
then
|
||||
exit 1
|
||||
else
|
||||
/bin/rm $test.cipher $test.clear
|
||||
fi
|
||||
echo base64
|
||||
$cmd enc -a -e < $test > $test.cipher
|
||||
$cmd enc -a -d < $test.cipher >$test.clear
|
||||
cmp $test $test.clear
|
||||
if [ $? != 0 ]
|
||||
then
|
||||
exit 1
|
||||
else
|
||||
/bin/rm $test.cipher $test.clear
|
||||
fi
|
||||
|
||||
for i in `$cmd list-cipher-commands`
|
||||
do
|
||||
echo $i
|
||||
$cmd $i -bufsize 113 -e -k test < $test > $test.$i.cipher
|
||||
$cmd $i -bufsize 157 -d -k test < $test.$i.cipher >$test.$i.clear
|
||||
cmp $test $test.$i.clear
|
||||
if [ $? != 0 ]
|
||||
then
|
||||
exit 1
|
||||
else
|
||||
/bin/rm $test.$i.cipher $test.$i.clear
|
||||
fi
|
||||
|
||||
echo $i base64
|
||||
$cmd $i -bufsize 113 -a -e -k test < $test > $test.$i.cipher
|
||||
$cmd $i -bufsize 157 -a -d -k test < $test.$i.cipher >$test.$i.clear
|
||||
cmp $test $test.$i.clear
|
||||
if [ $? != 0 ]
|
||||
then
|
||||
exit 1
|
||||
else
|
||||
/bin/rm $test.$i.cipher $test.$i.clear
|
||||
fi
|
||||
done
|
||||
rm -f $test
|
||||
BIN
test/p.zuc.cipher
Normal file
BIN
test/p.zuc.cipher
Normal file
Binary file not shown.
BIN
test/p.zuc.clear
Normal file
BIN
test/p.zuc.clear
Normal file
Binary file not shown.
Reference in New Issue
Block a user