Skip to content

Commit

Permalink
Merge branch 'irq-urgent-for-linus' of git://git.kernel.org/pub/scm/l…
Browse files Browse the repository at this point in the history
…inux/kernel/git/tip/tip

Pull irq fixes from Thomas Gleixner:
 "The irq department provides:

   - two fixes for the CPU affinity spread infrastructure to prevent
     unbalanced spreading in corner cases which leads to horrible
     performance, because interrupts are rather aggregated than spread

   - add a missing spinlock initializer in the imx-gpcv2 init code"

* 'irq-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
  irqchip/irq-imx-gpcv2: Fix spinlock initialization
  irq/affinity: Fix extra vecs calculation
  irq/affinity: Fix CPU spread for unbalanced nodes
  • Loading branch information
Linus Torvalds committed Apr 14, 2017
2 parents f399ecb + 75eb5e1 commit d295917
Show file tree
Hide file tree
Showing 2 changed files with 13 additions and 9 deletions.
2 changes: 2 additions & 0 deletions drivers/irqchip/irq-imx-gpcv2.c
Original file line number Diff line number Diff line change
Expand Up @@ -230,6 +230,8 @@ static int __init imx_gpcv2_irqchip_init(struct device_node *node,
return -ENOMEM;
}

raw_spin_lock_init(&cd->rlock);

cd->gpc_base = of_iomap(node, 0);
if (!cd->gpc_base) {
pr_err("fsl-gpcv2: unable to map gpc registers\n");
Expand Down
20 changes: 11 additions & 9 deletions kernel/irq/affinity.c
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ static int get_nodes_in_cpumask(const struct cpumask *mask, nodemask_t *nodemsk)
struct cpumask *
irq_create_affinity_masks(int nvecs, const struct irq_affinity *affd)
{
int n, nodes, vecs_per_node, cpus_per_vec, extra_vecs, curvec;
int n, nodes, cpus_per_vec, extra_vecs, curvec;
int affv = nvecs - affd->pre_vectors - affd->post_vectors;
int last_affv = affv + affd->pre_vectors;
nodemask_t nodemsk = NODE_MASK_NONE;
Expand Down Expand Up @@ -94,19 +94,21 @@ irq_create_affinity_masks(int nvecs, const struct irq_affinity *affd)
goto done;
}

/* Spread the vectors per node */
vecs_per_node = affv / nodes;
/* Account for rounding errors */
extra_vecs = affv - (nodes * vecs_per_node);

for_each_node_mask(n, nodemsk) {
int ncpus, v, vecs_to_assign = vecs_per_node;
int ncpus, v, vecs_to_assign, vecs_per_node;

/* Spread the vectors per node */
vecs_per_node = (affv - curvec) / nodes;

/* Get the cpus on this node which are in the mask */
cpumask_and(nmsk, cpu_online_mask, cpumask_of_node(n));

/* Calculate the number of cpus per vector */
ncpus = cpumask_weight(nmsk);
vecs_to_assign = min(vecs_per_node, ncpus);

/* Account for rounding errors */
extra_vecs = ncpus - vecs_to_assign * (ncpus / vecs_to_assign);

for (v = 0; curvec < last_affv && v < vecs_to_assign;
curvec++, v++) {
Expand All @@ -115,14 +117,14 @@ irq_create_affinity_masks(int nvecs, const struct irq_affinity *affd)
/* Account for extra vectors to compensate rounding errors */
if (extra_vecs) {
cpus_per_vec++;
if (!--extra_vecs)
vecs_per_node++;
--extra_vecs;
}
irq_spread_init_one(masks + curvec, nmsk, cpus_per_vec);
}

if (curvec >= last_affv)
break;
--nodes;
}

done:
Expand Down

0 comments on commit d295917

Please sign in to comment.