Patch to enhance cryptography on django.contrib.auth
|Reported by:||Chris Petrilli||Owned by:||nobody|
|Severity:||Keywords:||auth user crypto|
|Cc:||treborhudson@…, gajon@…, django@…, Rick@…||Triage Stage:||Design decision needed|
|Has patch:||yes||Needs documentation:||no|
|Needs tests:||yes||Patch needs improvement:||no|
The current instantiation of
django.contrib.auth has a few issues that could be improved. The three primary ones dealt with in this patch are:
- Increasing the size of the salt pool
- Making available SHA-256 for enhances security
- Making the selection of algorithms available in settings
The first, increasing the size of the salt pool, is based on decreasing the impact of a birthday paradox attack against the pool. The current approach uses a space of 165 (1,048,576) for all salts. While this would seem on the surface to be adequate, there is in-fact a 0.5 probability of 2 users having the same hash in any database of 1,206 or more users. More information on the probability can be found on Wikipedia. The patch changes the method used to calculate a salt to 10 random selections from printable characters, and increases the space to 2.18*1014 and creates a 0.5 probability situation around 447,656,038 at the cost of 5 bytes per entry.
The second issue is that SHA-1 has known collision issues, and so I've made a tiny patch to allow SHA-256 (a version of SHA-2) to be used. For this to be useful, however, I've refactored out the third item, and created a setting
AUTH_CRYPTO_ALGORITHM that can override the default algorithm. This has a default setting of 'sha1' but can be changed by the user.
Finally, I've also factored out the process of upgrading a password in place in
User.convert_password, and modified
User.check_password to automatically upgrade users as they sign in.