diff options
Diffstat (limited to '')
| -rw-r--r-- | src/cz/crcs/ectester/applet/AppletBase.java | 37 | ||||
| -rw-r--r-- | src/cz/crcs/ectester/applet/ECKeyGenerator.java | 154 | ||||
| -rw-r--r-- | src/cz/crcs/ectester/applet/ECKeyTester.java | 63 |
3 files changed, 182 insertions, 72 deletions
diff --git a/src/cz/crcs/ectester/applet/AppletBase.java b/src/cz/crcs/ectester/applet/AppletBase.java index 48e7785..c77294e 100644 --- a/src/cz/crcs/ectester/applet/AppletBase.java +++ b/src/cz/crcs/ectester/applet/AppletBase.java @@ -24,6 +24,7 @@ public abstract class AppletBase extends Applet { public static final byte INS_ALLOCATE_KA = (byte) 0x76; public static final byte INS_ALLOCATE_SIG = (byte) 0x77; public static final byte INS_GET_INFO = (byte) 0x78; + public static final byte INS_SET_DRY_RUN_MODE = (byte) 0x79; // PARAMETERS for P1 and P2 public static final byte KEYPAIR_LOCAL = (byte) 0x01; @@ -31,6 +32,8 @@ public abstract class AppletBase extends Applet { public static final byte KEYPAIR_BOTH = KEYPAIR_LOCAL | KEYPAIR_REMOTE; public static final byte EXPORT_TRUE = (byte) 0xff; public static final byte EXPORT_FALSE = (byte) 0x00; + public static final byte MODE_NORMAL = (byte) 0xaa; + public static final byte MODE_DRY_RUN = (byte) 0xbb; // STATUS WORDS public static final short SW_SIG_VERIFY_FAIL = (short) 0x0ee1; @@ -159,6 +162,9 @@ public abstract class AppletBase extends Applet { case INS_GET_INFO: length = insGetInfo(apdu); break; + case INS_SET_DRY_RUN_MODE: + length = insSetDryRunMode(apdu); + break; default: // The INS code is not supported by the dispatcher ISOException.throwIt(ISO7816.SW_INS_NOT_SUPPORTED); @@ -545,6 +551,26 @@ public abstract class AppletBase extends Applet { } /** + * Set the dry run mode of the applet. + * + * @param apdu P1 = byte mode (MODE_* || ...) + * @return length of response + */ + private short insSetDryRunMode(APDU apdu) { + byte[] apdubuf = apdu.getBuffer(); + byte mode = apduArray[ISO7816.OFFSET_P1]; + + short len = 0; + if (mode == MODE_NORMAL) { + len = setDryRunMode(apdubuf, false, (short) 0); + } + if (mode == MODE_DRY_RUN) { + len = setDryRunMode(apdubuf, true, (short) 0); + } + return len; + } + + /** * @param keyPair which keyPair to use, local/remote (KEYPAIR_* | ...) * @param keyLength key length to set * @param keyClass key class to allocate @@ -883,4 +909,15 @@ public abstract class AppletBase extends Applet { length += 2; return length; } + + private short setDryRunMode(byte[] buffer, boolean mode, short offset) { + if (keyTester != null) { + keyTester.setDryRun(mode); + } + if (keyGenerator != null) { + keyGenerator.setDryRun(mode); + } + Util.setShort(buffer, offset, ISO7816.SW_NO_ERROR); + return 2; + } } diff --git a/src/cz/crcs/ectester/applet/ECKeyGenerator.java b/src/cz/crcs/ectester/applet/ECKeyGenerator.java index 4326752..30910ca 100644 --- a/src/cz/crcs/ectester/applet/ECKeyGenerator.java +++ b/src/cz/crcs/ectester/applet/ECKeyGenerator.java @@ -14,6 +14,7 @@ import javacard.security.KeyPair; public class ECKeyGenerator { private short sw = ISO7816.SW_NO_ERROR; + private boolean dryRun = false; /** * @param keyClass @@ -24,12 +25,14 @@ public class ECKeyGenerator { sw = ISO7816.SW_NO_ERROR; KeyPair ecKeyPair = null; try { - ecKeyPair = new KeyPair(keyClass, keyLength); + if (!dryRun) { + ecKeyPair = new KeyPair(keyClass, keyLength); - if (ecKeyPair.getPublic() == null || ecKeyPair.getPrivate() == null) { - try { - ecKeyPair.genKeyPair(); - } catch (Exception ignored) { + if (ecKeyPair.getPublic() == null || ecKeyPair.getPrivate() == null) { + try { + ecKeyPair.genKeyPair(); + } catch (Exception ignored) { + } } } } catch (CardRuntimeException ce) { @@ -46,8 +49,10 @@ public class ECKeyGenerator { public short clearPair(KeyPair keypair, byte key) { try { sw = AppletUtil.keypairCheck(keypair); - if ((key & EC_Consts.KEY_PUBLIC) != 0) keypair.getPublic().clearKey(); - if ((key & EC_Consts.KEY_PRIVATE) != 0) keypair.getPrivate().clearKey(); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) keypair.getPublic().clearKey(); + if ((key & EC_Consts.KEY_PRIVATE) != 0) keypair.getPrivate().clearKey(); + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -61,7 +66,9 @@ public class ECKeyGenerator { public short generatePair(KeyPair keypair) { try { sw = AppletUtil.keypairCheck(keypair); - keypair.genKeyPair(); + if (!dryRun) { + keypair.genKeyPair(); + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -187,25 +194,35 @@ public class ECKeyGenerator { try { sw = AppletUtil.keypairCheck(keypair); - ECPublicKey ecPublicKey = (ECPublicKey) keypair.getPublic(); - ECPrivateKey ecPrivateKey = (ECPrivateKey) keypair.getPrivate(); + ECPublicKey ecPublicKey = null; + ECPrivateKey ecPrivateKey = null; + if (!dryRun) { + ecPublicKey = (ECPublicKey) keypair.getPublic(); + ecPrivateKey = (ECPrivateKey) keypair.getPrivate(); + } switch (param) { case EC_Consts.PARAMETER_FP: - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldFP(data, offset, length); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldFP(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldFP(data, offset, length); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldFP(data, offset, length); + } break; case EC_Consts.PARAMETER_F2M: if (length == 4) { short i = Util.getShort(data, (short) (offset + 2)); - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldF2M(i); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldF2M(i); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldF2M(i); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldF2M(i); + } } else if (length == 8) { short i1 = Util.getShort(data, (short) (offset + 2)); short i2 = Util.getShort(data, (short) (offset + 4)); short i3 = Util.getShort(data, (short) (offset + 6)); - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldF2M(i1, i2, i3); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldF2M(i1, i2, i3); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldF2M(i1, i2, i3); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldF2M(i1, i2, i3); + } // if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setFieldF2M(i3, i2, i1); // if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setFieldF2M(i3, i2, i1); } else { @@ -213,20 +230,28 @@ public class ECKeyGenerator { } break; case EC_Consts.PARAMETER_A: - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setA(data, offset, length); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setA(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setA(data, offset, length); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setA(data, offset, length); + } break; case EC_Consts.PARAMETER_B: - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setB(data, offset, length); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setB(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setB(data, offset, length); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setB(data, offset, length); + } break; case EC_Consts.PARAMETER_G: - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setG(data, offset, length); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setG(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setG(data, offset, length); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setG(data, offset, length); + } break; case EC_Consts.PARAMETER_R: - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setR(data, offset, length); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setR(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setR(data, offset, length); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setR(data, offset, length); + } break; case EC_Consts.PARAMETER_K: short k = 0; @@ -238,14 +263,20 @@ public class ECKeyGenerator { } else if (length == 1) { k = data[offset]; } - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setK(k); - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setK(k); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setK(k); + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setK(k); + } break; case EC_Consts.PARAMETER_S: - if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setS(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PRIVATE) != 0) ecPrivateKey.setS(data, offset, length); + } break; case EC_Consts.PARAMETER_W: - if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setW(data, offset, length); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) ecPublicKey.setW(data, offset, length); + } break; default: ISOException.throwIt(ISO7816.SW_FUNC_NOT_SUPPORTED); @@ -310,54 +341,75 @@ public class ECKeyGenerator { short length = 0; try { sw = AppletUtil.keypairCheck(keypair); - ECPublicKey ecPublicKey = (ECPublicKey) keypair.getPublic(); - ECPrivateKey ecPrivateKey = (ECPrivateKey) keypair.getPrivate(); + + ECPublicKey ecPublicKey = null; + ECPrivateKey ecPrivateKey = null; + if (!dryRun) { + ecPublicKey = (ECPublicKey) keypair.getPublic(); + ecPrivateKey = (ECPrivateKey) keypair.getPrivate(); + } switch (param) { case EC_Consts.PARAMETER_FP: - if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getField(outputBuffer, outputOffset); - if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getField(outputBuffer, outputOffset); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) + length = ecPublicKey.getField(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PRIVATE) != 0) + length = ecPrivateKey.getField(outputBuffer, outputOffset); + } break; case EC_Consts.PARAMETER_F2M: - if ((key & EC_Consts.KEY_PUBLIC) != 0) { + if ((key & EC_Consts.KEY_PUBLIC) != 0 && !dryRun) { Util.setShort(outputBuffer, outputOffset, ecPublicKey.getSize()); length = 2; length += ecPublicKey.getField(outputBuffer, (short) (outputOffset + 2)); } - if ((key & EC_Consts.KEY_PRIVATE) != 0) { + if ((key & EC_Consts.KEY_PRIVATE) != 0 && !dryRun) { Util.setShort(outputBuffer, outputOffset, ecPrivateKey.getSize()); length = 2; length += ecPrivateKey.getField(outputBuffer, (short) (outputOffset + 2)); } break; case EC_Consts.PARAMETER_A: - if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getA(outputBuffer, outputOffset); - if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getA(outputBuffer, outputOffset); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getA(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getA(outputBuffer, outputOffset); + } break; case EC_Consts.PARAMETER_B: - if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getB(outputBuffer, outputOffset); - if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getB(outputBuffer, outputOffset); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getB(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getB(outputBuffer, outputOffset); + } break; case EC_Consts.PARAMETER_G: - if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getG(outputBuffer, outputOffset); - if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getG(outputBuffer, outputOffset); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getG(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getG(outputBuffer, outputOffset); + } break; case EC_Consts.PARAMETER_R: - if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getR(outputBuffer, outputOffset); - if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getR(outputBuffer, outputOffset); + if (!dryRun) { + if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getR(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getR(outputBuffer, outputOffset); + } break; case EC_Consts.PARAMETER_K: - length = 2; - if ((key & EC_Consts.KEY_PUBLIC) != 0) - Util.setShort(outputBuffer, outputOffset, ecPublicKey.getK()); - if ((key & EC_Consts.KEY_PRIVATE) != 0) - Util.setShort(outputBuffer, outputOffset, ecPrivateKey.getK()); + if (!dryRun) { + length = 2; + if ((key & EC_Consts.KEY_PUBLIC) != 0) + Util.setShort(outputBuffer, outputOffset, ecPublicKey.getK()); + if ((key & EC_Consts.KEY_PRIVATE) != 0) + Util.setShort(outputBuffer, outputOffset, ecPrivateKey.getK()); + } break; case EC_Consts.PARAMETER_W: - if ((key & EC_Consts.KEY_PUBLIC) != 0) length = ecPublicKey.getW(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PUBLIC) != 0 && !dryRun) + length = ecPublicKey.getW(outputBuffer, outputOffset); break; case EC_Consts.PARAMETER_S: - if ((key & EC_Consts.KEY_PRIVATE) != 0) length = ecPrivateKey.getS(outputBuffer, outputOffset); + if ((key & EC_Consts.KEY_PRIVATE) != 0 && !dryRun) + length = ecPrivateKey.getS(outputBuffer, outputOffset); break; default: ISOException.throwIt(ISO7816.SW_FUNC_NOT_SUPPORTED); @@ -439,4 +491,8 @@ public class ECKeyGenerator { public short getSW() { return sw; } + + public void setDryRun(boolean dryRun) { + this.dryRun = dryRun; + } } diff --git a/src/cz/crcs/ectester/applet/ECKeyTester.java b/src/cz/crcs/ectester/applet/ECKeyTester.java index 0e46971..89590d0 100644 --- a/src/cz/crcs/ectester/applet/ECKeyTester.java +++ b/src/cz/crcs/ectester/applet/ECKeyTester.java @@ -18,12 +18,15 @@ public class ECKeyTester { private short sigType = 0; private short sw = ISO7816.SW_NO_ERROR; + private boolean dryRun = false; public short allocateKA(byte algorithm) { sw = ISO7816.SW_NO_ERROR; try { - ecKeyAgreement = KeyAgreement.getInstance(algorithm, false); - kaType = algorithm; + if (!dryRun) { + ecKeyAgreement = KeyAgreement.getInstance(algorithm, false); + kaType = algorithm; + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -33,8 +36,10 @@ public class ECKeyTester { public short allocateSig(byte algorithm) { sw = ISO7816.SW_NO_ERROR; try { - ecdsaSignature = Signature.getInstance(algorithm, false); - sigType = algorithm; + if (!dryRun) { + ecdsaSignature = Signature.getInstance(algorithm, false); + sigType = algorithm; + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -61,11 +66,13 @@ public class ECKeyTester { sw = AppletUtil.kaCheck(ecKeyAgreement); sw = AppletUtil.keypairCheck(privatePair); sw = AppletUtil.keypairCheck(publicPair); - short pubkeyLength = ((ECPublicKey) publicPair.getPublic()).getW(pubkeyBuffer, pubkeyOffset); - ecKeyAgreement.init(privatePair.getPrivate()); + if (!dryRun) { + short pubkeyLength = ((ECPublicKey) publicPair.getPublic()).getW(pubkeyBuffer, pubkeyOffset); + ecKeyAgreement.init(privatePair.getPrivate()); - pubkeyLength = EC_Consts.transformParameter(transformation, pubkeyBuffer, pubkeyOffset, pubkeyLength); - length = ecKeyAgreement.generateSecret(pubkeyBuffer, pubkeyOffset, pubkeyLength, outputBuffer, outputOffset); + pubkeyLength = EC_Consts.transformParameter(transformation, pubkeyBuffer, pubkeyOffset, pubkeyLength); + length = ecKeyAgreement.generateSecret(pubkeyBuffer, pubkeyOffset, pubkeyLength, outputBuffer, outputOffset); + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -88,9 +95,11 @@ public class ECKeyTester { sw = AppletUtil.kaCheck(ecKeyAgreement); sw = AppletUtil.keypairCheck(privatePair); - ecKeyAgreement.init(privatePair.getPrivate()); - pubkeyLength = EC_Consts.transformParameter(transformation, pubkey, pubkeyOffset, pubkeyLength); - length = ecKeyAgreement.generateSecret(pubkey, pubkeyOffset, pubkeyLength, outpuBuffer, outputOffset); + if (!dryRun) { + ecKeyAgreement.init(privatePair.getPrivate()); + pubkeyLength = EC_Consts.transformParameter(transformation, pubkey, pubkeyOffset, pubkeyLength); + length = ecKeyAgreement.generateSecret(pubkey, pubkeyOffset, pubkeyLength, outpuBuffer, outputOffset); + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -116,13 +125,14 @@ public class ECKeyTester { try { sw = AppletUtil.signCheck(ecdsaSignature); - ecdsaSignature.init(signKey, Signature.MODE_SIGN); - length = ecdsaSignature.sign(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset); + if (!dryRun) { + ecdsaSignature.init(signKey, Signature.MODE_SIGN); + length = ecdsaSignature.sign(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset); - ecdsaSignature.init(verifyKey, Signature.MODE_VERIFY); - boolean correct = ecdsaSignature.verify(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset, length); - if (!correct) { - sw = AppletBase.SW_SIG_VERIFY_FAIL; + ecdsaSignature.init(verifyKey, Signature.MODE_VERIFY); + if (!ecdsaSignature.verify(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset, length)) { + sw = AppletBase.SW_SIG_VERIFY_FAIL; + } } } catch (CardRuntimeException ce) { sw = ce.getReason(); @@ -144,8 +154,10 @@ public class ECKeyTester { try { sw = AppletUtil.signCheck(ecdsaSignature); - ecdsaSignature.init(signKey, Signature.MODE_SIGN); - length = ecdsaSignature.sign(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset); + if (!dryRun) { + ecdsaSignature.init(signKey, Signature.MODE_SIGN); + length = ecdsaSignature.sign(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset); + } } catch (CardRuntimeException ce) { sw = ce.getReason(); } @@ -167,10 +179,11 @@ public class ECKeyTester { try { sw = AppletUtil.signCheck(ecdsaSignature); - ecdsaSignature.init(verifyKey, Signature.MODE_VERIFY); - boolean correct = ecdsaSignature.verify(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset, sigLength); - if (!correct) { - sw = AppletBase.SW_SIG_VERIFY_FAIL; + if (!dryRun) { + ecdsaSignature.init(verifyKey, Signature.MODE_VERIFY); + if (!ecdsaSignature.verify(inputBuffer, inputOffset, inputLength, sigBuffer, sigOffset, sigLength)) { + sw = AppletBase.SW_SIG_VERIFY_FAIL; + } } } catch (CardRuntimeException ce) { sw = ce.getReason(); @@ -205,4 +218,8 @@ public class ECKeyTester { public short getSW() { return sw; } + + public void setDryRun(boolean dryRun) { + this.dryRun = dryRun; + } } |
