Tuesday, October 25, 2022

Adding Support for a Flash Chip in FlashcatUSB

Flash Programmers for Dumping Firmware

Blackbox IoT device hacking can be frustrating without any insight into the underlying software implementation(s). For this reason, I usually try to obtain a copy of the device firmware to extract the bootloader, kernel, root filesystem, and any other information that might inform run-time testing and targeted reverse engineering. Unfortunately, device vendors don't always provide access to firmware packages, and even when they do, the firmware blobs can be encrypted or obfuscated in a way that makes them useless without knowledge of the packaging format. Luckily there's another way to obtain device firmware - you can try to dump it directly from device storage (generally a dedicated flash chip).

Although I'm certainly not an expert on hardware hacking/RE, I occasionally find myself dumping flash chips. For chips with easily accessible pins (e.g., SOIC packages), it's usually easy enough to connect to the chip in-circuit using test clips and a serial cable. Other packages might be too small to easily hook up to (e.g., TSOP), or they might not have pins exposed at all (e.g., BGA). For these scenarios, I generally desolder the chip and dump it with a flash programmer.

There are quite a few "universal" flash programmers on the market. If I had endless cash for hobby projects, I'd probably get an industrial one that supports tens or hundreds of thousands of chips. There are two vendors/programmers that I've had on my radar for a while:

Not only are these devices expensive, but you have to spend hundreds or thousands of additional dollars for individual socket adapters. Unless I win the lottery, I can't imagine spending that much on hobby projects.

For people with a more modest budget (like myself), I recommend the FlashcatUSB XPORT from EmbeddedComputers.net. The programmer itself is only $40, and individual adapters range from ~$15 to $150.




Adding Support for the MT29F4G01ABAFDWB-IT


I recently wanted to dump the flash chip of an undisclosed IoT device. The chip appeared to be an 8x6mm WSON-8 package, with a Micron logo and "NQ464" printed on the surface (among other things). A quick Google search for "NQ464" revealed that the chip was probably a Micron MT29F4G01ABAFDWB-IT. After a bit more searching I also found the data sheet for the chip.

8x6mm WSON-8

