[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <20201028115612.780796355@goodmis.org>
Date: Wed, 28 Oct 2020 07:52:47 -0400
From: Steven Rostedt <rostedt@...dmis.org>
To: linux-kernel@...r.kernel.org
Cc: Masami Hiramatsu <mhiramat@...nel.org>,
Andrew Morton <akpm@...ux-foundation.org>
Subject: [PATCH 3/9] ftrace: Optimize testing what context current is in
From: "Steven Rostedt (VMware)" <rostedt@...dmis.org>
The preempt_count() is not a simple location in memory, it could be part of
per_cpu code or more. Each access to preempt_count(), or one of its accessor
functions (like in_interrupt()) takes several cycles. By reading
preempt_count() once, and then doing tests to find the context against the
value return is slightly faster than using in_nmi() and in_interrupt().
Signed-off-by: Steven Rostedt (VMware) <rostedt@...dmis.org>
---
include/linux/trace_recursion.h | 33 ++++++++++++++++++++-------------
1 file changed, 20 insertions(+), 13 deletions(-)
diff --git a/include/linux/trace_recursion.h b/include/linux/trace_recursion.h
index da17a1144bf4..04d21e9ec48b 100644
--- a/include/linux/trace_recursion.h
+++ b/include/linux/trace_recursion.h
@@ -111,22 +111,29 @@ enum {
#define TRACE_CONTEXT_MASK TRACE_LIST_MAX
+/*
+ * Used for setting context
+ * NMI = 0
+ * IRQ = 1
+ * SOFTIRQ = 2
+ * NORMAL = 3
+ */
+enum {
+ TRACE_CTX_NMI,
+ TRACE_CTX_IRQ,
+ TRACE_CTX_SOFTIRQ,
+ TRACE_CTX_NORMAL,
+};
+
static __always_inline int trace_get_context_bit(void)
{
- int bit;
-
- if (in_interrupt()) {
- if (in_nmi())
- bit = 0;
+ unsigned long pc = preempt_count();
- else if (in_irq())
- bit = 1;
- else
- bit = 2;
- } else
- bit = 3;
-
- return bit;
+ if (!(pc & (NMI_MASK | HARDIRQ_MASK | SOFTIRQ_OFFSET)))
+ return TRACE_CTX_NORMAL;
+ else
+ return pc & NMI_MASK ? TRACE_CTX_NMI :
+ pc & HARDIRQ_MASK ? TRACE_CTX_IRQ : TRACE_CTX_SOFTIRQ;
}
static __always_inline int trace_test_and_set_recursion(int start, int max)
--
2.28.0
Powered by blists - more mailing lists