src/share/vm/opto/library_call.cpp
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File
*** old/src/share/vm/opto/library_call.cpp	Wed Jan 14 10:19:27 2015
--- new/src/share/vm/opto/library_call.cpp	Wed Jan 14 10:19:27 2015

*** 3947,3968 **** --- 3947,4000 ---- // We know the copy is disjoint but we might not know if the // oop stores need checking. // Extreme case: Arrays.copyOf((Integer[])x, 10, String[].class). // This will fail a store-check if x contains any non-nulls. Node* alloc = tightly_coupled_allocation(newcopy, NULL); + if (_gvn.type(klass_node)->singleton()) { + ciKlass* subk = _gvn.type(load_object_klass(original))->is_klassptr()->klass(); + ciKlass* superk = _gvn.type(klass_node)->is_klassptr()->klass(); ArrayCopyNode* ac = ArrayCopyNode::make(this, true, original, start, newcopy, intcon(0), moved, alloc != NULL, + int test = C->static_subtype_check(superk, subk); + if (test != Compile::SSC_always_true && test != Compile::SSC_always_false) { + const TypeOopPtr* t_original = _gvn.type(original)->is_oopptr(); + if (t_original->speculative_type() != NULL) { + original = maybe_cast_profiled_obj(original, t_original->speculative_type(), true); + } + } + } + + bool validated = false; + // Reason_class_check rather than Reason_intrinsic because we + // want to intrinsify even if this traps. + if (!too_many_traps(Deoptimization::Reason_class_check)) { + Node* not_subtype_ctrl = gen_subtype_check(load_object_klass(original), + klass_node); + + if (not_subtype_ctrl != top()) { + PreserveJVMState pjvms(this); + set_control(not_subtype_ctrl); + uncommon_trap(Deoptimization::Reason_class_check, + Deoptimization::Action_make_not_entrant); + assert(stopped(), "Should be stopped"); + } + validated = true; + } + + ArrayCopyNode* ac = ArrayCopyNode::make(this, true, original, start, newcopy, intcon(0), moved, true, load_object_klass(original), klass_node); if (!is_copyOfRange) { ! ac->set_copyof(validated); } else { ! ac->set_copyofrange(validated); } Node* n = _gvn.transform(ac); assert(n == ac, "cannot disappear"); + if (n == ac) { ac->connect_outputs(this); + } else { + assert(validated, "shouldn't transform if all arguments not validated"); + set_all_memory(n); + } } } // original reexecute is set back here C->set_has_split_ifs(true); // Has chance for split-if optimization if (!stopped()) {

src/share/vm/opto/library_call.cpp
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File