1 /*
  2  * Copyright (c) 2021, 2022, 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 package org.openjdk.bench.java.lang.foreign;
 25 
 26 import java.lang.foreign.MemorySegment;
 27 
 28 import org.openjdk.jmh.annotations.Benchmark;
 29 import org.openjdk.jmh.annotations.BenchmarkMode;
 30 import org.openjdk.jmh.annotations.CompilerControl;
 31 import org.openjdk.jmh.annotations.Fork;
 32 import org.openjdk.jmh.annotations.Measurement;
 33 import org.openjdk.jmh.annotations.Mode;
 34 import org.openjdk.jmh.annotations.OutputTimeUnit;
 35 import org.openjdk.jmh.annotations.Param;
 36 import org.openjdk.jmh.annotations.Setup;
 37 import org.openjdk.jmh.annotations.State;
 38 import org.openjdk.jmh.annotations.Warmup;
 39 
 40 import java.lang.foreign.Arena;
 41 import java.nio.ByteBuffer;
 42 import java.util.concurrent.TimeUnit;
 43 
 44 import static java.lang.foreign.ValueLayout.JAVA_BYTE;
 45 
 46 @BenchmarkMode(Mode.AverageTime)
 47 @Warmup(iterations = 5, time = 500, timeUnit = TimeUnit.MILLISECONDS)
 48 @Measurement(iterations = 10, time = 500, timeUnit = TimeUnit.MILLISECONDS)
 49 @State(org.openjdk.jmh.annotations.Scope.Thread)
 50 @OutputTimeUnit(TimeUnit.NANOSECONDS)
 51 @Fork(value = 1, jvmArgsAppend = {
 52         "-Dforeign.restricted=permit",
 53         "--enable-native-access", "ALL-UNNAMED",
 54         "--enable-preview"})
 55 public class TestLoadBytes {
 56     @Param("1024")
 57     private int size;
 58 
 59     private byte[] srcArray;
 60     private ByteBuffer srcBufferNative;
 61     private MemorySegment srcSegmentImplicit;
 62 
 63     @Setup
 64     public void setup() {
 65         srcArray = new byte[size];
 66         for (int i = 0; i < srcArray.length; i++) {
 67             srcArray[i] = (byte) i;
 68         }
 69 
 70         srcBufferNative = ByteBuffer.allocateDirect(size);
 71         Arena scope = Arena.ofAuto();
 72         srcSegmentImplicit = scope.allocate(size, 1);
 73     }
 74 
 75     @Benchmark
 76     public int arrayScalar() {
 77         int size = 0;
 78         for (int i = 0; i < srcArray.length; i ++) {
 79             var v = srcArray[i];
 80             size += v;
 81         }
 82         return size;
 83     }
 84 
 85     @Benchmark
 86     public int arrayScalarConst() {
 87         int size = 0;
 88         for (int i = 0; i < 1024; i ++) {
 89             var v = srcArray[i];
 90             size += v;
 91         }
 92         return size;
 93     }
 94 
 95     @Benchmark
 96     public int bufferNativeScalar() {
 97         int size = 0;
 98         for (int i = 0; i < srcArray.length; i++) {
 99             var v = srcBufferNative.get(i);
100             size += v;
101         }
102         return size;
103     }
104 
105     @Benchmark
106     public int bufferNativeScalarConst() {
107         int size = 0;
108         for (int i = 0; i < 1024; i++) {
109             var v = srcBufferNative.get(i);
110             size += v;
111         }
112         return size;
113     }
114 
115     @Benchmark
116     public int segmentNativeScalar() {
117         int size = 0;
118         for (int i = 0; i < srcArray.length; i++) {
119             var v = srcSegmentImplicit.get(JAVA_BYTE, i);
120             size += v;
121         }
122         return size;
123     }
124 
125     @Benchmark
126     public int segmentNativeScalarConst() {
127         int size = 0;
128         for (int i = 0; i < 1024; i++) {
129             var v = srcSegmentImplicit.get(JAVA_BYTE, i);
130             size += v;
131         }
132         return size;
133     }
134 }