1 /* 2 * Copyright (c) 2007, 2019, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 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 #ifndef SHARE_OPTO_VECTORNODE_HPP 25 #define SHARE_OPTO_VECTORNODE_HPP 26 27 #include "opto/callnode.hpp" 28 #include "opto/matcher.hpp" 29 #include "opto/memnode.hpp" 30 #include "opto/node.hpp" 31 #include "opto/opcodes.hpp" 32 33 //------------------------------VectorNode------------------------------------- 34 // Vector Operation 35 class VectorNode : public TypeNode { 36 public: 37 38 VectorNode(Node* n1, const TypeVect* vt) : TypeNode(vt, 2) { 39 init_class_id(Class_Vector); 40 init_req(1, n1); 41 } 42 VectorNode(Node* n1, Node* n2, const TypeVect* vt) : TypeNode(vt, 3) { 43 init_class_id(Class_Vector); 44 init_req(1, n1); 45 init_req(2, n2); 46 } 47 48 VectorNode(Node* n1, Node* n2, Node* n3, const TypeVect* vt) : TypeNode(vt, 4) { 49 init_class_id(Class_Vector); 50 init_req(1, n1); 51 init_req(2, n2); 52 init_req(3, n3); 53 } 54 55 VectorNode(Node *n0, Node* n1, Node* n2, Node* n3, const TypeVect* vt) : TypeNode(vt, 5) { 56 init_class_id(Class_Vector); 57 init_req(1, n0); 58 init_req(2, n1); 59 init_req(3, n2); 60 init_req(4, n3); 61 } 62 63 const TypeVect* vect_type() const { return type()->is_vect(); } 64 uint length() const { return vect_type()->length(); } // Vector length 65 uint length_in_bytes() const { return vect_type()->length_in_bytes(); } 66 67 virtual int Opcode() const; 68 69 virtual uint ideal_reg() const { return Matcher::vector_ideal_reg(vect_type()->length_in_bytes()); } 70 71 static VectorNode* scalar2vector(Node* s, uint vlen, const Type* opd_t); 72 static VectorNode* shift_count(int opc, Node* cnt, uint vlen, BasicType bt); 73 static VectorNode* make(int opc, Node* n1, Node* n2, uint vlen, BasicType bt); 74 static VectorNode* make(int vopc, Node* n1, Node* n2, const TypeVect* vt); 75 static VectorNode* make(int opc, Node* n1, Node* n2, Node* n3, uint vlen, BasicType bt); 76 static VectorNode* make(int vopc, Node* n1, Node* n2, Node* n3, const TypeVect* vt); 77 78 static int opcode(int opc, BasicType bt); 79 static int replicate_opcode(BasicType bt); 80 static bool implemented(int opc, uint vlen, BasicType bt); 81 static bool is_shift(Node* n); 82 static bool is_vshift_cnt(Node* n); 83 static bool is_type_transition_short_to_int(Node* n); 84 static bool is_type_transition_to_int(Node* n); 85 static bool is_muladds2i(Node* n); 86 static bool is_roundopD(Node * n); 87 static bool is_invariant_vector(Node* n); 88 static bool is_all_ones_vector(Node* n); 89 static bool is_vector_bitwise_not_pattern(Node* n); 90 91 // [Start, end) half-open range defining which operands are vectors 92 static void vector_operands(Node* n, uint* start, uint* end); 93 94 static bool is_vector_shift(int opc); 95 static bool is_vector_shift_count(int opc); 96 97 static bool is_vector_shift(Node* n) { 98 return is_vector_shift(n->Opcode()); 99 } 100 static bool is_vector_shift_count(Node* n) { 101 return is_vector_shift_count(n->Opcode()); 102 } 103 }; 104 105 //===========================Vector=ALU=Operations============================= 106 107 //------------------------------AddVBNode-------------------------------------- 108 // Vector add byte 109 class AddVBNode : public VectorNode { 110 public: 111 AddVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 112 virtual int Opcode() const; 113 }; 114 115 //------------------------------AddVSNode-------------------------------------- 116 // Vector add char/short 117 class AddVSNode : public VectorNode { 118 public: 119 AddVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 120 virtual int Opcode() const; 121 }; 122 123 //------------------------------AddVINode-------------------------------------- 124 // Vector add int 125 class AddVINode : public VectorNode { 126 public: 127 AddVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 128 virtual int Opcode() const; 129 }; 130 131 //------------------------------AddVLNode-------------------------------------- 132 // Vector add long 133 class AddVLNode : public VectorNode { 134 public: 135 AddVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 136 virtual int Opcode() const; 137 }; 138 139 //------------------------------AddVFNode-------------------------------------- 140 // Vector add float 141 class AddVFNode : public VectorNode { 142 public: 143 AddVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 144 virtual int Opcode() const; 145 }; 146 147 //------------------------------AddVDNode-------------------------------------- 148 // Vector add double 149 class AddVDNode : public VectorNode { 150 public: 151 AddVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 152 virtual int Opcode() const; 153 }; 154 155 //------------------------------ReductionNode------------------------------------ 156 // Perform reduction of a vector 157 class ReductionNode : public Node { 158 public: 159 ReductionNode(Node *ctrl, Node* in1, Node* in2) : Node(ctrl, in1, in2) {} 160 161 static ReductionNode* make(int opc, Node *ctrl, Node* in1, Node* in2, BasicType bt); 162 static int opcode(int opc, BasicType bt); 163 static bool implemented(int opc, uint vlen, BasicType bt); 164 static Node* make_reduction_input(PhaseGVN& gvn, int opc, BasicType bt); 165 166 virtual const Type* bottom_type() const { 167 BasicType vbt = in(1)->bottom_type()->basic_type(); 168 return Type::get_const_basic_type(vbt); 169 } 170 171 virtual uint ideal_reg() const { 172 return bottom_type()->ideal_reg(); 173 } 174 }; 175 176 //------------------------------AddReductionVINode-------------------------------------- 177 // Vector add byte, short and int as a reduction 178 class AddReductionVINode : public ReductionNode { 179 public: 180 AddReductionVINode(Node * ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 181 virtual int Opcode() const; 182 }; 183 184 //------------------------------AddReductionVLNode-------------------------------------- 185 // Vector add long as a reduction 186 class AddReductionVLNode : public ReductionNode { 187 public: 188 AddReductionVLNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 189 virtual int Opcode() const; 190 }; 191 192 //------------------------------AddReductionVFNode-------------------------------------- 193 // Vector add float as a reduction 194 class AddReductionVFNode : public ReductionNode { 195 public: 196 AddReductionVFNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 197 virtual int Opcode() const; 198 }; 199 200 //------------------------------AddReductionVDNode-------------------------------------- 201 // Vector add double as a reduction 202 class AddReductionVDNode : public ReductionNode { 203 public: 204 AddReductionVDNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 205 virtual int Opcode() const; 206 }; 207 208 //------------------------------SubVBNode-------------------------------------- 209 // Vector subtract byte 210 class SubVBNode : public VectorNode { 211 public: 212 SubVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 213 virtual int Opcode() const; 214 }; 215 216 //------------------------------SubVSNode-------------------------------------- 217 // Vector subtract short 218 class SubVSNode : public VectorNode { 219 public: 220 SubVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 221 virtual int Opcode() const; 222 }; 223 224 //------------------------------SubVINode-------------------------------------- 225 // Vector subtract int 226 class SubVINode : public VectorNode { 227 public: 228 SubVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 229 virtual int Opcode() const; 230 }; 231 232 //------------------------------SubVLNode-------------------------------------- 233 // Vector subtract long 234 class SubVLNode : public VectorNode { 235 public: 236 SubVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 237 virtual int Opcode() const; 238 }; 239 240 //------------------------------SubVFNode-------------------------------------- 241 // Vector subtract float 242 class SubVFNode : public VectorNode { 243 public: 244 SubVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 245 virtual int Opcode() const; 246 }; 247 248 //------------------------------SubVDNode-------------------------------------- 249 // Vector subtract double 250 class SubVDNode : public VectorNode { 251 public: 252 SubVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 253 virtual int Opcode() const; 254 }; 255 256 //------------------------------MulVBNode-------------------------------------- 257 // Vector multiply byte 258 class MulVBNode : public VectorNode { 259 public: 260 MulVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 261 virtual int Opcode() const; 262 }; 263 264 //------------------------------MulVSNode-------------------------------------- 265 // Vector multiply short 266 class MulVSNode : public VectorNode { 267 public: 268 MulVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 269 virtual int Opcode() const; 270 }; 271 272 //------------------------------MulVINode-------------------------------------- 273 // Vector multiply int 274 class MulVINode : public VectorNode { 275 public: 276 MulVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 277 virtual int Opcode() const; 278 }; 279 280 //------------------------------MulVLNode-------------------------------------- 281 // Vector multiply long 282 class MulVLNode : public VectorNode { 283 public: 284 MulVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 285 virtual int Opcode() const; 286 }; 287 288 //------------------------------MulVFNode-------------------------------------- 289 // Vector multiply float 290 class MulVFNode : public VectorNode { 291 public: 292 MulVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 293 virtual int Opcode() const; 294 }; 295 296 //------------------------------MulVDNode-------------------------------------- 297 // Vector multiply double 298 class MulVDNode : public VectorNode { 299 public: 300 MulVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 301 virtual int Opcode() const; 302 }; 303 304 //------------------------------MulAddVS2VINode-------------------------------- 305 // Vector multiply shorts to int and add adjacent ints. 306 class MulAddVS2VINode : public VectorNode { 307 public: 308 MulAddVS2VINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 309 virtual int Opcode() const; 310 }; 311 312 //------------------------------FmaVDNode-------------------------------------- 313 // Vector multiply double 314 class FmaVDNode : public VectorNode { 315 public: 316 FmaVDNode(Node* in1, Node* in2, Node* in3, const TypeVect* vt) : VectorNode(in1, in2, in3, vt) {} 317 virtual int Opcode() const; 318 }; 319 320 //------------------------------FmaVFNode-------------------------------------- 321 // Vector multiply float 322 class FmaVFNode : public VectorNode { 323 public: 324 FmaVFNode(Node* in1, Node* in2, Node* in3, const TypeVect* vt) : VectorNode(in1, in2, in3, vt) {} 325 virtual int Opcode() const; 326 }; 327 328 //------------------------------CMoveVFNode-------------------------------------- 329 // Vector float conditional move 330 class CMoveVFNode : public VectorNode { 331 public: 332 CMoveVFNode(Node* in1, Node* in2, Node* in3, const TypeVect* vt) : VectorNode(in1, in2, in3, vt) {} 333 virtual int Opcode() const; 334 }; 335 336 //------------------------------CMoveVDNode-------------------------------------- 337 // Vector double conditional move 338 class CMoveVDNode : public VectorNode { 339 public: 340 CMoveVDNode(Node* in1, Node* in2, Node* in3, const TypeVect* vt) : VectorNode(in1, in2, in3, vt) {} 341 virtual int Opcode() const; 342 }; 343 344 //------------------------------MulReductionVINode-------------------------------------- 345 // Vector multiply byte, short and int as a reduction 346 class MulReductionVINode : public ReductionNode { 347 public: 348 MulReductionVINode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 349 virtual int Opcode() const; 350 }; 351 352 //------------------------------MulReductionVLNode-------------------------------------- 353 // Vector multiply int as a reduction 354 class MulReductionVLNode : public ReductionNode { 355 public: 356 MulReductionVLNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 357 virtual int Opcode() const; 358 }; 359 360 //------------------------------MulReductionVFNode-------------------------------------- 361 // Vector multiply float as a reduction 362 class MulReductionVFNode : public ReductionNode { 363 public: 364 MulReductionVFNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 365 virtual int Opcode() const; 366 }; 367 368 //------------------------------MulReductionVDNode-------------------------------------- 369 // Vector multiply double as a reduction 370 class MulReductionVDNode : public ReductionNode { 371 public: 372 MulReductionVDNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 373 virtual int Opcode() const; 374 }; 375 376 //------------------------------DivVFNode-------------------------------------- 377 // Vector divide float 378 class DivVFNode : public VectorNode { 379 public: 380 DivVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 381 virtual int Opcode() const; 382 }; 383 384 //------------------------------DivVDNode-------------------------------------- 385 // Vector Divide double 386 class DivVDNode : public VectorNode { 387 public: 388 DivVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 389 virtual int Opcode() const; 390 }; 391 392 //------------------------------AbsVBNode-------------------------------------- 393 // Vector Abs byte 394 class AbsVBNode : public VectorNode { 395 public: 396 AbsVBNode(Node* in, const TypeVect* vt) : VectorNode(in, vt) {} 397 virtual int Opcode() const; 398 }; 399 400 //------------------------------AbsVSNode-------------------------------------- 401 // Vector Abs short 402 class AbsVSNode : public VectorNode { 403 public: 404 AbsVSNode(Node* in, const TypeVect* vt) : VectorNode(in, vt) {} 405 virtual int Opcode() const; 406 }; 407 408 //------------------------------MinVNode-------------------------------------- 409 // Vector Min 410 class MinVNode : public VectorNode { 411 public: 412 MinVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 413 virtual int Opcode() const; 414 }; 415 416 //------------------------------MaxVNode-------------------------------------- 417 // Vector Max 418 class MaxVNode : public VectorNode { 419 public: 420 MaxVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 421 virtual int Opcode() const; 422 }; 423 424 //------------------------------AbsVINode-------------------------------------- 425 // Vector Abs int 426 class AbsVINode : public VectorNode { 427 public: 428 AbsVINode(Node* in, const TypeVect* vt) : VectorNode(in, vt) {} 429 virtual int Opcode() const; 430 }; 431 432 //------------------------------AbsVLNode-------------------------------------- 433 // Vector Abs long 434 class AbsVLNode : public VectorNode { 435 public: 436 AbsVLNode(Node* in, const TypeVect* vt) : VectorNode(in, vt) {} 437 virtual int Opcode() const; 438 }; 439 440 //------------------------------AbsVFNode-------------------------------------- 441 // Vector Abs float 442 class AbsVFNode : public VectorNode { 443 public: 444 AbsVFNode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 445 virtual int Opcode() const; 446 }; 447 448 //------------------------------AbsVDNode-------------------------------------- 449 // Vector Abs double 450 class AbsVDNode : public VectorNode { 451 public: 452 AbsVDNode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 453 virtual int Opcode() const; 454 }; 455 456 //------------------------------NegVINode-------------------------------------- 457 // Vector Neg int 458 class NegVINode : public VectorNode { 459 public: 460 NegVINode(Node* in, const TypeVect* vt) : VectorNode(in, vt) {} 461 virtual int Opcode() const; 462 }; 463 464 //------------------------------NegVFNode-------------------------------------- 465 // Vector Neg float 466 class NegVFNode : public VectorNode { 467 public: 468 NegVFNode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 469 virtual int Opcode() const; 470 }; 471 472 //------------------------------NegVDNode-------------------------------------- 473 // Vector Neg double 474 class NegVDNode : public VectorNode { 475 public: 476 NegVDNode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 477 virtual int Opcode() const; 478 }; 479 480 //------------------------------PopCountVINode--------------------------------- 481 // Vector popcount integer bits 482 class PopCountVINode : public VectorNode { 483 public: 484 PopCountVINode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 485 virtual int Opcode() const; 486 }; 487 488 //------------------------------SqrtVFNode-------------------------------------- 489 // Vector Sqrt float 490 class SqrtVFNode : public VectorNode { 491 public: 492 SqrtVFNode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 493 virtual int Opcode() const; 494 }; 495 //------------------------------RoundDoubleVNode-------------------------------- 496 // Vector round double 497 class RoundDoubleModeVNode : public VectorNode { 498 public: 499 RoundDoubleModeVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {} 500 virtual int Opcode() const; 501 }; 502 503 //------------------------------SqrtVDNode-------------------------------------- 504 // Vector Sqrt double 505 class SqrtVDNode : public VectorNode { 506 public: 507 SqrtVDNode(Node* in, const TypeVect* vt) : VectorNode(in,vt) {} 508 virtual int Opcode() const; 509 }; 510 511 //------------------------------LShiftVBNode----------------------------------- 512 // Vector left shift bytes 513 class LShiftVBNode : public VectorNode { 514 public: 515 LShiftVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 516 virtual int Opcode() const; 517 }; 518 519 //------------------------------LShiftVSNode----------------------------------- 520 // Vector left shift shorts 521 class LShiftVSNode : public VectorNode { 522 public: 523 LShiftVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 524 virtual int Opcode() const; 525 }; 526 527 //------------------------------LShiftVINode----------------------------------- 528 // Vector left shift ints 529 class LShiftVINode : public VectorNode { 530 public: 531 LShiftVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 532 virtual int Opcode() const; 533 }; 534 535 //------------------------------LShiftVLNode----------------------------------- 536 // Vector left shift longs 537 class LShiftVLNode : public VectorNode { 538 public: 539 LShiftVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 540 virtual int Opcode() const; 541 }; 542 543 //------------------------------RShiftVBNode----------------------------------- 544 // Vector right arithmetic (signed) shift bytes 545 class RShiftVBNode : public VectorNode { 546 public: 547 RShiftVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 548 virtual int Opcode() const; 549 }; 550 551 //------------------------------RShiftVSNode----------------------------------- 552 // Vector right arithmetic (signed) shift shorts 553 class RShiftVSNode : public VectorNode { 554 public: 555 RShiftVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 556 virtual int Opcode() const; 557 }; 558 559 //------------------------------RShiftVINode----------------------------------- 560 // Vector right arithmetic (signed) shift ints 561 class RShiftVINode : public VectorNode { 562 public: 563 RShiftVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 564 virtual int Opcode() const; 565 }; 566 567 //------------------------------RShiftVLNode----------------------------------- 568 // Vector right arithmetic (signed) shift longs 569 class RShiftVLNode : public VectorNode { 570 public: 571 RShiftVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 572 virtual int Opcode() const; 573 }; 574 575 //------------------------------URShiftVBNode---------------------------------- 576 // Vector right logical (unsigned) shift bytes 577 class URShiftVBNode : public VectorNode { 578 public: 579 URShiftVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 580 virtual int Opcode() const; 581 }; 582 583 //------------------------------URShiftVSNode---------------------------------- 584 // Vector right logical (unsigned) shift shorts 585 class URShiftVSNode : public VectorNode { 586 public: 587 URShiftVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 588 virtual int Opcode() const; 589 }; 590 591 //------------------------------URShiftVINode---------------------------------- 592 // Vector right logical (unsigned) shift ints 593 class URShiftVINode : public VectorNode { 594 public: 595 URShiftVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 596 virtual int Opcode() const; 597 }; 598 599 //------------------------------URShiftVLNode---------------------------------- 600 // Vector right logical (unsigned) shift longs 601 class URShiftVLNode : public VectorNode { 602 public: 603 URShiftVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 604 virtual int Opcode() const; 605 }; 606 607 //------------------------------LShiftCntVNode--------------------------------- 608 // Vector left shift count 609 class LShiftCntVNode : public VectorNode { 610 public: 611 LShiftCntVNode(Node* cnt, const TypeVect* vt) : VectorNode(cnt,vt) {} 612 virtual int Opcode() const; 613 }; 614 615 //------------------------------RShiftCntVNode--------------------------------- 616 // Vector right shift count 617 class RShiftCntVNode : public VectorNode { 618 public: 619 RShiftCntVNode(Node* cnt, const TypeVect* vt) : VectorNode(cnt,vt) {} 620 virtual int Opcode() const; 621 }; 622 623 //------------------------------AndVNode--------------------------------------- 624 // Vector and integer 625 class AndVNode : public VectorNode { 626 public: 627 AndVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 628 virtual int Opcode() const; 629 }; 630 631 //------------------------------AndReductionVNode-------------------------------------- 632 // Vector and byte, short, int, long as a reduction 633 class AndReductionVNode : public ReductionNode { 634 public: 635 AndReductionVNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 636 virtual int Opcode() const; 637 }; 638 639 //------------------------------OrVNode--------------------------------------- 640 // Vector or byte, short, int, long as a reduction 641 class OrVNode : public VectorNode { 642 public: 643 OrVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 644 virtual int Opcode() const; 645 }; 646 647 //------------------------------OrReductionVNode-------------------------------------- 648 // Vector xor byte, short, int, long as a reduction 649 class OrReductionVNode : public ReductionNode { 650 public: 651 OrReductionVNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 652 virtual int Opcode() const; 653 }; 654 655 //------------------------------XorReductionVNode-------------------------------------- 656 // Vector and int, long as a reduction 657 class XorReductionVNode : public ReductionNode { 658 public: 659 XorReductionVNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 660 virtual int Opcode() const; 661 }; 662 663 //------------------------------XorVNode--------------------------------------- 664 // Vector xor integer 665 class XorVNode : public VectorNode { 666 public: 667 XorVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {} 668 virtual int Opcode() const; 669 }; 670 671 //------------------------------MinReductionVNode-------------------------------------- 672 // Vector min byte, short, int, long, float, double as a reduction 673 class MinReductionVNode : public ReductionNode { 674 public: 675 MinReductionVNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 676 virtual int Opcode() const; 677 }; 678 679 //------------------------------MaxReductionVNode-------------------------------------- 680 // Vector min byte, short, int, long, float, double as a reduction 681 class MaxReductionVNode : public ReductionNode { 682 public: 683 MaxReductionVNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {} 684 virtual int Opcode() const; 685 }; 686 687 //================================= M E M O R Y =============================== 688 689 //------------------------------LoadVectorNode--------------------------------- 690 // Load Vector from memory 691 class LoadVectorNode : public LoadNode { 692 public: 693 LoadVectorNode(Node* c, Node* mem, Node* adr, const TypePtr* at, const TypeVect* vt, ControlDependency control_dependency = LoadNode::DependsOnlyOnTest) 694 : LoadNode(c, mem, adr, at, vt, MemNode::unordered, control_dependency) { 695 init_class_id(Class_LoadVector); 696 set_mismatched_access(); 697 } 698 699 const TypeVect* vect_type() const { return type()->is_vect(); } 700 uint length() const { return vect_type()->length(); } // Vector length 701 702 virtual int Opcode() const; 703 704 virtual uint ideal_reg() const { return Matcher::vector_ideal_reg(memory_size()); } 705 virtual BasicType memory_type() const { return T_VOID; } 706 virtual int memory_size() const { return vect_type()->length_in_bytes(); } 707 708 virtual int store_Opcode() const { return Op_StoreVector; } 709 710 static LoadVectorNode* make(int opc, Node* ctl, Node* mem, 711 Node* adr, const TypePtr* atyp, 712 uint vlen, BasicType bt, 713 ControlDependency control_dependency = LoadNode::DependsOnlyOnTest); 714 uint element_size(void) { return type2aelembytes(vect_type()->element_basic_type()); } 715 }; 716 717 //------------------------------LoadVectorGatherNode------------------------------ 718 // Load Vector from memory via index map 719 class LoadVectorGatherNode : public LoadVectorNode { 720 public: 721 LoadVectorGatherNode(Node* c, Node* mem, Node* adr, const TypePtr* at, const TypeVect* vt, Node* indices) 722 : LoadVectorNode(c, mem, adr, at, vt) { 723 init_class_id(Class_LoadVectorGather); 724 assert(indices->bottom_type()->is_vect(), "indices must be in vector"); 725 add_req(indices); 726 assert(req() == MemNode::ValueIn + 1, "match_edge expects that last input is in MemNode::ValueIn"); 727 } 728 729 virtual int Opcode() const; 730 virtual uint match_edge(uint idx) const { return idx == MemNode::Address || idx == MemNode::ValueIn; } 731 }; 732 733 //------------------------------StoreVectorNode-------------------------------- 734 // Store Vector to memory 735 class StoreVectorNode : public StoreNode { 736 public: 737 StoreVectorNode(Node* c, Node* mem, Node* adr, const TypePtr* at, Node* val) 738 : StoreNode(c, mem, adr, at, val, MemNode::unordered) { 739 init_class_id(Class_StoreVector); 740 set_mismatched_access(); 741 } 742 743 const TypeVect* vect_type() const { return in(MemNode::ValueIn)->bottom_type()->is_vect(); } 744 uint length() const { return vect_type()->length(); } // Vector length 745 746 virtual int Opcode() const; 747 748 virtual uint ideal_reg() const { return Matcher::vector_ideal_reg(memory_size()); } 749 virtual BasicType memory_type() const { return T_VOID; } 750 virtual int memory_size() const { return vect_type()->length_in_bytes(); } 751 752 static StoreVectorNode* make(int opc, Node* ctl, Node* mem, 753 Node* adr, const TypePtr* atyp, Node* val, 754 uint vlen); 755 756 uint element_size(void) { return type2aelembytes(vect_type()->element_basic_type()); } 757 }; 758 759 //------------------------------StoreVectorScatterNode------------------------------ 760 // Store Vector into memory via index map 761 762 class StoreVectorScatterNode : public StoreVectorNode { 763 public: 764 StoreVectorScatterNode(Node* c, Node* mem, Node* adr, const TypePtr* at, Node* val, Node* indices) 765 : StoreVectorNode(c, mem, adr, at, val) { 766 init_class_id(Class_StoreVectorScatter); 767 assert(indices->bottom_type()->is_vect(), "indices must be in vector"); 768 add_req(indices); 769 assert(req() == MemNode::ValueIn + 2, "match_edge expects that last input is in MemNode::ValueIn+1"); 770 } 771 virtual int Opcode() const; 772 virtual uint match_edge(uint idx) const { return idx == MemNode::Address || 773 idx == MemNode::ValueIn || 774 idx == MemNode::ValueIn + 1; } 775 }; 776 777 //=========================Promote_Scalar_to_Vector============================ 778 779 //------------------------------ReplicateBNode--------------------------------- 780 // Replicate byte scalar to be vector 781 class ReplicateBNode : public VectorNode { 782 public: 783 ReplicateBNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 784 virtual int Opcode() const; 785 }; 786 787 //------------------------------ReplicateSNode--------------------------------- 788 // Replicate short scalar to be vector 789 class ReplicateSNode : public VectorNode { 790 public: 791 ReplicateSNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 792 virtual int Opcode() const; 793 }; 794 795 //------------------------------ReplicateINode--------------------------------- 796 // Replicate int scalar to be vector 797 class ReplicateINode : public VectorNode { 798 public: 799 ReplicateINode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 800 virtual int Opcode() const; 801 }; 802 803 //------------------------------ReplicateLNode--------------------------------- 804 // Replicate long scalar to be vector 805 class ReplicateLNode : public VectorNode { 806 public: 807 ReplicateLNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 808 virtual int Opcode() const; 809 }; 810 811 //------------------------------ReplicateFNode--------------------------------- 812 // Replicate float scalar to be vector 813 class ReplicateFNode : public VectorNode { 814 public: 815 ReplicateFNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 816 virtual int Opcode() const; 817 }; 818 819 //------------------------------ReplicateDNode--------------------------------- 820 // Replicate double scalar to be vector 821 class ReplicateDNode : public VectorNode { 822 public: 823 ReplicateDNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 824 virtual int Opcode() const; 825 }; 826 827 //========================Pack_Scalars_into_a_Vector=========================== 828 829 //------------------------------PackNode--------------------------------------- 830 // Pack parent class (not for code generation). 831 class PackNode : public VectorNode { 832 public: 833 PackNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 834 PackNode(Node* in1, Node* n2, const TypeVect* vt) : VectorNode(in1, n2, vt) {} 835 virtual int Opcode() const; 836 837 void add_opd(Node* n) { 838 add_req(n); 839 } 840 841 // Create a binary tree form for Packs. [lo, hi) (half-open) range 842 PackNode* binary_tree_pack(int lo, int hi); 843 844 static PackNode* make(Node* s, uint vlen, BasicType bt); 845 }; 846 847 //------------------------------PackBNode-------------------------------------- 848 // Pack byte scalars into vector 849 class PackBNode : public PackNode { 850 public: 851 PackBNode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {} 852 virtual int Opcode() const; 853 }; 854 855 //------------------------------PackSNode-------------------------------------- 856 // Pack short scalars into a vector 857 class PackSNode : public PackNode { 858 public: 859 PackSNode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {} 860 PackSNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 861 virtual int Opcode() const; 862 }; 863 864 //------------------------------PackINode-------------------------------------- 865 // Pack integer scalars into a vector 866 class PackINode : public PackNode { 867 public: 868 PackINode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {} 869 PackINode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 870 virtual int Opcode() const; 871 }; 872 873 //------------------------------PackLNode-------------------------------------- 874 // Pack long scalars into a vector 875 class PackLNode : public PackNode { 876 public: 877 PackLNode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {} 878 PackLNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 879 virtual int Opcode() const; 880 }; 881 882 //------------------------------Pack2LNode------------------------------------- 883 // Pack 2 long scalars into a vector 884 class Pack2LNode : public PackNode { 885 public: 886 Pack2LNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 887 virtual int Opcode() const; 888 }; 889 890 //------------------------------PackFNode-------------------------------------- 891 // Pack float scalars into vector 892 class PackFNode : public PackNode { 893 public: 894 PackFNode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {} 895 PackFNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 896 virtual int Opcode() const; 897 }; 898 899 //------------------------------PackDNode-------------------------------------- 900 // Pack double scalars into a vector 901 class PackDNode : public PackNode { 902 public: 903 PackDNode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {} 904 PackDNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 905 virtual int Opcode() const; 906 }; 907 908 //------------------------------Pack2DNode------------------------------------- 909 // Pack 2 double scalars into a vector 910 class Pack2DNode : public PackNode { 911 public: 912 Pack2DNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {} 913 virtual int Opcode() const; 914 }; 915 916 917 class VectorLoadConstNode : public VectorNode { 918 public: 919 VectorLoadConstNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {} 920 virtual int Opcode() const; 921 }; 922 923 //========================Extract_Scalar_from_Vector=========================== 924 925 //------------------------------ExtractNode------------------------------------ 926 // Extract a scalar from a vector at position "pos" 927 class ExtractNode : public Node { 928 public: 929 ExtractNode(Node* src, ConINode* pos) : Node(NULL, src, (Node*)pos) { 930 assert(in(2)->get_int() >= 0, "positive constants"); 931 } 932 virtual int Opcode() const; 933 uint pos() const { return in(2)->get_int(); } 934 935 static Node* make(Node* v, uint position, BasicType bt); 936 static int opcode(BasicType bt); 937 }; 938 939 //------------------------------ExtractBNode----------------------------------- 940 // Extract a byte from a vector at position "pos" 941 class ExtractBNode : public ExtractNode { 942 public: 943 ExtractBNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 944 virtual int Opcode() const; 945 virtual const Type *bottom_type() const { return TypeInt::INT; } 946 virtual uint ideal_reg() const { return Op_RegI; } 947 }; 948 949 //------------------------------ExtractUBNode---------------------------------- 950 // Extract a boolean from a vector at position "pos" 951 class ExtractUBNode : public ExtractNode { 952 public: 953 ExtractUBNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 954 virtual int Opcode() const; 955 virtual const Type *bottom_type() const { return TypeInt::INT; } 956 virtual uint ideal_reg() const { return Op_RegI; } 957 }; 958 959 //------------------------------ExtractCNode----------------------------------- 960 // Extract a char from a vector at position "pos" 961 class ExtractCNode : public ExtractNode { 962 public: 963 ExtractCNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 964 virtual int Opcode() const; 965 virtual const Type *bottom_type() const { return TypeInt::CHAR; } 966 virtual uint ideal_reg() const { return Op_RegI; } 967 }; 968 969 //------------------------------ExtractSNode----------------------------------- 970 // Extract a short from a vector at position "pos" 971 class ExtractSNode : public ExtractNode { 972 public: 973 ExtractSNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 974 virtual int Opcode() const; 975 virtual const Type *bottom_type() const { return TypeInt::SHORT; } 976 virtual uint ideal_reg() const { return Op_RegI; } 977 }; 978 979 //------------------------------ExtractINode----------------------------------- 980 // Extract an int from a vector at position "pos" 981 class ExtractINode : public ExtractNode { 982 public: 983 ExtractINode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 984 virtual int Opcode() const; 985 virtual const Type *bottom_type() const { return TypeInt::INT; } 986 virtual uint ideal_reg() const { return Op_RegI; } 987 }; 988 989 //------------------------------ExtractLNode----------------------------------- 990 // Extract a long from a vector at position "pos" 991 class ExtractLNode : public ExtractNode { 992 public: 993 ExtractLNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 994 virtual int Opcode() const; 995 virtual const Type *bottom_type() const { return TypeLong::LONG; } 996 virtual uint ideal_reg() const { return Op_RegL; } 997 }; 998 999 //------------------------------ExtractFNode----------------------------------- 1000 // Extract a float from a vector at position "pos" 1001 class ExtractFNode : public ExtractNode { 1002 public: 1003 ExtractFNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 1004 virtual int Opcode() const; 1005 virtual const Type *bottom_type() const { return Type::FLOAT; } 1006 virtual uint ideal_reg() const { return Op_RegF; } 1007 }; 1008 1009 //------------------------------ExtractDNode----------------------------------- 1010 // Extract a double from a vector at position "pos" 1011 class ExtractDNode : public ExtractNode { 1012 public: 1013 ExtractDNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {} 1014 virtual int Opcode() const; 1015 virtual const Type *bottom_type() const { return Type::DOUBLE; } 1016 virtual uint ideal_reg() const { return Op_RegD; } 1017 }; 1018 1019 //------------------------------SetVectMaskINode------------------------------- 1020 // Provide a mask for a vector predicate machine 1021 class SetVectMaskINode : public Node { 1022 public: 1023 SetVectMaskINode(Node *c, Node *in1) : Node(c, in1) {} 1024 virtual int Opcode() const; 1025 const Type *bottom_type() const { return TypeInt::INT; } 1026 virtual uint ideal_reg() const { return Op_RegI; } 1027 virtual const Type *Value(PhaseGVN *phase) const { return TypeInt::INT; } 1028 }; 1029 1030 //------------------------------MacroLogicVNode------------------------------- 1031 // Vector logical operations packing node. 1032 class MacroLogicVNode : public VectorNode { 1033 private: 1034 MacroLogicVNode(Node* in1, Node* in2, Node* in3, Node* fn, const TypeVect* vt) 1035 : VectorNode(in1, in2, in3, fn, vt) {} 1036 1037 public: 1038 virtual int Opcode() const; 1039 1040 static MacroLogicVNode* make(PhaseGVN& igvn, Node* in1, Node* in2, Node* in3, uint truth_table, const TypeVect* vt); 1041 }; 1042 1043 class VectorMaskCmpNode : public VectorNode { 1044 private: 1045 BoolTest::mask _predicate; 1046 1047 protected: 1048 uint size_of() const { return sizeof(*this); } 1049 1050 public: 1051 VectorMaskCmpNode(BoolTest::mask predicate, Node* in1, Node* in2, ConINode* predicate_node, const TypeVect* vt) : 1052 VectorNode(in1, in2, predicate_node, vt), 1053 _predicate(predicate) { 1054 assert(in1->bottom_type()->is_vect()->element_basic_type() == in2->bottom_type()->is_vect()->element_basic_type(), 1055 "VectorMaskCmp inputs must have same type for elements"); 1056 assert(in1->bottom_type()->is_vect()->length() == in2->bottom_type()->is_vect()->length(), 1057 "VectorMaskCmp inputs must have same number of elements"); 1058 init_class_id(Class_VectorMaskCmp); 1059 } 1060 1061 virtual int Opcode() const; 1062 virtual uint hash() const { return VectorNode::hash() + _predicate; } 1063 virtual bool cmp( const Node &n ) const { 1064 return VectorNode::cmp(n) && _predicate == ((VectorMaskCmpNode&)n)._predicate; 1065 } 1066 BoolTest::mask get_predicate() { return _predicate; } 1067 #ifndef PRODUCT 1068 virtual void dump_spec(outputStream *st) const; 1069 #endif // !PRODUCT 1070 }; 1071 1072 // Used to wrap other vector nodes in order to add masking functionality. 1073 class VectorMaskWrapperNode : public VectorNode { 1074 public: 1075 VectorMaskWrapperNode(Node* vector, Node* mask) 1076 : VectorNode(vector, mask, vector->bottom_type()->is_vect()) { 1077 assert(mask->is_VectorMaskCmp(), "VectorMaskWrapper requires that second argument be a mask"); 1078 } 1079 1080 virtual int Opcode() const; 1081 Node* vector_val() const { return in(1); } 1082 Node* vector_mask() const { return in(2); } 1083 }; 1084 1085 class VectorTestNode : public Node { 1086 private: 1087 BoolTest::mask _predicate; 1088 1089 protected: 1090 uint size_of() const { return sizeof(*this); } 1091 1092 public: 1093 VectorTestNode( Node *in1, Node *in2, BoolTest::mask predicate) : Node(NULL, in1, in2), _predicate(predicate) { 1094 assert(in1->is_Vector() || in1->is_LoadVector(), "must be vector"); 1095 assert(in2->is_Vector() || in2->is_LoadVector(), "must be vector"); 1096 assert(in1->bottom_type()->is_vect()->element_basic_type() == in2->bottom_type()->is_vect()->element_basic_type(), 1097 "same type elements are needed"); 1098 assert(in1->bottom_type()->is_vect()->length() == in2->bottom_type()->is_vect()->length(), 1099 "same number of elements is needed"); 1100 } 1101 virtual int Opcode() const; 1102 virtual uint hash() const { return Node::hash() + _predicate; } 1103 virtual bool cmp( const Node &n ) const { 1104 return Node::cmp(n) && _predicate == ((VectorTestNode&)n)._predicate; 1105 } 1106 virtual const Type *bottom_type() const { return TypeInt::BOOL; } 1107 virtual uint ideal_reg() const { return Op_RegI; } // TODO Should be RegFlags but due to missing comparison flags for BoolTest 1108 // in middle-end, we make it boolean result directly. 1109 BoolTest::mask get_predicate() const { return _predicate; } 1110 }; 1111 1112 class VectorBlendNode : public VectorNode { 1113 public: 1114 VectorBlendNode(Node* vec1, Node* vec2, Node* mask) 1115 : VectorNode(vec1, vec2, mask, vec1->bottom_type()->is_vect()) { 1116 // assert(mask->is_VectorMask(), "VectorBlendNode requires that third argument be a mask"); 1117 } 1118 1119 virtual int Opcode() const; 1120 Node* vec1() const { return in(1); } 1121 Node* vec2() const { return in(2); } 1122 Node* vec_mask() const { return in(3); } 1123 }; 1124 1125 class VectorRearrangeNode : public VectorNode { 1126 public: 1127 VectorRearrangeNode(Node* vec1, Node* shuffle) 1128 : VectorNode(vec1, shuffle, vec1->bottom_type()->is_vect()) { 1129 // assert(mask->is_VectorMask(), "VectorBlendNode requires that third argument be a mask"); 1130 } 1131 1132 virtual int Opcode() const; 1133 Node* vec1() const { return in(1); } 1134 Node* vec_shuffle() const { return in(2); } 1135 }; 1136 1137 1138 class VectorLoadMaskNode : public VectorNode { 1139 public: 1140 VectorLoadMaskNode(Node* in, const TypeVect* vt) 1141 : VectorNode(in, vt) { 1142 assert(in->is_LoadVector(), "expected load vector"); 1143 assert(in->as_LoadVector()->vect_type()->element_basic_type() == T_BOOLEAN, "must be boolean"); 1144 } 1145 1146 virtual int Opcode() const; 1147 }; 1148 1149 class VectorLoadShuffleNode : public VectorNode { 1150 public: 1151 VectorLoadShuffleNode(Node* in, const TypeVect* vt) 1152 : VectorNode(in, vt) { 1153 assert(in->is_LoadVector(), "expected load vector"); 1154 assert(in->as_LoadVector()->vect_type()->element_basic_type() == T_BYTE, "must be BYTE"); 1155 } 1156 1157 int GetOutShuffleSize() const { return type2aelembytes(vect_type()->element_basic_type()); } 1158 virtual int Opcode() const; 1159 }; 1160 1161 class VectorStoreMaskNode : public VectorNode { 1162 protected: 1163 VectorStoreMaskNode(Node* in1, ConINode* in2, const TypeVect* vt) 1164 : VectorNode(in1, in2, vt) { } 1165 1166 public: 1167 virtual int Opcode() const; 1168 1169 static VectorStoreMaskNode* make(PhaseGVN& gvn, Node* in, BasicType in_type, uint num_elem); 1170 }; 1171 1172 // This is intended for use as a simple reinterpret node that has no cast. 1173 class VectorReinterpretNode : public VectorNode { 1174 private: 1175 const TypeVect* _src_vt; 1176 protected: 1177 uint size_of() const { return sizeof(*this); } 1178 public: 1179 VectorReinterpretNode(Node* in, const TypeVect* src_vt, const TypeVect* dst_vt) 1180 : VectorNode(in, dst_vt), _src_vt(src_vt) { } 1181 1182 virtual uint hash() const { return VectorNode::hash() + _src_vt->hash(); } 1183 virtual bool cmp( const Node &n ) const { 1184 return VectorNode::cmp(n) && !Type::cmp(_src_vt,((VectorReinterpretNode&)n)._src_vt); 1185 } 1186 virtual Node *Identity(PhaseGVN *phase); 1187 1188 virtual int Opcode() const; 1189 }; 1190 1191 class VectorCastNode : public VectorNode { 1192 public: 1193 VectorCastNode(Node* in, const TypeVect* vt) : VectorNode(in, vt) {} 1194 virtual int Opcode() const; 1195 1196 static VectorCastNode* make(int vopc, Node* n1, BasicType bt, uint vlen); 1197 static int opcode(BasicType bt); 1198 static bool implemented(BasicType bt, uint vlen); 1199 }; 1200 1201 class VectorCastB2XNode : public VectorCastNode { 1202 public: 1203 VectorCastB2XNode(Node* in, const TypeVect* vt) : VectorCastNode(in, vt) { 1204 assert(in->bottom_type()->is_vect()->element_basic_type() == T_BYTE, "must be byte"); 1205 } 1206 virtual int Opcode() const; 1207 }; 1208 1209 class VectorCastS2XNode : public VectorCastNode { 1210 public: 1211 VectorCastS2XNode(Node* in, const TypeVect* vt) : VectorCastNode(in, vt) { 1212 assert(in->bottom_type()->is_vect()->element_basic_type() == T_SHORT, "must be short"); 1213 } 1214 virtual int Opcode() const; 1215 }; 1216 1217 class VectorCastI2XNode : public VectorCastNode { 1218 public: 1219 VectorCastI2XNode(Node* in, const TypeVect* vt) : VectorCastNode(in, vt) { 1220 assert(in->bottom_type()->is_vect()->element_basic_type() == T_INT, "must be int"); 1221 } 1222 virtual int Opcode() const; 1223 }; 1224 1225 class VectorCastL2XNode : public VectorCastNode { 1226 public: 1227 VectorCastL2XNode(Node* in, const TypeVect* vt) : VectorCastNode(in, vt) { 1228 assert(in->bottom_type()->is_vect()->element_basic_type() == T_LONG, "must be long"); 1229 } 1230 virtual int Opcode() const; 1231 }; 1232 1233 class VectorCastF2XNode : public VectorCastNode { 1234 public: 1235 VectorCastF2XNode(Node* in, const TypeVect* vt) : VectorCastNode(in, vt) { 1236 assert(in->bottom_type()->is_vect()->element_basic_type() == T_FLOAT, "must be float"); 1237 } 1238 virtual int Opcode() const; 1239 }; 1240 1241 class VectorCastD2XNode : public VectorCastNode { 1242 public: 1243 VectorCastD2XNode(Node* in, const TypeVect* vt) : VectorCastNode(in, vt) { 1244 assert(in->bottom_type()->is_vect()->element_basic_type() == T_DOUBLE, "must be double"); 1245 } 1246 virtual int Opcode() const; 1247 }; 1248 1249 class VectorInsertNode : public VectorNode { 1250 public: 1251 VectorInsertNode(Node* vsrc, Node* new_val, ConINode* pos, const TypeVect* vt) : VectorNode(vsrc, new_val, (Node*)pos, vt) { 1252 assert(pos->get_int() >= 0, "positive constants"); 1253 assert(pos->get_int() < (int)vt->length(), "index must be less than vector length"); 1254 assert(Type::cmp(vt, vsrc->bottom_type()) == 0, "input and output must be same type"); 1255 } 1256 virtual int Opcode() const; 1257 uint pos() const { return in(3)->get_int(); } 1258 1259 static Node* make(Node* vec, Node* new_val, int position); 1260 }; 1261 1262 class VectorBoxNode : public Node { 1263 private: 1264 const TypeInstPtr* const _box_type; 1265 const TypeVect* const _vec_type; 1266 public: 1267 enum { 1268 Box = 1, 1269 Value = 2 1270 }; 1271 VectorBoxNode(Compile* C, Node* box, Node* val, 1272 const TypeInstPtr* box_type, const TypeVect* vt) 1273 : Node(NULL, box, val), _box_type(box_type), _vec_type(vt) { 1274 init_flags(Flag_is_macro); 1275 C->add_macro_node(this); 1276 } 1277 1278 const TypeInstPtr* box_type() const { assert(_box_type != NULL, ""); return _box_type; }; 1279 const TypeVect* vec_type() const { assert(_vec_type != NULL, ""); return _vec_type; }; 1280 1281 virtual int Opcode() const; 1282 virtual const Type* bottom_type() const { return _box_type; } 1283 virtual uint ideal_reg() const { return box_type()->ideal_reg(); } 1284 virtual uint size_of() const { return sizeof(*this); } 1285 1286 static const TypeFunc* vec_box_type(const TypeInstPtr* box_type); 1287 }; 1288 1289 class VectorBoxAllocateNode : public CallStaticJavaNode { 1290 public: 1291 VectorBoxAllocateNode(Compile* C, const TypeInstPtr* vbox_type) 1292 : CallStaticJavaNode(C, VectorBoxNode::vec_box_type(vbox_type), NULL, NULL, -1) { 1293 init_flags(Flag_is_macro); 1294 C->add_macro_node(this); 1295 } 1296 1297 virtual int Opcode() const; 1298 #ifndef PRODUCT 1299 virtual void dump_spec(outputStream *st) const; 1300 #endif // !PRODUCT 1301 }; 1302 1303 class VectorUnboxNode : public VectorNode { 1304 private: 1305 bool _shuffle_to_vector; 1306 protected: 1307 uint size_of() const { return sizeof(*this); } 1308 public: 1309 VectorUnboxNode(Compile* C, const TypeVect* vec_type, Node* obj, Node* mem, bool shuffle_to_vector) 1310 : VectorNode(mem, obj, vec_type) { 1311 _shuffle_to_vector = shuffle_to_vector; 1312 init_flags(Flag_is_macro); 1313 C->add_macro_node(this); 1314 } 1315 1316 virtual int Opcode() const; 1317 Node* obj() const { return in(2); } 1318 Node* mem() const { return in(1); } 1319 virtual Node *Identity(PhaseGVN *phase); 1320 bool is_shuffle_to_vector() { return _shuffle_to_vector; } 1321 }; 1322 1323 #endif // SHARE_OPTO_VECTORNODE_HPP