vectornode.hpp revision 3699:859c45fb8cea
1/*
2 * Copyright (c) 2007, 2012, 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_VM_OPTO_VECTORNODE_HPP
25#define SHARE_VM_OPTO_VECTORNODE_HPP
26
27#include "opto/matcher.hpp"
28#include "opto/memnode.hpp"
29#include "opto/node.hpp"
30#include "opto/opcodes.hpp"
31
32//------------------------------VectorNode-------------------------------------
33// Vector Operation
34class VectorNode : public TypeNode {
35 public:
36
37  VectorNode(Node* n1, const TypeVect* vt) : TypeNode(vt, 2) {
38    init_class_id(Class_Vector);
39    init_req(1, n1);
40  }
41  VectorNode(Node* n1, Node* n2, const TypeVect* vt) : TypeNode(vt, 3) {
42    init_class_id(Class_Vector);
43    init_req(1, n1);
44    init_req(2, n2);
45  }
46
47  const TypeVect* vect_type() const { return type()->is_vect(); }
48  uint length() const { return vect_type()->length(); } // Vector length
49  uint length_in_bytes() const { return vect_type()->length_in_bytes(); }
50
51  virtual int Opcode() const;
52
53  virtual uint ideal_reg() const { return Matcher::vector_ideal_reg(vect_type()->length_in_bytes()); }
54
55  static VectorNode* scalar2vector(Compile* C, Node* s, uint vlen, const Type* opd_t);
56  static VectorNode* shift_count(Compile* C, Node* shift, Node* cnt, uint vlen, BasicType bt);
57  static VectorNode* make(Compile* C, int opc, Node* n1, Node* n2, uint vlen, BasicType bt);
58
59  static int  opcode(int opc, BasicType bt);
60  static bool implemented(int opc, uint vlen, BasicType bt);
61  static bool is_shift(Node* n);
62  static bool is_invariant_vector(Node* n);
63  // [Start, end) half-open range defining which operands are vectors
64  static void vector_operands(Node* n, uint* start, uint* end);
65};
66
67//===========================Vector=ALU=Operations=============================
68
69//------------------------------AddVBNode--------------------------------------
70// Vector add byte
71class AddVBNode : public VectorNode {
72 public:
73  AddVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
74  virtual int Opcode() const;
75};
76
77//------------------------------AddVSNode--------------------------------------
78// Vector add char/short
79class AddVSNode : public VectorNode {
80 public:
81  AddVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
82  virtual int Opcode() const;
83};
84
85//------------------------------AddVINode--------------------------------------
86// Vector add int
87class AddVINode : public VectorNode {
88 public:
89  AddVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
90  virtual int Opcode() const;
91};
92
93//------------------------------AddVLNode--------------------------------------
94// Vector add long
95class AddVLNode : public VectorNode {
96 public:
97  AddVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
98  virtual int Opcode() const;
99};
100
101//------------------------------AddVFNode--------------------------------------
102// Vector add float
103class AddVFNode : public VectorNode {
104 public:
105  AddVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
106  virtual int Opcode() const;
107};
108
109//------------------------------AddVDNode--------------------------------------
110// Vector add double
111class AddVDNode : public VectorNode {
112 public:
113  AddVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
114  virtual int Opcode() const;
115};
116
117//------------------------------SubVBNode--------------------------------------
118// Vector subtract byte
119class SubVBNode : public VectorNode {
120 public:
121  SubVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
122  virtual int Opcode() const;
123};
124
125//------------------------------SubVSNode--------------------------------------
126// Vector subtract short
127class SubVSNode : public VectorNode {
128 public:
129  SubVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
130  virtual int Opcode() const;
131};
132
133//------------------------------SubVINode--------------------------------------
134// Vector subtract int
135class SubVINode : public VectorNode {
136 public:
137  SubVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
138  virtual int Opcode() const;
139};
140
141//------------------------------SubVLNode--------------------------------------
142// Vector subtract long
143class SubVLNode : public VectorNode {
144 public:
145  SubVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
146  virtual int Opcode() const;
147};
148
149//------------------------------SubVFNode--------------------------------------
150// Vector subtract float
151class SubVFNode : public VectorNode {
152 public:
153  SubVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
154  virtual int Opcode() const;
155};
156
157//------------------------------SubVDNode--------------------------------------
158// Vector subtract double
159class SubVDNode : public VectorNode {
160 public:
161  SubVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
162  virtual int Opcode() const;
163};
164
165//------------------------------MulVSNode--------------------------------------
166// Vector multiply short
167class MulVSNode : public VectorNode {
168 public:
169  MulVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
170  virtual int Opcode() const;
171};
172
173//------------------------------MulVINode--------------------------------------
174// Vector multiply int
175class MulVINode : public VectorNode {
176 public:
177  MulVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
178  virtual int Opcode() const;
179};
180
181//------------------------------MulVFNode--------------------------------------
182// Vector multiply float
183class MulVFNode : public VectorNode {
184 public:
185  MulVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
186  virtual int Opcode() const;
187};
188
189//------------------------------MulVDNode--------------------------------------
190// Vector multiply double
191class MulVDNode : public VectorNode {
192 public:
193  MulVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
194  virtual int Opcode() const;
195};
196
197//------------------------------DivVFNode--------------------------------------
198// Vector divide float
199class DivVFNode : public VectorNode {
200 public:
201  DivVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
202  virtual int Opcode() const;
203};
204
205//------------------------------DivVDNode--------------------------------------
206// Vector Divide double
207class DivVDNode : public VectorNode {
208 public:
209  DivVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
210  virtual int Opcode() const;
211};
212
213//------------------------------LShiftVBNode-----------------------------------
214// Vector left shift bytes
215class LShiftVBNode : public VectorNode {
216 public:
217  LShiftVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
218  virtual int Opcode() const;
219};
220
221//------------------------------LShiftVSNode-----------------------------------
222// Vector left shift shorts
223class LShiftVSNode : public VectorNode {
224 public:
225  LShiftVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
226  virtual int Opcode() const;
227};
228
229//------------------------------LShiftVINode-----------------------------------
230// Vector left shift ints
231class LShiftVINode : public VectorNode {
232 public:
233  LShiftVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
234  virtual int Opcode() const;
235};
236
237//------------------------------LShiftVLNode-----------------------------------
238// Vector left shift longs
239class LShiftVLNode : public VectorNode {
240 public:
241  LShiftVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
242  virtual int Opcode() const;
243};
244
245//------------------------------RShiftVBNode-----------------------------------
246// Vector right arithmetic (signed) shift bytes
247class RShiftVBNode : public VectorNode {
248 public:
249  RShiftVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
250  virtual int Opcode() const;
251};
252
253//------------------------------RShiftVSNode-----------------------------------
254// Vector right arithmetic (signed) shift shorts
255class RShiftVSNode : public VectorNode {
256 public:
257  RShiftVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
258  virtual int Opcode() const;
259};
260
261//------------------------------RShiftVINode-----------------------------------
262// Vector right arithmetic (signed) shift ints
263class RShiftVINode : public VectorNode {
264 public:
265  RShiftVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
266  virtual int Opcode() const;
267};
268
269//------------------------------RShiftVLNode-----------------------------------
270// Vector right arithmetic (signed) shift longs
271class RShiftVLNode : public VectorNode {
272 public:
273  RShiftVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
274  virtual int Opcode() const;
275};
276
277//------------------------------URShiftVBNode----------------------------------
278// Vector right logical (unsigned) shift bytes
279class URShiftVBNode : public VectorNode {
280 public:
281  URShiftVBNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
282  virtual int Opcode() const;
283};
284
285//------------------------------URShiftVSNode----------------------------------
286// Vector right logical (unsigned) shift shorts
287class URShiftVSNode : public VectorNode {
288 public:
289  URShiftVSNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
290  virtual int Opcode() const;
291};
292
293//------------------------------URShiftVINode----------------------------------
294// Vector right logical (unsigned) shift ints
295class URShiftVINode : public VectorNode {
296 public:
297  URShiftVINode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
298  virtual int Opcode() const;
299};
300
301//------------------------------URShiftVLNode----------------------------------
302// Vector right logical (unsigned) shift longs
303class URShiftVLNode : public VectorNode {
304 public:
305  URShiftVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
306  virtual int Opcode() const;
307};
308
309//------------------------------LShiftCntVNode---------------------------------
310// Vector left shift count
311class LShiftCntVNode : public VectorNode {
312 public:
313  LShiftCntVNode(Node* cnt, const TypeVect* vt) : VectorNode(cnt,vt) {}
314  virtual int Opcode() const;
315  virtual uint ideal_reg() const { return Matcher::vector_shift_count_ideal_reg(vect_type()->length_in_bytes()); }
316};
317
318//------------------------------RShiftCntVNode---------------------------------
319// Vector right shift count
320class RShiftCntVNode : public VectorNode {
321 public:
322  RShiftCntVNode(Node* cnt, const TypeVect* vt) : VectorNode(cnt,vt) {}
323  virtual int Opcode() const;
324  virtual uint ideal_reg() const { return Matcher::vector_shift_count_ideal_reg(vect_type()->length_in_bytes()); }
325};
326
327
328//------------------------------AndVNode---------------------------------------
329// Vector and integer
330class AndVNode : public VectorNode {
331 public:
332  AndVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
333  virtual int Opcode() const;
334};
335
336//------------------------------OrVNode---------------------------------------
337// Vector or integer
338class OrVNode : public VectorNode {
339 public:
340  OrVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
341  virtual int Opcode() const;
342};
343
344//------------------------------XorVNode---------------------------------------
345// Vector xor integer
346class XorVNode : public VectorNode {
347 public:
348  XorVNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
349  virtual int Opcode() const;
350};
351
352//================================= M E M O R Y ===============================
353
354//------------------------------LoadVectorNode---------------------------------
355// Load Vector from memory
356class LoadVectorNode : public LoadNode {
357 public:
358  LoadVectorNode(Node* c, Node* mem, Node* adr, const TypePtr* at, const TypeVect* vt)
359    : LoadNode(c, mem, adr, at, vt) {
360    init_class_id(Class_LoadVector);
361  }
362
363  const TypeVect* vect_type() const { return type()->is_vect(); }
364  uint length() const { return vect_type()->length(); } // Vector length
365
366  virtual int Opcode() const;
367
368  virtual uint ideal_reg() const  { return Matcher::vector_ideal_reg(memory_size()); }
369  virtual BasicType memory_type() const { return T_VOID; }
370  virtual int memory_size() const { return vect_type()->length_in_bytes(); }
371
372  virtual int store_Opcode() const { return Op_StoreVector; }
373
374  static LoadVectorNode* make(Compile* C, int opc, Node* ctl, Node* mem,
375                              Node* adr, const TypePtr* atyp, uint vlen, BasicType bt);
376};
377
378//------------------------------StoreVectorNode--------------------------------
379// Store Vector to memory
380class StoreVectorNode : public StoreNode {
381 public:
382  StoreVectorNode(Node* c, Node* mem, Node* adr, const TypePtr* at, Node* val)
383    : StoreNode(c, mem, adr, at, val) {
384    assert(val->is_Vector() || val->is_LoadVector(), "sanity");
385    init_class_id(Class_StoreVector);
386  }
387
388  const TypeVect* vect_type() const { return in(MemNode::ValueIn)->bottom_type()->is_vect(); }
389  uint length() const { return vect_type()->length(); } // Vector length
390
391  virtual int Opcode() const;
392
393  virtual uint ideal_reg() const  { return Matcher::vector_ideal_reg(memory_size()); }
394  virtual BasicType memory_type() const { return T_VOID; }
395  virtual int memory_size() const { return vect_type()->length_in_bytes(); }
396
397  static StoreVectorNode* make(Compile* C, int opc, Node* ctl, Node* mem,
398                               Node* adr, const TypePtr* atyp, Node* val,
399                               uint vlen);
400};
401
402
403//=========================Promote_Scalar_to_Vector============================
404
405//------------------------------ReplicateBNode---------------------------------
406// Replicate byte scalar to be vector
407class ReplicateBNode : public VectorNode {
408 public:
409  ReplicateBNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
410  virtual int Opcode() const;
411};
412
413//------------------------------ReplicateSNode---------------------------------
414// Replicate short scalar to be vector
415class ReplicateSNode : public VectorNode {
416 public:
417  ReplicateSNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
418  virtual int Opcode() const;
419};
420
421//------------------------------ReplicateINode---------------------------------
422// Replicate int scalar to be vector
423class ReplicateINode : public VectorNode {
424 public:
425  ReplicateINode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
426  virtual int Opcode() const;
427};
428
429//------------------------------ReplicateLNode---------------------------------
430// Replicate long scalar to be vector
431class ReplicateLNode : public VectorNode {
432 public:
433  ReplicateLNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
434  virtual int Opcode() const;
435};
436
437//------------------------------ReplicateFNode---------------------------------
438// Replicate float scalar to be vector
439class ReplicateFNode : public VectorNode {
440 public:
441  ReplicateFNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
442  virtual int Opcode() const;
443};
444
445//------------------------------ReplicateDNode---------------------------------
446// Replicate double scalar to be vector
447class ReplicateDNode : public VectorNode {
448 public:
449  ReplicateDNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
450  virtual int Opcode() const;
451};
452
453//========================Pack_Scalars_into_a_Vector===========================
454
455//------------------------------PackNode---------------------------------------
456// Pack parent class (not for code generation).
457class PackNode : public VectorNode {
458 public:
459  PackNode(Node* in1, const TypeVect* vt) : VectorNode(in1, vt) {}
460  PackNode(Node* in1, Node* n2, const TypeVect* vt) : VectorNode(in1, n2, vt) {}
461  virtual int Opcode() const;
462
463  void add_opd(Node* n) {
464    add_req(n);
465  }
466
467  // Create a binary tree form for Packs. [lo, hi) (half-open) range
468  PackNode* binary_tree_pack(Compile* C, int lo, int hi);
469
470  static PackNode* make(Compile* C, Node* s, uint vlen, BasicType bt);
471};
472
473//------------------------------PackBNode--------------------------------------
474// Pack byte scalars into vector
475class PackBNode : public PackNode {
476 public:
477  PackBNode(Node* in1, const TypeVect* vt)  : PackNode(in1, vt) {}
478  virtual int Opcode() const;
479};
480
481//------------------------------PackSNode--------------------------------------
482// Pack short scalars into a vector
483class PackSNode : public PackNode {
484 public:
485  PackSNode(Node* in1, const TypeVect* vt)  : PackNode(in1, vt) {}
486  PackSNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
487  virtual int Opcode() const;
488};
489
490//------------------------------PackINode--------------------------------------
491// Pack integer scalars into a vector
492class PackINode : public PackNode {
493 public:
494  PackINode(Node* in1, const TypeVect* vt)  : PackNode(in1, vt) {}
495  PackINode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
496  virtual int Opcode() const;
497};
498
499//------------------------------PackLNode--------------------------------------
500// Pack long scalars into a vector
501class PackLNode : public PackNode {
502 public:
503  PackLNode(Node* in1, const TypeVect* vt)  : PackNode(in1, vt) {}
504  PackLNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
505  virtual int Opcode() const;
506};
507
508//------------------------------Pack2LNode-------------------------------------
509// Pack 2 long scalars into a vector
510class Pack2LNode : public PackNode {
511 public:
512  Pack2LNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
513  virtual int Opcode() const;
514};
515
516//------------------------------PackFNode--------------------------------------
517// Pack float scalars into vector
518class PackFNode : public PackNode {
519 public:
520  PackFNode(Node* in1, const TypeVect* vt)  : PackNode(in1, vt) {}
521  PackFNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
522  virtual int Opcode() const;
523};
524
525//------------------------------PackDNode--------------------------------------
526// Pack double scalars into a vector
527class PackDNode : public PackNode {
528 public:
529  PackDNode(Node* in1, const TypeVect* vt) : PackNode(in1, vt) {}
530  PackDNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
531  virtual int Opcode() const;
532};
533
534//------------------------------Pack2DNode-------------------------------------
535// Pack 2 double scalars into a vector
536class Pack2DNode : public PackNode {
537 public:
538  Pack2DNode(Node* in1, Node* in2, const TypeVect* vt) : PackNode(in1, in2, vt) {}
539  virtual int Opcode() const;
540};
541
542
543//========================Extract_Scalar_from_Vector===========================
544
545//------------------------------ExtractNode------------------------------------
546// Extract a scalar from a vector at position "pos"
547class ExtractNode : public Node {
548 public:
549  ExtractNode(Node* src, ConINode* pos) : Node(NULL, src, (Node*)pos) {
550    assert(in(2)->get_int() >= 0, "positive constants");
551  }
552  virtual int Opcode() const;
553  uint  pos() const { return in(2)->get_int(); }
554
555  static Node* make(Compile* C, Node* v, uint position, BasicType bt);
556};
557
558//------------------------------ExtractBNode-----------------------------------
559// Extract a byte from a vector at position "pos"
560class ExtractBNode : public ExtractNode {
561 public:
562  ExtractBNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
563  virtual int Opcode() const;
564  virtual const Type *bottom_type() const { return TypeInt::INT; }
565  virtual uint ideal_reg() const { return Op_RegI; }
566};
567
568//------------------------------ExtractUBNode----------------------------------
569// Extract a boolean from a vector at position "pos"
570class ExtractUBNode : public ExtractNode {
571 public:
572  ExtractUBNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
573  virtual int Opcode() const;
574  virtual const Type *bottom_type() const { return TypeInt::INT; }
575  virtual uint ideal_reg() const { return Op_RegI; }
576};
577
578//------------------------------ExtractCNode-----------------------------------
579// Extract a char from a vector at position "pos"
580class ExtractCNode : public ExtractNode {
581 public:
582  ExtractCNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
583  virtual int Opcode() const;
584  virtual const Type *bottom_type() const { return TypeInt::INT; }
585  virtual uint ideal_reg() const { return Op_RegI; }
586};
587
588//------------------------------ExtractSNode-----------------------------------
589// Extract a short from a vector at position "pos"
590class ExtractSNode : public ExtractNode {
591 public:
592  ExtractSNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
593  virtual int Opcode() const;
594  virtual const Type *bottom_type() const { return TypeInt::INT; }
595  virtual uint ideal_reg() const { return Op_RegI; }
596};
597
598//------------------------------ExtractINode-----------------------------------
599// Extract an int from a vector at position "pos"
600class ExtractINode : public ExtractNode {
601 public:
602  ExtractINode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
603  virtual int Opcode() const;
604  virtual const Type *bottom_type() const { return TypeInt::INT; }
605  virtual uint ideal_reg() const { return Op_RegI; }
606};
607
608//------------------------------ExtractLNode-----------------------------------
609// Extract a long from a vector at position "pos"
610class ExtractLNode : public ExtractNode {
611 public:
612  ExtractLNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
613  virtual int Opcode() const;
614  virtual const Type *bottom_type() const { return TypeLong::LONG; }
615  virtual uint ideal_reg() const { return Op_RegL; }
616};
617
618//------------------------------ExtractFNode-----------------------------------
619// Extract a float from a vector at position "pos"
620class ExtractFNode : public ExtractNode {
621 public:
622  ExtractFNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
623  virtual int Opcode() const;
624  virtual const Type *bottom_type() const { return Type::FLOAT; }
625  virtual uint ideal_reg() const { return Op_RegF; }
626};
627
628//------------------------------ExtractDNode-----------------------------------
629// Extract a double from a vector at position "pos"
630class ExtractDNode : public ExtractNode {
631 public:
632  ExtractDNode(Node* src, ConINode* pos) : ExtractNode(src, pos) {}
633  virtual int Opcode() const;
634  virtual const Type *bottom_type() const { return Type::DOUBLE; }
635  virtual uint ideal_reg() const { return Op_RegD; }
636};
637
638#endif // SHARE_VM_OPTO_VECTORNODE_HPP
639