module Crypto.Cipher.Twofish
    ( Twofish128
    , Twofish192
    , Twofish256
    ) where

import Crypto.Cipher.Twofish.Primitive
import Crypto.Cipher.Types
import Crypto.Cipher.Utils

newtype Twofish128 = Twofish128 Twofish

instance Cipher Twofish128 where
    cipherName :: Twofish128 -> String
cipherName    Twofish128
_ = String
"Twofish128"
    cipherKeySize :: Twofish128 -> KeySizeSpecifier
cipherKeySize Twofish128
_ = Int -> KeySizeSpecifier
KeySizeFixed Int
16
    cipherInit :: forall key. ByteArray key => key -> CryptoFailable Twofish128
cipherInit key
key  = Twofish -> Twofish128
Twofish128 (Twofish -> Twofish128)
-> CryptoFailable Twofish -> CryptoFailable Twofish128
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (key -> CryptoFailable Twofish
forall key. ByteArray key => key -> CryptoFailable Twofish
initTwofish (key -> CryptoFailable Twofish)
-> CryptoFailable key -> CryptoFailable Twofish
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Twofish128 -> key -> CryptoFailable key
forall key cipher.
(ByteArrayAccess key, Cipher cipher) =>
cipher -> key -> CryptoFailable key
validateKeySize (Twofish128
forall a. HasCallStack => a
undefined :: Twofish128) key
key)

instance BlockCipher Twofish128 where
    blockSize :: Twofish128 -> Int
blockSize                 Twofish128
_ = Int
16
    ecbEncrypt :: forall ba. ByteArray ba => Twofish128 -> ba -> ba
ecbEncrypt (Twofish128 Twofish
key) = Twofish -> ba -> ba
forall ba. ByteArray ba => Twofish -> ba -> ba
encrypt Twofish
key
    ecbDecrypt :: forall ba. ByteArray ba => Twofish128 -> ba -> ba
ecbDecrypt (Twofish128 Twofish
key) = Twofish -> ba -> ba
forall ba. ByteArray ba => Twofish -> ba -> ba
decrypt Twofish
key

newtype Twofish192 = Twofish192 Twofish

instance Cipher Twofish192 where
    cipherName :: Twofish192 -> String
cipherName    Twofish192
_ = String
"Twofish192"
    cipherKeySize :: Twofish192 -> KeySizeSpecifier
cipherKeySize Twofish192
_ = Int -> KeySizeSpecifier
KeySizeFixed Int
24
    cipherInit :: forall key. ByteArray key => key -> CryptoFailable Twofish192
cipherInit key
key  = Twofish -> Twofish192
Twofish192 (Twofish -> Twofish192)
-> CryptoFailable Twofish -> CryptoFailable Twofish192
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (key -> CryptoFailable Twofish
forall key. ByteArray key => key -> CryptoFailable Twofish
initTwofish (key -> CryptoFailable Twofish)
-> CryptoFailable key -> CryptoFailable Twofish
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Twofish192 -> key -> CryptoFailable key
forall key cipher.
(ByteArrayAccess key, Cipher cipher) =>
cipher -> key -> CryptoFailable key
validateKeySize (Twofish192
forall a. HasCallStack => a
undefined :: Twofish192) key
key)

instance BlockCipher Twofish192 where
    blockSize :: Twofish192 -> Int
blockSize                 Twofish192
_ = Int
16
    ecbEncrypt :: forall ba. ByteArray ba => Twofish192 -> ba -> ba
ecbEncrypt (Twofish192 Twofish
key) = Twofish -> ba -> ba
forall ba. ByteArray ba => Twofish -> ba -> ba
encrypt Twofish
key
    ecbDecrypt :: forall ba. ByteArray ba => Twofish192 -> ba -> ba
ecbDecrypt (Twofish192 Twofish
key) = Twofish -> ba -> ba
forall ba. ByteArray ba => Twofish -> ba -> ba
decrypt Twofish
key

newtype Twofish256 = Twofish256 Twofish

instance Cipher Twofish256 where
    cipherName :: Twofish256 -> String
cipherName    Twofish256
_ = String
"Twofish256"
    cipherKeySize :: Twofish256 -> KeySizeSpecifier
cipherKeySize Twofish256
_ = Int -> KeySizeSpecifier
KeySizeFixed Int
32
    cipherInit :: forall key. ByteArray key => key -> CryptoFailable Twofish256
cipherInit key
key  = Twofish -> Twofish256
Twofish256 (Twofish -> Twofish256)
-> CryptoFailable Twofish -> CryptoFailable Twofish256
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (key -> CryptoFailable Twofish
forall key. ByteArray key => key -> CryptoFailable Twofish
initTwofish (key -> CryptoFailable Twofish)
-> CryptoFailable key -> CryptoFailable Twofish
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Twofish256 -> key -> CryptoFailable key
forall key cipher.
(ByteArrayAccess key, Cipher cipher) =>
cipher -> key -> CryptoFailable key
validateKeySize (Twofish256
forall a. HasCallStack => a
undefined :: Twofish256) key
key)

instance BlockCipher Twofish256 where
    blockSize :: Twofish256 -> Int
blockSize                 Twofish256
_ = Int
16
    ecbEncrypt :: forall ba. ByteArray ba => Twofish256 -> ba -> ba
ecbEncrypt (Twofish256 Twofish
key) = Twofish -> ba -> ba
forall ba. ByteArray ba => Twofish -> ba -> ba
encrypt Twofish
key
    ecbDecrypt :: forall ba. ByteArray ba => Twofish256 -> ba -> ba
ecbDecrypt (Twofish256 Twofish
key) = Twofish -> ba -> ba
forall ba. ByteArray ba => Twofish -> ba -> ba
decrypt Twofish
key