Android-устройство в качестве NFC Reader для другого Android HCE

Я осознал ситуацию, когда одно устройство Android в качестве считывателя NFC связывается с приложением HCE, установленным на другом устройстве Android. Но были две проблемы:

  1. Он работает только тогда, когда Android-версия устройства, которое работает в качестве считывателя NFC, 4.4 и выше.
  2. Связь между телефонами постоянно прерывалась и восстанавливалась (причина деактивации - DEACTIVATION_LINK_LOSS).

Вот основной класс моего приложения для чтения NFC:

public class ReadingCardActivity extends Activity {
    // list of NFC technologies detected:
    private final String[][] techList = new String[][]{
            new String[]{
                    NfcA.class.getName(),
                    NfcB.class.getName(),
                    NfcF.class.getName(),
                    NfcV.class.getName(),
                    IsoDep.class.getName(),
                    MifareClassic.class.getName(),
                    MifareUltralight.class.getName(),
                    Ndef.class.getName()
            }
    };
    TextView tv;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.tag);
        tv = (TextView) findViewById(R.id.tv);
        tv.setMovementMethod(new ScrollingMovementMethod());
    }

    @Override
    protected void onResume() {
        super.onResume();
        // creating pending intent:
        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, new Intent(this, getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
        // creating intent receiver for NFC events:
        IntentFilter filter = new IntentFilter();
        filter.addAction(NfcAdapter.ACTION_TAG_DISCOVERED);
        filter.addAction(NfcAdapter.ACTION_NDEF_DISCOVERED);
        filter.addAction(NfcAdapter.ACTION_TECH_DISCOVERED);
        // enabling foreground dispatch for getting intent from NFC event:
        NfcAdapter nfcAdapter = NfcAdapter.getDefaultAdapter(this);
        nfcAdapter.enableForegroundDispatch(this, pendingIntent, new IntentFilter[]{filter}, this.techList);
    }

    @Override
    protected void onPause() {
        super.onPause();
        // disabling foreground dispatch:
        NfcAdapter nfcAdapter = NfcAdapter.getDefaultAdapter(this);
        nfcAdapter.disableForegroundDispatch(this);
    }

    @Override
    protected void onNewIntent(Intent intent) {
        if (intent.getAction().equals(NfcAdapter.ACTION_TAG_DISCOVERED)) {
            if (intent.getAction() != null) {
                Tag tagFromIntent = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
                try {
                    IsoDep iso = IsoDep.get(tagFromIntent);
                    iso.connect();
                    tv.setText(tv.getText() + "\nResponse from card: " + Utils.byteArrayToHexString(selectAID(iso)));
                    iso.close();
                } catch (Exception ex) {
                    tv.setText(tv.getText() + "\nException: " + ex.toString());
                }
            }
        }
    }

    public byte[] selectAID(IsoDep iso) throws Exception {
        byte[] wakeUpCommand = {(byte) 0x00, (byte) 0xA4, (byte) 0x04,(byte) 0x00, (byte) 0x08,
                (byte) 0x4C, (byte) 0x65, (byte) 0x6C,(byte) 0x61,
                (byte) 0x6E, (byte) 0x74, (byte) 0x6F, (byte) 0x73,
                (byte) 0x00};
        return iso.transceive(wakeUpCommand);
    }
}

А вот мой сервис в приложении HCE:

@Override
    public byte[] processCommandApdu(byte[] apdu, Bundle extras) {
        sendResult("Terminal sent apdu " + Utils.byteArrayToHexString(apdu));
        byte[] response = Hex.decodeHex(SUCCESSFUL_RESPONSE.toCharArray());
        return response;
}

Вы также можете захотеть увидеть мой файл apduservice.xml, чтобы увидеть мой номер AID:

<?xml version="1.0" encoding="utf-8"?>
<host-apdu-service xmlns:android="http://schemas.android.com/apk/res/android"
                   android:requireDeviceUnlock="false">
    <aid-group android:category="other">
        <aid-filter android:name="4C656C616E746F73"/>
    </aid-group>
</host-apdu-service>

Это мой onDeactivated Метод в приложении HCE:

@Override
    public void onDeactivated(int reason) {
        switch (reason) {
            case DEACTIVATION_LINK_LOSS:
                sendResult("\nDeactivation was due to the NFC link being lost.\n");
                break;
            case DEACTIVATION_DESELECTED:
                sendResult("\nDeactivation was due to a different AID being selected.\n");
                break;
        }
    }

И вывод приложения HCE:

+---------------------------------------------+
Terminal sent apdu 00A40400084C656C616E746F7300
Deactivation was due to the NFC link being lost.
Terminal sent apdu 00A40400084C656C616E746F7300
Deactivation was due to the NFC link being lost.
Terminal sent apdu 00A40400084C656C616E746F7300
Deactivation was due to the NFC link being lost.
+---------------------------------------------+

Может ли кто-нибудь помочь мне с этими проблемами?

0 ответов

Другие вопросы по тегам