diff -r a3c63a9dfb2c -r 86b95fc6ca32 src/hotspot/share/opto/castnode.cpp --- a/src/hotspot/share/opto/castnode.cpp Thu Sep 05 12:39:48 2019 +0200 +++ b/src/hotspot/share/opto/castnode.cpp Thu Sep 05 13:56:17 2019 +0200 @@ -63,6 +63,14 @@ if (rt->empty()) assert(ft == Type::TOP, "special case #2"); break; } + case Op_CastLL: + { + const Type* t1 = phase->type(in(1)); + if (t1 == Type::TOP) assert(ft == Type::TOP, "special case #1"); + const Type* rt = t1->join_speculative(_type); + if (rt->empty()) assert(ft == Type::TOP, "special case #2"); + break; + } case Op_CastPP: if (phase->type(in(1)) == TypePtr::NULL_PTR && _type->isa_ptr() && _type->is_ptr()->_ptr == TypePtr::NotNull) @@ -96,6 +104,11 @@ cast->set_req(0, c); return cast; } + case Op_CastLL: { + Node* cast = new CastLLNode(n, t, carry_dependency); + cast->set_req(0, c); + return cast; + } case Op_CastPP: { Node* cast = new CastPPNode(n, t, carry_dependency); cast->set_req(0, c); @@ -279,6 +292,45 @@ } #endif +Node* CastLLNode::Ideal(PhaseGVN* phase, bool can_reshape) { + Node* progress = ConstraintCastNode::Ideal(phase, can_reshape); + if (progress != NULL) { + return progress; + } + + // Same as in CastIINode::Ideal but for TypeLong instead of TypeInt + if (can_reshape && !phase->C->major_progress()) { + const TypeLong* this_type = this->type()->is_long(); + const TypeLong* in_type = phase->type(in(1))->isa_long(); + if (in_type != NULL && this_type != NULL && + (in_type->_lo != this_type->_lo || + in_type->_hi != this_type->_hi)) { + jlong lo1 = this_type->_lo; + jlong hi1 = this_type->_hi; + int w1 = this_type->_widen; + + if (lo1 >= 0) { + // Keep a range assertion of >=0. + lo1 = 0; hi1 = max_jlong; + } else if (hi1 < 0) { + // Keep a range assertion of <0. + lo1 = min_jlong; hi1 = -1; + } else { + lo1 = min_jlong; hi1 = max_jlong; + } + const TypeLong* wtype = TypeLong::make(MAX2(in_type->_lo, lo1), + MIN2(in_type->_hi, hi1), + MAX2((int)in_type->_widen, w1)); + if (wtype != type()) { + set_type(wtype); + return this; + } + } + } + return NULL; +} + + //============================================================================= //------------------------------Identity--------------------------------------- // If input is already higher or equal to cast type, then this is an identity.