aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJ08nY2017-11-30 16:06:35 +0100
committerJ08nY2017-11-30 16:06:35 +0100
commit715dd7f068dfc9e5b90ce0c1e2d3aad0a9fe982a (patch)
treecdecbced6df60822a8c52ae83274309b59632d92
parent5026cc9f03f11fc2a473124e32867f3302f901f7 (diff)
downloadECTester-715dd7f068dfc9e5b90ce0c1e2d3aad0a9fe982a.tar.gz
ECTester-715dd7f068dfc9e5b90ce0c1e2d3aad0a9fe982a.tar.zst
ECTester-715dd7f068dfc9e5b90ce0c1e2d3aad0a9fe982a.zip
-rw-r--r--build-standalone.xml1
-rw-r--r--src/cz/crcs/ectester/standalone/libs/TomcryptLib.java2
-rw-r--r--src/cz/crcs/ectester/standalone/libs/jni/Makefile4
-rw-r--r--src/cz/crcs/ectester/standalone/libs/jni/NativeKeyAgreementSpi.java62
-rw-r--r--src/cz/crcs/ectester/standalone/libs/jni/native.h19
-rw-r--r--src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c52
6 files changed, 130 insertions, 10 deletions
diff --git a/build-standalone.xml b/build-standalone.xml
index 7261eee..8098ce2 100644
--- a/build-standalone.xml
+++ b/build-standalone.xml
@@ -100,6 +100,7 @@
<class name="cz.crcs.ectester.standalone.libs.jni.NativeKeyPairGeneratorSpi$TomCrypt"/>
<class name="cz.crcs.ectester.standalone.libs.jni.NativeECPublicKey$TomCrypt"/>
<class name="cz.crcs.ectester.standalone.libs.jni.NativeECPrivateKey$TomCrypt"/>
+ <class name="cz.crcs.ectester.standalone.libs.jni.NativeKeyAgreementSpi$TomCrypt"/>
</javah>
</target>
</project>
diff --git a/src/cz/crcs/ectester/standalone/libs/TomcryptLib.java b/src/cz/crcs/ectester/standalone/libs/TomcryptLib.java
index 78db00e..57b273a 100644
--- a/src/cz/crcs/ectester/standalone/libs/TomcryptLib.java
+++ b/src/cz/crcs/ectester/standalone/libs/TomcryptLib.java
@@ -9,7 +9,7 @@ import java.util.Set;
public class TomcryptLib extends NativeECLibrary {
public TomcryptLib() {
- super("tomcrypt_provider", "tommath", "tomcrypt");
+ super("tomcrypt_provider", "tommath", "tomcrypt");
}
@Override
diff --git a/src/cz/crcs/ectester/standalone/libs/jni/Makefile b/src/cz/crcs/ectester/standalone/libs/jni/Makefile
index 8750dd5..b60452f 100644
--- a/src/cz/crcs/ectester/standalone/libs/jni/Makefile
+++ b/src/cz/crcs/ectester/standalone/libs/jni/Makefile
@@ -36,10 +36,10 @@ JNI_PLATFORMINCLUDEDIR ?= $(JNI_INCLUDEDIR)/$(JNI_PLATFORM)
all: tomcrypt_provider.so
tomcrypt_provider.so: tomcrypt.o
- gcc -DLTM_DESC -DUSE_LTM -fPIC -g -shared -o $@ $< -ltommath -ltomcrypt
+ gcc -fPIC -g -shared -o $@ $< -L. -ltommath -ltomcrypt
%.o: %.c
- gcc -fPIC -g -I"$(JNI_INCLUDEDIR)" -I"$(JNI_PLATFORMINCLUDEDIR)" -I. -c $<
+ gcc -DLTM_DESC -fPIC -g -I"$(JNI_INCLUDEDIR)" -I"$(JNI_PLATFORMINCLUDEDIR)" -I. -c $<
clean:
rm -rf *.o
diff --git a/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyAgreementSpi.java b/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyAgreementSpi.java
index d1b1f42..fee0ea8 100644
--- a/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyAgreementSpi.java
+++ b/src/cz/crcs/ectester/standalone/libs/jni/NativeKeyAgreementSpi.java
@@ -1,46 +1,98 @@
package cz.crcs.ectester.standalone.libs.jni;
+import cz.crcs.ectester.common.util.ECUtil;
+
import javax.crypto.KeyAgreementSpi;
import javax.crypto.SecretKey;
import javax.crypto.ShortBufferException;
import java.security.*;
+import java.security.interfaces.ECPrivateKey;
+import java.security.interfaces.ECPublicKey;
import java.security.spec.AlgorithmParameterSpec;
+import java.security.spec.ECParameterSpec;
/**
* @author Jan Jancar johny@neuromancer.sk
*/
public abstract class NativeKeyAgreementSpi extends KeyAgreementSpi {
+ private ECPrivateKey privateKey;
+ private ECPublicKey publicKey;
+ private ECParameterSpec params;
+
@Override
protected void engineInit(Key key, SecureRandom random) throws InvalidKeyException {
-
+ if (!(key instanceof ECPrivateKey)) {
+ throw new InvalidKeyException
+ ("Key must be instance of PrivateKey");
+ }
+ privateKey = (ECPrivateKey) key;
+ this.params = privateKey.getParams();
}
@Override
protected void engineInit(Key key, AlgorithmParameterSpec params, SecureRandom random) throws InvalidKeyException, InvalidAlgorithmParameterException {
-
+ if (!(params instanceof ECParameterSpec)) {
+ throw new InvalidAlgorithmParameterException();
+ }
+ engineInit(key, random);
+ this.params = (ECParameterSpec) params;
}
@Override
protected Key engineDoPhase(Key key, boolean lastPhase) throws InvalidKeyException, IllegalStateException {
+ if (privateKey == null) {
+ throw new IllegalStateException("Not initialized");
+ }
+ if (publicKey != null) {
+ throw new IllegalStateException("Phase already executed");
+ }
+ if (!lastPhase) {
+ throw new IllegalStateException
+ ("Only two party agreement supported, lastPhase must be true");
+ }
+ if (!(key instanceof ECPublicKey)) {
+ throw new InvalidKeyException
+ ("Key must be a PublicKey with algorithm EC");
+ }
+ ECParameterSpec publicParams = ((ECPublicKey) key).getParams();
+ if (!(params.getCurve().equals(publicParams.getCurve()) &&
+ params.getGenerator().equals(publicParams.getGenerator()) &&
+ params.getOrder().equals(publicParams.getOrder()) &&
+ params.getCofactor() == publicParams.getCofactor())) {
+ throw new IllegalStateException("Mismatched parameters.");
+ }
+ publicKey = (ECPublicKey) key;
return null;
}
@Override
protected byte[] engineGenerateSecret() throws IllegalStateException {
- return new byte[0];
+ byte[] pubkey = ECUtil.toX962Uncompressed(publicKey.getW());
+ byte[] privkey = privateKey.getS().toByteArray();
+ return generateSecret(pubkey, privkey, params);
}
@Override
protected int engineGenerateSecret(byte[] sharedSecret, int offset) throws IllegalStateException, ShortBufferException {
- return 0;
+ byte[] secret = engineGenerateSecret();
+ if (sharedSecret.length < offset + secret.length) {
+ throw new ShortBufferException();
+ }
+ System.arraycopy(secret, 0, sharedSecret, offset, secret.length);
+ return secret.length;
}
@Override
protected SecretKey engineGenerateSecret(String algorithm) throws IllegalStateException, NoSuchAlgorithmException, InvalidKeyException {
- return null;
+ throw new NoSuchAlgorithmException(algorithm);
}
+ abstract byte[] generateSecret(byte[] pubkey, byte[] privkey, ECParameterSpec params);
+
+
public static class TomCrypt extends NativeKeyAgreementSpi {
+ @Override
+ native byte[] generateSecret(byte[] pubkey, byte[] privkey, ECParameterSpec params);
}
}
diff --git a/src/cz/crcs/ectester/standalone/libs/jni/native.h b/src/cz/crcs/ectester/standalone/libs/jni/native.h
index da3a89c..7f63f61 100644
--- a/src/cz/crcs/ectester/standalone/libs/jni/native.h
+++ b/src/cz/crcs/ectester/standalone/libs/jni/native.h
@@ -125,3 +125,22 @@ extern "C" {
}
#endif
#endif
+/* Header for class cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_TomCrypt */
+
+#ifndef _Included_cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_TomCrypt
+#define _Included_cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_TomCrypt
+#ifdef __cplusplus
+extern "C" {
+#endif
+/*
+ * Class: cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_TomCrypt
+ * Method: generateSecret
+ * Signature: ([B[BLjava/security/spec/ECParameterSpec;)[B
+ */
+JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_00024TomCrypt_generateSecret
+ (JNIEnv *, jobject, jbyteArray, jbyteArray, jobject);
+
+#ifdef __cplusplus
+}
+#endif
+#endif
diff --git a/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c b/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c
index f7dedce..b43b05a 100644
--- a/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c
+++ b/src/cz/crcs/ectester/standalone/libs/jni/tomcrypt.c
@@ -1,7 +1,6 @@
#include "native.h"
#include <stdio.h>
#include <string.h>
-#define LTM_DESC
#include <tomcrypt.h>
static prng_state ltc_prng;
@@ -287,7 +286,7 @@ static jobject generate_from_curve(JNIEnv *env, const ltc_ecc_set_type *curve) {
jbyteArray priv_bytes = (*env)->NewByteArray(env, curve->size);
jbyte *key_priv = (*env)->GetByteArrayElements(env, priv_bytes, NULL);
- mp_to_unsigned_bin(key.k, key_priv);
+ ltc_mp.unsigned_write(key.k, key_priv);
(*env)->ReleaseByteArrayElements(env, priv_bytes, key_priv, 0);
jobject ec_priv_param_spec = (*env)->NewLocalRef(env, ec_param_spec);
@@ -341,4 +340,53 @@ JNIEXPORT jobject JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyPai
} else {
return NULL;
}
+}
+
+JNIEXPORT jbyteArray JNICALL Java_cz_crcs_ectester_standalone_libs_jni_NativeKeyAgreementSpi_00024TomCrypt_generateSecret(JNIEnv *env, jobject this, jbyteArray pubkey, jbyteArray privkey, jobject params){
+ ltc_ecc_set_type *curve = create_curve(env, params);
+
+ jsize pub_size = (*env)->GetArrayLength(env, pubkey);
+ jbyte *pub_data = (*env)->GetByteArrayElements(env, pubkey, NULL);
+ jsize pub_half = (pub_size - 1) / 2;
+
+ ecc_key pub;
+ pub.type = PK_PUBLIC;
+ pub.idx = -1;
+ pub.dp = curve;
+ ltc_init_multi(&pub.pubkey.x, &pub.pubkey.y, &pub.pubkey.z, NULL);
+ ltc_mp.set_int(pub.pubkey.z, 1);
+ ltc_mp.unsigned_read(pub.pubkey.x, pub_data + 1, (unsigned long) pub_half);
+ ltc_mp.unsigned_read(pub.pubkey.y, pub_data + 1 + pub_half, (unsigned long) pub_half);
+
+ (*env)->ReleaseByteArrayElements(env, pubkey, pub_data, JNI_ABORT);
+
+ jsize priv_size = (*env)->GetArrayLength(env, privkey);
+ jbyte *priv_data = (*env)->GetByteArrayElements(env, privkey, NULL);
+
+ ecc_key priv;
+ priv.type = PK_PRIVATE;
+ priv.idx = -1;
+ priv.dp = curve;
+ ltc_mp.init(&priv.k);
+ ltc_mp.unsigned_read(priv.k, priv_data, (unsigned long) priv_size);
+
+ (*env)->ReleaseByteArrayElements(env, privkey, priv_data, JNI_ABORT);
+
+ unsigned char result[pub_half];
+
+ unsigned long output_len = pub_half;
+ int err;
+ if ((err = ecc_shared_secret(&priv, &pub, result, &output_len)) != CRYPT_OK) {
+ printf("Error during shared secret computation: %s\n", error_to_string(err));
+ free(curve);
+ return NULL;
+ }
+
+ jbyteArray output = (*env)->NewByteArray(env, pub_half);
+ jbyte *output_data = (*env)->GetByteArrayElements(env, output, NULL);
+ memcpy(output_data, result, pub_half);
+ (*env)->ReleaseByteArrayElements(env, output, output_data, JNI_COMMIT);
+
+ free(curve);
+ return output;
} \ No newline at end of file