79
79
"STORE_FAST" ,
80
80
"STORE_FAST_MAYBE_NULL" ,
81
81
"COPY" ,
82
-
83
82
# Arithmetic
84
83
"_BINARY_OP_MULTIPLY_INT" ,
85
84
"_BINARY_OP_ADD_INT" ,
86
85
"_BINARY_OP_SUBTRACT_INT" ,
87
-
88
86
}
89
87
90
88
arg_parser = argparse .ArgumentParser (
143
141
default = DEFAULT_ABSTRACT_INTERPRETER_OUTPUT ,
144
142
)
145
143
144
+
146
145
class Generator (Analyzer ):
147
146
def get_stack_effect_info (
148
147
self , thing : parsing .InstDef | parsing .Macro | parsing .Pseudo
@@ -183,10 +182,14 @@ def effect_str(effects: list[StackEffect]) -> str:
183
182
target_popped = effect_str (target_instr .input_effects )
184
183
target_pushed = effect_str (target_instr .output_effects )
185
184
popped , pushed = target_popped , target_pushed
185
+ case _:
186
+ typing .assert_never (thing )
186
187
return instr , popped , pushed
187
188
188
189
@contextlib .contextmanager
189
- def metadata_item (self , signature : str , open : str , close : str ) -> typing .Iterator [None ]:
190
+ def metadata_item (
191
+ self , signature : str , open : str , close : str
192
+ ) -> typing .Iterator [None ]:
190
193
self .out .emit ("" )
191
194
self .out .emit (f"extern { signature } ;" )
192
195
self .out .emit ("#ifdef NEED_OPCODE_METADATA" )
@@ -211,7 +214,9 @@ def write_function(
211
214
) -> None :
212
215
213
216
with self .metadata_item (
214
- f"int _PyOpcode_num_{ direction } (int opcode, int oparg, bool jump)" , "" , ""
217
+ f"int _PyOpcode_num_{ direction } (int opcode, int oparg, bool jump)" ,
218
+ "" ,
219
+ "" ,
215
220
):
216
221
with self .out .block ("switch(opcode)" ):
217
222
for instr , effect in data :
@@ -249,10 +254,11 @@ def assign_opcode_ids(self) -> None:
249
254
250
255
for instr in itertools .chain (
251
256
[instr for instr in self .instrs .values () if instr .kind != "op" ],
252
- self .macro_instrs .values ()):
257
+ self .macro_instrs .values (),
258
+ ):
253
259
assert isinstance (instr , (Instruction , MacroInstruction , PseudoInstruction ))
254
260
name = instr .name
255
- if name .startswith (' INSTRUMENTED_' ):
261
+ if name .startswith (" INSTRUMENTED_" ):
256
262
instrumented_ops .append (name )
257
263
else :
258
264
ops .append ((instr .instr_flags .HAS_ARG_FLAG , name ))
@@ -261,13 +267,13 @@ def assign_opcode_ids(self) -> None:
261
267
# rather than bytecodes.c, so we need to add it explicitly
262
268
# here (at least until we add something to bytecodes.c to
263
269
# declare external instructions).
264
- instrumented_ops .append (' INSTRUMENTED_LINE' )
270
+ instrumented_ops .append (" INSTRUMENTED_LINE" )
265
271
266
272
# assert lists are unique
267
273
assert len (set (ops )) == len (ops )
268
274
assert len (set (instrumented_ops )) == len (instrumented_ops )
269
275
270
- opname : list [str | None ] = [None ] * 512
276
+ opname : list [str | None ] = [None ] * 512
271
277
opmap : dict [str , int ] = {}
272
278
markers : dict [str , int ] = {}
273
279
@@ -278,16 +284,15 @@ def map_op(op: int, name: str) -> None:
278
284
opname [op ] = name
279
285
opmap [name ] = op
280
286
281
-
282
287
# 0 is reserved for cache entries. This helps debugging.
283
- map_op (0 , ' CACHE' )
288
+ map_op (0 , " CACHE" )
284
289
285
290
# 17 is reserved as it is the initial value for the specializing counter.
286
291
# This helps catch cases where we attempt to execute a cache.
287
- map_op (17 , ' RESERVED' )
292
+ map_op (17 , " RESERVED" )
288
293
289
294
# 166 is RESUME - it is hard coded as such in Tools/build/deepfreeze.py
290
- map_op (166 , ' RESUME' )
295
+ map_op (166 , " RESUME" )
291
296
292
297
next_opcode = 1
293
298
@@ -299,13 +304,13 @@ def map_op(op: int, name: str) -> None:
299
304
assert next_opcode < 255
300
305
map_op (next_opcode , name )
301
306
302
- if has_arg and ' HAVE_ARGUMENT' not in markers :
303
- markers [' HAVE_ARGUMENT' ] = next_opcode
307
+ if has_arg and " HAVE_ARGUMENT" not in markers :
308
+ markers [" HAVE_ARGUMENT" ] = next_opcode
304
309
305
310
# Instrumented opcodes are at the end of the valid range
306
311
min_instrumented = 254 - (len (instrumented_ops ) - 1 )
307
312
assert next_opcode <= min_instrumented
308
- markers [' MIN_INSTRUMENTED_OPCODE' ] = min_instrumented
313
+ markers [" MIN_INSTRUMENTED_OPCODE" ] = min_instrumented
309
314
for i , op in enumerate (instrumented_ops ):
310
315
map_op (min_instrumented + i , op )
311
316
@@ -317,7 +322,9 @@ def map_op(op: int, name: str) -> None:
317
322
self .opmap = opmap
318
323
self .markers = markers
319
324
320
- def write_opcode_ids (self , opcode_ids_h_filename : str , opcode_targets_filename : str ) -> None :
325
+ def write_opcode_ids (
326
+ self , opcode_ids_h_filename : str , opcode_targets_filename : str
327
+ ) -> None :
321
328
"""Write header file that defined the opcode IDs"""
322
329
323
330
with open (opcode_ids_h_filename , "w" ) as f :
@@ -330,7 +337,7 @@ def write_opcode_ids(self, opcode_ids_h_filename: str, opcode_targets_filename:
330
337
self .out .emit ("#ifndef Py_OPCODE_IDS_H" )
331
338
self .out .emit ("#define Py_OPCODE_IDS_H" )
332
339
self .out .emit ("#ifdef __cplusplus" )
333
- self .out .emit (" extern \" C \ " {" )
340
+ self .out .emit (' extern "C " {' )
334
341
self .out .emit ("#endif" )
335
342
self .out .emit ("" )
336
343
self .out .emit ("/* Instruction opcodes for compiled code */" )
@@ -363,7 +370,6 @@ def define(name: str, opcode: int) -> None:
363
370
targets [op ] = f"TARGET_{ name } "
364
371
f .write (",\n " .join ([f" &&{ s } " for s in targets ]))
365
372
366
-
367
373
def write_metadata (self , metadata_filename : str , pymetadata_filename : str ) -> None :
368
374
"""Write instruction metadata to output file."""
369
375
@@ -458,7 +464,7 @@ def write_metadata(self, metadata_filename: str, pymetadata_filename: str) -> No
458
464
"const struct opcode_metadata "
459
465
"_PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE]" ,
460
466
"=" ,
461
- ";"
467
+ ";" ,
462
468
):
463
469
# Write metadata for each instruction
464
470
for thing in self .everything :
@@ -471,13 +477,15 @@ def write_metadata(self, metadata_filename: str, pymetadata_filename: str) -> No
471
477
case parsing .Macro ():
472
478
self .write_metadata_for_macro (self .macro_instrs [thing .name ])
473
479
case parsing .Pseudo ():
474
- self .write_metadata_for_pseudo (self .pseudo_instrs [thing .name ])
480
+ self .write_metadata_for_pseudo (
481
+ self .pseudo_instrs [thing .name ]
482
+ )
475
483
476
484
with self .metadata_item (
477
485
"const struct opcode_macro_expansion "
478
486
"_PyOpcode_macro_expansion[OPCODE_MACRO_EXPANSION_SIZE]" ,
479
487
"=" ,
480
- ";"
488
+ ";" ,
481
489
):
482
490
# Write macro expansion for each non-pseudo instruction
483
491
for thing in self .everything :
@@ -514,7 +522,9 @@ def write_metadata(self, metadata_filename: str, pymetadata_filename: str) -> No
514
522
self .write_uop_items (lambda name , counter : f'[{ name } ] = "{ name } ",' )
515
523
516
524
with self .metadata_item (
517
- f"const char *const _PyOpcode_OpName[{ 1 + max (self .opmap .values ())} ]" , "=" , ";"
525
+ f"const char *const _PyOpcode_OpName[{ 1 + max (self .opmap .values ())} ]" ,
526
+ "=" ,
527
+ ";" ,
518
528
):
519
529
for name in self .opmap :
520
530
self .out .emit (f'[{ name } ] = "{ name } ",' )
@@ -527,11 +537,9 @@ def write_metadata(self, metadata_filename: str, pymetadata_filename: str) -> No
527
537
for m in family .members :
528
538
deoptcodes [m ] = name
529
539
# special case:
530
- deoptcodes [' BINARY_OP_INPLACE_ADD_UNICODE' ] = ' BINARY_OP'
540
+ deoptcodes [" BINARY_OP_INPLACE_ADD_UNICODE" ] = " BINARY_OP"
531
541
532
- with self .metadata_item (
533
- f"const uint8_t _PyOpcode_Deopt[256]" , "=" , ";"
534
- ):
542
+ with self .metadata_item (f"const uint8_t _PyOpcode_Deopt[256]" , "=" , ";" ):
535
543
for opt , deopt in sorted (deoptcodes .items ()):
536
544
self .out .emit (f"[{ opt } ] = { deopt } ," )
537
545
@@ -589,10 +597,9 @@ def write_metadata(self, metadata_filename: str, pymetadata_filename: str) -> No
589
597
if name not in specialized_ops :
590
598
self .out .emit (f"'{ name } ': { op } ," )
591
599
592
- for name in [' MIN_INSTRUMENTED_OPCODE' , ' HAVE_ARGUMENT' ]:
600
+ for name in [" MIN_INSTRUMENTED_OPCODE" , " HAVE_ARGUMENT" ]:
593
601
self .out .emit (f"{ name } = { self .markers [name ]} " )
594
602
595
-
596
603
def write_pseudo_instrs (self ) -> None :
597
604
"""Write the IS_PSEUDO_INSTR macro"""
598
605
self .out .emit ("\n \n #define IS_PSEUDO_INSTR(OP) ( \\ " )
@@ -815,7 +822,10 @@ def write_abstract_interpreter_instructions(
815
822
pass
816
823
case parsing .InstDef ():
817
824
instr = AbstractInstruction (self .instrs [thing .name ].inst )
818
- if instr .is_viable_uop () and instr .name not in SPECIALLY_HANDLED_ABSTRACT_INSTR :
825
+ if (
826
+ instr .is_viable_uop ()
827
+ and instr .name not in SPECIALLY_HANDLED_ABSTRACT_INSTR
828
+ ):
819
829
self .out .emit ("" )
820
830
with self .out .block (f"case { thing .name } :" ):
821
831
instr .write (self .out , tier = TIER_TWO )
@@ -878,8 +888,9 @@ def main() -> None:
878
888
a .write_opcode_ids (args .opcode_ids_h , args .opcode_targets_h )
879
889
a .write_metadata (args .metadata , args .pymetadata )
880
890
a .write_executor_instructions (args .executor_cases , args .emit_line_directives )
881
- a .write_abstract_interpreter_instructions (args .abstract_interpreter_cases ,
882
- args .emit_line_directives )
891
+ a .write_abstract_interpreter_instructions (
892
+ args .abstract_interpreter_cases , args .emit_line_directives
893
+ )
883
894
884
895
885
896
if __name__ == "__main__" :
0 commit comments