Bluecove : check if device is paired? - java

I am new to using Bluecove API and it seems that after a lot of research, I still cannot find a way to check if a RemoteDevice is already paired to the running machine or not.
First of all, I successfully manage to start a scan however, I find it strange that Bluecove does not offer a way to only look for devices that are in discoverable mode hence the need to check if paired or not ...
To be more precisded I am "translating" a project that I developped in C# using InTheHand.dll for Bluetooth management. This assembly is great and helped me achieved what I wanted to do : scan for devices in discoverable mode and in range, initiate pairing process, handle data via Bluetooth streams.
I need to do the same thing with Bluecove.
Why is it so hard to find answers ? The documentation says almost nothing about pairing although I managed to pair a device I knew was not paired via RemoteDevice.authenticate().
Anyway to summup :
How to start a scan for only devices in discovery mode ?
How to find out whether a device was already paired or not ?
Note :
using both RemoteDevice.isAuthenticated() and RemoteDeviceHelper.implIsAuthenticated(remoteDevice) always return false regardless of the paired status.
Note 2 :
Furthermore, having a lookg at RemoteDeviceHelper.javafrom http://bluecove.googlecode.com/svn/trunk/bluecove/src/main/java/com/intel/bluetooth/RemoteDeviceHelper.java , there is a private property for boolean paired.
It seems no public method will use it ...
Even weirder and desperatly frustating, in the debugger mode, looking at a specific RemoteDevice, I can see the value of this property. It is indeed false when device is not paired, and true if device is paired ! So why can't the API tell me so ?
What should I do ? Thanks for the help !

List of paired devices:
import javax.bluetooth.*
...
RemoteDevice[] rdList = LocalDevice.getLocalDevice().getDiscoveryAgent().retrieveDevices(DiscoveryAgent.PREKNOWN);
Get name & address of paired device:
rdList[0].getBlueToothAddress();
rdList[0].getFriendlyName(true);
Some comments:
list of paired devices can contain multiple devices having the same name
boolean parameter of getFriendlyName() means if agent should query device for its name, but returns cached name if device is not available (at least my tests showed that)

Related

Android, How to properly scan and filter ble UUID's

I am working with BluetoothLe on Android (min API : 21+). Currently the procedure of filtering service uuid's works, but not quite as expected. Below is a code segment used for setting up the basic scanner parameters, this is what currently works. Based on areas of other work with Ble, (iOS, Embedded Hardware) it becomes apparent that there are abilities to filter Ble devices based on their 16-bit UUID assignments only. Which brings me to Android... I realized android has had a rather rough start to Ble and its rather segmented ecosystem of devices, but I fail to see how/why android cant follow similar paths with the UUID's like other platforms. As all the UUID's coming from the Bluetooth SIG are 16-bit identifiers only with a mere definition of a UUID_BASE (00000000-0000-1000-8000-00805F9B34FB).
...
// devices UUID service
ParcelUuid parcelUuid = new ParcelUuid(UUID.fromString("1F0E0D0C-0B0A-0909-0807-060504030201"));
// devices UUID service mask
ParcelUuid parcelUuidMask = new ParcelUuid(UUID.fromString("00000D0C-0000-0000-0000-000000000000"));
// Filters and Settings
scanFilter = new ScanFilter.Builder().setServiceUuid(parcelUuid, parcelUuidMask).build();
scanFilterList.add(scanFilter);
scanSettings = new ScanSettings.Builder().setScanMode(ScanSettings.SCAN_MODE_LOW_POWER).build();
// Scanning Started
mBluetoothLeScanner.startScan(scanFilterList, scanSettings, scanCallback);
...
With all that stated above, I have two Embedded Hardware devices broadcasting Two of their own UUID Services that are very similar to one another but different non the less. Below are those UUID's, in all accounts only the MSB(Most Signifigant Byte) is the differentiator amongst them all. Also there Device Names are different.
Device One:
Service 1 - 1F0E0D0C-0B0A-0909-0807-060504030201
Service 2 - 2F0E0D0C-0B0A-0909-0807-060504030201
Device Two:
Service 1 - EF0E0D0C-0B0A-0909-0807-060504030201
Service 2 - FF0E0D0C-0B0A-0909-0807-060504030201
Common Identifier amongst the UUID's:
0x0D0C
From the code segment provided earlier, the ParcelUuid that is used in the setServiceUuid method appears to require an exact match for the scanner to even return a device, despite the matching mask needed. How then, do you make the request to the drivers/hardware to filter only by 16-bit Identifiers instead of the full 128-bit Identifiers?? Because the model I have presented above with the two different devices, each with their own Service UUID's different from the other, isn't capable of scanning and returning all the devices wanted or expected.
I feel like the problem I'm having is two-fold but needs to addressed, because I cant seem to find the answer anywhere. I have searched high and low for all forum post, stack questions/answer that touch on this topic but none of them appear to pop out as what I'm looking for. I'm not sure if my understanding of filtering on android is faulty, if android is missing features, or inability to find such features in the supplied classes of android. I have a few thoughts on how to accomplish this "feature" in software but it will be rather ugly, time consuming, and taxing on the battery. One such example is scanning openly and filtering it manually. But I think there is or should be a feature to support 128-bit AND 16-bit UUID filtering when scanning through devices.
Can anyone help shed light on this????
Also, apologies for the length of this posted question...
The mask i should be opposite - use 1's for bits to include and 0's for those that should be ignored.
filter: 1F0E0D0C-0B0A-0909-0807-060504030201
mask: 0000FFFF-0000-0000-0000-000000000000
Result is that any device which has '0D0C' is included. You'd probably want a "tighter" filter with more similarities in it than this.
I'm not sure exactly what you want to filter on, but if you simply want to apply the filter ????0D0C-????-????-????-????????????, you should have the parcelUuid set to 00000D0C-0000-0000-0000-000000000000 and the parcelUuidMask set to 0000FFFF-0000-0000-0000-000000000000.
You should filter the BLE based on MAC addresses , they filter like a charm and perhaps if you have found the solution for the UUID filtering please do share.

Android Development CellID in LTE network

I try to implement a function into my Android Application that finds out the cell id of the cell I'm in in a LTE network.
I recently read a lot about using TelephonyManager.getAllCellInfo() and then filter for CellInfoLte, but also that it's not implemented on every device.
So in my case calling telephonymaganger.getAllCellInfo() returns null.
I'm testing with a Samsung phone, what seems not to be the best case.
Is there any way to find out the Cell ID or is it just not accessible yet?
I had same problem a few months ago when using getNeigbouringCells() and finally I found this:
The cellid implementation varies from mobile device to mobile device
since these features are considered to be optional. for example:
Samsung (all devices): getNeigbouringCells () is not supported at all
and always returns an empty list.
Please take a look at this for more information:
http://wiki.opencellid.org/wiki/Android_library
You can check it with another phone but not Samsung phones. You can find so many reports about other vendors that have the same problem.

Android Bluetooth Low Energy: characteristic.getPermissions() returns 0?

I am writing an Android BLE application, and I am trying to get the permissions of a certain characteristic. I have already managed to get the characteristic properties with characteristic.getProperties(), and it returns a non-zero value, however, when I use the getPermission() method it returns 0 even though I am sure that the characteristic has PERMISSION_WRITE_ENCRYPTED_MITM (0x00000040).
Here is a code snippet
// properties
int properties = ch.getProperties();
DebugWrapper.infoMsg("properties: " + properties, TAG); //returns non-zero value
// permissions
int permissions = ch.getPermissions();
DebugWrapper.infoMsg("permissions: " + permissions, TAG); //returns zero value
Am I doing something wrong? Is there a specific way to get the permissions of the characteristic or is this a problem with the android api?
I am using API 19 and testing my program on a Samsung Galaxy Note 3.
I appreciate any help.
This looks like an issue with the underlying framework. This link shows the block of code that the framework executes when discovering services/characteristics on the remote device. You can see when the new BluetoothGattCharacteristic is created, the permissions parameter is always passed in as 0.
Additionally, even when the characteristic is later read, only the characteristic's value is updated, no other parameters are reset on the object.
Instead, it seems Android attempts to handle authentication/permission issues on a trial and error basis. In other words, the framework always attempts a basic read/write, and if it fails for authentication reasons, it automatically tries again with MITM authentication requested.

Android Id and its reliability

I want to generate Uuid for my app so I tried many methods for this.
1) Getting Serial number of device using android.os.Build.SERIAL(this returns "unknown" as result)
2) Dealing with device id (I don't know what it will return in case of tablet devices)
3) Getting Android id using android.provider.Settings.Secure.ANDROID_ID(seems some problem with android 2.2 version)
4) Generating Uuid using java.util.UUID
5) Generating pseudo Uuid using android.os.Build properties
All these methods shows some problems. So I am confused which to be choose? Can anybody suggest me best method?
Android Developer Blog says android id will be unique
Also I heard Android id of device can be changed on factory resetting or os updations .
So is there any chance of for duplication new android id generated during factory resetting or os updations ?
NB:Suppose A Condition
My question is what will happened same 2 device Model of same manufacture will under go restore or os updations.the Android id will change. I am asking about this new id. Will there any chance for android id be same in both device?
The ANDROID_ID is generated each time you initialize the device (after reset, etc.). It doesn't depend on model, serial no., etc. Even if you have two identical devices, their ANDROID_ID's after reset should be different. The ID is not particular special, except that it is global for the device. You can achieve the same thing with an UUID for your app.
Yes, there is a chance of duplicate ID's, but it's negligible.
There's 2^64 possible values for ANDROID_ID, and they are generated with some random function. But it is very very very unlikely that you will ever see a duplicate value - search for discussions about GUID uniqueness to get the point.
In short: you can assume that ANDROID_ID is unique.
Creating unique id's for android device has been discussed vivdly in this link In short use this.
import android.provider.Settings.Secure;
private String android_id = Secure.getString(getContext().getContentResolver(),
Secure.ANDROID_ID);

Changing Android Device name in code

I am trying to change the name of the Android Device that my program that is currently running on because the name of the device will contain information that is relevant when it communicates with other phones. The name of the phone will be constantly changed as phone scans for other phones and calculates information. Any ideas on how to change the name of the phone within the java code? I can't image it being more than a few lines of code, but I can't find anything.
Thanks in advance.
It's quite easy, get an instance of the bluetooth adaptor (since the only name you can set is the bluetooth name I think) that refers to the local device and call setName("newName"); on it.
BluetoothAdapter myDevice = BluetoothAdapter.getDefaultAdapter();
myDevice.setName("new name");
Quoting the docs:
Valid Bluetooth names are a maximum of 248 bytes using UTF-8 encoding, although many remote devices can only display the first 40 characters, and some may be limited to just 20.
So be careful with what you set as the device name. Oh, on another note, you can't change the name if the device bluetooth is off. So the actual code after checking it would be something on the lines of the following:
BluetoothAdapter myDevice = BluetoothAdapter.getDefaultAdapter();
if(myDevice.getState() == BluetoothAdapter.STATE_ON){
myDevice.setName("new name");
}
Important to note:
If you are going to test this on an emulator, beware that there are not bluetooth capabilities on the emulators and therefor the getDefaultAdapter() method returns null, resulting in a NullPointerException :)

Categories

Resources