Conversation
casaroli
force-pushed
the
fork-ostest-pffault
branch
from
September 26, 2026 22:52
b863480 to
52df455
Compare
casaroli
marked this pull request as ready for review
September 26, 2026 22:52
| A test that deliberately tries to escape the kernel/user boundary of | ||
| a protected or kernel build, and checks that the attempt is contained: | ||
| the offending task is terminated and everything else keeps running. | ||
| the offending process is terminated and everything else keeps running. |
Contributor
There was a problem hiding this comment.
let's merge the last two patch into one
…space. A small user program that reads or writes one address, by default 0x3fc98000, the base of the ESP32-S3 kernel DRAM region. A user process must not reach it, so the access must fault and only the process must die. "pffault w" makes the access a store, and a second argument names another address. With CONFIG_ESP32S3_PAGEFAULT and CONFIG_ESP32S3_PAGEFAULT_SELFTEST on the kernel side, "pffault r 0x80000000" exercises the recoverable-fault restart path, and "pffault r 0x0" the report path. Assisted-by: Claude Code:claude-opus-5-5 Signed-off-by: Marco Casaroli <marco.casaroli@gmail.com>
…lds. A test that a user process which makes a forbidden access is stopped, and that nothing else is. It spawns this program again as a separate process to make the access, because a kernel build does not give user code task_create(), and checks that the offender died, that the caller still runs and that a canary thread kept counting. The canary is what tells "the offender was contained" from "the whole system stopped". Every target has the outcome it expects: self the process's own data must succeed kernel kernel memory must fault periph a peripheral register must fault unmapped an address with no mapping must fault "self" is the control. Without it a build that refuses every access passes every other check. An MMU keeps processes apart but does not stop one reaching a peripheral, and an unmapped access is refused by another mechanism again, so neither is covered by the kernel target. The offender allocates memory and opens a file before the access. The test reads /proc/meminfo and /proc/<pid>/group/fd while it lives and after it is reaped, and fails if the counts never rose, since "the same before and after" says nothing if the resources were never seen. The addresses come from Kconfig, because a user process cannot see kernel symbols. A protected build derives the kernel target from CONFIG_NUTTX_USERSPACE when none is set. Assisted-by: Claude Code:claude-opus-5-5 Signed-off-by: Marco Casaroli <marco.casaroli@gmail.com>
casaroli
force-pushed
the
fork-ostest-pffault
branch
from
September 28, 2026 17:50
52df455 to
32912a1
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Two test programs for a protected build and a kernel build.
examples/pffaulttouches one kernel address from a user process. It is small and direct, and it shows the fault and the signal.examples/sandboxis the general test. Every target carries the outcome it expects, so the test fails a build that refuses everything as well as one that permits everything.selfkernelperiphunmappedThe
selftarget is the control. Without it a build that refuses every access passes every other check.The offending process allocates memory, writes to all of it, and opens a file before it makes the access. It still holds both when it dies. The test reads
/proc/meminfobefore, while the offender lives, and after it is reaped, and it reads/proc/<pid>/group/fdwhile the offender lives. A count that never rises is reported as a failure, because "the same before and after" says nothing if the memory was never seen.The offender is a process and not a task. A kernel build does not give
task_create()to user code, soposix_spawn()is used.Impact
Two new example programs,
pffaultandsandbox. No existing configuration in this repository selects them. The separatefork()andvfork()tests this branch used to carry are upstream already, through #3685.Testing
Board: ESP32-S3-DevKitC with an ESP32-S3-WROOM-2 N32R8V, 32 MB octal flash and 8 MB PSRAM.
Configuration:
esp32s3-devkit:kernel_oct, aBUILD_KERNELimage.The run above was made three times, which is twelve process deaths. The memory returns to the same value each time, and the descriptors are closed each time.
ostestruns to the end on the same image.tools/checkpatch.sh -c -u -m -greports no errors.