大家好,欢迎来到IT知识分享网。
文章目录
BLS数字签名原理
一、概念须知
- 曲线哈希(Hashing to the curve)
- 曲线配对(curves pairing)
- 双线性配对特性(方便理解聚合签名)
e ( a ∗ b , p ) = e ( b , a ∗ p ) e(a*b,p)=e(b,a*p) e(a∗b,p)=e(b,a∗p)
e ( a , b + c ) = e ( a , b ) ∗ e ( a , c ) e(a,b+c)=e(a,b)*e(a,c) e(a,b+c)=e(a,b)∗e(a,c)
更加具体的介绍,网上很多,此处不赘述。
二、基础应用
2.1 单个签名
1、 p k pk pk代表私钥, P = p k ∗ G P=pk*G P=pk∗G代表公钥, m s g msg msg代表要签名的消息
2、签名: S i g = p k ∗ H ( m s g ) Sig=pk*H(msg) Sig=pk∗H(msg) ,其中 H ( m s g ) H(msg) H(msg)为 m s g msg msg经过哈希运算得到的摘要信息
2.2 单个签名验证
我们可以使用公钥 P P P来验证签名。
验证过程可理解为:验证 公钥 和 消息 的哈希值(曲线上的两点) 与 曲线基点 G G G(也称:生成点)和 签名(曲线上的另外两个点)是否映射到同一个数。
e ( P , H ( m s g ) ) = e ( G , S i g ) e(P,H(msg))=e(G,Sig) e(P,H(msg))=e(G,Sig)
三、比特币中的应用
3.1 签名聚合
对于比特币来说,BLS极度优美。
一个区块中包含若干笔交易,每笔交易都有对应的签名(记为 s i g n sig_n sign),将每笔交易的签名进行简单聚合,可得到聚合签名 S i g Sig Sig
S i g = S i g 1 + S i g 2 + S i g 3 + . . . + S i g n Sig=Sig_1+Sig_2+Sig_3+…+Sig_n Sig=Sig1+Sig2+Sig3+…+Sign
3.2 聚合签名验证
聚合签名验证即为验证:
e ( G , S i g ) = e ( P 1 , H ( m s g 1 ) ) ∗ e ( P 2 , H ( m s g 2 ) ) ∗ . . . ∗ e ( P n , H ( m s g n ) ) e(G,Sig)=e(P_1,H(msg_1))*e(P_2,H(msg_2))*…*e(P_n,H(msg_n)) e(G,Sig)=e(P1,H(msg1))∗e(P2,H(msg2))∗…∗e(Pn,H(msgn))
即:知晓聚合签名、签名者的公钥、和每笔交易的摘要信息,即可同时验证多比交易。
上述等式推导过程:(选择性观看)
e ( G , S i g ) = e ( G , S i g 1 + S i g 2 + S i g 3 + . . . + S i g n ) = e ( G , p k 1 ∗ H ( m s g 1 ) + p k 2 ∗ H ( m s g 2 ) + . . . + p k n ∗ H ( m s g n ) ) = e ( G , p k 1 ∗ H ( m s g 1 ) ) ∗ e ( G , p k 2 ∗ H ( m s g 2 ) ) ∗ . . ∗ e ( G , p k n ∗ H ( m s g n ) ) = e ( p k 1 ∗ G , H ( m s g 1 ) ∗ e ( p k 2 ∗ G , H ( m s g 2 ) ∗ . . . ∗ e ( p k n ∗ G , H ( m s g n ) = e ( P 1 , H ( m s g 1 ) ) ∗ e ( P 2 , H ( m s g 2 ) ) ∗ . . . ∗ e ( P n , H ( m s g n ) ) e(G,Sig)\\=e(G,Sig_1+Sig_2+Sig_3+…+Sig_n)\\=e(G,pk_1*H(msg_1)+pk_2*H(msg_2)+…+pk_n*H(msg_n))\\=e(G,pk_1*H(msg_1))*e(G,pk_2*H(msg_2))*..*e(G,pk_n*H(msg_n))\\=e(pk_1*G,H(msg_1)*e(pk_2*G,H(msg_2)*…*e(pk_n*G,H(msg_n)\\=e(P_1,H(msg_1))*e(P_2,H(msg_2))*…*e(P_n,H(msg_n)) e(G,Sig)=e(G,Sig1+Sig2+Sig3+…+Sign)=e(G,pk1∗H(msg1)+pk2∗H(msg2)+…+pkn∗H(msgn))=e(G,pk1∗H(msg1))∗e(G,pk2∗H(msg2))∗..∗e(G,pkn∗H(msgn))=e(pk1∗G,H(msg1)∗e(pk2∗G,H(msg2)∗…∗e(pkn∗G,H(msgn)=e(P1,H(msg1))∗e(P2,H(msg2))∗…∗e(Pn,H(msgn))
应用聚合签名技术,可大大提升区块的验证速度!!!
四、联盟链中的应用
主要考虑应用到联盟链共识机制中,收集投票信息时采用!!!
可以降低主副节点间的通信复杂度!!!敲重点!!!
4.1 (m,m)多重签名
实际场景:系统内的所有节点需要针对一个信息(记为 m s g msg msg)进行投票
其中:
i – 节点私钥: p k i pk_i pki
ii – 节点公钥: P i = p k i ∗ G P_i=pk_i*G Pi=pki∗G
1、聚合:
(1)聚合公钥: P = p k 1 + p k 2 + . . . + p k n P=pk_1+pk_2+…+pk_n P=pk1+pk2+…+pkn
(ps:聚合公钥的计算方式有很多种,为了提升系统的安全系数,一般不会仅是进行加减法!!!本文方便理解,以加法为例。)
(2)聚合签名: S i g = S i g 1 + S i g 2 + S i g 3 + . . . + S i g n Sig=Sig_1+Sig_2+Sig_3+…+Sig_n Sig=Sig1+Sig2+Sig3+…+Sign
2、签名验证:
即为验证: e ( G , S i g ) = e ( P , H ( m s g ) ) e(G,Sig)=e(P,H(msg)) e(G,Sig)=e(P,H(msg))
推导:(选择性看)
e ( G , S i g ) = e ( G , S i g 1 + S i g 2 + . . . + S i g n ) = e ( G , ( p k 1 + p k 2 + . . . + p k n ) ∗ H ( m s g ) ) = e ( ( p k 1 + p k 2 + . . . + p k n ) ∗ G , H ( m s g ) ) = e ( P 1 + P 2 + . . . + P 3 , H ( m s g ) ) = e ( P , H ( m s g ) ) e(G,Sig)\\=e(G,Sig_1+Sig_2+…+Sig_n)\\=e(G,(pk_1+pk_2+…+pk_n)*H(msg)) \\=e((pk_1+pk_2+…+pk_n)*G,H(msg))\\ =e(P_1+P_2+…+P_3,H(msg))\\=e(P,H(msg)) e(G,Sig)=e(G,Sig1+Sig2+…+Sign)=e(G,(pk1+pk2+…+pkn)∗H(msg))=e((pk1+pk2+…+pkn)∗G,H(msg))=e(P1+P2+…+P3,H(msg))=e(P,H(msg))
4.2 (m,n)多重签名(较复杂,重点)
实际场景:系统内的部分节点对一个信息进行投票。
同样:
i – 节点私钥: p k i pk_i pki
ii – 节点公钥: P i = p k i ∗ G P_i=pk_i*G Pi=pki∗G
两个哈希函数:(注意区分)
i – 普通哈希函数 h a s h ( m ) hash(m) hash(m),结果为 一个 数字;
ii – 曲线哈希函数 H ( x ) H(x) H(x),结果为曲线上的点!!!
步骤
1、初始化:保证签名者之后无需通信
(1)聚合公钥: P = a 1 ∗ P 1 + a 2 ∗ P 2 + . . . + a n ∗ P n P=a_1*P_1+a_2*P_2+…+a_n*P_n P=a1∗P1+a2∗P2+…+an∗Pn
补充说明:关于 a n a_n an, a n a_n an是一个数字,计算方式有多种,本文取
a i = h a s h ( P i , ( P 1 , P 2 , . . . , P n ) ) a_i=hash(P_i,(P_1,P_2,…,P_n)) ai=hash(Pi,(P1,P2,…,Pn))
(2)成员密钥:
成员密钥的作用:验证 该成员 确实是 签名组 (我自己起的名字,可能不太准确)内的成员!!!
M K i = ( a 1 ∗ p k 1 ) ∗ H ( P , i ) + ( a 2 ∗ p k 2 ) ∗ H ( P , i ) + . . . + ( a n ∗ p k n ) ∗ H ( P , i ) MK_i=(a_1*pk_1)*H(P,i)+(a_2*pk_2)*H(P,i)+…+(a_n*pk_n)*H(P,i) MKi=(a1∗pk1)∗H(P,i)+(a2∗pk2)∗H(P,i)+…+(an∗pkn)∗H(P,i)
成员密钥的验证: e ( G , M K i ) = e ( P , H ( P , i ) ) e(G,MK_i)=e(P,H(P,i)) e(G,MKi)=e(P,H(P,i))
推导:(选择性观看!!!)
e ( G , M K i ) = e ( G , ( a 1 ∗ p k 1 ) ∗ H ( P , i ) + ( a 2 ∗ p k 2 ) ∗ H ( P , i ) + . . . + ( a n ∗ p k n ) ∗ H ( P , i ) ) = e ( G , ( a 1 ∗ p k 1 + a 2 ∗ p k 2 + . . . + a n ∗ p k n ) ∗ H ( P , i ) ) = e ( ( a 1 ∗ p k 1 + a 2 ∗ p k 2 + . . . + a n ∗ p k n ) ∗ G , H ( P , i ) ) = e ( a 1 ∗ ( p k 1 ∗ G ) + a 2 ∗ ( p k 2 ∗ G ) + . . . + a n ∗ ( p k n ∗ G ) , H ( P , i ) ) = e ( a 1 ∗ P 1 + a 2 ∗ P 2 + . . . + a n ∗ P n , H ( P , i ) ) = e ( P , H ( P , i ) ) e(G,MK_i)\\=e(G,(a_1*pk_1)*H(P,i)+(a_2*pk_2)*H(P,i)+…+(a_n*pk_n)*H(P,i))\\=e(G,(a_1*pk_1+a_2*pk_2+…+a_n*pk_n)*H(P,i))\\=e((a_1*pk_1+a_2*pk_2+…+a_n*pk_n)*G,H(P,i))\\=e(a_1*(pk_1*G)+a_2*(pk_2*G)+…+a_n*(pk_n*G),H(P,i))\\=e(a_1*P_1+a_2*P_2+…+a_n*P_n,H(P,i))\\=e(P,H(P,i)) e(G,MKi)=e(G,(a1∗pk1)∗H(P,i)+(a2∗pk2)∗H(P,i)+…+(an∗pkn)∗H(P,i))=e(G,(a1∗pk1+a2∗pk2+…+an∗pkn)∗H(P,i))=e((a1∗pk1+a2∗pk2+…+an∗pkn)∗G,H(P,i))=e(a1∗(pk1∗G)+a2∗(pk2∗G)+…+an∗(pkn∗G),H(P,i))=e(a1∗P1+a2∗P2+…+an∗Pn,H(P,i))=e(P,H(P,i))
2、聚合签名
如果使用私钥 p k 1 , p k 2 , . . . , p k m pk_1,pk_2,…,pk_m pk1,pk2,…,pkm对交易进行签名,我们会生成m个签名:
S i g 1 = p k 1 ∗ H ( P , m ) + M K 1 Sig_1=pk_1*H(P,m)+MK_1 Sig1=pk1∗H(P,m)+MK1
S i g 2 = p k 2 ∗ H ( P , m ) + M K 2 Sig_2=pk_2*H(P,m)+MK_2 Sig2=pk2∗H(P,m)+MK2
…
S i g m = p k m ∗ H ( P , m ) + M K m Sig_m=pk_m*H(P,m)+MK_m Sigm=pkm∗H(P,m)+MKm
聚合签名:
( S ′ , P ′ ) = ( S i g 1 + S i g 2 + . . . + S i g m , P 1 + P 2 + . . . . + P m ) (S’,P’)=(Sig_1+Sig_2+…+Sig_m,P_1+P_2+….+P_m) (S′,P′)=(Sig1+Sig2+…+Sigm,P1+P2+….+Pm)
3、签名验证
(m,n)多重签名验证即为验证等式:
e ( G , S ′ ) = e ( P ′ , H ( p , m ) ) ∗ e ( P ′ , H ( P , 1 ) + H ( P , 2 ) + . . . + H ( P , m ) ) e(G,S’)=e(P’,H(p,m))*e(P’,H(P,1)+H(P,2)+…+H(P,m)) e(G,S′)=e(P′,H(p,m))∗e(P′,H(P,1)+H(P,2)+…+H(P,m))
推导:(选择性看!!!)
e ( G , S ′ ) = e ( G , S i g 1 + S i g 2 + . . . + S i g m ) = e ( G , p k 1 ∗ H ( P , m ) + p k 2 ∗ H ( P , m ) + . . . + p k m ∗ H ( P , m ) + M K 1 + M K 2 + . . . + M K m ) = e ( G , p k 1 ∗ H ( P , m ) + p k 2 ∗ H ( P , m ) + . . . + p k m ∗ H ( P , m ) ) ∗ e ( G , M K 1 + M K 2 + . . . + M K m ) = e ( G ∗ ( p k 1 + p k 2 + . . . + p k m ) , H ( P , m ) ) ∗ e ( G , ( a 1 ∗ p k 1 + a 2 ∗ p k 2 + . . . + a m ∗ p k m ) ∗ ( H ( P , 1 ) + H ( P , 2 ) + . . . + H ( P , m ) ) ) = e ( P ′ , H ( P , m ) ) ∗ e ( P ′ , H ( P , 1 ) + H ( P , 2 ) + . . . + H ( P , m ) ) e(G,S’)\\=e(G,Sig_1+Sig_2+…+Sig_m)\\=e(G,pk_1*H(P,m)+pk_2*H(P,m)+…+pk_m*H(P,m)+MK_1+MK_2+…+MK_m)\\=e(G,pk_1*H(P,m)+pk_2*H(P,m)+…+pk_m*H(P,m))*e(G,MK_1+MK_2+…+MK_m)\\=e(G*(pk_1+pk_2+…+pk_m),H(P,m))*\\e(G,(a_1*pk_1+a_2*pk_2+…+a_m*pk_m)*(H(P,1)+H(P,2)+…+H(P,m)))\\=e(P’,H(P,m))*e(P’,H(P,1)+H(P,2)+…+H(P,m)) e(G,S′)=e(G,Sig1+Sig2+…+Sigm)=e(G,pk1∗H(P,m)+pk2∗H(P,m)+…+pkm∗H(P,m)+MK1+MK2+…+MKm)=e(G,pk1∗H(P,m)+pk2∗H(P,m)+…+pkm∗H(P,m))∗e(G,MK1+MK2+…+MKm)=e(G∗(pk1+pk2+…+pkm),H(P,m))∗e(G,(a1∗pk1+a2∗pk2+…+am∗pkm)∗(H(P,1)+H(P,2)+…+H(P,m)))=e(P′,H(P,m))∗e(P′,H(P,1)+H(P,2)+…+H(P,m))
五、BLS的缺陷
六、JAVA简单实现
很早以前写的了,不保证能运行成功。
public class Pki<R, T> {
Map<ClientID,privkey> public static Map<Integer, BigInteger> privKeys = new HashMap<>();//分私钥(PKI保存) //Map<clientID,pubKey> public static Map<Integer, Element> pubKeys = new HashMap<>();//分公钥(需要公布) //Map<clientId,keyInfo> public static Map<Integer, KeyInfo> keyInfos = new HashMap<>(); //初始化 - 一旦生成,就不可变! public static final Pairing bp = PairingFactory.getPairing("a.properties"); public static final Field G1 = bp.getG1(); public static final Field Zr = bp.getZr(); public static final Element g = G1.newRandomElement().getImmutable(); public static final int CERTAINTY = 256; public static final SecureRandom random = new SecureRandom(); //(Element)主公钥/主私钥 //(BigInteger)主私钥(Element)转换称为(BigInteger)形式,作为(secret)进行分割 private static final Element privateMaster = Zr.newRandomElement();//主私钥(私有) public static final Element publicMaster = g.duplicate().powZn(privateMaster);//主公钥(目前没有什么作用) private static final BigInteger secret = privateMaster.toBigInteger(); public static final BigInteger prime = new BigInteger(secret.bitLength() + 1, CERTAINTY, random); public static void split(final BigInteger secret, int needed, int available, BigInteger prime, Random random) {
/* * split(final BigInteger secret, int needed, int available, BigInteger prime, Random random) * - secret - 待分割的秘密 * - needed - 几份可拼凑成完整的 * - available - 分成几份 * - prime - 大素数 * - random - 随机数 * * 此函数执行后,会将:privKeys,pubKeys填满 * */ final BigInteger[] coeff = new BigInteger[needed]; coeff[0] = secret; for (int i = 1; i < needed; i++) {
BigInteger r; while (true) {
r = new BigInteger(prime.bitLength(), random); //r>0 && r<prime if (r.compareTo(BigInteger.ZERO) > 0 && r.compareTo(prime) < 0) {
break;//强制为+ } } coeff[i] = r; } for (int x = 1; x <= available; x++) {
BigInteger privKey = secret; for (int exp = 1; exp < needed; exp++) {
privKey = privKey.add(coeff[exp].multiply(BigInteger.valueOf(x).pow(exp))); } privKeys.put(x, privKey); Element pubKey = g.pow(privKey).getImmutable(); pubKeys.put(x, pubKey); KeyInfo keyInfo = new KeyInfo(pubKey, privKey); keyInfos.put(x, keyInfo); } } }
KeyInfo
import it.unisa.dia.gas.jpbc.Element; import java.math.BigInteger; public class KeyInfo {
private Element publicKey; private BigInteger privKey; public KeyInfo() {
} public KeyInfo(Element publicKey, BigInteger privKey) {
this.publicKey = publicKey; this.privKey = privKey; } @Override public String toString() {
return "KeyInfo{" + "publicKey=" + publicKey + ", privKey=" + privKey + '}'; } public Element getPublicKey() {
return this.publicKey; } public void setPublicKey(Element publicKey) {
this.publicKey = publicKey; } public BigInteger getPrivKey() {
return this.privKey; } public void setPrivKey(BigInteger privKey) {
this.privKey = privKey; } }
- 关于属性是否私有的设置:public ,private
根据个人需要,自行设置即可!
一般要做数据传输的话,privateKey会设置成private(非全网可见),publicKey设置成public(全网可见) - 此程序存在一定的缺陷,此处列出:
1.关于prime,没有进行处理;只是简单实现了门限签名的原理
不添加prime,可以成功分割签名,但是做不到聚合签名验证,验证会出现不一致!实际与理想 差了一个mod prime!!! 如有需要,请自己补充!(ps:博主能力有限,想了好几天没搞出来)
免责声明:本站所有文章内容,图片,视频等均是来源于用户投稿和互联网及文摘转载整编而成,不代表本站观点,不承担相关法律责任。其著作权各归其原作者或其出版社所有。如发现本站有涉嫌抄袭侵权/违法违规的内容,侵犯到您的权益,请在线联系站长,一经查实,本站将立刻删除。 本文来自网络,若有侵权,请联系删除,如若转载,请注明出处:https://haidsoft.com/150668.html