From bd18497110796c5d86cef202dc37798478c84cd2 Mon Sep 17 00:00:00 2001 From: Alexander Kanavin Date: Wed, 17 Jul 2024 20:22:14 +0200 Subject: lib/recipeutils: add a function to determine recipes with shared include files This functionality is needed for 'lockstep version upgrades' where several recipes need to be upgraded at the same time to produce a buildable outcome. The function itself obtains BBINCLUDED for each recipe and then massages the data until it takes the form of a list of sets: [{'cmake','cmake-native'}, {'qemu','qemu-native','qemu-system-native'}, ... ] There's also a selftest that checks for the above. Unfortunately this won't detect mutually exclusive recipes like mesa and mesa-gl as they're chosen with PREFERRED_PROVIDER and can't be enabled in the same build at the same time. ('devtool upgrade' will also accept just one of them but not the other) (From OE-Core rev: 2400920f8b84cca9d6c1f6a2e850630554fe00fa) Signed-off-by: Alexander Kanavin Signed-off-by: Richard Purdie --- meta/lib/oe/recipeutils.py | 37 +++++++++++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) (limited to 'meta/lib/oe') diff --git a/meta/lib/oe/recipeutils.py b/meta/lib/oe/recipeutils.py index f9d7dfe253..7586332fe0 100644 --- a/meta/lib/oe/recipeutils.py +++ b/meta/lib/oe/recipeutils.py @@ -1183,3 +1183,40 @@ def get_recipe_upgrade_status(recipes=None): pkgs_list = executor.map(_get_recipe_upgrade_status, data_copy_list) return pkgs_list + +def get_common_include_recipes(): + with bb.tinfoil.Tinfoil() as tinfoil: + tinfoil.prepare(config_only=False) + + recipes = tinfoil.all_recipe_files(variants=False) + + recipeincludes = {} + for fn in recipes: + data = tinfoil.parse_recipe_file(fn) + recipeincludes[fn] = {'bbincluded':data.getVar('BBINCLUDED').split(),'pn':data.getVar('PN')} + return _get_common_include_recipes(recipeincludes) + +def _get_common_include_recipes(recipeincludes_all): + recipeincludes = {} + for fn,data in recipeincludes_all.items(): + bbincluded_filtered = [i for i in data['bbincluded'] if os.path.dirname(i) == os.path.dirname(fn) and i != fn] + if bbincluded_filtered: + recipeincludes[data['pn']] = bbincluded_filtered + + recipeincludes_inverted = {} + for k,v in recipeincludes.items(): + for i in v: + recipeincludes_inverted.setdefault(i,set()).add(k) + + recipeincludes_inverted_filtered = {k:v for k,v in recipeincludes_inverted.items() if len(v) > 1} + + recipes_with_shared_includes = list() + for v in recipeincludes_inverted_filtered.values(): + recipeset = v + for v1 in recipeincludes_inverted_filtered.values(): + if recipeset.intersection(v1): + recipeset.update(v1) + if recipeset not in recipes_with_shared_includes: + recipes_with_shared_includes.append(recipeset) + + return recipes_with_shared_includes -- cgit v1.2.3-54-g00ecf