s390/smp: fix ipl from cpu with non-zero address
Commitaf51160ebd
("s390/smp: initialize cpu_present_mask in setup_arch") initializes the cpu_present_mask much earlier than before. However the cpu detection code relies on the fact that iff logical cpu 0 is marked present then also the corresponding physical cpu address within the pcpu_devices array slot is valid. Since commit44fd22992c
("[PATCH] Register the boot-cpu in the cpu maps earlier") this assumption is not true anymore. The patch marks logical cpu 0 as present in common code without that architecture code had a chance to setup the logical to physical map. With that change the cpu detection code assumes that the physical cpu address of cpu 0 is also 0, which is not necessarily true. Subsequently the physical cpu address of the ipl cpu will be mapped to a different logical cpu. If that cpu is brought online later the ipl cpu will send itself an initial cpu reset sigp signal. This in turn completely resets the ipl cpu and the system stops working. A dump of such a system looks like a "store status" has been forgotten. But actually the kernel itself removed all traces which would allow to easily tell what went wrong. To fix this initialize the logical to physical cpu address already in smp_setup_processor_id(). In addition remove the initialization of the cpu_present_mask and cpu_online_mask for cpu 0, since that has already been done. Also add a sanity check, just in case common code will be changed again... The problem can be easily reproduced within a z/VM guest: > chcpu -d 0 > vmcp ipl Fixes:af51160ebd
("s390/smp: initialize cpu_present_mask in setup_arch") Reported-by: Sebastian Ott <sebott@linux.vnet.ibm.com> Signed-off-by: Heiko Carstens <heiko.carstens@de.ibm.com> Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
This commit is contained in:
Родитель
d82c0d12c9
Коммит
0861b5a754
|
@ -909,13 +909,11 @@ void __init smp_prepare_boot_cpu(void)
|
|||
{
|
||||
struct pcpu *pcpu = pcpu_devices;
|
||||
|
||||
WARN_ON(!cpu_present(0) || !cpu_online(0));
|
||||
pcpu->state = CPU_STATE_CONFIGURED;
|
||||
pcpu->address = stap();
|
||||
pcpu->lowcore = (struct lowcore *)(unsigned long) store_prefix();
|
||||
S390_lowcore.percpu_offset = __per_cpu_offset[0];
|
||||
smp_cpu_set_polarization(0, POLARIZATION_UNKNOWN);
|
||||
set_cpu_present(0, true);
|
||||
set_cpu_online(0, true);
|
||||
}
|
||||
|
||||
void __init smp_cpus_done(unsigned int max_cpus)
|
||||
|
@ -924,6 +922,7 @@ void __init smp_cpus_done(unsigned int max_cpus)
|
|||
|
||||
void __init smp_setup_processor_id(void)
|
||||
{
|
||||
pcpu_devices[0].address = stap();
|
||||
S390_lowcore.cpu_nr = 0;
|
||||
S390_lowcore.spinlock_lockval = arch_spin_lockval(0);
|
||||
}
|
||||
|
|
Загрузка…
Ссылка в новой задаче