-
Notifications
You must be signed in to change notification settings - Fork 139
make Digest a strict datatype? #70
Comments
Yes, I think that's a sensible change. I wonder if Context should have the same treatment |
I'm a bit puzzled actually. Just was looking at the code, and trying couple of things to try to reproduce but just couldn't; is the problem not in the part that transform a |
Vincent Hanquez wrote:
I had some difficulty reproducing it too, only saw the problem on some I don't see how Digest x -> String could need 3 terabytes of memory, so see shy jo |
sorry for being unclear, but when I say the problem is in the i.e. the problem is:
Whereas if you write:
I think the |
although, it doesn't quite explain needing so much memory, maybe some context are not folded properly to the next one.. |
Yes, part of the problem was indeed that bang doesn't fully force String. Also, it's not really clear from the public API whether bang fully forces see shy jo |
Digest can be partially evaluated, which presents several gotchas.
I had some simple code using cryptonite to get a hash:
This worked ok, running in constant space. But, it kept the file handle open until some later point when the hash was used (or possibly open past use until garbage collected). That turned out to prevent eg, deleting the file under windows (which doesn't allow open files to be deleted), which broke my test suite. So, I made what seemed like an innocuous change to "fix" that:
But this version sometimes buffers the whole file content in memory. The bang pattern doesn't fully force the String, and so the Digest isn't fully forced either, and the hash can end up partially evaluated. In one case, hashing a 30 gb file resulted in a 30 gb malloc!
So, I had to do this (or could have used the NFData instance for Digest for same effect):
Which I think will avoid all problems, but was not easy to arrive at.
From my brief review of the API, I don't see any benefits to letting Digest be partially evaluated. So why not make the data type internally strict, or have hashLazy fully force it.
The text was updated successfully, but these errors were encountered: