This procedure replaces the original 8 MiB SPI NOR with a 16 MiB chip.

The transitional 16 MiB image is created from the router's original 8 MiB full-flash dump using this layout:

0x000000 - 0x7bffff   original bootloader/table/info/firmware
0x7c0000 - 0xfbffff   erased (0xff)
0xfc0000 - 0xfeffff   original config from 0x7c0000
0xff0000 - 0xffffff   original ART from 0x7f0000

The original dump must come from the same router because ART contains device-specific radio calibration data.

1. Read and verify the original 8 MiB flash

Read the flash at least twice:

flashrom -p serprog:dev=/dev/ttyACM0,spispeed=16M -r cpe510-original-read1.bin
flashrom -p serprog:dev=/dev/ttyACM0,spispeed=16M -r cpe510-original-read2.bin
cmp cpe510-original-read1.bin cpe510-original-read2.bin

No output from cmp means the dumps are identical. Alternatively:

sha256sum cpe510-original-read1.bin cpe510-original-read2.bin

The hashes must be identical. If the dumps differ, reduce the SPI speed and repeat the reads: 16M -> 8M -> 4M -> 2M -> 1M.

Do not continue until at least two complete reads are byte-for-byte identical.

Check the dump size:

wc -c cpe510-original-read1.bin

It must be:

8388608

2. Create the transitional 16 MiB image

Create an empty 16 MiB image filled with 0xff:

dd if=/dev/zero bs=1M count=16 2>/dev/null | tr '\000' '\377' > cpe510-migrated-16mb.bin

Copy the original flash up to the old config partition:

dd if=cpe510-original-read1.bin of=cpe510-migrated-16mb.bin bs=64K count=124 conv=notrunc

Move config from 0x7c0000 to 0xfc0000:

dd if=cpe510-original-read1.bin of=cpe510-migrated-16mb.bin \
			bs=64K skip=124 count=3 seek=252 conv=notrunc

Move ART from 0x7f0000 to 0xff0000:

dd if=cpe510-original-read1.bin of=cpe510-migrated-16mb.bin \
			bs=64K skip=127 count=1 seek=255 conv=notrunc

Check the resulting image size:

wc -c cpe510-migrated-16mb.bin

It must be:

16777216

3. Write and verify the new 16 MiB flash

Write the image:

flashrom -p serprog:dev=/dev/ttyACM0,spispeed=16M -w cpe510-migrated-16mb.bin

Read the entire chip back:

flashrom -p serprog:dev=/dev/ttyACM0,spispeed=16M -r cpe510-16mb-readback.bin

Compare:

cmp cpe510-migrated-16mb.bin cpe510-16mb-readback.bin

No output means the files are identical.

If they differ, reduce the SPI speed and repeat the write/read/compare procedure.

Do not continue until the complete readback is byte-for-byte identical to the image that was written.

4. Boot the transitional system

Install the 16 MiB flash and boot the router.

The first boot still uses the old 8 MiB OpenWrt kernel and partition layout. Wi-Fi may not work at this stage.

5. Install the final 16 MiB OpenWrt image

Copy the final 16 MiB CPE510 v3 sysupgrade image to /tmp.

The old kernel still reports the old 8 MiB firmware partition size, so the first upgrade must be forced:

sysupgrade -F -n /tmp/openwrt-ath79-generic-tplink_cpe510-v3-squashfs-sysupgrade.bin

-F is required only for this one migration upgrade.

6. Verify the final system

After reboot:

cat /proc/mtd

The final layout should contain:

firmware  00f80000
config    00030000
art       00010000

The final locations are:

firmware  0x040000 - 0xfbffff
config    0xfc0000 - 0xfeffff
ART       0xff0000 - 0xffffff

Verify that Wi-Fi works.

The migration is now complete.

For all future upgrades use the normal 16 MiB sysupgrade without -F:

sysupgrade /tmp/openwrt-ath79-generic-tplink_cpe510-v3-squashfs-sysupgrade.bin

The SPI programmer is no longer required for normal firmware upgrades.