From: Karl Mehltretter <kmehltretter@gmail.com>
To: Andrew Morton <akpm@linux-foundation.org>
Cc: Karl Mehltretter <kmehltretter@gmail.com>,
Andrey Konovalov <andreyknvl@gmail.com>,
Dmitry Vyukov <dvyukov@google.com>,
Alexander Potapenko <glider@google.com>,
Marco Elver <elver@google.com>,
Bradley Morgan <include@grrlz.net>,
kasan-dev@googlegroups.com, linux-kernel@vger.kernel.org
Subject: [PATCH 1/5] kcov: add kcov_pause()/kcov_resume() helpers
Date: Fri, 7 Aug 2026 22:50:23 +0200 [thread overview]
Message-ID: <20260807205027.31972-2-kmehltretter@gmail.com> (raw)
In-Reply-To: <20260807205027.31972-1-kmehltretter@gmail.com>
Interrupt-return work can run after HARDIRQ_OFFSET is dropped, when
in_task() is true. KCOV then attributes instrumented callees to the
interrupted task.
Add a KCOV_PAUSED bit next to KCOV_IN_CTXSW and mask both in
kcov_mode_enabled(). The context switch suppression keeps its own bit:
kcov_prepare_switch() runs on the previous task and kcov_finish_switch()
on the one switched in, so its lifetime is not a pause section.
Sections nest by passing the state returned by kcov_pause() to
kcov_resume(). Both operate on current. When task KCOV is active, remote
softirq sections save and restore the complete mode, preserving the
pause state.
The helpers are __always_inline, and the caller must be uninstrumented:
inlining does not remove the caller's own coverage callbacks.
Assisted-by: Claude:claude-opus-4-8
Assisted-by: Claude:claude-fable-5
Signed-off-by: Karl Mehltretter <kmehltretter@gmail.com>
---
include/linux/kcov.h | 25 ++++++++++++++++++++++++-
kernel/kcov.c | 2 +-
2 files changed, 25 insertions(+), 2 deletions(-)
diff --git a/include/linux/kcov.h b/include/linux/kcov.h
index 895b761b2db1..5a0a1a9bb7ef 100644
--- a/include/linux/kcov.h
+++ b/include/linux/kcov.h
@@ -2,6 +2,7 @@
#ifndef _LINUX_KCOV_H
#define _LINUX_KCOV_H
+#include <linux/bits.h>
#include <linux/sched.h>
#include <uapi/linux/kcov.h>
@@ -23,7 +24,8 @@ enum kcov_mode {
KCOV_MODE_TRACE_CMP = 3,
};
-#define KCOV_IN_CTXSW (1 << 30)
+#define KCOV_IN_CTXSW BIT(30)
+#define KCOV_PAUSED BIT(29)
void kcov_task_init(struct task_struct *t);
void kcov_task_exit(struct task_struct *t);
@@ -38,6 +40,25 @@ do { \
(t)->kcov_mode &= ~KCOV_IN_CTXSW; \
} while (0)
+/*
+ * Pause coverage for current. Pass the returned state to kcov_resume().
+ * Callers must be uninstrumented.
+ */
+static __always_inline unsigned int kcov_pause(struct task_struct *t)
+{
+ unsigned int paused;
+
+ paused = t->kcov_mode & KCOV_PAUSED;
+ t->kcov_mode |= KCOV_PAUSED;
+ return paused;
+}
+
+static __always_inline void kcov_resume(struct task_struct *t, unsigned int paused)
+{
+ if (!paused)
+ t->kcov_mode &= ~KCOV_PAUSED;
+}
+
/* See Documentation/dev-tools/kcov.rst for usage details. */
void kcov_remote_start(u64 handle);
void kcov_remote_stop(void);
@@ -93,6 +114,8 @@ void __sanitizer_cov_trace_switch(kcov_u64 val, void *cases);
static inline void kcov_task_init(struct task_struct *t) {}
static inline void kcov_task_exit(struct task_struct *t) {}
+static inline unsigned int kcov_pause(struct task_struct *t) { return 0; }
+static inline void kcov_resume(struct task_struct *t, unsigned int paused) {}
static inline void kcov_prepare_switch(struct task_struct *t) {}
static inline void kcov_finish_switch(struct task_struct *t) {}
static inline void kcov_remote_start(u64 handle) {}
diff --git a/kernel/kcov.c b/kernel/kcov.c
index 1df373fb562b..83d53e383822 100644
--- a/kernel/kcov.c
+++ b/kernel/kcov.c
@@ -830,7 +830,7 @@ static const struct file_operations kcov_fops = {
static inline bool kcov_mode_enabled(unsigned int mode)
{
- return (mode & ~KCOV_IN_CTXSW) != KCOV_MODE_DISABLED;
+ return (mode & ~(KCOV_IN_CTXSW | KCOV_PAUSED)) != KCOV_MODE_DISABLED;
}
static void kcov_remote_softirq_start(struct task_struct *t)
--
2.53.0
next prev parent reply other threads:[~2026-08-07 20:50 UTC|newest]
Thread overview: 12+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-08-07 20:50 [PATCH 0/5] kcov: suppress timer and scheduler coverage leaks Karl Mehltretter
2026-08-07 20:50 ` Karl Mehltretter [this message]
2026-08-08 1:16 ` [PATCH 1/5] kcov: add kcov_pause()/kcov_resume() helpers Bradley Morgan
2026-08-07 20:50 ` [PATCH 2/5] hrtimer: pause KCOV during deferred rearm Karl Mehltretter
2026-08-08 1:19 ` Bradley Morgan
2026-08-07 20:50 ` [PATCH 3/5] sched: pause KCOV in __schedule() Karl Mehltretter
2026-08-08 1:21 ` Bradley Morgan
2026-08-07 20:50 ` [PATCH 4/5] sched: pause KCOV in try_to_wake_up() Karl Mehltretter
2026-08-07 21:00 ` sashiko-bot
2026-08-08 1:28 ` Bradley Morgan
2026-08-07 20:50 ` [PATCH 5/5] sched: pause KCOV in wake_up_new_task() Karl Mehltretter
2026-08-08 1:36 ` Bradley Morgan
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260807205027.31972-2-kmehltretter@gmail.com \
--to=kmehltretter@gmail.com \
--cc=akpm@linux-foundation.org \
--cc=andreyknvl@gmail.com \
--cc=dvyukov@google.com \
--cc=elver@google.com \
--cc=glider@google.com \
--cc=include@grrlz.net \
--cc=kasan-dev@googlegroups.com \
--cc=linux-kernel@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox