< prev index next >

src/share/vm/opto/castnode.cpp

Print this page




  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "opto/addnode.hpp"
  27 #include "opto/callnode.hpp"
  28 #include "opto/castnode.hpp"
  29 #include "opto/connode.hpp"

  30 #include "opto/matcher.hpp"
  31 #include "opto/phaseX.hpp"
  32 #include "opto/rootnode.hpp"
  33 #include "opto/subnode.hpp"
  34 #include "opto/type.hpp"
  35 #include "opto/valuetypenode.hpp"
  36 
  37 //=============================================================================
  38 // If input is already higher or equal to cast type, then this is an identity.
  39 Node* ConstraintCastNode::Identity(PhaseGVN* phase) {
  40   Node* dom = dominating_cast(phase, phase);
  41   if (dom != NULL) {
  42     return dom;
  43   }
  44   if (_carry_dependency) {
  45     return this;
  46   }
  47   return phase->type(in(1))->higher_equal_speculative(_type) ? in(1) : this;
  48 }
  49 


 399   //   }
 400   //   // ELSE return same old type as before
 401   //   return _type;
 402   // }
 403   // // Not joining two pointers
 404   // return join;
 405 }
 406 
 407 Node* CheckCastPPNode::Ideal(PhaseGVN *phase, bool can_reshape) {
 408   // This is a value type. Its input is the return of a call: the call
 409   // returns a value type and we now know its exact type: build a
 410   // ValueTypePtrNode from the call.
 411   if (can_reshape &&
 412       in(0) == NULL &&
 413       phase->C->can_add_value_type_ptr() &&
 414       type()->isa_valuetypeptr() &&
 415       in(1) != NULL && in(1)->is_Proj() &&
 416       in(1)->in(0) != NULL && in(1)->in(0)->is_CallStaticJava() &&
 417       in(1)->in(0)->as_CallStaticJava()->method() != NULL &&
 418       in(1)->as_Proj()->_con == TypeFunc::Parms) {
 419     ciValueKlass* vk = type()->is_valuetypeptr()->value_type()->value_klass();
 420     assert(vk != phase->C->env()->___Value_klass(), "why cast to __Value?");
 421     PhaseIterGVN *igvn = phase->is_IterGVN();

 422 
 423     if (ValueTypeReturnedAsFields && vk->can_be_returned_as_fields()) {
 424       igvn->set_delay_transform(true);
 425       CallNode* call = in(1)->in(0)->as_Call();
 426       phase->C->remove_macro_node(call);
 427       // We now know the return type of the call
 428       const TypeTuple *range_sig = TypeTuple::make_range(vk, false);
 429       const TypeTuple *range_cc = TypeTuple::make_range(vk, true);
 430       assert(range_sig != call->_tf->range_sig() && range_cc != call->_tf->range_cc(), "type should change");
 431       call->_tf = TypeFunc::make(call->_tf->domain_sig(), call->_tf->domain_cc(),
 432                                  range_sig, range_cc);
 433       phase->set_type(call, call->Value(phase));
 434       phase->set_type(in(1), in(1)->Value(phase));
 435 










 436       CallProjections projs;
 437       call->extract_projections(&projs, true, true);























 438 
 439       Node* init_ctl = new Node(1);
 440       Node* init_mem = new Node(1);
 441       Node* init_io = new Node(1);
 442       Node* init_ex_ctl = new Node(1);
 443       Node* init_ex_mem = new Node(1);
 444       Node* init_ex_io = new Node(1);
 445       Node* res = new Node(1);
 446 
 447       Node* ctl = init_ctl;
 448       Node* mem = init_mem;
 449       Node* io = init_io;
 450       Node* ex_ctl = init_ex_ctl;
 451       Node* ex_mem = init_ex_mem;
 452       Node* ex_io = init_ex_io;
 453 
 454       // Either we get a buffered value pointer and we can case use it
 455       // or we get a tagged klass pointer and we need to allocate a
 456       // value.
 457       Node* cast = phase->transform(new CastP2XNode(ctl, res));
 458       Node* masked = phase->transform(new AndXNode(cast, phase->MakeConX(0x1)));
 459       Node* cmp = phase->transform(new CmpXNode(masked, phase->MakeConX(0x1)));
 460       Node* bol = phase->transform(new BoolNode(cmp, BoolTest::eq));
 461       IfNode* iff = phase->transform(new IfNode(ctl, bol, PROB_MAX, COUNT_UNKNOWN))->as_If();
 462       Node* iftrue = phase->transform(new IfTrueNode(iff));
 463       Node* iffalse = phase->transform(new IfFalseNode(iff));
 464 
 465       ctl = iftrue;
 466 
 467       Node* ex_r = new RegionNode(3);
 468       Node* ex_mem_phi = new PhiNode(ex_r, Type::MEMORY, TypePtr::BOTTOM);
 469       Node* ex_io_phi = new PhiNode(ex_r, Type::ABIO);
 470 
 471       ex_r->init_req(2, ex_ctl);
 472       ex_mem_phi->init_req(2, ex_mem);
 473       ex_io_phi->init_req(2, ex_io);
 474 
 475       // We need an oop pointer in case allocation elimination
 476       // fails. Allocate a new instance here.
 477       Node* javaoop = ValueTypeBaseNode::allocate(type(), ctl, mem, io,
 478                                                   call->in(TypeFunc::FramePtr),
 479                                                   ex_ctl, ex_mem, ex_io,
 480                                                   call->jvms(), igvn);
 481 
 482 
 483 
 484       ex_r->init_req(1, ex_ctl);
 485       ex_mem_phi->init_req(1, ex_mem);
 486       ex_io_phi->init_req(1, ex_io);
 487 
 488       ex_r = igvn->transform(ex_r);
 489       ex_mem_phi = igvn->transform(ex_mem_phi);
 490       ex_io_phi = igvn->transform(ex_io_phi);
 491 
 492       // Create the ValueTypePtrNode. This will add extra projections
 493       // to the call.
 494       ValueTypePtrNode* vtptr = ValueTypePtrNode::make(igvn, this);
 495       // Newly allocated value type must be initialized
 496       vtptr->store(igvn, ctl, mem->as_MergeMem(), javaoop);
 497       vtptr->set_oop(javaoop);
 498 
 499       Node* r = new RegionNode(3);
 500       Node* mem_phi = new PhiNode(r, Type::MEMORY, TypePtr::BOTTOM);
 501       Node* io_phi = new PhiNode(r, Type::ABIO);
 502       Node* res_phi = new PhiNode(r, type());
 503 
 504       r->init_req(1, ctl);
 505       mem_phi->init_req(1, mem);
 506       io_phi->init_req(1, io);
 507       res_phi->init_req(1, igvn->transform(vtptr));
 508 
 509       ctl = iffalse;
 510       mem = init_mem;
 511       io = init_io;
 512 
 513       Node* castnotnull = new CastPPNode(res, TypePtr::NOTNULL);
 514       castnotnull->set_req(0, ctl);
 515       castnotnull = phase->transform(castnotnull);
 516       Node* ccast = clone();
 517       ccast->set_req(0, ctl);
 518       ccast->set_req(1, castnotnull);
 519       ccast = phase->transform(ccast);
 520 
 521       vtptr = ValueTypePtrNode::make(*phase, mem, ccast);
 522 
 523       r->init_req(2, ctl);
 524       mem_phi->init_req(2, mem);
 525       io_phi->init_req(2, io);
 526       res_phi->init_req(2, igvn->transform(vtptr));
 527 
 528       r = igvn->transform(r);
 529       mem_phi = igvn->transform(mem_phi);
 530       io_phi = igvn->transform(io_phi);
 531       res_phi = igvn->transform(res_phi);
 532 
 533       igvn->replace_in_uses(projs.fallthrough_catchproj, r);
 534       igvn->replace_in_uses(projs.fallthrough_memproj, mem_phi);
 535       igvn->replace_in_uses(projs.fallthrough_ioproj, io_phi);
 536       igvn->replace_in_uses(projs.resproj, res_phi);
 537       igvn->replace_in_uses(projs.catchall_catchproj, ex_r);
 538       igvn->replace_in_uses(projs.catchall_memproj, ex_mem_phi);
 539       igvn->replace_in_uses(projs.catchall_ioproj, ex_io_phi);
 540 
 541       igvn->set_delay_transform(false);
 542 
 543       igvn->replace_node(init_ctl, projs.fallthrough_catchproj);
 544       igvn->replace_node(init_mem, projs.fallthrough_memproj);
 545       igvn->replace_node(init_io, projs.fallthrough_ioproj);
 546       igvn->replace_node(res, projs.resproj);
 547       igvn->replace_node(init_ex_ctl, projs.catchall_catchproj);
 548       igvn->replace_node(init_ex_mem, projs.catchall_memproj);
 549       igvn->replace_node(init_ex_io, projs.catchall_ioproj);
 550 
 551       return this;
 552     } else {
 553       CallNode* call = in(1)->in(0)->as_Call();
 554       // We now know the return type of the call
 555       const TypeTuple *range = TypeTuple::make_range(vk, false);
 556       if (range != call->_tf->range_sig()) {
 557         // Build the ValueTypePtrNode by loading the fields. Use call
 558         // return as oop edge in the ValueTypePtrNode.
 559         call->_tf = TypeFunc::make(call->_tf->domain_sig(), call->_tf->domain_cc(),
 560                                    range, range);
 561         phase->set_type(call, call->Value(phase));
 562         phase->set_type(in(1), in(1)->Value(phase));
 563         uint last = phase->C->unique();
 564         CallNode* call = in(1)->in(0)->as_Call();

 565         CallProjections projs;
 566         call->extract_projections(&projs, true, true);

 567         Node* mem = projs.fallthrough_memproj;
 568         Node* vtptr = ValueTypePtrNode::make(*phase, mem, in(1));
 569 



 570         return vtptr;
 571       }
 572     }
 573   }
 574   return NULL;
 575 }
 576 
 577 //=============================================================================
 578 //------------------------------Value------------------------------------------
 579 const Type* CastX2PNode::Value(PhaseGVN* phase) const {
 580   const Type* t = phase->type(in(1));
 581   if (t == Type::TOP) return Type::TOP;
 582   if (t->base() == Type_X && t->singleton()) {
 583     uintptr_t bits = (uintptr_t) t->is_intptr_t()->get_con();
 584     if (bits == 0)   return TypePtr::NULL_PTR;
 585     return TypeRawPtr::make((address) bits);
 586   }
 587   return CastX2PNode::bottom_type();
 588 }
 589 




  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "opto/addnode.hpp"
  27 #include "opto/callnode.hpp"
  28 #include "opto/castnode.hpp"
  29 #include "opto/connode.hpp"
  30 #include "opto/graphKit.hpp"
  31 #include "opto/matcher.hpp"
  32 #include "opto/phaseX.hpp"
  33 #include "opto/rootnode.hpp"
  34 #include "opto/subnode.hpp"
  35 #include "opto/type.hpp"
  36 #include "opto/valuetypenode.hpp"
  37 
  38 //=============================================================================
  39 // If input is already higher or equal to cast type, then this is an identity.
  40 Node* ConstraintCastNode::Identity(PhaseGVN* phase) {
  41   Node* dom = dominating_cast(phase, phase);
  42   if (dom != NULL) {
  43     return dom;
  44   }
  45   if (_carry_dependency) {
  46     return this;
  47   }
  48   return phase->type(in(1))->higher_equal_speculative(_type) ? in(1) : this;
  49 }
  50 


 400   //   }
 401   //   // ELSE return same old type as before
 402   //   return _type;
 403   // }
 404   // // Not joining two pointers
 405   // return join;
 406 }
 407 
 408 Node* CheckCastPPNode::Ideal(PhaseGVN *phase, bool can_reshape) {
 409   // This is a value type. Its input is the return of a call: the call
 410   // returns a value type and we now know its exact type: build a
 411   // ValueTypePtrNode from the call.
 412   if (can_reshape &&
 413       in(0) == NULL &&
 414       phase->C->can_add_value_type_ptr() &&
 415       type()->isa_valuetypeptr() &&
 416       in(1) != NULL && in(1)->is_Proj() &&
 417       in(1)->in(0) != NULL && in(1)->in(0)->is_CallStaticJava() &&
 418       in(1)->in(0)->as_CallStaticJava()->method() != NULL &&
 419       in(1)->as_Proj()->_con == TypeFunc::Parms) {
 420     const TypeValueTypePtr* cast_type = type()->is_valuetypeptr();
 421     ciValueKlass* vk = cast_type->value_type()->value_klass();
 422     assert(!vk->is__Value(), "why cast to __Value?");
 423     PhaseIterGVN* igvn = phase->is_IterGVN();
 424 
 425     if (ValueTypeReturnedAsFields && vk->can_be_returned_as_fields()) {
 426       igvn->set_delay_transform(true);
 427       CallNode* call = in(1)->in(0)->as_Call();
 428       igvn->C->remove_macro_node(call);
 429       // We now know the return type of the call
 430       const TypeTuple* range_sig = TypeTuple::make_range(vk, false);
 431       const TypeTuple* range_cc = TypeTuple::make_range(vk, true);
 432       assert(range_sig != call->_tf->range_sig() && range_cc != call->_tf->range_cc(), "type should change");
 433       call->_tf = TypeFunc::make(call->_tf->domain_sig(), call->_tf->domain_cc(),
 434                                  range_sig, range_cc);
 435       igvn->set_type(call, call->Value(igvn));
 436       igvn->set_type(in(1), in(1)->Value(igvn));
 437 
 438       Node* ctl_hook = new Node(1);
 439       Node* mem_hook = new Node(1);
 440       Node* io_hook = new Node(1);
 441       Node* res_hook = new Node(1);
 442       Node* ex_ctl_hook = new Node(1);
 443       Node* ex_mem_hook = new Node(1);
 444       Node* ex_io_hook = new Node(1);
 445 
 446       // Extract projections from the call and hook users to temporary nodes.
 447       // We will re-attach them to newly created PhiNodes below.
 448       CallProjections projs;
 449       call->extract_projections(&projs, true, true);
 450       igvn->replace_in_uses(projs.fallthrough_catchproj, ctl_hook);
 451       igvn->replace_in_uses(projs.fallthrough_memproj, mem_hook);
 452       igvn->replace_in_uses(projs.fallthrough_ioproj, io_hook);
 453       igvn->replace_in_uses(projs.resproj, res_hook);
 454       igvn->replace_in_uses(projs.catchall_catchproj, ex_ctl_hook);
 455       igvn->replace_in_uses(projs.catchall_memproj, ex_mem_hook);
 456       igvn->replace_in_uses(projs.catchall_ioproj, ex_io_hook);
 457 
 458       // Restore IO input of the CatchNode
 459       CatchNode* catchp = projs.fallthrough_catchproj->in(0)->as_Catch();
 460       catchp->set_req(TypeFunc::I_O, projs.catchall_ioproj);
 461       igvn->rehash_node_delayed(catchp);
 462 
 463       // Rebuild the output JVMState from the call and use it to initialize a GraphKit
 464       JVMState* new_jvms = call->jvms()->clone_shallow(igvn->C);
 465       SafePointNode* new_map = new SafePointNode(call->req(), new_jvms);
 466       for (uint i = TypeFunc::FramePtr; i < call->req(); i++) {
 467         new_map->init_req(i, call->in(i));
 468       }
 469       new_map->set_control(projs.fallthrough_catchproj);
 470       new_map->set_memory(MergeMemNode::make(projs.fallthrough_memproj));
 471       new_map->set_i_o(projs.fallthrough_ioproj);
 472       new_jvms->set_map(new_map);
 473 
 474       GraphKit kit(new_jvms, igvn);













 475 
 476       // Either we get a buffered value pointer and we can case use it
 477       // or we get a tagged klass pointer and we need to allocate a value.
 478       Node* cast = igvn->transform(new CastP2XNode(kit.control(), projs.resproj));
 479       Node* masked = igvn->transform(new AndXNode(cast, igvn->MakeConX(0x1)));
 480       Node* cmp = igvn->transform(new CmpXNode(masked, igvn->MakeConX(0x1)));
 481       Node* bol = kit.Bool(cmp, BoolTest::eq);
 482       IfNode* iff = kit.create_and_map_if(kit.control(), bol, PROB_MAX, COUNT_UNKNOWN);
 483       Node* iftrue = kit.IfTrue(iff);
 484       Node* iffalse = kit.IfFalse(iff);
 485 
 486       Node* region = new RegionNode(3);
 487       Node* mem_phi = new PhiNode(region, Type::MEMORY, TypePtr::BOTTOM);
 488       Node* io_phi = new PhiNode(region, Type::ABIO);
 489       Node* res_phi = new PhiNode(region, cast_type);
 490       Node* ex_region = new RegionNode(3);
 491       Node* ex_mem_phi = new PhiNode(ex_region, Type::MEMORY, TypePtr::BOTTOM);
 492       Node* ex_io_phi = new PhiNode(ex_region, Type::ABIO);
 493 
 494       // True branch: result is a tagged klass pointer
 495       // Allocate a value type (will add extra projections to the call)
 496       kit.set_control(iftrue);
 497       Node* res = igvn->transform(ValueTypePtrNode::make(&kit, vk, call));
 498       res = res->isa_ValueTypePtr()->allocate(&kit);
 499 
 500       // Get exception state
 501       GraphKit ekit(kit.transfer_exceptions_into_jvms(), igvn);
 502       SafePointNode* ex_map = ekit.combine_and_pop_all_exception_states();
 503       Node* ex_oop = ekit.use_exception_state(ex_map);
 504 
 505       region->init_req(1, kit.control());
 506       mem_phi->init_req(1, kit.reset_memory());
 507       io_phi->init_req(1, kit.i_o());
 508       res_phi->init_req(1, res);
 509       ex_region->init_req(1, ekit.control());
 510       ex_mem_phi->init_req(1, ekit.reset_memory());
 511       ex_io_phi->init_req(1, ekit.i_o());
 512 
 513       // False branch: result is not tagged
 514       // Load buffered value type from returned oop
 515       kit.set_control(iffalse);
 516       kit.set_all_memory(projs.fallthrough_memproj);
 517       kit.set_i_o(projs.fallthrough_ioproj);
 518       // Cast oop to NotNull
 519       ConstraintCastNode* res_cast = clone()->as_ConstraintCast();
 520       res_cast->set_req(0, kit.control());
 521       res_cast->set_req(1, projs.resproj);
 522       res_cast->set_type(cast_type->cast_to_ptr_type(TypePtr::NotNull));
 523       Node* ctl = kit.control(); // Control may get updated below
 524       res = ValueTypePtrNode::make(*igvn, ctl, kit.merged_memory(), igvn->transform(res_cast));
 525 
 526       region->init_req(2, ctl);
 527       mem_phi->init_req(2, kit.reset_memory());
 528       io_phi->init_req(2, kit.i_o());
 529       res_phi->init_req(2, igvn->transform(res));
 530       ex_region->init_req(2, projs.catchall_catchproj);
 531       ex_mem_phi->init_req(2, projs.catchall_memproj);
 532       ex_io_phi->init_req(2, projs.catchall_ioproj);





























 533 
 534       igvn->set_delay_transform(false);
 535 
 536       // Re-attach users to newly created PhiNodes
 537       igvn->replace_node(ctl_hook, igvn->transform(region));
 538       igvn->replace_node(mem_hook, igvn->transform(mem_phi));
 539       igvn->replace_node(io_hook, igvn->transform(io_phi));
 540       igvn->replace_node(res_hook, igvn->transform(res_phi));
 541       igvn->replace_node(ex_ctl_hook, igvn->transform(ex_region));
 542       igvn->replace_node(ex_mem_hook, igvn->transform(ex_mem_phi));
 543       igvn->replace_node(ex_io_hook, igvn->transform(ex_io_phi));
 544       return this;
 545     } else {
 546       CallNode* call = in(1)->in(0)->as_Call();
 547       // We now know the return type of the call
 548       const TypeTuple* range = TypeTuple::make_range(vk, false);
 549       if (range != call->_tf->range_sig()) {
 550         // Build the ValueTypePtrNode by loading the fields

 551         call->_tf = TypeFunc::make(call->_tf->domain_sig(), call->_tf->domain_cc(),
 552                                    range, range);
 553         phase->set_type(call, call->Value(phase));
 554         phase->set_type(in(1), in(1)->Value(phase));
 555         uint last = phase->C->unique();
 556         CallNode* call = in(1)->in(0)->as_Call();
 557         // Extract projections from the call and hook control users to temporary node
 558         CallProjections projs;
 559         call->extract_projections(&projs, true, true);
 560         Node* ctl = projs.fallthrough_catchproj;
 561         Node* mem = projs.fallthrough_memproj;
 562         Node* ctl_hook = new Node(1);
 563         igvn->replace_in_uses(ctl, ctl_hook);
 564         Node* vtptr = ValueTypePtrNode::make(*phase, ctl, mem, in(1));
 565         // Attach users to updated control
 566         igvn->replace_node(ctl_hook, ctl);
 567         return vtptr;
 568       }
 569     }
 570   }
 571   return NULL;
 572 }
 573 
 574 //=============================================================================
 575 //------------------------------Value------------------------------------------
 576 const Type* CastX2PNode::Value(PhaseGVN* phase) const {
 577   const Type* t = phase->type(in(1));
 578   if (t == Type::TOP) return Type::TOP;
 579   if (t->base() == Type_X && t->singleton()) {
 580     uintptr_t bits = (uintptr_t) t->is_intptr_t()->get_con();
 581     if (bits == 0)   return TypePtr::NULL_PTR;
 582     return TypeRawPtr::make((address) bits);
 583   }
 584   return CastX2PNode::bottom_type();
 585 }
 586 


< prev index next >