| ... | ... | @@ -6029,16 +6029,15 @@ fn switchExpr( |
| 6029 | 6029 | const cond_ty_inst = try parent_gz.addUnNode(.typeof, cond, operand_node); |
| 6030 | 6030 | const item_rl: ResultLoc = .{ .ty = cond_ty_inst }; |
| 6031 | 6031 | |
| 6032 | | // These contain the data that goes into the `extra` array for the SwitchBlock/SwitchBlockMulti. |
| 6033 | | // This is the optional else prong body. |
| 6034 | | var special_case_payload = ArrayListUnmanaged(u32){}; |
| 6035 | | defer special_case_payload.deinit(gpa); |
| 6036 | | // This is all the scalar cases. |
| 6037 | | var scalar_cases_payload = ArrayListUnmanaged(u32){}; |
| 6038 | | defer scalar_cases_payload.deinit(gpa); |
| 6039 | | // Same deal, but this is only the `extra` data for the multi cases. |
| 6040 | | var multi_cases_payload = ArrayListUnmanaged(u32){}; |
| 6041 | | defer multi_cases_payload.deinit(gpa); |
| 6032 | // This contains the data that goes into the `extra` array for the SwitchBlock/SwitchBlockMulti, |
| 6033 | // except the first cases_nodes.len slots are a table that indexes payloads later in the array, with |
| 6034 | // the special case index coming first, then scalar_case_len indexes, then multi_cases_len indexes |
| 6035 | var payloads = ArrayListUnmanaged(u32){}; |
| 6036 | defer payloads.deinit(gpa); |
| 6037 | const scalar_case_table: u32 = @boolToInt(special_prong != .none); |
| 6038 | const multi_case_table = scalar_case_table + scalar_cases_len; |
| 6039 | const case_table_len = multi_case_table + multi_cases_len; |
| 6040 | try payloads.resize(gpa, case_table_len); |
| 6042 | 6041 | |
| 6043 | 6042 | var block_scope = parent_gz.makeSubBlock(scope); |
| 6044 | 6043 | block_scope.setBreakResultLoc(rl); |
| ... | ... | @@ -6069,13 +6068,6 @@ fn switchExpr( |
| 6069 | 6068 | |
| 6070 | 6069 | var capture_val_scope: Scope.LocalVal = undefined; |
| 6071 | 6070 | const sub_scope = blk: { |
| 6072 | | const capture_index = if (is_multi_case) ci: { |
| 6073 | | multi_case_index += 1; |
| 6074 | | break :ci multi_case_index - 1; |
| 6075 | | } else ci: { |
| 6076 | | scalar_case_index += 1; |
| 6077 | | break :ci scalar_case_index - 1; |
| 6078 | | }; |
| 6079 | 6071 | const payload_token = case.payload_token orelse break :blk &case_scope.base; |
| 6080 | 6072 | const ident = if (token_tags[payload_token] == .asterisk) |
| 6081 | 6073 | payload_token + 1 |
| ... | ... | @@ -6109,6 +6101,7 @@ fn switchExpr( |
| 6109 | 6101 | 0b10 => .switch_capture_multi, |
| 6110 | 6102 | 0b11 => .switch_capture_multi_ref, |
| 6111 | 6103 | }; |
| 6104 | const capture_index = if (is_multi_case) multi_case_index else scalar_case_index; |
| 6112 | 6105 | break :capture try case_scope.add(.{ |
| 6113 | 6106 | .tag = capture_tag, |
| 6114 | 6107 | .data = .{ .switch_capture = .{ |
| ... | ... | @@ -6129,10 +6122,11 @@ fn switchExpr( |
| 6129 | 6122 | break :blk &capture_val_scope.base; |
| 6130 | 6123 | }; |
| 6131 | 6124 | |
| 6132 | | if (is_multi_case) { |
| 6133 | | // items_len, ranges_len, body_len |
| 6134 | | const header_index = multi_cases_payload.items.len; |
| 6135 | | try multi_cases_payload.resize(gpa, multi_cases_payload.items.len + 3); |
| 6125 | const header_index = @intCast(u32, payloads.items.len); |
| 6126 | const body_len_index = if (is_multi_case) blk: { |
| 6127 | payloads.items[multi_case_table + multi_case_index] = header_index; |
| 6128 | multi_case_index += 1; |
| 6129 | try payloads.resize(gpa, header_index + 3); // items_len, ranges_len, body_len |
| 6136 | 6130 | |
| 6137 | 6131 | // items |
| 6138 | 6132 | var items_len: u32 = 0; |
| ... | ... | @@ -6141,7 +6135,7 @@ fn switchExpr( |
| 6141 | 6135 | items_len += 1; |
| 6142 | 6136 | |
| 6143 | 6137 | const item_inst = try comptimeExpr(parent_gz, scope, item_rl, item_node); |
| 6144 | | try multi_cases_payload.append(gpa, @enumToInt(item_inst)); |
| 6138 | try payloads.append(gpa, @enumToInt(item_inst)); |
| 6145 | 6139 | } |
| 6146 | 6140 | |
| 6147 | 6141 | // ranges |
| ... | ... | @@ -6152,57 +6146,43 @@ fn switchExpr( |
| 6152 | 6146 | |
| 6153 | 6147 | const first = try comptimeExpr(parent_gz, scope, item_rl, node_datas[range].lhs); |
| 6154 | 6148 | const last = try comptimeExpr(parent_gz, scope, item_rl, node_datas[range].rhs); |
| 6155 | | try multi_cases_payload.appendSlice(gpa, &[_]u32{ |
| 6149 | try payloads.appendSlice(gpa, &[_]u32{ |
| 6156 | 6150 | @enumToInt(first), @enumToInt(last), |
| 6157 | 6151 | }); |
| 6158 | 6152 | } |
| 6159 | 6153 | |
| 6160 | | const case_result = try expr(&case_scope, sub_scope, block_scope.break_result_loc, case.ast.target_expr); |
| 6161 | | try checkUsed(parent_gz, &case_scope.base, sub_scope); |
| 6162 | | if (!parent_gz.refIsNoReturn(case_result)) { |
| 6163 | | block_scope.break_count += 1; |
| 6164 | | _ = try case_scope.addBreak(.@"break", switch_block, case_result); |
| 6165 | | } |
| 6166 | | |
| 6167 | | multi_cases_payload.items[header_index + 0] = items_len; |
| 6168 | | multi_cases_payload.items[header_index + 1] = ranges_len; |
| 6169 | | multi_cases_payload.items[header_index + 2] = @intCast(u32, case_scope.instructions.items.len); |
| 6170 | | try multi_cases_payload.appendSlice(gpa, case_scope.instructions.items); |
| 6171 | | } else if (case_node == special_node) { |
| 6172 | | const case_result = try expr(&case_scope, sub_scope, block_scope.break_result_loc, case.ast.target_expr); |
| 6173 | | try checkUsed(parent_gz, &case_scope.base, sub_scope); |
| 6174 | | if (!parent_gz.refIsNoReturn(case_result)) { |
| 6175 | | block_scope.break_count += 1; |
| 6176 | | _ = try case_scope.addBreak(.@"break", switch_block, case_result); |
| 6177 | | } |
| 6178 | | try special_case_payload.ensureUnusedCapacity(gpa, 1 + // body_len |
| 6179 | | case_scope.instructions.items.len); |
| 6180 | | special_case_payload.appendAssumeCapacity(@intCast(u32, case_scope.instructions.items.len)); |
| 6181 | | special_case_payload.appendSliceAssumeCapacity(case_scope.instructions.items); |
| 6182 | | } else { |
| 6154 | payloads.items[header_index] = items_len; |
| 6155 | payloads.items[header_index + 1] = ranges_len; |
| 6156 | break :blk header_index + 2; |
| 6157 | } else if (case_node == special_node) blk: { |
| 6158 | payloads.items[0] = header_index; |
| 6159 | try payloads.resize(gpa, header_index + 1); // body_len |
| 6160 | break :blk header_index; |
| 6161 | } else blk: { |
| 6162 | payloads.items[scalar_case_table + scalar_case_index] = header_index; |
| 6163 | scalar_case_index += 1; |
| 6164 | try payloads.resize(gpa, header_index + 2); // item, body_len |
| 6183 | 6165 | const item_node = case.ast.values[0]; |
| 6184 | 6166 | const item_inst = try comptimeExpr(parent_gz, scope, item_rl, item_node); |
| 6185 | | const case_result = try expr(&case_scope, sub_scope, block_scope.break_result_loc, case.ast.target_expr); |
| 6186 | | try checkUsed(parent_gz, &case_scope.base, sub_scope); |
| 6187 | | if (!parent_gz.refIsNoReturn(case_result)) { |
| 6188 | | block_scope.break_count += 1; |
| 6189 | | _ = try case_scope.addBreak(.@"break", switch_block, case_result); |
| 6190 | | } |
| 6191 | | try scalar_cases_payload.ensureUnusedCapacity(gpa, 2 + // item + body_len |
| 6192 | | case_scope.instructions.items.len); |
| 6193 | | scalar_cases_payload.appendAssumeCapacity(@enumToInt(item_inst)); |
| 6194 | | scalar_cases_payload.appendAssumeCapacity(@intCast(u32, case_scope.instructions.items.len)); |
| 6195 | | scalar_cases_payload.appendSliceAssumeCapacity(case_scope.instructions.items); |
| 6167 | payloads.items[header_index] = @enumToInt(item_inst); |
| 6168 | break :blk header_index + 1; |
| 6169 | }; |
| 6170 | |
| 6171 | const case_result = try expr(&case_scope, sub_scope, block_scope.break_result_loc, case.ast.target_expr); |
| 6172 | try checkUsed(parent_gz, &case_scope.base, sub_scope); |
| 6173 | if (!parent_gz.refIsNoReturn(case_result)) { |
| 6174 | block_scope.break_count += 1; |
| 6175 | _ = try case_scope.addBreak(.@"break", switch_block, case_result); |
| 6196 | 6176 | } |
| 6177 | payloads.items[body_len_index] = @intCast(u32, case_scope.instructions.items.len); |
| 6178 | try payloads.appendSlice(gpa, case_scope.instructions.items); |
| 6197 | 6179 | } |
| 6198 | 6180 | // Now that the item expressions are generated we can add this. |
| 6199 | 6181 | try parent_gz.instructions.append(gpa, switch_block); |
| 6200 | 6182 | |
| 6201 | 6183 | try astgen.extra.ensureUnusedCapacity(gpa, @typeInfo(Zir.Inst.SwitchBlock).Struct.fields.len + |
| 6202 | 6184 | @boolToInt(multi_cases_len != 0) + |
| 6203 | | special_case_payload.items.len + |
| 6204 | | scalar_cases_payload.items.len + |
| 6205 | | multi_cases_payload.items.len); |
| 6185 | payloads.items.len - case_table_len); |
| 6206 | 6186 | |
| 6207 | 6187 | const payload_index = astgen.addExtraAssumeCapacity(Zir.Inst.SwitchBlock{ |
| 6208 | 6188 | .operand = cond, |
| ... | ... | @@ -6215,62 +6195,58 @@ fn switchExpr( |
| 6215 | 6195 | }, |
| 6216 | 6196 | }); |
| 6217 | 6197 | |
| 6218 | | const zir_datas = astgen.instructions.items(.data); |
| 6219 | | const zir_tags = astgen.instructions.items(.tag); |
| 6220 | | |
| 6221 | | zir_datas[switch_block].pl_node.payload_index = payload_index; |
| 6222 | | |
| 6223 | 6198 | if (multi_cases_len != 0) { |
| 6224 | 6199 | astgen.extra.appendAssumeCapacity(multi_cases_len); |
| 6225 | 6200 | } |
| 6226 | 6201 | |
| 6227 | | const strat = rl.strategy(&block_scope); |
| 6228 | | switch (strat.tag) { |
| 6229 | | .break_operand => { |
| 6230 | | // Switch expressions return `true` for `nodeMayNeedMemoryLocation` thus |
| 6231 | | // `elide_store_to_block_ptr_instructions` will either be true, |
| 6232 | | // or all prongs are noreturn. |
| 6233 | | if (!strat.elide_store_to_block_ptr_instructions) { |
| 6234 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items); |
| 6235 | | astgen.extra.appendSliceAssumeCapacity(scalar_cases_payload.items); |
| 6236 | | astgen.extra.appendSliceAssumeCapacity(multi_cases_payload.items); |
| 6237 | | return indexToRef(switch_block); |
| 6238 | | } |
| 6202 | const zir_datas = astgen.instructions.items(.data); |
| 6203 | const zir_tags = astgen.instructions.items(.tag); |
| 6239 | 6204 | |
| 6240 | | // There will necessarily be a store_to_block_ptr for |
| 6241 | | // all prongs, except for prongs that ended with a noreturn instruction. |
| 6242 | | // Elide all the `store_to_block_ptr` instructions. |
| 6205 | zir_datas[switch_block].pl_node.payload_index = payload_index; |
| 6243 | 6206 | |
| 6244 | | // The break instructions need to have their operands coerced if the |
| 6245 | | // switch's result location is a `ty`. In this case we overwrite the |
| 6246 | | // `store_to_block_ptr` instruction with an `as` instruction and repurpose |
| 6247 | | // it as the break operand. |
| 6207 | const strat = rl.strategy(&block_scope); |
| 6208 | for (payloads.items[0..case_table_len]) |start_index, table_index| { |
| 6209 | var body_len_index = start_index; |
| 6210 | var end_index = start_index; |
| 6211 | if (table_index < scalar_case_table) { |
| 6212 | end_index += 1; |
| 6213 | } else if (table_index < multi_case_table) { |
| 6214 | body_len_index += 1; |
| 6215 | end_index += 2; |
| 6216 | } else { |
| 6217 | body_len_index += 2; |
| 6218 | const items_len = payloads.items[start_index]; |
| 6219 | const ranges_len = payloads.items[start_index + 1]; |
| 6220 | end_index += 3 + items_len + 2 * ranges_len; |
| 6221 | } |
| 6248 | 6222 | |
| 6249 | | var extra_index: usize = 0; |
| 6250 | | if (special_prong != .none) special_prong: { |
| 6251 | | const body_len_index = extra_index; |
| 6252 | | const body_len = special_case_payload.items[extra_index]; |
| 6253 | | extra_index += 1; |
| 6254 | | if (body_len < 2) { |
| 6255 | | extra_index += body_len; |
| 6256 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items[0..extra_index]); |
| 6257 | | break :special_prong; |
| 6258 | | } |
| 6259 | | extra_index += body_len - 2; |
| 6260 | | const store_inst = special_case_payload.items[extra_index]; |
| 6223 | const body_len = payloads.items[body_len_index]; |
| 6224 | end_index += body_len; |
| 6225 | |
| 6226 | switch (strat.tag) { |
| 6227 | .break_operand => blk: { |
| 6228 | // Switch expressions return `true` for `nodeMayNeedMemoryLocation` thus |
| 6229 | // `elide_store_to_block_ptr_instructions` will either be true, |
| 6230 | // or all prongs are noreturn. |
| 6231 | if (!strat.elide_store_to_block_ptr_instructions) |
| 6232 | break :blk; |
| 6233 | |
| 6234 | // There will necessarily be a store_to_block_ptr for |
| 6235 | // all prongs, except for prongs that ended with a noreturn instruction. |
| 6236 | // Elide all the `store_to_block_ptr` instructions. |
| 6237 | |
| 6238 | // The break instructions need to have their operands coerced if the |
| 6239 | // switch's result location is a `ty`. In this case we overwrite the |
| 6240 | // `store_to_block_ptr` instruction with an `as` instruction and repurpose |
| 6241 | // it as the break operand. |
| 6242 | if (body_len < 2) |
| 6243 | break :blk; |
| 6244 | const store_inst = payloads.items[end_index - 2]; |
| 6261 | 6245 | if (zir_tags[store_inst] != .store_to_block_ptr or |
| 6262 | 6246 | zir_datas[store_inst].bin.lhs != block_scope.rl_ptr) |
| 6263 | | { |
| 6264 | | extra_index += 2; |
| 6265 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items[0..extra_index]); |
| 6266 | | break :special_prong; |
| 6267 | | } |
| 6268 | | assert(zir_datas[store_inst].bin.lhs == block_scope.rl_ptr); |
| 6247 | break :blk; |
| 6248 | const break_inst = payloads.items[end_index - 1]; |
| 6269 | 6249 | if (block_scope.rl_ty_inst != .none) { |
| 6270 | | extra_index += 1; |
| 6271 | | const break_inst = special_case_payload.items[extra_index]; |
| 6272 | | extra_index += 1; |
| 6273 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items[0..extra_index]); |
| 6274 | 6250 | zir_tags[store_inst] = .as; |
| 6275 | 6251 | zir_datas[store_inst].bin = .{ |
| 6276 | 6252 | .lhs = block_scope.rl_ty_inst, |
| ... | ... | @@ -6278,168 +6254,30 @@ fn switchExpr( |
| 6278 | 6254 | }; |
| 6279 | 6255 | zir_datas[break_inst].@"break".operand = indexToRef(store_inst); |
| 6280 | 6256 | } else { |
| 6281 | | special_case_payload.items[body_len_index] -= 1; |
| 6282 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items[0..extra_index]); |
| 6283 | | extra_index += 1; |
| 6284 | | astgen.extra.appendAssumeCapacity(special_case_payload.items[extra_index]); |
| 6285 | | extra_index += 1; |
| 6286 | | } |
| 6287 | | } else { |
| 6288 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items[0..extra_index]); |
| 6289 | | } |
| 6290 | | extra_index = 0; |
| 6291 | | var scalar_i: u32 = 0; |
| 6292 | | while (scalar_i < scalar_cases_len) : (scalar_i += 1) { |
| 6293 | | const start_index = extra_index; |
| 6294 | | extra_index += 1; |
| 6295 | | const body_len_index = extra_index; |
| 6296 | | const body_len = scalar_cases_payload.items[extra_index]; |
| 6297 | | extra_index += 1; |
| 6298 | | if (body_len < 2) { |
| 6299 | | extra_index += body_len; |
| 6300 | | astgen.extra.appendSliceAssumeCapacity(scalar_cases_payload.items[start_index..extra_index]); |
| 6257 | payloads.items[body_len_index] -= 1; |
| 6258 | astgen.extra.appendSliceAssumeCapacity(payloads.items[start_index .. end_index - 2]); |
| 6259 | astgen.extra.appendAssumeCapacity(break_inst); |
| 6301 | 6260 | continue; |
| 6302 | 6261 | } |
| 6303 | | extra_index += body_len - 2; |
| 6304 | | const store_inst = scalar_cases_payload.items[extra_index]; |
| 6305 | | if (zir_tags[store_inst] != .store_to_block_ptr or |
| 6306 | | zir_datas[store_inst].bin.lhs != block_scope.rl_ptr) |
| 6307 | | { |
| 6308 | | extra_index += 2; |
| 6309 | | astgen.extra.appendSliceAssumeCapacity(scalar_cases_payload.items[start_index..extra_index]); |
| 6310 | | continue; |
| 6311 | | } |
| 6312 | | if (block_scope.rl_ty_inst != .none) { |
| 6313 | | extra_index += 1; |
| 6314 | | const break_inst = scalar_cases_payload.items[extra_index]; |
| 6315 | | extra_index += 1; |
| 6316 | | astgen.extra.appendSliceAssumeCapacity(scalar_cases_payload.items[start_index..extra_index]); |
| 6317 | | zir_tags[store_inst] = .as; |
| 6318 | | zir_datas[store_inst].bin = .{ |
| 6319 | | .lhs = block_scope.rl_ty_inst, |
| 6320 | | .rhs = zir_datas[break_inst].@"break".operand, |
| 6321 | | }; |
| 6322 | | zir_datas[break_inst].@"break".operand = indexToRef(store_inst); |
| 6323 | | } else { |
| 6324 | | scalar_cases_payload.items[body_len_index] -= 1; |
| 6325 | | astgen.extra.appendSliceAssumeCapacity(scalar_cases_payload.items[start_index..extra_index]); |
| 6326 | | extra_index += 1; |
| 6327 | | astgen.extra.appendAssumeCapacity(scalar_cases_payload.items[extra_index]); |
| 6328 | | extra_index += 1; |
| 6329 | | } |
| 6330 | | } |
| 6331 | | extra_index = 0; |
| 6332 | | var multi_i: u32 = 0; |
| 6333 | | while (multi_i < multi_cases_len) : (multi_i += 1) { |
| 6334 | | const start_index = extra_index; |
| 6335 | | const items_len = multi_cases_payload.items[extra_index]; |
| 6336 | | extra_index += 1; |
| 6337 | | const ranges_len = multi_cases_payload.items[extra_index]; |
| 6338 | | extra_index += 1; |
| 6339 | | const body_len_index = extra_index; |
| 6340 | | const body_len = multi_cases_payload.items[extra_index]; |
| 6341 | | extra_index += 1; |
| 6342 | | extra_index += items_len; |
| 6343 | | extra_index += 2 * ranges_len; |
| 6344 | | if (body_len < 2) { |
| 6345 | | extra_index += body_len; |
| 6346 | | astgen.extra.appendSliceAssumeCapacity(multi_cases_payload.items[start_index..extra_index]); |
| 6347 | | continue; |
| 6348 | | } |
| 6349 | | extra_index += body_len - 2; |
| 6350 | | const store_inst = multi_cases_payload.items[extra_index]; |
| 6351 | | if (zir_tags[store_inst] != .store_to_block_ptr or |
| 6352 | | zir_datas[store_inst].bin.lhs != block_scope.rl_ptr) |
| 6353 | | { |
| 6354 | | extra_index += 2; |
| 6355 | | astgen.extra.appendSliceAssumeCapacity(multi_cases_payload.items[start_index..extra_index]); |
| 6356 | | continue; |
| 6357 | | } |
| 6358 | | if (block_scope.rl_ty_inst != .none) { |
| 6359 | | extra_index += 1; |
| 6360 | | const break_inst = multi_cases_payload.items[extra_index]; |
| 6361 | | extra_index += 1; |
| 6362 | | astgen.extra.appendSliceAssumeCapacity(multi_cases_payload.items[start_index..extra_index]); |
| 6363 | | zir_tags[store_inst] = .as; |
| 6364 | | zir_datas[store_inst].bin = .{ |
| 6365 | | .lhs = block_scope.rl_ty_inst, |
| 6366 | | .rhs = zir_datas[break_inst].@"break".operand, |
| 6367 | | }; |
| 6368 | | zir_datas[break_inst].@"break".operand = indexToRef(store_inst); |
| 6369 | | } else { |
| 6370 | | assert(zir_datas[store_inst].bin.lhs == block_scope.rl_ptr); |
| 6371 | | multi_cases_payload.items[body_len_index] -= 1; |
| 6372 | | astgen.extra.appendSliceAssumeCapacity(multi_cases_payload.items[start_index..extra_index]); |
| 6373 | | extra_index += 1; |
| 6374 | | astgen.extra.appendAssumeCapacity(multi_cases_payload.items[extra_index]); |
| 6375 | | extra_index += 1; |
| 6376 | | } |
| 6377 | | } |
| 6378 | | |
| 6379 | | const block_ref = indexToRef(switch_block); |
| 6380 | | switch (rl) { |
| 6381 | | .ref => return block_ref, |
| 6382 | | else => return rvalue(parent_gz, rl, block_ref, switch_node), |
| 6383 | | } |
| 6384 | | }, |
| 6385 | | .break_void => { |
| 6386 | | assert(!strat.elide_store_to_block_ptr_instructions); |
| 6387 | | astgen.extra.appendSliceAssumeCapacity(special_case_payload.items); |
| 6388 | | astgen.extra.appendSliceAssumeCapacity(scalar_cases_payload.items); |
| 6389 | | astgen.extra.appendSliceAssumeCapacity(multi_cases_payload.items); |
| 6390 | | // Modify all the terminating instruction tags to become `break` variants. |
| 6391 | | var extra_index: usize = payload_index; |
| 6392 | | extra_index += 2; |
| 6393 | | extra_index += @boolToInt(multi_cases_len != 0); |
| 6394 | | if (special_prong != .none) { |
| 6395 | | const body_len = astgen.extra.items[extra_index]; |
| 6396 | | extra_index += 1; |
| 6397 | | const body = astgen.extra.items[extra_index..][0..body_len]; |
| 6398 | | extra_index += body_len; |
| 6399 | | const last = body[body.len - 1]; |
| 6400 | | if (zir_tags[last] == .@"break" and |
| 6401 | | zir_datas[last].@"break".block_inst == switch_block) |
| 6402 | | { |
| 6403 | | zir_datas[last].@"break".operand = .void_value; |
| 6404 | | } |
| 6405 | | } |
| 6406 | | var scalar_i: u32 = 0; |
| 6407 | | while (scalar_i < scalar_cases_len) : (scalar_i += 1) { |
| 6408 | | extra_index += 1; |
| 6409 | | const body_len = astgen.extra.items[extra_index]; |
| 6410 | | extra_index += 1; |
| 6411 | | const body = astgen.extra.items[extra_index..][0..body_len]; |
| 6412 | | extra_index += body_len; |
| 6413 | | const last = body[body.len - 1]; |
| 6414 | | if (zir_tags[last] == .@"break" and |
| 6415 | | zir_datas[last].@"break".block_inst == switch_block) |
| 6416 | | { |
| 6417 | | zir_datas[last].@"break".operand = .void_value; |
| 6418 | | } |
| 6419 | | } |
| 6420 | | var multi_i: u32 = 0; |
| 6421 | | while (multi_i < multi_cases_len) : (multi_i += 1) { |
| 6422 | | const items_len = astgen.extra.items[extra_index]; |
| 6423 | | extra_index += 1; |
| 6424 | | const ranges_len = astgen.extra.items[extra_index]; |
| 6425 | | extra_index += 1; |
| 6426 | | const body_len = astgen.extra.items[extra_index]; |
| 6427 | | extra_index += 1; |
| 6428 | | extra_index += items_len; |
| 6429 | | extra_index += 2 * ranges_len; |
| 6430 | | const body = astgen.extra.items[extra_index..][0..body_len]; |
| 6431 | | extra_index += body_len; |
| 6432 | | const last = body[body.len - 1]; |
| 6433 | | if (zir_tags[last] == .@"break" and |
| 6434 | | zir_datas[last].@"break".block_inst == switch_block) |
| 6262 | }, |
| 6263 | .break_void => { |
| 6264 | assert(!strat.elide_store_to_block_ptr_instructions); |
| 6265 | const last_inst = payloads.items[end_index - 1]; |
| 6266 | if (zir_tags[last_inst] == .@"break" and |
| 6267 | zir_datas[last_inst].@"break".block_inst == switch_block) |
| 6435 | 6268 | { |
| 6436 | | zir_datas[last].@"break".operand = .void_value; |
| 6269 | zir_datas[last_inst].@"break".operand = .void_value; |
| 6437 | 6270 | } |
| 6438 | | } |
| 6271 | }, |
| 6272 | } |
| 6439 | 6273 | |
| 6440 | | return indexToRef(switch_block); |
| 6441 | | }, |
| 6274 | astgen.extra.appendSliceAssumeCapacity(payloads.items[start_index..end_index]); |
| 6442 | 6275 | } |
| 6276 | |
| 6277 | const block_ref = indexToRef(switch_block); |
| 6278 | if (strat.tag == .break_operand and strat.elide_store_to_block_ptr_instructions and rl != .ref) |
| 6279 | return rvalue(parent_gz, rl, block_ref, switch_node); |
| 6280 | return block_ref; |
| 6443 | 6281 | } |
| 6444 | 6282 | |
| 6445 | 6283 | fn ret(gz: *GenZir, scope: *Scope, node: Ast.Node.Index) InnerError!Zir.Inst.Ref { |