-5

I am not able to get the pin number for my classic java card application. I have to write APDU command to verify PIN number.

Kindly help me out how to get PIN number

**Wallet.java**

package wallet;

import javacard.framework.*;

public class Wallet extends Applet {

    /**
    * Installs this applet.
    * 
    * @param bArray the array containing installation parameters
    * @param bOffset
    * the starting offset in bArray @param bLength
    * the length in bytes of the parameter data in bArray
    */


    // code of CLA byte in the command APDU header
    final static byte Wallet_CLA =(byte)0xB0;

    // codes of INS byte in the command APDU header
    final static byte VERIFY = (byte)0x20;
    final static byte CREDIT = (byte)0x30;
    final static byte DEBIT = (byte)0x40;
    final static byte GET_BALANCE = (byte)0x50;

    // maximum balance $32,76
    final static short MAX_BALANCE = 0x7FFF;
    // maximum transaction amount
    final static byte MAX_TRANSACTION_AMOUNT = 127;

    // maximum number of incorrect tries before the PIN is blocked
    final static byte PIN_TRY_LIMIT =(byte)0x03;

    // maximum size PIN
    final static byte MAX_PIN_SIZE =(byte)0x08;

    // signal that the PIN verification failed
    final static short SW_VERIFICATION_FAILED = 0x6300;

    // signal the the PIN validation is required
    // for a credit or a debit transaction
    final static short SW_PIN_VERIFICATION_REQUIRED = 0x6301;

    // signal invalid transaction amount
    // amount > MAX_TRANSACTION_AMOUNT or amount < 0
    final static short SW_INVALID_TRANSACTION_AMOUNT = 0x6a83;

    // signal that the balance exceed the maximum
    final static short SW_EXCEED_MAXIMUM_BALANCE = 0x6a84;

    // signal the the balance becomes negative
    final static short SW_NEGATIVE_BALANCE = 0x6a85;

    /* instance variables declaration */
    OwnerPIN pin;
    short balance;

    protected Wallet (byte[] bArray,short bOffset,byte bLength){

        // It is good programming practice to allocate all the memory that an applet needs during
        // its lifetime inside the constructor
        pin = new OwnerPIN(PIN_TRY_LIMIT, MAX_PIN_SIZE);

        // The installation parameters contain the PIN initialization value
        //        pin.update(bArray, bOffset, bLength);
        // Above command causes error.
        register();

    } // end of the constructor

    public static void install(byte[] bArray, short bOffset, byte bLength){
        // create a Wallet applet instance
        new Wallet(bArray, bOffset, bLength);
    } // end of install method

    public boolean select() {
        // The applet declines to be selected if the pin is blocked.
        if( pin.getTriesRemaining() == 0 )
            return false;

        return true;
    }// end of select method

    public void deselect() {
        // reset the pin value
        pin.reset();
    }

    /**
    * Processes an incoming APDU.
    * 
    * @see APDU
    * @param apdu
    * the incoming APDU
    */

    public void process(APDU apdu) {
        byte buffer[] = apdu.getBuffer();
        // check SELECT APDU command 
        if ((buffer[ISO7816.OFFSET_CLA] == 0) && (buffer[ISO7816.OFFSET_INS] == (byte)(0xA4)) )
            return;
        // verify the reset of commands have the correct CLA byte, which specifies the command structure
        if (buffer[ISO7816.OFFSET_CLA] != Wallet_CLA)
            ISOException.throwIt(ISO7816.SW_CLA_NOT_SUPPORTED);

        switch (buffer[ISO7816.OFFSET_INS]) {
            case GET_BALANCE:   getBalance(apdu);
                                return;
            case DEBIT:         debit(apdu);
                                return;
            case CREDIT:        credit(apdu);
                                return;
            case VERIFY:        verify(apdu);
                                return;
            default:       ISOException.throwIt(ISO7816.SW_INS_NOT_SUPPORTED);
        }
    } // end of process method


    private void verify(APDU apdu) {
        byte[] buffer = apdu.getBuffer();
        // retrieve the PIN data for validation.
        byte byteRead = (byte)(apdu.setIncomingAndReceive());

        // check pin the PIN data is read into the APDU buffer at the offset ISO7816.OFFSET_CDATA
        // the PIN data length = byteRead
        if ( pin.check(buffer, ISO7816.OFFSET_CDATA, byteRead) == false )
            ISOException.throwIt(SW_VERIFICATION_FAILED);

    }

}


**wallet.scr**

powerup;
// Select Wallet //aid/B239C74B30/39
0x00 0xA4 0x04 0x00 0x06 0xB2 0x39 0xC7 0x4B 0x30 0x3A 0x7F;  // check 0x3A 0x7f

//Send the APDU here 
// verify
0xB0 0x20 0x00 0x00 0x06 0xB2 0x39 0xC7 0x4B 0x30 0x3A 0x7F;

// credit
0xB0 0x30 0x00 0x00 0x01 0x09 0x7F;
//0x80 0xCA 0x00 0x00 <length> <data> 0x7F;

// debit
0xB0 0x40 0x00 0x00 0x01 0x05 0x7F;

// getBalance
0xB0 0x50 0x00 0x00 0x01 0x7F 0x02;
powerdown;

When I tried to update the pin, it gives response as 69 99 what should be the APDU command to install the applet.

  • -1 : You may/must not be able to get the PIN from your applet! Typically you are able to `set`/`change` it and `verify` it only. The above code doesn't make any sense for us. please add your applet program to the question. – Ebrahim Ghasemi May 25 '15 at 16:36
  • As i know, PIN as the installation parameter in installation command. – JavaCardOS May 27 '15 at 09:20
  • Thanks for the response. I have edited the code. Kindly Guide me how to install the PIN and what should be the APDU command for it, – Krishnakumar May 27 '15 at 13:05

1 Answers1

0

It seems what you want in above code is to have the Applet AID as pin value. In that case maybe you could check whether the AID is less than MAX_PIN_SIZE. Additionally, change your constructor as follow

protected Wallet (byte[] bArray,short bOffset,byte bLength){

    // It is good programming practice to allocate all the memory that an applet needs during
    // its lifetime inside the constructor
    pin = new OwnerPIN(PIN_TRY_LIMIT, MAX_PIN_SIZE);

    // The installation parameters contain the PIN initialization value
    pin.update(bArray, bOffset + 1, bArray[bOffset]);
    // Above command causes error.
    register();

} // end of the constructor

It will ensure that only the AID value will be passed to pin.update(), but you still need to ensure that your AID length is less than MAX_PIN_SIZE, otherwise PINException.ILLEGAL_VALUE will be thrown.

pradithya aria
  • 657
  • 5
  • 10