mirror of
https://github.com/python/cpython.git
synced 2025-08-30 21:48:47 +00:00
gh-104584: Allow unspecialized instructions in superblocks (#106497)
This adds several of unspecialized opcodes to superblocks: TO_BOOL, BINARY_SUBSCR, STORE_SUBSCR, UNPACK_SEQUENCE, LOAD_GLOBAL, LOAD_ATTR, COMPARE_OP, BINARY_OP. While we may not want that eventually, for now this helps finding bugs. There is a rudimentary test checking for UNPACK_SEQUENCE. Once we're ready to undo this, that would be simple: just replace the call to variable_used_unspecialized with a call to variable_used (as shown in a comment). Or add individual opcdes to FORBIDDEN_NAMES_IN_UOPS.
This commit is contained in:
parent
11038c56ad
commit
b3648f036e
4 changed files with 490 additions and 128 deletions
|
@ -425,8 +425,9 @@ class Instruction:
|
|||
return False
|
||||
res = True
|
||||
for forbidden in FORBIDDEN_NAMES_IN_UOPS:
|
||||
# TODO: Don't check in '#ifdef ENABLE_SPECIALIZATION' regions
|
||||
if variable_used(self.inst, forbidden):
|
||||
# NOTE: To disallow unspecialized uops, use
|
||||
# if variable_used(self.inst, forbidden):
|
||||
if variable_used_unspecialized(self.inst, forbidden):
|
||||
# print(f"Skipping {self.name} because it uses {forbidden}")
|
||||
res = False
|
||||
return res
|
||||
|
@ -1644,6 +1645,27 @@ def variable_used(node: parser.Node, name: str) -> bool:
|
|||
)
|
||||
|
||||
|
||||
def variable_used_unspecialized(node: parser.Node, name: str) -> bool:
|
||||
"""Like variable_used(), but skips #if ENABLE_SPECIALIZATION blocks."""
|
||||
tokens: list[lx.Token] = []
|
||||
skipping = False
|
||||
for i, token in enumerate(node.tokens):
|
||||
if token.kind == "MACRO":
|
||||
text = "".join(token.text.split())
|
||||
# TODO: Handle nested #if
|
||||
if text == "#if":
|
||||
if (
|
||||
i + 1 < len(node.tokens)
|
||||
and node.tokens[i + 1].text == "ENABLE_SPECIALIZATION"
|
||||
):
|
||||
skipping = True
|
||||
elif text in ("#else", "#endif"):
|
||||
skipping = False
|
||||
if not skipping:
|
||||
tokens.append(token)
|
||||
return any(token.kind == "IDENTIFIER" and token.text == name for token in tokens)
|
||||
|
||||
|
||||
def main():
|
||||
"""Parse command line, parse input, analyze, write output."""
|
||||
args = arg_parser.parse_args() # Prints message and sys.exit(2) on error
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue