module Crypto.Store.CMS.PEM
( readCMSFile
, readCMSFileFromMemory
, berToContentInfo
, pemToContentInfo
, writeCMSFile
, writeCMSFileToMemory
, contentInfoToDER
, contentInfoToPEM
) where
import qualified Data.ByteString as B
import Data.Maybe (catMaybes)
import Crypto.Store.CMS.Info
import Crypto.Store.CMS.Util
import Crypto.Store.Error
import Crypto.Store.PEM
readCMSFile :: FilePath -> IO [ContentInfo]
readCMSFile path = accumulate <$> readPEMs path
readCMSFileFromMemory :: B.ByteString -> [ContentInfo]
readCMSFileFromMemory = either (const []) accumulate . pemParseBS
accumulate :: [PEM] -> [ContentInfo]
accumulate = catMaybes . foldr (flip pemToContentInfo) []
berToContentInfo :: B.ByteString -> Either StoreError ContentInfo
berToContentInfo = decodeASN1Object
pemToContentInfo :: [Maybe ContentInfo] -> PEM -> [Maybe ContentInfo]
pemToContentInfo acc pem
| pemName pem `elem` names = decode (pemContent pem)
| otherwise = Nothing : acc
where
names = [ "CMS", "PKCS7" ]
decode bs =
case berToContentInfo bs of
Left _ -> Nothing : acc
Right info -> Just info : acc
writeCMSFile :: FilePath -> [ContentInfo] -> IO ()
writeCMSFile path = B.writeFile path . writeCMSFileToMemory
writeCMSFileToMemory :: [ContentInfo] -> B.ByteString
writeCMSFileToMemory = pemsWriteBS . map contentInfoToPEM
contentInfoToDER :: ContentInfo -> B.ByteString
contentInfoToDER = encodeASN1Object
contentInfoToPEM :: ContentInfo -> PEM
contentInfoToPEM info = PEM { pemName = "CMS", pemHeader = [], pemContent = bs}
where bs = contentInfoToDER info