2016-06-01 22 views
3

Я пытаюсь получить Elliptic Curve Diffie Hellman для работы на JavaCard (версия 2.2.1).Как работает Elliptic Curve Diffie Hellman на JavaCard в сочетании с Java?

На JavaCard, я следующий код прямо сейчас:

byte temp[] = new byte[100]; 
byte secret[] = new byte[100]; 
byte size = buf[ISO7816.OFFSET_LC]; 

Util.arrayCopy(buf, ISO7816.OFFSET_CDATA, temp, (byte) 0, size); 

// the public key is in temp 
short len = dh.generateSecret(temp, (byte) 0, size, secret, (byte) 0); 

Util.arrayCopy(temp, (byte) 0, buf, ISO7816.OFFSET_CDATA, size); 
//Util.arrayCopy(secret, (byte) 0, buf, ISO7816.OFFSET_CDATA, len); 
apdu.setOutgoingAndSend(ISO7816.OFFSET_CDATA, size); 

И я инициализировать dh следующим образом:

keyPair = new KeyPair(KeyPair.ALG_EC_FP, KeyBuilder.LENGTH_EC_F2M_163); 
keyPair.genKeyPair(); 
dh = KeyAgreement.getInstance(KeyAgreement.ALG_EC_SVDP_DH, false); 
dh.init(keyPair.getPrivate()); 

Все это, кажется, работает, за dh.generateSecret вызова, за исключением, где апплет просто, кажется, падает. Если я оставлю вызов и верну другие данные, это будет хорошо. В котором я импортирую данные, отправленные терминалом. В терминале у меня есть следующее:

// generate an ecdh keypair 
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("EC"); 
keyGen.initialize(163); 
KeyPair keyPair = keyGen.generateKeyPair(); 

// initialize DH 
KeyAgreement dh = KeyAgreement.getInstance("ECDH"); 
dh.init(keyPair.getPrivate()); 

//byte encKey[] = keyPair.getPublic().getEncoded(); 

// X9.62 encoding, no compression 
int qLength = (163+7)/8; 
byte[] xArr = ((ECPublicKey) keyPair.getPublic()).getW().getAffineX().toByteArray(); 
byte[] yArr = ((ECPublicKey) keyPair.getPublic()).getW().getAffineY().toByteArray(); 
byte[] enc2 = new byte[1+2*qLength]; 
enc2[0] = (byte) 0x04; 
System.arraycopy(xArr, 0, enc2, qLength - xArr.length, xArr.length); 
System.arraycopy(yArr, 0, enc2, 2* qLength - yArr.length, yArr.length); 

byte res[] =send((byte) 0x00, enc2).getData(); 

Я пробовал несколько вещей. Прямо сейчас код, который отправляет открытый ключ, пытается закодировать его в кодировке X9.62 (несжатый), как указано в документах JavaCard. Тем не менее, я также попробовал метод encode по умолчанию, который дает точно такой же результат.

Кажется, я не могу получить какую-либо ошибку из JavaCard о том, что происходит не так. Кто-нибудь знает, что происходит не так? Или у кого-нибудь есть рабочий пример о том, как сделать обмен ключами на JavaCard?

+0

У вас есть журналы APDU? –

+1

Всего несколько заметок: 'KeyPair.ALG_EC_FP, KeyBuilder.LENGTH_EC_F2M_163' - алгоритм и длина не совпадают. Вы указываете параметры области эллиптической кривой где-то в вашем коде? Эллиптическая кривая по умолчанию отсутствует, поэтому перед созданием новой пары ключей вы должны заполнить параметры как частным, так и открытым ключом. – vojta

ответ

0

Как Войта уже указывалось:

keyPair = new KeyPair(KeyPair.ALG_EC_FP, KeyBuilder.LENGTH_EC_F2M_163); 

просто пытается сгенерировать пару ключей, и это, вероятно, работает до точки. Но кривая Fp отличается от кривой F2m, и, насколько мне известно, кривых Fp 163 бит (насколько мне известно).

Это означает, что вы никогда не устанавливали параметры домена, если только вы не создали свой собственный, и я бы назвал это маловероятным.

Используйте кривую Fp с известной длиной ключа и задайте параметры, по крайней мере, для открытого ключа (для карт JCOP, возможно, вам придется также установить их для закрытого ключа). Обычно вы должны использовать размер ключа 224 бит или выше для обеспечения безопасности.