3

APDU 応答を TLV 形式に解析するために、多くのサンプル コードを試しました。応答の長さが短い場合は適切に解析できますが、長さが長い場合は問題に直面しています(ライブラリなしでタグの長さを計算する方法)

注:定数で定義済みのタグを使用しています

コード:

private HashMap<String, String> parseTLV(String apduResponse) {

    HashMap<String, String> tagValue = new HashMap<>();
    String remainingApdu = apduResponse.replaceAll(" ", "");
    if (remainingApdu.endsWith(ResponseTags._SUCCESS_STATUSWORDS)) {
        remainingApdu = remainingApdu.substring(0, remainingApdu.length() - 4);
    }
    while (remainingApdu != null && remainingApdu.length() > 2) {
        remainingApdu = addTagValue(tagValue, remainingApdu);
    }
    return tagValue;
}

addTagValue メソッド

   private String addTagValue(HashMap<String, String> tagValue, String apduResponse) {
        String tag = "";
        String length = "";
        String value = "";
        int tagLen = 0;

        if (tagUtils.isValidTag(apduResponse.substring(0, 2))) {
            tagLen = readTagLength(apduResponse.substring(3));
            // tagLen = 2;
            tag = apduResponse.substring(0, 2);
        } else if (tagUtils.isValidTag(apduResponse.substring(0, 4))) {
            tagLen = 4;
            tag = apduResponse.substring(0, 4);
        } else {
            return "";
        }
        Log.e("TAG_LEN","tag: "+tag+"taglen: "+tagLen);
        if (tagUtils.shouldCheckValueFor(tag)) {
            length = apduResponse.substring(tagLen, tagLen + 2);
            int len = tagUtils.hexToDecimal(length);
            value = apduResponse.substring(tagLen + 2, (len * 2) + tagLen + 2);
            tagValue.put(tag, value);
            if (ResponseTags.getRespTagsmap().containsKey(tag)) {
                //logData = logData + "\nKEY:" + tag + " TAG:" + ResponseTags.getRespTagsmap().get(tag)/* + " VALUE:" + value + "\n "*/;
            }
            if (tagUtils.isTemplateTag(tag)) {
              //  logData = logData + "\n\t-->";
                return addTagValue(tagValue, value) + apduResponse.substring(tag.length() + value.length() + length.length());
            } else {
                return apduResponse.substring(tag.length() + value.length() + length.length());
            }
        } else {
            value = apduResponse.substring(2, 4);
            tagValue.put(tag, value);
//            logData = logData + "\n\t\tKEY:" + tag + " TAG:" + ResponseTags.getRespTagsmap().get(tag) /*+ " VALUE:" + value + "\n "*/;
            return apduResponse.substring(tag.length() + value.length() + length.length());
        }
    }

readTagLength :

private int readTagLength(String apduResponse) {
    int len_bytes = 0;
    if (apduResponse.length() > 2) {
        len_bytes = (apduResponse.length()) / 2;
    }
    Log.e("tlv length:", "bytes:" + len_bytes);
    if (len_bytes < 128) {
        return 2;
    } else if (len_bytes > 127 && len_bytes < 255) {
        return 4;
    } else {
        return 6;
    }
}

数枚のカードで適切な長さを取得できません (apdu 応答が長い場合) 助けてください

4

2 に答える 2

1

コードに入る前に、まず入力データが適切であることを確認してください。完全なデータを取得し、https://www.emvlab.org/tlvutils/で試してください。

データが適切であることを確認したら、EMV 4.3 Book 3、付録 B BER-TLV データ オブジェクト セクション B1、B2、B3 の規則を細心の注意を払って確認します。

これに正確に従えば、タグの静的リストを保存する必要はありません。将来的に時間が節約されます。

于 2018-12-28T11:00:45.863 に答える