Accessing card-emulation mode on USB-NFC-Reader - android

I have an Android tablet with Android 4.2. This tablet does not have NFC hardware. However I have an external USB reader: ACR 1252U, that came with an Android library. I have asked some general questions of my setup here. Now that it gets more specific, I need to ask another one. In this previous question I found out, that I can use the ACS Android library to access the readers card emulation capabilities.
My first goal is to make that reader emulate an NFC tag, that contains a URL. Any NFC-capable Android phone should be able to scan this emulated tag and automatically open the browser. I have tested it, and it works with a real (physical) tag. But unfortunately I am not able to emulate this tag correctly...
Now I wrote an Android application, but I am stuck. According to the readers API (PDF), I can get it into card emulation mode by sending the command
E0 00 00 40 03 01 00 00
When I do this, it gives me the answer:
E1 00 00 00 03 01 01 01
This confirms, that it is in card emulation mode. With an Android application I now can scan the emulated Tag, which says, that this is recognized as a "NXP MIFARE Ultralight" tag.
My problem now is, how to feed the tag with a URL. According to the reader API (section 5.10.3), I need to send the command:
E0 00 00 60 13 01 01 00 0F D1 01 0B 55 01 67 6F 6F 67 6C 65 2E 63 6F 6D
where D1 01 0B 55 01 67 6F 6F 67 6C 65 2E 63 6F 6D is the NDEF message that contains the URL "http://www.google.com". I created this NDEF message using this Android Java code:
String target_url = "http://www.google.com";
Uri uri = Uri.parse(target_url);
NdefRecord recordNFC = NdefRecord.createUri(uri);
NdefMessage message = new NdefMessage(recordNFC);
An application on my Android phone, that reads NFC tag says the following:
As you can see, the URL is saved on the emulated tag.
So why doesn't the browser of my phone open the url?
Am I missing something? Are my commands wrong?
Why are there some "?" characters?

The command that you are using,
E0 00 00 60 <Lc> 01 01 <Byte address> <Length> <Data>
writes data bytes starting at block 3 of the emulated NFC Forum Type 2 tag. Thus, the byte address 0x00 addresses the first byte of block 3.
The problem that you are facing is that you only write the NDEF message itself starting at block 3 (byte 0). However, an NFC Forum Type 2 tag needs further metadata. Specifically, block 3 is the capability container block. For the specific memory layout presented by the ACR1252U, the CC block would need to be filled with the value
E1 10 06 00 (if write access should be allowed) or
E1 10 06 0F (if other NFC devices should treat the tag as read-only).
E1 is the magic number indicating that this is an NFC Forum tag, 10 refers to version 1.0 (the current version) of the data mapping defined by the NFC Forum Type 2 Tag Operation specification, and 06 indicates that the tag has a total of 12 data blocks.
Further, you need to wrap the NDEF message into an NDEF Message TLV block. The NDEF Message TLV block has the tag 0x03. Thus, the wrapped NDEF message would look like this:
03 0F D1010B5501676F6F676C652E636F6D
The tag memory, that you need to write would therefore look like this:
E1 10 06 00
03 0F D1 01
0B 55 01 67
6F 6F 67 6C
65 2E 63 6F
6D
Finally, you should fill the tag memory to full blocks by placing a Terminator TLV (tag 0xFE, no length) at the end and filling the remaining bytes with zeros (0x00). This also applies to the case where the data is already aligned to full blocks but there is further (empty) blocks beyond the end of your data.
E1 10 06 00
03 0F D1 01
0B 55 01 67
6F 6F 67 6C
65 2E 63 6F
6D FE 00 00
Thus, you would want to use the following write command to store the data on the emulated Type 2 tag:
E0 00 00 60 1C 01 01 00 18 E1 10 06 00 03 0F D1 01 0B 55 01 67 6F 6F 67 6C 65 2E 63 6F 6D FE 00 00

Related

How does one read data from a BLE device in Android?

