types: Use import typing as T

pull/6316/head
Daniel Mensinger 5 years ago
parent ab988198c7
commit 0302a697b8
No known key found for this signature in database
GPG Key ID: 54DD94C131E277D4
  1. 48
      mesonbuild/ast/introspection.py
  2. 4
      mesonbuild/ast/postprocess.py
  3. 102
      mesonbuild/interpreterbase.py
  4. 39
      mesonbuild/mparser.py

@ -23,7 +23,7 @@ from ..mesonlib import MachineChoice
from ..interpreterbase import InvalidArguments, TYPE_nvar
from ..build import Executable, Jar, SharedLibrary, SharedModule, StaticLibrary
from ..mparser import BaseNode, ArithmeticNode, ArrayNode, ElementaryNode, IdNode, FunctionNode, StringNode
from typing import Any, Dict, List, Optional
import typing as T
import os
build_target_functions = ['executable', 'jar', 'library', 'shared_library', 'shared_module', 'static_library', 'both_libraries']
@ -33,7 +33,7 @@ class IntrospectionHelper:
def __init__(self, cross_file: str) -> None:
self.cross_file = cross_file # type: str
self.native_file = None # type: str
self.cmd_line_options = {} # type: Dict[str, str]
self.cmd_line_options = {} # type: T.Dict[str, str]
class IntrospectionInterpreter(AstInterpreter):
# Interpreter to detect the options without a build directory
@ -42,11 +42,11 @@ class IntrospectionInterpreter(AstInterpreter):
source_root: str,
subdir: str,
backend: str,
visitors: Optional[List[AstVisitor]] = None,
cross_file: Optional[str] = None,
visitors: T.Optional[T.List[AstVisitor]] = None,
cross_file: T.Optional[str] = None,
subproject: str = '',
subproject_dir: str = 'subprojects',
env: Optional[environment.Environment] = None) -> None:
env: T.Optional[environment.Environment] = None) -> None:
visitors = visitors if visitors is not None else []
super().__init__(source_root, subdir, subproject, visitors=visitors)
@ -61,9 +61,9 @@ class IntrospectionInterpreter(AstInterpreter):
self.option_file = os.path.join(self.source_root, self.subdir, 'meson_options.txt')
self.backend = backend
self.default_options = {'backend': self.backend}
self.project_data = {} # type: Dict[str, Any]
self.targets = [] # type: List[Dict[str, Any]]
self.dependencies = [] # type: List[Dict[str, Any]]
self.project_data = {} # type: T.Dict[str, T.Any]
self.targets = [] # type: T.List[T.Dict[str, T.Any]]
self.dependencies = [] # type: T.List[T.Dict[str, T.Any]]
self.project_node = None # type: BaseNode
self.funcs.update({
@ -79,7 +79,7 @@ class IntrospectionInterpreter(AstInterpreter):
'both_libraries': self.func_both_lib,
})
def func_project(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> None:
def func_project(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> None:
if self.project_node:
raise InvalidArguments('Second call to project()')
self.project_node = node
@ -136,7 +136,7 @@ class IntrospectionInterpreter(AstInterpreter):
except (mesonlib.MesonException, RuntimeError):
return
def func_add_languages(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> None:
def func_add_languages(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> None:
args = self.flatten_args(args)
for for_machine in [MachineChoice.BUILD, MachineChoice.HOST]:
for lang in sorted(args, key=compilers.sort_clink):
@ -149,7 +149,7 @@ class IntrospectionInterpreter(AstInterpreter):
if lang not in self.coredata.compilers[for_machine]:
self.environment.detect_compiler_for(lang, for_machine)
def func_dependency(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> None:
def func_dependency(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> None:
args = self.flatten_args(args)
kwargs = self.flatten_kwargs(kwargs)
if not args:
@ -173,7 +173,7 @@ class IntrospectionInterpreter(AstInterpreter):
'node': node
}]
def build_target(self, node: BaseNode, args: List[TYPE_nvar], kwargs_raw: Dict[str, TYPE_nvar], targetclass) -> Optional[Dict[str, Any]]:
def build_target(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs_raw: T.Dict[str, TYPE_nvar], targetclass) -> T.Optional[T.Dict[str, T.Any]]:
args = self.flatten_args(args)
if not args or not isinstance(args[0], str):
return None
@ -186,7 +186,7 @@ class IntrospectionInterpreter(AstInterpreter):
kwargs = self.flatten_kwargs(kwargs_raw, True)
source_nodes = [] # type: List[BaseNode]
source_nodes = [] # type: T.List[BaseNode]
while srcqueue:
curr = srcqueue.pop(0)
arg_node = None
@ -221,8 +221,8 @@ class IntrospectionInterpreter(AstInterpreter):
kwargs_reduced = {k: v.value if isinstance(v, ElementaryNode) else v for k, v in kwargs_reduced.items()}
kwargs_reduced = {k: v for k, v in kwargs_reduced.items() if not isinstance(v, BaseNode)}
for_machine = MachineChoice.HOST
objects = [] # type: List[Any]
empty_sources = [] # type: List[Any]
objects = [] # type: T.List[T.Any]
empty_sources = [] # type: T.List[T.Any]
# Passing the unresolved sources list causes errors
target = targetclass(name, self.subdir, self.subproject, for_machine, empty_sources, objects, self.environment, kwargs_reduced)
@ -243,7 +243,7 @@ class IntrospectionInterpreter(AstInterpreter):
self.targets += [new_target]
return new_target
def build_library(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def build_library(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
default_library = self.coredata.get_builtin_option('default_library')
if default_library == 'shared':
return self.build_target(node, args, kwargs, SharedLibrary)
@ -253,28 +253,28 @@ class IntrospectionInterpreter(AstInterpreter):
return self.build_target(node, args, kwargs, SharedLibrary)
return None
def func_executable(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_executable(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_target(node, args, kwargs, Executable)
def func_static_lib(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_static_lib(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_target(node, args, kwargs, StaticLibrary)
def func_shared_lib(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_shared_lib(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_target(node, args, kwargs, SharedLibrary)
def func_both_lib(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_both_lib(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_target(node, args, kwargs, SharedLibrary)
def func_shared_module(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_shared_module(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_target(node, args, kwargs, SharedModule)
def func_library(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_library(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_library(node, args, kwargs)
def func_jar(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_jar(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
return self.build_target(node, args, kwargs, Jar)
def func_build_target(self, node: BaseNode, args: List[TYPE_nvar], kwargs: Dict[str, TYPE_nvar]) -> Optional[Dict[str, Any]]:
def func_build_target(self, node: BaseNode, args: T.List[TYPE_nvar], kwargs: T.Dict[str, TYPE_nvar]) -> T.Optional[T.Dict[str, T.Any]]:
if 'target_type' not in kwargs:
return None
target_type = kwargs.pop('target_type')

@ -17,7 +17,7 @@
from . import AstVisitor
from .. import mparser
from typing import Dict
import typing as T
class AstIndentationGenerator(AstVisitor):
def __init__(self) -> None:
@ -77,7 +77,7 @@ class AstIndentationGenerator(AstVisitor):
class AstIDGenerator(AstVisitor):
def __init__(self) -> None:
self.counter = {} # type: Dict[str, int]
self.counter = {} # type: T.Dict[str, int]
def visit_default_func(self, node: mparser.BaseNode) -> None:
name = type(node).__name__

@ -21,16 +21,16 @@ from . import environment, dependencies
import os, copy, re
import collections.abc
from functools import wraps
from typing import Any, Callable, ClassVar, Dict, Generic, List, Set, Sequence, Tuple, TypeVar, Optional, Union
import typing as T
class InterpreterObject:
def __init__(self):
self.methods = {} # type: Dict[str, Callable]
self.methods = {} # type: T.Dict[str, T.Callable]
# Current node set during a method call. This can be used as location
# when printing a warning message during a method call.
self.current_node = None # type: mparser.BaseNode
def method_call(self, method_name: str, args: List[Union[mparser.BaseNode, str, int, float, bool, list, dict, 'InterpreterObject', 'ObjectHolder']], kwargs: Dict[str, Union[mparser.BaseNode, str, int, float, bool, list, dict, 'InterpreterObject', 'ObjectHolder']]):
def method_call(self, method_name: str, args: T.List[T.Union[mparser.BaseNode, str, int, float, bool, list, dict, 'InterpreterObject', 'ObjectHolder']], kwargs: T.Dict[str, T.Union[mparser.BaseNode, str, int, float, bool, list, dict, 'InterpreterObject', 'ObjectHolder']]):
if method_name in self.methods:
method = self.methods[method_name]
if not getattr(method, 'no-args-flattening', False):
@ -38,24 +38,24 @@ class InterpreterObject:
return method(args, kwargs)
raise InvalidCode('Unknown method "%s" in object.' % method_name)
TV_InterpreterObject = TypeVar('TV_InterpreterObject')
TV_InterpreterObject = T.TypeVar('TV_InterpreterObject')
class ObjectHolder(Generic[TV_InterpreterObject]):
def __init__(self, obj: InterpreterObject, subproject: Optional[str] = None):
class ObjectHolder(T.Generic[TV_InterpreterObject]):
def __init__(self, obj: InterpreterObject, subproject: T.Optional[str] = None):
self.held_object = obj # type: InterpreterObject
self.subproject = subproject # type: str
def __repr__(self):
return '<Holder: {!r}>'.format(self.held_object)
TYPE_elementary = Union[str, int, float, bool]
TYPE_var = Union[TYPE_elementary, list, dict, InterpreterObject, ObjectHolder]
TYPE_nvar = Union[TYPE_var, mparser.BaseNode]
TYPE_nkwargs = Dict[Union[mparser.BaseNode, str], TYPE_nvar]
TYPE_elementary = T.Union[str, int, float, bool]
TYPE_var = T.Union[TYPE_elementary, list, dict, InterpreterObject, ObjectHolder]
TYPE_nvar = T.Union[TYPE_var, mparser.BaseNode]
TYPE_nkwargs = T.Dict[T.Union[mparser.BaseNode, str], TYPE_nvar]
# Decorators for method calls.
def check_stringlist(a: Any, msg: str = 'Arguments must be strings.') -> None:
def check_stringlist(a: T.Any, msg: str = 'Arguments must be strings.') -> None:
if not isinstance(a, list):
mlog.debug('Not a list:', str(a))
raise InvalidArguments('Argument not a list.')
@ -124,13 +124,13 @@ def _get_callee_args(wrapped_args, want_subproject: bool = False):
kwargs = kwargs if kwargs is not None else {}
return s, node, args, kwargs, subproject
def flatten(args: Union[TYPE_nvar, List[TYPE_nvar]]) -> List[TYPE_nvar]:
def flatten(args: T.Union[TYPE_nvar, T.List[TYPE_nvar]]) -> T.List[TYPE_nvar]:
if isinstance(args, mparser.StringNode):
assert isinstance(args.value, str)
return [args.value]
if not isinstance(args, collections.abc.Sequence):
return [args]
result = [] # type: List[TYPE_nvar]
result = [] # type: T.List[TYPE_nvar]
for a in args:
if isinstance(a, list):
rest = flatten(a)
@ -185,8 +185,8 @@ def disablerIfNotFound(f):
class permittedKwargs:
def __init__(self, permitted: Set[str]) -> None:
self.permitted = permitted # type: Set[str]
def __init__(self, permitted: T.Set[str]) -> None:
self.permitted = permitted # type: T.Set[str]
def __call__(self, f):
@wraps(f)
@ -206,7 +206,7 @@ class FeatureCheckBase:
# Class variable, shared across all instances
#
# Format: {subproject: {feature_version: set(feature_names)}}
feature_registry = {} # type: ClassVar[Dict[str, Dict[str, Set[str]]]]
feature_registry = {} # type: T.ClassVar[T.Dict[str, T.Dict[str, T.Set[str]]]]
def __init__(self, feature_name: str, version: str) -> None:
self.feature_name = feature_name # type: str
@ -293,7 +293,7 @@ class FeatureDeprecated(FeatureCheckBase):
class FeatureCheckKwargsBase:
def __init__(self, feature_name: str, feature_version: str, kwargs: List[str]) -> None:
def __init__(self, feature_name: str, feature_version: str, kwargs: T.List[str]) -> None:
self.feature_name = feature_name
self.feature_version = feature_version
self.kwargs = kwargs
@ -377,11 +377,11 @@ class InterpreterBase:
def __init__(self, source_root: str, subdir: str, subproject: str) -> None:
self.source_root = source_root
self.funcs = {} # type: Dict[str, Callable[[mparser.BaseNode, List[TYPE_nvar], Dict[str, TYPE_nvar]], TYPE_var]]
self.builtin = {} # type: Dict[str, InterpreterObject]
self.funcs = {} # type: T.Dict[str, T.Callable[[mparser.BaseNode, T.List[TYPE_nvar], T.Dict[str, TYPE_nvar]], TYPE_var]]
self.builtin = {} # type: T.Dict[str, InterpreterObject]
self.subdir = subdir
self.subproject = subproject
self.variables = {} # type: Dict[str, TYPE_var]
self.variables = {} # type: T.Dict[str, TYPE_var]
self.argument_depth = 0
self.current_lineno = -1
# Current node set during a function call. This can be used as location
@ -403,7 +403,7 @@ class InterpreterBase:
me.file = mesonfile
raise me
def join_path_strings(self, args: Sequence[str]) -> str:
def join_path_strings(self, args: T.Sequence[str]) -> str:
return os.path.join(*args).replace('\\', '/')
def parse_project(self) -> None:
@ -430,7 +430,7 @@ class InterpreterBase:
except SubdirDoneRequest:
pass
def evaluate_codeblock(self, node: mparser.CodeBlockNode, start: int = 0, end: Optional[int] = None) -> None:
def evaluate_codeblock(self, node: mparser.CodeBlockNode, start: int = 0, end: T.Optional[int] = None) -> None:
if node is None:
return
if not isinstance(node, mparser.CodeBlockNode):
@ -454,7 +454,7 @@ class InterpreterBase:
raise e
i += 1 # In THE FUTURE jump over blocks and stuff.
def evaluate_statement(self, cur: mparser.BaseNode) -> Optional[TYPE_var]:
def evaluate_statement(self, cur: mparser.BaseNode) -> T.Optional[TYPE_var]:
if isinstance(cur, mparser.FunctionNode):
return self.function_call(cur)
elif isinstance(cur, mparser.AssignmentNode):
@ -512,10 +512,10 @@ class InterpreterBase:
return arguments
@FeatureNew('dict', '0.47.0')
def evaluate_dictstatement(self, cur: mparser.DictNode) -> Dict[str, Any]:
def evaluate_dictstatement(self, cur: mparser.DictNode) -> T.Dict[str, T.Any]:
(arguments, kwargs) = self.reduce_arguments(cur.args, resolve_key_nodes=False)
assert (not arguments)
result = {} # type: Dict[str, Any]
result = {} # type: T.Dict[str, T.Any]
self.argument_depth += 1
for key, value in kwargs.items():
if not isinstance(key, mparser.StringNode):
@ -530,7 +530,7 @@ class InterpreterBase:
self.argument_depth -= 1
return result
def evaluate_notstatement(self, cur: mparser.NotNode) -> Union[bool, Disabler]:
def evaluate_notstatement(self, cur: mparser.NotNode) -> T.Union[bool, Disabler]:
v = self.evaluate_statement(cur.value)
if isinstance(v, Disabler):
return v
@ -538,7 +538,7 @@ class InterpreterBase:
raise InterpreterException('Argument to "not" is not a boolean.')
return not v
def evaluate_if(self, node: mparser.IfClauseNode) -> Optional[Disabler]:
def evaluate_if(self, node: mparser.IfClauseNode) -> T.Optional[Disabler]:
assert(isinstance(node, mparser.IfClauseNode))
for i in node.ifs:
result = self.evaluate_statement(i.condition)
@ -553,19 +553,19 @@ class InterpreterBase:
self.evaluate_codeblock(node.elseblock)
return None
def validate_comparison_types(self, val1: Any, val2: Any) -> bool:
def validate_comparison_types(self, val1: T.Any, val2: T.Any) -> bool:
if type(val1) != type(val2):
return False
return True
def evaluate_in(self, val1: Any, val2: Any) -> bool:
def evaluate_in(self, val1: T.Any, val2: T.Any) -> bool:
if not isinstance(val1, (str, int, float, ObjectHolder)):
raise InvalidArguments('lvalue of "in" operator must be a string, integer, float, or object')
if not isinstance(val2, (list, dict)):
raise InvalidArguments('rvalue of "in" operator must be an array or a dict')
return val1 in val2
def evaluate_comparison(self, node: mparser.ComparisonNode) -> Union[bool, Disabler]:
def evaluate_comparison(self, node: mparser.ComparisonNode) -> T.Union[bool, Disabler]:
val1 = self.evaluate_statement(node.left)
if isinstance(val1, Disabler):
return val1
@ -610,7 +610,7 @@ The result of this is undefined and will become a hard error in a future Meson r
else:
raise InvalidCode('You broke my compare eval.')
def evaluate_andstatement(self, cur: mparser.AndNode) -> Union[bool, Disabler]:
def evaluate_andstatement(self, cur: mparser.AndNode) -> T.Union[bool, Disabler]:
l = self.evaluate_statement(cur.left)
if isinstance(l, Disabler):
return l
@ -625,7 +625,7 @@ The result of this is undefined and will become a hard error in a future Meson r
raise InterpreterException('Second argument to "and" is not a boolean.')
return r
def evaluate_orstatement(self, cur: mparser.OrNode) -> Union[bool, Disabler]:
def evaluate_orstatement(self, cur: mparser.OrNode) -> T.Union[bool, Disabler]:
l = self.evaluate_statement(cur.left)
if isinstance(l, Disabler):
return l
@ -640,7 +640,7 @@ The result of this is undefined and will become a hard error in a future Meson r
raise InterpreterException('Second argument to "or" is not a boolean.')
return r
def evaluate_uminusstatement(self, cur) -> Union[int, Disabler]:
def evaluate_uminusstatement(self, cur) -> T.Union[int, Disabler]:
v = self.evaluate_statement(cur.value)
if isinstance(v, Disabler):
return v
@ -656,7 +656,7 @@ The result of this is undefined and will become a hard error in a future Meson r
raise InvalidCode('The division operator can only append a string.')
return self.join_path_strings((l, r))
def evaluate_division(self, l: Any, r: Any) -> Union[int, str]:
def evaluate_division(self, l: T.Any, r: T.Any) -> T.Union[int, str]:
if isinstance(l, str) or isinstance(r, str):
return self.evaluate_path_join(l, r)
if isinstance(l, int) and isinstance(r, int):
@ -665,7 +665,7 @@ The result of this is undefined and will become a hard error in a future Meson r
return l // r
raise InvalidCode('Division works only with strings or integers.')
def evaluate_arithmeticstatement(self, cur: mparser.ArithmeticNode) -> Union[int, str, dict, list, Disabler]:
def evaluate_arithmeticstatement(self, cur: mparser.ArithmeticNode) -> T.Union[int, str, dict, list, Disabler]:
l = self.evaluate_statement(cur.left)
if isinstance(l, Disabler):
return l
@ -751,7 +751,7 @@ The result of this is undefined and will become a hard error in a future Meson r
# Remember that all variables are immutable. We must always create a
# full new variable and then assign it.
old_variable = self.get_variable(varname)
new_value = None # type: Union[str, int, float, bool, dict, list]
new_value = None # type: T.Union[str, int, float, bool, dict, list]
if isinstance(old_variable, str):
if not isinstance(addition, str):
raise InvalidArguments('The += operator requires a string on the right hand side if the variable on the left is a string')
@ -803,14 +803,14 @@ The result of this is undefined and will become a hard error in a future Meson r
# We are already checking for the existance of __getitem__, so this should be save
raise InterpreterException('Index %d out of bounds of array of size %d.' % (index, len(iobject))) # type: ignore
def function_call(self, node: mparser.FunctionNode) -> Optional[TYPE_var]:
def function_call(self, node: mparser.FunctionNode) -> T.Optional[TYPE_var]:
func_name = node.func_name
(posargs, kwargs) = self.reduce_arguments(node.args)
if is_disabled(posargs, kwargs) and func_name != 'set_variable' and func_name != 'is_disabler':
return Disabler()
if func_name in self.funcs:
func = self.funcs[func_name]
func_args = posargs # type: Any
func_args = posargs # type: T.Any
if not getattr(func, 'no-args-flattening', False):
func_args = flatten(posargs)
@ -859,7 +859,7 @@ The result of this is undefined and will become a hard error in a future Meson r
obj.current_node = node
return obj.method_call(method_name, args, self.kwargs_string_keys(kwargs))
def bool_method_call(self, obj: bool, method_name: str, posargs: List[TYPE_nvar]) -> Union[str, int]:
def bool_method_call(self, obj: bool, method_name: str, posargs: T.List[TYPE_nvar]) -> T.Union[str, int]:
if method_name == 'to_string':
if not posargs:
if obj:
@ -881,7 +881,7 @@ The result of this is undefined and will become a hard error in a future Meson r
else:
raise InterpreterException('Unknown method "%s" for a boolean.' % method_name)
def int_method_call(self, obj: int, method_name: str, posargs: List[TYPE_nvar]) -> Union[str, bool]:
def int_method_call(self, obj: int, method_name: str, posargs: T.List[TYPE_nvar]) -> T.Union[str, bool]:
if method_name == 'is_even':
if not posargs:
return obj % 2 == 0
@ -901,7 +901,7 @@ The result of this is undefined and will become a hard error in a future Meson r
raise InterpreterException('Unknown method "%s" for an integer.' % method_name)
@staticmethod
def _get_one_string_posarg(posargs: List[TYPE_nvar], method_name: str) -> str:
def _get_one_string_posarg(posargs: T.List[TYPE_nvar], method_name: str) -> str:
if len(posargs) > 1:
m = '{}() must have zero or one arguments'
raise InterpreterException(m.format(method_name))
@ -913,7 +913,7 @@ The result of this is undefined and will become a hard error in a future Meson r
return s
return None
def string_method_call(self, obj: str, method_name: str, posargs: List[TYPE_nvar]) -> Union[str, int, bool, List[str]]:
def string_method_call(self, obj: str, method_name: str, posargs: T.List[TYPE_nvar]) -> T.Union[str, int, bool, T.List[str]]:
if method_name == 'strip':
s1 = self._get_one_string_posarg(posargs, 'strip')
if s1 is not None:
@ -962,7 +962,7 @@ The result of this is undefined and will become a hard error in a future Meson r
return mesonlib.version_compare(obj, cmpr)
raise InterpreterException('Unknown method "%s" for a string.' % method_name)
def format_string(self, templ: str, args: List[TYPE_nvar]) -> str:
def format_string(self, templ: str, args: T.List[TYPE_nvar]) -> str:
arg_strings = []
for arg in args:
if isinstance(arg, mparser.BaseNode):
@ -982,7 +982,7 @@ The result of this is undefined and will become a hard error in a future Meson r
def unknown_function_called(self, func_name: str) -> None:
raise InvalidCode('Unknown function "%s".' % func_name)
def array_method_call(self, obj: list, method_name: str, posargs: List[TYPE_nvar]) -> TYPE_var:
def array_method_call(self, obj: list, method_name: str, posargs: T.List[TYPE_nvar]) -> TYPE_var:
if method_name == 'contains':
def check_contains(el: list) -> bool:
if len(posargs) != 1:
@ -1022,7 +1022,7 @@ The result of this is undefined and will become a hard error in a future Meson r
m = 'Arrays do not have a method called {!r}.'
raise InterpreterException(m.format(method_name))
def dict_method_call(self, obj: dict, method_name: str, posargs: List[TYPE_nvar]) -> TYPE_var:
def dict_method_call(self, obj: dict, method_name: str, posargs: T.List[TYPE_nvar]) -> TYPE_var:
if method_name in ('has_key', 'get'):
if method_name == 'has_key':
if len(posargs) != 1:
@ -1058,15 +1058,15 @@ The result of this is undefined and will become a hard error in a future Meson r
raise InterpreterException('Dictionaries do not have a method called "%s".' % method_name)
def reduce_arguments(self, args: mparser.ArgumentNode, resolve_key_nodes: bool = True) -> Tuple[List[TYPE_nvar], TYPE_nkwargs]:
def reduce_arguments(self, args: mparser.ArgumentNode, resolve_key_nodes: bool = True) -> T.Tuple[T.List[TYPE_nvar], TYPE_nkwargs]:
assert(isinstance(args, mparser.ArgumentNode))
if args.incorrect_order():
raise InvalidArguments('All keyword arguments must be after positional arguments.')
self.argument_depth += 1
reduced_pos = [self.evaluate_statement(arg) for arg in args.arguments] # type: List[TYPE_nvar]
reduced_pos = [self.evaluate_statement(arg) for arg in args.arguments] # type: T.List[TYPE_nvar]
reduced_kw = {} # type: TYPE_nkwargs
for key, val in args.kwargs.items():
reduced_key = key # type: Union[str, mparser.BaseNode]
reduced_key = key # type: T.Union[str, mparser.BaseNode]
reduced_val = val # type: TYPE_nvar
if resolve_key_nodes and isinstance(key, mparser.IdNode):
assert isinstance(key.value, str)
@ -1092,8 +1092,8 @@ The result of this is undefined and will become a hard error in a future Meson r
kwargs[k] = v
return kwargs
def kwargs_string_keys(self, kwargs: TYPE_nkwargs) -> Dict[str, TYPE_nvar]:
kw = {} # type: Dict[str, TYPE_nvar]
def kwargs_string_keys(self, kwargs: TYPE_nkwargs) -> T.Dict[str, TYPE_nvar]:
kw = {} # type: T.Dict[str, TYPE_nvar]
for key, val in kwargs.items():
if not isinstance(key, str):
raise InterpreterException('Key of kwargs is not a string')
@ -1137,7 +1137,7 @@ To specify a keyword argument, use : instead of =.''')
return self.variables[varname]
raise InvalidCode('Unknown variable "%s".' % varname)
def is_assignable(self, value: Any) -> bool:
def is_assignable(self, value: T.Any) -> bool:
return isinstance(value, (InterpreterObject, dependencies.Dependency,
str, int, list, dict, mesonlib.File))

@ -17,11 +17,10 @@ import codecs
import textwrap
import types
import typing as T
from typing import Dict, Generic, Generator, List, Tuple, TypeVar, Optional, Union, TYPE_CHECKING
from .mesonlib import MesonException
from . import mlog
if TYPE_CHECKING:
if T.TYPE_CHECKING:
from .ast import AstVisitor
# This is the regex for the supported escape sequences of a regular string
@ -77,16 +76,16 @@ class BlockParseException(MesonException):
self.lineno = lineno
self.colno = colno
TV_TokenTypes = TypeVar('TV_TokenTypes', int, str, bool)
TV_TokenTypes = T.TypeVar('TV_TokenTypes', int, str, bool)
class Token(Generic[TV_TokenTypes]):
def __init__(self, tid: str, filename: str, line_start: int, lineno: int, colno: int, bytespan: Tuple[int, int], value: TV_TokenTypes) -> None:
class Token(T.Generic[TV_TokenTypes]):
def __init__(self, tid: str, filename: str, line_start: int, lineno: int, colno: int, bytespan: T.Tuple[int, int], value: TV_TokenTypes) -> None:
self.tid = tid # type: str
self.filename = filename # type: str
self.line_start = line_start # type: int
self.lineno = lineno # type: int
self.colno = colno # type: int
self.bytespan = bytespan # type: Tuple[int, int]
self.bytespan = bytespan # type: T.Tuple[int, int]
self.value = value # type: TV_TokenTypes
def __eq__(self, other) -> bool:
@ -150,7 +149,7 @@ class Lexer:
col = 0
while loc < len(self.code):
matched = False
value = None # type: Union[str, bool, int]
value = None # type: T.Union[str, bool, int]
for (tid, reg) in self.token_specification:
mo = reg.match(self.code, loc)
if mo:
@ -227,7 +226,7 @@ class Lexer:
raise ParseException('lexer', self.getline(line_start), lineno, col)
class BaseNode:
def __init__(self, lineno: int, colno: int, filename: str, end_lineno: Optional[int] = None, end_colno: Optional[int] = None) -> None:
def __init__(self, lineno: int, colno: int, filename: str, end_lineno: T.Optional[int] = None, end_colno: T.Optional[int] = None) -> None:
self.lineno = lineno # type: int
self.colno = colno # type: int
self.filename = filename # type: str
@ -246,11 +245,11 @@ class BaseNode:
if callable(func):
func(self)
class ElementaryNode(Generic[TV_TokenTypes], BaseNode):
class ElementaryNode(T.Generic[TV_TokenTypes], BaseNode):
def __init__(self, token: Token[TV_TokenTypes]) -> None:
super().__init__(token.lineno, token.colno, token.filename)
self.value = token.value # type: TV_TokenTypes
self.bytespan = token.bytespan # type: Tuple[int, int]
self.bytespan = token.bytespan # type: T.Tuple[int, int]
class BooleanNode(ElementaryNode[bool]):
def __init__(self, token: Token[bool]) -> None:
@ -287,9 +286,9 @@ class BreakNode(ElementaryNode):
class ArgumentNode(BaseNode):
def __init__(self, token: Token[TV_TokenTypes]) -> None:
super().__init__(token.lineno, token.colno, token.filename)
self.arguments = [] # type: List[BaseNode]
self.commas = [] # type: List[Token[TV_TokenTypes]]
self.kwargs = {} # type: Dict[BaseNode, BaseNode]
self.arguments = [] # type: T.List[BaseNode]
self.commas = [] # type: T.List[Token[TV_TokenTypes]]
self.kwargs = {} # type: T.Dict[BaseNode, BaseNode]
self.order_error = False
def prepend(self, statement: BaseNode) -> None:
@ -374,7 +373,7 @@ class NotNode(BaseNode):
class CodeBlockNode(BaseNode):
def __init__(self, token: Token[TV_TokenTypes]) -> None:
super().__init__(token.lineno, token.colno, token.filename)
self.lines = [] # type: List[BaseNode]
self.lines = [] # type: T.List[BaseNode]
class IndexNode(BaseNode):
def __init__(self, iobject: BaseNode, index: BaseNode) -> None:
@ -412,9 +411,9 @@ class PlusAssignmentNode(BaseNode):
self.value = value # type: BaseNode
class ForeachClauseNode(BaseNode):
def __init__(self, token: Token, varnames: List[str], items: BaseNode, block: CodeBlockNode) -> None:
def __init__(self, token: Token, varnames: T.List[str], items: BaseNode, block: CodeBlockNode) -> None:
super().__init__(token.lineno, token.colno, token.filename)
self.varnames = varnames # type: List[str]
self.varnames = varnames # type: T.List[str]
self.items = items # type: BaseNode
self.block = block # type: CodeBlockNode
@ -427,8 +426,8 @@ class IfNode(BaseNode):
class IfClauseNode(BaseNode):
def __init__(self, linenode: BaseNode) -> None:
super().__init__(linenode.lineno, linenode.colno, linenode.filename)
self.ifs = [] # type: List[IfNode]
self.elseblock = EmptyNode(linenode.lineno, linenode.colno, linenode.filename) # type: Union[EmptyNode, CodeBlockNode]
self.ifs = [] # type: T.List[IfNode]
self.elseblock = EmptyNode(linenode.lineno, linenode.colno, linenode.filename) # type: T.Union[EmptyNode, CodeBlockNode]
class UMinusNode(BaseNode):
def __init__(self, current_location: Token, value: BaseNode):
@ -722,7 +721,7 @@ class Parser:
self.expect('id')
assert isinstance(t.value, str)
varname = t
varnames = [t.value] # type: List[str]
varnames = [t.value] # type: T.List[str]
if self.accept('comma'):
t = self.current
@ -754,7 +753,7 @@ class Parser:
b = self.codeblock()
clause.ifs.append(IfNode(s, s, b))
def elseblock(self) -> Optional[CodeBlockNode]:
def elseblock(self) -> T.Optional[CodeBlockNode]:
if self.accept('else'):
self.expect('eol')
return self.codeblock()

Loading…
Cancel
Save