module Codec.Archive.Internal.Pack.Lazy ( entriesToBSL
                                        , entriesToBSL7zip
                                        , entriesToBSLzip
                                        , entriesToBSLCpio
                                        , entriesToBSLXar
                                        , entriesToBSLShar
                                        , entriesToBSLGeneral
                                        , entriesToIOChunks
                                        , packer
                                        , packFiles
                                        , packFilesZip
                                        , packFiles7zip
                                        , packFilesCpio
                                        , packFilesXar
                                        , packFilesShar
                                        ) where

import           Codec.Archive.Foreign
import           Codec.Archive.Internal.Monad
import           Codec.Archive.Internal.Pack
import           Codec.Archive.Internal.Pack.Common
import           Codec.Archive.Types
import           Control.Composition                ((.@))
import           Control.Monad.IO.Class             (liftIO)
import           Data.ByteString                    (packCStringLen)
import qualified Data.ByteString                    as BS
import qualified Data.ByteString.Lazy               as BSL
import qualified Data.DList                         as DL
import           Data.Foldable                      (toList)
import           Data.Functor                       (($>))
import           Data.IORef                         (modifyIORef', newIORef, readIORef)
import           Foreign.Concurrent                 (newForeignPtr)
import           Foreign.ForeignPtr                 (castForeignPtr, finalizeForeignPtr)
import           Foreign.Marshal.Alloc              (free, mallocBytes)
import           Foreign.Ptr                        (castPtr, freeHaskellFunPtr)
import           System.IO.Unsafe                   (unsafeDupablePerformIO)

packer :: (Traversable t) => (t (Entry FilePath BS.ByteString) -> BSL.ByteString) -> t FilePath -> IO BSL.ByteString
packer :: (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer = (FilePath -> IO (Entry FilePath ByteString))
-> t FilePath -> IO (t (Entry FilePath ByteString))
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
traverse FilePath -> IO (Entry FilePath ByteString)
mkEntry (t FilePath -> IO (t (Entry FilePath ByteString)))
-> ((t (Entry FilePath ByteString) -> ByteString)
    -> IO (t (Entry FilePath ByteString)) -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath
-> IO ByteString
forall b c a d. (b -> c) -> (a -> c -> d) -> a -> b -> d
.@ (t (Entry FilePath ByteString) -> ByteString)
-> IO (t (Entry FilePath ByteString)) -> IO ByteString
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap

-- | Pack files into a tar archive. This will be more efficient than
--
-- @BSL.writeFile fp . entriesToBSL@
--
-- @since 2.0.0.0
packFiles :: Traversable t
          => t FilePath -- ^ Filepaths relative to the current directory
          -> IO BSL.ByteString
packFiles :: t FilePath -> IO ByteString
packFiles = (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
forall (t :: * -> *).
Traversable t =>
(t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer t (Entry FilePath ByteString) -> ByteString
forall (t :: * -> *).
Foldable t =>
t (Entry FilePath ByteString) -> ByteString
entriesToBSL

-- | @since 2.0.0.0
packFilesZip :: Traversable t => t FilePath -> IO BSL.ByteString
packFilesZip :: t FilePath -> IO ByteString
packFilesZip = (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
forall (t :: * -> *).
Traversable t =>
(t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer t (Entry FilePath ByteString) -> ByteString
forall (t :: * -> *).
Foldable t =>
t (Entry FilePath ByteString) -> ByteString
entriesToBSLzip

-- | @since 2.0.0.0
packFiles7zip :: Traversable t => t FilePath -> IO BSL.ByteString
packFiles7zip :: t FilePath -> IO ByteString
packFiles7zip = (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
forall (t :: * -> *).
Traversable t =>
(t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer t (Entry FilePath ByteString) -> ByteString
forall (t :: * -> *).
Foldable t =>
t (Entry FilePath ByteString) -> ByteString
entriesToBSL7zip

-- | @since 2.2.3.0
packFilesCpio :: Traversable t => t FilePath -> IO BSL.ByteString
packFilesCpio :: t FilePath -> IO ByteString
packFilesCpio = (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
forall (t :: * -> *).
Traversable t =>
(t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer t (Entry FilePath ByteString) -> ByteString
forall (t :: * -> *).
Foldable t =>
t (Entry FilePath ByteString) -> ByteString
entriesToBSLCpio

-- | @since 2.2.4.0
packFilesXar :: Traversable t => t FilePath -> IO BSL.ByteString
packFilesXar :: t FilePath -> IO ByteString
packFilesXar = (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
forall (t :: * -> *).
Traversable t =>
(t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer t (Entry FilePath ByteString) -> ByteString
forall (t :: * -> *).
Foldable t =>
t (Entry FilePath ByteString) -> ByteString
entriesToBSLXar

-- | @since 3.0.0.0
packFilesShar :: Traversable t => t FilePath -> IO BSL.ByteString
packFilesShar :: t FilePath -> IO ByteString
packFilesShar = (t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
forall (t :: * -> *).
Traversable t =>
(t (Entry FilePath ByteString) -> ByteString)
-> t FilePath -> IO ByteString
packer t (Entry FilePath ByteString) -> ByteString
forall (t :: * -> *).
Foldable t =>
t (Entry FilePath ByteString) -> ByteString
entriesToBSLShar

-- | @since 1.0.5.0
entriesToBSLzip :: Foldable t => t (Entry FilePath BS.ByteString) -> BSL.ByteString
entriesToBSLzip :: t (Entry FilePath ByteString) -> ByteString
entriesToBSLzip = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString)
-> (t (Entry FilePath ByteString) -> IO ByteString)
-> t (Entry FilePath ByteString)
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ArchiveM ByteString -> IO ByteString
forall a. ArchiveM a -> IO a
noFail (ArchiveM ByteString -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ArchiveM ByteString)
-> t (Entry FilePath ByteString)
-> IO ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
archiveWriteSetFormatZip
{-# NOINLINE entriesToBSLzip #-}

-- | @since 1.0.5.0
entriesToBSL7zip :: Foldable t => t (Entry FilePath BS.ByteString) -> BSL.ByteString
entriesToBSL7zip :: t (Entry FilePath ByteString) -> ByteString
entriesToBSL7zip = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString)
-> (t (Entry FilePath ByteString) -> IO ByteString)
-> t (Entry FilePath ByteString)
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ArchiveM ByteString -> IO ByteString
forall a. ArchiveM a -> IO a
noFail (ArchiveM ByteString -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ArchiveM ByteString)
-> t (Entry FilePath ByteString)
-> IO ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
archiveWriteSetFormat7zip
{-# NOINLINE entriesToBSL7zip #-}

-- | @since 2.2.3.0
entriesToBSLCpio :: Foldable t => t (Entry FilePath BS.ByteString) -> BSL.ByteString
entriesToBSLCpio :: t (Entry FilePath ByteString) -> ByteString
entriesToBSLCpio = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString)
-> (t (Entry FilePath ByteString) -> IO ByteString)
-> t (Entry FilePath ByteString)
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ArchiveM ByteString -> IO ByteString
forall a. ArchiveM a -> IO a
noFail (ArchiveM ByteString -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ArchiveM ByteString)
-> t (Entry FilePath ByteString)
-> IO ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
archiveWriteSetFormatCpio
{-# NOINLINE entriesToBSLCpio #-}

-- | Won't work when built with @-system-libarchive@ or when libarchive is not
-- built with zlib support.
--
-- @since 2.2.4.0
entriesToBSLXar :: Foldable t => t (Entry FilePath BS.ByteString) -> BSL.ByteString
entriesToBSLXar :: t (Entry FilePath ByteString) -> ByteString
entriesToBSLXar = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString)
-> (t (Entry FilePath ByteString) -> IO ByteString)
-> t (Entry FilePath ByteString)
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ArchiveM ByteString -> IO ByteString
forall a. ArchiveM a -> IO a
noFail (ArchiveM ByteString -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ArchiveM ByteString)
-> t (Entry FilePath ByteString)
-> IO ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
archiveWriteSetFormatXar
{-# NOINLINE entriesToBSLXar #-}

-- | @since 3.0.0.0
entriesToBSLShar :: Foldable t => t (Entry FilePath BS.ByteString) -> BSL.ByteString
entriesToBSLShar :: t (Entry FilePath ByteString) -> ByteString
entriesToBSLShar = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString)
-> (t (Entry FilePath ByteString) -> IO ByteString)
-> t (Entry FilePath ByteString)
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ArchiveM ByteString -> IO ByteString
forall a. ArchiveM a -> IO a
noFail (ArchiveM ByteString -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ArchiveM ByteString)
-> t (Entry FilePath ByteString)
-> IO ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
archiveWriteSetFormatShar
{-# NOINLINE entriesToBSLShar #-}

-- | In general, this will be more efficient than 'entriesToBS'
--
-- @since 1.0.5.0
entriesToBSL :: Foldable t => t (Entry FilePath BS.ByteString) -> BSL.ByteString
entriesToBSL :: t (Entry FilePath ByteString) -> ByteString
entriesToBSL = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString)
-> (t (Entry FilePath ByteString) -> IO ByteString)
-> t (Entry FilePath ByteString)
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ArchiveM ByteString -> IO ByteString
forall a. ArchiveM a -> IO a
noFail (ArchiveM ByteString -> IO ByteString)
-> (t (Entry FilePath ByteString) -> ArchiveM ByteString)
-> t (Entry FilePath ByteString)
-> IO ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
archiveWriteSetFormatPaxRestricted
{-# NOINLINE entriesToBSL #-}

entriesToIOChunks :: Foldable t
                  => (ArchivePtr -> IO ArchiveResult) -- ^ Action to set format of archive
                  -> t (Entry FilePath BS.ByteString)
                  -> (BS.ByteString -> IO ()) -- ^ 'IO' Action to process the chunks
                  -> ArchiveM ()
entriesToIOChunks :: (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString)
-> (ByteString -> IO ())
-> ArchiveM ()
entriesToIOChunks ArchivePtr -> IO ArchiveResult
modifier t (Entry FilePath ByteString)
hsEntries' ByteString -> IO ()
chunkAct = do
    Ptr Archive
preA <- IO (Ptr Archive) -> ExceptT ArchiveResult IO (Ptr Archive)
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO IO (Ptr Archive)
archiveWriteNew
    FunPtr (ArchiveOpenCallbackRaw Any)
oc <- IO (FunPtr (ArchiveOpenCallbackRaw Any))
-> ExceptT ArchiveResult IO (FunPtr (ArchiveOpenCallbackRaw Any))
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO (FunPtr (ArchiveOpenCallbackRaw Any))
 -> ExceptT ArchiveResult IO (FunPtr (ArchiveOpenCallbackRaw Any)))
-> IO (FunPtr (ArchiveOpenCallbackRaw Any))
-> ExceptT ArchiveResult IO (FunPtr (ArchiveOpenCallbackRaw Any))
forall a b. (a -> b) -> a -> b
$ ArchiveOpenCallback Any -> IO (FunPtr (ArchiveOpenCallbackRaw Any))
forall a.
ArchiveOpenCallback a -> IO (FunPtr (ArchiveOpenCallbackRaw a))
mkOpenCallback ArchiveOpenCallback Any
forall (f :: * -> *) p p.
Applicative f =>
p -> p -> f ArchiveResult
doNothing
    FunPtr (ArchiveWriteCallback Any CChar)
wc <- IO (FunPtr (ArchiveWriteCallback Any CChar))
-> ExceptT
     ArchiveResult IO (FunPtr (ArchiveWriteCallback Any CChar))
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO (FunPtr (ArchiveWriteCallback Any CChar))
 -> ExceptT
      ArchiveResult IO (FunPtr (ArchiveWriteCallback Any CChar)))
-> IO (FunPtr (ArchiveWriteCallback Any CChar))
-> ExceptT
     ArchiveResult IO (FunPtr (ArchiveWriteCallback Any CChar))
forall a b. (a -> b) -> a -> b
$ ArchiveWriteCallback Any CChar
-> IO (FunPtr (ArchiveWriteCallback Any CChar))
forall a b.
ArchiveWriteCallback a b -> IO (FunPtr (ArchiveWriteCallback a b))
mkWriteCallback ArchiveWriteCallback Any CChar
forall b a p p.
(Integral b, Integral a) =>
p -> p -> Ptr CChar -> a -> IO b
chunkHelper
    FunPtr (ArchiveOpenCallbackRaw Any)
cc <- IO (FunPtr (ArchiveOpenCallbackRaw Any))
-> ExceptT ArchiveResult IO (FunPtr (ArchiveOpenCallbackRaw Any))
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO (FunPtr (ArchiveOpenCallbackRaw Any))
 -> ExceptT ArchiveResult IO (FunPtr (ArchiveOpenCallbackRaw Any)))
-> IO (FunPtr (ArchiveOpenCallbackRaw Any))
-> ExceptT ArchiveResult IO (FunPtr (ArchiveOpenCallbackRaw Any))
forall a b. (a -> b) -> a -> b
$ ArchiveOpenCallback Any -> IO (FunPtr (ArchiveOpenCallbackRaw Any))
forall a.
ArchiveOpenCallback a -> IO (FunPtr (ArchiveOpenCallbackRaw a))
mkCloseCallback (\Ptr Archive
_ Ptr Any
ptr -> FunPtr (ArchiveOpenCallbackRaw Any) -> IO ()
forall a. FunPtr a -> IO ()
freeHaskellFunPtr FunPtr (ArchiveOpenCallbackRaw Any)
oc IO () -> IO () -> IO ()
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> FunPtr (ArchiveWriteCallback Any CChar) -> IO ()
forall a. FunPtr a -> IO ()
freeHaskellFunPtr FunPtr (ArchiveWriteCallback Any CChar)
wc IO () -> IO () -> IO ()
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> Ptr Any -> IO ()
forall a. Ptr a -> IO ()
free Ptr Any
ptr IO () -> ArchiveResult -> IO ArchiveResult
forall (f :: * -> *) a b. Functor f => f a -> b -> f b
$> ArchiveResult
ArchiveOk)
    ArchivePtr
a <- IO ArchivePtr -> ExceptT ArchiveResult IO ArchivePtr
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO ArchivePtr -> ExceptT ArchiveResult IO ArchivePtr)
-> IO ArchivePtr -> ExceptT ArchiveResult IO ArchivePtr
forall a b. (a -> b) -> a -> b
$ ForeignPtr Any -> ArchivePtr
forall a b. ForeignPtr a -> ForeignPtr b
castForeignPtr (ForeignPtr Any -> ArchivePtr)
-> IO (ForeignPtr Any) -> IO ArchivePtr
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Ptr Any -> IO () -> IO (ForeignPtr Any)
forall a. Ptr a -> IO () -> IO (ForeignPtr a)
newForeignPtr (Ptr Archive -> Ptr Any
forall a b. Ptr a -> Ptr b
castPtr Ptr Archive
preA) (Ptr Archive -> IO CInt
archiveFree Ptr Archive
preA IO CInt -> IO () -> IO ()
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> FunPtr (ArchiveOpenCallbackRaw Any) -> IO ()
forall a. FunPtr a -> IO ()
freeHaskellFunPtr FunPtr (ArchiveOpenCallbackRaw Any)
cc)
    Ptr Any
nothingPtr <- IO (Ptr Any) -> ExceptT ArchiveResult IO (Ptr Any)
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO (Ptr Any) -> ExceptT ArchiveResult IO (Ptr Any))
-> IO (Ptr Any) -> ExceptT ArchiveResult IO (Ptr Any)
forall a b. (a -> b) -> a -> b
$ Int -> IO (Ptr Any)
forall a. Int -> IO (Ptr a)
mallocBytes Int
0
    IO ArchiveResult -> ArchiveM ()
ignore (IO ArchiveResult -> ArchiveM ())
-> IO ArchiveResult -> ArchiveM ()
forall a b. (a -> b) -> a -> b
$ ArchivePtr -> IO ArchiveResult
modifier ArchivePtr
a
    IO ArchiveResult -> ArchiveM ()
handle (IO ArchiveResult -> ArchiveM ())
-> IO ArchiveResult -> ArchiveM ()
forall a b. (a -> b) -> a -> b
$ ArchivePtr
-> Ptr Any
-> FunPtr (ArchiveOpenCallbackRaw Any)
-> FunPtr (ArchiveWriteCallback Any CChar)
-> FunPtr (ArchiveOpenCallbackRaw Any)
-> IO ArchiveResult
forall a b.
ArchivePtr
-> Ptr a
-> FunPtr (ArchiveOpenCallbackRaw a)
-> FunPtr (ArchiveWriteCallback a b)
-> FunPtr (ArchiveOpenCallbackRaw a)
-> IO ArchiveResult
archiveWriteOpen ArchivePtr
a Ptr Any
nothingPtr FunPtr (ArchiveOpenCallbackRaw Any)
oc FunPtr (ArchiveWriteCallback Any CChar)
wc FunPtr (ArchiveOpenCallbackRaw Any)
cc
    ArchivePtr -> t (Entry FilePath ByteString) -> ArchiveM ()
forall (t :: * -> *).
Foldable t =>
ArchivePtr -> t (Entry FilePath ByteString) -> ArchiveM ()
packEntries ArchivePtr
a t (Entry FilePath ByteString)
hsEntries'
    IO () -> ArchiveM ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> ArchiveM ()) -> IO () -> ArchiveM ()
forall a b. (a -> b) -> a -> b
$ ArchivePtr -> IO ()
forall a. ForeignPtr a -> IO ()
finalizeForeignPtr ArchivePtr
a

    where doNothing :: p -> p -> f ArchiveResult
doNothing p
_ p
_ = ArchiveResult -> f ArchiveResult
forall (f :: * -> *) a. Applicative f => a -> f a
pure ArchiveResult
ArchiveOk
          chunkHelper :: p -> p -> Ptr CChar -> a -> IO b
chunkHelper p
_ p
_ Ptr CChar
bufPtr a
sz = do
            let bytesRead :: b
bytesRead = b -> b -> b
forall a. Ord a => a -> a -> a
min (a -> b
forall a b. (Integral a, Num b) => a -> b
fromIntegral a
sz) (b
32 b -> b -> b
forall a. Num a => a -> a -> a
* b
1024)
            ByteString
bs <- CStringLen -> IO ByteString
packCStringLen (Ptr CChar
bufPtr, b -> Int
forall a b. (Integral a, Num b) => a -> b
fromIntegral b
bytesRead)
            ByteString -> IO ()
chunkAct ByteString
bs
            b -> IO b
forall (f :: * -> *) a. Applicative f => a -> f a
pure b
bytesRead

entriesToBSLGeneral :: Foldable t => (ArchivePtr -> IO ArchiveResult) -> t (Entry FilePath BS.ByteString) -> ArchiveM BSL.ByteString
entriesToBSLGeneral :: (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString) -> ArchiveM ByteString
entriesToBSLGeneral ArchivePtr -> IO ArchiveResult
modifier t (Entry FilePath ByteString)
hsEntries' = do
    IORef (DList ByteString)
preRef <- IO (IORef (DList ByteString))
-> ExceptT ArchiveResult IO (IORef (DList ByteString))
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO (IORef (DList ByteString))
 -> ExceptT ArchiveResult IO (IORef (DList ByteString)))
-> IO (IORef (DList ByteString))
-> ExceptT ArchiveResult IO (IORef (DList ByteString))
forall a b. (a -> b) -> a -> b
$ DList ByteString -> IO (IORef (DList ByteString))
forall a. a -> IO (IORef a)
newIORef DList ByteString
forall a. Monoid a => a
mempty
    let chunkAct :: ByteString -> IO ()
chunkAct = IORef (DList ByteString) -> ByteString -> IO ()
forall a. IORef (DList a) -> a -> IO ()
writeBSL IORef (DList ByteString)
preRef
    (ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString)
-> (ByteString -> IO ())
-> ArchiveM ()
forall (t :: * -> *).
Foldable t =>
(ArchivePtr -> IO ArchiveResult)
-> t (Entry FilePath ByteString)
-> (ByteString -> IO ())
-> ArchiveM ()
entriesToIOChunks ArchivePtr -> IO ArchiveResult
modifier t (Entry FilePath ByteString)
hsEntries' ByteString -> IO ()
chunkAct
    [ByteString] -> ByteString
BSL.fromChunks ([ByteString] -> ByteString)
-> (DList ByteString -> [ByteString])
-> DList ByteString
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DList ByteString -> [ByteString]
forall (t :: * -> *) a. Foldable t => t a -> [a]
toList (DList ByteString -> ByteString)
-> ExceptT ArchiveResult IO (DList ByteString)
-> ArchiveM ByteString
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> IO (DList ByteString)
-> ExceptT ArchiveResult IO (DList ByteString)
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IORef (DList ByteString) -> IO (DList ByteString)
forall a. IORef a -> IO a
readIORef IORef (DList ByteString)
preRef)

    where writeBSL :: IORef (DList a) -> a -> IO ()
writeBSL IORef (DList a)
bsRef a
chunk =
            IORef (DList a) -> (DList a -> DList a) -> IO ()
forall a. IORef a -> (a -> a) -> IO ()
modifyIORef' IORef (DList a)
bsRef (DList a -> a -> DList a
forall a. DList a -> a -> DList a
`DL.snoc` a
chunk)