Skip to content

Commit

Permalink
[ADP-322] Simplify functions within AES256CBC. (#4581)
Browse files Browse the repository at this point in the history
This PR:
- uses function
[`stripPrefix`](https://hackage.haskell.org/package/bytestring-0.12.1.0/docs/Data-ByteString.html#v:stripPrefix)
to replace usages of
[`splitAt`](https://hackage.haskell.org/package/bytestring-0.12.1.0/docs/Data-ByteString.html#v:splitAt)
that require further equality checks.
- defines a named constant `saltLengthBytes = 8` to avoid repetition of
the magic constant `8`.

## Issue

ADP-322
  • Loading branch information
paweljakubas committed May 8, 2024
2 parents c2d8bb9 + 49f2040 commit eda0d55
Showing 1 changed file with 22 additions and 24 deletions.
46 changes: 22 additions & 24 deletions lib/crypto-primitives/src/Cryptography/Cipher/AES256CBC.hs
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ encrypt
-- ^ Payload: must be a multiple of a block size, ie., 16 bytes.
-> Either CipherError ByteString
encrypt mode keyBytes ivBytes saltM msg
| any ((/= 8) . BS.length) saltM =
| any ((/= saltLengthBytes) . BS.length) saltM =
Left WrongSaltSize
| mode == WithoutPadding && BS.length msg `mod` 16 /= 0 =
Left WrongPayloadSize
Expand All @@ -129,9 +129,6 @@ encrypt mode keyBytes ivBytes saltM msg
WithoutPadding -> id
WithPadding -> PKCS7.pad

saltPrefix :: ByteString
saltPrefix = "Salted__"

-- | Decrypt using AES256 using CBC mode.
decrypt
:: CipherMode
Expand All @@ -147,30 +144,31 @@ decrypt mode key iv msg = do
when (mode == WithoutPadding && BS.length msg `mod` 16 /= 0) $
Left WrongPayloadSize
initedIV <- first FromCryptonite (createIV iv)
let (prefix,rest) = BS.splitAt 8 msg
let saltDetected = prefix == saltPrefix
if saltDetected then
second (, Just $ BS.take 8 rest) $
bimap FromCryptonite
(\c -> cbcDecrypt c initedIV (BS.drop 8 rest)) (initCipher key) >>=
unpad
else
second (, Nothing) $
bimap FromCryptonite
(\c -> cbcDecrypt c initedIV msg) (initCipher key) >>=
unpad
case BS.stripPrefix saltPrefix msg of
Just rest ->
second (, Just $ BS.take saltLengthBytes rest) $
bimap FromCryptonite
(\c -> cbcDecrypt c initedIV (BS.drop saltLengthBytes rest))
(initCipher key) >>=
unpad
Nothing ->
second (, Nothing) $
bimap FromCryptonite
(\c -> cbcDecrypt c initedIV msg) (initCipher key) >>=
unpad
where
unpad :: ByteString -> Either CipherError ByteString
unpad p = case mode of
WithoutPadding -> Right p
WithPadding -> maybeToEither EmptyPayload (PKCS7.unpad p)

saltLengthBytes :: Int
saltLengthBytes = 8

saltPrefix :: ByteString
saltPrefix = "Salted__"

getSaltFromEncrypted :: ByteString -> Maybe ByteString
getSaltFromEncrypted msg = do
when (BS.length msg < 32) Nothing
let (prefix,rest) = BS.splitAt 8 msg
let saltDetected = prefix == saltPrefix
if saltDetected then
Just $ BS.take 8 rest
else
Nothing
getSaltFromEncrypted msg
| BS.length msg < 32 = Nothing
| otherwise = BS.take saltLengthBytes <$> BS.stripPrefix saltPrefix msg

0 comments on commit eda0d55

Please sign in to comment.