| ... | ... | @@ -86,6 +86,7 @@ pub fn generate(gpa: *Allocator, tree: ast.Tree) InnerError!Zir { |
| 86 | 86 | |
| 87 | 87 | var gen_scope: GenZir = .{ |
| 88 | 88 | .force_comptime = true, |
| 89 | .in_defer = false, |
| 89 | 90 | .parent = &top_scope.base, |
| 90 | 91 | .anon_name_strategy = .parent, |
| 91 | 92 | .decl_node_index = 0, |
| ... | ... | @@ -2118,14 +2119,20 @@ fn genDefers( |
| 2118 | 2119 | const defer_scope = scope.cast(Scope.Defer).?; |
| 2119 | 2120 | scope = defer_scope.parent; |
| 2120 | 2121 | const expr_node = node_datas[defer_scope.defer_node].rhs; |
| 2122 | const prev_in_defer = gz.in_defer; |
| 2123 | gz.in_defer = true; |
| 2121 | 2124 | try unusedResultExpr(gz, defer_scope.parent, expr_node); |
| 2125 | gz.in_defer = prev_in_defer; |
| 2122 | 2126 | }, |
| 2123 | 2127 | .defer_error => { |
| 2124 | 2128 | const defer_scope = scope.cast(Scope.Defer).?; |
| 2125 | 2129 | scope = defer_scope.parent; |
| 2126 | 2130 | if (err_code == .none) continue; |
| 2127 | 2131 | const expr_node = node_datas[defer_scope.defer_node].rhs; |
| 2132 | const prev_in_defer = gz.in_defer; |
| 2133 | gz.in_defer = true; |
| 2128 | 2134 | try unusedResultExpr(gz, defer_scope.parent, expr_node); |
| 2135 | gz.in_defer = prev_in_defer; |
| 2129 | 2136 | }, |
| 2130 | 2137 | .namespace => unreachable, |
| 2131 | 2138 | .top => unreachable, |
| ... | ... | @@ -2728,6 +2735,7 @@ fn fnDecl( |
| 2728 | 2735 | |
| 2729 | 2736 | var decl_gz: GenZir = .{ |
| 2730 | 2737 | .force_comptime = true, |
| 2738 | .in_defer = false, |
| 2731 | 2739 | .decl_node_index = fn_proto.ast.proto_node, |
| 2732 | 2740 | .decl_line = gz.calcLine(decl_node), |
| 2733 | 2741 | .parent = scope, |
| ... | ... | @@ -2851,6 +2859,7 @@ fn fnDecl( |
| 2851 | 2859 | |
| 2852 | 2860 | var fn_gz: GenZir = .{ |
| 2853 | 2861 | .force_comptime = false, |
| 2862 | .in_defer = false, |
| 2854 | 2863 | .decl_node_index = fn_proto.ast.proto_node, |
| 2855 | 2864 | .decl_line = decl_gz.decl_line, |
| 2856 | 2865 | .parent = &decl_gz.base, |
| ... | ... | @@ -2981,6 +2990,7 @@ fn globalVarDecl( |
| 2981 | 2990 | .decl_line = gz.calcLine(node), |
| 2982 | 2991 | .astgen = astgen, |
| 2983 | 2992 | .force_comptime = true, |
| 2993 | .in_defer = false, |
| 2984 | 2994 | .anon_name_strategy = .parent, |
| 2985 | 2995 | }; |
| 2986 | 2996 | defer block_scope.instructions.deinit(gpa); |
| ... | ... | @@ -3117,6 +3127,7 @@ fn comptimeDecl( |
| 3117 | 3127 | |
| 3118 | 3128 | var decl_block: GenZir = .{ |
| 3119 | 3129 | .force_comptime = true, |
| 3130 | .in_defer = false, |
| 3120 | 3131 | .decl_node_index = node, |
| 3121 | 3132 | .decl_line = gz.calcLine(node), |
| 3122 | 3133 | .parent = scope, |
| ... | ... | @@ -3169,6 +3180,7 @@ fn usingnamespaceDecl( |
| 3169 | 3180 | |
| 3170 | 3181 | var decl_block: GenZir = .{ |
| 3171 | 3182 | .force_comptime = true, |
| 3183 | .in_defer = false, |
| 3172 | 3184 | .decl_node_index = node, |
| 3173 | 3185 | .decl_line = gz.calcLine(node), |
| 3174 | 3186 | .parent = scope, |
| ... | ... | @@ -3214,6 +3226,7 @@ fn testDecl( |
| 3214 | 3226 | |
| 3215 | 3227 | var decl_block: GenZir = .{ |
| 3216 | 3228 | .force_comptime = true, |
| 3229 | .in_defer = false, |
| 3217 | 3230 | .decl_node_index = node, |
| 3218 | 3231 | .decl_line = gz.calcLine(node), |
| 3219 | 3232 | .parent = scope, |
| ... | ... | @@ -3235,6 +3248,7 @@ fn testDecl( |
| 3235 | 3248 | |
| 3236 | 3249 | var fn_block: GenZir = .{ |
| 3237 | 3250 | .force_comptime = false, |
| 3251 | .in_defer = false, |
| 3238 | 3252 | .decl_node_index = node, |
| 3239 | 3253 | .decl_line = decl_block.decl_line, |
| 3240 | 3254 | .parent = &decl_block.base, |
| ... | ... | @@ -3319,6 +3333,7 @@ fn structDeclInner( |
| 3319 | 3333 | .decl_line = gz.calcLine(node), |
| 3320 | 3334 | .astgen = astgen, |
| 3321 | 3335 | .force_comptime = true, |
| 3336 | .in_defer = false, |
| 3322 | 3337 | .ref_start_index = gz.ref_start_index, |
| 3323 | 3338 | }; |
| 3324 | 3339 | defer block_scope.instructions.deinit(gpa); |
| ... | ... | @@ -3580,6 +3595,7 @@ fn unionDeclInner( |
| 3580 | 3595 | .decl_line = gz.calcLine(node), |
| 3581 | 3596 | .astgen = astgen, |
| 3582 | 3597 | .force_comptime = true, |
| 3598 | .in_defer = false, |
| 3583 | 3599 | .ref_start_index = gz.ref_start_index, |
| 3584 | 3600 | }; |
| 3585 | 3601 | defer block_scope.instructions.deinit(gpa); |
| ... | ... | @@ -3976,6 +3992,7 @@ fn containerDecl( |
| 3976 | 3992 | .decl_line = gz.calcLine(node), |
| 3977 | 3993 | .astgen = astgen, |
| 3978 | 3994 | .force_comptime = true, |
| 3995 | .in_defer = false, |
| 3979 | 3996 | .ref_start_index = gz.ref_start_index, |
| 3980 | 3997 | }; |
| 3981 | 3998 | defer block_scope.instructions.deinit(gpa); |
| ... | ... | @@ -4432,6 +4449,8 @@ fn tryExpr( |
| 4432 | 4449 | return astgen.failNode(node, "invalid 'try' outside function scope", .{}); |
| 4433 | 4450 | }; |
| 4434 | 4451 | |
| 4452 | if (parent_gz.in_defer) return astgen.failNode(node, "try is not allowed inside defer expression", .{}); |
| 4453 | |
| 4435 | 4454 | var block_scope = parent_gz.makeSubBlock(scope); |
| 4436 | 4455 | block_scope.setBreakResultLoc(rl); |
| 4437 | 4456 | defer block_scope.instructions.deinit(astgen.gpa); |
| ... | ... | @@ -5962,6 +5981,8 @@ fn ret(gz: *GenZir, scope: *Scope, node: ast.Node.Index) InnerError!Zir.Inst.Ref |
| 5962 | 5981 | const node_datas = tree.nodes.items(.data); |
| 5963 | 5982 | const main_tokens = tree.nodes.items(.main_token); |
| 5964 | 5983 | |
| 5984 | if (gz.in_defer) return astgen.failNode(node, "cannot return from defer expression", .{}); |
| 5985 | |
| 5965 | 5986 | const operand_node = node_datas[node].lhs; |
| 5966 | 5987 | if (operand_node != 0) { |
| 5967 | 5988 | const rl: ResultLoc = if (nodeMayNeedMemoryLocation(tree, operand_node)) .{ |
| ... | ... | @@ -8040,6 +8061,7 @@ const GenZir = struct { |
| 8040 | 8061 | const base_tag: Scope.Tag = .gen_zir; |
| 8041 | 8062 | base: Scope = Scope{ .tag = base_tag }, |
| 8042 | 8063 | force_comptime: bool, |
| 8064 | in_defer: bool, |
| 8043 | 8065 | /// How decls created in this scope should be named. |
| 8044 | 8066 | anon_name_strategy: Zir.Inst.NameStrategy = .anon, |
| 8045 | 8067 | /// The end of special indexes. `Zir.Inst.Ref` subtracts against this number to convert |
| ... | ... | @@ -8087,6 +8109,7 @@ const GenZir = struct { |
| 8087 | 8109 | fn makeSubBlock(gz: *GenZir, scope: *Scope) GenZir { |
| 8088 | 8110 | return .{ |
| 8089 | 8111 | .force_comptime = gz.force_comptime, |
| 8112 | .in_defer = gz.in_defer, |
| 8090 | 8113 | .ref_start_index = gz.ref_start_index, |
| 8091 | 8114 | .decl_node_index = gz.decl_node_index, |
| 8092 | 8115 | .decl_line = gz.decl_line, |