diff options
author | Jussi Pakkanen <jpakkane@gmail.com> | 2021-01-04 23:42:50 +0000 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-01-04 23:42:50 +0000 |
commit | d47a5c81a9af992eca42d857477f2bb5821712b6 (patch) | |
tree | 9c9ff772c696661a1582dc81c86273e8d975a13f /mesonbuild/interpreter.py | |
parent | 6b515c432109cf7ab488da37cddeb1752e91fa5c (diff) | |
parent | f14bf8b2ed052f68857ed3eaec08a326d335a3a4 (diff) | |
download | meson-d47a5c81a9af992eca42d857477f2bb5821712b6.zip meson-d47a5c81a9af992eca42d857477f2bb5821712b6.tar.gz meson-d47a5c81a9af992eca42d857477f2bb5821712b6.tar.bz2 |
Merge pull request #8080 from dcbaker/submit/option-key-type
Use an object for option keys
Diffstat (limited to 'mesonbuild/interpreter.py')
-rw-r--r-- | mesonbuild/interpreter.py | 103 |
1 files changed, 48 insertions, 55 deletions
diff --git a/mesonbuild/interpreter.py b/mesonbuild/interpreter.py index a4a9fb2..c20c205 100644 --- a/mesonbuild/interpreter.py +++ b/mesonbuild/interpreter.py @@ -21,7 +21,7 @@ from . import optinterpreter from . import compilers from .wrap import wrap, WrapMode from . import mesonlib -from .mesonlib import FileMode, MachineChoice, Popen_safe, listify, extract_as_list, has_path_sep, unholder +from .mesonlib import FileMode, MachineChoice, OptionKey, Popen_safe, listify, extract_as_list, has_path_sep, unholder from .dependencies import ExternalProgram from .dependencies import InternalDependency, Dependency, NotFoundDependency, DependencyException from .depfile import DepFile @@ -51,6 +51,7 @@ import typing as T import importlib if T.TYPE_CHECKING: + from .compilers import Compiler from .envconfig import MachineInfo from .environment import Environment from .modules import ExtensionModule @@ -77,11 +78,11 @@ class OverrideProgram(dependencies.ExternalProgram): class FeatureOptionHolder(InterpreterObject, ObjectHolder): - def __init__(self, env, name, option): + def __init__(self, env: 'Environment', name, option): InterpreterObject.__init__(self) ObjectHolder.__init__(self, option) if option.is_auto(): - self.held_object = env.coredata.builtins['auto_features'] + self.held_object = env.coredata.options[OptionKey('auto_features')] self.name = name self.methods.update({'enabled': self.enabled_method, 'disabled': self.disabled_method, @@ -1057,7 +1058,7 @@ find_library_permitted_kwargs = set([ find_library_permitted_kwargs |= set(['header_' + k for k in header_permitted_kwargs]) class CompilerHolder(InterpreterObject): - def __init__(self, compiler, env, subproject): + def __init__(self, compiler: 'Compiler', env: 'Environment', subproject: str): InterpreterObject.__init__(self) self.compiler = compiler self.environment = env @@ -1141,8 +1142,7 @@ class CompilerHolder(InterpreterObject): i.held_object.get_curdir(), idir) args += self.compiler.get_include_args(idir, False) if not nobuiltins: - for_machine = Interpreter.machine_from_native_kwarg(kwargs) - opts = self.environment.coredata.compiler_options[for_machine][self.compiler.language] + opts = self.environment.coredata.options args += self.compiler.get_option_compile_args(opts) if mode == 'link': args += self.compiler.get_option_link_args(opts) @@ -2150,7 +2150,7 @@ class MesonMain(InterpreterObject): @noPosargs @permittedKwargs({}) def is_unity_method(self, args, kwargs): - optval = self.interpreter.environment.coredata.get_builtin_option('unity') + optval = self.interpreter.environment.coredata.get_option(OptionKey('unity')) if optval == 'on' or (optval == 'subprojects' and self.interpreter.is_subproject()): return True return False @@ -2473,12 +2473,11 @@ class Interpreter(InterpreterBase): def get_non_matching_default_options(self) -> T.Iterator[T.Tuple[str, str, coredata.UserOption]]: env = self.environment for def_opt_name, def_opt_value in self.project_default_options.items(): - for opts in env.coredata.get_all_options(): - cur_opt_value = opts.get(def_opt_name) - if cur_opt_value is not None: - def_opt_value = env.coredata.validate_option_value(def_opt_name, def_opt_value) - if def_opt_value != cur_opt_value.value: - yield (def_opt_name, def_opt_value, cur_opt_value) + cur_opt_value = self.coredata.options.get(def_opt_name) + if cur_opt_value is not None: + def_opt_value = env.coredata.validate_option_value(def_opt_name, def_opt_value) + if def_opt_value != cur_opt_value.value: + yield (str(def_opt_name), def_opt_value, cur_opt_value) def build_func_dict(self): self.funcs.update({'add_global_arguments': self.func_add_global_arguments, @@ -2905,7 +2904,7 @@ external dependencies (including libraries) must go to "dependencies".''') return self.disabled_subproject(subp_name, disabled_feature=feature) default_options = mesonlib.stringlistify(kwargs.get('default_options', [])) - default_options = coredata.create_options_dict(default_options) + default_options = coredata.create_options_dict(default_options, subp_name) if subp_name == '': raise InterpreterException('Subproject name must not be empty.') @@ -3008,7 +3007,7 @@ external dependencies (including libraries) must go to "dependencies".''') def _do_subproject_cmake(self, subp_name, subdir, subdir_abs, default_options, kwargs): with mlog.nested(): new_build = self.build.copy() - prefix = self.coredata.builtins['prefix'].value + prefix = self.coredata.options[OptionKey('prefix')].value from .modules.cmake import CMakeSubprojectOptions options = kwargs.get('options', CMakeSubprojectOptions()) @@ -3049,28 +3048,21 @@ external dependencies (including libraries) must go to "dependencies".''') mlog.log() return result - def get_option_internal(self, optname): - raw_optname = optname - if self.is_subproject(): - optname = self.subproject + ':' + optname - + def get_option_internal(self, optname: str): + key = OptionKey.from_string(optname).evolve(subproject=self.subproject) - for opts in [ - self.coredata.base_options, compilers.base_options, self.coredata.builtins, - dict(self.coredata.get_prefixed_options_per_machine(self.coredata.builtins_per_machine)), - dict(self.coredata.flatten_lang_iterator( - self.coredata.get_prefixed_options_per_machine(self.coredata.compiler_options))), - ]: - v = opts.get(optname) - if v is None or v.yielding: - v = opts.get(raw_optname) - if v is not None: - return v + if not key.is_project(): + for opts in [self.coredata.options, compilers.base_options]: + v = opts.get(key) + if v is None or v.yielding: + v = opts.get(key.as_root()) + if v is not None: + return v try: - opt = self.coredata.user_options[optname] - if opt.yielding and ':' in optname and raw_optname in self.coredata.user_options: - popt = self.coredata.user_options[raw_optname] + opt = self.coredata.options[key] + if opt.yielding and key.subproject and key.as_root() in self.coredata.options: + popt = self.coredata.options[key.as_root()] if type(opt) is type(popt): opt = popt else: @@ -3082,7 +3074,7 @@ external dependencies (including libraries) must go to "dependencies".''') mlog.warning('Option {0!r} of type {1!r} in subproject {2!r} cannot yield ' 'to parent option of type {3!r}, ignoring parent value. ' 'Use -D{2}:{0}=value to set the value for this option manually' - '.'.format(raw_optname, opt_type, self.subproject, popt_type), + '.'.format(optname, opt_type, self.subproject, popt_type), location=self.current_node) return opt except KeyError: @@ -3124,7 +3116,7 @@ external dependencies (including libraries) must go to "dependencies".''') # The backend is already set when parsing subprojects if self.backend is not None: return - backend = self.coredata.get_builtin_option('backend') + backend = self.coredata.get_option(OptionKey('backend')) from .backend import backends self.backend = backends.get_backend_from_name(backend, self.build, self) @@ -3133,14 +3125,14 @@ external dependencies (including libraries) must go to "dependencies".''') if backend != self.backend.name: if self.backend.name.startswith('vs'): mlog.log('Auto detected Visual Studio backend:', mlog.bold(self.backend.name)) - self.coredata.set_builtin_option('backend', self.backend.name) + self.coredata.set_option(OptionKey('backend'), self.backend.name) # Only init backend options on first invocation otherwise it would # override values previously set from command line. if self.environment.first_invocation: self.coredata.init_backend_options(backend) - options = {k: v for k, v in self.environment.raw_options.items() if k.startswith('backend_')} + options = {k: v for k, v in self.environment.options.items() if k.is_backend()} self.coredata.set_options(options) @stringArgs @@ -3164,7 +3156,7 @@ external dependencies (including libraries) must go to "dependencies".''') if os.path.exists(self.option_file): oi = optinterpreter.OptionInterpreter(self.subproject) oi.process(self.option_file) - self.coredata.merge_user_options(oi.options) + self.coredata.update_project_options(oi.options) self.add_build_def_file(self.option_file) # Do not set default_options on reconfigure otherwise it would override @@ -3172,7 +3164,7 @@ external dependencies (including libraries) must go to "dependencies".''') # default_options in a project will trigger a reconfigure but won't # have any effect. self.project_default_options = mesonlib.stringlistify(kwargs.get('default_options', [])) - self.project_default_options = coredata.create_options_dict(self.project_default_options) + self.project_default_options = coredata.create_options_dict(self.project_default_options, self.subproject) if self.environment.first_invocation: default_options = self.project_default_options.copy() default_options.update(self.default_project_options) @@ -3214,7 +3206,7 @@ external dependencies (including libraries) must go to "dependencies".''') self.build.subproject_dir = self.subproject_dir # Load wrap files from this (sub)project. - wrap_mode = self.coredata.get_builtin_option('wrap_mode') + wrap_mode = self.coredata.get_option(OptionKey('wrap_mode')) if not self.is_subproject() or wrap_mode != WrapMode.nopromote: subdir = os.path.join(self.subdir, spdirname) r = wrap.Resolver(self.environment.get_source_dir(), subdir, wrap_mode) @@ -3526,7 +3518,7 @@ external dependencies (including libraries) must go to "dependencies".''') return progobj fallback = None - wrap_mode = self.coredata.get_builtin_option('wrap_mode') + wrap_mode = self.coredata.get_option(OptionKey('wrap_mode')) if wrap_mode != WrapMode.nofallback and self.environment.wrap_resolver: fallback = self.environment.wrap_resolver.find_program_provider(args) if fallback and wrap_mode == WrapMode.forcefallback: @@ -3830,8 +3822,8 @@ external dependencies (including libraries) must go to "dependencies".''') if self.get_subproject(subp_name): return self.get_subproject_dep(name, display_name, subp_name, varname, kwargs) - wrap_mode = self.coredata.get_builtin_option('wrap_mode') - force_fallback_for = self.coredata.get_builtin_option('force_fallback_for') + wrap_mode = self.coredata.get_option(OptionKey('wrap_mode')) + force_fallback_for = self.coredata.get_option(OptionKey('force_fallback_for')) force_fallback = (force_fallback or wrap_mode == WrapMode.forcefallback or name in force_fallback_for or @@ -3877,11 +3869,11 @@ external dependencies (including libraries) must go to "dependencies".''') # Explicitly listed fallback preferences for specific subprojects # take precedence over wrap-mode - force_fallback_for = self.coredata.get_builtin_option('force_fallback_for') + force_fallback_for = self.coredata.get_option(OptionKey('force_fallback_for')) if name in force_fallback_for or subp_name in force_fallback_for: mlog.log('Looking for a fallback subproject for the dependency', mlog.bold(display_name), 'because:\nUse of fallback was forced for that specific subproject') - elif self.coredata.get_builtin_option('wrap_mode') == WrapMode.nofallback: + elif self.coredata.get_option(OptionKey('wrap_mode')) == WrapMode.nofallback: mlog.log('Not looking for a fallback subproject for the dependency', mlog.bold(display_name), 'because:\nUse of fallback ' 'dependencies is disabled.') @@ -3889,7 +3881,7 @@ external dependencies (including libraries) must go to "dependencies".''') m = 'Dependency {!r} not found and fallback is disabled' raise DependencyException(m.format(display_name)) return self.notfound_dependency() - elif self.coredata.get_builtin_option('wrap_mode') == WrapMode.forcefallback: + elif self.coredata.get_option(OptionKey('wrap_mode')) == WrapMode.forcefallback: mlog.log('Looking for a fallback subproject for the dependency', mlog.bold(display_name), 'because:\nUse of fallback dependencies is forced.') else: @@ -4778,15 +4770,15 @@ different subdirectory. break def check_clang_asan_lundef(self) -> None: - if 'b_lundef' not in self.coredata.base_options: + if OptionKey('b_lundef') not in self.coredata.options: return - if 'b_sanitize' not in self.coredata.base_options: + if OptionKey('b_sanitize') not in self.coredata.options: return - if (self.coredata.base_options['b_lundef'].value and - self.coredata.base_options['b_sanitize'].value != 'none'): + if (self.coredata.options[OptionKey('b_lundef')].value and + self.coredata.options[OptionKey('b_sanitize')].value != 'none'): mlog.warning('''Trying to use {} sanitizer on Clang with b_lundef. This will probably not work. -Try setting b_lundef to false instead.'''.format(self.coredata.base_options['b_sanitize'].value), +Try setting b_lundef to false instead.'''.format(self.coredata.options[OptionKey('b_sanitize')].value), location=self.current_node) def evaluate_subproject_info(self, path_from_source_root, subproject_dir): @@ -4881,10 +4873,11 @@ Try setting b_lundef to false instead.'''.format(self.coredata.base_options['b_s # Check if user forces non-PIC static library. pic = True + key = OptionKey('b_staticpic') if 'pic' in kwargs: pic = kwargs['pic'] - elif 'b_staticpic' in self.environment.coredata.base_options: - pic = self.environment.coredata.base_options['b_staticpic'].value + elif key in self.environment.coredata.options: + pic = self.environment.coredata.options[key].value if pic: # Exclude sources from args and kwargs to avoid building them twice @@ -4901,7 +4894,7 @@ Try setting b_lundef to false instead.'''.format(self.coredata.base_options['b_s return BothLibrariesHolder(shared_holder, static_holder, self) def build_library(self, node, args, kwargs): - default_library = self.coredata.get_builtin_option('default_library', self.subproject) + default_library = self.coredata.get_option(OptionKey('default_library', subproject=self.subproject)) if default_library == 'shared': return self.build_target(node, args, kwargs, SharedLibraryHolder) elif default_library == 'static': |