Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/haskell/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Haskell 这个椭圆曲线代码的错误在哪里_Haskell_Elliptic Curve - Fatal编程技术网

Haskell 这个椭圆曲线代码的错误在哪里

Haskell 这个椭圆曲线代码的错误在哪里,haskell,elliptic-curve,Haskell,Elliptic Curve,我正试图用haskell编写一个椭圆曲线的elgamal实现。 但是在我的点加法函数中有一些问题:只要我不断地把起点加到它本身,我就永远不会到达无穷远(O)的点。 这是我的密码: addP :: Curve->Point->Point->Point addP _ O O = O addP _ O p = p addP _ p O = p addP curve@(a,b,p) (P x1 y1) (P x2 y2) | x1 == x2 && y1 == -y2

我正试图用haskell编写一个椭圆曲线的elgamal实现。 但是在我的点加法函数中有一些问题:只要我不断地把起点加到它本身,我就永远不会到达无穷远(O)的点。 这是我的密码:

addP :: Curve->Point->Point->Point
addP _ O O = O
addP _ O p = p
addP _ p O = p
addP curve@(a,b,p) (P x1 y1) (P x2 y2) | x1 == x2 && y1 == -y2 = O
                                       | otherwise = P x3 ((m*(x1-x3)-y1) `mod''` p)
    where x3 = (((m*m)-x1-x2) `mod''` p)
          m | x1 /= x2 = (y2-y1)/(x2-x1)
            | otherwise = (3*(x1*x1)+a)/(2*y1)
其中,曲线定义为

-- first double=a, second double=b, third double=p in y^2=x^3+ax+b mod p
type Curve = (Double, Double, Double) 
data Point = P Double Double |
             P
             deriving (Eq, Read, Show)
点的定义是

-- first double=a, second double=b, third double=p in y^2=x^3+ax+b mod p
type Curve = (Double, Double, Double) 
data Point = P Double Double |
             P
             deriving (Eq, Read, Show)
有人知道我做错了什么吗

只要我不断地给自己加起点,我就永远不会到达无穷远(O)的点

你能把你学到这一点的参考/链接贴出来吗。我对椭圆曲线的了解非常有限,但我对Haskell知之甚少,所以我试着看看你的代码是怎么回事。在使用模算术模素数p时,我首先注意到除法和double的用法。我无法看到你的mod“”做了什么,所以我对你的代码做了一点修改,它对我来说运行良好

type Curve = ( Integer , Integer , Integer )
data Point = P Integer Integer | O
         deriving (Eq, Read, Show)


extendedGcd :: Integer -> Integer -> ( Integer , Integer )
extendedGcd a b
  | b == 0 = ( 1 , 0 )
  | otherwise = ( t , s - q * t ) where
      ( q , r ) = quotRem a b 
      ( s , t ) = extendedGcd b r


modInv :: Integer -> Integer -> Integer
modInv  a b
  | gcd a b /= 1 = error " gcd is not 1 "
  | otherwise = d where
     d = until ( > 0 ) ( + b  ) . fst.extendedGcd a $ b


addP :: Curve->Point->Point->Point
addP _ O O = O 
addP _ O p = p 
addP _ p O = p 
addP ( a, b, p ) ( P x1 y1 ) ( P x2 y2 ) 
    | x1 == x2 && mod ( y1 + y2 ) p == 0 = O 
    | otherwise = P x3 ( mod ( m * ( x1 - x3 ) - y1 ) p ) where
            m | x1 /= x2 = ( mod ( y2 - y1 ) p ) * modInv ( mod ( x2 - x1 ) p ) p
              | otherwise = ( 3 * x1 * x1 + a ) * modInv  ( 2*y1 ) p
            x3 = mod ( m * m - x1 - x2 ) p
让我们取曲线y^2=x^3+x+1模13。Z_13=[0,1,2,3,4,5,6,7,8,9,10,11,12]。Z_13的二次剩余(QR)=[0,1,3,4,9,10,12]和二次非剩余(QNR)=[2,5,6,7,8,11]。取x=0,我们得到y^2=1(mod 13),因为1在QR中,所以这个方程的解是1和12。我们得到两点(0,1)和(0,12)。把x=1,y^2=3(mod 13),这样x=1对应的点是(1,4)和(1,9)。把x=2,y^2=11(mod 13),11是QNR,所以我们没有解。当一个解存在时,它给我们两个点,这两个点都是模素数p(在这种情况下是13)的倒数。给定曲线上的总分为(0,1)、(0,12)、(1,4)、(1,9)、(4,2)、(4,11)、(5,1)、(5,12)、(7,0)、(8,1)、(8,12)、(10,6)、(10,7)、(11,2)、(11,11)。您可以尝试所有的点,看看哪一个生成整个组

 *Main>take 20 . iterate ( addP ( 1 , 1 , 13 )  ( P 7 0 ) ) $ ( P 7 0  )
 [P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O,P 7 0,O]
 *Main> take 20 . iterate ( addP ( 1 , 1 , 13 )  ( P 0 12 ) ) $ ( P 0 12  )
 [P 0 12,P 10 6,P 7 0,P 10 7,P 0 1,O,P 0 12,P 10 6,P 7 0,P 10 7,P 0 1,O,P 0 12,P 10 6,P 7 0,P 10 7,P 0 1,O,P 0 12,P 10 6]
回到Elgamal系统
1.Bob选择椭圆曲线E(a,b)而不是GF(p)或GF(2^n)。
2.Bob在曲线e1(x1,y1)上选择了一个点
3.Bob选择了一个整数d.
4.Bob计算e2(x2,y2)=d*e1(x1,y1)。
5.Bob宣布E(a,b,p)、e1(x1,y1)和e2(x2,y2)为您的公钥,并保留d为私钥

加密
Alice选择曲线上的点P作为她的纯文本。她选择了一个随机数r并计算C1=r*e1,C2=P+r*e2
解密。
Bob在接收C1和C2后,计算C2-d*C1=>P+r*e2-d*r*e1
=>P+r*d*e1-d*r*e1=>P

编辑:你是对的!如果使用生成器元素并不断添加它,则可以生成整个组。参见Christof Paar的讲座[1]。

[1]

还有什么额外的
|p
在那里做?