module Codec.MIME.QuotedPrintable
( decode
, encode
) where
import Data.Char
decode :: String -> String
decode :: String -> String
decode "" = ""
decode ('=':'\r':'\n':xs :: String
xs) = String -> String
decode String
xs
decode ('=':x1 :: Char
x1:x2 :: Char
x2:xs :: String
xs)
| Char -> Bool
isHexDigit Char
x1 Bool -> Bool -> Bool
&& Char -> Bool
isHexDigit Char
x2 =
Int -> Char
chr (Char -> Int
digitToInt Char
x1 Int -> Int -> Int
forall a. Num a => a -> a -> a
* 16 Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Char -> Int
digitToInt Char
x2) Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
decode String
xs
decode ('=':xs :: String
xs) = '='Char -> String -> String
forall a. a -> [a] -> [a]
:String -> String
decode String
xs
decode (x1 :: Char
x1:xs :: String
xs) = Char
x1Char -> String -> String
forall a. a -> [a] -> [a]
:String -> String
decode String
xs
encode :: String -> String
encode :: String -> String
encode xs :: String
xs = Int -> String -> String
encodeLength 0 String
xs
encodeLength :: Int -> String -> String
encodeLength :: Int -> String -> String
encodeLength _ "" = ""
encodeLength n :: Int
n (x :: Char
x:xs :: String
xs)
| Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
>= 72 = '='Char -> String -> String
forall a. a -> [a] -> [a]
:'\r'Char -> String -> String
forall a. a -> [a] -> [a]
:'\n'Char -> String -> String
forall a. a -> [a] -> [a]
:Int -> String -> String
encodeLength 0 (Char
xChar -> String -> String
forall a. a -> [a] -> [a]
:String
xs)
encodeLength _ ('=':xs :: String
xs)
= '='Char -> String -> String
forall a. a -> [a] -> [a]
:'3'Char -> String -> String
forall a. a -> [a] -> [a]
:'D'Char -> String -> String
forall a. a -> [a] -> [a]
:Int -> String -> String
encodeLength 0 String
xs
encodeLength n :: Int
n (x :: Char
x:xs :: String
xs)
| Int
ox Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
>= 0x100 = String -> String
forall a. HasCallStack => String -> a
error ("QuotedPrintable.encode: encountered > 8 bit character: " String -> String -> String
forall a. [a] -> [a] -> [a]
++ (Char, Int) -> String
forall a. Show a => a -> String
show (Char
x,Int
ox))
| Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
>= 72 = '='Char -> String -> String
forall a. a -> [a] -> [a]
:'\r'Char -> String -> String
forall a. a -> [a] -> [a]
:'\n'Char -> String -> String
forall a. a -> [a] -> [a]
:Int -> String -> String
encodeLength 0 (Char
xChar -> String -> String
forall a. a -> [a] -> [a]
:String
xs)
| Int
ox Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
>= 0x21 Bool -> Bool -> Bool
&& Int
ox Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= 0x7e = Char
x Char -> String -> String
forall a. a -> [a] -> [a]
: Int -> String -> String
encodeLength (Int
nInt -> Int -> Int
forall a. Num a => a -> a -> a
+1) String
xs
| Int
ox Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== 0x09 Bool -> Bool -> Bool
|| Int
ox Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== 0x20 = Char
x Char -> String -> String
forall a. a -> [a] -> [a]
: Int -> String -> String
encodeLength (Int
nInt -> Int -> Int
forall a. Num a => a -> a -> a
+1) String
xs
| Bool
otherwise = '='Char -> String -> String
forall a. a -> [a] -> [a]
:Int -> Char
showH (Int
ox Int -> Int -> Int
forall a. Integral a => a -> a -> a
`div` 0x10)Char -> String -> String
forall a. a -> [a] -> [a]
: Int -> Char
showH (Int
ox Int -> Int -> Int
forall a. Integral a => a -> a -> a
`mod` 0x10)Char -> String -> String
forall a. a -> [a] -> [a]
:Int -> String -> String
encodeLength (Int
nInt -> Int -> Int
forall a. Num a => a -> a -> a
+3) String
xs
where
ox :: Int
ox = Char -> Int
ord Char
x
showH :: Int -> Char
showH v :: Int
v
| Int
v Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
< 10 = Int -> Char
chr (Int
ord_0 Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
v)
| Bool
otherwise = Int -> Char
chr (Int
ord_A Int -> Int -> Int
forall a. Num a => a -> a -> a
+ (Int
vInt -> Int -> Int
forall a. Num a => a -> a -> a
-10))
ord_0 :: Int
ord_0 = Char -> Int
ord '0'
ord_A :: Int
ord_A = Char -> Int
ord 'A'