diff options
| author | Heiko Carstens <heiko.carstens@de.ibm.com> | 2011-11-14 05:19:08 -0500 |
|---|---|---|
| committer | Martin Schwidefsky <schwidefsky@de.ibm.com> | 2011-11-14 05:19:09 -0500 |
| commit | f6bf1a8acd2cb3a92a7b7c9ab03e56a32ac5ece5 (patch) | |
| tree | 1917e79c8e0181248537c2a2fb03343b4fd6449b | |
| parent | 6ed54387dc470fc439cb154724a1ac81d251c126 (diff) | |
[S390] topology: fix topology on z10 machines
Make sure that all cpus in a book on a z10 appear as book siblings
and not as core siblings. This fixes some performance regressions that
appeared after the book scheduling domain got introduced.
Signed-off-by: Heiko Carstens <heiko.carstens@de.ibm.com>
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
| -rw-r--r-- | arch/s390/kernel/topology.c | 45 |
1 files changed, 38 insertions, 7 deletions
diff --git a/arch/s390/kernel/topology.c b/arch/s390/kernel/topology.c index 77b8942b9a15..fdb5b8cb260f 100644 --- a/arch/s390/kernel/topology.c +++ b/arch/s390/kernel/topology.c | |||
| @@ -68,8 +68,10 @@ static cpumask_t cpu_group_map(struct mask_info *info, unsigned int cpu) | |||
| 68 | return mask; | 68 | return mask; |
| 69 | } | 69 | } |
| 70 | 70 | ||
| 71 | static void add_cpus_to_mask(struct topology_cpu *tl_cpu, | 71 | static struct mask_info *add_cpus_to_mask(struct topology_cpu *tl_cpu, |
| 72 | struct mask_info *book, struct mask_info *core) | 72 | struct mask_info *book, |
| 73 | struct mask_info *core, | ||
| 74 | int z10) | ||
| 73 | { | 75 | { |
| 74 | unsigned int cpu; | 76 | unsigned int cpu; |
| 75 | 77 | ||
| @@ -88,10 +90,16 @@ static void add_cpus_to_mask(struct topology_cpu *tl_cpu, | |||
| 88 | cpu_book_id[lcpu] = book->id; | 90 | cpu_book_id[lcpu] = book->id; |
| 89 | #endif | 91 | #endif |
| 90 | cpumask_set_cpu(lcpu, &core->mask); | 92 | cpumask_set_cpu(lcpu, &core->mask); |
| 91 | cpu_core_id[lcpu] = core->id; | 93 | if (z10) { |
| 94 | cpu_core_id[lcpu] = rcpu; | ||
| 95 | core = core->next; | ||
| 96 | } else { | ||
| 97 | cpu_core_id[lcpu] = core->id; | ||
| 98 | } | ||
| 92 | smp_cpu_polarization[lcpu] = tl_cpu->pp; | 99 | smp_cpu_polarization[lcpu] = tl_cpu->pp; |
| 93 | } | 100 | } |
| 94 | } | 101 | } |
| 102 | return core; | ||
| 95 | } | 103 | } |
| 96 | 104 | ||
| 97 | static void clear_masks(void) | 105 | static void clear_masks(void) |
| @@ -123,18 +131,41 @@ static void tl_to_cores(struct sysinfo_15_1_x *info) | |||
| 123 | { | 131 | { |
| 124 | #ifdef CONFIG_SCHED_BOOK | 132 | #ifdef CONFIG_SCHED_BOOK |
| 125 | struct mask_info *book = &book_info; | 133 | struct mask_info *book = &book_info; |
| 134 | struct cpuid cpu_id; | ||
| 126 | #else | 135 | #else |
| 127 | struct mask_info *book = NULL; | 136 | struct mask_info *book = NULL; |
| 128 | #endif | 137 | #endif |
| 129 | struct mask_info *core = &core_info; | 138 | struct mask_info *core = &core_info; |
| 130 | union topology_entry *tle, *end; | 139 | union topology_entry *tle, *end; |
| 140 | int z10 = 0; | ||
| 131 | 141 | ||
| 132 | 142 | #ifdef CONFIG_SCHED_BOOK | |
| 143 | get_cpu_id(&cpu_id); | ||
| 144 | z10 = cpu_id.machine == 0x2097 || cpu_id.machine == 0x2098; | ||
| 145 | #endif | ||
| 133 | spin_lock_irq(&topology_lock); | 146 | spin_lock_irq(&topology_lock); |
| 134 | clear_masks(); | 147 | clear_masks(); |
| 135 | tle = info->tle; | 148 | tle = info->tle; |
| 136 | end = (union topology_entry *)((unsigned long)info + info->length); | 149 | end = (union topology_entry *)((unsigned long)info + info->length); |
| 137 | while (tle < end) { | 150 | while (tle < end) { |
| 151 | #ifdef CONFIG_SCHED_BOOK | ||
| 152 | if (z10) { | ||
| 153 | switch (tle->nl) { | ||
| 154 | case 1: | ||
| 155 | book = book->next; | ||
| 156 | book->id = tle->container.id; | ||
| 157 | break; | ||
| 158 | case 0: | ||
| 159 | core = add_cpus_to_mask(&tle->cpu, book, core, z10); | ||
| 160 | break; | ||
| 161 | default: | ||
| 162 | clear_masks(); | ||
| 163 | goto out; | ||
| 164 | } | ||
| 165 | tle = next_tle(tle); | ||
| 166 | continue; | ||
| 167 | } | ||
| 168 | #endif | ||
| 138 | switch (tle->nl) { | 169 | switch (tle->nl) { |
| 139 | #ifdef CONFIG_SCHED_BOOK | 170 | #ifdef CONFIG_SCHED_BOOK |
| 140 | case 2: | 171 | case 2: |
| @@ -147,7 +178,7 @@ static void tl_to_cores(struct sysinfo_15_1_x *info) | |||
| 147 | core->id = tle->container.id; | 178 | core->id = tle->container.id; |
| 148 | break; | 179 | break; |
| 149 | case 0: | 180 | case 0: |
| 150 | add_cpus_to_mask(&tle->cpu, book, core); | 181 | add_cpus_to_mask(&tle->cpu, book, core, z10); |
| 151 | break; | 182 | break; |
| 152 | default: | 183 | default: |
| 153 | clear_masks(); | 184 | clear_masks(); |
| @@ -328,8 +359,8 @@ void __init s390_init_cpu_topology(void) | |||
| 328 | for (i = 0; i < TOPOLOGY_NR_MAG; i++) | 359 | for (i = 0; i < TOPOLOGY_NR_MAG; i++) |
| 329 | printk(" %d", info->mag[i]); | 360 | printk(" %d", info->mag[i]); |
| 330 | printk(" / %d\n", info->mnest); | 361 | printk(" / %d\n", info->mnest); |
| 331 | alloc_masks(info, &core_info, 2); | 362 | alloc_masks(info, &core_info, 1); |
| 332 | #ifdef CONFIG_SCHED_BOOK | 363 | #ifdef CONFIG_SCHED_BOOK |
| 333 | alloc_masks(info, &book_info, 3); | 364 | alloc_masks(info, &book_info, 2); |
| 334 | #endif | 365 | #endif |
| 335 | } | 366 | } |
