diff options
Diffstat (limited to 'arch/s390/kernel/early.c')
-rw-r--r-- | arch/s390/kernel/early.c | 125 |
1 files changed, 122 insertions, 3 deletions
diff --git a/arch/s390/kernel/early.c b/arch/s390/kernel/early.c index 68ec4083bf73..d0e09684b9ce 100644 --- a/arch/s390/kernel/early.c +++ b/arch/s390/kernel/early.c | |||
@@ -139,15 +139,15 @@ static noinline __init void detect_machine_type(void) | |||
139 | 139 | ||
140 | /* Running under z/VM ? */ | 140 | /* Running under z/VM ? */ |
141 | if (cpuinfo->cpu_id.version == 0xff) | 141 | if (cpuinfo->cpu_id.version == 0xff) |
142 | machine_flags |= 1; | 142 | machine_flags |= MACHINE_FLAG_VM; |
143 | 143 | ||
144 | /* Running on a P/390 ? */ | 144 | /* Running on a P/390 ? */ |
145 | if (cpuinfo->cpu_id.machine == 0x7490) | 145 | if (cpuinfo->cpu_id.machine == 0x7490) |
146 | machine_flags |= 4; | 146 | machine_flags |= MACHINE_FLAG_P390; |
147 | 147 | ||
148 | /* Running under KVM ? */ | 148 | /* Running under KVM ? */ |
149 | if (cpuinfo->cpu_id.version == 0xfe) | 149 | if (cpuinfo->cpu_id.version == 0xfe) |
150 | machine_flags |= 64; | 150 | machine_flags |= MACHINE_FLAG_KVM; |
151 | } | 151 | } |
152 | 152 | ||
153 | #ifdef CONFIG_64BIT | 153 | #ifdef CONFIG_64BIT |
@@ -268,6 +268,118 @@ static noinline __init void setup_lowcore_early(void) | |||
268 | s390_base_pgm_handler_fn = early_pgm_check_handler; | 268 | s390_base_pgm_handler_fn = early_pgm_check_handler; |
269 | } | 269 | } |
270 | 270 | ||
271 | static noinline __init void setup_hpage(void) | ||
272 | { | ||
273 | #ifndef CONFIG_DEBUG_PAGEALLOC | ||
274 | unsigned int facilities; | ||
275 | |||
276 | facilities = stfl(); | ||
277 | if (!(facilities & (1UL << 23)) || !(facilities & (1UL << 29))) | ||
278 | return; | ||
279 | machine_flags |= MACHINE_FLAG_HPAGE; | ||
280 | __ctl_set_bit(0, 23); | ||
281 | #endif | ||
282 | } | ||
283 | |||
284 | static __init void detect_mvpg(void) | ||
285 | { | ||
286 | #ifndef CONFIG_64BIT | ||
287 | int rc; | ||
288 | |||
289 | asm volatile( | ||
290 | " la 0,0\n" | ||
291 | " mvpg %2,%2\n" | ||
292 | "0: la %0,0\n" | ||
293 | "1:\n" | ||
294 | EX_TABLE(0b,1b) | ||
295 | : "=d" (rc) : "0" (-EOPNOTSUPP), "a" (0) : "memory", "cc", "0"); | ||
296 | if (!rc) | ||
297 | machine_flags |= MACHINE_FLAG_MVPG; | ||
298 | #endif | ||
299 | } | ||
300 | |||
301 | static __init void detect_ieee(void) | ||
302 | { | ||
303 | #ifndef CONFIG_64BIT | ||
304 | int rc, tmp; | ||
305 | |||
306 | asm volatile( | ||
307 | " efpc %1,0\n" | ||
308 | "0: la %0,0\n" | ||
309 | "1:\n" | ||
310 | EX_TABLE(0b,1b) | ||
311 | : "=d" (rc), "=d" (tmp): "0" (-EOPNOTSUPP) : "cc"); | ||
312 | if (!rc) | ||
313 | machine_flags |= MACHINE_FLAG_IEEE; | ||
314 | #endif | ||
315 | } | ||
316 | |||
317 | static __init void detect_csp(void) | ||
318 | { | ||
319 | #ifndef CONFIG_64BIT | ||
320 | int rc; | ||
321 | |||
322 | asm volatile( | ||
323 | " la 0,0\n" | ||
324 | " la 1,0\n" | ||
325 | " la 2,4\n" | ||
326 | " csp 0,2\n" | ||
327 | "0: la %0,0\n" | ||
328 | "1:\n" | ||
329 | EX_TABLE(0b,1b) | ||
330 | : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc", "0", "1", "2"); | ||
331 | if (!rc) | ||
332 | machine_flags |= MACHINE_FLAG_CSP; | ||
333 | #endif | ||
334 | } | ||
335 | |||
336 | static __init void detect_diag9c(void) | ||
337 | { | ||
338 | unsigned int cpu_address; | ||
339 | int rc; | ||
340 | |||
341 | cpu_address = stap(); | ||
342 | asm volatile( | ||
343 | " diag %2,0,0x9c\n" | ||
344 | "0: la %0,0\n" | ||
345 | "1:\n" | ||
346 | EX_TABLE(0b,1b) | ||
347 | : "=d" (rc) : "0" (-EOPNOTSUPP), "d" (cpu_address) : "cc"); | ||
348 | if (!rc) | ||
349 | machine_flags |= MACHINE_FLAG_DIAG9C; | ||
350 | } | ||
351 | |||
352 | static __init void detect_diag44(void) | ||
353 | { | ||
354 | #ifdef CONFIG_64BIT | ||
355 | int rc; | ||
356 | |||
357 | asm volatile( | ||
358 | " diag 0,0,0x44\n" | ||
359 | "0: la %0,0\n" | ||
360 | "1:\n" | ||
361 | EX_TABLE(0b,1b) | ||
362 | : "=d" (rc) : "0" (-EOPNOTSUPP) : "cc"); | ||
363 | if (!rc) | ||
364 | machine_flags |= MACHINE_FLAG_DIAG44; | ||
365 | #endif | ||
366 | } | ||
367 | |||
368 | static __init void detect_machine_facilities(void) | ||
369 | { | ||
370 | #ifdef CONFIG_64BIT | ||
371 | unsigned int facilities; | ||
372 | |||
373 | facilities = stfl(); | ||
374 | if (facilities & (1 << 28)) | ||
375 | machine_flags |= MACHINE_FLAG_IDTE; | ||
376 | if (facilities & (1 << 23)) | ||
377 | machine_flags |= MACHINE_FLAG_PFMF; | ||
378 | if (facilities & (1 << 4)) | ||
379 | machine_flags |= MACHINE_FLAG_MVCOS; | ||
380 | #endif | ||
381 | } | ||
382 | |||
271 | /* | 383 | /* |
272 | * Save ipl parameters, clear bss memory, initialize storage keys | 384 | * Save ipl parameters, clear bss memory, initialize storage keys |
273 | * and create a kernel NSS at startup if the SAVESYS= parm is defined | 385 | * and create a kernel NSS at startup if the SAVESYS= parm is defined |
@@ -285,6 +397,13 @@ void __init startup_init(void) | |||
285 | create_kernel_nss(); | 397 | create_kernel_nss(); |
286 | sort_main_extable(); | 398 | sort_main_extable(); |
287 | setup_lowcore_early(); | 399 | setup_lowcore_early(); |
400 | detect_mvpg(); | ||
401 | detect_ieee(); | ||
402 | detect_csp(); | ||
403 | detect_diag9c(); | ||
404 | detect_diag44(); | ||
405 | detect_machine_facilities(); | ||
406 | setup_hpage(); | ||
288 | sclp_read_info_early(); | 407 | sclp_read_info_early(); |
289 | sclp_facilities_detect(); | 408 | sclp_facilities_detect(); |
290 | memsize = sclp_memory_detect(); | 409 | memsize = sclp_memory_detect(); |