OpenWrt – Blame information for rev 4
?pathlinks?
Rev | Author | Line No. | Line |
---|---|---|---|
4 | office | 1 | From 71270226b14733a4b1f2cde58ea9265caa50b38d Mon Sep 17 00:00:00 2001 |
2 | From: Adrian Panella <ianchi74@outlook.com> |
||
3 | Date: Thu, 9 Mar 2017 09:37:17 +0100 |
||
4 | Subject: [PATCH 67/69] generic: Mangle bootloader's kernel arguments |
||
5 | |||
6 | The command-line arguments provided by the boot loader will be |
||
7 | appended to a new device tree property: bootloader-args. |
||
8 | If there is a property "append-rootblock" in DT under /chosen |
||
9 | and a root= option in bootloaders command line it will be parsed |
||
10 | and added to DT bootargs with the form: <append-rootblock>XX. |
||
11 | Only command line ATAG will be processed, the rest of the ATAGs |
||
12 | sent by bootloader will be ignored. |
||
13 | This is usefull in dual boot systems, to get the current root partition |
||
14 | without afecting the rest of the system. |
||
15 | |||
16 | Signed-off-by: Adrian Panella <ianchi74@outlook.com> |
||
17 | --- |
||
18 | arch/arm/Kconfig | 11 +++++ |
||
19 | arch/arm/boot/compressed/atags_to_fdt.c | 72 ++++++++++++++++++++++++++++++++- |
||
20 | init/main.c | 16 ++++++++ |
||
21 | 3 files changed, 98 insertions(+), 1 deletion(-) |
||
22 | |||
23 | --- a/arch/arm/Kconfig |
||
24 | +++ b/arch/arm/Kconfig |
||
25 | @@ -1938,6 +1938,17 @@ config ARM_ATAG_DTB_COMPAT_CMDLINE_EXTEN |
||
26 | The command-line arguments provided by the boot loader will be |
||
27 | appended to the the device tree bootargs property. |
||
28 | |||
29 | +config ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE |
||
30 | + bool "Append rootblock parsing bootloader's kernel arguments" |
||
31 | + help |
||
32 | + The command-line arguments provided by the boot loader will be |
||
33 | + appended to a new device tree property: bootloader-args. |
||
34 | + If there is a property "append-rootblock" in DT under /chosen |
||
35 | + and a root= option in bootloaders command line it will be parsed |
||
36 | + and added to DT bootargs with the form: <append-rootblock>XX. |
||
37 | + Only command line ATAG will be processed, the rest of the ATAGs |
||
38 | + sent by bootloader will be ignored. |
||
39 | + |
||
40 | endchoice |
||
41 | |||
42 | config CMDLINE |
||
43 | --- a/arch/arm/boot/compressed/atags_to_fdt.c |
||
44 | +++ b/arch/arm/boot/compressed/atags_to_fdt.c |
||
45 | @@ -4,6 +4,8 @@ |
||
46 | |||
47 | #if defined(CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_EXTEND) |
||
48 | #define do_extend_cmdline 1 |
||
49 | +#elif defined(CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE) |
||
50 | +#define do_extend_cmdline 1 |
||
51 | #else |
||
52 | #define do_extend_cmdline 0 |
||
53 | #endif |
||
54 | @@ -67,6 +69,59 @@ static uint32_t get_cell_size(const void |
||
55 | return cell_size; |
||
56 | } |
||
57 | |||
58 | +#if defined(CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE) |
||
59 | + |
||
60 | +static char *append_rootblock(char *dest, const char *str, int len, void *fdt) |
||
61 | +{ |
||
62 | + char *ptr, *end; |
||
63 | + char *root="root="; |
||
64 | + int i, l; |
||
65 | + const char *rootblock; |
||
66 | + |
||
67 | + //ARM doesn't have __HAVE_ARCH_STRSTR, so search manually |
||
68 | + ptr = str - 1; |
||
69 | + |
||
70 | + do { |
||
71 | + //first find an 'r' at the begining or after a space |
||
72 | + do { |
||
73 | + ptr++; |
||
74 | + ptr = strchr(ptr, 'r'); |
||
75 | + if(!ptr) return dest; |
||
76 | + |
||
77 | + } while (ptr != str && *(ptr-1) != ' '); |
||
78 | + |
||
79 | + //then check for the rest |
||
80 | + for(i = 1; i <= 4; i++) |
||
81 | + if(*(ptr+i) != *(root+i)) break; |
||
82 | + |
||
83 | + } while (i != 5); |
||
84 | + |
||
85 | + end = strchr(ptr, ' '); |
||
86 | + end = end ? (end - 1) : (strchr(ptr, 0) - 1); |
||
87 | + |
||
88 | + //find partition number (assumes format root=/dev/mtdXX | /dev/mtdblockXX | yy:XX ) |
||
89 | + for( i = 0; end >= ptr && *end >= '0' && *end <= '9'; end--, i++); |
||
90 | + ptr = end + 1; |
||
91 | + |
||
92 | + /* if append-rootblock property is set use it to append to command line */ |
||
93 | + rootblock = getprop(fdt, "/chosen", "append-rootblock", &l); |
||
94 | + if(rootblock != NULL) { |
||
95 | + if(*dest != ' ') { |
||
96 | + *dest = ' '; |
||
97 | + dest++; |
||
98 | + len++; |
||
99 | + } |
||
100 | + if (len + l + i <= COMMAND_LINE_SIZE) { |
||
101 | + memcpy(dest, rootblock, l); |
||
102 | + dest += l - 1; |
||
103 | + memcpy(dest, ptr, i); |
||
104 | + dest += i; |
||
105 | + } |
||
106 | + } |
||
107 | + return dest; |
||
108 | +} |
||
109 | +#endif |
||
110 | + |
||
111 | static void merge_fdt_bootargs(void *fdt, const char *fdt_cmdline) |
||
112 | { |
||
113 | char cmdline[COMMAND_LINE_SIZE]; |
||
114 | @@ -86,12 +141,21 @@ static void merge_fdt_bootargs(void *fdt |
||
115 | |||
116 | /* and append the ATAG_CMDLINE */ |
||
117 | if (fdt_cmdline) { |
||
118 | + |
||
119 | +#if defined(CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE) |
||
120 | + //save original bootloader args |
||
121 | + //and append ubi.mtd with root partition number to current cmdline |
||
122 | + setprop_string(fdt, "/chosen", "bootloader-args", fdt_cmdline); |
||
123 | + ptr = append_rootblock(ptr, fdt_cmdline, len, fdt); |
||
124 | + |
||
125 | +#else |
||
126 | len = strlen(fdt_cmdline); |
||
127 | if (ptr - cmdline + len + 2 < COMMAND_LINE_SIZE) { |
||
128 | *ptr++ = ' '; |
||
129 | memcpy(ptr, fdt_cmdline, len); |
||
130 | ptr += len; |
||
131 | } |
||
132 | +#endif |
||
133 | } |
||
134 | *ptr = '\0'; |
||
135 | |||
136 | @@ -148,7 +212,9 @@ int atags_to_fdt(void *atag_list, void * |
||
137 | else |
||
138 | setprop_string(fdt, "/chosen", "bootargs", |
||
139 | atag->u.cmdline.cmdline); |
||
140 | - } else if (atag->hdr.tag == ATAG_MEM) { |
||
141 | + } |
||
142 | +#ifndef CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE |
||
143 | + else if (atag->hdr.tag == ATAG_MEM) { |
||
144 | if (memcount >= sizeof(mem_reg_property)/4) |
||
145 | continue; |
||
146 | if (!atag->u.mem.size) |
||
147 | @@ -187,6 +253,10 @@ int atags_to_fdt(void *atag_list, void * |
||
148 | setprop(fdt, "/memory", "reg", mem_reg_property, |
||
149 | 4 * memcount * memsize); |
||
150 | } |
||
151 | +#else |
||
152 | + |
||
153 | + } |
||
154 | +#endif |
||
155 | |||
156 | return fdt_pack(fdt); |
||
157 | } |
||
158 | --- a/init/main.c |
||
159 | +++ b/init/main.c |
||
160 | @@ -95,6 +95,10 @@ |
||
161 | #include <asm/sections.h> |
||
162 | #include <asm/cacheflush.h> |
||
163 | |||
164 | +#if defined(CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE) |
||
165 | +#include <linux/of.h> |
||
166 | +#endif |
||
167 | + |
||
168 | static int kernel_init(void *); |
||
169 | |||
170 | extern void init_IRQ(void); |
||
171 | @@ -574,6 +578,18 @@ asmlinkage __visible void __init start_k |
||
172 | page_alloc_init(); |
||
173 | |||
174 | pr_notice("Kernel command line: %s\n", boot_command_line); |
||
175 | + |
||
176 | +#if defined(CONFIG_ARM_ATAG_DTB_COMPAT_CMDLINE_MANGLE) |
||
177 | + //Show bootloader's original command line for reference |
||
178 | + if(of_chosen) { |
||
179 | + const char *prop = of_get_property(of_chosen, "bootloader-args", NULL); |
||
180 | + if(prop) |
||
181 | + pr_notice("Bootloader command line (ignored): %s\n", prop); |
||
182 | + else |
||
183 | + pr_notice("Bootloader command line not present\n"); |
||
184 | + } |
||
185 | +#endif |
||
186 | + |
||
187 | parse_early_param(); |
||
188 | after_dashes = parse_args("Booting kernel", |
||
189 | static_command_line, __start___param, |