[Back to the Floodgap main page] Back to Floodgap Department of Hacking
[DCS-900]

Hacking the D-Link DCS-900 @ Floodgap Department of Hacking

Today our victim topic will be the D-Link DCS-900 Internet-enabled webcam. They're low resolution and have absolutely potty low-light performance, but they're cheap, small, easy to find used and pretty tough, and as long as they're behind a firewall or reverse proxy, can be used securely. Plus, being Ethernet only you won't have to worry about someone getting into the WiFi, and they're easy to integrate into many security software setups with basic JPEG and MJPEG options. I've got them all over this house in places you can see them and a few places you can't.

Last updated 30 July 2019.

Specs

The DCS-900 is a rebadged Cellvision (now SparkLAN) device in two revisions, the "rev A" being based on the CAS-230 and the "rev B" on the CAS-330. It looks like D-Link made a number of derivatives; the DCS-1000 appears to be the same basic chipset and has the same capabilities but in a different form factor. There are wireless versions of these cameras which are broadly similar and were also released as the DCS-900W, etc., but I won't discuss those much here. The two versions are easily distinguished not only by the rear label but also the front LEDs: revision A units have a green power LED and an amber activity LED; Revision B units have a red power LED and a green activity LED.

Note that Cellvision cameras of this era, of which the DCS-900 is but one of many from a great number of manufacturers (the TRENDnet TV-IP100 and TV-IP200 series are others), allow several terrible ways of attacking the admin interface via XSS and should never be directly exposed to the outside world. All of my cameras are gated through reverse proxies. While you can use the XSS attacks to change the username and password of a victim unit, since I'm not a blackhat I won't elucidate further; just apply power and hold the factory reset button in for a few seconds on a used unit you need to get control over.

Both the A and B revisions are based on the RDC Semiconductor R1610 family, an unusual 80C186-compatible RISC "Network Processor Unit" is a 16-bit CPU with a five-stage pipeline, 1MB of address space, 64K of I/O, two DMA channels, multiple IRQs and timers and a single Fast Ethernet (10/100) MAC. Revision B systems have larger flash (2MB versus 512K) to accommodate their nicer configuration interfaces but their basic functionality is largely the same.

The cameras come internally as three boards that interlock with pin headers. Note the labeling.

The camera board is more or less interchangeable between revisions, but while the power/network board is electrically compatible with both revisions the firmware may not know how to drive it. The external power supply so far is the only component that has ever failed on any of my multiple units and they are easily replaced with a wallwart of the same specification.

[Typical image.]
Typical image frame in afternoon sunlight at 640x480 with lowest compression (i.e., highest quality) settings.
Compare with the night images below.

Imaging

The DCS-900's camera can generate up to a 640x480 JPEG still image or stream it in Motion JPEG. Unfortunately, the R1610 is not well-suited to this task and while low resolution MJPEG streams such as 160x120 and 320x240 run at decent frame rates, 640x480 typically crawls at a sluggish single-digit fps. Other than the fact Revision A units don't offer the 160x120 resolution, there is no appreciable difference in imaging between Revision A and Revision B. Image quality is greatly improved by setting compression in the admin interface as low as possible, which has been done here. The camera does have adjustable settings for contrast and brightness, as well as the proper frequency of power mains so that lights visible in the shot will be less likely to show banding. All grabs on this page use North American 60Hz mains frequency and default image settings otherwise.

Focus is manually done with the camera focus ring and cannot be adjusted by software (on the other hand, this also means the camera stays focused on what you focus on). There is no motion sensing internal to the camera. Although Revision B units offer a pantiltcontrol.cgi endpoint, there is no pan-and-tilt hardware, so it doesn't actually do anything.

The camera also lacks an infrared sensor or LEDs, so dark rooms only display image noise, and the image tends to be quite poor in low light levels. The images at right show the same scene as above, but at nighttime and lit only by a desklamp behind the camera, at 160x120 and 320x240 resolutions. Click either image for the full 640x480 frame (64K) for comparison, and then compare with the same scene above.

