Our Online Store have the new products: RFID antenna board. Currently it can work with JC10M24R and JCOP4 card chips.
Compared with normal cards, the antenna board module has a smaller size and fixed holes, which is easy to integrate in the IOT(Internet Of Things) project.

verify function cannot work

JavaCard Applet Development Related Questions and Answers.
Diorin
Posts: 18
Joined: Thu Nov 26, 2015 4:08 am
Points :151
Contact:

verify function cannot work

Post by Diorin » Sun Aug 27, 2017 11:25 pm

I encountered a problem when testing the sign/verify function of the java card. I can successfully upload and install the applet. And the signature generation can also work fine as well. But the verify function never works. It always threw error INVALID_SIGNATURE. Could anyone help me find where I made mistake? Thanks a lot.

Code: Select all

package signECC;

import javacard.framework.*;
import javacard.security.*;

public class SignECC extends Applet {

     final static byte SignECC_CLA = (byte)0xB0;

     final static byte INS_GEN_KEY_PAIR = (byte)0x10;
     final static byte INS_SIGN = (byte)0x20;
     final static byte INS_VERIFY = (byte)0x30;
     
     final static short INVALID_SIGNATURE = 0x6A80;
     final static short PROBLEM_KEY_GENERATION = 0x6A81;
     
     final static short e1 = 0x0007;
     final static short e2 = 0x0006;
     final static short e3 = 0x0003;
     
     final static byte[] data = {(byte)0x01, (byte)0x23, (byte)0x45, (byte)0x67, (byte)0x89,
                            (byte)0xAB, (byte)0xCD, (byte)0xEF};

     final static short k = 0x0002;
     
    static byte[] a = {(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x01};
    static byte[] b = {(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x01};
     
    static byte[] pointG = {(byte)0x04, (byte)0x02, (byte)0xFE, (byte)0x13, (byte)0xC0,
                             (byte)0x53, (byte)0x7B, (byte)0xBC, (byte)0x11, (byte)0xAC,
                             (byte)0xAA, (byte)0x07, (byte)0xD7, (byte)0x93, (byte)0xDE,
                             (byte)0x4E, (byte)0x6D, (byte)0x5E, (byte)0x5C, (byte)0x94,
                             (byte)0xEE, (byte)0xE8, (byte)0x02, (byte)0x89, (byte)0x07,
                             (byte)0x0F, (byte)0xB0, (byte)0x5D, (byte)0x38, (byte)0xFF,
                             (byte)0x58, (byte)0x32, (byte)0x1F, (byte)0x2E, (byte)0x80,
                             (byte)0x05, (byte)0x36, (byte)0xD5, (byte)0x38, (byte)0xCC,
                             (byte)0xDA, (byte)0xA3, (byte)0xD9};
   
    static byte[] r = {(byte)0x04, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
                        (byte)0x02, (byte)0x01, (byte)0x08, (byte)0xA2, (byte)0xE0,
                        (byte)0xCC, (byte)0x0D, (byte)0x99, (byte)0xF8, (byte)0xA5, (byte)0xEF};
   
    private KeyPair keyPair;
     private ECPrivateKey ECPrivate;
     private ECPublicKey ECPublic;
     private Signature signature;
     short signLength;
     private byte[] output;
     
     private SignECC (byte[] bArray,short bOffset,byte bLength){
 
          signature = Signature.getInstance(Signature.ALG_ECDSA_SHA, false);

          output = JCSystem.makeTransientByteArray((short)100, JCSystem.CLEAR_ON_DESELECT);
         
          register();
     }
     
     public static void install(byte[] bArray, short bOffset, byte bLength) {
          new SignECC(bArray, bOffset, bLength);
     }

     public boolean select() {
              return true;
     }
     
     public void deselect(){
         
     }
     
     public void process(APDU apdu) {

         byte[] buffer = apdu.getBuffer();

         if ((buffer[ISO7816.OFFSET_CLA] == 0) && (buffer[ISO7816.OFFSET_INS] == (byte)(0xA4)) )
           return;

         if (buffer[ISO7816.OFFSET_CLA] != SignECC_CLA)
            ISOException.throwIt(ISO7816.SW_CLA_NOT_SUPPORTED);
         switch (buffer[ISO7816.OFFSET_INS]) {
           case INS_GEN_KEY_PAIR: 
                 generate_KeyPair(apdu);
                return;
           case INS_SIGN:
                 generate_signature(apdu);
                return;
           case INS_VERIFY:
                 verify_signature(apdu);
                return;
           default: ISOException.throwIt(ISO7816.SW_INS_NOT_SUPPORTED);
         }
     }
     
     private void generate_KeyPair(APDU apdu){

          keyPair = new KeyPair(KeyPair.ALG_EC_F2M, KeyBuilder.LENGTH_EC_F2M_163);
          keyPair.genKeyPair();
         
          ECPublic = (ECPublicKey)keyPair.getPublic();
          ECPrivate = (ECPrivateKey)keyPair.getPrivate();
         
            ECPublic.setFieldF2M(e1, e2, e3);
            ECPublic.setA(a, (short)0, (short)21);
            ECPublic.setB(b, (short)0, (short)21);
            ECPublic.setG(pointG, (short)0, (short)43);
            ECPublic.setK(k);
            ECPublic.setR(r, (short)0, (short)21);
         
          ECPrivate.setFieldF2M(e1, e2, e3);
          ECPrivate.setA(a, (short)0, (short)21);
          ECPrivate.setB(b, (short)0, (short)21);
          ECPrivate.setG(pointG, (short)0, (short)43);
          ECPrivate.setK(k);
          ECPrivate.setR(r, (short)0, (short)21);
    }
     
     private void generate_signature(APDU apdu){
          byte[] buffer = apdu.getBuffer();
         
          signature.init(ECPrivate, Signature.MODE_SIGN);
          signLength = signature.sign(data, (short)0, (short)8, output,(short)0);
          short size = Util.arrayCopy(output, (short)0, buffer, (short)0, signLength);
          apdu.setOutgoingAndSend((short)0, size);
     }
     
     private void verify_signature(APDU apdu){

            signature.init(ECPublic, Signature.MODE_VERIFY);
            boolean result = signature.verify(data, (short)0, (short)8, output, (short)0, signLength);
            if(result == false)
            ISOException.throwIt(INVALID_SIGNATURE);
     }
     
}


JCaberham
Posts: 26
Joined: Mon Nov 30, 2015 3:02 am
Points :208
Contact:

Re: verify function cannot work

Post by JCaberham » Mon Aug 28, 2017 5:14 am

It seems that the keypair you set is invalid. You do not need to set the keys manually as

Code: Select all

keyPair.genKeyPair();
actually generates a valid keypair for you.

Diorin
Posts: 18
Joined: Thu Nov 26, 2015 4:08 am
Points :151
Contact:

Re: verify function cannot work

Post by Diorin » Mon Aug 28, 2017 10:33 pm

How stupid I am. That's the problem. Thank you so much for your pointer.

Post Reply Previous topicNext topic

Who is online

Users browsing this forum: No registered users and 55 guests

JavaCard OS : Disclaimer