| ... | @@ -1308,6 +1308,15 @@ const Memory = struct { | ... | @@ -1308,6 +1308,15 @@ const Memory = struct { |
| 1308 | } | 1308 | } |
| 1309 | }; | 1309 | }; |
| 1310 | | 1310 | |
| | 1311 | fn encodeImm(encoder: Encoder, imm: i32, size: u64) void { |
| | 1312 | switch (size) { |
| | 1313 | 8 => encoder.imm8(@intCast(i8, imm)), |
| | 1314 | 16 => encoder.imm16(@intCast(i16, imm)), |
| | 1315 | 32, 64 => encoder.imm32(imm), |
| | 1316 | else => unreachable, |
| | 1317 | } |
| | 1318 | } |
| | 1319 | |
| 1311 | const RegisterOrMemory = union(enum) { | 1320 | const RegisterOrMemory = union(enum) { |
| 1312 | register: Register, | 1321 | register: Register, |
| 1313 | memory: Memory, | 1322 | memory: Memory, |
| ... | @@ -1365,13 +1374,7 @@ fn lowerToIEnc(tag: Tag, imm: i32, code: *std.ArrayList(u8)) LoweringError!void | ... | @@ -1365,13 +1374,7 @@ fn lowerToIEnc(tag: Tag, imm: i32, code: *std.ArrayList(u8)) LoweringError!void |
| 1365 | encoder.prefix16BitMode(); | 1374 | encoder.prefix16BitMode(); |
| 1366 | } | 1375 | } |
| 1367 | opc.encode(encoder); | 1376 | opc.encode(encoder); |
| 1368 | if (immOpSize(imm) == 8) { | 1377 | encodeImm(encoder, imm, immOpSize(imm)); |
| 1369 | encoder.imm8(@intCast(i8, imm)); | | |
| 1370 | } else if (immOpSize(imm) == 16) { | | |
| 1371 | encoder.imm16(@intCast(i16, imm)); | | |
| 1372 | } else { | | |
| 1373 | encoder.imm32(imm); | | |
| 1374 | } | | |
| 1375 | } | 1378 | } |
| 1376 | | 1379 | |
| 1377 | fn lowerToOEnc(tag: Tag, reg: Register, code: *std.ArrayList(u8)) LoweringError!void { | 1380 | fn lowerToOEnc(tag: Tag, reg: Register, code: *std.ArrayList(u8)) LoweringError!void { |
| ... | @@ -1549,18 +1552,7 @@ fn lowerToMiEnc(tag: Tag, reg_or_mem: RegisterOrMemory, imm: i32, code: *std.Arr | ... | @@ -1549,18 +1552,7 @@ fn lowerToMiEnc(tag: Tag, reg_or_mem: RegisterOrMemory, imm: i32, code: *std.Arr |
| 1549 | }); | 1552 | }); |
| 1550 | opc.encode(encoder); | 1553 | opc.encode(encoder); |
| 1551 | encoder.modRm_direct(modrm_ext, dst_reg.lowId()); | 1554 | encoder.modRm_direct(modrm_ext, dst_reg.lowId()); |
| 1552 | switch (dst_reg.size()) { | 1555 | encodeImm(encoder, imm, dst_reg.size()); |
| 1553 | 8 => { | | |
| 1554 | const imm8 = try math.cast(i8, imm); | | |
| 1555 | encoder.imm8(imm8); | | |
| 1556 | }, | | |
| 1557 | 16 => { | | |
| 1558 | const imm16 = try math.cast(i16, imm); | | |
| 1559 | encoder.imm16(imm16); | | |
| 1560 | }, | | |
| 1561 | 32, 64 => encoder.imm32(imm), | | |
| 1562 | else => unreachable, | | |
| 1563 | } | | |
| 1564 | }, | 1556 | }, |
| 1565 | .memory => |dst_mem| { | 1557 | .memory => |dst_mem| { |
| 1566 | const opc = getOpCode(tag, .mi, dst_mem.ptr_size == .byte_ptr).?; | 1558 | const opc = getOpCode(tag, .mi, dst_mem.ptr_size == .byte_ptr).?; |
| ... | @@ -1582,19 +1574,7 @@ fn lowerToMiEnc(tag: Tag, reg_or_mem: RegisterOrMemory, imm: i32, code: *std.Arr | ... | @@ -1582,19 +1574,7 @@ fn lowerToMiEnc(tag: Tag, reg_or_mem: RegisterOrMemory, imm: i32, code: *std.Arr |
| 1582 | opc.encode(encoder); | 1574 | opc.encode(encoder); |
| 1583 | Memory.encodeDsOrRip(encoder, modrm_ext, dst_mem.disp, dst_mem.rip); | 1575 | Memory.encodeDsOrRip(encoder, modrm_ext, dst_mem.disp, dst_mem.rip); |
| 1584 | } | 1576 | } |
| 1585 | switch (dst_mem.ptr_size) { | 1577 | encodeImm(encoder, imm, dst_mem.ptr_size.size()); |
| 1586 | .byte_ptr => { | | |
| 1587 | const imm8 = try math.cast(i8, imm); | | |
| 1588 | encoder.imm8(imm8); | | |
| 1589 | }, | | |
| 1590 | .word_ptr => { | | |
| 1591 | const imm16 = try math.cast(i16, imm); | | |
| 1592 | encoder.imm16(imm16); | | |
| 1593 | }, | | |
| 1594 | .dword_ptr, .qword_ptr => { | | |
| 1595 | encoder.imm32(imm); | | |
| 1596 | }, | | |
| 1597 | } | | |
| 1598 | }, | 1578 | }, |
| 1599 | } | 1579 | } |
| 1600 | } | 1580 | } |
| ... | @@ -1760,16 +1740,7 @@ fn lowerToRmiEnc( | ... | @@ -1760,16 +1740,7 @@ fn lowerToRmiEnc( |
| 1760 | } | 1740 | } |
| 1761 | }, | 1741 | }, |
| 1762 | } | 1742 | } |
| 1763 | switch (reg.size()) { | 1743 | encodeImm(encoder, imm, reg.size()); |
| 1764 | // TODO 8bit immediate | | |
| 1765 | 8 => unreachable, | | |
| 1766 | 16 => { | | |
| 1767 | const imm16 = try math.cast(i16, imm); | | |
| 1768 | encoder.imm16(imm16); | | |
| 1769 | }, | | |
| 1770 | 32, 64 => encoder.imm32(imm), | | |
| 1771 | else => unreachable, | | |
| 1772 | } | | |
| 1773 | } | 1744 | } |
| 1774 | | 1745 | |
| 1775 | fn expectEqualHexStrings(expected: []const u8, given: []const u8, assembly: []const u8) !void { | 1746 | fn expectEqualHexStrings(expected: []const u8, given: []const u8, assembly: []const u8) !void { |