在uboot中添加一个命令set_test_param,设置环境变量test_param为1,再传递到内核,并可在用户空间访问。
uboot和linux内核的参数传递通过相同的数据结构struct tag实现;在用户空间访问通过proc文件系统实现。
以下是需要修改的代码(git diff得出):
diff --git a/uboot/arch/arm/include/asm/setup.h b/uboot/arch/arm/include/asm/setup.h
index 89df4dc..e95dc82 100644
--- a/uboot/arch/arm/include/asm/setup.h
+++ b/uboot/arch/arm/include/asm/setup.h
@@ -188,6 +188,12 @@ struct tag_cmdline {
char cmdline[1]; /* this is the minimum size */
};
+//gxh add
+#define ATAG_test_param 0x5441000a
+struct tag_test_param {
+ char test_param[8]; /* this is the minimum size */
+};
+
/* acorn RiscPC specific information */
#define ATAG_ACORN 0x41000101
@@ -218,6 +224,9 @@ struct tag {
struct tag_videolfb videolfb;
struct tag_cmdline cmdline;
+ //gxh add
+ struct tag_test_param test_param;
+
/*
* Acorn specific
*/
diff --git a/uboot/arch/arm/lib/bootm.c b/uboot/arch/arm/lib/bootm.c
index 7a22048..1539ed8 100644
--- a/uboot/arch/arm/lib/bootm.c
+++ b/uboot/arch/arm/lib/bootm.c
@@ -29,6 +29,8 @@
DECLARE_GLOBAL_DATA_PTR;
+static void setup_test_param_tag (bd_t *bd, char *test_param); //gxh add
+
#if defined (CONFIG_SETUP_MEMORY_TAGS) || \
defined (CONFIG_CMDLINE_TAG) || \
defined (CONFIG_INITRD_TAG) || \
@@ -63,6 +65,9 @@ int do_bootm_linux(int flag, int argc, char * const argv[], bootm_headers_t *ima
char *pxa_commandline = getenv ("pxa_bootargs");
#endif
+ //gxh add
+ char *test_param = getenv("test_param");
+
if ((flag != 0) && (flag != BOOTM_STATE_OS_GO))
return 1;
@@ -102,6 +107,10 @@ int do_bootm_linux(int flag, int argc, char * const argv[], bootm_headers_t *ima
if (images->rd_start && images->rd_end)
setup_initrd_tag (bd, images->rd_start, images->rd_end);
#endif
+
+ //gxh add
+ setup_test_param_tag(bd, test_param);
+
setup_end_tag (bd);
#endif
@@ -123,6 +132,32 @@ int do_bootm_linux(int flag, int argc, char * const argv[], bootm_headers_t *ima
return 1;
}
+//gxh add
+static void setup_test_param_tag (bd_t *bd, char *test_param)
+{
+ char *p;
+
+ if (!test_param)
+ return;
+
+ for (p = test_param; *p == ' '; p++);
+
+ /* skip non-existent command lines so the kernel will still
+ * use its default command line.
+ */
+ if (*p == '\0')
+ return;
+
+
+ params->hdr.tag = ATAG_test_param;
+ params->hdr.size = tag_size (tag_test_param);
+
+ strcpy (params->u.test_param.test_param, p);
+
+ //printf("params->u.test_param.test_param: %s\n", params->u.test_param.test_param);
+
+ params = tag_next (params);
+}
#if defined (CONFIG_SETUP_MEMORY_TAGS) || \
defined (CONFIG_CMDLINE_TAG) || \
diff --git a/uboot/common/Makefile b/uboot/common/Makefile
index 2cd1480..4627e1f 100644
--- a/uboot/common/Makefile
+++ b/uboot/common/Makefile
@@ -118,7 +118,8 @@ COBJS-$(CONFIG_CMD_MG_DISK) += cmd_mgdisk.o
COBJS-$(CONFIG_MII) += miiphyutil.o
COBJS-$(CONFIG_CMD_MII) += miiphyutil.o
COBJS-$(CONFIG_CMD_MII) += cmd_mii.o
-COBJS-$(CONFIG_CMD_MISC) += cmd_misc.o
+#COBJS-$(CONFIG_CMD_MISC) += cmd_misc.o
+COBJS-y += cmd_misc.o
COBJS-$(CONFIG_CMD_MMC) += cmd_mmc.o
COBJS-$(CONFIG_MP) += cmd_mp.o
COBJS-$(CONFIG_CMD_MTDPARTS) += cmd_mtdparts.o
diff --git a/uboot/common/cmd_misc.c b/uboot/common/cmd_misc.c
index 061b1bb..ab59ca0 100644
--- a/uboot/common/cmd_misc.c
+++ b/uboot/common/cmd_misc.c
@@ -53,3 +53,28 @@ U_BOOT_CMD(
"N\n"
" - delay execution for N seconds (N is _decimal_ !!!)"
);
+
+
+/**************************gxh add**********************************************/
+
+int do_test_param (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
+{
+ setenv("test_param", "1");
+}
+
+U_BOOT_CMD(
+ set_test_param , 2, 1, do_test_param,
+ "Trun on test_param mode.",
+ NULL
+);
diff --git a/kernel/arch/arm/include/asm/setup.h b/kernel/arch/arm/include/asm/setup.h
index 5ccce0a..6eb875d 100644
--- a/kernel/arch/arm/include/asm/setup.h
+++ b/kernel/arch/arm/include/asm/setup.h
@@ -143,6 +143,12 @@ struct tag_memclk {
__u32 fmemclk;
};
+//gxh add
+#define ATAG_test_param 0x5441000a
+struct tag_test_param {
+ char test_param[8]; /* this is the minimum size */
+};
+
struct tag {
struct tag_header hdr;
union {
@@ -155,7 +161,9 @@ struct tag {
struct tag_revision revision;
struct tag_videolfb videolfb;
struct tag_cmdline cmdline;
-
+ //gxh add
+ struct tag_test_param test_param;
+
/*
* Acorn specific
*/
diff --git a/kernel/arch/arm/kernel/setup.c b/kernel/arch/arm/kernel/setup.c
index c6c57b6..ba00880 100644
--- a/kernel/arch/arm/kernel/setup.c
+++ b/kernel/arch/arm/kernel/setup.c
@@ -123,6 +123,9 @@ static char default_command_line[COMMAND_LINE_SIZE] __initdata = CONFIG_CMDLINE;
static union { char c[4]; unsigned long l; } endian_test __initdata = { { 'l', '?', '?', 'b' } };
#define ENDIANNESS ((char)endian_test.l)
+//gxh add
+char default_test_param[8] = {'\0'};
+
DEFINE_PER_CPU(struct cpuinfo_arm, cpu_data);
/*
@@ -635,6 +638,17 @@ static int __init parse_tag_cmdline(const struct tag *tag)
__tagtable(ATAG_CMDLINE, parse_tag_cmdline);
+//gxh add
+static int __init parse_tag_test_param(const struct tag *tag)
+{
+ //printk(KERN_INFO "test_param:%s", tag->u.test_param.test_param);
+ //printk(KERN_INFO "test_param_type:0x%08x\n", tag->hdr.tag);
+ strlcpy(default_test_param, tag->u.test_param.test_param, 4);
+ return 0;
+}
+__tagtable(ATAG_test_param, parse_tag_test_param);
+
+
/*
* Scan the tag table for this tag, and call its parse function.
* The tag table is built by the linker from all the __tagtable
diff --git a/kernel/arch/arm/plat-pxa/generic.c b/kernel/arch/arm/plat-pxa/generic.c
index 3b0adcf..96ed2db 100644
--- a/kernel/arch/arm/plat-pxa/generic.c
+++ b/kernel/arch/arm/plat-pxa/generic.c
@@ -64,6 +64,35 @@ static int __init create_pxa_cmdline_proc_file(void)
}
module_init(create_pxa_cmdline_proc_file);
+#if 1 //gxh add
+
+extern char default_test_param[8];
+
+static ssize_t test_param_read_proc(char *page, char **start, off_t off,
+ int count, int *eof, void *data)
+{
+ int len = strlen(default_test_param);
+
+ sprintf(page, "%s\n", default_test_param);
+ return len + 1;
+}
+static int __init create_test_param_proc_file(void)
+{
+ struct proc_dir_entry *test_param_proc_file =
+ create_proc_entry("test_param", 0644, NULL);
+
+ if (test_param_proc_file)
+ test_param_proc_file->read_proc = test_param_read_proc;
+ else
+ printk(KERN_INFO "test_param proc file create failed!\n");
+
+ return 0;
+}
+module_init(create_test_param_proc_file);
+
+#endif
+
+
static int android_project = 0;
static int __init android_setup(char *__unused)
{
欢迎光临 Chinaunix (http://bbs.chinaunix.net/) | Powered by Discuz! X3.2 |