From: Mike Rapoport <rppt@kernel.org>
To: Pasha Tatashin <pasha.tatashin@soleen.com>
Cc: akpm@linux-foundation.org, mhocko@suse.com, vbabka@suse.cz,
david@redhat.com, quic_charante@quicinc.com,
lizhe.67@bytedance.com, linux-kernel@vger.kernel.org,
linux-mm@kvack.org
Subject: Re: [PATCH v3] mm/page_ext: Do not allocate space for page_ext->flags if not needed
Date: Mon, 16 Jan 2023 11:00:48 +0200 [thread overview]
Message-ID: <Y8USQBPlMNTTIyIO@kernel.org> (raw)
In-Reply-To: <20230113154253.92480-1-pasha.tatashin@soleen.com>
On Fri, Jan 13, 2023 at 03:42:53PM +0000, Pasha Tatashin wrote:
> There is 8 byte page_ext->flags field allocated per page whenever
> CONFIG_PAGE_EXTENSION is enabled. However, not every user of page_ext
> uses flags. Therefore, check whether flags is needed at least by one
> user and if so allocate space for it.
>
> For example when page_table_check is enabled, on a machine with 128G
> of memory before the fix:
>
> [ 2.244288] allocated 536870912 bytes of page_ext
> after the fix:
> [ 2.160154] allocated 268435456 bytes of page_ext
>
> Also, add a comment before page_ext_operations that describes the
> field, and remove check if need() is set, as that is now a required
Nit: fields
> field.
>
> Signed-off-by: Pasha Tatashin <pasha.tatashin@soleen.com>
> ---
> include/linux/page_ext.h | 19 +++++++++++++++++++
> mm/page_ext.c | 14 ++++++++++++--
> mm/page_owner.c | 1 +
> mm/page_table_check.c | 1 +
> 4 files changed, 33 insertions(+), 2 deletions(-)
>
> Changelog:
> v2: Fixed field name in page_owner.c that caused build error.
> v3: Added comment before page_ext_operations, removed check if
> need is null.
>
> diff --git a/include/linux/page_ext.h b/include/linux/page_ext.h
> index 22be4582faae..be0b465c7d78 100644
> --- a/include/linux/page_ext.h
> +++ b/include/linux/page_ext.h
> @@ -7,15 +7,31 @@
> #include <linux/stackdepot.h>
>
> struct pglist_data;
> +
> +/*
Please make it kerneldoc.
> + * Each Page Extension client must define page_ext_operations in
> + * page_ext_ops array.
> + * offset offset to the client's data within page_ext. Offset is returned to
> + * the client by page_ext_init.
> + * size the size of the client data within page_ext.
> + * need() function that returns true if client requires page_ext
> + * init() (optional) called to initialize client once page_exts are allocated.
> + * using_shared_ext_flags true when client is using shared page_ext->flags
> + * field.
> + */
> struct page_ext_operations {
> size_t offset;
> size_t size;
> bool (*need)(void);
> void (*init)(void);
> + bool using_shared_ext_flags;
I'd s/using_shared_ext_flags/need_shared_flags.
> };
>
> #ifdef CONFIG_PAGE_EXTENSION
>
> +/*
> + * The page_ext_flags users must set using_shared_ext_flags to true.
> + */
> enum page_ext_flags {
> PAGE_EXT_OWNER,
> PAGE_EXT_OWNER_ALLOCATED,
> @@ -31,6 +47,9 @@ enum page_ext_flags {
> * page_ext helps us add more information about the page.
> * All page_ext are allocated at boot or memory hotplug event,
> * then the page_ext for pfn always exists.
> + * Note: that if none of the users of page_ext is setting
I'd drop that ^that
> + * using_shared_ext_flags to true, the field cannot be used,
> + * as it will be overlapped with another data.
> */
> struct page_ext {
> unsigned long flags;
> diff --git a/mm/page_ext.c b/mm/page_ext.c
> index 4ee522fd381c..d14dbd44fa49 100644
> --- a/mm/page_ext.c
> +++ b/mm/page_ext.c
> @@ -71,6 +71,7 @@ static bool need_page_idle(void)
> }
> static struct page_ext_operations page_idle_ops __initdata = {
> .need = need_page_idle,
> + .using_shared_ext_flags = true,
> };
> #endif
>
> @@ -86,7 +87,7 @@ static struct page_ext_operations *page_ext_ops[] __initdata = {
> #endif
> };
>
> -unsigned long page_ext_size = sizeof(struct page_ext);
> +unsigned long page_ext_size;
>
> static unsigned long total_usage;
> static struct page_ext *lookup_page_ext(const struct page *page);
> @@ -106,7 +107,16 @@ static bool __init invoke_need_callbacks(void)
> bool need = false;
>
> for (i = 0; i < entries; i++) {
> - if (page_ext_ops[i]->need && page_ext_ops[i]->need()) {
> + if (page_ext_ops[i]->need()) {
> + if (page_ext_ops[i]->using_shared_ext_flags) {
> + page_ext_size = sizeof(struct page_ext);
> + break;
> + }
> + }
> + }
> +
> + for (i = 0; i < entries; i++) {
> + if (page_ext_ops[i]->need()) {
> page_ext_ops[i]->offset = page_ext_size;
> page_ext_size += page_ext_ops[i]->size;
> need = true;
> diff --git a/mm/page_owner.c b/mm/page_owner.c
> index 2d27f532df4c..1a62ab3fc00e 100644
> --- a/mm/page_owner.c
> +++ b/mm/page_owner.c
> @@ -99,6 +99,7 @@ struct page_ext_operations page_owner_ops = {
> .size = sizeof(struct page_owner),
> .need = need_page_owner,
> .init = init_page_owner,
> + .using_shared_ext_flags = true,
> };
>
> static inline struct page_owner *get_page_owner(struct page_ext *page_ext)
> diff --git a/mm/page_table_check.c b/mm/page_table_check.c
> index 93e633c1d587..74cfe89d5f53 100644
> --- a/mm/page_table_check.c
> +++ b/mm/page_table_check.c
> @@ -45,6 +45,7 @@ struct page_ext_operations page_table_check_ops = {
> .size = sizeof(struct page_table_check),
> .need = need_page_table_check,
> .init = init_page_table_check,
> + .using_shared_ext_flags = false,
> };
>
> static struct page_table_check *get_page_table_check(struct page_ext *page_ext)
> --
> 2.39.0.314.g84b9a713c41-goog
>
>
--
Sincerely yours,
Mike.
next prev parent reply other threads:[~2023-01-16 9:01 UTC|newest]
Thread overview: 6+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-01-13 15:42 [PATCH v3] mm/page_ext: Do not allocate space for page_ext->flags if not needed Pasha Tatashin
2023-01-16 9:00 ` Mike Rapoport [this message]
2023-01-17 20:04 ` Pasha Tatashin
2023-01-16 10:51 ` Vlastimil Babka
2023-01-16 10:53 ` David Hildenbrand
2023-01-17 20:05 ` Pasha Tatashin
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=Y8USQBPlMNTTIyIO@kernel.org \
--to=rppt@kernel.org \
--cc=akpm@linux-foundation.org \
--cc=david@redhat.com \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-mm@kvack.org \
--cc=lizhe.67@bytedance.com \
--cc=mhocko@suse.com \
--cc=pasha.tatashin@soleen.com \
--cc=quic_charante@quicinc.com \
--cc=vbabka@suse.cz \
/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 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.