Connecting B4A Android Application to Desktop using VB6 - android

I am using basic4android and have created an application which simply stores and pushes all mobile phone keystrokes. This is functioning when I storing and dumping the data remotely online, however I am attempting to store the data to display on a listening vb6 form application. Basically each time a new record of X number of words is triggered, it should simply display that text block on my running VB form label. Please note I am using a usb cable from the device to the PC. Sorry about the noob question.
How can I push data from my android device to my listening VB6 form app via USB?
Thanks.

This is a tricky one, since it is not obvious what is the driver that is talking to the android phone. If you are lucky, the driver maps itself to a COM port. For instance, on my box, the "Samsung Mobile USB Modem #2" device maps itself to COM4.
If your device is using a COM port mapping, then add the Microsoft Comm Control to your Components list. Simple code which waits for input forever, and writes to Debug.Print is as follows:
If MSComm1.PortOpen = True Then MSComm1.PortOpen = False
MSComm1.CommPort = "4" ' <=== "1" = COM1, "2" = COM2, "3" = COM3, "4" = COM4
MSComm1.Settings = "1200,n,8,1" ' You can probably replace 1200 with a much higher value, e.g. 230400
MSComm1.RThreshold = 1
MSComm1.InputLen = 1
MSComm1.PortOpen = True
Do
DoEvents
Debug.Print MSComm1.Input
Loop Until False
If the driver uses other mechanisms, this will be a lot more complicated, and require messing around with drivers and the Windows API - not for the faint-hearted.

Like Mark Bertenshaw said, although I wouldn't loop to obtain the data but use the OnComm() event:
Private Sub MSComm1_OnComm()
Dim strInput As String
Select Case MSComm1.CommEvent
Case comEvReceive
strInput = MSComm1.Input
Debug.Print strInput
End Select
End Sub

Related

data from android studio to matlab via bluetooth

I am new to android studios and I have the task to develop an app which transfers data from an app (Acceleration sensor data - i have created this app already which shows the data) to matlab (on the pc).
I don't really know how I should do this. I've experimented a bit with bluetooth apps, but I don't have a clue how to connect to Matlab.
I would be greatful for your help.
Thanks in advance,
Annika
Unfortunately I can not speak to the android side of things, but MatLab can connect to generic devices with the UART interface, which is fairly low level.
The process with some microprocessors that I am using is to connect the device to the PC, and then note the Outgoing com port.
(In windows 10, these can be found in Bluetooth settings -> More Bluetooth options)
Then you can use
s = serial('COM<what you found in settings>');
s.Baudrate=115200;
s.InputBufferSize = 100;
fopen(s{i});
serials = instrfindall;
to open an connection. The critical command is serial, the other parameters depend on your device/ configuration. Sometimes there can be issues, in which case one options is to build a loop that tries again until it works.
You then collect the data sent via UART via
flushinput(serials);
temp = fscanf(serials,'%s');
and then split the string. If data is sent continuously, you wrap this into a while loop.
After you are done, you can clean up via
fclose(s{i});
delete(instrfind)
instrreset
It should be noted, that establishing a connection takes longer, the more enabled COM ports there are. So it might be worth disabling all those you don't need.
For more specific things matlab can do, check out What Is the MATLAB Serial Port Interface

Receiving data back from a BLE embedded device on Android

