< prev index next > src/hotspot/cpu/x86/sharedRuntime_x86_64.cpp
Print this page
#include "c1/c1_Runtime1.hpp"
#endif
#ifdef COMPILER2
#include "opto/runtime.hpp"
#endif
+ #if INCLUDE_SHENANDOAHGC
+ #include "gc/shenandoah/shenandoahRuntime.hpp"
+ #endif
#if INCLUDE_JVMCI
#include "jvmci/jvmciJavaClasses.hpp"
#endif
#define __ masm->
rbp_off, rbpH_off, // copy of rbp we will restore
return_off, returnH_off, // slot for return address
reg_save_size // size in compiler stack slots
};
+ static void adjust_wide_vectors_support(bool& wide_vectors);
+
public:
static OopMap* save_live_registers(MacroAssembler* masm, int additional_frame_words, int* total_frame_words, bool save_wide_vectors);
static void restore_live_registers(MacroAssembler* masm, bool restore_wide_vectors = false);
// Offsets into the register save area
// During deoptimization only the result registers need to be restored,
// all the other values have already been extracted.
static void restore_result_registers(MacroAssembler* masm);
};
- OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_frame_words, int* total_frame_words, bool save_wide_vectors) {
- int off = 0;
- int num_xmm_regs = XMMRegister::available_xmm_registers();
+ // TODO: Should be upstreamed separately.
+ void RegisterSaver::adjust_wide_vectors_support(bool& wide_vectors) {
#if COMPILER2_OR_JVMCI
- if (save_wide_vectors && UseAVX == 0) {
- save_wide_vectors = false; // vectors larger than 16 byte long are supported only with AVX
+ if (wide_vectors && UseAVX == 0) {
+ wide_vectors = false; // vectors larger than 16 byte long are supported only with AVX
}
- assert(!save_wide_vectors || MaxVectorSize <= 64, "Only up to 64 byte long vectors are supported");
+ assert(!wide_vectors || MaxVectorSize <= 64, "Only up to 64 byte long vectors are supported");
#else
- save_wide_vectors = false; // vectors are generated only by C2 and JVMCI
+ wide_vectors = false; // vectors are generated only by C2 and JVMCI
#endif
+ }
+
+ OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_frame_words, int* total_frame_words, bool save_wide_vectors) {
+ int off = 0;
+ int num_xmm_regs = XMMRegister::available_xmm_registers();
+
+ adjust_wide_vectors_support(save_wide_vectors);
// Always make the frame size 16-byte aligned, both vector and non vector stacks are always allocated
int frame_size_in_bytes = align_up(reg_save_size*BytesPerInt, num_xmm_regs);
// OopMap frame size is in compiler stack slots (jint's) not bytes or words
int frame_size_in_slots = frame_size_in_bytes / BytesPerInt;
if (frame::arg_reg_save_area_bytes != 0) {
// Pop arg register save area
__ addptr(rsp, frame::arg_reg_save_area_bytes);
}
- #if COMPILER2_OR_JVMCI
- if (restore_wide_vectors) {
- assert(UseAVX > 0, "Vectors larger than 16 byte long are supported only with AVX");
- assert(MaxVectorSize <= 64, "Only up to 64 byte long vectors are supported");
- }
- #else
- assert(!restore_wide_vectors, "vectors are generated only by C2");
- #endif
+ adjust_wide_vectors_support(restore_wide_vectors);
__ vzeroupper();
// On EVEX enabled targets everything is handled in pop fpu state
if (restore_wide_vectors) {
false);
return stub;
}
#endif // INCLUDE_JFR
+
+ RuntimeStub* SharedRuntime::generate_shenandoah_stub(StubId stub_id) {
+ assert(UseShenandoahGC, "Only generate when Shenandoah is enabled");
+
+ const char* name = SharedRuntime::stub_name(stub_id);
+ address stub_addr = nullptr;
+ bool returns_obj = true;
+
+ switch (stub_id) {
+ case StubId::shared_shenandoah_keepalive_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::write_barrier_pre);
+ returns_obj = false;
+ break;
+ }
+ case StubId::shared_shenandoah_lrb_strong_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong);
+ break;
+ }
+ case StubId::shared_shenandoah_lrb_weak_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak);
+ break;
+ }
+ case StubId::shared_shenandoah_lrb_phantom_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_phantom);
+ break;
+ }
+ case StubId::shared_shenandoah_lrb_strong_narrow_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong_narrow);
+ break;
+ }
+ case StubId::shared_shenandoah_lrb_weak_narrow_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak_narrow);
+ break;
+ }
+ case StubId::shared_shenandoah_lrb_phantom_narrow_id: {
+ stub_addr = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_phantom_narrow);
+ break;
+ }
+ default:
+ ShouldNotReachHere();
+ }
+
+ CodeBuffer code(name, 2048, 64);
+ MacroAssembler* masm = new MacroAssembler(&code);
+ address start = __ pc();
+
+ int frame_size_in_words;
+ OopMap* map = RegisterSaver::save_live_registers(masm, 0, &frame_size_in_words, true);
+ address frame_complete_pc = __ pc();
+
+ address post_call_pc;
+
+ // Call the runtime. This is what MacroAssember::call_VM_leaf does,
+ // but we also want to have exact post-call PC for oop map location.
+ {
+ Label L_stack_aligned, L_end;
+
+ #ifdef _WIN64
+ // Windows always allocates space for it's register args
+ __ subptr(rsp, frame::arg_reg_save_area_bytes);
+ #endif
+
+ __ testptr(rsp, 15);
+ __ jccb(Assembler::zero, L_stack_aligned);
+ __ subptr(rsp, 8);
+ __ call(RuntimeAddress(stub_addr));
+ post_call_pc = __ pc();
+ __ addptr(rsp, 8);
+ __ jmpb(L_end);
+ __ bind(L_stack_aligned);
+ __ call(RuntimeAddress(stub_addr));
+ post_call_pc = __ pc();
+ __ bind(L_end);
+
+ #ifdef _WIN64
+ __ addptr(rsp, frame::arg_reg_save_area_bytes);
+ #endif
+ }
+
+ if (returns_obj) {
+ // RegisterSaver would clobber the call result when restoring.
+ // Carry the result out of this stub by overwriting saved register.
+ __ movptr(Address(rsp, RegisterSaver::rax_offset_in_bytes()), rax);
+ }
+
+ OopMapSet* oop_maps = new OopMapSet();
+ oop_maps->add_gc_map(post_call_pc - start, map);
+
+ RegisterSaver::restore_live_registers(masm, true);
+ __ ret(0);
+
+ return RuntimeStub::new_runtime_stub(name,
+ &code,
+ frame_complete_pc - start,
+ frame_size_in_words,
+ oop_maps,
+ true);
+ }
< prev index next >