Home Home > GIT Browse > stable
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJiri Slaby <jslaby@suse.cz>2019-02-12 22:18:26 +0100
committerJiri Slaby <jslaby@suse.cz>2019-02-12 22:21:32 +0100
commit04d407887ba95f81550acfdb90e5982ce5a50f1d (patch)
tree3b57a57521d9007717f7d742238aac6f34062d88
parentf418b8eac91b66d6c3c3f601fb3077a83a2ce280 (diff)
serial: fix race between flush_to_ldisc and tty_open
-rw-r--r--patches.kernel.org/4.20.8-339-serial-fix-race-between-flush_to_ldisc-and-tty.patch89
-rw-r--r--series.conf1
2 files changed, 90 insertions, 0 deletions
diff --git a/patches.kernel.org/4.20.8-339-serial-fix-race-between-flush_to_ldisc-and-tty.patch b/patches.kernel.org/4.20.8-339-serial-fix-race-between-flush_to_ldisc-and-tty.patch
new file mode 100644
index 0000000000..8320f29806
--- /dev/null
+++ b/patches.kernel.org/4.20.8-339-serial-fix-race-between-flush_to_ldisc-and-tty.patch
@@ -0,0 +1,89 @@
+From: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Date: Thu, 31 Jan 2019 17:43:16 +0800
+Subject: [PATCH] serial: fix race between flush_to_ldisc and tty_open
+References: bnc#1012628
+Patch-mainline: 4.20.8
+Git-commit: fedb5760648a291e949f2380d383b5b2d2749b5e
+
+commit fedb5760648a291e949f2380d383b5b2d2749b5e upstream.
+
+There still is a race window after the commit b027e2298bd588
+("tty: fix data race between tty_init_dev and flush of buf"),
+and we encountered this crash issue if receive_buf call comes
+before tty initialization completes in tty_open and
+tty->driver_data may be NULL.
+
+CPU0 CPU1
+---- ----
+ tty_open
+ tty_init_dev
+ tty_ldisc_unlock
+ schedule
+flush_to_ldisc
+ receive_buf
+ tty_port_default_receive_buf
+ tty_ldisc_receive_buf
+ n_tty_receive_buf_common
+ __receive_buf
+ uart_flush_chars
+ uart_start
+ /*tty->driver_data is NULL*/
+ tty->ops->open
+ /*init tty->driver_data*/
+
+it can be fixed by extending ldisc semaphore lock in tty_init_dev
+to driver_data initialized completely after tty->ops->open(), but
+this will lead to get lock on one function and unlock in some other
+function, and hard to maintain, so fix this race only by checking
+tty->driver_data when receiving, and return if tty->driver_data
+is NULL, and n_tty_receive_buf_common maybe calls uart_unthrottle,
+so add the same check.
+
+Because the tty layer knows nothing about the driver associated with the
+device, the tty layer can not do anything here, it is up to the tty
+driver itself to check for this type of race. Fix up the serial driver
+to correctly check to see if it is finished binding with the device when
+being called, and if not, abort the tty calls.
+
+[Description and problem report and testing from Li RongQing, I rewrote
+the patch to be in the serial layer, not in the tty core - gregkh]
+
+Reported-by: Li RongQing <lirongqing@baidu.com>
+Tested-by: Li RongQing <lirongqing@baidu.com>
+Signed-off-by: Wang Li <wangli39@baidu.com>
+Signed-off-by: Zhang Yu <zhangyu31@baidu.com>
+Signed-off-by: Li RongQing <lirongqing@baidu.com>
+Cc: stable <stable@vger.kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Jiri Slaby <jslaby@suse.cz>
+---
+ drivers/tty/serial/serial_core.c | 6 ++++++
+ 1 file changed, 6 insertions(+)
+
+diff --git a/drivers/tty/serial/serial_core.c b/drivers/tty/serial/serial_core.c
+index 5c01bb6d1c24..556f50aa1b58 100644
+--- a/drivers/tty/serial/serial_core.c
++++ b/drivers/tty/serial/serial_core.c
+@@ -130,6 +130,9 @@ static void uart_start(struct tty_struct *tty)
+ struct uart_port *port;
+ unsigned long flags;
+
++ if (!state)
++ return;
++
+ port = uart_port_lock(state, flags);
+ __uart_start(tty);
+ uart_port_unlock(port, flags);
+@@ -727,6 +730,9 @@ static void uart_unthrottle(struct tty_struct *tty)
+ upstat_t mask = UPSTAT_SYNC_FIFO;
+ struct uart_port *port;
+
++ if (!state)
++ return;
++
+ port = uart_port_ref(state);
+ if (!port)
+ return;
+--
+2.20.1
+
diff --git a/series.conf b/series.conf
index 3ee7884d91..ce92e6b8dc 100644
--- a/series.conf
+++ b/series.conf
@@ -1075,6 +1075,7 @@
patches.kernel.org/4.20.8-336-x86-MCE-Initialize-mce.bank-in-the-case-of-a-f.patch
patches.kernel.org/4.20.8-337-perf-core-Don-t-WARN-for-impossible-ring-buffe.patch
patches.kernel.org/4.20.8-338-perf-tests-evsel-tp-sched-Fix-bitwise-operator.patch
+ patches.kernel.org/4.20.8-339-serial-fix-race-between-flush_to_ldisc-and-tty.patch
########################################################
# Build fixes that apply to the vanilla kernel too.