1 /* 2 * Copyright (c) 2017, 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 25 package org.graalvm.compiler.core.test; 26 27 import java.nio.ByteBuffer; 28 import java.nio.ByteOrder; 29 import java.util.ArrayList; 30 import java.util.Collection; 31 import org.junit.Test; 32 import org.junit.runner.RunWith; 33 import org.junit.runners.Parameterized; 34 import org.junit.runners.Parameterized.Parameter; 35 import org.junit.runners.Parameterized.Parameters; 36 37 @RunWith(Parameterized.class) 38 public class DirectByteBufferTest extends GraalCompilerTest { 39 40 class Ret { 41 42 byte byteValue = 0; 43 short shortValue = 0; 44 int intValue = 0; 45 long longValue = 0; 46 float floatValue = 0.0f; 47 double doubleValue = 0.0d; 48 49 @Override 50 public boolean equals(Object obj) { 51 if (!(obj instanceof Ret)) { 52 return false; 53 } 54 55 Ret other = (Ret) obj; 56 if (this.byteValue != other.byteValue) { 57 return false; 58 } 59 if (this.shortValue != other.shortValue) { 60 return false; 61 } 62 if (this.intValue != other.intValue) { 63 return false; 64 } 65 if (this.longValue != other.longValue) { 66 return false; 67 } 68 if (Float.floatToRawIntBits(this.floatValue) != Float.floatToRawIntBits(other.floatValue)) { 69 return false; 70 } 71 if (Double.doubleToRawLongBits(this.doubleValue) != Double.doubleToRawLongBits(other.doubleValue)) { 72 return false; 73 } 74 75 return true; 76 } 77 78 @Override 79 public int hashCode() { 80 return 0; 81 } 82 83 @Override 84 public String toString() { 85 return String.format("0x%02x, 0x%04x, 0x%08x, 0x%016x,0x%08x, 0x%016x", byteValue, shortValue, intValue, Float.floatToRawIntBits(floatValue), Double.doubleToRawLongBits(doubleValue)); 86 } 87 } 88 89 @Parameters(name = "{0}") 90 public static Collection<Object[]> data() { 91 ArrayList<Object[]> ret = new ArrayList<>(); 92 ret.add(new Object[]{ByteOrder.BIG_ENDIAN}); 93 ret.add(new Object[]{ByteOrder.LITTLE_ENDIAN}); 94 return ret; 95 } 96 97 @Parameter public ByteOrder byteOrder; 98 99 Ret alignedReadSnippet(byte[] arg) { 100 ByteBuffer buffer = makeDirect(arg, byteOrder); 101 102 Ret ret = new Ret(); 103 ret.byteValue = buffer.get(); 104 ret.byteValue += buffer.get(); 105 ret.shortValue = buffer.getShort(); 106 ret.intValue = buffer.getInt(); 107 ret.longValue = buffer.getLong(); 108 ret.doubleValue = buffer.getDouble(); 109 ret.floatValue = buffer.getFloat(); 110 111 return ret; 112 } 113 114 @Test 115 public void testReadAligned() { 116 byte[] input = new byte[28]; 117 for (int i = 0; i < 28; i++) { 118 input[i] = (byte) (7 * (i + 42)); 119 } 120 test("alignedReadSnippet", input); 121 } 122 123 byte[] alignedWriteSnippet(byte a, byte b, short c, int d, long e, double f, float g) { 124 byte[] ret = new byte[28]; 125 ByteBuffer buffer = makeDirect(28, byteOrder); 126 127 buffer.put(a); 128 buffer.put(b); 129 buffer.putShort(c); 130 buffer.putInt(d); 131 buffer.putLong(e); 132 buffer.putDouble(f); 133 buffer.putFloat(g); 134 135 buffer.position(0); 136 buffer.get(ret); 137 138 return ret; 139 } 140 141 @Test 142 public void testWriteAligned() { 143 test("alignedWriteSnippet", (byte) 5, (byte) -3, (short) 17, 42, 0x3FC30A25644B7130L, 84.72, 1.23f); 144 } 145 146 Ret unalignedReadSnippet(byte[] arg) { 147 ByteBuffer buffer = makeDirect(arg, byteOrder); 148 149 Ret ret = new Ret(); 150 ret.byteValue = buffer.get(); 151 ret.shortValue = buffer.getShort(); 152 ret.intValue = buffer.getInt(); 153 ret.longValue = buffer.getLong(); 154 ret.doubleValue = buffer.getDouble(); 155 ret.floatValue = buffer.getFloat(); 156 157 return ret; 158 } 159 160 @Test 161 public void testReadUnaligned() { 162 byte[] input = new byte[27]; 163 for (int i = 0; i < 27; i++) { 164 input[i] = (byte) (7 * (i + 42)); 165 } 166 test("unalignedReadSnippet", input); 167 } 168 169 byte[] unalignedWriteSnippet(byte a, short b, int c, long d, double e, float f) { 170 byte[] ret = new byte[27]; 171 ByteBuffer buffer = makeDirect(27, byteOrder); 172 173 buffer.put(a); 174 buffer.putShort(b); 175 buffer.putInt(c); 176 buffer.putLong(d); 177 buffer.putDouble(e); 178 buffer.putFloat(f); 179 180 buffer.position(0); 181 buffer.get(ret); 182 183 return ret; 184 } 185 186 @Test 187 public void testWriteUnaligned() { 188 test("unalignedWriteSnippet", (byte) -3, (short) 17, 42, 0x3FC30A25644B7130L, 84.72, 1.23f); 189 } 190 191 private static ByteBuffer makeDirect(byte[] bytes, ByteOrder byteOrder) { 192 int length = bytes.length; 193 ByteBuffer buffer = ByteBuffer.allocateDirect(length).order(byteOrder); 194 buffer.put(bytes); 195 buffer.position(0); 196 return buffer; 197 } 198 199 private static ByteBuffer makeDirect(int length, ByteOrder byteOrder) { 200 ByteBuffer buffer = ByteBuffer.allocateDirect(length).order(byteOrder); 201 buffer.position(0); 202 return buffer; 203 } 204 }