tools/testing/selftests/powerpc/tm/tm-signal-pagefault.c
Source file repositories/reference/linux-study-clean/tools/testing/selftests/powerpc/tm/tm-signal-pagefault.c
File Facts
- System
- Linux kernel
- Corpus path
tools/testing/selftests/powerpc/tm/tm-signal-pagefault.c- Extension
.c- Size
- 7675 bytes
- Lines
- 286
- Domain
- Support Tooling And Documentation
- Bucket
- tools
- Inferred role
- Support Tooling And Documentation: implementation source
- Status
- source implementation candidate
Why This File Exists
Repository support layer: documentation, build tooling, samples, user-space helper tools, generated initramfs support, licenses, and validation utilities.
- Repository support layer: documentation, build tooling, samples, user-space helper tools, generated initramfs support, licenses, and validation utilities.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
stdio.hstdlib.hstring.hlinux/userfaultfd.hpoll.hunistd.hsys/ioctl.hsys/syscall.hfcntl.hsys/mman.hpthread.hsignal.herrno.htm.h
Detected Declarations
function setup_uf_memfunction signal_handlerfunction have_userfaultfdfunction tm_signal_pagefaultfunction main
Annotated Snippet
if (poll(&pollfd, 1, -1) == -1) {
perror("poll() failed");
exit(EXIT_FAILURE);
}
nread = read(uffd, &msg, sizeof(msg));
if (nread == 0) {
fprintf(stderr, "read(): EOF on userfaultfd\n");
exit(EXIT_FAILURE);
}
if (nread == -1) {
perror("read() failed");
exit(EXIT_FAILURE);
}
/* We expect only one kind of event */
if (msg.event != UFFD_EVENT_PAGEFAULT) {
fprintf(stderr, "Unexpected event on userfaultfd\n");
exit(EXIT_FAILURE);
}
/*
* We need to handle page faults in units of pages(!).
* So, round faulting address down to page boundary.
*/
uffdio_copy.dst = msg.arg.pagefault.address & ~(pagesize-1);
offset = (char *) uffdio_copy.dst - uf_mem;
uffdio_copy.src = (unsigned long) &backing_mem[offset];
uffdio_copy.len = pagesize;
uffdio_copy.mode = 0;
uffdio_copy.copy = 0;
if (ioctl(uffd, UFFDIO_COPY, &uffdio_copy) == -1) {
perror("ioctl-UFFDIO_COPY failed");
exit(EXIT_FAILURE);
}
}
}
void setup_uf_mem(void)
{
long uffd; /* userfaultfd file descriptor */
pthread_t thr;
struct uffdio_api uffdio_api;
struct uffdio_register uffdio_register;
int ret;
pagesize = sysconf(_SC_PAGE_SIZE);
/* Create and enable userfaultfd object */
uffd = syscall(__NR_userfaultfd, O_CLOEXEC | O_NONBLOCK);
if (uffd == -1) {
perror("userfaultfd() failed");
exit(EXIT_FAILURE);
}
uffdio_api.api = UFFD_API;
uffdio_api.features = 0;
if (ioctl(uffd, UFFDIO_API, &uffdio_api) == -1) {
perror("ioctl-UFFDIO_API failed");
exit(EXIT_FAILURE);
}
/*
* Create a private anonymous mapping. The memory will be demand-zero
* paged, that is, not yet allocated. When we actually touch the memory
* the related page will be allocated via the userfaultfd mechanism.
*/
uf_mem = mmap(NULL, UF_MEM_SIZE, PROT_READ | PROT_WRITE,
MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
if (uf_mem == MAP_FAILED) {
perror("mmap() failed");
exit(EXIT_FAILURE);
}
/*
* Register the memory range of the mapping we've just mapped to be
* handled by the userfaultfd object. In 'mode' we request to track
* missing pages (i.e. pages that have not yet been faulted-in).
*/
uffdio_register.range.start = (unsigned long) uf_mem;
uffdio_register.range.len = UF_MEM_SIZE;
uffdio_register.mode = UFFDIO_REGISTER_MODE_MISSING;
if (ioctl(uffd, UFFDIO_REGISTER, &uffdio_register) == -1) {
perror("ioctl-UFFDIO_REGISTER");
exit(EXIT_FAILURE);
}
/* Create a thread that will process the userfaultfd events */
Annotation
- Immediate include surface: `stdio.h`, `stdlib.h`, `string.h`, `linux/userfaultfd.h`, `poll.h`, `unistd.h`, `sys/ioctl.h`, `sys/syscall.h`.
- Detected declarations: `function setup_uf_mem`, `function signal_handler`, `function have_userfaultfd`, `function tm_signal_pagefault`, `function main`.
- Atlas domain: Support Tooling And Documentation / tools.
- 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.