mirror of
https://github.com/torvalds/linux.git
synced 2024-12-12 14:12:51 +00:00
mtd: phram: dot not crash when built-in and passing boot param
This patch is based on Ville Herva's similar patch to block2mtd. Trying to pass a parameter through the kernel command line when built-in would crash the kernel, as phram_setup() was called so early that kmalloc() was not functional yet. This patch only saves the parameter string at the early boot stage, and parses it later when init_phram() is called. The same happens in both module and built-in cases. With this patch, I can boot with a statically-compiled phram, and mount a ext2 root fs from physical RAM, without the need for a initrd. This has been tested in built-in and module cases, with and without a parameter string. Artem: amended comments a bit Signed-off-by: Hervé Fache <h-fache@ti.com> Signed-off-by: Artem Bityutskiy <artem.bityutskiy@linux.intel.com> Signed-off-by: David Woodhouse <David.Woodhouse@intel.com>
This commit is contained in:
parent
09ef90d965
commit
b2a2a84d35
@ -39,7 +39,8 @@ static int phram_erase(struct mtd_info *mtd, struct erase_info *instr)
|
||||
|
||||
memset(start + instr->addr, 0xff, instr->len);
|
||||
|
||||
/* This'll catch a few races. Free the thing before returning :)
|
||||
/*
|
||||
* This'll catch a few races. Free the thing before returning :)
|
||||
* I don't feel at all ashamed. This kind of thing is possible anyway
|
||||
* with flash, but unlikely.
|
||||
*/
|
||||
@ -204,7 +205,17 @@ static inline void kill_final_newline(char *str)
|
||||
return 1; \
|
||||
} while (0)
|
||||
|
||||
static int phram_setup(const char *val, struct kernel_param *kp)
|
||||
/*
|
||||
* This shall contain the module parameter if any. It is of the form:
|
||||
* - phram=<device>,<address>,<size> for module case
|
||||
* - phram.phram=<device>,<address>,<size> for built-in case
|
||||
* We leave 64 bytes for the device name, 12 for the address and 12 for the
|
||||
* size.
|
||||
* Example: phram.phram=rootfs,0xa0000000,512Mi
|
||||
*/
|
||||
static __initdata char phram_paramline[64+12+12];
|
||||
|
||||
static int phram_setup(const char *val)
|
||||
{
|
||||
char buf[64+12+12], *str = buf;
|
||||
char *token[3];
|
||||
@ -253,12 +264,28 @@ static int phram_setup(const char *val, struct kernel_param *kp)
|
||||
return ret;
|
||||
}
|
||||
|
||||
module_param_call(phram, phram_setup, NULL, NULL, 000);
|
||||
static int __init phram_param_call(const char *val, struct kernel_param *kp)
|
||||
{
|
||||
/*
|
||||
* This function is always called before 'init_phram()', whether
|
||||
* built-in or module.
|
||||
*/
|
||||
if (strlen(val) >= sizeof(phram_paramline))
|
||||
return -ENOSPC;
|
||||
strcpy(phram_paramline, val);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
module_param_call(phram, phram_param_call, NULL, NULL, 000);
|
||||
MODULE_PARM_DESC(phram, "Memory region to map. \"phram=<name>,<start>,<length>\"");
|
||||
|
||||
|
||||
static int __init init_phram(void)
|
||||
{
|
||||
if (phram_paramline[0])
|
||||
return phram_setup(phram_paramline);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user