setATRHistBytes()方法始终返回false [英] setATRHistBytes() method always returns false

查看:104
本文介绍了setATRHistBytes()方法始终返回false的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我编写了以下程序,将智能卡的ATR中的 Historical Bytes (历史字节)更改为例如0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00.我使用GPSystem.setATRHistBytes()设置历史字节.

I wrote the following program to change the Historical Bytes in the ATR of my smartcard to, for example, 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00. I use GPSystem.setATRHistBytes() to set the historical bytes.

请注意,0x00 0x00 ... 0x00不是我用于历史字节的实际值,但我检查了它.实际值是一个由15个字节组成的数组,该数组等于另一个现有卡的历史字节.

Note that 0x00 0x00 ... 0x00 is not the actual value that I'm using for the historical bytes but I censored it. The actual value is an array of 15 bytes that is equal to the historical bytes of another exisitng card.

package org.globalplatform;

import javacard.framework.*;
import org.globalplatform.GPSystem;

public class TestPrj extends Applet {

    public static final byte[] HIST_B= {(byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00};
    public static byte counter = (byte) 0x00;

    public static void install(byte[] bArray, short bOffset, byte bLength) {
        new TestPrj();
    }

    protected TestPrj() {
        register();
    }

    public void process(APDU apdu) {

        if (selectingApplet()) {
            if (counter == 0x03) {
                counter = (byte) (counter + 1);
                boolean changed = GPSystem.setATRHistBytes(HIST_B, (short) 0, (byte) HIST_B.length);
                if (changed) {
                    ISOException.throwIt((short) 0x9000);
                } else {
                    ISOException.throwIt((short) 0x6400);
                }

            } else {
                counter = (byte) (counter + 1);
            }
        }

        ISOException.throwIt((short) counter);
    }
}

将上述程序转换为其CAP文件并以Default Selected特权安装小程序(使用GPSystem.setATRHistBytes()必需)后,更改历史字节仍然有问题.

After converting the above program to its CAP file and installing the applet with Default Selected privilege (which is required to use GPSystem.setATRHistBytes()), I still have problems with changing the historical bytes.

根据我收到的APDU响应,似乎setATRHistBytes()方法始终返回false,指示历史字节未更新.

Based on the APDU responses that I receive, it seems that the setATRHistBytes() method always returns false indicating the the historical bytes are not updated.

Connect successful.
Download Cap begin...
Download Cap successful.
Install Applet begin...
Install Applet successful.
Send: 00 A4 04 00 06 01 02 03 04 05 01
Recv: 00 01
Time used: 22.000 ms
Send: 00 A4 04 00 06 01 02 03 04 05 01
Recv: 00 02
Time used: 23.000 ms
Send: 00 A4 04 00 06 01 02 03 04 05 01
Recv: 00 03
Time used: 24.000 ms
Send: 00 A4 04 00 06 01 02 03 04 05 01
Recv: 64 00
Time used: 15.000 ms
Send: 00 A4 04 00 06 01 02 03 04 05 01
Recv: 00 05
Time used: 15.000 ms

请注意,01 02 03 04 05 01是我的applet AID.

Note that 01 02 03 04 05 01 is my applet AID.

我的卡是JCOP v2.4.2 R3,我试图同时使用GP 2.2.1 v1.6和GP 2.2 v1.4 API进行编译.

My card is JCOP v2.4.2 R3 and I tried to compile against both GP 2.2.1 v1.6 and GP 2.2 v1.4 APIs.

推荐答案

setATRHistBytes(byte[] baBuffer, short sOffset, byte bLength)需要一个作为输入缓冲区(baBuffer)传递的全局数组.请参见 API文档:

setATRHistBytes(byte[] baBuffer, short sOffset, byte bLength) requires a global array passed as input buffer (baBuffer). See the API documentation:

baBuffer-包含ATR历史字节的源字节数组. 必须是全局数组.

baBuffer - the source byte array containing the ATR historical bytes. Must be a global array.

全局数组是一种特殊的数组,由Java Card运行时管理,并且所有小程序都可以访问.在调用process() applet lifecylce方法期间,可以期望Java Card applet可用的唯一全局缓冲区是APDU缓冲区.

A global array is a special array that is managed by the Java Card runtime and accessible by all applets. During the invokation of the process() applet lifecylce method, the only global buffer that you can expect to be available to your Java Card applet is the APDU buffer.

因此,您需要将HIST_B的内容复制到APDU缓冲区中,然后将APDU缓冲区传递到setATRHistBytes():

Therefore, you need to copy the contents of HIST_B into the APDU buffer and then pass the APDU buffer into setATRHistBytes():

byte[] buffer = apdu.getBuffer();
Util.arrayCopyNonAtomic(HIST_B, (short)0, buffer, (short)0, (short)HIST_B.length);
boolean changed = GPSystem.setATRHistBytes(buffer, (short)0, (short)HIST_B.length);

这篇关于setATRHistBytes()方法始终返回false的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