|
4 | 4 |
|
5 | 5 | #define __ masm->
|
6 | 6 |
|
| 7 | +// extern void object_reference_write_slow_call(void* obj, void* dst, uint64_t val); |
| 8 | + |
| 9 | +// void write_post(char* SIDE_METADATA_BASE_ADDRESS, void* obj, uint64_t val) { |
| 10 | +// char tmp2 = *(SIDE_METADATA_BASE_ADDRESS + ((uint64_t)obj >> 6)); |
| 11 | +// char tmp3 = ((uint64_t)obj >> 3) & 7; |
| 12 | +// tmp2 = tmp2 >> tmp3; |
| 13 | +// if ((tmp2 & 1) == 1) { |
| 14 | +// object_reference_write_slow_call(obj, 0, val); |
| 15 | +// } |
| 16 | +// } |
| 17 | + |
| 18 | +// write_post(char*, void*, unsigned long): |
| 19 | +// srli a5,a1,6 |
| 20 | +// add a0,a0,a5 |
| 21 | +// lbu a5,0(a0) |
| 22 | +// srli a3,a1,3 |
| 23 | +// andi a3,a3,7 |
| 24 | +// sraw a5,a5,a3 |
| 25 | +// andi a5,a5,1 |
| 26 | +// mv a4,a1 |
| 27 | +// bne a5,zero,.L4 |
| 28 | +// ret |
| 29 | +// .L4: |
| 30 | +// li a1,0 |
| 31 | +// mv a0,a4 |
| 32 | +// tail _Z32object_reference_write_slow_callPvS_m |
7 | 33 | void MMTkObjectBarrierSetAssembler::object_reference_write_post(MacroAssembler* masm, DecoratorSet decorators, Address dst, Register val, Register tmp1, Register tmp2) const {
|
8 |
| - assert(false, "Not implemented"); |
| 34 | + // tmp1 and tmp2 is from MacroAssembler::access_store_at |
| 35 | + // See tmplateTable_riscv, we don't actually get any temporary register. |
| 36 | + // printf("object_reference_write_post\n"); |
| 37 | + if (can_remove_barrier(decorators, val, /* skip_const_null */ true)) return; |
| 38 | +#if MMTK_ENABLE_BARRIER_FASTPATH |
| 39 | + Label done; |
| 40 | + |
| 41 | + Register obj = dst.base(); |
| 42 | + assert(obj->is_valid(), "dst must be an offset from a base register"); |
| 43 | + assert_different_registers(obj, t0, t1); |
| 44 | + assert_different_registers(val, t0, t1); |
| 45 | + |
| 46 | + // t0 = load-byte (SIDE_METADATA_BASE_ADDRESS + (obj >> 6)); |
| 47 | + __ mv(t0, obj); |
| 48 | + __ srli(t0, t0, 6); // t0 = obj >> 6; |
| 49 | + __ li(t1, SIDE_METADATA_BASE_ADDRESS); |
| 50 | + __ add(t0, t0, t1); // t0 = SIDE_METADATA_BASE_ADDRESS + (obj >> 6); |
| 51 | + __ lbu(t0, Address(t0, 0)); |
| 52 | + // t1 = (obj >> 3) & 7 |
| 53 | + __ mv(t1, obj); |
| 54 | + __ srli(t1, t1, 3); |
| 55 | + __ andi(t1, t1, 7); |
| 56 | + // t0 = t0 >> t1 |
| 57 | + __ sraw(t0, t0, t1); |
| 58 | + // if ((t0 & 1) == 1) fall through to slowpath; |
| 59 | + __ andi(t0, t0, 1); |
| 60 | + __ bnez(t0, done); // (t0 & 1) == 1 is equivalent to (t0 & 1) != 0 |
| 61 | + // setup calling convention |
| 62 | + __ mv(c_rarg0, obj); |
| 63 | + __ la(c_rarg1, dst); |
| 64 | + __ mv(c_rarg2, val == noreg ? zr : val); |
| 65 | + __ call_VM_leaf_base(FN_ADDR(MMTkBarrierSetRuntime::object_reference_write_slow_call), 3); |
| 66 | + |
| 67 | + __ bind(done); |
| 68 | +#else |
| 69 | + __ mv(c_rarg0, obj); |
| 70 | + __ la(c_rarg1, dst); |
| 71 | + __ mv(c_rarg2, val == noreg ? zr : val); |
| 72 | + __ call_VM_leaf_base(FN_ADDR(MMTkBarrierSetRuntime::object_reference_write_post_call), 3); |
| 73 | +#endif |
9 | 74 | }
|
10 | 75 |
|
11 | 76 | void MMTkObjectBarrierSetAssembler::arraycopy_epilogue(MacroAssembler* masm, DecoratorSet decorators, bool is_oop,
|
|
0 commit comments