Need help obtaining flash layout (D-Link DIR-845L)

Hi everyone,

in order to add support for my D-Link device to LEDE one of the first steps is to get the flash layout, so I can create a device tree file.

But I'm having trouble with that.

What I know from the boot log, that I collected over the serial port (full log is in the wiki entry, linked above):

3: System Boot system code via Flash. 
## Booting image at b0050000 ... 
We have SEAMA, Image Size = 8765472 
Verifying Checksum ... 
Uncompressing SEAMA linux.lzma ... 
OK 
## Transferring control to Linux (at address 80000000) ... 
## Giving linux memsize in MB, 128 

Starting kernel ... 

Linux version 2.6.33.2 (tom_lin@RangeRover) (gcc version 4.3.3 (GCC) ) #1 Tue Oct 8 11:02:48 CST 2013 
ISPRAM0: PA=002f0000,Size=00008000,enabled 
Ralink RT63165 SOC prom init 
bootconsole [early0] enabled 
CPU revision is: 00019555 (MIPS 34Kc) 
Determined physical RAM map:
 memory: 07fe0000 @ 00020000 (usable)

But the log doesn't contain the flash layout.

I also know:

cat /proc/mtd
dev:    size   erasesize  name
mtd0: 01000000 00010000 "raspi"
mtd1: 0070c000 00010000 "rootfs"
mtd2: 00f10000 00010000 "upgrade"
mtd3: 00010000 00010000 "devconf"
mtd4: 00010000 00010000 "devdata"
mtd5: 00020000 00010000 "langpack"
mtd6: 01000000 00010000 "flash"
mtd7: 00030000 00010000 "u-boot"
mtd8: 00008000 00010000 "boot env"
mtd9: 00080000 00010000 "mydlink"

So I know the size of each partition and their name but not their start address.

I'm not able to run dmesg for some reason.

My last idea is:
dump the flash using dd into a binary file, copy this file to my pc (Wiki)
and analyze it there with binwalker.

Is there another better way?
If not: How can I correctly dump the flash?

Regards,
Djfe

See the section Discovery (How to find out) in this OpenWRT article...

https://wiki.openwrt.org/doc/techref/flash.layout

Thx for your advice! :slight_smile:

I think, I got it now.

I made some calculations, there where still some open questions about the position of the partitions after that.
But then I started looking at wiki pages of similar d-link devices and found the DIR-645.
The layout and names match what runs on my device (only on a 16mb flash chip instead of 8mb), so it's probably the same layout and d-link just reused it for the new generation.

I'm gonna take a look at the dts file of that device now.

I just realize: the old device doesn't have the "mydlink" partition, yet.
So there's one thing missing still.
Any ideas? :slight_smile:

Btw. what does "SEAMA" stand for?
I'm asking because of the following line in the boot log:

SEAMA: found image @ '/dev/mtdblock/5', image size: 100093

I only know that the name is related to some headers in the firmware file but wasn't able to find anything about the name using google.
My guess is, that my board probably also needs to end up in this file:
https://github.com/lede-project/source/blob/master/target/linux/ramips/base-files/etc/uci-defaults/09_fix-seama-header

You need to know what kind of images u-boot can boot. In recent D-Link routers factory image format is SEAMA. It has internal device name (it is wrgnd21_dlob.hans_dir845 in your case) and also likely has to be encrypted to be accepted by OEM web interface update page. You have to look at D-Link GPL tarball for your device and learn how to cook acceptable images. "seama" and "encimg" utilities are used in chain to cook it.

PS firmware is not encrypted.

ok, thx for already taking a look at the firmware :slight_smile:

very good to know.

when I want to boot from tftp to ram (serial console),
does the firmware also need this format or a different one?

Nobody but D-Link's uboot developers can answer you. You have to investigate all by yourself.
Good starting point is to dump fullflash from your device. Did you manage to do this?

Yes, I dumped each mtd partition into a separate file using dd
dd if=/dev/mtd6 of=/path-to-usb-stick/mtd6.img bs=65536

mtd6 representing the full flash dump, since the partition spans the whole flash chip

If you want to take a look, then I can provide the files.
Just tell me how you prefer to get them.

