From df871b12425d5a517d2677ab0b1bd013ad7652f1 Mon Sep 17 00:00:00 2001 From: Fan-Wu Yang Date: Tue, 25 Apr 2017 19:40:20 +1200 Subject: [PATCH] Added tests to fix ByteConverter - Integers cutting and chopping now works - Integer to bytes word - bytes to integer also work #story[782] --- .../Networking/BinaryMessageDecoder.java | 56 +---------- .../Networking/Utils/ByteConverter.java | 96 +++++++++++++++---- .../seng302/Networking/ByteConverterTest.java | 71 ++++++++++++++ 3 files changed, 154 insertions(+), 69 deletions(-) create mode 100644 src/test/java/seng302/Networking/ByteConverterTest.java diff --git a/src/main/java/seng302/Networking/BinaryMessageDecoder.java b/src/main/java/seng302/Networking/BinaryMessageDecoder.java index 4832fcd5..6e270aea 100644 --- a/src/main/java/seng302/Networking/BinaryMessageDecoder.java +++ b/src/main/java/seng302/Networking/BinaryMessageDecoder.java @@ -56,9 +56,9 @@ public class BinaryMessageDecoder { crc.update(this.fullMessage); //run through the checks - if (this.message.length != twoByteToInt(this.headerMessageLength) && this.message.length != twoByteToIntBE(this.headerMessageLength)){ + if (this.message.length != ByteConverter.bytesToInt(this.headerMessageLength) && this.message.length != ByteConverter.bytesToInt(this.headerMessageLength, ByteOrder.BIG_ENDIAN)){ System.err.println("message length in header does not equal the message length"); - System.err.println("message length in header: " + twoByteToInt(this.headerMessageLength)); + System.err.println("message length in header: " + ByteConverter.bytesToInt(this.headerMessageLength)); System.err.println("message length: " + this.message.length); return null; }else if(this.headerSync1 != 0x47){ @@ -142,62 +142,16 @@ public class BinaryMessageDecoder { } - private short bytesToShort(byte[] bytesShort){ - ByteBuffer wrapped = ByteBuffer.wrap(bytesShort); - short num = wrapped.getShort(); - return num; - } - - private int bytesToInt(byte[] bytesInt){ - ByteBuffer wrapped = ByteBuffer.wrap(bytesInt); - int num = wrapped.getInt(); - return num; - } - - private int twoByteToInt(byte[] bytesInt){ - byte[] bytes = new byte[2]; - bytes[1] = bytesInt[0]; - bytes[0] = bytesInt[1]; - int num = ByteBuffer.wrap(bytes).getShort(); - - return num; - } - - private int twoByteToIntBE(byte[] bytesInt){ - ByteBuffer byteBuffer = ByteBuffer.allocate(4); - byteBuffer.order(ByteOrder.BIG_ENDIAN); - byteBuffer.put((byte)0); - byteBuffer.put((byte)0); - byteBuffer.put(bytesInt); - int num = byteBuffer.getInt(0); - return num; - } - - private long bytesToLong(byte[] bytesLong){ - ByteBuffer byteBuffer = ByteBuffer.allocate(8); - byteBuffer.order(ByteOrder.BIG_ENDIAN); - byteBuffer.put((byte)0); - byteBuffer.put((byte)0); - byteBuffer.put(bytesLong[0]); - byteBuffer.put(bytesLong[1]); - byteBuffer.put(bytesLong[2]); - byteBuffer.put(bytesLong[3]); - byteBuffer.put(bytesLong[4]); - byteBuffer.put(bytesLong[5]); - long longVal = byteBuffer.getLong(0); - return longVal; - } - public long getTimeStamp() { - return bytesToLong(this.headerTimeStamp); + return ByteConverter.bytesToLong(this.headerTimeStamp); } public int getSourceID() { - return bytesToInt(this.headerSourceID); + return ByteConverter.bytesToInt(this.headerSourceID); } public short getMessageLength() { - return bytesToShort(this.headerMessageLength); + return ByteConverter.bytesToShort(this.headerMessageLength); } public int getMessageType(){ diff --git a/src/main/java/seng302/Networking/Utils/ByteConverter.java b/src/main/java/seng302/Networking/Utils/ByteConverter.java index 26184bd9..2c4c160d 100644 --- a/src/main/java/seng302/Networking/Utils/ByteConverter.java +++ b/src/main/java/seng302/Networking/Utils/ByteConverter.java @@ -2,12 +2,19 @@ package seng302.Networking.Utils; import java.nio.ByteBuffer; import java.nio.ByteOrder; +import java.util.Arrays; /** * Created by fwy13 on 25/04/17. */ public class ByteConverter { + public static int IntegerSize = 4; + public static int LongSize = 8; + public static int CharSize = 2; + public static int ShortSize = 2; + + //default for AC35 is Little Endian therefore all overloads will be done with Little_Endian unless told else wise public static int bytesToInt(byte bite){ @@ -15,11 +22,6 @@ public class ByteConverter { return bytesToInt(bytes, ByteOrder.LITTLE_ENDIAN); } - public static int bytesToInt(byte bite, ByteOrder byteOrder){ - byte[] bytes = {bite}; - return bytesToInt(bytes, byteOrder); - } - public static int bytesToInt(byte[] bytes){ return bytesToInt(bytes, ByteOrder.LITTLE_ENDIAN); } @@ -28,10 +30,10 @@ public class ByteConverter { byte[] bites = new byte[4]; if (byteOrder == ByteOrder.LITTLE_ENDIAN){ for (int i = 0; i < bytes.length; i++){ - bites[i] = bytes[i]; - if (i > 4){//break if over the limit - break; - } + bites[i] = bytes[i]; + if (i > 4){//break if over the limit + break; + } } for (int i = bytes.length; i < 4; i++){ bites[i] = 0b0; @@ -55,11 +57,6 @@ public class ByteConverter { return bytesToLong(bytes, ByteOrder.LITTLE_ENDIAN); } - public static long bytesToLong(byte bite, ByteOrder byteOrder){ - byte[] bytes = {bite}; - return bytesToLong(bytes, byteOrder); - } - public static long bytesToLong(byte[] bytes){ return bytesToLong(bytes, ByteOrder.LITTLE_ENDIAN); } @@ -67,6 +64,16 @@ public class ByteConverter { public static long bytesToLong(byte[] bytes, ByteOrder byteOrder){ byte[] bites = new byte[8]; if (byteOrder == ByteOrder.LITTLE_ENDIAN) { + for (int i = 0; i < 8 - bytes.length; i++) { + bites[i] = 0b0; + } + for (int i = 8 - bytes.length; i < 8; i++) { + bites[i] = bytes[i]; + if (i > 8){//break if over the limit + break; + } + } + }else{//if big endian for (int i = 0; i < bytes.length; i++) { bites[i] = bytes[i]; if (i > 8){//break if over hte limit @@ -76,17 +83,70 @@ public class ByteConverter { for (int i = bytes.length; i < 8; i++) { bites[i] = 0b0; } + } + return ByteBuffer.wrap(bites).order(byteOrder).getLong(); + } + + public static short bytesToShort(byte bite){ + byte[] bytes = {bite}; + return bytesToShort(bytes, ByteOrder.LITTLE_ENDIAN); + } + + public static short bytesToShort(byte bite, ByteOrder byteOrder){ + byte[] bytes = {bite}; + return bytesToShort(bytes, byteOrder); + } + + public static short bytesToShort(byte[] bytes){ + return bytesToShort(bytes, ByteOrder.LITTLE_ENDIAN); + } + + public static short bytesToShort(byte[] bytes, ByteOrder byteOrder){ + byte[] bites = new byte[2]; + if (byteOrder == ByteOrder.LITTLE_ENDIAN) { + for (int i = 0; i < bytes.length; i++) { + bites[i] = bytes[i]; + if (i > 2){//break if over hte limit + break; + } + } + for (int i = bytes.length; i < 2; i++) { + bites[i] = 0b0; + } }else{//if big endian - for (int i = 0; i < 8 - bytes.length; i++) { + for (int i = 0; i < 2 - bytes.length; i++) { bites[i] = 0b0; } - for (int i = 8 - bytes.length; i < 8; i++) { + for (int i = 8 - bytes.length; i < 2; i++) { bites[i] = bytes[i]; - if (i > 8){//break if over the limit + if (i > 2){//break if over the limit break; } } } - return ByteBuffer.wrap(bites).order(byteOrder).getInt(); + return ByteBuffer.wrap(bites).order(byteOrder).getShort(); } + + public static byte[] intToBytes(int i){ + return intToBytes(i, 4, ByteOrder.LITTLE_ENDIAN); + } + + public static byte[] intToBytes(int i ,int size){ + return intToBytes(i, size, ByteOrder.LITTLE_ENDIAN); + } + public static byte[] intToBytes(int i ,int size, ByteOrder byteOrder){ + ByteBuffer buffer = ByteBuffer.allocate(IntegerSize); + buffer.order(byteOrder); + buffer.putInt(i); + byte[] copy = buffer.array(); + byte[] bytes = new byte[size]; + if (byteOrder == ByteOrder.LITTLE_ENDIAN){ + bytes = Arrays.copyOfRange(copy, 0, size); + }else{// if it is Big Endian + bytes = Arrays.copyOfRange(copy, IntegerSize - size, IntegerSize); + } + return bytes; + } + + } diff --git a/src/test/java/seng302/Networking/ByteConverterTest.java b/src/test/java/seng302/Networking/ByteConverterTest.java new file mode 100644 index 00000000..ffc45bd6 --- /dev/null +++ b/src/test/java/seng302/Networking/ByteConverterTest.java @@ -0,0 +1,71 @@ +package seng302.Networking; + +import org.junit.Test; +import seng302.Networking.Utils.ByteConverter; + +import java.nio.ByteOrder; +import java.util.Arrays; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; + + +/** + * Created by fwy13 on 25/04/17. + */ +public class ByteConverterTest { + + @Test + public void testIntToByte(){ + int int1 = 100; //100 in bytes + byte[] bytes1 = {100, 0, 0, 0};//this is in little endian + assertTrue(testArrayContents(ByteConverter.intToBytes(int1), bytes1)); + byte[] bytes2 = {0, 0, 0, 100};// this is big endian + assertTrue(testArrayContents(ByteConverter.intToBytes(int1, ByteConverter.IntegerSize, ByteOrder.BIG_ENDIAN), bytes2)); + //test chopping + byte[] chopped1 = ByteConverter.intToBytes(int1, 3, ByteOrder.LITTLE_ENDIAN); + byte[] bytes3 = {100, 0, 0}; + assertTrue(testArrayContents(chopped1, bytes3)); + byte[] chopped2 = ByteConverter.intToBytes(int1, 2, ByteOrder.LITTLE_ENDIAN); + byte[] bytes4 = {100, 0}; + assertTrue(testArrayContents(chopped2, bytes4)); + byte[] chopped3 = ByteConverter.intToBytes(int1, 1, ByteOrder.LITTLE_ENDIAN); + byte[] bytes5 = {100}; + assertTrue(testArrayContents(chopped3, bytes5)); + + byte[] chopped4 = ByteConverter.intToBytes(int1, 3, ByteOrder.BIG_ENDIAN); + byte[] bytes6 = {0, 0, 100}; + assertTrue(testArrayContents(chopped4, bytes6)); + byte[] chopped5 = ByteConverter.intToBytes(int1, 2, ByteOrder.BIG_ENDIAN); + byte[] bytes7 = {0, 100}; + assertTrue(testArrayContents(chopped5, bytes7)); + byte[] chopped6 = ByteConverter.intToBytes(int1, 1, ByteOrder.BIG_ENDIAN); + byte[] bytes8 = {100}; + assertTrue(testArrayContents(chopped6, bytes8)); + } + + @Test + public void testByteToInt(){ + int int1 = 100; //100 in bytes + byte[] bytes1 = {100, 0, 0, 0};//this is in little endian + assertTrue(ByteConverter.bytesToInt(bytes1) == int1); + assertTrue(ByteConverter.bytesToInt(bytes1, ByteOrder.LITTLE_ENDIAN) == int1); + byte[] bytes2 = {0, 0, 0, 100};// this is big endian + assertTrue(ByteConverter.bytesToInt(bytes2, ByteOrder.BIG_ENDIAN) == int1); + //check single bytes to integers + assertTrue(ByteConverter.bytesToInt((byte)100) == int1); + } + + public boolean testArrayContents(byte[] bytes1, byte[] bytes2){ + if (bytes1.length != bytes2.length){ + return false; + } + for (int i = 0; i < bytes1.length; i++){ + if (bytes1[i] != bytes2[i]){ + return false; + } + } + return true; + } + +}