Skip to content

Commit b18e569

Browse files
author
Maxime Chevalier-Boisvert
committed
Fixed bug with direct jump and block queueing
1 parent 46d5917 commit b18e569

File tree

4 files changed

+62
-14
lines changed

4 files changed

+62
-14
lines changed

bootstraptest/test_ujit.rb

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,21 @@ def alias_then_hash(klass, method_to_redefine)
2929
retval
3030
}
3131

32-
# test for GC safety. Don't invalidate dead iseqs.
32+
# Ruby-to-Ruby call and C call
33+
assert_normal_exit %q{
34+
def bar
35+
puts('hi!')
36+
end
37+
38+
def foo
39+
bar
40+
end
41+
42+
foo()
43+
foo()
44+
}
45+
46+
# Test for GC safety. Don't invalidate dead iseqs.
3347
assert_normal_exit %q{
3448
Class.new do
3549
def foo

ujit_codegen.c

Lines changed: 41 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
#include <assert.h>
21
#include "insns.inc"
32
#include "internal.h"
43
#include "vm_core.h"
@@ -35,7 +34,7 @@ jit_get_opcode(jitstate_t* jit)
3534

3635
// Get the index of the next instruction
3736
static uint32_t
38-
jit_next_idx(jitstate_t* jit)
37+
jit_next_insn_idx(jitstate_t* jit)
3938
{
4039
return jit->insn_idx + insn_len(jit_get_opcode(jit));
4140
}
@@ -140,6 +139,7 @@ ujit_gen_block(ctx_t* ctx, block_t* block)
140139
{
141140
RUBY_ASSERT(cb != NULL);
142141
RUBY_ASSERT(block != NULL);
142+
RUBY_ASSERT(!(block->blockid.idx == 0 && ctx->stack_size > 0));
143143

144144
const rb_iseq_t *iseq = block->blockid.iseq;
145145
uint32_t insn_idx = block->blockid.idx;
@@ -805,7 +805,7 @@ gen_branchif(jitstate_t* jit, ctx_t* ctx)
805805
test(cb, val_opnd, imm_opnd(~Qnil));
806806

807807
// Get the branch target instruction offsets
808-
uint32_t next_idx = jit_next_idx(jit);
808+
uint32_t next_idx = jit_next_insn_idx(jit);
809809
uint32_t jump_idx = next_idx + (uint32_t)jit_get_arg(jit, 0);
810810
blockid_t next_block = { jit->iseq, next_idx };
811811
blockid_t jump_block = { jit->iseq, jump_idx };
@@ -862,7 +862,7 @@ gen_branchunless(jitstate_t* jit, ctx_t* ctx)
862862
test(cb, val_opnd, imm_opnd(~Qnil));
863863

864864
// Get the branch target instruction offsets
865-
uint32_t next_idx = jit_next_idx(jit);
865+
uint32_t next_idx = jit_next_insn_idx(jit);
866866
uint32_t jump_idx = next_idx + (uint32_t)jit_get_arg(jit, 0);
867867
blockid_t next_block = { jit->iseq, next_idx };
868868
blockid_t jump_block = { jit->iseq, jump_idx };
@@ -884,7 +884,7 @@ static bool
884884
gen_jump(jitstate_t* jit, ctx_t* ctx)
885885
{
886886
// Get the branch target instruction offsets
887-
uint32_t jump_idx = jit_next_idx(jit) + (int32_t)jit_get_arg(jit, 0);
887+
uint32_t jump_idx = jit_next_insn_idx(jit) + (int32_t)jit_get_arg(jit, 0);
888888
blockid_t jump_block = { jit->iseq, jump_idx };
889889

890890
//
@@ -1103,7 +1103,7 @@ gen_opt_swb_cfunc(jitstate_t* jit, ctx_t* ctx, struct rb_call_data * cd, const r
11031103

11041104
// Jump (fall through) to the call continuation block
11051105
// We do this to end the current block after the call
1106-
blockid_t cont_block = { jit->iseq, jit_next_idx(jit) };
1106+
blockid_t cont_block = { jit->iseq, jit_next_insn_idx(jit) };
11071107
gen_direct_jump(
11081108
ctx,
11091109
cont_block
@@ -1150,8 +1150,7 @@ gen_opt_swb_iseq(jitstate_t* jit, ctx_t* ctx, struct rb_call_data * cd, const rb
11501150
mov(cb, REG0, recv);
11511151

11521152
// Callee method ID
1153-
//ID mid = vm_ci_mid(cd->ci);
1154-
//printf("JITting call to Ruby function \"%s\", argc: %d\n", rb_id2name(mid), argc);
1153+
//printf("JITting call to Ruby function \"%s\", argc: %d\n", rb_id2name(vm_ci_mid(cd->ci)), argc);
11551154
//print_str(cb, "");
11561155
//print_str(cb, "recv");
11571156
//print_ptr(cb, recv);
@@ -1242,12 +1241,44 @@ gen_opt_swb_iseq(jitstate_t* jit, ctx_t* ctx, struct rb_call_data * cd, const rb
12421241
mov(cb, REG0, const_ptr_opnd(start_pc));
12431242
mov(cb, member_opnd(REG1, rb_control_frame_t, pc), REG0);
12441243

1244+
1245+
1246+
12451247
//print_str(cb, "calling Ruby func:");
1246-
//print_str(cb, rb_id2name(mid));
1248+
//print_str(cb, rb_id2name(vm_ci_mid(cd->ci)));
1249+
1250+
12471251

12481252
// Write the post call bytes, exit to the interpreter
12491253
cb_write_post_call_bytes(cb);
12501254

1255+
1256+
1257+
/*
1258+
// Directly jump to the entry point of the callee
1259+
gen_direct_jump(
1260+
&DEFAULT_CTX,
1261+
(blockid_t){ iseq, 0 }
1262+
);
1263+
*/
1264+
1265+
1266+
1267+
1268+
1269+
1270+
1271+
// TODO: need to pop args in the caller ctx
1272+
1273+
// TODO: stub so we can return to JITted code
1274+
//blockid_t cont_block = { jit->iseq, jit_next_insn_idx(jit) };
1275+
1276+
1277+
1278+
1279+
1280+
1281+
12511282
return true;
12521283
}
12531284

@@ -1305,7 +1336,7 @@ gen_opt_send_without_block(jitstate_t* jit, ctx_t* ctx)
13051336

13061337
static bool
13071338
gen_leave(jitstate_t* jit, ctx_t* ctx)
1308-
{
1339+
{
13091340
// Only the return value should be on the stack
13101341
RUBY_ASSERT(ctx->stack_size == 1);
13111342

ujit_core.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,6 @@
1616
// Maximum number of branch instructions we can track
1717
#define MAX_BRANCHES 32768
1818

19-
// Default versioning context (no type information)
20-
const ctx_t DEFAULT_CTX = { { 0 }, 0 };
21-
2219
// Table of block versions indexed by (iseq, index) tuples
2320
st_table *version_tbl;
2421

@@ -271,6 +268,9 @@ block_t* gen_block_version(blockid_t blockid, const ctx_t* start_ctx)
271268
block->blockid = last_branch->targets[0];
272269
memcpy(&block->ctx, ctx, sizeof(ctx_t));
273270

271+
// Use the context from the branch
272+
*ctx = last_branch->target_ctxs[0];
273+
274274
// Generate code for the current block
275275
ujit_gen_block(ctx, block);
276276

ujit_core.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,9 @@
2020
// Maximum number of temp value types we keep track of
2121
#define MAX_TEMP_TYPES 8
2222

23+
// Default versioning context (no type information)
24+
#define DEFAULT_CTX ( (ctx_t){ { 0 }, 0 } )
25+
2326
/**
2427
Code generation context
2528
Contains information we can use to optimize code

0 commit comments

Comments
 (0)