@@ -161,6 +161,11 @@ struct compiler {
161161 int c_optimize ; /* optimization level */
162162 int c_interactive ; /* true if in interactive mode */
163163 int c_nestlevel ;
164+ int c_do_not_emit_bytecode ; /* The compiler won't emit any bytecode
165+ if this value is different from zero.
166+ This can be used to temporarily visit
167+ nodes without emitting bytecode to
168+ check only errors. */
164169
165170 PyObject * c_const_cache ; /* Python dict holding all constants,
166171 including names tuple */
@@ -340,6 +345,7 @@ PyAST_CompileObject(mod_ty mod, PyObject *filename, PyCompilerFlags *flags,
340345 c .c_flags = flags ;
341346 c .c_optimize = (optimize == -1 ) ? config -> optimization_level : optimize ;
342347 c .c_nestlevel = 0 ;
348+ c .c_do_not_emit_bytecode = 0 ;
343349
344350 if (!_PyAST_Optimize (mod , arena , c .c_optimize )) {
345351 goto finally ;
@@ -1152,6 +1158,9 @@ compiler_addop(struct compiler *c, int opcode)
11521158 struct instr * i ;
11531159 int off ;
11541160 assert (!HAS_ARG (opcode ));
1161+ if (c -> c_do_not_emit_bytecode ) {
1162+ return 1 ;
1163+ }
11551164 off = compiler_next_instr (c , c -> u -> u_curblock );
11561165 if (off < 0 )
11571166 return 0 ;
@@ -1305,6 +1314,10 @@ merge_consts_recursive(struct compiler *c, PyObject *o)
13051314static Py_ssize_t
13061315compiler_add_const (struct compiler * c , PyObject * o )
13071316{
1317+ if (c -> c_do_not_emit_bytecode ) {
1318+ return 0 ;
1319+ }
1320+
13081321 PyObject * key = merge_consts_recursive (c , o );
13091322 if (key == NULL ) {
13101323 return -1 ;
@@ -1318,6 +1331,10 @@ compiler_add_const(struct compiler *c, PyObject *o)
13181331static int
13191332compiler_addop_load_const (struct compiler * c , PyObject * o )
13201333{
1334+ if (c -> c_do_not_emit_bytecode ) {
1335+ return 1 ;
1336+ }
1337+
13211338 Py_ssize_t arg = compiler_add_const (c , o );
13221339 if (arg < 0 )
13231340 return 0 ;
@@ -1328,6 +1345,10 @@ static int
13281345compiler_addop_o (struct compiler * c , int opcode , PyObject * dict ,
13291346 PyObject * o )
13301347{
1348+ if (c -> c_do_not_emit_bytecode ) {
1349+ return 1 ;
1350+ }
1351+
13311352 Py_ssize_t arg = compiler_add_o (c , dict , o );
13321353 if (arg < 0 )
13331354 return 0 ;
@@ -1339,6 +1360,11 @@ compiler_addop_name(struct compiler *c, int opcode, PyObject *dict,
13391360 PyObject * o )
13401361{
13411362 Py_ssize_t arg ;
1363+
1364+ if (c -> c_do_not_emit_bytecode ) {
1365+ return 1 ;
1366+ }
1367+
13421368 PyObject * mangled = _Py_Mangle (c -> u -> u_private , o );
13431369 if (!mangled )
13441370 return 0 ;
@@ -1359,6 +1385,10 @@ compiler_addop_i(struct compiler *c, int opcode, Py_ssize_t oparg)
13591385 struct instr * i ;
13601386 int off ;
13611387
1388+ if (c -> c_do_not_emit_bytecode ) {
1389+ return 1 ;
1390+ }
1391+
13621392 /* oparg value is unsigned, but a signed C int is usually used to store
13631393 it in the C code (like Python/ceval.c).
13641394
@@ -1385,6 +1415,10 @@ compiler_addop_j(struct compiler *c, int opcode, basicblock *b, int absolute)
13851415 struct instr * i ;
13861416 int off ;
13871417
1418+ if (c -> c_do_not_emit_bytecode ) {
1419+ return 1 ;
1420+ }
1421+
13881422 assert (HAS_ARG (opcode ));
13891423 assert (b != NULL );
13901424 off = compiler_next_instr (c , c -> u -> u_curblock );
@@ -1519,6 +1553,17 @@ compiler_addop_j(struct compiler *c, int opcode, basicblock *b, int absolute)
15191553 } \
15201554}
15211555
1556+ /* These macros allows to check only for errors and not emmit bytecode
1557+ * while visiting nodes.
1558+ */
1559+
1560+ #define BEGIN_DO_NOT_EMIT_BYTECODE { \
1561+ c->c_do_not_emit_bytecode++;
1562+
1563+ #define END_DO_NOT_EMIT_BYTECODE \
1564+ c->c_do_not_emit_bytecode--; \
1565+ }
1566+
15221567/* Search if variable annotations are present statically in a block. */
15231568
15241569static int
@@ -2546,13 +2591,23 @@ compiler_if(struct compiler *c, stmt_ty s)
25462591 return 0 ;
25472592
25482593 constant = expr_constant (s -> v .If .test );
2549- /* constant = 0: "if 0" Leave the optimizations to
2550- * the pephole optimizer to check for syntax errors
2551- * in the block.
2594+ /* constant = 0: "if 0"
25522595 * constant = 1: "if 1", "if 2", ...
25532596 * constant = -1: rest */
2554- if (constant == 1 ) {
2597+ if (constant == 0 ) {
2598+ BEGIN_DO_NOT_EMIT_BYTECODE
2599+ VISIT_SEQ (c , stmt , s -> v .If .body );
2600+ END_DO_NOT_EMIT_BYTECODE
2601+ if (s -> v .If .orelse ) {
2602+ VISIT_SEQ (c , stmt , s -> v .If .orelse );
2603+ }
2604+ } else if (constant == 1 ) {
25552605 VISIT_SEQ (c , stmt , s -> v .If .body );
2606+ if (s -> v .If .orelse ) {
2607+ BEGIN_DO_NOT_EMIT_BYTECODE
2608+ VISIT_SEQ (c , stmt , s -> v .If .orelse );
2609+ END_DO_NOT_EMIT_BYTECODE
2610+ }
25562611 } else {
25572612 if (asdl_seq_LEN (s -> v .If .orelse )) {
25582613 next = compiler_new_block (c );
@@ -2662,8 +2717,12 @@ compiler_while(struct compiler *c, stmt_ty s)
26622717 int constant = expr_constant (s -> v .While .test );
26632718
26642719 if (constant == 0 ) {
2665- if (s -> v .While .orelse )
2720+ BEGIN_DO_NOT_EMIT_BYTECODE
2721+ VISIT_SEQ (c , stmt , s -> v .While .body );
2722+ END_DO_NOT_EMIT_BYTECODE
2723+ if (s -> v .While .orelse ) {
26662724 VISIT_SEQ (c , stmt , s -> v .While .orelse );
2725+ }
26672726 return 1 ;
26682727 }
26692728 loop = compiler_new_block (c );
0 commit comments