1 /* SPDX-License-Identifier: GPL-2.0 */
3 #ifndef _LINUX_PAGE_FRAG_CACHE_H
4 #define _LINUX_PAGE_FRAG_CACHE_H
6 #include <linux/bits.h>
7 #include <linux/log2.h>
8 #include <linux/mm_types_task.h>
9 #include <linux/types.h>
11 #if (PAGE_SIZE < PAGE_FRAG_CACHE_MAX_SIZE)
12 /* Use a full byte here to enable assembler optimization as the shift
13 * operation is usually expecting a byte.
15 #define PAGE_FRAG_CACHE_ORDER_MASK GENMASK(7, 0)
17 /* Compiler should be able to figure out we don't read things as any value
20 #define PAGE_FRAG_CACHE_ORDER_MASK 0
23 #define PAGE_FRAG_CACHE_PFMEMALLOC_BIT (PAGE_FRAG_CACHE_ORDER_MASK + 1)
25 static inline bool encoded_page_decode_pfmemalloc(unsigned long encoded_page
)
27 return !!(encoded_page
& PAGE_FRAG_CACHE_PFMEMALLOC_BIT
);
30 static inline void page_frag_cache_init(struct page_frag_cache
*nc
)
35 static inline bool page_frag_cache_is_pfmemalloc(struct page_frag_cache
*nc
)
37 return encoded_page_decode_pfmemalloc(nc
->encoded_page
);
40 void page_frag_cache_drain(struct page_frag_cache
*nc
);
41 void __page_frag_cache_drain(struct page
*page
, unsigned int count
);
42 void *__page_frag_alloc_align(struct page_frag_cache
*nc
, unsigned int fragsz
,
43 gfp_t gfp_mask
, unsigned int align_mask
);
45 static inline void *page_frag_alloc_align(struct page_frag_cache
*nc
,
46 unsigned int fragsz
, gfp_t gfp_mask
,
49 WARN_ON_ONCE(!is_power_of_2(align
));
50 return __page_frag_alloc_align(nc
, fragsz
, gfp_mask
, -align
);
53 static inline void *page_frag_alloc(struct page_frag_cache
*nc
,
54 unsigned int fragsz
, gfp_t gfp_mask
)
56 return __page_frag_alloc_align(nc
, fragsz
, gfp_mask
, ~0u);
59 void page_frag_free(void *addr
);