diff options
15 files changed, 136 insertions, 22 deletions
diff --git a/docs/CURVES.md b/docs/CURVES.md index a9b8b68..a417035 100644 --- a/docs/CURVES.md +++ b/docs/CURVES.md @@ -41,6 +41,7 @@ Barreto-Naehrig curves from: A Family of Implementation-Friendly BN Elliptic Cur ### Other An assortment of some other curves. Montgomery curves transformed into short Weierstrass form from <https://eprint.iacr.org/2013/647.pdf> + Curve25519 transformed into short Weierstrass form. @@ -83,6 +84,11 @@ Contains curves that are composite order, with points not on the subgroup genera Generated using [ecgen](https://github.com/J08nY/ecgen). +### supersingular +Contains supersingular curves, over F_p with order equal to p + 1. These have embedding degree equal to 2. + +Generated using [ecgen](https://github.com/J08nY/ecgen). + ## Other ### Wycheproof diff --git a/docs/TESTS.md b/docs/TESTS.md index 5ec3b63..4d71ea6 100644 --- a/docs/TESTS.md +++ b/docs/TESTS.md @@ -3,6 +3,7 @@ - `default` - `test-vectors` - `compression` + - `miscellaneous` - `wrong`* - `composite`* - `invalid`* @@ -155,4 +156,12 @@ P-256 curve which leaked information about the private key. For example: ```bash java -jar ECTester.jar -t edge-cases +``` + +## Miscellaneous +Some miscellaneous tests, tries ECDH and ECDSA over supersingular curves and Barreto-Naehrig curves with small embedding degree and CM discriminant. + +For example: +```bash +java -jar ECTester.jar -t miscellaneous ```
\ No newline at end of file diff --git a/src/cz/crcs/ectester/data/categories.xml b/src/cz/crcs/ectester/data/categories.xml index e725db0..38ce683 100644 --- a/src/cz/crcs/ectester/data/categories.xml +++ b/src/cz/crcs/ectester/data/categories.xml @@ -89,4 +89,9 @@ <directory>wycheproof</directory> <desc>Test cases from google Wycheproof project: https://github.com/google/wycheproof</desc> </category> + <category> + <name>supersingular</name> + <directory>supersingular</directory> + <desc>Some supersingular curves, over F_p with order equal to p + 1.</desc> + </category> </categories>
\ No newline at end of file diff --git a/src/cz/crcs/ectester/data/supersingular/curves.xml b/src/cz/crcs/ectester/data/supersingular/curves.xml new file mode 100644 index 0000000..186a8a7 --- /dev/null +++ b/src/cz/crcs/ectester/data/supersingular/curves.xml @@ -0,0 +1,32 @@ +<?xml version="1.0" encoding="utf-8" ?> +<curves xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" + xsi:noNamespaceSchemaLocation="../schema.xsd"> + <curve> + <id>ss128</id> + <bits>128</bits> + <field>prime</field> + <file>ss128.csv</file> + <desc>Supersingular curve</desc> + </curve> + <curve> + <id>ss192</id> + <bits>192</bits> + <field>prime</field> + <file>ss192.csv</file> + <desc>Supersingular curve</desc> + </curve> + <curve> + <id>ss224</id> + <bits>224</bits> + <field>prime</field> + <file>ss224.csv</file> + <desc>Supersingular curve</desc> + </curve> + <curve> + <id>ss256</id> + <bits>256</bits> + <field>prime</field> + <file>ss256.csv</file> + <desc>Supersingular curve</desc> + </curve> +</curves>
\ No newline at end of file diff --git a/src/cz/crcs/ectester/data/supersingular/ss128.csv b/src/cz/crcs/ectester/data/supersingular/ss128.csv new file mode 100644 index 0000000..9dd4f13 --- /dev/null +++ b/src/cz/crcs/ectester/data/supersingular/ss128.csv @@ -0,0 +1 @@ +0x9ad6ed2af5bd6f3a9ac1d052ea17b2a9,0x8a3fe60aedb247e20a2d0c4a07de4d37,0x10970720080b27589094c408e2396572,0x563804cbd66f054434143af1e3ec6eaf,0x42af7ba7a078ef8fa3c0f253d1ccc16a,0x4d6b76957adeb79d4d60e829750bd955,0x02
\ No newline at end of file diff --git a/src/cz/crcs/ectester/data/supersingular/ss192.csv b/src/cz/crcs/ectester/data/supersingular/ss192.csv new file mode 100644 index 0000000..0c8ae8b --- /dev/null +++ b/src/cz/crcs/ectester/data/supersingular/ss192.csv @@ -0,0 +1 @@ +0x8c4dbc0e122afdeb466c2b7c3321e72531ac1cd8435f5159,0x64ff701953d8a795e3d9fa41a85eb2bd355479744198ae6c,0x274e4bf4be5256556292313a8ac33467fc57a36401c6a2ed,0x6c39b62a8665aca35dc1669dd483a1e881c65557bbed7f8c,0x1f90241e9bdb361251343bf4cb1ff19545e1e0fff2c8f235,0x4626de0709157ef5a33615be1990f39298d60e6c21afa8ad,0x02
\ No newline at end of file diff --git a/src/cz/crcs/ectester/data/supersingular/ss224.csv b/src/cz/crcs/ectester/data/supersingular/ss224.csv new file mode 100644 index 0000000..01eaa35 --- /dev/null +++ b/src/cz/crcs/ectester/data/supersingular/ss224.csv @@ -0,0 +1 @@ +0xa52f9550f18b8475c5cddd1232428b0c6138aa8704759eab7916f839,0x35186ffe96c8460148b9070efdde881f68647ff48a93854966ebf457,0x701725525ac33e747d14d603346402ecf8d42a9279e21962122b03e2,0x726e4342d936e7c3f004d36b5a703ca35d000014e70bceb1e956f7cc,0x9b3785caa9b028340c564ec4e7450229b7a0b16bc7185c78d852e2a6,0x1084c221b1c126d893c7c94e9ea0411ad685aaa71a0bc31125b57f39,0x0a
\ No newline at end of file diff --git a/src/cz/crcs/ectester/data/supersingular/ss256.csv b/src/cz/crcs/ectester/data/supersingular/ss256.csv new file mode 100644 index 0000000..47a8174 --- /dev/null +++ b/src/cz/crcs/ectester/data/supersingular/ss256.csv @@ -0,0 +1 @@ +0xf9cde8953b26ab31fe1b135266d2f9187e3d9df982880f05cc80f1998b9b0c8d,0xdf0a21f2f4d03d6ca2e151406e17cc1f0300287a348bc4452d7320db6138269e,0x1ac3c6a246566dc55b39c211f8bb2cf97b3d757f4dfc4ac09f0dd0be2a62e5ef,0x3c52f9e66b5c180923ac7bfb7f88f0162ee1dca122aa8dda1e8de3e044cb55a6,0x89c2f4437118d2edb0021706feef5a4419150afd7d1c3b7401eee93c2e547264,0x7ce6f44a9d935598ff0d89a933697c8c3f1ecefcc1440782e64078ccc5cd8647,0x02
\ No newline at end of file diff --git a/src/cz/crcs/ectester/reader/ECTesterReader.java b/src/cz/crcs/ectester/reader/ECTesterReader.java index ab022dd..89cfca1 100644 --- a/src/cz/crcs/ectester/reader/ECTesterReader.java +++ b/src/cz/crcs/ectester/reader/ECTesterReader.java @@ -273,7 +273,7 @@ public class ECTesterReader { actions.addOption(Option.builder("ln").longOpt("list-named").desc("Print the list of supported named curves and keys.").hasArg().argName("what").optionalArg(true).build()); actions.addOption(Option.builder("e").longOpt("export").desc("Export the defaut curve parameters of the card(if any).").build()); actions.addOption(Option.builder("g").longOpt("generate").desc("Generate [amount] of EC keys.").hasArg().argName("amount").optionalArg(true).build()); - actions.addOption(Option.builder("t").longOpt("test").desc("Test ECC support. [test_suite]:\n- default:\n- compression:\n- invalid:\n- twist:\n- degenerate:\n- cofactor:\n- wrong:\n- composite:\n- test-vectors:\n- edge-cases:").hasArg().argName("test_suite").optionalArg(true).build()); + actions.addOption(Option.builder("t").longOpt("test").desc("Test ECC support. [test_suite]:\n- default:\n- compression:\n- invalid:\n- twist:\n- degenerate:\n- cofactor:\n- wrong:\n- composite:\n- test-vectors:\n- edge-cases:\n- miscellaneous:").hasArg().argName("test_suite").optionalArg(true).build()); actions.addOption(Option.builder("dh").longOpt("ecdh").desc("Do EC KeyAgreement (ECDH...), [count] times.").hasArg().argName("count").optionalArg(true).build()); actions.addOption(Option.builder("dsa").longOpt("ecdsa").desc("Sign data with ECDSA, [count] times.").hasArg().argName("count").optionalArg(true).build()); actions.addOption(Option.builder("ls").longOpt("list-suites").desc("List supported test suites.").build()); @@ -332,13 +332,14 @@ public class ECTesterReader { new CardDefaultSuite(null, null, null), new CardTestVectorSuite(null, null, null), new CardCompressionSuite(null, null, null), - new CardWrongCurvesSuite(null, null, null), - new CardDegenerateCurvesSuite(null, null, null), + new CardWrongSuite(null, null, null), + new CardDegenerateSuite(null, null, null), new CardCofactorSuite(null, null, null), - new CardCompositeCurvesSuite(null, null, null), - new CardInvalidCurvesSuite(null, null, null), + new CardCompositeSuite(null, null, null), + new CardInvalidSuite(null, null, null), new CardEdgeCasesSuite(null, null, null), - new CardTwistTestSuite(null, null, null)}; + new CardTwistSuite(null, null, null), + new CardMiscSuite(null, null, null)}; for (CardTestSuite suite : suites) { System.out.println(" - " + Colors.bold(suite.getName())); for (String line : suite.getDescription()) { @@ -457,6 +458,9 @@ public class ECTesterReader { case "compression": suite = new CardCompressionSuite(writer, cfg, cardManager); break; + case "miscellaneous": + suite = new CardMiscSuite(writer, cfg, cardManager); + break; default: // These run are dangerous, prompt before them. System.out.println("The test you selected (" + cfg.testSuite + ") is potentially dangerous."); @@ -472,19 +476,19 @@ public class ECTesterReader { } switch (cfg.testSuite) { case "wrong": - suite = new CardWrongCurvesSuite(writer, cfg, cardManager); + suite = new CardWrongSuite(writer, cfg, cardManager); break; case "composite": - suite = new CardCompositeCurvesSuite(writer, cfg, cardManager); + suite = new CardCompositeSuite(writer, cfg, cardManager); break; case "invalid": - suite = new CardInvalidCurvesSuite(writer, cfg, cardManager); + suite = new CardInvalidSuite(writer, cfg, cardManager); break; case "degenerate": - suite = new CardDegenerateCurvesSuite(writer, cfg, cardManager); + suite = new CardDegenerateSuite(writer, cfg, cardManager); break; case "twist": - suite = new CardTwistTestSuite(writer, cfg, cardManager); + suite = new CardTwistSuite(writer, cfg, cardManager); break; case "cofactor": suite = new CardCofactorSuite(writer, cfg, cardManager); @@ -824,7 +828,7 @@ public class ECTesterReader { } testSuite = cli.getOptionValue("test", "default").toLowerCase(); - String[] tests = new String[]{"default", "composite", "compression", "invalid", "degenerate", "test-vectors", "wrong", "twist", "cofactor", "edge-cases"}; + String[] tests = new String[]{"default", "composite", "compression", "invalid", "degenerate", "test-vectors", "wrong", "twist", "cofactor", "edge-cases", "miscellaneous"}; if (!Arrays.asList(tests).contains(testSuite)) { System.err.println(Colors.error("Unknown test suite " + testSuite + ". Should be one of: " + Arrays.toString(tests))); return false; diff --git a/src/cz/crcs/ectester/reader/test/CardCompositeCurvesSuite.java b/src/cz/crcs/ectester/reader/test/CardCompositeSuite.java index 2b3724c..0d4d2e0 100644 --- a/src/cz/crcs/ectester/reader/test/CardCompositeCurvesSuite.java +++ b/src/cz/crcs/ectester/reader/test/CardCompositeSuite.java @@ -22,9 +22,9 @@ import static cz.crcs.ectester.common.test.Result.ExpectedValue; /** * @author Jan Jancar johny@neuromancer.sk */ -public class CardCompositeCurvesSuite extends CardTestSuite { +public class CardCompositeSuite extends CardTestSuite { - public CardCompositeCurvesSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { + public CardCompositeSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { super(writer, cfg, cardManager, "composite", "The composite suite runs ECDH over curves with composite order. This should generally fail, as using such a curve is unsafe."); } diff --git a/src/cz/crcs/ectester/reader/test/CardDegenerateCurvesSuite.java b/src/cz/crcs/ectester/reader/test/CardDegenerateSuite.java index 0cc9186..7483b2b 100644 --- a/src/cz/crcs/ectester/reader/test/CardDegenerateCurvesSuite.java +++ b/src/cz/crcs/ectester/reader/test/CardDegenerateSuite.java @@ -20,9 +20,9 @@ import java.util.Map; /** * @author Jan Jancar johny@neuromancer.sk */ -public class CardDegenerateCurvesSuite extends CardTestSuite { +public class CardDegenerateSuite extends CardTestSuite { - public CardDegenerateCurvesSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { + public CardDegenerateSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { super(writer, cfg, cardManager, "degenerate", "The degenerate suite tests whether the card rejects points outside of the curve during ECDH.", "The tested points lie on a part of the plane for which some Edwards, Hessian and Huff form addition formulas work."); } diff --git a/src/cz/crcs/ectester/reader/test/CardInvalidCurvesSuite.java b/src/cz/crcs/ectester/reader/test/CardInvalidSuite.java index 425fa06..2543027 100644 --- a/src/cz/crcs/ectester/reader/test/CardInvalidCurvesSuite.java +++ b/src/cz/crcs/ectester/reader/test/CardInvalidSuite.java @@ -20,9 +20,9 @@ import static cz.crcs.ectester.common.test.Result.ExpectedValue; /** * @author Jan Jancar johny@neuromancer.sk */ -public class CardInvalidCurvesSuite extends CardTestSuite { +public class CardInvalidSuite extends CardTestSuite { - public CardInvalidCurvesSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { + public CardInvalidSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { super(writer, cfg, cardManager, "invalid", "The invalid curve suite tests whether the card rejects points outside of the curve during ECDH."); } diff --git a/src/cz/crcs/ectester/reader/test/CardMiscSuite.java b/src/cz/crcs/ectester/reader/test/CardMiscSuite.java new file mode 100644 index 0000000..d969cf9 --- /dev/null +++ b/src/cz/crcs/ectester/reader/test/CardMiscSuite.java @@ -0,0 +1,54 @@ +package cz.crcs.ectester.reader.test; + +import cz.crcs.ectester.applet.ECTesterApplet; +import cz.crcs.ectester.applet.EC_Consts; +import cz.crcs.ectester.common.ec.EC_Curve; +import cz.crcs.ectester.common.output.TestWriter; +import cz.crcs.ectester.common.test.CompoundTest; +import cz.crcs.ectester.common.test.Result; +import cz.crcs.ectester.common.test.Test; +import cz.crcs.ectester.common.util.CardUtil; +import cz.crcs.ectester.data.EC_Store; +import cz.crcs.ectester.reader.CardMngr; +import cz.crcs.ectester.reader.ECTesterReader; +import cz.crcs.ectester.reader.command.Command; + +import java.util.Map; + +/** + * @author Jan Jancar johny@neuromancer.sk + */ +public class CardMiscSuite extends CardTestSuite { + + public CardMiscSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { + super(writer, cfg, cardManager, "miscellaneous", "Some miscellaneous tests, tries ECDH and ECDSA over supersingular curves and some Barreto-Naehrig curves with small embedding degree and CM discriminant."); + } + + @Override + protected void runTests() throws Exception { + Map<String, EC_Curve> ssCurves = EC_Store.getInstance().getObjects(EC_Curve.class, "supersingular"); + Map<String, EC_Curve> bnCurves = EC_Store.getInstance().getObjects(EC_Curve.class, "Barreto-Naehrig"); + + testCurves(ssCurves, "supersingular"); + + testCurves(bnCurves, "Barreto-Naehrig"); + } + + private void testCurves(Map<String, EC_Curve> curves, String catName) throws Exception { + for (EC_Curve curve : curves.values()) { + Test allocateFirst = runTest(CommandTest.expect(new Command.Allocate(this.card, ECTesterApplet.KEYPAIR_BOTH, curve.getBits(), curve.getField()), Result.ExpectedValue.SUCCESS)); + if (!allocateFirst.ok()) { + doTest(CompoundTest.all(Result.ExpectedValue.SUCCESS, "No support for " + curve.getBits() + "b " + CardUtil.getKeyTypeString(curve.getField()) + ".", allocateFirst)); + continue; + } + + Test set = CommandTest.expect(new Command.Set(this.card, ECTesterApplet.KEYPAIR_BOTH, EC_Consts.CURVE_external, curve.getParams(), curve.flatten()), Result.ExpectedValue.SUCCESS); + Test generate = CommandTest.expect(new Command.Generate(this.card, ECTesterApplet.KEYPAIR_BOTH), Result.ExpectedValue.SUCCESS); + Test ka = CommandTest.expect(new Command.ECDH(this.card, ECTesterApplet.KEYPAIR_LOCAL, ECTesterApplet.KEYPAIR_REMOTE, ECTesterApplet.EXPORT_FALSE, EC_Consts.TRANSFORMATION_NONE, EC_Consts.KeyAgreement_ALG_EC_SVDP_DH), Result.ExpectedValue.SUCCESS); + Test sig = CommandTest.expect(new Command.ECDSA(this.card, ECTesterApplet.KEYPAIR_LOCAL, EC_Consts.Signature_ALG_ECDSA_SHA, ECTesterApplet.EXPORT_FALSE, null), Result.ExpectedValue.SUCCESS); + + doTest(CompoundTest.greedyAll(Result.ExpectedValue.SUCCESS, "Tests over " + curve.getBits() + " " + catName + " curve: " + curve.getId() + ".", allocateFirst, set, generate, ka, sig)); + new Command.Cleanup(this.card).send(); + } + } +} diff --git a/src/cz/crcs/ectester/reader/test/CardTwistTestSuite.java b/src/cz/crcs/ectester/reader/test/CardTwistSuite.java index ab8e144..46da415 100644 --- a/src/cz/crcs/ectester/reader/test/CardTwistTestSuite.java +++ b/src/cz/crcs/ectester/reader/test/CardTwistSuite.java @@ -18,8 +18,8 @@ import java.util.*; /** * @author Jan Jancar johny@neuromancer.sk */ -public class CardTwistTestSuite extends CardTestSuite { - public CardTwistTestSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { +public class CardTwistSuite extends CardTestSuite { + public CardTwistSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { super(writer, cfg, cardManager, "twist", "The twist test suite tests whether the card correctly rejects points on the quadratic twist of the curve during ECDH."); } diff --git a/src/cz/crcs/ectester/reader/test/CardWrongCurvesSuite.java b/src/cz/crcs/ectester/reader/test/CardWrongSuite.java index 8b648b9..6c0d5f5 100644 --- a/src/cz/crcs/ectester/reader/test/CardWrongCurvesSuite.java +++ b/src/cz/crcs/ectester/reader/test/CardWrongSuite.java @@ -27,9 +27,9 @@ import static cz.crcs.ectester.common.test.Result.ExpectedValue; /** * @author Jan Jancar johny@neuromancer.sk */ -public class CardWrongCurvesSuite extends CardTestSuite { +public class CardWrongSuite extends CardTestSuite { - public CardWrongCurvesSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { + public CardWrongSuite(TestWriter writer, ECTesterReader.Config cfg, CardMngr cardManager) { super(writer, cfg, cardManager, "wrong", "The wrong curve suite tests whether the card rejects domain parameters which are not curves."); } |