I also created three diff files between D-Link's kernel and the Linux kernel (same version number) to get the changes they made to architecture, includes and drivers:
https://wiki.openwrt.org/doc/devel/add.new.platform#creating_a_hardware_specific_kernel_patch

I know OpenWrt/Linux doesn't support the rt6856f from ralink, yet. So I have to implement a working driver for it/complement existing ramips drivers to make this work.

Which will be likely the hardest part of this.

I'm going to take a look at https://lwn.net/Kernel/LDD3/ now in order to learn how to write drivers.
And after that at the mentioned diff files and the current ramips folder.

any help or guidance with this task would be very much appreciated :slight_smile:

PS:
Are there any articles (wiki etc.) I should read, that list coding conventions specific to how stuff is handled in lede/openwrt?
I only found some YouTube recordings from talks by the devs, that kind of cover this.

I have a question about the mtd9 partition ("mydlink"):
it's 512KiB big and is filled with "FF"s

since it's an mtd block device:
is it guaranteed to be on the flash? (and therefore in mtd0/mtd6)

If so, then my guess for now is, that it sits between Byte number 8AC060 and Byte number and 8F0060 of the flash, because it's the only section that's big enough (6592KiB) to contain it. And it's completely filled with ("FF"s)

Something else that's confusing right now:
There is 256KiB of data sitting after rootfs (in mtd2 (upgrade partition)) and I don't know what it is.
Since it's part of the upgrade partition, my guess is, that OpenWRT can simply overwrite it and use the full 15424 KiB of the upgrade partition (seems like D-Link didn't need the full 16MB of the flash chip), since the next firmware upgrade will include the 256KiB sitting after rootfs.

This is pretty much the final flash layout of the device:
https://wiki.openwrt.org/inbox/d-link/d-link_dir-845l_rev._a1#flash_layout

Now I need to figure out a layout for OpenWRT.
the layout in the dts, I have for now (based on dir-645)

&spi0 {
	status = "okay";

	m25p80@0 {
		#address-cells = <1>;
		#size-cells = <1>;
		compatible = "jedec,spi-nor";
		reg = <0>;
		spi-max-frequency = <25000000>;

		partition@0 {
			label = "uboot";
			reg = <0x0 0x30000>;
			read-only;
		};

		partition@30000 {
			label = "uboot-env";
			reg = <0x30000 0x4000>;
			read-only;
		};

		factory: partition@34000 {
			label = "factory";
			reg = <0x34000 0x4000>;
			read-only;
		};

		partition@38000 {
			label = "nvram";
			reg = <0x38000 0x8000>;
			read-only;
		};

		partition@40000 {
			label = "devdata";
			reg = <0x40000 0x10000>;
		};

		partition@50000 {
			label = "firmware";
			reg = <0x50000 0xfb0000>;
		};
	};
};

my guess for now is, that the data after rootfs is from a previous firmware, that has been larger.
(does flashing the device only erase necessary 64KiB blocks? (64KiB is the erasesize)
If so, then that would explain it.)

mydlink is not important for OpenWRT, so I won't declare it.
langpack is a secondary partition with it's own SEAMA header, it's probably for the language pack (.lng file that comes with the firmware)
the devs that added support for the DIR-645 from d-link seem to have written over that partition, as if it isn't there.

since mtd blocks are specified in the kernel, it should be safe to overwrite the memory, right?
In-case the user decides to go back to the official firmware, the included kernel should know again, that the memory is for the optional language pack. (that's my guess)

My fear is though: the SEAMA header will be overwritten this way, causing issues in the stock firmware in-case the user decides to return.

If anyone here knows more about the matter (d-link stock firmware), then pls speak up ^^ (I would be glad)

If not, then I'll find it out later on and reduce the "firmware" size.
At least it won't be an issue for me, since I have backup images of all partitions.

back to old the layout above:
boot env is the same as in the stock firmware.
factory / nvram are the first / last 32KiB from the remaining memory in devdata (mtd4)
factory is a good name for the memory that includes stuff like MACs and default PWs (shouldn't be touched)
(I don't know why the name nvram, yet. or whether it is even used by openwrt (anymore))

mtd3/devconf is now called devdata (for whatever reason)
I think, that devconf is the memory, that gets modified, if you press the reset button. (at least the boot log after pressing reset, says so)

1 Like