diff options
-rw-r--r-- | bitbake-dev/AUTHORS | 2 | ||||
-rw-r--r-- | bitbake-dev/ChangeLog | 2 | ||||
-rwxr-xr-x | bitbake-dev/bin/bitbake | 14 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/command.py | 1 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/cooker.py | 10 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/fetch/__init__.py | 50 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/fetch/git.py | 42 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/providers.py | 2 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/server/__init__.py | 1 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/server/none.py (renamed from bitbake-dev/lib/bb/xmlrpcserver.py) | 0 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/server/xmlrpc.py | 145 | ||||
-rw-r--r-- | bitbake-dev/lib/bb/utils.py | 16 |
12 files changed, 237 insertions, 48 deletions
diff --git a/bitbake-dev/AUTHORS b/bitbake-dev/AUTHORS index 9d592608bb..a4014b1e39 100644 --- a/bitbake-dev/AUTHORS +++ b/bitbake-dev/AUTHORS @@ -2,7 +2,7 @@ Tim Ansell <mithro@mithis.net> Phil Blundell <pb@handhelds.org> Seb Frankengul <seb@frankengul.org> Holger Freyther <zecke@handhelds.org> -Marcin Juszkiewicz <marcin@haerwu.biz> +Marcin Juszkiewicz <marcin@juszkiewicz.com.pl> Chris Larson <kergoth@handhelds.org> Ulrich Luckas <luckas@musoft.de> Mickey Lauer <mickey@Vanille.de> diff --git a/bitbake-dev/ChangeLog b/bitbake-dev/ChangeLog index 65c5e4bf36..22124cb7ea 100644 --- a/bitbake-dev/ChangeLog +++ b/bitbake-dev/ChangeLog @@ -176,6 +176,8 @@ Changes in Bitbake 1.9.x: - Set HOME environmental variable when running fetcher commands (from Poky) - Make sure allowed variables inherited from the environment are exported again (from Poky) - When running a stage task in bbshell, run populate_staging, not the stage task (from Poky) + - Fix + character escaping from PACKAGES_DYNAMIC (thanks Otavio Salvador) + - Addition of BBCLASSEXTEND support for allowing one recipe to provide multiple targets (from Poky) Changes in Bitbake 1.8.0: - Release 1.7.x as a stable series diff --git a/bitbake-dev/bin/bitbake b/bitbake-dev/bin/bitbake index 34c49b8c58..cabdf2b452 100755 --- a/bitbake-dev/bin/bitbake +++ b/bitbake-dev/bin/bitbake @@ -144,7 +144,11 @@ Default BBFILES are the .bb files in the current directory.""" ) configuration.pkgs_to_build = [] configuration.pkgs_to_build.extend(args[1:]) - cooker = bb.cooker.BBCooker(configuration) + # Save a logfile for cooker into the current working directory. When the + # server is daemonized this logfile will be truncated. + cooker_logfile = os.path.join (os.getcwd(), "cooker.log") + + cooker = bb.cooker.BBCooker(configuration, bb.server.xmlrpc) # Clear away any spurious environment variables. But don't wipe the # environment totally. This is necessary to ensure the correct operation @@ -152,13 +156,13 @@ Default BBFILES are the .bb files in the current directory.""" ) bb.utils.clean_environment() cooker.parseCommandLine() + + + + host = cooker.server.host port = cooker.server.port - # Save a logfile for cooker into the current working directory. When the - # server is daemonized this logfile will be truncated. - cooker_logfile = os.path.join (os.getcwd(), "cooker.log") - daemonize.createDaemon(cooker.serve, cooker_logfile) del cooker diff --git a/bitbake-dev/lib/bb/command.py b/bitbake-dev/lib/bb/command.py index e7c3770ffc..1a1bf00b33 100644 --- a/bitbake-dev/lib/bb/command.py +++ b/bitbake-dev/lib/bb/command.py @@ -57,7 +57,6 @@ class Command: async_cmds[command] = (method) def runCommand(self, commandline): - bb.debug("Running command %s" % commandline) try: command = commandline.pop(0) if command in CommandsSync.__dict__: diff --git a/bitbake-dev/lib/bb/cooker.py b/bitbake-dev/lib/bb/cooker.py index b2b237b4c7..1bf7d4bd14 100644 --- a/bitbake-dev/lib/bb/cooker.py +++ b/bitbake-dev/lib/bb/cooker.py @@ -25,7 +25,8 @@ import sys, os, getopt, glob, copy, os.path, re, time import bb from bb import utils, data, parse, event, cache, providers, taskdata, runqueue -from bb import xmlrpcserver, command +from bb import command +import bb.server.xmlrpc import itertools, sre_constants class MultipleMatches(Exception): @@ -62,14 +63,13 @@ class BBCooker: Manages one bitbake build run """ - def __init__(self, configuration): + def __init__(self, configuration, server): self.status = None self.cache = None self.bb_cache = None - self.server = bb.xmlrpcserver.BitBakeXMLRPCServer(self) - #self.server.register_function(self.showEnvironment) + self.server = server.BitBakeServer(self) self.configuration = configuration @@ -680,7 +680,7 @@ class BBCooker: retval = False if not retval: self.command.finishAsyncCommand() - bb.event.fire(bb.event.BuildCompleted(buildname, targets, self.configuration.event_data, failures)) + bb.event.fire(bb.event.BuildCompleted(buildname, item, self.configuration.event_data, failures)) return False return 0.5 diff --git a/bitbake-dev/lib/bb/fetch/__init__.py b/bitbake-dev/lib/bb/fetch/__init__.py index b8a00107e2..ab4658bc3b 100644 --- a/bitbake-dev/lib/bb/fetch/__init__.py +++ b/bitbake-dev/lib/bb/fetch/__init__.py @@ -99,6 +99,11 @@ def fetcher_init(d): pd.delDomain("BB_URI_HEADREVS") else: bb.msg.fatal(bb.msg.domain.Fetcher, "Invalid SRCREV cache policy of: %s" % srcrev_policy) + + for m in methods: + if hasattr(m, "init"): + m.init(d) + # Make sure our domains exist pd.addDomain("BB_URI_HEADREVS") pd.addDomain("BB_URI_LOCALCOUNT") @@ -147,14 +152,16 @@ def init(urls, d, setup = True): urldata_cache[fn] = urldata return urldata -def go(d): +def go(d, urls = None): """ Fetch all urls init must have previously been called """ - urldata = init([], d, True) + if not urls: + urls = d.getVar("SRC_URI", 1).split() + urldata = init(urls, d, True) - for u in urldata: + for u in urls: ud = urldata[u] m = ud.method if ud.localfile: @@ -465,6 +472,23 @@ class Fetch(object): srcrev_internal_helper = staticmethod(srcrev_internal_helper) + def localcount_internal_helper(ud, d): + """ + Return: + a) a locked localcount if specified + b) None otherwise + """ + + localcount= None + if 'name' in ud.parm: + pn = data.getVar("PN", d, 1) + localcount = data.getVar("LOCALCOUNT_" + ud.parm['name'], d, 1) + if not localcount: + localcount = data.getVar("LOCALCOUNT", d, 1) + return localcount + + localcount_internal_helper = staticmethod(localcount_internal_helper) + def try_mirror(d, tarfn): """ Try to use a mirrored version of the sources. We do this @@ -553,12 +577,7 @@ class Fetch(object): """ """ - has_sortable_valid = hasattr(self, "_sortable_revision_valid") - has_sortable = hasattr(self, "_sortable_revision") - - if has_sortable and not has_sortable_valid: - return self._sortable_revision(url, ud, d) - elif has_sortable and self._sortable_revision_valid(url, ud, d): + if hasattr(self, "_sortable_revision"): return self._sortable_revision(url, ud, d) pd = persist_data.PersistData(d) @@ -566,13 +585,24 @@ class Fetch(object): latest_rev = self._build_revision(url, ud, d) last_rev = pd.getValue("BB_URI_LOCALCOUNT", key + "_rev") - count = pd.getValue("BB_URI_LOCALCOUNT", key + "_count") + uselocalcount = bb.data.getVar("BB_LOCALCOUNT_OVERRIDE", d, True) or False + count = None + if uselocalcount: + count = Fetch.localcount_internal_helper(ud, d) + if count is None: + count = pd.getValue("BB_URI_LOCALCOUNT", key + "_count") if last_rev == latest_rev: return str(count + "+" + latest_rev) + buildindex_provided = hasattr(self, "_sortable_buildindex") + if buildindex_provided: + count = self._sortable_buildindex(url, ud, d, latest_rev) + if count is None: count = "0" + elif uselocalcount or buildindex_provided: + count = str(count) else: count = str(int(count) + 1) diff --git a/bitbake-dev/lib/bb/fetch/git.py b/bitbake-dev/lib/bb/fetch/git.py index 911c5e437f..43053d6c46 100644 --- a/bitbake-dev/lib/bb/fetch/git.py +++ b/bitbake-dev/lib/bb/fetch/git.py @@ -28,6 +28,12 @@ from bb.fetch import runfetchcmd class Git(Fetch): """Class to fetch a module or modules from git repositories""" + def init(self, d): + # + # Only enable _sortable revision if the key is set + # + if bb.data.getVar("BB_GIT_CLONE_FOR_SRCREV", d, True): + self._sortable_buildindex = self._sortable_buildindex_disabled def supports(self, url, ud, d): """ Check to see if a given url can be fetched with git. @@ -145,44 +151,32 @@ class Git(Fetch): def _build_revision(self, url, ud, d): return ud.tag - def _sortable_revision_valid(self, url, ud, d): - return bb.data.getVar("BB_GIT_CLONE_FOR_SRCREV", d, True) or False - - def _sortable_revision(self, url, ud, d): + def _sortable_buildindex_disabled(self, url, ud, d, rev): """ - This is only called when _sortable_revision_valid called true - - We will have to get the updated revision. + Return a suitable buildindex for the revision specified. This is done by counting revisions + using "git rev-list" which may or may not work in different circumstances. """ gitsrcname = '%s%s' % (ud.host, ud.path.replace('/', '.')) repodir = os.path.join(data.expand('${GITDIR}', d), gitsrcname) - key = "GIT_CACHED_REVISION-%s-%s" % (gitsrcname, ud.tag) - if bb.data.getVar(key, d): - return bb.data.getVar(key, d) - - - # Runtime warning on wrongly configured sources - if ud.tag == "1": - bb.msg.error(1, bb.msg.domain.Fetcher, "SRCREV is '1'. This indicates a configuration error of %s" % url) - return "0+1" - cwd = os.getcwd() # Check if we have the rev already if not os.path.exists(repodir): - print "no repo" self.go(None, ud, d) + if not os.path.exists(repodir): + bb.msg.error(bb.msg.domain.Fetcher, "GIT repository for %s doesn't exist in %s, cannot get sortable buildnumber, using old value" % (url, repodir)) + return None + os.chdir(repodir) - if not self._contains_ref(ud.tag, d): + if not self._contains_ref(rev, d): self.go(None, ud, d) - output = runfetchcmd("git rev-list %s -- 2> /dev/null | wc -l" % ud.tag, d, quiet=True) + output = runfetchcmd("git rev-list %s -- 2> /dev/null | wc -l" % rev, d, quiet=True) os.chdir(cwd) - sortable_revision = "%s+%s" % (output.split()[0], ud.tag) - bb.data.setVar(key, sortable_revision, d) - return sortable_revision - + buildindex = "%s" % output.split()[0] + bb.msg.debug(1, bb.msg.domain.Fetcher, "GIT repository for %s in %s is returning %s revisions in rev-list before %s" % (url, repodir, buildindex, rev)) + return buildindex diff --git a/bitbake-dev/lib/bb/providers.py b/bitbake-dev/lib/bb/providers.py index 8970fb3be1..6c1cf78eb3 100644 --- a/bitbake-dev/lib/bb/providers.py +++ b/bitbake-dev/lib/bb/providers.py @@ -191,7 +191,7 @@ def _filterProviders(providers, item, cfgData, dataCache): eligible.append(preferred_versions[pn][1]) # Now add latest verisons - for pn in pkg_pn.keys(): + for pn in sortpkg_pn.keys(): if pn in preferred_versions and preferred_versions[pn][1]: continue preferred_versions[pn] = findLatestProvider(pn, cfgData, dataCache, sortpkg_pn[pn][0]) diff --git a/bitbake-dev/lib/bb/server/__init__.py b/bitbake-dev/lib/bb/server/__init__.py new file mode 100644 index 0000000000..0dd04cf724 --- /dev/null +++ b/bitbake-dev/lib/bb/server/__init__.py @@ -0,0 +1 @@ +import xmlrpc diff --git a/bitbake-dev/lib/bb/xmlrpcserver.py b/bitbake-dev/lib/bb/server/none.py index ef061bc5dd..ef061bc5dd 100644 --- a/bitbake-dev/lib/bb/xmlrpcserver.py +++ b/bitbake-dev/lib/bb/server/none.py diff --git a/bitbake-dev/lib/bb/server/xmlrpc.py b/bitbake-dev/lib/bb/server/xmlrpc.py new file mode 100644 index 0000000000..c5937abd66 --- /dev/null +++ b/bitbake-dev/lib/bb/server/xmlrpc.py @@ -0,0 +1,145 @@ +# +# BitBake XMLRPC Server +# +# Copyright (C) 2006 - 2007 Michael 'Mickey' Lauer +# Copyright (C) 2006 - 2008 Richard Purdie +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License version 2 as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along +# with this program; if not, write to the Free Software Foundation, Inc., +# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + +""" + This module implements an xmlrpc server for BitBake. + + Use this by deriving a class from BitBakeXMLRPCServer and then adding + methods which you want to "export" via XMLRPC. If the methods have the + prefix xmlrpc_, then registering those function will happen automatically, + if not, you need to call register_function. + + Use register_idle_function() to add a function which the xmlrpc server + calls from within server_forever when no requests are pending. Make sure + that those functions are non-blocking or else you will introduce latency + in the server's main loop. +""" + +import bb +import xmlrpclib + +DEBUG = False + +from SimpleXMLRPCServer import SimpleXMLRPCServer, SimpleXMLRPCRequestHandler +import inspect, select + +class BitBakeServerCommands(): + def __init__(self, server, cooker): + self.cooker = cooker + self.server = server + + def registerEventHandler(self, host, port): + """ + Register a remote UI Event Handler + """ + s = xmlrpclib.Server("http://%s:%d" % (host, port), allow_none=True) + return bb.event.register_UIHhandler(s) + + def unregisterEventHandler(self, handlerNum): + """ + Unregister a remote UI Event Handler + """ + return bb.event.unregister_UIHhandler(handlerNum) + + def runCommand(self, command): + """ + Run a cooker command on the server + """ + return self.cooker.command.runCommand(command) + + def terminateServer(self): + """ + Trigger the server to quit + """ + self.server.quit = True + print "Server (cooker) exitting" + return + + def ping(self): + """ + Dummy method which can be used to check the server is still alive + """ + return True + +class BitBakeServer(SimpleXMLRPCServer): + # remove this when you're done with debugging + # allow_reuse_address = True + + def __init__(self, cooker, interface = ("localhost", 0)): + """ + Constructor + """ + SimpleXMLRPCServer.__init__(self, interface, + requestHandler=SimpleXMLRPCRequestHandler, + logRequests=False, allow_none=True) + self._idlefuns = {} + self.host, self.port = self.socket.getsockname() + #self.register_introspection_functions() + commands = BitBakeServerCommands(self, cooker) + self.autoregister_all_functions(commands, "") + + def autoregister_all_functions(self, context, prefix): + """ + Convenience method for registering all functions in the scope + of this class that start with a common prefix + """ + methodlist = inspect.getmembers(context, inspect.ismethod) + for name, method in methodlist: + if name.startswith(prefix): + self.register_function(method, name[len(prefix):]) + + def register_idle_function(self, function, data): + """Register a function to be called while the server is idle""" + assert callable(function) + self._idlefuns[function] = data + + def serve_forever(self): + """ + Serve Requests. Overloaded to honor a quit command + """ + self.quit = False + while not self.quit: + #print "Idle queue length %s" % len(self._idlefuns) + if len(self._idlefuns) == 0: + self.timeout = None + else: + self.timeout = 0 + self.handle_request() + #print "Idle timeout, running idle functions" + for function, data in self._idlefuns.items(): + try: + retval = function(self, data, False) + if not retval: + del self._idlefuns[function] + except SystemExit: + raise + except: + import traceback + traceback.print_exc() + pass + + # Tell idle functions we're exiting + for function, data in self._idlefuns.items(): + try: + retval = function(self, data, True) + except: + pass + + self.server_close() + return diff --git a/bitbake-dev/lib/bb/utils.py b/bitbake-dev/lib/bb/utils.py index 603c926422..5b0aaba4a7 100644 --- a/bitbake-dev/lib/bb/utils.py +++ b/bitbake-dev/lib/bb/utils.py @@ -21,8 +21,9 @@ BitBake Utility Functions digits = "0123456789" ascii_letters = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ" +separators = ".-" -import re, fcntl, os +import re, fcntl, os, types def explode_version(s): r = [] @@ -39,12 +40,15 @@ def explode_version(s): r.append(m.group(1)) s = m.group(2) continue + r.append(s[0]) s = s[1:] return r def vercmp_part(a, b): va = explode_version(a) vb = explode_version(b) + sa = False + sb = False while True: if va == []: ca = None @@ -56,6 +60,16 @@ def vercmp_part(a, b): cb = vb.pop(0) if ca == None and cb == None: return 0 + + if type(ca) is types.StringType: + sa = ca in separators + if type(cb) is types.StringType: + sb = cb in separators + if sa and not sb: + return -1 + if not sa and sb: + return 1 + if ca > cb: return 1 if ca < cb: |