From: "Matthew Wilcox (Oracle)" <willy@infradead.org> To: linux-fsdevel@vger.kernel.org, linux-mm@kvack.org Cc: "Matthew Wilcox (Oracle)" <willy@infradead.org>, linux-kernel@vger.kernel.org Subject: [PATCH v2 08/27] mm: Handle per-folio private data Date: Mon, 18 Jan 2021 17:01:29 +0000 Message-ID: <20210118170148.3126186-9-willy@infradead.org> (raw) In-Reply-To: <20210118170148.3126186-1-willy@infradead.org> Add folio_private() and set_folio_private() which mirror page_private() and set_page_private() -- ie folio private data is the same as page private data. Turn attach_page_private() into attach_folio_private() and reimplement attach_page_private() as a wrapper. No filesystem which uses page private data currently supports compound pages, so we're free to define the rules. attach_page_private() may only be called on a head page; if you want to add private data to a tail page, you can call set_page_private() directly (and shouldn't increment the page refcount! That should be done when adding private data to the head page / folio). Signed-off-by: Matthew Wilcox (Oracle) <willy@infradead.org> --- include/linux/mm_types.h | 16 ++++++++++++++ include/linux/pagemap.h | 48 ++++++++++++++++++++++++---------------- 2 files changed, 45 insertions(+), 19 deletions(-) diff --git a/include/linux/mm_types.h b/include/linux/mm_types.h index 875dc6cd6ad2..750184130074 100644 --- a/include/linux/mm_types.h +++ b/include/linux/mm_types.h @@ -258,6 +258,12 @@ static inline atomic_t *compound_pincount_ptr(struct page *page) #define PAGE_FRAG_CACHE_MAX_SIZE __ALIGN_MASK(32768, ~PAGE_MASK) #define PAGE_FRAG_CACHE_MAX_ORDER get_order(PAGE_FRAG_CACHE_MAX_SIZE) +/* + * page_private can be used on tail pages. However, PagePrivate is only + * checked by the VM on the head page. So page_private on the tail pages + * should be used for data that's ancillary to the head page (eg attaching + * buffer heads to tail pages after attaching buffer heads to the head page) + */ #define page_private(page) ((page)->private) static inline void set_page_private(struct page *page, unsigned long private) @@ -265,6 +271,16 @@ static inline void set_page_private(struct page *page, unsigned long private) page->private = private; } +static inline unsigned long folio_private(struct folio *folio) +{ + return folio->page.private; +} + +static inline void set_folio_private(struct folio *folio, unsigned long v) +{ + folio->page.private = v; +} + struct page_frag_cache { void * va; #if (PAGE_SIZE < PAGE_FRAG_CACHE_MAX_SIZE) diff --git a/include/linux/pagemap.h b/include/linux/pagemap.h index 4317f34866c7..a739ada01d27 100644 --- a/include/linux/pagemap.h +++ b/include/linux/pagemap.h @@ -245,42 +245,52 @@ static inline int page_cache_add_speculative(struct page *page, int count) } /** - * attach_page_private - Attach private data to a page. - * @page: Page to attach data to. - * @data: Data to attach to page. + * attach_folio_private - Attach private data to a folio. + * @folio: Folio to attach data to. + * @data: Data to attach to folio. * - * Attaching private data to a page increments the page's reference count. - * The data must be detached before the page will be freed. + * Attaching private data to a folio increments the page's reference count. + * The data must be detached before the folio will be freed. */ -static inline void attach_page_private(struct page *page, void *data) +static inline void attach_folio_private(struct folio *folio, void *data) { - get_page(page); - set_page_private(page, (unsigned long)data); - SetPagePrivate(page); + get_folio(folio); + set_folio_private(folio, (unsigned long)data); + SetFolioPrivate(folio); } /** - * detach_page_private - Detach private data from a page. - * @page: Page to detach data from. + * detach_folio_private - Detach private data from a folio. + * @folio: Folio to detach data from. * - * Removes the data that was previously attached to the page and decrements + * Removes the data that was previously attached to the folio and decrements * the refcount on the page. * - * Return: Data that was attached to the page. + * Return: Data that was attached to the folio. */ -static inline void *detach_page_private(struct page *page) +static inline void *detach_folio_private(struct folio *folio) { - void *data = (void *)page_private(page); + void *data = (void *)folio_private(folio); - if (!PagePrivate(page)) + if (!FolioPrivate(folio)) return NULL; - ClearPagePrivate(page); - set_page_private(page, 0); - put_page(page); + ClearFolioPrivate(folio); + set_folio_private(folio, 0); + put_folio(folio); return data; } +static inline void attach_page_private(struct page *page, void *data) +{ + attach_folio_private((struct folio *)page, data); +} + +static inline void *detach_page_private(struct page *page) +{ + return detach_folio_private((struct folio *)page); +} + #ifdef CONFIG_NUMA extern struct page *__page_cache_alloc(gfp_t gfp); #else -- 2.29.2
next prev parent reply index Thread overview: 28+ messages / expand[flat|nested] mbox.gz Atom feed top 2021-01-18 17:01 [PATCH v2 00/27] Page folios Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 01/27] mm: Introduce struct folio Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 02/27] mm: Add folio_pgdat Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 03/27] mm/vmstat: Add folio stat wrappers Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 04/27] mm/debug: Add VM_BUG_ON_FOLIO and VM_WARN_ON_ONCE_FOLIO Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 05/27] mm: Add put_folio Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 06/27] mm: Add get_folio Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 07/27] mm: Create FolioFlags Matthew Wilcox (Oracle) 2021-01-18 17:01 ` Matthew Wilcox (Oracle) [this message] 2021-01-18 17:01 ` [PATCH v2 09/27] mm: Add folio_index, folio_page and folio_contains Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 10/27] mm/util: Add folio_mapping and folio_file_mapping Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 11/27] mm/memcg: Add folio_memcg, lock_folio_memcg and unlock_folio_memcg Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 12/27] mm/memcg: Add mem_cgroup_folio_lruvec Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 13/27] mm: Add unlock_folio Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 14/27] mm: Add lock_folio Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 15/27] mm: Add lock_folio_killable Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 16/27] mm: Convert lock_page_async to lock_folio_async Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 17/27] mm/filemap: Convert lock_page_for_iocb to lock_folio_for_iocb Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 18/27] mm/filemap: Convert wait_on_page_locked_async to wait_on_folio_locked_async Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 19/27] mm/filemap: Convert end_page_writeback to end_folio_writeback Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 20/27] mm: Convert wait_on_page_bit to wait_on_folio_bit Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 21/27] mm: Add wait_for_stable_folio and wait_on_folio_writeback Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 22/27] mm: Add wait_on_folio_locked & wait_on_folio_locked_killable Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 23/27] mm: Convert lock_page_or_retry to lock_folio_or_retry Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 24/27] mm/filemap: Convert wake_up_page_bit to wake_up_folio_bit Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 25/27] mm: Convert test_clear_page_writeback to test_clear_folio_writeback Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 26/27] mm/filemap: Convert page wait queues to be folios Matthew Wilcox (Oracle) 2021-01-18 17:01 ` [PATCH v2 27/27] cachefiles: Switch to wait_page_key Matthew Wilcox (Oracle)
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=20210118170148.3126186-9-willy@infradead.org \ --to=willy@infradead.org \ --cc=linux-fsdevel@vger.kernel.org \ --cc=linux-kernel@vger.kernel.org \ --cc=linux-mm@kvack.org \ /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
Linux-Fsdevel Archive on lore.kernel.org Archives are clonable: git clone --mirror https://lore.kernel.org/linux-fsdevel/0 linux-fsdevel/git/0.git # If you have public-inbox 1.1+ installed, you may # initialize and index your mirror using the following commands: public-inbox-init -V2 linux-fsdevel linux-fsdevel/ https://lore.kernel.org/linux-fsdevel \ linux-fsdevel@vger.kernel.org public-inbox-index linux-fsdevel Example config snippet for mirrors Newsgroup available over NNTP: nntp://nntp.lore.kernel.org/org.kernel.vger.linux-fsdevel AGPL code for this site: git clone https://public-inbox.org/public-inbox.git