Thread (21 messages) 21 messages, 4 authors, 2024-08-23

Re: [BUG] tracing: dynamic ftrace selftest detected failures

From: Mark Rutland <mark.rutland@arm.com>
Date: 2024-08-21 15:42:11
Also in: lkml, llvm

On Wed, Aug 21, 2024 at 04:32:46PM +0100, Mark Rutland wrote:
On Wed, Aug 21, 2024 at 07:05:39AM +0900, Masami Hiramatsu wrote:
quoted
On Tue, 20 Aug 2024 08:10:42 -0700
Sami Tolvanen [off-list ref] wrote:
quoted
On Tue, Aug 20, 2024 at 3:48 AM Mark Rutland [off-list ref] wrote:
quoted
On Tue, Aug 20, 2024 at 10:03:30AM +0900, Masami Hiramatsu wrote:
quoted
On Mon, 19 Aug 2024 12:02:44 -0400
Steven Rostedt [off-list ref] wrote:
quoted
On Tue, 20 Aug 2024 00:56:49 +0900
Masami Hiramatsu (Google) [off-list ref] wrote:
quoted
quoted
We may need to add "noinline" or something to make sure those functions
don't get inlined for LTO.
Yeah, we need such option at least for function call test.
Could you add the noinline, and if it fixes the issue send a patch?
I found the target function already has "noinline". I tried to add noinline
to the testing function (callsite), but it also did not work.
I think "noinline" is for the compiler, but LTO is done by the linker.
If LTO is breaking noinline, then that has much larger implications for
noinstr code and similar, and means that LTO is unsound...
The noinline attribute is preserved in LLVM IR, so it should continue
to work with LTO. Which function are we talking about here? Are you
sure the function was inlined instead of being dropped completely?
Does marking the function __used help?
We are talking about trace_selftest_startup_dynamic_tracing() in
kernel/trace/trace_selftest.c. The callee is func() which is actually
DYN_FTRACE_TEST_NAME() in kernel/trace/trace_selftest_dynamic.c.
That function passed as pointer (but the compiler can embed it by constant
propagation.)
Ah, so IIUC the function isn't being inlined; the call is being
optimized away becase callee() has no side-effects.

That can happen without LTO if the caller is in the same compilation
unit, and I have worked around that in the past by adding a barrier()
into the callee.
FWIW, that was in samples/ftrace/ftrace-ops.c, where tracee_relevant() and
tracee_irrelevant() have the barrier():

| /*
|  * Marked as noinline to ensure that an out-of-line traceable copy is
|  * generated by the compiler.
|  *
|  * The barrier() ensures the compiler won't elide calls by determining there
|  * are no side-effects.
|  */
| static noinline void tracee_relevant(void)
| {
|         barrier();
| }

... so we already have precedent for that in tracing code.

Mark.
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help