mm/kmsan/init.c
Source file repositories/reference/linux-study-clean/mm/kmsan/init.c
File Facts
- System
- Linux kernel
- Corpus path
mm/kmsan/init.c- Extension
.c- Size
- 6555 bytes
- Lines
- 238
- Domain
- Core OS
- Bucket
- Memory Management
- Inferred role
- Core OS: implementation source
- Status
- source implementation candidate
Why This File Exists
Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.
- Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
kmsan.hasm/sections.hlinux/mm.hlinux/memblock.h../internal.h
Detected Declarations
struct start_end_pairstruct metadata_page_pairstruct smallstackfunction kmsan_record_future_shadow_rangefunction datafunction kmsan_memblock_discardfunction smallstack_pushfunction do_collectionfunction collect_splitfunction kmsan_memblock_discardfunction kmsan_init_runtime
Annotated Snippet
struct start_end_pair {
u64 start, end;
};
static struct start_end_pair start_end_pairs[NUM_FUTURE_RANGES] __initdata;
static int future_index __initdata;
/*
* Record a range of memory for which the metadata pages will be created once
* the page allocator becomes available.
*/
static void __init kmsan_record_future_shadow_range(void *start, void *end)
{
u64 nstart = (u64)start, nend = (u64)end, cstart, cend;
bool merged = false;
KMSAN_WARN_ON(future_index == NUM_FUTURE_RANGES);
KMSAN_WARN_ON((nstart >= nend) ||
/* Virtual address 0 is valid on s390. */
(!IS_ENABLED(CONFIG_S390) && !nstart) || !nend);
nstart = ALIGN_DOWN(nstart, PAGE_SIZE);
nend = ALIGN(nend, PAGE_SIZE);
/*
* Scan the existing ranges to see if any of them overlaps with
* [start, end). In that case, merge the two ranges instead of
* creating a new one.
* The number of ranges is less than 20, so there is no need to organize
* them into a more intelligent data structure.
*/
for (int i = 0; i < future_index; i++) {
cstart = start_end_pairs[i].start;
cend = start_end_pairs[i].end;
if ((cstart < nstart && cend < nstart) ||
(cstart > nend && cend > nend))
/* ranges are disjoint - do not merge */
continue;
start_end_pairs[i].start = min(nstart, cstart);
start_end_pairs[i].end = max(nend, cend);
merged = true;
break;
}
if (merged)
return;
start_end_pairs[future_index].start = nstart;
start_end_pairs[future_index].end = nend;
future_index++;
}
/*
* Initialize the shadow for existing mappings during kernel initialization.
* These include kernel text/data sections, NODE_DATA and future ranges
* registered while creating other data (e.g. percpu).
*
* Allocations via memblock can be only done before slab is initialized.
*/
void __init kmsan_init_shadow(void)
{
const size_t nd_size = sizeof(pg_data_t);
phys_addr_t p_start, p_end;
u64 loop;
int nid;
for_each_reserved_mem_range(loop, &p_start, &p_end)
kmsan_record_future_shadow_range(phys_to_virt(p_start),
phys_to_virt(p_end));
/* Allocate shadow for .data */
kmsan_record_future_shadow_range(_sdata, _edata);
for_each_online_node(nid)
kmsan_record_future_shadow_range(
NODE_DATA(nid), (char *)NODE_DATA(nid) + nd_size);
for (int i = 0; i < future_index; i++)
kmsan_init_alloc_meta_for_range(
(void *)start_end_pairs[i].start,
(void *)start_end_pairs[i].end);
}
struct metadata_page_pair {
struct page *shadow, *origin;
};
static struct metadata_page_pair held_back[NR_PAGE_ORDERS] __initdata;
/*
* Eager metadata allocation. When the memblock allocator is freeing pages to
* pagealloc, we use 2/3 of them as metadata for the remaining 1/3.
* We store the pointers to the returned blocks of pages in held_back[] grouped
* by their order: when kmsan_memblock_free_pages() is called for the first
* time with a certain order, it is reserved as a shadow block, for the second
Annotation
- Immediate include surface: `kmsan.h`, `asm/sections.h`, `linux/mm.h`, `linux/memblock.h`, `../internal.h`.
- Detected declarations: `struct start_end_pair`, `struct metadata_page_pair`, `struct smallstack`, `function kmsan_record_future_shadow_range`, `function data`, `function kmsan_memblock_discard`, `function smallstack_push`, `function do_collection`, `function collect_split`, `function kmsan_memblock_discard`.
- Atlas domain: Core OS / Memory Management.
- Implementation status: source implementation candidate.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.