From 3752782cb77749ef11d947a26cfa7e4905662339 Mon Sep 17 00:00:00 2001 From: Charlie Davies Date: Thu, 18 Feb 2021 20:52:17 +0000 Subject: bitbake: bitbake: providers: introduce logic for REQUIRED_VERSION variable This commit adds checks during the findPreferredProvider function for a new variable REQUIRED_VERSION. This can be set, in exactly the same manner as PREFERRED_VERSION, on a per package basis to enforce the use of a particular version of a package. REQUIRED_VERSION is similar in behaviour to PREFERRED_VERSION except if the version specified by REQUIRED_VERSION is not found an error occurs and the execution of Bitbake stops. Fixes [YOCTO #10096] (Bitbake rev: 5cbf6d95fc1009e78e7d0745a49e0bf418b37abb) Signed-off-by: Charlie Davies Signed-off-by: Richard Purdie --- bitbake/lib/bb/providers.py | 56 +++++++++++++++++++++++++++++++++------------ 1 file changed, 41 insertions(+), 15 deletions(-) (limited to 'bitbake/lib/bb/providers.py') diff --git a/bitbake/lib/bb/providers.py b/bitbake/lib/bb/providers.py index e8241d90c0..09e5701f2e 100644 --- a/bitbake/lib/bb/providers.py +++ b/bitbake/lib/bb/providers.py @@ -85,6 +85,21 @@ def sortPriorities(pn, dataCache, pkg_pn = None): return tmp_pn +def versionVariableMatch(cfgData, keyword, pn): + """ + Return the value of the _VERSION variable if set. + """ + + # pn can contain '_', e.g. gcc-cross-x86_64 and an override cannot + # hence we do this manually rather than use OVERRIDES + ver = cfgData.getVar("%s_VERSION_pn-%s" % (keyword, pn)) + if not ver: + ver = cfgData.getVar("%s_VERSION_%s" % (keyword, pn)) + if not ver: + ver = cfgData.getVar("%s_VERSION" % keyword) + + return ver + def preferredVersionMatch(pe, pv, pr, preferred_e, preferred_v, preferred_r): """ Check if the version pe,pv,pr is the preferred one. @@ -100,19 +115,28 @@ def preferredVersionMatch(pe, pv, pr, preferred_e, preferred_v, preferred_r): def findPreferredProvider(pn, cfgData, dataCache, pkg_pn = None, item = None): """ - Find the first provider in pkg_pn with a PREFERRED_VERSION set. + Find the first provider in pkg_pn with REQUIRED_VERSION or PREFERRED_VERSION set. """ preferred_file = None preferred_ver = None + required = False - # pn can contain '_', e.g. gcc-cross-x86_64 and an override cannot - # hence we do this manually rather than use OVERRIDES - preferred_v = cfgData.getVar("PREFERRED_VERSION_pn-%s" % pn) - if not preferred_v: - preferred_v = cfgData.getVar("PREFERRED_VERSION_%s" % pn) - if not preferred_v: - preferred_v = cfgData.getVar("PREFERRED_VERSION") + required_v = versionVariableMatch(cfgData, "REQUIRED", pn) + preferred_v = versionVariableMatch(cfgData, "PREFERRED", pn) + + itemstr = "" + if item: + itemstr = " (for item %s)" % item + + if required_v is not None: + if preferred_v is not None: + logger.warn("REQUIRED_VERSION and PREFERRED_VERSION for package %s%s are both set using REQUIRED_VERSION %s", pn, itemstr, required_v) + else: + logger.debug("REQUIRED_VERSION is set for package %s%s", pn, itemstr) + # REQUIRED_VERSION always takes precedence over PREFERRED_VERSION + preferred_v = required_v + required = True if preferred_v: m = re.match(r'(\d+:)*(.*)(_.*)*', preferred_v) @@ -145,11 +169,9 @@ def findPreferredProvider(pn, cfgData, dataCache, pkg_pn = None, item = None): pv_str = preferred_v if not (preferred_e is None): pv_str = '%s:%s' % (preferred_e, pv_str) - itemstr = "" - if item: - itemstr = " (for item %s)" % item if preferred_file is None: - logger.warn("preferred version %s of %s not available%s", pv_str, pn, itemstr) + if not required: + logger.warn("preferred version %s of %s not available%s", pv_str, pn, itemstr) available_vers = [] for file_set in pkg_pn: for f in file_set: @@ -162,11 +184,15 @@ def findPreferredProvider(pn, cfgData, dataCache, pkg_pn = None, item = None): if available_vers: available_vers.sort() logger.warn("versions of %s available: %s", pn, ' '.join(available_vers)) + if required: + logger.error("required version %s of %s not available%s", pv_str, pn, itemstr) else: - logger.debug("selecting %s as PREFERRED_VERSION %s of package %s%s", preferred_file, pv_str, pn, itemstr) - - return (preferred_ver, preferred_file) + if required: + logger.debug("selecting %s as REQUIRED_VERSION %s of package %s%s", preferred_file, pv_str, pn, itemstr) + else: + logger.debug("selecting %s as PREFERRED_VERSION %s of package %s%s", preferred_file, pv_str, pn, itemstr) + return (preferred_ver, preferred_file, required) def findLatestProvider(pn, cfgData, dataCache, file_set): """ -- cgit v1.2.3-54-g00ecf