From 9ab5c21fddae9f48efa7c960f5d7f6bab7ffe2d2 Mon Sep 17 00:00:00 2001 From: ligi Date: Sat, 10 Jan 2015 16:25:40 +0100 Subject: [PATCH 1/3] speed improvements and add test-cases --- .../main/java/org/ethereum/util/ByteUtil.java | 43 ++++++++----------- .../main/java/org/ethereum/vm/DataWord.java | 33 +++++++------- .../java/test/ethereum/util/ByteUtilTest.java | 20 ++++++--- 3 files changed, 49 insertions(+), 47 deletions(-) diff --git a/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java b/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java index 316be3ae..ec421720 100644 --- a/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java +++ b/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java @@ -83,7 +83,7 @@ public class ByteUtil { int length = a.length < b.length ? a.length : b.length; while (i < length) { if (a[i] != b[i]) - break; + return i; i++; } return i; @@ -122,12 +122,11 @@ public class ByteUtil { */ public static byte[] calcPacketLength(byte[] msg) { int msgLen = msg.length; - byte[] len = { + return new byte[]{ (byte) ((msgLen >> 24) & 0xFF), (byte) ((msgLen >> 16) & 0xFF), (byte) ((msgLen >> 8) & 0xFF), (byte) ((msgLen) & 0xFF)}; - return len; } /** @@ -254,15 +253,12 @@ public class ByteUtil { } public static int firstNonZeroByte(byte[] data) { - int firstNonZero = -1; - int i = 0; - for (; i < data.length; ++i) { + for (int i = 0; i < data.length; ++i) { if (data[i] != 0) { - firstNonZero = i; - break; + return i; } } - return firstNonZero; + return -1; } public static byte[] stripLeadingZeroes(byte[] data) { @@ -270,23 +266,20 @@ public class ByteUtil { if (data == null) return null; - int firstNonZero = firstNonZeroByte(data); - int i = 0; - for (; i < data.length; ++i) { - if (data[i] != 0) { - firstNonZero = i; - break; - } + final int firstNonZero = firstNonZeroByte(data); + switch (firstNonZero) { + case -1: + return new byte[0]; + + case 0: + return data; + + default: + byte[] result = new byte[data.length - firstNonZero]; + System.arraycopy(data, firstNonZero, result, 0, data.length - firstNonZero); + + return result; } - if (i == data.length) - return new byte[1]; - if (firstNonZero == 0) - return data; - - byte[] result = new byte[data.length - firstNonZero]; - System.arraycopy(data, firstNonZero, result, 0, data.length - firstNonZero); - - return result; } /** diff --git a/ethereumj-core/src/main/java/org/ethereum/vm/DataWord.java b/ethereumj-core/src/main/java/org/ethereum/vm/DataWord.java index f8dc9e44..f2d82de3 100644 --- a/ethereumj-core/src/main/java/org/ethereum/vm/DataWord.java +++ b/ethereumj-core/src/main/java/org/ethereum/vm/DataWord.java @@ -32,30 +32,31 @@ public class DataWord implements Comparable { } public DataWord(int num) { - ByteBuffer bInt = ByteBuffer.allocate(4).putInt(num); - ByteBuffer data = ByteBuffer.allocate(32); - System.arraycopy(bInt.array(), 0, data.array(), 28, 4); - this.data = data.array(); + this(ByteBuffer.allocate(4).putInt(num)); } public DataWord(long num) { - ByteBuffer bLong = ByteBuffer.allocate(8).putLong(num); - ByteBuffer data = ByteBuffer.allocate(32); - System.arraycopy(bLong.array(), 0, data.array(), 24, 8); + this(ByteBuffer.allocate(8).putLong(num)); + } + + private DataWord(ByteBuffer buffer) { + final ByteBuffer data = ByteBuffer.allocate(32); + final byte[] array = buffer.array(); + System.arraycopy(array, 0, data.array(), 32 - array.length, array.length); this.data = data.array(); } - public DataWord(String data){ + public DataWord(String data) { this(Hex.decode(data)); } - + public DataWord(byte[] data) { if (data == null) this.data = ByteUtil.EMPTY_BYTE_ARRAY; else if (data.length <= 32) System.arraycopy(data, 0, this.data, 32 - data.length, data.length); else - throw new RuntimeException("Data word can't exit 32 bytes: " + data); + throw new RuntimeException("Data word can't exceed 32 bytes: " + data); } public byte[] getData() { @@ -107,11 +108,10 @@ public class DataWord implements Comparable { } public boolean isZero() { - byte result = 0; for (byte tmp : data) { - result |= tmp; + if (tmp != 0) return false; } - return result == 0; + return true; } // only in case of signed operation @@ -282,9 +282,8 @@ public class DataWord implements Comparable { DataWord dataWord = (DataWord) o; - if (!java.util.Arrays.equals(data, dataWord.data)) return false; + return java.util.Arrays.equals(data, dataWord.data); - return true; } @Override @@ -316,8 +315,8 @@ public class DataWord implements Comparable { if (firstNonZero == -1) return 0; return 31 - firstNonZero + 1; } - - public boolean isHex(String hex){ + + public boolean isHex(String hex) { return Hex.toHexString(data).equals(hex); } } diff --git a/ethereumj-core/src/test/java/test/ethereum/util/ByteUtilTest.java b/ethereumj-core/src/test/java/test/ethereum/util/ByteUtilTest.java index b76b43a9..e330b69d 100644 --- a/ethereumj-core/src/test/java/test/ethereum/util/ByteUtilTest.java +++ b/ethereumj-core/src/test/java/test/ethereum/util/ByteUtilTest.java @@ -100,11 +100,21 @@ public class ByteUtilTest { @Test public void testStripLeadingZeroes() { - byte[] test1 = new byte[]{0x00, 0x01}; - byte[] test2 = new byte[]{0x00, 0x00, 0x01}; - byte[] expected = new byte[]{0x01}; - assertArrayEquals(expected, ByteUtil.stripLeadingZeroes(test1)); - assertArrayEquals(expected, ByteUtil.stripLeadingZeroes(test2)); + byte[] test1 = null; + byte[] test2 = new byte[]{}; + byte[] test3 = new byte[]{0x00}; + byte[] test4 = new byte[]{0x00, 0x01}; + byte[] test5 = new byte[]{0x00, 0x00, 0x01}; + byte[] expected1 = null; + byte[] expected2 = new byte[]{}; + byte[] expected3 = new byte[]{}; + byte[] expected4 = new byte[]{0x01}; + byte[] expected5 = new byte[]{0x01}; + assertArrayEquals(expected1, ByteUtil.stripLeadingZeroes(test1)); + assertArrayEquals(expected2, ByteUtil.stripLeadingZeroes(test2)); + assertArrayEquals(expected3, ByteUtil.stripLeadingZeroes(test3)); + assertArrayEquals(expected4, ByteUtil.stripLeadingZeroes(test4)); + assertArrayEquals(expected5, ByteUtil.stripLeadingZeroes(test5)); } @Test From 3a8258a07e786ed1cd989a9f67b151f508710d87 Mon Sep 17 00:00:00 2001 From: ligi Date: Sat, 10 Jan 2015 21:05:00 +0100 Subject: [PATCH 2/3] use the available ZERO_BYTE_ARRAY --- ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java b/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java index ec421720..025b7504 100644 --- a/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java +++ b/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java @@ -269,7 +269,7 @@ public class ByteUtil { final int firstNonZero = firstNonZeroByte(data); switch (firstNonZero) { case -1: - return new byte[0]; + return ZERO_BYTE_ARRAY; case 0: return data; From 59a5baff816197afe502162651891ac0238abc2d Mon Sep 17 00:00:00 2001 From: ligi Date: Sat, 10 Jan 2015 21:37:40 +0100 Subject: [PATCH 3/3] we want EMPTY_BYTE_ARRAY --- ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java b/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java index 025b7504..201fe87e 100644 --- a/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java +++ b/ethereumj-core/src/main/java/org/ethereum/util/ByteUtil.java @@ -269,7 +269,7 @@ public class ByteUtil { final int firstNonZero = firstNonZeroByte(data); switch (firstNonZero) { case -1: - return ZERO_BYTE_ARRAY; + return EMPTY_BYTE_ARRAY; case 0: return data;