mesonlib: make OptionOverrideProxy a true MutableMapping

So that we can actually use it anyplace that an OptionDictType could be
used. I've also done a bit optimizing/simplifying of the implementation.
This is needed for cuda, as it returns an OptionOverrideProxy where we
ask for an OptionDicType
pull/7795/head
Dylan Baker 4 years ago
parent 224a752489
commit 6d173f9678
  1. 3
      mesonbuild/coredata.py
  2. 49
      mesonbuild/mesonlib.py
  3. 2
      mesonbuild/mintro.py

@ -34,8 +34,9 @@ if T.TYPE_CHECKING:
from . import dependencies
from .compilers.compilers import Compiler, CompileResult # noqa: F401
from .environment import Environment
from .mesonlib import OptionOverrideProxy
OptionDictType = T.Dict[str, 'UserOption[T.Any]']
OptionDictType = T.Union[T.Dict[str, 'UserOption[T.Any]'], OptionOverrideProxy]
CompilerCheckCacheKey = T.Tuple[T.Tuple[str, ...], str, str, T.Tuple[str, ...], str]
version = '0.55.999'

@ -1696,7 +1696,7 @@ class OptionProxy(T.Generic[_T]):
self.value = value
class OptionOverrideProxy:
class OptionOverrideProxy(collections.abc.MutableMapping):
'''Mimic an option list but transparently override selected option
values.
@ -1706,23 +1706,30 @@ class OptionOverrideProxy:
# python 3.8 or typing_extensions
def __init__(self, overrides: T.Dict[str, T.Any], *options: 'OptionDictType'):
self.overrides = overrides
self.options = options
def __getitem__(self, option_name: str) -> T.Any:
for opts in self.options:
if option_name in opts:
return self._get_override(option_name, opts[option_name])
raise KeyError('Option not found', option_name)
def _get_override(self, option_name: str, base_opt: 'UserOption[T.Any]') -> T.Union[OptionProxy[T.Any], 'UserOption[T.Any]']:
if option_name in self.overrides:
return OptionProxy(base_opt.validate_value(self.overrides[option_name]))
return base_opt
def copy(self) -> T.Dict[str, T.Any]:
result = {} # type: T.Dict[str, T.Any]
for opts in self.options:
for option_name in opts:
result[option_name] = self._get_override(option_name, opts[option_name])
return result
self.overrides = overrides.copy()
self.options = {} # type: T.Dict[str, UserOption]
for o in options:
self.options.update(o)
def __getitem__(self, key: str) -> T.Union['UserOption', OptionProxy]:
if key in self.options:
opt = self.options[key]
if key in self.overrides:
return OptionProxy(opt.validate_value(self.overrides[key]))
return opt
raise KeyError('Option not found', key)
def __setitem__(self, key: str, value: T.Union['UserOption', OptionProxy]) -> None:
self.overrides[key] = value.value
def __delitem__(self, key: str) -> None:
del self.overrides[key]
def __iter__(self) -> T.Iterator[str]:
return iter(self.options)
def __len__(self) -> int:
return len(self.options)
def copy(self) -> 'OptionOverrideProxy':
return OptionOverrideProxy(self.overrides.copy(), self.options.copy())

@ -220,7 +220,7 @@ def list_buildoptions(coredata: cdata.CoreData, subprojects: T.Optional[T.List[s
sub_core_options[sub + ':' + k] = o
core_options.update(sub_core_options)
def add_keys(options: T.Dict[str, cdata.UserOption], section: str, machine: str = 'any') -> None:
def add_keys(options: 'cdata.OptionDictType', section: str, machine: str = 'any') -> None:
for key in sorted(options.keys()):
opt = options[key]
optdict = {'name': key, 'value': opt.value, 'section': section, 'machine': machine}

Loading…
Cancel
Save