22 */ |
22 */ |
23 |
23 |
24 |
24 |
25 package org.graalvm.compiler.lir.amd64.vector; |
25 package org.graalvm.compiler.lir.amd64.vector; |
26 |
26 |
27 import jdk.vm.ci.meta.AllocatableValue; |
|
28 import jdk.vm.ci.meta.Value; |
|
29 import org.graalvm.compiler.asm.amd64.AMD64Address; |
|
30 import org.graalvm.compiler.asm.amd64.AMD64VectorAssembler; |
|
31 import org.graalvm.compiler.asm.amd64.AVXKind; |
|
32 import org.graalvm.compiler.lir.LIRFrameState; |
|
33 import org.graalvm.compiler.lir.LIRInstructionClass; |
|
34 import org.graalvm.compiler.lir.Opcode; |
|
35 import org.graalvm.compiler.lir.amd64.AMD64AddressValue; |
|
36 import org.graalvm.compiler.lir.asm.CompilationResultBuilder; |
|
37 |
|
38 import static jdk.vm.ci.code.ValueUtil.asRegister; |
27 import static jdk.vm.ci.code.ValueUtil.asRegister; |
39 import static jdk.vm.ci.code.ValueUtil.isRegister; |
28 import static jdk.vm.ci.code.ValueUtil.isRegister; |
40 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.COMPOSITE; |
29 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.COMPOSITE; |
41 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.CONST; |
30 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.CONST; |
42 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.REG; |
31 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.REG; |
43 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.STACK; |
32 import static org.graalvm.compiler.lir.LIRInstruction.OperandFlag.STACK; |
44 import static org.graalvm.compiler.lir.LIRValueUtil.asConstant; |
33 import static org.graalvm.compiler.lir.LIRValueUtil.asConstant; |
45 import static org.graalvm.compiler.lir.LIRValueUtil.isConstantValue; |
34 import static org.graalvm.compiler.lir.LIRValueUtil.isConstantValue; |
46 |
35 |
|
36 import org.graalvm.compiler.asm.amd64.AMD64Address; |
|
37 import org.graalvm.compiler.asm.amd64.AMD64Assembler.VexRMOp; |
|
38 import org.graalvm.compiler.asm.amd64.AMD64Assembler.VexRVMOp; |
|
39 import org.graalvm.compiler.asm.amd64.AMD64MacroAssembler; |
|
40 import org.graalvm.compiler.asm.amd64.AVXKind; |
|
41 import org.graalvm.compiler.lir.LIRFrameState; |
|
42 import org.graalvm.compiler.lir.LIRInstructionClass; |
|
43 import org.graalvm.compiler.lir.Opcode; |
|
44 import org.graalvm.compiler.lir.amd64.AMD64AddressValue; |
|
45 import org.graalvm.compiler.lir.amd64.AMD64LIRInstruction; |
|
46 import org.graalvm.compiler.lir.asm.CompilationResultBuilder; |
|
47 |
|
48 import jdk.vm.ci.meta.AllocatableValue; |
|
49 import jdk.vm.ci.meta.Value; |
|
50 |
47 public class AMD64VectorUnary { |
51 public class AMD64VectorUnary { |
48 |
52 |
49 public static final class AVXUnaryOp extends AMD64VectorLIRInstruction { |
53 public static final class AVXUnaryOp extends AMD64LIRInstruction { |
50 public static final LIRInstructionClass<AVXUnaryOp> TYPE = LIRInstructionClass.create(AVXUnaryOp.class); |
54 public static final LIRInstructionClass<AVXUnaryOp> TYPE = LIRInstructionClass.create(AVXUnaryOp.class); |
51 |
55 |
52 @Opcode private final AMD64VectorAssembler.VexRMOp opcode; |
56 @Opcode private final VexRMOp opcode; |
53 private final AVXKind.AVXSize size; |
57 private final AVXKind.AVXSize size; |
54 |
58 |
55 @Def({REG}) protected AllocatableValue result; |
59 @Def({REG}) protected AllocatableValue result; |
56 @Use({REG, STACK}) protected AllocatableValue input; |
60 @Use({REG, STACK}) protected AllocatableValue input; |
57 |
61 |
58 public AVXUnaryOp(AMD64VectorAssembler.VexRMOp opcode, AVXKind.AVXSize size, AllocatableValue result, AllocatableValue input) { |
62 public AVXUnaryOp(VexRMOp opcode, AVXKind.AVXSize size, AllocatableValue result, AllocatableValue input) { |
59 super(TYPE); |
63 super(TYPE); |
60 this.opcode = opcode; |
64 this.opcode = opcode; |
61 this.size = size; |
65 this.size = size; |
62 this.result = result; |
66 this.result = result; |
63 this.input = input; |
67 this.input = input; |
64 } |
68 } |
65 |
69 |
66 @Override |
70 @Override |
67 public void emitCode(CompilationResultBuilder crb, AMD64VectorAssembler vasm) { |
71 public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) { |
68 if (isRegister(input)) { |
72 if (isRegister(input)) { |
69 opcode.emit(vasm, size, asRegister(result), asRegister(input)); |
73 opcode.emit(masm, size, asRegister(result), asRegister(input)); |
70 } else { |
74 } else { |
71 opcode.emit(vasm, size, asRegister(result), (AMD64Address) crb.asAddress(input)); |
75 opcode.emit(masm, size, asRegister(result), (AMD64Address) crb.asAddress(input)); |
72 } |
76 } |
73 } |
77 } |
74 } |
78 } |
75 |
79 |
76 public static final class AVXUnaryMemoryOp extends AMD64VectorLIRInstruction { |
80 public static final class AVXUnaryMemoryOp extends AMD64LIRInstruction { |
77 public static final LIRInstructionClass<AVXUnaryMemoryOp> TYPE = LIRInstructionClass.create(AVXUnaryMemoryOp.class); |
81 public static final LIRInstructionClass<AVXUnaryMemoryOp> TYPE = LIRInstructionClass.create(AVXUnaryMemoryOp.class); |
78 |
82 |
79 @Opcode private final AMD64VectorAssembler.VexRMOp opcode; |
83 @Opcode private final VexRMOp opcode; |
80 private final AVXKind.AVXSize size; |
84 private final AVXKind.AVXSize size; |
81 |
85 |
82 @Def({REG}) protected AllocatableValue result; |
86 @Def({REG}) protected AllocatableValue result; |
83 @Use({COMPOSITE}) protected AMD64AddressValue input; |
87 @Use({COMPOSITE}) protected AMD64AddressValue input; |
84 @State protected LIRFrameState state; |
88 @State protected LIRFrameState state; |
85 |
89 |
86 public AVXUnaryMemoryOp(AMD64VectorAssembler.VexRMOp opcode, AVXKind.AVXSize size, AllocatableValue result, AMD64AddressValue input, LIRFrameState state) { |
90 public AVXUnaryMemoryOp(VexRMOp opcode, AVXKind.AVXSize size, AllocatableValue result, AMD64AddressValue input, LIRFrameState state) { |
87 super(TYPE); |
91 super(TYPE); |
88 this.opcode = opcode; |
92 this.opcode = opcode; |
89 this.size = size; |
93 this.size = size; |
90 this.result = result; |
94 this.result = result; |
91 this.input = input; |
95 this.input = input; |
92 this.state = state; |
96 this.state = state; |
93 } |
97 } |
94 |
98 |
95 @Override |
99 @Override |
96 public void emitCode(CompilationResultBuilder crb, AMD64VectorAssembler vasm) { |
100 public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) { |
97 if (state != null) { |
101 if (state != null) { |
98 crb.recordImplicitException(vasm.position(), state); |
102 crb.recordImplicitException(masm.position(), state); |
99 } |
103 } |
100 opcode.emit(vasm, size, asRegister(result), input.toAddress()); |
104 opcode.emit(masm, size, asRegister(result), input.toAddress()); |
101 } |
105 } |
102 } |
106 } |
103 |
107 |
104 public static final class AVXBroadcastOp extends AMD64VectorLIRInstruction { |
108 public static final class AVXBroadcastOp extends AMD64LIRInstruction { |
105 public static final LIRInstructionClass<AVXBroadcastOp> TYPE = LIRInstructionClass.create(AVXBroadcastOp.class); |
109 public static final LIRInstructionClass<AVXBroadcastOp> TYPE = LIRInstructionClass.create(AVXBroadcastOp.class); |
106 |
110 |
107 @Opcode private final AMD64VectorAssembler.VexRMOp opcode; |
111 @Opcode private final VexRMOp opcode; |
108 private final AVXKind.AVXSize size; |
112 private final AVXKind.AVXSize size; |
109 |
113 |
110 @Def({REG}) protected AllocatableValue result; |
114 @Def({REG}) protected AllocatableValue result; |
111 @Use({REG, STACK, CONST}) protected Value input; |
115 @Use({REG, STACK, CONST}) protected Value input; |
112 |
116 |
113 public AVXBroadcastOp(AMD64VectorAssembler.VexRMOp opcode, AVXKind.AVXSize size, AllocatableValue result, Value input) { |
117 public AVXBroadcastOp(VexRMOp opcode, AVXKind.AVXSize size, AllocatableValue result, Value input) { |
114 super(TYPE); |
118 super(TYPE); |
115 this.opcode = opcode; |
119 this.opcode = opcode; |
116 this.size = size; |
120 this.size = size; |
117 this.result = result; |
121 this.result = result; |
118 this.input = input; |
122 this.input = input; |
119 } |
123 } |
120 |
124 |
121 @Override |
125 @Override |
122 public void emitCode(CompilationResultBuilder crb, AMD64VectorAssembler vasm) { |
126 public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) { |
123 if (isRegister(input)) { |
127 if (isRegister(input)) { |
124 opcode.emit(vasm, size, asRegister(result), asRegister(input)); |
128 opcode.emit(masm, size, asRegister(result), asRegister(input)); |
125 } else if (isConstantValue(input)) { |
129 } else if (isConstantValue(input)) { |
126 int align = input.getPlatformKind().getSizeInBytes(); |
130 int align = input.getPlatformKind().getSizeInBytes(); |
127 AMD64Address address = (AMD64Address) crb.recordDataReferenceInCode(asConstant(input), align); |
131 AMD64Address address = (AMD64Address) crb.recordDataReferenceInCode(asConstant(input), align); |
128 opcode.emit(vasm, size, asRegister(result), address); |
132 opcode.emit(masm, size, asRegister(result), address); |
129 } else { |
133 } else { |
130 opcode.emit(vasm, size, asRegister(result), (AMD64Address) crb.asAddress(input)); |
134 opcode.emit(masm, size, asRegister(result), (AMD64Address) crb.asAddress(input)); |
131 } |
135 } |
132 } |
136 } |
133 } |
137 } |
134 |
138 |
135 public static final class AVXConvertMemoryOp extends AMD64VectorLIRInstruction { |
139 public static final class AVXConvertMemoryOp extends AMD64LIRInstruction { |
136 public static final LIRInstructionClass<AVXConvertMemoryOp> TYPE = LIRInstructionClass.create(AVXConvertMemoryOp.class); |
140 public static final LIRInstructionClass<AVXConvertMemoryOp> TYPE = LIRInstructionClass.create(AVXConvertMemoryOp.class); |
137 |
141 |
138 @Opcode private final AMD64VectorAssembler.VexRVMOp opcode; |
142 @Opcode private final VexRVMOp opcode; |
139 private final AVXKind.AVXSize size; |
143 private final AVXKind.AVXSize size; |
140 |
144 |
141 @Def({REG}) protected AllocatableValue result; |
145 @Def({REG}) protected AllocatableValue result; |
142 @Use({COMPOSITE}) protected AMD64AddressValue input; |
146 @Use({COMPOSITE}) protected AMD64AddressValue input; |
143 @State protected LIRFrameState state; |
147 @State protected LIRFrameState state; |
144 |
148 |
145 public AVXConvertMemoryOp(AMD64VectorAssembler.VexRVMOp opcode, AVXKind.AVXSize size, AllocatableValue result, AMD64AddressValue input, LIRFrameState state) { |
149 public AVXConvertMemoryOp(VexRVMOp opcode, AVXKind.AVXSize size, AllocatableValue result, AMD64AddressValue input, LIRFrameState state) { |
146 super(TYPE); |
150 super(TYPE); |
147 this.opcode = opcode; |
151 this.opcode = opcode; |
148 this.size = size; |
152 this.size = size; |
149 this.result = result; |
153 this.result = result; |
150 this.input = input; |
154 this.input = input; |
151 this.state = state; |
155 this.state = state; |
152 } |
156 } |
153 |
157 |
154 @Override |
158 @Override |
155 public void emitCode(CompilationResultBuilder crb, AMD64VectorAssembler vasm) { |
159 public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) { |
156 if (state != null) { |
160 if (state != null) { |
157 crb.recordImplicitException(vasm.position(), state); |
161 crb.recordImplicitException(masm.position(), state); |
158 } |
162 } |
159 opcode.emit(vasm, size, asRegister(result), asRegister(result), input.toAddress()); |
163 opcode.emit(masm, size, asRegister(result), asRegister(result), input.toAddress()); |
160 } |
164 } |
161 } |
165 } |
162 |
166 |
163 public static final class AVXConvertOp extends AMD64VectorLIRInstruction { |
167 public static final class AVXConvertOp extends AMD64LIRInstruction { |
164 public static final LIRInstructionClass<AVXConvertOp> TYPE = LIRInstructionClass.create(AVXConvertOp.class); |
168 public static final LIRInstructionClass<AVXConvertOp> TYPE = LIRInstructionClass.create(AVXConvertOp.class); |
165 |
169 |
166 @Opcode private final AMD64VectorAssembler.VexRVMOp opcode; |
170 @Opcode private final VexRVMOp opcode; |
167 @Def({REG}) protected AllocatableValue result; |
171 @Def({REG}) protected AllocatableValue result; |
168 @Use({REG, STACK}) protected AllocatableValue input; |
172 @Use({REG, STACK}) protected AllocatableValue input; |
169 |
173 |
170 public AVXConvertOp(AMD64VectorAssembler.VexRVMOp opcode, AllocatableValue result, AllocatableValue input) { |
174 public AVXConvertOp(VexRVMOp opcode, AllocatableValue result, AllocatableValue input) { |
171 super(TYPE); |
175 super(TYPE); |
172 this.opcode = opcode; |
176 this.opcode = opcode; |
173 this.result = result; |
177 this.result = result; |
174 this.input = input; |
178 this.input = input; |
175 } |
179 } |
176 |
180 |
177 @Override |
181 @Override |
178 public void emitCode(CompilationResultBuilder crb, AMD64VectorAssembler vasm) { |
182 public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) { |
179 if (isRegister(input)) { |
183 if (isRegister(input)) { |
180 if (!asRegister(input).equals(asRegister(result))) { |
184 if (!asRegister(input).equals(asRegister(result))) { |
181 // clear result register to avoid unnecessary dependency |
185 // clear result register to avoid unnecessary dependency |
182 AMD64VectorAssembler.VexRVMOp.VXORPD.emit(vasm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), asRegister(result)); |
186 VexRVMOp.VXORPD.emit(masm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), asRegister(result)); |
183 } |
187 } |
184 opcode.emit(vasm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), asRegister(input)); |
188 opcode.emit(masm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), asRegister(input)); |
185 } else { |
189 } else { |
186 AMD64VectorAssembler.VexRVMOp.VXORPD.emit(vasm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), asRegister(result)); |
190 VexRVMOp.VXORPD.emit(masm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), asRegister(result)); |
187 opcode.emit(vasm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), (AMD64Address) crb.asAddress(input)); |
191 opcode.emit(masm, AVXKind.AVXSize.XMM, asRegister(result), asRegister(result), (AMD64Address) crb.asAddress(input)); |
188 } |
192 } |
189 } |
193 } |
190 } |
194 } |
191 } |
195 } |