configure_file: emit FeatureNew when a cmake-formatted file has too many tokens

In commit 97a72a1c53 we started to allow
cmakedefine with 3 tokens, as cmake expects (unlike mesondefine). This
would silently start working even if the declared minimum version was
older than 0.54.1
This commit is contained in:
Eli Schwartz 2023-03-08 00:09:29 -05:00 committed by Dylan Baker
parent 83b4f14fce
commit a410bbdf12
2 changed files with 13 additions and 8 deletions

View File

@ -2611,7 +2611,7 @@ class Interpreter(InterpreterBase, HoldableObject):
file_encoding = kwargs['encoding'] file_encoding = kwargs['encoding']
missing_variables, confdata_useless = \ missing_variables, confdata_useless = \
mesonlib.do_conf_file(inputs_abs[0], ofile_abs, conf, mesonlib.do_conf_file(inputs_abs[0], ofile_abs, conf,
fmt, file_encoding) fmt, file_encoding, self.subproject)
if missing_variables: if missing_variables:
var_list = ", ".join(repr(m) for m in sorted(missing_variables)) var_list = ", ".join(repr(m) for m in sorted(missing_variables))
mlog.warning( mlog.warning(

View File

@ -44,6 +44,7 @@ if T.TYPE_CHECKING:
from ..coredata import KeyedOptionDictType, UserOption from ..coredata import KeyedOptionDictType, UserOption
from ..environment import Environment from ..environment import Environment
from ..compilers.compilers import Compiler from ..compilers.compilers import Compiler
from ..interpreterbase.baseobjects import SubProject
class _EnvPickleLoadable(Protocol): class _EnvPickleLoadable(Protocol):
@ -1205,7 +1206,7 @@ def do_replacement(regex: T.Pattern[str], line: str,
return re.sub(regex, variable_replace, line), missing_variables return re.sub(regex, variable_replace, line), missing_variables
def do_define(regex: T.Pattern[str], line: str, confdata: 'ConfigurationData', def do_define(regex: T.Pattern[str], line: str, confdata: 'ConfigurationData',
variable_format: Literal['meson', 'cmake', 'cmake@']) -> str: variable_format: Literal['meson', 'cmake', 'cmake@'], subproject: T.Optional[SubProject] = None) -> str:
def get_cmake_define(line: str, confdata: 'ConfigurationData') -> str: def get_cmake_define(line: str, confdata: 'ConfigurationData') -> str:
arr = line.split() arr = line.split()
define_value = [] define_value = []
@ -1218,8 +1219,12 @@ def do_define(regex: T.Pattern[str], line: str, confdata: 'ConfigurationData',
return ' '.join(define_value) return ' '.join(define_value)
arr = line.split() arr = line.split()
if variable_format == 'meson' and len(arr) != 2: if len(arr) != 2:
if variable_format == 'meson':
raise MesonException('#mesondefine does not contain exactly two tokens: %s' % line.strip()) raise MesonException('#mesondefine does not contain exactly two tokens: %s' % line.strip())
elif subproject is not None:
from ..interpreterbase.decorators import FeatureNew
FeatureNew.single_use('cmakedefine without exactly two tokens', '0.54.1', subproject)
varname = arr[1] varname = arr[1]
try: try:
@ -1255,7 +1260,7 @@ def get_variable_regex(variable_format: Literal['meson', 'cmake', 'cmake@'] = 'm
def do_conf_str(src: str, data: list, confdata: 'ConfigurationData', def do_conf_str(src: str, data: list, confdata: 'ConfigurationData',
variable_format: Literal['meson', 'cmake', 'cmake@'], variable_format: Literal['meson', 'cmake', 'cmake@'],
encoding: str = 'utf-8') -> T.Tuple[T.List[str], T.Set[str], bool]: encoding: str = 'utf-8', subproject: T.Optional[SubProject] = None) -> T.Tuple[T.List[str], T.Set[str], bool]:
def line_is_valid(line: str, variable_format: str) -> bool: def line_is_valid(line: str, variable_format: str) -> bool:
if variable_format == 'meson': if variable_format == 'meson':
if '#cmakedefine' in line: if '#cmakedefine' in line:
@ -1279,7 +1284,7 @@ def do_conf_str(src: str, data: list, confdata: 'ConfigurationData',
for line in data: for line in data:
if line.startswith(search_token): if line.startswith(search_token):
confdata_useless = False confdata_useless = False
line = do_define(regex, line, confdata, variable_format) line = do_define(regex, line, confdata, variable_format, subproject)
else: else:
if not line_is_valid(line, variable_format): if not line_is_valid(line, variable_format):
raise MesonException(f'Format error in {src}: saw "{line.strip()}" when format set to "{variable_format}"') raise MesonException(f'Format error in {src}: saw "{line.strip()}" when format set to "{variable_format}"')
@ -1293,14 +1298,14 @@ def do_conf_str(src: str, data: list, confdata: 'ConfigurationData',
def do_conf_file(src: str, dst: str, confdata: 'ConfigurationData', def do_conf_file(src: str, dst: str, confdata: 'ConfigurationData',
variable_format: Literal['meson', 'cmake', 'cmake@'], variable_format: Literal['meson', 'cmake', 'cmake@'],
encoding: str = 'utf-8') -> T.Tuple[T.Set[str], bool]: encoding: str = 'utf-8', subproject: T.Optional[SubProject] = None) -> T.Tuple[T.Set[str], bool]:
try: try:
with open(src, encoding=encoding, newline='') as f: with open(src, encoding=encoding, newline='') as f:
data = f.readlines() data = f.readlines()
except Exception as e: except Exception as e:
raise MesonException(f'Could not read input file {src}: {e!s}') raise MesonException(f'Could not read input file {src}: {e!s}')
(result, missing_variables, confdata_useless) = do_conf_str(src, data, confdata, variable_format, encoding) (result, missing_variables, confdata_useless) = do_conf_str(src, data, confdata, variable_format, encoding, subproject)
dst_tmp = dst + '~' dst_tmp = dst + '~'
try: try:
with open(dst_tmp, 'w', encoding=encoding, newline='') as f: with open(dst_tmp, 'w', encoding=encoding, newline='') as f: