【密码学基础】【SM2公钥算法】【ECC算法实现】椭圆曲线运算算法、求解椭圆曲线上的点,

椭圆曲线点集产生方法如下

 通过该方法得到如下算法:

#计算椭圆曲线的点集
def calculate(a,b,p):
    results = ""
    for x in range(p):
        z = (pow(x,3)+a*x+b) % p
        result = (pow(z,(p-1)/2)) % p
        x1 = pow(z,(p+1)/4) % p
        x2 = p - pow(z,(p+1)/4) % p
        start = "当x={x}时,     \tz = {z}, z ^ {t} = {result}".format(x=x,z=z,t=(p-1)/2,result=result)
        info = " \t--是平方剩余 ({},{}) and ({},{})".format(x,int(x1),x,int(x2)) if result == 1 else "不是平方剩余"
        results += start + info + "\n"
    return results

运行结果:

当x=0时,        z = 1, z ^ 9.0 = 1.0    --是平方剩余 (0,1) and (0,18)
当x=1时,        z = 3, z ^ 9.0 = 18.0不是平方剩余
当x=2时,        z = 11, z ^ 9.0 = 1.0   --是平方剩余 (2,7) and (2,12)
当x=3时,        z = 12, z ^ 9.0 = 18.0不是平方剩余
当x=4时,        z = 12, z ^ 9.0 = 18.0不是平方剩余
当x=5时,        z = 17, z ^ 9.0 = 1.0   --是平方剩余 (5,6) and (5,13)
当x=6时,        z = 14, z ^ 9.0 = 18.0不是平方剩余
当x=7时,        z = 9, z ^ 9.0 = 1.0    --是平方剩余 (7,16) and (7,3)
当x=8时,        z = 8, z ^ 9.0 = 18.0不是平方剩余
当x=9时,        z = 17, z ^ 9.0 = 1.0   --是平方剩余 (9,6) and (9,13)
当x=10时,       z = 4, z ^ 9.0 = 1.0    --是平方剩余 (10,17) and (10,2)
当x=11时,       z = 13, z ^ 9.0 = 18.0不是平方剩余
当x=12时,       z = 12, z ^ 9.0 = 18.0不是平方剩余
当x=13时,       z = 7, z ^ 9.0 = 1.0    --是平方剩余 (13,11) and (13,8)
当x=14时,       z = 4, z ^ 9.0 = 1.0    --是平方剩余 (14,17) and (14,2)
当x=15时,       z = 9, z ^ 9.0 = 1.0    --是平方剩余 (15,16) and (15,3)
当x=16时,       z = 9, z ^ 9.0 = 1.0    --是平方剩余 (16,16) and (16,3)
当x=17时,       z = 10, z ^ 9.0 = 18.0不是平方剩余
当x=18时,       z = 18, z ^ 9.0 = 18.0不是平方剩余

 通过椭圆曲线上的运算规则

 得到如下加法、乘法、减法运算算法

def Operations_elliptic_curves(dot1,dot2,p):
    def Operations_elliptic_curves_jia(dot1,dot2,p):
        if dot1 != dot2:  # both points are the same point. p = 3
            A = ((int(dot2[1]) - int(dot1[1])) % p / (int(dot2[0]) - int(dot1[0]))) % p
        else:
            A = int(3 * int(dot1[0])**2 + 1) / int(2 * (dot1[1]))  
        if A % 1 :
            fenmu = 1
            for fenmu in range(1,1000):
                if (A * fenmu % 1) == 0:
                    break
            fenzi = (fenmu * A) % p
            x = 1
            for x in range(1,p):
                if (x * fenmu) % p == 1:
                    break
            A = (x * fenzi) % p
        print("α = ",int(A))
        x3 = (A**2 - int(dot1[0]) - int(dot2[0])) % p  # x3 = A^2 - 2*x1 - x2. p
        y3 = (A * int(dot1[0] - x3) - int(dot1[1])) % p  # y3 = A * (x1 - x3
        return (int(x3),int(y3))  
    def Operations_elliptic_curves_cheng(dot1,dot2,p):
        dot3 = dot2
        for i in range(int(dot1-1)):
            #print(dot3,dot2)
            dot3 = Operations_elliptic_curves_jia(dot2,dot3,p)
        return (int(dot3[0]),int(dot3[1]))  
    if isinstance(dot1,tuple):  # p = 3, symbol = '+'  (addition)  (p = 2, symbol = '*
        return  str(dot1)+" + "+str(dot2)+" = "+ str(Operations_elliptic_curves_jia(dot1,dot2,p))  
    elif isinstance(dot1,int):  
        return str(dot1)+str(dot2)+" = "+ str(Operations_elliptic_curves_cheng(dot1,dot2,p))  # p = 2, symbol = '*'  (
    else:
        return "Error: Argument must be a tuple or an integer."  


#输入两个元组,返回相减结果
def Operations_elliptic_curves_jian(dot1,dot2,p):  # p = 3, symbol = '+'  (addition)  (p = 2, symbol = '*'  (p = 3, symbol = '*'  (multiplication)  (p = 2, symbol = '*'  (multiplication)  (p = 2, symbol = '*'  (multiplication)  (p = 2, symbol = '*'  (multiplication)  (p = 2, symbol = '*'  (multiplication)  (p = 2, symbol = '*
            dot4 = (dot2[0],p-dot2[1])
            return Operations_elliptic_curves(dot1,dot4,p).replace("+", "-")

主函数调用该函数的例子:

if __name__ == "__main__":
    #如下为4个例子
    # 求点集
    #print(calculate(1,1,19))
    #加法
    print(Operations_elliptic_curves((5,4),(12,4),23))
    #乘法
    print(Operations_elliptic_curves(3,(7,12),23))
    #减法
    print(Operations_elliptic_curves_jian((6,19),(12,4),23))

 最终输出结果:

α =  0
(5, 4) + (12, 4) = (6, 19)
α =  10
α =  6
3(7, 12) = (12, 4)
α =  0
(6, 19) - (12, 19) = (5, 4)

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值