ElGamal加密算法

 

ElGamal加密算法

ElGamal加密是一种公共密钥密码系统。它使用非对称密钥加密在双方之间进行通信并加密消息。
该密码系统基于难以找到循环群中离散对数的困难,即使我们知道g a和g k,也很难计算g ak

ElGamal密码系统的想法
假设Alice想与Bob交流。

  1. 鲍勃生成公钥和私钥:
    • 鲍勃选择一个非常大的数q和一个循环群q
    • 从环状基团˚F q,他选择的任何元素
      一个元件一个,使得满足gcd(A,Q)= 1。
    • 然后,他计算h = g a
    • 鲍勃发布Fh = g aqg作为他的公钥,并保留a作为私钥。
  2. 爱丽丝使用鲍勃的公钥加密数据:
    • 爱丽丝从循环群F中选择一个元素k 使gcd(k,q)= 1。
    • 然后,她计算出p = g k和s = h k = g ak 
    • 她与M乘以s。
    • 然后她发送(p,M * s)=(g k,M * s)。
  3. 鲍勃解密消息:
    • 鲍勃计算s ' = p a = g ak
    • 他将M * s除以s '得到M,即s = s '

以下是ElGamal密码系统在Python中的实现

# Python program to illustrate ElGamal encryption   
    
import random    
from math import pow  
    
a = random.randint(2, 10)   
    
def gcd(a, b):   
    if a < b:   
        return gcd(b, a)   
    elif a % b == 0:   
        return b;   
    else:   
        return gcd(b, a % b)   
    
# Generating large random numbers   
def gen_key(q):   
    
    key = random.randint(pow(10, 20), q)   
    while gcd(q, key) != 1:   
        key = random.randint(pow(10, 20), q)   
    
    return key   
    
# Modular exponentiation   
def power(a, b, c):   
    x = 1  
    y = a   
    
    while b > 0:   
        if b % 2 == 0:   
            x = (x * y) % c;   
        y = (y * y) % c   
        b = int(b / 2)   
    
    return x % c   
    
# Asymmetric encryption   
def encrypt(msg, q, h, g):   
    
    en_msg = []   
    
    k = gen_key(q)# Private key for sender   
    s = power(h, k, q)   
    p = power(g, k, q)   
        
    for i in range(0, len(msg)):   
        en_msg.append(msg[i])   
    
    print("g^k used : ", p)   
    print("g^ak used : ", s)   
    for i in range(0, len(en_msg)):   
        en_msg[i] = s * ord(en_msg[i])   
    
    return en_msg, p   
    
def decrypt(en_msg, p, key, q):   
    
    dr_msg = []   
    h = power(p, key, q)   
    for i in range(0, len(en_msg)):   
        dr_msg.append(chr(int(en_msg[i]/h)))   
            
    return dr_msg   
    
# Driver code   
def main():   
    
    msg = 'encryption'  
    print("Original Message :", msg)   
    
    q = random.randint(pow(10, 20), pow(10, 50))   
    g = random.randint(2, q)   
    
    key = gen_key(q)# Private key for receiver   
    h = power(g, key, q)   
    print("g used : ", g)   
    print("g^a used : ", h)   
    
    en_msg, p = encrypt(msg, q, h, g)   
    dr_msg = decrypt(en_msg, p, key, q)   
    dmsg = ''.join(dr_msg)   
    print("Decrypted Message :", dmsg);   
    
    
if __name__ == '__main__':   
    main()   

样本输出:

原始消息:加密
g使用:5860696954522417707188952371547944035333315907890
使用的g ^ a:4711309755639364289552454834506215144653958055252
使用的g ^ k:12475188089503227615789015740709091911412567126782
使用的g ^ ak:39448787632167136161153337226654906357756740068295
解密消息:加密

在该密码系统中,原始消息M通过将ak乘以来掩盖为了去除面罩,以k的形式给出线索除非有人知道一个,他将无法取回中号这是因为很难找到循环组中的离散对数,并且仅知道g a和g k不足以计算g ak

 

 

posted @ 2019-12-06 22:41  AbbySec  阅读(4860)  评论(0编辑  收藏  举报