1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package io.netty.buffer;
17
18 import io.netty.microbench.util.AbstractMicrobenchmark;
19 import org.openjdk.jmh.annotations.Benchmark;
20 import org.openjdk.jmh.annotations.Measurement;
21 import org.openjdk.jmh.annotations.Param;
22 import org.openjdk.jmh.annotations.Setup;
23 import org.openjdk.jmh.annotations.TearDown;
24 import org.openjdk.jmh.annotations.Warmup;
25
26 import java.nio.charset.Charset;
27 import java.util.Arrays;
28 import java.util.concurrent.TimeUnit;
29
30 @Warmup(iterations = 5, time = 1, timeUnit = TimeUnit.SECONDS)
31 @Measurement(iterations = 10, time = 1, timeUnit = TimeUnit.SECONDS)
32 public class AbstractByteBufGetCharSequenceBenchmark extends AbstractMicrobenchmark {
33
34 public enum ByteBufType {
35 DIRECT {
36 @Override
37 ByteBuf newBuffer(byte[] bytes, int length) {
38 ByteBuf buffer = Unpooled.directBuffer(length);
39 buffer.writeBytes(bytes, 0, length);
40 return buffer;
41 }
42 },
43 HEAP_OFFSET {
44 @Override
45 ByteBuf newBuffer(byte[] bytes, int length) {
46 return Unpooled.wrappedBuffer(bytes, 1, length);
47 }
48 },
49 HEAP {
50 @Override
51 ByteBuf newBuffer(byte[] bytes, int length) {
52 return Unpooled.wrappedBuffer(bytes, 0, length);
53 }
54 },
55 COMPOSITE {
56 @Override
57 ByteBuf newBuffer(byte[] bytes, int length) {
58 CompositeByteBuf buffer = Unpooled.compositeBuffer();
59 int offset = 0;
60
61 int capacity = length / 8;
62
63 while (length > 0) {
64 buffer.addComponent(true, Unpooled.wrappedBuffer(bytes, offset, Math.min(length, capacity)));
65 length -= capacity;
66 offset += capacity;
67 }
68 return buffer;
69 }
70 };
71 abstract ByteBuf newBuffer(byte[] bytes, int length);
72 }
73
74 @Param({ "8", "64", "1024", "10240", "1073741824" })
75 public int size;
76
77 @Param({
78 "US-ASCII",
79 "ISO_8859_1",
80 })
81 public String charsetName;
82
83 @Param
84 public ByteBufType bufferType;
85
86 private ByteBuf buffer;
87 private Charset charset;
88
89 @Override
90 protected String[] jvmArgs() {
91
92 return new String[] { "-XX:MaxDirectMemorySize=2g", "-Xmx8g", "-Xms8g", "-Xmn6g" };
93 }
94
95 @Setup
96 public void setup() {
97 byte[] bytes = new byte[size + 2];
98 Arrays.fill(bytes, (byte) 'a');
99
100
101 buffer = bufferType.newBuffer(bytes, size);
102 charset = Charset.forName(charsetName);
103 }
104
105 @TearDown
106 public void teardown() {
107 buffer.release();
108 }
109
110 @Benchmark
111 public int getCharSequence() {
112 return traverse(buffer.getCharSequence(buffer.readerIndex(), size, charset));
113 }
114
115 @Benchmark
116 public int getCharSequenceOld() {
117 return traverse(buffer.toString(buffer.readerIndex(), size, charset));
118 }
119
120 private static int traverse(CharSequence cs) {
121 int i = 0, len = cs.length();
122 while (i < len && cs.charAt(i++) != 0) {
123
124 }
125 return i;
126 }
127 }