< prev index next >

src/hotspot/share/opto/addnode.cpp

Print this page

        

*** 234,243 **** --- 234,277 ---- return NULL; } //============================================================================= + + static Node* convert_add_to_muladd(PhaseGVN *phase, Node* in1, Node* in2) { + // Only convert to this type of node if backend supports and if vectorizer supports it as well. + // The reason vectorizer is also checked is because this transformation is explicitly done + // to make vectorizer analysis easier for forms where type transition happens during operation. + if (Matcher::match_rule_supported(Op_MulAddS2I) && + Matcher::match_rule_supported(Op_MulAddVS2VI)) { + if (in1->Opcode() == Op_MulI && in2->Opcode() == Op_MulI) { + Node* mul_in1 = in1->in(1); + Node* mul_in2 = in1->in(2); + Node* mul_in3 = in2->in(1); + Node* mul_in4 = in2->in(2); + + if (mul_in1->Opcode() == Op_LoadS && + mul_in2->Opcode() == Op_LoadS && + mul_in3->Opcode() == Op_LoadS && + mul_in4->Opcode() == Op_LoadS) { + Node* adr1 = mul_in1->in(MemNode::Address); + Node* adr2 = mul_in2->in(MemNode::Address); + Node* adr3 = mul_in3->in(MemNode::Address); + Node* adr4 = mul_in4->in(MemNode::Address); + + if (adr1->is_AddP() && adr2->is_AddP() && adr3->is_AddP() && adr4->is_AddP()) { + if ((adr1->in(AddPNode::Base) == adr3->in(AddPNode::Base)) && + (adr2->in(AddPNode::Base) == adr4->in(AddPNode::Base))) { + return new MulAddS2INode(mul_in1, mul_in2, mul_in3, mul_in4); + } + } + } + } + } + return NULL; + } + //------------------------------Idealize--------------------------------------- Node *AddINode::Ideal(PhaseGVN *phase, bool can_reshape) { Node* in1 = in(1); Node* in2 = in(2); int op1 = in1->Opcode();
*** 318,327 **** --- 352,366 ---- return new URShiftINode( a, in1->in(2) ); } } } + Node* muladd = convert_add_to_muladd(phase, in1, in2); + if (muladd != NULL) { + return muladd; + } + return AddNode::Ideal(phase, can_reshape); } //------------------------------Identity---------------------------------------
< prev index next >