From 22e4cfaf40a259be007bddc7b5cd765390de1c11 Mon Sep 17 00:00:00 2001 From: J08nY Date: Sat, 10 Feb 2018 19:59:41 +0100 Subject: Handle exceptions in Tests and TestSuites grafeully. --- src/cz/crcs/ectester/reader/output/TextTestWriter.java | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'src/cz/crcs/ectester/reader/output/TextTestWriter.java') diff --git a/src/cz/crcs/ectester/reader/output/TextTestWriter.java b/src/cz/crcs/ectester/reader/output/TextTestWriter.java index eb52937..cc168de 100644 --- a/src/cz/crcs/ectester/reader/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/TextTestWriter.java @@ -5,6 +5,7 @@ import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; import cz.crcs.ectester.common.util.ByteUtil; import cz.crcs.ectester.reader.CardMngr; +import cz.crcs.ectester.reader.response.Response; import cz.crcs.ectester.reader.test.CardTestSuite; import cz.crcs.ectester.reader.test.CommandTestable; @@ -27,7 +28,10 @@ public class TextTestWriter extends BaseTextTestWriter { protected String testableString(Testable t) { if (t instanceof CommandTestable) { CommandTestable cmd = (CommandTestable) t; - return writer.responseSuffix(cmd.getResponse()); + Response response = cmd.getResponse(); + if (response != null) { + return writer.responseSuffix(response); + } } return ""; } -- cgit v1.2.3-70-g09d2 From 89ddc1ec043075dbd19c2ec0bcd77b9b83302837 Mon Sep 17 00:00:00 2001 From: J08nY Date: Wed, 25 Apr 2018 14:10:23 +0200 Subject: Add ECTester version to test run output. --- src/cz/crcs/ectester/reader/ECTesterReader.java | 4 ++-- src/cz/crcs/ectester/reader/output/TextTestWriter.java | 2 ++ src/cz/crcs/ectester/reader/output/XMLTestWriter.java | 2 ++ src/cz/crcs/ectester/reader/output/YAMLTestWriter.java | 2 ++ src/cz/crcs/ectester/standalone/ECTesterStandalone.java | 4 ++-- src/cz/crcs/ectester/standalone/output/TextTestWriter.java | 6 +++++- src/cz/crcs/ectester/standalone/output/XMLTestWriter.java | 2 ++ src/cz/crcs/ectester/standalone/output/YAMLTestWriter.java | 2 ++ 8 files changed, 19 insertions(+), 5 deletions(-) (limited to 'src/cz/crcs/ectester/reader/output/TextTestWriter.java') diff --git a/src/cz/crcs/ectester/reader/ECTesterReader.java b/src/cz/crcs/ectester/reader/ECTesterReader.java index 84c0439..e982721 100644 --- a/src/cz/crcs/ectester/reader/ECTesterReader.java +++ b/src/cz/crcs/ectester/reader/ECTesterReader.java @@ -66,9 +66,9 @@ public class ECTesterReader { private Config cfg; private Options opts = new Options(); - private static final String VERSION = "v0.2.0"; + public static final String VERSION = "v0.2.0"; private static final String DESCRIPTION = "ECTesterReader " + VERSION + ", a javacard Elliptic Curve Cryptography support tester/utility."; - private static final String LICENSE = "MIT Licensed\nCopyright (c) 2016-2017 Petr Svenda "; + private static final String LICENSE = "MIT Licensed\nCopyright (c) 2016-2018 Petr Svenda "; private static final String CLI_HEADER = "\n" + DESCRIPTION + "\n\n"; private static final String CLI_FOOTER = "\n" + LICENSE; diff --git a/src/cz/crcs/ectester/reader/output/TextTestWriter.java b/src/cz/crcs/ectester/reader/output/TextTestWriter.java index cc168de..1dd21ae 100644 --- a/src/cz/crcs/ectester/reader/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/TextTestWriter.java @@ -5,6 +5,7 @@ import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; import cz.crcs.ectester.common.util.ByteUtil; import cz.crcs.ectester.reader.CardMngr; +import cz.crcs.ectester.reader.ECTesterReader; import cz.crcs.ectester.reader.response.Response; import cz.crcs.ectester.reader.test.CardTestSuite; import cz.crcs.ectester.reader.test.CommandTestable; @@ -41,6 +42,7 @@ public class TextTestWriter extends BaseTextTestWriter { if (suite instanceof CardTestSuite) { CardTestSuite cardSuite = (CardTestSuite) suite; StringBuilder sb = new StringBuilder(); + sb.append("═══ ECTester version: " + ECTesterReader.VERSION).append(System.lineSeparator()); sb.append("═══ Card ATR: ").append(ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)).append(System.lineSeparator()); try { CardMngr.CPLC cplc = cardSuite.getCard().getCPLC(); diff --git a/src/cz/crcs/ectester/reader/output/XMLTestWriter.java b/src/cz/crcs/ectester/reader/output/XMLTestWriter.java index ebe07a6..14b7763 100644 --- a/src/cz/crcs/ectester/reader/output/XMLTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/XMLTestWriter.java @@ -5,6 +5,7 @@ import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; import cz.crcs.ectester.common.util.ByteUtil; import cz.crcs.ectester.reader.CardMngr; +import cz.crcs.ectester.reader.ECTesterReader; import cz.crcs.ectester.reader.command.Command; import cz.crcs.ectester.reader.response.Response; import cz.crcs.ectester.reader.test.CardTestSuite; @@ -113,6 +114,7 @@ public class XMLTestWriter extends BaseXMLTestWriter { CardTestSuite cardSuite = (CardTestSuite) suite; Element result = doc.createElement("device"); result.setAttribute("type", "card"); + result.setAttribute("ectester", ECTesterReader.VERSION); result.appendChild(cplcElement(cardSuite.getCard())); Element atr = doc.createElement("ATR"); diff --git a/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java b/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java index 4f83ca8..4c908cc 100644 --- a/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java @@ -5,6 +5,7 @@ import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; import cz.crcs.ectester.common.util.ByteUtil; import cz.crcs.ectester.reader.CardMngr; +import cz.crcs.ectester.reader.ECTesterReader; import cz.crcs.ectester.reader.command.Command; import cz.crcs.ectester.reader.response.Response; import cz.crcs.ectester.reader.test.CardTestSuite; @@ -88,6 +89,7 @@ public class YAMLTestWriter extends BaseYAMLTestWriter { CardTestSuite cardSuite = (CardTestSuite) suite; Map result = new HashMap<>(); result.put("type", "card"); + result.put("ectester", ECTesterReader.VERSION); result.put("cplc", cplcObject(cardSuite.getCard())); result.put("ATR", ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)); return result; diff --git a/src/cz/crcs/ectester/standalone/ECTesterStandalone.java b/src/cz/crcs/ectester/standalone/ECTesterStandalone.java index caf99ae..5f2a420 100644 --- a/src/cz/crcs/ectester/standalone/ECTesterStandalone.java +++ b/src/cz/crcs/ectester/standalone/ECTesterStandalone.java @@ -70,9 +70,9 @@ public class ECTesterStandalone { private Options opts = new Options(); private TreeParser optParser; private TreeCommandLine cli; - private static final String VERSION = "v0.2.0"; + public static final String VERSION = "v0.2.0"; private static final String DESCRIPTION = "ECTesterStandalone " + VERSION + ", an Elliptic Curve Cryptography support tester/utility."; - private static final String LICENSE = "MIT Licensed\nCopyright (c) 2016-2017 Petr Svenda "; + private static final String LICENSE = "MIT Licensed\nCopyright (c) 2016-2018 Petr Svenda "; private static final String CLI_HEADER = "\n" + DESCRIPTION + "\n\n"; private static final String CLI_FOOTER = "\n" + LICENSE; diff --git a/src/cz/crcs/ectester/standalone/output/TextTestWriter.java b/src/cz/crcs/ectester/standalone/output/TextTestWriter.java index 716451b..26e1b1a 100644 --- a/src/cz/crcs/ectester/standalone/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/standalone/output/TextTestWriter.java @@ -3,6 +3,7 @@ package cz.crcs.ectester.standalone.output; import cz.crcs.ectester.common.output.BaseTextTestWriter; import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; +import cz.crcs.ectester.standalone.ECTesterStandalone; import cz.crcs.ectester.standalone.test.StandaloneTestSuite; import java.io.PrintStream; @@ -25,7 +26,10 @@ public class TextTestWriter extends BaseTextTestWriter { protected String deviceString(TestSuite suite) { if (suite instanceof StandaloneTestSuite) { StandaloneTestSuite standaloneSuite = (StandaloneTestSuite) suite; - return standaloneSuite.getLibrary().name(); + StringBuilder sb = new StringBuilder(); + sb.append("═══ ECTester version: " + ECTesterStandalone.VERSION).append(System.lineSeparator()); + sb.append("═══ " + standaloneSuite.getLibrary().name()).append(System.lineSeparator()); + return sb.toString(); } return ""; } diff --git a/src/cz/crcs/ectester/standalone/output/XMLTestWriter.java b/src/cz/crcs/ectester/standalone/output/XMLTestWriter.java index 63838cb..2a35ce3 100644 --- a/src/cz/crcs/ectester/standalone/output/XMLTestWriter.java +++ b/src/cz/crcs/ectester/standalone/output/XMLTestWriter.java @@ -4,6 +4,7 @@ import cz.crcs.ectester.common.output.BaseXMLTestWriter; import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; import cz.crcs.ectester.common.util.ByteUtil; +import cz.crcs.ectester.standalone.ECTesterStandalone; import cz.crcs.ectester.standalone.test.KeyAgreementTestable; import cz.crcs.ectester.standalone.test.KeyGeneratorTestable; import cz.crcs.ectester.standalone.test.SignatureTestable; @@ -118,6 +119,7 @@ public class XMLTestWriter extends BaseXMLTestWriter { StandaloneTestSuite standaloneSuite = (StandaloneTestSuite) suite; Element result = doc.createElement("device"); result.setAttribute("type", "library"); + result.setAttribute("ectester", ECTesterStandalone.VERSION); Element name = doc.createElement("name"); name.setTextContent(standaloneSuite.getLibrary().name()); diff --git a/src/cz/crcs/ectester/standalone/output/YAMLTestWriter.java b/src/cz/crcs/ectester/standalone/output/YAMLTestWriter.java index 1ec132d..c452133 100644 --- a/src/cz/crcs/ectester/standalone/output/YAMLTestWriter.java +++ b/src/cz/crcs/ectester/standalone/output/YAMLTestWriter.java @@ -4,6 +4,7 @@ import cz.crcs.ectester.common.output.BaseYAMLTestWriter; import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; import cz.crcs.ectester.common.util.ByteUtil; +import cz.crcs.ectester.standalone.ECTesterStandalone; import cz.crcs.ectester.standalone.test.KeyAgreementTestable; import cz.crcs.ectester.standalone.test.KeyGeneratorTestable; import cz.crcs.ectester.standalone.test.SignatureTestable; @@ -97,6 +98,7 @@ public class YAMLTestWriter extends BaseYAMLTestWriter { StandaloneTestSuite standaloneSuite = (StandaloneTestSuite) suite; Map result = new HashMap<>(); result.put("type", "library"); + result.put("ectester", ECTesterStandalone.VERSION); result.put("name", standaloneSuite.getLibrary().name()); return result; } -- cgit v1.2.3-70-g09d2 From 4db61445a293fd98a1c023df6ede143eeb88b84b Mon Sep 17 00:00:00 2001 From: J08nY Date: Tue, 3 Jul 2018 23:35:03 +0200 Subject: Add git commit to version number for better versioning of tests. --- nbproject/dist-build.xml | 5 +++++ src/cz/crcs/ectester/reader/ECTesterReader.java | 26 +++++++++++++++++----- .../ectester/reader/output/TextTestWriter.java | 2 +- .../crcs/ectester/reader/output/XMLTestWriter.java | 2 +- .../ectester/reader/output/YAMLTestWriter.java | 2 +- 5 files changed, 29 insertions(+), 8 deletions(-) (limited to 'src/cz/crcs/ectester/reader/output/TextTestWriter.java') diff --git a/nbproject/dist-build.xml b/nbproject/dist-build.xml index c317d95..b1bfadf 100644 --- a/nbproject/dist-build.xml +++ b/nbproject/dist-build.xml @@ -10,6 +10,10 @@ + + + + @@ -20,6 +24,7 @@ + diff --git a/src/cz/crcs/ectester/reader/ECTesterReader.java b/src/cz/crcs/ectester/reader/ECTesterReader.java index 7dc11fa..ab022dd 100644 --- a/src/cz/crcs/ectester/reader/ECTesterReader.java +++ b/src/cz/crcs/ectester/reader/ECTesterReader.java @@ -26,7 +26,6 @@ import cz.crcs.ectester.applet.ECTesterApplet; import cz.crcs.ectester.applet.EC_Consts; import cz.crcs.ectester.common.cli.CLITools; import cz.crcs.ectester.common.cli.Colors; -import cz.crcs.ectester.common.ec.EC_Curve; import cz.crcs.ectester.common.ec.EC_Params; import cz.crcs.ectester.common.output.OutputLogger; import cz.crcs.ectester.common.output.TestWriter; @@ -45,11 +44,14 @@ import org.apache.commons.cli.*; import javax.smartcardio.CardException; import javax.xml.parsers.ParserConfigurationException; import java.io.*; +import java.net.URL; +import java.net.URLClassLoader; import java.nio.file.Files; import java.util.Arrays; import java.util.LinkedList; import java.util.List; import java.util.Scanner; +import java.util.jar.Manifest; import static cz.crcs.ectester.applet.EC_Consts.KeyAgreement_ALG_EC_SVDP_DH; import static cz.crcs.ectester.applet.EC_Consts.Signature_ALG_ECDSA_SHA; @@ -69,16 +71,30 @@ public class ECTesterReader { private Options opts = new Options(); public static final String VERSION = "v0.2.0"; - private static final String DESCRIPTION = "ECTesterReader " + VERSION + ", a javacard Elliptic Curve Cryptography support tester/utility."; - private static final String LICENSE = "MIT Licensed\nCopyright (c) 2016-2018 Petr Svenda "; - private static final String CLI_HEADER = "\n" + DESCRIPTION + "\n\n"; - private static final String CLI_FOOTER = "\n" + LICENSE; + public static String GIT_COMMIT = ""; + private static String DESCRIPTION; + private static String LICENSE = "MIT Licensed\nCopyright (c) 2016-2018 Petr Svenda "; + private static String CLI_HEADER; + private static String CLI_FOOTER = "\n" + LICENSE; private static final byte[] SELECT_ECTESTERAPPLET = {(byte) 0x00, (byte) 0xa4, (byte) 0x04, (byte) 0x00, (byte) 0x0a, (byte) 0x45, (byte) 0x43, (byte) 0x54, (byte) 0x65, (byte) 0x73, (byte) 0x74, (byte) 0x65, (byte) 0x72, (byte) 0x30, (byte) 0x31}; private static final byte[] AID = {(byte) 0x45, (byte) 0x43, (byte) 0x54, (byte) 0x65, (byte) 0x73, (byte) 0x74, (byte) 0x65, (byte) 0x72, (byte) 0x30, (byte) 0x31}; private static final byte[] INSTALL_DATA = new byte[10]; + static { + URLClassLoader cl = (URLClassLoader) ECTesterReader.class.getClassLoader(); + try { + URL url = cl.findResource("META-INF/MANIFEST.MF"); + Manifest manifest = new Manifest(url.openStream()); + String commit = manifest.getMainAttributes().getValue("Git-Commit"); + GIT_COMMIT = (commit == null) ? "" : "(git " + commit + ")"; + } catch (Exception ignored) { } + + DESCRIPTION = "ECTesterReader " + VERSION + GIT_COMMIT + ", a javacard Elliptic Curve Cryptography support tester/utility."; + CLI_HEADER = "\n" + DESCRIPTION + "\n\n";; + } + private void run(String[] args) { try { CommandLine cli = parseArgs(args); diff --git a/src/cz/crcs/ectester/reader/output/TextTestWriter.java b/src/cz/crcs/ectester/reader/output/TextTestWriter.java index 1dd21ae..35d0900 100644 --- a/src/cz/crcs/ectester/reader/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/TextTestWriter.java @@ -42,7 +42,7 @@ public class TextTestWriter extends BaseTextTestWriter { if (suite instanceof CardTestSuite) { CardTestSuite cardSuite = (CardTestSuite) suite; StringBuilder sb = new StringBuilder(); - sb.append("═══ ECTester version: " + ECTesterReader.VERSION).append(System.lineSeparator()); + sb.append("═══ ECTester version: " + ECTesterReader.VERSION + ECTesterReader.GIT_COMMIT).append(System.lineSeparator()); sb.append("═══ Card ATR: ").append(ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)).append(System.lineSeparator()); try { CardMngr.CPLC cplc = cardSuite.getCard().getCPLC(); diff --git a/src/cz/crcs/ectester/reader/output/XMLTestWriter.java b/src/cz/crcs/ectester/reader/output/XMLTestWriter.java index 14b7763..00cc6c6 100644 --- a/src/cz/crcs/ectester/reader/output/XMLTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/XMLTestWriter.java @@ -114,7 +114,7 @@ public class XMLTestWriter extends BaseXMLTestWriter { CardTestSuite cardSuite = (CardTestSuite) suite; Element result = doc.createElement("device"); result.setAttribute("type", "card"); - result.setAttribute("ectester", ECTesterReader.VERSION); + result.setAttribute("ectester", ECTesterReader.VERSION + ECTesterReader.GIT_COMMIT); result.appendChild(cplcElement(cardSuite.getCard())); Element atr = doc.createElement("ATR"); diff --git a/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java b/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java index 820521d..080fa8b 100644 --- a/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/YAMLTestWriter.java @@ -86,7 +86,7 @@ public class YAMLTestWriter extends BaseYAMLTestWriter { CardTestSuite cardSuite = (CardTestSuite) suite; Map result = new LinkedHashMap<>(); result.put("type", "card"); - result.put("ectester", ECTesterReader.VERSION); + result.put("ectester", ECTesterReader.VERSION + ECTesterReader.GIT_COMMIT); result.put("cplc", cplcObject(cardSuite.getCard())); result.put("ATR", ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)); return result; -- cgit v1.2.3-70-g09d2 From 2defb6ef4806e6e79b70505b00dea1fbc2bcdf1d Mon Sep 17 00:00:00 2001 From: J08nY Date: Thu, 5 Jul 2018 22:27:40 +0200 Subject: Add testing of previous prime R to wrong test suite. --- README.md | 4 ++-- src/cz/crcs/ectester/common/cli/Colors.java | 4 ++++ .../ectester/common/output/BaseTextTestWriter.java | 4 ++-- .../crcs/ectester/reader/output/TextTestWriter.java | 7 ++++--- src/cz/crcs/ectester/reader/test/CardWrongSuite.java | 20 ++++++++++++++++---- 5 files changed, 28 insertions(+), 11 deletions(-) (limited to 'src/cz/crcs/ectester/reader/output/TextTestWriter.java') diff --git a/README.md b/README.md index 9305e3c..1bcef72 100644 --- a/README.md +++ b/README.md @@ -110,7 +110,7 @@ For format of this file see [FORMAT](docs/FORMAT.md). #### Test `-t / --test [test_suite]` -Perform support and performance tests of ECC. +Perform support,performance and vulnerability tests of ECC. Use with `-o / --output [out_type:]` to output the test results to a file. For possible formats of this file see [FORMAT](docs/FORMAT.md). @@ -165,7 +165,7 @@ This shows that JCardsim simulates 112b Fp support with default curve present an ═══ Date: 2018.05.02 20:29:38 ═══ ECTester version: v0.2.0 ═══ Card ATR: 3bfa1800008131fe454a434f5033315632333298 - OK ┳ Tests of 112b ALG_EC_FP support. ┃ SUCCESS ┃ All sub-tests matched the expected mask. + OK ┳ (0) Tests of 112b ALG_EC_FP support. ┃ SUCCESS ┃ All sub-tests matched the expected mask. ┣ OK ━ Allocate both keypairs 112b ALG_EC_FP ┃ SUCCESS ┃ 22 ms ┃ OK (0x9000) OK (0x9000) ┣ OK ━ Generate both keypairs ┃ SUCCESS ┃ 23 ms ┃ OK (0x9000) OK (0x9000) ┣ OK ━ Allocate both keypairs 112b ALG_EC_FP ┃ SUCCESS ┃ 0 ms ┃ OK (0x9000) OK (0x9000) diff --git a/src/cz/crcs/ectester/common/cli/Colors.java b/src/cz/crcs/ectester/common/cli/Colors.java index cdc42e8..7601088 100644 --- a/src/cz/crcs/ectester/common/cli/Colors.java +++ b/src/cz/crcs/ectester/common/cli/Colors.java @@ -90,4 +90,8 @@ public class Colors { public static String bold(String text) { return colored(text, Attribute.BOLD); } + + public static String underline(String text) { + return colored(text, Attribute.UNDERLINE); + } } \ No newline at end of file diff --git a/src/cz/crcs/ectester/common/output/BaseTextTestWriter.java b/src/cz/crcs/ectester/common/output/BaseTextTestWriter.java index eef767b..f28f90a 100644 --- a/src/cz/crcs/ectester/common/output/BaseTextTestWriter.java +++ b/src/cz/crcs/ectester/common/output/BaseTextTestWriter.java @@ -27,13 +27,13 @@ public abstract class BaseTextTestWriter implements TestWriter { @Override public void begin(TestSuite suite) { - output.println("═══ Running test suite: " + Colors.bold(suite.getName()) + " ═══"); + output.println("═══ " + Colors.underline("Running test suite:") + " " + Colors.bold(suite.getName()) + " ═══"); for (String d : suite.getDescription()) { output.println("═══ " + d); } DateFormat dateFormat = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss"); Date date = new Date(); - output.println("═══ Date: " + dateFormat.format(date)); + output.println("═══ " + Colors.underline("Date:") + " " + dateFormat.format(date)); output.print(deviceString(suite)); } diff --git a/src/cz/crcs/ectester/reader/output/TextTestWriter.java b/src/cz/crcs/ectester/reader/output/TextTestWriter.java index 35d0900..a8e4ce9 100644 --- a/src/cz/crcs/ectester/reader/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/TextTestWriter.java @@ -1,5 +1,6 @@ package cz.crcs.ectester.reader.output; +import cz.crcs.ectester.common.cli.Colors; import cz.crcs.ectester.common.output.BaseTextTestWriter; import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; @@ -42,12 +43,12 @@ public class TextTestWriter extends BaseTextTestWriter { if (suite instanceof CardTestSuite) { CardTestSuite cardSuite = (CardTestSuite) suite; StringBuilder sb = new StringBuilder(); - sb.append("═══ ECTester version: " + ECTesterReader.VERSION + ECTesterReader.GIT_COMMIT).append(System.lineSeparator()); - sb.append("═══ Card ATR: ").append(ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)).append(System.lineSeparator()); + sb.append("═══ " + Colors.underline("ECTester version:") + " " + ECTesterReader.VERSION + ECTesterReader.GIT_COMMIT).append(System.lineSeparator()); + sb.append("═══ " + Colors.underline("Card ATR:") + " ").append(ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)).append(System.lineSeparator()); try { CardMngr.CPLC cplc = cardSuite.getCard().getCPLC(); if (!cplc.values().isEmpty()) { - sb.append("═══ Card CPLC data:").append(System.lineSeparator()); + sb.append("═══ " + Colors.underline("Card CPLC data:")).append(System.lineSeparator()); for (Map.Entry entry : cplc.values().entrySet()) { CardMngr.CPLC.Field field = entry.getKey(); byte[] value = entry.getValue(); diff --git a/src/cz/crcs/ectester/reader/test/CardWrongSuite.java b/src/cz/crcs/ectester/reader/test/CardWrongSuite.java index 2057093..34d151b 100644 --- a/src/cz/crcs/ectester/reader/test/CardWrongSuite.java +++ b/src/cz/crcs/ectester/reader/test/CardWrongSuite.java @@ -24,6 +24,7 @@ import java.util.Map; import java.util.Random; import static cz.crcs.ectester.common.test.Result.ExpectedValue; + /** * @author Jan Jancar johny@neuromancer.sk */ @@ -112,22 +113,33 @@ public class CardWrongSuite extends CardTestSuite { Test resetSetup = CompoundTest.all(ExpectedValue.SUCCESS, "Reset keypair.", set.clone()); Test randomG = ecdhTest(new Command.Transform(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.KEY_BOTH, EC_Consts.PARAMETER_G, (short) (EC_Consts.TRANSFORMATION_FULLRANDOM | EC_Consts.TRANSFORMATION_04_MASK)), "Set G = random non-point/point-like.", "ECDH with non-point G."); + Test fullRandomG = ecdhTest(new Command.Transform(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.KEY_BOTH, EC_Consts.PARAMETER_G, EC_Consts.TRANSFORMATION_FULLRANDOM), "Set G = random data.", "ECDH with G = random data."); Test zeroG = ecdhTest(new Command.Transform(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.KEY_BOTH, EC_Consts.PARAMETER_G, EC_Consts.TRANSFORMATION_INFINITY), "Set G = inifnity.", "ECDH with G = infinity."); - Test wrongG = CompoundTest.all(ExpectedValue.SUCCESS, "Tests with corrupted G parameter.", zeroG, randomG); + Test wrongG = CompoundTest.all(ExpectedValue.SUCCESS, "Tests with corrupted G parameter.", randomG, fullRandomG, zeroG); byte[] originalR = new byte[keyLength]; EC_Consts.getCurveParameter(curve, EC_Consts.PARAMETER_R, originalR, (short) 0); BigInteger originalBigR = new BigInteger(1, originalR); + + BigInteger prevPrimeR; + do { + prevPrimeR = BigInteger.probablePrime(keyLength, r); + } while (prevPrimeR.compareTo(originalBigR) >= 0); + byte[] prevRBytes = ECUtil.toByteArray(prevPrimeR, keyLength); + EC_Params prevRData = new EC_Params(EC_Consts.PARAMETER_R, new byte[][]{prevRBytes}); + Test prevprimeWrongR = ecdhTest(new Command.Set(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.CURVE_external, prevRData.getParams(), prevRData.flatten()), "Set R = some prime (but [r]G != infinity) smaller than original R.", "ECDH with wrong R, prevprime."); + BigInteger nextPrimeR = originalBigR.nextProbablePrime(); byte[] nextRBytes = ECUtil.toByteArray(nextPrimeR, keyLength); EC_Params nextRData = new EC_Params(EC_Consts.PARAMETER_R, new byte[][]{nextRBytes}); - Test primeWrongR = ecdhTest(new Command.Set(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.CURVE_external, nextRData.getParams(), nextRData.flatten()), "Set R = some prime (but [r]G != infinity).", "ECDH with wrong R, prime."); + Test nextprimeWrongR = ecdhTest(new Command.Set(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.CURVE_external, nextRData.getParams(), nextRData.flatten()), "Set R = some prime (but [r]G != infinity) larger than original R.", "ECDH with wrong R, nextprime."); + byte[] nonprimeRBytes = nextRBytes.clone(); nonprimeRBytes[0] ^= 1; EC_Params nonprimeWrongRData = new EC_Params(EC_Consts.PARAMETER_R, new byte[][]{nonprimeRBytes}); Test nonprimeWrongR = ecdhTest(new Command.Set(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.CURVE_external, nonprimeWrongRData.getParams(), nonprimeWrongRData.flatten()), "Set R = some composite (but [r]G != infinity).", "ECDH with wrong R, composite."); - Test wrongR = CompoundTest.all(ExpectedValue.SUCCESS, "Tests with corrupted R parameter.", primeWrongR, nonprimeWrongR); + Test wrongR = CompoundTest.all(ExpectedValue.SUCCESS, "Tests with corrupted R parameter.", prevprimeWrongR, nextprimeWrongR, nonprimeWrongR); doTest(CompoundTest.all(ExpectedValue.SUCCESS, "Tests of " + keyLength + "b " + CardUtil.getKeyTypeString(KeyPair.ALG_EC_FP), setup, wrongPrime, resetSetup, wrongG, resetSetup.clone(), wrongR, resetSetup.clone())); } @@ -197,6 +209,6 @@ public class CardWrongSuite extends CardTestSuite { return; } ecdh.run(); - },fullDesc, preparePhase, allocateECDH, ecdh); + }, fullDesc, preparePhase, allocateECDH, ecdh); } } -- cgit v1.2.3-70-g09d2 From 41e5246ed925eee65d86b8463635ea57e2eb706c Mon Sep 17 00:00:00 2001 From: J08nY Date: Wed, 18 Jul 2018 23:04:35 +0200 Subject: Elementary support for OpenSSL. --- build-standalone.xml | 5 + docs/LIBS.md | 9 +- .../ectester/reader/output/TextTestWriter.java | 6 +- .../ectester/standalone/ECTesterStandalone.java | 17 +- .../crcs/ectester/standalone/libs/OpensslLib.java | 19 + src/cz/crcs/ectester/standalone/libs/jni/Makefile | 10 +- .../standalone/libs/jni/NativeECPrivateKey.java | 6 + .../standalone/libs/jni/NativeECPublicKey.java | 6 + .../libs/jni/NativeKeyPairGeneratorSpi.java | 18 + .../standalone/libs/jni/NativeProvider.java | 10 + src/cz/crcs/ectester/standalone/libs/jni/botan.cpp | 50 --- .../crcs/ectester/standalone/libs/jni/cryptopp.cpp | 53 --- src/cz/crcs/ectester/standalone/libs/jni/native.h | 125 +++++++ src/cz/crcs/ectester/standalone/libs/jni/openssl.c | 393 +++++++++++++++++++++ .../crcs/ectester/standalone/libs/jni/tomcrypt.c | 1 + .../ectester/standalone/output/TextTestWriter.java | 5 +- 16 files changed, 617 insertions(+), 116 deletions(-) create mode 100644 src/cz/crcs/ectester/standalone/libs/OpensslLib.java create mode 100644 src/cz/crcs/ectester/standalone/libs/jni/openssl.c (limited to 'src/cz/crcs/ectester/reader/output/TextTestWriter.java') diff --git a/build-standalone.xml b/build-standalone.xml index 4190300..f1ff001 100644 --- a/build-standalone.xml +++ b/build-standalone.xml @@ -122,6 +122,11 @@ + + + + + diff --git a/docs/LIBS.md b/docs/LIBS.md index bfe20cd..59a183f 100644 --- a/docs/LIBS.md +++ b/docs/LIBS.md @@ -5,8 +5,8 @@ Popular libraries with at least some ECC support: - [libgcrypt](https://www.gnupg.org/related_software/libgcrypt/) - [mbedTLS](https://tls.mbed.org/) - [Nettle](http://www.lysator.liu.se/~nisse/nettle/) - - [OpenSSL](https://www.openssl.org/) - [OpenSSL (FIPS mode)](https://www.openssl.org/docs/fipsnotes.html) + - BoringSSL - [Microsoft CNG](https://msdn.microsoft.com/en-us/library/windows/desktop/aa376210(v=vs.85).aspx) - [Microsoft .NET crypto](https://docs.microsoft.com/en-us/dotnet/standard/security/cryptography-model) @@ -54,6 +54,13 @@ Popular libraries with at least some ECC support: - Uses Lopez-Dahab (Montgomery) ladder, XZ coordinates (ec2_mont.c): Fast multiplication on elliptic curves over GF(2^m) without precomputation (Algorithm 2P) - Contains an implementation of IEEE P1363 algorithm A.10.3 using affine coordinates (ec2_aff.c) - Has some custom arithmetic for some of the NIST primes. + - [OpenSSL](https://www.openssl.org/) + - C + - For prime field curves: + - Uses Jacobian coordinates, and Montgomery ladder, also uses wNAF-based interleaving multi-exponentiation method(ec_mult.c): http://www.bmoeller.de/pdf/TI-01-08.multiexp.pdf + - Also uses multiplication with precomputation by wNAF splitting(ec_mult.c) + - For binary field curves: + - Uses Jacobian coordinates, and Lopez-Dahab ladder, also uses wNAF-based interleaving multi-exponentiation method(ec2_smpl.c) - [Botan](https://botan.randombit.net/) - C++ - Uses blinded(randomized) Montgomery ladder. diff --git a/src/cz/crcs/ectester/reader/output/TextTestWriter.java b/src/cz/crcs/ectester/reader/output/TextTestWriter.java index a8e4ce9..ad35012 100644 --- a/src/cz/crcs/ectester/reader/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/reader/output/TextTestWriter.java @@ -43,12 +43,12 @@ public class TextTestWriter extends BaseTextTestWriter { if (suite instanceof CardTestSuite) { CardTestSuite cardSuite = (CardTestSuite) suite; StringBuilder sb = new StringBuilder(); - sb.append("═══ " + Colors.underline("ECTester version:") + " " + ECTesterReader.VERSION + ECTesterReader.GIT_COMMIT).append(System.lineSeparator()); - sb.append("═══ " + Colors.underline("Card ATR:") + " ").append(ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)).append(System.lineSeparator()); + sb.append("═══ ").append(Colors.underline("ECTester version:")).append(" ").append(ECTesterReader.VERSION).append(ECTesterReader.GIT_COMMIT).append(System.lineSeparator()); + sb.append("═══ ").append(Colors.underline("Card ATR:")).append(" ").append(ByteUtil.bytesToHex(cardSuite.getCard().getATR().getBytes(), false)).append(System.lineSeparator()); try { CardMngr.CPLC cplc = cardSuite.getCard().getCPLC(); if (!cplc.values().isEmpty()) { - sb.append("═══ " + Colors.underline("Card CPLC data:")).append(System.lineSeparator()); + sb.append("═══ ").append(Colors.underline("Card CPLC data:")).append(System.lineSeparator()); for (Map.Entry entry : cplc.values().entrySet()) { CardMngr.CPLC.Field field = entry.getKey(); byte[] value = entry.getValue(); diff --git a/src/cz/crcs/ectester/standalone/ECTesterStandalone.java b/src/cz/crcs/ectester/standalone/ECTesterStandalone.java index c223af6..9df6c61 100644 --- a/src/cz/crcs/ectester/standalone/ECTesterStandalone.java +++ b/src/cz/crcs/ectester/standalone/ECTesterStandalone.java @@ -66,7 +66,7 @@ import java.util.stream.Collectors; * @version v0.2.0 */ public class ECTesterStandalone { - private ProviderECLibrary[] libs = new ProviderECLibrary[]{new SunECLib(), new BouncyCastleLib(), new TomcryptLib(), new BotanLib(), new CryptoppLib()}; + private ProviderECLibrary[] libs = new ProviderECLibrary[]{new SunECLib(), new BouncyCastleLib(), new TomcryptLib(), new BotanLib(), new CryptoppLib(), new OpensslLib()}; private Config cfg; private Options opts = new Options(); @@ -205,6 +205,7 @@ public class ECTesterStandalone { opts.addOption(Option.builder("V").longOpt("version").desc("Print version info.").build()); opts.addOption(Option.builder("h").longOpt("help").desc("Print help.").build()); + opts.addOption(Option.builder("C").longOpt("color").desc("Print stuff with color, requires ANSI terminal.").build()); return optParser.parse(opts, args); } @@ -215,22 +216,22 @@ public class ECTesterStandalone { private void listLibraries() { for (ProviderECLibrary lib : libs) { if (lib.isInitialized() && (cfg.selected == null || lib == cfg.selected)) { - System.out.println("\t- " + lib.name()); + System.out.println("\t- " + Colors.bold(lib.name())); Set kpgs = lib.getKPGs(); if (!kpgs.isEmpty()) { - System.out.println("\t\t- KeyPairGenerators: " + String.join(", ", kpgs.stream().map(KeyPairGeneratorIdent::getName).collect(Collectors.toList()))); + System.out.println(Colors.bold("\t\t- KeyPairGenerators: ") + String.join(", ", kpgs.stream().map(KeyPairGeneratorIdent::getName).collect(Collectors.toList()))); } Set eckas = lib.getKAs(); if (!eckas.isEmpty()) { - System.out.println("\t\t- KeyAgreements: " + String.join(", ", eckas.stream().map(KeyAgreementIdent::getName).collect(Collectors.toList()))); + System.out.println(Colors.bold("\t\t- KeyAgreements: ") + String.join(", ", eckas.stream().map(KeyAgreementIdent::getName).collect(Collectors.toList()))); } Set sigs = lib.getSigs(); if (!sigs.isEmpty()) { - System.out.println("\t\t- Signatures: " + String.join(", ", sigs.stream().map(SignatureIdent::getName).collect(Collectors.toList()))); + System.out.println(Colors.bold("\t\t- Signatures: ") + String.join(", ", sigs.stream().map(SignatureIdent::getName).collect(Collectors.toList()))); } Set curves = lib.getCurves(); if (!curves.isEmpty()) { - System.out.println("\t\t- Curves: " + String.join(", ", curves)); + System.out.println(Colors.bold("\t\t- Curves: ") + String.join(", ", curves)); } System.out.println(); } @@ -540,12 +541,16 @@ public class ECTesterStandalone { public static class Config { private ProviderECLibrary[] libs; public ProviderECLibrary selected = null; + public boolean color = false; public Config(ProviderECLibrary[] libs) { this.libs = libs; } boolean readOptions(TreeCommandLine cli) { + color = cli.hasOption("color"); + Colors.enabled = color; + if (cli.isNext("generate") || cli.isNext("export") || cli.isNext("ecdh") || cli.isNext("ecdsa") || cli.isNext("test")) { if (!cli.hasArg(-1)) { System.err.println("Missing library name argument."); diff --git a/src/cz/crcs/ectester/standalone/libs/OpensslLib.java b/src/cz/crcs/ectester/standalone/libs/OpensslLib.java new file mode 100644 index 0000000..e558336 --- /dev/null +++ b/src/cz/crcs/ectester/standalone/libs/OpensslLib.java @@ -0,0 +1,19 @@ +package cz.crcs.ectester.standalone.libs; + +import java.security.Provider; +import java.util.Set; + +/** + * @author Jan Jancar johny@neuromancer.sk + */ +public class OpensslLib extends NativeECLibrary { + public OpensslLib() { + super("openssl_provider", "crypto"); + } + + @Override + native Provider createProvider(); + + @Override + public native Set getCurves(); +} diff --git a/src/cz/crcs/ectester/standalone/libs/jni/Makefile b/src/cz/crcs/ectester/standalone/libs/jni/Makefile index 17c1efb..9c3557c 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/Makefile +++ b/src/cz/crcs/ectester/standalone/libs/jni/Makefile @@ -42,7 +42,7 @@ CFLAGS+=-fPIC -g -I"$(JNI_INCLUDEDIR)" -I"$(JNI_PLATFORMINCLUDEDIR)" -I. CXXFLAGS+=-fPIC -g -I"$(JNI_INCLUDEDIR)" -I"$(JNI_PLATFORMINCLUDEDIR)" -I. -all: tomcrypt_provider.so botan_provider.so cryptopp_provider.so +all: tomcrypt_provider.so botan_provider.so cryptopp_provider.so openssl_provider.so # Common utils c_utils.o: c_utils.c @@ -52,6 +52,14 @@ cpp_utils.o: cpp_utils.cpp $(CXX) $(CXXFLAGS) -c $< +# OpenSSL shim +openssl_provider.so: openssl.o c_utils.o + $(CC) -fPIC -g -shared -o $@ $^ -L. $(shell pkg-config --libs openssl) + +openssl.o: openssl.c + $(CC) $(shel pkg-config --cflags openssl) $(CFLAGS) -c $< + + # Libtomcrypt shim tomcrypt_provider.so: tomcrypt.o c_utils.o $(CC) -fPIC -g -shared -o $@ $^ -L. -ltommath $(shell pkg-config --libs libtomcrypt) diff --git a/src/cz/crcs/ectester/standalone/libs/jni/NativeECPrivateKey.java b/src/cz/crcs/ectester/standalone/libs/jni/NativeECPrivateKey.java index a209fa1..39539df 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/NativeECPrivateKey.java +++ b/src/cz/crcs/ectester/standalone/libs/jni/NativeECPrivateKey.java @@ -71,4 +71,10 @@ public abstract class NativeECPrivateKey implements ECPrivateKey { super(keyData, params); } } + + public static class Openssl extends Raw { + public Openssl(byte[] keyData, ECParameterSpec params) { + super(keyData, params); + } + } } diff --git a/src/cz/crcs/ectester/standalone/libs/jni/NativeECPublicKey.java b/src/cz/crcs/ectester/standalone/libs/jni/NativeECPublicKey.java index f53cd26..1085083 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/NativeECPublicKey.java +++ b/src/cz/crcs/ectester/standalone/libs/jni/NativeECPublicKey.java @@ -73,4 +73,10 @@ public abstract class NativeECPublicKey implements ECPublicKey { super(keyData, params); } } + + public static class Openssl extends ANSIX962 { + public Openssl(byte[] keyData, ECParameterSpec params) { + super(keyData, params); + } + } } diff --git a/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyPairGeneratorSpi.java b/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyPairGeneratorSpi.java index a7b1a61..6e441e5 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyPairGeneratorSpi.java +++ b/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyPairGeneratorSpi.java @@ -155,4 +155,22 @@ public abstract class NativeKeyPairGeneratorSpi extends KeyPairGeneratorSpi { super("ECDSA"); } } + + public static class Openssl extends NativeKeyPairGeneratorSpi { + public Openssl() { + initialize(256, new SecureRandom()); + } + + @Override + native boolean keysizeSupported(int keysize); + + @Override + native boolean paramsSupported(AlgorithmParameterSpec params); + + @Override + native KeyPair generate(int keysize, SecureRandom random); + + @Override + native KeyPair generate(AlgorithmParameterSpec params, SecureRandom random); + } } diff --git a/src/cz/crcs/ectester/standalone/libs/jni/NativeProvider.java b/src/cz/crcs/ectester/standalone/libs/jni/NativeProvider.java index 593295e..a4967e5 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/NativeProvider.java +++ b/src/cz/crcs/ectester/standalone/libs/jni/NativeProvider.java @@ -49,4 +49,14 @@ public abstract class NativeProvider extends Provider { @Override native void setup(); } + + public static class Openssl extends NativeProvider { + + public Openssl(String name, double version, String info) { + super(name, version, info); + } + + @Override + native void setup(); + } } diff --git a/src/cz/crcs/ectester/standalone/libs/jni/botan.cpp b/src/cz/crcs/ectester/standalone/libs/jni/botan.cpp index 6a1e6d6..a37cb88 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/botan.cpp +++ b/src/cz/crcs/ectester/standalone/libs/jni/botan.cpp @@ -20,11 +20,6 @@ static jclass provider_class; -/* - * Class: cz_crcs_ectester_standalone_libs_BotanLib - * Method: createProvider - * Signature: ()Ljava/security/Provider; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_BotanLib_createProvider(JNIEnv *env, jobject self) { /* Create the custom provider. */ jclass local_provider_class = env->FindClass("cz/crcs/ectester/standalone/libs/jni/NativeProvider$Botan"); @@ -44,11 +39,6 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_BotanLib_createP return env->NewObject(provider_class, init, name, version, info); } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeProvider_Botan - * Method: setup - * Signature: ()V - */ JNIEXPORT void JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeProvider_00024Botan_setup(JNIEnv *env, jobject self){ jmethodID provider_put = env->GetMethodID(provider_class, "put", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;"); @@ -88,11 +78,6 @@ JNIEXPORT void JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeProvider_ init_classes(env, "Botan"); } -/* - * Class: cz_crcs_ectester_standalone_libs_BotanLib - * Method: getCurves - * Signature: ()Ljava/util/Set; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_BotanLib_getCurves(JNIEnv *env, jobject self){ jclass set_class = env->FindClass("java/util/TreeSet"); @@ -111,20 +96,10 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_BotanLib_getCurv return result; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Botan - * Method: keysizeSupported - * Signature: (I)Z - */ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Botan_keysizeSupported(JNIEnv *env, jobject self, jint keysize){ return JNI_TRUE; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Botan - * Method: paramsSupported - * Signature: (Ljava/security/spec/AlgorithmParameterSpec;)Z - */ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Botan_paramsSupported(JNIEnv *env, jobject self, jobject params){ if (params == NULL) { return JNI_FALSE; @@ -319,11 +294,6 @@ static jobject generate_from_group(JNIEnv* env, jobject self, Botan::EC_Group gr return env->NewObject(keypair_class, keypair_init, pubkey, privkey); } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Botan - * Method: generate - * Signature: (ILjava/security/SecureRandom;)Ljava/security/KeyPair; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Botan_generate__ILjava_security_SecureRandom_2(JNIEnv *env, jobject self, jint keysize, jobject random){ const std::set& curves = Botan::EC_Group::known_named_groups(); for (auto it = curves.begin(); it != curves.end(); ++it) { @@ -339,21 +309,11 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPai return NULL; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Botan - * Method: generate - * Signature: (Ljava/security/spec/AlgorithmParameterSpec;Ljava/security/SecureRandom;)Ljava/security/KeyPair; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Botan_generate__Ljava_security_spec_AlgorithmParameterSpec_2Ljava_security_SecureRandom_2(JNIEnv *env, jobject self, jobject params, jobject random){ Botan::EC_Group curve_group = group_from_params(env, params); return generate_from_group(env, self, curve_group); } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_Botan - * Method: generateSecret - * Signature: ([B[BLjava/security/spec/ECParameterSpec;)[B - */ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_00024Botan_generateSecret(JNIEnv *env, jobject self, jbyteArray pubkey, jbyteArray privkey, jobject params){ Botan::EC_Group curve_group = group_from_params(env, params); @@ -420,11 +380,6 @@ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKey return result; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_Botan - * Method: sign - * Signature: ([B[BLjava/security/spec/ECParameterSpec;)[B - */ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_00024Botan_sign(JNIEnv *env, jobject self, jbyteArray data, jbyteArray privkey, jobject params){ Botan::EC_Group curve_group = group_from_params(env, params); @@ -488,11 +443,6 @@ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSig return result; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_Botan - * Method: verify - * Signature: ([B[B[BLjava/security/spec/ECParameterSpec;)Z - */ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_00024Botan_verify(JNIEnv *env, jobject self, jbyteArray signature, jbyteArray data, jbyteArray pubkey, jobject params){ Botan::EC_Group curve_group = group_from_params(env, params); diff --git a/src/cz/crcs/ectester/standalone/libs/jni/cryptopp.cpp b/src/cz/crcs/ectester/standalone/libs/jni/cryptopp.cpp index e83f808..0ba026f 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/cryptopp.cpp +++ b/src/cz/crcs/ectester/standalone/libs/jni/cryptopp.cpp @@ -70,11 +70,6 @@ using CryptoPP::Integer; static jclass provider_class; -/* - * Class: cz_crcs_ectester_standalone_libs_CryptoppLib - * Method: createProvider - * Signature: ()Ljava/security/Provider; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_CryptoppLib_createProvider(JNIEnv *env, jobject self) { /* Create the custom provider. */ jclass local_provider_class = env->FindClass("cz/crcs/ectester/standalone/libs/jni/NativeProvider$Cryptopp"); @@ -100,11 +95,6 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_CryptoppLib_crea return env->NewObject(provider_class, init, name, version, info); } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeProvider_Cryptopp - * Method: setup - * Signature: ()V - */ JNIEXPORT void JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeProvider_00024Cryptopp_setup(JNIEnv *env, jobject self){ jmethodID provider_put = env->GetMethodID(provider_class, "put", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;"); @@ -157,11 +147,6 @@ static std::string oid_to_str(const OID &oid) { return ss.str(); } -/* - * Class: cz_crcs_ectester_standalone_libs_CryptoppLib - * Method: getCurves - * Signature: ()Ljava/util/Set; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_CryptoppLib_getCurves(JNIEnv *env, jobject self){ jclass set_class = env->FindClass("java/util/TreeSet"); @@ -180,11 +165,6 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_CryptoppLib_getC return result; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Cryptopp - * Method: keysizeSupported - * Signature: (I)Z - */ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Cryptopp_keysizeSupported(JNIEnv *env, jobject self, jint keysize){ std::vector ecp_oids = get_curve_oids(); for (auto oid = ecp_oids.begin(); oid != ecp_oids.end(); ++oid) { @@ -204,11 +184,6 @@ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPa return JNI_FALSE; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Cryptopp - * Method: paramsSupported - * Signature: (Ljava/security/spec/AlgorithmParameterSpec;)Z - */ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Cryptopp_paramsSupported(JNIEnv *env, jobject self, jobject params){ if (params == NULL) { return JNI_FALSE; @@ -546,11 +521,6 @@ template jobject generate_from_group(JNIEnv *env, DL_GroupParameters_ return env->NewObject(keypair_class, keypair_init, pubkey, privkey); } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Cryptopp - * Method: generate - * Signature: (ILjava/security/SecureRandom;)Ljava/security/KeyPair; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Cryptopp_generate__ILjava_security_SecureRandom_2(JNIEnv *env, jobject self, jint keysize, jobject random){ std::vector ecp_oids = get_curve_oids(); for (auto oid = ecp_oids.begin(); oid != ecp_oids.end(); ++oid) { @@ -572,11 +542,6 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPai return NULL; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Cryptopp - * Method: generate - * Signature: (Ljava/security/spec/AlgorithmParameterSpec;Ljava/security/SecureRandom;)Ljava/security/KeyPair; - */ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Cryptopp_generate__Ljava_security_spec_AlgorithmParameterSpec_2Ljava_security_SecureRandom_2(JNIEnv *env, jobject self, jobject params, jobject random) { std::unique_ptr> ecp_group = fp_group_from_params(env, params); if (ecp_group == nullptr) { @@ -588,12 +553,6 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPai return NULL; } - -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_Cryptopp - * Method: generateSecret - * Signature: ([B[BLjava/security/spec/ECParameterSpec;)[B - */ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_00024Cryptopp_generateSecret(JNIEnv *env, jobject self, jbyteArray pubkey, jbyteArray privkey, jobject params) { jsize privkey_length = env->GetArrayLength(privkey); jbyte *privkey_data = env->GetByteArrayElements(privkey, NULL); @@ -663,12 +622,6 @@ jbyteArray sign_message(JNIEnv *env, DL_GroupParameters_EC group, jbyteArray return result; } - -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_Cryptopp - * Method: sign - * Signature: ([B[BLjava/security/spec/ECParameterSpec;)[B - */ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_00024Cryptopp_sign(JNIEnv *env, jobject self, jbyteArray data, jbyteArray privkey, jobject params) { jclass cryptopp_sig_class = env->FindClass("cz/crcs/ectester/standalone/libs/jni/NativeSignatureSpi$Cryptopp"); jfieldID type_id = env->GetFieldID(cryptopp_sig_class, "type", "Ljava/lang/String;"); @@ -715,7 +668,6 @@ JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSig return result; } - template jboolean verify_message(JNIEnv *env, DL_GroupParameters_EC group, jbyteArray data, jbyteArray signature, jbyteArray pubkey) { typename EC::Point pkey_point; @@ -739,11 +691,6 @@ jboolean verify_message(JNIEnv *env, DL_GroupParameters_EC group, jbyteArray return result; } -/* - * Class: cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_Cryptopp - * Method: verify - * Signature: ([B[B[BLjava/security/spec/ECParameterSpec;)Z - */ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSignatureSpi_00024Cryptopp_verify(JNIEnv *env, jobject self, jbyteArray signature, jbyteArray data, jbyteArray pubkey, jobject params) { jclass cryptopp_sig_class = env->FindClass("cz/crcs/ectester/standalone/libs/jni/NativeSignatureSpi$Cryptopp"); jfieldID type_id = env->GetFieldID(cryptopp_sig_class, "type", "Ljava/lang/String;"); diff --git a/src/cz/crcs/ectester/standalone/libs/jni/native.h b/src/cz/crcs/ectester/standalone/libs/jni/native.h index 9385a4b..6aacdd3 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/native.h +++ b/src/cz/crcs/ectester/standalone/libs/jni/native.h @@ -513,3 +513,128 @@ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeSigna } #endif #endif +/* Header for class cz_crcs_ectester_standalone_libs_OpensslLib */ + +#ifndef _Included_cz_crcs_ectester_standalone_libs_OpensslLib +#define _Included_cz_crcs_ectester_standalone_libs_OpensslLib +#ifdef __cplusplus +extern "C" { +#endif +/* + * Class: cz_crcs_ectester_standalone_libs_OpensslLib + * Method: createProvider + * Signature: ()Ljava/security/Provider; + */ +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_OpensslLib_createProvider + (JNIEnv *, jobject); + +/* + * Class: cz_crcs_ectester_standalone_libs_OpensslLib + * Method: getCurves + * Signature: ()Ljava/util/Set; + */ +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_OpensslLib_getCurves + (JNIEnv *, jobject); + +#ifdef __cplusplus +} +#endif +#endif +/* Header for class cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl */ + +#ifndef _Included_cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl +#define _Included_cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl +#ifdef __cplusplus +extern "C" { +#endif +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_serialVersionUID +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_serialVersionUID 1421746759512286392LL +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_MAX_ARRAY_SIZE +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_MAX_ARRAY_SIZE 2147483639L +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_KEYS +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_KEYS 0L +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_VALUES +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_VALUES 1L +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_ENTRIES +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_ENTRIES 2L +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_serialVersionUID +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_serialVersionUID 4112578634029874840LL +#undef cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_serialVersionUID +#define cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl_serialVersionUID -4298000515446427739LL +/* + * Class: cz_crcs_ectester_standalone_libs_jni_NativeProvider_Openssl + * Method: setup + * Signature: ()V + */ +JNIEXPORT void JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeProvider_00024Openssl_setup + (JNIEnv *, jobject); + +#ifdef __cplusplus +} +#endif +#endif +/* Header for class cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl */ + +#ifndef _Included_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl +#define _Included_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl +#ifdef __cplusplus +extern "C" { +#endif +/* + * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl + * Method: keysizeSupported + * Signature: (I)Z + */ +JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_keysizeSupported + (JNIEnv *, jobject, jint); + +/* + * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl + * Method: paramsSupported + * Signature: (Ljava/security/spec/AlgorithmParameterSpec;)Z + */ +JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_paramsSupported + (JNIEnv *, jobject, jobject); + +/* + * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl + * Method: generate + * Signature: (ILjava/security/SecureRandom;)Ljava/security/KeyPair; + */ +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_generate__ILjava_security_SecureRandom_2 + (JNIEnv *, jobject, jint, jobject); + +/* + * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_Openssl + * Method: generate + * Signature: (Ljava/security/spec/AlgorithmParameterSpec;Ljava/security/SecureRandom;)Ljava/security/KeyPair; + */ +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_generate__Ljava_security_spec_AlgorithmParameterSpec_2Ljava_security_SecureRandom_2 + (JNIEnv *, jobject, jobject, jobject); + +#ifdef __cplusplus +} +#endif +#endif +/* Header for class cz_crcs_ectester_standalone_libs_jni_NativeECPublicKey_Openssl */ + +#ifndef _Included_cz_crcs_ectester_standalone_libs_jni_NativeECPublicKey_Openssl +#define _Included_cz_crcs_ectester_standalone_libs_jni_NativeECPublicKey_Openssl +#ifdef __cplusplus +extern "C" { +#endif +#ifdef __cplusplus +} +#endif +#endif +/* Header for class cz_crcs_ectester_standalone_libs_jni_NativeECPrivateKey_Openssl */ + +#ifndef _Included_cz_crcs_ectester_standalone_libs_jni_NativeECPrivateKey_Openssl +#define _Included_cz_crcs_ectester_standalone_libs_jni_NativeECPrivateKey_Openssl +#ifdef __cplusplus +extern "C" { +#endif +#ifdef __cplusplus +} +#endif +#endif diff --git a/src/cz/crcs/ectester/standalone/libs/jni/openssl.c b/src/cz/crcs/ectester/standalone/libs/jni/openssl.c new file mode 100644 index 0000000..ae6a222 --- /dev/null +++ b/src/cz/crcs/ectester/standalone/libs/jni/openssl.c @@ -0,0 +1,393 @@ +#include "native.h" +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#include "c_utils.h" + + +static jclass provider_class; + +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_OpensslLib_createProvider(JNIEnv *env, jobject self) { + /* Create the custom provider. */ + jclass local_provider_class = (*env)->FindClass(env, "cz/crcs/ectester/standalone/libs/jni/NativeProvider$Openssl"); + provider_class = (*env)->NewGlobalRef(env, local_provider_class); + + jmethodID init = (*env)->GetMethodID(env, local_provider_class, "", "(Ljava/lang/String;DLjava/lang/String;)V"); + + jstring name = (*env)->NewStringUTF(env, OPENSSL_VERSION_TEXT); + double version = ((double)((OPENSSL_VERSION_NUMBER & 0xff000000L) >> 30)) + ((double)((OPENSSL_VERSION_NUMBER & 0xff0000L) >> 20)); + + return (*env)->NewObject(env, provider_class, init, name, version, name); +} + +JNIEXPORT void JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeProvider_00024Openssl_setup(JNIEnv *env, jobject self) { + OPENSSL_no_config(); + ERR_load_crypto_strings(); + OpenSSL_add_all_algorithms(); + + jmethodID provider_put = (*env)->GetMethodID(env, provider_class, "put", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;"); + + jstring ec = (*env)->NewStringUTF(env, "KeyPairGenerator.EC"); + jstring ec_value = (*env)->NewStringUTF(env, "cz.crcs.ectester.standalone.libs.jni.NativeKeyPairGeneratorSpi$Openssl"); + (*env)->CallObjectMethod(env, self, provider_put, ec, ec_value); + + init_classes(env, "Openssl"); +} + +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_OpensslLib_getCurves(JNIEnv *env, jobject self) { + jclass hash_set_class = (*env)->FindClass(env, "java/util/TreeSet"); + + jmethodID hash_set_ctr = (*env)->GetMethodID(env, hash_set_class, "", "()V"); + jmethodID hash_set_add = (*env)->GetMethodID(env, hash_set_class, "add", "(Ljava/lang/Object;)Z"); + + jobject result = (*env)->NewObject(env, hash_set_class, hash_set_ctr); + + size_t ncurves = EC_get_builtin_curves(NULL, 0); + EC_builtin_curve curves[ncurves]; + EC_get_builtin_curves(curves, ncurves); + + for (size_t i = 0; i < ncurves; ++i) { + jstring curve_name = (*env)->NewStringUTF(env, OBJ_nid2sn(curves[i].nid)); + (*env)->CallBooleanMethod(env, result, hash_set_add, curve_name); + } + + return result; +} + +JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_keysizeSupported(JNIEnv *env, jobject self, jint keysize) { + size_t ncurves = EC_get_builtin_curves(NULL, 0); + EC_builtin_curve curves[ncurves]; + EC_get_builtin_curves(curves, ncurves); + + for (size_t i = 0; i < ncurves; ++i) { + EC_GROUP *curve = EC_GROUP_new_by_curve_name(curves[i].nid); + if (EC_GROUP_get_degree(curve) == keysize) { + EC_GROUP_clear_free(curve); + return JNI_TRUE; + } + EC_GROUP_free(curve); + } + return JNI_FALSE; +} + +static jobject bignum_to_biginteger(JNIEnv *env, const BIGNUM *bn) { + jmethodID biginteger_init = (*env)->GetMethodID(env, biginteger_class, "", "(I[B)V"); + int size = BN_num_bytes(bn); + jbyteArray bytes = (*env)->NewByteArray(env, size); + jbyte *data = (*env)->GetByteArrayElements(env, bytes, NULL); + BN_bn2bin(bn, data); + (*env)->ReleaseByteArrayElements(env, bytes, data, JNI_COMMIT); + jobject result = (*env)->NewObject(env, biginteger_class, biginteger_init, 0, bytes); + return result; +} + +static BIGNUM *biginteger_to_bignum(JNIEnv *env, jobject bigint) { + jmethodID to_byte_array = (*env)->GetMethodID(env, biginteger_class, "toByteArray", "()[B"); + + jbyteArray byte_array = (jbyteArray) (*env)->CallObjectMethod(env, bigint, to_byte_array); + jsize byte_length = (*env)->GetArrayLength(env, byte_array); + jbyte *byte_data = (*env)->GetByteArrayElements(env, byte_array, NULL); + BIGNUM *result = BN_bin2bn(byte_data, byte_length, NULL); + (*env)->ReleaseByteArrayElements(env, byte_array, byte_data, JNI_ABORT); + return result; +} + +static EC_GROUP *create_curve(JNIEnv *env, jobject params) { + jmethodID get_curve = (*env)->GetMethodID(env, ec_parameter_spec_class, "getCurve", "()Ljava/security/spec/EllipticCurve;"); + jobject elliptic_curve = (*env)->CallObjectMethod(env, params, get_curve); + + jmethodID get_field = (*env)->GetMethodID(env, elliptic_curve_class, "getField", "()Ljava/security/spec/ECField;"); + jobject field = (*env)->CallObjectMethod(env, elliptic_curve, get_field); + + jmethodID get_bits = (*env)->GetMethodID(env, fp_field_class, "getFieldSize", "()I"); + jint bits = (*env)->CallIntMethod(env, field, get_bits); + jint bytes = (bits + 7) / 8; + + jmethodID get_a = (*env)->GetMethodID(env, elliptic_curve_class, "getA", "()Ljava/math/BigInteger;"); + jobject a = (*env)->CallObjectMethod(env, elliptic_curve, get_a); + BIGNUM *a_bn = biginteger_to_bignum(env, a); + + jmethodID get_b = (*env)->GetMethodID(env, elliptic_curve_class, "getB", "()Ljava/math/BigInteger;"); + jobject b = (*env)->CallObjectMethod(env, elliptic_curve, get_b); + BIGNUM *b_bn = biginteger_to_bignum(env, b); + + jmethodID get_g = (*env)->GetMethodID(env, ec_parameter_spec_class, "getGenerator", "()Ljava/security/spec/ECPoint;"); + jobject g = (*env)->CallObjectMethod(env, params, get_g); + + jmethodID get_x = (*env)->GetMethodID(env, point_class, "getAffineX", "()Ljava/math/BigInteger;"); + jobject gx = (*env)->CallObjectMethod(env, g, get_x); + BIGNUM *gx_bn = biginteger_to_bignum(env, gx); + + jmethodID get_y = (*env)->GetMethodID(env, point_class, "getAffineY", "()Ljava/math/BigInteger;"); + jobject gy = (*env)->CallObjectMethod(env, g, get_y); + BIGNUM *gy_bn = biginteger_to_bignum(env, gy); + + EC_GROUP *result; + EC_POINT *g_point; + + if ((*env)->IsInstanceOf(env, field, fp_field_class)) { + jmethodID get_p = (*env)->GetMethodID(env, fp_field_class, "getP", "()Ljava/math/BigInteger;"); + jobject p = (*env)->CallObjectMethod(env, field, get_p); + + BIGNUM *p_bn = biginteger_to_bignum(env, p); + result = EC_GROUP_new_curve_GFp(p_bn, a_bn, b_bn, NULL); + BN_free(p_bn); + + g_point = EC_POINT_new(result); + EC_POINT_set_affine_coordinates_GFp(result, g_point, gx_bn, gy_bn, NULL); + } else if ((*env)->IsInstanceOf(env, field, f2m_field_class)) { + + jmethodID get_reduction_poly = (*env)->GetMethodID(env, f2m_field_class, "getReductionPolynomial", "()Ljava/math/BigInteger;"); + jobject red_poly = (*env)->CallObjectMethod(env, field, get_reduction_poly); + + BIGNUM *p_bn = biginteger_to_bignum(env, red_poly); + result = EC_GROUP_new_curve_GF2m(p_bn, a_bn, b_bn, NULL); + BN_free(p_bn); + + g_point = EC_POINT_new(result); + EC_POINT_set_affine_coordinates_GF2m(result, g_point, gx_bn, gy_bn, NULL); + } else { + return NULL; + } + + BN_free(a_bn); + BN_free(b_bn); + + jmethodID get_n = (*env)->GetMethodID(env, ec_parameter_spec_class, "getOrder", "()Ljava/math/BigInteger;"); + jobject n = (*env)->CallObjectMethod(env, params, get_n); + BIGNUM *n_bn = biginteger_to_bignum(env, n); + + jmethodID get_h = (*env)->GetMethodID(env, ec_parameter_spec_class, "getCofactor", "()I"); + jint h = (*env)->CallIntMethod(env, params, get_h); + BIGNUM *h_bn = BN_new(); + BN_set_word(h_bn, h); + + EC_GROUP_set_generator(result, g_point, n_bn, h_bn); + + BN_free(gx_bn); + BN_free(gy_bn); + BN_free(n_bn); + BN_free(h_bn); + + return result; +} + +JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_paramsSupported(JNIEnv *env, jobject self, jobject params){ + if (params == NULL) { + return JNI_FALSE; + } + + if ((*env)->IsInstanceOf(env, params, ec_parameter_spec_class)) { + EC_GROUP *curve = create_curve(env, params); + jboolean result = (EC_GROUP_check(curve, NULL) == 1) ? JNI_TRUE : JNI_FALSE; + EC_GROUP_free(curve); + return result; + } else if ((*env)->IsInstanceOf(env, params, ecgen_parameter_spec_class)) { + jmethodID get_name = (*env)->GetMethodID(env, ecgen_parameter_spec_class, "getName", "()Ljava/lang/String;"); + jstring name = (*env)->CallObjectMethod(env, params, get_name); + const char *utf_name = (*env)->GetStringUTFChars(env, name, NULL); + size_t ncurves = EC_get_builtin_curves(NULL, 0); + EC_builtin_curve curves[ncurves]; + EC_get_builtin_curves(curves, ncurves); + for (size_t i = 0; i < ncurves; ++i) { + if (strcasecmp(utf_name, OBJ_nid2sn(curves[i].nid)) == 0) { + (*env)->ReleaseStringUTFChars(env, name, utf_name); + return JNI_TRUE; + } + } + (*env)->ReleaseStringUTFChars(env, name, utf_name); + return JNI_FALSE; + } else { + return JNI_FALSE; + } +} + +static jobject create_ec_param_spec(JNIEnv *env, const EC_GROUP *curve) { + int field_type = EC_METHOD_get_field_type(EC_GROUP_method_of(curve)); + BIGNUM *a; + BIGNUM *b; + + BIGNUM *gx; + BIGNUM *gy; + jobject field; + + if (field_type == NID_X9_62_prime_field) { + BIGNUM *p = BN_new(); + a = BN_new(); + b = BN_new(); + EC_GROUP_get_curve_GFp(curve, p, a, b, NULL); + + jobject p_int = bignum_to_biginteger(env, p); + + jmethodID fp_field_init = (*env)->GetMethodID(env, fp_field_class, "", "(Ljava/math/BigInteger;)V"); + field = (*env)->NewObject(env, fp_field_class, fp_field_init, p_int); + + BN_free(p); + + gx = BN_new(); + gy = BN_new(); + EC_POINT_get_affine_coordinates_GFp(curve, EC_GROUP_get0_generator(curve), gx, gy, NULL); + + } else if (field_type == NID_X9_62_characteristic_two_field) { + a = BN_new(); + b = BN_new(); + EC_GROUP_get_curve_GF2m(curve, NULL, a, b, NULL); + + int basis_type = EC_GROUP_get_basis_type(curve); + jintArray ks; + jint *ks_data; + if (basis_type == NID_X9_62_tpBasis) { + ks = (*env)->NewIntArray(env, 1); + ks_data = (*env)->GetIntArrayElements(env, ks, NULL); + EC_GROUP_get_trinomial_basis(curve, &ks_data[0]); + } else if (basis_type == NID_X9_62_ppBasis) { + ks = (*env)->NewIntArray(env, 3); + ks_data = (*env)->GetIntArrayElements(env, ks, NULL); + EC_GROUP_get_pentanomial_basis(curve, &ks_data[0], &ks_data[1], &ks_data[2]); + } else { + return NULL; + } + (*env)->ReleaseIntArrayElements(env, ks, ks_data, JNI_COMMIT); + + jint m = EC_GROUP_get_degree(curve); + + jmethodID f2m_field_init = (*env)->GetMethodID(env, f2m_field_class, "", "(I[I)V"); + field = (*env)->NewObject(env, f2m_field_class, f2m_field_init, m, ks); + + gx = BN_new(); + gy = BN_new(); + EC_POINT_get_affine_coordinates_GF2m(curve, EC_GROUP_get0_generator(curve), gx, gy, NULL); + } else { + return NULL; + } + + jobject a_int = bignum_to_biginteger(env, a); + jobject b_int = bignum_to_biginteger(env, b); + + jmethodID elliptic_curve_init = (*env)->GetMethodID(env, elliptic_curve_class, "", "(Ljava/security/spec/ECField;Ljava/math/BigInteger;Ljava/math/BigInteger;)V"); + jobject elliptic_curve = (*env)->NewObject(env, elliptic_curve_class, elliptic_curve_init, field, a_int, b_int); + fprintf(stderr, "field: %p, a_int: %p, b_int: %p\n", field, a_int, b_int); + fflush(stderr); + + BN_free(a); + BN_free(b); + + jobject gx_int = bignum_to_biginteger(env, gx); + jobject gy_int = bignum_to_biginteger(env, gy); + + BN_free(gx); + BN_free(gy); + + jmethodID point_init = (*env)->GetMethodID(env, point_class, "", "(Ljava/math/BigInteger;Ljava/math/BigInteger;)V"); + jobject g = (*env)->NewObject(env, point_class, point_init, gx_int, gy_int); + + jobject order = bignum_to_biginteger(env, EC_GROUP_get0_order(curve)); + jint cofactor = BN_get_word(EC_GROUP_get0_cofactor(curve)); + + jmethodID ec_parameter_spec_init = (*env)->GetMethodID(env, ec_parameter_spec_class, "", "(Ljava/security/spec/EllipticCurve;Ljava/security/spec/ECPoint;Ljava/math/BigInteger;I)V"); + return (*env)->NewObject(env, ec_parameter_spec_class, ec_parameter_spec_init, elliptic_curve, g, order, cofactor); +} + +static jobject generate_from_curve(JNIEnv *env, const EC_GROUP *curve) { + jint keysize = EC_GROUP_get_degree(curve); + unsigned long key_bytes = (keysize + 7) / 8; + + EC_KEY *key = EC_KEY_new(); + EC_KEY_set_group(key, curve); + EC_KEY_generate_key(key); + + jbyteArray priv_bytes = (*env)->NewByteArray(env, key_bytes); + jbyte *key_priv = (*env)->GetByteArrayElements(env, priv_bytes, NULL); + BN_bn2binpad(EC_KEY_get0_private_key(key), key_priv, key_bytes); + (*env)->ReleaseByteArrayElements(env, priv_bytes, key_priv, JNI_COMMIT); + + unsigned long key_len = 2*keysize + 1; + jbyteArray pub_bytes = (*env)->NewByteArray(env, key_len); + jbyte *key_pub = (*env)->GetByteArrayElements(env, pub_bytes, NULL); + EC_POINT_point2oct(curve, EC_KEY_get0_public_key(key), POINT_CONVERSION_UNCOMPRESSED, key_pub, key_len, NULL); + (*env)->ReleaseByteArrayElements(env, pub_bytes, key_pub, JNI_COMMIT); + + EC_KEY_free(key); + + jobject ec_param_spec = create_ec_param_spec(env, curve); + + jobject ec_pub_param_spec = (*env)->NewLocalRef(env, ec_param_spec); + jmethodID ec_pub_init = (*env)->GetMethodID(env, pubkey_class, "", "([BLjava/security/spec/ECParameterSpec;)V"); + jobject pubkey = (*env)->NewObject(env, pubkey_class, ec_pub_init, pub_bytes, ec_param_spec); + + jobject ec_priv_param_spec = (*env)->NewLocalRef(env, ec_param_spec); + jmethodID ec_priv_init = (*env)->GetMethodID(env, privkey_class, "", "([BLjava/security/spec/ECParameterSpec;)V"); + jobject privkey = (*env)->NewObject(env, privkey_class, ec_priv_init, priv_bytes, ec_priv_param_spec); + + jmethodID keypair_init = (*env)->GetMethodID(env, keypair_class, "", "(Ljava/security/PublicKey;Ljava/security/PrivateKey;)V"); + return (*env)->NewObject(env, keypair_class, keypair_init, pubkey, privkey); +} + +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_generate__ILjava_security_SecureRandom_2(JNIEnv *env, jobject self, jint keysize, jobject random) { + size_t ncurves = EC_get_builtin_curves(NULL, 0); + EC_builtin_curve curves[ncurves]; + EC_get_builtin_curves(curves, ncurves); + + EC_GROUP *curve = NULL; + for (size_t i = 0; i < ncurves; ++i) { + curve = EC_GROUP_new_by_curve_name(curves[i].nid); + if (EC_GROUP_get_degree(curve) == keysize) { + break; + } + EC_GROUP_free(curve); + } + + if (!curve) { + throw_new(env, "java/security/InvalidAlgorithmParameterException", "Curve for given bitsize not found."); + return NULL; + } + + jobject result = generate_from_curve(env, curve); + EC_GROUP_free(curve); + return result; +} + + + +JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPairGeneratorSpi_00024Openssl_generate__Ljava_security_spec_AlgorithmParameterSpec_2Ljava_security_SecureRandom_2(JNIEnv *env, jobject self, jobject params, jobject random) { + if ((*env)->IsInstanceOf(env, params, ec_parameter_spec_class)) { + EC_GROUP *curve = create_curve(env, params); + jobject result = generate_from_curve(env, curve); + EC_GROUP_free(curve); + return result; + } else if ((*env)->IsInstanceOf(env, params, ecgen_parameter_spec_class)) { + jmethodID get_name = (*env)->GetMethodID(env, ecgen_parameter_spec_class, "getName", "()Ljava/lang/String;"); + jstring name = (*env)->CallObjectMethod(env, params, get_name); + const char* utf_name = (*env)->GetStringUTFChars(env, name, NULL); + size_t ncurves = EC_get_builtin_curves(NULL, 0); + EC_builtin_curve curves[ncurves]; + EC_get_builtin_curves(curves, ncurves); + EC_GROUP *curve; + for (size_t i = 0; i < ncurves; ++i) { + if (strcasecmp(utf_name, OBJ_nid2sn(curves[i].nid)) == 0) { + curve = EC_GROUP_new_by_curve_name(curves[i].nid); + break; + } + } + (*env)->ReleaseStringUTFChars(env, name, utf_name); + if (!curve) { + throw_new(env, "java/security/InvalidAlgorithmParameterException", "Curve for given bitsize not found."); + return NULL; + } + jobject result = generate_from_curve(env, curve); + EC_GROUP_free(curve); + return result; + } else { + throw_new(env, "java/security/InvalidAlgorithmParameterException", "Curve not found."); + return NULL; + } +} \ No newline at end of file diff --git a/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c b/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c index 29ee707..dc3abd9 100644 --- a/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c +++ b/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c @@ -128,6 +128,7 @@ JNIEXPORT jboolean JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPa } curve++; } + (*env)->ReleaseStringUTFChars(env, name, utf_name); return JNI_FALSE; } else { return JNI_FALSE; diff --git a/src/cz/crcs/ectester/standalone/output/TextTestWriter.java b/src/cz/crcs/ectester/standalone/output/TextTestWriter.java index 2e29b07..93be3a8 100644 --- a/src/cz/crcs/ectester/standalone/output/TextTestWriter.java +++ b/src/cz/crcs/ectester/standalone/output/TextTestWriter.java @@ -1,5 +1,6 @@ package cz.crcs.ectester.standalone.output; +import cz.crcs.ectester.common.cli.Colors; import cz.crcs.ectester.common.output.BaseTextTestWriter; import cz.crcs.ectester.common.test.TestSuite; import cz.crcs.ectester.common.test.Testable; @@ -45,8 +46,8 @@ public class TextTestWriter extends BaseTextTestWriter { if (suite instanceof StandaloneTestSuite) { StandaloneTestSuite standaloneSuite = (StandaloneTestSuite) suite; StringBuilder sb = new StringBuilder(); - sb.append("═══ ECTester version: " + ECTesterStandalone.VERSION).append(System.lineSeparator()); - sb.append("═══ ").append(standaloneSuite.getLibrary().name()).append(System.lineSeparator()); + sb.append("═══ ").append(Colors.underline("ECTester version:")).append(" ").append(ECTesterStandalone.VERSION).append(System.lineSeparator()); + sb.append("═══ ").append(Colors.underline("Library:")).append(standaloneSuite.getLibrary().name()).append(System.lineSeparator()); return sb.toString(); } return ""; -- cgit v1.2.3-70-g09d2