My mobile phone app is supposed to be the central device and the BLE kit is supposed to be the peripheral device. I have managed to write to Kit, as in send data. The kit itself according to it documentation has this:
According to the documentation: The Rx (receive) and Tx (transmit) Characteristics are named from the point of view of the Peripheral BGX device.
To send a string to be received by the Peripheral serial interface, write to the Rx Characteristic.
To read a string transmitted from the Peripheral serial interface, enable Notifications or Indications from the Tx Characteristic then wait for subsequent Notification or Indication Events to occur.
So how exactly am I supposed to Read data from the device mentioned if the characteristic for receiving data doesn't have READ as one of its properties?
When I sent data as in writing data to the device I used the writeCharacteristic function.
fun write(message:String){
val bytes = BigInteger(message.replace("\\s".toRegex(), ""), 16).toByteArray()
Timber.i("Bytes value ---> ${bytes.toHexString()}")
val device = getBleDevice()
val characteristicRX = getBleCharacteristic()
writeCharacteristic(device, characteristicRX, bytes)
}
Then I would call this function to send:
fun sendMessage(message:String){
Timber.i("Check if isConnected = true --> ${isConnected.value}")
if(isConnected.value == true){
write(message)
}else{
Timber.e("Make sure that you connected and paired with the desired device.")
}
}
So how do I go on about receiving data instead from the BLE device? Wouldn't the readCharacteristic function come into play here? I ask this because the code I am working on was original designed to exchange data using classical Bluetooth and I was tasked with converting it into BLE instead. But when I used a serial monitor to see the bytes being sent I found that the buttons that are supposed to trigger receiving data are instead sending it to the Kit. This caught my attention as I haven't started working on the reading mechanism and the screenshot I posted here also has me puzzled, as I have thought that the TX characteristic would be a readable one not writeable.
In my app each parameter has a code. If it's a write command it looks like this:
enum class WriteCommandCodes(val value: String) {
TOOL_ADDRESS("08 00 00 00 20 30 04 27"),
RPM_THRESHOLD("08 00 00 00 20 30 04 13"),
BACKLASH_1("08 00 00 00 20 30 04 22"),
BACKLASH_2("08 00 00 00 20 30 04 23"),
DELAY("08 00 00 00 20 30 04 20"),
BATTERY1_CAPACITY("08 00 00 00 20 30 0F"),
BATTERY2_CAPACITY("08 00 00 00 20 30 10")}
the payload that is created later on has both the parameter's code and the data being sent.
for the Read parameters I have this:
enum class ReadRequestCodes(val value: String) {
KEY_ADDRESS("08 00 00 00 20 30 05 11 00 00 00 00 00"),
TOOL_ADDRESS("08 00 00 00 20 30 05 27 00 00 00 00 00"),
RPM_THRESHOLD("08 00 00 00 20 30 05 13 00 00 00 00 00"),
BACKLASH("08 00 00 00 20 30 05 22 00 00 00 00 00"),
POWER_SRC_TYPE("08 00 00 00 20 30 05 26 00 00 00 00 00"),
BATTERY1_PERCENTAGE("08 00 00 00 20 30 11 00 00 00 00 00 00"),
BATTERY2_PERCENTAGE("08 00 00 00 20 30 12 00 00 00 00 00 00")}
The same is supposed to happen only difference is I'll be receiving this time around.
Yes you override the default onCharacteristicChanged method and implement what you want to do with the new data. You can see someone doing something similar here
BLE receiving GATT notifications from a characteristic

How to parse data from NfcA tag?

