|
1 | 1 | #ifndef OPCODE_H
|
2 | 2 | #define OPCODE_H
|
3 | 3 |
|
4 |
| -// ADD_LIKE r8 , imm8 -- op1 /0 ib |
5 |
| -// ADD_LIKE r16, imm8 -- op2 /0 ib |
6 |
| -// ADD_LIKE r32, imm8 -- op2 /0 ib |
7 |
| -// ADD_LIKE r64, imm8 -- REX.W + op2 /0 ib |
8 |
| -// ADD_LIKE r16, imm16 -- op3 /0 iw |
9 |
| -// ADD_LIKE r32, imm32 -- op3 /0 id |
10 |
| -// ADD_LIKE r64, imm32 -- REX.W + op3 /0 id |
| 4 | +// ADD_LIKE r8 , imm8 -- op1 /digit ib |
| 5 | +// ADD_LIKE r16, imm8 -- op2 /digit ib |
| 6 | +// ADD_LIKE r32, imm8 -- op2 /digit ib |
| 7 | +// ADD_LIKE r64, imm8 -- REX.W + op2 /digit ib |
| 8 | +// ADD_LIKE r16, imm16 -- op3 /digit iw |
| 9 | +// ADD_LIKE r32, imm32 -- op3 /digit id |
| 10 | +// ADD_LIKE r64, imm32 -- REX.W + op3 /digit id |
11 | 11 | template <uint8_t digit, uint8_t op_1, uint8_t op_2, uint8_t op_3,
|
12 | 12 | size_t s, size_t i,
|
13 | 13 | size_t imms, typename Immediate_type<imms>::type x, bool is_var>
|
@@ -35,13 +35,13 @@ constexpr auto ADD_LIKE (Register<s, i> reg, Immediate<imms, x, is_var> imm)
|
35 | 35 | }
|
36 | 36 | }
|
37 | 37 |
|
38 |
| -// ADD_LIKE m8, imm8 -- op1 /0 ib |
39 |
| -// ADD_LIKE m16, imm8 -- op2 /0 ib |
40 |
| -// ADD_LIKE m32, imm8 -- op2 /0 ib |
41 |
| -// ADD_LIKE m64, imm8 -- REX.W + op2 /0 ib |
42 |
| -// ADD_LIKE m16, imm16 -- op3 /0 iw |
43 |
| -// ADD_LIKE m32, imm32 -- op3 /0 id |
44 |
| -// ADD_LIKE m64, imm32 -- REX.W + op3 /0 id |
| 38 | +// ADD_LIKE m8, imm8 -- op1 /digit ib |
| 39 | +// ADD_LIKE m16, imm8 -- op2 /digit ib |
| 40 | +// ADD_LIKE m32, imm8 -- op2 /digit ib |
| 41 | +// ADD_LIKE m64, imm8 -- REX.W + op2 /digit ib |
| 42 | +// ADD_LIKE m16, imm16 -- op3 /digit iw |
| 43 | +// ADD_LIKE m32, imm32 -- op3 /digit id |
| 44 | +// ADD_LIKE m64, imm32 -- REX.W + op3 /digit id |
45 | 45 | template <uint8_t digit, uint8_t op_1, uint8_t op_2, uint8_t op_3,
|
46 | 46 | size_t s, typename r1, typename r2, typename scale, typename disp,
|
47 | 47 | size_t imms, typename Immediate_type<imms>::type x, bool is_var>
|
@@ -69,6 +69,31 @@ constexpr auto ADD_LIKE (Memory<s, r1, r2, scale, disp> mem, Immediate<imms, x,
|
69 | 69 | }
|
70 | 70 | }
|
71 | 71 |
|
| 72 | +// ADD_LIKE m8, imm8 -- op1 /digit ib |
| 73 | +// ADD_LIKE m16, imm16 -- op2 /digit iw |
| 74 | +// ADD_LIKE m32, imm32 -- op2 /digit id |
| 75 | +// ADD_LIKE m64, imm64 -- REX.W + op2 /digit id |
| 76 | +template <uint8_t digit, uint8_t op_1, uint8_t op_2, |
| 77 | + size_t s, typename r1, typename r2, typename scale, typename disp, |
| 78 | + size_t imms, typename Immediate_type<imms>::type x, bool is_var> |
| 79 | +constexpr auto ADD_LIKE_SAME_SIZE (Memory<s, r1, r2, scale, disp> mem, Immediate<imms, x, is_var> imm) |
| 80 | +{ |
| 81 | + if constexpr (is_m8(mem) && is_imm8(imm)) |
| 82 | + { |
| 83 | + return rex<0, 0>(mem) + opcode<op_1>() + modrm<digit>(mem) + to_bytes(imm); |
| 84 | + } |
| 85 | + else if constexpr ((is_m16(mem) && is_imm16(imm)) || |
| 86 | + (is_m32(mem) && is_imm32(imm)) || |
| 87 | + (is_m64(mem) && is_imm32(imm))) |
| 88 | + { |
| 89 | + return rex<is_m64(mem)?1:0, 0>(mem) + opcode<op_2>() + modrm<digit>(mem) + to_bytes(imm); |
| 90 | + } |
| 91 | + else |
| 92 | + { |
| 93 | + |
| 94 | + } |
| 95 | +} |
| 96 | + |
72 | 97 | // ADD_LIKE r8, r8 -- op1 /r
|
73 | 98 | // ADD_LIKE r16, r16 -- op2 /r
|
74 | 99 | // ADD_LIKE r32, r32 -- op2 /r
|
@@ -410,6 +435,110 @@ constexpr auto INC (Memory<memsize, r1, r2, scale, disp> mem)
|
410 | 435 | }
|
411 | 436 | }
|
412 | 437 |
|
| 438 | + |
| 439 | +// JE rel8 |
| 440 | +// JE rel32 |
| 441 | +//template <size_t s, typename Immediate_type<imms>::type x, bool is_var> |
| 442 | +//constexpr auto JE (Immediate<s, x, is_var> imm) |
| 443 | +//{ |
| 444 | +// if constexpr (is_imm8(imm)) |
| 445 | +// { |
| 446 | +// return opcode<'\x74'>() + to_bytes(imm); |
| 447 | +// } |
| 448 | +// else if constexpr (is_imm32(imm)) |
| 449 | +// { |
| 450 | +// return opcode<'\x0f'>() + opcode<'\x84'>() + to_bytes(imm); |
| 451 | +// } |
| 452 | +// else |
| 453 | +// { |
| 454 | +// |
| 455 | +// } |
| 456 | +//} |
| 457 | + |
| 458 | +// JNE rel8 |
| 459 | +// JNE rel32 |
| 460 | +//template <size_t s, typename Immediate_type<imms>::type x, bool is_var> |
| 461 | +//constexpr auto JNE (Immediate<s, x, is_var> imm) |
| 462 | +//{ |
| 463 | +// if constexpr (is_imm8(imm)) |
| 464 | +// { |
| 465 | +// return opcode<'\x75'>() + to_bytes(imm); |
| 466 | +// } |
| 467 | +// else if constexpr (is_imm32(imm)) |
| 468 | +// { |
| 469 | +// return opcode<'\x0f'>() + opcode<'\x85'>() + to_bytes(imm); |
| 470 | +// } |
| 471 | +// else |
| 472 | +// { |
| 473 | +// |
| 474 | +// } |
| 475 | +//} |
| 476 | + |
| 477 | +// MOV r8, imm8 -- c6 /0 ib |
| 478 | +// MOV r16, imm16 -- c7 /0 iw |
| 479 | +// MOV r32, imm32 -- c7 /0 id |
| 480 | +// MOV r64, imm64 -- REX.W + c7 /0 /id |
| 481 | +template <size_t s, size_t i, |
| 482 | + size_t imms, typename Immediate_type<imms>::type x, bool is_var> |
| 483 | +constexpr auto MOV (Register<s, i> reg, Immediate<imms, x, is_var> imm) |
| 484 | +{ |
| 485 | + //return ADD_LIKE_SAME_SIZE<0, '\xc6', '\xc7'>(reg, imm); |
| 486 | + if constexpr (is_r8(reg) && is_imm8(imm)) |
| 487 | + { |
| 488 | + return rex<0>(reg) + opcode<'\xb0' + reg.index % 8>() + to_bytes(imm); |
| 489 | + } |
| 490 | + else if constexpr ((is_r16(reg) && is_imm16(imm)) || |
| 491 | + (is_r32(reg) && is_imm32(imm)) || |
| 492 | + (is_r64(reg) && is_imm64(imm))) |
| 493 | + { |
| 494 | + return rex<is_r64(reg)?1:0>(reg) + opcode<'\xb8' + reg.index % 8>() + to_bytes(imm); |
| 495 | + } |
| 496 | +} |
| 497 | + |
| 498 | +// MOV m8, imm8 -- c6 /0 ib |
| 499 | +// MOV m16, imm16 -- c7 /0 iw |
| 500 | +// MOV m32, imm32 -- c7 /0 id |
| 501 | +// MOV m64, imm32 -- REX.W + c7 /0 /id |
| 502 | +template <size_t s, typename r1, typename r2, typename scale, typename disp, |
| 503 | + size_t imms, typename Immediate_type<imms>::type x, bool is_var> |
| 504 | +constexpr auto MOV (Memory<s, r1, r2, scale, disp> mem, Immediate<imms, x, is_var> imm) |
| 505 | +{ |
| 506 | + return ADD_LIKE_SAME_SIZE<0, '\xc6', '\xc7'>(mem, imm); |
| 507 | +} |
| 508 | + |
| 509 | +// MOV r8, r8 -- 88 /r |
| 510 | +// MOV r16, r16 -- 89 /r |
| 511 | +// MOV r32, r32 -- 89 /r |
| 512 | +// MOV r64, r64 -- REX.W + 89 /r |
| 513 | +template <size_t s1, size_t i1, size_t s2, size_t i2> |
| 514 | +constexpr auto MOV (Register<s1, i1> reg1, Register<s2, i2> reg2) |
| 515 | +{ |
| 516 | + return ADD_LIKE<'\x88', '\x89'>(reg1, reg2); |
| 517 | +} |
| 518 | + |
| 519 | +// MOV m8, r8 -- 88 /r |
| 520 | +// MOV m16, r16 -- 89 /r |
| 521 | +// MOV m32, r32 -- 89 /r |
| 522 | +// MOV m64, r64 -- REX.W + 89 /r |
| 523 | +template <size_t memsize, typename r1, typename r2, typename scale, typename disp, |
| 524 | + size_t regsize, size_t i> |
| 525 | +constexpr auto MOV (Memory<memsize, r1, r2, scale, disp> mem, Register<regsize, i> reg) |
| 526 | +{ |
| 527 | + return ADD_LIKE<'\x88', '\x89'>(mem, reg); |
| 528 | +} |
| 529 | + |
| 530 | +// MOV r8, m8 -- 8a /r |
| 531 | +// MOV r16, m16 -- 8b /r |
| 532 | +// MOV r32, m32 -- 8b /r |
| 533 | +// MOV r64, m64 -- REX.W + 8b /r |
| 534 | +template <size_t regsize, size_t i, |
| 535 | + size_t memsize, typename r1, typename r2, typename scale, typename disp> |
| 536 | +constexpr auto MOV (Register<regsize, i> reg, Memory<memsize, r1, r2, scale, disp> mem) |
| 537 | +{ |
| 538 | + return ADD_LIKE<'\x8a', '\x8b'>(reg, mem); |
| 539 | +} |
| 540 | + |
| 541 | + |
413 | 542 | //! SYSCALL
|
414 | 543 | constexpr auto SYSCALL ()
|
415 | 544 | {
|
|
0 commit comments