diff options
Diffstat (limited to 'internal')
| -rw-r--r-- | internal/generate/classify_test.go | 14 | ||||
| -rw-r--r-- | internal/generate/family.go | 18 | ||||
| -rw-r--r-- | internal/generate/family_test.go | 10 |
3 files changed, 38 insertions, 4 deletions
diff --git a/internal/generate/classify_test.go b/internal/generate/classify_test.go index 77e19d1..bebf85e 100644 --- a/internal/generate/classify_test.go +++ b/internal/generate/classify_test.go @@ -2276,10 +2276,16 @@ func TestClassifySchedGetattrPidNotFd(t *testing.T) { // IPC like the futex_* shared-memory primitives (see family.go / family_test.go), // - return classifies as UNCLASSIFIED (0/-1, no byte transfer). // -// NOTE: get_robust_list/set_robust_list are robust-futex bookkeeping and could -// arguably sit with futex_* under IPC; that grouping question is tracked as a -// follow-up rather than changed here, since the syscalls register/query a -// per-thread pointer (like rseq) rather than operating on shared memory. +// FAMILY DECISION (resolved): get_robust_list/set_robust_list stay FamilyMisc and +// are NOT moved to FamilyIPC for "futex consistency". The boundary rule (spelled +// out next to the futex block in family.go) is operation-vs-registration: a +// syscall is IPC only if it PERFORMS the actual IPC/sync operation (futex +// wait/wake/requeue, or an op on an IPC object). These two only register/query +// the per-thread robust-futex list head pointer — per get_robust_list(2) the list +// is "managed in user space: the kernel knows only about the location of the head" +// — and never wait, wake, or touch the shared futex word. That is per-thread +// bookkeeping, structurally identical to rseq, so they share rseq's Misc family. +// The contrast assertion below (futex == IPC) pins both sides of the boundary. func TestClassifyGetRobustListPidNotFd(t *testing.T) { // Field layout mirrors the actual kernel tracepoint format for // sys_enter_get_robust_list: int pid, struct robust_list_head **head_ptr, diff --git a/internal/generate/family.go b/internal/generate/family.go index fd61961..dafbe13 100644 --- a/internal/generate/family.go +++ b/internal/generate/family.go @@ -49,6 +49,24 @@ var syscallFamilies = map[string]SyscallFamily{ // futex_waitv. The futex word is a userspace pointer, so argument capture // is handled by KindFutex (null_event); the family tag only affects // per-family aggregation/reporting. + // + // Boundary rule for the futex/IPC vs Misc split (keep consistent): a + // syscall is IPC only if it PERFORMS the actual IPC/synchronization + // operation — wait/wake/requeue on the futex word, or an operation on an + // IPC object (semaphore, message queue, shared-memory segment, pipe, etc.). + // By contrast, per-thread registration/bookkeeping that merely hands the + // kernel a pointer it consults LATER (at thread exit) is NOT IPC and stays + // in Misc. get_robust_list/set_robust_list fall in the latter camp: per + // get_robust_list(2), the robust futex list is "managed in user space: the + // kernel knows only about the location of the head of the list." They + // register/query that per-thread head pointer; they never wait, wake, or + // touch the shared futex word themselves. That makes them structurally + // identical to rseq (per-thread restartable-sequences area registration), + // so both deliberately fall through to FamilyMisc (they are absent from this + // explicit table by design — see ClassifySyscallFamily's default and the + // rseq/robust_list assertions in family_test.go / classify_test.go). Do not + // promote them to IPC for "futex consistency": the consistent axis is + // operation-vs-registration, not name similarity. "futex": FamilyIPC, "futex_wait": FamilyIPC, "futex_wake": FamilyIPC, "futex_requeue": FamilyIPC, "futex_waitv": FamilyIPC, diff --git a/internal/generate/family_test.go b/internal/generate/family_test.go index 71f0d0d..7302919 100644 --- a/internal/generate/family_test.go +++ b/internal/generate/family_test.go @@ -152,6 +152,16 @@ func TestClassifySyscallFamily(t *testing.T) { // (also Misc). set_tid_address is Process, but rseq is grouped with the // robust-list pair rather than the tid-address syscall; keep this in sync // with the Misc list in docs/syscall-tracing-plan.md. + // + // Boundary rule (see family.go futex block): a syscall is IPC only if it + // PERFORMS the actual IPC/sync operation (futex wait/wake/requeue, or an + // op on an IPC object). set_robust_list/get_robust_list merely register or + // query the per-thread robust-futex list head pointer — "managed in user + // space: the kernel knows only about the location of the head" + // (get_robust_list(2)) — and never wait/wake or touch the shared futex + // word. That is registration/bookkeeping, exactly like rseq, so they stay + // Misc and are NOT promoted to IPC alongside futex_* (asserted as IPC just + // above). The split axis is operation-vs-registration, not name similarity. {"sys_enter_rseq", FamilyMisc}, {"sys_exit_rseq", FamilyMisc}, {"sys_enter_set_robust_list", FamilyMisc}, |
