aboutsummaryrefslogtreecommitdiffstats
path: root/arch/s390/kernel/early.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/s390/kernel/early.c')
-rw-r--r--arch/s390/kernel/early.c74
1 files changed, 46 insertions, 28 deletions
diff --git a/arch/s390/kernel/early.c b/arch/s390/kernel/early.c
index cae14c499511..bf8b4ae7ff2d 100644
--- a/arch/s390/kernel/early.c
+++ b/arch/s390/kernel/early.c
@@ -6,6 +6,9 @@
6 * Heiko Carstens <heiko.carstens@de.ibm.com> 6 * Heiko Carstens <heiko.carstens@de.ibm.com>
7 */ 7 */
8 8
9#define KMSG_COMPONENT "setup"
10#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt
11
9#include <linux/compiler.h> 12#include <linux/compiler.h>
10#include <linux/init.h> 13#include <linux/init.h>
11#include <linux/errno.h> 14#include <linux/errno.h>
@@ -16,6 +19,7 @@
16#include <linux/module.h> 19#include <linux/module.h>
17#include <linux/pfn.h> 20#include <linux/pfn.h>
18#include <linux/uaccess.h> 21#include <linux/uaccess.h>
22#include <linux/kernel.h>
19#include <asm/ebcdic.h> 23#include <asm/ebcdic.h>
20#include <asm/ipl.h> 24#include <asm/ipl.h>
21#include <asm/lowcore.h> 25#include <asm/lowcore.h>
@@ -35,8 +39,6 @@
35 39
36char kernel_nss_name[NSS_NAME_SIZE + 1]; 40char kernel_nss_name[NSS_NAME_SIZE + 1];
37 41
38static unsigned long machine_flags;
39
40static void __init setup_boot_command_line(void); 42static void __init setup_boot_command_line(void);
41 43
42/* 44/*
@@ -81,6 +83,8 @@ asm(
81 " br 14\n" 83 " br 14\n"
82 " .size savesys_ipl_nss, .-savesys_ipl_nss\n"); 84 " .size savesys_ipl_nss, .-savesys_ipl_nss\n");
83 85
86static __initdata char upper_command_line[COMMAND_LINE_SIZE];
87
84static noinline __init void create_kernel_nss(void) 88static noinline __init void create_kernel_nss(void)
85{ 89{
86 unsigned int i, stext_pfn, eshared_pfn, end_pfn, min_size; 90 unsigned int i, stext_pfn, eshared_pfn, end_pfn, min_size;
@@ -90,7 +94,6 @@ static noinline __init void create_kernel_nss(void)
90 int response; 94 int response;
91 size_t len; 95 size_t len;
92 char *savesys_ptr; 96 char *savesys_ptr;
93 char upper_command_line[COMMAND_LINE_SIZE];
94 char defsys_cmd[DEFSYS_CMD_SIZE]; 97 char defsys_cmd[DEFSYS_CMD_SIZE];
95 char savesys_cmd[SAVESYS_CMD_SIZE]; 98 char savesys_cmd[SAVESYS_CMD_SIZE];
96 99
@@ -141,6 +144,8 @@ static noinline __init void create_kernel_nss(void)
141 __cpcmd(defsys_cmd, NULL, 0, &response); 144 __cpcmd(defsys_cmd, NULL, 0, &response);
142 145
143 if (response != 0) { 146 if (response != 0) {
147 pr_err("Defining the Linux kernel NSS failed with rc=%d\n",
148 response);
144 kernel_nss_name[0] = '\0'; 149 kernel_nss_name[0] = '\0';
145 return; 150 return;
146 } 151 }
@@ -153,8 +158,11 @@ static noinline __init void create_kernel_nss(void)
153 * max SAVESYS_CMD_SIZE 158 * max SAVESYS_CMD_SIZE
154 * On error: response contains the numeric portion of cp error message. 159 * On error: response contains the numeric portion of cp error message.
155 * for SAVESYS it will be >= 263 160 * for SAVESYS it will be >= 263
161 * for missing privilege class, it will be 1
156 */ 162 */
157 if (response > SAVESYS_CMD_SIZE) { 163 if (response > SAVESYS_CMD_SIZE || response == 1) {
164 pr_err("Saving the Linux kernel NSS failed with rc=%d\n",
165 response);
158 kernel_nss_name[0] = '\0'; 166 kernel_nss_name[0] = '\0';
159 return; 167 return;
160 } 168 }
@@ -205,12 +213,9 @@ static noinline __init void detect_machine_type(void)
205 213
206 /* Running under KVM? If not we assume z/VM */ 214 /* Running under KVM? If not we assume z/VM */
207 if (!memcmp(vmms.vm[0].cpi, "\xd2\xe5\xd4", 3)) 215 if (!memcmp(vmms.vm[0].cpi, "\xd2\xe5\xd4", 3))
208 machine_flags |= MACHINE_FLAG_KVM; 216 S390_lowcore.machine_flags |= MACHINE_FLAG_KVM;
209 else 217 else
210 machine_flags |= MACHINE_FLAG_VM; 218 S390_lowcore.machine_flags |= MACHINE_FLAG_VM;
211
212 /* Store machine flags for setting up lowcore early */
213 S390_lowcore.machine_flags = machine_flags;
214} 219}
215 220
216static __init void early_pgm_check_handler(void) 221static __init void early_pgm_check_handler(void)
@@ -245,7 +250,7 @@ static noinline __init void setup_hpage(void)
245 facilities = stfl(); 250 facilities = stfl();
246 if (!(facilities & (1UL << 23)) || !(facilities & (1UL << 29))) 251 if (!(facilities & (1UL << 23)) || !(facilities & (1UL << 29)))
247 return; 252 return;
248 machine_flags |= MACHINE_FLAG_HPAGE; 253 S390_lowcore.machine_flags |= MACHINE_FLAG_HPAGE;
249 __ctl_set_bit(0, 23); 254 __ctl_set_bit(0, 23);
250#endif 255#endif
251} 256}
@@ -263,7 +268,7 @@ static __init void detect_mvpg(void)
263 EX_TABLE(0b,1b) 268 EX_TABLE(0b,1b)
264 : "=d" (rc) : "0" (-EOPNOTSUPP), "a" (0) : "memory", "cc", "0"); 269 : "=d" (rc) : "0" (-EOPNOTSUPP), "a" (0) : "memory", "cc", "0");
265 if (!rc) 270 if (!rc)
266 machine_flags |= MACHINE_FLAG_MVPG; 271 S390_lowcore.machine_flags |= MACHINE_FLAG_MVPG;
267#endif 272#endif
268} 273}
269 274
@@ -279,7 +284,7 @@ static __init void detect_ieee(void)
279 EX_TABLE(0b,1b) 284 EX_TABLE(0b,1b)
280 : "=d" (rc), "=d" (tmp): "0" (-EOPNOTSUPP) : "cc"); 285 : "=d" (rc), "=d" (tmp): "0" (-EOPNOTSUPP) : "cc");
281 if (!rc) 286 if (!rc)
282 machine_flags |= MACHINE_FLAG_IEEE; 287 S390_lowcore.machine_flags |= MACHINE_FLAG_IEEE;
283#endif 288#endif
284} 289}
285 290
@@ -298,7 +303,7 @@ static __init void detect_csp(void)
298 EX_TABLE(0b,1b) 303 EX_TABLE(0b,1b)
299 : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc", "0", "1", "2"); 304 : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc", "0", "1", "2");
300 if (!rc) 305 if (!rc)
301 machine_flags |= MACHINE_FLAG_CSP; 306 S390_lowcore.machine_flags |= MACHINE_FLAG_CSP;
302#endif 307#endif
303} 308}
304 309
@@ -315,7 +320,7 @@ static __init void detect_diag9c(void)
315 EX_TABLE(0b,1b) 320 EX_TABLE(0b,1b)
316 : "=d" (rc) : "0" (-EOPNOTSUPP), "d" (cpu_address) : "cc"); 321 : "=d" (rc) : "0" (-EOPNOTSUPP), "d" (cpu_address) : "cc");
317 if (!rc) 322 if (!rc)
318 machine_flags |= MACHINE_FLAG_DIAG9C; 323 S390_lowcore.machine_flags |= MACHINE_FLAG_DIAG9C;
319} 324}
320 325
321static __init void detect_diag44(void) 326static __init void detect_diag44(void)
@@ -330,7 +335,7 @@ static __init void detect_diag44(void)
330 EX_TABLE(0b,1b) 335 EX_TABLE(0b,1b)
331 : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc"); 336 : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc");
332 if (!rc) 337 if (!rc)
333 machine_flags |= MACHINE_FLAG_DIAG44; 338 S390_lowcore.machine_flags |= MACHINE_FLAG_DIAG44;
334#endif 339#endif
335} 340}
336 341
@@ -341,11 +346,11 @@ static __init void detect_machine_facilities(void)
341 346
342 facilities = stfl(); 347 facilities = stfl();
343 if (facilities & (1 << 28)) 348 if (facilities & (1 << 28))
344 machine_flags |= MACHINE_FLAG_IDTE; 349 S390_lowcore.machine_flags |= MACHINE_FLAG_IDTE;
345 if (facilities & (1 << 23)) 350 if (facilities & (1 << 23))
346 machine_flags |= MACHINE_FLAG_PFMF; 351 S390_lowcore.machine_flags |= MACHINE_FLAG_PFMF;
347 if (facilities & (1 << 4)) 352 if (facilities & (1 << 4))
348 machine_flags |= MACHINE_FLAG_MVCOS; 353 S390_lowcore.machine_flags |= MACHINE_FLAG_MVCOS;
349#endif 354#endif
350} 355}
351 356
@@ -367,21 +372,35 @@ static __init void rescue_initrd(void)
367} 372}
368 373
369/* Set up boot command line */ 374/* Set up boot command line */
370static void __init setup_boot_command_line(void) 375static void __init append_to_cmdline(size_t (*ipl_data)(char *, size_t))
371{ 376{
372 char *parm = NULL; 377 char *parm, *delim;
378 size_t rc, len;
379
380 len = strlen(boot_command_line);
381
382 delim = boot_command_line + len; /* '\0' character position */
383 parm = boot_command_line + len + 1; /* append right after '\0' */
373 384
385 rc = ipl_data(parm, COMMAND_LINE_SIZE - len - 1);
386 if (rc) {
387 if (*parm == '=')
388 memmove(boot_command_line, parm + 1, rc);
389 else
390 *delim = ' '; /* replace '\0' with space */
391 }
392}
393
394static void __init setup_boot_command_line(void)
395{
374 /* copy arch command line */ 396 /* copy arch command line */
375 strlcpy(boot_command_line, COMMAND_LINE, ARCH_COMMAND_LINE_SIZE); 397 strlcpy(boot_command_line, COMMAND_LINE, ARCH_COMMAND_LINE_SIZE);
376 398
377 /* append IPL PARM data to the boot command line */ 399 /* append IPL PARM data to the boot command line */
378 if (MACHINE_IS_VM) { 400 if (MACHINE_IS_VM)
379 parm = boot_command_line + strlen(boot_command_line); 401 append_to_cmdline(append_ipl_vmparm);
380 *parm++ = ' '; 402
381 get_ipl_vmparm(parm); 403 append_to_cmdline(append_ipl_scpdata);
382 if (parm[0] == '=')
383 memmove(boot_command_line, parm + 1, strlen(parm));
384 }
385} 404}
386 405
387 406
@@ -413,7 +432,6 @@ void __init startup_init(void)
413 setup_hpage(); 432 setup_hpage();
414 sclp_facilities_detect(); 433 sclp_facilities_detect();
415 detect_memory_layout(memory_chunk); 434 detect_memory_layout(memory_chunk);
416 S390_lowcore.machine_flags = machine_flags;
417#ifdef CONFIG_DYNAMIC_FTRACE 435#ifdef CONFIG_DYNAMIC_FTRACE
418 S390_lowcore.ftrace_func = (unsigned long)ftrace_caller; 436 S390_lowcore.ftrace_func = (unsigned long)ftrace_caller;
419#endif 437#endif