Skip to content

Commit

Permalink
Merge pull request #2285 from nicolatimeus/enh_binary-parser
Browse files Browse the repository at this point in the history
Changes to the binary parser library
  • Loading branch information
MMaiero authored Oct 18, 2018
2 parents f908a16 + 3fddcc1 commit 13b3696
Show file tree
Hide file tree
Showing 25 changed files with 835 additions and 216 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
/*******************************************************************************
* Copyright (c) 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Eurotech
*******************************************************************************/
package org.eclipse.kura.driver.binary;

import static java.util.Objects.requireNonNull;

public abstract class AbstractBinaryData<T> implements BinaryData<T> {

protected final Endianness endianness;
protected final int size;

/**
* Creates a new {@link BinaryData} instance.
*
* @param endianness
* the endianness of the data
* @param size
* the size of the data
*/
public AbstractBinaryData(Endianness endianness, int size) {
requireNonNull(endianness, "Endianness cannot be null");
if (size <= 0) {
throw new IllegalArgumentException("Size must be positive");
}
this.endianness = endianness;
this.size = size;
}

/**
* @return the endianness of the data
*/
public Endianness getEndianness() {
return this.endianness;
}

/**
* @return the size of the data
*/
public int getSize() {
return this.size;
}

}
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,49 +12,23 @@

package org.eclipse.kura.driver.binary;

import static java.util.Objects.requireNonNull;

