-
Notifications
You must be signed in to change notification settings - Fork 17
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
GHC 9.6 compatibility by forking more packages #5
Comments
This is what in my mind. |
If we remove dependencies on Here is what I have so far, do you like this approach? diff --git a/Crypto/Cipher/Types/Utils.hs b/Crypto/Cipher/Types/Utils.hs
index 1185404..06e45d0 100644
--- a/Crypto/Cipher/Types/Utils.hs
+++ b/Crypto/Cipher/Types/Utils.hs
@@ -9,11 +9,10 @@
--
module Crypto.Cipher.Types.Utils where
-import Crypto.Internal.ByteArray (ByteArray)
-import qualified Crypto.Internal.ByteArray as B
+import qualified Data.ByteString as B
-- | Chunk some input byte array into @sz byte list of byte array.
-chunk :: ByteArray b => Int -> b -> [b]
+chunk :: Int -> B.ByteString -> [B.ByteString]
chunk sz bs = split bs
where split b | B.length b <= sz = [b]
| otherwise =
diff --git a/Crypto/Data/Padding.hs b/Crypto/Data/Padding.hs
index 902b132..e2735b8 100644
--- a/Crypto/Data/Padding.hs
+++ b/Crypto/Data/Padding.hs
@@ -14,8 +14,13 @@ module Crypto.Data.Padding
, unpad
) where
-import Data.ByteArray (ByteArray, Bytes)
-import qualified Data.ByteArray as B
+import Data.ByteString (ByteString)
+import qualified Data.ByteString as B
+import qualified Data.ByteString.Unsafe as BU
+import Foreign.Ptr (castPtr)
+import Foreign.C.Types (CInt)
+import System.IO.Unsafe (unsafePerformIO)
+import LibSodium.Bindings.Comparison (sodiumMemcmp)
-- | Format of padding
data Format =
@@ -25,7 +30,7 @@ data Format =
deriving (Show, Eq)
-- | Apply some pad to a bytearray
-pad :: ByteArray byteArray => Format -> byteArray -> byteArray
+pad :: Format -> ByteString -> ByteString
pad PKCS5 bin = pad (PKCS7 8) bin
pad (PKCS7 sz) bin = bin `B.append` paddingString
where
@@ -41,21 +46,26 @@ pad (ZERO sz) bin = bin `B.append` paddingString
m = len `mod` sz
len = B.length bin
+constTimingCompare :: ByteString -> ByteString -> CInt
+constTimingCompare p1 p2 = unsafePerformIO $ BU.unsafeUseAsCStringLen p1 $ \(c1, l1) ->
+ BU.unsafeUseAsCStringLen p2 $ \(c2, l2) ->
+ pure $ sodiumMemcmp (castPtr c1) (castPtr c2) (fromIntegral l1)
+
-- | Try to remove some padding from a bytearray.
-unpad :: ByteArray byteArray => Format -> byteArray -> Maybe byteArray
+unpad :: Format -> ByteString -> Maybe ByteString
unpad PKCS5 bin = unpad (PKCS7 8) bin
unpad (PKCS7 sz) bin
| len == 0 = Nothing
| (len `mod` sz) /= 0 = Nothing
| paddingSz < 1 || paddingSz > len = Nothing
- | paddingWitness `B.constEq` padding = Just content
+ | constTimingCompare paddingWitness padding == 0 = Just content
| otherwise = Nothing
where
len = B.length bin
paddingByte = B.index bin (len - 1)
paddingSz = fromIntegral paddingByte
(content, padding) = B.splitAt (len - paddingSz) bin
- paddingWitness = B.replicate paddingSz paddingByte :: Bytes
+ paddingWitness = B.replicate paddingSz paddingByte
unpad (ZERO sz) bin
| len == 0 = Nothing
| (len `mod` sz) /= 0 = Nothing
diff --git a/Crypto/Internal/ByteArray.hs b/Crypto/Internal/ByteArray.hs
index 57ab57a..592ceb2 100644
--- a/Crypto/Internal/ByteArray.hs
+++ b/Crypto/Internal/ByteArray.hs
@@ -10,30 +10,18 @@
{-# LANGUAGE BangPatterns #-}
{-# OPTIONS_HADDOCK hide #-}
module Crypto.Internal.ByteArray
- ( module Data.ByteArray
- , module Data.ByteArray.Mapping
- , module Data.ByteArray.Encoding
- , constAllZero
+ ( constAllZero
) where
-import Data.ByteArray
-import Data.ByteArray.Mapping
-import Data.ByteArray.Encoding
+import Data.ByteString
+import Data.ByteString.Unsafe
-import Data.Bits ((.|.))
-import Data.Word (Word8)
-import Foreign.Ptr (Ptr)
-import Foreign.Storable (peekByteOff)
+import LibSodium.Bindings.Comparison
+
+import Foreign.Ptr (castPtr)
import Crypto.Internal.Compat (unsafeDoIO)
-constAllZero :: ByteArrayAccess ba => ba -> Bool
-constAllZero b = unsafeDoIO $ withByteArray b $ \p -> loop p 0 0
- where
- loop :: Ptr b -> Int -> Word8 -> IO Bool
- loop p i !acc
- | i == len = return $! acc == 0
- | otherwise = do
- e <- peekByteOff p i
- loop p (i+1) (acc .|. e)
- len = Data.ByteArray.length b
+constAllZero :: ByteString -> Bool
+constAllZero b = unsafeDoIO $ unsafeUseAsCStringLen b $ \(p1, l1) ->
+ pure $ sodiumIsZero (castPtr p1) (fromIntegral l1) == 1
diff --git a/crypton.cabal b/crypton.cabal
index eec79fe..b0b313d 100644
--- a/crypton.cabal
+++ b/crypton.cabal
@@ -251,8 +251,7 @@ Library
Build-depends: base
Build-depends: bytestring
- , memory >= 0.14.18
- , basement >= 0.0.6
+ , libsodium-bindings
, ghc-prim
ghc-options: -Wall -fwarn-tabs -optc-O3
if os(linux)
@@ -462,7 +461,6 @@ Test-Suite test-crypton
XSalsa
Build-Depends: base >= 0 && < 10
, bytestring
- , memory
, tasty
, tasty-quickcheck
, tasty-hunit
@@ -479,7 +477,6 @@ Benchmark bench-crypton
Build-Depends: base
, bytestring
, deepseq
- , memory
, gauge
, random
, crypton
|
Yes. This is exactly the same as my middle plan. |
I don't know this area well. Doesn't |
It doesn't provide a constant-time comparison function. The I assume the same motivation applies for behavior of the
The |
FYI: Vincent has completely gone out from the Haskell community. |
I have been bitten by the dependency on basement. It fails to build on 32 bit architectures with current versions of ghc. Fix is easy but it won't be applied to basement. haskell-foundation/foundation#565 |
Since crypton is a new package, I was wondering whether it doesn't make sense to make big changes now, which is early in its development cycle. That would include stuff like e.g. changes in central dependencies, like basement and foundation.
It seems inconsistent to me to simply fork crypton off, while leaving the dependency on basement intact. Foundation is also suffering from lack of maintenance, and these issues could also affect crypton and warp.
For example, there is a bug in rotateL for Word256 with no reply from the maintainer:
And there is this incompatibility with GHC 9.6, which seems fairly foundational (excuse my pun). Since Vincent disagrees with the direction of GHC, it seems he refuses to make it compatible with newer GHC versions. Since crypton is a new fork, it would make sense to offer compatiblity with newer GHC. That way, another fork could be avoided. Would be nice if we could minimize the amount of forking.
EDIT: Note that the above incompatibility has been addressed, and that foundation-0.0.30 is in fact compatible with GHC 9.6 even though the linked issue was not marked as fixed.
The text was updated successfully, but these errors were encountered: