[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

[minion-cvs] Client work: random path lengths and queue cleaning.



Update of /home/minion/cvsroot/src/minion/lib/mixminion
In directory moria.mit.edu:/tmp/cvs-serv6793/lib/mixminion

Modified Files:
	ClientMain.py Crypto.py Main.py Packet.py test.py 
Log Message:
Client work: random path lengths and queue cleaning.

TODO: 
- Rework todo 
- postpone sighup to 0.0.6
- schedule full windows client for 0.0.6

ClientMain, test:
- Add ~n path element for random-length paths.

ClientMain, Main
- Debug and finish clean-queue command.

Crypto, test:
- Add normal distribution.

Packet:
- Validate headers before generating them.




Index: ClientMain.py
===================================================================
RCS file: /home/minion/cvsroot/src/minion/lib/mixminion/ClientMain.py,v
retrieving revision 1.99
retrieving revision 1.100
diff -u -d -r1.99 -r1.100
--- ClientMain.py	10 Jul 2003 21:52:31 -0000	1.99
+++ ClientMain.py	13 Jul 2003 02:59:30 -0000	1.100
@@ -15,6 +15,7 @@
 import cPickle
 import getopt
 import getpass
+import math
 import os
 import re
 import signal
@@ -749,6 +750,8 @@
        specified.  Specifically, if nHops is used _without_ a star on the
        path, nHops must equal the path length; and if nHops is used _with_ a
        star on the path, nHops must be >= the path length.
+
+       DOCDOC ~
     """
     if not path:
         path = '*'
@@ -757,6 +760,7 @@
     #     or "<swap>"
     #     or "?"
     p = []
+    #XXXX005 test 'filename:with:colons',b,c
     while path:
         if path[0] == "'":
             m = re.match(r"'([^']+|\\')*'", path)
@@ -788,12 +792,15 @@
             path = path[1:]
             p.append("<swap>")
 
-
-    #p = path.replace(":", ",<swap>,").split(",")
     path = []
     for ent in p:
         if re.match(r'\*(\d+)', ent):
             path.extend(["?"]*int(ent[1:]))
+        elif re.match(r'\~(\d+)', ent):
+            avg = int(ent[1:])
+            n = int(mixminion.Crypto.getCommonPRNG().getNormal(avg, 1.5)+0.5)
+            if n < 0: n = 0
+            path.extend(['?']*n)
         else:
             path.append(ent)
 
@@ -1377,7 +1384,7 @@
         for h in self.getHandles():
             when = self.getPacket(h)[2]
             if when < cutoff:
-                remove.append(when)
+                remove.append(h)
         LOG.info("Removing %s old messages from queue", len(remove))
         for h in remove:
             self.removePacket(h)
@@ -2727,24 +2734,24 @@
     client.flushQueue(count)
 
 _CLEAN_QUEUE_USAGE = """\
-Usage: %(cmd)s <-D n|--days=n> [options]
+Usage: %(cmd)s <-d n|--days=n> [options]
   -h, --help                 Print this usage message and exit.
   -v, --verbose              Display extra debugging messages.
   -f <file>, --config=<file> Use a configuration file other than ~.mixminionrc
                                (You can also use MIXMINIONRC=FILE)
-  -D <n>, --days=<n>         Remove all messages older than <n> days old.
+  -d <n>, --days=<n>         Remove all messages older than <n> days old.
 
 EXAMPLES:
   Remove all pending messages older than one week.
-      %(cmd)s -D 30
+      %(cmd)s -d 30
 """.strip()
 
 def cleanQueue(cmd, args):
-    options, args = getopt.getopt(args, "hvf:D:",
+    options, args = getopt.getopt(args, "hvf:d:",
              ["help", "verbose", "config=", "days=",])
-    days = 0
+    days = None
     for o,v in options:
-        if o in ('-D','--days'):
+        if o in ('-d','--days'):
             try:
                 days = int(v)
             except ValueError:

Index: Crypto.py
===================================================================
RCS file: /home/minion/cvsroot/src/minion/lib/mixminion/Crypto.py,v
retrieving revision 1.46
retrieving revision 1.47
diff -u -d -r1.46 -r1.47
--- Crypto.py	10 Jul 2003 20:01:30 -0000	1.46
+++ Crypto.py	13 Jul 2003 02:59:30 -0000	1.47
@@ -11,6 +11,7 @@
 import binascii
 import copy_reg
 import errno
+import math
 import os
 import stat
 import sys
@@ -189,6 +190,8 @@
     """Returns (count) bytes of true random data from a true source of
        entropy (/dev/urandom).  May read ahead and cache values.
     """
+    if _theTrueRNG is None:
+        configure_trng(None)
     return _theTrueRNG.getBytes(count)
 
 # Specified in the Mixminion spec.  It's a Thomas Paine quotation.
@@ -473,6 +476,9 @@
 # we assert it.
 assert sys.maxint >= 0x7fffffff
 
+# Magic number used for normal distribution
+NV_MAGICCONST = 4 * math.exp(-0.5)/math.sqrt(2.0)
+
 class RNG:
     '''Base implementation class for random number generators.  Works
        by requesting a bunch of bytes via self._prng, and doling them
@@ -556,6 +562,19 @@
             if 0x7fffffff - max >= o:
                 return o % max
 
+    def getNormal(self, m, s):
+        """Return a random value with mean m and standard deviation s.
+        """
+        # Lifted from random.py in standard python dist.
+        while 1:
+            u1 = self.getFloat()
+            u2 = 1.0 - self.getFloat()
+            z = NV_MAGICCONST*(u1-0.5)/u2
+            zz = z*z/4.0
+            if zz <= -math.log(u2):
+                break
+        return m + z*s
+
     def getFloat(self):
         """Return a floating-point number between 0 and 1."""
         b = self.getBytes(4)
@@ -744,4 +763,6 @@
 # Return the shared instance of the true RNG.
 def getTrueRNG():
     """Return the shared instance of the true RNG."""
+    if _theTrueRNG is None:
+        configure_trng(None)
     return _theTrueRNG

Index: Main.py
===================================================================
RCS file: /home/minion/cvsroot/src/minion/lib/mixminion/Main.py,v
retrieving revision 1.53
retrieving revision 1.54
diff -u -d -r1.53 -r1.54
--- Main.py	10 Jul 2003 23:12:03 -0000	1.53
+++ Main.py	13 Jul 2003 02:59:30 -0000	1.54
@@ -127,6 +127,7 @@
     "inspect-surbs" :  ( 'mixminion.ClientMain', 'inspectSURBs' ),
     "flush" :          ( 'mixminion.ClientMain', 'flushQueue' ),
     "inspect-queue" :  ( 'mixminion.ClientMain', 'listQueue' ),
+    "clean-queue" :    ( 'mixminion.ClientMain', 'cleanQueue' ),
     "ping" :           ( 'mixminion.ClientMain', 'runPing' ),
     "server-start" :   ( 'mixminion.server.ServerMain', 'runServer' ),
     "server-stop" :    ( 'mixminion.server.ServerMain', 'signalServer' ),
@@ -154,6 +155,7 @@
   "       queue          [Schedule an anonymous message to be sent later]\n"+
   "       flush          [Send all messages waiting in the queue]\n"+
   "       inspect-queue  [Describe all messages waiting in the queue]\n"+
+  "       clean-queue    [Remove old messages from the queue\n"+
   "       import-server  [Tell the client about a new server]\n"+
   "       list-servers   [Print a list of currently known servers]\n"+
   "       update-servers [Download a fresh server directory]\n"+

Index: Packet.py
===================================================================
RCS file: /home/minion/cvsroot/src/minion/lib/mixminion/Packet.py,v
retrieving revision 1.50
retrieving revision 1.51
diff -u -d -r1.50 -r1.51
--- Packet.py	8 Jul 2003 19:13:50 -0000	1.50
+++ Packet.py	13 Jul 2003 02:59:30 -0000	1.51
@@ -695,7 +695,10 @@
     hitems = headers.items()
     hitems.sort()
     for k,v in hitems:
-        items.append("%s:%s\n"%(k,v))
+        item = "%s:%s\n"%(k,v)
+        if not HEADER_RE.match(item) or "\n" in k or "\n" in v:
+            raise ParseError("Invalid value for %s header"%k)
+        items.append(item)
     items.append("\n")
     return "".join(items)
 

Index: test.py
===================================================================
RCS file: /home/minion/cvsroot/src/minion/lib/mixminion/test.py,v
retrieving revision 1.136
retrieving revision 1.137
diff -u -d -r1.136 -r1.137
--- test.py	10 Jul 2003 23:11:15 -0000	1.136
+++ test.py	13 Jul 2003 02:59:30 -0000	1.137
@@ -1080,6 +1080,14 @@
         for i in xrange(1,10000,17):
             self.failUnless(0 <= PRNG.getInt(10) < 10)
             self.failUnless(0 <= PRNG.getInt(i) < i)
+        
+        # Check getNormal
+        tot = 0
+        for i in xrange(1,1000):
+            v = PRNG.getNormal(5,1)
+            self.failUnless(0 <= v <= 10)
+            tot += v
+        self.failUnless(4500<tot<5500)
 
 ##      itot=ftot=0
 ##      for i in xrange(1000000):
@@ -5531,10 +5539,6 @@
              ("Fred1", "Fred2", "Lola2", "Alice0", "Alice1",
               "Bob3", "Bob4", "Lisa1") ], identity)
 
-        print
-        print fname, fileURL(fname)
-        print "================================"
-
         # Replace the real URL and fingerprint with the ones we have; for
         # unit testing purposes, we can't rely on an http server.
         mixminion.ClientMain.MIXMINION_DIRECTORY_URL = fileURL(fname)
@@ -5837,6 +5841,11 @@
         p1,p2 = ppath(ks, None, 'Bob:Alice,*', mboxWithServer, nHops=5)
         pathIs((p1[0],p2[0],p2[-1]), (bob, alice, lola))
         eq((len(p1),len(p2)), (1,5))
+
+        # 1d'. Tilde
+        p1,p2 = ppath(ks, None, '?,~4,Bob,Joe', email) #default nHops=6
+        p = p1+p2
+        pathIs((p2[-1], p2[-2],), (joe, bob))
 
         # 1e. Complex.
         try: