Skip to content

Folio

include/mem/folio.h View source View on GitHub
struct folio (8 fields) source
§ struct page *base_page
§ atomic(enum folio_flags) flags
§ uint8_t order

2^order pages

§ refcount_t refcount
§ mapcount_t mapcount
§ void *mapping

tagged, anon_vma or file_vma_range

§ pgoff_t index
§ struct list_node lru

reclaim linkage

enum folio_flags : uint32_t (7 variants) source

folio_flags: 32-bit bitflags

┌────────────────────────────────────┐
Bits │ 31..8 7..4 3..0 │
Use │ (reserved) ..LU DMAO │
└────────────────────────────────────┘

O - On an LRU / reclaim list A - Anon: mapping is an anon_vma (clear => file_vma_range) M - Mapped at least once (mapcount has been nonzero) D - Dirty: needs writeback U - Uptodate: contents valid L - Locked: I/O in flight

Reserved bits fill in as the pager arrives (writeback, referenced, reclaim, mlocked, swapbacked, …). Width is uint32_t for headroom.

§ FOLIO_FLAGS_NONE = 0
§ FOLIO_FLAG_ON_LRU = (1u << 0)
§ FOLIO_FLAG_ANON = (1u << 1)
§ FOLIO_FLAG_MAPPED = (1u << 2)
§ FOLIO_FLAG_DIRTY = (1u << 3)
§ FOLIO_FLAG_UPTODATE = (1u << 4)
§ FOLIO_FLAG_LOCKED = (1u << 5)
enum folio_tag : uintptr_t (2 variants) source
§ FOLIO_TAG_ADDRESS_SPACE = 1
§ FOLIO_TAG_ANON = 2
uint32_t page_get_folio_index(struct page *p)
source
bool page_is_folio_head(struct page *p)
source
struct folio * folio_alloc_folio_struct(void)
source
void folio_free_folio_struct(struct folio *f)
source
struct folio * folio_alloc_full(
    uint8_t order,
    struct alloc_params params
)
source
void folio_free(struct folio *folio)
source
void folio_bind_pages(struct folio *f)
source

page <-> folio backptrs, give every struct page folio at alloc, clear them at free

void folio_unbind_pages(struct folio *f)
source
void folio_zero(struct folio *f)
source

Operates on the data pages

void folio_copy(const struct folio *src, struct folio *dst)
source

LRU

void folio_add_lru(struct folio *f)
source
void folio_del_lru(struct folio *f)
source
void page_set_folio(struct page *p, struct folio *f)
source

Some struct page functions here for folio

struct folio * page_get_folio(const struct page *p)
source
void page_clear_folio(struct page *p)
source
bool folio_mapped(const struct folio *f)
source
unsigned long folio_nr_pages(const struct folio *f)
source
void folio_set_tag(struct folio *f, enum folio_tag t)
source
enum folio_tag folio_get_tag(const struct folio *f)
source
bool folio_test_flag(const struct folio *f, enum folio_flags m)
source
void folio_set_flag(struct folio *f, enum folio_flags m)
source
void folio_clear_flag(struct folio *f, enum folio_flags m)
source
bool folio_test_set_flag(struct folio *f, enum folio_flags m)
source
bool folio_getref(struct folio *f)
source
void folio_putref(struct folio *f)
source
struct page * folio_get_page(const struct folio *f, size_t n)
source

Nth page

pfn_t folio_get_pfn(const struct folio *f)
source
struct folio * folio_from_page(const struct page *p)
source

reverse of folio_page(): a mapped frame -> its folio, via the page backpointer. The fault/rmap paths take a PTE’s phys and land back here.

struct folio * folio_from_paddr(paddr_t pa)
source
paddr_t folio_get_paddr(const struct folio *f)
source
vaddr_t folio_get_vaddr(const struct folio *f)
source

HHDM map of base

paddr_t folio_get_paddr_for(const struct folio *f, size_t n)
source
vaddr_t folio_get_vaddr_for(const struct folio *f, size_t n)
source

HHDM map of page n

void folio_mark_dirty(struct folio *f)
source

state

void folio_mark_uptodate(struct folio *f)
source
void folio_set_anon(
    struct folio *f,
    struct anon_vma *av,
    pgoff_t index
)
source
bool folio_is_anon(const struct folio *f)
source
bool folio_is_file_vma_range(const struct folio *f)
source
struct anon_vma * folio_get_anon_vma(const struct folio *f)
source
struct file_vma_range * folio_get_file_vma_range(const struct folio *f)
source
bool folio_trylock(struct folio *f)
source
void folio_lock(struct folio *f)
source
void folio_unlock(struct folio *f)
source
void folio_mapcount_inc(struct folio *f)
source

mapcount, number of PTEs pointing at this folio

bool folio_mapcount_dec(struct folio *f)
source
#define FOLIO_TAG_BITS 0x7
source
#define folio_for_each_page_struct(p_, f_)
source
Expansion
#define folio_for_each_page_struct(p_, f_) \
    for (size_t __folio_page_idx = 0; \
         __folio_page_idx < folio_nr_pages(f_) && \
         (((p_) = folio_get_page((f_), __folio_page_idx)), true); \
         __folio_page_idx++)
#define folio_for_each_page_paddr(p_, f_)
source
Expansion
#define folio_for_each_page_paddr(p_, f_) \
    for (size_t __folio_paddr_idx = 0; \
         __folio_paddr_idx < folio_nr_pages(f_) && \
         (((p_) = folio_get_paddr_for((f_), __folio_paddr_idx)), true); \
         __folio_paddr_idx++)
#define folio_for_each_page_vaddr(p_, f_)
source
Expansion
#define folio_for_each_page_vaddr(p_, f_) \
    for (size_t __folio_vaddr_idx = 0; \
         __folio_vaddr_idx < folio_nr_pages(f_) && \
         (((p_) = folio_get_vaddr_for((f_), __folio_vaddr_idx)), true); \
         __folio_vaddr_idx++)
#define folio_alloc(order, ...)
source
Expansion
#define folio_alloc(order, ...) \
    folio_alloc_full((order), alloc_params_with_defaults( \
                                  ALLOC_FLAGS_DEFAULT, ALLOC_BEHAVIOR_DEFAULT, \
                                  ##__VA_ARGS__))