aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/copyjit.c17
-rw-r--r--src/copyjit.h12
2 files changed, 29 insertions, 0 deletions
diff --git a/src/copyjit.c b/src/copyjit.c
index 393c8e1..0de85d3 100644
--- a/src/copyjit.c
+++ b/src/copyjit.c
@@ -471,6 +471,23 @@ void compile_start(ctx_t *ctx)
ctx->pc = ctx->buf;
}
+reloc_t compile_placeholder(ctx_t *ctx, compile_callback_t call)
+{
+ reloc_t r = {0};
+ r.addr = call(ctx, 0);
+
+ /* the immediate is the last sizeof(uintptr_t) bytes of the generated
+ * instruction
+ * (at least we assume, the user could've passed anything to our callback) */
+ r.imm = ((uintptr_t *)ctx->pc) - 1;
+ return r;
+}
+
+void compile_patch(reloc_t reloc, void *addr)
+{
+ *reloc.imm = (uintptr_t)addr;
+}
+
void compile_finish(ctx_t *ctx)
{
__builtin___clear_cache(ctx->buf, ctx->buf + ctx->size);
diff --git a/src/copyjit.h b/src/copyjit.h
index d752144..8170204 100644
--- a/src/copyjit.h
+++ b/src/copyjit.h
@@ -3,12 +3,21 @@
#ifndef HMMJIT_H
#define HMMJIT_H
+#include <stdint.h>
+
typedef struct {
char *pc;
char *buf;
size_t size;
} ctx_t;
+typedef struct {
+ void *addr;
+ uintptr_t *imm;
+} reloc_t;
+
+typedef void *(*compile_callback_t)(ctx_t *, unsigned long);
+
#include "../lib/op_decls.h"
#include "../lib/imm_decls.h"
@@ -30,6 +39,9 @@ void *compile_sly(ctx_t *ctx, unsigned long i);
/** @todo add in placeholders (for example for load immediate but we don't know
* what the immediate is yet) */
+reloc_t compile_placeholder(ctx_t *ctx, compile_callback_t call);
+void compile_patch(reloc_t reloc, void *addr);
+
void compile_start(ctx_t *ctx);
void compile_finish(ctx_t *ctx);
unsigned long run(ctx_t *ctx);