All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0/7] genirq/affinity: abstract new API from managed irq affinity spread
@ 2021-08-14 12:35 Ming Lei
  2021-08-14 12:35 ` [PATCH 1/7] genirq/affinity: remove the 'firstvec' parameter from irq_build_affinity_masks Ming Lei
                   ` (6 more replies)
  0 siblings, 7 replies; 31+ messages in thread
From: Ming Lei @ 2021-08-14 12:35 UTC (permalink / raw)
  To: Thomas Gleixner, Jens Axboe
  Cc: linux-kernel, linux-block, Christoph Hellwig, Ming Lei

Hello,

irq_build_affinity_masks() actually grouping CPUs evenly into each managed
irq vector according to NUMA and CPU locality, and it is reasonable to abstract
one generic API for grouping CPUs evenly, the idea is suggested by Thomas
Gleixner.

group_cpus_evenly() is abstracted and put into lib/, so blk-mq can re-use
it to build default queue mapping.

Please comments!

Since RFC:
	- remove RFC
	- rebase on -next tree


Ming Lei (7):
  genirq/affinity: remove the 'firstvec' parameter from
    irq_build_affinity_masks
  genirq/affinity: pass affinity managed mask array to
    irq_build_affinity_masks
  genirq/affinity: don't pass irq_affinity_desc array to
    irq_build_affinity_masks
  genirq/affinity: rename irq_build_affinity_masks as group_cpus_evenly
  genirq/affinity: move group_cpus_evenly() into lib/
  lib/group_cpus: allow to group cpus in case of !CONFIG_SMP
  blk-mq: build default queue map via group_cpus_evenly()

 block/blk-mq-cpumap.c      |  64 ++----
 include/linux/group_cpus.h |  28 +++
 kernel/irq/affinity.c      | 404 +-----------------------------------
 lib/Makefile               |   2 +
 lib/group_cpus.c           | 413 +++++++++++++++++++++++++++++++++++++
 5 files changed, 465 insertions(+), 446 deletions(-)
 create mode 100644 include/linux/group_cpus.h
 create mode 100644 lib/group_cpus.c

-- 
2.31.1


