diff options
Diffstat (limited to 'kernel/irq/affinity.c')
-rw-r--r-- | kernel/irq/affinity.c | 16 |
1 files changed, 12 insertions, 4 deletions
diff --git a/kernel/irq/affinity.c b/kernel/irq/affinity.c index 82e8799374e9..278289c091bb 100644 --- a/kernel/irq/affinity.c +++ b/kernel/irq/affinity.c | |||
@@ -238,9 +238,10 @@ static int irq_build_affinity_masks(const struct irq_affinity *affd, | |||
238 | * Returns the irq_affinity_desc pointer or NULL if allocation failed. | 238 | * Returns the irq_affinity_desc pointer or NULL if allocation failed. |
239 | */ | 239 | */ |
240 | struct irq_affinity_desc * | 240 | struct irq_affinity_desc * |
241 | irq_create_affinity_masks(unsigned int nvecs, const struct irq_affinity *affd) | 241 | irq_create_affinity_masks(unsigned int nvecs, struct irq_affinity *affd) |
242 | { | 242 | { |
243 | unsigned int affvecs, curvec, usedvecs, nr_sets, i; | 243 | unsigned int affvecs, curvec, usedvecs, nr_sets, i; |
244 | unsigned int set_size[IRQ_AFFINITY_MAX_SETS]; | ||
244 | struct irq_affinity_desc *masks = NULL; | 245 | struct irq_affinity_desc *masks = NULL; |
245 | 246 | ||
246 | /* | 247 | /* |
@@ -250,6 +251,9 @@ irq_create_affinity_masks(unsigned int nvecs, const struct irq_affinity *affd) | |||
250 | if (nvecs == affd->pre_vectors + affd->post_vectors) | 251 | if (nvecs == affd->pre_vectors + affd->post_vectors) |
251 | return NULL; | 252 | return NULL; |
252 | 253 | ||
254 | if (WARN_ON_ONCE(affd->nr_sets > IRQ_AFFINITY_MAX_SETS)) | ||
255 | return NULL; | ||
256 | |||
253 | masks = kcalloc(nvecs, sizeof(*masks), GFP_KERNEL); | 257 | masks = kcalloc(nvecs, sizeof(*masks), GFP_KERNEL); |
254 | if (!masks) | 258 | if (!masks) |
255 | return NULL; | 259 | return NULL; |
@@ -263,11 +267,15 @@ irq_create_affinity_masks(unsigned int nvecs, const struct irq_affinity *affd) | |||
263 | */ | 267 | */ |
264 | affvecs = nvecs - affd->pre_vectors - affd->post_vectors; | 268 | affvecs = nvecs - affd->pre_vectors - affd->post_vectors; |
265 | nr_sets = affd->nr_sets; | 269 | nr_sets = affd->nr_sets; |
266 | if (!nr_sets) | 270 | if (!nr_sets) { |
267 | nr_sets = 1; | 271 | nr_sets = 1; |
272 | set_size[0] = affvecs; | ||
273 | } else { | ||
274 | memcpy(set_size, affd->set_size, nr_sets * sizeof(unsigned int)); | ||
275 | } | ||
268 | 276 | ||
269 | for (i = 0, usedvecs = 0; i < nr_sets; i++) { | 277 | for (i = 0, usedvecs = 0; i < nr_sets; i++) { |
270 | unsigned int this_vecs = affd->sets ? affd->sets[i] : affvecs; | 278 | unsigned int this_vecs = set_size[i]; |
271 | int ret; | 279 | int ret; |
272 | 280 | ||
273 | ret = irq_build_affinity_masks(affd, curvec, this_vecs, | 281 | ret = irq_build_affinity_masks(affd, curvec, this_vecs, |
@@ -314,7 +322,7 @@ unsigned int irq_calc_affinity_vectors(unsigned int minvec, unsigned int maxvec, | |||
314 | unsigned int i; | 322 | unsigned int i; |
315 | 323 | ||
316 | for (i = 0, set_vecs = 0; i < affd->nr_sets; i++) | 324 | for (i = 0, set_vecs = 0; i < affd->nr_sets; i++) |
317 | set_vecs += affd->sets[i]; | 325 | set_vecs += affd->set_size[i]; |
318 | } else { | 326 | } else { |
319 | get_online_cpus(); | 327 | get_online_cpus(); |
320 | set_vecs = cpumask_weight(cpu_possible_mask); | 328 | set_vecs = cpumask_weight(cpu_possible_mask); |