You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by ro...@apache.org on 2018/11/20 12:21:01 UTC

qpid-proton-j git commit: PROTON-1965: Optimize CompositeReadableBuffer::equals for the single-array case.

Repository: qpid-proton-j
Updated Branches:
  refs/heads/master 459b84d44 -> 243dd0dd7


PROTON-1965: Optimize CompositeReadableBuffer::equals for the single-array case.

PR from Francesco Nigro with fixup from Robbie. This closes #20.


Project: http://git-wip-us.apache.org/repos/asf/qpid-proton-j/repo
Commit: http://git-wip-us.apache.org/repos/asf/qpid-proton-j/commit/243dd0dd
Tree: http://git-wip-us.apache.org/repos/asf/qpid-proton-j/tree/243dd0dd
Diff: http://git-wip-us.apache.org/repos/asf/qpid-proton-j/diff/243dd0dd

Branch: refs/heads/master
Commit: 243dd0dd77f228300957ccec74c8fff27e9db3cd
Parents: 459b84d
Author: Francesco Nigro <ni...@gmail.com>
Authored: Tue Nov 20 11:58:31 2018 +0000
Committer: Robbie Gemmell <ro...@apache.org>
Committed: Tue Nov 20 11:58:31 2018 +0000

----------------------------------------------------------------------
 .../proton/codec/CompositeReadableBuffer.java   | 32 +++++--
 .../codec/CompositeReadableBufferBenchmark.java | 88 ++++++++++++++++++++
 2 files changed, 113 insertions(+), 7 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/qpid-proton-j/blob/243dd0dd/proton-j/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBuffer.java
----------------------------------------------------------------------
diff --git a/proton-j/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBuffer.java b/proton-j/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBuffer.java
index 1441dcb..409b192 100644
--- a/proton-j/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBuffer.java
+++ b/proton-j/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBuffer.java
@@ -834,22 +834,40 @@ public class CompositeReadableBuffer implements ReadableBuffer {
             return false;
         }
 
-        ReadableBuffer buffer = (ReadableBuffer)other;
-        if (this.remaining() != buffer.remaining()) {
+        ReadableBuffer buffer = (ReadableBuffer) other;
+        final int remaining = remaining();
+        if (remaining != buffer.remaining()) {
             return false;
         }
 
-        final int origPos = position();
+        if (hasArray()) {
+            return equals(currentArray, currentOffset, remaining, buffer);
+        } else {
+            return equals(this, buffer);
+        }
+    }
+
+    private static boolean equals(byte[] buffer, int start, int length, ReadableBuffer other) {
+        final int position = other.position();
+        for (int i = 0; i < length; i++) {
+            if (buffer[start + i] != other.get(position + i)) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    private static boolean equals(ReadableBuffer buffer, ReadableBuffer other) {
+        final int origPos = buffer.position();
         try {
-            for (int i = buffer.position(); hasRemaining(); i++) {
-                if (!equals(this.get(), buffer.get(i))) {
+            for (int i = other.position(); buffer.hasRemaining(); i++) {
+                if (!equals(buffer.get(), other.get(i))) {
                     return false;
                 }
             }
-
             return true;
         } finally {
-            position(origPos);
+            buffer.position(origPos);
         }
     }
 

http://git-wip-us.apache.org/repos/asf/qpid-proton-j/blob/243dd0dd/tests/performance-jmh/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBufferBenchmark.java
----------------------------------------------------------------------
diff --git a/tests/performance-jmh/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBufferBenchmark.java b/tests/performance-jmh/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBufferBenchmark.java
new file mode 100644
index 0000000..4d58a68
--- /dev/null
+++ b/tests/performance-jmh/src/main/java/org/apache/qpid/proton/codec/CompositeReadableBufferBenchmark.java
@@ -0,0 +1,88 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.qpid.proton.codec;
+
+import org.apache.qpid.proton.codec.ReadableBuffer.ByteBufferReader;
+import org.openjdk.jmh.annotations.*;
+import org.openjdk.jmh.profile.GCProfiler;
+import org.openjdk.jmh.runner.Runner;
+import org.openjdk.jmh.runner.RunnerException;
+import org.openjdk.jmh.runner.options.Options;
+import org.openjdk.jmh.runner.options.OptionsBuilder;
+
+import java.nio.ByteBuffer;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Test performance of the CompositeReadableBuffer class
+ */
+@State(Scope.Benchmark)
+@BenchmarkMode(Mode.AverageTime)
+@OutputTimeUnit(TimeUnit.NANOSECONDS)
+@Warmup(iterations = 5, time = 1)
+@Measurement(iterations = 5, time = 1)
+public class CompositeReadableBufferBenchmark {
+
+    private CompositeReadableBuffer composite;
+    @Param({"8", "64", "1024"})
+    private int size;
+    private ReadableBuffer.ByteBufferReader bufferReader;
+    @Param({"false", "true"})
+    private boolean direct;
+    @Param({"1", "2"})
+    private int chunks;
+
+    @Setup
+    public void init() {
+        bufferReader =
+                direct ? ByteBufferReader.wrap(ByteBuffer.allocateDirect(size)) : ByteBufferReader.wrap(new byte[size]);
+        composite = new CompositeReadableBuffer();
+        int sizePerChunk = size / chunks;
+        for (int i = 0; i < chunks; i++) {
+            final byte[] content = new byte[sizePerChunk];
+            composite.append(content);
+        }
+        int remaining = size - composite.capacity();
+        if (remaining > 0) {
+            byte[] lastChunk = new byte[remaining];
+            composite.append(lastChunk);
+        }
+    }
+
+    @Benchmark
+    public boolean equalsToByteBufferReader() {
+        composite.position(0);
+        return composite.equals(bufferReader);
+    }
+
+    public static void main(String[] args) throws RunnerException {
+        runBenchmark(CompositeReadableBuffer.class);
+    }
+
+    public static void runBenchmark(Class<?> benchmarkClass) throws RunnerException {
+        final Options opt = new OptionsBuilder()
+                .include(benchmarkClass.getSimpleName())
+                .addProfiler(GCProfiler.class)
+                .shouldDoGC(true)
+                .warmupIterations(5)
+                .measurementIterations(5)
+                .forks(1)
+                .build();
+        new Runner(opt).run();
+    }
+}


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org