From c5e5f7ded20812780880e3381318bd2bbd38303a Mon Sep 17 00:00:00 2001 From: chenglei Date: Sun, 10 Oct 2021 20:29:57 +0800 Subject: [PATCH 1/4] HBASE-26344 Fix Bug for MultiByteBuff.put(int, byte) --- .../hadoop/hbase/nio/MultiByteBuff.java | 13 +++-- .../hadoop/hbase/nio/TestMultiByteBuff.java | 52 +++++++++++++++++++ 2 files changed, 60 insertions(+), 5 deletions(-) diff --git a/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java b/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java index a25791e5ce83..9ddbb2ac37d9 100644 --- a/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java +++ b/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java @@ -181,6 +181,9 @@ public byte getByteAfterPosition(int offset) { * Returns in which sub ByteBuffer, the given element index will be available. */ private int getItemIndex(int elemIndex) { + if (elemIndex < 0) { + throw new IndexOutOfBoundsException(); + } int index = 1; while (elemIndex >= this.itemBeginPos[index]) { index++; @@ -721,15 +724,15 @@ public MultiByteBuff put(byte b) { } /** - * Writes a byte to this MBB at the given index - * @param index - * @param b - * @return this object + * Writes a byte to this MBB at the given index and won't affect the position of any of the + * buffers. + * @throws IndexOutOfBoundsException If index is negative or not smaller than the + * {@link MultiByteBuff#limit} */ @Override public MultiByteBuff put(int index, byte b) { checkRefCount(); - int itemIndex = getItemIndex(limit); + int itemIndex = getItemIndex(index); ByteBuffer item = items[itemIndex]; item.put(index - itemBeginPos[itemIndex], b); return this; diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java index 563f82a1cd99..2598b72a68e8 100644 --- a/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java +++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java @@ -594,4 +594,56 @@ private void doTestPositionalPutByteBuff(ByteBuff srcByteBuff) throws Exception assertTrue(e != null); } } + + @Test + public void testPositionalPutByte() throws Exception { + ByteBuffer bb1 = ByteBuffer.allocate(50); + ByteBuffer bb2 = ByteBuffer.allocate(50); + ByteBuffer bb3 = ByteBuffer.allocate(50); + ByteBuffer bb4 = ByteBuffer.allocate(50); + MultiByteBuff srcMultiByteBuff = new MultiByteBuff(bb1, bb2, bb3, bb4); + for (int i = 1; i <= 200; i++) { + srcMultiByteBuff.put((byte) 0xff); + } + + srcMultiByteBuff.put(20, (byte) 0); + byte val = srcMultiByteBuff.get(20); + assertTrue(val == 0); + + srcMultiByteBuff.put(50, (byte) 0); + val = srcMultiByteBuff.get(50); + assertTrue(val == 0); + + srcMultiByteBuff.put(80, (byte) 0); + val = srcMultiByteBuff.get(80); + assertTrue(val == 0); + + srcMultiByteBuff.put(100, (byte) 0); + val = srcMultiByteBuff.get(100); + assertTrue(val == 0); + + srcMultiByteBuff.put(121, (byte) 0); + val = srcMultiByteBuff.get(121); + assertTrue(val == 0); + + srcMultiByteBuff.put(150, (byte) 0); + val = srcMultiByteBuff.get(150); + assertTrue(val == 0); + + srcMultiByteBuff.put(180, (byte) 0); + val = srcMultiByteBuff.get(180); + assertTrue(val == 0); + + try { + srcMultiByteBuff.put(200, (byte) 0); + } catch (IndexOutOfBoundsException e) { + assertTrue(e != null); + } + + try { + srcMultiByteBuff.put(260, (byte) 0); + } catch (IndexOutOfBoundsException e) { + assertTrue(e != null); + } + } } From f18f3d9b1b9a196960c117bba50dc5434a9022b9 Mon Sep 17 00:00:00 2001 From: chenglei Date: Sun, 10 Oct 2021 20:33:43 +0800 Subject: [PATCH 2/4] add more comments --- .../src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java | 1 + 1 file changed, 1 insertion(+) diff --git a/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java b/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java index 9ddbb2ac37d9..f9000ed953ad 100644 --- a/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java +++ b/hbase-common/src/main/java/org/apache/hadoop/hbase/nio/MultiByteBuff.java @@ -726,6 +726,7 @@ public MultiByteBuff put(byte b) { /** * Writes a byte to this MBB at the given index and won't affect the position of any of the * buffers. + * @return this object * @throws IndexOutOfBoundsException If index is negative or not smaller than the * {@link MultiByteBuff#limit} */ From 792b9c2b28eb506669334622d0404eb4dc738260 Mon Sep 17 00:00:00 2001 From: chenglei Date: Wed, 13 Oct 2021 10:18:20 +0800 Subject: [PATCH 3/4] fix checkstyle error --- .../java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java index 2598b72a68e8..1874cb7ceb18 100644 --- a/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java +++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java @@ -635,7 +635,7 @@ public void testPositionalPutByte() throws Exception { assertTrue(val == 0); try { - srcMultiByteBuff.put(200, (byte) 0); + srcMultiByteBuff.put(200, (byte) 0); } catch (IndexOutOfBoundsException e) { assertTrue(e != null); } From 78f13c205134202567dcad7ad1029b2ab4aef8e9 Mon Sep 17 00:00:00 2001 From: chenglei Date: Wed, 13 Oct 2021 10:32:28 +0800 Subject: [PATCH 4/4] fix javac error --- .../hadoop/hbase/nio/TestMultiByteBuff.java | 2 + .../hadoop/hbase/util/TestOrderedBytes.java | 58 ++++++++++++------- 2 files changed, 40 insertions(+), 20 deletions(-) diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java index 1874cb7ceb18..b40ac0c22a88 100644 --- a/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java +++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/nio/TestMultiByteBuff.java @@ -636,12 +636,14 @@ public void testPositionalPutByte() throws Exception { try { srcMultiByteBuff.put(200, (byte) 0); + fail(); } catch (IndexOutOfBoundsException e) { assertTrue(e != null); } try { srcMultiByteBuff.put(260, (byte) 0); + fail(); } catch (IndexOutOfBoundsException e) { assertTrue(e != null); } diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/util/TestOrderedBytes.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/util/TestOrderedBytes.java index 45b8e3547ce1..c8e0381969b2 100644 --- a/hbase-common/src/test/java/org/apache/hadoop/hbase/util/TestOrderedBytes.java +++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/util/TestOrderedBytes.java @@ -1263,26 +1263,44 @@ public void testEncodedValueCheck() { int cnt = 0; PositionedByteRange buff = new SimplePositionedMutableByteRange(1024); for (Order ord : new Order[] { Order.ASCENDING, Order.DESCENDING }) { - int o; - o = OrderedBytes.encodeNull(buff, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, negInf, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, negLarge, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, negMed, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, negSmall, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, zero, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, posSmall, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, posMed, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, posLarge, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, posInf, ord); cnt++; - o = OrderedBytes.encodeNumeric(buff, nan, ord); cnt++; - o = OrderedBytes.encodeInt8(buff, int8, ord); cnt++; - o = OrderedBytes.encodeInt16(buff, int16, ord); cnt++; - o = OrderedBytes.encodeInt32(buff, int32, ord); cnt++; - o = OrderedBytes.encodeInt64(buff, int64, ord); cnt++; - o = OrderedBytes.encodeFloat32(buff, float32, ord); cnt++; - o = OrderedBytes.encodeFloat64(buff, float64, ord); cnt++; - o = OrderedBytes.encodeString(buff, text, ord); cnt++; - o = OrderedBytes.encodeBlobVar(buff, blobVar, ord); cnt++; + OrderedBytes.encodeNull(buff, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, negInf, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, negLarge, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, negMed, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, negSmall, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, zero, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, posSmall, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, posMed, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, posLarge, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, posInf, ord); + cnt++; + OrderedBytes.encodeNumeric(buff, nan, ord); + cnt++; + OrderedBytes.encodeInt8(buff, int8, ord); + cnt++; + OrderedBytes.encodeInt16(buff, int16, ord); + cnt++; + OrderedBytes.encodeInt32(buff, int32, ord); + cnt++; + OrderedBytes.encodeInt64(buff, int64, ord); + cnt++; + OrderedBytes.encodeFloat32(buff, float32, ord); + cnt++; + OrderedBytes.encodeFloat64(buff, float64, ord); + cnt++; + OrderedBytes.encodeString(buff, text, ord); + cnt++; + OrderedBytes.encodeBlobVar(buff, blobVar, ord); + cnt++; } buff.setPosition(0);