^ permalink raw reply	[flat|nested] 31+ messages in thread
* Re: [PATCH 5/7] genirq/affinity: move group_cpus_evenly() into lib/
@ 2021-08-15  1:49 kernel test robot
  2021-08-16 10:08   ` kernel test robot
  0 siblings, 1 reply; 31+ messages in thread
From: kernel test robot @ 2021-08-15  1:49 UTC (permalink / raw)
  To: kbuild

[-- Attachment #1: Type: text/plain, Size: 23674 bytes --]

CC: clang-built-linux(a)googlegroups.com
CC: kbuild-all(a)lists.01.org
In-Reply-To: <20210814123532.229494-6-ming.lei@redhat.com>
References: <20210814123532.229494-6-ming.lei@redhat.com>
TO: Ming Lei <ming.lei@redhat.com>
TO: Thomas Gleixner <tglx@linutronix.de>
TO: Jens Axboe <axboe@kernel.dk>
CC: linux-kernel(a)vger.kernel.org
CC: linux-block(a)vger.kernel.org
CC: Christoph Hellwig <hch@lst.de>
CC: Ming Lei <ming.lei@redhat.com>

Hi Ming,

Thank you for the patch! Perhaps something to improve:

[auto build test WARNING on tip/irq/core]
[also build test WARNING on next-20210813]
[cannot apply to block/for-next linux/master linus/master v5.14-rc5]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch]

url:    https://github.com/0day-ci/linux/commits/Ming-Lei/genirq-affinity-abstract-new-API-from-managed-irq-affinity-spread/20210814-203741
base:   https://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git 04c2721d3530f0723b4c922a8fa9f26b202a20de
:::::: branch date: 13 hours ago
:::::: commit date: 13 hours ago
config: x86_64-randconfig-c001-20210814 (attached as .config)
compiler: clang version 14.0.0 (https://github.com/llvm/llvm-project 1f7b25ea76a925aca690da28de9d78db7ca99d0c)
reproduce (this is a W=1 build):
        wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross
        chmod +x ~/bin/make.cross
        # install x86_64 cross compiling tool for clang build
        # apt-get install binutils-x86-64-linux-gnu
        # https://github.com/0day-ci/linux/commit/759f72186bfdd5c3ba8b53ac0749cf7ba930012c
        git remote add linux-review https://github.com/0day-ci/linux
        git fetch --no-tags linux-review Ming-Lei/genirq-affinity-abstract-new-API-from-managed-irq-affinity-spread/20210814-203741
        git checkout 759f72186bfdd5c3ba8b53ac0749cf7ba930012c
        # save the attached .config to linux build tree
        COMPILER_INSTALL_PATH=$HOME/0day COMPILER=clang make.cross ARCH=x86_64 clang-analyzer 

If you fix the issue, kindly add following tag as appropriate
Reported-by: kernel test robot <lkp@intel.com>


clang-analyzer warnings: (new ones prefixed by >>)
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
   Suppressed 7 warnings (6 in non-user code, 1 with check filters).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   5 warnings generated.
   Suppressed 5 warnings (5 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   5 warnings generated.
   Suppressed 5 warnings (5 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   5 warnings generated.
   Suppressed 5 warnings (5 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   5 warnings generated.
   Suppressed 5 warnings (5 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   3 warnings generated.
   Suppressed 3 warnings (3 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
   lib/glob.c:48:32: warning: Assigned value is garbage or undefined [clang-analyzer-core.uninitialized.Assign]
           char const *back_pat = NULL, *back_str = back_str;
                                         ^          ~~~~~~~~
   lib/glob.c:48:32: note: Assigned value is garbage or undefined
           char const *back_pat = NULL, *back_str = back_str;
                                         ^          ~~~~~~~~
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
   lib/strnlen_user.c:34:2: warning: Value stored to 'src' is never read [clang-analyzer-deadcode.DeadStores]
           src -= align;
           ^      ~~~~~
   lib/strnlen_user.c:34:2: note: Value stored to 'src' is never read
           src -= align;
           ^      ~~~~~
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
   Suppressed 7 warnings (7 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
   Suppressed 7 warnings (7 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   6 warnings generated.
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
   lib/oid_registry.c:149:3: warning: Value stored to 'num' is never read [clang-analyzer-deadcode.DeadStores]
                   num = 0;
                   ^     ~
   lib/oid_registry.c:149:3: note: Value stored to 'num' is never read
                   num = 0;
                   ^     ~
   Suppressed 6 warnings (6 in non-user code).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   9 warnings generated.
   Suppressed 9 warnings (2 in non-user code, 7 with check filters).
   Use -header-filter=.* to display errors from all non-system headers. Use -system-headers to display errors from system headers as well.
   7 warnings generated.
>> lib/group_cpus.c:236:22: warning: Division by zero [clang-analyzer-core.DivideZero]
                                    numgrps * ncpus / remaining_ncpus);
                                                    ^
   lib/group_cpus.c:352:2: note: Taking false branch
           if (!zalloc_cpumask_var(&nmsk, GFP_KERNEL))
           ^
   lib/group_cpus.c:355:2: note: Taking false branch
           if (!zalloc_cpumask_var(&npresmsk, GFP_KERNEL))
           ^
   lib/group_cpus.c:359:7: note: 'node_to_cpumask' is non-null
           if (!node_to_cpumask)
                ^~~~~~~~~~~~~~~
   lib/group_cpus.c:359:2: note: Taking false branch
           if (!node_to_cpumask)
           ^
   lib/group_cpus.c:363:6: note: Assuming 'masks' is non-null
           if (!masks)
               ^~~~~~
   lib/group_cpus.c:363:2: note: Taking false branch
           if (!masks)
           ^
   lib/group_cpus.c:371:8: note: Calling '__group_cpus_evenly'
           ret = __group_cpus_evenly(curgrp, numgrps, node_to_cpumask,
                 ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   lib/group_cpus.c:257:6: note: Assuming the condition is false
           if (!cpumask_weight(cpu_mask))
               ^~~~~~~~~~~~~~~~~~~~~~~~~
   lib/group_cpus.c:257:2: note: Taking false branch
           if (!cpumask_weight(cpu_mask))
           ^
   lib/group_cpus.c:266:6: note: Assuming 'numgrps' is > 'nodes'
           if (numgrps <= nodes) {
               ^~~~~~~~~~~~~~~~
   lib/group_cpus.c:266:2: note: Taking false branch
           if (numgrps <= nodes) {
           ^
   lib/group_cpus.c:279:6: note: Assuming 'node_groups' is non-null
           if (!node_groups)
               ^~~~~~~~~~~~
   lib/group_cpus.c:279:2: note: Taking false branch
           if (!node_groups)
           ^
   lib/group_cpus.c:283:2: note: Calling 'alloc_nodes_groups'
           alloc_nodes_groups(numgrps, node_to_cpumask, cpu_mask,
           ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   lib/group_cpus.c:134:14: note: 'remaining_ncpus' initialized to 0
           unsigned n, remaining_ncpus = 0;
                       ^~~~~~~~~~~~~~~
   lib/group_cpus.c:136:2: note: Loop condition is true.  Entering loop body
           for (n = 0; n < nr_node_ids; n++) {
           ^
   lib/group_cpus.c:136:2: note: Loop condition is false. Execution continues on line 141
   lib/group_cpus.c:141:2: note: Taking false branch
           for_each_node_mask(n, nodemsk) {
           ^
   include/linux/nodemask.h:384:2: note: expanded from macro 'for_each_node_mask'
           if (!nodes_empty(mask))                         \
           ^
   lib/group_cpus.c:153:12: note: '__UNIQUE_ID___x401' is < '__UNIQUE_ID___y402'
           numgrps = min_t(unsigned, remaining_ncpus, numgrps);
                     ^
   include/linux/minmax.h:104:27: note: expanded from macro 'min_t'
   #define min_t(type, x, y)       __careful_cmp((type)(x), (type)(y), <)
                                   ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   include/linux/minmax.h:38:3: note: expanded from macro '__careful_cmp'
                   __cmp_once(x, y, __UNIQUE_ID(__x), __UNIQUE_ID(__y), op))
                   ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   include/linux/minmax.h:33:3: note: expanded from macro '__cmp_once'
                   __cmp(unique_x, unique_y, op); })
                   ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   include/linux/minmax.h:28:26: note: expanded from macro '__cmp'
   #define __cmp(x, y, op) ((x) op (y) ? (x) : (y))
                            ^~~
   lib/group_cpus.c:153:12: note: '?' condition is true
           numgrps = min_t(unsigned, remaining_ncpus, numgrps);
                     ^
   include/linux/minmax.h:104:27: note: expanded from macro 'min_t'
   #define min_t(type, x, y)       __careful_cmp((type)(x), (type)(y), <)
                                   ^
   include/linux/minmax.h:38:3: note: expanded from macro '__careful_cmp'
                   __cmp_once(x, y, __UNIQUE_ID(__x), __UNIQUE_ID(__y), op))
                   ^
   include/linux/minmax.h:33:3: note: expanded from macro '__cmp_once'
                   __cmp(unique_x, unique_y, op); })
                   ^
   include/linux/minmax.h:28:26: note: expanded from macro '__cmp'
   #define __cmp(x, y, op) ((x) op (y) ? (x) : (y))
                            ^
   lib/group_cpus.c:226:2: note: Loop condition is true.  Entering loop body
           for (n = 0; n < nr_node_ids; n++) {
           ^
   lib/group_cpus.c:229:7: note: Assuming the condition is false
                   if (node_groups[n].ncpus == UINT_MAX)
                       ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   lib/group_cpus.c:229:3: note: Taking false branch
                   if (node_groups[n].ncpus == UINT_MAX)
                   ^
   lib/group_cpus.c:232:3: note: Taking true branch
                   WARN_ON_ONCE(numgrps == 0);
                   ^
   include/asm-generic/bug.h:105:2: note: expanded from macro 'WARN_ON_ONCE'

vim +236 lib/group_cpus.c

759f72186bfdd5 Ming Lei 2021-08-14  113  
759f72186bfdd5 Ming Lei 2021-08-14  114  /*
759f72186bfdd5 Ming Lei 2021-08-14  115   * Allocate group number for each node, so that for each node:
759f72186bfdd5 Ming Lei 2021-08-14  116   *
759f72186bfdd5 Ming Lei 2021-08-14  117   * 1) the allocated number is >= 1
759f72186bfdd5 Ming Lei 2021-08-14  118   *
759f72186bfdd5 Ming Lei 2021-08-14  119   * 2) the allocated number is <= active CPU number of this node
759f72186bfdd5 Ming Lei 2021-08-14  120   *
759f72186bfdd5 Ming Lei 2021-08-14  121   * The actual allocated total groups may be less than @numgrps when
759f72186bfdd5 Ming Lei 2021-08-14  122   * active total CPU number is less than @numgrps.
759f72186bfdd5 Ming Lei 2021-08-14  123   *
759f72186bfdd5 Ming Lei 2021-08-14  124   * Active CPUs means the CPUs in '@cpu_mask AND @node_to_cpumask[]'
759f72186bfdd5 Ming Lei 2021-08-14  125   * for each node.
759f72186bfdd5 Ming Lei 2021-08-14  126   */
759f72186bfdd5 Ming Lei 2021-08-14  127  static void alloc_nodes_groups(unsigned int numgrps,
759f72186bfdd5 Ming Lei 2021-08-14  128  			       cpumask_var_t *node_to_cpumask,
759f72186bfdd5 Ming Lei 2021-08-14  129  			       const struct cpumask *cpu_mask,
759f72186bfdd5 Ming Lei 2021-08-14  130  			       const nodemask_t nodemsk,
759f72186bfdd5 Ming Lei 2021-08-14  131  			       struct cpumask *nmsk,
759f72186bfdd5 Ming Lei 2021-08-14  132  			       struct node_groups *node_groups)
759f72186bfdd5 Ming Lei 2021-08-14  133  {
759f72186bfdd5 Ming Lei 2021-08-14  134  	unsigned n, remaining_ncpus = 0;
759f72186bfdd5 Ming Lei 2021-08-14  135  
759f72186bfdd5 Ming Lei 2021-08-14  136  	for (n = 0; n < nr_node_ids; n++) {
759f72186bfdd5 Ming Lei 2021-08-14  137  		node_groups[n].id = n;
759f72186bfdd5 Ming Lei 2021-08-14  138  		node_groups[n].ncpus = UINT_MAX;
759f72186bfdd5 Ming Lei 2021-08-14  139  	}
759f72186bfdd5 Ming Lei 2021-08-14  140  
759f72186bfdd5 Ming Lei 2021-08-14  141  	for_each_node_mask(n, nodemsk) {
759f72186bfdd5 Ming Lei 2021-08-14  142  		unsigned ncpus;
759f72186bfdd5 Ming Lei 2021-08-14  143  
759f72186bfdd5 Ming Lei 2021-08-14  144  		cpumask_and(nmsk, cpu_mask, node_to_cpumask[n]);
759f72186bfdd5 Ming Lei 2021-08-14  145  		ncpus = cpumask_weight(nmsk);
759f72186bfdd5 Ming Lei 2021-08-14  146  
759f72186bfdd5 Ming Lei 2021-08-14  147  		if (!ncpus)
759f72186bfdd5 Ming Lei 2021-08-14  148  			continue;
759f72186bfdd5 Ming Lei 2021-08-14  149  		remaining_ncpus += ncpus;
759f72186bfdd5 Ming Lei 2021-08-14  150  		node_groups[n].ncpus = ncpus;
759f72186bfdd5 Ming Lei 2021-08-14  151  	}
759f72186bfdd5 Ming Lei 2021-08-14  152  
759f72186bfdd5 Ming Lei 2021-08-14  153  	numgrps = min_t(unsigned, remaining_ncpus, numgrps);
759f72186bfdd5 Ming Lei 2021-08-14  154  
759f72186bfdd5 Ming Lei 2021-08-14  155  	sort(node_groups, nr_node_ids, sizeof(node_groups[0]),
759f72186bfdd5 Ming Lei 2021-08-14  156  	     ncpus_cmp_func, NULL);
759f72186bfdd5 Ming Lei 2021-08-14  157  
759f72186bfdd5 Ming Lei 2021-08-14  158  	/*
759f72186bfdd5 Ming Lei 2021-08-14  159  	 * Allocate groups for each node according to the ratio of this
759f72186bfdd5 Ming Lei 2021-08-14  160  	 * node's nr_cpus to remaining un-assigned ncpus. 'numgrps' is
759f72186bfdd5 Ming Lei 2021-08-14  161  	 * bigger than number of active numa nodes. Always start the
759f72186bfdd5 Ming Lei 2021-08-14  162  	 * allocation from the node with minimized nr_cpus.
759f72186bfdd5 Ming Lei 2021-08-14  163  	 *
759f72186bfdd5 Ming Lei 2021-08-14  164  	 * This way guarantees that each active node gets allocated at
759f72186bfdd5 Ming Lei 2021-08-14  165  	 * least one group, and the theory is simple: over-allocation
759f72186bfdd5 Ming Lei 2021-08-14  166  	 * is only done when this node is assigned by one group, so
759f72186bfdd5 Ming Lei 2021-08-14  167  	 * other nodes will be allocated >= 1 groups, since 'numgrps' is
759f72186bfdd5 Ming Lei 2021-08-14  168  	 * bigger than number of numa nodes.
759f72186bfdd5 Ming Lei 2021-08-14  169  	 *
759f72186bfdd5 Ming Lei 2021-08-14  170  	 * One perfect invariant is that number of allocated groups for
759f72186bfdd5 Ming Lei 2021-08-14  171  	 * each node is <= CPU count of this node:
759f72186bfdd5 Ming Lei 2021-08-14  172  	 *
759f72186bfdd5 Ming Lei 2021-08-14  173  	 * 1) suppose there are two nodes: A and B
759f72186bfdd5 Ming Lei 2021-08-14  174  	 * 	ncpu(X) is CPU count of node X
759f72186bfdd5 Ming Lei 2021-08-14  175  	 * 	grps(X) is the group count allocated to node X via this
759f72186bfdd5 Ming Lei 2021-08-14  176  	 * 	algorithm
759f72186bfdd5 Ming Lei 2021-08-14  177  	 *
759f72186bfdd5 Ming Lei 2021-08-14  178  	 * 	ncpu(A) <= ncpu(B)
759f72186bfdd5 Ming Lei 2021-08-14  179  	 * 	ncpu(A) + ncpu(B) = N
759f72186bfdd5 Ming Lei 2021-08-14  180  	 * 	grps(A) + grps(B) = G
759f72186bfdd5 Ming Lei 2021-08-14  181  	 *
759f72186bfdd5 Ming Lei 2021-08-14  182  	 * 	grps(A) = max(1, round_down(G * ncpu(A) / N))
759f72186bfdd5 Ming Lei 2021-08-14  183  	 * 	grps(B) = G - grps(A)
759f72186bfdd5 Ming Lei 2021-08-14  184  	 *
759f72186bfdd5 Ming Lei 2021-08-14  185  	 * 	both N and G are integer, and 2 <= G <= N, suppose
759f72186bfdd5 Ming Lei 2021-08-14  186  	 * 	G = N - delta, and 0 <= delta <= N - 2
759f72186bfdd5 Ming Lei 2021-08-14  187  	 *
759f72186bfdd5 Ming Lei 2021-08-14  188  	 * 2) obviously grps(A) <= ncpu(A) because:
759f72186bfdd5 Ming Lei 2021-08-14  189  	 *
759f72186bfdd5 Ming Lei 2021-08-14  190  	 * 	if grps(A) is 1, then grps(A) <= ncpu(A) given
759f72186bfdd5 Ming Lei 2021-08-14  191  	 * 	ncpu(A) >= 1
759f72186bfdd5 Ming Lei 2021-08-14  192  	 *
759f72186bfdd5 Ming Lei 2021-08-14  193  	 * 	otherwise,
759f72186bfdd5 Ming Lei 2021-08-14  194  	 * 		grps(A) <= G * ncpu(A) / N <= ncpu(A), given G <= N
759f72186bfdd5 Ming Lei 2021-08-14  195  	 *
759f72186bfdd5 Ming Lei 2021-08-14  196  	 * 3) prove how grps(B) <= ncpu(B):
759f72186bfdd5 Ming Lei 2021-08-14  197  	 *
759f72186bfdd5 Ming Lei 2021-08-14  198  	 * 	if round_down(G * ncpu(A) / N) == 0, vecs(B) won't be
759f72186bfdd5 Ming Lei 2021-08-14  199  	 * 	over-allocated, so grps(B) <= ncpu(B),
759f72186bfdd5 Ming Lei 2021-08-14  200  	 *
759f72186bfdd5 Ming Lei 2021-08-14  201  	 * 	otherwise:
759f72186bfdd5 Ming Lei 2021-08-14  202  	 *
759f72186bfdd5 Ming Lei 2021-08-14  203  	 * 	grps(A) =
759f72186bfdd5 Ming Lei 2021-08-14  204  	 * 		round_down(G * ncpu(A) / N) =
759f72186bfdd5 Ming Lei 2021-08-14  205  	 * 		round_down((N - delta) * ncpu(A) / N) =
759f72186bfdd5 Ming Lei 2021-08-14  206  	 * 		round_down((N * ncpu(A) - delta * ncpu(A)) / N)	 >=
759f72186bfdd5 Ming Lei 2021-08-14  207  	 * 		round_down((N * ncpu(A) - delta * N) / N)	 =
759f72186bfdd5 Ming Lei 2021-08-14  208  	 * 		cpu(A) - delta
759f72186bfdd5 Ming Lei 2021-08-14  209  	 *
759f72186bfdd5 Ming Lei 2021-08-14  210  	 * 	then:
759f72186bfdd5 Ming Lei 2021-08-14  211  	 *
759f72186bfdd5 Ming Lei 2021-08-14  212  	 * 	grps(A) - G >= ncpu(A) - delta - G
759f72186bfdd5 Ming Lei 2021-08-14  213  	 * 	=>
759f72186bfdd5 Ming Lei 2021-08-14  214  	 * 	G - grps(A) <= G + delta - ncpu(A)
759f72186bfdd5 Ming Lei 2021-08-14  215  	 * 	=>
759f72186bfdd5 Ming Lei 2021-08-14  216  	 * 	grps(B) <= N - ncpu(A)
759f72186bfdd5 Ming Lei 2021-08-14  217  	 * 	=>
759f72186bfdd5 Ming Lei 2021-08-14  218  	 * 	grps(B) <= cpu(B)
759f72186bfdd5 Ming Lei 2021-08-14  219  	 *
759f72186bfdd5 Ming Lei 2021-08-14  220  	 * For nodes >= 3, it can be thought as one node and another big
759f72186bfdd5 Ming Lei 2021-08-14  221  	 * node given that is exactly what this algorithm is implemented,
759f72186bfdd5 Ming Lei 2021-08-14  222  	 * and we always re-calculate 'remaining_ncpus' & 'numgrps', and
759f72186bfdd5 Ming Lei 2021-08-14  223  	 * finally for each node X: grps(X) <= ncpu(X).
759f72186bfdd5 Ming Lei 2021-08-14  224  	 *
759f72186bfdd5 Ming Lei 2021-08-14  225  	 */
759f72186bfdd5 Ming Lei 2021-08-14  226  	for (n = 0; n < nr_node_ids; n++) {
759f72186bfdd5 Ming Lei 2021-08-14  227  		unsigned ngroups, ncpus;
759f72186bfdd5 Ming Lei 2021-08-14  228  
759f72186bfdd5 Ming Lei 2021-08-14  229  		if (node_groups[n].ncpus == UINT_MAX)
759f72186bfdd5 Ming Lei 2021-08-14  230  			continue;
759f72186bfdd5 Ming Lei 2021-08-14  231  
759f72186bfdd5 Ming Lei 2021-08-14  232  		WARN_ON_ONCE(numgrps == 0);
759f72186bfdd5 Ming Lei 2021-08-14  233  
759f72186bfdd5 Ming Lei 2021-08-14  234  		ncpus = node_groups[n].ncpus;
759f72186bfdd5 Ming Lei 2021-08-14  235  		ngroups = max_t(unsigned, 1,
759f72186bfdd5 Ming Lei 2021-08-14 @236  				 numgrps * ncpus / remaining_ncpus);
759f72186bfdd5 Ming Lei 2021-08-14  237  		WARN_ON_ONCE(ngroups > ncpus);
759f72186bfdd5 Ming Lei 2021-08-14  238  
759f72186bfdd5 Ming Lei 2021-08-14  239  		node_groups[n].ngroups = ngroups;
759f72186bfdd5 Ming Lei 2021-08-14  240  
759f72186bfdd5 Ming Lei 2021-08-14  241  		remaining_ncpus -= ncpus;
759f72186bfdd5 Ming Lei 2021-08-14  242  		numgrps -= ngroups;
759f72186bfdd5 Ming Lei 2021-08-14  243  	}
759f72186bfdd5 Ming Lei 2021-08-14  244  }
759f72186bfdd5 Ming Lei 2021-08-14  245  

---
0-DAY CI Kernel Test Service, Intel Corporation
https://lists.01.org/hyperkitty/list/kbuild-all(a)lists.01.org

[-- Attachment #2: config.gz --]
[-- Type: application/gzip, Size: 31626 bytes --]

^ permalink raw reply	[flat|nested] 31+ messages in thread

end of thread, other threads:[~2021-08-18  8:38 UTC | newest]

Thread overview: 31+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2021-08-14 12:35 [PATCH 0/7] genirq/affinity: abstract new API from managed irq affinity spread Ming Lei
2021-08-14 12:35 ` [PATCH 1/7] genirq/affinity: remove the 'firstvec' parameter from irq_build_affinity_masks Ming Lei
2021-08-17  4:45   ` Christoph Hellwig
2021-08-14 12:35 ` [PATCH 2/7] genirq/affinity: pass affinity managed mask array to irq_build_affinity_masks Ming Lei
2021-08-17  4:46   ` Christoph Hellwig
2021-08-14 12:35 ` [PATCH 3/7] genirq/affinity: don't pass irq_affinity_desc " Ming Lei
2021-08-17  4:49   ` Christoph Hellwig
2021-08-14 12:35 ` [PATCH 4/7] genirq/affinity: rename irq_build_affinity_masks as group_cpus_evenly Ming Lei
2021-08-17  4:50   ` Christoph Hellwig
2021-08-18  8:38     ` Ming Lei
2021-08-14 12:35 ` [PATCH 5/7] genirq/affinity: move group_cpus_evenly() into lib/ Ming Lei
2021-08-14 17:01   ` kernel test robot
2021-08-14 17:01     ` kernel test robot
2021-08-16  1:04     ` Ming Lei
2021-08-16  1:04       ` Ming Lei
2021-08-17  4:52       ` Christoph Hellwig
2021-08-17  4:52         ` Christoph Hellwig
2021-08-14 17:15   ` kernel test robot
2021-08-14 17:15     ` kernel test robot
2021-08-14 12:35 ` [PATCH 6/7] lib/group_cpus: allow to group cpus in case of !CONFIG_SMP Ming Lei
2021-08-17  4:52   ` Christoph Hellwig
2021-08-14 12:35 ` [PATCH 7/7] blk-mq: build default queue map via group_cpus_evenly() Ming Lei
2021-08-14 16:31   ` kernel test robot
2021-08-14 16:31     ` kernel test robot
2021-08-14 20:49   ` kernel test robot
2021-08-14 20:49     ` kernel test robot
2021-08-16  7:23     ` Ming Lei
2021-08-16  7:23       ` Ming Lei
  -- strict thread matches above, loose matches on Subject: below --
2021-08-15  1:49 [PATCH 5/7] genirq/affinity: move group_cpus_evenly() into lib/ kernel test robot
2021-08-16 10:08 ` kernel test robot
2021-08-16 10:08   ` kernel test robot

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.