When I put SIII (Android 4.3) on ACR122U NFC reader the LED keeps blinking green. When I put Samsung S4 (Android 4.3) LED turns green till the time phone is on the reader. In both the cases NFC is turned on and device is in unlocked state.
This behaviour translates into frequent disconnections in SIII and a stable connection on S4. Why two phones behave differently? I am aware of the fact that two phones have NFC chipsets from two different vendors namely NXP and Broadcom.
My question is what is the source for such inconsistent behaviour among these devices?
Another question is why does phone give an ATR at all?
The command sequence for software card emulation using an ACR122U/PN532 can be found in this answer.
In addition to that, there are different versions of the ACR122U:
Some always indicate the presence of a smartcard. In that case it is possible to connect to the "simulated" card using
// SCardConnect with SCARD_SHARE_SHARED, SCARD_PROTOCOL_ANY
Card card = cardTerminal.connect("*");
CardChannel cardChannel = card.getBasicChannel();
After that, PN532 commands can be sent using APDU wrapping:
> FF000000 Lc PN532-COMMAND
< PN532-RESPONSE 9000
with the cardChannel.transmit
method:
CommandAPDU commandAPDU = ...
// SCardTransmit
Response responseAPDU = cardChannel.transmit(commandAPDU);
Other versions of the ACR122U do not always "simulate" the presence of a smartcard. Instead they automatically poll for contactless cards and only indicate card-presence if an actual card is presented to the reader. In that case using cardTerminal.connect("*");
would be only possible if there is an actual card present. However, this is typically not the case in situations where the ACR122U is used in software card emulation mode. In that case it is still possible to establish a connection to the reader using direct mode
// SCardConnect with SCARD_SHARE_DIRECT
Card card = cardTerminal.connect("direct");
After that, the same APDU-wrapped PN532 commands can be exchanged with the reader using escape commands (you might want to check the manual if the escape command is correct for your reader version):
final int IOCTL_SMARTCARD_ACR122_ESCAPE_COMMAND = 0x003136B0; //IOCTL(3500) for Windows
//final int IOCTL_SMARTCARD_ACR122_ESCAPE_COMMAND = 0x42000DAC; //IOCTL(3500) for Linux
byte[] commandAPDU = ...
// SCardControl
byte[] responseAPDU = card.transmitControlCommand(IOCTL_SMARTCARD_ACR122_ESCAPE_COMMAND, commandAPDU);