Cryptography and D

Rikki Cattermole via Digitalmars-d digitalmars-d at puremagic.com
Sun Jul 6 01:22:15 PDT 2014


On 6/07/2014 6:45 p.m., Nick Sabalausky wrote:
> On 7/6/2014 1:00 AM, Rikki Cattermole wrote:
>> On 6/07/2014 6:06 a.m., Nick Sabalausky wrote:
>>>
>>> Also, DAuth encourages passwords to be stored in a special structure:
>>>
>>>    https://github.com/Abscissa/DAuth/blob/master/src/dauth/core.d#L311
>>>
>>> which attempts to zero-out the password from memory as early as it can
>>> (and encourages the user to populate it via char[] not string to avoid
>>> having an un-wipable immutable plain-text copy in memory. See
>>> 'toPassword' vs 'dupPassword'). I'm certain the implementation can be
>>> improved. And I'd kinda like to make it scoped if I can, instead of
>>> refcounted. But it's something.
>>>
>>> Obviously there are natural limits to these measures, so it can't
>>> *guarantee* anything, only help guide the application developer. And it
>>> doesn't/can't address all possible issues. But it's at least something.
>>
>> For reference, Cmsed's password authentication that is built in will
>> automatically hash passwords and will not store in any way the plain
>> text version [0].
>> Also supports upgrading hashes as needed. From older algorithms to newer
>> preferred ones.
>>
>> [0]
>> https://github.com/rikkimax/Cmsed/blob/master/source/user/cmsed/user/models/userauth.d#L57
>>
>>
>
> Unfortunately, that doesn't really address the issue. The password
> always has to come from somewhere in plaintext. By the time it gets to
> *any* hashing function it's already existed in memory in plaintext.
>
> No offense intended, but here's the thing:
>
> That "class UserPassword" cannot even be *used* until the plaintext
> password already exists in memory. It must get passed into UserPassword
> (via opAssign) as a string. Problem is, AFAICS, nothing appears to be
> removing that original plaintext copy from memory. Once it's in a
> UserPassword object, the original copy *still* sits around waiting to
> [maybe/eventually] get garbage collected or read by some bug/exploit.
>
> Worse, that plaintext data is marked as immutable (because it's a
> string), so it *cannot* be safely wiped from memory without breaking the
> type system.
>
> The idea behind the auto-zeroing Password type in DAuth: you do your
> best to give it [hopefully] the one and only copy of the plaintext
> password data, in mutable form, and DAuth nukes it from memory as soon
> as it's able to. Not if/when GC kicks in, sweeps it, and reuses it. And
> not just a copy of the data, but the actual [hopefully] original buffer.
> Any further attempts (deliberate or accidental) to read that data
> through any other reference will only receive zeros.

My reasoning is simple. Only upon setting the password for a user will 
the plaintext version ever be in memory or when logging in for 
authentication.
Now this should be coming as a parameter via routes in some format as a 
string. If this cannot be caught by the GC and cleaned up, how exactly 
does your method help?

So as far as I'm concerned, if it cannot be cleaned up, there are bigger 
problems to worry about then just securing this one tiny piece of code.

Unless of course, we want some method to guard against this e.g. all 
data given to routes in Vibe is actually protected and will be 
forcefully freed upon finishing of the route.

> On a different note though, it does seem I may have been hasty in
> grouping RIPEMD in the "weak" category. I was unfamiliar with it and
> assumed it was on par with MD5. A brief search seems to suggest that may
> not necessarily be the case.

To me it was one of the *better* options available when I wrote it, 
hence it was my initial one.



More information about the Digitalmars-d mailing list