cryptocipher 0.2.11 → 0.2.12
raw patch · 3 files changed
+52/−13 lines, 3 filesPVP ok
version bump matches the API change (PVP)
API changes (from Hackage documentation)
+ Crypto.Cipher.DH: generateParams :: CryptoRandomGen g => g -> Int -> Integer -> Either GenError (Params, g)
+ Crypto.Cipher.DH: generatePrivate :: CryptoRandomGen g => g -> Int -> Either GenError (PrivateNumber, g)
Files
- Crypto/Cipher/DH.hs +17/−5
- Number/Prime.hs +34/−7
- cryptocipher.cabal +1/−1
Crypto/Cipher/DH.hs view
@@ -12,13 +12,17 @@ , PublicNumber , PrivateNumber , SharedKey+ , generateParams+ , generatePrivate , generatePublic , getShared ) where import Number.ModArithmetic (exponantiation_rtl_binary)-import Number.Prime+import Number.Prime (generateSafePrime)+import Number.Generate (generateOfSize) import Crypto.Random+import Control.Arrow (first) type Params = (Integer,Integer) {- P prime, G generator -} @@ -31,14 +35,22 @@ newtype SharedKey = SharedKey Integer {- S -} deriving (Show,Read,Eq,Enum,Real,Num,Ord) -generateParams :: CryptoRandomGen g => g -> Params-generateParams = undefined+-- | generate params from a specific generator (2 or 5 are common values)+-- we generate a safe prime (a prime number of the form 2p+1 where p is also prime)+generateParams :: CryptoRandomGen g => g -> Int -> Integer -> Either GenError (Params, g)+generateParams rng bits generator =+ either Left (Right . first (\p -> (p, generator))) $ generateSafePrime rng bits -generatePrivate :: CryptoRandomGen g => g -> PrivateNumber-generatePrivate rng = undefined+-- | generate a private number with no specific property+-- this number is usually called X in DH text.+generatePrivate :: CryptoRandomGen g => g -> Int -> Either GenError (PrivateNumber, g)+generatePrivate rng bits = either Left (Right . first PrivateNumber) $ generateOfSize rng bits +-- | generate a public number that is for the other party benefits.+-- this number is usually called Y in DH text. generatePublic :: Params -> PrivateNumber -> PublicNumber generatePublic (p,g) (PrivateNumber x) = PublicNumber $ exponantiation_rtl_binary g x p +-- | generate a shared key using our private number and the other party public number getShared :: Params -> PrivateNumber -> PublicNumber -> SharedKey getShared (p,_) (PrivateNumber x) (PublicNumber y) = SharedKey $ exponantiation_rtl_binary y x p
Number/Prime.hs view
@@ -1,6 +1,9 @@ module Number.Prime ( generatePrime+ , generateSafePrime , isProbablyPrime+ , findPrimeFrom+ , findPrimeFromWith , primalityTestNaive -- , primalityTestAKS , primalityTestMillerRabin@@ -21,18 +24,41 @@ | any (\p -> p `divides` n) (filter (< n) smallPrimes) = Right (False, rng) | otherwise = primalityTestMillerRabin rng 30 n +-- | generate a prime number of the required bitsize generatePrime :: CryptoRandomGen g => g -> Int -> Either GenError (Integer, g) generatePrime rng bits = case generateOfSize rng bits of Left err -> Left err Right (sp, rng') -> findPrimeFrom rng' sp -findPrimeFrom :: CryptoRandomGen g => g -> Integer -> Either GenError (Integer, g)-findPrimeFrom rng n- | even n = findPrimeFrom rng (n+1)+-- | generate a prime number of the form 2p+1 where p is also prime.+-- it is also know as a Sophie Germaine prime or safe prime.+--+-- The number of safe prime is significantly smaller to the number of prime,+-- as such it shouldn't be used if this number is supposed to be kept safe.+generateSafePrime :: CryptoRandomGen g => g -> Int -> Either GenError (Integer, g)+generateSafePrime rng bits = case generateOfSize rng bits of+ Left err -> Left err+ Right (sp, rng') -> case findPrimeFromWith rng' (\g i -> isProbablyPrime g (2*i+1)) (sp `div` 2) of+ Left err -> Left err+ Right (p, rng'') -> Right (2*p+1, rng'')++-- | find a prime from a starting point where the property hold.+findPrimeFromWith :: CryptoRandomGen g => g -> (g -> Integer -> Either GenError (Bool,g)) -> Integer -> Either GenError (Integer, g)+findPrimeFromWith rng prop n+ | even n = findPrimeFromWith rng prop (n+1) | otherwise = case isProbablyPrime rng n of Left err -> Left err- Right (isPPrime, rng') -> if isPPrime then Right (n, rng') else findPrimeFrom rng' (n+2)+ Right (False, rng') -> findPrimeFromWith rng' prop (n+2)+ Right (True, rng') ->+ case prop rng' n of+ Left err -> Left err+ Right (False, rng'') -> findPrimeFromWith rng'' prop (n+2)+ Right (True, rng'') -> Right (n, rng'') +-- | find a prime from a starting point with no specific property.+findPrimeFrom :: CryptoRandomGen g => g -> Integer -> Either GenError (Integer, g)+findPrimeFrom rng n = findPrimeFromWith rng (\g _ -> Right (True, g)) n+ -- | Miller Rabin algorithm return if the number is probably prime or composite. -- the tries parameter is the number of recursion, that determines the accuracy of the test. primalityTestMillerRabin :: CryptoRandomGen g => g -> Int -> Integer -> Either GenError (Bool, g)@@ -79,9 +105,9 @@ -- for p prime, the euler totient (# of coprime to n) is clearly n -1 totient = n-1 ubound = (fst $ sqrti totient) * (logi n)- logi n- | n == 0 = 0- | otherwise = 1 + logi (n `shiftR` 1)+ logi z+ | z == 0 = 0+ | otherwise = 1 + logi (z `shiftR` 1) -- | Test naively is integer is prime. -- while naive, we skip even number and stop iteration at i > sqrt(n)@@ -149,4 +175,5 @@ ] {-# INLINE divides #-}+divides :: Integer -> Integer -> Bool divides i n = n `mod` i == 0
cryptocipher.cabal view
@@ -1,5 +1,5 @@ Name: cryptocipher-Version: 0.2.11+Version: 0.2.12 Description: Symmetrical Block, Stream and PubKey Ciphers License: BSD3 License-file: LICENSE