Smart bulbs are widely known as a successful offering in home automation and IoT products, as they are internet-capable light bulbs that allow home users to customize the colors, schedule on and off times, and control them remotely. Some even play music and could improve your sleep . Any device that can wireless connect with phone applications must be rigorously tested for potential safety and privacy implications, so our security research team investigated the smart bulb market.
Understanding the Smart BulbIn our research laboratory, we tested different bulbs to see different perspectives. In the end, we tested with one of the most popular smart bulbs in the market Magic Blue .The price for this bulb and similar ones are around 5 to 10, depending on the seller.
Device characteristics: Works On >= Android 4.3 or > iOS 7.0 Power: 4.5W Lúmens: 350Lm Color Temperature: 2800K 3200K Bluetooth Version: 4.0 Registered Manufacturer: IEEE Registration Authority
Besides identifying some common components on these type of devices, looking at the “insides” of this bulb shows us that it’s possible there is auniversal asynchronous receiver-transmitter ( UART ). However, after connecting to it, it didn’t output anything. From what we saw, these bulbs have the following first three bytes on their Bluetooth address (bd_addr),which usually represents the manufacturer:
F8:1D:78
After a few Google searches, we found that a Chinese company called Zengge makes these bulbs. They have the following information on their site :
Zengge works as partners supplying famous brand like Philips and Osram etc. [sic]Other bulbs have similar characteristics, and the Android application supplied even works on different bulbs.
As a side note, some Bluetooth Low Energy (Bluetooth LE, often referred to asBLE, formerly marketed as Bluetooth Smart) bulbs on the market are sold as Bluetooth Smart, but in reality, they’re Bluetooth Smart Ready and the technology used to communicate with the mobile application is the radio frequency communication ( RFCOMM ) protocolon the host Bluetooth stack and not the Low Energy Attribute Protocol ( ATT ). We focused our research on bulbs that used ATT to communicate.
The pairing method for our target is Just Works, which allowed us to sniff the communication.
Sniffing Communication Between the Bulb and the Mobile ApplicationThis process involved the following hardware:
3 Ubertooth (aka uberteeth) Smart Bulb Mobile Phone LaptopWe paired the mobile phone with the iLight app with the smart bulb and started changing colors. At the same time, we connected three ubertooth dongles (to cover all advertisement channels 37, 38 and 39) to our linux machine and used the following command:
ubertooth-btle -U 0 -A 37 -f -c bulb_37.pcap ubertooth-btle -U 1 -A 38 -f -c bulb_38.pcap ubertooth-btle -U 2 -A 39 -f -c bulb_39.pcapAfter a while, we get traffic that we can analyze using Wireshark.
Packet 1061 that we captured with bulb_37.pcap has a write command from the phone to the bulb with the value:
5639ddff00f0aa
At this point, we can store this value for later, like the handle 0x000b.Just by looking at it you can find some possible HEX color codes, like the ones already disclosed in the wild . Using the BLEAHtool , we can also confirm that this handle provides the Write permission:
By the way, we could also use the HCI dump log from Android , but we wanted to keep things as real as possible.
Reversing the Mobile ApplicationWe used the adb tool to download the Android application and used jadx to analyze it.Our objective was to make sure that the changing color commands are the same as what we found by sniffing the application. Connecting the phone with our laptop and using:
adb shell pm path com.Zengge.BluetoothLightDark
Returns the path of the package:
package:/data/app/com.Zengge.BluetoothLightDark-1/base.apk
Now we can download it to our desktop:
private BluetoothGattCharacteristic getSendCharacteristic() { if (this.f4737f != null) { return this.f4737f; } if (this.f4736e == null) { return null; } for (BluetoothGattCharacteristic bluetoothGattCharacteristic : this.f4736e.getCharacteristics()) { if (Long.toHexString(bluetoothGattCharacteristic.getUuid().getMostSignificantBits()).substring(0, 4).equalsIgnoreCase("FFE9")) { this.f4737f = bluetoothGattCharacteristic; return bluetoothGattCharacteristic; } } return null; }FFE9 is, in fact, the only writable characteristic.
public void sendData(byte[] bArr, int i) { BluetoothGattCharacteristic sendCharacteristic = getSendCharacteristic(); if (sendCharacteristic != null) { sendCharacteristic.setWriteType(i); sendCharacteristic.setValue(bArr); this.f4734c.writeCharacteristic(sendCharacteristic); "---sendData:" + C1425a.m7435a(bArr) + " by:" + sendCharacteristic.getUuid(); } }To be sure we’re catching the real function, let’s search for “sendData” using logcat:
adb logcat | grep sendData 10-25 10:04:42.748 21822 21822 V SMB : sendData:56ff0d0700f0aa We clicked on the mobile app for a “re