aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJussi Pakkanen <jpakkane@gmail.com>2021-05-09 20:27:06 +0300
committerJussi Pakkanen <jpakkane@gmail.com>2021-05-09 20:27:06 +0300
commit2ca9bffc913685275d16d2bc1a0c873c9c09ca23 (patch)
tree405afe9286e90f9c9bd7e5f1d2689c0bd90fe291
parent1d06d4ca1a5a2da157966fad915f9d72d2228421 (diff)
downloadmeson-overrides.zip
meson-overrides.tar.gz
meson-overrides.tar.bz2
Add general override functionality. Closes #3001.overrides
-rw-r--r--mesonbuild/coredata.py23
-rw-r--r--mesonbuild/interpreter/interpreter.py4
-rwxr-xr-xrun_unittests.py5
-rw-r--r--test cases/unit/96 overriding/meson.build4
-rw-r--r--test cases/unit/96 overriding/native_overrides.txt2
-rw-r--r--test cases/unit/96 overriding/subprojects/somesub/meson.build3
6 files changed, 41 insertions, 0 deletions
diff --git a/mesonbuild/coredata.py b/mesonbuild/coredata.py
index 49b84b9..55b52d4 100644
--- a/mesonbuild/coredata.py
+++ b/mesonbuild/coredata.py
@@ -374,6 +374,22 @@ class DependencyCache:
def clear(self) -> None:
self.__cache.clear()
+
+class OptionOverrides:
+ def __init__(self):
+ self.subproject_overrides = {} # Overrides option value in all subprojects but not the main project.
+ # FIXME add per-project overrides here
+
+ def add_subprojects_override(self, key, value):
+ self.subproject_overrides[key] = value
+
+ def value_if_overridden(self, key, subproject): # FIXME add target as an argument?
+ if subproject == '':
+ return None
+ if key not in self.subproject_overrides:
+ return None
+ return self.subproject_overrides[key]
+
# Can't bind this near the class method it seems, sadly.
_V = T.TypeVar('_V')
@@ -400,6 +416,7 @@ class CoreData:
self.options: 'KeyedOptionDictType' = {}
self.cross_files = self.__load_config_files(options, scratch_dir, 'cross')
self.compilers = PerMachine(OrderedDict(), OrderedDict()) # type: PerMachine[T.Dict[str, Compiler]]
+ self.overrides = OptionOverrides()
# Set of subprojects that have already been initialized once, this is
# required to be stored and reloaded with the coredata, as we don't
@@ -415,6 +432,7 @@ class CoreData:
self.config_files = self.__load_config_files(options, scratch_dir, 'native')
self.builtin_options_libdir_cross_fixup()
self.init_builtins('')
+ self.init_overrides()
@staticmethod
def __load_config_files(options: argparse.Namespace, scratch_dir: str, ftype: str) -> T.List[str]:
@@ -541,6 +559,11 @@ class CoreData:
for key, opt in BUILTIN_OPTIONS_PER_MACHINE.items():
self.add_builtin_option(self.options, key.evolve(subproject=subproject, machine=for_machine), opt)
+ def init_overrides(self) -> None:
+ sections = MachineFileParser(self.config_files).sections
+ for k, v in sections.get('override_subprojects', {}).items():
+ self.overrides.add_subprojects_override(k, v)
+
@staticmethod
def add_builtin_option(opts_map: 'KeyedOptionDictType', key: OptionKey,
opt: 'BuiltinOption') -> None:
diff --git a/mesonbuild/interpreter/interpreter.py b/mesonbuild/interpreter/interpreter.py
index c67e840..a4c94ed 100644
--- a/mesonbuild/interpreter/interpreter.py
+++ b/mesonbuild/interpreter/interpreter.py
@@ -858,6 +858,10 @@ external dependencies (including libraries) must go to "dependencies".''')
def get_option_internal(self, optname: str):
key = OptionKey.from_string(optname).evolve(subproject=self.subproject)
+ maybe_v = self.coredata.overrides.value_if_overridden(optname, self.subproject)
+ if maybe_v is not None:
+ return maybe_v
+
if not key.is_project():
for opts in [self.coredata.options, compilers.base_options]:
v = opts.get(key)
diff --git a/run_unittests.py b/run_unittests.py
index 89b00f6..efa49a7 100755
--- a/run_unittests.py
+++ b/run_unittests.py
@@ -5702,6 +5702,11 @@ class AllPlatformTests(BasePlatformTests):
link_args = env.coredata.get_external_link_args(cc.for_machine, cc.language)
self.assertEqual(sorted(link_args), sorted(['-flto']))
+ def test_overrides(self):
+ testdir = os.path.join(self.unit_test_dir, '96 overriding')
+ native_file = os.path.join(testdir, 'native_overrides.txt')
+ self.init(testdir, extra_args=['--native-file', native_file])
+
class FailureTests(BasePlatformTests):
'''
Tests that test failure conditions. Build files here should be dynamically
diff --git a/test cases/unit/96 overriding/meson.build b/test cases/unit/96 overriding/meson.build
new file mode 100644
index 0000000..cbed903
--- /dev/null
+++ b/test cases/unit/96 overriding/meson.build
@@ -0,0 +1,4 @@
+project('mainprog', 'c')
+
+assert(get_option('buildtype') == 'debug')
+subproject('somesub')
diff --git a/test cases/unit/96 overriding/native_overrides.txt b/test cases/unit/96 overriding/native_overrides.txt
new file mode 100644
index 0000000..e40a2b2
--- /dev/null
+++ b/test cases/unit/96 overriding/native_overrides.txt
@@ -0,0 +1,2 @@
+[override_subprojects]
+buildtype = 'debugoptimized'
diff --git a/test cases/unit/96 overriding/subprojects/somesub/meson.build b/test cases/unit/96 overriding/subprojects/somesub/meson.build
new file mode 100644
index 0000000..f513bff
--- /dev/null
+++ b/test cases/unit/96 overriding/subprojects/somesub/meson.build
@@ -0,0 +1,3 @@
+project('somesub', 'c')
+
+assert(get_option('buildtype') == 'debugoptimized')