diff --git a/src/hotspot/cpu/riscv/macroAssembler_riscv.cpp b/src/hotspot/cpu/riscv/macroAssembler_riscv.cpp index 0e6a9099265ce..d2edf2464c887 100644 --- a/src/hotspot/cpu/riscv/macroAssembler_riscv.cpp +++ b/src/hotspot/cpu/riscv/macroAssembler_riscv.cpp @@ -2495,6 +2495,51 @@ void MacroAssembler::encode_heap_oop(Register d, Register s) { } } +void MacroAssembler::encode_heap_oop_not_null(Register r) { +#ifdef ASSERT + if (CheckCompressedOops) { + Label ok; + bnez(r, ok); + stop("null oop passed to encode_heap_oop_not_null"); + bind(ok); + } +#endif + verify_oop_msg(r, "broken oop in encode_heap_oop_not_null"); + if (CompressedOops::base() != nullptr) { + sub(r, r, xheapbase); + } + if (CompressedOops::shift() != 0) { + assert(LogMinObjAlignmentInBytes == CompressedOops::shift(), "decode alg wrong"); + srli(r, r, LogMinObjAlignmentInBytes); + } +} + +void MacroAssembler::encode_heap_oop_not_null(Register dst, Register src) { +#ifdef ASSERT + if (CheckCompressedOops) { + Label ok; + bnez(src, ok); + stop("null oop passed to encode_heap_oop_not_null2"); + bind(ok); + } +#endif + verify_oop_msg(src, "broken oop in encode_heap_oop_not_null2"); + + Register data = src; + if (CompressedOops::base() != nullptr) { + sub(dst, src, xheapbase); + data = dst; + } + if (CompressedOops::shift() != 0) { + assert(LogMinObjAlignmentInBytes == CompressedOops::shift(), "decode alg wrong"); + srli(dst, data, LogMinObjAlignmentInBytes); + data = dst; + } + if (data == src) { + mv(dst, src); + } +} + void MacroAssembler::load_klass(Register dst, Register src, Register tmp) { assert_different_registers(dst, tmp); assert_different_registers(src, tmp); diff --git a/src/hotspot/cpu/riscv/macroAssembler_riscv.hpp b/src/hotspot/cpu/riscv/macroAssembler_riscv.hpp index 4373ebada146a..0ed15a0fc5202 100644 --- a/src/hotspot/cpu/riscv/macroAssembler_riscv.hpp +++ b/src/hotspot/cpu/riscv/macroAssembler_riscv.hpp @@ -206,6 +206,8 @@ class MacroAssembler: public Assembler { void decode_heap_oop_not_null(Register dst, Register src); void decode_heap_oop(Register d, Register s); void decode_heap_oop(Register r) { decode_heap_oop(r, r); } + void encode_heap_oop_not_null(Register r); + void encode_heap_oop_not_null(Register dst, Register src); void encode_heap_oop(Register d, Register s); void encode_heap_oop(Register r) { encode_heap_oop(r, r); }; void load_heap_oop(Register dst, Address src, Register tmp1, diff --git a/src/hotspot/cpu/riscv/riscv.ad b/src/hotspot/cpu/riscv/riscv.ad index 4ed449032d6e9..06e1d067d000a 100644 --- a/src/hotspot/cpu/riscv/riscv.ad +++ b/src/hotspot/cpu/riscv/riscv.ad @@ -8404,6 +8404,7 @@ instruct round_float_reg(iRegINoSp dst, fRegF src, fRegF ftmp) %{ // Convert oop pointer into compressed form instruct encodeHeapOop(iRegNNoSp dst, iRegP src) %{ + predicate(n->bottom_type()->make_ptr()->ptr() != TypePtr::NotNull); match(Set dst (EncodeP src)); ins_cost(ALU_COST); format %{ "encode_heap_oop $dst, $src\t#@encodeHeapOop" %} @@ -8415,6 +8416,17 @@ instruct encodeHeapOop(iRegNNoSp dst, iRegP src) %{ ins_pipe(pipe_class_default); %} +instruct encodeHeapOop_not_null(iRegNNoSp dst, iRegP src) { + predicate(n->bottom_type()->make_ptr()->ptr() == TypePtr::NotNull); + match(Set dst (EncodeP src)); + ins_cost(ALU_COST); + format %{ "encode_heap_oop_not_null $dst, $src\t#@encodeHeapOop_not_null" %} + ins_encode %{ + __ encode_heap_oop_not_null($dst$$Register, $src$$Register); + %} + ins_pipe(pipe_class_default); +} + instruct decodeHeapOop(iRegPNoSp dst, iRegN src) %{ predicate(n->bottom_type()->is_ptr()->ptr() != TypePtr::NotNull && n->bottom_type()->is_ptr()->ptr() != TypePtr::Constant);