1. 引言
当前的数字签名方案主要有:
- RSA
- ECDSA
- EdDSA:已废弃DSA,将EdDSA纳入FIPS 186。
这些数字签名方案都不可抗量子攻击。为此,需要新的量子强健的签名方案,NIST引入了3种新的PQC数字签名标准化方案:
- 1)CRYSTALS-Dilithium数字签名方案:基于Lattice安全假设。分为:
- Dilithium2 (Level 1):等价为128-bit AES
- Dilithium3 (Level 3):等价为192-bit AES
- Dilithium5 (Level 5):等价为256-bit AES
- 2)Falcon数字签名方案:基于Lattice安全假设。分为:
- Falcon-512 (Level 1)
- Falcon-1024 (Level 5)
- 3)SPHINCS+数字签名方案:基于Hash安全假设,分为:
- SPHINCS+-128 (Level 1)
- SPHINCS+-192 (Level 3)
- SPHINCS+-256 (Level 5)
总体结论为:
Dilithum为通用数字签名方案,FALCON签名size有优势。Dilithum和FALCON为基于lattice的数字方案,SPHINCS+ 为基于哈希的数字签名方案,具有小的公私钥size,但是签名size相对要大很多。
根据PQC Digital Signature Speed Tests,这3个方案的密钥生成、签名、验签用时对比情况为:
由此可知,与FALCON 和 SPHINCS+ 相比,Dilithium在各个维度性能最优。SPHINCS+ 系列中,SPINHCS+-Haraka的性能最优。
FALCON在密钥生成时性能要弱于Dilithium,但签名和验签性能二者相当。与签名和验签相比,密钥生成阶段发生的频次要低很多,因此该问题不大。
仍然根据PQC Digital Signature Speed Tests,这三个方案的密钥size和签名size对比为:
由此可知,SPHINCS+ 的公私钥size都不错,有32-byte私钥和64-byte公钥——与ECC类似。但是其数字签名size超过17kB。
Dilithium性能不错,但FALCON的签名size有优势,FALCON-512 的签名为690-byte,而Dilithium-2签名有2,420-byte。
Dilithium的私钥为1,312-byte,公钥为2,528-byte,签名为2,420-byte。Falcon的密钥size相当。
总体的密钥size情况为:
Method Public key size Private key size Signature size Security level
------------------------------------------------------------------------------------------------------
Crystals Dilithium 2 1,312 2,528 2,420 1 (128-bit) Lattice
Crystals Dilithium 3 1,952 4,000 3,293 3 (192-bit) Lattice
Crystals Dilithium 5 2,592 4,864 4,595 5 (256-bit) Lattice
Falcon 512 (Lattice) 897 1,281 690 1 (128-bit) Lattice
Falcon 1024 1,793 2,305 1,330 5 (256-bit) Lattice
Sphincs SHA256-128f Simple 32 64 17,088 1 (128-bit) Hash-based
Sphincs SHA256-192f Simple 48 96 35,664 3 (192-bit) Hash-based
Sphincs SHA256-256f Simple 64 128 49,856 5 (256-bit) Hash-based
RSA-2048 256 256 256
ECC 256-bit 64 32 256
2. SPHINCS+
近20年来,Daniel J Bernstein (djb) 在密码学领域有突出贡献,其创建了ChaCha20, Salsa20, Curve 25519, twisted elliptic curves, AES timing attacks等等。其核心贡献之一为
The SPHINCS+ Signature Framework。
当前大多数基于哈希的方案都需要记录之前签名的私钥,而SPHINCS为基于哈希的stateless的签名方案。
SPHINCS+ 256 128-bit的公钥size为32字节,私钥size为64字节,签名为17kB。4核3.5GHz处理器在一秒内可做数百次哈希运算,
其它的哈希方案有Haraka 和 SHAKE-256 的128-bit、192-bit 以及 256-bit 版本。
基于hash的tree会使用WOTS和HORST,以及其他参数,如:
- n n n — length of hash in WOTS / HORST (in bits)
- m m m — length of message hash (in bits)
- h h h — height of the hyper-tree
- d d d — layers of the hyper-tree
- w w w — Winternitz parameter used for WOTS signature
- t a u tau tau — layers in the HORST tree ( 2 t a u 2^{tau} 2tau is no. of secret-key elements)
- k k k — number of revealed secret-key elements per HORST signature
以
n
=
256
,
m
=
512
,
h
=
2
,
d
=
1
,
w
=
4
,
t
a
u
=
8
,
k
=
64
n=256, m=512, h=2, d=1, w=4, tau=8, k=64
n=256,m=512,h=2,d=1,w=4,tau=8,k=64为例:
某些操作使用BLAKE哈希方案,且ChaCha用于生成随机数。
2.1 Winternitz one time signature scheme (W-OTS)
W-OTS具有相对小的密钥和签名size,且是量子强健的。其生成 w w w次 32×256 bit 随机私钥。若 w = 8 w=8 w=8,则对这些私钥哈希 2 w 2w 2w次,可创建32×256 bits 公钥。每次取8bits,然后将私钥哈希 256 − n 256-n 256−n(其中 n n n为8-bit binary int)次。签名为自随机私钥派生的32个哈希值。验签时,接收者会解析签名哈希(每次使用8 bits,提取 8 bit int n n n值),然后自签名可派生出签名。
Winternitz one time signature scheme (W-OTS)方案具体为:
- 首先创建32个256-bit随机值。这32个值为私钥。
- 对每个随机值做256次哈希运算之后的32个值为公钥。
- 对待签名message做SHA-256哈希,生成32个8-bit values( N 1 , N 2 , ⋯ , N 32 N1,N2,\cdots,N32 N1,N2,⋯,N32)。
- 对message哈希结果的每个8-bit value( N 1 , N 2 , ⋯ , N 32 N1,N2,\cdots,N32 N1,N2,⋯,N32),做 256 − N 256-N 256−N次哈希运算,其中 N N N为该8-bit value的值。
- 验签时,对待签名message做SHA-256哈希,生成32个8-bit values( N 1 , N 2 , ⋯ , N 32 N1,N2,\cdots,N32 N1,N2,⋯,N32)。对每个8-bit signature值做 N N N次哈希运算,其中 N N N为相应待签名message哈希结果的8-bit value值。每次操作的结果应等于公钥。
W-OTS示例见Quantum Robust: Winternitz one time signature scheme (W-OTS):
Hashing number: 256
==== Private key (keep secret) =====
Priv[0]: bd344c6110628aa38c9b5ca6458bed7b78425b2e82efa0624a578031562f82ee
Priv[1]: 20670af5b1663fa9fad49fab6a692ae5989cff77439f98d2288f173b17a8d99f
Priv[2]: 625aa290fd1f88c930451ff743d5d9ef90e7064368fb23a18c9fd048474818f2
Priv[3]: ee0e1363cbd5f61017ba27bfe91ec53969d28d143ed59a99efb020941bc4990f
Priv[4]: ce94d7282ee3f7b05b99768695ff224b5994900c6182dfb89d596d8b7b405ec6
Priv[5]: d0c59651e951b0bb8d5a2d7b93f6739c9ce4a0c0c0f63bfce23b331b947eb285
==== Public key (show everyone)=====
Pub[0]: 45fdac6339e80cadd1331cce026cd0364ea84146a36f6f3f2449b66fb55a217a
Pub[1]: 184cf92f22072fef078fa4a93ec2044f07ac8b12e326509474209312cace8a5a
Pub[2]: a47548d4537bd284e7d7f935f41570866d9c6a72c463bb2a2b10c8c7907621f0
Pub[3]: 60395e575522cacb70d866211c64e8a74e562c79d1fffce224d1013d088bf66f
Pub[4]: 8be7b53d5b56e698b8798f2a707fba7b8e417554fd489d74cc40fe8574d7589e
Pub[5]: 9fac35971dae3a5c77ae7b5c720a72f90ee53852668c96c78e095cbb52af20a1
==== Message to sign ===============
Message: The quick brown fox jumps over the lazy dog
SHA-256: d7a8fbb307d7809469ca9abcb0082e4f8d5651e46d3cdb762d02d0bf37c9e592
==== Signature =====================
Sign[0]: 45cb53c5c33af9b20426fd0233fd63d92bf0c2ded367163e6f2f93588a33c6d8
Sign[1]: e8c35987101f2d11d7056a2fe78069d3ed73aee315ebef8c2d40e04973301c26
Sign[2]: 59220d80b7c958957b28511f4081341cc4a00a0d6d5e1d05351be7dec3ca8aaa
Sign[3]: 72a906d719be18e1592314bf6f6c521a325a9de2b5b9e9e13117bf01b0157f5c
The signature test is True
2.2 SPHINCS+签名
SPHINCS+ 具有短的公钥和私钥size,但前签名要远长于Dilithium签名和Falcon签名。
详细实现见SPHINCS+ - Digital Signature:
相同安全级别的情况下,SPHINCS+ 签名为49KB,而Dilithium签名仅为4KB,Falcon签名仅为1KB。
SPHINCS+ - Digital Signature的具体代码实现可为:
#include "api.h"
#define MLEN 59
char *showhex(uint8_t a[], int size) ;char *showhex(uint8_t a[], int size) {
char *s = malloc(size * 2 + 1); for (int i = 0; i < size; i++)
sprintf(s + i * 2, "%02x", a[i]); return(s);
}int main(void)
{
size_t i, j;
int ret;
size_t mlen, smlen;
uint8_t b;
uint8_t m[MLEN + CRYPTO_BYTES];
uint8_t m2[MLEN + CRYPTO_BYTES];
uint8_t sm[MLEN + CRYPTO_BYTES];
uint8_t pk[CRYPTO_PUBLICKEYBYTES];
uint8_t sk[CRYPTO_SECRETKEYBYTES];
randombytes(m, MLEN); crypto_sign_keypair(pk, sk);
crypto_sign(sm, &smlen, m, MLEN, sk);
ret = crypto_sign_open(m2, &mlen, sm, smlen, pk); if(ret) {
fprintf(stderr, "Verification failed\n");
return -1;
}
if(smlen != MLEN + CRYPTO_BYTES) {
fprintf(stderr, "Signed message lengths wrong\n");
return -1;
}
if(mlen != MLEN) {
fprintf(stderr, "Message lengths wrong\n");
return -1;
}
for(j = 0; j < MLEN; ++j) {
if(m2[j] != m[j]) {
fprintf(stderr, "Messages don't match\n");
return -1;
}
}
randombytes((uint8_t *)&j, sizeof(j));
do {
randombytes(&b, 1);
} while(!b);
sm[j % (MLEN + CRYPTO_BYTES)] += b;
ret = crypto_sign_open(m2, &mlen, sm, smlen, pk);
if(!ret) {
fprintf(stderr, "Trivial forgeries possible\n");
return -1;
}
printf("NAME: %s\n", CRYPTO_ALGNAME);
printf("CRYPTO_PUBLICKEYBYTES = %d\n", CRYPTO_PUBLICKEYBYTES);
printf("CRYPTO_SECRETKEYBYTES = %d\n", CRYPTO_SECRETKEYBYTES);
printf("CRYPTO_BYTES = %d\n", CRYPTO_BYTES); printf("Signature Length + Msg = %ld\n", smlen); printf("\nAlice Public key: %s\n",showhex(pk,CRYPTO_PUBLICKEYBYTES));
printf("Alice Secret key: %s\n",showhex(pk,CRYPTO_SECRETKEYBYTES)); printf("\nMessage: %s\n",showhex(m,MLEN));
printf("Signature (Showing 1/32th of signature): %s\n",showhex(sm,smlen/32));
return 0;
}
运行SPHINCS+ 128示例可知,公钥size为32字节,私钥size为64字节,数字签名为17,088字节:
NAME: SPHINCS+
CRYPTO_PUBLICKEYBYTES = 32
CRYPTO_SECRETKEYBYTES = 64
CRYPTO_BYTES = 17088
Signature Length + Msg = 17147Alice Public key: 2fbdcbb6ec87851c3674e0a38f551ca1bb44677ae13969ed16c1350fe95238ce
Alice Secret key: 2fbdcbb6ec87851c3674e0a38f551ca1bb44677ae13969ed16c1350fe95238ce79fb06c5872fbccf30afefc46d1a74791273744e66c59a1b517278a58c33b706Message: 79fb06c5872fbccf30afefc46d1a74791273744e66c59a1b517278a58c33b7062fbdcbb6ec87851c3674e0a38f551ca1c890f02e568a49a7fcc14c
Signature (Showing 1/32th of signature): d681767c6c41ecd17ffd2eda21143b305e133be88bb770a451403a199d9de6e292b16fb4d614817e28e14f07809488f506d18c58db6a3d9106b357a333d75e3d10c9ba78a7eb1a070a08084ee6878b95c9d7c9d24fa377f4131d07dbb07c123eb88a9e8196699f2ed35a62a3fd2c25eb4398a43bc89dd9f3f9fbd479d34395bfba932d9971e68e560b93ceac905afe3a0c87311b345e72fec4b67f0094a693e14fafd890498b3fd0c4c7dfa4f594d35413f3489a40c06bd2c82b8cd4d101a3afba346cf6cd723d23f8aeeee8c8bbcc4f5d70a5975815cad42bc3a59ff5f4af7dc07c9cc26002d25c9a4f2c55e45136f37d4c7a5055c0a76736578da27994472fe81409d1b4578d05d4256444a152e437368040addd4b25c452578199f855ea090a3afe6b49df75505385d8a76460ad0ff8e290ca5db7a0c4a2aab38ad1c544f273776ccb5d12bfaca08271319b3b4aa7b179d5b31034366664cd5290be8f411170015c8f07286445ef6164a5fff825dda62ea61a56418c4a62955537904d87ac2f89b1b5e8c6208fa9192f21019d6730b39dfe8bb4e681551f75902e92a1ff92adf6eaa773c6d0937fcb6abc583872cc61f8ab136e8dbffa43c4711f7677553efaadea1c12002acf0ec222a8217d22ea896d2de8df88704296ff1be222fa8b1a09af78ef2a0483c0b525e04563eaf2db5001d884d74c6a609da361a7808be4264bc00fb56c9fc382f80bd0a150211f817991a25bfaf804
参考资料
[1] Prof Bill Buchanan OBE 2023年5月2日博客 Digital Signatures for the Future: Dilithium, FALCON and SPHINCS+