I am working on an Android BLE project. We are using BLE to configure some settings on an embedded device. The embedded device was going to take a long time to come up so I started using BlueSim to emulate the embedded connection.
There are essentially two messages that the Android (I'm requiring KitKat) device sends off to the embedded device. One is to write settings....One is to read the settings.
A Write message is going out to endpoint 0xFFF1 like the following
byte[] data2Send = new byte[11];
data2Send[0] = 0xAA; // signifying this is a write message to device
data2Send[1] = 0x01; // data value
data2Send[2] = 0x38; // data value
data2Send[3] = 0x47; // data value
data2Send[4] = 0x24; // data value
data2Send[5] = 0x01; // data value
data2Send[6] = 0x36; // data value
data2Send[7] = 0x49; // data value
data2Send[8] = 0x0b; // data value
data2Send[9] = 0x63; // data value
data2Send[10] = 0x0D; // CR to indicate the last byte of the packet
characteristic.setValue(data2Send);
boolean status = mBluetoothGatt.writeCharacteristic(characteristic);
Log.v(TAG,"Status is:" + String.valueOf(status));
I had verified this using BlueSim and we have confirmed that this works when transmitting data to the embedded device. We can successfully change all of the settings.
The other message is a Read request of the device so I can know what settings are already in there or to confirm that the settings actually changed.......
byte[] data3Send = new byte[3];
data3Send[0] = 0x55; // Signify this is a start of a READ message
data3Send[1] = 0x42; // Second part of the read designator
data3Send[2] = 0x0d; // Carriage return saying this is the last bit
characteristic.setValue(data3Send);
boolean status = mBluetoothGatt.writeCharacteristic(characteristic);
Log.v(TAG,"Status is:" + String.valueOf(status))
When I send this message over to BlueSim, I see the message on my iPhone and immediately send the settings back out. On Android I see the 11 bytes that are coming back informing me of all the settings! This almost happens instantaneously. Great!
But when we do this on the embedded device I see one byte come back. That's it. Using a debugger on the embedded side we can see all 11 bytes going into the BLE module on the embedded device. If we use a PC rather than my Android device we can see all 11 bytes show up on the PC (the manufacturer of the BLE module has a terminal like app that you can 'sniff' the data with).
The embedded device is an 8 bit micro that is hooked up to a BLE module (TI CC2540 chipset) via a UART so it's obviously SLOWER than the iPhone where BlueSim is running. The embedded device is going to need some time to receive the BLE message, process the request, and shove data back out the BLE module. Is there some setting I have to set in my Android program to allow for a slower response to come back?
I tried downloading LightBlue on iOS and sending that read request out, and we get the same results. We see the first byte of the data packet show up in LightBlue. But only that one.
Any help would be greatly appreciated as always.
It sounds like you are experiencing an issue with the TI Module, not Android. Not sure if its the same issue, but it seems others have been getting headaches from trying to establish connections from Android to the CC254X. See here: https://e2e.ti.com/support/wireless_connectivity/f/538/t/401240

Add IMEI and MAC to wlan0 to Genymotion/AndroVM

Is there any way to add IMEI to AndroVM (now Genymotion) or any other Android Emulator. And also I want MAC address for wlan0 port. We already have emulators which contain MAC at lan0 port but not for wlan.
How can we do so?
if someone in your acquaintances has done so please ask them to contribute.
Details:
I am trying to build a cloud based Android App testing center as my pre final year college project for partial fulfillment towards my Bachelor of Technology (Computer Science) degree.
I am wondering how we can get more configurations for Genymotion.
Or if you can provide me with more device configurations and if it is possible to build configurations for genymotion for different devices very quickly.
Secondly, How to add MAC addresses and IMEI number to the builds?
We are trying to emulate a mobile device (non Google nexus) to make a cloud based testing centre.
For this we are trying to use androVM (Genymotion) and we are facing a few problems
What have we done so far
Building the androVm source code in "VBOX86tp-userdebug" mode from the scratch after following the steps given on official Android website.
After building the source code on a virtual ec2 server, typing the emulator command runs but its blank.
And if possible can AndroVm be run in "Fastboot" mode so that we can install it on the device.
We have been working on "building the androVm" from source code and trying to accomplish few tasks like
Running it with the img's available after the building process is complete.
Making it portable ie creating an iso/ova out of all the stuff found in the out directory.
What we have tried till now
Downloading of the AndroVm source code
initializing the repo using repo init
Downloading the source code using repo sync
choosing the lunch menu using lunch
choosing vbox86tp-userdebug
Other menus full-eng didn't work so discontinued
Few errors that came our way
Make errors: they were pretty straightforward so resolved
system.img was not being generated: resolved by making it again
bin/bash jar command error: happened to be the path error resolved by the exporting the path to jar command.
Few Questions
What an OVA file consits of and how can it be created? From what I have seen it contains few VMDK's and few configurations files attached to it,
How to convert the platform specific image files(system.img ramdisk.img userdata.img) into an OVA or ISO file.
If at all we are missing few files to give to the emulator, can you just name them.
Also how to add IMEI number
We already have MAC for eth0/1 port but we want it on wlan port
Now to make things interesting
This is the reply I got from Genymotion Team:
I want my project to cover various configurations but for starters if i can get something like Samsung Galaxy phones and tab or as a
start if I can get Samsung galaxy tab 2.
You can change the screen size and DPI for each virtual device. You
can toggle navigation bar and virtual keyboard. However, we cannot
provide virtual devices that contains proprietary applications like
Samsung.
Now here what we get is the MAC address of eth0/1 port. What if I need wlan MAC.
Unless one of the two network interface have been disabled, there
should be 2 interfaces, 2 IP, and 2 MAC addresses: adb shell ip a. 2:
eth0: mtu 1500 qdisc pfifo_fast
state UP qlen 1000
link/ether 08:00:27:d4:fe:e0 brd ff:ff:ff:ff:ff:ff
inet 192.168.56.101/24 brd 192.168.56.255 scope global eth0
inet6 fe80::a00:27ff:fed4:fee0/64 scope link
valid_lft forever preferred_lft forever 3: eth1: mtu 1500 qdisc pfifo_fast state UP qlen 1000
link/ether 08:00:27:c8:37:e7 brd ff:ff:ff:ff:ff:ff
inet 10.0.3.15/24 brd 10.0.3.255 scope global eth1
inet6 fe80::a00:27ff:fec8:37e7/64 scope link .
Sorry, but we do not provide support for specific ROM. However, I
strongly recommend you to visit the community at:
https://groups.google.com/forum/#!forum/genymotion-users
1. What an OVA file consits of and how can it be created ?From what i have seen it contains few VMDK's and few configurations files
attached to it,
"The entire directory can be distributed as an OVA package, which is a
tar archive file with the OVF directory inside."
(http://en.wikipedia.org/wiki/Open_Virtualization_Format)
2. How to convert the platform specific image files(system.img ramdisk.img userdata.img) into an OVA or ISO file.
If at all we are missing few files to give to the emulator, can you just name them.
Please read the community tutorials
3. Also how to add IMEI number
There is currently no way to add IMEI number. This feature will come
in the near future
4. We already have MAC for eth0 port but we want it on wlan port
There is 2 interfaces: eth0 and eth1. Eth0 is used for Genymotion
application widgets. If this network connection is broken, Genymotion
would not be able to start anymore. Eth1 is used for network current
access (fake WiFi connection). You can change this network
configuration as you want.
It is a common practice for mobile applications to identify the user by IMSI number (associated with the SIM card) or IMEI number (unique ID of the device). Of course, it is also possible on Android:
TelehponyManager manager = (TelehponyManager)getSystemService(TELEPHONY_SERVICE);
String imei = manager.getDeviceId();
String imsi = manager.getSubscriberId();
This code works perfectly fine on a real device, however under emulator IMEI is always all-zero and it’s not configurable. It quickly becomes awkward when debugging a network-enabled application which uses IMEI as a user ID.
Trying to resolve the problem I first looked at the TelephonyManager service, just to find the following snippet:
private IPhoneSubInfo getSubscriberInfo() {
// get it each time because that process crashes a lot
return IPhoneSubInfo.Stub.asInterface(ServiceManager.getService("iphonesubinfo"));
}
Fair comment, isn’t it? It really made my day :)
Anyway, code analysis shows that IMEI/IMSI request goes down through all the telephony layers (see the diagram), eventually getting to the baseband device. In case of emulated system, rild daemon is used together with libreference-ril.so – reference Vendor RIL library which talks to the baseband modem device using plain, old AT commands.
The modem device itself is emulated outside the Android system, as part of qemu (which is the heart of the emulator). Details of the communication between the emulator and the Android system running inside the emulator are interesting on its own (all the communication goes through a virtual serial port, Android system’s qemud daemon is used to (de)multiplex the data). I’ll try to post a brief introduction to the topic soon.
Virtual modem implementation can be found in external/qemu/telephony/android_modem.c. The most important part of the file is this function:
const char* amodem_send( AModem modem, const char* cmd );
This function is called for each received AT command. For each command sDefaultResponses array is searched for a given command and either predefined response is sent, or a command handler is executed. The array itself looks like:
static const struct {
const char* cmd; /* command coming from libreference-ril.so, if first
character is '!', then the rest is a prefix only */
const char* answer; /* default answer, NULL if needs specific handling or
if OK is good enough */
ResponseHandler handler; /* specific handler, ignored if 'answer' is not NULL,
NULL if OK is good enough */
} sDefaultResponses[] =
{
/* ... */
{ "+CIMI", OPERATOR_HOME_MCCMNC "000000000", NULL }, /* request internation subscriber identification number */
{ "+CGSN", "000000000000000", NULL }, /* request model version */
/* ... */
};
Two array rows cited above are responsible for IMSI and IMEI retrieval. As you can see, both values are hardcoded and there is no chance to modify them without recompiling the emulator.
However, an old-school hack comes in handy. The emulator binary is not encrypted nor compressed, so the string literals should be visible inside the emulator binary. In fact they are, and IMEI number can be modified in a few simple steps:
** backup the emulator binary
** open the binary with your favourite hex editor
** search for +CGSN string followed by a null byte, it should be followed by 15 digits of the IMEI number
** edit the number, be careful not to change the number of digits
** save the file, that’s all!
Sure, it’s not a perfectly comfortable solution, yet better than nothing. In the next part I’ll explain how to make IMEI number a configurable option. Enjoy!

Discovering vendor-specific bluetooth devices only

Need to discover or search for Bluetooth devices of certain "vendor-specific" devices.
"vendor-specific" means all devices will have similar starting bits in their "MAC" address
For example, I want to search only for devices whose MAC address starts with 12:34:56:
It should search only for specific series of MAC addresses and list them.
Perform a full discovery, then filter using BluetoothDevice.getAddress()
// Define Vendor ID Prefix
public static final String VENDOR_ID = "12:34:56:"
// First, do a full discovery...
BluetoothAdapter.getDefaultAdapter().startDiscovery()
//...
// Then, for each device returned from discovery...
if ( device.getAddress().startsWith(VENDOR_ID) ) {
// Do Something
}
My Explanation will be based on the BluetoothChat example from the Android SDK, hopefully this is ok, otherwise I would need to write a lot more. If you haven't seen the BluetoothChat example, go take a look, it's really nice!
If you want to use a device where you don't know the complete adress, you'll have to do a complete discovery with BluetoothAdapter.startDiscovery() and search the received addresses for the ones you want to.
If you know the complete address of the device you want to connect to you can directly connect to this device with BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(address)

any way to discover Android devices on your network?

I want to be able to discover Android devices on my network and possibly retrieve some device information about them. This is very easy with Apple devices since they run Bonjour services. However, I can't seem to find any similar service running on Android.
This must work without modifying the Android device, installing some service, or opening some port. It's meant to work with vanilla Android devices in the way that Bonjour helps you find vanilla Apple devices. Even being able to just verify that the device is running Android would be sufficient.
Chosen Answer: Although it's not the top rated answer (yet), please take a look at the response by Luis. As he mentions, you can use a DNS lookup (using your local DNS server) to discover Android devices. I have found this to have a 100% success rate, as Android forces devices to use a hostname of android-_____. This is apparently difficult to change on the phone, even if it is rooted. So I think this is a pretty accurate method. Thanks, Luis!
Example:
$ nslookup 192.168.1.104 192.168.1.1
Server: 192.168.1.1
Address: 192.168.1.1#53
104.1.168.192.in-addr.arpa name = android-711c129e251f14cf.\001.
Sample Code: If you wanted to implement this in Java (e.g., to run on Android), you can't easily use getHostName() because it uses the external DNS servers. You want to use the local DNS server on your router, for example. Luis mentions below that you could modify the DNS servers of the Wifi connection, but that could possibly break other things. Instead, I've found the dnsjava library to be extremely helpful to send targeted DNS requests. Here is some sample code using the library:
String ipAddress = "104.1.168.192";
String dnsblDomain = "in-addr.arpa";
Record[] records;
Lookup lookup = new Lookup(ipAddress + "." + dnsblDomain, Type.PTR);
SimpleResolver resolver = new SimpleResolver();
resolver.setAddress(InetAddress.getByName("192.168.1.1"));
lookup.setResolver(resolver);
records = lookup.run();
if(lookup.getResult() == Lookup.SUCCESSFUL) {
for (int i = 0; i < records.length; i++) {
if(records[i] instanceof PTRRecord) {
PTRRecord ptr = (PTRRecord) records[i];
System.out.println("DNS Record: " + records[0].rdataToString());
}
}
} else {
System.out.println("Failed lookup");
}
} catch(Exception e) {
System.out.println("Exception: " + e);
}
This gives me the output:
DNS Record: android-711c129e251f14cf.\001.
Bingo.
There is an very simple approach that gave me positive results in few different devices.
When a device connects to your router it receives an IP (i.e. DHCP) and registers a name in DNS. The name that is registered seems to be always in the form android_nnnnnnnn.
Of course, you can name any computer with the same approach and trick the check, resulting in false positives ...
Also, I can't ensure that all device suppliers are following the same approach, but I've found it to work correctly in a few devices from different brands (including different SDK levels) that I've tested.
--EDITED--
How to do it
It depends on where you would be running the code to discover the Android devices. Assuming that you would be running the code in an Android device:
First discover devices responding to ping in your network. You can use the code in my answer to this post: execComd() to run a ping command.
Get the name of responding devices using the code:
InetAddress inetAddress = InetAddress.getByName(string_with_ip_addr);
String name = inetAddress.getCanonicalHostName();
--EDIT 2--
Proof of concept
The method below is just a proof of concept for what I've wrote above.
I'm using isReachable() method to generate the ICMP request, which is said to only work with rooted devices in many posts, which is the case for the device used for testing it. However, I didn't give root permissions for the application running this code, so I believe it couldn't set the SIUD bit, which is the reason why some claim that this method fails. I would like to do it here from the perspective of someone testing it on a non-rooted device.
To call use:
ArrayList<String> hosts = scanSubNet("192.168.1.");
It returns in hosts, a list of names for devices responding to ping request.
private ArrayList<String> scanSubNet(String subnet){
ArrayList<String> hosts = new ArrayList<String>();
InetAddress inetAddress = null;
for(int i=1; i<10; i++){
Log.d(TAG, "Trying: " + subnet + String.valueOf(i));
try {
inetAddress = InetAddress.getByName(subnet + String.valueOf(i));
if(inetAddress.isReachable(1000)){
hosts.add(inetAddress.getHostName());
Log.d(TAG, inetAddress.getHostName());
}
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
return hosts;
}
Regards.
Android is not going to be as easy as iOS. There is no Bonjour equivalent.
Android 4.0, Ice Cream Sandwich, introduced Wi-Fi Direct Peer to Peer networking. At first I hoped it might be able to be scanned in the the way your thinking, but it helps Android devices communicate without an access point, so they're not really "on your network". Besides, ICS runs on only a fraction of Android devices.
Rather than an active netscan approach, you're left with a passive monitoring approach. If your network is secure, sniffing the encrypted packet is possible, but inconvenient. You'll have to
put your network interface into monitor mode
capture the 4-way handshake
decrypt it using the network's pre-shared key
this will give you the key you need to decrypt traffic
If you want to see this in action, Wireshark supports WPA decryption.
Once you're able to view the Wi-Fi traffic, you will notice Android devices tend to communicate with certain Google servers and their HTTP connections have User Agent strings that can be identified.
This is the basis for a workable passive solution.
Tenable Network Security offer products that seem to take this type of approach.
Another Idea
#Michelle Cannon mentioned Libelium's Meshlium Xtreme whose approach will not get you all the way there (not without good up to date MAC address range tables). But it could be part of reaching a lesser goal.
You can:
Detect all wireless devices
Eliminate Apple devices using the MAC's Organizationally Unique Identifier (OUI)
Tell it's a mobile device by by monitoring signal strength to determine it's moving (and mobile devices will tend to show up and go away)
You may be able to use the MAC OUI as a hint it's Android
You may be able to use the MAC OUI as a hint it's not Android (but a laptop or wireless card, etc.).
This may be workable if your willing to detect devices that are probably Android.
DHCP Fingerprinting
#Michelle Cannon suggested DHCP fingerprinting. I wasn't sure at first but I have to thank him for suggesting what's looking like the best bet for simple passive scanning. As a cautionary tail, I'd like to explain why I was late to the party.
There are things we know, thinks we don't know, and things we think we know but are wrong.
In a lot of ways, it's good that Android uses the Linux kernel. But it's not good if you want to discover Android devices on your network. Android's TCP/IP stack is Linux's therefor Android devices will look like Linux devices or so I thought at first. But then I realized Linux has a lot of build configuration parameters so there could be something distinctive about Android when seen on a network, but what?
DHCP fingerprinting uses a the exact DHCP options requested by the device plus timing. For this to work you generally need an up to date fingerprint database to match against. At first it looked like fingerbank was crowed sourcing this data, but then I noticed their files hadn't been updated for almost a year. With all the different Android device types, I don't think it's practical to keep updated fingerprints for a single project.
But then I looked at the actual DHCP signatures for Android and I noticed this:
Android 1.0: dhcpvendorcode=dhcpcd 4.0.0-beta9
Android 1.5-2.1: dhcpvendorcode=dhcpcd 4.0.1
Android 2.2: dhcpvendorcode=dhcpcd 4.0.15
Android 3.0: dhcpvendorcode=dhcpcd-5.2.10
Linux normally uses dhclient as their DHCP client, but Android is using dhcpcd. Android has a strong preference for using software licensed with the BSD style where possible and dhcpcd uses a BSD license. It would seem dhcpvendorcode could be used as a strong indicator that a mobile device is running Android.
DHCP monitoring
A client uses DHCP to get an IP address when joining a network so it's starting without an IP address. It gets around this problem by using UDP broadcasts for the initial exchange. On Wi-Fi, even with WPA, broadcast traffic is not encrypted. So you can just listen on UDP port 67 for client to server traffic and 68 for the reverse. You don't even need to put your network interface into promiscuous mode. You can easily monitor this traffic using a protocol analyzer like Wireshark.
I preferred to write code to monitor the traffic and decided to use Python. I selected pydhcplib to handle the details of DHCP. My experience with this library was not smooth. I needed to manually download and place IN.py and TYPES.py support files. And their packet to string conversion was leaving the dhcpvendorcode blank. It did parse the DHCP packets correctly, so I just wrote my own print code.
Here's code that monitors DHCP traffic from client to server:
#!/usr/bin/python
from pydhcplib.dhcp_packet import *
from pydhcplib.dhcp_network import *
from pydhcplib.dhcp_constants import *
netopt = {
'client_listen_port':"68",
'server_listen_port':"67",
'listen_address':"0.0.0.0"
}
class Server(DhcpServer):
def __init__(self, options):
DhcpServer.__init__(
self,options["listen_address"],
options["client_listen_port"],
options["server_listen_port"])
def PrintOptions(self, packet, options=['vendor_class', 'host_name', 'chaddr']):
# uncomment next line to print full details
# print packet.str()
for option in options:
# chaddr is not really and option, it's in the fixed header
if option == 'chaddr':
begin = DhcpFields[option][0]
end = begin+6
opdata = packet.packet_data[begin:end]
hex = ['0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f']
print option+':', ':'.join([(hex[i/16]+hex[i%16]) for i in opdata])
else:
opdata = packet.options_data.get(option)
if opdata:
print option+':', ''.join([chr(i) for i in opdata if i != 0])
print
def HandleDhcpDiscover(self, packet):
print "DHCP DISCOVER"
self.PrintOptions(packet)
def HandleDhcpRequest(self, packet):
print "DHCP REQUEST"
self.PrintOptions(packet)
## def HandleDhcpDecline(self, packet):
## self.PrintOptions(packet)
## def HandleDhcpRelease(self, packet):
## self.PrintOptions(packet)
## def HandleDhcpInform(self, packet):
## self.PrintOptions(packet)
server = Server(netopt)
while True :
server.GetNextDhcpPacket()
This code is based on pydhcplib's server example because it listens for client requests, like a server.
When my Nexus 7 Android 4.2 tablet connects, this interesting information is captured (redacted):
DHCP REQUEST
vendor_class: dhcpcd-5.5.6
host_name: android-5c1b97cdffffffff
chaddr: 10:bf:48:ff:ff:ff
DHCP DISCOVER
vendor_class: dhcpcd-5.5.6
host_name: android-5c1b97cdffffffff
chaddr: 10:bf:48:ff:ff:ff
The host name seems to have a fixed format and is easily parsed. If you need the IP address you can monitor the server to client traffic. Note: only the initial exchange, when an new client first shows up without an IP address, is broadcast. Future lease extensions, etc., are not broadcast.
Reverse DNS Lookup
#Luis posted a great solution that demonstrates how simpler is better. Even after seeing Android's DHCP client was setting host_name to android-5c1b97cdffffffff, I didn't think to ask the router for it's list of names using reverse DNS lookups. The router adds the host_name to it's DNS server so you can still access the device if its IP address changes.
The host_name is expected to remain listed in the DNS for the duration of the DHCP lease. You could check if the device is still present by pinging it.
One drawback to depending on host_name is there are ways this could be changed. It's easy for the device manufacturer or carrier to change the host_name (though after searching, I've been unable to find any evidence they ever have). There are apps to change host name, but they require root so that's, at most, an edge case.
Finally there's an open Android Issue 6111: Allow a hostname to be specified that currently has 629 stars. It would not be surprising to see configurable host_name in Android Settings at some point in the future, maybe soon. So if you start depending on host_name to identify Android devices, realize it could be yanked out from under you.
If you're doing live tracking, another potential problem with Reverse DNS Lookup is you have to decide how frequently to scan. (Of course this is not an issue if you're just taking a one-time snapshot.) Frequent scanning consumes network resources, infrequent leaves you with stale data. Here's how adding DHCP monitoring can help:
On startup use Reverse DNS Lookup to find devices
Ping devices to see if they are still active
Monitor DHCP traffic to detect new devices instantly
Occasionally rerun DNS Lookup to find devices you might have missed
If you need to notice devices leaving, ping devices at desired timing resolution
While it's not easy (nor 100% accurate), there are several techniques that make it possible to discover Android devices on your network.
AFAIK, Android system doesn't provide any zeroconf app/service on it's built-in system app/service stack. To enable the auto-discovery on the actual device attached to local network, you need either install some third-party zeroconf app or develop your own app/service and install it on the actual device, some API options are:
JmDNS (for Apple's bonjour protocol)
Cling (for Microsoft's UPnP protocol)
Android NSD API (introduced since Android 4.1)
I am not quite clear about your requirements, if you want something similar (i.e. auto discover and connect) on vanilla Android devices, you can probably use Wi-Fi direct which is now available on some later device running Android 4.0, however, it requires both devices support Wi-Fi Direct and only create an ad-hoc P2P connection with Wi-Fi turned off, much like a bluetooth connection with a longer range:
For Wi-Fi Direct API support, check out official guide - Connecting Devices Wirelessly.
I am looking at this an thinking
http://www.libelium.com/smartphones_iphone_android_detection
pay special note to this
Do the users need to have an specific app installed or interact somehow to be detected?
No, the scan is performed silently, Meshlium just detects the "beacon frames" originated by the Wifi and Bluetooth radios integrated in the Smartphones. Users just need to have at least one of the two wireless interfaces turned on.
Long time ago I use to use an app called stumbler on my mac to find wifi networks, I think this is similar
Other ideas
Well if I need to determine android phones on a local network how would I do it. Absent of a dns service running I only have a couple possibilities
The SSID if its being broadcast - can't tell me anything The ip address - android lets you have a lot of control over host naming so I guess you could define a specific ip range to your android devices. -not to useful.
Alternately lets say I see an unknown device on the network, if bluetooth is turned on then I am broadcasting a bluetooth device signature SDPP that I can use to deduce my device type.
If I were running a service that supported android and I wanted to discover specific android devices on my network, then I could just register the mac addresses for those devices and watch for them on the network.
Other than that you would need to run either a bonjour (dns-sd) or upnpp dameon on the device.
Updated Response
Sorry, I haven't understood the original question correctly. Only your comment made it really clear to me that you do not want to have to install anything on the target devices but you just want a way of discovering random phones in your network.
I'm not sure if this would really be possible in the way you want it. Without having any network discovery service running on Android you will not find the device in first place. Of course you can use some low-level network protocols but that would only give you an indicator that there's something but not what it is (being an Android device, a PC, a whatever else).
The most promising approach would be to check for preinstalled apps that have network functionality of some kind. E.g. Samsung devices have Kies Air (if the user enables it), Motorola are using UPnP for their Media Server and HTC has something own as well, if I remember correctly. However, there's no app that is installed on all Android devices of all vendors and carriers. So you can't rely on solely one of those but would need to check for various different services using their specific protocols and behaviors in order to get additional information about the device. And, of course, the user would have to enable the functionality in order for you to use it.
Old response
An additional alternative to yorkw's list is AllJoyn by Qualcomm. It's an open source cross-platform discovery and peer-to-peer communication framework I've used in the past myself already.
Though Qualcomm is a big sponsor of AllJoyn this does not mean that you need a Qualcomm chipset in your define. In fact AllJoyn works on any chipset including Intel and nVidia. It doesn't require rooted phones or any other modifications to the Android framework and just works "out of the box" using Wi-Fi and/or Bluetooth as pairing methods.
I am learning a lot from this topic.
there is also something called dhcp fingerprinting, apparently different devices act differently to the kind of network scans we've been discussing such as those using NMAP a linux scanner. Maps of the behavior from these probes are available on the internet.
http://www.enterasys.com/company/literature/device-profiling-sab.pdf
https://media.defcon.org/dc-19/presentations/Bilodeau/DEFCON-19-Bilodeau-FingerBank.pdf
http://community.arubanetworks.com/t5/ArubaOS-and-Mobility-Controllers/COTD-DHCP-Fingerprinting-how-to-ArubaOS-6-0-1-0-and-above/td-p/11164
http://myweb.cableone.net/xnih/
Here's a one liner that pings all of the machines on your network (assuming your network is 192.168.1.x) and does a reverse lookup on their names:
for i in {1..255}; do echo ping -t 4 192.168.1.${i} ; done | parallel -j 0 --no-notice 2> /dev/null | awk '/ttl/ { print $4 }' | sort | uniq | sed 's/://' | xargs -n 1 host
Requires GNU parallel to work. You can install that on OSX using "brew install parallel"
From this you can just look at the devices named android-c40a2b8027d663dd.home. or whatever.
You can then trying running nmap -O on a device to see what else you can figure out:
sudo nmap -O android-297e7f9fccaa5b5f.home.
But it's not really that fruitful.

Categories

Resources