| ... | ... | @@ -5598,8 +5598,48 @@ fn zirArrayMul(sema: *Sema, block: *Scope.Block, inst: Zir.Inst.Index) CompileEr |
| 5598 | 5598 | const tracy = trace(@src()); |
| 5599 | 5599 | defer tracy.end(); |
| 5600 | 5600 | |
| 5601 | | _ = inst; |
| 5602 | | return sema.mod.fail(&block.base, sema.src, "TODO implement zirArrayMul", .{}); |
| 5601 | const inst_data = sema.code.instructions.items(.data)[inst].pl_node; |
| 5602 | const extra = sema.code.extraData(Zir.Inst.Bin, inst_data.payload_index).data; |
| 5603 | const lhs = sema.resolveInst(extra.lhs); |
| 5604 | const lhs_ty = sema.typeOf(lhs); |
| 5605 | const lhs_src: LazySrcLoc = .{ .node_offset_bin_lhs = inst_data.src_node }; |
| 5606 | const rhs_src: LazySrcLoc = .{ .node_offset_bin_rhs = inst_data.src_node }; |
| 5607 | |
| 5608 | // In `**` rhs has to be comptime-known, but lhs can be runtime-known |
| 5609 | const tomulby = try sema.resolveInt(block, rhs_src, extra.rhs, Type.initTag(.usize)); |
| 5610 | const mulinfo = getArrayCatInfo(lhs_ty) orelse |
| 5611 | return sema.mod.fail(&block.base, lhs_src, "expected array, found '{}'", .{lhs_ty}); |
| 5612 | |
| 5613 | const final_len = std.math.mul(u64, mulinfo.len, tomulby) catch return sema.mod.fail(&block.base, rhs_src, "operation results in overflow", .{}); |
| 5614 | if (try sema.resolveDefinedValue(block, lhs_src, lhs)) |lhs_val| { |
| 5615 | if (lhs_ty.zigTypeTag() == .Pointer) { |
| 5616 | var anon_decl = try block.startAnonDecl(); |
| 5617 | defer anon_decl.deinit(); |
| 5618 | const lhs_sub_val = (try lhs_val.pointerDeref(anon_decl.arena())).?; |
| 5619 | |
| 5620 | const final_ty = if (mulinfo.sentinel) |sent| |
| 5621 | try Type.Tag.array_sentinel.create(anon_decl.arena(), .{ .len = final_len, .elem_type = mulinfo.elem_type, .sentinel = sent }) |
| 5622 | else |
| 5623 | try Type.Tag.array.create(anon_decl.arena(), .{ .len = final_len, .elem_type = mulinfo.elem_type }); |
| 5624 | |
| 5625 | const buf = try anon_decl.arena().alloc(Value, final_len); |
| 5626 | var i: u64 = 0; |
| 5627 | while (i < tomulby) : (i += 1) { |
| 5628 | var j: u64 = 0; |
| 5629 | while (j < mulinfo.len) : (j += 1) { |
| 5630 | const val = try lhs_sub_val.elemValue(sema.arena, j); |
| 5631 | buf[mulinfo.len * i + j] = try val.copy(anon_decl.arena()); |
| 5632 | } |
| 5633 | } |
| 5634 | const val = try Value.Tag.array.create(anon_decl.arena(), buf); |
| 5635 | return sema.analyzeDeclRef(try anon_decl.finish( |
| 5636 | final_ty, |
| 5637 | val, |
| 5638 | )); |
| 5639 | } |
| 5640 | return sema.mod.fail(&block.base, lhs_src, "TODO array_mul more types of Values", .{}); |
| 5641 | } |
| 5642 | return sema.mod.fail(&block.base, lhs_src, "TODO runtime array_mul", .{}); |
| 5603 | 5643 | } |
| 5604 | 5644 | |
| 5605 | 5645 | fn zirNegate( |