1 /* 2 * Copyright (c) 2015, 2015, 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 package org.graalvm.compiler.lir.jtt; 24 25 import org.junit.Before; 26 import org.junit.Test; 27 28 import org.graalvm.compiler.core.common.LIRKind; 29 import org.graalvm.compiler.lir.Variable; 30 import org.graalvm.compiler.lir.VirtualStackSlot; 31 import org.graalvm.compiler.lir.framemap.FrameMapBuilder; 32 import org.graalvm.compiler.lir.gen.LIRGeneratorTool; 33 34 import jdk.vm.ci.meta.JavaKind; 35 import jdk.vm.ci.meta.PlatformKind; 36 import jdk.vm.ci.meta.Value; 37 import jdk.vm.ci.meta.ValueKind; 38 39 public class StackMoveTest extends LIRTest { 40 private static PlatformKind byteKind; 41 private static PlatformKind shortKind; 42 43 @Before 44 public void setUp() { 45 byteKind = getBackend().getTarget().arch.getPlatformKind(JavaKind.Byte); 46 shortKind = getBackend().getTarget().arch.getPlatformKind(JavaKind.Short); 47 } 48 49 private static class StackCopySpec extends LIRTestSpecification { 50 @Override 51 public void generate(LIRGeneratorTool gen, Value a) { 52 FrameMapBuilder frameMapBuilder = gen.getResult().getFrameMapBuilder(); 53 ValueKind<?> valueKind = getValueKind(a); 54 55 // create slots 56 VirtualStackSlot s1 = frameMapBuilder.allocateSpillSlot(valueKind); 57 VirtualStackSlot s2 = frameMapBuilder.allocateSpillSlot(valueKind); 58 59 // start emit 60 gen.emitMove(s1, a); 61 Value copy1 = gen.emitMove(s1); 62 gen.append(gen.getSpillMoveFactory().createStackMove(s2, s1)); 63 Variable result = gen.emitMove(s2); 64 // end emit 65 66 // set output and result 67 setResult(result); 68 setOutput("slotcopy", copy1); 69 setOutput("slot1", s1); 70 setOutput("slot2", s2); 71 } 72 73 protected ValueKind<?> getValueKind(Value value) { 74 return value.getValueKind(); 75 } 76 } 77 78 private static final LIRTestSpecification stackCopy = new StackCopySpec(); 79 80 /* 81 * int 82 */ 83 84 @SuppressWarnings("unused") 85 @LIRIntrinsic 86 public static int copyInt(LIRTestSpecification spec, int a) { 87 return a; 88 } 89 90 public int[] testInt(int a, int[] out) { 91 out[0] = copyInt(stackCopy, a); 92 out[1] = getOutput(stackCopy, "slotcopy", a); 93 out[2] = getOutput(stackCopy, "slot1", a); 94 out[3] = getOutput(stackCopy, "slot2", a); 95 return out; 96 } 97 98 @Test 99 public void runInt() throws Throwable { 100 runTest("testInt", Integer.MIN_VALUE, supply(() -> new int[4])); 101 runTest("testInt", -1, supply(() -> new int[4])); 102 runTest("testInt", 0, supply(() -> new int[4])); 103 runTest("testInt", 1, supply(() -> new int[4])); 104 runTest("testInt", Integer.MAX_VALUE, supply(() -> new int[4])); 105 } 106 107 /* 108 * long 109 */ 110 111 @SuppressWarnings("unused") 112 @LIRIntrinsic 113 public static long copyLong(LIRTestSpecification spec, long a) { 114 return a; 115 } 116 117 public long[] testLong(long a, long[] out) { 118 out[0] = copyLong(stackCopy, a); 119 out[1] = getOutput(stackCopy, "slotcopy", a); 120 out[2] = getOutput(stackCopy, "slot1", a); 121 out[3] = getOutput(stackCopy, "slot2", a); 122 return out; 123 } 124 125 @Test 126 public void runLong() throws Throwable { 127 runTest("testLong", Long.MIN_VALUE, supply(() -> new long[3])); 128 runTest("testLong", -1L, supply(() -> new long[3])); 129 runTest("testLong", 0L, supply(() -> new long[3])); 130 runTest("testLong", 1L, supply(() -> new long[3])); 131 runTest("testLong", Long.MAX_VALUE, supply(() -> new long[3])); 132 } 133 134 /* 135 * float 136 */ 137 138 @SuppressWarnings("unused") 139 @LIRIntrinsic 140 public static float copyFloat(LIRTestSpecification spec, float a) { 141 return a; 142 } 143 144 public float[] testFloat(float a, float[] out) { 145 out[0] = copyFloat(stackCopy, a); 146 out[1] = getOutput(stackCopy, "slotcopy", a); 147 out[2] = getOutput(stackCopy, "slot1", a); 148 out[3] = getOutput(stackCopy, "slot2", a); 149 return out; 150 } 151 152 @Test 153 public void runFloat() throws Throwable { 154 runTest("testFloat", Float.MIN_VALUE, supply(() -> new float[3])); 155 runTest("testFloat", -1f, supply(() -> new float[3])); 156 runTest("testFloat", -0.1f, supply(() -> new float[3])); 157 runTest("testFloat", 0f, supply(() -> new float[3])); 158 runTest("testFloat", 0.1f, supply(() -> new float[3])); 159 runTest("testFloat", 1f, supply(() -> new float[3])); 160 runTest("testFloat", Float.MAX_VALUE, supply(() -> new float[3])); 161 } 162 163 /* 164 * double 165 */ 166 167 @SuppressWarnings("unused") 168 @LIRIntrinsic 169 public static double copyDouble(LIRTestSpecification spec, double a) { 170 return a; 171 } 172 173 public double[] testDouble(double a, double[] out) { 174 out[0] = copyDouble(stackCopy, a); 175 out[1] = getOutput(stackCopy, "slotcopy", a); 176 out[2] = getOutput(stackCopy, "slot1", a); 177 out[3] = getOutput(stackCopy, "slot2", a); 178 return out; 179 } 180 181 @Test 182 public void runDouble() throws Throwable { 183 runTest("testDouble", Double.MIN_VALUE, supply(() -> new double[3])); 184 runTest("testDouble", -1., supply(() -> new double[3])); 185 runTest("testDouble", -0.1, supply(() -> new double[3])); 186 runTest("testDouble", 0., supply(() -> new double[3])); 187 runTest("testDouble", 0.1, supply(() -> new double[3])); 188 runTest("testDouble", 1., supply(() -> new double[3])); 189 runTest("testDouble", Double.MAX_VALUE, supply(() -> new double[3])); 190 } 191 192 /* 193 * short 194 */ 195 196 private static final LIRTestSpecification shortStackCopy = new StackCopySpec() { 197 @Override 198 protected ValueKind<?> getValueKind(Value value) { 199 return LIRKind.value(shortKind); 200 } 201 }; 202 203 @SuppressWarnings("unused") 204 @LIRIntrinsic 205 public static short copyShort(LIRTestSpecification spec, short a) { 206 return a; 207 } 208 209 public short[] testShort(short a, short[] out) { 210 out[0] = copyShort(shortStackCopy, a); 211 out[1] = getOutput(shortStackCopy, "slotcopy", a); 212 out[2] = getOutput(shortStackCopy, "slot1", a); 213 out[3] = getOutput(shortStackCopy, "slot2", a); 214 return out; 215 } 216 217 @Test 218 public void runShort() throws Throwable { 219 runTest("testShort", Short.MIN_VALUE, supply(() -> new short[3])); 220 runTest("testShort", (short) -1, supply(() -> new short[3])); 221 runTest("testShort", (short) 0, supply(() -> new short[3])); 222 runTest("testShort", (short) 1, supply(() -> new short[3])); 223 runTest("testShort", Short.MAX_VALUE, supply(() -> new short[3])); 224 } 225 226 /* 227 * byte 228 */ 229 230 private static final LIRTestSpecification byteStackCopy = new StackCopySpec() { 231 @Override 232 protected ValueKind<?> getValueKind(Value value) { 233 return LIRKind.value(byteKind); 234 } 235 }; 236 237 @SuppressWarnings("unused") 238 @LIRIntrinsic 239 public static byte copyByte(LIRTestSpecification spec, byte a) { 240 return a; 241 } 242 243 public byte[] testByte(byte a, byte[] out) { 244 out[0] = copyByte(byteStackCopy, a); 245 out[1] = getOutput(byteStackCopy, "slotcopy", a); 246 out[2] = getOutput(byteStackCopy, "slot1", a); 247 out[3] = getOutput(byteStackCopy, "slot2", a); 248 return out; 249 } 250 251 @Test 252 public void runByte() throws Throwable { 253 runTest("testByte", Byte.MIN_VALUE, supply(() -> new byte[3])); 254 runTest("testByte", (byte) -1, supply(() -> new byte[3])); 255 runTest("testByte", (byte) 0, supply(() -> new byte[3])); 256 runTest("testByte", (byte) 1, supply(() -> new byte[3])); 257 runTest("testByte", Byte.MAX_VALUE, supply(() -> new byte[3])); 258 } 259 }