/**
* This class can be used to read/write a block of data in a {@link Buffer} to/from an instance of type T.
*
* @param <T>
* the type to be used for reading or writing.
*/
public abstract class BinaryData<T> {

protected final Endianness endianness;
protected final int size;

/**
* Creates a new {@link BinaryData} instance.
*
* @param endianness
* the endianness of the data
* @param size
* the size of the data
*/
public BinaryData(Endianness endianness, int size) {
requireNonNull(endianness, "Endianness cannot be null");
if (size <= 0) {
throw new IllegalArgumentException("Size must be positive");
}
this.endianness = endianness;
this.size = size;
}
public interface BinaryData<T> {

/**
* @return the endianness of the data
*/
public Endianness getEndianness() {
return this.endianness;
}
public Endianness getEndianness();

/**
* @return the size of the data
*/
public int getSize() {
return this.size;
}
public int getSize();

/**
* Writes the provided value into the provided {@link Buffer}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
package org.eclipse.kura.driver.binary;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class ByteArray extends AbstractBinaryData<byte[]> {

private static final Logger logger = LoggerFactory.getLogger(ByteArray.class);

public ByteArray(int size) {
super(Endianness.LITTLE_ENDIAN, size);
}

@Override
public void write(Buffer buf, int offset, byte[] value) {

final int transferSize = getTransferSize(buf, offset);

buf.write(offset, transferSize, value);
}

@Override
public byte[] read(final Buffer buf, final int offset) {

final int transferSize = getTransferSize(buf, offset);
byte[] data = new byte[transferSize];

buf.read(offset, data);

return data;
}

private int getTransferSize(final Buffer buf, final int offset) {

final int size = getSize();
final int bufferAvailable = buf.getLength() - offset;

if (bufferAvailable < size) {
logger.debug("received buffer is too small");
}

return Math.min(bufferAvailable, size);
}

@Override
public Class<byte[]> getValueType() {
return byte[].class;
}

}
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class Double extends BinaryData<java.lang.Double> {
class Double extends AbstractBinaryData<java.lang.Double> {

public Double(Endianness endianness) {
super(endianness, 8);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class Float extends BinaryData<java.lang.Float> {
class Float extends AbstractBinaryData<java.lang.Float> {

public Float(Endianness endianness) {
super(endianness, 4);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class Int16 extends BinaryData<Integer> {
class Int16 extends AbstractBinaryData<Integer> {

public Int16(Endianness endianness) {
super(endianness, 2);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class Int32 extends BinaryData<Integer> {
class Int32 extends AbstractBinaryData<Integer> {

public Int32(Endianness endianness) {
super(endianness, 4);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class Int64 extends BinaryData<Long> {
class Int64 extends AbstractBinaryData<Long> {

public Int64(Endianness endianness) {
super(endianness, 8);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class Int8 extends BinaryData<Integer> {
class Int8 extends AbstractBinaryData<Integer> {

public Int8() {
super(Endianness.BIG_ENDIAN, 1);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
package org.eclipse.kura.driver.binary;

import java.math.BigInteger;
import java.util.Arrays;
import java.util.function.Function;

import org.eclipse.kura.type.BooleanValue;
import org.eclipse.kura.type.DataType;
import org.eclipse.kura.type.DoubleValue;
import org.eclipse.kura.type.FloatValue;
import org.eclipse.kura.type.IntegerValue;
import org.eclipse.kura.type.LongValue;
import org.eclipse.kura.type.StringValue;
import org.eclipse.kura.type.TypedValue;

public final class TypeUtil {

private TypeUtil() {
}

public static <T> Function<T, TypedValue<?>> toTypedValue(final Class<T> sourceType, final DataType targetType) {
if (targetType == DataType.STRING) {
if (sourceType == byte[].class) {
return value -> new StringValue(Arrays.toString((byte[]) value));
} else {
return value -> new StringValue(value.toString());
}
}
if (targetType == DataType.BOOLEAN) {
if (sourceType == Boolean.class) {
return value -> new BooleanValue((Boolean) value);
} else if (sourceType == String.class) {
return value -> new BooleanValue(Boolean.parseBoolean((String) value));
} else if (sourceType.isAssignableFrom(Number.class)) {
return value -> new BooleanValue(((Number) value).doubleValue() != 0);
}
}
if (Number.class.isAssignableFrom(sourceType)) {
if (targetType == DataType.INTEGER) {
return value -> new IntegerValue(((Number) value).intValue());
} else if (targetType == DataType.LONG) {
return value -> new LongValue(((Number) value).longValue());
} else if (targetType == DataType.FLOAT) {
return value -> new FloatValue(((Number) value).floatValue());
} else if (targetType == DataType.DOUBLE) {
return value -> new DoubleValue(((Number) value).doubleValue());
}
}
if (sourceType == String.class) {
if (targetType == DataType.INTEGER) {
return value -> new IntegerValue(Integer.parseInt((String) value));
} else if (targetType == DataType.LONG) {
return value -> new LongValue(Long.parseLong((String) value));
} else if (targetType == DataType.FLOAT) {
return value -> new FloatValue(java.lang.Float.parseFloat((String) value));
} else if (targetType == DataType.DOUBLE) {
return value -> new DoubleValue(java.lang.Double.parseDouble((String) value));
}
}
throw new IllegalArgumentException("Cannot convert from native type " + sourceType.getSimpleName()
+ " to Kura data type " + targetType.name());
}

@SuppressWarnings("unchecked")
public static <T> Function<TypedValue<?>, T> fromTypedValue(final Class<T> targetType, final DataType sourceType) {
if (targetType == String.class) {
if (sourceType == DataType.BYTE_ARRAY) {
return value -> (T) Arrays.toString((byte[]) value.getValue());
} else {
return value -> (T) value.toString();
}
}
if (targetType == Boolean.class) {
if (sourceType == DataType.BOOLEAN) {
return value -> (T) value.getValue();
} else if (sourceType == DataType.STRING) {
return value -> (T) (Boolean) Boolean.parseBoolean((String) value.getValue());
} else if (sourceType != DataType.BYTE_ARRAY) {
return value -> (T) (Boolean) (((Number) value.getValue()).doubleValue() != 0);
}
}
if (sourceType == DataType.STRING) {
if (targetType == Integer.class) {
return value -> (T) (Integer) Integer.parseInt((String) value.getValue());
} else if (targetType == Long.class) {
return value -> (T) (Long) Long.parseLong((String) value.getValue());
} else if (targetType == java.lang.Float.class) {
return value -> (T) (java.lang.Float) java.lang.Float.parseFloat((String) value.getValue());
} else if (targetType == java.lang.Double.class) {
return value -> (T) (java.lang.Double) java.lang.Double.parseDouble((String) value.getValue());
}
} else {
if (targetType == Integer.class) {
return value -> (T) (Integer) ((Number) value.getValue()).intValue();
} else if (targetType == Long.class) {
return value -> (T) (Long) ((Number) value.getValue()).longValue();
} else if (targetType == java.lang.Float.class) {
return value -> (T) (java.lang.Float) ((Number) value.getValue()).floatValue();
} else if (targetType == java.lang.Double.class) {
return value -> (T) (java.lang.Double) ((Number) value.getValue()).doubleValue();
} else if (targetType == BigInteger.class) {
return value -> (T) BigInteger.valueOf(((Number) value.getValue()).longValue());
}
}
throw new IllegalArgumentException("Cannot convert from Kura data type " + sourceType.name()
+ " to native type " + targetType.getSimpleName());
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2017 Eurotech and/or its affiliates and others
* Copyright (c) 2017, 2018 Eurotech and/or its affiliates and others
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
Expand All @@ -12,7 +12,7 @@

package org.eclipse.kura.driver.binary;

class UInt16 extends BinaryData<Integer> {
class UInt16 extends AbstractBinaryData<Integer> {

public UInt16(Endianness endianness) {
super(endianness, 2);
Expand Down
Loading

0 comments on commit 13b3696

Please sign in to comment.