hi all,

for some (up to now) unknown reasons the generation of md5-hashes fails in 
modpython (for me and at least one other user on irc). I discovered this bug 
while switching a django-setup from the builtin dev-server to modpython: it 
complained that I had tampered with the session cookies - which I didn't ;)

the session ids looked a little unusual: all hashes started with 16 leading 
zeros. So next, I tried generating md5-hashes in django and they also had the 
leading zeros PLUS when generating a couple of hashes for different strings 
in one request the resulting hashes were all the same. After that I tested 
md5 hash generation in "plain" modpy - which had the same problems. the odd 
thing is: using the md5-module in "regular" python works totally fine! since 
this clearly seems to be a modpy issue, there's a thread on the modpy 
mailinglist:
        http://modpython.org/pipermail/mod_python/2006-June/021482.html
note that, there already have been confirmations that this is not a general 
modpython issue.

the first workaround was to replace md5 with sha - but since that can hardly 
be called a solution, I propose that the use of hashing algorithms should 
be "uncoupled" from the actual implementation used. the appended diff might 
be a start of into that direction, but certainly might need some clean up ;)
-- 
cheers,

        Nikl


--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users
-~----------~----~----~----~------~----~------~--~---
Index: conf/global_settings.py
===================================================================
--- conf/global_settings.py	(revision 3212)
+++ conf/global_settings.py	(working copy)
@@ -221,6 +221,9 @@
 # Hint: you really don't!
 TRANSACTIONS_MANAGED = False
 
+# Which hashing algorithm do you prefer? (see django.util.hashes for available algorithms)
+FAVORITE_HASH_ALGO = "md5"
+
 ##############
 # MIDDLEWARE #
 ##############
Index: contrib/sessions/models.py
===================================================================
--- contrib/sessions/models.py	(revision 3212)
+++ contrib/sessions/models.py	(working copy)
@@ -1,6 +1,7 @@
-import base64, md5, random, sys
+import base64, random, sys
 import cPickle as pickle
 from django.db import models
+from django.utils.hashes import hash
 from django.utils.translation import gettext_lazy as _
 from django.conf import settings
 
@@ -8,15 +9,15 @@
     def encode(self, session_dict):
         "Returns the given session dictionary pickled and encoded as a string."
         pickled = pickle.dumps(session_dict)
-        pickled_md5 = md5.new(pickled + settings.SECRET_KEY).hexdigest()
-        return base64.encodestring(pickled + pickled_md5)
+        pickled_hash = hash.new(pickled + settings.SECRET_KEY).hexdigest()
+        return base64.encodestring(pickled + pickled_hash)
 
     def get_new_session_key(self):
         "Returns session key that isn't being used."
         # The random module is seeded when this Apache child is created.
         # Use person_id and SECRET_KEY as added salt.
         while 1:
-            session_key = md5.new(str(random.randint(0, sys.maxint - 1)) + str(random.randint(0, sys.maxint - 1)) + settings.SECRET_KEY).hexdigest()
+            session_key = hash.new(str(random.randint(0, sys.maxint - 1)) + str(random.randint(0, sys.maxint - 1)) + settings.SECRET_KEY).hexdigest()
             try:
                 self.get(session_key=session_key)
             except self.model.DoesNotExist:
@@ -49,8 +50,8 @@
 
     def get_decoded(self):
         encoded_data = base64.decodestring(self.session_data)
-        pickled, tamper_check = encoded_data[:-32], encoded_data[-32:]
-        if md5.new(pickled + settings.SECRET_KEY).hexdigest() != tamper_check:
+        pickled, tamper_check = encoded_data[:hash.digest_size*-2], encoded_data[hash.digest_size*-2:]
+        if hash.new(pickled + settings.SECRET_KEY).hexdigest() != tamper_check:
             from django.core.exceptions import SuspiciousOperation
             raise SuspiciousOperation, "User tampered with session cookie."
         try:
Index: contrib/admin/views/decorators.py
===================================================================
--- contrib/admin/views/decorators.py	(revision 3212)
+++ contrib/admin/views/decorators.py	(working copy)
@@ -2,8 +2,9 @@
 from django.conf import settings
 from django.contrib.auth.models import User, SESSION_KEY
 from django.shortcuts import render_to_response
+from django.utils.hashes import hash
 from django.utils.translation import gettext_lazy
-import base64, datetime, md5
+import base64, datetime
 import cPickle as pickle
 
 ERROR_MESSAGE = gettext_lazy("Please enter a correct username and password. Note that both fields are case-sensitive.")
@@ -28,13 +29,13 @@
 
 def _encode_post_data(post_data):
     pickled = pickle.dumps(post_data)
-    pickled_md5 = md5.new(pickled + settings.SECRET_KEY).hexdigest()
-    return base64.encodestring(pickled + pickled_md5)
+    pickled_hash = hash.new(pickled + settings.SECRET_KEY).hexdigest()
+    return base64.encodestring(pickled + pickled_hash)
 
 def _decode_post_data(encoded_data):
     encoded_data = base64.decodestring(encoded_data)
-    pickled, tamper_check = encoded_data[:-32], encoded_data[-32:]
-    if md5.new(pickled + settings.SECRET_KEY).hexdigest() != tamper_check:
+    pickled, tamper_check = encoded_data[:hash.digest_size*-2], encoded_data[hash.digest_size*-2:]
+    if hash.new(pickled + settings.SECRET_KEY).hexdigest() != tamper_check:
         from django.core.exceptions import SuspiciousOperation
         raise SuspiciousOperation, "User may have tampered with session cookie."
     return pickle.loads(pickled)

Reply via email to