Background
HackerNews had a link to this article about a lawsuit against We-Vibe, an internet-connected sex toy manufacturer. I wasn’t aware that sex toys had become internet connected. Knowing a little about how IoT devices are usually built I imagined there were probably a lot of security issues with those in existence. I figured this could be a fun side-project and decided to do a little research.
A quick Google search demonstrated that there are a ton of devices out there. Which should I choose to investigate? Since I had lawsuits on my mind I figured it was best to focus on a name brand that had some money and could pay out in a lawsuit. This also seemed like a more interesting case to me; nobody would be surprised if the no-name brand had poor security but I expect that most end-users of name-brand items assume the product is secure. For these reasons I ended up focusing on a device called the Kiiroo Onyx. This product is associated with a big, name brand that you probably have heard of: Fleshlight.
Pwning the device
There was just a small issue - I didn’t own the product and didn’t really feel like shelling out a few hundred dollars on a whim that there might be some security issues. Plus I wasn’t entirely sure I wanted the device shipped to my home or office ;-). So I decided to start with the software and take it from there. And I figured the Android app would be the simplest place to start since I could easily disassemble it.
It didn’t take long to find issues. The devices is able to be controlled over the internet and the software uses PubNub for real-time messaging. But they didn’t bother to use any authentication! The following code was enough to “watch” all Kiiroo devices!
var _ = require('underscore'); var PubNub = require('pubnub’); var pn = new PubNub({ publishKey: 'pub-c-2859d4b9-7f64-428d-85f3-02aeef648325', subscribeKey: 'sub-c-296aa490-f663-11e5-ba5f-0619f8945a4f', ssl: true }); pn.hereNow({ includeUUIDs: true, includeChannels: true}, function (status, response) { var channel_names = _.pluck(response.channels, 'name’); pn.addListener({ status: function(evt) { // can see connects/disconnects here }, presence: function(evt) { // and room presence here }, message: function(evt) { if (evt.message && evt.message.deviceName && evt.message.deviceName.match(/pearl|onyx/gi)) { // this is a kiiroo device console.log(evt); } } }); });
Indeed, it seems the device uses integers 0-100 to denote movement. Following a single device I could watch it move from 0 to 100 and back in increasing speeds until it stopped 😬
Using the same idea we can also easily write messages into the stream, too! Once we have a channel name we can just execute pn.publish({channel: …, message: …})
. Since the device interprets the messages into movement data by doing so you could easily write a script to control the entire experience for both parties 😮
To make matters worse, there was identifying information, too. Each stream included the usernames of the parties and I expect many overlapped with Facebook or Twitter account names.
Accessing the video (forever?!)
Another vulnerability I found related to the way they handled video tokens. The app supports video conferencing - presumably so that users don’t have to Facetime and can stay in-app. They use a 3rd party provider HidashHi to handle that. In order to make it easy for users to connect to each-other they provide a QR code that I guess you can scan with the app. But while HidashHi uses a 128-bit token, the QR code only wraps an 8-digit code that then maps to that 128-bit token. So they’re taking this 128-bit token and reducing it to ~26bits. And they don’t rotate the video tokens!
Why is this a problem? It wouldn’t take a bad actor very long to generate every single “QR code” url, validate against the auth api and thereby snag every video token in use. Once a bad actor has a valid video token, they could poll, waiting for a feed to go live and gain access to that live feed. And since the token never changes, as a user of the device there’s no way to know if this already happened and someone is watching you!
Bluetooth
I found some odd things about how they handle Bluetooth that made me think it would be easy to take over a nearby device. But I didn’t have a physical device so I couldn’t actually test that...
Resolution
I reached out to Kiiroo about the vulnerabilities. They said they would make the security vulnerabilities one of their top priorities. A couple weeks later I attempted to connect to PubNub and they had already implemented authentication, so that’s good!
They offered me a $250 bounty but required that I not write a blog post if they paid me so I declined. They also offered to send me a device for further testing but again made that dependent on not posting anything publicly so I declined that as well.
Update 2017/10/08
I read this pentestpartners post with great interest:
Note that there is no PIN or password protection, or the PIN is static and generic (0000 / 1234 etc) on these devices. This isn’t a problem just with the Hush, we’ve found the same problem in the following… Kiiroo Fleshlight
It makes me feel pretty good that I realized this without even having access to the device! 😄