[Twisted-Python] Non-blocking Resolution

Moshe Zadka m at moshez.org
Sun Sep 23 07:00:06 MDT 2001


Here is a patch for stopping to use the native (blocking!) resolve,
and using an internal resolver. Later "mktap" could grow arguments
to set the resolver, and other things.
I have not yet done UDP, but I plan to do it soon enough, if this
patch is deemed acceptable.

Note that this means a resolver must be persistable. The DNS
resolver is not peristable, but I already have a patch to make
it so.

Index: twisted/internet/main.py
===================================================================
RCS file: /cvs/Twisted/twisted/internet/main.py,v
retrieving revision 1.27
diff -u -r1.27 main.py
--- twisted/internet/main.py	2001/09/19 12:18:09	1.27
+++ twisted/internet/main.py	2001/09/23 13:07:25
@@ -50,9 +50,13 @@
         if os.name == "posix":
             self.uid = uid or os.getuid()
             self.gid = gid or os.getgid()
+        self.resolver = DummyResolver()
 
-    persistentVersion = 1
+    persistentVersion = 2
 
+    def upgradeToVersion2(self):
+        self.resolver = DummyResolver()
+
     def upgradeToVersion1(self):
         """Version 1 Persistence Upgrade
         """
@@ -161,6 +165,7 @@
     def run(self, save=1):
         """Run this application, running the main loop if necessary.
         """
+        global resolver
         if not self.running:
             threadable.dispatcher.own(self)
             delayeds.extend(self.delayeds)
@@ -174,6 +179,7 @@
                     return
             for service in self.services.values():
                 service.startService()
+            resolver = self.resolver
             self.running = 1
             threadable.dispatcher.disown(self)
         if not running:
@@ -192,6 +198,11 @@
     """
     theTimeouts.later(method, seconds)
 
+class DummyResolver:
+
+    def resolve(self, address, success, fail):
+        fail()
+
 reads = {}
 writes = {}
 running = None
@@ -199,6 +210,7 @@
 if threadable.threaded:
     delayeds.append(threadtask.theScheduler)
 shutdowns = [theTimeouts.runEverything]
+resolver = DummyResolver()
 
 def shutDown(a=None, b=None):
     """Run all shutdown callbacks (save all running Applications) and exit.
@@ -523,6 +535,7 @@
     # currentPlugins = os.path.abspath("TwistedPlugins")
     allPlugins = [systemPlugins, userPlugins, confPlugins] #, currentPlugins]
     sys.path.extend(allPlugins)
+
 
 # Sibling Import
 import process
Index: twisted/internet/tcp.py
===================================================================
RCS file: /cvs/Twisted/twisted/internet/tcp.py,v
retrieving revision 1.22
diff -u -r1.22 tcp.py
--- twisted/internet/tcp.py	2001/09/11 04:08:28	1.22
+++ twisted/internet/tcp.py	2001/09/23 13:07:26
@@ -28,6 +28,7 @@
 import socket
 import sys
 import traceback
+import string
 
 if os.name == 'nt':
     EWOULDBLOCK = 10035
@@ -49,7 +50,7 @@
 
 # Sibling Imports
 import abstract
-from main import CONNECTION_LOST, CONNECTION_DONE
+import main
 
 class Connection(abstract.FileDescriptor,
                  protocol.Transport,
@@ -79,9 +80,9 @@
             if se.args[0] == EWOULDBLOCK:
                 return
             else:
-                return CONNECTION_LOST
+                return main.CONNECTION_LOST
         if not data:
-            return CONNECTION_LOST
+            return main.CONNECTION_LOST
         return self.protocol.dataReceived(data)
 
     def writeSomeData(self, data):
@@ -95,7 +96,7 @@
         except socket.error, se:
             if se.args[0] == EWOULDBLOCK:
                 return 0
-            return CONNECTION_LOST
+            return main.CONNECTION_LOST
 
     def connectionLost(self):
         """See abstract.FileDescriptor.connectionLost().
@@ -145,6 +146,7 @@
         self.port = port
         Connection.__init__(self, skt, protocol)
         self.doWrite = self.doConnect
+        self.resolveAddress()
         self.doConnect()
         self.logstr = self.protocol.__class__.__name__+",client"
 	if timeout is not None:
@@ -161,13 +163,32 @@
         # factored out so as to minimise the code necessary for SecureClient
         return socket.socket(socket.AF_INET,socket.SOCK_STREAM)
 
+    def resolveAddress(self):
+        parts = string.split(self.addr[0], '.')
+        if len(parts) == 4:
+            try:
+                for part in map(int, parts):
+                    if not (0<=part<256):
+                        break
+                else:
+                    self.realAddress = self.addr[0]
+                    return
+            except ValueError:
+                pass
+        main.resolver.resolve(self.addr[0], self.setRealAddress, 
+                                            self.failIfNotConnected)
+
+    def setRealAddress(self, address):
+        self.realAddress = address
+        self.doConnect()
+
     def doConnect(self):
         """I connect the socket.
         
         Then, call the protocol's makeConnection, and start waiting for data.
         """
         try:
-            self.socket.connect(self.addr)
+            self.socket.connect((self.realAddress, self.addr[1]))
         except socket.error, se:
             if se.args[0] == EMYSTERY:
                 self.startWriting()

-- 
The Official Moshe Zadka FAQ: http://moshez.geek
The Official Moshe Zadka FAQ For Dummies: http://moshez.org
Read the FAQ





More information about the Twisted-Python mailing list