18 lines
1.5 KiB
Python
18 lines
1.5 KiB
Python
#!/usr/bin/env python3
|
|
"""Keep tupleconcat's b declaration C89-safe and assignment after validation."""
|
|
import re
|
|
import sys
|
|
from pathlib import Path
|
|
source = Path(sys.argv[1] if len(sys.argv) > 1 else 'cpython/Objects/tupleobject.c')
|
|
match = re.search(r'tupleconcat\(PyTupleObject \*a, PyObject \*bb\)\n\{(.*?)\n\}', source.read_text(), re.S)
|
|
assert match, 'tupleconcat definition missing'
|
|
body = match.group(1)
|
|
assert re.match(r'\s*Py_ssize_t size;\s*Py_ssize_t i;\s*PyObject \*\*src, \*\*dest;\s*PyTupleObject \*np;\s*PyTupleObject \*b;\s*if', body), 'tupleconcat: b must be declared in the opening declaration group'
|
|
assert 'PyTupleObject *b =' not in body, 'tupleconcat: late initialized b declaration is not C89'
|
|
validation = re.search(r'if \(!PyTuple_Check\(bb\)\) \{.*?return NULL;\s*\}\s*b = \(PyTupleObject \*\)bb;\s*if \(Py_SIZE\(b\) == 0 && PyTuple_CheckExact\(a\)\)', body, re.S)
|
|
assert validation, 'tupleconcat: b assignment must follow type-check/error return and precede empty-b check'
|
|
assert body.index('return bb;') < validation.start(), 'tupleconcat: empty-a exact-b fast return must remain first'
|
|
assert body.count('b = (PyTupleObject *)bb;') == 1, 'tupleconcat: exactly one b assignment required'
|
|
assert body.index('b = (PyTupleObject *)bb;') < body.index('np = tuple_alloc(size);') < body.index('src = b->ob_item;') < body.index('_PyObject_GC_TRACK(np);'), 'tupleconcat: cast/allocation/copy/GC order changed'
|
|
print('tupleconcat b C89 declaration and validation/assignment order: PASS')
|