mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Yury Norov <yury.norov@gmail.com>
To: linux-kernel@vger.kernel.org
Cc: Yury Norov <yury.norov@gmail.com>,
	Andy Shevchenko <andriy.shevchenko@linux.intel.com>,
	Rasmus Villemoes <linux@rasmusvillemoes.dk>,
	Andrew Morton <akpm@linux-foundation.org>,
	Stephen Rothwell <sfr@canb.auug.org.au>,
	Peter Zijlstra <peterz@infradead.org>,
	Thomas Gleixner <tglx@linutronix.de>,
	"Paul E . McKenney" <paulmck@kernel.org>,
	Vlastimil Babka <vbabka@suse.cz>,
	Dmitry Vyukov <dvyukov@google.com>,
	Valentin Schneider <vschneid@redhat.com>,
	Sander Vanheule <sander@svanheule.net>,
	Alexey Klimov <klimov.linux@gmail.com>,
	Eric Biggers <ebiggers@google.com>
Subject: [PATCH 4/4] lib/cpumask: add FORCE_NR_CPUS config option
Date: Mon, 29 Aug 2022 09:57:48 -0700	[thread overview]
Message-ID: <20220829165748.1008477-5-yury.norov@gmail.com> (raw)
In-Reply-To: <20220829165748.1008477-1-yury.norov@gmail.com>

The size of cpumasks is hard-limited by compile-time parameter NR_CPUS,
but defined at boot-time when kernel parses ACPI/DT tables, and stored in
nr_cpu_ids. In many practical cases, number of CPUs for a target is known
at compile time, and can be provided with NR_CPUS.

In that case, compiler may be instructed to rely on NR_CPUS as on actual
number of CPUs, not an upper limit. It allows to optimize many cpumask
routines and significantly shrink size of the kernel image.

This patch adds FORCE_NR_CPUS option to teach the compiler to rely on
NR_CPUS and enable corresponding optimizations.

If FORCE_NR_CPUS=y, kernel will not set nr_cpu_ids at boot, but only check
that the actual number of possible CPUs is equal to NR_CPUS, and WARN if
that doesn't hold.

The new option is especially useful in embedded applications because
kernel configurations are unique for each SoC, the number of CPUs is
constant and known well, and memory limitations are typically harder.

For my 4-CPU ARM64 build with NR_CPUS=4, FORCE_NR_CPUS=y saves 46KB:
  add/remove: 3/4 grow/shrink: 46/729 up/down: 652/-46952 (-46300)

Signed-off-by: Yury Norov <yury.norov@gmail.com>
---
 include/linux/cpumask.h |  4 ++--
 include/linux/smp.h     |  4 ++++
 kernel/smp.c            |  2 ++
 lib/Kconfig             | 10 ++++++++++
 4 files changed, 18 insertions(+), 2 deletions(-)

diff --git a/include/linux/cpumask.h b/include/linux/cpumask.h
index b7b863cf8831..702c05329853 100644
--- a/include/linux/cpumask.h
+++ b/include/linux/cpumask.h
@@ -35,8 +35,8 @@ typedef struct cpumask { DECLARE_BITMAP(bits, NR_CPUS); } cpumask_t;
  */
 #define cpumask_pr_args(maskp)		nr_cpu_ids, cpumask_bits(maskp)
 
-#if NR_CPUS == 1
-#define nr_cpu_ids		1U
+#if (NR_CPUS == 1) || defined(CONFIG_FORCE_NR_CPUS)
+#define nr_cpu_ids ((unsigned int)NR_CPUS)
 #else
 extern unsigned int nr_cpu_ids;
 #endif
diff --git a/include/linux/smp.h b/include/linux/smp.h
index c9e7a9abef2f..e9e74e08c886 100644
--- a/include/linux/smp.h
+++ b/include/linux/smp.h
@@ -183,7 +183,11 @@ static inline int get_boot_cpu_id(void)
 
 static inline void set_nr_cpu_ids(unsigned int nr)
 {
+#ifdef CONFIG_FORCE_NR_CPUS
+	WARN_ON(nr_cpu_ids != nr);
+#else
 	nr_cpu_ids = nr;
+#endif
 }
 
 #else /* !SMP */
diff --git a/kernel/smp.c b/kernel/smp.c
index 27d4ed0aee55..9cd1d02221ba 100644
--- a/kernel/smp.c
+++ b/kernel/smp.c
@@ -1088,9 +1088,11 @@ static int __init maxcpus(char *str)
 
 early_param("maxcpus", maxcpus);
 
+#ifndef CONFIG_FORCE_NR_CPUS
 /* Setup number of possible processor ids */
 unsigned int nr_cpu_ids __read_mostly = NR_CPUS;
 EXPORT_SYMBOL(nr_cpu_ids);
+#endif
 
 /* An arch may set nr_cpu_ids earlier if needed, so this would be redundant */
 void __init setup_nr_cpu_ids(void)
diff --git a/lib/Kconfig b/lib/Kconfig
index dc1ab2ed1dc6..5de23382e5f3 100644
--- a/lib/Kconfig
+++ b/lib/Kconfig
@@ -527,6 +527,16 @@ config CPUMASK_OFFSTACK
 	  them on the stack.  This is a bit more expensive, but avoids
 	  stack overflow.
 
+config FORCE_NR_CPUS
+       bool "NR_CPUS is set to an actual number of CPUs"
+       depends on SMP
+       default n
+       help
+         Say Yes if you have NR_CPUS set to an actual number of possible
+         CPUs in your system, not to a default value. This forces the core
+         code to rely on compile-time value and optimize kernel routines
+         better.
+
 config CPU_RMAP
 	bool
 	depends on SMP
-- 
2.34.1


  parent reply	other threads:[~2022-08-29 16:58 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-08-29 16:57 [PATCH 0/4] cpumask: cleanup nr_cpu_ids vs nr_cpumask_bits mess Yury Norov
2022-08-29 16:57 ` [PATCH 1/4] smp: add set_nr_cpu_ids() Yury Norov
2022-08-29 16:57 ` [PATCH 2/4] lib/cpumask: delete misleading comment Yury Norov
2022-08-29 16:57 ` [PATCH 3/4] lib/cpumask: deprecate nr_cpumask_bits Yury Norov
2022-08-29 16:57 ` Yury Norov [this message]
2022-08-29 17:02   ` [PATCH 4/4] lib/cpumask: add FORCE_NR_CPUS config option Andy Shevchenko
     [not found]   ` <202208310215.C2IzssKr-lkp@intel.com>
2022-08-30 21:02     ` Yury Norov
2022-09-02 17:31       ` Yury Norov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20220829165748.1008477-5-yury.norov@gmail.com \
    --to=yury.norov@gmail.com \
    --cc=akpm@linux-foundation.org \
    --cc=andriy.shevchenko@linux.intel.com \
    --cc=dvyukov@google.com \
    --cc=ebiggers@google.com \
    --cc=klimov.linux@gmail.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux@rasmusvillemoes.dk \
    --cc=paulmck@kernel.org \
    --cc=peterz@infradead.org \
    --cc=sander@svanheule.net \
    --cc=sfr@canb.auug.org.au \
    --cc=tglx@linutronix.de \
    --cc=vbabka@suse.cz \
    --cc=vschneid@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®