diff options
Diffstat (limited to 'base64/base64.hs')
| -rw-r--r-- | base64/base64.hs | 45 |
1 files changed, 45 insertions, 0 deletions
diff --git a/base64/base64.hs b/base64/base64.hs new file mode 100644 index 0000000..13f12bb --- /dev/null +++ b/base64/base64.hs @@ -0,0 +1,45 @@ +-- +-- Miguel's Naive +-- Base64 Encoder -- Coded on a winter afterfnoon on 19th Feb 2018 A.D. +-- to fully understand base64 encoding and play with +-- haskell, which is always an indisputable pleasure. +-- +-- The following lines were written in full awareness +-- that 'libraries' for this purpose, which perform way +-- better, are in existence. +-- +-- Coded in big anger due to nick's stories about saving his binary +-- format, encrypted passwords in an ascii config file, featuring +-- strange letters and characters. +-- +-- Example Usage: echo "just testing" | stack runghc base64.hs | stack runghc base64 -- -d +-- (You can cross check with base64 / base64 -d) + +import System.Environment +import qualified Data.List.Split as T +import qualified Data.List as L +import qualified Data.Map.Strict as M +import qualified Data.ByteString.Lazy as B +import Text.Printf +import Data.Maybe +import Data.Char +import Control.Monad + +main = do args<-getArgs + if length args == 0 then go encode64 + else when (args!!0 == "-d") $ go decode64 + where go f = getContents >>= putStr.(++"\n").f + +fromBase64 x = (['A'..'Z']++['a'..'z']++['0'..'9']++['+','/']) !! x +mapBase64 = M.fromList $ map (\x-> (fromBase64 x,x)) [0..63] +binToDec = sum . map (2^) . L.findIndices (=='1') . reverse + +encode64 x = pad64 (length x) . map (fromBase64 . binToDec) . T.chunksOf 6 . + concat . map (printf "%08b" ) $ x ++ cycle "\000" + +decode64 x = map (chr . binToDec) . T.chunksOf 8 . + concat . map ( printf "%06b" . fromJust) . filter isJust . + map (flip M.lookup mapBase64) $ x + +pad64 l = (++(take m ((cycle "=")))) . take ((l+m)*3 `div` 2 -3-m) + where m = mod (3 - mod l 3) 3 |
