Scapy Support for USB Protocol on Facedancer Boards, MAX2420, etc.

Immediately following the public release of the Facedancer10 PCBs by neighbors Travis Goodspeed and Sergey Bratus at REcon 2012, I began to develop a Scapy layer to support interacting with the MAX2420 chip used.

The initial code released in the GoodFET repository by Travis has some great examples, one of which is using the Facedancer to emulate a device using the USB HID (human-interface-device) specification. However, when looking at modifying the code to extend it, or use it for fuzzing, a major issue is determining the meaning of fields and the legitimate (and illegitimate) values for them, as well as the relationships between fields. This information is crucial to both specification-compliant use, or fuzzing.

For a few reasons, I’m not releasing this into the scapy-com or to the GoodFET trunk repository at this time. I do not feel that this USB layer is yet fully implemented enough to add to scapy-com. Further, although you hopefully know that USB is best thought of as a network, and not a (trusted) bus, I still see some disparities between the protocol I’ve implemented Scapy support for interacting with USB, and the common Scapy protocols (ntp, ftp, 802.11, etc). I’ve decided not to add this to the GoodFET trunk right now because it would add a dependency on Scapy for people using the goodfet.maxusbhid script.

Having said that, if you’re seriously playing with the Facedancer or the MAX2420 chip in another capacity, I strongly suggest using this Scapy layer. It makes it much easier to understand and implement the protocol. For example, bit flags are referenced logically, nesting of descriptors is implemented per the USB specification, and Unicode encoding on string descriptors is handled for you.

Currently the following classes are available:

  • class USBSetup(Packet):
  • class USBDeviceDescriptor(Packet):
  • class USBDescriptorHID(Packet):
  • class USBDescriptorEndpoint(Packet):
  • class USBDescriptorInterface(Packet):
  • class USBConfigurationDescriptor(Packet):
  • class USBStringDescriptor(Packet):
  • class USBStringDescriptorLanguage(USBStringDescriptor):

Additionally, test cases are implemented which compare the construction against the hand-crafted byte-arrays used in Travis’ code (TestDeviceDescriptor, TestConfigurationDescriptor, TestStringDescriptor). I’ve also tried to include comments and links to the specification in the code.

Despite the features available, there is still much cleanup to be done and more features to be added (only so much can be jammed out during a conference). Please let me know if you’re using it, and also please feel free to send suggestions, patches, extensions, etc. I’ll aim to continue development on this at a later point, but currently my available time has switched to the Api-Mote.

The current code, is available in the GoodFET SVN repository, under the contrib tree (svn path: https://goodfet.svn.sourceforge.net/svnroot/goodfet/contrib/facedancer/scapy). The usb_max.py file is a Scapy layer, and the GoodFETMAXUSB.py file is a branch of Travis’ original file that uses the Scapy classes. Just copy it over the existing file in your GoodFET client folder, and drop usb_max.py right alongside it. Ensure you have Scapy installed.

Here’s a quick example of using it combined with Travis’ original code to exploit a known issue with Xorg. A one line change is made to my published version, which when run causes a quick crash of Xorg and needs a reboot, as previously identified and reported on here.

Project link: NA