summaryrefslogtreecommitdiff
path: root/Feistel.hs
blob: 23914529c5a325ac9500c0e6b2ee6f7175eaaaee (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
{-# LANGUAGE UnboxedTuples #-}
module Feistel where

import qualified Data.ByteString as B
import qualified Data.ByteString.Lazy as L
import Data.Word
import Data.Bits
import Data.Binary
import System.Endian

toW32Pair :: B.ByteString -> ( Word32, Word32 )
toW32Pair b = let (x1, x2) = B.splitAt 4 b
                  w1 = decode32be x1
                  w2 = decode32be x2
              in ( w1,w2 )

fromW32Pair :: (Word32, Word32) -> B.ByteString
fromW32Pair (w1,w2)
    = let w1' = fromIntegral w1
          w2' = fromIntegral w2
          w = (w1' `shiftL` 32) .|. w2'
      in encode64be w


decode32be :: B.ByteString -> Word32
decode32be s = id $!
    (fromIntegral (s `B.index` 0) `shiftL` 24) .|.
    (fromIntegral (s `B.index` 1) `shiftL` 16) .|.
    (fromIntegral (s `B.index` 2) `shiftL`  8) .|.
    (fromIntegral (s `B.index` 3) )

encode64be :: Word64 -> B.ByteString
encode64be w = B.pack . map fromIntegral $
                [ (w `shiftR` 56) .&. 0xff
                , (w `shiftR` 48) .&. 0xff
                , (w `shiftR` 40) .&. 0xff
                , (w `shiftR` 32) .&. 0xff
                , (w `shiftR` 24) .&. 0xff
                , (w `shiftR` 16) .&. 0xff
                , (w `shiftR` 8) .&. 0xff
                , w .&. 0xff
                ]

splitWord32 :: Word32 -> (# Word8, Word8, Word8, Word8 #)
splitWord32 w = (# a,b,c,d #)
 where
    a = fromIntegral $ w `shiftR` 24
    b = fromIntegral $ w `shiftR` 16
    c = fromIntegral $ w `shiftR` 8
    d = fromIntegral $ w