mirror of
https://github.com/guanzhi/GmSSL.git
synced 2026-06-13 08:23:50 +08:00
version 2.5.3
new sms4 api, go api and ciphersuites
This commit is contained in:
@@ -24,3 +24,9 @@ INCLUDE[e_aes_cbc_hmac_sha256.o]=../modes
|
||||
INCLUDE[e_camellia.o]=.. ../modes
|
||||
INCLUDE[e_des.o]=..
|
||||
INCLUDE[e_des3.o]=..
|
||||
INCLUDE[e_sms4.o]=.. ../modes ../sms4
|
||||
INCLUDE[e_sms4_ccm.o]=.. ../modes
|
||||
INCLUDE[e_sms4_gcm.o]=.. ../modes
|
||||
INCLUDE[e_sms4_ocb.o]=.. ../modes
|
||||
INCLUDE[e_sms4_xts.o]=.. ../modes
|
||||
INCLUDE[e_sms4_wrap.o]=.. ../modes
|
||||
|
||||
@@ -60,12 +60,13 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/objects.h>
|
||||
#include "evp_locl.h"
|
||||
# include "internal/evp_int.h"
|
||||
#include "../modes/modes_lcl.h"
|
||||
#include "internal/evp_int.h"
|
||||
#include "modes_lcl.h"
|
||||
|
||||
#ifndef OPENSSL_NO_SMS4
|
||||
|
||||
# include <openssl/sms4.h>
|
||||
# include "sms4_lcl.h"
|
||||
|
||||
typedef struct {
|
||||
block128_f block;
|
||||
@@ -73,7 +74,10 @@ typedef struct {
|
||||
cbc128_f cbc;
|
||||
ctr128_f ctr;
|
||||
} stream;
|
||||
sms4_key_t ks;
|
||||
union {
|
||||
double align;
|
||||
sms4_key_t ks;
|
||||
} ks;
|
||||
} EVP_SMS4_KEY;
|
||||
|
||||
|
||||
@@ -85,12 +89,19 @@ static int sms4_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
|
||||
mode = EVP_CIPHER_CTX_mode(ctx);
|
||||
|
||||
if ((mode == EVP_CIPH_ECB_MODE || mode == EVP_CIPH_CBC_MODE) && !enc) {
|
||||
sms4_set_decrypt_key(&dat->ks, key);
|
||||
sms4_set_decrypt_key(&dat->ks.ks, key);
|
||||
} else {
|
||||
sms4_set_encrypt_key(&dat->ks, key);
|
||||
sms4_set_encrypt_key(&dat->ks.ks, key);
|
||||
}
|
||||
dat->block = (block128_f)sms4_encrypt;
|
||||
dat->stream.cbc = mode == EVP_CIPH_CBC_MODE ? (cbc128_f) sms4_cbc_encrypt : NULL;
|
||||
|
||||
if (mode == EVP_CIPH_CTR_MODE) {
|
||||
# ifdef SMS4_AVX2
|
||||
dat->stream.ctr = (ctr128_f) sms4_avx2_ctr32_encrypt_blocks;
|
||||
# else
|
||||
dat->stream.ctr = (ctr128_f) sms4_ctr32_encrypt_blocks;
|
||||
# endif
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -106,7 +117,7 @@ static int sms4_ctrl(EVP_CIPHER_CTX *c, int type, int arg, void *ptr)
|
||||
}
|
||||
}
|
||||
|
||||
IMPLEMENT_BLOCK_CIPHER(sms4, ks, sms4, EVP_SMS4_KEY, NID_sms4,
|
||||
IMPLEMENT_BLOCK_CIPHER(sms4, ks.ks, sms4, EVP_SMS4_KEY, NID_sms4,
|
||||
SMS4_BLOCK_SIZE, SMS4_KEY_LENGTH, SMS4_IV_LENGTH, 128,
|
||||
EVP_CIPH_FLAG_DEFAULT_ASN1, sms4_init_key, NULL, NULL, NULL, sms4_ctrl)
|
||||
|
||||
@@ -118,19 +129,19 @@ static int sms4_cfb1_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
EVP_SMS4_KEY *sms4_key = (EVP_SMS4_KEY *)ctx->cipher_data;
|
||||
|
||||
if (ctx->flags & EVP_CIPH_FLAG_LENGTH_BITS) {
|
||||
CRYPTO_cfb128_1_encrypt(in, out, len, &sms4_key->ks,
|
||||
CRYPTO_cfb128_1_encrypt(in, out, len, &sms4_key->ks.ks,
|
||||
ctx->iv, &ctx->num, ctx->encrypt, (block128_f)sms4_encrypt);
|
||||
return 1;
|
||||
}
|
||||
|
||||
while (len >= MAXBITCHUNK) {
|
||||
CRYPTO_cfb128_1_encrypt(in, out, MAXBITCHUNK * 8, &sms4_key->ks,
|
||||
CRYPTO_cfb128_1_encrypt(in, out, MAXBITCHUNK * 8, &sms4_key->ks.ks,
|
||||
ctx->iv, &ctx->num, ctx->encrypt, (block128_f)sms4_encrypt);
|
||||
len -= MAXBITCHUNK;
|
||||
}
|
||||
|
||||
if (len) {
|
||||
CRYPTO_cfb128_1_encrypt(in, out, len * 8, &sms4_key->ks,
|
||||
CRYPTO_cfb128_1_encrypt(in, out, len * 8, &sms4_key->ks.ks,
|
||||
ctx->iv, &ctx->num, ctx->encrypt, (block128_f)sms4_encrypt);
|
||||
}
|
||||
|
||||
@@ -160,7 +171,7 @@ static int sms4_cfb8_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
{
|
||||
EVP_SMS4_KEY *sms4_key = (EVP_SMS4_KEY *)ctx->cipher_data;
|
||||
|
||||
CRYPTO_cfb128_8_encrypt(in, out, len, &sms4_key->ks,
|
||||
CRYPTO_cfb128_8_encrypt(in, out, len, &sms4_key->ks.ks,
|
||||
ctx->iv, &ctx->num, ctx->encrypt, (block128_f)sms4_encrypt);
|
||||
|
||||
return 1;
|
||||
@@ -190,10 +201,16 @@ static int sms4_ctr_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
unsigned int num = EVP_CIPHER_CTX_num(ctx);
|
||||
EVP_SMS4_KEY *sms4 = (EVP_SMS4_KEY *)ctx->cipher_data;
|
||||
|
||||
CRYPTO_ctr128_encrypt(in, out, len, &sms4->ks,
|
||||
EVP_CIPHER_CTX_iv_noconst(ctx),
|
||||
EVP_CIPHER_CTX_buf_noconst(ctx), &num,
|
||||
sms4->block);
|
||||
if (sms4->stream.ctr)
|
||||
CRYPTO_ctr128_encrypt_ctr32(in, out, len, &sms4->ks.ks,
|
||||
EVP_CIPHER_CTX_iv_noconst(ctx),
|
||||
EVP_CIPHER_CTX_buf_noconst(ctx),
|
||||
&num, sms4->stream.ctr);
|
||||
else
|
||||
CRYPTO_ctr128_encrypt(in, out, len, &sms4->ks.ks,
|
||||
EVP_CIPHER_CTX_iv_noconst(ctx),
|
||||
EVP_CIPHER_CTX_buf_noconst(ctx), &num,
|
||||
sms4->block);
|
||||
|
||||
EVP_CIPHER_CTX_set_num(ctx, num);
|
||||
return 1;
|
||||
|
||||
@@ -61,12 +61,12 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/objects.h>
|
||||
#include "evp_locl.h"
|
||||
# include "internal/evp_int.h"
|
||||
#include "../modes/modes_lcl.h"
|
||||
#include "internal/evp_int.h"
|
||||
#include "modes_lcl.h"
|
||||
|
||||
#ifndef OPENSSL_NO_SMS4
|
||||
|
||||
#include <openssl/sms4.h>
|
||||
# include <openssl/sms4.h>
|
||||
|
||||
typedef struct {
|
||||
union {
|
||||
@@ -312,10 +312,10 @@ static int sms4_ccm_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
}
|
||||
}
|
||||
|
||||
#define SMS4_CCM_BLOCK_SIZE 1
|
||||
#define SMS4_CCM_IV_LENGTH 7
|
||||
# define SMS4_CCM_BLOCK_SIZE 1
|
||||
# define SMS4_CCM_IV_LENGTH 7
|
||||
|
||||
#define SMS4_CCM_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 \
|
||||
# define SMS4_CCM_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 \
|
||||
| EVP_CIPH_CUSTOM_IV | EVP_CIPH_FLAG_CUSTOM_CIPHER \
|
||||
| EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_CTRL_INIT \
|
||||
| EVP_CIPH_CUSTOM_COPY \
|
||||
|
||||
@@ -62,12 +62,12 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/objects.h>
|
||||
#include "evp_locl.h"
|
||||
# include "internal/evp_int.h"
|
||||
#include "../modes/modes_lcl.h"
|
||||
#include "internal/evp_int.h"
|
||||
#include "modes_lcl.h"
|
||||
|
||||
#ifndef OPENSSL_NO_SMS4
|
||||
|
||||
#include <openssl/sms4.h>
|
||||
# include <openssl/sms4.h>
|
||||
|
||||
typedef struct {
|
||||
union {
|
||||
@@ -434,10 +434,10 @@ static int sms4_gcm_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
|
||||
}
|
||||
|
||||
#define SMS4_GCM_BLOCK_SIZE 1
|
||||
#define SMS4_GCM_IV_LENGTH 12
|
||||
# define SMS4_GCM_BLOCK_SIZE 1
|
||||
# define SMS4_GCM_IV_LENGTH 12
|
||||
|
||||
#define SMS4_GCM_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 \
|
||||
# define SMS4_GCM_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 \
|
||||
| EVP_CIPH_CUSTOM_IV | EVP_CIPH_FLAG_CUSTOM_CIPHER \
|
||||
| EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_CTRL_INIT \
|
||||
| EVP_CIPH_CUSTOM_COPY | EVP_CIPH_GCM_MODE \
|
||||
|
||||
@@ -61,8 +61,8 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/objects.h>
|
||||
#include "evp_locl.h"
|
||||
# include "internal/evp_int.h"
|
||||
#include "../modes/modes_lcl.h"
|
||||
#include "internal/evp_int.h"
|
||||
#include "modes_lcl.h"
|
||||
|
||||
#ifndef OPENSSL_NO_SMS4
|
||||
|
||||
@@ -345,9 +345,9 @@ static int sms4_ocb_cleanup(EVP_CIPHER_CTX *c)
|
||||
return 1;
|
||||
}
|
||||
|
||||
#define SMS4_OCB_IV_LENGTH 12
|
||||
# define SMS4_OCB_IV_LENGTH 12
|
||||
|
||||
#define SMS4_OCB_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 \
|
||||
# define SMS4_OCB_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 \
|
||||
| EVP_CIPH_CUSTOM_IV | EVP_CIPH_FLAG_CUSTOM_CIPHER \
|
||||
| EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_CTRL_INIT \
|
||||
| EVP_CIPH_CUSTOM_COPY \
|
||||
|
||||
@@ -61,8 +61,8 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/objects.h>
|
||||
#include "evp_locl.h"
|
||||
# include "internal/evp_int.h"
|
||||
#include "../modes/modes_lcl.h"
|
||||
#include "internal/evp_int.h"
|
||||
#include "modes_lcl.h"
|
||||
|
||||
#ifndef OPENSSL_NO_SMS4
|
||||
# include <openssl/sms4.h>
|
||||
@@ -152,7 +152,7 @@ static int sms4_wrap_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
return rv ? (int)rv : -1;
|
||||
}
|
||||
|
||||
#define SMS4_WRAP_FLAGS (EVP_CIPH_WRAP_MODE \
|
||||
# define SMS4_WRAP_FLAGS (EVP_CIPH_WRAP_MODE \
|
||||
| EVP_CIPH_CUSTOM_IV | EVP_CIPH_FLAG_CUSTOM_CIPHER \
|
||||
| EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_FLAG_DEFAULT_ASN1)
|
||||
|
||||
|
||||
@@ -61,8 +61,8 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/objects.h>
|
||||
#include "evp_locl.h"
|
||||
# include "internal/evp_int.h"
|
||||
#include "../modes/modes_lcl.h"
|
||||
#include "internal/evp_int.h"
|
||||
#include "modes_lcl.h"
|
||||
|
||||
#ifndef OPENSSL_NO_SMS4
|
||||
# include <openssl/sms4.h>
|
||||
@@ -151,9 +151,9 @@ static int sms4_xts_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
||||
return 1;
|
||||
}
|
||||
|
||||
#define SMS4_XTS_BLOCK_SIZE 1
|
||||
# define SMS4_XTS_BLOCK_SIZE 1
|
||||
|
||||
#define SMS4_XTS_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 | EVP_CIPH_CUSTOM_IV \
|
||||
# define SMS4_XTS_FLAGS (EVP_CIPH_FLAG_DEFAULT_ASN1 | EVP_CIPH_CUSTOM_IV \
|
||||
| EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_CTRL_INIT \
|
||||
| EVP_CIPH_CUSTOM_COPY)
|
||||
|
||||
|
||||
@@ -62,17 +62,29 @@
|
||||
|
||||
static int sm9hash2_sm3_init(EVP_MD_CTX *ctx)
|
||||
{
|
||||
return 0;
|
||||
if (!ctx || !EVP_MD_CTX_md_data(ctx)) {
|
||||
return 0;
|
||||
}
|
||||
sm3_init(EVP_MD_CTX_md_data(ctx));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int sm9hash2_sm3_update(EVP_MD_CTX *ctx, const void *in, size_t inlen)
|
||||
{
|
||||
return 0;
|
||||
if (!ctx || !EVP_MD_CTX_md_data(ctx) || (!in && inlen != 0)) {
|
||||
return 0;
|
||||
}
|
||||
sm3_update(EVP_MD_CTX_md_data(ctx), in, inlen);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int sm9hash2_sm3_final(EVP_MD_CTX *ctx, unsigned char *md)
|
||||
{
|
||||
return 0;
|
||||
if (!ctx || !EVP_MD_CTX_md_data(ctx) || !md) {
|
||||
return 0;
|
||||
}
|
||||
sm3_final(EVP_MD_CTX_md_data(ctx), md);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int sm9hash2_sm3_ctrl(EVP_MD_CTX *ctx, int cmd, int p1, void *p2)
|
||||
|
||||
59
crypto/include/internal/rotate.h
Normal file
59
crypto/include/internal/rotate.h
Normal file
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* Copyright 1999-2016 The OpenSSL Project Authors. 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 <openssl/crypto.h>
|
||||
|
||||
/*
|
||||
* Engage compiler specific rotate intrinsic function if available.
|
||||
*/
|
||||
#undef ROL32
|
||||
#ifndef PEDANTIC
|
||||
# if defined(_MSC_VER)
|
||||
# define ROL32(a,n) _lrotl(a,n)
|
||||
# elif defined(__ICC)
|
||||
# define ROL32(a,n) _rotl(a,n)
|
||||
# elif defined(__GNUC__) && __GNUC__>=2 && !defined(OPENSSL_NO_ASM) && !defined(OPENSSL_NO_INLINE_ASM)
|
||||
/*
|
||||
* Some GNU C inline assembler templates. Note that these are
|
||||
* rotates by *constant* number of bits! But that's exactly
|
||||
* what we need here...
|
||||
* <appro@fy.chalmers.se>
|
||||
*/
|
||||
# if defined(__i386) || defined(__i386__) || defined(__x86_64) || defined(__x86_64__)
|
||||
# define ROL32(a,n) ({ register unsigned int ret; \
|
||||
asm ( \
|
||||
"roll %1,%0" \
|
||||
: "=r"(ret) \
|
||||
: "I"(n), "0"((unsigned int)(a)) \
|
||||
: "cc"); \
|
||||
ret; \
|
||||
})
|
||||
# elif defined(_ARCH_PPC) || defined(_ARCH_PPC64) || \
|
||||
defined(__powerpc) || defined(__ppc__) || defined(__powerpc64__)
|
||||
# define ROL32(a,n) ({ register unsigned int ret; \
|
||||
asm ( \
|
||||
"rlwinm %0,%1,%2,0,31" \
|
||||
: "=r"(ret) \
|
||||
: "r"(a), "I"(n)); \
|
||||
ret; \
|
||||
})
|
||||
# elif defined(__s390x__)
|
||||
# define ROL32(a,n) ({ register unsigned int ret; \
|
||||
asm ("rll %0,%1,%2" \
|
||||
: "=r"(ret) \
|
||||
: "r"(a), "I"(n)); \
|
||||
ret; \
|
||||
})
|
||||
# endif
|
||||
# endif
|
||||
#endif /* PEDANTIC */
|
||||
|
||||
#ifndef ROL32
|
||||
# define ROL32(a,n) (((a)<<(n))|(((a)&0xffffffff)>>(32-(n))))
|
||||
#endif
|
||||
@@ -56,15 +56,6 @@
|
||||
#include <openssl/crypto.h>
|
||||
#include "sm9_lcl.h"
|
||||
|
||||
/*
|
||||
int SM9_do_wrap_key(const EVP_MD *kdf_md
|
||||
unsigned char *key, size_t keylen, EC_POINT *C,
|
||||
SM9PublicKey *pk);
|
||||
|
||||
int SM9_do_unwrap_key(const EVP_MD *kdf_md,
|
||||
unsigned char *key, size_t keylen, const EC_POINT *C,
|
||||
SM9PublicKey *pk);
|
||||
*/
|
||||
|
||||
int SM9_unwrap_key(int type,
|
||||
unsigned char *key, size_t keylen,
|
||||
@@ -82,7 +73,7 @@ int SM9_unwrap_key(int type,
|
||||
const EVP_MD *kdf_md;
|
||||
unsigned char wbuf[384];
|
||||
unsigned char *out = key;
|
||||
size_t outlen = keylen;
|
||||
size_t outlen = keylen;
|
||||
unsigned char counter[4] = {0, 0, 0, 1};
|
||||
unsigned char dgst[64];
|
||||
unsigned int len;
|
||||
@@ -132,7 +123,7 @@ int SM9_unwrap_key(int type,
|
||||
if (!fp12_to_bin(w, wbuf)) {
|
||||
SM9err(SM9_F_SM9_UNWRAP_KEY, ERR_R_MALLOC_FAILURE);
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
|
||||
/* K = KDF(C||w||ID_B, klen) */
|
||||
while (outlen > 0) {
|
||||
@@ -261,7 +252,7 @@ int SM9_wrap_key(int type, /* NID_sm9kdf_with_sm3 */
|
||||
|
||||
do {
|
||||
unsigned char *out = key;
|
||||
size_t outlen = keylen;
|
||||
size_t outlen = keylen;
|
||||
unsigned char counter[4] = {0, 0, 0, 1};
|
||||
unsigned int len;
|
||||
|
||||
@@ -337,11 +328,6 @@ end:
|
||||
return ret;
|
||||
}
|
||||
|
||||
int SM9_MASTER_KEY_ciphertext_size(const SM9_MASTER_KEY *master, size_t len)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
int SM9_encrypt(int type,
|
||||
const unsigned char *in, size_t inlen,
|
||||
unsigned char *out, size_t *outlen,
|
||||
@@ -441,7 +427,7 @@ int SM9_decrypt(int type,
|
||||
int C2_len;
|
||||
unsigned char mac[EVP_MAX_MD_SIZE];
|
||||
unsigned int maclen = sizeof(mac);
|
||||
int len, i;
|
||||
int i;
|
||||
|
||||
/* parse type */
|
||||
switch (type) {
|
||||
@@ -525,6 +511,7 @@ int SM9_decrypt(int type,
|
||||
|
||||
end:
|
||||
SM9Ciphertext_free(sm9cipher);
|
||||
OPENSSL_clear_free(key, keylen);
|
||||
if (key)
|
||||
OPENSSL_clear_free(key, keylen);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -54,9 +54,6 @@
|
||||
#include "../bn/bn_lcl.h"
|
||||
#include "sm9_lcl.h"
|
||||
|
||||
static int BN_hash_to_range(const EVP_MD *md, BIGNUM **bn,
|
||||
const void *s, size_t slen, const BIGNUM *range, BN_CTX *bn_ctx);
|
||||
|
||||
#if 0
|
||||
typedef struct {
|
||||
int nid;
|
||||
@@ -152,28 +149,6 @@ int SM9PublicKey_get_gmtls_encoded(SM9PublicParameters *mpk,
|
||||
}
|
||||
|
||||
|
||||
int SM9_hash2(const EVP_MD *md, BIGNUM **r,
|
||||
const unsigned char *data, size_t datalen,
|
||||
const unsigned char *elem, size_t elemlen,
|
||||
const BIGNUM *range, BN_CTX *ctx)
|
||||
{
|
||||
unsigned char *buf;
|
||||
|
||||
if (!(buf = OPENSSL_malloc(datalen + elemlen))) {
|
||||
return 0;
|
||||
}
|
||||
memcpy(buf, data, datalen);
|
||||
memcpy(buf + datalen, elem, elemlen);
|
||||
|
||||
if (!BN_hash_to_range(md, r, buf, datalen + elemlen, range, ctx)) {
|
||||
OPENSSL_free(buf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
OPENSSL_free(buf);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int SM9_DigestInit(EVP_MD_CTX *ctx, unsigned char prefix,
|
||||
const EVP_MD *md, ENGINE *impl)
|
||||
{
|
||||
@@ -234,6 +209,10 @@ int sm9_check_sign_scheme(int nid)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* SM9_hash2() should be implemented as an EVP_MD module
|
||||
* and refactor the SM9_SignInit/Update/Final API
|
||||
*/
|
||||
#if 0
|
||||
int BN_hash_to_range(const EVP_MD *md, BIGNUM **bn,
|
||||
const void *s, size_t slen, const BIGNUM *range, BN_CTX *bn_ctx)
|
||||
{
|
||||
@@ -315,3 +294,25 @@ end:
|
||||
OPENSSL_free(buf);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int SM9_hash2(const EVP_MD *md, BIGNUM **r,
|
||||
const unsigned char *data, size_t datalen,
|
||||
const unsigned char *elem, size_t elemlen,
|
||||
const BIGNUM *range, BN_CTX *ctx)
|
||||
{
|
||||
EVP_MD_CTX *mctx = NULL;
|
||||
|
||||
if (!(mctx = EVP_MD_CTX_new())) {
|
||||
}
|
||||
|
||||
if (!EVP_DigestInit_ex(mctx, md, NULL)
|
||||
|| !EVP_DigestUpdate(mctx, data, datalen)
|
||||
|| !EVP_DigestUpdate(mctx, elem, elemlen)
|
||||
|| !EVP_DigestFinal_ex(mctx, buf, &buflen)) {
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -183,9 +183,11 @@ static int pkey_sm9_master_encrypt(EVP_PKEY_CTX *ctx,
|
||||
|
||||
static int pkey_sm9_master_derive(EVP_PKEY_CTX *ctx, unsigned char *key, size_t *keylen)
|
||||
{
|
||||
/*
|
||||
SM9_MASTER_PKEY_CTX *dctx = EVP_PKEY_CTX_get_data(ctx);
|
||||
SM9_MASTER_KEY *sm9_master = EVP_PKEY_get0_SM9_MASTER(
|
||||
EVP_PKEY_CTX_get0_pkey(ctx));
|
||||
*/
|
||||
|
||||
return -2;
|
||||
}
|
||||
|
||||
@@ -166,6 +166,7 @@ static int fp2_equ(const fp2_t a, const fp2_t b)
|
||||
return !BN_cmp(a[0], b[0]) && !BN_cmp(a[1], b[1]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp2_equ_hex(const fp2_t a, const char *str[2], BN_CTX *ctx)
|
||||
{
|
||||
fp2_t t;
|
||||
@@ -173,7 +174,9 @@ static int fp2_equ_hex(const fp2_t a, const char *str[2], BN_CTX *ctx)
|
||||
fp2_set_hex(t, str);
|
||||
return fp2_equ(a, t);
|
||||
}
|
||||
#endif
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp2_add_word(fp2_t r, const fp2_t a, unsigned long b, const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
BIGNUM *w = NULL;
|
||||
@@ -187,6 +190,7 @@ static int fp2_add_word(fp2_t r, const fp2_t a, unsigned long b, const BIGNUM *p
|
||||
BN_free(w);
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp2_add(fp2_t r, const fp2_t a, const fp2_t b, const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
@@ -299,7 +303,7 @@ static int fp2_mul_num(fp2_t r, const fp2_t a, const BIGNUM *n, const BIGNUM *p,
|
||||
BIGNUM *r1 = NULL;
|
||||
if (!(r0 = BN_CTX_get(ctx))
|
||||
|| !(r1 = BN_CTX_get(ctx))
|
||||
|
||||
|
||||
|| !BN_mod_mul(r0, a[0], n, p, ctx)
|
||||
|| !BN_mod_mul(r1, a[1], n, p, ctx)
|
||||
|
||||
@@ -426,11 +430,13 @@ static int fp2_inv(fp2_t r, const fp2_t a, const BIGNUM *p, BN_CTX *ctx)
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp2_div(fp2_t r, const fp2_t a, const fp2_t b, const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
return fp2_inv(r, b, p, ctx)
|
||||
&& fp2_mul(r, a, r, p, ctx);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp2_to_bin(const fp2_t a, unsigned char to[64])
|
||||
{
|
||||
@@ -443,9 +449,10 @@ static int fp2_to_bin(const fp2_t a, unsigned char to[64])
|
||||
static int fp2_from_bin(fp2_t a, const unsigned char from[64])
|
||||
{
|
||||
return BN_bin2bn(from, 32, a[1])
|
||||
&& BN_bin2bn(from + 32, 32, a[0]);
|
||||
&& BN_bin2bn(from + 32, 32, a[0]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp2_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
const char *_a[] = {
|
||||
@@ -540,7 +547,7 @@ static int fp2_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
fp2_sqr_u(r, a, p, ctx);
|
||||
ok = fp2_equ_hex(r, sqru_a, ctx);
|
||||
printf("fp2 test %d: %s\n", __LINE__, ok ? "ok" : "error");
|
||||
|
||||
|
||||
fp2_inv(r, a, p, ctx);
|
||||
ok = fp2_equ_hex(r, inv_a, ctx);
|
||||
printf("fp2 test %d: %s\n", __LINE__, ok ? "ok" : "error");
|
||||
@@ -561,6 +568,7 @@ static int fp2_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp4_init(fp4_t a, BN_CTX *ctx)
|
||||
{
|
||||
@@ -580,11 +588,13 @@ static void fp4_cleanup(fp4_t a)
|
||||
fp2_cleanup(a[1]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static void fp4_clear_cleanup(fp4_t a)
|
||||
{
|
||||
fp2_clear_cleanup(a[0]);
|
||||
fp2_clear_cleanup(a[1]);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp4_print(const fp4_t a)
|
||||
{
|
||||
@@ -672,6 +682,7 @@ static int fp4_equ(const fp4_t a, const fp4_t b)
|
||||
&& fp2_equ(a[1], b[1]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp4_equ_hex(const fp4_t a, const char *str[4], BN_CTX *ctx)
|
||||
{
|
||||
fp4_t t;
|
||||
@@ -679,6 +690,7 @@ static int fp4_equ_hex(const fp4_t a, const char *str[4], BN_CTX *ctx)
|
||||
fp4_set_hex(t, str);
|
||||
return fp4_equ(a, t);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp4_to_bin(const fp4_t a, unsigned char to[128])
|
||||
{
|
||||
@@ -863,6 +875,7 @@ static int fp4_inv(fp4_t r, const fp4_t a, const BIGNUM *p, BN_CTX *ctx)
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp4_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
const char *_a[] = {
|
||||
@@ -999,6 +1012,7 @@ static int fp4_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
int fp12_init(fp12_t a, BN_CTX *ctx)
|
||||
{
|
||||
@@ -1021,12 +1035,14 @@ void fp12_cleanup(fp12_t a)
|
||||
fp4_cleanup(a[2]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static void fp12_clear_cleanup(fp12_t a)
|
||||
{
|
||||
fp4_clear_cleanup(a[0]);
|
||||
fp4_clear_cleanup(a[1]);
|
||||
fp4_clear_cleanup(a[2]);
|
||||
}
|
||||
#endif
|
||||
|
||||
int fp12_print(const fp12_t a)
|
||||
{
|
||||
@@ -1036,6 +1052,7 @@ int fp12_print(const fp12_t a)
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_is_zero(const fp12_t a)
|
||||
{
|
||||
return fp4_is_zero(a[0])
|
||||
@@ -1056,6 +1073,7 @@ static void fp12_set_zero(fp12_t r)
|
||||
fp4_set_zero(r[1]);
|
||||
fp4_set_zero(r[2]);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp12_set_one(fp12_t r)
|
||||
{
|
||||
@@ -1071,12 +1089,14 @@ static int fp12_copy(fp12_t r, const fp12_t a)
|
||||
&& fp4_copy(r[2], a[2]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_set(fp12_t r, const fp4_t a0, const fp4_t a1, const fp4_t a2)
|
||||
{
|
||||
return fp4_copy(r[0], a0)
|
||||
&& fp4_copy(r[1], a1)
|
||||
&& fp4_copy(r[2], a2);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp12_set_hex(fp12_t r, const char *str[12])
|
||||
{
|
||||
@@ -1085,12 +1105,14 @@ static int fp12_set_hex(fp12_t r, const char *str[12])
|
||||
&& fp4_set_hex(r[2], str + 8);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_set_fp4(fp12_t r, const fp4_t a)
|
||||
{
|
||||
fp4_set_zero(r[1]);
|
||||
fp4_set_zero(r[2]);
|
||||
return fp4_copy(r[0], a);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp12_set_fp2(fp12_t r, const fp2_t a)
|
||||
{
|
||||
@@ -1106,6 +1128,7 @@ static int fp12_set_bn(fp12_t r, const BIGNUM *a)
|
||||
return fp4_set_bn(r[0], a);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_set_word(fp12_t r, unsigned long a)
|
||||
{
|
||||
fp4_set_zero(r[1]);
|
||||
@@ -1119,6 +1142,7 @@ static int fp12_set_u(fp12_t r)
|
||||
fp4_set_zero(r[2]);
|
||||
return fp4_set_u(r[0]);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp12_set_v(fp12_t r)
|
||||
{
|
||||
@@ -1127,12 +1151,14 @@ static int fp12_set_v(fp12_t r)
|
||||
return fp4_set_v(r[0]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_set_w(fp12_t r)
|
||||
{
|
||||
fp4_set_zero(r[0]);
|
||||
fp4_set_zero(r[2]);
|
||||
return fp4_set_one(r[1]);
|
||||
}
|
||||
#endif
|
||||
|
||||
static int fp12_set_w_sqr(fp12_t r)
|
||||
{
|
||||
@@ -1148,6 +1174,7 @@ static int fp12_equ(const fp12_t a, const fp12_t b)
|
||||
&& fp4_equ(a[2], b[2]);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_equ_hex(const fp12_t a, const char *str[12], BN_CTX *ctx)
|
||||
{
|
||||
fp12_t t;
|
||||
@@ -1155,6 +1182,7 @@ static int fp12_equ_hex(const fp12_t a, const char *str[12], BN_CTX *ctx)
|
||||
fp12_set_hex(t, str);
|
||||
return fp12_equ(a, t);
|
||||
}
|
||||
#endif
|
||||
|
||||
int fp12_to_bin(const fp12_t a, unsigned char to[384])
|
||||
{
|
||||
@@ -1165,14 +1193,13 @@ int fp12_to_bin(const fp12_t a, unsigned char to[384])
|
||||
|
||||
static int fp12_from_bin(fp4_t a, const unsigned char from[384])
|
||||
{
|
||||
return fp4_from_bin(a[2], from)
|
||||
&& fp4_from_bin(a[1], from + 128)
|
||||
&& fp4_from_bin(a[0], from + 256);
|
||||
return fp4_from_bin(&a[2], from)
|
||||
&& fp4_from_bin(&a[1], from + 128)
|
||||
&& fp4_from_bin(&a[0], from + 256);
|
||||
}
|
||||
|
||||
static int fp12_add(fp12_t r, const fp12_t a, const fp12_t b, const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
|
||||
return fp4_add(r[0], a[0], b[0], p, ctx)
|
||||
&& fp4_add(r[1], a[1], b[1], p, ctx)
|
||||
&& fp4_add(r[2], a[2], b[2], p, ctx);
|
||||
@@ -1189,7 +1216,7 @@ static int fp12_tri(fp12_t r, const fp12_t a, const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
fp12_t t;
|
||||
fp12_init(t, ctx);
|
||||
|
||||
|
||||
if (!fp12_dbl(t, a, p, ctx)
|
||||
|| !fp12_add(r, t, a, p, ctx)) {
|
||||
fp12_cleanup(t);
|
||||
@@ -1323,7 +1350,7 @@ static int fp12_inv(fp12_t r, const fp12_t a, const BIGNUM *p, BN_CTX *ctx)
|
||||
|| !fp4_mul(t, t, a[1], p, ctx)
|
||||
|| !fp4_add(k, k, t, p, ctx)
|
||||
|| !fp4_inv(k, k, p, ctx)
|
||||
|
||||
|
||||
/* r2 = a1^2 * k */
|
||||
|| !fp4_sqr(r[2], a[1], p, ctx)
|
||||
|| !fp4_mul(r[2], r[2], k, p, ctx)
|
||||
@@ -1348,12 +1375,12 @@ static int fp12_inv(fp12_t r, const fp12_t a, const BIGNUM *p, BN_CTX *ctx)
|
||||
return 1;
|
||||
|
||||
} else {
|
||||
|
||||
|
||||
fp4_t t0, t1, t2, t3;
|
||||
|
||||
if (!(fp4_init(t0, ctx))
|
||||
|| !(fp4_init(t1, ctx)) //FIXME
|
||||
|| !(fp4_init(t2, ctx))
|
||||
|| !(fp4_init(t2, ctx))
|
||||
|| !(fp4_init(t3, ctx))
|
||||
|
||||
/* t0 = a1^2 - a0 * a2 */
|
||||
@@ -1377,7 +1404,7 @@ static int fp12_inv(fp12_t r, const fp12_t a, const BIGNUM *p, BN_CTX *ctx)
|
||||
|| !fp4_sub(t3, t3, r[0], p, ctx)
|
||||
|| !fp4_inv(t3, t3, p, ctx)
|
||||
|| !fp4_mul(t3, a[2], t3, p, ctx)
|
||||
|
||||
|
||||
/* r0 = t2 * t3 */
|
||||
|| !fp4_mul(r[0], t2, t3, p, ctx)
|
||||
|
||||
@@ -1443,6 +1470,8 @@ int fp12_pow(fp12_t r, const fp12_t a, const BIGNUM *k, const BIGNUM *p, BN_CTX
|
||||
}
|
||||
|
||||
fp12_copy(r, t);
|
||||
|
||||
fp12_cleanup(t);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -1466,19 +1495,20 @@ static int fp12_fast_expo_p2(fp12_t r, const fp12_t a, const BIGNUM *p, BN_CTX *
|
||||
pw21 = SM9_get0_fast_final_exponent_p21();
|
||||
pw22 = SM9_get0_fast_final_exponent_p22();
|
||||
pw23 = SM9_get0_fast_final_exponent_p23();
|
||||
|
||||
|
||||
if(!fp2_copy(r[0][0], a[0][0])
|
||||
|| !fp2_neg (r[0][1], a[0][1], p, ctx)
|
||||
|| !fp2_mul_num(r[1][0], a[1][0], pw20, p, ctx)
|
||||
|| !fp2_mul_num(r[1][1], a[1][1], pw21, p, ctx)
|
||||
|| !fp2_mul_num(r[2][0], a[2][0], pw22, p, ctx)
|
||||
|| !fp2_mul_num(r[2][1], a[2][1], pw23, p, ctx)) {
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int fp12_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
const char *_a[] = {
|
||||
@@ -1762,6 +1792,7 @@ static int fp12_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
int point_init(point_t *P, BN_CTX *ctx)
|
||||
{
|
||||
@@ -1940,7 +1971,7 @@ int point_is_on_curve(point_t *P, const BIGNUM *p, BN_CTX *ctx)
|
||||
if (!r) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
|
||||
fp2_set_5u(b);
|
||||
|
||||
if (!point_get_affine_coordinates(P, x, y)
|
||||
@@ -1979,7 +2010,7 @@ int point_to_octets(const point_t *P, unsigned char to[129], BN_CTX *ctx)
|
||||
fp2_to_bin(y, to + 65);
|
||||
fp2_cleanup(x);
|
||||
fp2_cleanup(y);
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -2090,7 +2121,7 @@ int point_add(point_t *R, const point_t *P, const point_t *Q, const BIGNUM *p, B
|
||||
|
||||
if (!point_get_affine_coordinates(P, x1, y1)
|
||||
|| !point_get_affine_coordinates(Q, x2, y2)
|
||||
|| !fp2_add(t, y1, y2, p, ctx)) {
|
||||
|| !fp2_add(t, y1, y2, p, ctx)) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
@@ -2195,6 +2226,7 @@ int point_mul_generator(point_t *R, const BIGNUM *k, const BIGNUM *p, BN_CTX *ct
|
||||
return point_mul(R, k, &G, p, ctx);
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int point_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
const char *_G[] = {
|
||||
@@ -2263,7 +2295,7 @@ static int point_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
printf("point test %d: %s\n", __LINE__, ok ? "ok" : "error");
|
||||
|
||||
point_sub(&P, &P, &G, p, ctx);
|
||||
ok = point_equ_hex(&P, sub_3G_G, ctx);
|
||||
ok = point_equ_hex(&P, sub_3G_G, ctx);
|
||||
printf("point test %d: %s\n", __LINE__, ok ? "ok" : "error");
|
||||
|
||||
point_neg(&P, &G, p, ctx);
|
||||
@@ -2290,11 +2322,12 @@ static int point_test(const BIGNUM *p, BN_CTX *ctx)
|
||||
|
||||
ok = point_equ(&P, &G);
|
||||
printf("point test %d: %s\n", __LINE__, ok ? "ok" : "error");
|
||||
|
||||
|
||||
//fp12_cleanup(x);
|
||||
//fp12_cleanup(y);
|
||||
return 1;
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int eval_tangent(fp12_t r, const point_t *T, const BIGNUM *xP, const BIGNUM *yP,
|
||||
const BIGNUM *p, BN_CTX *ctx)
|
||||
@@ -2315,7 +2348,7 @@ static int eval_tangent(fp12_t r, const point_t *T, const BIGNUM *xP, const BIGN
|
||||
}
|
||||
|
||||
point_get_ext_affine_coordinates(T, xT, yT, p, ctx);
|
||||
|
||||
|
||||
ret = 0;
|
||||
if (!fp12_set_bn(x, xP)
|
||||
|| !fp12_set_bn(y, yP)
|
||||
@@ -2343,14 +2376,14 @@ end:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int eval_line(fp12_t r, const point_t *T, const point_t *Q,
|
||||
static int eval_line(fp12_t r, const point_t *T, const point_t *Q,
|
||||
const BIGNUM *xP, const BIGNUM *yP,
|
||||
const BIGNUM *p, BN_CTX *ctx)
|
||||
{
|
||||
int ret;
|
||||
fp12_t x, y, lambda, t;
|
||||
fp12_t xT, yT, xQ, yQ;
|
||||
|
||||
|
||||
ret = 1;
|
||||
ret &= fp12_init(x, ctx);
|
||||
ret &= fp12_init(y, ctx);
|
||||
@@ -2445,6 +2478,8 @@ static int final_expo(fp12_t r, const fp12_t a, const BIGNUM *k, const BIGNUM *p
|
||||
}
|
||||
}
|
||||
fp12_copy(r, t);
|
||||
|
||||
fp12_cleanup(t);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -2478,11 +2513,11 @@ static int fast_final_expo(fp12_t r, const fp12_t a, const BIGNUM *k, const BIGN
|
||||
if (!fp12_copy(t0, t)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
if(!fp12_fast_expo_p2(t, t, p, ctx)){
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
if (!fp12_mul(t, t0, t, p, ctx)) {
|
||||
return 0;
|
||||
}
|
||||
@@ -2503,6 +2538,9 @@ static int fast_final_expo(fp12_t r, const fp12_t a, const BIGNUM *k, const BIGN
|
||||
}
|
||||
}
|
||||
fp12_copy(r, t);
|
||||
|
||||
fp12_cleanup(t);
|
||||
fp12_cleanup(t0);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -2517,7 +2555,7 @@ static int rate(fp12_t f, const point_t *Q, const BIGNUM *xP, const BIGNUM *yP,
|
||||
memset(&T, 0, sizeof(T));
|
||||
memset(&Q1, 0, sizeof(Q1));
|
||||
memset(&Q2, 0, sizeof(Q2));
|
||||
|
||||
|
||||
point_init(&T, ctx);
|
||||
point_init(&Q1, ctx);
|
||||
point_init(&Q2, ctx);
|
||||
@@ -2582,7 +2620,7 @@ static int rate(fp12_t f, const point_t *Q, const BIGNUM *xP, const BIGNUM *yP,
|
||||
eval_line(g, &T, &Q2, xP, yP, p, ctx);
|
||||
fp12_mul(f, f, g, p, ctx);
|
||||
|
||||
/* T = T - Q2 */
|
||||
/* T = T - Q2 */
|
||||
point_add(&T, &T, &Q2, p, ctx);
|
||||
|
||||
#ifdef NOSM9_FAST
|
||||
@@ -2662,6 +2700,7 @@ int rate_pairing(fp12_t r, const point_t *Q, const EC_POINT *P, BN_CTX *ctx)
|
||||
return ret;
|
||||
}
|
||||
|
||||
#if SM9_TEST
|
||||
static int rate_test(void)
|
||||
{
|
||||
const char *Ppubs_str[] = {
|
||||
@@ -2699,7 +2738,7 @@ static int rate_test(void)
|
||||
point_set_affine_coordinates_hex(&Ppubs, Ppubs_str);
|
||||
|
||||
fp12_init(g, ctx);
|
||||
rate_pairing(g, &Ppubs, P1, ctx);
|
||||
rate_pairing(g, &Ppubs, P1, ctx);
|
||||
|
||||
ok = fp12_equ_hex(g, g_str, ctx);
|
||||
printf("rate %d: %s\n", __LINE__, ok ? "ok" : "error");
|
||||
@@ -2711,6 +2750,7 @@ static int rate_test(void)
|
||||
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* for SM9 sign, the (xP, yP) is the fixed generator of E(Fp)
|
||||
*/
|
||||
|
||||
@@ -1,4 +1,9 @@
|
||||
LIBS=../../libcrypto
|
||||
SOURCE[../../libcrypto]=\
|
||||
sms4_common.c sms4_setkey.c sms4_enc.c sms4_enc_nblks.c \
|
||||
sms4_common.c sms4_setkey.c sms4_enc.c sms4_enc_avx2.c sms4_ede.c \
|
||||
sms4_ecb.c sms4_cbc.c sms4_cfb.c sms4_ctr.c sms4_ofb.c sms4_wrap.c
|
||||
|
||||
|
||||
INCLUDE[sms4_setkey.o]=../modes
|
||||
INCLUDE[sms4_enc.o]=../modes
|
||||
INCLUDE[sms4_enc_avx2.o]=../modes
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
129
crypto/sms4/sms4_ede.c
Normal file
129
crypto/sms4/sms4_ede.c
Normal file
@@ -0,0 +1,129 @@
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2014 - 2019 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 <openssl/sms4.h>
|
||||
#include <openssl/modes.h>
|
||||
|
||||
|
||||
void sms4_ede_set_encrypt_key(sms4_ede_key_t *key,
|
||||
const unsigned char user_key[48])
|
||||
{
|
||||
sms4_set_encrypt_key(&key->k1, user_key);
|
||||
sms4_set_decrypt_key(&key->k2, user_key + 16);
|
||||
sms4_set_encrypt_key(&key->k3, user_key + 32);
|
||||
}
|
||||
|
||||
void sms4_ede_set_decrypt_key(sms4_ede_key_t *key,
|
||||
const unsigned char user_key[48])
|
||||
{
|
||||
sms4_set_decrypt_key(&key->k1, user_key + 32);
|
||||
sms4_set_encrypt_key(&key->k2, user_key + 16);
|
||||
sms4_set_decrypt_key(&key->k3, user_key);
|
||||
}
|
||||
|
||||
void sms4_ede_encrypt(const unsigned char in[16], unsigned char out[16],
|
||||
const sms4_ede_key_t *key)
|
||||
{
|
||||
sms4_encrypt(in, out, &key->k1);
|
||||
sms4_encrypt(out, out, &key->k2);
|
||||
sms4_encrypt(out, out, &key->k3);
|
||||
}
|
||||
|
||||
void sms4_ede_ecb_encrypt(const unsigned char *in, unsigned char *out,
|
||||
const sms4_ede_key_t *key, int enc)
|
||||
{
|
||||
sms4_ede_encrypt(in, out, key);
|
||||
}
|
||||
|
||||
void sms4_ede_cbc_encrypt(const unsigned char *in, unsigned char *out,
|
||||
size_t len, const sms4_ede_key_t *key, unsigned char *iv, int enc)
|
||||
{
|
||||
if (enc)
|
||||
CRYPTO_cbc128_encrypt(in, out, len, key, iv,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
else CRYPTO_cbc128_decrypt(in, out, len, key, iv,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
}
|
||||
|
||||
void sms4_ede_cfb128_encrypt(const unsigned char *in, unsigned char *out,
|
||||
size_t len, const sms4_ede_key_t *key, unsigned char *iv, int *num,
|
||||
int enc)
|
||||
{
|
||||
CRYPTO_cfb128_encrypt(in, out, len, key, iv, num, enc,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
}
|
||||
|
||||
void sms4_ede_ofb128_encrypt(const unsigned char *in, unsigned char *out,
|
||||
size_t len, const sms4_ede_key_t *key, unsigned char *iv, int *num)
|
||||
{
|
||||
CRYPTO_ofb128_encrypt(in, out, len, key, iv, num,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
}
|
||||
|
||||
void sms4_ede_ctr128_encrypt(const unsigned char *in, unsigned char *out,
|
||||
size_t len, const sms4_ede_key_t *key, unsigned char *iv,
|
||||
unsigned char ecount_buf[SMS4_BLOCK_SIZE], unsigned int *num)
|
||||
{
|
||||
CRYPTO_ctr128_encrypt(in, out, len, key, iv, ecount_buf, num,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
}
|
||||
|
||||
int sms4_ede_wrap_key(sms4_ede_key_t *key, const unsigned char *iv,
|
||||
unsigned char *out, const unsigned char *in, unsigned int inlen)
|
||||
{
|
||||
return CRYPTO_128_wrap(key, iv, out, in, inlen,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
}
|
||||
|
||||
int sms4_ede_unwrap_key(sms4_ede_key_t *key, const unsigned char *iv,
|
||||
unsigned char *out, const unsigned char *in, unsigned int inlen)
|
||||
{
|
||||
return CRYPTO_128_unwrap(key, iv, out, in, inlen,
|
||||
(block128_f)sms4_ede_encrypt);
|
||||
}
|
||||
@@ -47,39 +47,87 @@
|
||||
* ====================================================================
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <openssl/sms4.h>
|
||||
#include "internal/rotate.h"
|
||||
#include "modes_lcl.h"
|
||||
#include "sms4_lcl.h"
|
||||
|
||||
|
||||
#define L32(x) \
|
||||
((x) ^ \
|
||||
ROT32((x), 2) ^ \
|
||||
ROT32((x), 10) ^ \
|
||||
ROT32((x), 18) ^ \
|
||||
ROT32((x), 24))
|
||||
#define L32(x) \
|
||||
((x) ^ \
|
||||
ROL32((x), 2) ^ \
|
||||
ROL32((x), 10) ^ \
|
||||
ROL32((x), 18) ^ \
|
||||
ROL32((x), 24))
|
||||
|
||||
#define ROUND(x0, x1, x2, x3, x4, i) \
|
||||
x4 = x1 ^ x2 ^ x3 ^ *(rk + i); \
|
||||
x4 = S32(x4); \
|
||||
#define ROUND_SBOX(x0, x1, x2, x3, x4, i) \
|
||||
x4 = x1 ^ x2 ^ x3 ^ *(rk + i); \
|
||||
x4 = S32(x4); \
|
||||
x4 = x0 ^ L32(x4)
|
||||
|
||||
void sms4_encrypt(const unsigned char *in, unsigned char *out, const sms4_key_t *key)
|
||||
#define ROUND_TBOX(x0, x1, x2, x3, x4, i) \
|
||||
x4 = x1 ^ x2 ^ x3 ^ *(rk + i); \
|
||||
t0 = ROL32(SMS4_T[(uint8_t)x4], 8); \
|
||||
x4 >>= 8; \
|
||||
x0 ^= t0; \
|
||||
t0 = ROL32(SMS4_T[(uint8_t)x4], 16); \
|
||||
x4 >>= 8; \
|
||||
x0 ^= t0; \
|
||||
t0 = ROL32(SMS4_T[(uint8_t)x4], 24); \
|
||||
x4 >>= 8; \
|
||||
x0 ^= t0; \
|
||||
t1 = SMS4_T[x4]; \
|
||||
x4 = x0 ^ t1
|
||||
|
||||
#define ROUND_DBOX(x0, x1, x2, x3, x4, i) \
|
||||
x4 = x1 ^ x2 ^ x3 ^ *(rk + i); \
|
||||
x4 = x0 ^ SMS4_D[(uint16_t)(x4 >> 16)] ^ \
|
||||
ROL32(SMS4_D[(uint16_t)x4], 16)
|
||||
|
||||
#define ROUND ROUND_TBOX
|
||||
|
||||
|
||||
void sms4_encrypt(const unsigned char in[16], unsigned char out[16], const sms4_key_t *key)
|
||||
{
|
||||
const uint32_t *rk = key->rk;
|
||||
uint32_t x0, x1, x2, x3, x4;
|
||||
uint32_t t0, t1;
|
||||
|
||||
x0 = GET32(in );
|
||||
x1 = GET32(in + 4);
|
||||
x2 = GET32(in + 8);
|
||||
x3 = GET32(in + 12);
|
||||
|
||||
x0 = GETU32(in );
|
||||
x1 = GETU32(in + 4);
|
||||
x2 = GETU32(in + 8);
|
||||
x3 = GETU32(in + 12);
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
|
||||
PUT32(x0, out );
|
||||
PUT32(x4, out + 4);
|
||||
PUT32(x3, out + 8);
|
||||
PUT32(x2, out + 12);
|
||||
|
||||
x0 = x1 = x2 = x3 = x4 = 0;
|
||||
PUTU32(out , x0);
|
||||
PUTU32(out + 4, x4);
|
||||
PUTU32(out + 8, x3);
|
||||
PUTU32(out + 12, x2);
|
||||
}
|
||||
|
||||
/* caller make sure counter not overflow */
|
||||
void sms4_ctr32_encrypt_blocks(const unsigned char *in, unsigned char *out,
|
||||
size_t blocks, const sms4_key_t *key, const unsigned char iv[16])
|
||||
{
|
||||
const uint32_t *rk = key->rk;
|
||||
unsigned int c0 = GETU32(iv );
|
||||
unsigned int c1 = GETU32(iv + 4);
|
||||
unsigned int c2 = GETU32(iv + 8);
|
||||
unsigned int c3 = GETU32(iv + 12);
|
||||
uint32_t x0, x1, x2, x3, x4;
|
||||
uint32_t t0, t1;
|
||||
|
||||
while (blocks--) {
|
||||
x0 = c0;
|
||||
x1 = c1;
|
||||
x2 = c2;
|
||||
x3 = c3;
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
PUTU32(out , GETU32(in ) ^ x0);
|
||||
PUTU32(out + 4, GETU32(in + 4) ^ x4);
|
||||
PUTU32(out + 8, GETU32(in + 8) ^ x3);
|
||||
PUTU32(out + 12, GETU32(in + 12) ^ x2);
|
||||
in += 16;
|
||||
out += 16;
|
||||
c3++;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2014 - 2016 The GmSSL Project. All rights reserved.
|
||||
* Copyright (c) 2014 - 2019 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
|
||||
@@ -47,32 +47,15 @@
|
||||
* ====================================================================
|
||||
*/
|
||||
|
||||
|
||||
#include <immintrin.h>
|
||||
#include <openssl/sms4.h>
|
||||
#include "internal/rotate.h"
|
||||
#include "modes_lcl.h"
|
||||
#include "sms4_lcl.h"
|
||||
|
||||
static __m256i mask_ffff;
|
||||
static __m256i vindex_0s;
|
||||
static __m256i vindex_4i;
|
||||
static __m256i vindex_swap;
|
||||
static __m256i vindex_read;
|
||||
#ifdef SMS4_AVX2
|
||||
# include <immintrin.h>
|
||||
|
||||
|
||||
void sms4_avx2_encrypt_init(sms4_key_t *key)
|
||||
{
|
||||
mask_ffff = _mm256_set1_epi32(0xffff);
|
||||
vindex_0s = _mm256_set1_epi32(0);
|
||||
vindex_4i = _mm256_setr_epi32(0,4,8,12,16,20,24,28);
|
||||
vindex_read = _mm256_setr_epi32(0,8,16,24,1,9,17,25);
|
||||
vindex_swap = _mm256_setr_epi8(
|
||||
3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12,
|
||||
3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12
|
||||
);
|
||||
sms4_init_sbox32();
|
||||
}
|
||||
|
||||
#define GET_BLKS(x0, x1, x2, x3, in) \
|
||||
# define GET_BLKS(x0, x1, x2, x3, in) \
|
||||
t0 = _mm256_i32gather_epi32((int *)(in+4*0), vindex_4i, 4); \
|
||||
t1 = _mm256_i32gather_epi32((int *)(in+4*1), vindex_4i, 4); \
|
||||
t2 = _mm256_i32gather_epi32((int *)(in+4*2), vindex_4i, 4); \
|
||||
@@ -82,7 +65,7 @@ void sms4_avx2_encrypt_init(sms4_key_t *key)
|
||||
x2 = _mm256_shuffle_epi8(t2, vindex_swap); \
|
||||
x3 = _mm256_shuffle_epi8(t3, vindex_swap)
|
||||
|
||||
#define PUT_BLKS(out, x0, x1, x2, x3) \
|
||||
# define PUT_BLKS(out, x0, x1, x2, x3) \
|
||||
t0 = _mm256_shuffle_epi8(x0, vindex_swap); \
|
||||
t1 = _mm256_shuffle_epi8(x1, vindex_swap); \
|
||||
t2 = _mm256_shuffle_epi8(x2, vindex_swap); \
|
||||
@@ -91,59 +74,135 @@ void sms4_avx2_encrypt_init(sms4_key_t *key)
|
||||
_mm256_storeu_si256((__m256i *)(out+32*1), t1); \
|
||||
_mm256_storeu_si256((__m256i *)(out+32*2), t2); \
|
||||
_mm256_storeu_si256((__m256i *)(out+32*3), t3); \
|
||||
x0 = _mm256_i32gather_epi32((int *)(in+32*0), vindex_read, 4); \
|
||||
x1 = _mm256_i32gather_epi32((int *)(in+32*1), vindex_read, 4); \
|
||||
x2 = _mm256_i32gather_epi32((int *)(in+32*2), vindex_read, 4); \
|
||||
x3 = _mm256_i32gather_epi32((int *)(in+32*3), vindex_read, 4); \
|
||||
_mm256_storeu_si256((__m256i *)(out+2*0), x0); \
|
||||
_mm256_storeu_si256((__m256i *)(out+2*1), x1); \
|
||||
_mm256_storeu_si256((__m256i *)(out+2*2), x2); \
|
||||
_mm256_storeu_si256((__m256i *)(out+2*3), x3)
|
||||
x0 = _mm256_i32gather_epi32((int *)(out+8*0), vindex_read, 4); \
|
||||
x1 = _mm256_i32gather_epi32((int *)(out+8*1), vindex_read, 4); \
|
||||
x2 = _mm256_i32gather_epi32((int *)(out+8*2), vindex_read, 4); \
|
||||
x3 = _mm256_i32gather_epi32((int *)(out+8*3), vindex_read, 4); \
|
||||
_mm256_storeu_si256((__m256i *)(out+32*0), x0); \
|
||||
_mm256_storeu_si256((__m256i *)(out+32*1), x1); \
|
||||
_mm256_storeu_si256((__m256i *)(out+32*2), x2); \
|
||||
_mm256_storeu_si256((__m256i *)(out+32*3), x3)
|
||||
|
||||
#define S(x0, t0, t1, t2) \
|
||||
t0 = _mm256_and_si256(x0, mask_ffff); \
|
||||
t1 = _mm256_i32gather_epi32(SBOX32L, t0, 4); \
|
||||
t0 = _mm256_srli_epi32(x0, 16); \
|
||||
t2 = _mm256_i32gather_epi32(SBOX32H, t0, 4); \
|
||||
x0 = _mm256_xor_si256(t1, t2)
|
||||
# define _mm256_rotl_epi32(a, i) _mm256_xor_si256( \
|
||||
_mm256_slli_epi32(a, i), _mm256_srli_epi32(a, 32 - i))
|
||||
|
||||
#define ROT(r0, x0, i, t0, t1) \
|
||||
t0 = _mm256_slli_epi32(x0, i); \
|
||||
t1 = _mm256_srli_epi32(x0,32-i); \
|
||||
r0 = _mm256_xor_si256(t0, t1)
|
||||
# define INDEX_MASK_TBOX 0xff
|
||||
|
||||
#define L(x0, t0, t1, t2, t3, t4) \
|
||||
ROT(t0, x0, 2, t2, t3); \
|
||||
ROT(t1, x0, 10, t2, t3); \
|
||||
t4 = _mm256_xor_si256(t0, t1); \
|
||||
ROT(t0, x0, 18, t2, t3); \
|
||||
ROT(t1, x0, 24, t2, t3); \
|
||||
t3 = _mm256_xor_si256(t0, t1); \
|
||||
t2 = _mm256_xor_si256(x0, t3); \
|
||||
x0 = _mm256_xor_si256(t2, t4)
|
||||
# define ROUND_TBOX(x0, x1, x2, x3, x4, i) \
|
||||
t0 = _mm256_set1_epi32(*(rk + i)); \
|
||||
t1 = _mm256_xor_si256(x1, x2); \
|
||||
t2 = _mm256_xor_si256(x3, t0); \
|
||||
x4 = _mm256_xor_si256(t1, t2); \
|
||||
t0 = _mm256_and_si256(x4, vindex_mask); \
|
||||
t0 = _mm256_i32gather_epi32((int *)SMS4_T, t0, 4); \
|
||||
t0 = _mm256_rotl_epi32(t0, 8); \
|
||||
x4 = _mm256_srli_epi32(x4, 8); \
|
||||
x0 = _mm256_xor_si256(x0, t0); \
|
||||
t0 = _mm256_and_si256(x4, vindex_mask); \
|
||||
t0 = _mm256_i32gather_epi32((int *)SMS4_T, t0, 4); \
|
||||
t0 = _mm256_rotl_epi32(t0, 16); \
|
||||
x4 = _mm256_srli_epi32(x4, 8); \
|
||||
x0 = _mm256_xor_si256(x0, t0); \
|
||||
t0 = _mm256_and_si256(x4, vindex_mask); \
|
||||
t0 = _mm256_i32gather_epi32((int *)SMS4_T, t0, 4); \
|
||||
t0 = _mm256_rotl_epi32(t0, 24); \
|
||||
x4 = _mm256_srli_epi32(x4, 8); \
|
||||
x0 = _mm256_xor_si256(x0, t0); \
|
||||
t1 = _mm256_i32gather_epi32((int *)SMS4_T, x4, 4); \
|
||||
x4 = _mm256_xor_si256(x0, t1)
|
||||
|
||||
#define ROUND(x0, x1, x2, x3, x4, i) \
|
||||
t0 = _mm256_i32gather_epi32(rk+i, vindex_0s, 4); \
|
||||
t1 = _mm256_xor_si256(x1, x2); \
|
||||
t2 = _mm256_xor_si256(x3, t0); \
|
||||
t0 = _mm256_xor_si256(t1, t2); \
|
||||
S(t0, x4, t1, t2); \
|
||||
L(t0, x4, t1, t2, t3, t4); \
|
||||
x4 = _mm256_xor_si256(x0, t0);
|
||||
# define INDEX_MASK_DBOX 0xffff
|
||||
|
||||
# define ROUND_DBOX(x0, x1, x2, x3, x4, i) \
|
||||
t0 = _mm256_set1_epi32(*(rk + i)); \
|
||||
t1 = _mm256_xor_si256(x1, x2); \
|
||||
t2 = _mm256_xor_si256(x3, t0); \
|
||||
x4 = _mm256_xor_si256(t1, t2); \
|
||||
t0 = _mm256_srli_epi32(x4, 16); \
|
||||
t1 = _mm256_i32gather_epi32((int *)SMS4_D, t0, 4); \
|
||||
t2 = _mm256_and_si256(x4, vindex_mask); \
|
||||
t3 = _mm256_i32gather_epi32((int *)SMS4_D, t2, 4); \
|
||||
t0 = _mm256_rotl_epi32(t3, 16); \
|
||||
x4 = _mm256_xor_si256(x0, t1); \
|
||||
x4 = _mm256_xor_si256(x4, t0)
|
||||
|
||||
# define ROUND ROUND_TBOX
|
||||
# define INDEX_MASK INDEX_MASK_TBOX
|
||||
|
||||
|
||||
void sms4_avx2_encrypt_8blocks(const unsigned char *in, unsigned char *out, const sms4_key_t *key)
|
||||
void sms4_avx2_ecb_encrypt_blocks(const unsigned char *in, unsigned char *out,
|
||||
size_t blocks, const sms4_key_t *key)
|
||||
{
|
||||
const int *rk = (int *)key->rk;
|
||||
__m256i x0, x1, x2, x3, x4;
|
||||
__m256i t0, t1, t2, t3, t4;
|
||||
GET_BLKS(x0, x1, x2, x3, in);
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
PUT_BLKS(out, x0, x4, x3, x2);
|
||||
__m256i t0, t1, t2, t3;
|
||||
__m256i vindex_4i = _mm256_setr_epi32(0,4,8,12,16,20,24,28);
|
||||
__m256i vindex_mask = _mm256_set1_epi32(INDEX_MASK);
|
||||
__m256i vindex_read = _mm256_setr_epi32(0,8,16,24,1,9,17,25);
|
||||
__m256i vindex_swap = _mm256_setr_epi8(
|
||||
3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12,
|
||||
3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12
|
||||
);
|
||||
|
||||
while (blocks >= 8) {
|
||||
GET_BLKS(x0, x1, x2, x3, in);
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
PUT_BLKS(out, x0, x4, x3, x2);
|
||||
in += 128;
|
||||
out += 128;
|
||||
blocks -= 8;
|
||||
}
|
||||
|
||||
while (blocks--) {
|
||||
sms4_encrypt(in, out, key);
|
||||
in += 16;
|
||||
out += 16;
|
||||
}
|
||||
}
|
||||
|
||||
void sms4_avx2_encrypt_16blocks(const unsigned char *in, unsigned char *out, const sms4_key_t *key)
|
||||
void sms4_avx2_ctr32_encrypt_blocks(const unsigned char *in, unsigned char *out,
|
||||
size_t blocks, const sms4_key_t *key, const unsigned char iv[16])
|
||||
{
|
||||
sms4_encrypt_8blocks(key, in, out);
|
||||
sms4_encrypt_8blocks(key, in + 16*8, out + 16*8);
|
||||
const int *rk = (int *)key->rk;
|
||||
__m256i x0, x1, x2, x3, x4;
|
||||
__m256i t0, t1, t2, t3;
|
||||
__m256i vindex_4i = _mm256_setr_epi32(0,4,8,12,16,20,24,28);
|
||||
__m256i vindex_mask = _mm256_set1_epi32(INDEX_MASK);
|
||||
__m256i vindex_read = _mm256_setr_epi32(0,8,16,24,1,9,17,25);
|
||||
__m256i vindex_swap = _mm256_setr_epi8(
|
||||
3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12,
|
||||
3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12
|
||||
);
|
||||
__m256i incr = _mm256_setr_epi32(0, 1, 2, 3, 4, 5, 6, 7);
|
||||
int c0 = (int)GETU32(iv );
|
||||
int c1 = (int)GETU32(iv + 4);
|
||||
int c2 = (int)GETU32(iv + 8);
|
||||
int c3 = (int)GETU32(iv + 12);
|
||||
|
||||
while (blocks >= 8) {
|
||||
x0 = _mm256_set1_epi32(c0);
|
||||
x1 = _mm256_set1_epi32(c1);
|
||||
x2 = _mm256_set1_epi32(c2);
|
||||
x3 = _mm256_set1_epi32(c3);
|
||||
x3 = _mm256_add_epi32(x3, incr);
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
GET_BLKS(t0, t1, t2, t3, in);
|
||||
x0 = _mm256_xor_si256(x0, t0);
|
||||
x4 = _mm256_xor_si256(x4, t1);
|
||||
x3 = _mm256_xor_si256(x3, t2);
|
||||
x2 = _mm256_xor_si256(x2, t3);
|
||||
PUT_BLKS(out, x0, x4, x3, x2);
|
||||
c3 += 8;
|
||||
in += 128;
|
||||
out += 128;
|
||||
blocks -= 8;
|
||||
}
|
||||
|
||||
if (blocks) {
|
||||
unsigned char ctr[16];
|
||||
memcpy(ctr, iv, 12);
|
||||
PUTU32(ctr + 12, c3);
|
||||
sms4_ctr32_encrypt_blocks(in, out, blocks, key, ctr);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -1,73 +0,0 @@
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2014 - 2017 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 <openssl/sms4.h>
|
||||
|
||||
void sms4_encrypt_init(sms4_key_t *key)
|
||||
{
|
||||
}
|
||||
|
||||
void sms4_encrypt_8blocks(const unsigned char *in, unsigned char *out, const sms4_key_t *key)
|
||||
{
|
||||
sms4_encrypt(in, out, key);
|
||||
sms4_encrypt(in + 16, out + 16, key);
|
||||
sms4_encrypt(in + 16 * 2, out + 16 * 2, key);
|
||||
sms4_encrypt(in + 16 * 3, out + 16 * 3, key);
|
||||
sms4_encrypt(in + 16 * 4, out + 16 * 4, key);
|
||||
sms4_encrypt(in + 16 * 5, out + 16 * 5, key);
|
||||
sms4_encrypt(in + 16 * 6, out + 16 * 6, key);
|
||||
sms4_encrypt(in + 16 * 7, out + 16 * 7, key);
|
||||
}
|
||||
|
||||
void sms4_encrypt_16blocks(const unsigned char *in, unsigned char *out, const sms4_key_t *key)
|
||||
{
|
||||
sms4_encrypt_8blocks(in, out, key);
|
||||
sms4_encrypt_8blocks(in + 16 * 8, out + 16 * 8, key);
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2014 - 2017 The GmSSL Project. All rights reserved.
|
||||
* Copyright (c) 2014 - 2019 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
|
||||
@@ -50,37 +50,18 @@
|
||||
#ifndef HEADER_SMS4_LCL_H
|
||||
#define HEADER_SMS4_LCL_H
|
||||
|
||||
#include <openssl/sms4.h>
|
||||
#include <openssl/e_os2.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
extern const uint8_t SMS4_S[256];
|
||||
extern const uint32_t SMS4_T[256];
|
||||
extern const uint32_t SMS4_D[65536];
|
||||
|
||||
extern uint8_t SBOX[256];
|
||||
extern uint32_t SBOX32L[256 * 256];
|
||||
extern uint32_t SBOX32H[256 * 256];
|
||||
|
||||
|
||||
#define GET32(pc) ( \
|
||||
((uint32_t)(pc)[0] << 24) ^ \
|
||||
((uint32_t)(pc)[1] << 16) ^ \
|
||||
((uint32_t)(pc)[2] << 8) ^ \
|
||||
((uint32_t)(pc)[3]))
|
||||
|
||||
#define PUT32(st, ct) \
|
||||
(ct)[0] = (uint8_t)((st) >> 24); \
|
||||
(ct)[1] = (uint8_t)((st) >> 16); \
|
||||
(ct)[2] = (uint8_t)((st) >> 8); \
|
||||
(ct)[3] = (uint8_t)(st)
|
||||
|
||||
#define ROT32(x,i) \
|
||||
(((x) << i) | ((x) >> (32-i)))
|
||||
|
||||
#define S32(A) \
|
||||
((SBOX[((A) >> 24) ] << 24) ^ \
|
||||
(SBOX[((A) >> 16) & 0xff] << 16) ^ \
|
||||
(SBOX[((A) >> 8) & 0xff] << 8) ^ \
|
||||
(SBOX[((A)) & 0xff]))
|
||||
#define S32(A) \
|
||||
((SMS4_S[((A) >> 24) ] << 24) ^ \
|
||||
(SMS4_S[((A) >> 16) & 0xff] << 16) ^ \
|
||||
(SMS4_S[((A) >> 8) & 0xff] << 8) ^ \
|
||||
(SMS4_S[((A)) & 0xff]))
|
||||
|
||||
#define ROUNDS(x0, x1, x2, x3, x4) \
|
||||
ROUND(x0, x1, x2, x3, x4, 0); \
|
||||
@@ -116,9 +97,14 @@ extern uint32_t SBOX32H[256 * 256];
|
||||
ROUND(x0, x1, x2, x3, x4, 30); \
|
||||
ROUND(x1, x2, x3, x4, x0, 31)
|
||||
|
||||
void sms4_init_sbox32(void);
|
||||
void sms4_ctr32_encrypt_blocks(const unsigned char *in, unsigned char *out,
|
||||
size_t blocks, const sms4_key_t *key, const unsigned char iv[16]);
|
||||
|
||||
# ifdef SMS4_AVX2
|
||||
void sms4_avx2_ecb_encrypt_blocks(const unsigned char *in, unsigned char *out,
|
||||
size_t blocks, const sms4_key_t *key);
|
||||
void sms4_avx2_ctr32_encrypt_blocks(const unsigned char *in, unsigned char *out,
|
||||
size_t blocks, const sms4_key_t *key, const unsigned char iv[16]);
|
||||
# endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/* ====================================================================
|
||||
* Copyright (c) 2014 - 2017 The GmSSL Project. All rights reserved.
|
||||
* Copyright (c) 2014 - 2019 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
|
||||
@@ -48,6 +48,8 @@
|
||||
*/
|
||||
|
||||
#include <openssl/sms4.h>
|
||||
#include "internal/rotate.h"
|
||||
#include "modes_lcl.h"
|
||||
#include "sms4_lcl.h"
|
||||
|
||||
static uint32_t FK[4] = {
|
||||
@@ -67,8 +69,8 @@ static uint32_t CK[32] = {
|
||||
|
||||
#define L32_(x) \
|
||||
((x) ^ \
|
||||
ROT32((x), 13) ^ \
|
||||
ROT32((x), 23))
|
||||
ROL32((x), 13) ^ \
|
||||
ROL32((x), 23))
|
||||
|
||||
#define ENC_ROUND(x0, x1, x2, x3, x4, i) \
|
||||
x4 = x1 ^ x2 ^ x3 ^ *(CK + i); \
|
||||
@@ -82,35 +84,36 @@ static uint32_t CK[32] = {
|
||||
x4 = x0 ^ L32_(x4); \
|
||||
*(rk + 31 - i) = x4
|
||||
|
||||
void sms4_set_encrypt_key(sms4_key_t *key, const unsigned char *user_key)
|
||||
void sms4_set_encrypt_key(sms4_key_t *key, const unsigned char user_key[16])
|
||||
{
|
||||
uint32_t *rk = key->rk;
|
||||
uint32_t x0, x1, x2, x3, x4;
|
||||
|
||||
x0 = GET32(user_key ) ^ FK[0];
|
||||
x1 = GET32(user_key + 4) ^ FK[1];
|
||||
x2 = GET32(user_key + 8) ^ FK[2];
|
||||
x3 = GET32(user_key + 12) ^ FK[3];
|
||||
x0 = GETU32(user_key ) ^ FK[0];
|
||||
x1 = GETU32(user_key + 4) ^ FK[1];
|
||||
x2 = GETU32(user_key + 8) ^ FK[2];
|
||||
x3 = GETU32(user_key + 12) ^ FK[3];
|
||||
|
||||
#define ROUND ENC_ROUND
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
#undef ROUND
|
||||
|
||||
x0 = x1 = x2 = x3 = x4 = 0;
|
||||
}
|
||||
|
||||
void sms4_set_decrypt_key(sms4_key_t *key, const unsigned char *user_key)
|
||||
void sms4_set_decrypt_key(sms4_key_t *key, const unsigned char user_key[16])
|
||||
{
|
||||
uint32_t *rk = key->rk;
|
||||
uint32_t x0, x1, x2, x3, x4;
|
||||
|
||||
x0 = GET32(user_key ) ^ FK[0];
|
||||
x1 = GET32(user_key + 4) ^ FK[1];
|
||||
x2 = GET32(user_key + 8) ^ FK[2];
|
||||
x3 = GET32(user_key + 12) ^ FK[3];
|
||||
x0 = GETU32(user_key ) ^ FK[0];
|
||||
x1 = GETU32(user_key + 4) ^ FK[1];
|
||||
x2 = GETU32(user_key + 8) ^ FK[2];
|
||||
x3 = GETU32(user_key + 12) ^ FK[3];
|
||||
|
||||
#undef ROUND
|
||||
#define ROUND DEC_ROUND
|
||||
ROUNDS(x0, x1, x2, x3, x4);
|
||||
#undef ROUND
|
||||
|
||||
x0 = x1 = x2 = x3 = x4 = 0;
|
||||
}
|
||||
|
||||
47
crypto/zuc/zuc256.c
Normal file
47
crypto/zuc/zuc256.c
Normal file
@@ -0,0 +1,47 @@
|
||||
|
||||
ZUC_UINT7 D[16] = {
|
||||
0x22,
|
||||
0x2F,
|
||||
0x24,
|
||||
0x2A,
|
||||
0x6D,
|
||||
0x40,
|
||||
0x40,
|
||||
0x40,
|
||||
0x40,
|
||||
0x40,
|
||||
0x40,
|
||||
0x40,
|
||||
0x52,
|
||||
0x10,
|
||||
0x30
|
||||
};
|
||||
|
||||
void ZUC_set_key(ZUC_KEY *key, const unsigned char *user_key, const unsigned char *iv)
|
||||
{
|
||||
LFSR[0] = MAKEU31(K[0], D[0], K[21], K[16]);
|
||||
LFSR[1] = MAKEU31(K[1], D[1], K[22], K[17]);
|
||||
LFSR[2] = MAKEU31(K[2], D[2], K[23], K[18]);
|
||||
LFSR[3] = MAKEU31(K[3], D[3], K[24], K[19]);
|
||||
LFSR[4] = MAKEU31(K[4], D[4], K[25], K[20]);
|
||||
LFSR[5] = MAKEU31(IV[0], (D[5] | IV[17]), K[5], K[26]);
|
||||
LFSR[6] = MAKEU31(IV[1], (D[6] | IV[18]), K[6], K[27]);
|
||||
LFSR[7] = MAKEU31(IV[10], (D[7] | IV[19]), K[7], IV[2]);
|
||||
LFSR[8] = MAKEU31(K[8], (D[8] | IV[20]), IV[13], IV[11]);
|
||||
LFSR[9] = MAKEU31(K[9], (D[9] | IV[21]), IV[12], IV[4]);
|
||||
LFSR[10] = MAKEU31(IV[5], (D[10] | IV[22]), K[10], K[28]);
|
||||
LFSR[11] = MAKEU31(K[11], (D[11] | IV[23]), IV[6], IV[13]);
|
||||
LFSR[12] = MAKEU31(K[12], (D[12] | IV[24]), IV[7], IV[14]);
|
||||
LFSR[13] = MAKEU31(K[13], D[13], IV[15], IV[8]);
|
||||
LFSR[14] = MAKEU31(K[14], (D[14] | (K[31] >> 4)), IV[16], IV[9]);
|
||||
LFSR[15] = MAKEU31(K[15], (D[15] | (K[31] & 0xF0)), K[30], K[29]);
|
||||
|
||||
R1 = R2 = 0;
|
||||
|
||||
for (i = 0; i < 32; i++) {
|
||||
BitReconstruction3(X0, X1, X2);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -192,6 +192,7 @@ void ZUC_set_key(ZUC_KEY *key, const unsigned char *user_key, const unsigned cha
|
||||
for (i = 0; i < 16; i++) {
|
||||
LFSR[i] = MAKEU31(user_key[i], KD[i], iv[i]);
|
||||
}
|
||||
|
||||
R1 = 0;
|
||||
R2 = 0;
|
||||
|
||||
@@ -246,3 +247,135 @@ void ZUC_generate_keystream(ZUC_KEY *key, size_t nwords, uint32_t *keystream)
|
||||
key->R1 = R1;
|
||||
key->R2 = R2;
|
||||
}
|
||||
|
||||
#if 0
|
||||
typedef unsigned char ZUC_UINT7;
|
||||
|
||||
static const ZUC_UINT7 D[16] = {
|
||||
0x22,0x2F,0x24,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30
|
||||
};
|
||||
|
||||
#define ZUC256_MAKEU31(a,b,c,d) \
|
||||
(((uint32_t)(a) << 23) | \
|
||||
((uint32_t)(b) << 16) | \
|
||||
((uint32_t)(c) << 8) | \
|
||||
(uint32_t)(d))
|
||||
|
||||
void ZUC256_set_key(ZUC_KEY *key, const unsigned char *K, const unsigned char *IV)
|
||||
{
|
||||
ZUC_UINT31 *LFSR = key->LFSR;
|
||||
uint32_t R1, R2;
|
||||
uint32_t X0, X1, X2;
|
||||
uint32_t W, W1, W2, U, V;
|
||||
int i;
|
||||
|
||||
LFSR[0] = ZUC256_MAKEU31(K[0], D[0], K[21], K[16]);
|
||||
LFSR[1] = ZUC256_MAKEU31(K[1], D[1], K[22], K[17]);
|
||||
LFSR[2] = ZUC256_MAKEU31(K[2], D[2], K[23], K[18]);
|
||||
LFSR[3] = ZUC256_MAKEU31(K[3], D[3], K[24], K[19]);
|
||||
LFSR[4] = ZUC256_MAKEU31(K[4], D[4], K[25], K[20]);
|
||||
LFSR[5] = ZUC256_MAKEU31(IV[0], (D[5] | IV[17]), K[5], K[26]);
|
||||
LFSR[6] = ZUC256_MAKEU31(IV[1], (D[6] | IV[18]), K[6], K[27]);
|
||||
LFSR[7] = ZUC256_MAKEU31(IV[10], (D[7] | IV[19]), K[7], IV[2]);
|
||||
LFSR[8] = ZUC256_MAKEU31(K[8], (D[8] | IV[20]), IV[13], IV[11]);
|
||||
LFSR[9] = ZUC256_MAKEU31(K[9], (D[9] | IV[21]), IV[12], IV[4]);
|
||||
LFSR[10] = ZUC256_MAKEU31(IV[5], (D[10] | IV[22]), K[10], K[28]);
|
||||
LFSR[11] = ZUC256_MAKEU31(K[11], (D[11] | IV[23]), IV[6], IV[13]);
|
||||
LFSR[12] = ZUC256_MAKEU31(K[12], (D[12] | IV[24]), IV[7], IV[14]);
|
||||
LFSR[13] = ZUC256_MAKEU31(K[13], D[13], IV[15], IV[8]);
|
||||
LFSR[14] = ZUC256_MAKEU31(K[14], (D[14] | (K[31] >> 4)), IV[16], IV[9]);
|
||||
LFSR[15] = ZUC256_MAKEU31(K[15], (D[15] | (K[31] & 0x0F)), K[30], K[29]);
|
||||
|
||||
R1 = 0;
|
||||
R2 = 0;
|
||||
|
||||
for (i = 0; i < 32; i++) {
|
||||
BitReconstruction3(X0, X1, X2);
|
||||
W = F(X0, X1, X2);
|
||||
LFSRWithInitialisationMode(W >> 1);
|
||||
}
|
||||
|
||||
BitReconstruction2(X1, X2);
|
||||
F_(X1, X2);
|
||||
LFSRWithWorkMode();
|
||||
|
||||
key->R1 = R1;
|
||||
key->R2 = R2;
|
||||
}
|
||||
|
||||
|
||||
static const ZUC_UINT7 ZUC256_MAC32_D[] = {
|
||||
0x22,0x2F,0x25,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30
|
||||
};
|
||||
|
||||
static const ZUC_UINT7 ZUC256_MAC64_D[] = {
|
||||
0x23,0x2F,0x24,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30,
|
||||
};
|
||||
|
||||
static const ZUC_UINT7 ZUC256_MAC128_D[] = {
|
||||
0x23,0x2F,0x25,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30,
|
||||
};
|
||||
|
||||
int ZUC256_set_mac_key(ZUC_KEY *key, const unsigned char *key,
|
||||
const unsigned char *IV, int macbits)
|
||||
{
|
||||
const ZUC_UINT7 *K;
|
||||
ZUC_UINT31 *LFSR = key->LFSR;
|
||||
uint32_t R1, R2;
|
||||
uint32_t X0, X1, X2;
|
||||
uint32_t W, W1, W2, U, V;
|
||||
int i;
|
||||
|
||||
switch (macbits) {
|
||||
case 32:
|
||||
D = ZUC256_MAC32_D;
|
||||
break;
|
||||
case 64:
|
||||
D = ZUC256_MAC64_D;
|
||||
break;
|
||||
case 128:
|
||||
D = ZUC256_MAC128_D;
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
||||
LFSR[0] = MAKEU31(K[0], D[0], K[21], K[16]);
|
||||
LFSR[1] = MAKEU31(K[1], D[1], K[22], K[17]);
|
||||
LFSR[2] = MAKEU31(K[2], D[2], K[23], K[18]);
|
||||
LFSR[3] = MAKEU31(K[3], D[3], K[24], K[19]);
|
||||
LFSR[4] = MAKEU31(K[4], D[4], K[25], K[20]);
|
||||
LFSR[5] = MAKEU31(IV[0], (D[5] | IV[17]), K[5], K[26]);
|
||||
LFSR[6] = MAKEU31(IV[1], (D[6] | IV[18]), K[6], K[27]);
|
||||
LFSR[7] = MAKEU31(IV[10], (D[7] | IV[19]), K[7], IV[2]);
|
||||
LFSR[8] = MAKEU31(K[8], (D[8] | IV[20]), IV[13], IV[11]);
|
||||
LFSR[9] = MAKEU31(K[9], (D[9] | IV[21]), IV[12], IV[4]);
|
||||
LFSR[10] = MAKEU31(IV[5], (D[10] | IV[22]), K[10], K[28]);
|
||||
LFSR[11] = MAKEU31(K[11], (D[11] | IV[23]), IV[6], IV[13]);
|
||||
LFSR[12] = MAKEU31(K[12], (D[12] | IV[24]), IV[7], IV[14]);
|
||||
LFSR[13] = MAKEU31(K[13], D[13], IV[15], IV[8]);
|
||||
LFSR[14] = MAKEU31(K[14], (D[14] | (K[31] >> 4)), IV[16], IV[9]);
|
||||
LFSR[15] = MAKEU31(K[15], (D[15] | (K[31] & 0xF0)), K[30], K[29]);
|
||||
|
||||
R1 = 0;
|
||||
R2 = 0;
|
||||
|
||||
for (i = 0; i < 32; i++) {
|
||||
BitReconstruction3(X0, X1, X2);
|
||||
W = F(X0, X1, X2);
|
||||
LFSRWithInitialisationMode(W >> 1);
|
||||
}
|
||||
|
||||
BitReconstruction2(X1, X2);
|
||||
F_(X1, X2);
|
||||
LFSRWithWorkMode();
|
||||
|
||||
key->R1 = R1;
|
||||
key->R2 = R2;
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
121
crypto/zuc/zuc_mac.c
Normal file
121
crypto/zuc/zuc_mac.c
Normal file
@@ -0,0 +1,121 @@
|
||||
|
||||
|
||||
#include <openssl/zuc.h>
|
||||
|
||||
static const ZUC_UINT7 ZUC256_MAC32_D[] = {
|
||||
0x22,0x2F,0x25,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30
|
||||
};
|
||||
|
||||
static const ZUC_UINT7 ZUC256_MAC64_D[] = {
|
||||
0x23,0x2F,0x24,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30,
|
||||
};
|
||||
|
||||
static const ZUC_UINT7 ZUC256_MAC128_D[] = {
|
||||
0x23,0x2F,0x25,0x2A,0x6D,0x40,0x40,0x40,
|
||||
0x40,0x40,0x40,0x40,0x40,0x52,0x10,0x30,
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
ZUC_KEY zuc;
|
||||
ZUC_MAC_TAG t1;
|
||||
ZUC_MAC_TAG t2;
|
||||
int macbits;
|
||||
} ZUC256_MAC_CTX;
|
||||
|
||||
|
||||
int ZUC_MAC_init(ZUC_MAC *ctx, const unsigned char *key, int bits,
|
||||
const unsigned char *iv, int macbits)
|
||||
{
|
||||
const ZUC_UINT7 *K;
|
||||
ZUC_UINT31 *LFSR = key->LFSR;
|
||||
uint32_t R1, R2;
|
||||
uint32_t X0, X1, X2;
|
||||
uint32_t W, W1, W2, U, V;
|
||||
int i;
|
||||
|
||||
switch (macbits) {
|
||||
case 32:
|
||||
K = KD32;
|
||||
break;
|
||||
case 64:
|
||||
K = KD64;
|
||||
break;
|
||||
case 128:
|
||||
K = KD128;
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
||||
LFSR[0] = MAKEU31(K[0], D[0], K[21], K[16]);
|
||||
LFSR[1] = MAKEU31(K[1], D[1], K[22], K[17]);
|
||||
LFSR[2] = MAKEU31(K[2], D[2], K[23], K[18]);
|
||||
LFSR[3] = MAKEU31(K[3], D[3], K[24], K[19]);
|
||||
LFSR[4] = MAKEU31(K[4], D[4], K[25], K[20]);
|
||||
LFSR[5] = MAKEU31(IV[0], (D[5] | IV[17]), K[5], K[26]);
|
||||
LFSR[6] = MAKEU31(IV[1], (D[6] | IV[18]), K[6], K[27]);
|
||||
LFSR[7] = MAKEU31(IV[10], (D[7] | IV[19]), K[7], IV[2]);
|
||||
LFSR[8] = MAKEU31(K[8], (D[8] | IV[20]), IV[13], IV[11]);
|
||||
LFSR[9] = MAKEU31(K[9], (D[9] | IV[21]), IV[12], IV[4]);
|
||||
LFSR[10] = MAKEU31(IV[5], (D[10] | IV[22]), K[10], K[28]);
|
||||
LFSR[11] = MAKEU31(K[11], (D[11] | IV[23]), IV[6], IV[13]);
|
||||
LFSR[12] = MAKEU31(K[12], (D[12] | IV[24]), IV[7], IV[14]);
|
||||
LFSR[13] = MAKEU31(K[13], D[13], IV[15], IV[8]);
|
||||
LFSR[14] = MAKEU31(K[14], (D[14] | (K[31] >> 4)), IV[16], IV[9]);
|
||||
LFSR[15] = MAKEU31(K[15], (D[15] | (K[31] & 0xF0)), K[30], K[29]);
|
||||
|
||||
R1 = 0;
|
||||
R2 = 0;
|
||||
|
||||
for (i = 0; i < 32; i++) {
|
||||
BitReconstruction3(X0, X1, X2);
|
||||
W = F(X0, X1, X2);
|
||||
LFSRWithInitialisationMode(W >> 1);
|
||||
}
|
||||
|
||||
BitReconstruction2(X1, X2);
|
||||
F_(X1, X2);
|
||||
LFSRWithWorkMode();
|
||||
|
||||
key->R1 = R1;
|
||||
key->R2 = R2;
|
||||
|
||||
}
|
||||
|
||||
|
||||
#define MAKEU32(i,A,B) (((A) << (i)) | ((B) >> (32 - (i))))
|
||||
#define MASKU8(i,M) (-(((M) >> (7-i)) & 0x01))
|
||||
|
||||
int ZUC256_MAC32(ZUC256_MAC_CTX *ctx, const unsigned char *data, size_t len)
|
||||
{
|
||||
uint32_t T;
|
||||
uint32_t Z;
|
||||
uint32_t *m = data;
|
||||
|
||||
T = ZUC256_generate_keyword(key);
|
||||
Z0 = ZUC256_generate_keyword(key);
|
||||
Z1 = ZUC256_generate_keyword(key);
|
||||
|
||||
for (i = 0; i < len; i++) {
|
||||
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 0) % 32) & MASKU8(data[i], 7);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 1) % 32) & MASKU8(data[i], 6);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 2) % 32) & MASKU8(data[i], 5);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 3) % 32) & MASKU8(data[i], 4);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 4) % 32) & MASKU8(data[i], 3);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 5) % 32) & MASKU8(data[i], 2);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 6) % 32) & MASKU8(data[i], 1);
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8 + 7) % 32) & MASKU8(data[i], 0);
|
||||
|
||||
if (i % 4 == 3) {
|
||||
Z0 = Z1;
|
||||
Z1 = ZUC256_generate_keyword(key);
|
||||
}
|
||||
}
|
||||
|
||||
T ^= MAKEU32(Z0, Z1, (i * 8) % 32);
|
||||
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user