From bab799297fe5f4131b1aeacf64642b4f8426048b Mon Sep 17 00:00:00 2001
From: Brian Warner <warner@allmydata.com>
Date: Tue, 2 Sep 2008 20:32:51 -0700
Subject: [PATCH] testutil.PollMixin: use a custom exception (and convert it)
 to avoid the ugly 'stash' cycle

---
 src/allmydata/util/testutil.py | 19 ++++++++++++-------
 1 file changed, 12 insertions(+), 7 deletions(-)

diff --git a/src/allmydata/util/testutil.py b/src/allmydata/util/testutil.py
index ec6afdc1..c43b1219 100644
--- a/src/allmydata/util/testutil.py
+++ b/src/allmydata/util/testutil.py
@@ -41,6 +41,9 @@ class SignalMixin:
 class TimeoutError(Exception):
     pass
 
+class PollComplete(Exception):
+    pass
+
 class PollMixin:
 
     def poll(self, check_f, pollinterval=0.01, timeout=None):
@@ -48,22 +51,24 @@ class PollMixin:
         # True, at which point the Deferred will fire.. If check_f raises an
         # exception, the Deferred will errback. If the check_f does not
         # indicate success within timeout= seconds, the Deferred will
-        # errback. If timeout=None, no timeout will be enforced.
+        # errback. If timeout=None, no timeout will be enforced, and the loop
+        # will poll forever (or really until Trial times out).
         cutoff = None
         if timeout is not None:
             cutoff = time.time() + timeout
-        stash = [] # ick. We have to pass the LoopingCall into itself
-        lc = task.LoopingCall(self._poll, check_f, stash, cutoff)
-        stash.append(lc)
+        lc = task.LoopingCall(self._poll, check_f, cutoff)
         d = lc.start(pollinterval)
+        def _convert_done(f):
+            f.trap(PollComplete)
+            return None
+        d.addErrback(_convert_done)
         return d
 
-    def _poll(self, check_f, stash, cutoff):
+    def _poll(self, check_f, cutoff):
         if cutoff is not None and time.time() > cutoff:
             raise TimeoutError()
-        lc = stash[0]
         if check_f():
-            lc.stop()
+            raise PollComplete()
 
 class StallMixin:
     def stall(self, res=None, delay=1):
-- 
2.45.2