summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--iseq.c12
-rw-r--r--ujit_asm.c37
-rw-r--r--ujit_asm.h26
-rw-r--r--ujit_asm_tests.c54
4 files changed, 82 insertions, 47 deletions
diff --git a/iseq.c b/iseq.c
index 67af3371dd..03f322e514 100644
--- a/iseq.c
+++ b/iseq.c
@@ -3225,6 +3225,18 @@ rb_vm_encoded_insn_data_table_init(void)
head += sizeof(handmade_pop);
memcpy(head, ujit_post_call_bytes, sizeof(ujit_post_call_bytes));
// TODO this is small enough to fit in the page we allocated but that can change
+
+
+
+
+
+
+
+
+
+
+
+
}
int
diff --git a/ujit_asm.c b/ujit_asm.c
index d8d7756ac4..15b0dc5d05 100644
--- a/ujit_asm.c
+++ b/ujit_asm.c
@@ -32,6 +32,24 @@ const x86opnd_t R13 = { OPND_REG, 64, .reg = { REG_GP, 13 }};
const x86opnd_t R14 = { OPND_REG, 64, .reg = { REG_GP, 14 }};
const x86opnd_t R15 = { OPND_REG, 64, .reg = { REG_GP, 15 }};
+// 32-bit GP registers
+const x86opnd_t EAX = { OPND_REG, 32, .reg = { REG_GP, 0 }};
+const x86opnd_t ECX = { OPND_REG, 32, .reg = { REG_GP, 1 }};
+const x86opnd_t EDX = { OPND_REG, 32, .reg = { REG_GP, 2 }};
+const x86opnd_t EBX = { OPND_REG, 32, .reg = { REG_GP, 3 }};
+const x86opnd_t ESP = { OPND_REG, 32, .reg = { REG_GP, 4 }};
+const x86opnd_t EBP = { OPND_REG, 32, .reg = { REG_GP, 5 }};
+const x86opnd_t ESI = { OPND_REG, 32, .reg = { REG_GP, 6 }};
+const x86opnd_t EDI = { OPND_REG, 32, .reg = { REG_GP, 7 }};
+const x86opnd_t R8D = { OPND_REG, 32, .reg = { REG_GP, 8 }};
+const x86opnd_t R9D = { OPND_REG, 32, .reg = { REG_GP, 9 }};
+const x86opnd_t R10D = { OPND_REG, 32, .reg = { REG_GP, 10 }};
+const x86opnd_t R11D = { OPND_REG, 32, .reg = { REG_GP, 11 }};
+const x86opnd_t R12D = { OPND_REG, 32, .reg = { REG_GP, 12 }};
+const x86opnd_t R13D = { OPND_REG, 32, .reg = { REG_GP, 13 }};
+const x86opnd_t R14D = { OPND_REG, 32, .reg = { REG_GP, 14 }};
+const x86opnd_t R15D = { OPND_REG, 32, .reg = { REG_GP, 15 }};
+
// Compute the number of bits needed to encode a signed value
size_t sig_imm_size(int64_t imm)
{
@@ -874,3 +892,22 @@ void ret(codeblock_t* cb)
//cb.writeASM("ret");
cb_write_byte(cb, 0xC3);
}
+
+/// sub - Integer subtraction
+void sub(codeblock_t* cb, x86opnd_t opnd0, x86opnd_t opnd1)
+{
+ cb_write_rm_multi(
+ cb,
+ "sub",
+ 0x28, // opMemReg8
+ 0x29, // opMemRegPref
+ 0x2A, // opRegMem8
+ 0x2B, // opRegMemPref
+ 0x80, // opMemImm8
+ 0x83, // opMemImmSml
+ 0x81, // opMemImmLrg
+ 0x05, // opExtImm
+ opnd0,
+ opnd1
+ );
+}
diff --git a/ujit_asm.h b/ujit_asm.h
index 1f8ed35f8f..bc93b1e360 100644
--- a/ujit_asm.h
+++ b/ujit_asm.h
@@ -149,6 +149,24 @@ const x86opnd_t R13;
const x86opnd_t R14;
const x86opnd_t R15;
+// 32-bit GP registers
+const x86opnd_t EAX;
+const x86opnd_t ECX;
+const x86opnd_t EDX;
+const x86opnd_t EBX;
+const x86opnd_t EBP;
+const x86opnd_t ESP;
+const x86opnd_t ESI;
+const x86opnd_t EDI;
+const x86opnd_t R8D;
+const x86opnd_t R9D;
+const x86opnd_t R10D;
+const x86opnd_t R11D;
+const x86opnd_t R12D;
+const x86opnd_t R13D;
+const x86opnd_t R14D;
+const x86opnd_t R15D;
+
// Memory operand with base register and displacement/offset
x86opnd_t mem_opnd(size_t num_bits, x86opnd_t base_reg, int32_t disp);
@@ -170,16 +188,12 @@ void cb_write_epilogue(codeblock_t* cb);
void add(codeblock_t* cb, x86opnd_t opnd0, x86opnd_t opnd1);
void call(codeblock_t* cb, x86opnd_t opnd);
void jmp(codeblock_t* cb, x86opnd_t opnd);
+void lea(codeblock_t* cb, x86opnd_t dst, x86opnd_t src);
void mov(codeblock_t* cb, x86opnd_t dst, x86opnd_t src);
void nop(codeblock_t* cb, size_t length);
void push(codeblock_t* cb, x86opnd_t reg);
void pop(codeblock_t* cb, x86opnd_t reg);
void ret(codeblock_t* cb);
-
-
-
-
-
-
+void sub(codeblock_t* cb, x86opnd_t opnd0, x86opnd_t opnd1);
#endif
diff --git a/ujit_asm_tests.c b/ujit_asm_tests.c
index b705c7bfe7..72b5c829f5 100644
--- a/ujit_asm_tests.c
+++ b/ujit_asm_tests.c
@@ -70,30 +70,17 @@ void run_tests()
);
*/
cb_set_pos(cb, 0); add(cb, RAX, RBX); check_bytes(cb, "4801D8");
- //cb_set_pos(cb, 0); add(cb, ECX, EDX); check_bytes(cb, "01D1");
+ cb_set_pos(cb, 0); add(cb, ECX, EDX); check_bytes(cb, "01D1");
cb_set_pos(cb, 0); add(cb, RDX, R14); check_bytes(cb, "4C01F2");
cb_set_pos(cb, 0); add(cb, mem_opnd(64, RAX, 0), RDX); check_bytes(cb, "480110");
cb_set_pos(cb, 0); add(cb, RDX, mem_opnd(64, RAX, 0)); check_bytes(cb, "480310");
cb_set_pos(cb, 0); add(cb, RDX, mem_opnd(64, RAX, 8)); check_bytes(cb, "48035008");
cb_set_pos(cb, 0); add(cb, RDX, mem_opnd(64, RAX, 255)); check_bytes(cb, "480390FF000000");
cb_set_pos(cb, 0); add(cb, mem_opnd(64, RAX, 127), imm_opnd(255)); check_bytes(cb, "4881407FFF000000");
- /*
- test(
- delegate void (CodeBlock cb) { cb.add(X86Opnd(32, RAX), X86Opnd(EDX)); },
- "0110"
- );
- */
+ cb_set_pos(cb, 0); add(cb, mem_opnd(32, RAX, 0), EDX); check_bytes(cb, "0110");
cb_set_pos(cb, 0); add(cb, RSP, imm_opnd(8)); check_bytes(cb, "4883C408");
- /*
- test(
- delegate void (CodeBlock cb) { cb.add(X86Opnd(ECX), X86Opnd(8)); },
- "83C108"
- );
- test(
- delegate void (CodeBlock cb) { cb.add(X86Opnd(ECX), X86Opnd(255)); },
- "81C1FF000000"
- );
- */
+ cb_set_pos(cb, 0); add(cb, ECX, imm_opnd(8)); check_bytes(cb, "83C108");
+ cb_set_pos(cb, 0); add(cb, ECX, imm_opnd(255)); check_bytes(cb, "81C1FF000000");
// call
/*
@@ -121,34 +108,17 @@ void run_tests()
cb_set_pos(cb, 0); jmp(cb, R12); check_bytes(cb, "41FFE4");
// lea
- //cb_set_pos(cb, 0); mov(cb, EBX, mem_opnd(32, RSP, 4))); check_bytes(cb, "8D5C2404");
+ //cb_set_pos(cb, 0); lea(cb, EBX, mem_opnd(32, RSP, 4)); check_bytes(cb, "8D5C2404");
// mov
- /*
- test(
- delegate void (CodeBlock cb) { cb.mov(X86Opnd(EAX), X86Opnd(7)); },
- "B807000000"
- );
- test(
- delegate void (CodeBlock cb) { cb.mov(X86Opnd(EAX), X86Opnd(-3)); },
- "B8FDFFFFFF"
- );
- */
+ cb_set_pos(cb, 0); mov(cb, EAX, imm_opnd(7)); check_bytes(cb, "B807000000");
+ cb_set_pos(cb, 0); mov(cb, EAX, imm_opnd(-3)); check_bytes(cb, "B8FDFFFFFF");
cb_set_pos(cb, 0); mov(cb, R15, imm_opnd(3)); check_bytes(cb, "49BF0300000000000000");
+ cb_set_pos(cb, 0); mov(cb, EAX, EBX); check_bytes(cb, "89D8");
+ cb_set_pos(cb, 0); mov(cb, EAX, ECX); check_bytes(cb, "89C8");
+ cb_set_pos(cb, 0); mov(cb, EDX, mem_opnd(32, RBX, 128)); check_bytes(cb, "8B9380000000");
/*
test(
- delegate void (CodeBlock cb) { cb.mov(X86Opnd(EAX), X86Opnd(EBX)); },
- "89D8"
- );
- test(
- delegate void (CodeBlock cb) { cb.mov(X86Opnd(EAX), X86Opnd(ECX)); },
- "89C8"
- );
- test(
- delegate void (CodeBlock cb) { cb.mov(X86Opnd(EDX), X86Opnd(32, RBX, 128)); },
- "8B9380000000"
- );
- test(
delegate void (CodeBlock cb) { cb.mov(X86Opnd(AL), X86Opnd(8, RCX, 0, 1, RDX)); },
"8A0411"
);
@@ -185,7 +155,9 @@ void run_tests()
// ret
cb_set_pos(cb, 0); ret(cb); check_bytes(cb, "C3");
-
+ // sub
+ cb_set_pos(cb, 0); sub(cb, EAX, imm_opnd(1)); check_bytes(cb, "83E801");
+ cb_set_pos(cb, 0); sub(cb, RAX, imm_opnd(2)); check_bytes(cb, "4883E802");