I'm developing two applications that use NFC on Android 4.3 for peer-to-peer communication, I have three questions about it.
Can NFC on Android exchange data between two applications with only 1 beam? If it can how to do that and if it cannot then why?
How can I get NFC hardware ID? I'm gonna use it for hardware lock/restriction. If NFC do not have ID, then why?
Is NFC communication secure? must I encrypt the data? If it is then why and if I is not then why?
I'm not quite sure I understand your first question. I assume that you are asking if its possible to establish bidirectional communication between two apps on two different phones. If that's the case, the simple answer is: Beam can't be used to do that. With Android Beam (Android's peer-to-peer mode functionality) you can only send one message in one direction at a time. (Actually you can send one message from each side if your users are good at simultaneously clicking the Beam UI on both devices.)
There simply is no NFC hardware ID. The NFC standard (ISO/IEC 18092) was designed so that devices use random identifiers to protect users' privacy.
No, the NFC interface protocols currently do not implement security features. Encryption/integrity protection/etc. is the responsibility of the application layer. However, there are standards that could add encryption/etc. to lower layers, but these standards are not implemented on current NFC devices.
Related
I'm studying the Bluetooth Low Energy (BLE) protocol (v4.2), and in particular its security features.
I'm trying to understand how the encryption of data transmitted between a mobile App and a BLE device works.
The official documentation (v4.2) specifies the methods to encrypt data, authenticate the devices, generate the keys used in the encryption and pairing phase, etc..
First doubt (I want to be sure to have understood some concepts):
all these functions are implemented in the host level, so if I want to encrypt data transmitted between an App (Android) and a BLE device (like a fitness tracker),
do I have to implement (or enable) these methods on the BLE device?
In this way, the developer should only care about the implementation of these features on the BLE device, since the Android Bluetooth stack just support these features. Am I right?
If I'm wrong, what is the right way to implement these features (on both mobile app and BLE device)?
Second doubt:
Why some BLE devices, implement their own cryptography, on top the GATT protocol, instead using the security features provided by the SIG?
Third and last doubt:
Are the security features specified by the SIG mandatory or are optional?
As you can see I have some doubts, and maybe some questions could be silly, so if someone could clarify how the security mechanisms (like encryption) can be implemented between an App and a BLE device,
and at which levels these features are implemented (OS or application level), I will appreciate a lot.
If you use the standard BLE encryption, it is actually the link layer at the controller that does the encryption/decryption/verifying auth tags. But it's the host layer (SMP) that defines how two devices pair, bond and exchange keys. It's also that layer that tells the link layer to start encryption using the exchanged keys. On Android and iOS, it's the OS that manages the pairing and bonding and implements the SMP. Whether or not Bluetooth pairing/bonding/encryption is used is fully up to the device, and is optional. If it's not supported it must still support to send the error code "Pairing Not Supported"
The Bluetooth standard only has one "use case". This use case is to provide a method for securing the link between two devices so that, after bonding, no one should be able to impersonate a device or be able to manipulate or decrypt the traffic. As you might know, the "LE Legacy Pairing" which is the only pairing method specified up to Bluetooth v4.1, has several flaws that makes it unsecure if the attacker sniffs the traffic during pairing (both for "Just works" and "MITM/passkey entry", but not OOB). The new "LE Secure Connections" defined by Bluetooth v4.2 however uses Diffie Hellman to make it more secure.
Even though Bluetooth pairing itself provides security, there are some flaws in both the Android API and the iOS API that still may not be enough for an app developer if good security is needed. Notably, iOS does not provide any API whatsoever to detect if a given device is actually bonded or if a link is encrypted. It does however show a popup to the user when the pairing starts, but the app knows nothing about that pairing. So, from an iOS app's point of view, you don't know:
If you have paired to the device.
If you talk to a genuine device or a chinese copy.
The security level, i.e. if the pairing used Just Works, MITM legacy pairing or LE Secure Connections.
If the current link is encrypted.
Android is a little bit better. There the app can at least know if the device is bonded or not (but not the other three). There is also an API "createBond" to start the bonding process. The Windows API is much better here, since you can enforce encrypted link when doing GATT operations.
Any of these reasons may be enough for a developer to implement the security from scratch on top of GATT instead. In particular one often common use case is that the developer wants the use case "log in to the peripheral" with a PIN or password. The Bluetooth standard does not support that use case in any way (and no, using "MITM protected pairing with static passkey" doesn't work, since that protocol by design reveals the passkey after one or a few tries).
Anyway, if you develop your own peripheral with your own hardware and want to use the Bluetooth standard's pairing/bonding/encryption, the SDKs by the manufacturers of the BLE chips have usually already implemented this. However, you still need to set it up correctly for it to work. Usually you only have to configure some parameters (like if you have a display or the user can enter a passkey) and then the rest is automatically handled internally by their SDK.
UPDATE:
Source code for Android can be found at https://android.googlesource.com/platform/system/bt/, https://android.googlesource.com/platform/packages/apps/Bluetooth/ and https://android.googlesource.com/platform/frameworks/base/+/master/core/java/android/bluetooth.
I am looking for a way to establish p2p communication between an Android phone (lets call it A) and a PN532+microcontroller (lets call them B).
By p2p I mean a scenario in which:
1. A sends some application specific data to B
2. B receives data and sends a response containing application specific data to A.
I have seen similar questions but most of them date back to 2011, stating that such functionality is not yet supported by the API. Looking at the latest API I can still only see a solution in which B is treated as a TAG.
Am I missing something or is the kind of communication I am looking for is still not supported?
When you want to specifically use NFC peer-to-peer mode, then the same answers are valid today: Android only supports Android Beam for P2P communication. Hence, you can, in general, only transmit one message into one direction and you need to tap the Beam UI each time you want to send data. However, if your interaction is exactly 1 message from Android to PN532 and then 1 message from PN532 to Android, and you are okay with tapping the Beam UI when sending from Android, you could use some tricks to first receive the message from Android, then disconnect and reconnect to send the response to Android.
When you are open to support other modes, then you have some options:
If the Android device has Android 4.4 or later and supports host card emulation (HCE): Use the PN532 in reader/writer mode and implement a HCE service on the Android side.
Otherwise, use the PN532 in host card emulation mode and access it from the Android side using the standard NFC reader/writer API (e.g. IsoDep / NfcA or NfcF).
I want to create an application to exchange information between 2 devices via NFC.
I know how to make one mobile send information to the other using Android Beam. What I don't know is how two phones could send data to each other with just one touch.
Is this possible? If yes, how?
That depends on what you are trying to achieve and what Android version(s) you are using:
Both devices with Android < 4.0
Both devices can send one NDEF message each with no user interaction required. The messages cannot depend on each other (i.e. it's not possible that one device sends a message and the other one sends an answer to this). You would use a combination of enableForegroundNdefPush() and enableForegroundDispatch() to achieve this.
At least one device with Android < 4.4
Both devices can (theoretically) send one NDEF message per touch, but user interaction is required on both devices (i.e. the user needs to touch the Beam UI). Moreover the Beam UI on both devices needs to be touched pretty much at the same time. Otherwise, the Beam UI on the other device will get interrupted due to the received NDEF message. Thus, this "solution" is not really usable. You would use a combination of setNdefPushMessage*() and enableForegroundDispatch() to achieve this.
Both devices with Android 4.4+
Starting with version 4.4, Android has two new features:
NFC reader mode and
Host-based Card Emulation (HCE).
When you combine those feature (i.e. you have a HCE on-host card emulation service on one device and put the second device into reader mode), both devices can communicate with each other (real bi-directional communication) using ISO 7816-4 APDUs.
This is possible, as explained online here. There is also an API demo in the API demos provided with the SDK that discusses this.
However, keep in mind that NFC has a very small payload size, and you're unlikely to be able to transfer any sizable data using it. NFC should instead be used to quickly setup bluetooth connections, or another form of wireless transfer like WiFi direct, which can then be used to transfer larger amounts of data.
Is it possible for an Android application to send a previously stored RFID card ID to a NFC reader? The aim would be to use an Android device to enable access to a room instead of a physical RFID card.
Having read a lot of other threads about NFC/RFID & card-emulation, I came to the conclusion it was not available for now in Android but I'm still kinda confused if it apply to this particular case. Can't the application simply send the card ID within a NDEF message or an APDU command or I'm just completely dreaming?
Well, strictly speaking. For what you want to do you don't need card emulation. You just need to send a token to the door lock that can be validated.
You could do this with Android beam by pushing an NDEF message to a device that is compatible, SNEP is the protocol you'll be looking for.
A solution I would prefer would be to get the door lock device to emulate a tag. Then you could have your Android app register a listener for that tag (Doesn't even need to be running). When the tag is detected that app will fire up and send your secure token to the lock by using the tag write NFC functions in the Android SDK.
Securing your token is another matter.
The android view:
Long story short: It's not possible.
Long story long:
It would be possible from a hardware and software point of view to do this. The NFC chips are perfectly capable to emulate most (not all) standard tags. The functionality to do this is even built in the lower level software but not exposed to applications.
Why: Emulating tags is what the entire mobile payment infrastructure is built upon. Allowing two card emulations of the same type at once is for most NFC chips not possible and will also shut off mobile payment as mobile payment readers only accept a single tag at once (for security reasons).
Things are a bit different for RIM based Blackberry phones, they allow card emulations (even have this feature out of the box) but they don't do any mobile payment at the moment as far as I know.
It is possible?
I state that NFC is enabled on my phone and everything looks correct
I tried with an app called NFC TagWriter by NXP but don't work.
I create a tag with this app and then I tried to listen with other device but don't work, then I installed same app on the other device but don't work.
Please help me or suggested to me another way to do(share tag NFC).
THANKS!
The Android Beamâ„¢ feature allows a device to push an NDEF message onto another device by physically tapping the devices together. This interaction provides an easier way to send data than other wireless technologies like Bluetooth, because with NFC, no manual device discovery or pairing is required. The connection is automatically started when two devices come into range. Android Beam is available through a set of NFC APIs, so any application can transmit information between devices. For example, the Contacts, Browser, and YouTube applications use Android Beam to share contacts, web pages, and videos with other devices.
Reference from Developer Documentation
Also check this for Blog , it explains how to communicate between devices.
You can have (indepedent) p2p communication in 2 directions, and enableForegroundNdefPush is deprecated now; please, use setNdefPushMessage