Both revisions offer a direct endpoint for the configured image at /IMAGE.JPG or /image.jpg (e.g., http://camera_host_name/image.jpg). There does not appear to be a way to access different image dimensions from the image URL; you have to change the camera settings first.

Although the base firmware provides ActiveX and Java applets to view its MJPEG stream, this isn't necessary on modern systems as the the stream is directly accessible at /VIDEO.CGI or /video.cgi (e.g., http://camera_host_name/video.cgi). Revision A streams up to and including at least firmware version 2.28 seem to work fine with anything, including Firefox and VLC. However, firmware 2.51 and later and all Revision B units have defective MIME headers which Firefox will refuse to process (VLC works fine, as do other browsers). This does not appear to have been fixed in any version of the firmware. Revision B units also have a bug where frame rates on this endpoint are abnormally low; using /mjpeg.cgi seems to yield better throughput but does not work on Revision A units.

Networking

Again: do not expose these cameras to the Internet unprotected due to XSS attacks possible against the administration interface. My units are behind reverse proxies and only allow access to the image endpoints.

From a factory reset both revisions come up with a fixed address 192.168.0.20 (I use a Mac set to 192.168.0.99 to talk to freshly reset units). At this point you can assign them a static IP or a dynamic one via the web admin interface (both units support DHCP and PPPoE, but Revision A also supports RARP or BOOTP). The unit's internal clock can be set manually or via NTP.

It is easy to overwhelm the camera's rather weak CPU with requests, which is another reason to use a reverse proxy and let the proxy do caching if needed. Revision B units seem especially prone to networking issues. Revision A units will shrug off excess traffic, though their responsiveness will suffer.

Revision B units support acting as an FTP client and will upload images on a schedule to a configured server. Both revisions claim to support DynDNS, though I have doubts this works anymore and I wouldn't use this feature anyway. Likewise, while Revision B supports UPnP, I would turn this off. Both revisions also offer a second HTTP port option, presumably for firewall traversal with port forwarding, but has no additional functionality.

The /iocontrol.cgi endpoint seen on some other related Cellvision rebadged cameras (like the TRENDnet TV-IP200) does not seem to support all the features of some other units. However, both the /devinfo.cgi and /config.cgi endpoints do work and will disclose login and administrative information!

Firmware

Firmware files are exactly the same size as the flash memory, so most likely they are loaded into RAM and then written out.

Revision A units do not have a means of uploading firmware from the web interface. Instead, they use a modified TFTP (over UDP) protocol where the filename isn't transmitted (the initial packet is 00 02 00 6f 63 74 65 74 00, i.e., opcode 2 with a null filename in octet mode, and then proceeding with a standard TFTP transmission in 512-byte blocks). You can send this type of transmission with a hacked copy of a TFTP client, or use the provided Windows-only software (IPView Lite). There does appear to be a checksum which is enforced by the unit itself: a trivial cosmetic modification of the 2.28 firmware was rejected by my test unit, which is to say it was ignored after it was successfully uploaded and not committed to flash, but it did accept the 2.51 firmware unmodified. Although there is no apparent digital signature, the checksum must be embedded in the file since it is exactly 512K in length. I do not know over what byte range the checksum extends or the algorithm (I suspect a CRC-16 or CRC-32 of some sort).

Unfortunately, Revision A units are very easy to brick. While attempting to flash the unit back to 2.28 a protocol error occurred in the middle of transmission, which is apparently unrecoverable and put the unit into a "factory recovery" mode (the manual even warns about this possibility). In this mode, the power LED flashes off and on instead of steady and normal operation is absent. While something does issue Ethernet packets on 192.168.0.20 if you force a hard reset, it does not respond to TFTP or HTTP requests, and an examination of the CPU board did not show any obvious points to connect a serial cable to. This unit is now a dud in my spare parts box. If your Revision A unit is running 2.28 or earlier, I would strongly advise not flashing it to a later version: there is no security benefit, no new features are introduced (at least in later releases of the 2.x firmware), you will possibly introduce the MJPEG stream glitch if the firmware is sufficiently recent, and you might brick it in the process.

Revision B units directly accept firmware files from their web interface and are capable of flashing themselves independently. They seem more reliable at doing so than Revision A units. They also have embedded checksums in their 2MB files, and the camera will give you an error in the web interface if the checksum fails. Again, I do not know over what byte range the checksum extends or the algorithm.

Revision A contains references to these files and endpoints:

HOME.HTM TITLE.HTM TOP.HTM AVIEW.HTM JVIEW.HTM REPLY.HTM ABOUT.HTM CONFIG1.HTM CONFIG2.HTM CONFIG3.HTM CONFIG4.HTM CONFIG6.HTM CONFIG7.HTM

IOCONTROL.CGI DEVINFO.CGI VIDEO.CGI CONFIG.CGI

IMAGE.JPG LOGO.JPG TABLELM.JPG TABLERM.JPG CENTERMA.JPG ENABLE.JPG DISABLE.JPG APPLY.JPG CANCEL.JPG BOTTOM.JPG DEVICE.JPG ADVANCE.JPG TOOLS.JPG STATUS.JPG HELP.JPG HOME.JPG ACTIVEX.JPG JAVA.JPG CONFIG.JPG DEFAULT0.JPG DEFAULT1.JPG IMAGE0.JPG IMAGE1.JPG SYSTEM0.JPG SYSTEM1.JPG DATETM0.JPG DATETM1.JPG ADMIN0.JPG ADMIN1.JPG

Revision B contains references to these files and endpoints:

HOME.HTM VERSION.HTM TOP.HTM IMODE.HTM AVIEW.HTM JVIEW.HTM BACKUP.HTM DATETIME.HTM DOBACK.HTM DORESET.HTM DOTEST.HTM DOUPGRD.HTM EMAIL.HTM ERRMSG.HTM HELP.HTM HELPHOME.HTM HELPADVA.HTM HELPTOOL.HTM HELPSTAT.HTM HELPHELP.HTM NETWORK.HTM REPLY.HTM REPLYD.HTM REPLYK.HTM RESET.HTM NULLDATE.HTM SETDATE.HTM ERRDATE.HTM NULLEML.HTM SETEML.HTM ERREML.HTM NULLFTP.HTM SETFTP.HTM ERRFTP.HTM NULLNET.HTM SETNET.HTM ERRNET.HTM NULLSYS.HTM SETSYS.HTM ERRSYS.HTM NULLUSER.HTM SETUSER.HTM ERRUSER.HTM NULLVDO.HTM SETVDO.HTM ERRVDO.HTM STSNET.HTM STSSYS.HTM STSUSER.HTM STSVDO.HTM SYSTEM.HTM TEST.HTM UPGRADE.HTM UPLOAD.HTM USER.HTM VIDEO.HTM

IMAGE.CGI NETWORK.CGI USER.CGI USERLIST.CGI DATETIME.CGI UPLOAD.CGI EMAIL.CGI ISYSTEM.CGI IIMAGE.CGI INETWORK.CGI IUSER.CGI CGIVER.CGI SETCFG.CGI RESET.CGI IACTIVEUSER.CGI CGIVERSION.CGI IOCONTROL.CGI DEVINFO.CGI VIDEO.CGI MJPEG.CGI CONFIG.CGI PANTILTCONTROL.CGI MESSAGE.CGI SMOBILE.CGI EMOBILE.CGI SNAPSHOT.CGI

ACTIVEX.JPG BACKUP0.JPG BACKUP1.JPG BOTTOM.JPG DATETM0.JPG DATETM1.JPG DEVICE.JPG DLOADBAR.GIF DOWN_03.JPG EMAIL0.JPG EMAIL1.JPG FAPPLY.JPG FCANCEL.JPG FREFRESH.JPG HOME.JPG JAVA.JPG LOGO.JPG MADVANCE.JPG MHELP.JPG MSTATUS.JPG MTOOLS.JPG NETWORK0.JPG NETWORK1.JPG RESET0.JPG RESET1.JPG SETUP.JPG SYSTEM0.JPG SYSTEM1.JPG TEST0.JPG TEST1.JPG UPGRADE0.JPG UPGRADE1.JPG UPLOAD0.JPG UPLOAD1.JPG USER0.JPG USER1.JPG VIDEO0.JPG VIDEO1.JPG

Some users have reported success flashing generic Cellvision or other rebadged camera firmware to their DCS-900 system. This seems risky, even on a Revision B unit.

Files and Downloads

My collection of firmware images and utilties is on the Floodgap gopher server, including IPView Lite. They may or may not work for you. They may brick your camera(s). You use them at your own risk.

IPView Lite requires at least Windows 98; it may run on Windows 95 as well. The administrator password defaults to username admin with a blank password.


Cameron Kaiser