I am reading NfcA tags using RFID reader described in following link.
MF7-28
I have connected this tag reader serially, reader is sending data when I scan the tags with the reader.
But data doesn't match with the serial ID of the tags.
Serial Id is printed on the tag and we can also read it using Android phone.
Data Got From reader : BF 96 F6 93 75 95 75 79 E5 EB F9 00
Data from Android : EC E5 86 73 FC 88 04 00 C0 8E 1E 97 45 00 17 13
Where Serial Id printed on tag is : 73 86 E5 EC , so this must be the revers of first 4 bytes in reverse order EC E5 86 73.
Can anyone please help me to decode the data from tag Reader?
or is that possible to write some code in android to get the data in the same format return by tag reader?
Following is the complete hex from Sector 1.
ECE58673FC880400C08E1E9745001713
140103E103E103E103E103E103E103E1
03E103E103E103E103E103E103E103E1
A0A1A2A3A4A5787788C1FFFFFFFFFFFF

How to calculate IV on AuthenticateISO on DESFire EV1

I'm having troubles creating new IV after authenticating. I'm not sure if my understanding of the concept is right, even with MIFARE documentation. Data on the card is fully enciphered.
These are the steps I'm taking:
AuthenticateISO with zero IV (0x1A with 3K3DES key)
Response from card (encrypted RandA'):
08 48 CD A3 43 C5 00 FE 1D 78 D1 E5 A9 24 26 5A 91 00
First 8 bytes should be CMAC and updated IV(?): 08 48 CD A3 43 C5 00 FE
Create 3K3DES session key: 74 EF 23 87 10 E4 3B E6 BE C8 4C 41 74 03 08 A9 7F F3 FA 59 15 E4 C5 06
Call getValue:90 6C 00 00 01 [FileID] 00
Response from card: A2 3C CB 70 BE 4D D5 22 91 00
Decrypt first 8 bytes from response with session key and updated IV
Decrypted result: 7F 7D 80 F5 [CRC32]
After the last step, the first four bytes should be the value and the last four CRC32. But for sure I'm not doing something right with IV, because result isn't correct. It should be 0F A0 00 00 [CRC32].
Could anyone have any pointers to what I'm doing wrong? I've been trying to solve this for at least 2 weeks and have come nowhere.
You put Android Tag in your Question. I would suggest you to use TapLinx SDK which is free of charge and offer Java Level APIs for MIFARE and some other NXP Cards. It makes communication to card a lot easier and Documentation is good.
MIFARE Developer Page
TapLinx SDK download and Application Note

Android HCE: are there rules for AID?

I'm trying to use an ACR122 NFC reader to select an application emulated in
one Nexus 5 using Android Host Card Emulation. However, small AIDs are not
recognized.
My goal is to use a three byte long AID, as I do in a DESfire card. My first goal
is only to be able to do a SELECT command.
My test app uses the following configuration for AIDs:
<host-apdu-service xmlns:android="http://schemas.android.com/apk/res/android"
android:description="#string/service_descr"
android:requireDeviceUnlock="false" >
<aid-group
android:category="other"
android:description="#string/aid_descr" >
<aid-filter android:name="A0A1A2" />
<aid-filter android:name="B0B1B2B3" />
<aid-filter android:name="C0C1C2C3C4" />
<aid-filter android:name="D0D1D2D3D4D5" />
<aid-filter android:name="E0E1E2E3E4E5E6" />
</aid-group>
</host-apdu-service>
If I run the following APDUs:
00 a4 04 00 03 a0 a1 a2 00
00 a4 04 00 04 b0 b1 b2 b3 00
00 a4 04 00 05 c0 c1 c2 c3 c4 00
00 a4 04 00 06 d0 d1 d2 d3 d4 d5 00
00 a4 04 00 07 e0 e1 e2 e3 e4 e5 e6 00
I always get the following responses:
=> 00 a4 04 00 03 a0 a1 a2 00
<= 6f 00
=> 00 a4 04 00 04 b0 b1 b2 b3 00
<= 6a 82
=> 00 a4 04 00 05 c0 c1 c2 c3 c4 00
<= 90 00
=> 00 a4 04 00 06 d0 d1 d2 d3 d4 d5 00
<= 90 00
=> 00 a4 04 00 07 e0 e1 e2 e3 e4 e5 e6 00
<= 90 00
So, only AIDs with length greater than 5 bytes will work with Android? Or am I
doing something really wrong?
The rules for smartcard application identifiers (AIDs) are defined in ISO/IEC 7816-4. An AID may consist of up to 16 bytes. Based on the first 4 bits, AIDs are divided into different groups. The most relevant groups defined in ISO/IEC 7816-4 are:
AIDs starting with 'A': internationally registered AIDs
AIDs starting with 'D': nationally registered AIDs
AIDs starting with 'F': proprietary AIDs (no registration)
For (inter)nationally registered AIDs, the AID is split into two parts, a 5-byte mandatory RID (registered application provider identifier), and an optional PIX (proprietary application identifier extension) of up to 11 bytes.
For proprietary AIDs (F...) ISO/IEC 7816-4 does not clearly mandate any minimum length requirements.
In addition to this, when it comes to HCE and routing of card emulation communication from the NFC controller to secure elements or the application processor, there is the NFC Forum NCI specification. This specification mandates an AID (used in AID-based routing entries) to be between 5 and 16 bytes. Btw. the same limitation applies to smartcards following the Java Card specifications.
When it comes to Android, there is a hard-coded requirement that AIDs received in a SELECT command consist of at least 5 bytes:
In method resolveAid() in RegisteredAidCache.java on line 142
In method findSelectAid() in HostEmulationManager.java on line 390 (which actually causes the odd behavior that the 4 byte AID is rejected with a "File or application not found" (6A82) status word as the check does not properly account for the Le byte)
According to EMV standards, an AID is made up of a Registered Application Provider Identifier (RID) having a minimum of 5 bytes, and an optional Application Identifier Extension (PIX) or proprietary Application Identifier having a maximum length of 11 bytes, which together make up the Application ID (AID), thus, the application ID can never be less than 5 bytes in length. If there are several applications present in the card, the AIDs will have the optional app identifiers appended to the RID to differentiate between the applications present in the card. Please read up on EMV standards on their site: EMVCO, and especially their books, Book 1 to Book 4, to understand more in this.

Is there an NFC API for the Smartwatch 3 (SWR50)

Just to be sure and have clarification of that at first, is the NFC of the Smartwatch 3 just an embedded tag or is it a theoretically fully functioning NFC-chip?
Hoping it's not just a tag, we want to build an Android Wear app using NFC and for this the biggest question is:
Is there (gonna be?) a API to use the NFC chip of the SWR50?
If not is there any other way to activate it, or maybe might an updated version of Android Wear bring support for the chip to the smartwatch?
Any help is appreciated!
Thanks, Chris
TLDR:
Basically it's the same question for the new smartwatch 3 of sony: Is NFC usable for developers?
Is there an NFC API for the Sony SmartWatch 2?
I finally got my hands on one of those smart watches. This is what I found so far.
Scanning the SWR50 as a tag:
The SWR50 is identified as an NFC Forum Type 2 Tag manufactured by Broadcom. The 7-byte-UID of the watch that I tested is 2e020d00000000. Both, the fact that I could not find any dedicated Type 2 tags from Broadcom and the many zeros in the UID, make me think that this might be a tag emulated using some NFC controller.
The tag has 122 blocks (times 4 bytes makes 488 bytes in total) containing the following data:
0: 2e 02 0d 0c 1: 00 00 00 00
2: 00 00 ff ff 3: e1 11 3c 0f
4: 00 00 00 01 5: 03 78 30 35
6: 03 31 d4 0f 7: 1f 61 6e 64
8: 72 6f 69 64 9: 2e 63 6f 6d
10: 3a 70 6b 67 11: 63 6f 6d 2e
12: 67 6f 6f 67 13: 6c 65 2e 61
14: 6e 64 72 6f 15: 69 64 2e 77
16: 65 61 72 61 17: 62 6c 65 2e
18: 61 70 70 fe 19: ff ff ff ff
20: 30 a8 db f2 21: 43 1c ff ff
22: 30 a8 db f5 23: 2a 78 ff ff
24: 14 39 2d 4d 25: f2 6a 91 40
26: ff ff ff ff 27: ff ff ff ff
(remaining blocks are all filled with ff ff ff ff)
The static lock bits (block 2, bytes 2 and 3) are all set (indicates locked state).
Block 3 contains a capability container for a Type 2 tag (magic byte 0xE1).
However, the mapping version number 1.1 (0x11) does not comply to any of the current mapping version documents provided by the NFC Forum! The only mapping version number that is currently defined is 1.0.
Block 4 contains 3 NULL TLVs (0x00) and the first byte of a Lock Control TLV (tag 0x01).
The Lock Control TLV indicates that there are 48 lock bits located starting at byte position 232 (= 7 * 25 + 8). I.e. 6 bytes starting at block 58, so they are all set (0xFFFFFFFFFFFF). Each lock bit locks 3 bytes, so they indicate that blocks 16 to 51 are locked.
Block 6 contains the start of an NDEF Message TLV (tag 0x03, length 0x31). The NDEF message consists of a single NDEF record (Android Application Record for app com.google.android.wearable.app):
+--------------------------------------------+
| TNF: EXTERNAL TYPE |
| Type: urn:nfc:ext:android.com:pkg |
+--------------------------------------------+
| Payload: com.google.android.wearable.app |
+--------------------------------------------+
Block 18 contains a Terminator TLV (tag 0xFE) indicating the last TLV block within the tag memory area.
Blocks 20 and 21 (first 2 bytes) contain the device Bluetooth address.
Blocks 22 and 23 (first 2 bytes) contain something that looks like a Bluetooth address too.
Blocks 24 and 25 contain the device serial number.
The remaining blocks are all filled with FF FF FF FF.
Android NFC API access:
Requesting an instance of the NFC adapter fails (the getDefaultAdapter() method returns null):
NfcManager nfcMgr = (NfcManager)mContext.getSystemService(Context.NFC_SERVICE);
NfcAdapter nfcAdapter = nfcMgr.getDefaultAdapter(); // -> null
In addition there is a log message that the device does not support NFC.
V/NFC: this device does not have NFC support
Looking at the NFC system features, none of the NFC system features are available:
PackageManager pkgMgr = mContext.getPackageManager();
boolean featureNfc = pkgMgr.hasSystemFeature("android.hardware.nfc"); // -> false
boolean featureHce = pkgMgr.hasSystemFeature("android.hardware.nfc.hce"); // -> false
Both featureNfc and featureHce are false, so neither android.hardware.nfc nor android.hardware.nfc.hce are available.
So there is currently no NFC API available on the SWR50.
Firmware analysis:
There is a file named BCM43341B0_002.001.014.0122.0174.hcd under /system/vendor/firmware/, so it seems that the watch actually does contain Broadcom's BCM43341 quad-radio chip which also contains an NFC controller.
/proc/misc lists bcm2079x, so it seems that the bcm2079x driver was compiled into the kernel.
There is no NFC service app (Nfc*.apk) on the /system partition.
So there might be support for NFC from the hardware side and the kernel side, but the user-space part of the NFC stack is missing. Though the kernel driver might just as well point to nowhere. And the firmware of the BCM43341 might be coded in a way that the NFC controller simply emulates the Type 2 tag while being inaccessible from the operating system.
There is a fully functional chip in the SmartWatch 3. It is today acting according to the spec linked by CM787 (here's a new one as the old one seems dead).
When Android Wear officially expands on the support for NFC, the SmartWatch 3 will be able to follow.
Nope. It says the NFC is for powering on or pairing on the spec sheet. Doesn't look like 3rd party developers are going to get a crack at it this time around.
The smartwatch supports NFC, based on the specs here http://www.smartwatchspecifications.com/Device/smartwatch-3-swr50/, yet there is no NFC API available as of now, hopefully there will be one, I'm also looking for this functionality, planning to develop apps with this feature

Categories

Resources