static int symtable_visit_genexp(struct symtable *st, expr_ty e) { comprehension_ty outermost = ((comprehension_ty) (asdl_seq_GET(e->v.GeneratorExp.generators, 0))); /* Outermost iterator is evaluated in current scope */ VISIT(st, expr, outermost->iter); /* Create generator scope for the rest */ if (!GET_IDENTIFIER(genexpr) || !symtable_enter_block(st, genexpr, FunctionBlock, (void *)e, 0)) { return 0; } st->st_cur->ste_generator = 1; /* Outermost iter is received as an argument */ if (!symtable_implicit_arg(st, 0)) { symtable_exit_block(st, (void *)e); return 0; } VISIT_IN_BLOCK(st, expr, outermost->target, (void*)e); VISIT_SEQ_IN_BLOCK(st, expr, outermost->ifs, (void*)e); VISIT_SEQ_TAIL_IN_BLOCK(st, comprehension, e->v.GeneratorExp.generators, 1, (void*)e); VISIT_IN_BLOCK(st, expr, e->v.GeneratorExp.elt, (void*)e); return symtable_exit_block(st, (void *)e); }
static int symtable_handle_comprehension(struct symtable *st, expr_ty e, identifier scope_name, asdl_seq *generators, expr_ty elt, expr_ty value) { int is_generator = (e->kind == GeneratorExp_kind); int needs_tmp = !is_generator; comprehension_ty outermost = ((comprehension_ty) asdl_seq_GET(generators, 0)); /* Outermost iterator is evaluated in current scope */ VISIT(st, expr, outermost->iter); /* Create comprehension scope for the rest */ if (!scope_name || !symtable_enter_block(st, scope_name, FunctionBlock, (void *)e, 0)) { return 0; } st->st_cur->ste_generator = is_generator; /* Outermost iter is received as an argument */ if (!symtable_implicit_arg(st, 0)) { symtable_exit_block(st, (void *)e); return 0; } /* Allocate temporary name if needed */ if (needs_tmp && !symtable_new_tmpname(st)) { symtable_exit_block(st, (void *)e); return 0; } VISIT_IN_BLOCK(st, expr, outermost->target, (void*)e); VISIT_SEQ_IN_BLOCK(st, expr, outermost->ifs, (void*)e); VISIT_SEQ_TAIL_IN_BLOCK(st, comprehension, generators, 1, (void*)e); if (value) VISIT_IN_BLOCK(st, expr, value, (void*)e); VISIT_IN_BLOCK(st, expr, elt, (void*)e); return symtable_exit_block(st, (void *)e); }