diff options
| author | Maxime Chevalier-Boisvert <maxime.chevalierboisvert@shopify.com> | 2020-09-10 17:20:46 -0400 |
|---|---|---|
| committer | Alan Wu <XrXr@users.noreply.github.com> | 2021-10-20 18:19:23 -0400 |
| commit | 1c8fb90f6bde0c630f5dc532dfe198218bc9f910 (patch) | |
| tree | b6e0cbb41043040d397b7eca230c7a100fb9cd88 | |
| parent | 566d4abee5e8e59ce6e080f28a25b7c3431c5b3b (diff) | |
Add new files, ujit_compile.c, ujit_compile.h
| -rw-r--r-- | common.mk | 1 | ||||
| -rw-r--r-- | compile.c | 15 | ||||
| -rw-r--r-- | ujit_compile.c | 63 | ||||
| -rw-r--r-- | ujit_compile.h | 14 |
4 files changed, 85 insertions, 8 deletions
@@ -151,6 +151,7 @@ COMMONOBJS = array.$(OBJEXT) \ vm_sync.$(OBJEXT) \ vm_trace.$(OBJEXT) \ ujit_asm.$(OBJEXT) \ + ujit_compile.$(OBJEXT) \ $(COROUTINE_OBJ) \ $(DTRACE_OBJ) \ $(BUILTIN_ENCOBJS) \ @@ -43,6 +43,7 @@ #include "builtin.h" #include "insns.inc" #include "insns_info.inc" +#include "ujit_compile.h" #undef RUBY_UNTYPED_DATA_WARNING #define RUBY_UNTYPED_DATA_WARNING 0 @@ -856,8 +857,6 @@ rb_iseq_compile_node(rb_iseq_t *iseq, const NODE *node) return iseq_setup(iseq, ret); } -extern uint8_t *native_pop_code; // TODO global hack - static int rb_iseq_translate_threaded_code(rb_iseq_t *iseq) { @@ -870,17 +869,17 @@ rb_iseq_translate_threaded_code(rb_iseq_t *iseq) { int insn = (int)iseq->body->iseq_encoded[i]; int len = insn_len(insn); - encoded[i] = (VALUE)table[insn]; - - if (insn == BIN(pop)) - encoded[i] = (VALUE)native_pop_code; - const char* name = insn_name(insn); - printf("%s\n", name); + uint8_t* native_code_ptr = ujit_compile_insn(iseq, i); + if (native_code_ptr) + encoded[i] = (VALUE)native_code_ptr; + else + encoded[i] = (VALUE)table[insn]; i += len; } + FL_SET((VALUE)iseq, ISEQ_TRANSLATED); #endif return COMPILE_OK; diff --git a/ujit_compile.c b/ujit_compile.c new file mode 100644 index 0000000000..9ed2cc7727 --- /dev/null +++ b/ujit_compile.c @@ -0,0 +1,63 @@ +#include <assert.h> +#include "insns.inc" +#include "internal.h" +#include "vm_core.h" +#include "vm_callinfo.h" +#include "builtin.h" +#include "insns_info.inc" +#include "ujit_compile.h" +#include "ujit_asm.h" + +// NOTE: do we have to deal with multiple Ruby processes/threads compiling +// functions with the new Ractor in Ruby 3.0? If so, we need to think about +// a strategy for handling that. What does Ruby currently do for its own +// iseq translation? +static codeblock_t block; +static codeblock_t* cb = NULL; + +extern uint8_t* native_pop_code; // FIXME global hack + +// Generate a chunk of machinecode for one individual bytecode instruction +// Eventually, this will handle multiple instructions in a sequence +uint8_t* ujit_compile_insn(rb_iseq_t *iseq, size_t insn_idx) +{ + // Allocate the code block if not previously allocated + if (!cb) + { + // 4MB ought to be enough for anybody + cb = █ + cb_init(cb, 4000000); + } + + int insn = (int)iseq->body->iseq_encoded[insn_idx]; + + //const char* name = insn_name(insn); + //printf("%s\n", name); + + if (insn == BIN(pop)) + { + //printf("COMPILING %ld\n", cb->write_pos); + + return native_pop_code; + + /* + // Get a pointer to the current write position in the code block + uint8_t* code_ptr = &cb->mem_block[cb->write_pos]; + + // Write the pre call bytes + cb_write_prologue(cb); + + sub(cb, mem_opnd(64, RDI, 8), imm_opnd(8)); // decrement SP + add(cb, RSI, imm_opnd(8)); // increment PC + mov(cb, mem_opnd(64, RDI, 0), RSI); // write new PC to EC object, not necessary for pop bytecode? + mov(cb, RAX, RSI); // return new PC + + // Write the post call bytes + cb_write_epilogue(cb); + + return code_ptr; + */ + } + + return 0; +} diff --git a/ujit_compile.h b/ujit_compile.h new file mode 100644 index 0000000000..4f00c4cb44 --- /dev/null +++ b/ujit_compile.h @@ -0,0 +1,14 @@ +#ifndef UJIT_COMPILE_H +#define UJIT_COMPILE_H 1 + +#include "stddef.h" +#include "stdint.h" + +#ifndef rb_iseq_t +typedef struct rb_iseq_struct rb_iseq_t; +#define rb_iseq_t rb_iseq_t +#endif + +uint8_t* ujit_compile_insn(rb_iseq_t* iseq, size_t insn_idx); + +#endif |
