[darcs-devel] Poor Speed Writing Binary Patches.

Ralph Corderoy ralph at inputplus.co.uk
Sat Apr 16 03:40:31 PDT 2005


Hi,

I've been looking at the time taken to do `darcs record' after a `darcs
add' of a 4MiB binary file containing the repeating byte sequence
0..255.

I've sent a patch for fpstring.c to David that speeds things up by
1/16th but have some questions on the Haskell in PatchShow.lhs.

    showBinary :: FileName -> PackedString -> PackedString -> Doc

    showBinary f o n =
        blueText "binary" <+> fn2d f
     $$ invisibleText "oldhex"
     $$ (vcat $ map makeprintable $ break_every 78 $ fromPS2Hex o)
     $$ invisibleText "newhex"
     $$ (vcat $ map makeprintable $ break_every 78 $ fromPS2Hex n)
         where makeprintable ps = invisibleText "*" <> invisiblePS ps

    break_every :: Int -> PackedString -> [PackedString]
    break_every n ps | lengthPS ps < n = [ps]
                     | otherwise = takePS n ps : break_every n (dropPS n ps)

The C function in fpstring.c corresponding to fromPS2Hex gets called
once with all 4MiB of data.  It writes 8MiB of text to another place in
memory and doesn't take long about it.  I assume the `laziness' in
Haskell means that the break_every just passes 78 characters at a time
to the caller rather than copying that 8MiB into another large lump of
memory so all 78 length strings exist at once.  Likewise, the prefixing
with a `*' doesn't result in another set also existing.  Is that true?

However, even if that's the case, this seems like a time when a
routine's required that takes `o' and writes directly to the file,
converting to hex, prefixing with `*', and splitting into lines all in
one go?

Cheers,


Ralph.





More information about the darcs-devel mailing list