summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorCGantert345 <57003061+CGantert345@users.noreply.github.com>2022-01-25 13:33:37 +0100
committerCGantert345 <57003061+CGantert345@users.noreply.github.com>2022-01-25 13:33:37 +0100
commit7af6c4ca50322258bbd23214920c4c9122482966 (patch)
tree83be3be35d497fbdc00bc5c10a7dc0bad2bd8aad /src
parentsignature validation changed to work with teh dynamic header version 2. (diff)
downloadUIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.tar
UIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.tar.gz
UIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.tar.bz2
UIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.tar.lz
UIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.tar.xz
UIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.tar.zst
UIC-barcode-7af6c4ca50322258bbd23214920c4c9122482966.zip
Diffstat (limited to 'src')
-rw-r--r--src/main/java/org/uic/barcode/asn1/uper/AsnUtils.java16
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/Constants.java3
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/api/IDynamicFrame.java3
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/api/SimpleData.java7
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/api/SimpleDynamicFrame.java68
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/api/SimpleLevel1Data.java1
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/v1/DynamicFrameCoderV1.java12
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/v2/DynamicFrameCoderV2.java2
-rw-r--r--src/main/java/org/uic/barcode/dynamicFrame/v2/Level1DataType.java25
-rw-r--r--src/test/java/org/uic/barcode/test/DynamicFrameV2FcbVersion3Test.java176
-rw-r--r--src/test/java/org/uic/barcode/test/DynamicFrameV2ValidityDateTest.java208
11 files changed, 472 insertions, 49 deletions
diff --git a/src/main/java/org/uic/barcode/asn1/uper/AsnUtils.java b/src/main/java/org/uic/barcode/asn1/uper/AsnUtils.java
index dbb95c9..414f181 100644
--- a/src/main/java/org/uic/barcode/asn1/uper/AsnUtils.java
+++ b/src/main/java/org/uic/barcode/asn1/uper/AsnUtils.java
@@ -1,5 +1,7 @@
package org.uic.barcode.asn1.uper;
+import java.math.BigInteger;
+
public class AsnUtils {
@@ -55,5 +57,19 @@ public class AsnUtils {
boolean result = (bytes[index / 8] & mask[index % 8]) != 0;
return result;
}
+
+ public static byte[] shiftBytesToLeft(byte[] bytes, int shift) {
+
+ // create from array
+ BigInteger bigInt = new BigInteger(bytes);
+
+ // shift
+ BigInteger shiftInt = bigInt.shiftLeft(shift);
+
+ // back to array
+ return shiftInt.toByteArray();
+
+ }
+
}
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/Constants.java b/src/main/java/org/uic/barcode/dynamicFrame/Constants.java
index ba15f3f..3623817 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/Constants.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/Constants.java
@@ -38,4 +38,7 @@ public class Constants {
public static String DYNAMIC_BARCODE_FORMAT_VERSION_1 = "U1";
public static String DYNAMIC_BARCODE_FORMAT_VERSION_2 = "U2";
+
+ public static String DYNAMIC_BARCODE_FORMAT_VERSION_1_BIN = "10101010110001";
+ public static String DYNAMIC_BARCODE_FORMAT_VERSION_2_BIN = "10101010110010";
}
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/api/IDynamicFrame.java b/src/main/java/org/uic/barcode/dynamicFrame/api/IDynamicFrame.java
index 1e8a0ff..d901a6e 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/api/IDynamicFrame.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/api/IDynamicFrame.java
@@ -79,8 +79,9 @@ public interface IDynamicFrame{
*
* @param bytes the bytes
* @return the dynamic header
+ * @throws EncodingFormatException
*/
- public void decode(byte[] bytes);
+ public void decode(byte[] bytes) throws EncodingFormatException;
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleData.java b/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleData.java
index cb762de..d6e1410 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleData.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleData.java
@@ -1,12 +1,5 @@
package org.uic.barcode.dynamicFrame.api;
-import org.uic.barcode.asn1.datatypes.CharacterRestriction;
-import org.uic.barcode.asn1.datatypes.HasExtensionMarker;
-import org.uic.barcode.asn1.datatypes.RestrictedString;
-import org.uic.barcode.asn1.datatypes.Sequence;
-import org.uic.barcode.asn1.datatypesimpl.OctetString;
-import org.uic.barcode.asn1.uper.UperEncoder;
-
/**
* The Class DataType.
*/
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleDynamicFrame.java b/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleDynamicFrame.java
index ec52758..65b81d6 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleDynamicFrame.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleDynamicFrame.java
@@ -120,7 +120,7 @@ public class SimpleDynamicFrame implements IDynamicFrame {
return DynamicFrameCoderV1.encode(this);
- } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1.equals(format)) {
+ } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2.equals(format)) {
return DynamicFrameCoderV2.encode(this);
@@ -135,13 +135,12 @@ public class SimpleDynamicFrame implements IDynamicFrame {
return DynamicFrameCoderV1.encode(level1Data);
- } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1.equals(format)) {
+ } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2.equals(format)) {
return DynamicFrameCoderV2.encode(level1Data);
}
-
- return null;
+ throw new EncodingFormatException("Dynamic Header Version not supported: " + format);
}
private byte[] getEncoded(String path, byte[] data) throws EncodingFormatException {
@@ -150,29 +149,29 @@ public class SimpleDynamicFrame implements IDynamicFrame {
return DynamicFrameCoderV1.getEncoded(path, data);
- } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1.equals(format)) {
+ } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2.equals(format)) {
return DynamicFrameCoderV2.getEncoded(path, data);
}
- return null;
+ throw new EncodingFormatException("Dynamic Header Version not supported: " + format);
}
- private byte[] encode(ILevel2Data level2SignedData2) throws EncodingFormatException {
+ private byte[] encode(ILevel2Data level2Data) throws EncodingFormatException {
if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1.equals(format)) {
- return DynamicFrameCoderV1.encode(level2SignedData2);
+ return DynamicFrameCoderV1.encode(level2Data);
- } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1.equals(format)) {
+ } else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2.equals(format)) {
- return DynamicFrameCoderV2.encode(level2SignedData2);
+ return DynamicFrameCoderV2.encode(level2Data);
}
- return null;
+ throw new EncodingFormatException("Dynamic Header Version not supported: " + format);
}
/**
@@ -182,22 +181,24 @@ public class SimpleDynamicFrame implements IDynamicFrame {
*
* @param bytes the bytes
* @return the dynamic header
+ * @throws EncodingFormatException
*/
- public void decode(byte[] bytes) {
+ public void decode(byte[] bytes) throws EncodingFormatException {
String format = getFormat(bytes);
if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1.equals(format)) {
DynamicFrameCoderV1.decode(this,bytes);
+ return;
} else if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2.equals(format)) {
DynamicFrameCoderV2.decode(this,bytes);
-
+ return;
}
-
+ throw new EncodingFormatException("Dynamic Header Version not supported");
}
@@ -211,12 +212,35 @@ public class SimpleDynamicFrame implements IDynamicFrame {
* @return true, if is static header
*/
private static String getFormat(byte[] data) {
- byte[] start = "U1".getBytes();
- if (start[0] != data[0] || start[1]!= start[1]) {
+
+ if (data == null || data.length < 4) return null;
+
+ byte[] startBits = new byte[4];
+ startBits[0] = data[0];
+ startBits[1] = data[1];
+ startBits[2] = data[2];
+ startBits[3] = data[3];
+
+ String start = AsnUtils.toBooleanString(startBits);
+
+ /*
+ * bitshift:
+ *
+ * version 1:
+ * optional Level2Data 1 bit
+ * length of format: 8 bit
+ *
+ * version 2:
+ * extensionIndicator 1 bit
+ * optional Level2Data 1 bit
+ * length of format: 8 bit
+ */
+
+ if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1_BIN.equals(start.substring(9, 23))) {
return Constants.DYNAMIC_BARCODE_FORMAT_VERSION_1;
}
- start = "U2".getBytes();
- if (start[0] != data[0] || start[1]!= start[1]) {
+
+ if (Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2_BIN.equals(start.substring(10, 24))) {
return Constants.DYNAMIC_BARCODE_FORMAT_VERSION_2;
}
return null;
@@ -392,13 +416,9 @@ public class SimpleDynamicFrame implements IDynamicFrame {
try {
- //byte[] encodedData = encode(level2Data.getLevel1Data());
- //String s1 = AsnUtils.toBooleanString(encodedData);
- //TODO
- byte[] encodedData2 = getEncoded("Level1Data", data);
- //String s2 = AsnUtils.toBooleanString(encodedData2);
+ byte[] encodedData = getEncoded("Level1Data", data);
- sig.update(encodedData2);
+ sig.update(encodedData);
} catch (SignatureException e) {
return Constants.LEVEL1_VALIDATION_SIG_ALG_NOT_IMPLEMENTED;
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleLevel1Data.java b/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleLevel1Data.java
index 241cf6d..e9b1d4e 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleLevel1Data.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/api/SimpleLevel1Data.java
@@ -3,7 +3,6 @@ package org.uic.barcode.dynamicFrame.api;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
-import org.uic.barcode.asn1.uper.UperEncoder;
/**
* The Class SignedDataType.
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/v1/DynamicFrameCoderV1.java b/src/main/java/org/uic/barcode/dynamicFrame/v1/DynamicFrameCoderV1.java
index 1cffa12..39fcf32 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/v1/DynamicFrameCoderV1.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/v1/DynamicFrameCoderV1.java
@@ -113,9 +113,9 @@ public class DynamicFrameCoderV1 {
}
- public static byte[] encode(ILevel2Data level2SignedData) throws EncodingFormatException {
+ public static byte[] encode(ILevel2Data level2Data) throws EncodingFormatException {
- Level2DataType asn = populateAsn(level2SignedData);
+ Level2DataType asn = populateAsn(level2Data);
return UperEncoder.encode(asn);
}
@@ -150,10 +150,10 @@ public class DynamicFrameCoderV1 {
asnLevel2.setLevel1Data(asnLevel1);
if (level2.getLevel2Data() != null) {
- DataType data2 = new DataType();
- data2.setFormat(level2.getLevel2Data().getFormat());
- data2.setData(new OctetString(level2.getLevel2Data().getData()));
- asnLevel2.setLevel2Data(data2);
+ DataType asnData = new DataType();
+ asnData.setFormat(level2.getLevel2Data().getFormat());
+ asnData.setData(new OctetString(level2.getLevel2Data().getData()));
+ asnLevel2.setLevel2Data(asnData);
}
return asnLevel2;
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/v2/DynamicFrameCoderV2.java b/src/main/java/org/uic/barcode/dynamicFrame/v2/DynamicFrameCoderV2.java
index bdaa31a..de475a9 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/v2/DynamicFrameCoderV2.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/v2/DynamicFrameCoderV2.java
@@ -120,7 +120,7 @@ public class DynamicFrameCoderV2 {
DynamicFrame asnFrame = new DynamicFrame();
- frame.setFormat(frame.getFormat());
+ asnFrame.setFormat(frame.getFormat());
if (frame.getLevel2Signature() != null && frame.getLevel2Signature().length > 0) {
asnFrame.setLevel2Signature(new OctetString(frame.getLevel2Signature()));
diff --git a/src/main/java/org/uic/barcode/dynamicFrame/v2/Level1DataType.java b/src/main/java/org/uic/barcode/dynamicFrame/v2/Level1DataType.java
index 1dff709..63db364 100644
--- a/src/main/java/org/uic/barcode/dynamicFrame/v2/Level1DataType.java
+++ b/src/main/java/org/uic/barcode/dynamicFrame/v2/Level1DataType.java
@@ -100,16 +100,16 @@ public class Level1DataType {
/** The End of validity year. */
@FieldOrder(order = 9)
@IntRange(minValue=2016,maxValue=2269)
- public Long EndOfValidityYear;
+ @Asn1Optional public Long EndOfValidityYear;
/** The End of validity day. */
@FieldOrder(order = 10)
@IntRange(minValue=1,maxValue=366)
- public Long EndOfValidityDay;
+ @Asn1Optional public Long EndOfValidityDay;
/** The End of validity time. */
@FieldOrder(order = 11)
- @IntRange(minValue=0,maxValue=1440)
+ @IntRange(minValue=0,maxValue=1439)
@Asn1Optional public Long EndOfValidityTime;
@@ -309,25 +309,26 @@ public class Level1DataType {
}
/**
- * Sets the end of validity date. The validity date has to be provided in UTC.
- *
+ * Sets the end of validity date.
* @param date the new end of validity date
*/
public void setEndOfValidityDate(Date date){
- if (date == null) {
- date = Calendar.getInstance().getTime();
- }
+ if (date == null) return;
+ TimeZone local = TimeZone.getDefault();
+ TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
+
Calendar cal = Calendar.getInstance();
cal.setTime(date);
-
+
this.EndOfValidityYear = new Long( cal.get(Calendar.YEAR));
this.EndOfValidityDay = new Long (cal.get(Calendar.DAY_OF_YEAR));
int time = cal.get(Calendar.HOUR_OF_DAY) * 60 + cal.get(Calendar.MINUTE);
if (time >= 0) {
this.EndOfValidityTime = new Long (time );
}
+ TimeZone.setDefault(local);
}
@@ -340,6 +341,9 @@ public class Level1DataType {
if (this.EndOfValidityYear == null || this.EndOfValidityDay == null) return null;
+ TimeZone local = TimeZone.getDefault();
+ TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
+
Calendar cal = Calendar.getInstance();
cal.clear();
cal.setTimeZone(TimeZone.getTimeZone("UTC"));
@@ -356,6 +360,9 @@ public class Level1DataType {
}
Date d = cal.getTime();
+
+ TimeZone.setDefault(local);
+
return d;
}
diff --git a/src/test/java/org/uic/barcode/test/DynamicFrameV2FcbVersion3Test.java b/src/test/java/org/uic/barcode/test/DynamicFrameV2FcbVersion3Test.java
new file mode 100644
index 0000000..8014b78
--- /dev/null
+++ b/src/test/java/org/uic/barcode/test/DynamicFrameV2FcbVersion3Test.java
@@ -0,0 +1,176 @@
+package org.uic.barcode.test;
+
+import java.io.IOException;
+import java.security.InvalidAlgorithmParameterException;
+import java.security.InvalidKeyException;
+import java.security.KeyPair;
+import java.security.KeyPairGenerator;
+import java.security.NoSuchAlgorithmException;
+import java.security.NoSuchProviderException;
+import java.security.SecureRandom;
+import java.security.Security;
+import java.security.SignatureException;
+import java.util.zip.DataFormatException;
+
+import org.bouncycastle.jce.ECNamedCurveTable;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+import org.bouncycastle.jce.spec.ECParameterSpec;
+import org.junit.Before;
+import org.junit.Test;
+import org.uic.barcode.Decoder;
+import org.uic.barcode.Encoder;
+import org.uic.barcode.dynamicFrame.Constants;
+import org.uic.barcode.dynamicFrame.api.IData;
+import org.uic.barcode.test.utils.SimpleUICTestTicket;
+import org.uic.barcode.ticket.EncodingFormatException;
+import org.uic.barcode.ticket.api.spec.IUicRailTicket;
+
+public class DynamicFrameV2FcbVersion3Test {
+
+ public String signatureAlgorithmOID = null;
+ public String elipticCurve = null;
+ public String keyPairAlgorithmOID = null;
+
+ public KeyPair keyPair = null;
+
+ public IUicRailTicket testFCBticket = null;
+
+
+ @Before public void initialize() {
+
+ signatureAlgorithmOID = Constants.ECDSA_SHA256;
+ keyPairAlgorithmOID = Constants.KG_EC_256;
+ elipticCurve = "secp256k1";
+
+ testFCBticket = SimpleUICTestTicket.getUicTestTicket();
+
+ Security.addProvider(new BouncyCastleProvider());
+
+ try {
+ keyPair = generateECKeys(Constants.KG_EC, elipticCurve);
+ //keyPair = generateECDSAKeys("ECDSA", "B-571");
+ } catch (Exception e) {
+ assert(false);
+ }
+
+ assert(keyPair != null);
+
+ }
+
+
+ @Test public void testDynamicHeaderBarcodeEncodingFCB3() {
+
+ IUicRailTicket ticket = testFCBticket;
+
+ Encoder enc = null;
+
+ try {
+ enc = new Encoder(ticket, null, Encoder.UIC_BARCODE_TYPE_DOSIPAS, 2, 3);
+ } catch (IOException | EncodingFormatException e1) {
+ assert(false);
+ }
+
+ assert(enc != null);
+
+ try {
+ enc.signLevel1("1080", keyPair.getPrivate(), signatureAlgorithmOID, "1");
+ } catch (Exception e) {
+ assert(false);
+ }
+
+
+ byte[] encoded = null;
+ try {
+ encoded = enc.encode();
+ } catch (Exception e) {
+ assert(false);
+ }
+
+ assert(encoded != null);
+
+
+ }
+
+ @Test public void testDynamicHeaderBarcodeDecodingFCB3() {
+
+ IUicRailTicket ticket = testFCBticket;
+
+ Encoder enc = null;
+
+ try {
+ enc = new Encoder(ticket, null, Encoder.UIC_BARCODE_TYPE_DOSIPAS, 2, 3);
+ } catch (IOException | EncodingFormatException e1) {
+ assert(false);
+ }
+
+ assert(enc != null);
+
+ try {
+ enc.signLevel1("1080", keyPair.getPrivate(), signatureAlgorithmOID, "1");
+ } catch (Exception e) {
+ assert(false);
+ }
+
+
+ byte[] encoded = null;
+ try {
+ encoded = enc.encode();
+ } catch (Exception e) {
+ assert(false);
+ }
+
+ assert(encoded != null);
+
+ Decoder dec = null;
+ try {
+ dec = new Decoder(encoded);
+ } catch (IOException e) {
+ assert(false);
+ } catch (EncodingFormatException e) {
+ assert(false);
+ } catch (DataFormatException e) {
+ assert(false);
+ }
+ assert(dec != null);
+
+ int signatureCheck = 0;
+ try {
+ signatureCheck = dec.validateLevel1(keyPair.getPublic(),null);
+ } catch (InvalidKeyException | NoSuchAlgorithmException | SignatureException | IllegalArgumentException
+ | UnsupportedOperationException | IOException | EncodingFormatException e) {
+ assert(false);
+ }
+
+ assert(signatureCheck == Constants.LEVEL1_VALIDATION_OK);
+
+ assert(dec.getDynamicHeader().getFormat().equals("U2"));
+
+ for (IData data : dec.getDynamicHeader().getLevel2Data().getLevel1Data().getData()) {
+ assert(data.getFormat().equals("FCB3") );
+ }
+
+ SimpleUICTestTicket.compare(ticket, dec.getUicTicket());
+
+
+
+
+ }
+
+ public KeyPair generateECDSAKeys(String keyAlgorithmName, String paramName) throws NoSuchAlgorithmException, NoSuchProviderException, InvalidAlgorithmParameterException{
+ ECParameterSpec ecSpec = ECNamedCurveTable.getParameterSpec(paramName);
+ KeyPairGenerator g = KeyPairGenerator.getInstance(keyAlgorithmName, "BC");
+ g.initialize(ecSpec, new SecureRandom());
+ return g.generateKeyPair();
+ }
+
+ public KeyPair generateECKeys(String keyAlgorithmOid, String curve) throws Exception{
+
+ String keyAlgorithmName = "ECDSA";
+ ECParameterSpec ecSpec = ECNamedCurveTable.getParameterSpec(curve);
+ KeyPairGenerator g = KeyPairGenerator.getInstance(keyAlgorithmName, "BC");
+ g.initialize(ecSpec, new SecureRandom());
+ return g.generateKeyPair();
+ }
+
+
+}
diff --git a/src/test/java/org/uic/barcode/test/DynamicFrameV2ValidityDateTest.java b/src/test/java/org/uic/barcode/test/DynamicFrameV2ValidityDateTest.java
new file mode 100644
index 0000000..03536c4
--- /dev/null
+++ b/src/test/java/org/uic/barcode/test/DynamicFrameV2ValidityDateTest.java
@@ -0,0 +1,208 @@
+package org.uic.barcode.test;
+
+import java.io.IOException;
+import java.security.InvalidAlgorithmParameterException;
+import java.security.InvalidKeyException;
+import java.security.KeyPair;
+import java.security.KeyPairGenerator;
+import java.security.NoSuchAlgorithmException;
+import java.security.NoSuchProviderException;
+import java.security.SecureRandom;
+import java.security.Security;
+import java.security.SignatureException;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.TimeZone;
+import java.util.zip.DataFormatException;
+
+import org.bouncycastle.jce.ECNamedCurveTable;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+import org.bouncycastle.jce.spec.ECParameterSpec;
+import org.junit.Before;
+import org.junit.Test;
+import org.uic.barcode.Decoder;
+import org.uic.barcode.Encoder;
+import org.uic.barcode.dynamicFrame.Constants;
+import org.uic.barcode.dynamicFrame.api.IData;
+import org.uic.barcode.test.utils.SimpleUICTestTicket;
+import org.uic.barcode.ticket.EncodingFormatException;
+import org.uic.barcode.ticket.api.spec.IUicRailTicket;
+
+public class DynamicFrameV2ValidityDateTest {
+
+ public String signatureAlgorithmOID = null;
+ public String elipticCurve = null;
+ public String keyPairAlgorithmOID = null;
+
+ public KeyPair keyPair = null;
+
+ public IUicRailTicket testFCBticket = null;
+
+
+ @Before public void initialize() {
+
+ signatureAlgorithmOID = Constants.ECDSA_SHA256;
+ keyPairAlgorithmOID = Constants.KG_EC_256;
+ elipticCurve = "secp256k1";
+
+ testFCBticket = SimpleUICTestTicket.getUicTestTicket();
+
+ Security.addProvider(new BouncyCastleProvider());
+
+ try {
+ keyPair = generateECKeys(Constants.KG_EC, elipticCurve);
+ //keyPair = generateECDSAKeys("ECDSA", "B-571");
+ } catch (Exception e) {
+ assert(false);
+ }
+
+ assert(keyPair != null);
+
+ }
+
+
+ @Test public void testDynamicHeaderBarcodeEncodingFCB3() {
+
+ IUicRailTicket ticket = testFCBticket;
+
+ Encoder enc = null;
+
+ try {
+ enc = new Encoder(ticket, null, Encoder.UIC_BARCODE_TYPE_DOSIPAS, 2, 3);
+ } catch (IOException | EncodingFormatException e1) {
+ assert(false);
+ }
+
+ assert(enc != null);
+
+ TimeZone local = TimeZone.getDefault();
+ TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
+ Date endDate = null;
+ try {
+ endDate = new SimpleDateFormat( "yyyy.MM.dd-HH:mm" ).parse( "2021.03.04-12:30" );
+ } catch (ParseException e1) {
+ assert(false);
+ }
+ TimeZone.setDefault(local);
+
+ enc.getDynamicFrame().getLevel2Data().getLevel1Data().setEndOfBarcodeValidity(endDate);
+
+ try {
+ enc.signLevel1("1080", keyPair.getPrivate(), signatureAlgorithmOID, "1");
+ } catch (Exception e) {
+ assert(false);
+ }
+
+
+ byte[] encoded = null;
+ try {
+ encoded = enc.encode();
+ } catch (Exception e) {
+ assert(false);
+ }
+
+ assert(encoded != null);
+
+
+ }
+
+ @Test public void testDynamicHeaderBarcodeDecodingFCB3() {
+
+ IUicRailTicket ticket = testFCBticket;
+
+ Encoder enc = null;
+
+ try {
+ enc = new Encoder(ticket, null, Encoder.UIC_BARCODE_TYPE_DOSIPAS, 2, 3);
+ } catch (IOException | EncodingFormatException e1) {
+ assert(false);
+ }
+
+ assert(enc != null);
+
+ TimeZone local = TimeZone.getDefault();
+ TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
+ Date endDate = null;
+ try {
+ endDate = new SimpleDateFormat( "yyyy.MM.dd-HH:mm" ).parse( "2021.03.04-12:30" );
+ } catch (ParseException e1) {
+ assert(false);
+ }
+ TimeZone.setDefault(local);
+
+ enc.getDynamicFrame().getLevel2Data().getLevel1Data().setEndOfBarcodeValidity(endDate);
+
+ try {
+ enc.signLevel1("1080", keyPair.getPrivate(), signatureAlgorithmOID, "1");
+ } catch (Exception e) {
+ assert(false);
+ }
+
+
+ byte[] encoded = null;
+ try {
+ encoded = enc.encode();
+ } catch (Exception e) {
+ assert(false);
+ }
+
+ assert(encoded != null);
+
+ Decoder dec = null;
+ try {
+ dec = new Decoder(encoded);
+ } catch (IOException e) {
+ assert(false);
+ } catch (EncodingFormatException e) {
+ assert(false);
+ } catch (DataFormatException e) {
+ assert(false);
+ }
+ assert(dec != null);
+
+ int signatureCheck = 0;
+ try {
+ signatureCheck = dec.validateLevel1(keyPair.getPublic(),null);
+ } catch (InvalidKeyException | NoSuchAlgorithmException | SignatureException | IllegalArgumentException
+ | UnsupportedOperationException | IOException | EncodingFormatException e) {
+ assert(false);
+ }
+
+ assert(signatureCheck == Constants.LEVEL1_VALIDATION_OK);
+
+ assert(dec.getDynamicHeader().getFormat().equals("U2"));
+
+ for (IData data : dec.getDynamicHeader().getLevel2Data().getLevel1Data().getData()) {
+ assert(data.getFormat().equals("FCB3") );
+ }
+
+ Date endDate2 = dec.getDynamicHeader().getLevel2Data().getLevel1Data().getEndOfBarcodeValidity();
+
+
+ TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
+ String date2 = new SimpleDateFormat( "yyyy.MM.dd-HH:mm" ).format(endDate2);
+ TimeZone.setDefault(local);
+
+ assert("2021.03.04-12:30".equals(date2));
+
+ }
+
+ public KeyPair generateECDSAKeys(String keyAlgorithmName, String paramName) throws NoSuchAlgorithmException, NoSuchProviderException, InvalidAlgorithmParameterException{
+ ECParameterSpec ecSpec = ECNamedCurveTable.getParameterSpec(paramName);
+ KeyPairGenerator g = KeyPairGenerator.getInstance(keyAlgorithmName, "BC");
+ g.initialize(ecSpec, new SecureRandom());
+ return g.generateKeyPair();
+ }
+
+ public KeyPair generateECKeys(String keyAlgorithmOid, String curve) throws Exception{
+
+ String keyAlgorithmName = "ECDSA";
+ ECParameterSpec ecSpec = ECNamedCurveTable.getParameterSpec(curve);
+ KeyPairGenerator g = KeyPairGenerator.getInstance(keyAlgorithmName, "BC");
+ g.initialize(ecSpec, new SecureRandom());
+ return g.generateKeyPair();
+ }
+
+
+}