@@ -2961,16 +2961,34 @@ static void ir_count_defers(IrBuilder *irb, Scope *inner_scope, Scope *outer_sco
2961
2961
results[ReturnKindUnconditional] = 0;
2962
2962
results[ReturnKindError] = 0;
2963
2963
2964
- while (inner_scope != outer_scope) {
2965
- assert(inner_scope);
2966
- if (inner_scope->id == ScopeIdDefer) {
2967
- AstNode *defer_node = inner_scope->source_node;
2968
- assert(defer_node->type == NodeTypeDefer);
2969
- ReturnKind defer_kind = defer_node->data.defer.kind;
2970
- results[defer_kind] += 1;
2964
+ Scope *scope = inner_scope;
2971
2965
2966
+ while (scope != outer_scope) {
2967
+ assert(scope);
2968
+ switch (scope->id) {
2969
+ case ScopeIdDefer: {
2970
+ AstNode *defer_node = scope->source_node;
2971
+ assert(defer_node->type == NodeTypeDefer);
2972
+ ReturnKind defer_kind = defer_node->data.defer.kind;
2973
+ results[defer_kind] += 1;
2974
+ scope = scope->parent;
2975
+ continue;
2976
+ }
2977
+ case ScopeIdDecls:
2978
+ case ScopeIdFnDef:
2979
+ return;
2980
+ case ScopeIdBlock:
2981
+ case ScopeIdVarDecl:
2982
+ case ScopeIdLoop:
2983
+ case ScopeIdSuspend:
2984
+ case ScopeIdCompTime:
2985
+ scope = scope->parent;
2986
+ continue;
2987
+ case ScopeIdDeferExpr:
2988
+ case ScopeIdCImport:
2989
+ case ScopeIdCoroPrelude:
2990
+ zig_unreachable();
2972
2991
}
2973
- inner_scope = inner_scope->parent;
2974
2992
}
2975
2993
}
2976
2994
@@ -2986,27 +3004,43 @@ static bool ir_gen_defers_for_block(IrBuilder *irb, Scope *inner_scope, Scope *o
2986
3004
if (!scope)
2987
3005
return is_noreturn;
2988
3006
2989
- if (scope->id == ScopeIdDefer) {
2990
- AstNode *defer_node = scope->source_node;
2991
- assert(defer_node->type == NodeTypeDefer);
2992
- ReturnKind defer_kind = defer_node->data.defer.kind;
2993
- if (defer_kind == ReturnKindUnconditional ||
2994
- (gen_error_defers && defer_kind == ReturnKindError))
2995
- {
2996
- AstNode *defer_expr_node = defer_node->data.defer.expr;
2997
- Scope *defer_expr_scope = defer_node->data.defer.expr_scope;
2998
- IrInstruction *defer_expr_value = ir_gen_node(irb, defer_expr_node, defer_expr_scope);
2999
- if (defer_expr_value != irb->codegen->invalid_instruction) {
3000
- if (defer_expr_value->value.type != nullptr && defer_expr_value->value.type->id == TypeTableEntryIdUnreachable) {
3001
- is_noreturn = true;
3002
- } else {
3003
- ir_mark_gen(ir_build_check_statement_is_void(irb, defer_expr_scope, defer_expr_node, defer_expr_value));
3007
+ switch (scope->id) {
3008
+ case ScopeIdDefer: {
3009
+ AstNode *defer_node = scope->source_node;
3010
+ assert(defer_node->type == NodeTypeDefer);
3011
+ ReturnKind defer_kind = defer_node->data.defer.kind;
3012
+ if (defer_kind == ReturnKindUnconditional ||
3013
+ (gen_error_defers && defer_kind == ReturnKindError))
3014
+ {
3015
+ AstNode *defer_expr_node = defer_node->data.defer.expr;
3016
+ Scope *defer_expr_scope = defer_node->data.defer.expr_scope;
3017
+ IrInstruction *defer_expr_value = ir_gen_node(irb, defer_expr_node, defer_expr_scope);
3018
+ if (defer_expr_value != irb->codegen->invalid_instruction) {
3019
+ if (defer_expr_value->value.type != nullptr && defer_expr_value->value.type->id == TypeTableEntryIdUnreachable) {
3020
+ is_noreturn = true;
3021
+ } else {
3022
+ ir_mark_gen(ir_build_check_statement_is_void(irb, defer_expr_scope, defer_expr_node, defer_expr_value));
3023
+ }
3004
3024
}
3005
3025
}
3026
+ scope = scope->parent;
3027
+ continue;
3006
3028
}
3007
-
3029
+ case ScopeIdDecls:
3030
+ case ScopeIdFnDef:
3031
+ return is_noreturn;
3032
+ case ScopeIdBlock:
3033
+ case ScopeIdVarDecl:
3034
+ case ScopeIdLoop:
3035
+ case ScopeIdSuspend:
3036
+ case ScopeIdCompTime:
3037
+ scope = scope->parent;
3038
+ continue;
3039
+ case ScopeIdDeferExpr:
3040
+ case ScopeIdCImport:
3041
+ case ScopeIdCoroPrelude:
3042
+ zig_unreachable();
3008
3043
}
3009
- scope = scope->parent;
3010
3044
}
3011
3045
return is_noreturn;
3012
3046
}
0 commit comments