[PubKey] move ElGamal to use HashAlgorithm and ByteArrayAccess.
This commit is contained in:
parent
5d2b417854
commit
fdf735d4e2
@ -33,15 +33,15 @@ module Crypto.PubKey.ElGamal
|
|||||||
) where
|
) where
|
||||||
|
|
||||||
import Data.Maybe (fromJust)
|
import Data.Maybe (fromJust)
|
||||||
import Data.ByteString (ByteString)
|
|
||||||
import Crypto.Internal.Imports
|
import Crypto.Internal.Imports
|
||||||
|
import Crypto.Internal.ByteArray (ByteArrayAccess)
|
||||||
import Crypto.Number.ModArithmetic (expSafe, expFast, inverse)
|
import Crypto.Number.ModArithmetic (expSafe, expFast, inverse)
|
||||||
import Crypto.Number.Generate (generateMax)
|
import Crypto.Number.Generate (generateMax)
|
||||||
import Crypto.Number.Serialize (os2ip)
|
import Crypto.Number.Serialize (os2ip)
|
||||||
import Crypto.Number.Basic (gcde)
|
import Crypto.Number.Basic (gcde)
|
||||||
import Crypto.Random.Types
|
import Crypto.Random.Types
|
||||||
import Crypto.PubKey.HashDescr (HashFunction)
|
|
||||||
import Crypto.PubKey.DH (PrivateNumber(..), PublicNumber(..), Params(..), SharedKey(..))
|
import Crypto.PubKey.DH (PrivateNumber(..), PublicNumber(..), Params(..), SharedKey(..))
|
||||||
|
import Crypto.Hash
|
||||||
|
|
||||||
-- | ElGamal Signature
|
-- | ElGamal Signature
|
||||||
data Signature = Signature (Integer, Integer)
|
data Signature = Signature (Integer, Integer)
|
||||||
@ -95,18 +95,19 @@ decrypt (Params p _) (PrivateNumber a) (c1,c2) = (c2 * sm1) `mod` p
|
|||||||
-- with some appropriate value of k, the signature generation can fail,
|
-- with some appropriate value of k, the signature generation can fail,
|
||||||
-- and no signature is returned. User of this function need to retry
|
-- and no signature is returned. User of this function need to retry
|
||||||
-- with a different k value.
|
-- with a different k value.
|
||||||
signWith :: Integer -- ^ random number k, between 0 and p-1 and gcd(k,p-1)=1
|
signWith :: (ByteArrayAccess msg, HashAlgorithm hash)
|
||||||
|
=> Integer -- ^ random number k, between 0 and p-1 and gcd(k,p-1)=1
|
||||||
-> Params -- ^ DH params (p,g)
|
-> Params -- ^ DH params (p,g)
|
||||||
-> PrivateNumber -- ^ DH private key
|
-> PrivateNumber -- ^ DH private key
|
||||||
-> HashFunction -- ^ collision resistant hash function
|
-> hash -- ^ collision resistant hash algorithm
|
||||||
-> ByteString -- ^ message to sign
|
-> msg -- ^ message to sign
|
||||||
-> Maybe Signature
|
-> Maybe Signature
|
||||||
signWith k (Params p g) (PrivateNumber x) hashF msg
|
signWith k (Params p g) (PrivateNumber x) hashAlg msg
|
||||||
| k >= p-1 || d > 1 = Nothing -- gcd(k,p-1) is not 1
|
| k >= p-1 || d > 1 = Nothing -- gcd(k,p-1) is not 1
|
||||||
| s == 0 = Nothing
|
| s == 0 = Nothing
|
||||||
| otherwise = Just $ Signature (r,s)
|
| otherwise = Just $ Signature (r,s)
|
||||||
where r = expSafe g k p
|
where r = expSafe g k p
|
||||||
h = os2ip $ hashF msg
|
h = os2ip $ hashWith hashAlg msg
|
||||||
s = ((h - x*r) * kInv) `mod` (p-1)
|
s = ((h - x*r) * kInv) `mod` (p-1)
|
||||||
(kInv,_,d) = gcde k (p-1)
|
(kInv,_,d) = gcde k (p-1)
|
||||||
|
|
||||||
@ -116,28 +117,29 @@ signWith k (Params p g) (PrivateNumber x) hashF msg
|
|||||||
-- as the signature might fail, the function will automatically retry
|
-- as the signature might fail, the function will automatically retry
|
||||||
-- until a proper signature has been created.
|
-- until a proper signature has been created.
|
||||||
--
|
--
|
||||||
sign :: MonadRandom m
|
sign :: (ByteArrayAccess msg, HashAlgorithm hash, MonadRandom m)
|
||||||
=> Params -- ^ DH params (p,g)
|
=> Params -- ^ DH params (p,g)
|
||||||
-> PrivateNumber -- ^ DH private key
|
-> PrivateNumber -- ^ DH private key
|
||||||
-> HashFunction -- ^ collision resistant hash function
|
-> hash -- ^ collision resistant hash algorithm
|
||||||
-> ByteString -- ^ message to sign
|
-> msg -- ^ message to sign
|
||||||
-> m Signature
|
-> m Signature
|
||||||
sign params@(Params p _) priv hashF msg = do
|
sign params@(Params p _) priv hashAlg msg = do
|
||||||
k <- generateMax (p-1)
|
k <- generateMax (p-1)
|
||||||
case signWith k params priv hashF msg of
|
case signWith k params priv hashAlg msg of
|
||||||
Nothing -> sign params priv hashF msg
|
Nothing -> sign params priv hashAlg msg
|
||||||
Just sig -> return sig
|
Just sig -> return sig
|
||||||
|
|
||||||
-- | verify a signature
|
-- | verify a signature
|
||||||
verify :: Params
|
verify :: (ByteArrayAccess msg, HashAlgorithm hash)
|
||||||
|
=> Params
|
||||||
-> PublicNumber
|
-> PublicNumber
|
||||||
-> HashFunction
|
-> hash
|
||||||
-> ByteString
|
-> msg
|
||||||
-> Signature
|
-> Signature
|
||||||
-> Bool
|
-> Bool
|
||||||
verify (Params p g) (PublicNumber y) hashF msg (Signature (r,s))
|
verify (Params p g) (PublicNumber y) hashAlg msg (Signature (r,s))
|
||||||
| or [r <= 0,r >= p,s <= 0,s >= (p-1)] = False
|
| or [r <= 0,r >= p,s <= 0,s >= (p-1)] = False
|
||||||
| otherwise = lhs == rhs
|
| otherwise = lhs == rhs
|
||||||
where h = os2ip $ hashF msg
|
where h = os2ip $ hashWith hashAlg msg
|
||||||
lhs = expFast g h p
|
lhs = expFast g h p
|
||||||
rhs = (expFast y r p * expFast r s p) `mod` p
|
rhs = (expFast y r p * expFast r s p) `mod` p
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user