| ... | ... | @@ -1138,6 +1138,8 @@ fn airNot(self: *Self, inst: Air.Inst.Index) !void { |
| 1138 | 1138 | } }, |
| 1139 | 1139 | }); |
| 1140 | 1140 | |
| 1141 | try self.truncRegister(dest_reg, dest_reg, int_info.signedness, int_info.bits); |
| 1142 | |
| 1141 | 1143 | break :result MCValue{ .register = dest_reg }; |
| 1142 | 1144 | } else { |
| 1143 | 1145 | return self.fail("TODO AArch64 not on integers > u64/i64", .{}); |
| ... | ... | @@ -1516,11 +1518,8 @@ fn binOp( |
| 1516 | 1518 | const int_info = lhs_ty.intInfo(self.target.*); |
| 1517 | 1519 | if (int_info.bits <= 64) { |
| 1518 | 1520 | const result_reg = result.register; |
| 1519 | | |
| 1520 | | if (int_info.bits < 64) { |
| 1521 | | try self.truncRegister(result_reg, result_reg, int_info.signedness, int_info.bits); |
| 1522 | | return result; |
| 1523 | | } else return result; |
| 1521 | try self.truncRegister(result_reg, result_reg, int_info.signedness, int_info.bits); |
| 1522 | return result; |
| 1524 | 1523 | } else { |
| 1525 | 1524 | return self.fail("TODO binary operations on integers > u64/i64", .{}); |
| 1526 | 1525 | } |
| ... | ... | @@ -1554,8 +1553,8 @@ fn binOp( |
| 1554 | 1553 | else => unreachable, |
| 1555 | 1554 | } |
| 1556 | 1555 | }, |
| 1557 | | .shl, |
| 1558 | | .shr, |
| 1556 | .shl_exact, |
| 1557 | .shr_exact, |
| 1559 | 1558 | => { |
| 1560 | 1559 | switch (lhs_ty.zigTypeTag()) { |
| 1561 | 1560 | .Vector => return self.fail("TODO binary operations on vectors", .{}), |
| ... | ... | @@ -1565,16 +1564,16 @@ fn binOp( |
| 1565 | 1564 | const rhs_immediate_ok = rhs == .immediate; |
| 1566 | 1565 | |
| 1567 | 1566 | const mir_tag_register: Mir.Inst.Tag = switch (tag) { |
| 1568 | | .shl => .lsl_register, |
| 1569 | | .shr => switch (lhs_ty.intInfo(self.target.*).signedness) { |
| 1567 | .shl_exact => .lsl_register, |
| 1568 | .shr_exact => switch (int_info.signedness) { |
| 1570 | 1569 | .signed => Mir.Inst.Tag.asr_register, |
| 1571 | 1570 | .unsigned => Mir.Inst.Tag.lsr_register, |
| 1572 | 1571 | }, |
| 1573 | 1572 | else => unreachable, |
| 1574 | 1573 | }; |
| 1575 | 1574 | const mir_tag_immediate: Mir.Inst.Tag = switch (tag) { |
| 1576 | | .shl => .lsl_immediate, |
| 1577 | | .shr => switch (lhs_ty.intInfo(self.target.*).signedness) { |
| 1575 | .shl_exact => .lsl_immediate, |
| 1576 | .shr_exact => switch (int_info.signedness) { |
| 1578 | 1577 | .signed => Mir.Inst.Tag.asr_immediate, |
| 1579 | 1578 | .unsigned => Mir.Inst.Tag.lsr_immediate, |
| 1580 | 1579 | }, |
| ... | ... | @@ -1593,6 +1592,38 @@ fn binOp( |
| 1593 | 1592 | else => unreachable, |
| 1594 | 1593 | } |
| 1595 | 1594 | }, |
| 1595 | .shl, |
| 1596 | .shr, |
| 1597 | => { |
| 1598 | const base_tag: Air.Inst.Tag = switch (tag) { |
| 1599 | .shl => .shl_exact, |
| 1600 | .shr => .shr_exact, |
| 1601 | else => unreachable, |
| 1602 | }; |
| 1603 | |
| 1604 | // Generate a shl_exact/shr_exact |
| 1605 | const result = try self.binOp(base_tag, maybe_inst, lhs, rhs, lhs_ty, rhs_ty); |
| 1606 | |
| 1607 | // Truncate if necessary |
| 1608 | switch (tag) { |
| 1609 | .shr => return result, |
| 1610 | .shl => switch (lhs_ty.zigTypeTag()) { |
| 1611 | .Vector => return self.fail("TODO binary operations on vectors", .{}), |
| 1612 | .Int => { |
| 1613 | const int_info = lhs_ty.intInfo(self.target.*); |
| 1614 | if (int_info.bits <= 64) { |
| 1615 | const result_reg = result.register; |
| 1616 | try self.truncRegister(result_reg, result_reg, int_info.signedness, int_info.bits); |
| 1617 | return result; |
| 1618 | } else { |
| 1619 | return self.fail("TODO binary operations on integers > u64/i64", .{}); |
| 1620 | } |
| 1621 | }, |
| 1622 | else => unreachable, |
| 1623 | }, |
| 1624 | else => unreachable, |
| 1625 | } |
| 1626 | }, |
| 1596 | 1627 | .bool_and, |
| 1597 | 1628 | .bool_or, |
| 1598 | 1629 | => { |