diff --git a/src/hotspot/share/c1/c1_IR.hpp b/src/hotspot/share/c1/c1_IR.hpp index c808d063cec..3eddaa40dbc 100644 --- a/src/hotspot/share/c1/c1_IR.hpp +++ b/src/hotspot/share/c1/c1_IR.hpp @@ -245,18 +245,18 @@ class IRScopeDebugInfo: public CompilationResourceObj { DebugToken* monvals = recorder->create_monitor_values(monitors()); // reexecute allowed only for the topmost frame bool reexecute = topmost ? should_reexecute() : false; - bool return_oop = false; // This flag will be ignored since it used only for C2 with escape analysis. - bool return_vt = false; + bool return_oop = false; + bool return_scalarized = false; if (maybe_return_as_fields) { return_oop = true; - return_vt = true; + return_scalarized = true; } bool rethrow_exception = false; bool is_opt_native = false; bool has_ea_local_in_scope = false; bool arg_escape = false; recorder->describe_scope(pc_offset, methodHandle(), scope()->method(), bci(), - reexecute, rethrow_exception, is_method_handle_invoke, is_opt_native, return_oop, return_vt, + reexecute, rethrow_exception, is_method_handle_invoke, is_opt_native, return_oop, return_scalarized, has_ea_local_in_scope, arg_escape, locvals, expvals, monvals); } }; diff --git a/src/hotspot/share/c1/c1_LIR.cpp b/src/hotspot/share/c1/c1_LIR.cpp index 58ae140bd75..0b28483510e 100644 --- a/src/hotspot/share/c1/c1_LIR.cpp +++ b/src/hotspot/share/c1/c1_LIR.cpp @@ -1074,38 +1074,28 @@ void LIR_OpJavaCall::emit_code(LIR_Assembler* masm) { } bool LIR_OpJavaCall::maybe_return_as_fields(ciInlineKlass** vk_ret) const { - if (InlineTypeReturnedAsFields) { - if (method()->signature()->maybe_returns_inline_type()) { - ciType* return_type = method()->return_type(); - if (return_type->is_inlinetype()) { - ciInlineKlass* vk = return_type->as_inline_klass(); - if (vk->can_be_returned_as_fields()) { - if (vk_ret != NULL) { - *vk_ret = vk; - } - return true; - } - } else { - assert(return_type->is_instance_klass() && !return_type->as_instance_klass()->is_loaded(), "must be"); - if (vk_ret != NULL) { - *vk_ret = NULL; - } - return true; - } - } else if (is_method_handle_invoke()) { - BasicType bt = method()->return_type()->basic_type(); - if (bt == T_OBJECT || bt == T_INLINE_TYPE) { - // An inline type might be returned from the call but we don't know its - // type. Either we get a buffered inline type (and nothing needs to be done) - // or one of the inlines being returned is the klass of the inline type - // (RAX on x64, with LSB set to 1) and we need to allocate an inline - // type instance of that type and initialize it with other values being - // returned (in other registers). + if (InlineTypeReturnedAsFields && + (method()->signature()->returns_inline_type() || + method()->is_method_handle_intrinsic())) { + ciType* return_type = method()->return_type(); + if (return_type->is_inlinetype()) { + ciInlineKlass* vk = return_type->as_inline_klass(); + if (vk->can_be_returned_as_fields()) { if (vk_ret != NULL) { - *vk_ret = NULL; + *vk_ret = vk; } return true; } + } else if (return_type->is_instance_klass()) { + // An inline type might be returned from the call but we don't know its + // type. Either we get a buffered inline type (and nothing needs to be done) + // or one of the inlines being returned is the klass of the inline type + // (RAX on x64, with LSB set to 1) and we need to allocate an inline + // type instance of that type and initialize it with other values being + // returned (in other registers). + assert(!return_type->as_instance_klass()->is_loaded() || + method()->is_method_handle_intrinsic(), "unexpected return type"); + return true; } } return false; diff --git a/src/hotspot/share/c1/c1_LIRAssembler.cpp b/src/hotspot/share/c1/c1_LIRAssembler.cpp index 8ff2a02a1a1..c1ec43e2abb 100644 --- a/src/hotspot/share/c1/c1_LIRAssembler.cpp +++ b/src/hotspot/share/c1/c1_LIRAssembler.cpp @@ -331,7 +331,6 @@ void LIR_Assembler::check_no_unbound_labels() { //----------------------------------debug info-------------------------------- - void LIR_Assembler::add_debug_info_for_branch(CodeEmitInfo* info) { int pc_offset = code_offset(); flush_debug_info(pc_offset); @@ -341,7 +340,6 @@ void LIR_Assembler::add_debug_info_for_branch(CodeEmitInfo* info) { } } - void LIR_Assembler::add_call_info(int pc_offset, CodeEmitInfo* cinfo, bool maybe_return_as_fields) { flush_debug_info(pc_offset); cinfo->record_debug_info(compilation()->debug_info_recorder(), pc_offset, maybe_return_as_fields); @@ -487,7 +485,7 @@ void LIR_Assembler::emit_call(LIR_OpJavaCall* op) { compilation()->set_has_method_handle_invokes(true); } - ciInlineKlass* vk; + ciInlineKlass* vk = NULL; if (op->maybe_return_as_fields(&vk)) { int offset = store_inline_type_fields_to_buf(vk); add_call_info(offset, op->info(), true); diff --git a/src/hotspot/share/ci/ciSignature.cpp b/src/hotspot/share/ci/ciSignature.cpp index e0172516afb..d92446e49ca 100644 --- a/src/hotspot/share/ci/ciSignature.cpp +++ b/src/hotspot/share/ci/ciSignature.cpp @@ -71,19 +71,9 @@ ciSignature::ciSignature(ciKlass* accessing_klass, const constantPoolHandle& cpo } // ------------------------------------------------------------------ -// ciSignature::maybe_returns_inline_type -// -// True if we statically know that the return value is never null, or -// if the return type has a Q signature but is not yet loaded, in which case -// it could be a never-null type. -bool ciSignature::maybe_returns_inline_type() const { - ciType* ret_type = return_type(); - if (ret_type->is_inlinetype()) { - return true; - } else if (ret_type->is_instance_klass() && !ret_type->as_instance_klass()->is_loaded()) { - GUARDED_VM_ENTRY(if (get_symbol()->is_Q_method_signature()) { return true; }) - } - return false; +// ciSignature::returns_inline_type +bool ciSignature::returns_inline_type() const { + GUARDED_VM_ENTRY(return get_symbol()->is_Q_method_signature();) } // ------------------------------------------------------------------ diff --git a/src/hotspot/share/ci/ciSignature.hpp b/src/hotspot/share/ci/ciSignature.hpp index c37bd3400f2..8faf9f5362b 100644 --- a/src/hotspot/share/ci/ciSignature.hpp +++ b/src/hotspot/share/ci/ciSignature.hpp @@ -57,7 +57,7 @@ class ciSignature : public ResourceObj { ciType* return_type() const { return _return_type; } ciType* type_at(int index) const { return _types.at(index); } - bool maybe_returns_inline_type() const; + bool returns_inline_type() const; int size() const { return _size; } int count() const { return _types.length(); } diff --git a/src/hotspot/share/code/debugInfoRec.cpp b/src/hotspot/share/code/debugInfoRec.cpp index 476825591cf..1aef6d96aee 100644 --- a/src/hotspot/share/code/debugInfoRec.cpp +++ b/src/hotspot/share/code/debugInfoRec.cpp @@ -289,7 +289,7 @@ void DebugInformationRecorder::describe_scope(int pc_offset, bool is_method_handle_invoke, bool is_optimized_linkToNative, bool return_oop, - bool return_vt, + bool return_scalarized, bool has_ea_local_in_scope, bool arg_escape, DebugToken* locals, @@ -309,7 +309,7 @@ void DebugInformationRecorder::describe_scope(int pc_offset, last_pd->set_is_method_handle_invoke(is_method_handle_invoke); last_pd->set_is_optimized_linkToNative(is_optimized_linkToNative); last_pd->set_return_oop(return_oop); - last_pd->set_return_vt(return_vt); + last_pd->set_return_scalarized(return_scalarized); last_pd->set_has_ea_local_in_scope(has_ea_local_in_scope); last_pd->set_arg_escape(arg_escape); diff --git a/src/hotspot/share/code/debugInfoRec.hpp b/src/hotspot/share/code/debugInfoRec.hpp index 3a413247f04..174844f3454 100644 --- a/src/hotspot/share/code/debugInfoRec.hpp +++ b/src/hotspot/share/code/debugInfoRec.hpp @@ -106,7 +106,7 @@ class DebugInformationRecorder: public ResourceObj { bool is_method_handle_invoke = false, bool is_optimized_linkToNative = false, bool return_oop = false, - bool return_vt = false, + bool return_scalarized = false, bool has_ea_local_in_scope = false, bool arg_escape = false, DebugToken* locals = NULL, diff --git a/src/hotspot/share/code/nmethod.cpp b/src/hotspot/share/code/nmethod.cpp index 68aba3a053c..1d4353a6d47 100644 --- a/src/hotspot/share/code/nmethod.cpp +++ b/src/hotspot/share/code/nmethod.cpp @@ -3382,7 +3382,7 @@ void nmethod::print_code_comment_on(outputStream* st, int column, address begin, break; } } - st->print(" {reexecute=%d rethrow=%d return_oop=%d return_vt=%d}", sd->should_reexecute(), sd->rethrow_exception(), sd->return_oop(), sd->return_vt()); + st->print(" {reexecute=%d rethrow=%d return_oop=%d return_scalarized=%d}", sd->should_reexecute(), sd->rethrow_exception(), sd->return_oop(), sd->return_scalarized()); } // Print all scopes diff --git a/src/hotspot/share/code/pcDesc.hpp b/src/hotspot/share/code/pcDesc.hpp index bc0682dfefc..c7d9f4415e3 100644 --- a/src/hotspot/share/code/pcDesc.hpp +++ b/src/hotspot/share/code/pcDesc.hpp @@ -46,7 +46,7 @@ class PcDesc { PCDESC_has_ea_local_in_scope = 1 << 4, PCDESC_arg_escape = 1 << 5, PCDESC_is_optimized_linkToNative = 1 << 6, - PCDESC_return_vt = 1 << 7 + PCDESC_return_scalarized = 1 << 7 }; int _flags; @@ -96,8 +96,8 @@ class PcDesc { bool return_oop() const { return (_flags & PCDESC_return_oop) != 0; } void set_return_oop(bool z) { set_flag(PCDESC_return_oop, z); } - bool return_vt() const { return (_flags & PCDESC_return_vt) != 0; } - void set_return_vt(bool z) { set_flag(PCDESC_return_vt, z); } + bool return_scalarized() const { return (_flags & PCDESC_return_scalarized) != 0; } + void set_return_scalarized(bool z) { set_flag(PCDESC_return_scalarized, z); } // Indicates if there are objects in scope that, based on escape analysis, are local to the // compiled method or local to the current thread, i.e. NoEscape or ArgEscape bool has_ea_local_in_scope() const { return (_flags & PCDESC_has_ea_local_in_scope) != 0; } diff --git a/src/hotspot/share/code/scopeDesc.cpp b/src/hotspot/share/code/scopeDesc.cpp index baa64d3b7fa..f9544da884f 100644 --- a/src/hotspot/share/code/scopeDesc.cpp +++ b/src/hotspot/share/code/scopeDesc.cpp @@ -40,7 +40,7 @@ ScopeDesc::ScopeDesc(const CompiledMethod* code, PcDesc* pd, bool ignore_objects _reexecute = pd->should_reexecute(); _rethrow_exception = pd->rethrow_exception(); _return_oop = pd->return_oop(); - _return_vt = pd->return_vt(); + _return_scalarized = pd->return_scalarized(); _has_ea_local_in_scope = ignore_objects ? false : pd->has_ea_local_in_scope(); _arg_escape = ignore_objects ? false : pd->arg_escape(); decode_body(); @@ -54,7 +54,7 @@ void ScopeDesc::initialize(const ScopeDesc* parent, int decode_offset) { _reexecute = false; //reexecute only applies to the first scope _rethrow_exception = false; _return_oop = false; - _return_vt = false; + _return_scalarized = false; _has_ea_local_in_scope = parent->has_ea_local_in_scope(); _arg_escape = false; decode_body(); diff --git a/src/hotspot/share/code/scopeDesc.hpp b/src/hotspot/share/code/scopeDesc.hpp index f41c3b47767..934930048a2 100644 --- a/src/hotspot/share/code/scopeDesc.hpp +++ b/src/hotspot/share/code/scopeDesc.hpp @@ -75,7 +75,7 @@ class ScopeDesc : public ResourceObj { bool should_reexecute() const { return _reexecute; } bool rethrow_exception() const { return _rethrow_exception; } bool return_oop() const { return _return_oop; } - bool return_vt() const { return _return_vt; } + bool return_scalarized() const { return _return_scalarized; } // Returns true if one or more NoEscape or ArgEscape objects exist in // any of the scopes at compiled pc. bool has_ea_local_in_scope() const { return _has_ea_local_in_scope; } @@ -109,7 +109,7 @@ class ScopeDesc : public ResourceObj { bool _reexecute; bool _rethrow_exception; bool _return_oop; - bool _return_vt; + bool _return_scalarized; bool _has_ea_local_in_scope; // One or more NoEscape or ArgEscape objects exist in // any of the scopes at compiled pc. bool _arg_escape; // Compiled Java call in youngest scope passes ArgEscape diff --git a/src/hotspot/share/opto/inlinetypenode.cpp b/src/hotspot/share/opto/inlinetypenode.cpp index 4ec1a7c92f3..7f3dab68cd4 100644 --- a/src/hotspot/share/opto/inlinetypenode.cpp +++ b/src/hotspot/share/opto/inlinetypenode.cpp @@ -957,7 +957,9 @@ Node* InlineTypePtrNode::Ideal(PhaseGVN* phase, bool can_reshape) { } } if (useless) { - phase->is_IterGVN()->replace_node(this, get_oop()); + PhaseIterGVN* igvn = phase->is_IterGVN(); + igvn->_worklist.push(this); + igvn->replace_in_uses(this, get_oop()); return NULL; } } diff --git a/src/hotspot/share/opto/machnode.cpp b/src/hotspot/share/opto/machnode.cpp index 81ed0fe231e..f1ea2cfc594 100644 --- a/src/hotspot/share/opto/machnode.cpp +++ b/src/hotspot/share/opto/machnode.cpp @@ -725,7 +725,7 @@ bool MachCallNode::returns_pointer() const { r->field_at(TypeFunc::Parms)->isa_ptr()); } -bool MachCallNode::returns_vt() const { +bool MachCallNode::returns_scalarized() const { return tf()->returns_inline_type_as_fields(); } diff --git a/src/hotspot/share/opto/machnode.hpp b/src/hotspot/share/opto/machnode.hpp index 5a04dea88ab..8b3ce6d3785 100644 --- a/src/hotspot/share/opto/machnode.hpp +++ b/src/hotspot/share/opto/machnode.hpp @@ -945,7 +945,7 @@ class MachCallNode : public MachSafePointNode { // Similar to cousin class CallNode::returns_pointer bool returns_pointer() const; - bool returns_vt() const; + bool returns_scalarized() const; bool guaranteed_safepoint() const { return _guaranteed_safepoint; } diff --git a/src/hotspot/share/opto/output.cpp b/src/hotspot/share/opto/output.cpp index 0beb984e2d7..26d2d330c68 100644 --- a/src/hotspot/share/opto/output.cpp +++ b/src/hotspot/share/opto/output.cpp @@ -1049,7 +1049,7 @@ void PhaseOutput::Process_OopMap_Node(MachNode *mach, int current_offset) { bool is_method_handle_invoke = false; bool is_opt_native = false; bool return_oop = false; - bool return_vt = false; + bool return_scalarized = false; bool has_ea_local_in_scope = sfn->_has_ea_local_in_scope; bool arg_escape = false; @@ -1072,11 +1072,11 @@ void PhaseOutput::Process_OopMap_Node(MachNode *mach, int current_offset) { } // Check if a call returns an object. - if (mcall->returns_pointer() || mcall->returns_vt()) { + if (mcall->returns_pointer() || mcall->returns_scalarized()) { return_oop = true; } - if (mcall->returns_vt()) { - return_vt = true; + if (mcall->returns_scalarized()) { + return_scalarized = true; } safepoint_pc_offset += mcall->ret_addr_offset(); C->debug_info()->add_safepoint(safepoint_pc_offset, mcall->_oop_map); @@ -1202,7 +1202,7 @@ void PhaseOutput::Process_OopMap_Node(MachNode *mach, int current_offset) { is_method_handle_invoke, is_opt_native, return_oop, - return_vt, + return_scalarized, has_ea_local_in_scope, arg_escape, locvals, diff --git a/src/hotspot/share/runtime/deoptimization.cpp b/src/hotspot/share/runtime/deoptimization.cpp index 0a10c100ec6..b793bbcfdcb 100644 --- a/src/hotspot/share/runtime/deoptimization.cpp +++ b/src/hotspot/share/runtime/deoptimization.cpp @@ -208,7 +208,7 @@ static bool eliminate_allocations(JavaThread* thread, int exec_mode, CompiledMet // of all oop return values. GrowableArray return_oops; InlineKlass* vk = NULL; - if (save_oop_result && scope->return_vt()) { + if (save_oop_result && scope->return_scalarized()) { vk = InlineKlass::returned_inline_klass(map); if (vk != NULL) { vk->save_oop_fields(map, return_oops);