From: Greg Kroah-Hartman Date: Mon, 9 Aug 2021 07:34:01 +0000 (+0200) Subject: 5.10-stable patches X-Git-Tag: v4.4.280~69 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=e8a020b080b0973b1cfe26875651427ac7669cfa;p=thirdparty%2Fkernel%2Fstable-queue.git 5.10-stable patches added patches: alsa-seq-fix-racy-deletion-of-subscriber.patch revert-acpica-fix-memory-leak-caused-by-_cid-repair-function.patch --- diff --git a/queue-5.10/alsa-seq-fix-racy-deletion-of-subscriber.patch b/queue-5.10/alsa-seq-fix-racy-deletion-of-subscriber.patch new file mode 100644 index 00000000000..42c290f050a --- /dev/null +++ b/queue-5.10/alsa-seq-fix-racy-deletion-of-subscriber.patch @@ -0,0 +1,116 @@ +From 97367c97226aab8b298ada954ce12659ee3ad2a4 Mon Sep 17 00:00:00 2001 +From: Takashi Iwai +Date: Tue, 3 Aug 2021 13:43:12 +0200 +Subject: ALSA: seq: Fix racy deletion of subscriber + +From: Takashi Iwai + +commit 97367c97226aab8b298ada954ce12659ee3ad2a4 upstream. + +It turned out that the current implementation of the port subscription +is racy. The subscription contains two linked lists, and we have to +add to or delete from both lists. Since both connection and +disconnection procedures perform the same order for those two lists +(i.e. src list, then dest list), when a deletion happens during a +connection procedure, the src list may be deleted before the dest list +addition completes, and this may lead to a use-after-free or an Oops, +even though the access to both lists are protected via mutex. + +The simple workaround for this race is to change the access order for +the disconnection, namely, dest list, then src list. This assures +that the connection has been established when disconnecting, and also +the concurrent deletion can be avoided. + +Reported-and-tested-by: folkert +Cc: +Link: https://lore.kernel.org/r/20210801182754.GP890690@belle.intranet.vanheusden.com +Link: https://lore.kernel.org/r/20210803114312.2536-1-tiwai@suse.de +Signed-off-by: Takashi Iwai +Signed-off-by: Greg Kroah-Hartman +--- + sound/core/seq/seq_ports.c | 39 +++++++++++++++++++++++++++------------ + 1 file changed, 27 insertions(+), 12 deletions(-) + +--- a/sound/core/seq/seq_ports.c ++++ b/sound/core/seq/seq_ports.c +@@ -514,10 +514,11 @@ static int check_and_subscribe_port(stru + return err; + } + +-static void delete_and_unsubscribe_port(struct snd_seq_client *client, +- struct snd_seq_client_port *port, +- struct snd_seq_subscribers *subs, +- bool is_src, bool ack) ++/* called with grp->list_mutex held */ ++static void __delete_and_unsubscribe_port(struct snd_seq_client *client, ++ struct snd_seq_client_port *port, ++ struct snd_seq_subscribers *subs, ++ bool is_src, bool ack) + { + struct snd_seq_port_subs_info *grp; + struct list_head *list; +@@ -525,7 +526,6 @@ static void delete_and_unsubscribe_port( + + grp = is_src ? &port->c_src : &port->c_dest; + list = is_src ? &subs->src_list : &subs->dest_list; +- down_write(&grp->list_mutex); + write_lock_irq(&grp->list_lock); + empty = list_empty(list); + if (!empty) +@@ -535,6 +535,18 @@ static void delete_and_unsubscribe_port( + + if (!empty) + unsubscribe_port(client, port, grp, &subs->info, ack); ++} ++ ++static void delete_and_unsubscribe_port(struct snd_seq_client *client, ++ struct snd_seq_client_port *port, ++ struct snd_seq_subscribers *subs, ++ bool is_src, bool ack) ++{ ++ struct snd_seq_port_subs_info *grp; ++ ++ grp = is_src ? &port->c_src : &port->c_dest; ++ down_write(&grp->list_mutex); ++ __delete_and_unsubscribe_port(client, port, subs, is_src, ack); + up_write(&grp->list_mutex); + } + +@@ -590,27 +602,30 @@ int snd_seq_port_disconnect(struct snd_s + struct snd_seq_client_port *dest_port, + struct snd_seq_port_subscribe *info) + { +- struct snd_seq_port_subs_info *src = &src_port->c_src; ++ struct snd_seq_port_subs_info *dest = &dest_port->c_dest; + struct snd_seq_subscribers *subs; + int err = -ENOENT; + +- down_write(&src->list_mutex); ++ /* always start from deleting the dest port for avoiding concurrent ++ * deletions ++ */ ++ down_write(&dest->list_mutex); + /* look for the connection */ +- list_for_each_entry(subs, &src->list_head, src_list) { ++ list_for_each_entry(subs, &dest->list_head, dest_list) { + if (match_subs_info(info, &subs->info)) { +- atomic_dec(&subs->ref_count); /* mark as not ready */ ++ __delete_and_unsubscribe_port(dest_client, dest_port, ++ subs, false, ++ connector->number != dest_client->number); + err = 0; + break; + } + } +- up_write(&src->list_mutex); ++ up_write(&dest->list_mutex); + if (err < 0) + return err; + + delete_and_unsubscribe_port(src_client, src_port, subs, true, + connector->number != src_client->number); +- delete_and_unsubscribe_port(dest_client, dest_port, subs, false, +- connector->number != dest_client->number); + kfree(subs); + return 0; + } diff --git a/queue-5.10/revert-acpica-fix-memory-leak-caused-by-_cid-repair-function.patch b/queue-5.10/revert-acpica-fix-memory-leak-caused-by-_cid-repair-function.patch new file mode 100644 index 00000000000..a1faec44a23 --- /dev/null +++ b/queue-5.10/revert-acpica-fix-memory-leak-caused-by-_cid-repair-function.patch @@ -0,0 +1,36 @@ +From 6511a8b5b7a65037340cd8ee91a377811effbc83 Mon Sep 17 00:00:00 2001 +From: "Rafael J. Wysocki" +Date: Tue, 3 Aug 2021 18:14:44 +0200 +Subject: Revert "ACPICA: Fix memory leak caused by _CID repair function" + +From: Rafael J. Wysocki + +commit 6511a8b5b7a65037340cd8ee91a377811effbc83 upstream. + +Revert commit c27bac0314131 ("ACPICA: Fix memory leak caused by _CID +repair function") which is reported to cause a boot issue on Acer +Swift 3 (SF314-51). + +Reported-by: Adrien Precigout +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Greg Kroah-Hartman +--- + drivers/acpi/acpica/nsrepair2.c | 7 ------- + 1 file changed, 7 deletions(-) + +--- a/drivers/acpi/acpica/nsrepair2.c ++++ b/drivers/acpi/acpica/nsrepair2.c +@@ -375,13 +375,6 @@ acpi_ns_repair_CID(struct acpi_evaluate_ + + (*element_ptr)->common.reference_count = + original_ref_count; +- +- /* +- * The original_element holds a reference from the package object +- * that represents _HID. Since a new element was created by _HID, +- * remove the reference from the _CID package. +- */ +- acpi_ut_remove_reference(original_element); + } + + element_ptr++;