Hello, I'm working on x86 using usb for boot. It works for me if usb and usb-storage drivers enabled via make kernel_menuconfig.
One thing I had to fix for get it working: mtd2block does not long enough until usb has been up. This patch was made against 2.6.32 at 10.03 (put in target/linux/generic-2.6/patches-2.6.32). This is same as I wrote at https://dev.openwrt.org/ticket/9780 The second one (068-block2mtd_probe.patch, adds the wait for device probe) was missing on ticket. The patch is based on the code at http://permalink.gmane.org/gmane.linux.drivers.mtd/26384 (by Tobias Diedrich). Maybe we find a way to integrate usbboot options (enable usb+usb-storage directly into kernel if usb boot enabled via option). I'll have a look on that later. With best regards Christoph -- Linux User Group Wernigerode http://www.lug-wr.de/) but
--- a/drivers/mtd/devices/block2mtd.c +++ b/drivers/mtd/devices/block2mtd.c @@ -268,6 +268,7 @@ static int _open_bdev(struct block2mtd_d /* We might not have rootfs mounted at this point. Try to resolve the device name by other means. */ + wait_for_device_probe(); dev_t devt = name_to_dev_t(dev->devname); if (devt) { bdev = open_by_devnum(devt, FMODE_WRITE | FMODE_READ);
--- a/drivers/mtd/devices/block2mtd.c.orig 2011-07-22 10:17:24.006187073 +0200 +++ a/drivers/mtd/devices/block2mtd.c 2011-07-22 10:48:03.706185480 +0200 @@ -18,6 +18,8 @@ #include <linux/buffer_head.h> #include <linux/mutex.h> #include <linux/mount.h> +#include <linux/delay.h> +#include <linux/kthread.h> #define ERROR(fmt, args...) printk(KERN_ERR "block2mtd: " fmt "\n" , ## args) #define INFO(fmt, args...) printk(KERN_INFO "block2mtd: " fmt "\n" , ## args) @@ -475,7 +477,31 @@ #endif -static int block2mtd_setup2(const char *val) +struct block2mtd_setupasync_params { + char *name; + int erase_size; + char *mtdname; +}; + +static int block2mtd_setupasync(void *p) +{ + struct block2mtd_setupasync_params *params = p; + int i; + + printk(KERN_WARNING "block2mtd: spawned kernel thread for async waiting on '%s'\n", params->name); + for (i=0; i<20; i++) { + msleep(1000); + + if (add_device(params->name, params->erase_size, params->mtdname) != NULL) + break; + } + kfree(params->name); + kfree(params); + + return 0; +} + +static int block2mtd_setup2(const char *val, int async) { char buf[80 + 12 + 80]; /* 80 for device, 12 for erase size, 80 for name */ char *str = buf; @@ -483,6 +509,7 @@ char *name; size_t erase_size = PAGE_SIZE; int i, ret; + struct block2mtd_setupasync_params *params; if (strnlen(val, sizeof(buf)) >= sizeof(buf)) parse_err("parameter too long"); @@ -512,7 +539,33 @@ if (token[2] && (strlen(token[2]) + 1 > 80)) parse_err("mtd device name too long"); - add_device(name, erase_size, token[2]); + if (add_device(name, erase_size, token[2]) != NULL) + return 0; + + params = kzalloc(sizeof(struct block2mtd_setupasync_params), GFP_KERNEL); + if (!params) + return 0; + + params->name = kmalloc(strlen(name)+1, GFP_KERNEL); + params->erase_size = erase_size; + if (!params->name) { + kfree(params); + return 0; + } + + memcpy(params->name, name, strlen(name)+1); + + params->mtdname = kmalloc(strlen(token[2])+1, GFP_KERNEL); + + if (!params->mtdname) { + kfree(params); + return 0; + } + + memcpy(params->mtdname, token[2], strlen(token[2])+1); + + if (async) + kthread_run(block2mtd_setupasync, params, "block2mtd/setupasync"); return 0; } @@ -521,7 +574,7 @@ static int block2mtd_setup(const char *val, struct kernel_param *kp) { #ifdef MODULE - return block2mtd_setup2(val); + return block2mtd_setup2(val, 0); #else /* If more parameters are later passed in via /sys/module/block2mtd/parameters/block2mtd @@ -529,7 +582,7 @@ we can parse the argument now. */ if (block2mtd_init_called) - return block2mtd_setup2(val); + return block2mtd_setup2(val, 0); /* During early boot stage, we only save the parameters here. We must parse them later: if the param passed @@ -554,7 +607,7 @@ #ifndef MODULE if (strlen(block2mtd_paramline)) - ret = block2mtd_setup2(block2mtd_paramline); + ret = block2mtd_setup2(block2mtd_paramline, 1); block2mtd_init_called = 1; #endif
signature.asc
Description: This is a digitally signed message part.
_______________________________________________ openwrt-devel mailing list openwrt-devel@lists.openwrt.org https://lists.openwrt.org/mailman/listinfo/openwrt-devel