=== modified file 'doc/changes.rst'
--- doc/changes.rst	2012-01-30 17:51:11 +0000
+++ doc/changes.rst	2012-01-30 17:54:30 +0000
@@ -7,6 +7,8 @@
 ================================
 * Add new android_install_binaries action
 * Fix problem when reporting failure messages that contain unicode
+* Refactor click-through workaround, and add support for new omap3
+  hwpacks
 
 .. _version_0_4_5:
 

=== modified file 'lava_dispatcher/client/lmc_utils.py'
--- lava_dispatcher/client/lmc_utils.py	2012-01-27 03:27:03 +0000
+++ lava_dispatcher/client/lmc_utils.py	2012-01-30 03:48:10 +0000
@@ -147,31 +147,104 @@
         logging_system('rm -rf ' + mntdir)
 
 def _run_linaro_media_create(cmd):
+    """Run linaro-media-create and accept licenses thrown up in the process.
+    """
     proc = pexpect.spawn(cmd, logfile=sys.stdout)
-    done = False
-
-    while not done:
-        id = proc.expect(["SNOWBALL CLICK-WRAP",
-                          "Do you accept the",
-                          "Configuring startupfiles",
-                          "Configuring ux500-firmware",
-                          "Configuring lbsd",
-                          "Configuring mali400-dev",
-                          pexpect.EOF], timeout=86400)
-        if id == 0:
-            proc.send('\t')
-            time.sleep(1)
-            proc.send('\r')
-
-        elif id == 1:
-            if not mali400:
-                proc.send('\t')
-            time.sleep(1)
-            proc.send('\r')
-        elif id == 6:
-            done = True
-        elif id == 5:
-            mali400 = True
-        else:
-            mali400 = False
-
+
+    # This code is a bit out of control.  It describes a state machine.  Each
+    # state has a name, a mapping patterns to wait for -> state to move to, a
+    # timeout for how long to wait for said pattern and optionally some input
+    # to send to l-m-c when you enter the step.
+
+    # The basic outline is this:
+
+    # We wait for l-m-c to actually start.  This has an enormous timeout,
+    # because 'cmd' starts with 'flock /var/lock/lava-lmc.lck' and when lots
+    # of jobs start at the same time, it can be a long time before the lock is
+    # acquired.
+
+    # Once its going, we watch for a couple of key phrases that suggets a
+    # license popup has appeared.  The next few states navigate through the
+    # dialogs and then accept the license.  The 'say-yes' state has extra fun
+    # stuff to try to move to a state where the "<Ok>" button is highlighted
+    # before pressing space (the acceptance dialogs are not consistent about
+    # whether <Ok> is the default or not!).
+
+    states = {
+        'waiting': {
+            'expectations': {
+                "linaro-hwpack-install": 'default',
+                },
+            'timeout': 86400,
+            },
+        'default': {
+            'expectations': {
+                "TI TSPA Software License Agreement": 'accept-tspa',
+                "SNOWBALL CLICK-WRAP": 'accept-snowball',
+                },
+            'timeout': 3600,
+            },
+        'accept-tspa': {
+            'expectations': {"<Ok>": 'accept-tspa-1'},
+            'timeout': 1,
+            },
+        'accept-tspa-1': {
+            'input': "\t ",
+            'expectations': {
+                "Accept TI TSPA Software License Agreement": 'say-yes',
+                },
+            'timeout': 1,
+            },
+        'say-yes': {
+            'expectations': {
+                "  <Yes>": 'say-yes-tab',
+                "\\033\[41m<(Yes|Ok)>": 'say-yes-space',
+                },
+            'timeout': 1,
+            },
+        'say-yes-tab': {
+            'input': "\t",
+            'expectations': {
+                ".": 'say-yes',
+                },
+            'timeout': 1,
+            },
+        'say-yes-space': {
+            'input': " ",
+            'expectations': {
+                ".": 'default',
+                },
+            'timeout': 1,
+            },
+        'accept-snowball': {
+            'expectations': {"<Ok>": 'accept-snowball-1'},
+            'timeout': 1,
+            },
+        'accept-snowball-1': {
+            'input': "\t ",
+            'expectations': {
+                "Do you accept": 'say-yes',
+                },
+            'timeout': 1,
+            },
+        }
+
+
+    state = 'waiting'
+
+    while True:
+        state_data = states[state]
+        patterns = []
+        next_state_names = []
+        if 'input' in state_data:
+            proc.send(state_data['input'])
+        for pattern, next_state in state_data['expectations'].items():
+            patterns.append(pattern)
+            next_state_names.append(next_state)
+        patterns.append(pexpect.EOF)
+        next_state_names.append(None)
+        logging.debug('waiting for %r' % patterns)
+        match_id = proc.expect(patterns, timeout=state_data['timeout'])
+        state = next_state_names[match_id]
+        if state is None:
+            return

