From: Greg Kroah-Hartman Date: Thu, 15 Jul 2021 14:15:41 +0000 (+0200) Subject: 5.4-stable patches X-Git-Tag: v5.4.133~29 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=5eaf53dba09bc69f196e6f9e8bfdde94e67e71c4;p=thirdparty%2Fkernel%2Fstable-queue.git 5.4-stable patches added patches: asoc-tegra-set-driver_name-tegra-for-all-machine-drivers.patch coresight-tmc-etf-fix-global-out-of-bounds-in-tmc_update_etf_buffer.patch dm-btree-remove-assign-new_root-only-when-removal-succeeds.patch extcon-intel-mrfld-sync-hardware-and-software-state-on-init.patch ipack-carriers-tpci200-fix-a-double-free-in-tpci200_pci_probe.patch ipmi-watchdog-stop-watchdog-timer-when-the-current-action-is-none.patch media-subdev-disallow-ioctl-for-saa6588-davinci.patch mips-fix-mipsel-linux-ld-decompress.c-undefined-reference-to-memmove.patch nvmem-core-add-a-missing-of_node_put.patch pci-aardvark-fix-checking-for-pio-non-posted-request.patch pci-aardvark-implement-workaround-for-the-readback-value-of-vend_id.patch pci-leave-apple-thunderbolt-controllers-on-for-s2idle-or-standby.patch power-supply-ab8500-fix-an-old-bug.patch qemu_fw_cfg-make-fw_cfg_rev_attr-a-proper-kobj_attribute.patch rq-qos-fix-missed-wake-ups-in-rq_qos_throttle-try-two.patch seq_buf-fix-overflow-in-seq_buf_putmem_hex.patch thermal-drivers-int340x-processor_thermal-fix-tcc-setting.patch tracing-resize-tgid_map-to-pid_max-not-pid_max_default.patch tracing-simplify-fix-saved_tgids-logic.patch ubifs-fix-races-between-xattr_-set-get-and-listxattr-operations.patch xfrm-policy-read-seqcount-outside-of-rcu-read-side-in-xfrm_policy_lookup_bytype.patch --- diff --git a/queue-5.4/asoc-tegra-set-driver_name-tegra-for-all-machine-drivers.patch b/queue-5.4/asoc-tegra-set-driver_name-tegra-for-all-machine-drivers.patch new file mode 100644 index 00000000000..2b4061bc14a --- /dev/null +++ b/queue-5.4/asoc-tegra-set-driver_name-tegra-for-all-machine-drivers.patch @@ -0,0 +1,131 @@ +From f6eb84fa596abf28959fc7e0b626f925eb1196c7 Mon Sep 17 00:00:00 2001 +From: Dmitry Osipenko +Date: Sat, 29 May 2021 18:46:46 +0300 +Subject: ASoC: tegra: Set driver_name=tegra for all machine drivers + +From: Dmitry Osipenko + +commit f6eb84fa596abf28959fc7e0b626f925eb1196c7 upstream. + +The driver_name="tegra" is now required by the newer ALSA UCMs, otherwise +Tegra UCMs don't match by the path/name. + +All Tegra machine drivers are specifying the card's name, but it has no +effect if model name is specified in the device-tree since it overrides +the card's name. We need to set the driver_name to "tegra" in order to +get a usable lookup path for the updated ALSA UCMs. The new UCM lookup +path has a form of driver_name/card_name. + +The old lookup paths that are based on driver module name continue to +work as before. Note that UCM matching never worked for Tegra ASoC drivers +if they were compiled as built-in, this is fixed by supporting the new +naming scheme. + +Cc: stable@vger.kernel.org +Signed-off-by: Dmitry Osipenko +Link: https://lore.kernel.org/r/20210529154649.25936-2-digetx@gmail.com +Signed-off-by: Mark Brown +Signed-off-by: Greg Kroah-Hartman + +--- + sound/soc/tegra/tegra_alc5632.c | 1 + + sound/soc/tegra/tegra_max98090.c | 1 + + sound/soc/tegra/tegra_rt5640.c | 1 + + sound/soc/tegra/tegra_rt5677.c | 1 + + sound/soc/tegra/tegra_sgtl5000.c | 1 + + sound/soc/tegra/tegra_wm8753.c | 1 + + sound/soc/tegra/tegra_wm8903.c | 1 + + sound/soc/tegra/tegra_wm9712.c | 1 + + sound/soc/tegra/trimslice.c | 1 + + 9 files changed, 9 insertions(+) + +--- a/sound/soc/tegra/tegra_alc5632.c ++++ b/sound/soc/tegra/tegra_alc5632.c +@@ -139,6 +139,7 @@ static struct snd_soc_dai_link tegra_alc + + static struct snd_soc_card snd_soc_tegra_alc5632 = { + .name = "tegra-alc5632", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_alc5632_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_max98090.c ++++ b/sound/soc/tegra/tegra_max98090.c +@@ -182,6 +182,7 @@ static struct snd_soc_dai_link tegra_max + + static struct snd_soc_card snd_soc_tegra_max98090 = { + .name = "tegra-max98090", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_max98090_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_rt5640.c ++++ b/sound/soc/tegra/tegra_rt5640.c +@@ -132,6 +132,7 @@ static struct snd_soc_dai_link tegra_rt5 + + static struct snd_soc_card snd_soc_tegra_rt5640 = { + .name = "tegra-rt5640", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_rt5640_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_rt5677.c ++++ b/sound/soc/tegra/tegra_rt5677.c +@@ -175,6 +175,7 @@ static struct snd_soc_dai_link tegra_rt5 + + static struct snd_soc_card snd_soc_tegra_rt5677 = { + .name = "tegra-rt5677", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_rt5677_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_sgtl5000.c ++++ b/sound/soc/tegra/tegra_sgtl5000.c +@@ -97,6 +97,7 @@ static struct snd_soc_dai_link tegra_sgt + + static struct snd_soc_card snd_soc_tegra_sgtl5000 = { + .name = "tegra-sgtl5000", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_sgtl5000_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_wm8753.c ++++ b/sound/soc/tegra/tegra_wm8753.c +@@ -101,6 +101,7 @@ static struct snd_soc_dai_link tegra_wm8 + + static struct snd_soc_card snd_soc_tegra_wm8753 = { + .name = "tegra-wm8753", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_wm8753_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_wm8903.c ++++ b/sound/soc/tegra/tegra_wm8903.c +@@ -217,6 +217,7 @@ static struct snd_soc_dai_link tegra_wm8 + + static struct snd_soc_card snd_soc_tegra_wm8903 = { + .name = "tegra-wm8903", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_wm8903_dai, + .num_links = 1, +--- a/sound/soc/tegra/tegra_wm9712.c ++++ b/sound/soc/tegra/tegra_wm9712.c +@@ -54,6 +54,7 @@ static struct snd_soc_dai_link tegra_wm9 + + static struct snd_soc_card snd_soc_tegra_wm9712 = { + .name = "tegra-wm9712", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &tegra_wm9712_dai, + .num_links = 1, +--- a/sound/soc/tegra/trimslice.c ++++ b/sound/soc/tegra/trimslice.c +@@ -94,6 +94,7 @@ static struct snd_soc_dai_link trimslice + + static struct snd_soc_card snd_soc_trimslice = { + .name = "tegra-trimslice", ++ .driver_name = "tegra", + .owner = THIS_MODULE, + .dai_link = &trimslice_tlv320aic23_dai, + .num_links = 1, diff --git a/queue-5.4/coresight-tmc-etf-fix-global-out-of-bounds-in-tmc_update_etf_buffer.patch b/queue-5.4/coresight-tmc-etf-fix-global-out-of-bounds-in-tmc_update_etf_buffer.patch new file mode 100644 index 00000000000..c8883686915 --- /dev/null +++ b/queue-5.4/coresight-tmc-etf-fix-global-out-of-bounds-in-tmc_update_etf_buffer.patch @@ -0,0 +1,87 @@ +From 5fae8a946ac2df879caf3f79a193d4766d00239b Mon Sep 17 00:00:00 2001 +From: Sai Prakash Ranjan +Date: Mon, 14 Jun 2021 11:59:00 -0600 +Subject: coresight: tmc-etf: Fix global-out-of-bounds in tmc_update_etf_buffer() + +From: Sai Prakash Ranjan + +commit 5fae8a946ac2df879caf3f79a193d4766d00239b upstream. + +commit 6f755e85c332 ("coresight: Add helper for inserting synchronization +packets") removed trailing '\0' from barrier_pkt array and updated the +call sites like etb_update_buffer() to have proper checks for barrier_pkt +size before read but missed updating tmc_update_etf_buffer() which still +reads barrier_pkt past the array size resulting in KASAN out-of-bounds +bug. Fix this by adding a check for barrier_pkt size before accessing +like it is done in etb_update_buffer(). + + BUG: KASAN: global-out-of-bounds in tmc_update_etf_buffer+0x4b8/0x698 + Read of size 4 at addr ffffffd05b7d1030 by task perf/2629 + + Call trace: + dump_backtrace+0x0/0x27c + show_stack+0x20/0x2c + dump_stack+0x11c/0x188 + print_address_description+0x3c/0x4a4 + __kasan_report+0x140/0x164 + kasan_report+0x10/0x18 + __asan_report_load4_noabort+0x1c/0x24 + tmc_update_etf_buffer+0x4b8/0x698 + etm_event_stop+0x248/0x2d8 + etm_event_del+0x20/0x2c + event_sched_out+0x214/0x6f0 + group_sched_out+0xd0/0x270 + ctx_sched_out+0x2ec/0x518 + __perf_event_task_sched_out+0x4fc/0xe6c + __schedule+0x1094/0x16a0 + preempt_schedule_irq+0x88/0x170 + arm64_preempt_schedule_irq+0xf0/0x18c + el1_irq+0xe8/0x180 + perf_event_exec+0x4d8/0x56c + setup_new_exec+0x204/0x400 + load_elf_binary+0x72c/0x18c0 + search_binary_handler+0x13c/0x420 + load_script+0x500/0x6c4 + search_binary_handler+0x13c/0x420 + exec_binprm+0x118/0x654 + __do_execve_file+0x77c/0xba4 + __arm64_compat_sys_execve+0x98/0xac + el0_svc_common+0x1f8/0x5e0 + el0_svc_compat_handler+0x84/0xb0 + el0_svc_compat+0x10/0x50 + + The buggy address belongs to the variable: + barrier_pkt+0x10/0x40 + + Memory state around the buggy address: + ffffffd05b7d0f00: fa fa fa fa 04 fa fa fa fa fa fa fa 00 00 00 00 + ffffffd05b7d0f80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 + >ffffffd05b7d1000: 00 00 00 00 00 00 fa fa fa fa fa fa 00 00 00 03 + ^ + ffffffd05b7d1080: fa fa fa fa 00 02 fa fa fa fa fa fa 03 fa fa fa + ffffffd05b7d1100: fa fa fa fa 00 00 00 00 05 fa fa fa fa fa fa fa + ================================================================== + +Link: https://lore.kernel.org/r/20210505093430.18445-1-saiprakash.ranjan@codeaurora.org +Fixes: 0c3fc4d5fa26 ("coresight: Add barrier packet for synchronisation") +Cc: stable@vger.kernel.org +Signed-off-by: Sai Prakash Ranjan +Signed-off-by: Suzuki K Poulose +Signed-off-by: Mathieu Poirier +Link: https://lore.kernel.org/r/20210614175901.532683-6-mathieu.poirier@linaro.org +Signed-off-by: Greg Kroah-Hartman +--- + drivers/hwtracing/coresight/coresight-tmc-etf.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/hwtracing/coresight/coresight-tmc-etf.c ++++ b/drivers/hwtracing/coresight/coresight-tmc-etf.c +@@ -528,7 +528,7 @@ static unsigned long tmc_update_etf_buff + buf_ptr = buf->data_pages[cur] + offset; + *buf_ptr = readl_relaxed(drvdata->base + TMC_RRD); + +- if (lost && *barrier) { ++ if (lost && i < CORESIGHT_BARRIER_PKT_SIZE) { + *buf_ptr = *barrier; + barrier++; + } diff --git a/queue-5.4/dm-btree-remove-assign-new_root-only-when-removal-succeeds.patch b/queue-5.4/dm-btree-remove-assign-new_root-only-when-removal-succeeds.patch new file mode 100644 index 00000000000..9450012aa81 --- /dev/null +++ b/queue-5.4/dm-btree-remove-assign-new_root-only-when-removal-succeeds.patch @@ -0,0 +1,60 @@ +From b6e58b5466b2959f83034bead2e2e1395cca8aeb Mon Sep 17 00:00:00 2001 +From: Hou Tao +Date: Thu, 17 Jun 2021 15:45:47 +0800 +Subject: dm btree remove: assign new_root only when removal succeeds + +From: Hou Tao + +commit b6e58b5466b2959f83034bead2e2e1395cca8aeb upstream. + +remove_raw() in dm_btree_remove() may fail due to IO read error +(e.g. read the content of origin block fails during shadowing), +and the value of shadow_spine::root is uninitialized, but +the uninitialized value is still assign to new_root in the +end of dm_btree_remove(). + +For dm-thin, the value of pmd->details_root or pmd->root will become +an uninitialized value, so if trying to read details_info tree again +out-of-bound memory may occur as showed below: + + general protection fault, probably for non-canonical address 0x3fdcb14c8d7520 + CPU: 4 PID: 515 Comm: dmsetup Not tainted 5.13.0-rc6 + Hardware name: QEMU Standard PC + RIP: 0010:metadata_ll_load_ie+0x14/0x30 + Call Trace: + sm_metadata_count_is_more_than_one+0xb9/0xe0 + dm_tm_shadow_block+0x52/0x1c0 + shadow_step+0x59/0xf0 + remove_raw+0xb2/0x170 + dm_btree_remove+0xf4/0x1c0 + dm_pool_delete_thin_device+0xc3/0x140 + pool_message+0x218/0x2b0 + target_message+0x251/0x290 + ctl_ioctl+0x1c4/0x4d0 + dm_ctl_ioctl+0xe/0x20 + __x64_sys_ioctl+0x7b/0xb0 + do_syscall_64+0x40/0xb0 + entry_SYSCALL_64_after_hwframe+0x44/0xae + +Fixing it by only assign new_root when removal succeeds + +Signed-off-by: Hou Tao +Cc: stable@vger.kernel.org +Signed-off-by: Mike Snitzer +Signed-off-by: Greg Kroah-Hartman +--- + drivers/md/persistent-data/dm-btree-remove.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/drivers/md/persistent-data/dm-btree-remove.c ++++ b/drivers/md/persistent-data/dm-btree-remove.c +@@ -549,7 +549,8 @@ int dm_btree_remove(struct dm_btree_info + delete_at(n, index); + } + +- *new_root = shadow_root(&spine); ++ if (!r) ++ *new_root = shadow_root(&spine); + exit_shadow_spine(&spine); + + return r; diff --git a/queue-5.4/extcon-intel-mrfld-sync-hardware-and-software-state-on-init.patch b/queue-5.4/extcon-intel-mrfld-sync-hardware-and-software-state-on-init.patch new file mode 100644 index 00000000000..59086908db9 --- /dev/null +++ b/queue-5.4/extcon-intel-mrfld-sync-hardware-and-software-state-on-init.patch @@ -0,0 +1,48 @@ +From ecb5bdff901139850fb3ca3ae2d0cccac045bc52 Mon Sep 17 00:00:00 2001 +From: Ferry Toth +Date: Tue, 18 May 2021 23:27:09 +0200 +Subject: extcon: intel-mrfld: Sync hardware and software state on init + +From: Ferry Toth + +commit ecb5bdff901139850fb3ca3ae2d0cccac045bc52 upstream. + +extcon driver for Basin Cove PMIC shadows the switch status used for dwc3 +DRD to detect a change in the switch position. This change initializes the +status at probe time. + +Cc: stable@vger.kernel.org +Fixes: 492929c54791 ("extcon: mrfld: Introduce extcon driver for Basin Cove PMIC") +Reviewed-by: Andy Shevchenko +Signed-off-by: Ferry Toth +Signed-off-by: Chanwoo Choi +Signed-off-by: Greg Kroah-Hartman +--- + drivers/extcon/extcon-intel-mrfld.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +--- a/drivers/extcon/extcon-intel-mrfld.c ++++ b/drivers/extcon/extcon-intel-mrfld.c +@@ -197,6 +197,7 @@ static int mrfld_extcon_probe(struct pla + struct intel_soc_pmic *pmic = dev_get_drvdata(dev->parent); + struct regmap *regmap = pmic->regmap; + struct mrfld_extcon_data *data; ++ unsigned int status; + unsigned int id; + int irq, ret; + +@@ -244,6 +245,14 @@ static int mrfld_extcon_probe(struct pla + /* Get initial state */ + mrfld_extcon_role_detect(data); + ++ /* ++ * Cached status value is used for cable detection, see comments ++ * in mrfld_extcon_cable_detect(), we need to sync cached value ++ * with a real state of the hardware. ++ */ ++ regmap_read(regmap, BCOVE_SCHGRIRQ1, &status); ++ data->status = status; ++ + mrfld_extcon_clear(data, BCOVE_MIRQLVL1, BCOVE_LVL1_CHGR); + mrfld_extcon_clear(data, BCOVE_MCHGRIRQ1, BCOVE_CHGRIRQ_ALL); + diff --git a/queue-5.4/ipack-carriers-tpci200-fix-a-double-free-in-tpci200_pci_probe.patch b/queue-5.4/ipack-carriers-tpci200-fix-a-double-free-in-tpci200_pci_probe.patch new file mode 100644 index 00000000000..e14577347f9 --- /dev/null +++ b/queue-5.4/ipack-carriers-tpci200-fix-a-double-free-in-tpci200_pci_probe.patch @@ -0,0 +1,45 @@ +From 9272e5d0028d45a3b45b58c9255e6e0df53f7ad9 Mon Sep 17 00:00:00 2001 +From: Lv Yunlong +Date: Mon, 24 May 2021 02:32:05 -0700 +Subject: ipack/carriers/tpci200: Fix a double free in tpci200_pci_probe + +From: Lv Yunlong + +commit 9272e5d0028d45a3b45b58c9255e6e0df53f7ad9 upstream. + +In the out_err_bus_register error branch of tpci200_pci_probe, +tpci200->info->cfg_regs is freed by tpci200_uninstall()-> +tpci200_unregister()->pci_iounmap(..,tpci200->info->cfg_regs) +in the first time. + +But later, iounmap() is called to free tpci200->info->cfg_regs +again. + +My patch sets tpci200->info->cfg_regs to NULL after tpci200_uninstall() +to avoid the double free. + +Fixes: cea2f7cdff2af ("Staging: ipack/bridges/tpci200: Use the TPCI200 in big endian mode") +Cc: stable +Acked-by: Samuel Iglesias Gonsalvez +Signed-off-by: Lv Yunlong +Link: https://lore.kernel.org/r/20210524093205.8333-1-lyl2019@mail.ustc.edu.cn +Signed-off-by: Greg Kroah-Hartman +--- + drivers/ipack/carriers/tpci200.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +--- a/drivers/ipack/carriers/tpci200.c ++++ b/drivers/ipack/carriers/tpci200.c +@@ -596,8 +596,11 @@ static int tpci200_pci_probe(struct pci_ + + out_err_bus_register: + tpci200_uninstall(tpci200); ++ /* tpci200->info->cfg_regs is unmapped in tpci200_uninstall */ ++ tpci200->info->cfg_regs = NULL; + out_err_install: +- iounmap(tpci200->info->cfg_regs); ++ if (tpci200->info->cfg_regs) ++ iounmap(tpci200->info->cfg_regs); + out_err_ioremap: + pci_release_region(pdev, TPCI200_CFG_MEM_BAR); + out_err_pci_request: diff --git a/queue-5.4/ipmi-watchdog-stop-watchdog-timer-when-the-current-action-is-none.patch b/queue-5.4/ipmi-watchdog-stop-watchdog-timer-when-the-current-action-is-none.patch new file mode 100644 index 00000000000..50fbb7b91b6 --- /dev/null +++ b/queue-5.4/ipmi-watchdog-stop-watchdog-timer-when-the-current-action-is-none.patch @@ -0,0 +1,72 @@ +From 2253042d86f57d90a621ac2513a7a7a13afcf809 Mon Sep 17 00:00:00 2001 +From: Petr Pavlu +Date: Thu, 13 May 2021 14:26:36 +0200 +Subject: ipmi/watchdog: Stop watchdog timer when the current action is 'none' + +From: Petr Pavlu + +commit 2253042d86f57d90a621ac2513a7a7a13afcf809 upstream. + +When an IPMI watchdog timer is being stopped in ipmi_close() or +ipmi_ioctl(WDIOS_DISABLECARD), the current watchdog action is updated to +WDOG_TIMEOUT_NONE and _ipmi_set_timeout(IPMI_SET_TIMEOUT_NO_HB) is called +to install this action. The latter function ends up invoking +__ipmi_set_timeout() which makes the actual 'Set Watchdog Timer' IPMI +request. + +For IPMI 1.0, this operation results in fully stopping the watchdog timer. +For IPMI >= 1.5, function __ipmi_set_timeout() always specifies the "don't +stop" flag in the prepared 'Set Watchdog Timer' IPMI request. This causes +that the watchdog timer has its action correctly updated to 'none' but the +timer continues to run. A problem is that IPMI firmware can then still log +an expiration event when the configured timeout is reached, which is +unexpected because the watchdog timer was requested to be stopped. + +The patch fixes this problem by not setting the "don't stop" flag in +__ipmi_set_timeout() when the current action is WDOG_TIMEOUT_NONE which +results in stopping the watchdog timer. This makes the behaviour for +IPMI >= 1.5 consistent with IPMI 1.0. It also matches the logic in +__ipmi_heartbeat() which does not allow to reset the watchdog if the +current action is WDOG_TIMEOUT_NONE as that would start the timer. + +Signed-off-by: Petr Pavlu +Message-Id: <10a41bdc-9c99-089c-8d89-fa98ce5ea080@suse.com> +Cc: stable@vger.kernel.org +Signed-off-by: Corey Minyard +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/char/ipmi/ipmi_watchdog.c | 22 ++++++++++++---------- + 1 file changed, 12 insertions(+), 10 deletions(-) + +--- a/drivers/char/ipmi/ipmi_watchdog.c ++++ b/drivers/char/ipmi/ipmi_watchdog.c +@@ -366,16 +366,18 @@ static int __ipmi_set_timeout(struct ipm + data[0] = 0; + WDOG_SET_TIMER_USE(data[0], WDOG_TIMER_USE_SMS_OS); + +- if ((ipmi_version_major > 1) +- || ((ipmi_version_major == 1) && (ipmi_version_minor >= 5))) { +- /* This is an IPMI 1.5-only feature. */ +- data[0] |= WDOG_DONT_STOP_ON_SET; +- } else if (ipmi_watchdog_state != WDOG_TIMEOUT_NONE) { +- /* +- * In ipmi 1.0, setting the timer stops the watchdog, we +- * need to start it back up again. +- */ +- hbnow = 1; ++ if (ipmi_watchdog_state != WDOG_TIMEOUT_NONE) { ++ if ((ipmi_version_major > 1) || ++ ((ipmi_version_major == 1) && (ipmi_version_minor >= 5))) { ++ /* This is an IPMI 1.5-only feature. */ ++ data[0] |= WDOG_DONT_STOP_ON_SET; ++ } else { ++ /* ++ * In ipmi 1.0, setting the timer stops the watchdog, we ++ * need to start it back up again. ++ */ ++ hbnow = 1; ++ } + } + + data[1] = 0; diff --git a/queue-5.4/media-subdev-disallow-ioctl-for-saa6588-davinci.patch b/queue-5.4/media-subdev-disallow-ioctl-for-saa6588-davinci.patch new file mode 100644 index 00000000000..754bab750d8 --- /dev/null +++ b/queue-5.4/media-subdev-disallow-ioctl-for-saa6588-davinci.patch @@ -0,0 +1,169 @@ +From 0a7790be182d32b9b332a37cb4206e24fe94b728 Mon Sep 17 00:00:00 2001 +From: Arnd Bergmann +Date: Mon, 14 Jun 2021 12:34:09 +0200 +Subject: media: subdev: disallow ioctl for saa6588/davinci + +From: Arnd Bergmann + +commit 0a7790be182d32b9b332a37cb4206e24fe94b728 upstream. + +The saa6588_ioctl() function expects to get called from other kernel +functions with a 'saa6588_command' pointer, but I found nothing stops it +from getting called from user space instead, which seems rather dangerous. + +The same thing happens in the davinci vpbe driver with its VENC_GET_FLD +command. + +As a quick fix, add a separate .command() callback pointer for this +driver and change the two callers over to that. This change can easily +get backported to stable kernels if necessary, but since there are only +two drivers, we may want to eventually replace this with a set of more +specialized callbacks in the long run. + +Fixes: c3fda7f835b0 ("V4L/DVB (10537): saa6588: convert to v4l2_subdev.") +Cc: stable@vger.kernel.org +Signed-off-by: Arnd Bergmann +Reviewed-by: Laurent Pinchart +Signed-off-by: Hans Verkuil +Signed-off-by: Mauro Carvalho Chehab +Signed-off-by: Greg Kroah-Hartman +--- + drivers/media/i2c/saa6588.c | 4 ++-- + drivers/media/pci/bt8xx/bttv-driver.c | 6 +++--- + drivers/media/pci/saa7134/saa7134-video.c | 6 +++--- + drivers/media/platform/davinci/vpbe_display.c | 2 +- + drivers/media/platform/davinci/vpbe_venc.c | 6 ++---- + include/media/v4l2-subdev.h | 4 ++++ + 6 files changed, 15 insertions(+), 13 deletions(-) + +--- a/drivers/media/i2c/saa6588.c ++++ b/drivers/media/i2c/saa6588.c +@@ -380,7 +380,7 @@ static void saa6588_configure(struct saa + + /* ---------------------------------------------------------------------- */ + +-static long saa6588_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg) ++static long saa6588_command(struct v4l2_subdev *sd, unsigned int cmd, void *arg) + { + struct saa6588 *s = to_saa6588(sd); + struct saa6588_command *a = arg; +@@ -433,7 +433,7 @@ static int saa6588_s_tuner(struct v4l2_s + /* ----------------------------------------------------------------------- */ + + static const struct v4l2_subdev_core_ops saa6588_core_ops = { +- .ioctl = saa6588_ioctl, ++ .command = saa6588_command, + }; + + static const struct v4l2_subdev_tuner_ops saa6588_tuner_ops = { +--- a/drivers/media/pci/bt8xx/bttv-driver.c ++++ b/drivers/media/pci/bt8xx/bttv-driver.c +@@ -3187,7 +3187,7 @@ static int radio_release(struct file *fi + + btv->radio_user--; + +- bttv_call_all(btv, core, ioctl, SAA6588_CMD_CLOSE, &cmd); ++ bttv_call_all(btv, core, command, SAA6588_CMD_CLOSE, &cmd); + + if (btv->radio_user == 0) + btv->has_radio_tuner = 0; +@@ -3268,7 +3268,7 @@ static ssize_t radio_read(struct file *f + cmd.result = -ENODEV; + radio_enable(btv); + +- bttv_call_all(btv, core, ioctl, SAA6588_CMD_READ, &cmd); ++ bttv_call_all(btv, core, command, SAA6588_CMD_READ, &cmd); + + return cmd.result; + } +@@ -3289,7 +3289,7 @@ static __poll_t radio_poll(struct file * + cmd.instance = file; + cmd.event_list = wait; + cmd.poll_mask = res; +- bttv_call_all(btv, core, ioctl, SAA6588_CMD_POLL, &cmd); ++ bttv_call_all(btv, core, command, SAA6588_CMD_POLL, &cmd); + + return cmd.poll_mask; + } +--- a/drivers/media/pci/saa7134/saa7134-video.c ++++ b/drivers/media/pci/saa7134/saa7134-video.c +@@ -1179,7 +1179,7 @@ static int video_release(struct file *fi + + saa_call_all(dev, tuner, standby); + if (vdev->vfl_type == VFL_TYPE_RADIO) +- saa_call_all(dev, core, ioctl, SAA6588_CMD_CLOSE, &cmd); ++ saa_call_all(dev, core, command, SAA6588_CMD_CLOSE, &cmd); + mutex_unlock(&dev->lock); + + return 0; +@@ -1198,7 +1198,7 @@ static ssize_t radio_read(struct file *f + cmd.result = -ENODEV; + + mutex_lock(&dev->lock); +- saa_call_all(dev, core, ioctl, SAA6588_CMD_READ, &cmd); ++ saa_call_all(dev, core, command, SAA6588_CMD_READ, &cmd); + mutex_unlock(&dev->lock); + + return cmd.result; +@@ -1214,7 +1214,7 @@ static __poll_t radio_poll(struct file * + cmd.event_list = wait; + cmd.poll_mask = 0; + mutex_lock(&dev->lock); +- saa_call_all(dev, core, ioctl, SAA6588_CMD_POLL, &cmd); ++ saa_call_all(dev, core, command, SAA6588_CMD_POLL, &cmd); + mutex_unlock(&dev->lock); + + return rc | cmd.poll_mask; +--- a/drivers/media/platform/davinci/vpbe_display.c ++++ b/drivers/media/platform/davinci/vpbe_display.c +@@ -48,7 +48,7 @@ static int venc_is_second_field(struct v + + ret = v4l2_subdev_call(vpbe_dev->venc, + core, +- ioctl, ++ command, + VENC_GET_FLD, + &val); + if (ret < 0) { +--- a/drivers/media/platform/davinci/vpbe_venc.c ++++ b/drivers/media/platform/davinci/vpbe_venc.c +@@ -521,9 +521,7 @@ static int venc_s_routing(struct v4l2_su + return ret; + } + +-static long venc_ioctl(struct v4l2_subdev *sd, +- unsigned int cmd, +- void *arg) ++static long venc_command(struct v4l2_subdev *sd, unsigned int cmd, void *arg) + { + u32 val; + +@@ -542,7 +540,7 @@ static long venc_ioctl(struct v4l2_subde + } + + static const struct v4l2_subdev_core_ops venc_core_ops = { +- .ioctl = venc_ioctl, ++ .command = venc_command, + }; + + static const struct v4l2_subdev_video_ops venc_video_ops = { +--- a/include/media/v4l2-subdev.h ++++ b/include/media/v4l2-subdev.h +@@ -162,6 +162,9 @@ struct v4l2_subdev_io_pin_config { + * @s_gpio: set GPIO pins. Very simple right now, might need to be extended with + * a direction argument if needed. + * ++ * @command: called by in-kernel drivers in order to call functions internal ++ * to subdev drivers driver that have a separate callback. ++ * + * @ioctl: called at the end of ioctl() syscall handler at the V4L2 core. + * used to provide support for private ioctls used on the driver. + * +@@ -193,6 +196,7 @@ struct v4l2_subdev_core_ops { + int (*load_fw)(struct v4l2_subdev *sd); + int (*reset)(struct v4l2_subdev *sd, u32 val); + int (*s_gpio)(struct v4l2_subdev *sd, u32 val); ++ long (*command)(struct v4l2_subdev *sd, unsigned int cmd, void *arg); + long (*ioctl)(struct v4l2_subdev *sd, unsigned int cmd, void *arg); + #ifdef CONFIG_COMPAT + long (*compat_ioctl32)(struct v4l2_subdev *sd, unsigned int cmd, diff --git a/queue-5.4/mips-fix-mipsel-linux-ld-decompress.c-undefined-reference-to-memmove.patch b/queue-5.4/mips-fix-mipsel-linux-ld-decompress.c-undefined-reference-to-memmove.patch new file mode 100644 index 00000000000..d7fd92fe42a --- /dev/null +++ b/queue-5.4/mips-fix-mipsel-linux-ld-decompress.c-undefined-reference-to-memmove.patch @@ -0,0 +1,65 @@ +From hsiangkao@linux.alibaba.com Thu Jul 15 15:22:55 2021 +From: Gao Xiang +Date: Thu, 15 Jul 2021 21:08:06 +0800 +Subject: MIPS: fix "mipsel-linux-ld: decompress.c:undefined reference to `memmove'" +To: stable , Greg Kroah-Hartman +Cc: Gao Xiang , kernel test robot +Message-ID: <20210715130806.195223-1-hsiangkao@linux.alibaba.com> + +From: Gao Xiang + +This is _not_ an upstream commit and just for 5.4.y only. + +kernel test robot reported a 5.4.y build issue found by randconfig [1] +after backporting commit 89b158635ad7 ("lib/lz4: explicitly support +in-place decompression"") due to "undefined reference to `memmove'". + +However, upstream and 5.10 LTS seem fine. After digging further, +I found commit a510b616131f ("MIPS: Add support for ZSTD-compressed +kernels") introduced memmove() occasionally and it has been included +since v5.10. + +This partially cherry-picks the memmove() part of commit a510b616131f +to fix the reported build regression since we don't need the whole +patch for 5.4 LTS at all. + +[1] https://lore.kernel.org/r/202107070120.6dOj1kB7-lkp@intel.com/ +Fixes: defcc2b5e54a ("lib/lz4: explicitly support in-place decompression") # 5.4.y +Reported-by: kernel test robot +Signed-off-by: Gao Xiang +Signed-off-by: Greg Kroah-Hartman + +--- + arch/mips/boot/compressed/string.c | 17 +++++++++++++++++ + 1 file changed, 17 insertions(+) + +--- a/arch/mips/boot/compressed/string.c ++++ b/arch/mips/boot/compressed/string.c +@@ -5,6 +5,7 @@ + * Very small subset of simple string routines + */ + ++#include + #include + + void *memcpy(void *dest, const void *src, size_t n) +@@ -27,3 +28,19 @@ void *memset(void *s, int c, size_t n) + ss[i] = c; + return s; + } ++ ++void * __weak memmove(void *dest, const void *src, size_t n) ++{ ++ unsigned int i; ++ const char *s = src; ++ char *d = dest; ++ ++ if ((uintptr_t)dest < (uintptr_t)src) { ++ for (i = 0; i < n; i++) ++ d[i] = s[i]; ++ } else { ++ for (i = n; i > 0; i--) ++ d[i - 1] = s[i - 1]; ++ } ++ return dest; ++} diff --git a/queue-5.4/nvmem-core-add-a-missing-of_node_put.patch b/queue-5.4/nvmem-core-add-a-missing-of_node_put.patch new file mode 100644 index 00000000000..68fd83389e4 --- /dev/null +++ b/queue-5.4/nvmem-core-add-a-missing-of_node_put.patch @@ -0,0 +1,58 @@ +From 63879e2964bceee2aa5bbe8b99ea58bba28bb64f Mon Sep 17 00:00:00 2001 +From: Christophe JAILLET +Date: Fri, 11 Jun 2021 11:23:21 +0100 +Subject: nvmem: core: add a missing of_node_put + +From: Christophe JAILLET + +commit 63879e2964bceee2aa5bbe8b99ea58bba28bb64f upstream. + +'for_each_child_of_node' performs an of_node_get on each iteration, so a +return from the middle of the loop requires an of_node_put. + +Fixes: e888d445ac33 ("nvmem: resolve cells from DT at registration time") +Cc: +Signed-off-by: Christophe JAILLET +Signed-off-by: Srinivas Kandagatla +Link: https://lore.kernel.org/r/20210611102321.11509-1-srinivas.kandagatla@linaro.org +Signed-off-by: Greg Kroah-Hartman +--- + drivers/nvmem/core.c | 9 ++++++--- + 1 file changed, 6 insertions(+), 3 deletions(-) + +--- a/drivers/nvmem/core.c ++++ b/drivers/nvmem/core.c +@@ -318,15 +318,17 @@ static int nvmem_add_cells_from_of(struc + continue; + if (len < 2 * sizeof(u32)) { + dev_err(dev, "nvmem: invalid reg on %pOF\n", child); ++ of_node_put(child); + return -EINVAL; + } + + cell = kzalloc(sizeof(*cell), GFP_KERNEL); +- if (!cell) ++ if (!cell) { ++ of_node_put(child); + return -ENOMEM; ++ } + + cell->nvmem = nvmem; +- cell->np = of_node_get(child); + cell->offset = be32_to_cpup(addr++); + cell->bytes = be32_to_cpup(addr); + cell->name = kasprintf(GFP_KERNEL, "%pOFn", child); +@@ -347,11 +349,12 @@ static int nvmem_add_cells_from_of(struc + cell->name, nvmem->stride); + /* Cells already added will be freed later. */ + kfree_const(cell->name); +- of_node_put(cell->np); + kfree(cell); ++ of_node_put(child); + return -EINVAL; + } + ++ cell->np = of_node_get(child); + nvmem_cell_add(cell); + } + diff --git a/queue-5.4/pci-aardvark-fix-checking-for-pio-non-posted-request.patch b/queue-5.4/pci-aardvark-fix-checking-for-pio-non-posted-request.patch new file mode 100644 index 00000000000..24ab743fd3a --- /dev/null +++ b/queue-5.4/pci-aardvark-fix-checking-for-pio-non-posted-request.patch @@ -0,0 +1,36 @@ +From 8ceeac307a79f68c0d0c72d6e48b82fa424204ec Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Pali=20Roh=C3=A1r?= +Date: Thu, 24 Jun 2021 23:33:43 +0200 +Subject: PCI: aardvark: Fix checking for PIO Non-posted Request +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Pali Rohár + +commit 8ceeac307a79f68c0d0c72d6e48b82fa424204ec upstream. + +PIO_NON_POSTED_REQ for PIO_STAT register is incorrectly defined. Bit 10 in +register PIO_STAT indicates the response is to a non-posted request. + +Link: https://lore.kernel.org/r/20210624213345.3617-2-pali@kernel.org +Signed-off-by: Pali Rohár +Signed-off-by: Lorenzo Pieralisi +Reviewed-by: Marek Behún +Cc: stable@vger.kernel.org +Signed-off-by: Greg Kroah-Hartman +--- + drivers/pci/controller/pci-aardvark.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/pci/controller/pci-aardvark.c ++++ b/drivers/pci/controller/pci-aardvark.c +@@ -61,7 +61,7 @@ + #define PIO_COMPLETION_STATUS_UR 1 + #define PIO_COMPLETION_STATUS_CRS 2 + #define PIO_COMPLETION_STATUS_CA 4 +-#define PIO_NON_POSTED_REQ BIT(0) ++#define PIO_NON_POSTED_REQ BIT(10) + #define PIO_ADDR_LS (PIO_BASE_ADDR + 0x8) + #define PIO_ADDR_MS (PIO_BASE_ADDR + 0xc) + #define PIO_WR_DATA (PIO_BASE_ADDR + 0x10) diff --git a/queue-5.4/pci-aardvark-implement-workaround-for-the-readback-value-of-vend_id.patch b/queue-5.4/pci-aardvark-implement-workaround-for-the-readback-value-of-vend_id.patch new file mode 100644 index 00000000000..55485f46cef --- /dev/null +++ b/queue-5.4/pci-aardvark-implement-workaround-for-the-readback-value-of-vend_id.patch @@ -0,0 +1,65 @@ +From 7f71a409fe3d9358da07c77f15bb5b7960f12253 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Pali=20Roh=C3=A1r?= +Date: Fri, 25 Jun 2021 00:26:20 +0200 +Subject: PCI: aardvark: Implement workaround for the readback value of VEND_ID +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Pali Rohár + +commit 7f71a409fe3d9358da07c77f15bb5b7960f12253 upstream. + +Marvell Armada 3700 Functional Errata, Guidelines, and Restrictions +document describes in erratum 4.1 PCIe value of vendor ID (Ref #: 243): + + The readback value of VEND_ID (RD0070000h [15:0]) is 1B4Bh, while it + should read 11ABh. + + The firmware can write the correct value, 11ABh, through VEND_ID + (RD0076044h [15:0]). + +Implement this workaround in aardvark driver for both PCI vendor id and PCI +subsystem vendor id. + +This change affects and fixes PCI vendor id of emulated PCIe root bridge. +After this change emulated PCIe root bridge has correct vendor id. + +Link: https://lore.kernel.org/r/20210624222621.4776-5-pali@kernel.org +Fixes: 8a3ebd8de328 ("PCI: aardvark: Implement emulated root PCI bridge config space") +Signed-off-by: Pali Rohár +Signed-off-by: Lorenzo Pieralisi +Reviewed-by: Marek Behún +Cc: stable@vger.kernel.org +Signed-off-by: Greg Kroah-Hartman +--- + drivers/pci/controller/pci-aardvark.c | 11 +++++++++++ + 1 file changed, 11 insertions(+) + +--- a/drivers/pci/controller/pci-aardvark.c ++++ b/drivers/pci/controller/pci-aardvark.c +@@ -127,6 +127,7 @@ + #define LTSSM_MASK 0x3f + #define LTSSM_L0 0x10 + #define RC_BAR_CONFIG 0x300 ++#define VENDOR_ID_REG (LMI_BASE_ADDR + 0x44) + + /* PCIe core controller registers */ + #define CTRL_CORE_BASE_ADDR 0x18000 +@@ -268,6 +269,16 @@ static void advk_pcie_setup_hw(struct ad + reg |= (IS_RC_MSK << IS_RC_SHIFT); + advk_writel(pcie, reg, PCIE_CORE_CTRL0_REG); + ++ /* ++ * Replace incorrect PCI vendor id value 0x1b4b by correct value 0x11ab. ++ * VENDOR_ID_REG contains vendor id in low 16 bits and subsystem vendor ++ * id in high 16 bits. Updating this register changes readback value of ++ * read-only vendor id bits in PCIE_CORE_DEV_ID_REG register. Workaround ++ * for erratum 4.1: "The value of device and vendor ID is incorrect". ++ */ ++ reg = (PCI_VENDOR_ID_MARVELL << 16) | PCI_VENDOR_ID_MARVELL; ++ advk_writel(pcie, reg, VENDOR_ID_REG); ++ + /* Set Advanced Error Capabilities and Control PF0 register */ + reg = PCIE_CORE_ERR_CAPCTL_ECRC_CHK_TX | + PCIE_CORE_ERR_CAPCTL_ECRC_CHK_TX_EN | diff --git a/queue-5.4/pci-leave-apple-thunderbolt-controllers-on-for-s2idle-or-standby.patch b/queue-5.4/pci-leave-apple-thunderbolt-controllers-on-for-s2idle-or-standby.patch new file mode 100644 index 00000000000..2b725e4c5ef --- /dev/null +++ b/queue-5.4/pci-leave-apple-thunderbolt-controllers-on-for-s2idle-or-standby.patch @@ -0,0 +1,65 @@ +From 4694ae373dc2114f9a82f6ae15737e65af0c6dea Mon Sep 17 00:00:00 2001 +From: Konstantin Kharlamov +Date: Fri, 21 May 2021 02:55:01 +0300 +Subject: PCI: Leave Apple Thunderbolt controllers on for s2idle or standby + +From: Konstantin Kharlamov + +commit 4694ae373dc2114f9a82f6ae15737e65af0c6dea upstream. + +On Macbook 2013, resuming from suspend-to-idle or standby resulted in the +external monitor no longer being detected, a stacktrace, and errors like +this in dmesg: + + pcieport 0000:06:00.0: can't change power state from D3hot to D0 (config space inaccessible) + +The reason is that we know how to turn power to the Thunderbolt controller +*off* via the SXIO/SXFP/SXLF methods, but we don't know how to turn power +back on. We have to rely on firmware to turn the power back on. + +When going to the "suspend-to-idle" or "standby" system sleep states, +firmware is not involved either on the suspend side or the resume side, so +we can't use SXIO/SXFP/SXLF to turn the power off. + +Skip SXIO/SXFP/SXLF when firmware isn't involved in suspend, e.g., when +we're going to the "suspend-to-idle" or "standby" system sleep states. + +Fixes: 1df5172c5c25 ("PCI: Suspend/resume quirks for Apple thunderbolt") +Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=212767 +Link: https://lore.kernel.org/r/20210520235501.917397-1-Hi-Angel@yandex.ru +Signed-off-by: Konstantin Kharlamov +Signed-off-by: Bjorn Helgaas +Reviewed-by: Lukas Wunner +Cc: stable@vger.kernel.org +Signed-off-by: Greg Kroah-Hartman +--- + drivers/pci/quirks.c | 11 +++++++++++ + 1 file changed, 11 insertions(+) + +--- a/drivers/pci/quirks.c ++++ b/drivers/pci/quirks.c +@@ -27,6 +27,7 @@ + #include + #include + #include ++#include + #include + #include /* isa_dma_bridge_buggy */ + #include "pci.h" +@@ -3667,6 +3668,16 @@ static void quirk_apple_poweroff_thunder + return; + if (pci_pcie_type(dev) != PCI_EXP_TYPE_UPSTREAM) + return; ++ ++ /* ++ * SXIO/SXFP/SXLF turns off power to the Thunderbolt controller. ++ * We don't know how to turn it back on again, but firmware does, ++ * so we can only use SXIO/SXFP/SXLF if we're suspending via ++ * firmware. ++ */ ++ if (!pm_suspend_via_firmware()) ++ return; ++ + bridge = ACPI_HANDLE(&dev->dev); + if (!bridge) + return; diff --git a/queue-5.4/power-supply-ab8500-fix-an-old-bug.patch b/queue-5.4/power-supply-ab8500-fix-an-old-bug.patch new file mode 100644 index 00000000000..192b2b2c549 --- /dev/null +++ b/queue-5.4/power-supply-ab8500-fix-an-old-bug.patch @@ -0,0 +1,38 @@ +From f1c74a6c07e76fcb31a4bcc1f437c4361a2674ce Mon Sep 17 00:00:00 2001 +From: Linus Walleij +Date: Sun, 27 Jun 2021 01:47:49 +0200 +Subject: power: supply: ab8500: Fix an old bug + +From: Linus Walleij + +commit f1c74a6c07e76fcb31a4bcc1f437c4361a2674ce upstream. + +Trying to get the AB8500 charging driver working I ran into a bit +of bitrot: we haven't used the driver for a while so errors in +refactorings won't be noticed. + +This one is pretty self evident: use argument to the macro or we +end up with a random pointer to something else. + +Cc: stable@vger.kernel.org +Cc: Krzysztof Kozlowski +Cc: Marcus Cooper +Fixes: 297d716f6260 ("power_supply: Change ownership from driver to core") +Signed-off-by: Linus Walleij +Signed-off-by: Sebastian Reichel +Signed-off-by: Greg Kroah-Hartman +--- + include/linux/mfd/abx500/ux500_chargalg.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/include/linux/mfd/abx500/ux500_chargalg.h ++++ b/include/linux/mfd/abx500/ux500_chargalg.h +@@ -15,7 +15,7 @@ + * - POWER_SUPPLY_TYPE_USB, + * because only them store as drv_data pointer to struct ux500_charger. + */ +-#define psy_to_ux500_charger(x) power_supply_get_drvdata(psy) ++#define psy_to_ux500_charger(x) power_supply_get_drvdata(x) + + /* Forward declaration */ + struct ux500_charger; diff --git a/queue-5.4/qemu_fw_cfg-make-fw_cfg_rev_attr-a-proper-kobj_attribute.patch b/queue-5.4/qemu_fw_cfg-make-fw_cfg_rev_attr-a-proper-kobj_attribute.patch new file mode 100644 index 00000000000..8e8d7350f39 --- /dev/null +++ b/queue-5.4/qemu_fw_cfg-make-fw_cfg_rev_attr-a-proper-kobj_attribute.patch @@ -0,0 +1,65 @@ +From fca41af18e10318e4de090db47d9fa7169e1bf2f Mon Sep 17 00:00:00 2001 +From: Nathan Chancellor +Date: Thu, 11 Feb 2021 12:42:58 -0700 +Subject: qemu_fw_cfg: Make fw_cfg_rev_attr a proper kobj_attribute +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Nathan Chancellor + +commit fca41af18e10318e4de090db47d9fa7169e1bf2f upstream. + +fw_cfg_showrev() is called by an indirect call in kobj_attr_show(), +which violates clang's CFI checking because fw_cfg_showrev()'s second +parameter is 'struct attribute', whereas the ->show() member of 'struct +kobj_structure' expects the second parameter to be of type 'struct +kobj_attribute'. + +$ cat /sys/firmware/qemu_fw_cfg/rev +3 + +$ dmesg | grep "CFI failure" +[ 26.016832] CFI failure (target: fw_cfg_showrev+0x0/0x8): + +Fix this by converting fw_cfg_rev_attr to 'struct kobj_attribute' where +this would have been caught automatically by the incompatible pointer +types compiler warning. Update fw_cfg_showrev() accordingly. + +Fixes: 75f3e8e47f38 ("firmware: introduce sysfs driver for QEMU's fw_cfg device") +Link: https://github.com/ClangBuiltLinux/linux/issues/1299 +Signed-off-by: Nathan Chancellor +Reviewed-by: Sami Tolvanen +Tested-by: Sedat Dilek +Reviewed-by: Sami Tolvanen +Reviewed-by: Philippe Mathieu-Daudé +Signed-off-by: Kees Cook +Cc: stable@vger.kernel.org +Link: https://lore.kernel.org/r/20210211194258.4137998-1-nathan@kernel.org +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/firmware/qemu_fw_cfg.c | 8 +++----- + 1 file changed, 3 insertions(+), 5 deletions(-) + +--- a/drivers/firmware/qemu_fw_cfg.c ++++ b/drivers/firmware/qemu_fw_cfg.c +@@ -296,15 +296,13 @@ static int fw_cfg_do_platform_probe(stru + return 0; + } + +-static ssize_t fw_cfg_showrev(struct kobject *k, struct attribute *a, char *buf) ++static ssize_t fw_cfg_showrev(struct kobject *k, struct kobj_attribute *a, ++ char *buf) + { + return sprintf(buf, "%u\n", fw_cfg_rev); + } + +-static const struct { +- struct attribute attr; +- ssize_t (*show)(struct kobject *k, struct attribute *a, char *buf); +-} fw_cfg_rev_attr = { ++static const struct kobj_attribute fw_cfg_rev_attr = { + .attr = { .name = "rev", .mode = S_IRUSR }, + .show = fw_cfg_showrev, + }; diff --git a/queue-5.4/rq-qos-fix-missed-wake-ups-in-rq_qos_throttle-try-two.patch b/queue-5.4/rq-qos-fix-missed-wake-ups-in-rq_qos_throttle-try-two.patch new file mode 100644 index 00000000000..aa89de921f6 --- /dev/null +++ b/queue-5.4/rq-qos-fix-missed-wake-ups-in-rq_qos_throttle-try-two.patch @@ -0,0 +1,98 @@ +From 11c7aa0ddea8611007768d3e6b58d45dc60a19e1 Mon Sep 17 00:00:00 2001 +From: Jan Kara +Date: Mon, 7 Jun 2021 13:26:13 +0200 +Subject: rq-qos: fix missed wake-ups in rq_qos_throttle try two + +From: Jan Kara + +commit 11c7aa0ddea8611007768d3e6b58d45dc60a19e1 upstream. + +Commit 545fbd0775ba ("rq-qos: fix missed wake-ups in rq_qos_throttle") +tried to fix a problem that a process could be sleeping in rq_qos_wait() +without anyone to wake it up. However the fix is not complete and the +following can still happen: + +CPU1 (waiter1) CPU2 (waiter2) CPU3 (waker) +rq_qos_wait() rq_qos_wait() + acquire_inflight_cb() -> fails + acquire_inflight_cb() -> fails + + completes IOs, inflight + decreased + prepare_to_wait_exclusive() + prepare_to_wait_exclusive() + has_sleeper = !wq_has_single_sleeper() -> true as there are two sleepers + has_sleeper = !wq_has_single_sleeper() -> true + io_schedule() io_schedule() + +Deadlock as now there's nobody to wakeup the two waiters. The logic +automatically blocking when there are already sleepers is really subtle +and the only way to make it work reliably is that we check whether there +are some waiters in the queue when adding ourselves there. That way, we +are guaranteed that at least the first process to enter the wait queue +will recheck the waiting condition before going to sleep and thus +guarantee forward progress. + +Fixes: 545fbd0775ba ("rq-qos: fix missed wake-ups in rq_qos_throttle") +CC: stable@vger.kernel.org +Signed-off-by: Jan Kara +Link: https://lore.kernel.org/r/20210607112613.25344-1-jack@suse.cz +Signed-off-by: Jens Axboe +Signed-off-by: Greg Kroah-Hartman +--- + block/blk-rq-qos.c | 4 ++-- + include/linux/wait.h | 2 +- + kernel/sched/wait.c | 9 +++++++-- + 3 files changed, 10 insertions(+), 5 deletions(-) + +--- a/block/blk-rq-qos.c ++++ b/block/blk-rq-qos.c +@@ -266,8 +266,8 @@ void rq_qos_wait(struct rq_wait *rqw, vo + if (!has_sleeper && acquire_inflight_cb(rqw, private_data)) + return; + +- prepare_to_wait_exclusive(&rqw->wait, &data.wq, TASK_UNINTERRUPTIBLE); +- has_sleeper = !wq_has_single_sleeper(&rqw->wait); ++ has_sleeper = !prepare_to_wait_exclusive(&rqw->wait, &data.wq, ++ TASK_UNINTERRUPTIBLE); + do { + /* The memory barrier in set_task_state saves us here. */ + if (data.got_token) +--- a/include/linux/wait.h ++++ b/include/linux/wait.h +@@ -1121,7 +1121,7 @@ do { \ + * Waitqueues which are removed from the waitqueue_head at wakeup time + */ + void prepare_to_wait(struct wait_queue_head *wq_head, struct wait_queue_entry *wq_entry, int state); +-void prepare_to_wait_exclusive(struct wait_queue_head *wq_head, struct wait_queue_entry *wq_entry, int state); ++bool prepare_to_wait_exclusive(struct wait_queue_head *wq_head, struct wait_queue_entry *wq_entry, int state); + long prepare_to_wait_event(struct wait_queue_head *wq_head, struct wait_queue_entry *wq_entry, int state); + void finish_wait(struct wait_queue_head *wq_head, struct wait_queue_entry *wq_entry); + long wait_woken(struct wait_queue_entry *wq_entry, unsigned mode, long timeout); +--- a/kernel/sched/wait.c ++++ b/kernel/sched/wait.c +@@ -232,17 +232,22 @@ prepare_to_wait(struct wait_queue_head * + } + EXPORT_SYMBOL(prepare_to_wait); + +-void ++/* Returns true if we are the first waiter in the queue, false otherwise. */ ++bool + prepare_to_wait_exclusive(struct wait_queue_head *wq_head, struct wait_queue_entry *wq_entry, int state) + { + unsigned long flags; ++ bool was_empty = false; + + wq_entry->flags |= WQ_FLAG_EXCLUSIVE; + spin_lock_irqsave(&wq_head->lock, flags); +- if (list_empty(&wq_entry->entry)) ++ if (list_empty(&wq_entry->entry)) { ++ was_empty = list_empty(&wq_head->head); + __add_wait_queue_entry_tail(wq_head, wq_entry); ++ } + set_current_state(state); + spin_unlock_irqrestore(&wq_head->lock, flags); ++ return was_empty; + } + EXPORT_SYMBOL(prepare_to_wait_exclusive); + diff --git a/queue-5.4/seq_buf-fix-overflow-in-seq_buf_putmem_hex.patch b/queue-5.4/seq_buf-fix-overflow-in-seq_buf_putmem_hex.patch new file mode 100644 index 00000000000..97f0237cb26 --- /dev/null +++ b/queue-5.4/seq_buf-fix-overflow-in-seq_buf_putmem_hex.patch @@ -0,0 +1,41 @@ +From d3b16034a24a112bb83aeb669ac5b9b01f744bb7 Mon Sep 17 00:00:00 2001 +From: Yun Zhou +Date: Sat, 26 Jun 2021 11:21:55 +0800 +Subject: seq_buf: Fix overflow in seq_buf_putmem_hex() + +From: Yun Zhou + +commit d3b16034a24a112bb83aeb669ac5b9b01f744bb7 upstream. + +There's two variables being increased in that loop (i and j), and i +follows the raw data, and j follows what is being written into the buffer. +We should compare 'i' to MAX_MEMHEX_BYTES or compare 'j' to HEX_CHARS. +Otherwise, if 'j' goes bigger than HEX_CHARS, it will overflow the +destination buffer. + +Link: https://lore.kernel.org/lkml/20210625122453.5e2fe304@oasis.local.home/ +Link: https://lkml.kernel.org/r/20210626032156.47889-1-yun.zhou@windriver.com + +Cc: stable@vger.kernel.org +Fixes: 5e3ca0ec76fce ("ftrace: introduce the "hex" output method") +Signed-off-by: Yun Zhou +Signed-off-by: Steven Rostedt (VMware) +Signed-off-by: Greg Kroah-Hartman +--- + lib/seq_buf.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/lib/seq_buf.c ++++ b/lib/seq_buf.c +@@ -228,8 +228,10 @@ int seq_buf_putmem_hex(struct seq_buf *s + + WARN_ON(s->size == 0); + ++ BUILD_BUG_ON(MAX_MEMHEX_BYTES * 2 >= HEX_CHARS); ++ + while (len) { +- start_len = min(len, HEX_CHARS - 1); ++ start_len = min(len, MAX_MEMHEX_BYTES); + #ifdef __BIG_ENDIAN + for (i = 0, j = 0; i < start_len; i++) { + #else diff --git a/queue-5.4/series b/queue-5.4/series index 02b7ad0d349..7316256383d 100644 --- a/queue-5.4/series +++ b/queue-5.4/series @@ -90,3 +90,24 @@ ata-ahci_sunxi-disable-dipm.patch cpu-hotplug-cure-the-cpusets-trainwreck.patch clocksource-arm_arch_timer-improve-allwinner-a64-timer-workaround.patch fpga-stratix10-soc-add-missing-fpga_mgr_free-call.patch +mips-fix-mipsel-linux-ld-decompress.c-undefined-reference-to-memmove.patch +asoc-tegra-set-driver_name-tegra-for-all-machine-drivers.patch +qemu_fw_cfg-make-fw_cfg_rev_attr-a-proper-kobj_attribute.patch +ipmi-watchdog-stop-watchdog-timer-when-the-current-action-is-none.patch +xfrm-policy-read-seqcount-outside-of-rcu-read-side-in-xfrm_policy_lookup_bytype.patch +thermal-drivers-int340x-processor_thermal-fix-tcc-setting.patch +ubifs-fix-races-between-xattr_-set-get-and-listxattr-operations.patch +power-supply-ab8500-fix-an-old-bug.patch +nvmem-core-add-a-missing-of_node_put.patch +extcon-intel-mrfld-sync-hardware-and-software-state-on-init.patch +seq_buf-fix-overflow-in-seq_buf_putmem_hex.patch +rq-qos-fix-missed-wake-ups-in-rq_qos_throttle-try-two.patch +tracing-simplify-fix-saved_tgids-logic.patch +tracing-resize-tgid_map-to-pid_max-not-pid_max_default.patch +ipack-carriers-tpci200-fix-a-double-free-in-tpci200_pci_probe.patch +coresight-tmc-etf-fix-global-out-of-bounds-in-tmc_update_etf_buffer.patch +dm-btree-remove-assign-new_root-only-when-removal-succeeds.patch +pci-leave-apple-thunderbolt-controllers-on-for-s2idle-or-standby.patch +pci-aardvark-fix-checking-for-pio-non-posted-request.patch +pci-aardvark-implement-workaround-for-the-readback-value-of-vend_id.patch +media-subdev-disallow-ioctl-for-saa6588-davinci.patch diff --git a/queue-5.4/thermal-drivers-int340x-processor_thermal-fix-tcc-setting.patch b/queue-5.4/thermal-drivers-int340x-processor_thermal-fix-tcc-setting.patch new file mode 100644 index 00000000000..1f01ccd4445 --- /dev/null +++ b/queue-5.4/thermal-drivers-int340x-processor_thermal-fix-tcc-setting.patch @@ -0,0 +1,89 @@ +From fe6a6de6692e7f7159c1ff42b07ecd737df712b4 Mon Sep 17 00:00:00 2001 +From: Srinivas Pandruvada +Date: Mon, 28 Jun 2021 14:58:03 -0700 +Subject: thermal/drivers/int340x/processor_thermal: Fix tcc setting + +From: Srinivas Pandruvada + +commit fe6a6de6692e7f7159c1ff42b07ecd737df712b4 upstream. + +The following fixes are done for tcc sysfs interface: +- TCC is 6 bits only from bit 29-24 +- TCC of 0 is valid +- When BIT(31) is set, this register is read only +- Check for invalid tcc value +- Error for negative values + +Fixes: fdf4f2fb8e899 ("drivers: thermal: processor_thermal_device: Export sysfs interface for TCC offset") +Signed-off-by: Srinivas Pandruvada +Cc: stable@vger.kernel.org +Acked-by: Zhang Rui +Signed-off-by: Daniel Lezcano +Link: https://lore.kernel.org/r/20210628215803.75038-1-srinivas.pandruvada@linux.intel.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/thermal/intel/int340x_thermal/processor_thermal_device.c | 20 ++++++---- + 1 file changed, 12 insertions(+), 8 deletions(-) + +--- a/drivers/thermal/intel/int340x_thermal/processor_thermal_device.c ++++ b/drivers/thermal/intel/int340x_thermal/processor_thermal_device.c +@@ -150,24 +150,27 @@ static ssize_t tcc_offset_degree_celsius + if (err) + return err; + +- val = (val >> 24) & 0xff; ++ val = (val >> 24) & 0x3f; + return sprintf(buf, "%d\n", (int)val); + } + +-static int tcc_offset_update(int tcc) ++static int tcc_offset_update(unsigned int tcc) + { + u64 val; + int err; + +- if (!tcc) ++ if (tcc > 63) + return -EINVAL; + + err = rdmsrl_safe(MSR_IA32_TEMPERATURE_TARGET, &val); + if (err) + return err; + +- val &= ~GENMASK_ULL(31, 24); +- val |= (tcc & 0xff) << 24; ++ if (val & BIT(31)) ++ return -EPERM; ++ ++ val &= ~GENMASK_ULL(29, 24); ++ val |= (tcc & 0x3f) << 24; + + err = wrmsrl_safe(MSR_IA32_TEMPERATURE_TARGET, val); + if (err) +@@ -176,14 +179,15 @@ static int tcc_offset_update(int tcc) + return 0; + } + +-static int tcc_offset_save; ++static unsigned int tcc_offset_save; + + static ssize_t tcc_offset_degree_celsius_store(struct device *dev, + struct device_attribute *attr, const char *buf, + size_t count) + { ++ unsigned int tcc; + u64 val; +- int tcc, err; ++ int err; + + err = rdmsrl_safe(MSR_PLATFORM_INFO, &val); + if (err) +@@ -192,7 +196,7 @@ static ssize_t tcc_offset_degree_celsius + if (!(val & BIT(30))) + return -EACCES; + +- if (kstrtoint(buf, 0, &tcc)) ++ if (kstrtouint(buf, 0, &tcc)) + return -EINVAL; + + err = tcc_offset_update(tcc); diff --git a/queue-5.4/tracing-resize-tgid_map-to-pid_max-not-pid_max_default.patch b/queue-5.4/tracing-resize-tgid_map-to-pid_max-not-pid_max_default.patch new file mode 100644 index 00000000000..dcbf39e8d4a --- /dev/null +++ b/queue-5.4/tracing-resize-tgid_map-to-pid_max-not-pid_max_default.patch @@ -0,0 +1,176 @@ +From 4030a6e6a6a4a42ff8c18414c9e0c93e24cc70b8 Mon Sep 17 00:00:00 2001 +From: Paul Burton +Date: Thu, 1 Jul 2021 10:24:07 -0700 +Subject: tracing: Resize tgid_map to pid_max, not PID_MAX_DEFAULT + +From: Paul Burton + +commit 4030a6e6a6a4a42ff8c18414c9e0c93e24cc70b8 upstream. + +Currently tgid_map is sized at PID_MAX_DEFAULT entries, which means that +on systems where pid_max is configured higher than PID_MAX_DEFAULT the +ftrace record-tgid option doesn't work so well. Any tasks with PIDs +higher than PID_MAX_DEFAULT are simply not recorded in tgid_map, and +don't show up in the saved_tgids file. + +In particular since systemd v243 & above configure pid_max to its +highest possible 1<<22 value by default on 64 bit systems this renders +the record-tgids option of little use. + +Increase the size of tgid_map to the configured pid_max instead, +allowing it to cover the full range of PIDs up to the maximum value of +PID_MAX_LIMIT if the system is configured that way. + +On 64 bit systems with pid_max == PID_MAX_LIMIT this will increase the +size of tgid_map from 256KiB to 16MiB. Whilst this 64x increase in +memory overhead sounds significant 64 bit systems are presumably best +placed to accommodate it, and since tgid_map is only allocated when the +record-tgid option is actually used presumably the user would rather it +spends sufficient memory to actually record the tgids they expect. + +The size of tgid_map could also increase for CONFIG_BASE_SMALL=y +configurations, but these seem unlikely to be systems upon which people +are both configuring a large pid_max and running ftrace with record-tgid +anyway. + +Of note is that we only allocate tgid_map once, the first time that the +record-tgid option is enabled. Therefore its size is only set once, to +the value of pid_max at the time the record-tgid option is first +enabled. If a user increases pid_max after that point, the saved_tgids +file will not contain entries for any tasks with pids beyond the earlier +value of pid_max. + +Link: https://lkml.kernel.org/r/20210701172407.889626-2-paulburton@google.com + +Fixes: d914ba37d714 ("tracing: Add support for recording tgid of tasks") +Cc: Ingo Molnar +Cc: Joel Fernandes +Cc: +Signed-off-by: Paul Burton +[ Fixed comment coding style ] +Signed-off-by: Steven Rostedt (VMware) +Signed-off-by: Greg Kroah-Hartman +--- + kernel/trace/trace.c | 63 ++++++++++++++++++++++++++++++++++++++------------- + 1 file changed, 47 insertions(+), 16 deletions(-) + +--- a/kernel/trace/trace.c ++++ b/kernel/trace/trace.c +@@ -1934,8 +1934,15 @@ void tracing_reset_all_online_cpus(void) + } + } + ++/* ++ * The tgid_map array maps from pid to tgid; i.e. the value stored at index i ++ * is the tgid last observed corresponding to pid=i. ++ */ + static int *tgid_map; + ++/* The maximum valid index into tgid_map. */ ++static size_t tgid_map_max; ++ + #define SAVED_CMDLINES_DEFAULT 128 + #define NO_CMDLINE_MAP UINT_MAX + static arch_spinlock_t trace_cmdline_lock = __ARCH_SPIN_LOCK_UNLOCKED; +@@ -2208,24 +2215,41 @@ void trace_find_cmdline(int pid, char co + preempt_enable(); + } + ++static int *trace_find_tgid_ptr(int pid) ++{ ++ /* ++ * Pairs with the smp_store_release in set_tracer_flag() to ensure that ++ * if we observe a non-NULL tgid_map then we also observe the correct ++ * tgid_map_max. ++ */ ++ int *map = smp_load_acquire(&tgid_map); ++ ++ if (unlikely(!map || pid > tgid_map_max)) ++ return NULL; ++ ++ return &map[pid]; ++} ++ + int trace_find_tgid(int pid) + { +- if (unlikely(!tgid_map || !pid || pid > PID_MAX_DEFAULT)) +- return 0; ++ int *ptr = trace_find_tgid_ptr(pid); + +- return tgid_map[pid]; ++ return ptr ? *ptr : 0; + } + + static int trace_save_tgid(struct task_struct *tsk) + { ++ int *ptr; ++ + /* treat recording of idle task as a success */ + if (!tsk->pid) + return 1; + +- if (unlikely(!tgid_map || tsk->pid > PID_MAX_DEFAULT)) ++ ptr = trace_find_tgid_ptr(tsk->pid); ++ if (!ptr) + return 0; + +- tgid_map[tsk->pid] = tsk->tgid; ++ *ptr = tsk->tgid; + return 1; + } + +@@ -4583,6 +4607,8 @@ int trace_keep_overwrite(struct tracer * + + int set_tracer_flag(struct trace_array *tr, unsigned int mask, int enabled) + { ++ int *map; ++ + if ((mask == TRACE_ITER_RECORD_TGID) || + (mask == TRACE_ITER_RECORD_CMD)) + lockdep_assert_held(&event_mutex); +@@ -4605,10 +4631,19 @@ int set_tracer_flag(struct trace_array * + trace_event_enable_cmd_record(enabled); + + if (mask == TRACE_ITER_RECORD_TGID) { +- if (!tgid_map) +- tgid_map = kvcalloc(PID_MAX_DEFAULT + 1, +- sizeof(*tgid_map), +- GFP_KERNEL); ++ if (!tgid_map) { ++ tgid_map_max = pid_max; ++ map = kvcalloc(tgid_map_max + 1, sizeof(*tgid_map), ++ GFP_KERNEL); ++ ++ /* ++ * Pairs with smp_load_acquire() in ++ * trace_find_tgid_ptr() to ensure that if it observes ++ * the tgid_map we just allocated then it also observes ++ * the corresponding tgid_map_max value. ++ */ ++ smp_store_release(&tgid_map, map); ++ } + if (!tgid_map) { + tr->trace_flags &= ~TRACE_ITER_RECORD_TGID; + return -ENOMEM; +@@ -5015,18 +5050,14 @@ static void *saved_tgids_next(struct seq + { + int pid = ++(*pos); + +- if (pid > PID_MAX_DEFAULT) +- return NULL; +- +- return &tgid_map[pid]; ++ return trace_find_tgid_ptr(pid); + } + + static void *saved_tgids_start(struct seq_file *m, loff_t *pos) + { +- if (!tgid_map || *pos > PID_MAX_DEFAULT) +- return NULL; ++ int pid = *pos; + +- return &tgid_map[*pos]; ++ return trace_find_tgid_ptr(pid); + } + + static void saved_tgids_stop(struct seq_file *m, void *v) diff --git a/queue-5.4/tracing-simplify-fix-saved_tgids-logic.patch b/queue-5.4/tracing-simplify-fix-saved_tgids-logic.patch new file mode 100644 index 00000000000..78056e5471e --- /dev/null +++ b/queue-5.4/tracing-simplify-fix-saved_tgids-logic.patch @@ -0,0 +1,111 @@ +From b81b3e959adb107cd5b36c7dc5ba1364bbd31eb2 Mon Sep 17 00:00:00 2001 +From: Paul Burton +Date: Tue, 29 Jun 2021 17:34:05 -0700 +Subject: tracing: Simplify & fix saved_tgids logic + +From: Paul Burton + +commit b81b3e959adb107cd5b36c7dc5ba1364bbd31eb2 upstream. + +The tgid_map array records a mapping from pid to tgid, where the index +of an entry within the array is the pid & the value stored at that index +is the tgid. + +The saved_tgids_next() function iterates over pointers into the tgid_map +array & dereferences the pointers which results in the tgid, but then it +passes that dereferenced value to trace_find_tgid() which treats it as a +pid & does a further lookup within the tgid_map array. It seems likely +that the intent here was to skip over entries in tgid_map for which the +recorded tgid is zero, but instead we end up skipping over entries for +which the thread group leader hasn't yet had its own tgid recorded in +tgid_map. + +A minimal fix would be to remove the call to trace_find_tgid, turning: + + if (trace_find_tgid(*ptr)) + +into: + + if (*ptr) + +..but it seems like this logic can be much simpler if we simply let +seq_read() iterate over the whole tgid_map array & filter out empty +entries by returning SEQ_SKIP from saved_tgids_show(). Here we take that +approach, removing the incorrect logic here entirely. + +Link: https://lkml.kernel.org/r/20210630003406.4013668-1-paulburton@google.com + +Fixes: d914ba37d714 ("tracing: Add support for recording tgid of tasks") +Cc: Ingo Molnar +Cc: Joel Fernandes +Cc: +Signed-off-by: Paul Burton +Signed-off-by: Steven Rostedt (VMware) +Signed-off-by: Greg Kroah-Hartman +--- + kernel/trace/trace.c | 38 +++++++++++++------------------------- + 1 file changed, 13 insertions(+), 25 deletions(-) + +--- a/kernel/trace/trace.c ++++ b/kernel/trace/trace.c +@@ -5013,37 +5013,20 @@ static const struct file_operations trac + + static void *saved_tgids_next(struct seq_file *m, void *v, loff_t *pos) + { +- int *ptr = v; ++ int pid = ++(*pos); + +- if (*pos || m->count) +- ptr++; +- +- (*pos)++; +- +- for (; ptr <= &tgid_map[PID_MAX_DEFAULT]; ptr++) { +- if (trace_find_tgid(*ptr)) +- return ptr; +- } ++ if (pid > PID_MAX_DEFAULT) ++ return NULL; + +- return NULL; ++ return &tgid_map[pid]; + } + + static void *saved_tgids_start(struct seq_file *m, loff_t *pos) + { +- void *v; +- loff_t l = 0; +- +- if (!tgid_map) ++ if (!tgid_map || *pos > PID_MAX_DEFAULT) + return NULL; + +- v = &tgid_map[0]; +- while (l <= *pos) { +- v = saved_tgids_next(m, v, &l); +- if (!v) +- return NULL; +- } +- +- return v; ++ return &tgid_map[*pos]; + } + + static void saved_tgids_stop(struct seq_file *m, void *v) +@@ -5052,9 +5035,14 @@ static void saved_tgids_stop(struct seq_ + + static int saved_tgids_show(struct seq_file *m, void *v) + { +- int pid = (int *)v - tgid_map; ++ int *entry = (int *)v; ++ int pid = entry - tgid_map; ++ int tgid = *entry; ++ ++ if (tgid == 0) ++ return SEQ_SKIP; + +- seq_printf(m, "%d %d\n", pid, trace_find_tgid(pid)); ++ seq_printf(m, "%d %d\n", pid, tgid); + return 0; + } + diff --git a/queue-5.4/ubifs-fix-races-between-xattr_-set-get-and-listxattr-operations.patch b/queue-5.4/ubifs-fix-races-between-xattr_-set-get-and-listxattr-operations.patch new file mode 100644 index 00000000000..630d69fdd55 --- /dev/null +++ b/queue-5.4/ubifs-fix-races-between-xattr_-set-get-and-listxattr-operations.patch @@ -0,0 +1,220 @@ +From f4e3634a3b642225a530c292fdb1e8a4007507f5 Mon Sep 17 00:00:00 2001 +From: Zhihao Cheng +Date: Mon, 31 May 2021 20:52:09 +0800 +Subject: ubifs: Fix races between xattr_{set|get} and listxattr operations + +From: Zhihao Cheng + +commit f4e3634a3b642225a530c292fdb1e8a4007507f5 upstream. + +UBIFS may occur some problems with concurrent xattr_{set|get} and +listxattr operations, such as assertion failure, memory corruption, +stale xattr value[1]. + +Fix it by importing a new rw-lock in @ubifs_inode to serilize write +operations on xattr, concurrent read operations are still effective, +just like ext4. + +[1] https://lore.kernel.org/linux-mtd/20200630130438.141649-1-houtao1@huawei.com + +Fixes: 1e51764a3c2ac05a23 ("UBIFS: add new flash file system") +Cc: stable@vger.kernel.org # v2.6+ +Signed-off-by: Zhihao Cheng +Reviewed-by: Sascha Hauer +Signed-off-by: Richard Weinberger +Signed-off-by: Greg Kroah-Hartman +--- + fs/ubifs/super.c | 1 + + fs/ubifs/ubifs.h | 2 ++ + fs/ubifs/xattr.c | 44 +++++++++++++++++++++++++++++++++----------- + 3 files changed, 36 insertions(+), 11 deletions(-) + +--- a/fs/ubifs/super.c ++++ b/fs/ubifs/super.c +@@ -257,6 +257,7 @@ static struct inode *ubifs_alloc_inode(s + memset((void *)ui + sizeof(struct inode), 0, + sizeof(struct ubifs_inode) - sizeof(struct inode)); + mutex_init(&ui->ui_mutex); ++ init_rwsem(&ui->xattr_sem); + spin_lock_init(&ui->ui_lock); + return &ui->vfs_inode; + }; +--- a/fs/ubifs/ubifs.h ++++ b/fs/ubifs/ubifs.h +@@ -356,6 +356,7 @@ struct ubifs_gced_idx_leb { + * @ui_mutex: serializes inode write-back with the rest of VFS operations, + * serializes "clean <-> dirty" state changes, serializes bulk-read, + * protects @dirty, @bulk_read, @ui_size, and @xattr_size ++ * @xattr_sem: serilizes write operations (remove|set|create) on xattr + * @ui_lock: protects @synced_i_size + * @synced_i_size: synchronized size of inode, i.e. the value of inode size + * currently stored on the flash; used only for regular file +@@ -409,6 +410,7 @@ struct ubifs_inode { + unsigned int bulk_read:1; + unsigned int compr_type:2; + struct mutex ui_mutex; ++ struct rw_semaphore xattr_sem; + spinlock_t ui_lock; + loff_t synced_i_size; + loff_t ui_size; +--- a/fs/ubifs/xattr.c ++++ b/fs/ubifs/xattr.c +@@ -285,6 +285,7 @@ int ubifs_xattr_set(struct inode *host, + if (!xent) + return -ENOMEM; + ++ down_write(&ubifs_inode(host)->xattr_sem); + /* + * The extended attribute entries are stored in LNC, so multiple + * look-ups do not involve reading the flash. +@@ -319,6 +320,7 @@ int ubifs_xattr_set(struct inode *host, + iput(inode); + + out_free: ++ up_write(&ubifs_inode(host)->xattr_sem); + kfree(xent); + return err; + } +@@ -341,18 +343,19 @@ ssize_t ubifs_xattr_get(struct inode *ho + if (!xent) + return -ENOMEM; + ++ down_read(&ubifs_inode(host)->xattr_sem); + xent_key_init(c, &key, host->i_ino, &nm); + err = ubifs_tnc_lookup_nm(c, &key, xent, &nm); + if (err) { + if (err == -ENOENT) + err = -ENODATA; +- goto out_unlock; ++ goto out_cleanup; + } + + inode = iget_xattr(c, le64_to_cpu(xent->inum)); + if (IS_ERR(inode)) { + err = PTR_ERR(inode); +- goto out_unlock; ++ goto out_cleanup; + } + + ui = ubifs_inode(inode); +@@ -374,7 +377,8 @@ ssize_t ubifs_xattr_get(struct inode *ho + out_iput: + mutex_unlock(&ui->ui_mutex); + iput(inode); +-out_unlock: ++out_cleanup: ++ up_read(&ubifs_inode(host)->xattr_sem); + kfree(xent); + return err; + } +@@ -406,16 +410,21 @@ ssize_t ubifs_listxattr(struct dentry *d + dbg_gen("ino %lu ('%pd'), buffer size %zd", host->i_ino, + dentry, size); + ++ down_read(&host_ui->xattr_sem); + len = host_ui->xattr_names + host_ui->xattr_cnt; +- if (!buffer) ++ if (!buffer) { + /* + * We should return the minimum buffer size which will fit a + * null-terminated list of all the extended attribute names. + */ +- return len; ++ err = len; ++ goto out_err; ++ } + +- if (len > size) +- return -ERANGE; ++ if (len > size) { ++ err = -ERANGE; ++ goto out_err; ++ } + + lowest_xent_key(c, &key, host->i_ino); + while (1) { +@@ -437,8 +446,9 @@ ssize_t ubifs_listxattr(struct dentry *d + pxent = xent; + key_read(c, &xent->key, &key); + } +- + kfree(pxent); ++ up_read(&host_ui->xattr_sem); ++ + if (err != -ENOENT) { + ubifs_err(c, "cannot find next direntry, error %d", err); + return err; +@@ -446,6 +456,10 @@ ssize_t ubifs_listxattr(struct dentry *d + + ubifs_assert(c, written <= size); + return written; ++ ++out_err: ++ up_read(&host_ui->xattr_sem); ++ return err; + } + + static int remove_xattr(struct ubifs_info *c, struct inode *host, +@@ -504,6 +518,7 @@ int ubifs_purge_xattrs(struct inode *hos + ubifs_warn(c, "inode %lu has too many xattrs, doing a non-atomic deletion", + host->i_ino); + ++ down_write(&ubifs_inode(host)->xattr_sem); + lowest_xent_key(c, &key, host->i_ino); + while (1) { + xent = ubifs_tnc_next_ent(c, &key, &nm); +@@ -523,7 +538,7 @@ int ubifs_purge_xattrs(struct inode *hos + ubifs_ro_mode(c, err); + kfree(pxent); + kfree(xent); +- return err; ++ goto out_err; + } + + ubifs_assert(c, ubifs_inode(xino)->xattr); +@@ -535,7 +550,7 @@ int ubifs_purge_xattrs(struct inode *hos + kfree(xent); + iput(xino); + ubifs_err(c, "cannot remove xattr, error %d", err); +- return err; ++ goto out_err; + } + + iput(xino); +@@ -544,14 +559,19 @@ int ubifs_purge_xattrs(struct inode *hos + pxent = xent; + key_read(c, &xent->key, &key); + } +- + kfree(pxent); ++ up_write(&ubifs_inode(host)->xattr_sem); ++ + if (err != -ENOENT) { + ubifs_err(c, "cannot find next direntry, error %d", err); + return err; + } + + return 0; ++ ++out_err: ++ up_write(&ubifs_inode(host)->xattr_sem); ++ return err; + } + + /** +@@ -594,6 +614,7 @@ static int ubifs_xattr_remove(struct ino + if (!xent) + return -ENOMEM; + ++ down_write(&ubifs_inode(host)->xattr_sem); + xent_key_init(c, &key, host->i_ino, &nm); + err = ubifs_tnc_lookup_nm(c, &key, xent, &nm); + if (err) { +@@ -618,6 +639,7 @@ static int ubifs_xattr_remove(struct ino + iput(inode); + + out_free: ++ up_write(&ubifs_inode(host)->xattr_sem); + kfree(xent); + return err; + } diff --git a/queue-5.4/xfrm-policy-read-seqcount-outside-of-rcu-read-side-in-xfrm_policy_lookup_bytype.patch b/queue-5.4/xfrm-policy-read-seqcount-outside-of-rcu-read-side-in-xfrm_policy_lookup_bytype.patch new file mode 100644 index 00000000000..232290e8189 --- /dev/null +++ b/queue-5.4/xfrm-policy-read-seqcount-outside-of-rcu-read-side-in-xfrm_policy_lookup_bytype.patch @@ -0,0 +1,102 @@ +From d7b0408934c749f546b01f2b33d07421a49b6f3e Mon Sep 17 00:00:00 2001 +From: Varad Gautam +Date: Fri, 28 May 2021 18:04:06 +0200 +Subject: xfrm: policy: Read seqcount outside of rcu-read side in xfrm_policy_lookup_bytype + +From: Varad Gautam + +commit d7b0408934c749f546b01f2b33d07421a49b6f3e upstream. + +xfrm_policy_lookup_bytype loops on seqcount mutex xfrm_policy_hash_generation +within an RCU read side critical section. Although ill advised, this is fine if +the loop is bounded. + +xfrm_policy_hash_generation wraps mutex hash_resize_mutex, which is used to +serialize writers (xfrm_hash_resize, xfrm_hash_rebuild). This is fine too. + +On PREEMPT_RT=y, the read_seqcount_begin call within xfrm_policy_lookup_bytype +emits a mutex lock/unlock for hash_resize_mutex. Mutex locking is fine, since +RCU read side critical sections are allowed to sleep with PREEMPT_RT. + +xfrm_hash_resize can, however, block on synchronize_rcu while holding +hash_resize_mutex. + +This leads to the following situation on PREEMPT_RT, where the writer is +blocked on RCU grace period expiry, while the reader is blocked on a lock held +by the writer: + +Thead 1 (xfrm_hash_resize) Thread 2 (xfrm_policy_lookup_bytype) + + rcu_read_lock(); +mutex_lock(&hash_resize_mutex); + read_seqcount_begin(&xfrm_policy_hash_generation); + mutex_lock(&hash_resize_mutex); // block +xfrm_bydst_resize(); +synchronize_rcu(); // block + + +Move the read_seqcount_begin call outside of the RCU read side critical section, +and do an rcu_read_unlock/retry if we got stale data within the critical section. + +On non-PREEMPT_RT, this shortens the time spent within RCU read side critical +section in case the seqcount needs a retry, and avoids unbounded looping. + +Fixes: 77cc278f7b20 ("xfrm: policy: Use sequence counters with associated lock") +Signed-off-by: Varad Gautam +Cc: linux-rt-users +Cc: netdev@vger.kernel.org +Cc: stable@vger.kernel.org # v4.9 +Cc: Steffen Klassert +Cc: Herbert Xu +Cc: "David S. Miller" +Cc: Jakub Kicinski +Cc: Florian Westphal +Cc: "Ahmed S. Darwish" +Signed-off-by: Steffen Klassert +Acked-by: Ahmed S. Darwish +Signed-off-by: Greg Kroah-Hartman +--- + net/xfrm/xfrm_policy.c | 21 ++++++++++++++------- + 1 file changed, 14 insertions(+), 7 deletions(-) + +--- a/net/xfrm/xfrm_policy.c ++++ b/net/xfrm/xfrm_policy.c +@@ -2089,12 +2089,15 @@ static struct xfrm_policy *xfrm_policy_l + if (unlikely(!daddr || !saddr)) + return NULL; + +- rcu_read_lock(); + retry: +- do { +- sequence = read_seqcount_begin(&xfrm_policy_hash_generation); +- chain = policy_hash_direct(net, daddr, saddr, family, dir); +- } while (read_seqcount_retry(&xfrm_policy_hash_generation, sequence)); ++ sequence = read_seqcount_begin(&xfrm_policy_hash_generation); ++ rcu_read_lock(); ++ ++ chain = policy_hash_direct(net, daddr, saddr, family, dir); ++ if (read_seqcount_retry(&xfrm_policy_hash_generation, sequence)) { ++ rcu_read_unlock(); ++ goto retry; ++ } + + ret = NULL; + hlist_for_each_entry_rcu(pol, chain, bydst) { +@@ -2125,11 +2128,15 @@ static struct xfrm_policy *xfrm_policy_l + } + + skip_inexact: +- if (read_seqcount_retry(&xfrm_policy_hash_generation, sequence)) ++ if (read_seqcount_retry(&xfrm_policy_hash_generation, sequence)) { ++ rcu_read_unlock(); + goto retry; ++ } + +- if (ret && !xfrm_pol_hold_rcu(ret)) ++ if (ret && !xfrm_pol_hold_rcu(ret)) { ++ rcu_read_unlock(); + goto retry; ++ } + fail: + rcu_read_unlock(); +