Skip to content

Commit e2d8177

Browse files
macro_collector: be stricter about unusual macros
When looking for constructors, do complain if we see an unusual macro with a parameter: there's a significant chance that it's something new that will require specific handling. As a consequence, we need to explicitly skip more things that are known not to be constructors. Keep ignoring macros without parameters that don't look like constructors for the types we care about. Those probably don't matter. Signed-off-by: Gilles Peskine <[email protected]>
1 parent b4035db commit e2d8177

File tree

1 file changed

+27
-2
lines changed

1 file changed

+27
-2
lines changed

scripts/mbedtls_framework/macro_collector.py

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -279,6 +279,21 @@ def record_algorithm_subtype(self, name: str, expansion: str) -> None:
279279
r'(.+)')
280280
_deprecated_definition_re = re.compile(r'\s*MBEDTLS_DEPRECATED')
281281

282+
# Macro that is a destructor, not a constructor (i.e. takes a thing as
283+
# an argument and analyzes it, rather than constructing a thing).
284+
_destructor_name_re = re.compile(r'.*(_GET_|_IS_)|.*_LENGTH\Z')
285+
286+
# Macro that converts between things, rather than building a thing from
287+
# scratch.
288+
_conversion_macro_names = frozenset([
289+
'PSA_KEY_TYPE_KEY_PAIR_OF_PUBLIC_KEY',
290+
'PSA_KEY_TYPE_PUBLIC_KEY_OF_KEY_PAIR',
291+
'PSA_ALG_FULL_LENGTH_MAC',
292+
'PSA_ALG_AEAD_WITH_DEFAULT_LENGTH_TAG',
293+
'PSA_JPAKE_EXPECTED_INPUTS',
294+
'PSA_JPAKE_EXPECTED_OUTPUTS',
295+
])
296+
282297
def read_line(self, line):
283298
"""Parse a C header line and record the PSA identifier it defines if any.
284299
This function analyzes lines that start with "#define PSA_"
@@ -297,6 +312,12 @@ def read_line(self, line):
297312
# backward compatibility aliases that share
298313
# numerical values with non-deprecated values.
299314
return
315+
if re.match(self._destructor_name_re, name):
316+
# Not a constructor
317+
return
318+
if name in self._conversion_macro_names:
319+
# Not a constructor
320+
return
300321
if self.is_internal_name(name):
301322
# Macro only to build actual values
302323
return
@@ -324,9 +345,13 @@ def read_line(self, line):
324345
self.algorithms_from_hash[name] = self.algorithm_tester(name)
325346
elif name.startswith('PSA_KEY_USAGE_') and not parameter:
326347
self.key_usage_flags.add(name)
327-
else:
328-
# Other macro without parameter
348+
elif parameter is None:
349+
# Macro with no parameter, whose name does not start with one
350+
# of the prefixes we look for. Just ignore it.
329351
return
352+
else:
353+
raise Exception("Unsupported macro and parameter name: {}({})"
354+
.format(name, parameter))
330355

331356
_nonascii_re = re.compile(rb'[^\x00-\x7f]+')
332357
_continued_line_re = re.compile(rb'\\\r?\n\Z')

0 commit comments

Comments
 (0)