[pypy-svn] r41194 - pypy/dist/pypy/tool/build

guido at codespeak.net guido at codespeak.net
Fri Mar 23 16:51:17 CET 2007


Author: guido
Date: Fri Mar 23 16:51:15 2007
New Revision: 41194

Added:
   pypy/dist/pypy/tool/build/multibuild.py
Modified:
   pypy/dist/pypy/tool/build/buildserver.py
   pypy/dist/pypy/tool/build/compile.py
Log:
Added multibuild.py script that mimics translator/goal/multibuild.py, but
instead of building locally it uses the build tool, rolling back some change
that applied some (useless) blocking while loading the zip from the build
server, fixed some logic in reconnecting code.


Modified: pypy/dist/pypy/tool/build/buildserver.py
==============================================================================
--- pypy/dist/pypy/tool/build/buildserver.py	(original)
+++ pypy/dist/pypy/tool/build/buildserver.py	Fri Mar 23 16:51:15 2007
@@ -53,8 +53,6 @@
                     # end of data is marked by sending a None
                     if chunk is None:
                         break
-                    else:
-                        self.channel.send(None)
                     gotdata = True
                     fp.write(chunk)
             finally:
@@ -120,7 +118,6 @@
     def write(self, data):
         self.loc += len(data)
         self.channel.send(data)
-        self.channel.receive() # to make sure stuff is only sent when required
 
     def close(self):
         self.channel.send(None)

Modified: pypy/dist/pypy/tool/build/compile.py
==============================================================================
--- pypy/dist/pypy/tool/build/compile.py	(original)
+++ pypy/dist/pypy/tool/build/compile.py	Fri Mar 23 16:51:15 2007
@@ -66,21 +66,19 @@
             self._connect()
             self.channel.send(data)
 
-    def _receive_twice(self):
-        try:
-            ret = self.channel.receive()
-        except EOFError, e:
-            print 'error during receive: %s, retrying' % (e,)
-            self.close()
-            self._connect()
-            ret = self.channel.receive()
+    def _receive(self):
+        ret = self.channel.receive()
         if isinstance(ret, Exception):
             raise ret.__class__, ret # tb?
         return ret
 
     def _try_twice(self, command, data):
-        self._send_twice((command, data))
-        return self._receive_twice()
+        try:
+            self._send_twice((command, data))
+            return self._receive()
+        except EOFError:
+            self._send_twice((command, data))
+            return self._receive()
 
     def start_compile(self, request):
         req = request.serialize()
@@ -94,6 +92,8 @@
 
     def save_zip(self, path):
         self._send_twice(('zip', self.requestid))
+        # XXX let's not try to fiddle about with re-sending the zip on
+        # failures, people can always go to the web page
         fp = path.open('w')
         try:
             while 1:
@@ -138,7 +138,7 @@
                          help='block until build is available and download it '
                               'immediately')
 
-    (options, args) = optparser.parse_args()
+    (options, args) = optparser.parse_args(args)
 
     if not args or len(args) != 1:
         optparser.error('please provide an email address')
@@ -172,6 +172,7 @@
     msa = ServerAccessor(config)
     print 'going to start compile'
     ret = msa.start_compile(request)
+    reqid = ret['id']
     if ret['path']:
         print ('a suitable result is already available, you can '
                'find it at "%s" on %s' % (ret['path'],
@@ -192,10 +193,14 @@
             time.sleep(POLLTIME)
         if error and error != 'None':
             print 'error:', error
+            return (False, error)
         else:
-            zipfile = py.path.local('data.zip')
+            zipfile = py.path.local('pypy-%s.zip' % (retid,))
             msa.save_zip(zipfile)
-            print 'done, the result can be found in "data.zip"'
-    elif inprogress:
+            print 'done, the result can be found in %s' % (zipfile,)
+            return (True, ret['message'])
+    elif not foreground and inprogress and not ret['path']:
         print 'you will be mailed once it\'s ready'
+    elif foreground:
+        return (False, ret['message'])
 

Added: pypy/dist/pypy/tool/build/multibuild.py
==============================================================================
--- (empty file)
+++ pypy/dist/pypy/tool/build/multibuild.py	Fri Mar 23 16:51:15 2007
@@ -0,0 +1,93 @@
+""" multibuild.py variant that uses startcompile to run the builds
+
+    see pypy/translator/goal/multibuild.py for the original version (by mwh)
+    that builds on the local host
+"""
+
+import autopath
+import sys
+import random
+import os
+import threading
+from pypy.translator.goal.multibuild import get_options, exe_name_from_options
+from pypy.tool.build import config
+from pypy.tool.build.compile import getrequest, main
+
+class ConfigWrapper(object):
+    def __init__(self, orgconfig):
+        self.__dict__.update(orgconfig.__dict__)
+
+def setconfig(conf, overrides):
+    for name, value in overrides.iteritems():
+        try:
+            homeconfig, name = conf._cfgimpl_get_home_by_path(name)
+            homeconfig.setoption(name, value, 'default')
+        except AttributeError:
+            pass
+
+def override_conf(config, opts):
+    for k, v in opts.items():
+        for c in (config.system_config, config.compile_config,
+                  config.tool_config):
+            try:
+                c.set(**{k: v})
+            except AttributeError:
+                pass
+
+def startcompile(exe_name, config, opts):
+    try:
+        override_conf(config, opts)
+    except:
+        return exe_name_from_options(newconfig.compile_config, opts), \
+               "didn't configure"
+    request, foreground = getrequest(config, sys.argv[3:])
+    hasbuilt, message = main(config, request, True)
+    hasbuilt, message = (True, 'foo')
+    return hasbuilt and 'successfully built' or 'not built: %s' % (message,)
+
+def wait_until_done():
+    while 1:
+        for t in threading.enumerate():
+            if t != threading.currentThread() and t.isAlive():
+                t.join()
+        else:
+            break
+
+results = []
+def build_pypy_with_options(basedir, opts):
+    """ start blocking (--foreground) startcompile with opts
+    """
+    newconfig = ConfigWrapper(config)
+    newconfig.system_config = config.system_config.copy()
+    newconfig.compile_config = config.compile_config.copy()
+    newconfig.tool_config = config.tool_config.copy()
+
+    exe_name = os.path.join(basedir, exe_name_from_options(
+                                      newconfig.compile_config, opts))
+
+    print 'starting: %s' % (exe_name,)
+    sys.stdout.flush()
+
+    status = startcompile(exe_name, newconfig, opts)
+
+    results.append((exe_name, status))
+
+    print '%s: %s' % (exe_name, status)
+
+if __name__ == '__main__':
+    basedir = sys.argv[1]
+    optionsfile = sys.argv[2]
+    results = []
+    options = list(get_options(optionsfile))
+    random.shuffle(options)
+    for opts in options:
+        t = threading.Thread(target=build_pypy_with_options,
+                             args=(basedir, opts))
+        t.start()
+    wait_until_done()
+    print 'done'
+
+    out = open(os.path.join(basedir, 'results'), 'w')
+    for exe, r in results:
+        print >>out, exe, r
+



More information about the Pypy-commit mailing list