Electronic – ARM Linux and UBoot – Can I make a read-only MTD writable


I have several embedded Linux devices installed at customer sites. We have an updated Linux kernel we are prepared to deploy to these devices. The problem is that on these devices, the U-Boot arguments are specified such that:

bootargs = {....} mtdparts=atmel_nand:16M(kernel)ro,240M(rootfs)

So, I can't flash_erase to nandwrite the kernel or U-Boot over SSH because MTD0 is read-only. I can't tweak the U-Boot args without serial access. For many of the customers, taking all the devices down and serially hooking them up and interrupting U-Boot to get to the bootargs would be extremely cumbersome. Is there any way to change MTD0 from ro to rw from the kernel once it's loaded?

Best Answer

Have you considered creating a simple kernel module you can insert to make the MTD partition(s) writable? I had this same problem and was able to work around it by writing a kernel module. For simplicity, I just went ahead and had it make every MTD device writable. Basically, the module has to do something like this in its init function:

struct mtd_info *mtd;
int x;
bool keep_going = true;

for (x = 0; keep_going; x++) {
    mtd = get_mtd_device(NULL, x);
    if (!IS_ERR(mtd)) {
        mtd->flags |= MTD_WRITEABLE;
    } else {
        keep_going = false;

After inserting this module, I was successfully able to use flash_erase and nandwrite while booted in the kernel, whereas before, flash_erase was telling me: "error 13 (Permission denied)"