anonymization: remove from waveguide

The loguploader handles MAC address anonymization now,
both the Python version used on older kernels and the
C version used on newer kernels.

Remove anonymization from waveguide, rely on the uploader.

Change-Id: I5d1d25c386bf0450a98d09321d23489fa8c6a823
diff --git a/waveguide/log.py b/waveguide/log.py
index af05667..cf9ccb6 100644
--- a/waveguide/log.py
+++ b/waveguide/log.py
@@ -17,15 +17,11 @@
 """Helper functions for logging."""
 
 import errno
-import hmac
 import os
-import struct
 import sys
-import helpers
 
 
 LOGLEVEL = 0
-ANONYMIZE = True
 STATUS_DIR = None
 
 
@@ -47,62 +43,6 @@
     Log(s, *args)
 
 
-SOFT = 'AEIOUY' 'V'
-HARD = 'BCDFGHJKLMNPQRSTVWXYZ' 'AEIOU'
-
-
-def Trigraph(num):
-  """Given a value from 0..4095, encode it as a cons+vowel+cons sequence."""
-  ns = len(SOFT)
-  nh = len(HARD)
-  assert nh * ns * nh >= 4096
-  c3 = num % nh
-  c2 = (num / nh) % ns
-  c1 = num / nh / ns
-  return HARD[c1] + SOFT[c2] + HARD[c3]
-
-
-def WordFromBinary(s):
-  """Encode a binary blob into a string of pronounceable syllables."""
-  out = []
-  while s:
-    part = s[:3]
-    s = s[3:]
-    while len(part) < 4:
-      part = '\0' + part
-    bits = struct.unpack('!I', part)[0]
-    out += [(bits >> 12) & 0xfff,
-            (bits >> 0)  & 0xfff]
-  return ''.join(Trigraph(i) for i in out)
-
-
-# Note(apenwarr): There are a few ways to do this.  I elected to go with
-# short human-usable strings (allowing for the small possibility of
-# collisions) since the log messages will probably be "mostly" used by
-# humans.
-#
-# An alternative would be to use "format preserving encryption" (basically
-# a secure 1:1 mapping of unencrypted to anonymized, in the same number of
-# bits) and then produce longer "words" with no possibility of collision.
-# But with our current WordFromBinary() implementation, that would be
-# 12 characters long, which is kind of inconvenient and we probably don't
-# need that level of care.  Inside waveguide we use the real MAC addresses
-# so collisions won't cause a real problem.
-#
-# TODO(apenwarr): consider not anonymizing the OUI.
-#   That way we could see any behaviour differences between vendors.
-#   Sadly, that might make it too easy to brute force a MAC address back out;
-#   the remaining 3 bytes have too little entropy.
-#
-def AnonymizeMAC(consensus_key, macbin):
-  """Anonymize a binary MAC address using the given key."""
-  assert len(macbin) == 6
-  if consensus_key and ANONYMIZE:
-    return WordFromBinary(hmac.new(consensus_key, macbin).digest())[:6]
-  else:
-    return helpers.DecodeMAC(macbin)
-
-
 def WriteEventFile(name):
   """Create a file in STATUS_DIR if it does not already exist.
 
diff --git a/waveguide/log_test.py b/waveguide/log_test.py
deleted file mode 100755
index fabc09f..0000000
--- a/waveguide/log_test.py
+++ /dev/null
@@ -1,35 +0,0 @@
-#!/usr/bin/python
-import log
-from wvtest import wvtest
-
-
-@wvtest.wvtest
-def AnonTest():
-  m1 = '\x01\x02\x03\x04\x05\x06'
-  m2 = '\x31\x32\x33\x34\x35\x36'
-
-  s1 = log.AnonymizeMAC(None, m1)
-  s2 = log.AnonymizeMAC(None, m2)
-  a1a = log.AnonymizeMAC('key', m1)
-  a2a = log.AnonymizeMAC('key', m2)
-  a1b = log.AnonymizeMAC('key2', m1)
-  a2b = log.AnonymizeMAC('key2', m2)
-
-  # make sure they're printable strings
-  wvtest.WVPASSEQ(s1, str(s1))
-  wvtest.WVPASSEQ(a1a, str(a1a))
-  wvtest.WVPASSEQ(a1b, str(a1b))
-
-  # and reasonably sized
-  wvtest.WVPASSLE(len(a1a), 8)
-
-  # and change when the key or MAC changes
-  wvtest.WVPASSNE(s1, s2)
-  wvtest.WVPASSNE(a1a, a1b)
-  wvtest.WVPASSNE(a2a, a2b)
-  wvtest.WVPASSNE(a1a, a2a)
-  wvtest.WVPASSNE(a1b, a2b)
-
-
-if __name__ == '__main__':
-  wvtest.wvtest_main()
diff --git a/waveguide/waveguide.py b/waveguide/waveguide.py
index 87324c3..594f83f 100755
--- a/waveguide/waveguide.py
+++ b/waveguide/waveguide.py
@@ -58,8 +58,7 @@
 tx-interval=      Seconds between state transmits (0 to disable) [15]
 autochan-interval= Seconds between autochannel decisions (0 to disable) [300]
 print-interval=   Seconds between state printouts to log (0 to disable) [16]
-D,debug           Increase (non-anonymized!) debug output level
-no-anonymize      Don't anonymize MAC addresses in logs
+D,debug           Increase debug output level
 status-dir=       Directory to store status information [/tmp/waveguide]
 watch-pid=        Shut down if the given process pid disappears
 auto-disable-threshold=  Shut down if >= RSSI received from other AP [-30]
@@ -240,11 +239,8 @@
   def Filename(self, suffix):
     return os.path.join(opt.status_dir, '%s.%s' % (self.vdevname, suffix))
 
-  def AnonymizeMAC(self, mac):
-    return log.AnonymizeMAC(consensus_key, mac)
-
   def _LogPrefix(self):
-    return '%s(%s): ' % (self.vdevname, self.AnonymizeMAC(self.mac))
+    return '%s(%s): ' % (self.vdevname, helpers.DecodeMAC(self.mac))
 
   def Log(self, s, *args):
     log.Log(self._LogPrefix() + s, *args)
@@ -291,7 +287,7 @@
       self.Debug('ignoring peer due to key mismatch')
       return 0
     if p.me.mac not in self.peer_list:
-      self.Log('added a peer: %s', self.AnonymizeMAC(p.me.mac))
+      self.Log('added a peer: %s', helpers.DecodeMAC(p.me.mac))
     self.peer_list[p.me.mac] = p
     self.MaybeAutoDisable()
     return 1
@@ -445,7 +441,7 @@
       return None
     for peer in sorted(self.peer_list.values(), key=lambda p: p.me.mac):
       self.Debug('considering auto disable: peer=%s',
-                 self.AnonymizeMAC(peer.me.mac))
+                 helpers.DecodeMAC(peer.me.mac))
       if peer.me.mac not in self.bss_list:
         self.Debug('--> peer no match')
       else:
@@ -478,11 +474,11 @@
     """Writes/removes the auto-disable file based on ShouldAutoDisable()."""
     ad = self.ShouldAutoDisable()
     if ad and self.auto_disabled != ad:
-      self.Log('auto-disabling because of %s', self.AnonymizeMAC(ad))
+      self.Log('auto-disabling because of %s', helpers.DecodeMAC(ad))
       helpers.WriteFileAtomic(self.Filename('disabled'), helpers.DecodeMAC(ad))
     elif self.auto_disabled and not ad:
       self.Log('auto-enabling because %s disappeared',
-               self.AnonymizeMAC(self.auto_disabled))
+               helpers.DecodeMAC(self.auto_disabled))
       helpers.Unlink(self.Filename('disabled'))
     self.auto_disabled = ad
 
@@ -960,17 +956,12 @@
       helpers.WriteFileAtomic(os.path.join(WIFIBLASTER_DIR, g.group()),
                               '%d %s' % (time.time(), line))
 
-  def _AnonymizeResult(self, line):
-    def Repl(match):
-      return log.AnonymizeMAC(consensus_key, helpers.EncodeMAC(match.group()))
-    return re.sub(MACADDR_REGEX, Repl, line)
-
   def _HandleResults(self, errcode, stdout, stderr):
     """Callback for 'wifiblaster' results."""
     log.Debug('wifiblaster err:%r stdout:%r stderr:%r', errcode, stdout[:70],
               stderr)
     for line in stdout.splitlines():
-      log.Log('wifiblaster: %s' % self._AnonymizeResult(line))
+      log.Log('wifiblaster: %s' % line)
       self._SaveResult(line)
 
   def _StrToBool(self, s):
@@ -1090,7 +1081,6 @@
   if opt.watch_pid and opt.watch_pid <= 1:
     o.fatal('--watch-pid must be empty or > 1')
   log.LOGLEVEL = opt.debug
-  log.ANONYMIZE = opt.anonymize
   log.STATUS_DIR = opt.status_dir
 
   try:
@@ -1232,11 +1222,11 @@
         self_signals[m.mac] = bss_signal
         peer_data[m.mac] = seen_peers
         log.Log('%s: APs=%-4d peer-APs=%s stations=%s',
-                m.AnonymizeMAC(p.me.mac), len(p.seen_bss),
-                ','.join('%s(%d)' % (m.AnonymizeMAC(i.mac), i.rssi)
+                helpers.DecodeMAC(p.me.mac), len(p.seen_bss),
+                ','.join('%s(%d)' % (helpers.DecodeMAC(i.mac), i.rssi)
                          for i in sorted(seen_bss_peers,
                                          key=lambda i: -i.rssi)),
-                ','.join('%s(%d)' % (m.AnonymizeMAC(i.mac), i.rssi)
+                ','.join('%s(%d)' % (helpers.DecodeMAC(i.mac), i.rssi)
                          for i in sorted(p.assoc,
                                          key=lambda i: -i.rssi)))
 
@@ -1251,7 +1241,7 @@
       can2G_count = can5G_count = 0
       for m in managers:
         for assoc in m.assoc_list.itervalues():
-          anon = m.AnonymizeMAC(assoc.mac)
+          station = helpers.DecodeMAC(assoc.mac)
           if log_sta_band_capabilities:
             if assoc.can5G:
               can5G_count += 1
@@ -1259,11 +1249,10 @@
             else:
               can2G_count += 1
               capability = '2.4'
-            log.Log('Connected station %s supports %s GHz', anon, capability)
-          station = helpers.DecodeMAC(assoc.mac)
+            log.Log('Connected station %s supports %s GHz', station, capability)
           species = clientinfo.taxonomize(station)
           if species:
-            log.Log('Connected station %s taxonomy: %s' % (anon, species))
+            log.Log('Connected station %s taxonomy: %s', station, species)
       if log_sta_band_capabilities:
         log.Log('Connected stations: total %d, 5 GHz %d, 2.4 GHz %d',
                 can5G_count + can2G_count, can5G_count, can2G_count)
diff --git a/waveguide/wifiblaster_controller_test.py b/waveguide/wifiblaster_controller_test.py
index 9e300f2..12ff480 100755
--- a/waveguide/wifiblaster_controller_test.py
+++ b/waveguide/wifiblaster_controller_test.py
@@ -71,13 +71,6 @@
     stdout = ('version=1 mac=11:11:11:11:11:11 throughput=10000000 '
               'samples=5000000,15000000\n'
               'malformed 11:11:11:11:11:11 but has macs 11:11:11:11:11:11\n')
-
-    result = wc._AnonymizeResult(stdout)
-    expected = ('version=1 mac=CYAFVU throughput=10000000 '
-                'samples=5000000,15000000\n'
-                'malformed CYAFVU but has macs CYAFVU\n')
-    wvtest.WVPASSEQ(result, expected)
-
     expected = [('version=1 mac=11:11:11:11:11:11 throughput=10000000 '
                  'samples=5000000,15000000'),
                 'malformed 11:11:11:11:11:11 but has macs 11:11:11:11:11:11']