From: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
To: linux-kernel@vger.kernel.org
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
stable@vger.kernel.org,
"Steven Rostedt (VMware)" <rostedt@goodmis.org>,
Sasha Levin <sashal@kernel.org>
Subject: [PATCH 4.4 01/64] ring-buffer: Fix recursion protection transitions between interrupt context
Date: Tue, 17 Nov 2020 14:04:24 +0100 [thread overview]
Message-ID: <20201117122106.199383932@linuxfoundation.org> (raw)
In-Reply-To: <20201117122106.144800239@linuxfoundation.org>
From: Steven Rostedt (VMware) <rostedt@goodmis.org>
[ Upstream commit b02414c8f045ab3b9afc816c3735bc98c5c3d262 ]
The recursion protection of the ring buffer depends on preempt_count() to be
correct. But it is possible that the ring buffer gets called after an
interrupt comes in but before it updates the preempt_count(). This will
trigger a false positive in the recursion code.
Use the same trick from the ftrace function callback recursion code which
uses a "transition" bit that gets set, to allow for a single recursion for
to handle transitions between contexts.
Cc: stable@vger.kernel.org
Fixes: 567cd4da54ff4 ("ring-buffer: User context bit recursion checking")
Signed-off-by: Steven Rostedt (VMware) <rostedt@goodmis.org>
Signed-off-by: Sasha Levin <sashal@kernel.org>
---
kernel/trace/ring_buffer.c | 54 +++++++++++++++++++++++++++++++-------
1 file changed, 44 insertions(+), 10 deletions(-)
diff --git a/kernel/trace/ring_buffer.c b/kernel/trace/ring_buffer.c
index 1c1ecc1d49ad2..547a3a5ac57b5 100644
--- a/kernel/trace/ring_buffer.c
+++ b/kernel/trace/ring_buffer.c
@@ -416,14 +416,16 @@ struct rb_event_info {
/*
* Used for which event context the event is in.
- * NMI = 0
- * IRQ = 1
- * SOFTIRQ = 2
- * NORMAL = 3
+ * TRANSITION = 0
+ * NMI = 1
+ * IRQ = 2
+ * SOFTIRQ = 3
+ * NORMAL = 4
*
* See trace_recursive_lock() comment below for more details.
*/
enum {
+ RB_CTX_TRANSITION,
RB_CTX_NMI,
RB_CTX_IRQ,
RB_CTX_SOFTIRQ,
@@ -2585,10 +2587,10 @@ rb_wakeups(struct ring_buffer *buffer, struct ring_buffer_per_cpu *cpu_buffer)
* a bit of overhead in something as critical as function tracing,
* we use a bitmask trick.
*
- * bit 0 = NMI context
- * bit 1 = IRQ context
- * bit 2 = SoftIRQ context
- * bit 3 = normal context.
+ * bit 1 = NMI context
+ * bit 2 = IRQ context
+ * bit 3 = SoftIRQ context
+ * bit 4 = normal context.
*
* This works because this is the order of contexts that can
* preempt other contexts. A SoftIRQ never preempts an IRQ
@@ -2611,6 +2613,30 @@ rb_wakeups(struct ring_buffer *buffer, struct ring_buffer_per_cpu *cpu_buffer)
* The least significant bit can be cleared this way, and it
* just so happens that it is the same bit corresponding to
* the current context.
+ *
+ * Now the TRANSITION bit breaks the above slightly. The TRANSITION bit
+ * is set when a recursion is detected at the current context, and if
+ * the TRANSITION bit is already set, it will fail the recursion.
+ * This is needed because there's a lag between the changing of
+ * interrupt context and updating the preempt count. In this case,
+ * a false positive will be found. To handle this, one extra recursion
+ * is allowed, and this is done by the TRANSITION bit. If the TRANSITION
+ * bit is already set, then it is considered a recursion and the function
+ * ends. Otherwise, the TRANSITION bit is set, and that bit is returned.
+ *
+ * On the trace_recursive_unlock(), the TRANSITION bit will be the first
+ * to be cleared. Even if it wasn't the context that set it. That is,
+ * if an interrupt comes in while NORMAL bit is set and the ring buffer
+ * is called before preempt_count() is updated, since the check will
+ * be on the NORMAL bit, the TRANSITION bit will then be set. If an
+ * NMI then comes in, it will set the NMI bit, but when the NMI code
+ * does the trace_recursive_unlock() it will clear the TRANSTION bit
+ * and leave the NMI bit set. But this is fine, because the interrupt
+ * code that set the TRANSITION bit will then clear the NMI bit when it
+ * calls trace_recursive_unlock(). If another NMI comes in, it will
+ * set the TRANSITION bit and continue.
+ *
+ * Note: The TRANSITION bit only handles a single transition between context.
*/
static __always_inline int
@@ -2629,8 +2655,16 @@ trace_recursive_lock(struct ring_buffer_per_cpu *cpu_buffer)
} else
bit = RB_CTX_NORMAL;
- if (unlikely(val & (1 << bit)))
- return 1;
+ if (unlikely(val & (1 << bit))) {
+ /*
+ * It is possible that this was called by transitioning
+ * between interrupt context, and preempt_count() has not
+ * been updated yet. In this case, use the TRANSITION bit.
+ */
+ bit = RB_CTX_TRANSITION;
+ if (val & (1 << bit))
+ return 1;
+ }
val |= (1 << bit);
cpu_buffer->current_context = val;
--
2.27.0
next prev parent reply other threads:[~2020-11-17 13:06 UTC|newest]
Thread overview: 68+ messages / expand[flat|nested] mbox.gz Atom feed top
2020-11-17 13:04 [PATCH 4.4 00/64] 4.4.244-rc1 review Greg Kroah-Hartman
2020-11-17 13:04 ` Greg Kroah-Hartman [this message]
2020-11-17 13:04 ` [PATCH 4.4 02/64] gfs2: Wake up when sd_glock_disposal becomes zero Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 03/64] mm: mempolicy: fix potential pte_unmap_unlock pte error Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 04/64] time: Prevent undefined behaviour in timespec64_to_ns() Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 05/64] btrfs: reschedule when cloning lots of extents Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 06/64] net: xfrm: fix a race condition during allocing spi Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 07/64] perf tools: Add missing swap for ino_generation Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 08/64] ALSA: hda: prevent undefined shift in snd_hdac_ext_bus_get_link() Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 09/64] can: dev: can_get_echo_skb(): prevent call to kfree_skb() in hard IRQ context Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 10/64] can: dev: __can_get_echo_skb(): fix real payload length return value for RTR frames Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 11/64] can: can_create_echo_skb(): fix echo skb generation: always use skb_clone() Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 12/64] can: peak_usb: add range checking in decode operations Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 13/64] can: peak_usb: peak_usb_get_ts_time(): fix timestamp wrapping Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 14/64] Btrfs: fix missing error return if writeback for extent buffer never started Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 15/64] pinctrl: devicetree: Avoid taking direct reference to device name string Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 16/64] i40e: Wrong truncation from u16 to u8 Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 17/64] i40e: Fix of memory leak and integer truncation in i40e_virtchnl.c Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 18/64] geneve: add transport ports in route lookup for geneve Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 19/64] ath9k_htc: Use appropriate rs_datalen type Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 20/64] usb: gadget: goku_udc: fix potential crashes in probe Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 21/64] gfs2: Free rd_bits later in gfs2_clear_rgrpd to fix use-after-free Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 22/64] gfs2: check for live vs. read-only file system in gfs2_fitrim Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 23/64] drm/amdgpu: perform srbm soft reset always on SDMA resume Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 24/64] mac80211: fix use of skb payload instead of header Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 25/64] mac80211: always wind down STA state Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 26/64] cfg80211: regulatory: Fix inconsistent format argument Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 27/64] iommu/amd: Increase interrupt remapping table limit to 512 entries Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 28/64] xfs: fix a missing unlock on error in xfs_fs_map_blocks Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 29/64] of/address: Fix of_node memory leak in of_dma_is_coherent Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 30/64] cosa: Add missing kfree in error path of cosa_write Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 31/64] perf: Fix get_recursion_context() Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 32/64] ext4: correctly report "not supported" for {usr,grp}jquota when !CONFIG_QUOTA Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 33/64] ext4: unlock xattr_sem properly in ext4_inline_data_truncate() Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 34/64] usb: cdc-acm: Add DISABLE_ECHO for Renesas USB Download mode Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 35/64] mei: protect mei_cl_mtu from null dereference Greg Kroah-Hartman
2020-11-17 13:04 ` [PATCH 4.4 36/64] ocfs2: initialize ip_next_orphan Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 37/64] dont dump the threads that had been already exiting when zapped Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 38/64] drm/gma500: Fix out-of-bounds access to struct drm_device.vblank[] Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 39/64] pinctrl: amd: use higher precision for 512 RtcClk Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 40/64] pinctrl: amd: fix incorrect way to disable debounce filter Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 41/64] swiotlb: fix "x86: Dont panic if can not alloc buffer for swiotlb" Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 42/64] IPv6: Set SIT tunnel hard_header_len to zero Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 43/64] net/af_iucv: fix null pointer dereference on shutdown Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 44/64] net/x25: Fix null-ptr-deref in x25_connect Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 45/64] net: Update window_clamp if SOCK_RCVBUF is set Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 46/64] random32: make prandom_u32() output unpredictable Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 47/64] x86/speculation: Allow IBPB to be conditionally enabled on CPUs with always-on STIBP Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 48/64] xen/events: avoid removing an event channel while handling it Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 49/64] xen/events: add a proper barrier to 2-level uevent unmasking Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 50/64] xen/events: fix race in evtchn_fifo_unmask() Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 51/64] xen/events: add a new "late EOI" evtchn framework Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 52/64] xen/blkback: use lateeoi irq binding Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 53/64] xen/netback: " Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 54/64] xen/scsiback: " Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 55/64] xen/pciback: " Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 56/64] xen/events: switch user event channels to lateeoi model Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 57/64] xen/events: use a common cpu hotplug hook for event channels Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 58/64] xen/events: defer eoi in case of excessive number of events Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 59/64] xen/events: block rogue events for some time Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 60/64] perf/core: Fix race in the perf_mmap_close() function Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 61/64] Revert "kernel/reboot.c: convert simple_strtoul to kstrtoint" Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 62/64] reboot: fix overflow parsing reboot cpu number Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 63/64] ext4: fix leaking sysfs kobject after failed mount Greg Kroah-Hartman
2020-11-17 13:05 ` [PATCH 4.4 64/64] Convert trailing spaces and periods in path components Greg Kroah-Hartman
2020-11-17 18:27 ` [PATCH 4.4 00/64] 4.4.244-rc1 review Pavel Machek
2020-11-18 11:25 ` Naresh Kamboju
2020-11-18 15:22 ` Guenter Roeck
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=20201117122106.199383932@linuxfoundation.org \
--to=gregkh@linuxfoundation.org \
--cc=linux-kernel@vger.kernel.org \
--cc=rostedt@goodmis.org \
--cc=sashal@kernel.org \
--cc=stable@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;
as well as URLs for NNTP newsgroup(s).