@@ -23,20 +23,14 @@ module Handle.ReadWrite
23 (allBenchmarks)
23 (allBenchmarks)
26−import Control.Exception (SomeException)
27−import System.IO (Handle, hClose, hPutChar)
26+import System.IO (Handle)
28import Prelude hiding (last, length)
27import Prelude hiding (last, length)
29import Streamly.Internal.Data.Array.Storable.Foreign.Types (defaultChunkSize)
28import Streamly.Internal.Data.Array.Storable.Foreign.Types (defaultChunkSize)
31−import qualified Streamly.Data.Fold as FL
32−import qualified Streamly.Unicode.Stream as SS
33import qualified Streamly.FileSystem.Handle as FH
30import qualified Streamly.FileSystem.Handle as FH
34import qualified Streamly.Internal.Data.Unfold as IUF
31import qualified Streamly.Internal.Data.Unfold as IUF
35−import qualified Streamly.Internal.Unicode.Stream as IUS
36import qualified Streamly.Internal.FileSystem.Handle as IFH
32import qualified Streamly.Internal.FileSystem.Handle as IFH
37import qualified Streamly.Internal.Memory.ArrayStream as AS
33import qualified Streamly.Internal.Memory.ArrayStream as AS
38−import qualified Streamly.Internal.Unicode.Array.Char as IUA
39−import qualified Streamly.Internal.Data.Stream.IsStream as IP
40import qualified Streamly.Data.Array.Storable.Foreign as A
34import qualified Streamly.Data.Array.Storable.Foreign as A
41import qualified Streamly.Prelude as S
35import qualified Streamly.Prelude as S
@@ -69,19 +63,6 @@ inspect $ hasNoTypeClasses 'copyChunks
69inspect $ 'copyChunks `hasNoType` ''Step
63inspect $ 'copyChunks `hasNoType` ''Step
73−copyCodecUtf8ArraysLenient :: Handle -> Handle -> IO ()
74−copyCodecUtf8ArraysLenient inh outh =
75− S.fold (FH.write outh)
77− $ IUS.decodeUtf8Arrays
81−inspect $ hasNoTypeClasses 'copyCodecUtf8ArraysLenient
82−-- inspect $ 'copyCodecUtf8ArraysLenient `hasNoType` ''Step
85o_1_space_copy_chunked :: BenchEnv -> [Benchmark]
66o_1_space_copy_chunked :: BenchEnv -> [Benchmark]
86o_1_space_copy_chunked env =
67o_1_space_copy_chunked env =
87 [ bgroup "copy/toChunks"
68 [ bgroup "copy/toChunks"
@@ -89,8 +70,6 @@ o_1_space_copy_chunked env =
89 copyChunks inH (nullH env)
70 copyChunks inH (nullH env)
90 , mkBench "raw" env $ \inH outH ->
71 , mkBench "raw" env $ \inH outH ->
91 copyChunks inH outH
72 copyChunks inH outH
92− , mkBenchSmall "decodeEncodeUtf8Lenient" env $ \inH outH ->
93− copyCodecUtf8ArraysLenient inH outH
@@ -111,70 +90,6 @@ inspect $ 'copyStream `hasNoType` ''AT.ArrayUnsafe -- FH.write/writeNUnsafe
111inspect $ 'copyStream `hasNoType` ''Strict.Tuple3' -- FH.write/lchunksOf
90inspect $ 'copyStream `hasNoType` ''Strict.Tuple3' -- FH.write/lchunksOf
114−-- | Copy file (encodeLatin1')
115−copyStreamLatin1' :: Handle -> Handle -> IO ()
116−copyStreamLatin1' inh outh =
117− S.fold (FH.write outh)
120− $ S.unfold FH.read inh
123−inspect $ hasNoTypeClasses 'copyStreamLatin1'
124−inspect $ 'copyStreamLatin1' `hasNoType` ''Step
125−inspect $ 'copyStreamLatin1' `hasNoType` ''IUF.ConcatState -- FH.read/UF.concat
126−inspect $ 'copyStreamLatin1' `hasNoType` ''A.ReadUState -- FH.read/A.read
127−inspect $ 'copyStreamLatin1' `hasNoType` ''AT.ArrayUnsafe -- FH.write/writeNUnsafe
128−inspect $ 'copyStreamLatin1' `hasNoType` ''Strict.Tuple3' -- FH.write/lchunksOf
131−-- | Copy file (encodeLatin1)
132−copyStreamLatin1 :: Handle -> Handle -> IO ()
133−copyStreamLatin1 inh outh =
134− S.fold (FH.write outh)
137− $ S.unfold FH.read inh
140−inspect $ hasNoTypeClasses 'copyStreamLatin1
141−inspect $ 'copyStreamLatin1 `hasNoType` ''Step
142−inspect $ 'copyStreamLatin1 `hasNoType` ''IUF.ConcatState -- FH.read/UF.concat
143−inspect $ 'copyStreamLatin1 `hasNoType` ''A.ReadUState -- FH.read/A.read
144−inspect $ 'copyStreamLatin1 `hasNoType` ''AT.ArrayUnsafe -- FH.write/writeNUnsafe
145−inspect $ 'copyStreamLatin1 `hasNoType` ''Strict.Tuple3' -- FH.write/lchunksOf
149−_copyStreamUtf8' :: Handle -> Handle -> IO ()
150−_copyStreamUtf8' inh outh =
151− S.fold (FH.write outh)
154− $ S.unfold FH.read inh
157−inspect $ hasNoTypeClasses '_copyStreamUtf8'
158−-- inspect $ '_copyStreamUtf8 `hasNoType` ''Step
159−-- inspect $ '_copyStreamUtf8 `hasNoType` ''AT.FlattenState
160−-- inspect $ '_copyStreamUtf8 `hasNoType` ''D.ConcatMapUState
164−copyStreamUtf8 :: Handle -> Handle -> IO ()
165−copyStreamUtf8 inh outh =
166− S.fold (FH.write outh)
169− $ S.unfold FH.read inh
172−inspect $ hasNoTypeClasses 'copyStreamUtf8
173−-- inspect $ 'copyStreamUtf8Lax `hasNoType` ''Step
174−-- inspect $ 'copyStreamUtf8Lax `hasNoType` ''AT.FlattenState
175−-- inspect $ 'copyStreamUtf8Lax `hasNoType` ''D.ConcatMapUState
178o_1_space_copy_read :: BenchEnv -> [Benchmark]
93o_1_space_copy_read :: BenchEnv -> [Benchmark]
179o_1_space_copy_read env =
94o_1_space_copy_read env =
180 [ bgroup "copy/read"
95 [ bgroup "copy/read"
@@ -182,17 +97,6 @@ o_1_space_copy_read env =
182 copyStream inh (nullH env)
97 copyStream inh (nullH env)
183 , mkBench "rawToFile" env $ \inh outh ->
98 , mkBench "rawToFile" env $ \inh outh ->
184 copyStream inh outh
99 copyStream inh outh
185− -- This needs an ascii file, as decode just errors out.
186− , mkBench "SS.encodeLatin1' . SS.decodeLatin1" env $ \inh outh ->
187− copyStreamLatin1' inh outh
188− , mkBench "SS.encodeLatin1 . SS.decodeLatin1" env $ \inh outh ->
189− copyStreamLatin1 inh outh
191− , mkBench "copyUtf8" env $ \inh outh ->
192− _copyStreamUtf8' inh outh
194− , mkBenchSmall "SS.encodeUtf8 . SS.decodeUtf8Lax" env $ \inh outh ->
195− copyStreamUtf8 inh outh
@@ -344,120 +248,6 @@ o_1_space_copy_toChunks_group_ungroup env =
347−-------------------------------------------------------------------------------
348−-- copy with group/ungroup transformations
349−-------------------------------------------------------------------------------
351−linesUnlinesCopy :: Handle -> Handle -> IO ()
352−linesUnlinesCopy inh outh =
353− S.fold (FH.write outh)
355− $ IUS.unlines IUF.fromList
356− $ S.splitOnSuffix (== '\n') FL.toList
358− $ S.unfold FH.read inh
360−linesUnlinesArrayWord8Copy :: Handle -> Handle -> IO ()
361−linesUnlinesArrayWord8Copy inh outh =
362− S.fold (FH.write outh)
363− $ IP.interposeSuffix 10 A.read
364− $ S.splitOnSuffix (== 10) A.write
365− $ S.unfold FH.read inh
367−-- XXX splitSuffixOn requires -funfolding-use-threshold=150 for better fusion
368−-- | Lines and unlines
369−linesUnlinesArrayCharCopy :: Handle -> Handle -> IO ()
370−linesUnlinesArrayCharCopy inh outh =
371− S.fold (FH.write outh)
376− $ S.unfold FH.read inh
379−inspect $ hasNoTypeClassesExcept 'linesUnlinesArrayCharCopy [''Storable]
380−-- inspect $ 'linesUnlinesArrayCharCopy `hasNoType` ''Step
383−-- XXX to write this we need to be able to map decodeUtf8 on the A.read fold.
384−-- For that we have to write decodeUtf8 as a Pipe.
386−{-# INLINE linesUnlinesArrayUtf8Copy #-}
387−linesUnlinesArrayUtf8Copy :: Handle -> Handle -> IO ()
388−linesUnlinesArrayUtf8Copy inh outh =
389− S.fold (FH.write outh)
391− $ IP.intercalate (A.fromList [10]) (pipe SS.decodeUtf8P A.read)
392− $ S.splitOnSuffix (== '\n') (IFL.lmap SS.encodeUtf8' A.write)
394− $ S.unfold FH.read inh
397−-- | Word, unwords and copy
398−wordsUnwordsCopyWord8 :: Handle -> Handle -> IO ()
399−wordsUnwordsCopyWord8 inh outh =
400− S.fold (FH.write outh)
401− $ IP.interposeSuffix 32 IUF.fromList
402− $ S.wordsBy isSp FL.toList
403− $ S.unfold FH.read inh
406−inspect $ hasNoTypeClasses 'wordsUnwordsCopyWord8
407−-- inspect $ 'wordsUnwordsCopyWord8 `hasNoType` ''Step
410−-- | Word, unwords and copy
411−wordsUnwordsCopy :: Handle -> Handle -> IO ()
412−wordsUnwordsCopy inh outh =
413− S.fold (FH.write outh)
415− $ IUS.unwords IUF.fromList
416− -- XXX This pipeline does not fuse with wordsBy but fuses with splitOn
417− -- with -funfolding-use-threshold=300. With wordsBy it does not fuse
418− -- even with high limits for inlining and spec-constr ghc options. With
419− -- -funfolding-use-threshold=400 it performs pretty well and there
420− -- is no evidence in the core that a join point involving Step
421− -- constructors is not getting inlined. Not being able to fuse at all in
422− -- this case could be an unknown issue, need more investigation.
423− $ S.wordsBy isSpace FL.toList
424− -- -- $ S.splitOn isSpace FL.toList
426− $ S.unfold FH.read inh
429−-- inspect $ hasNoTypeClasses 'wordsUnwordsCopy
430−-- inspect $ 'wordsUnwordsCopy `hasNoType` ''Step
433−{-# NOINLINE wordsUnwordsCharArrayCopy #-}
434−wordsUnwordsCharArrayCopy :: Handle -> Handle -> IO ()
435−wordsUnwordsCharArrayCopy inh outh =
436− S.fold (FH.write outh)
441− $ S.unfold FH.read inh
443−o_1_space_copy_read_group_ungroup :: BenchEnv -> [Benchmark]
444−o_1_space_copy_read_group_ungroup env =
445− [ bgroup "copy/read/group-ungroup"
446− [ mkBenchSmall "US.unlines . S.splitOnSuffix ([Word8])" env
447− $ \inh outh -> linesUnlinesCopy inh outh
448− , mkBenchSmall "S.interposeSuffix . S.splitOnSuffix(Array Word8)" env
449− $ \inh outh -> linesUnlinesArrayWord8Copy inh outh
450− , mkBenchSmall "UA.unlines . UA.lines (Array Char)" env
451− $ \inh outh -> linesUnlinesArrayCharCopy inh outh
453− , mkBenchSmall "S.interposeSuffix . S.wordsBy ([Word8])" env
454− $ \inh outh -> wordsUnwordsCopyWord8 inh outh
455− , mkBenchSmall "US.unwords . S.wordsBy ([Char])" env
456− $ \inh outh -> wordsUnwordsCopy inh outh
457− , mkBenchSmall "UA.unwords . UA.words (Array Char)" env
458− $ \inh outh -> wordsUnwordsCharArrayCopy inh outh
462-------------------------------------------------------------------------------
252-------------------------------------------------------------------------------
@@ -470,5 +260,4 @@ allBenchmarks env = Prelude.concat
470 , o_1_space_copy_fromBytes env
260 , o_1_space_copy_fromBytes env
471 , o_1_space_copy env
261 , o_1_space_copy env
472 , o_1_space_copy_toChunks_group_ungroup env
262 , o_1_space_copy_toChunks_group_ungroup env
473− , o_1_space_copy_read_group_ungroup env