Image of a 
MT29F4G01ABAFDWB-IT in the Amazon Echo Dot (from Brian Dorey's blog)


I desoldered the flash chip and inserted it into the Flashcat using the 8x6mm WSON-8 adapter, which can be obtained here for $58 (for comparison, a Xeltec adapter for this chip is $525).

8x6mm WSON-8 socket adapter from EmbeddedComputers.net


(Side note: I had no intention of re-soldering the chip to the board, as I'm not good at precision soldering and I had a few more of the undisclosed device under test.)

Unfortunately, the Flashcat software displayed an error:

"Flash memory detected but not found in Flash library"

After consulting the product page for the FlashcatUSB XPORT, I saw that it had support for similar chips, but not the specific one that I wanted to extract data from:


Worse yet, the Flashcat GUI tool didn't allow me to specify the custom settings I needed, as some of them seemed to be out of the selectable range (e.g., 4096 for page size).


Now, I probably could've used the command-line tool to manually specify parameters, or used the socket adapter as a breakout board to attach a serial cable, but the Flashcat software is open source and already supports very similar chips, so I thought it'd be fun to try to add support for my target chip. I downloaded the latest source code and searched for the name of a supported Micron chip:

~/FCUSB_SRC643_102422 $ grep -rl MT29F4G01AAA
Source/FlashMemory.vb

I opened the project in Visual Studio, inspected FlashMemory.vb, and saw that it was probably very easy to add support for a new SPI NAND chip:

Private Sub SPINAND_Database()
    FlashDB.Add(New SPI_NAND("Micron MT29F1G01ABA", &H2C, &H14, 2048, 128, 64, 1024, False, SPI_3V)) '1Gb
    FlashDB.Add(New SPI_NAND("Micron MT29F1G01ABB", &H2C, &H15, 2048, 128, 64, 1024, False, SPI_1V8)) '1Gb
    FlashDB.Add(New SPI_NAND("Micron MT29F2G01AAA", &H2C, &H22, 2048, 128, 64, 2048, True, SPI_3V)) '2Gb
    FlashDB.Add(New SPI_NAND("Micron MT29F2G01ABA", &H2C, &H24, 2048, 128, 64, 2048, True, SPI_3V)) '2Gb
    FlashDB.Add(New SPI_NAND("Micron MT29F2G01ABB", &H2C, &H25, 2048, 128, 64, 2048, True, SPI_1V8)) '2Gb
    FlashDB.Add(New SPI_NAND("Micron MT29F4G01ADA", &H2C, &H36, 2048, 128, 64, 4096, True, SPI_3V)) '4Gb
    FlashDB.Add(New SPI_NAND("Micron MT29F4G01AAA", &H2C, &H32, 2048, 128, 64, 4096, True, SPI_3V)) '4Gb

The definition of the SPI_NAND constructor was pretty straightforward:

Public Class SPI_NAND : Inherits G_NAND
    Public ReadOnly Property PLANE_SELECT As Boolean 'Indicates that this device needs to select a plane when accessing pages
    Public Property READ_CMD_DUMMY As Boolean = False 'Write a dummy byte after read command
    Public Property STACKED_DIES As Integer = 1 'If device has more than one die, set this value

    Sub New(FlashName As String, MFG As Byte, ID As UInt32, PageSize As UInt16, SpareSize As UInt16, PageCount As UInt16, BlockCount As UInt16, plane_select As Boolean, vcc As VCC_IF)
        MyBase.New(FlashName, MFG, ID, PageSize, SpareSize, PageCount, BlockCount, vcc)
        Me.PLANE_SELECT = plane_select
        Me.FLASH_TYPE = MemoryType.SERIAL_NAND
    End Sub
End Class

I consulted the data sheet to find the parameters I needed:

Data sheet, page 1

Data sheet, page 27

The chip only has one plane, so I assumed plane_select could be set to false (though I'm not sure if this is sound logic). Finally, I added support for the MT29F4G01ABA with a single line of code:

FlashDB.Add(New SPI_NAND("Micron MT29F4G01ABA", &H2C, &H34, 4096, 256, 64, 2048, False, SPI_3V)) '4Gb

After downloading a dependency, I compiled and ran the updated Flashcat software, which correctly identified the flash chip:

Then I started the dump:

Dumping the whole chip took about 4.5 hours at a reported rate of ~30KB/s. This is awfully slow, but it seems to be a limitation of FlashcatUSB (see the update below).

After the dump finished, I was able to confirm that it worked (note that I've truncated the following output):

$ binwalk Micron_MT29F4G01ABA_00-1FFFFFFF.bin
DECIMAL       HEXADECIMAL     DESCRIPTION
--------------------------------------------------------------------------------
606856        0x94288         CRC32 polynomial table, little endian
2889792       0x2C1840        device tree image (dtb)
3151936       0x301840        device tree image (dtb)
5511232       0x541840        device tree image (dtb)
5773376       0x581840        device tree image (dtb)
...
21675123      0x14ABC73       Neighborly text, "neighbor dump requestbor dump request"
...
46923776      0x2CC0000       UBI erase count header, version: 1, EC: 0x1, VID header offset: 0x1000, data offset: 0x2000

I guess I should contact EmbeddedComputers.net so they can add support for this chip.


For anyone looking to get started with this kind of project, I compiled a list of tools and resources I used during this adventure:

This adds up to about $270 (before tax and shipping).


Update (2022-10-26)

I contacted EmbeddedComputers.net and they added official support for the Micron  MT29F4G01ABA. They were also kind enough to give a brief explanation about the slow SPI NAND speeds:

Reading/writing a SPI NAND device using Classic/XPORT is slow, because the protocol has to be implemented via software. It's not the same as a SPI NOR flash. These types of chips implement a NAND protocol (similar to a parallel X8 NAND chip), but use the SPI bus instead. FlashcatUSB Professional, which is optimized for serial protocols, supports SPI NAND via its FPGA and it implements the entire protocol in hardware, so it can achieve read/write speeds of 1MB/s+.

You can see how the protocol is decoded and implemented in the SPI_NAND.vb file.

The FlashcatUSB Pro is only $59.99, so perhaps I'll get one too. Seems more convenient than hooking up a serial cable at least.


No comments:

Post a Comment