From: Sasha Levin Date: Tue, 19 Sep 2023 17:29:03 +0000 (-0400) Subject: Fixes for 6.5 X-Git-Tag: v5.10.196~38 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=be4fd9697cdffd702438895aabaeb4427ae01dd2;p=thirdparty%2Fkernel%2Fstable-queue.git Fixes for 6.5 Signed-off-by: Sasha Levin --- diff --git a/queue-6.5/acpi-video-add-backlight-native-dmi-quirk-for-apple-.patch b/queue-6.5/acpi-video-add-backlight-native-dmi-quirk-for-apple-.patch new file mode 100644 index 00000000000..7895ecae0f4 --- /dev/null +++ b/queue-6.5/acpi-video-add-backlight-native-dmi-quirk-for-apple-.patch @@ -0,0 +1,56 @@ +From c9a113dea3a1bf99eed327789c3416828d3e7768 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 7 Aug 2023 11:44:08 +0200 +Subject: ACPI: video: Add backlight=native DMI quirk for Apple iMac12,1 and + iMac12,2 + +From: Hans de Goede + +[ Upstream commit 8cf04bb321f036dd2e523e993897e0789bd5265c ] + +Linux defaults to picking the non-working ACPI video backlight interface +on the Apple iMac12,1 and iMac12,2. + +Add a DMI quirk to pick the working native radeon_bl0 interface instead. + +Link: https://gitlab.freedesktop.org/drm/amd/-/issues/1838 +Link: https://gitlab.freedesktop.org/drm/amd/-/issues/2753 +Signed-off-by: Hans de Goede +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Sasha Levin +--- + drivers/acpi/video_detect.c | 18 ++++++++++++++++++ + 1 file changed, 18 insertions(+) + +diff --git a/drivers/acpi/video_detect.c b/drivers/acpi/video_detect.c +index 0c376edd64fe1..442396f6ed1f9 100644 +--- a/drivers/acpi/video_detect.c ++++ b/drivers/acpi/video_detect.c +@@ -495,6 +495,24 @@ static const struct dmi_system_id video_detect_dmi_table[] = { + DMI_MATCH(DMI_PRODUCT_NAME, "iMac11,3"), + }, + }, ++ { ++ /* https://gitlab.freedesktop.org/drm/amd/-/issues/1838 */ ++ .callback = video_detect_force_native, ++ /* Apple iMac12,1 */ ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "Apple Inc."), ++ DMI_MATCH(DMI_PRODUCT_NAME, "iMac12,1"), ++ }, ++ }, ++ { ++ /* https://gitlab.freedesktop.org/drm/amd/-/issues/2753 */ ++ .callback = video_detect_force_native, ++ /* Apple iMac12,2 */ ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "Apple Inc."), ++ DMI_MATCH(DMI_PRODUCT_NAME, "iMac12,2"), ++ }, ++ }, + { + /* https://bugzilla.redhat.com/show_bug.cgi?id=1217249 */ + .callback = video_detect_force_native, +-- +2.40.1 + diff --git a/queue-6.5/acpi-video-add-backlight-native-dmi-quirk-for-lenovo.patch b/queue-6.5/acpi-video-add-backlight-native-dmi-quirk-for-lenovo.patch new file mode 100644 index 00000000000..4c4af2122e3 --- /dev/null +++ b/queue-6.5/acpi-video-add-backlight-native-dmi-quirk-for-lenovo.patch @@ -0,0 +1,47 @@ +From 65ea05f982888ba760d308e90846e2e6d62ba6e1 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 18 Apr 2023 08:42:00 +0200 +Subject: ACPI: video: Add backlight=native DMI quirk for Lenovo Ideapad Z470 + +From: Jiri Slaby (SUSE) + +[ Upstream commit 96b709be183c56293933ef45b8b75f8af268c6de ] + +The Lenovo Ideapad Z470 predates Windows 8, so it defaults to using +acpi_video for backlight control. But this is not functional on this +model. + +Add a DMI quirk to use the native backlight interface which works. + +Link: https://bugzilla.suse.com/show_bug.cgi?id=1208724 +Signed-off-by: Jiri Slaby (SUSE) +Reviewed-by: Hans de Goede +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Sasha Levin +--- + drivers/acpi/video_detect.c | 9 +++++++++ + 1 file changed, 9 insertions(+) + +diff --git a/drivers/acpi/video_detect.c b/drivers/acpi/video_detect.c +index 18cc08c858cf2..0c376edd64fe1 100644 +--- a/drivers/acpi/video_detect.c ++++ b/drivers/acpi/video_detect.c +@@ -445,6 +445,15 @@ static const struct dmi_system_id video_detect_dmi_table[] = { + DMI_MATCH(DMI_BOARD_NAME, "Lenovo IdeaPad S405"), + }, + }, ++ { ++ /* https://bugzilla.suse.com/show_bug.cgi?id=1208724 */ ++ .callback = video_detect_force_native, ++ /* Lenovo Ideapad Z470 */ ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), ++ DMI_MATCH(DMI_PRODUCT_VERSION, "IdeaPad Z470"), ++ }, ++ }, + { + /* https://bugzilla.redhat.com/show_bug.cgi?id=1187004 */ + .callback = video_detect_force_native, +-- +2.40.1 + diff --git a/queue-6.5/acpi-x86-s2idle-catch-multiple-acpi_type_package-obj.patch b/queue-6.5/acpi-x86-s2idle-catch-multiple-acpi_type_package-obj.patch new file mode 100644 index 00000000000..b3ba5f0eb1e --- /dev/null +++ b/queue-6.5/acpi-x86-s2idle-catch-multiple-acpi_type_package-obj.patch @@ -0,0 +1,41 @@ +From 1815c1db2a9d8c640f3bed0d5e2538a88af9882f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 18 Aug 2023 14:40:03 -0500 +Subject: ACPI: x86: s2idle: Catch multiple ACPI_TYPE_PACKAGE objects + +From: Mario Limonciello + +[ Upstream commit 883cf0d4cf288313b71146ddebdf5d647b76c78b ] + +If a badly constructed firmware includes multiple `ACPI_TYPE_PACKAGE` +objects while evaluating the AMD LPS0 _DSM, there will be a memory +leak. Explicitly guard against this. + +Suggested-by: Bjorn Helgaas +Signed-off-by: Mario Limonciello +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Sasha Levin +--- + drivers/acpi/x86/s2idle.c | 6 ++++++ + 1 file changed, 6 insertions(+) + +diff --git a/drivers/acpi/x86/s2idle.c b/drivers/acpi/x86/s2idle.c +index 60cc4605169c5..60835953ebfc4 100644 +--- a/drivers/acpi/x86/s2idle.c ++++ b/drivers/acpi/x86/s2idle.c +@@ -113,6 +113,12 @@ static void lpi_device_get_constraints_amd(void) + union acpi_object *package = &out_obj->package.elements[i]; + + if (package->type == ACPI_TYPE_PACKAGE) { ++ if (lpi_constraints_table) { ++ acpi_handle_err(lps0_device_handle, ++ "Duplicate constraints list\n"); ++ goto free_acpi_buffer; ++ } ++ + lpi_constraints_table = kcalloc(package->package.count, + sizeof(*lpi_constraints_table), + GFP_KERNEL); +-- +2.40.1 + diff --git a/queue-6.5/acpica-add-aml_no_operand_resolve-flag-to-timer.patch b/queue-6.5/acpica-add-aml_no_operand_resolve-flag-to-timer.patch new file mode 100644 index 00000000000..2a075402467 --- /dev/null +++ b/queue-6.5/acpica-add-aml_no_operand_resolve-flag-to-timer.patch @@ -0,0 +1,60 @@ +From 5fe8082ea480d073139fd9141d4c159acc63ef95 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 26 Jun 2023 22:26:06 +0000 +Subject: ACPICA: Add AML_NO_OPERAND_RESOLVE flag to Timer + +From: Abhishek Mainkar + +[ Upstream commit 3a21ffdbc825e0919db9da0e27ee5ff2cc8a863e ] + +ACPICA commit 90310989a0790032f5a0140741ff09b545af4bc5 + +According to the ACPI specification 19.6.134, no argument is required to be passed for ASL Timer instruction. For taking care of no argument, AML_NO_OPERAND_RESOLVE flag is added to ASL Timer instruction opcode. + +When ASL timer instruction interpreted by ACPI interpreter, getting error. After adding AML_NO_OPERAND_RESOLVE flag to ASL Timer instruction opcode, issue is not observed. + +============================================================= +UBSAN: array-index-out-of-bounds in acpica/dswexec.c:401:12 index -1 is out of range for type 'union acpi_operand_object *[9]' +CPU: 37 PID: 1678 Comm: cat Not tainted +6.0.0-dev-th500-6.0.y-1+bcf8c46459e407-generic-64k +HW name: NVIDIA BIOS v1.1.1-d7acbfc-dirty 12/19/2022 Call trace: + dump_backtrace+0xe0/0x130 + show_stack+0x20/0x60 + dump_stack_lvl+0x68/0x84 + dump_stack+0x18/0x34 + ubsan_epilogue+0x10/0x50 + __ubsan_handle_out_of_bounds+0x80/0x90 + acpi_ds_exec_end_op+0x1bc/0x6d8 + acpi_ps_parse_loop+0x57c/0x618 + acpi_ps_parse_aml+0x1e0/0x4b4 + acpi_ps_execute_method+0x24c/0x2b8 + acpi_ns_evaluate+0x3a8/0x4bc + acpi_evaluate_object+0x15c/0x37c + acpi_evaluate_integer+0x54/0x15c + show_power+0x8c/0x12c [acpi_power_meter] + +Link: https://github.com/acpica/acpica/commit/90310989 +Signed-off-by: Abhishek Mainkar +Signed-off-by: Bob Moore +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Sasha Levin +--- + drivers/acpi/acpica/psopcode.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/acpi/acpica/psopcode.c b/drivers/acpi/acpica/psopcode.c +index 09029fe545f14..39e31030e5f49 100644 +--- a/drivers/acpi/acpica/psopcode.c ++++ b/drivers/acpi/acpica/psopcode.c +@@ -603,7 +603,7 @@ const struct acpi_opcode_info acpi_gbl_aml_op_info[AML_NUM_OPCODES] = { + + /* 7E */ ACPI_OP("Timer", ARGP_TIMER_OP, ARGI_TIMER_OP, ACPI_TYPE_ANY, + AML_CLASS_EXECUTE, AML_TYPE_EXEC_0A_0T_1R, +- AML_FLAGS_EXEC_0A_0T_1R), ++ AML_FLAGS_EXEC_0A_0T_1R | AML_NO_OPERAND_RESOLVE), + + /* ACPI 5.0 opcodes */ + +-- +2.40.1 + diff --git a/queue-6.5/alsa-hda-intel-dsp-cfg-add-lunarlake-support.patch b/queue-6.5/alsa-hda-intel-dsp-cfg-add-lunarlake-support.patch new file mode 100644 index 00000000000..2f1bc3affc5 --- /dev/null +++ b/queue-6.5/alsa-hda-intel-dsp-cfg-add-lunarlake-support.patch @@ -0,0 +1,43 @@ +From 1d6c692fde9f6b38f4bb03f9aab7462ca50193ea Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 2 Aug 2023 10:01:04 -0500 +Subject: ALSA: hda: intel-dsp-cfg: add LunarLake support + +From: Pierre-Louis Bossart + +[ Upstream commit d2852b8c045ebd31d753b06f2810df5be30ed56a ] + +One more PCI ID for the road. + +Signed-off-by: Pierre-Louis Bossart +Reviewed-by: Ranjani Sridharan +Reviewed-by: Bard Liao +Link: https://lore.kernel.org/r/20230802150105.24604-5-pierre-louis.bossart@linux.intel.com +Signed-off-by: Takashi Iwai +Signed-off-by: Sasha Levin +--- + sound/hda/intel-dsp-config.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/sound/hda/intel-dsp-config.c b/sound/hda/intel-dsp-config.c +index 317bdf6dcbef4..2873420c9aca8 100644 +--- a/sound/hda/intel-dsp-config.c ++++ b/sound/hda/intel-dsp-config.c +@@ -481,6 +481,14 @@ static const struct config_entry config_table[] = { + }, + #endif + ++/* Lunar Lake */ ++#if IS_ENABLED(CONFIG_SND_SOC_SOF_LUNARLAKE) ++ /* Lunarlake-P */ ++ { ++ .flags = FLAG_SOF | FLAG_SOF_ONLY_IF_DMIC_OR_SOUNDWIRE, ++ .device = PCI_DEVICE_ID_INTEL_HDA_LNL_P, ++ }, ++#endif + }; + + static const struct config_entry *snd_intel_dsp_find_config +-- +2.40.1 + diff --git a/queue-6.5/alx-fix-oob-read-compiler-warning.patch b/queue-6.5/alx-fix-oob-read-compiler-warning.patch new file mode 100644 index 00000000000..823533ffe27 --- /dev/null +++ b/queue-6.5/alx-fix-oob-read-compiler-warning.patch @@ -0,0 +1,54 @@ +From 3388463a27d0199c61c21ba82eb9cd5177d36574 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 21 Aug 2023 09:32:18 +0800 +Subject: alx: fix OOB-read compiler warning +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: GONG, Ruiqi + +[ Upstream commit 3a198c95c95da10ad844cbeade2fe40bdf14c411 ] + +The following message shows up when compiling with W=1: + +In function ‘fortify_memcpy_chk’, + inlined from ‘alx_get_ethtool_stats’ at drivers/net/ethernet/atheros/alx/ethtool.c:297:2: +./include/linux/fortify-string.h:592:4: error: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Werror=attribute-warning] + 592 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +In order to get alx stats altogether, alx_get_ethtool_stats() reads +beyond hw->stats.rx_ok. Fix this warning by directly copying hw->stats, +and refactor the unnecessarily complicated BUILD_BUG_ON btw. + +Signed-off-by: GONG, Ruiqi +Reviewed-by: Simon Horman +Link: https://lore.kernel.org/r/20230821013218.1614265-1-gongruiqi@huaweicloud.com +Signed-off-by: Paolo Abeni +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/atheros/alx/ethtool.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +diff --git a/drivers/net/ethernet/atheros/alx/ethtool.c b/drivers/net/ethernet/atheros/alx/ethtool.c +index b716adacd8159..7f6b69a523676 100644 +--- a/drivers/net/ethernet/atheros/alx/ethtool.c ++++ b/drivers/net/ethernet/atheros/alx/ethtool.c +@@ -292,9 +292,8 @@ static void alx_get_ethtool_stats(struct net_device *netdev, + spin_lock(&alx->stats_lock); + + alx_update_hw_stats(hw); +- BUILD_BUG_ON(sizeof(hw->stats) - offsetof(struct alx_hw_stats, rx_ok) < +- ALX_NUM_STATS * sizeof(u64)); +- memcpy(data, &hw->stats.rx_ok, ALX_NUM_STATS * sizeof(u64)); ++ BUILD_BUG_ON(sizeof(hw->stats) != ALX_NUM_STATS * sizeof(u64)); ++ memcpy(data, &hw->stats, sizeof(hw->stats)); + + spin_unlock(&alx->stats_lock); + } +-- +2.40.1 + diff --git a/queue-6.5/arm-9317-1-kexec-make-smp-stop-calls-asynchronous.patch b/queue-6.5/arm-9317-1-kexec-make-smp-stop-calls-asynchronous.patch new file mode 100644 index 00000000000..067b884ce97 --- /dev/null +++ b/queue-6.5/arm-9317-1-kexec-make-smp-stop-calls-asynchronous.patch @@ -0,0 +1,81 @@ +From a9743bb4d8a23ed852f3468668b287ec01ea814f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 09:37:32 +0100 +Subject: ARM: 9317/1: kexec: Make smp stop calls asynchronous +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Mårten Lindahl + +[ Upstream commit 8922ba71c969d2a0c01a94372a71477d879470de ] + +If a panic is triggered by a hrtimer interrupt all online cpus will be +notified and set offline. But as highlighted by commit 19dbdcb8039c +("smp: Warn on function calls from softirq context") this call should +not be made synchronous with disabled interrupts: + + softdog: Initiating panic + Kernel panic - not syncing: Software Watchdog Timer expired + WARNING: CPU: 1 PID: 0 at kernel/smp.c:753 smp_call_function_many_cond + unwind_backtrace: + show_stack + dump_stack_lvl + __warn + warn_slowpath_fmt + smp_call_function_many_cond + smp_call_function + crash_smp_send_stop.part.0 + machine_crash_shutdown + __crash_kexec + panic + softdog_fire + __hrtimer_run_queues + hrtimer_interrupt + +Make the smp call for machine_crash_nonpanic_core() asynchronous. + +Signed-off-by: Mårten Lindahl +Signed-off-by: Russell King (Oracle) +Signed-off-by: Sasha Levin +--- + arch/arm/kernel/machine_kexec.c | 14 +++++++++++++- + 1 file changed, 13 insertions(+), 1 deletion(-) + +diff --git a/arch/arm/kernel/machine_kexec.c b/arch/arm/kernel/machine_kexec.c +index 46364b699cc30..5d07cf9e0044d 100644 +--- a/arch/arm/kernel/machine_kexec.c ++++ b/arch/arm/kernel/machine_kexec.c +@@ -94,16 +94,28 @@ static void machine_crash_nonpanic_core(void *unused) + } + } + ++static DEFINE_PER_CPU(call_single_data_t, cpu_stop_csd) = ++ CSD_INIT(machine_crash_nonpanic_core, NULL); ++ + void crash_smp_send_stop(void) + { + static int cpus_stopped; + unsigned long msecs; ++ call_single_data_t *csd; ++ int cpu, this_cpu = raw_smp_processor_id(); + + if (cpus_stopped) + return; + + atomic_set(&waiting_for_crash_ipi, num_online_cpus() - 1); +- smp_call_function(machine_crash_nonpanic_core, NULL, false); ++ for_each_online_cpu(cpu) { ++ if (cpu == this_cpu) ++ continue; ++ ++ csd = &per_cpu(cpu_stop_csd, cpu); ++ smp_call_function_single_async(cpu, csd); ++ } ++ + msecs = 1000; /* Wait at most a second for the other cpus to stop */ + while ((atomic_read(&waiting_for_crash_ipi) > 0) && msecs) { + mdelay(1); +-- +2.40.1 + diff --git a/queue-6.5/arm64-dts-qcom-sc8280xp-x13s-add-camera-activity-led.patch b/queue-6.5/arm64-dts-qcom-sc8280xp-x13s-add-camera-activity-led.patch new file mode 100644 index 00000000000..20d7a91e912 --- /dev/null +++ b/queue-6.5/arm64-dts-qcom-sc8280xp-x13s-add-camera-activity-led.patch @@ -0,0 +1,58 @@ +From 2ee89570b5fd9cdc61e00749f8d3a2aefef65aac Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 5 Aug 2023 11:01:33 +0200 +Subject: arm64: dts: qcom: sc8280xp-x13s: Add camera activity LED + +From: Konrad Dybcio + +[ Upstream commit 1c63dd1c5fdafa8854526d7d60d2b741c813678d ] + +Disappointigly, the camera activity LED is implemented in software. +Hook it up as a gpio-led and (until we have camera *and* a "camera on" +LED trigger) configure it as a panic indicator. + +Signed-off-by: Konrad Dybcio +Link: https://lore.kernel.org/r/20230805-topic-x13s_cam_led-v1-1-443d752158c4@linaro.org +Signed-off-by: Bjorn Andersson +Signed-off-by: Sasha Levin +--- + .../dts/qcom/sc8280xp-lenovo-thinkpad-x13s.dts | 16 ++++++++++++++++ + 1 file changed, 16 insertions(+) + +diff --git a/arch/arm64/boot/dts/qcom/sc8280xp-lenovo-thinkpad-x13s.dts b/arch/arm64/boot/dts/qcom/sc8280xp-lenovo-thinkpad-x13s.dts +index 059dfccdfe7c2..b51787b6561d7 100644 +--- a/arch/arm64/boot/dts/qcom/sc8280xp-lenovo-thinkpad-x13s.dts ++++ b/arch/arm64/boot/dts/qcom/sc8280xp-lenovo-thinkpad-x13s.dts +@@ -12,6 +12,7 @@ + #include + #include + #include ++#include + #include + + #include "sc8280xp.dtsi" +@@ -78,6 +79,21 @@ switch-lid { + }; + }; + ++ leds { ++ compatible = "gpio-leds"; ++ ++ led-camera-indicator { ++ label = "white:camera-indicator"; ++ function = LED_FUNCTION_INDICATOR; ++ color = ; ++ gpios = <&tlmm 28 GPIO_ACTIVE_HIGH>; ++ linux,default-trigger = "none"; ++ default-state = "off"; ++ /* Reuse as a panic indicator until we get a "camera on" trigger */ ++ panic-indicator; ++ }; ++ }; ++ + pmic-glink { + compatible = "qcom,sc8280xp-pmic-glink", "qcom,pmic-glink"; + +-- +2.40.1 + diff --git a/queue-6.5/arm64-dts-qcom-sm6125-pdx201-correct-ramoops-pmsg-si.patch b/queue-6.5/arm64-dts-qcom-sm6125-pdx201-correct-ramoops-pmsg-si.patch new file mode 100644 index 00000000000..786d67bd60c --- /dev/null +++ b/queue-6.5/arm64-dts-qcom-sm6125-pdx201-correct-ramoops-pmsg-si.patch @@ -0,0 +1,39 @@ +From 391926109fa5426a1753762849e03572aa9c6151 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 18 Jun 2023 13:44:38 +0200 +Subject: arm64: dts: qcom: sm6125-pdx201: correct ramoops pmsg-size + +From: Krzysztof Kozlowski + +[ Upstream commit c42f5452de6ad2599c6e5e2a64c180a4ac835d27 ] + +There is no 'msg-size' property in ramoops, so assume intention was for +'pmsg-size': + + sm6125-sony-xperia-seine-pdx201.dtb: ramoops@ffc00000: Unevaluated properties are not allowed ('msg-size' was unexpected) + +Signed-off-by: Krzysztof Kozlowski +Reviewed-by: Konrad Dybcio +Link: https://lore.kernel.org/r/20230618114442.140185-3-krzysztof.kozlowski@linaro.org +Signed-off-by: Bjorn Andersson +Signed-off-by: Sasha Levin +--- + arch/arm64/boot/dts/qcom/sm6125-sony-xperia-seine-pdx201.dts | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/arm64/boot/dts/qcom/sm6125-sony-xperia-seine-pdx201.dts b/arch/arm64/boot/dts/qcom/sm6125-sony-xperia-seine-pdx201.dts +index 9f8a9ef398a26..de85086c65adc 100644 +--- a/arch/arm64/boot/dts/qcom/sm6125-sony-xperia-seine-pdx201.dts ++++ b/arch/arm64/boot/dts/qcom/sm6125-sony-xperia-seine-pdx201.dts +@@ -79,7 +79,7 @@ pstore_mem: ramoops@ffc00000 { + reg = <0x0 0xffc40000 0x0 0xc0000>; + record-size = <0x1000>; + console-size = <0x40000>; +- msg-size = <0x20000 0x20000>; ++ pmsg-size = <0x20000>; + }; + + cmdline_mem: memory@ffd00000 { +-- +2.40.1 + diff --git a/queue-6.5/arm64-dts-qcom-sm6125-sprout-correct-ramoops-pmsg-si.patch b/queue-6.5/arm64-dts-qcom-sm6125-sprout-correct-ramoops-pmsg-si.patch new file mode 100644 index 00000000000..a6f04e0a704 --- /dev/null +++ b/queue-6.5/arm64-dts-qcom-sm6125-sprout-correct-ramoops-pmsg-si.patch @@ -0,0 +1,39 @@ +From 4d1a93dc24049c123f5165bd4b596a693ed1d198 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 18 Jun 2023 13:44:39 +0200 +Subject: arm64: dts: qcom: sm6125-sprout: correct ramoops pmsg-size + +From: Krzysztof Kozlowski + +[ Upstream commit 2951e7e7611a3ea04de98d0f1bfc4e7ec609ef29 ] + +There is no 'msg-size' property in ramoops, so assume intention was for +'pmsg-size': + + sm6125-xiaomi-laurel-sprout.dtb: ramoops@ffc00000: Unevaluated properties are not allowed ('msg-size' was unexpected) + +Signed-off-by: Krzysztof Kozlowski +Reviewed-by: Konrad Dybcio +Link: https://lore.kernel.org/r/20230618114442.140185-4-krzysztof.kozlowski@linaro.org +Signed-off-by: Bjorn Andersson +Signed-off-by: Sasha Levin +--- + arch/arm64/boot/dts/qcom/sm6125-xiaomi-laurel-sprout.dts | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/arm64/boot/dts/qcom/sm6125-xiaomi-laurel-sprout.dts b/arch/arm64/boot/dts/qcom/sm6125-xiaomi-laurel-sprout.dts +index a7f4aeae9c1a5..7c58d1299a609 100644 +--- a/arch/arm64/boot/dts/qcom/sm6125-xiaomi-laurel-sprout.dts ++++ b/arch/arm64/boot/dts/qcom/sm6125-xiaomi-laurel-sprout.dts +@@ -52,7 +52,7 @@ pstore_mem: ramoops@ffc00000 { + reg = <0x0 0xffc40000 0x0 0xc0000>; + record-size = <0x1000>; + console-size = <0x40000>; +- msg-size = <0x20000 0x20000>; ++ pmsg-size = <0x20000>; + }; + + cmdline_mem: memory@ffd00000 { +-- +2.40.1 + diff --git a/queue-6.5/arm64-dts-qcom-sm6350-correct-ramoops-pmsg-size.patch b/queue-6.5/arm64-dts-qcom-sm6350-correct-ramoops-pmsg-size.patch new file mode 100644 index 00000000000..a9d405d9da1 --- /dev/null +++ b/queue-6.5/arm64-dts-qcom-sm6350-correct-ramoops-pmsg-size.patch @@ -0,0 +1,39 @@ +From e02b3f8099e3127447ef6f9f0fc393b983c2ef46 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 18 Jun 2023 13:44:40 +0200 +Subject: arm64: dts: qcom: sm6350: correct ramoops pmsg-size + +From: Krzysztof Kozlowski + +[ Upstream commit c86b97a72065e06eacb993dc71fa9febc93422af ] + +There is no 'msg-size' property in ramoops, so assume intention was for +'pmsg-size': + + sm6350-sony-xperia-lena-pdx213.dtb: ramoops@ffc00000: Unevaluated properties are not allowed ('msg-size' was unexpected) + +Signed-off-by: Krzysztof Kozlowski +Reviewed-by: Konrad Dybcio +Link: https://lore.kernel.org/r/20230618114442.140185-5-krzysztof.kozlowski@linaro.org +Signed-off-by: Bjorn Andersson +Signed-off-by: Sasha Levin +--- + arch/arm64/boot/dts/qcom/sm6350.dtsi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/arm64/boot/dts/qcom/sm6350.dtsi b/arch/arm64/boot/dts/qcom/sm6350.dtsi +index 7cafb32fbb941..4b4ea156a92c5 100644 +--- a/arch/arm64/boot/dts/qcom/sm6350.dtsi ++++ b/arch/arm64/boot/dts/qcom/sm6350.dtsi +@@ -673,7 +673,7 @@ ramoops: ramoops@ffc00000 { + reg = <0 0xffc00000 0 0x100000>; + record-size = <0x1000>; + console-size = <0x40000>; +- msg-size = <0x20000 0x20000>; ++ pmsg-size = <0x20000>; + ecc-size = <16>; + no-map; + }; +-- +2.40.1 + diff --git a/queue-6.5/arm64-dts-qcom-sm8150-kumano-correct-ramoops-pmsg-si.patch b/queue-6.5/arm64-dts-qcom-sm8150-kumano-correct-ramoops-pmsg-si.patch new file mode 100644 index 00000000000..695e94ce814 --- /dev/null +++ b/queue-6.5/arm64-dts-qcom-sm8150-kumano-correct-ramoops-pmsg-si.patch @@ -0,0 +1,39 @@ +From 4e9064b25046b6d9e2076b8ec71986a16fe1f977 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 18 Jun 2023 13:44:41 +0200 +Subject: arm64: dts: qcom: sm8150-kumano: correct ramoops pmsg-size + +From: Krzysztof Kozlowski + +[ Upstream commit 4e6b942f092653ebcdbbc0819b2d1f08ab415bdc ] + +There is no 'msg-size' property in ramoops, so assume intention was for +'pmsg-size': + + sm8150-sony-xperia-kumano-griffin.dtb: ramoops@ffc00000: Unevaluated properties are not allowed ('msg-size' was unexpected) + +Signed-off-by: Krzysztof Kozlowski +Reviewed-by: Konrad Dybcio +Link: https://lore.kernel.org/r/20230618114442.140185-6-krzysztof.kozlowski@linaro.org +Signed-off-by: Bjorn Andersson +Signed-off-by: Sasha Levin +--- + arch/arm64/boot/dts/qcom/sm8150-sony-xperia-kumano.dtsi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/arm64/boot/dts/qcom/sm8150-sony-xperia-kumano.dtsi b/arch/arm64/boot/dts/qcom/sm8150-sony-xperia-kumano.dtsi +index baafea53770bf..ae0ca48b89a59 100644 +--- a/arch/arm64/boot/dts/qcom/sm8150-sony-xperia-kumano.dtsi ++++ b/arch/arm64/boot/dts/qcom/sm8150-sony-xperia-kumano.dtsi +@@ -222,7 +222,7 @@ ramoops@ffc00000 { + reg = <0x0 0xffc00000 0x0 0x100000>; + record-size = <0x1000>; + console-size = <0x40000>; +- msg-size = <0x20000 0x20000>; ++ pmsg-size = <0x20000>; + ecc-size = <16>; + no-map; + }; +-- +2.40.1 + diff --git a/queue-6.5/arm64-dts-qcom-sm8250-edo-correct-ramoops-pmsg-size.patch b/queue-6.5/arm64-dts-qcom-sm8250-edo-correct-ramoops-pmsg-size.patch new file mode 100644 index 00000000000..aae85e942f0 --- /dev/null +++ b/queue-6.5/arm64-dts-qcom-sm8250-edo-correct-ramoops-pmsg-size.patch @@ -0,0 +1,39 @@ +From c762d780d55c7237f862440c00ca349e6a63df66 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 18 Jun 2023 13:44:42 +0200 +Subject: arm64: dts: qcom: sm8250-edo: correct ramoops pmsg-size + +From: Krzysztof Kozlowski + +[ Upstream commit 7dc3606f91427414d00a2fb09e6e0e32c14c2093 ] + +There is no 'msg-size' property in ramoops, so assume intention was for +'pmsg-size': + + sm8250-sony-xperia-edo-pdx206.dtb: ramoops@ffc00000: Unevaluated properties are not allowed ('msg-size' was unexpected) + +Signed-off-by: Krzysztof Kozlowski +Reviewed-by: Konrad Dybcio +Link: https://lore.kernel.org/r/20230618114442.140185-7-krzysztof.kozlowski@linaro.org +Signed-off-by: Bjorn Andersson +Signed-off-by: Sasha Levin +--- + arch/arm64/boot/dts/qcom/sm8250-sony-xperia-edo.dtsi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/arm64/boot/dts/qcom/sm8250-sony-xperia-edo.dtsi b/arch/arm64/boot/dts/qcom/sm8250-sony-xperia-edo.dtsi +index b044cffb419e5..6b044eca7ad5a 100644 +--- a/arch/arm64/boot/dts/qcom/sm8250-sony-xperia-edo.dtsi ++++ b/arch/arm64/boot/dts/qcom/sm8250-sony-xperia-edo.dtsi +@@ -126,7 +126,7 @@ ramoops@ffc00000 { + reg = <0x0 0xffc00000 0x0 0x100000>; + record-size = <0x1000>; + console-size = <0x40000>; +- msg-size = <0x20000 0x20000>; ++ pmsg-size = <0x20000>; + ecc-size = <16>; + no-map; + }; +-- +2.40.1 + diff --git a/queue-6.5/asoc-intel-sof_sdw-update-bt-offload-config-for-soun.patch b/queue-6.5/asoc-intel-sof_sdw-update-bt-offload-config-for-soun.patch new file mode 100644 index 00000000000..e0acd9ef402 --- /dev/null +++ b/queue-6.5/asoc-intel-sof_sdw-update-bt-offload-config-for-soun.patch @@ -0,0 +1,43 @@ +From b1e2f06be6330f44a5728c6da3d8c9f8fc2cf7b6 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 31 Jul 2023 16:42:38 -0500 +Subject: ASoC: Intel: sof_sdw: Update BT offload config for soundwire config + +From: Uday M Bhat + +[ Upstream commit a14aded9299187bb17ef90700eb2cf1120ef5885 ] + +For soundwire config, SSP1 is used for BT offload. This is enabled +in sof_sdw_quirk_table + +Reviewed-by: Kai Vehmanen +Reviewed-by: Ranjani Sridharan +Reviewed-by: Bard Liao +Signed-off-by: Uday M Bhat +Signed-off-by: Jairaj Arava +Signed-off-by: Pierre-Louis Bossart +Link: https://lore.kernel.org/r/20230731214257.444605-5-pierre-louis.bossart@linux.intel.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + sound/soc/intel/boards/sof_sdw.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/sound/soc/intel/boards/sof_sdw.c b/sound/soc/intel/boards/sof_sdw.c +index 0201029899cad..c86f8f9a61003 100644 +--- a/sound/soc/intel/boards/sof_sdw.c ++++ b/sound/soc/intel/boards/sof_sdw.c +@@ -467,7 +467,9 @@ static const struct dmi_system_id sof_sdw_quirk_table[] = { + DMI_MATCH(DMI_SYS_VENDOR, "Google"), + DMI_MATCH(DMI_PRODUCT_NAME, "Rex"), + }, +- .driver_data = (void *)(SOF_SDW_PCH_DMIC), ++ .driver_data = (void *)(SOF_SDW_PCH_DMIC | ++ SOF_BT_OFFLOAD_SSP(1) | ++ SOF_SSP_BT_OFFLOAD_PRESENT), + }, + /* LunarLake devices */ + { +-- +2.40.1 + diff --git a/queue-6.5/asoc-sof-amd-clear-panic-mask-status-when-panic-occu.patch b/queue-6.5/asoc-sof-amd-clear-panic-mask-status-when-panic-occu.patch new file mode 100644 index 00000000000..50fb7b318df --- /dev/null +++ b/queue-6.5/asoc-sof-amd-clear-panic-mask-status-when-panic-occu.patch @@ -0,0 +1,46 @@ +From db647398618c5e4a5562fa528405f5ed1768890b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 23 Aug 2023 13:03:38 +0530 +Subject: ASoC: SOF: amd: clear panic mask status when panic occurs + +From: Vijendar Mukunda + +[ Upstream commit 3d02e1c439b4140215b624d423aa3c7554b17a5a ] + +Due to scratch memory persistence, Once the DSP panic is reported, need to +clear the panic mask after handling DSP panic. Otherwise, It results in DSP +panic on next reboot. + +Signed-off-by: Vijendar Mukunda +Link: https://lore.kernel.org/r/20230823073340.2829821-6-Vijendar.Mukunda@amd.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + sound/soc/sof/amd/acp-ipc.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/sound/soc/sof/amd/acp-ipc.c b/sound/soc/sof/amd/acp-ipc.c +index 8a0fc635a997c..d07dc78074cc3 100644 +--- a/sound/soc/sof/amd/acp-ipc.c ++++ b/sound/soc/sof/amd/acp-ipc.c +@@ -168,6 +168,8 @@ irqreturn_t acp_sof_ipc_irq_thread(int irq, void *context) + if ((status & SOF_IPC_PANIC_MAGIC_MASK) == SOF_IPC_PANIC_MAGIC) { + snd_sof_dsp_panic(sdev, sdev->dsp_box.offset + sizeof(status), + true); ++ status = 0; ++ acp_mailbox_write(sdev, sdev->dsp_box.offset, &status, sizeof(status)); + return IRQ_HANDLED; + } + snd_sof_ipc_msgs_rx(sdev); +@@ -197,6 +199,8 @@ irqreturn_t acp_sof_ipc_irq_thread(int irq, void *context) + acp_mailbox_read(sdev, sdev->debug_box.offset, &status, sizeof(u32)); + if ((status & SOF_IPC_PANIC_MAGIC_MASK) == SOF_IPC_PANIC_MAGIC) { + snd_sof_dsp_panic(sdev, sdev->dsp_oops_offset, true); ++ status = 0; ++ acp_mailbox_write(sdev, sdev->debug_box.offset, &status, sizeof(status)); + return IRQ_HANDLED; + } + +-- +2.40.1 + diff --git a/queue-6.5/asoc-sof-topology-simplify-code-to-prevent-static-an.patch b/queue-6.5/asoc-sof-topology-simplify-code-to-prevent-static-an.patch new file mode 100644 index 00000000000..230540d18ba --- /dev/null +++ b/queue-6.5/asoc-sof-topology-simplify-code-to-prevent-static-an.patch @@ -0,0 +1,64 @@ +From 0d14a4290b981b0d78fe9371e97337fd6d79257a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 31 Jul 2023 16:37:43 -0500 +Subject: ASoC: SOF: topology: simplify code to prevent static analysis + warnings +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Pierre-Louis Bossart + +[ Upstream commit 55cb3dc271d81f1982c949a2ac483a6daf613b92 ] + +make KCFLAGS='-fanalyzer' sound/soc/sof/intel/ reports a possible NULL +pointer dereference. + +sound/soc/sof/topology.c:1136:21: error: dereference of NULL ‘w’ +[CWE-476] [-Werror=analyzer-null-dereference] + + 1136 | strcmp(w->sname, rtd->dai_link->stream_name)) + +The code is rather confusing and can be simplified to make static +analysis happy. No functionality change. + +Signed-off-by: Pierre-Louis Bossart +Reviewed-by: Rander Wang +Reviewed-by: Daniel Baluta +Reviewed-by: Yaochun Hung +Link: https://lore.kernel.org/r/20230731213748.440285-4-pierre-louis.bossart@linux.intel.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + sound/soc/sof/topology.c | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/sound/soc/sof/topology.c b/sound/soc/sof/topology.c +index 698129dccc7df..3866dd3cba695 100644 +--- a/sound/soc/sof/topology.c ++++ b/sound/soc/sof/topology.c +@@ -1117,10 +1117,11 @@ static void sof_disconnect_dai_widget(struct snd_soc_component *scomp, + { + struct snd_soc_card *card = scomp->card; + struct snd_soc_pcm_runtime *rtd; ++ const char *sname = w->sname; + struct snd_soc_dai *cpu_dai; + int i, stream; + +- if (!w->sname) ++ if (!sname) + return; + + if (w->id == snd_soc_dapm_dai_out) +@@ -1133,7 +1134,7 @@ static void sof_disconnect_dai_widget(struct snd_soc_component *scomp, + list_for_each_entry(rtd, &card->rtd_list, list) { + /* does stream match DAI link ? */ + if (!rtd->dai_link->stream_name || +- strcmp(w->sname, rtd->dai_link->stream_name)) ++ strcmp(sname, rtd->dai_link->stream_name)) + continue; + + for_each_rtd_cpu_dais(rtd, i, cpu_dai) +-- +2.40.1 + diff --git a/queue-6.5/ata-libata-core-fetch-sense-data-for-successful-comm.patch b/queue-6.5/ata-libata-core-fetch-sense-data-for-successful-comm.patch new file mode 100644 index 00000000000..11d4967f70f --- /dev/null +++ b/queue-6.5/ata-libata-core-fetch-sense-data-for-successful-comm.patch @@ -0,0 +1,68 @@ +From e0d5ca37f6dea43f58be8cd072f3af6924aaaf2e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 13 Sep 2023 17:04:43 +0200 +Subject: ata: libata-core: fetch sense data for successful commands iff CDL + enabled + +From: Niklas Cassel + +[ Upstream commit 5e35a9ac3fe3a0d571b899a16ca84253e53dc70c ] + +Currently, we fetch sense data for a _successful_ command if either: +1) Command was NCQ and ATA_DFLAG_CDL_ENABLED flag set (flag + ATA_DFLAG_CDL_ENABLED will only be set if the Successful NCQ command + sense data supported bit is set); or +2) Command was non-NCQ and regular sense data reporting is enabled. + +This means that case 2) will trigger for a non-NCQ command which has +ATA_SENSE bit set, regardless if CDL is enabled or not. + +This decision was by design. If the device reports that it has sense data +available, it makes sense to fetch that sense data, since the sk/asc/ascq +could be important information regardless if CDL is enabled or not. + +However, the fetching of sense data for a successful command is done via +ATA EH. Considering how intricate the ATA EH is, we really do not want to +invoke ATA EH unless absolutely needed. + +Before commit 18bd7718b5c4 ("scsi: ata: libata: Handle completion of CDL +commands using policy 0xD") we never fetched sense data for successful +commands. + +In order to not invoke the ATA EH unless absolutely necessary, even if the +device claims support for sense data reporting, only fetch sense data for +successful (NCQ and non-NCQ commands) commands that are using CDL. + +[Damien] Modified the check to test the qc flag ATA_QCFLAG_HAS_CDL +instead of the device support for CDL, which is implied for commands +using CDL. + +Fixes: 3ac873c76d79 ("ata: libata-core: fix when to fetch sense data for successful commands") +Signed-off-by: Niklas Cassel +Signed-off-by: Damien Le Moal +Signed-off-by: Sasha Levin +--- + drivers/ata/libata-core.c | 7 ++----- + 1 file changed, 2 insertions(+), 5 deletions(-) + +diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c +index c7a29c3ac6701..291e128f4d2b4 100644 +--- a/drivers/ata/libata-core.c ++++ b/drivers/ata/libata-core.c +@@ -4919,11 +4919,8 @@ void ata_qc_complete(struct ata_queued_cmd *qc) + * been aborted by the device due to a limit timeout using the policy + * 0xD. For these commands, invoke EH to get the command sense data. + */ +- if (qc->result_tf.status & ATA_SENSE && +- ((ata_is_ncq(qc->tf.protocol) && +- dev->flags & ATA_DFLAG_CDL_ENABLED) || +- (!ata_is_ncq(qc->tf.protocol) && +- ata_id_sense_reporting_enabled(dev->id)))) { ++ if (qc->flags & ATA_QCFLAG_HAS_CDL && ++ qc->result_tf.status & ATA_SENSE) { + /* + * Tell SCSI EH to not overwrite scmd->result even if this + * command is finished with result SAM_STAT_GOOD. +-- +2.40.1 + diff --git a/queue-6.5/ata-libata-remove-references-to-non-existing-error_h.patch b/queue-6.5/ata-libata-remove-references-to-non-existing-error_h.patch new file mode 100644 index 00000000000..5fe5c33f540 --- /dev/null +++ b/queue-6.5/ata-libata-remove-references-to-non-existing-error_h.patch @@ -0,0 +1,925 @@ +From 8df03fd2bc8c18590abf842bc2d997fb2972ceb4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 31 Jul 2023 16:34:12 +0200 +Subject: ata: libata: remove references to non-existing error_handler() + +From: Hannes Reinecke + +[ Upstream commit ff8072d589dcff7c1f0345a6ec98b5fc1e9ee2a1 ] + +With commit 65a15d6560df ("scsi: ipr: Remove SATA support") all +libata drivers now have the error_handler() callback provided, +so we can stop checking for non-existing error_handler callback. + +Signed-off-by: Hannes Reinecke +[niklas: fixed review comments, rebased, solved conflicts during rebase, +fixed bug that unconditionally dumped all QCs, removed the now unused +function ata_dump_status(), removed the now unreachable failure paths in +atapi_qc_complete(), removed the non-EH function to request ATAPI sense] +Signed-off-by: Niklas Cassel +Reviewed-by: John Garry +Reviewed-by: Jason Yan +Reviewed-by: Martin K. Petersen +Signed-off-by: Damien Le Moal +Stable-dep-of: 5e35a9ac3fe3 ("ata: libata-core: fetch sense data for successful commands iff CDL enabled") +Signed-off-by: Sasha Levin +--- + drivers/ata/libata-core.c | 209 +++++++++++++++----------------------- + drivers/ata/libata-eh.c | 152 ++++++++++++--------------- + drivers/ata/libata-sata.c | 7 +- + drivers/ata/libata-scsi.c | 161 ++--------------------------- + drivers/ata/libata-sff.c | 30 ++---- + include/linux/libata.h | 2 +- + 6 files changed, 170 insertions(+), 391 deletions(-) + +diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c +index 04db0f2c683a7..c7a29c3ac6701 100644 +--- a/drivers/ata/libata-core.c ++++ b/drivers/ata/libata-core.c +@@ -1586,13 +1586,11 @@ static unsigned ata_exec_internal_sg(struct ata_device *dev, + } + } + +- if (ap->ops->error_handler) +- ata_eh_release(ap); ++ ata_eh_release(ap); + + rc = wait_for_completion_timeout(&wait, msecs_to_jiffies(timeout)); + +- if (ap->ops->error_handler) +- ata_eh_acquire(ap); ++ ata_eh_acquire(ap); + + ata_sff_flush_pio_task(ap); + +@@ -1607,10 +1605,7 @@ static unsigned ata_exec_internal_sg(struct ata_device *dev, + if (qc->flags & ATA_QCFLAG_ACTIVE) { + qc->err_mask |= AC_ERR_TIMEOUT; + +- if (ap->ops->error_handler) +- ata_port_freeze(ap); +- else +- ata_qc_complete(qc); ++ ata_port_freeze(ap); + + ata_dev_warn(dev, "qc timeout after %u msecs (cmd 0x%x)\n", + timeout, command); +@@ -4874,126 +4869,103 @@ static void ata_verify_xfer(struct ata_queued_cmd *qc) + void ata_qc_complete(struct ata_queued_cmd *qc) + { + struct ata_port *ap = qc->ap; ++ struct ata_device *dev = qc->dev; ++ struct ata_eh_info *ehi = &dev->link->eh_info; + + /* Trigger the LED (if available) */ + ledtrig_disk_activity(!!(qc->tf.flags & ATA_TFLAG_WRITE)); + +- /* XXX: New EH and old EH use different mechanisms to +- * synchronize EH with regular execution path. +- * +- * In new EH, a qc owned by EH is marked with ATA_QCFLAG_EH. +- * Normal execution path is responsible for not accessing a +- * qc owned by EH. libata core enforces the rule by returning NULL +- * from ata_qc_from_tag() for qcs owned by EH. ++ /* ++ * In order to synchronize EH with the regular execution path, a qc that ++ * is owned by EH is marked with ATA_QCFLAG_EH. + * +- * Old EH depends on ata_qc_complete() nullifying completion +- * requests if ATA_QCFLAG_EH_SCHEDULED is set. Old EH does +- * not synchronize with interrupt handler. Only PIO task is +- * taken care of. ++ * The normal execution path is responsible for not accessing a qc owned ++ * by EH. libata core enforces the rule by returning NULL from ++ * ata_qc_from_tag() for qcs owned by EH. + */ +- if (ap->ops->error_handler) { +- struct ata_device *dev = qc->dev; +- struct ata_eh_info *ehi = &dev->link->eh_info; +- +- if (unlikely(qc->err_mask)) +- qc->flags |= ATA_QCFLAG_EH; ++ if (unlikely(qc->err_mask)) ++ qc->flags |= ATA_QCFLAG_EH; + +- /* +- * Finish internal commands without any further processing +- * and always with the result TF filled. +- */ +- if (unlikely(ata_tag_internal(qc->tag))) { +- fill_result_tf(qc); +- trace_ata_qc_complete_internal(qc); +- __ata_qc_complete(qc); +- return; +- } ++ /* ++ * Finish internal commands without any further processing and always ++ * with the result TF filled. ++ */ ++ if (unlikely(ata_tag_internal(qc->tag))) { ++ fill_result_tf(qc); ++ trace_ata_qc_complete_internal(qc); ++ __ata_qc_complete(qc); ++ return; ++ } + +- /* +- * Non-internal qc has failed. Fill the result TF and +- * summon EH. +- */ +- if (unlikely(qc->flags & ATA_QCFLAG_EH)) { +- fill_result_tf(qc); +- trace_ata_qc_complete_failed(qc); +- ata_qc_schedule_eh(qc); +- return; +- } ++ /* Non-internal qc has failed. Fill the result TF and summon EH. */ ++ if (unlikely(qc->flags & ATA_QCFLAG_EH)) { ++ fill_result_tf(qc); ++ trace_ata_qc_complete_failed(qc); ++ ata_qc_schedule_eh(qc); ++ return; ++ } + +- WARN_ON_ONCE(ata_port_is_frozen(ap)); ++ WARN_ON_ONCE(ata_port_is_frozen(ap)); + +- /* read result TF if requested */ +- if (qc->flags & ATA_QCFLAG_RESULT_TF) +- fill_result_tf(qc); ++ /* read result TF if requested */ ++ if (qc->flags & ATA_QCFLAG_RESULT_TF) ++ fill_result_tf(qc); + +- trace_ata_qc_complete_done(qc); ++ trace_ata_qc_complete_done(qc); + ++ /* ++ * For CDL commands that completed without an error, check if we have ++ * sense data (ATA_SENSE is set). If we do, then the command may have ++ * been aborted by the device due to a limit timeout using the policy ++ * 0xD. For these commands, invoke EH to get the command sense data. ++ */ ++ if (qc->result_tf.status & ATA_SENSE && ++ ((ata_is_ncq(qc->tf.protocol) && ++ dev->flags & ATA_DFLAG_CDL_ENABLED) || ++ (!ata_is_ncq(qc->tf.protocol) && ++ ata_id_sense_reporting_enabled(dev->id)))) { + /* +- * For CDL commands that completed without an error, check if +- * we have sense data (ATA_SENSE is set). If we do, then the +- * command may have been aborted by the device due to a limit +- * timeout using the policy 0xD. For these commands, invoke EH +- * to get the command sense data. ++ * Tell SCSI EH to not overwrite scmd->result even if this ++ * command is finished with result SAM_STAT_GOOD. + */ +- if (qc->result_tf.status & ATA_SENSE && +- ((ata_is_ncq(qc->tf.protocol) && +- dev->flags & ATA_DFLAG_CDL_ENABLED) || +- (!ata_is_ncq(qc->tf.protocol) && +- ata_id_sense_reporting_enabled(dev->id)))) { +- /* +- * Tell SCSI EH to not overwrite scmd->result even if +- * this command is finished with result SAM_STAT_GOOD. +- */ +- qc->scsicmd->flags |= SCMD_FORCE_EH_SUCCESS; +- qc->flags |= ATA_QCFLAG_EH_SUCCESS_CMD; +- ehi->dev_action[dev->devno] |= ATA_EH_GET_SUCCESS_SENSE; +- +- /* +- * set pending so that ata_qc_schedule_eh() does not +- * trigger fast drain, and freeze the port. +- */ +- ap->pflags |= ATA_PFLAG_EH_PENDING; +- ata_qc_schedule_eh(qc); +- return; +- } ++ qc->scsicmd->flags |= SCMD_FORCE_EH_SUCCESS; ++ qc->flags |= ATA_QCFLAG_EH_SUCCESS_CMD; ++ ehi->dev_action[dev->devno] |= ATA_EH_GET_SUCCESS_SENSE; + +- /* Some commands need post-processing after successful +- * completion. ++ /* ++ * set pending so that ata_qc_schedule_eh() does not trigger ++ * fast drain, and freeze the port. + */ +- switch (qc->tf.command) { +- case ATA_CMD_SET_FEATURES: +- if (qc->tf.feature != SETFEATURES_WC_ON && +- qc->tf.feature != SETFEATURES_WC_OFF && +- qc->tf.feature != SETFEATURES_RA_ON && +- qc->tf.feature != SETFEATURES_RA_OFF) +- break; +- fallthrough; +- case ATA_CMD_INIT_DEV_PARAMS: /* CHS translation changed */ +- case ATA_CMD_SET_MULTI: /* multi_count changed */ +- /* revalidate device */ +- ehi->dev_action[dev->devno] |= ATA_EH_REVALIDATE; +- ata_port_schedule_eh(ap); +- break; ++ ap->pflags |= ATA_PFLAG_EH_PENDING; ++ ata_qc_schedule_eh(qc); ++ return; ++ } + +- case ATA_CMD_SLEEP: +- dev->flags |= ATA_DFLAG_SLEEPING; ++ /* Some commands need post-processing after successful completion. */ ++ switch (qc->tf.command) { ++ case ATA_CMD_SET_FEATURES: ++ if (qc->tf.feature != SETFEATURES_WC_ON && ++ qc->tf.feature != SETFEATURES_WC_OFF && ++ qc->tf.feature != SETFEATURES_RA_ON && ++ qc->tf.feature != SETFEATURES_RA_OFF) + break; +- } +- +- if (unlikely(dev->flags & ATA_DFLAG_DUBIOUS_XFER)) +- ata_verify_xfer(qc); ++ fallthrough; ++ case ATA_CMD_INIT_DEV_PARAMS: /* CHS translation changed */ ++ case ATA_CMD_SET_MULTI: /* multi_count changed */ ++ /* revalidate device */ ++ ehi->dev_action[dev->devno] |= ATA_EH_REVALIDATE; ++ ata_port_schedule_eh(ap); ++ break; + +- __ata_qc_complete(qc); +- } else { +- if (qc->flags & ATA_QCFLAG_EH_SCHEDULED) +- return; ++ case ATA_CMD_SLEEP: ++ dev->flags |= ATA_DFLAG_SLEEPING; ++ break; ++ } + +- /* read result TF if failed or requested */ +- if (qc->err_mask || qc->flags & ATA_QCFLAG_RESULT_TF) +- fill_result_tf(qc); ++ if (unlikely(dev->flags & ATA_DFLAG_DUBIOUS_XFER)) ++ ata_verify_xfer(qc); + +- __ata_qc_complete(qc); +- } ++ __ata_qc_complete(qc); + } + EXPORT_SYMBOL_GPL(ata_qc_complete); + +@@ -5039,11 +5011,8 @@ void ata_qc_issue(struct ata_queued_cmd *qc) + struct ata_link *link = qc->dev->link; + u8 prot = qc->tf.protocol; + +- /* Make sure only one non-NCQ command is outstanding. The +- * check is skipped for old EH because it reuses active qc to +- * request ATAPI sense. +- */ +- WARN_ON_ONCE(ap->ops->error_handler && ata_tag_valid(link->active_tag)); ++ /* Make sure only one non-NCQ command is outstanding. */ ++ WARN_ON_ONCE(ata_tag_valid(link->active_tag)); + + if (ata_is_ncq(prot)) { + WARN_ON_ONCE(link->sactive & (1 << qc->hw_tag)); +@@ -5917,15 +5886,9 @@ void __ata_port_probe(struct ata_port *ap) + + int ata_port_probe(struct ata_port *ap) + { +- int rc = 0; +- +- if (ap->ops->error_handler) { +- __ata_port_probe(ap); +- ata_port_wait_eh(ap); +- } else { +- rc = ata_bus_probe(ap); +- } +- return rc; ++ __ata_port_probe(ap); ++ ata_port_wait_eh(ap); ++ return 0; + } + + +@@ -6130,9 +6093,6 @@ static void ata_port_detach(struct ata_port *ap) + struct ata_link *link; + struct ata_device *dev; + +- if (!ap->ops->error_handler) +- goto skip_eh; +- + /* tell EH we're leaving & flush EH */ + spin_lock_irqsave(ap->lock, flags); + ap->pflags |= ATA_PFLAG_UNLOADING; +@@ -6148,7 +6108,6 @@ static void ata_port_detach(struct ata_port *ap) + cancel_delayed_work_sync(&ap->hotplug_task); + cancel_delayed_work_sync(&ap->scsi_rescan_task); + +- skip_eh: + /* clean up zpodd on port removal */ + ata_for_each_link(link, ap, HOST_FIRST) { + ata_for_each_dev(dev, link, ALL) { +diff --git a/drivers/ata/libata-eh.c b/drivers/ata/libata-eh.c +index 35e03679b0bfe..9d6affabf225a 100644 +--- a/drivers/ata/libata-eh.c ++++ b/drivers/ata/libata-eh.c +@@ -571,13 +571,10 @@ void ata_scsi_cmd_error_handler(struct Scsi_Host *host, struct ata_port *ap, + /* make sure sff pio task is not running */ + ata_sff_flush_pio_task(ap); + +- if (!ap->ops->error_handler) +- return; +- + /* synchronize with host lock and sort out timeouts */ + + /* +- * For new EH, all qcs are finished in one of three ways - ++ * For EH, all qcs are finished in one of three ways - + * normal completion, error completion, and SCSI timeout. + * Both completions can race against SCSI timeout. When normal + * completion wins, the qc never reaches EH. When error +@@ -659,94 +656,87 @@ EXPORT_SYMBOL(ata_scsi_cmd_error_handler); + void ata_scsi_port_error_handler(struct Scsi_Host *host, struct ata_port *ap) + { + unsigned long flags; ++ struct ata_link *link; + +- /* invoke error handler */ +- if (ap->ops->error_handler) { +- struct ata_link *link; +- +- /* acquire EH ownership */ +- ata_eh_acquire(ap); ++ /* acquire EH ownership */ ++ ata_eh_acquire(ap); + repeat: +- /* kill fast drain timer */ +- del_timer_sync(&ap->fastdrain_timer); ++ /* kill fast drain timer */ ++ del_timer_sync(&ap->fastdrain_timer); + +- /* process port resume request */ +- ata_eh_handle_port_resume(ap); ++ /* process port resume request */ ++ ata_eh_handle_port_resume(ap); + +- /* fetch & clear EH info */ +- spin_lock_irqsave(ap->lock, flags); ++ /* fetch & clear EH info */ ++ spin_lock_irqsave(ap->lock, flags); + +- ata_for_each_link(link, ap, HOST_FIRST) { +- struct ata_eh_context *ehc = &link->eh_context; +- struct ata_device *dev; ++ ata_for_each_link(link, ap, HOST_FIRST) { ++ struct ata_eh_context *ehc = &link->eh_context; ++ struct ata_device *dev; + +- memset(&link->eh_context, 0, sizeof(link->eh_context)); +- link->eh_context.i = link->eh_info; +- memset(&link->eh_info, 0, sizeof(link->eh_info)); ++ memset(&link->eh_context, 0, sizeof(link->eh_context)); ++ link->eh_context.i = link->eh_info; ++ memset(&link->eh_info, 0, sizeof(link->eh_info)); + +- ata_for_each_dev(dev, link, ENABLED) { +- int devno = dev->devno; ++ ata_for_each_dev(dev, link, ENABLED) { ++ int devno = dev->devno; + +- ehc->saved_xfer_mode[devno] = dev->xfer_mode; +- if (ata_ncq_enabled(dev)) +- ehc->saved_ncq_enabled |= 1 << devno; +- } ++ ehc->saved_xfer_mode[devno] = dev->xfer_mode; ++ if (ata_ncq_enabled(dev)) ++ ehc->saved_ncq_enabled |= 1 << devno; + } ++ } + +- ap->pflags |= ATA_PFLAG_EH_IN_PROGRESS; +- ap->pflags &= ~ATA_PFLAG_EH_PENDING; +- ap->excl_link = NULL; /* don't maintain exclusion over EH */ ++ ap->pflags |= ATA_PFLAG_EH_IN_PROGRESS; ++ ap->pflags &= ~ATA_PFLAG_EH_PENDING; ++ ap->excl_link = NULL; /* don't maintain exclusion over EH */ + +- spin_unlock_irqrestore(ap->lock, flags); ++ spin_unlock_irqrestore(ap->lock, flags); + +- /* invoke EH, skip if unloading or suspended */ +- if (!(ap->pflags & (ATA_PFLAG_UNLOADING | ATA_PFLAG_SUSPENDED))) +- ap->ops->error_handler(ap); +- else { +- /* if unloading, commence suicide */ +- if ((ap->pflags & ATA_PFLAG_UNLOADING) && +- !(ap->pflags & ATA_PFLAG_UNLOADED)) +- ata_eh_unload(ap); +- ata_eh_finish(ap); +- } ++ /* invoke EH, skip if unloading or suspended */ ++ if (!(ap->pflags & (ATA_PFLAG_UNLOADING | ATA_PFLAG_SUSPENDED))) ++ ap->ops->error_handler(ap); ++ else { ++ /* if unloading, commence suicide */ ++ if ((ap->pflags & ATA_PFLAG_UNLOADING) && ++ !(ap->pflags & ATA_PFLAG_UNLOADED)) ++ ata_eh_unload(ap); ++ ata_eh_finish(ap); ++ } + +- /* process port suspend request */ +- ata_eh_handle_port_suspend(ap); ++ /* process port suspend request */ ++ ata_eh_handle_port_suspend(ap); + +- /* Exception might have happened after ->error_handler +- * recovered the port but before this point. Repeat +- * EH in such case. +- */ +- spin_lock_irqsave(ap->lock, flags); ++ /* ++ * Exception might have happened after ->error_handler recovered the ++ * port but before this point. Repeat EH in such case. ++ */ ++ spin_lock_irqsave(ap->lock, flags); + +- if (ap->pflags & ATA_PFLAG_EH_PENDING) { +- if (--ap->eh_tries) { +- spin_unlock_irqrestore(ap->lock, flags); +- goto repeat; +- } +- ata_port_err(ap, +- "EH pending after %d tries, giving up\n", +- ATA_EH_MAX_TRIES); +- ap->pflags &= ~ATA_PFLAG_EH_PENDING; ++ if (ap->pflags & ATA_PFLAG_EH_PENDING) { ++ if (--ap->eh_tries) { ++ spin_unlock_irqrestore(ap->lock, flags); ++ goto repeat; + } ++ ata_port_err(ap, ++ "EH pending after %d tries, giving up\n", ++ ATA_EH_MAX_TRIES); ++ ap->pflags &= ~ATA_PFLAG_EH_PENDING; ++ } + +- /* this run is complete, make sure EH info is clear */ +- ata_for_each_link(link, ap, HOST_FIRST) +- memset(&link->eh_info, 0, sizeof(link->eh_info)); ++ /* this run is complete, make sure EH info is clear */ ++ ata_for_each_link(link, ap, HOST_FIRST) ++ memset(&link->eh_info, 0, sizeof(link->eh_info)); + +- /* end eh (clear host_eh_scheduled) while holding +- * ap->lock such that if exception occurs after this +- * point but before EH completion, SCSI midlayer will +- * re-initiate EH. +- */ +- ap->ops->end_eh(ap); ++ /* ++ * end eh (clear host_eh_scheduled) while holding ap->lock such that if ++ * exception occurs after this point but before EH completion, SCSI ++ * midlayer will re-initiate EH. ++ */ ++ ap->ops->end_eh(ap); + +- spin_unlock_irqrestore(ap->lock, flags); +- ata_eh_release(ap); +- } else { +- WARN_ON(ata_qc_from_tag(ap, ap->link.active_tag) == NULL); +- ap->ops->eng_timeout(ap); +- } ++ spin_unlock_irqrestore(ap->lock, flags); ++ ata_eh_release(ap); + + scsi_eh_flush_done_q(&ap->eh_done_q); + +@@ -912,8 +902,6 @@ void ata_qc_schedule_eh(struct ata_queued_cmd *qc) + { + struct ata_port *ap = qc->ap; + +- WARN_ON(!ap->ops->error_handler); +- + qc->flags |= ATA_QCFLAG_EH; + ata_eh_set_pending(ap, 1); + +@@ -934,8 +922,6 @@ void ata_qc_schedule_eh(struct ata_queued_cmd *qc) + */ + void ata_std_sched_eh(struct ata_port *ap) + { +- WARN_ON(!ap->ops->error_handler); +- + if (ap->pflags & ATA_PFLAG_INITIALIZING) + return; + +@@ -989,8 +975,6 @@ static int ata_do_link_abort(struct ata_port *ap, struct ata_link *link) + struct ata_queued_cmd *qc; + int tag, nr_aborted = 0; + +- WARN_ON(!ap->ops->error_handler); +- + /* we're gonna abort all commands, no need for fast drain */ + ata_eh_set_pending(ap, 0); + +@@ -1065,8 +1049,6 @@ EXPORT_SYMBOL_GPL(ata_port_abort); + */ + static void __ata_port_freeze(struct ata_port *ap) + { +- WARN_ON(!ap->ops->error_handler); +- + if (ap->ops->freeze) + ap->ops->freeze(ap); + +@@ -1091,8 +1073,6 @@ static void __ata_port_freeze(struct ata_port *ap) + */ + int ata_port_freeze(struct ata_port *ap) + { +- WARN_ON(!ap->ops->error_handler); +- + __ata_port_freeze(ap); + + return ata_port_abort(ap); +@@ -1112,9 +1092,6 @@ void ata_eh_freeze_port(struct ata_port *ap) + { + unsigned long flags; + +- if (!ap->ops->error_handler) +- return; +- + spin_lock_irqsave(ap->lock, flags); + __ata_port_freeze(ap); + spin_unlock_irqrestore(ap->lock, flags); +@@ -1134,9 +1111,6 @@ void ata_eh_thaw_port(struct ata_port *ap) + { + unsigned long flags; + +- if (!ap->ops->error_handler) +- return; +- + spin_lock_irqsave(ap->lock, flags); + + ap->pflags &= ~ATA_PFLAG_FROZEN; +diff --git a/drivers/ata/libata-sata.c b/drivers/ata/libata-sata.c +index 85e279a12f62c..99d4ab04bcce6 100644 +--- a/drivers/ata/libata-sata.c ++++ b/drivers/ata/libata-sata.c +@@ -1158,12 +1158,7 @@ EXPORT_SYMBOL_GPL(ata_sas_port_alloc); + */ + int ata_sas_port_start(struct ata_port *ap) + { +- /* +- * the port is marked as frozen at allocation time, but if we don't +- * have new eh, we won't thaw it +- */ +- if (!ap->ops->error_handler) +- ap->pflags &= ~ATA_PFLAG_FROZEN; ++ /* the port is marked as frozen at allocation time */ + return 0; + } + EXPORT_SYMBOL_GPL(ata_sas_port_start); +diff --git a/drivers/ata/libata-scsi.c b/drivers/ata/libata-scsi.c +index c6ece32de8e31..e55db9a6826f3 100644 +--- a/drivers/ata/libata-scsi.c ++++ b/drivers/ata/libata-scsi.c +@@ -709,47 +709,6 @@ static void ata_qc_set_pc_nbytes(struct ata_queued_cmd *qc) + qc->nbytes = scsi_bufflen(scmd) + qc->extrabytes; + } + +-/** +- * ata_dump_status - user friendly display of error info +- * @ap: the port in question +- * @tf: ptr to filled out taskfile +- * +- * Decode and dump the ATA error/status registers for the user so +- * that they have some idea what really happened at the non +- * make-believe layer. +- * +- * LOCKING: +- * inherited from caller +- */ +-static void ata_dump_status(struct ata_port *ap, struct ata_taskfile *tf) +-{ +- u8 stat = tf->status, err = tf->error; +- +- if (stat & ATA_BUSY) { +- ata_port_warn(ap, "status=0x%02x {Busy} ", stat); +- } else { +- ata_port_warn(ap, "status=0x%02x { %s%s%s%s%s%s%s} ", stat, +- stat & ATA_DRDY ? "DriveReady " : "", +- stat & ATA_DF ? "DeviceFault " : "", +- stat & ATA_DSC ? "SeekComplete " : "", +- stat & ATA_DRQ ? "DataRequest " : "", +- stat & ATA_CORR ? "CorrectedError " : "", +- stat & ATA_SENSE ? "Sense " : "", +- stat & ATA_ERR ? "Error " : ""); +- if (err) +- ata_port_warn(ap, "error=0x%02x {%s%s%s%s%s%s", err, +- err & ATA_ABORTED ? +- "DriveStatusError " : "", +- err & ATA_ICRC ? +- (err & ATA_ABORTED ? +- "BadCRC " : "Sector ") : "", +- err & ATA_UNC ? "UncorrectableError " : "", +- err & ATA_IDNF ? "SectorIdNotFound " : "", +- err & ATA_TRK0NF ? "TrackZeroNotFound " : "", +- err & ATA_AMNF ? "AddrMarkNotFound " : ""); +- } +-} +- + /** + * ata_to_sense_error - convert ATA error to SCSI error + * @id: ATA device number +@@ -758,7 +717,6 @@ static void ata_dump_status(struct ata_port *ap, struct ata_taskfile *tf) + * @sk: the sense key we'll fill out + * @asc: the additional sense code we'll fill out + * @ascq: the additional sense code qualifier we'll fill out +- * @verbose: be verbose + * + * Converts an ATA error into a SCSI error. Fill out pointers to + * SK, ASC, and ASCQ bytes for later use in fixed or descriptor +@@ -768,7 +726,7 @@ static void ata_dump_status(struct ata_port *ap, struct ata_taskfile *tf) + * spin_lock_irqsave(host lock) + */ + static void ata_to_sense_error(unsigned id, u8 drv_stat, u8 drv_err, u8 *sk, +- u8 *asc, u8 *ascq, int verbose) ++ u8 *asc, u8 *ascq) + { + int i; + +@@ -847,7 +805,7 @@ static void ata_to_sense_error(unsigned id, u8 drv_stat, u8 drv_err, u8 *sk, + *sk = sense_table[i][1]; + *asc = sense_table[i][2]; + *ascq = sense_table[i][3]; +- goto translate_done; ++ return; + } + } + } +@@ -862,7 +820,7 @@ static void ata_to_sense_error(unsigned id, u8 drv_stat, u8 drv_err, u8 *sk, + *sk = stat_table[i][1]; + *asc = stat_table[i][2]; + *ascq = stat_table[i][3]; +- goto translate_done; ++ return; + } + } + +@@ -873,12 +831,6 @@ static void ata_to_sense_error(unsigned id, u8 drv_stat, u8 drv_err, u8 *sk, + *sk = ABORTED_COMMAND; + *asc = 0x00; + *ascq = 0x00; +- +- translate_done: +- if (verbose) +- pr_err("ata%u: translated ATA stat/err 0x%02x/%02x to SCSI SK/ASC/ASCQ 0x%x/%02x/%02x\n", +- id, drv_stat, drv_err, *sk, *asc, *ascq); +- return; + } + + /* +@@ -904,7 +856,6 @@ static void ata_gen_passthru_sense(struct ata_queued_cmd *qc) + struct ata_taskfile *tf = &qc->result_tf; + unsigned char *sb = cmd->sense_buffer; + unsigned char *desc = sb + 8; +- int verbose = qc->ap->ops->error_handler == NULL; + u8 sense_key, asc, ascq; + + memset(sb, 0, SCSI_SENSE_BUFFERSIZE); +@@ -916,7 +867,7 @@ static void ata_gen_passthru_sense(struct ata_queued_cmd *qc) + if (qc->err_mask || + tf->status & (ATA_BUSY | ATA_DF | ATA_ERR | ATA_DRQ)) { + ata_to_sense_error(qc->ap->print_id, tf->status, tf->error, +- &sense_key, &asc, &ascq, verbose); ++ &sense_key, &asc, &ascq); + ata_scsi_set_sense(qc->dev, cmd, sense_key, asc, ascq); + } else { + /* +@@ -999,7 +950,6 @@ static void ata_gen_ata_sense(struct ata_queued_cmd *qc) + struct scsi_cmnd *cmd = qc->scsicmd; + struct ata_taskfile *tf = &qc->result_tf; + unsigned char *sb = cmd->sense_buffer; +- int verbose = qc->ap->ops->error_handler == NULL; + u64 block; + u8 sense_key, asc, ascq; + +@@ -1017,7 +967,7 @@ static void ata_gen_ata_sense(struct ata_queued_cmd *qc) + if (qc->err_mask || + tf->status & (ATA_BUSY | ATA_DF | ATA_ERR | ATA_DRQ)) { + ata_to_sense_error(qc->ap->print_id, tf->status, tf->error, +- &sense_key, &asc, &ascq, verbose); ++ &sense_key, &asc, &ascq); + ata_scsi_set_sense(dev, cmd, sense_key, asc, ascq); + } else { + /* Could not decode error */ +@@ -1186,9 +1136,6 @@ void ata_scsi_slave_destroy(struct scsi_device *sdev) + unsigned long flags; + struct ata_device *dev; + +- if (!ap->ops->error_handler) +- return; +- + spin_lock_irqsave(ap->lock, flags); + dev = __ata_scsi_find_dev(ap, sdev); + if (dev && dev->sdev) { +@@ -1675,7 +1622,6 @@ static void ata_qc_done(struct ata_queued_cmd *qc) + + static void ata_scsi_qc_complete(struct ata_queued_cmd *qc) + { +- struct ata_port *ap = qc->ap; + struct scsi_cmnd *cmd = qc->scsicmd; + u8 *cdb = cmd->cmnd; + int need_sense = (qc->err_mask != 0) && +@@ -1699,9 +1645,6 @@ static void ata_scsi_qc_complete(struct ata_queued_cmd *qc) + /* Keep the SCSI ML and status byte, clear host byte. */ + cmd->result &= 0x0000ffff; + +- if (need_sense && !ap->ops->error_handler) +- ata_dump_status(ap, &qc->result_tf); +- + ata_qc_done(qc); + } + +@@ -2608,71 +2551,6 @@ static unsigned int ata_scsiop_report_luns(struct ata_scsi_args *args, u8 *rbuf) + return 0; + } + +-static void atapi_sense_complete(struct ata_queued_cmd *qc) +-{ +- if (qc->err_mask && ((qc->err_mask & AC_ERR_DEV) == 0)) { +- /* FIXME: not quite right; we don't want the +- * translation of taskfile registers into +- * a sense descriptors, since that's only +- * correct for ATA, not ATAPI +- */ +- ata_gen_passthru_sense(qc); +- } +- +- ata_qc_done(qc); +-} +- +-/* is it pointless to prefer PIO for "safety reasons"? */ +-static inline int ata_pio_use_silly(struct ata_port *ap) +-{ +- return (ap->flags & ATA_FLAG_PIO_DMA); +-} +- +-static void atapi_request_sense(struct ata_queued_cmd *qc) +-{ +- struct ata_port *ap = qc->ap; +- struct scsi_cmnd *cmd = qc->scsicmd; +- +- memset(cmd->sense_buffer, 0, SCSI_SENSE_BUFFERSIZE); +- +-#ifdef CONFIG_ATA_SFF +- if (ap->ops->sff_tf_read) +- ap->ops->sff_tf_read(ap, &qc->tf); +-#endif +- +- /* fill these in, for the case where they are -not- overwritten */ +- cmd->sense_buffer[0] = 0x70; +- cmd->sense_buffer[2] = qc->tf.error >> 4; +- +- ata_qc_reinit(qc); +- +- /* setup sg table and init transfer direction */ +- sg_init_one(&qc->sgent, cmd->sense_buffer, SCSI_SENSE_BUFFERSIZE); +- ata_sg_init(qc, &qc->sgent, 1); +- qc->dma_dir = DMA_FROM_DEVICE; +- +- memset(&qc->cdb, 0, qc->dev->cdb_len); +- qc->cdb[0] = REQUEST_SENSE; +- qc->cdb[4] = SCSI_SENSE_BUFFERSIZE; +- +- qc->tf.flags |= ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE; +- qc->tf.command = ATA_CMD_PACKET; +- +- if (ata_pio_use_silly(ap)) { +- qc->tf.protocol = ATAPI_PROT_DMA; +- qc->tf.feature |= ATAPI_PKT_DMA; +- } else { +- qc->tf.protocol = ATAPI_PROT_PIO; +- qc->tf.lbam = SCSI_SENSE_BUFFERSIZE; +- qc->tf.lbah = 0; +- } +- qc->nbytes = SCSI_SENSE_BUFFERSIZE; +- +- qc->complete_fn = atapi_sense_complete; +- +- ata_qc_issue(qc); +-} +- + /* + * ATAPI devices typically report zero for their SCSI version, and sometimes + * deviate from the spec WRT response data format. If SCSI version is +@@ -2698,9 +2576,8 @@ static void atapi_qc_complete(struct ata_queued_cmd *qc) + struct scsi_cmnd *cmd = qc->scsicmd; + unsigned int err_mask = qc->err_mask; + +- /* handle completion from new EH */ +- if (unlikely(qc->ap->ops->error_handler && +- (err_mask || qc->flags & ATA_QCFLAG_SENSE_VALID))) { ++ /* handle completion from EH */ ++ if (unlikely(err_mask || qc->flags & ATA_QCFLAG_SENSE_VALID)) { + + if (!(qc->flags & ATA_QCFLAG_SENSE_VALID)) { + /* FIXME: not quite right; we don't want the +@@ -2732,23 +2609,10 @@ static void atapi_qc_complete(struct ata_queued_cmd *qc) + return; + } + +- /* successful completion or old EH failure path */ +- if (unlikely(err_mask & AC_ERR_DEV)) { +- cmd->result = SAM_STAT_CHECK_CONDITION; +- atapi_request_sense(qc); +- return; +- } else if (unlikely(err_mask)) { +- /* FIXME: not quite right; we don't want the +- * translation of taskfile registers into +- * a sense descriptors, since that's only +- * correct for ATA, not ATAPI +- */ +- ata_gen_passthru_sense(qc); +- } else { +- if (cmd->cmnd[0] == INQUIRY && (cmd->cmnd[1] & 0x03) == 0) +- atapi_fixup_inquiry(cmd); +- cmd->result = SAM_STAT_GOOD; +- } ++ /* successful completion path */ ++ if (cmd->cmnd[0] == INQUIRY && (cmd->cmnd[1] & 0x03) == 0) ++ atapi_fixup_inquiry(cmd); ++ cmd->result = SAM_STAT_GOOD; + + ata_qc_done(qc); + } +@@ -4797,9 +4661,6 @@ int ata_scsi_user_scan(struct Scsi_Host *shost, unsigned int channel, + unsigned long flags; + int devno, rc = 0; + +- if (!ap->ops->error_handler) +- return -EOPNOTSUPP; +- + if (lun != SCAN_WILD_CARD && lun) + return -EINVAL; + +diff --git a/drivers/ata/libata-sff.c b/drivers/ata/libata-sff.c +index 9d28badfe41d6..84471d92cd1b9 100644 +--- a/drivers/ata/libata-sff.c ++++ b/drivers/ata/libata-sff.c +@@ -883,31 +883,21 @@ static void ata_hsm_qc_complete(struct ata_queued_cmd *qc, int in_wq) + { + struct ata_port *ap = qc->ap; + +- if (ap->ops->error_handler) { +- if (in_wq) { +- /* EH might have kicked in while host lock is +- * released. +- */ +- qc = ata_qc_from_tag(ap, qc->tag); +- if (qc) { +- if (likely(!(qc->err_mask & AC_ERR_HSM))) { +- ata_sff_irq_on(ap); +- ata_qc_complete(qc); +- } else +- ata_port_freeze(ap); +- } +- } else { +- if (likely(!(qc->err_mask & AC_ERR_HSM))) ++ if (in_wq) { ++ /* EH might have kicked in while host lock is released. */ ++ qc = ata_qc_from_tag(ap, qc->tag); ++ if (qc) { ++ if (likely(!(qc->err_mask & AC_ERR_HSM))) { ++ ata_sff_irq_on(ap); + ata_qc_complete(qc); +- else ++ } else + ata_port_freeze(ap); + } + } else { +- if (in_wq) { +- ata_sff_irq_on(ap); +- ata_qc_complete(qc); +- } else ++ if (likely(!(qc->err_mask & AC_ERR_HSM))) + ata_qc_complete(qc); ++ else ++ ata_port_freeze(ap); + } + } + +diff --git a/include/linux/libata.h b/include/linux/libata.h +index 820f7a3a2749b..3eeea76c30de4 100644 +--- a/include/linux/libata.h ++++ b/include/linux/libata.h +@@ -1785,7 +1785,7 @@ static inline struct ata_queued_cmd *ata_qc_from_tag(struct ata_port *ap, + { + struct ata_queued_cmd *qc = __ata_qc_from_tag(ap, tag); + +- if (unlikely(!qc) || !ap->ops->error_handler) ++ if (unlikely(!qc)) + return qc; + + if ((qc->flags & (ATA_QCFLAG_ACTIVE | +-- +2.40.1 + diff --git a/queue-6.5/autofs-fix-memory-leak-of-waitqueues-in-autofs_catat.patch b/queue-6.5/autofs-fix-memory-leak-of-waitqueues-in-autofs_catat.patch new file mode 100644 index 00000000000..833e5f06567 --- /dev/null +++ b/queue-6.5/autofs-fix-memory-leak-of-waitqueues-in-autofs_catat.patch @@ -0,0 +1,106 @@ +From 3d3f1a1f0368dbbe588de3620cacee76eab1ffc8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 4 Aug 2023 13:33:12 +0800 +Subject: autofs: fix memory leak of waitqueues in autofs_catatonic_mode + +From: Fedor Pchelkin + +[ Upstream commit ccbe77f7e45dfb4420f7f531b650c00c6e9c7507 ] + +Syzkaller reports a memory leak: + +BUG: memory leak +unreferenced object 0xffff88810b279e00 (size 96): + comm "syz-executor399", pid 3631, jiffies 4294964921 (age 23.870s) + hex dump (first 32 bytes): + 00 00 00 00 00 00 00 00 08 9e 27 0b 81 88 ff ff ..........'..... + 08 9e 27 0b 81 88 ff ff 00 00 00 00 00 00 00 00 ..'............. + backtrace: + [] kmalloc_trace+0x20/0x90 mm/slab_common.c:1046 + [] kmalloc include/linux/slab.h:576 [inline] + [] autofs_wait+0x3fa/0x9a0 fs/autofs/waitq.c:378 + [] autofs_do_expire_multi+0xa7/0x3e0 fs/autofs/expire.c:593 + [] autofs_expire_multi+0x53/0x80 fs/autofs/expire.c:619 + [] autofs_root_ioctl_unlocked+0x322/0x3b0 fs/autofs/root.c:897 + [] autofs_root_ioctl+0x25/0x30 fs/autofs/root.c:910 + [] vfs_ioctl fs/ioctl.c:51 [inline] + [] __do_sys_ioctl fs/ioctl.c:870 [inline] + [] __se_sys_ioctl fs/ioctl.c:856 [inline] + [] __x64_sys_ioctl+0xfc/0x140 fs/ioctl.c:856 + [] do_syscall_x64 arch/x86/entry/common.c:50 [inline] + [] do_syscall_64+0x35/0xb0 arch/x86/entry/common.c:80 + [] entry_SYSCALL_64_after_hwframe+0x63/0xcd + +autofs_wait_queue structs should be freed if their wait_ctr becomes zero. +Otherwise they will be lost. + +In this case an AUTOFS_IOC_EXPIRE_MULTI ioctl is done, then a new +waitqueue struct is allocated in autofs_wait(), its initial wait_ctr +equals 2. After that wait_event_killable() is interrupted (it returns +-ERESTARTSYS), so that 'wq->name.name == NULL' condition may be not +satisfied. Actually, this condition can be satisfied when +autofs_wait_release() or autofs_catatonic_mode() is called and, what is +also important, wait_ctr is decremented in those places. Upon the exit of +autofs_wait(), wait_ctr is decremented to 1. Then the unmounting process +begins: kill_sb calls autofs_catatonic_mode(), which should have freed the +waitqueues, but it only decrements its usage counter to zero which is not +a correct behaviour. + +edit:imk +This description is of course not correct. The umount performed as a result +of an expire is a umount of a mount that has been automounted, it's not the +autofs mount itself. They happen independently, usually after everything +mounted within the autofs file system has been expired away. If everything +hasn't been expired away the automount daemon can still exit leaving mounts +in place. But expires done in both cases will result in a notification that +calls autofs_wait_release() with a result status. The problem case is the +summary execution of of the automount daemon. In this case any waiting +processes won't be woken up until either they are terminated or the mount +is umounted. +end edit: imk + +So in catatonic mode we should free waitqueues which counter becomes zero. + +edit: imk +Initially I was concerned that the calling of autofs_wait_release() and +autofs_catatonic_mode() was not mutually exclusive but that can't be the +case (obviously) because the queue entry (or entries) is removed from the +list when either of these two functions are called. Consequently the wait +entry will be freed by only one of these functions or by the woken process +in autofs_wait() depending on the order of the calls. +end edit: imk + +Reported-by: syzbot+5e53f70e69ff0c0a1c0c@syzkaller.appspotmail.com +Suggested-by: Takeshi Misawa +Signed-off-by: Fedor Pchelkin +Signed-off-by: Alexey Khoroshilov +Signed-off-by: Ian Kent +Cc: Matthew Wilcox +Cc: Andrei Vagin +Cc: autofs@vger.kernel.org +Cc: linux-kernel@vger.kernel.org +Message-Id: <169112719161.7590.6700123246297365841.stgit@donald.themaw.net> +Signed-off-by: Christian Brauner +Signed-off-by: Sasha Levin +--- + fs/autofs/waitq.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +diff --git a/fs/autofs/waitq.c b/fs/autofs/waitq.c +index 54c1f8b8b0757..efdc76732faed 100644 +--- a/fs/autofs/waitq.c ++++ b/fs/autofs/waitq.c +@@ -32,8 +32,9 @@ void autofs_catatonic_mode(struct autofs_sb_info *sbi) + wq->status = -ENOENT; /* Magic is gone - report failure */ + kfree(wq->name.name - wq->offset); + wq->name.name = NULL; +- wq->wait_ctr--; + wake_up_interruptible(&wq->queue); ++ if (!--wq->wait_ctr) ++ kfree(wq); + wq = nwq; + } + fput(sbi->pipe); /* Close the pipe */ +-- +2.40.1 + diff --git a/queue-6.5/blk-mq-fix-tags-leak-when-shrink-nr_hw_queues.patch b/queue-6.5/blk-mq-fix-tags-leak-when-shrink-nr_hw_queues.patch new file mode 100644 index 00000000000..00000a6627a --- /dev/null +++ b/queue-6.5/blk-mq-fix-tags-leak-when-shrink-nr_hw_queues.patch @@ -0,0 +1,55 @@ +From 27a486968e71cda6512269f614fd4ec685755bbd Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 21 Aug 2023 17:56:00 +0800 +Subject: blk-mq: fix tags leak when shrink nr_hw_queues + +From: Chengming Zhou + +[ Upstream commit e1dd7bc93029024af5688253b0c05181d6e01f8e ] + +Although we don't need to realloc set->tags[] when shrink nr_hw_queues, +we need to free them. Or these tags will be leaked. + +How to reproduce: +1. mount -t configfs configfs /mnt +2. modprobe null_blk nr_devices=0 submit_queues=8 +3. mkdir /mnt/nullb/nullb0 +4. echo 1 > /mnt/nullb/nullb0/power +5. echo 4 > /mnt/nullb/nullb0/submit_queues +6. rmdir /mnt/nullb/nullb0 + +In step 4, will alloc 9 tags (8 submit queues and 1 poll queue), then +in step 5, new_nr_hw_queues = 5 (4 submit queues and 1 poll queue). +At last in step 6, only these 5 tags are freed, the other 4 tags leaked. + +Signed-off-by: Chengming Zhou +Reviewed-by: Ming Lei +Link: https://lore.kernel.org/r/20230821095602.70742-1-chengming.zhou@linux.dev +Signed-off-by: Jens Axboe +Signed-off-by: Sasha Levin +--- + block/blk-mq.c | 6 +++++- + 1 file changed, 5 insertions(+), 1 deletion(-) + +diff --git a/block/blk-mq.c b/block/blk-mq.c +index 953f08354c8c3..d9b365c2eaa0d 100644 +--- a/block/blk-mq.c ++++ b/block/blk-mq.c +@@ -4402,9 +4402,13 @@ static int blk_mq_realloc_tag_set_tags(struct blk_mq_tag_set *set, + int new_nr_hw_queues) + { + struct blk_mq_tags **new_tags; ++ int i; + +- if (set->nr_hw_queues >= new_nr_hw_queues) ++ if (set->nr_hw_queues >= new_nr_hw_queues) { ++ for (i = new_nr_hw_queues; i < set->nr_hw_queues; i++) ++ __blk_mq_free_map_and_rqs(set, i); + goto done; ++ } + + new_tags = kcalloc_node(new_nr_hw_queues, sizeof(struct blk_mq_tags *), + GFP_KERNEL, set->numa_node); +-- +2.40.1 + diff --git a/queue-6.5/blk-mq-fix-tags-uaf-when-shrinking-q-nr_hw_queues.patch b/queue-6.5/blk-mq-fix-tags-uaf-when-shrinking-q-nr_hw_queues.patch new file mode 100644 index 00000000000..492efd140c5 --- /dev/null +++ b/queue-6.5/blk-mq-fix-tags-uaf-when-shrinking-q-nr_hw_queues.patch @@ -0,0 +1,78 @@ +From 21e83fd7bf60c763036a94ec5f1f8aca8f29d3d5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 8 Sep 2023 08:57:02 +0800 +Subject: blk-mq: fix tags UAF when shrinking q->nr_hw_queues + +From: Chengming Zhou + +[ Upstream commit 6be6d112419713334ddd9c01f219ca16adaa4c76 ] + +When nr_hw_queues shrink, we free the excess tags before realloc'ing +hw_ctxs for each queue. During that resize, we may need to access those +tags, like blk_mq_tag_idle(hctx) will access queue shared tags. + +This can cause a slab use-after-free, as reported by KASAN. Fix it by +moving the releasing of excess tags to the end. + +Fixes: e1dd7bc93029 ("blk-mq: fix tags leak when shrink nr_hw_queues") +Reported-by: Yi Zhang +Closes: https://lore.kernel.org/all/CAHj4cs_CK63uoDpGBGZ6DN4OCTpzkR3UaVgK=LX8Owr8ej2ieQ@mail.gmail.com/ +Cc: Ming Lei +Signed-off-by: Chengming Zhou +Reviewed-by: Hannes Reinecke +Link: https://lore.kernel.org/r/20230908005702.2183908-1-chengming.zhou@linux.dev +Signed-off-by: Jens Axboe +Signed-off-by: Sasha Levin +--- + block/blk-mq.c | 13 +++++++------ + 1 file changed, 7 insertions(+), 6 deletions(-) + +diff --git a/block/blk-mq.c b/block/blk-mq.c +index d9b365c2eaa0d..a90f1efb1c978 100644 +--- a/block/blk-mq.c ++++ b/block/blk-mq.c +@@ -4404,11 +4404,8 @@ static int blk_mq_realloc_tag_set_tags(struct blk_mq_tag_set *set, + struct blk_mq_tags **new_tags; + int i; + +- if (set->nr_hw_queues >= new_nr_hw_queues) { +- for (i = new_nr_hw_queues; i < set->nr_hw_queues; i++) +- __blk_mq_free_map_and_rqs(set, i); ++ if (set->nr_hw_queues >= new_nr_hw_queues) + goto done; +- } + + new_tags = kcalloc_node(new_nr_hw_queues, sizeof(struct blk_mq_tags *), + GFP_KERNEL, set->numa_node); +@@ -4708,7 +4705,8 @@ static void __blk_mq_update_nr_hw_queues(struct blk_mq_tag_set *set, + { + struct request_queue *q; + LIST_HEAD(head); +- int prev_nr_hw_queues; ++ int prev_nr_hw_queues = set->nr_hw_queues; ++ int i; + + lockdep_assert_held(&set->tag_list_lock); + +@@ -4735,7 +4733,6 @@ static void __blk_mq_update_nr_hw_queues(struct blk_mq_tag_set *set, + blk_mq_sysfs_unregister_hctxs(q); + } + +- prev_nr_hw_queues = set->nr_hw_queues; + if (blk_mq_realloc_tag_set_tags(set, nr_hw_queues) < 0) + goto reregister; + +@@ -4771,6 +4768,10 @@ static void __blk_mq_update_nr_hw_queues(struct blk_mq_tag_set *set, + + list_for_each_entry(q, &set->tag_list, tag_set_list) + blk_mq_unfreeze_queue(q); ++ ++ /* Free the excess tags when nr_hw_queues shrink. */ ++ for (i = set->nr_hw_queues; i < prev_nr_hw_queues; i++) ++ __blk_mq_free_map_and_rqs(set, i); + } + + void blk_mq_update_nr_hw_queues(struct blk_mq_tag_set *set, int nr_hw_queues) +-- +2.40.1 + diff --git a/queue-6.5/bluetooth-btusb-add-a-new-vid-pid-0489-e0f6-for-mt79.patch b/queue-6.5/bluetooth-btusb-add-a-new-vid-pid-0489-e0f6-for-mt79.patch new file mode 100644 index 00000000000..c4c32d8f166 --- /dev/null +++ b/queue-6.5/bluetooth-btusb-add-a-new-vid-pid-0489-e0f6-for-mt79.patch @@ -0,0 +1,78 @@ +From 0500541602ed56dc37421a0587ee2adb0d703730 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 30 Jun 2023 21:32:30 +0800 +Subject: Bluetooth: btusb: Add a new VID/PID 0489/e0f6 for MT7922 + +From: Chris Lu + +[ Upstream commit b6cfa1c29afb6d527652938b0eb8db17b194bddc ] + +Add VID/PID 0489/e0f6 for MediaTek MT7922 USB Bluetooth chip. + +The information in /sys/kernel/debug/usb/devices about the Bluetooth +device is listed as the below. + +T: Bus=01 Lev=01 Prnt=01 Port=04 Cnt=03 Dev#= 4 Spd=480 MxCh= 0 +D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 +P: Vendor=0489 ProdID=e0f6 Rev= 1.00 +S: Manufacturer=MediaTek Inc. +S: Product=Wireless_Device +S: SerialNumber=000000000 +C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA +A: FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01 +I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=125us +E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms +E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms +I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms +I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms +I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms +I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms +I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms +I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms +I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms +I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us +I: If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 512 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 512 Ivl=125us + +Signed-off-by: Chris Lu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/btusb.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c +index e5c7852f8b133..3cdb2dea1f559 100644 +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -631,6 +631,9 @@ static const struct usb_device_id blacklist_table[] = { + { USB_DEVICE(0x0489, 0xe0f5), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, ++ { USB_DEVICE(0x0489, 0xe0f6), .driver_info = BTUSB_MEDIATEK | ++ BTUSB_WIDEBAND_SPEECH | ++ BTUSB_VALID_LE_STATES }, + + /* Additional Realtek 8723AE Bluetooth devices */ + { USB_DEVICE(0x0930, 0x021d), .driver_info = BTUSB_REALTEK }, +-- +2.40.1 + diff --git a/queue-6.5/bluetooth-btusb-add-device-0489-e0f5-as-mt7922-devic.patch b/queue-6.5/bluetooth-btusb-add-device-0489-e0f5-as-mt7922-devic.patch new file mode 100644 index 00000000000..8671e06bb74 --- /dev/null +++ b/queue-6.5/bluetooth-btusb-add-device-0489-e0f5-as-mt7922-devic.patch @@ -0,0 +1,81 @@ +From 588c90ec0ef2d90cde1fd7b87ae4e6ae751ad2de Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 2 Jul 2023 23:01:38 +0200 +Subject: Bluetooth: btusb: Add device 0489:e0f5 as MT7922 device + +From: Valentin David + +[ Upstream commit e160a8f4e920e5cf4e16a17f57367954c9436aea ] + +Asus ROG Ally gaming computer has a MediaTek MT7922 chip that uses USB id +0489:e0f5 and needs to be added to the table. Without this, the device is +not usable and gives the following error: + +Bluetooth: hci0: Opcode 0x c03 failed: -110 + +Output from /sys/kernel/debug/usb/devices: + +T: Bus=01 Lev=01 Prnt=01 Port=03 Cnt=03 Dev#= 4 Spd=480 MxCh= 0 +D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 +P: Vendor=0489 ProdID=e0f5 Rev= 1.00 +S: Manufacturer=MediaTek Inc. +S: Product=Wireless_Device +S: SerialNumber=000000000 +C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA +A: FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01 +I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=125us +E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms +E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms +I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms +I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms +I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms +I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms +I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms +I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms +I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms +I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us +I: If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 512 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 512 Ivl=125us + +Signed-off-by: Valentin David +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/btusb.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c +index e685acc5cacd9..e5c7852f8b133 100644 +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -628,6 +628,9 @@ static const struct usb_device_id blacklist_table[] = { + { USB_DEVICE(0x0489, 0xe0f2), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, ++ { USB_DEVICE(0x0489, 0xe0f5), .driver_info = BTUSB_MEDIATEK | ++ BTUSB_WIDEBAND_SPEECH | ++ BTUSB_VALID_LE_STATES }, + + /* Additional Realtek 8723AE Bluetooth devices */ + { USB_DEVICE(0x0930, 0x021d), .driver_info = BTUSB_REALTEK }, +-- +2.40.1 + diff --git a/queue-6.5/bluetooth-btusb-add-new-vid-pid-0489-e102-for-mt7922.patch b/queue-6.5/bluetooth-btusb-add-new-vid-pid-0489-e102-for-mt7922.patch new file mode 100644 index 00000000000..a760cdf2348 --- /dev/null +++ b/queue-6.5/bluetooth-btusb-add-new-vid-pid-0489-e102-for-mt7922.patch @@ -0,0 +1,78 @@ +From a048f5fe9535c89f1805271df93435d4f779cbee Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 7 Jul 2023 14:29:58 +0800 +Subject: Bluetooth: btusb: Add new VID/PID 0489/e102 for MT7922 + +From: Chris Lu + +[ Upstream commit bf809efdcc4df4132c8c261fbba7121909dc6211 ] + +Add VID 0489 & PID e102 for MediaTek MT7922 USB Bluetooth chip. + +The information in /sys/kernel/debug/usb/devices about the Bluetooth +device is listed as the below. + +T: Bus=05 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#= 2 Spd=480 MxCh= 0 +D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 +P: Vendor=0489 ProdID=e102 Rev= 1.00 +S: Manufacturer=MediaTek Inc. +S: Product=Wireless_Device +S: SerialNumber=000000000 +C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA +A: FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01 +I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=125us +E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms +E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms +I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms +I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms +I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms +I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms +I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms +I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms +I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms +I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us +I: If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 512 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 512 Ivl=125us + +Signed-off-by: Chris Lu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/btusb.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c +index 3cdb2dea1f559..81a58f3e1db42 100644 +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -634,6 +634,9 @@ static const struct usb_device_id blacklist_table[] = { + { USB_DEVICE(0x0489, 0xe0f6), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, ++ { USB_DEVICE(0x0489, 0xe102), .driver_info = BTUSB_MEDIATEK | ++ BTUSB_WIDEBAND_SPEECH | ++ BTUSB_VALID_LE_STATES }, + + /* Additional Realtek 8723AE Bluetooth devices */ + { USB_DEVICE(0x0930, 0x021d), .driver_info = BTUSB_REALTEK }, +-- +2.40.1 + diff --git a/queue-6.5/bluetooth-btusb-add-new-vid-pid-04ca-3804-for-mt7922.patch b/queue-6.5/bluetooth-btusb-add-new-vid-pid-04ca-3804-for-mt7922.patch new file mode 100644 index 00000000000..2560f78e0f1 --- /dev/null +++ b/queue-6.5/bluetooth-btusb-add-new-vid-pid-04ca-3804-for-mt7922.patch @@ -0,0 +1,78 @@ +From 63ef608d69a1203de7644487c7032b202ebf5102 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 7 Jul 2023 14:29:59 +0800 +Subject: Bluetooth: btusb: Add new VID/PID 04ca/3804 for MT7922 + +From: Chris Lu + +[ Upstream commit 59be4be82bd3639cd9dbfb92df0f6263ab2c2e28 ] + +Add VID 04ca & PID 3804 for MediaTek MT7922 USB Bluetooth chip. + +The information in /sys/kernel/debug/usb/devices about the Bluetooth +device is listed as the below. + +T: Bus=05 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#= 2 Spd=480 MxCh= 0 +D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 +P: Vendor=04ca ProdID=3804 Rev= 1.00 +S: Manufacturer=MediaTek Inc. +S: Product=Wireless_Device +S: SerialNumber=000000000 +C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA +A: FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01 +I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=125us +E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms +E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms +I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms +I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms +I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms +I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms +I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms +I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms +I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms +I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us +I: If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 512 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 512 Ivl=125us + +Signed-off-by: Chris Lu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/btusb.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c +index 81a58f3e1db42..26203b16ad911 100644 +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -637,6 +637,9 @@ static const struct usb_device_id blacklist_table[] = { + { USB_DEVICE(0x0489, 0xe102), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, ++ { USB_DEVICE(0x04ca, 0x3804), .driver_info = BTUSB_MEDIATEK | ++ BTUSB_WIDEBAND_SPEECH | ++ BTUSB_VALID_LE_STATES }, + + /* Additional Realtek 8723AE Bluetooth devices */ + { USB_DEVICE(0x0930, 0x021d), .driver_info = BTUSB_REALTEK }, +-- +2.40.1 + diff --git a/queue-6.5/bluetooth-btusb-add-support-for-another-mediatek-792.patch b/queue-6.5/bluetooth-btusb-add-support-for-another-mediatek-792.patch new file mode 100644 index 00000000000..5f24a0e347f --- /dev/null +++ b/queue-6.5/bluetooth-btusb-add-support-for-another-mediatek-792.patch @@ -0,0 +1,78 @@ +From 8d2f1e5ecc96d452156c5f87ceefd383fca6d73e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 12 Jul 2023 22:36:02 +0100 +Subject: Bluetooth: btusb: Add support for another MediaTek 7922 VID/PID + +From: Roger Gammans + +[ Upstream commit 0cefdaed944d1617852762ff1f66364199cf5d7d ] + +This one is found on the Dell Inspiron 2-in-1 7435 + +The information in /sys/kernel/debug/usb/devices about the Bluetooth +device is listed as the below. + +T: Bus=03 Lev=01 Prnt=01 Port=02 Cnt=01 Dev#= 2 Spd=480 MxCh= 0 +D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 +P: Vendor=0489 ProdID=e0f1 Rev= 1.00 +S: Manufacturer=MediaTek Inc. +S: Product=Wireless_Device +S: SerialNumber=000000000 +C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA +A: FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01 +I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=125us +E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms +E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms +I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms +I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms +I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms +I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms +I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms +I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms +I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms +I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us +I: If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) +E: Ad=8a(I) Atr=03(Int.) MxPS= 512 Ivl=125us +E: Ad=0a(O) Atr=03(Int.) MxPS= 512 Ivl=125us + +Signed-off-by: Roger Gammans +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/btusb.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c +index 26203b16ad911..dfdfb72d350fe 100644 +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -625,6 +625,9 @@ static const struct usb_device_id blacklist_table[] = { + { USB_DEVICE(0x0489, 0xe0e4), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, ++ { USB_DEVICE(0x0489, 0xe0f1), .driver_info = BTUSB_MEDIATEK | ++ BTUSB_WIDEBAND_SPEECH | ++ BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x0489, 0xe0f2), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, +-- +2.40.1 + diff --git a/queue-6.5/bluetooth-fix-hci_suspend_sync-crash.patch b/queue-6.5/bluetooth-fix-hci_suspend_sync-crash.patch new file mode 100644 index 00000000000..984a702f2a0 --- /dev/null +++ b/queue-6.5/bluetooth-fix-hci_suspend_sync-crash.patch @@ -0,0 +1,66 @@ +From 01191ba045cba26364de1b42ace1f0d7e42d11a7 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 5 Jul 2023 21:06:47 +0000 +Subject: Bluetooth: Fix hci_suspend_sync crash + +From: Ying Hsu + +[ Upstream commit 573ebae162111063eedc6c838a659ba628f66a0f ] + +If hci_unregister_dev() frees the hci_dev object but hci_suspend_notifier +may still be accessing it, it can cause the program to crash. +Here's the call trace: + <4>[102152.653246] Call Trace: + <4>[102152.653254] hci_suspend_sync+0x109/0x301 [bluetooth] + <4>[102152.653259] hci_suspend_dev+0x78/0xcd [bluetooth] + <4>[102152.653263] hci_suspend_notifier+0x42/0x7a [bluetooth] + <4>[102152.653268] notifier_call_chain+0x43/0x6b + <4>[102152.653271] __blocking_notifier_call_chain+0x48/0x69 + <4>[102152.653273] __pm_notifier_call_chain+0x22/0x39 + <4>[102152.653276] pm_suspend+0x287/0x57c + <4>[102152.653278] state_store+0xae/0xe5 + <4>[102152.653281] kernfs_fop_write+0x109/0x173 + <4>[102152.653284] __vfs_write+0x16f/0x1a2 + <4>[102152.653287] ? selinux_file_permission+0xca/0x16f + <4>[102152.653289] ? security_file_permission+0x36/0x109 + <4>[102152.653291] vfs_write+0x114/0x21d + <4>[102152.653293] __x64_sys_write+0x7b/0xdb + <4>[102152.653296] do_syscall_64+0x59/0x194 + <4>[102152.653299] entry_SYSCALL_64_after_hwframe+0x5c/0xc1 + +This patch holds the reference count of the hci_dev object while +processing it in hci_suspend_notifier to avoid potential crash +caused by the race condition. + +Signed-off-by: Ying Hsu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_core.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c +index 2c845c9a26be0..29ae9b254a34e 100644 +--- a/net/bluetooth/hci_core.c ++++ b/net/bluetooth/hci_core.c +@@ -2436,6 +2436,9 @@ static int hci_suspend_notifier(struct notifier_block *nb, unsigned long action, + if (hci_dev_test_flag(hdev, HCI_USER_CHANNEL)) + return NOTIFY_DONE; + ++ /* To avoid a potential race with hci_unregister_dev. */ ++ hci_dev_hold(hdev); ++ + if (action == PM_SUSPEND_PREPARE) + ret = hci_suspend_dev(hdev); + else if (action == PM_POST_SUSPEND) +@@ -2445,6 +2448,7 @@ static int hci_suspend_notifier(struct notifier_block *nb, unsigned long action, + bt_dev_err(hdev, "Suspend notifier action (%lu) failed: %d", + action, ret); + ++ hci_dev_put(hdev); + return NOTIFY_DONE; + } + +-- +2.40.1 + diff --git a/queue-6.5/bpf-consider-non-owning-refs-to-refcounted-nodes-rcu.patch b/queue-6.5/bpf-consider-non-owning-refs-to-refcounted-nodes-rcu.patch new file mode 100644 index 00000000000..2ae813c5102 --- /dev/null +++ b/queue-6.5/bpf-consider-non-owning-refs-to-refcounted-nodes-rcu.patch @@ -0,0 +1,100 @@ +From 7d407207b328dbc8a991d00aa763a4d583a368b1 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 21 Aug 2023 12:33:09 -0700 +Subject: bpf: Consider non-owning refs to refcounted nodes RCU protected + +From: Dave Marchevsky + +[ Upstream commit 0816b8c6bf7fc87cec4273dc199e8f0764b9e7b1 ] + +An earlier patch in the series ensures that the underlying memory of +nodes with bpf_refcount - which can have multiple owners - is not reused +until RCU grace period has elapsed. This prevents +use-after-free with non-owning references that may point to +recently-freed memory. While RCU read lock is held, it's safe to +dereference such a non-owning ref, as by definition RCU GP couldn't have +elapsed and therefore underlying memory couldn't have been reused. + +From the perspective of verifier "trustedness" non-owning refs to +refcounted nodes are now trusted only in RCU CS and therefore should no +longer pass is_trusted_reg, but rather is_rcu_reg. Let's mark them +MEM_RCU in order to reflect this new state. + +Signed-off-by: Dave Marchevsky +Link: https://lore.kernel.org/r/20230821193311.3290257-6-davemarchevsky@fb.com +Signed-off-by: Alexei Starovoitov +Signed-off-by: Sasha Levin +--- + include/linux/bpf.h | 3 ++- + kernel/bpf/verifier.c | 13 ++++++++++++- + 2 files changed, 14 insertions(+), 2 deletions(-) + +diff --git a/include/linux/bpf.h b/include/linux/bpf.h +index f316affcd2e13..28e2e0ce2ed07 100644 +--- a/include/linux/bpf.h ++++ b/include/linux/bpf.h +@@ -640,7 +640,8 @@ enum bpf_type_flag { + MEM_RCU = BIT(13 + BPF_BASE_TYPE_BITS), + + /* Used to tag PTR_TO_BTF_ID | MEM_ALLOC references which are non-owning. +- * Currently only valid for linked-list and rbtree nodes. ++ * Currently only valid for linked-list and rbtree nodes. If the nodes ++ * have a bpf_refcount_field, they must be tagged MEM_RCU as well. + */ + NON_OWN_REF = BIT(14 + BPF_BASE_TYPE_BITS), + +diff --git a/kernel/bpf/verifier.c b/kernel/bpf/verifier.c +index 76845dd22cd26..9cdba4ce23d2b 100644 +--- a/kernel/bpf/verifier.c ++++ b/kernel/bpf/verifier.c +@@ -7841,6 +7841,7 @@ int check_func_arg_reg_off(struct bpf_verifier_env *env, + case PTR_TO_BTF_ID | PTR_TRUSTED: + case PTR_TO_BTF_ID | MEM_RCU: + case PTR_TO_BTF_ID | MEM_ALLOC | NON_OWN_REF: ++ case PTR_TO_BTF_ID | MEM_ALLOC | NON_OWN_REF | MEM_RCU: + /* When referenced PTR_TO_BTF_ID is passed to release function, + * its fixed offset must be 0. In the other cases, fixed offset + * can be non-zero. This was already checked above. So pass +@@ -10302,6 +10303,7 @@ static int process_kf_arg_ptr_to_btf_id(struct bpf_verifier_env *env, + static int ref_set_non_owning(struct bpf_verifier_env *env, struct bpf_reg_state *reg) + { + struct bpf_verifier_state *state = env->cur_state; ++ struct btf_record *rec = reg_btf_record(reg); + + if (!state->active_lock.ptr) { + verbose(env, "verifier internal error: ref_set_non_owning w/o active lock\n"); +@@ -10314,6 +10316,9 @@ static int ref_set_non_owning(struct bpf_verifier_env *env, struct bpf_reg_state + } + + reg->type |= NON_OWN_REF; ++ if (rec->refcount_off >= 0) ++ reg->type |= MEM_RCU; ++ + return 0; + } + +@@ -11154,6 +11159,11 @@ static int check_kfunc_call(struct bpf_verifier_env *env, struct bpf_insn *insn, + struct bpf_func_state *state; + struct bpf_reg_state *reg; + ++ if (in_rbtree_lock_required_cb(env) && (rcu_lock || rcu_unlock)) { ++ verbose(env, "Calling bpf_rcu_read_{lock,unlock} in unnecessary rbtree callback\n"); ++ return -EACCES; ++ } ++ + if (rcu_lock) { + verbose(env, "nested rcu read lock (kernel function %s)\n", func_name); + return -EINVAL; +@@ -16453,7 +16463,8 @@ static int do_check(struct bpf_verifier_env *env) + return -EINVAL; + } + +- if (env->cur_state->active_rcu_lock) { ++ if (env->cur_state->active_rcu_lock && ++ !in_rbtree_lock_required_cb(env)) { + verbose(env, "bpf_rcu_read_unlock is missing\n"); + return -EINVAL; + } +-- +2.40.1 + diff --git a/queue-6.5/bpf-consider-non-owning-refs-trusted.patch b/queue-6.5/bpf-consider-non-owning-refs-trusted.patch new file mode 100644 index 00000000000..5ec5b224fe2 --- /dev/null +++ b/queue-6.5/bpf-consider-non-owning-refs-trusted.patch @@ -0,0 +1,69 @@ +From edf42ff1b974487da39b94b4287ffcd252589250 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 21 Aug 2023 12:33:06 -0700 +Subject: bpf: Consider non-owning refs trusted + +From: Dave Marchevsky + +[ Upstream commit 2a6d50b50d6d589d43a90d6ca990b8b811e67701 ] + +Recent discussions around default kptr "trustedness" led to changes such +as commit 6fcd486b3a0a ("bpf: Refactor RCU enforcement in the +verifier."). One of the conclusions of those discussions, as expressed +in code and comments in that patch, is that we'd like to move away from +'raw' PTR_TO_BTF_ID without some type flag or other register state +indicating trustedness. Although PTR_TRUSTED and PTR_UNTRUSTED flags mark +this state explicitly, the verifier currently considers trustedness +implied by other register state. For example, owning refs to graph +collection nodes must have a nonzero ref_obj_id, so they pass the +is_trusted_reg check despite having no explicit PTR_{UN}TRUSTED flag. +This patch makes trustedness of non-owning refs to graph collection +nodes explicit as well. + +By definition, non-owning refs are currently trusted. Although the ref +has no control over pointee lifetime, due to non-owning ref clobbering +rules (see invalidate_non_owning_refs) dereferencing a non-owning ref is +safe in the critical section controlled by bpf_spin_lock associated with +its owning collection. + +Note that the previous statement does not hold true for nodes with shared +ownership due to the use-after-free issue that this series is +addressing. True shared ownership was disabled by commit 7deca5eae833 +("bpf: Disable bpf_refcount_acquire kfunc calls until race conditions are fixed"), +though, so the statement holds for now. Further patches in the series will change +the trustedness state of non-owning refs before re-enabling +bpf_refcount_acquire. + +Let's add NON_OWN_REF type flag to BPF_REG_TRUSTED_MODIFIERS such that a +non-owning ref reg state would pass is_trusted_reg check. Somewhat +surprisingly, this doesn't result in any change to user-visible +functionality elsewhere in the verifier: graph collection nodes are all +marked MEM_ALLOC, which tends to be handled in separate codepaths from +"raw" PTR_TO_BTF_ID. Regardless, let's be explicit here and document the +current state of things before changing it elsewhere in the series. + +Signed-off-by: Dave Marchevsky +Acked-by: Yonghong Song +Link: https://lore.kernel.org/r/20230821193311.3290257-3-davemarchevsky@fb.com +Signed-off-by: Alexei Starovoitov +Signed-off-by: Sasha Levin +--- + include/linux/bpf_verifier.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/include/linux/bpf_verifier.h b/include/linux/bpf_verifier.h +index f70f9ac884d24..b6e58dab8e275 100644 +--- a/include/linux/bpf_verifier.h ++++ b/include/linux/bpf_verifier.h +@@ -745,7 +745,7 @@ static inline bool bpf_prog_check_recur(const struct bpf_prog *prog) + } + } + +-#define BPF_REG_TRUSTED_MODIFIERS (MEM_ALLOC | PTR_TRUSTED) ++#define BPF_REG_TRUSTED_MODIFIERS (MEM_ALLOC | PTR_TRUSTED | NON_OWN_REF) + + static inline bool bpf_type_has_unsafe_modifiers(u32 type) + { +-- +2.40.1 + diff --git a/queue-6.5/btrfs-add-a-helper-to-read-the-superblock-metadata_u.patch b/queue-6.5/btrfs-add-a-helper-to-read-the-superblock-metadata_u.patch new file mode 100644 index 00000000000..94735458144 --- /dev/null +++ b/queue-6.5/btrfs-add-a-helper-to-read-the-superblock-metadata_u.patch @@ -0,0 +1,58 @@ +From d51f341460f11bb99cd5bb33abbc865e4e582859 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 31 Jul 2023 19:16:32 +0800 +Subject: btrfs: add a helper to read the superblock metadata_uuid + +From: Anand Jain + +[ Upstream commit 4844c3664a72d36cc79752cb651c78860b14c240 ] + +In some cases, we need to read the FSID from the superblock when the +metadata_uuid is not set, and otherwise, read the metadata_uuid. So, +add a helper. + +Reviewed-by: Johannes Thumshirn +Tested-by: Guilherme G. Piccoli +Signed-off-by: Anand Jain +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Stable-dep-of: 6bfe3959b0e7 ("btrfs: compare the correct fsid/metadata_uuid in btrfs_validate_super") +Signed-off-by: Sasha Levin +--- + fs/btrfs/volumes.c | 8 ++++++++ + fs/btrfs/volumes.h | 1 + + 2 files changed, 9 insertions(+) + +diff --git a/fs/btrfs/volumes.c b/fs/btrfs/volumes.c +index 6aa9bf3661ac8..51070c0d4141e 100644 +--- a/fs/btrfs/volumes.c ++++ b/fs/btrfs/volumes.c +@@ -681,6 +681,14 @@ static int btrfs_open_one_device(struct btrfs_fs_devices *fs_devices, + return -EINVAL; + } + ++u8 *btrfs_sb_fsid_ptr(struct btrfs_super_block *sb) ++{ ++ bool has_metadata_uuid = (btrfs_super_incompat_flags(sb) & ++ BTRFS_FEATURE_INCOMPAT_METADATA_UUID); ++ ++ return has_metadata_uuid ? sb->metadata_uuid : sb->fsid; ++} ++ + /* + * Handle scanned device having its CHANGING_FSID_V2 flag set and the fs_devices + * being created with a disk that has already completed its fsid change. Such +diff --git a/fs/btrfs/volumes.h b/fs/btrfs/volumes.h +index b8c51f16ba867..0f87057bb575f 100644 +--- a/fs/btrfs/volumes.h ++++ b/fs/btrfs/volumes.h +@@ -749,5 +749,6 @@ int btrfs_verify_dev_extents(struct btrfs_fs_info *fs_info); + bool btrfs_repair_one_zone(struct btrfs_fs_info *fs_info, u64 logical); + + bool btrfs_pinned_by_swapfile(struct btrfs_fs_info *fs_info, void *ptr); ++u8 *btrfs_sb_fsid_ptr(struct btrfs_super_block *sb); + + #endif +-- +2.40.1 + diff --git a/queue-6.5/btrfs-compare-the-correct-fsid-metadata_uuid-in-btrf.patch b/queue-6.5/btrfs-compare-the-correct-fsid-metadata_uuid-in-btrf.patch new file mode 100644 index 00000000000..768bbc411e9 --- /dev/null +++ b/queue-6.5/btrfs-compare-the-correct-fsid-metadata_uuid-in-btrf.patch @@ -0,0 +1,66 @@ +From b78d7b64beb89e103958ac4b4d61c20470e03f1f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 31 Jul 2023 19:16:35 +0800 +Subject: btrfs: compare the correct fsid/metadata_uuid in btrfs_validate_super + +From: Anand Jain + +[ Upstream commit 6bfe3959b0e7a526f5c64747801a8613f002f05a ] + +The function btrfs_validate_super() should verify the metadata_uuid in +the provided superblock argument. Because, all its callers expect it to +do that. + +Such as in the following stacks: + + write_all_supers() + sb = fs_info->super_for_commit; + btrfs_validate_write_super(.., sb) + btrfs_validate_super(.., sb, ..) + + scrub_one_super() + btrfs_validate_super(.., sb, ..) + +And + check_dev_super() + btrfs_validate_super(.., sb, ..) + +However, it currently verifies the fs_info::super_copy::metadata_uuid +instead. Fix this using the correct metadata_uuid in the superblock +argument. + +CC: stable@vger.kernel.org # 5.4+ +Reviewed-by: Johannes Thumshirn +Tested-by: Guilherme G. Piccoli +Signed-off-by: Anand Jain +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Signed-off-by: Sasha Levin +--- + fs/btrfs/disk-io.c | 8 +++----- + 1 file changed, 3 insertions(+), 5 deletions(-) + +diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c +index 4494883a19abc..0593f8f458a6e 100644 +--- a/fs/btrfs/disk-io.c ++++ b/fs/btrfs/disk-io.c +@@ -2391,13 +2391,11 @@ int btrfs_validate_super(struct btrfs_fs_info *fs_info, + ret = -EINVAL; + } + +- if (btrfs_fs_incompat(fs_info, METADATA_UUID) && +- memcmp(fs_info->fs_devices->metadata_uuid, +- fs_info->super_copy->metadata_uuid, BTRFS_FSID_SIZE)) { ++ if (memcmp(fs_info->fs_devices->metadata_uuid, btrfs_sb_fsid_ptr(sb), ++ BTRFS_FSID_SIZE) != 0) { + btrfs_err(fs_info, + "superblock metadata_uuid doesn't match metadata uuid of fs_devices: %pU != %pU", +- fs_info->super_copy->metadata_uuid, +- fs_info->fs_devices->metadata_uuid); ++ btrfs_sb_fsid_ptr(sb), fs_info->fs_devices->metadata_uuid); + ret = -EINVAL; + } + +-- +2.40.1 + diff --git a/queue-6.5/btrfs-handle-errors-properly-in-update_inline_extent.patch b/queue-6.5/btrfs-handle-errors-properly-in-update_inline_extent.patch new file mode 100644 index 00000000000..002dcade589 --- /dev/null +++ b/queue-6.5/btrfs-handle-errors-properly-in-update_inline_extent.patch @@ -0,0 +1,200 @@ +From 3f125860f5144bcab7ac817a61fc5bae1806855a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 9 Aug 2023 15:08:21 +0800 +Subject: btrfs: handle errors properly in update_inline_extent_backref() + +From: Qu Wenruo + +[ Upstream commit 257614301a5db9f7b0548584ca207ad7785c8b89 ] + +[PROBLEM] +Inside function update_inline_extent_backref(), we have several +BUG_ON()s along with some ASSERT()s which can be triggered by corrupted +filesystem. + +[ANAYLYSE] +Most of those BUG_ON()s and ASSERT()s are just a way of handling +unexpected on-disk data. + +Although we have tree-checker to rule out obviously incorrect extent +tree blocks, it's not enough for these ones. Thus we need proper error +handling for them. + +[FIX] +Thankfully all the callers of update_inline_extent_backref() would +eventually handle the errror by aborting the current transaction. +So this patch would do the proper error handling by: + +- Make update_inline_extent_backref() to return int + The return value would be either 0 or -EUCLEAN. + +- Replace BUG_ON()s and ASSERT()s with proper error handling + This includes: + * Dump the bad extent tree leaf + * Output an error message for the cause + This would include the extent bytenr, num_bytes (if needed), the bad + values and expected good values. + * Return -EUCLEAN + + Note here we remove all the WARN_ON()s, as eventually the transaction + would be aborted, thus a backtrace would be triggered anyway. + +- Better comments on why we expect refs == 1 and refs_to_mode == -1 for + tree blocks + +Reviewed-by: Josef Bacik +Signed-off-by: Qu Wenruo +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent-tree.c | 73 +++++++++++++++++++++++++++++++++++------- + 1 file changed, 61 insertions(+), 12 deletions(-) + +diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c +index e5566827da17e..c47fbb99e99d9 100644 +--- a/fs/btrfs/extent-tree.c ++++ b/fs/btrfs/extent-tree.c +@@ -402,11 +402,11 @@ int btrfs_get_extent_inline_ref_type(const struct extent_buffer *eb, + } + } + ++ WARN_ON(1); + btrfs_print_leaf(eb); + btrfs_err(eb->fs_info, + "eb %llu iref 0x%lx invalid extent inline ref type %d", + eb->start, (unsigned long)iref, type); +- WARN_ON(1); + + return BTRFS_REF_TYPE_INVALID; + } +@@ -1079,13 +1079,13 @@ static int lookup_extent_backref(struct btrfs_trans_handle *trans, + /* + * helper to update/remove inline back ref + */ +-static noinline_for_stack +-void update_inline_extent_backref(struct btrfs_path *path, ++static noinline_for_stack int update_inline_extent_backref(struct btrfs_path *path, + struct btrfs_extent_inline_ref *iref, + int refs_to_mod, + struct btrfs_delayed_extent_op *extent_op) + { + struct extent_buffer *leaf = path->nodes[0]; ++ struct btrfs_fs_info *fs_info = leaf->fs_info; + struct btrfs_extent_item *ei; + struct btrfs_extent_data_ref *dref = NULL; + struct btrfs_shared_data_ref *sref = NULL; +@@ -1098,18 +1098,33 @@ void update_inline_extent_backref(struct btrfs_path *path, + + ei = btrfs_item_ptr(leaf, path->slots[0], struct btrfs_extent_item); + refs = btrfs_extent_refs(leaf, ei); +- WARN_ON(refs_to_mod < 0 && refs + refs_to_mod <= 0); ++ if (unlikely(refs_to_mod < 0 && refs + refs_to_mod <= 0)) { ++ struct btrfs_key key; ++ u32 extent_size; ++ ++ btrfs_item_key_to_cpu(leaf, &key, path->slots[0]); ++ if (key.type == BTRFS_METADATA_ITEM_KEY) ++ extent_size = fs_info->nodesize; ++ else ++ extent_size = key.offset; ++ btrfs_print_leaf(leaf); ++ btrfs_err(fs_info, ++ "invalid refs_to_mod for extent %llu num_bytes %u, has %d expect >= -%llu", ++ key.objectid, extent_size, refs_to_mod, refs); ++ return -EUCLEAN; ++ } + refs += refs_to_mod; + btrfs_set_extent_refs(leaf, ei, refs); + if (extent_op) + __run_delayed_extent_op(extent_op, leaf, ei); + ++ type = btrfs_get_extent_inline_ref_type(leaf, iref, BTRFS_REF_TYPE_ANY); + /* +- * If type is invalid, we should have bailed out after +- * lookup_inline_extent_backref(). ++ * Function btrfs_get_extent_inline_ref_type() has already printed ++ * error messages. + */ +- type = btrfs_get_extent_inline_ref_type(leaf, iref, BTRFS_REF_TYPE_ANY); +- ASSERT(type != BTRFS_REF_TYPE_INVALID); ++ if (unlikely(type == BTRFS_REF_TYPE_INVALID)) ++ return -EUCLEAN; + + if (type == BTRFS_EXTENT_DATA_REF_KEY) { + dref = (struct btrfs_extent_data_ref *)(&iref->offset); +@@ -1119,10 +1134,43 @@ void update_inline_extent_backref(struct btrfs_path *path, + refs = btrfs_shared_data_ref_count(leaf, sref); + } else { + refs = 1; +- BUG_ON(refs_to_mod != -1); ++ /* ++ * For tree blocks we can only drop one ref for it, and tree ++ * blocks should not have refs > 1. ++ * ++ * Furthermore if we're inserting a new inline backref, we ++ * won't reach this path either. That would be ++ * setup_inline_extent_backref(). ++ */ ++ if (unlikely(refs_to_mod != -1)) { ++ struct btrfs_key key; ++ ++ btrfs_item_key_to_cpu(leaf, &key, path->slots[0]); ++ ++ btrfs_print_leaf(leaf); ++ btrfs_err(fs_info, ++ "invalid refs_to_mod for tree block %llu, has %d expect -1", ++ key.objectid, refs_to_mod); ++ return -EUCLEAN; ++ } + } + +- BUG_ON(refs_to_mod < 0 && refs < -refs_to_mod); ++ if (unlikely(refs_to_mod < 0 && refs < -refs_to_mod)) { ++ struct btrfs_key key; ++ u32 extent_size; ++ ++ btrfs_item_key_to_cpu(leaf, &key, path->slots[0]); ++ if (key.type == BTRFS_METADATA_ITEM_KEY) ++ extent_size = fs_info->nodesize; ++ else ++ extent_size = key.offset; ++ btrfs_print_leaf(leaf); ++ btrfs_err(fs_info, ++"invalid refs_to_mod for backref entry, iref %lu extent %llu num_bytes %u, has %d expect >= -%llu", ++ (unsigned long)iref, key.objectid, extent_size, ++ refs_to_mod, refs); ++ return -EUCLEAN; ++ } + refs += refs_to_mod; + + if (refs > 0) { +@@ -1142,6 +1190,7 @@ void update_inline_extent_backref(struct btrfs_path *path, + btrfs_truncate_item(path, item_size, 1); + } + btrfs_mark_buffer_dirty(leaf); ++ return 0; + } + + static noinline_for_stack +@@ -1170,7 +1219,7 @@ int insert_inline_extent_backref(struct btrfs_trans_handle *trans, + bytenr, num_bytes, root_objectid, path->slots[0]); + return -EUCLEAN; + } +- update_inline_extent_backref(path, iref, refs_to_add, extent_op); ++ ret = update_inline_extent_backref(path, iref, refs_to_add, extent_op); + } else if (ret == -ENOENT) { + setup_inline_extent_backref(trans->fs_info, path, iref, parent, + root_objectid, owner, offset, +@@ -1190,7 +1239,7 @@ static int remove_extent_backref(struct btrfs_trans_handle *trans, + + BUG_ON(!is_data && refs_to_drop != 1); + if (iref) +- update_inline_extent_backref(path, iref, -refs_to_drop, NULL); ++ ret = update_inline_extent_backref(path, iref, -refs_to_drop, NULL); + else if (is_data) + ret = remove_extent_data_ref(trans, root, path, refs_to_drop); + else +-- +2.40.1 + diff --git a/queue-6.5/btrfs-introduce-struct-to-consolidate-extent-buffer-.patch b/queue-6.5/btrfs-introduce-struct-to-consolidate-extent-buffer-.patch new file mode 100644 index 00000000000..94435c303b4 --- /dev/null +++ b/queue-6.5/btrfs-introduce-struct-to-consolidate-extent-buffer-.patch @@ -0,0 +1,111 @@ +From 3021d0d6437a85e3510bf2c79c3051a43b904019 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 01:12:31 +0900 +Subject: btrfs: introduce struct to consolidate extent buffer write context + +From: Naohiro Aota + +[ Upstream commit 861093eff4f01319edfc1d1ee276a7f2bf720f1d ] + +Introduce btrfs_eb_write_context to consolidate writeback_control and the +exntent buffer context. This will help adding a block group context as +well. + +While at it, move the eb context setting before +btrfs_check_meta_write_pointer(). We can set it here because we anyway need +to skip pages in the same eb if that eb is rejected by +btrfs_check_meta_write_pointer(). + +Suggested-by: Christoph Hellwig +Reviewed-by: Christoph Hellwig +Reviewed-by: Johannes Thumshirn +Signed-off-by: Naohiro Aota +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Stable-dep-of: 13bb483d32ab ("btrfs: zoned: activate metadata block group on write time") +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent_io.c | 14 +++++++------- + fs/btrfs/extent_io.h | 5 +++++ + 2 files changed, 12 insertions(+), 7 deletions(-) + +diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c +index 90ad3006ef3a7..b3bf2e2704888 100644 +--- a/fs/btrfs/extent_io.c ++++ b/fs/btrfs/extent_io.c +@@ -1877,9 +1877,9 @@ static int submit_eb_subpage(struct page *page, struct writeback_control *wbc) + * previous call. + * Return <0 for fatal error. + */ +-static int submit_eb_page(struct page *page, struct writeback_control *wbc, +- struct extent_buffer **eb_context) ++static int submit_eb_page(struct page *page, struct btrfs_eb_write_context *ctx) + { ++ struct writeback_control *wbc = ctx->wbc; + struct address_space *mapping = page->mapping; + struct btrfs_block_group *cache = NULL; + struct extent_buffer *eb; +@@ -1908,7 +1908,7 @@ static int submit_eb_page(struct page *page, struct writeback_control *wbc, + return 0; + } + +- if (eb == *eb_context) { ++ if (eb == ctx->eb) { + spin_unlock(&mapping->private_lock); + return 0; + } +@@ -1917,6 +1917,8 @@ static int submit_eb_page(struct page *page, struct writeback_control *wbc, + if (!ret) + return 0; + ++ ctx->eb = eb; ++ + if (!btrfs_check_meta_write_pointer(eb->fs_info, eb, &cache)) { + /* + * If for_sync, this hole will be filled with +@@ -1930,8 +1932,6 @@ static int submit_eb_page(struct page *page, struct writeback_control *wbc, + return ret; + } + +- *eb_context = eb; +- + if (!lock_extent_buffer_for_io(eb, wbc)) { + btrfs_revert_meta_write_pointer(cache, eb); + if (cache) +@@ -1954,7 +1954,7 @@ static int submit_eb_page(struct page *page, struct writeback_control *wbc, + int btree_write_cache_pages(struct address_space *mapping, + struct writeback_control *wbc) + { +- struct extent_buffer *eb_context = NULL; ++ struct btrfs_eb_write_context ctx = { .wbc = wbc }; + struct btrfs_fs_info *fs_info = BTRFS_I(mapping->host)->root->fs_info; + int ret = 0; + int done = 0; +@@ -1996,7 +1996,7 @@ int btree_write_cache_pages(struct address_space *mapping, + for (i = 0; i < nr_folios; i++) { + struct folio *folio = fbatch.folios[i]; + +- ret = submit_eb_page(&folio->page, wbc, &eb_context); ++ ret = submit_eb_page(&folio->page, &ctx); + if (ret == 0) + continue; + if (ret < 0) { +diff --git a/fs/btrfs/extent_io.h b/fs/btrfs/extent_io.h +index c5fae3a7d911b..ecc1660007c11 100644 +--- a/fs/btrfs/extent_io.h ++++ b/fs/btrfs/extent_io.h +@@ -94,6 +94,11 @@ struct extent_buffer { + #endif + }; + ++struct btrfs_eb_write_context { ++ struct writeback_control *wbc; ++ struct extent_buffer *eb; ++}; ++ + /* + * Get the correct offset inside the page of extent buffer. + * +-- +2.40.1 + diff --git a/queue-6.5/btrfs-output-extra-debug-info-if-we-failed-to-find-a.patch b/queue-6.5/btrfs-output-extra-debug-info-if-we-failed-to-find-a.patch new file mode 100644 index 00000000000..84f738dcec0 --- /dev/null +++ b/queue-6.5/btrfs-output-extra-debug-info-if-we-failed-to-find-a.patch @@ -0,0 +1,52 @@ +From bdb73444dfe4f9e25201328d85d0da9939ccce6a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 1 Aug 2023 19:02:28 +0800 +Subject: btrfs: output extra debug info if we failed to find an inline backref + +From: Qu Wenruo + +[ Upstream commit 7f72f50547b7af4ddf985b07fc56600a4deba281 ] + +[BUG] +Syzbot reported several warning triggered inside +lookup_inline_extent_backref(). + +[CAUSE] +As usual, the reproducer doesn't reliably trigger locally here, but at +least we know the WARN_ON() is triggered when an inline backref can not +be found, and it can only be triggered when @insert is true. (I.e. +inserting a new inline backref, which means the backref should already +exist) + +[ENHANCEMENT] +After the WARN_ON(), dump all the parameters and the extent tree +leaf to help debug. + +Link: https://syzkaller.appspot.com/bug?extid=d6f9ff86c1d804ba2bc6 +Signed-off-by: Qu Wenruo +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent-tree.c | 5 +++++ + 1 file changed, 5 insertions(+) + +diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c +index c47fbb99e99d9..0917c5f39e3d0 100644 +--- a/fs/btrfs/extent-tree.c ++++ b/fs/btrfs/extent-tree.c +@@ -869,6 +869,11 @@ int lookup_inline_extent_backref(struct btrfs_trans_handle *trans, + err = -ENOENT; + goto out; + } else if (WARN_ON(ret)) { ++ btrfs_print_leaf(path->nodes[0]); ++ btrfs_err(fs_info, ++"extent item not found for insert, bytenr %llu num_bytes %llu parent %llu root_objectid %llu owner %llu offset %llu", ++ bytenr, num_bytes, parent, root_objectid, owner, ++ offset); + err = -EIO; + goto out; + } +-- +2.40.1 + diff --git a/queue-6.5/btrfs-zoned-activate-metadata-block-group-on-write-t.patch b/queue-6.5/btrfs-zoned-activate-metadata-block-group-on-write-t.patch new file mode 100644 index 00000000000..302fab87b41 --- /dev/null +++ b/queue-6.5/btrfs-zoned-activate-metadata-block-group-on-write-t.patch @@ -0,0 +1,185 @@ +From e0f9d17b787d1fae190f05f699ba6a4907ac6b2e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 01:12:37 +0900 +Subject: btrfs: zoned: activate metadata block group on write time + +From: Naohiro Aota + +[ Upstream commit 13bb483d32abb6f8ebd40141d87eb68f11cc2dd2 ] + +In the current implementation, block groups are activated at reservation +time to ensure that all reserved bytes can be written to an active metadata +block group. However, this approach has proven to be less efficient, as it +activates block groups more frequently than necessary, putting pressure on +the active zone resource and leading to potential issues such as early +ENOSPC or hung_task. + +Another drawback of the current method is that it hampers metadata +over-commit, and necessitates additional flush operations and block group +allocations, resulting in decreased overall performance. + +To address these issues, this commit introduces a write-time activation of +metadata and system block group. This involves reserving at least one +active block group specifically for a metadata and system block group. + +Since metadata write-out is always allocated sequentially, when we need to +write to a non-active block group, we can wait for the ongoing IOs to +complete, activate a new block group, and then proceed with writing to the +new block group. + +Fixes: b09315139136 ("btrfs: zoned: activate metadata block group on flush_space") +CC: stable@vger.kernel.org # 6.1+ +Signed-off-by: Naohiro Aota +Signed-off-by: David Sterba +Signed-off-by: Sasha Levin +--- + fs/btrfs/block-group.c | 11 ++++++ + fs/btrfs/fs.h | 3 ++ + fs/btrfs/zoned.c | 81 ++++++++++++++++++++++++++++++++++++++++-- + 3 files changed, 93 insertions(+), 2 deletions(-) + +diff --git a/fs/btrfs/block-group.c b/fs/btrfs/block-group.c +index 82324c327a502..75385503a35b6 100644 +--- a/fs/btrfs/block-group.c ++++ b/fs/btrfs/block-group.c +@@ -4273,6 +4273,17 @@ int btrfs_free_block_groups(struct btrfs_fs_info *info) + struct btrfs_caching_control *caching_ctl; + struct rb_node *n; + ++ if (btrfs_is_zoned(info)) { ++ if (info->active_meta_bg) { ++ btrfs_put_block_group(info->active_meta_bg); ++ info->active_meta_bg = NULL; ++ } ++ if (info->active_system_bg) { ++ btrfs_put_block_group(info->active_system_bg); ++ info->active_system_bg = NULL; ++ } ++ } ++ + write_lock(&info->block_group_cache_lock); + while (!list_empty(&info->caching_block_groups)) { + caching_ctl = list_entry(info->caching_block_groups.next, +diff --git a/fs/btrfs/fs.h b/fs/btrfs/fs.h +index 203d2a2678287..1f2d331121064 100644 +--- a/fs/btrfs/fs.h ++++ b/fs/btrfs/fs.h +@@ -766,6 +766,9 @@ struct btrfs_fs_info { + u64 data_reloc_bg; + struct mutex zoned_data_reloc_io_lock; + ++ struct btrfs_block_group *active_meta_bg; ++ struct btrfs_block_group *active_system_bg; ++ + u64 nr_global_roots; + + spinlock_t zone_active_bgs_lock; +diff --git a/fs/btrfs/zoned.c b/fs/btrfs/zoned.c +index cc117283d0c88..f97e927499d7a 100644 +--- a/fs/btrfs/zoned.c ++++ b/fs/btrfs/zoned.c +@@ -65,6 +65,9 @@ + + #define SUPER_INFO_SECTORS ((u64)BTRFS_SUPER_INFO_SIZE >> SECTOR_SHIFT) + ++static void wait_eb_writebacks(struct btrfs_block_group *block_group); ++static int do_zone_finish(struct btrfs_block_group *block_group, bool fully_written); ++ + static inline bool sb_zone_is_full(const struct blk_zone *zone) + { + return (zone->cond == BLK_ZONE_COND_FULL) || +@@ -1758,6 +1761,62 @@ void btrfs_finish_ordered_zoned(struct btrfs_ordered_extent *ordered) + } + } + ++static bool check_bg_is_active(struct btrfs_eb_write_context *ctx, ++ struct btrfs_block_group **active_bg) ++{ ++ const struct writeback_control *wbc = ctx->wbc; ++ struct btrfs_block_group *block_group = ctx->zoned_bg; ++ struct btrfs_fs_info *fs_info = block_group->fs_info; ++ ++ if (test_bit(BLOCK_GROUP_FLAG_ZONE_IS_ACTIVE, &block_group->runtime_flags)) ++ return true; ++ ++ if (fs_info->treelog_bg == block_group->start) { ++ if (!btrfs_zone_activate(block_group)) { ++ int ret_fin = btrfs_zone_finish_one_bg(fs_info); ++ ++ if (ret_fin != 1 || !btrfs_zone_activate(block_group)) ++ return false; ++ } ++ } else if (*active_bg != block_group) { ++ struct btrfs_block_group *tgt = *active_bg; ++ ++ /* zoned_meta_io_lock protects fs_info->active_{meta,system}_bg. */ ++ lockdep_assert_held(&fs_info->zoned_meta_io_lock); ++ ++ if (tgt) { ++ /* ++ * If there is an unsent IO left in the allocated area, ++ * we cannot wait for them as it may cause a deadlock. ++ */ ++ if (tgt->meta_write_pointer < tgt->start + tgt->alloc_offset) { ++ if (wbc->sync_mode == WB_SYNC_NONE || ++ (wbc->sync_mode == WB_SYNC_ALL && !wbc->for_sync)) ++ return false; ++ } ++ ++ /* Pivot active metadata/system block group. */ ++ btrfs_zoned_meta_io_unlock(fs_info); ++ wait_eb_writebacks(tgt); ++ do_zone_finish(tgt, true); ++ btrfs_zoned_meta_io_lock(fs_info); ++ if (*active_bg == tgt) { ++ btrfs_put_block_group(tgt); ++ *active_bg = NULL; ++ } ++ } ++ if (!btrfs_zone_activate(block_group)) ++ return false; ++ if (*active_bg != block_group) { ++ ASSERT(*active_bg == NULL); ++ *active_bg = block_group; ++ btrfs_get_block_group(block_group); ++ } ++ } ++ ++ return true; ++} ++ + /* + * Check if @ctx->eb is aligned to the write pointer. + * +@@ -1792,8 +1851,26 @@ int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, + ctx->zoned_bg = block_group; + } + +- if (block_group->meta_write_pointer == eb->start) +- return 0; ++ if (block_group->meta_write_pointer == eb->start) { ++ struct btrfs_block_group **tgt; ++ ++ if (!test_bit(BTRFS_FS_ACTIVE_ZONE_TRACKING, &fs_info->flags)) ++ return 0; ++ ++ if (block_group->flags & BTRFS_BLOCK_GROUP_SYSTEM) ++ tgt = &fs_info->active_system_bg; ++ else ++ tgt = &fs_info->active_meta_bg; ++ if (check_bg_is_active(ctx, tgt)) ++ return 0; ++ } ++ ++ /* ++ * Since we may release fs_info->zoned_meta_io_lock, someone can already ++ * start writing this eb. In that case, we can just bail out. ++ */ ++ if (block_group->meta_write_pointer > eb->start) ++ return -EBUSY; + + /* If for_sync, this hole will be filled with trasnsaction commit. */ + if (wbc->sync_mode == WB_SYNC_ALL && !wbc->for_sync) +-- +2.40.1 + diff --git a/queue-6.5/btrfs-zoned-defer-advancing-meta-write-pointer.patch b/queue-6.5/btrfs-zoned-defer-advancing-meta-write-pointer.patch new file mode 100644 index 00000000000..11efd186560 --- /dev/null +++ b/queue-6.5/btrfs-zoned-defer-advancing-meta-write-pointer.patch @@ -0,0 +1,122 @@ +From 6788945b73431a1e3dc65d7ae4e2e75614827987 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 01:12:34 +0900 +Subject: btrfs: zoned: defer advancing meta write pointer + +From: Naohiro Aota + +[ Upstream commit 0356ad41e0ddb8cf0ea4d68820c92598413e445b ] + +We currently advance the meta_write_pointer in +btrfs_check_meta_write_pointer(). That makes it necessary to revert it +when locking the buffer failed. Instead, we can advance it just before +sending the buffer. + +Also, this is necessary for the following commit. In the commit, it needs +to release the zoned_meta_io_lock to allow IOs to come in and wait for them +to fill the currently active block group. If we advance the +meta_write_pointer before locking the extent buffer, the following extent +buffer can pass the meta_write_pointer check, resulting in an unaligned +write failure. + +Advancing the pointer is still thread-safe as the extent buffer is locked. + +Reviewed-by: Christoph Hellwig +Reviewed-by: Johannes Thumshirn +Signed-off-by: Naohiro Aota +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Stable-dep-of: 13bb483d32ab ("btrfs: zoned: activate metadata block group on write time") +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent_io.c | 7 +++---- + fs/btrfs/zoned.c | 15 +-------------- + fs/btrfs/zoned.h | 8 -------- + 3 files changed, 4 insertions(+), 26 deletions(-) + +diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c +index d4bac66cee533..2ebc982e8eccb 100644 +--- a/fs/btrfs/extent_io.c ++++ b/fs/btrfs/extent_io.c +@@ -1927,15 +1927,14 @@ static int submit_eb_page(struct page *page, struct btrfs_eb_write_context *ctx) + } + + if (!lock_extent_buffer_for_io(eb, wbc)) { +- btrfs_revert_meta_write_pointer(ctx->zoned_bg, eb); + free_extent_buffer(eb); + return 0; + } ++ /* Implies write in zoned mode. */ + if (ctx->zoned_bg) { +- /* +- * Implies write in zoned mode. Mark the last eb in a block group. +- */ ++ /* Mark the last eb in the block group. */ + btrfs_schedule_zone_finish_bg(ctx->zoned_bg, eb); ++ ctx->zoned_bg->meta_write_pointer += eb->len; + } + write_one_eb(eb, wbc); + free_extent_buffer(eb); +diff --git a/fs/btrfs/zoned.c b/fs/btrfs/zoned.c +index 6e406f1b0d21e..cc117283d0c88 100644 +--- a/fs/btrfs/zoned.c ++++ b/fs/btrfs/zoned.c +@@ -1792,11 +1792,8 @@ int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, + ctx->zoned_bg = block_group; + } + +- if (block_group->meta_write_pointer == eb->start) { +- block_group->meta_write_pointer = eb->start + eb->len; +- ++ if (block_group->meta_write_pointer == eb->start) + return 0; +- } + + /* If for_sync, this hole will be filled with trasnsaction commit. */ + if (wbc->sync_mode == WB_SYNC_ALL && !wbc->for_sync) +@@ -1804,16 +1801,6 @@ int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, + return -EBUSY; + } + +-void btrfs_revert_meta_write_pointer(struct btrfs_block_group *cache, +- struct extent_buffer *eb) +-{ +- if (!btrfs_is_zoned(eb->fs_info) || !cache) +- return; +- +- ASSERT(cache->meta_write_pointer == eb->start + eb->len); +- cache->meta_write_pointer = eb->start; +-} +- + int btrfs_zoned_issue_zeroout(struct btrfs_device *device, u64 physical, u64 length) + { + if (!btrfs_dev_is_sequential(device, physical)) +diff --git a/fs/btrfs/zoned.h b/fs/btrfs/zoned.h +index c0859d8be1520..74ec37a25808a 100644 +--- a/fs/btrfs/zoned.h ++++ b/fs/btrfs/zoned.h +@@ -60,8 +60,6 @@ bool btrfs_use_zone_append(struct btrfs_bio *bbio); + void btrfs_record_physical_zoned(struct btrfs_bio *bbio); + int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, + struct btrfs_eb_write_context *ctx); +-void btrfs_revert_meta_write_pointer(struct btrfs_block_group *cache, +- struct extent_buffer *eb); + int btrfs_zoned_issue_zeroout(struct btrfs_device *device, u64 physical, u64 length); + int btrfs_sync_zone_write_pointer(struct btrfs_device *tgt_dev, u64 logical, + u64 physical_start, u64 physical_pos); +@@ -194,12 +192,6 @@ static inline int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, + return 0; + } + +-static inline void btrfs_revert_meta_write_pointer( +- struct btrfs_block_group *cache, +- struct extent_buffer *eb) +-{ +-} +- + static inline int btrfs_zoned_issue_zeroout(struct btrfs_device *device, + u64 physical, u64 length) + { +-- +2.40.1 + diff --git a/queue-6.5/btrfs-zoned-introduce-block-group-context-to-btrfs_e.patch b/queue-6.5/btrfs-zoned-introduce-block-group-context-to-btrfs_e.patch new file mode 100644 index 00000000000..8f7ec0486e7 --- /dev/null +++ b/queue-6.5/btrfs-zoned-introduce-block-group-context-to-btrfs_e.patch @@ -0,0 +1,182 @@ +From 3f40bc328cc1bf4e100d886abf45c56868f6f7da Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 01:12:32 +0900 +Subject: btrfs: zoned: introduce block group context to btrfs_eb_write_context + +From: Naohiro Aota + +[ Upstream commit 7db94301a980c9da4168ac7ce61e7bde297306ba ] + +For metadata write out on the zoned mode, we call +btrfs_check_meta_write_pointer() to check if an extent buffer to be written +is aligned to the write pointer. + +We look up a block group containing the extent buffer for every extent +buffer, which takes unnecessary effort as the writing extent buffers are +mostly contiguous. + +Introduce "zoned_bg" to cache the block group working on. Also, while +at it, rename "cache" to "block_group". + +Reviewed-by: Christoph Hellwig +Reviewed-by: Johannes Thumshirn +Signed-off-by: Naohiro Aota +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Stable-dep-of: 13bb483d32ab ("btrfs: zoned: activate metadata block group on write time") +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent_io.c | 15 +++++++-------- + fs/btrfs/extent_io.h | 2 ++ + fs/btrfs/zoned.c | 35 ++++++++++++++++++++--------------- + fs/btrfs/zoned.h | 6 ++---- + 4 files changed, 31 insertions(+), 27 deletions(-) + +diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c +index b3bf2e2704888..c2be1561a52cb 100644 +--- a/fs/btrfs/extent_io.c ++++ b/fs/btrfs/extent_io.c +@@ -1881,7 +1881,6 @@ static int submit_eb_page(struct page *page, struct btrfs_eb_write_context *ctx) + { + struct writeback_control *wbc = ctx->wbc; + struct address_space *mapping = page->mapping; +- struct btrfs_block_group *cache = NULL; + struct extent_buffer *eb; + int ret; + +@@ -1919,7 +1918,7 @@ static int submit_eb_page(struct page *page, struct btrfs_eb_write_context *ctx) + + ctx->eb = eb; + +- if (!btrfs_check_meta_write_pointer(eb->fs_info, eb, &cache)) { ++ if (!btrfs_check_meta_write_pointer(eb->fs_info, ctx)) { + /* + * If for_sync, this hole will be filled with + * trasnsaction commit. +@@ -1933,18 +1932,15 @@ static int submit_eb_page(struct page *page, struct btrfs_eb_write_context *ctx) + } + + if (!lock_extent_buffer_for_io(eb, wbc)) { +- btrfs_revert_meta_write_pointer(cache, eb); +- if (cache) +- btrfs_put_block_group(cache); ++ btrfs_revert_meta_write_pointer(ctx->zoned_bg, eb); + free_extent_buffer(eb); + return 0; + } +- if (cache) { ++ if (ctx->zoned_bg) { + /* + * Implies write in zoned mode. Mark the last eb in a block group. + */ +- btrfs_schedule_zone_finish_bg(cache, eb); +- btrfs_put_block_group(cache); ++ btrfs_schedule_zone_finish_bg(ctx->zoned_bg, eb); + } + write_one_eb(eb, wbc); + free_extent_buffer(eb); +@@ -2057,6 +2053,9 @@ int btree_write_cache_pages(struct address_space *mapping, + ret = 0; + if (!ret && BTRFS_FS_ERROR(fs_info)) + ret = -EROFS; ++ ++ if (ctx.zoned_bg) ++ btrfs_put_block_group(ctx.zoned_bg); + btrfs_zoned_meta_io_unlock(fs_info); + return ret; + } +diff --git a/fs/btrfs/extent_io.h b/fs/btrfs/extent_io.h +index ecc1660007c11..f61b7896320a1 100644 +--- a/fs/btrfs/extent_io.h ++++ b/fs/btrfs/extent_io.h +@@ -97,6 +97,8 @@ struct extent_buffer { + struct btrfs_eb_write_context { + struct writeback_control *wbc; + struct extent_buffer *eb; ++ /* Block group @eb resides in. Only used for zoned mode. */ ++ struct btrfs_block_group *zoned_bg; + }; + + /* +diff --git a/fs/btrfs/zoned.c b/fs/btrfs/zoned.c +index d9e6df2da272c..92f11176216b5 100644 +--- a/fs/btrfs/zoned.c ++++ b/fs/btrfs/zoned.c +@@ -1759,30 +1759,35 @@ void btrfs_finish_ordered_zoned(struct btrfs_ordered_extent *ordered) + } + + bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, +- struct extent_buffer *eb, +- struct btrfs_block_group **cache_ret) ++ struct btrfs_eb_write_context *ctx) + { +- struct btrfs_block_group *cache; +- bool ret = true; ++ const struct extent_buffer *eb = ctx->eb; ++ struct btrfs_block_group *block_group = ctx->zoned_bg; + + if (!btrfs_is_zoned(fs_info)) + return true; + +- cache = btrfs_lookup_block_group(fs_info, eb->start); +- if (!cache) +- return true; ++ if (block_group) { ++ if (block_group->start > eb->start || ++ block_group->start + block_group->length <= eb->start) { ++ btrfs_put_block_group(block_group); ++ block_group = NULL; ++ ctx->zoned_bg = NULL; ++ } ++ } + +- if (cache->meta_write_pointer != eb->start) { +- btrfs_put_block_group(cache); +- cache = NULL; +- ret = false; +- } else { +- cache->meta_write_pointer = eb->start + eb->len; ++ if (!block_group) { ++ block_group = btrfs_lookup_block_group(fs_info, eb->start); ++ if (!block_group) ++ return true; ++ ctx->zoned_bg = block_group; + } + +- *cache_ret = cache; ++ if (block_group->meta_write_pointer != eb->start) ++ return false; ++ block_group->meta_write_pointer = eb->start + eb->len; + +- return ret; ++ return true; + } + + void btrfs_revert_meta_write_pointer(struct btrfs_block_group *cache, +diff --git a/fs/btrfs/zoned.h b/fs/btrfs/zoned.h +index 27322b926038c..49d5bd87245c5 100644 +--- a/fs/btrfs/zoned.h ++++ b/fs/btrfs/zoned.h +@@ -59,8 +59,7 @@ void btrfs_redirty_list_add(struct btrfs_transaction *trans, + bool btrfs_use_zone_append(struct btrfs_bio *bbio); + void btrfs_record_physical_zoned(struct btrfs_bio *bbio); + bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, +- struct extent_buffer *eb, +- struct btrfs_block_group **cache_ret); ++ struct btrfs_eb_write_context *ctx); + void btrfs_revert_meta_write_pointer(struct btrfs_block_group *cache, + struct extent_buffer *eb); + int btrfs_zoned_issue_zeroout(struct btrfs_device *device, u64 physical, u64 length); +@@ -190,8 +189,7 @@ static inline void btrfs_record_physical_zoned(struct btrfs_bio *bbio) + } + + static inline bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, +- struct extent_buffer *eb, +- struct btrfs_block_group **cache_ret) ++ struct btrfs_eb_write_context *ctx) + { + return true; + } +-- +2.40.1 + diff --git a/queue-6.5/btrfs-zoned-return-int-from-btrfs_check_meta_write_p.patch b/queue-6.5/btrfs-zoned-return-int-from-btrfs_check_meta_write_p.patch new file mode 100644 index 00000000000..cec846dbb84 --- /dev/null +++ b/queue-6.5/btrfs-zoned-return-int-from-btrfs_check_meta_write_p.patch @@ -0,0 +1,137 @@ +From e1ca319bf461817cea6dded666c0f59d65d20d01 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 01:12:33 +0900 +Subject: btrfs: zoned: return int from btrfs_check_meta_write_pointer + +From: Naohiro Aota + +[ Upstream commit 2ad8c0510a965113404cfe670b41ddc34fb66100 ] + +Now that we have writeback_control passed to +btrfs_check_meta_write_pointer(), we can move the wbc condition in +submit_eb_page() to btrfs_check_meta_write_pointer() and return int. + +Reviewed-by: Christoph Hellwig +Reviewed-by: Johannes Thumshirn +Signed-off-by: Naohiro Aota +Reviewed-by: David Sterba +Signed-off-by: David Sterba +Stable-dep-of: 13bb483d32ab ("btrfs: zoned: activate metadata block group on write time") +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent_io.c | 11 +++-------- + fs/btrfs/zoned.c | 30 ++++++++++++++++++++++-------- + fs/btrfs/zoned.h | 10 +++++----- + 3 files changed, 30 insertions(+), 21 deletions(-) + +diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c +index c2be1561a52cb..d4bac66cee533 100644 +--- a/fs/btrfs/extent_io.c ++++ b/fs/btrfs/extent_io.c +@@ -1918,14 +1918,9 @@ static int submit_eb_page(struct page *page, struct btrfs_eb_write_context *ctx) + + ctx->eb = eb; + +- if (!btrfs_check_meta_write_pointer(eb->fs_info, ctx)) { +- /* +- * If for_sync, this hole will be filled with +- * trasnsaction commit. +- */ +- if (wbc->sync_mode == WB_SYNC_ALL && !wbc->for_sync) +- ret = -EAGAIN; +- else ++ ret = btrfs_check_meta_write_pointer(eb->fs_info, ctx); ++ if (ret) { ++ if (ret == -EBUSY) + ret = 0; + free_extent_buffer(eb); + return ret; +diff --git a/fs/btrfs/zoned.c b/fs/btrfs/zoned.c +index 92f11176216b5..6e406f1b0d21e 100644 +--- a/fs/btrfs/zoned.c ++++ b/fs/btrfs/zoned.c +@@ -1758,14 +1758,23 @@ void btrfs_finish_ordered_zoned(struct btrfs_ordered_extent *ordered) + } + } + +-bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, +- struct btrfs_eb_write_context *ctx) ++/* ++ * Check if @ctx->eb is aligned to the write pointer. ++ * ++ * Return: ++ * 0: @ctx->eb is at the write pointer. You can write it. ++ * -EAGAIN: There is a hole. The caller should handle the case. ++ * -EBUSY: There is a hole, but the caller can just bail out. ++ */ ++int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, ++ struct btrfs_eb_write_context *ctx) + { ++ const struct writeback_control *wbc = ctx->wbc; + const struct extent_buffer *eb = ctx->eb; + struct btrfs_block_group *block_group = ctx->zoned_bg; + + if (!btrfs_is_zoned(fs_info)) +- return true; ++ return 0; + + if (block_group) { + if (block_group->start > eb->start || +@@ -1779,15 +1788,20 @@ bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, + if (!block_group) { + block_group = btrfs_lookup_block_group(fs_info, eb->start); + if (!block_group) +- return true; ++ return 0; + ctx->zoned_bg = block_group; + } + +- if (block_group->meta_write_pointer != eb->start) +- return false; +- block_group->meta_write_pointer = eb->start + eb->len; ++ if (block_group->meta_write_pointer == eb->start) { ++ block_group->meta_write_pointer = eb->start + eb->len; + +- return true; ++ return 0; ++ } ++ ++ /* If for_sync, this hole will be filled with trasnsaction commit. */ ++ if (wbc->sync_mode == WB_SYNC_ALL && !wbc->for_sync) ++ return -EAGAIN; ++ return -EBUSY; + } + + void btrfs_revert_meta_write_pointer(struct btrfs_block_group *cache, +diff --git a/fs/btrfs/zoned.h b/fs/btrfs/zoned.h +index 49d5bd87245c5..c0859d8be1520 100644 +--- a/fs/btrfs/zoned.h ++++ b/fs/btrfs/zoned.h +@@ -58,8 +58,8 @@ void btrfs_redirty_list_add(struct btrfs_transaction *trans, + struct extent_buffer *eb); + bool btrfs_use_zone_append(struct btrfs_bio *bbio); + void btrfs_record_physical_zoned(struct btrfs_bio *bbio); +-bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, +- struct btrfs_eb_write_context *ctx); ++int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, ++ struct btrfs_eb_write_context *ctx); + void btrfs_revert_meta_write_pointer(struct btrfs_block_group *cache, + struct extent_buffer *eb); + int btrfs_zoned_issue_zeroout(struct btrfs_device *device, u64 physical, u64 length); +@@ -188,10 +188,10 @@ static inline void btrfs_record_physical_zoned(struct btrfs_bio *bbio) + { + } + +-static inline bool btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, +- struct btrfs_eb_write_context *ctx) ++static inline int btrfs_check_meta_write_pointer(struct btrfs_fs_info *fs_info, ++ struct btrfs_eb_write_context *ctx) + { +- return true; ++ return 0; + } + + static inline void btrfs_revert_meta_write_pointer( +-- +2.40.1 + diff --git a/queue-6.5/bus-ti-sysc-configure-uart-quirks-for-k3-soc.patch b/queue-6.5/bus-ti-sysc-configure-uart-quirks-for-k3-soc.patch new file mode 100644 index 00000000000..8bf690b063d --- /dev/null +++ b/queue-6.5/bus-ti-sysc-configure-uart-quirks-for-k3-soc.patch @@ -0,0 +1,39 @@ +From 789ef46a286770e7722ad6af3745b4aa3cc3af0b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 4 Aug 2023 13:38:01 +0300 +Subject: bus: ti-sysc: Configure uart quirks for k3 SoC + +From: Tony Lindgren + +[ Upstream commit 03a711d3cb83692733f865312f49e665c49de6de ] + +Enable the uart quirks similar to the earlier SoCs. Let's assume we are +likely going to need a k3 specific quirk mask separate from the earlier +SoCs, so let's not start changing the revision register mask at this point. + +Note that SYSC_QUIRK_LEGACY_IDLE will be needed until we can remove the +need for pm_runtime_irq_safe() from 8250_omap driver. + +Reviewed-by: Nishanth Menon +Signed-off-by: Tony Lindgren +Signed-off-by: Sasha Levin +--- + drivers/bus/ti-sysc.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/drivers/bus/ti-sysc.c b/drivers/bus/ti-sysc.c +index c95fa4335fee2..9766dbf607f97 100644 +--- a/drivers/bus/ti-sysc.c ++++ b/drivers/bus/ti-sysc.c +@@ -1525,6 +1525,8 @@ static const struct sysc_revision_quirk sysc_revision_quirks[] = { + SYSC_QUIRK_SWSUP_SIDLE | SYSC_QUIRK_LEGACY_IDLE), + SYSC_QUIRK("uart", 0, 0x50, 0x54, 0x58, 0x47422e03, 0xffffffff, + SYSC_QUIRK_SWSUP_SIDLE | SYSC_QUIRK_LEGACY_IDLE), ++ SYSC_QUIRK("uart", 0, 0x50, 0x54, 0x58, 0x47424e03, 0xffffffff, ++ SYSC_QUIRK_SWSUP_SIDLE | SYSC_QUIRK_LEGACY_IDLE), + + /* Quirks that need to be set based on the module address */ + SYSC_QUIRK("mcpdm", 0x40132000, 0, 0x10, -ENODEV, 0x50000800, 0xffffffff, +-- +2.40.1 + diff --git a/queue-6.5/can-sun4i_can-add-acceptance-register-quirk.patch b/queue-6.5/can-sun4i_can-add-acceptance-register-quirk.patch new file mode 100644 index 00000000000..35b410aa2c2 --- /dev/null +++ b/queue-6.5/can-sun4i_can-add-acceptance-register-quirk.patch @@ -0,0 +1,80 @@ +From a0394423eb7c8129b231e15bc889b6a641f0ccc2 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 22 Jul 2023 08:15:52 +1000 +Subject: can: sun4i_can: Add acceptance register quirk + +From: John Watts + +[ Upstream commit 8cda0c6dfd42ee6f2586e7dffb553aaf1fcb62ca ] + +The Allwinner D1's CAN controllers have the ACPC and ACPM registers +moved down. Compensate for this by adding an offset quirk for the +acceptance registers. + +Signed-off-by: John Watts +Link: https://lore.kernel.org/all/20230721221552.1973203-5-contact@jookia.org +Signed-off-by: Marc Kleine-Budde +Signed-off-by: Sasha Levin +--- + drivers/net/can/sun4i_can.c | 10 ++++++++-- + 1 file changed, 8 insertions(+), 2 deletions(-) + +diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c +index 0827830bbf28c..1f90fe6dbb8bb 100644 +--- a/drivers/net/can/sun4i_can.c ++++ b/drivers/net/can/sun4i_can.c +@@ -205,9 +205,11 @@ + * struct sun4ican_quirks - Differences between SoC variants. + * + * @has_reset: SoC needs reset deasserted. ++ * @acp_offset: Offset of ACPC and ACPM registers + */ + struct sun4ican_quirks { + bool has_reset; ++ int acp_offset; + }; + + struct sun4ican_priv { +@@ -216,6 +218,7 @@ struct sun4ican_priv { + struct clk *clk; + struct reset_control *reset; + spinlock_t cmdreg_lock; /* lock for concurrent cmd register writes */ ++ int acp_offset; + }; + + static const struct can_bittiming_const sun4ican_bittiming_const = { +@@ -338,8 +341,8 @@ static int sun4i_can_start(struct net_device *dev) + } + + /* set filters - we accept all */ +- writel(0x00000000, priv->base + SUN4I_REG_ACPC_ADDR); +- writel(0xFFFFFFFF, priv->base + SUN4I_REG_ACPM_ADDR); ++ writel(0x00000000, priv->base + SUN4I_REG_ACPC_ADDR + priv->acp_offset); ++ writel(0xFFFFFFFF, priv->base + SUN4I_REG_ACPM_ADDR + priv->acp_offset); + + /* clear error counters and error code capture */ + writel(0, priv->base + SUN4I_REG_ERRC_ADDR); +@@ -768,10 +771,12 @@ static const struct ethtool_ops sun4ican_ethtool_ops = { + + static const struct sun4ican_quirks sun4ican_quirks_a10 = { + .has_reset = false, ++ .acp_offset = 0, + }; + + static const struct sun4ican_quirks sun4ican_quirks_r40 = { + .has_reset = true, ++ .acp_offset = 0, + }; + + static const struct of_device_id sun4ican_of_match[] = { +@@ -870,6 +875,7 @@ static int sun4ican_probe(struct platform_device *pdev) + priv->base = addr; + priv->clk = clk; + priv->reset = reset; ++ priv->acp_offset = quirks->acp_offset; + spin_lock_init(&priv->cmdreg_lock); + + platform_set_drvdata(pdev, dev); +-- +2.40.1 + diff --git a/queue-6.5/can-sun4i_can-add-support-for-the-allwinner-d1.patch b/queue-6.5/can-sun4i_can-add-support-for-the-allwinner-d1.patch new file mode 100644 index 00000000000..be8394f62c0 --- /dev/null +++ b/queue-6.5/can-sun4i_can-add-support-for-the-allwinner-d1.patch @@ -0,0 +1,83 @@ +From 4bcd425e7d66fddd134b66f7c2f6225cf7ab5e5c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 22 Jul 2023 08:15:53 +1000 +Subject: can: sun4i_can: Add support for the Allwinner D1 + +From: John Watts + +[ Upstream commit 8abb95250ae6af2d51993da8fcae18da2ce24cc4 ] + +The controllers present in the D1 are extremely similar to the R40 +and require the same reset quirks, but An extra quirk is needed to support +receiving packets. + +Signed-off-by: John Watts +Link: https://lore.kernel.org/all/20230721221552.1973203-6-contact@jookia.org +Signed-off-by: Marc Kleine-Budde +Signed-off-by: Sasha Levin +--- + drivers/net/can/Kconfig | 4 ++-- + drivers/net/can/sun4i_can.c | 12 +++++++++++- + 2 files changed, 13 insertions(+), 3 deletions(-) + +diff --git a/drivers/net/can/Kconfig b/drivers/net/can/Kconfig +index a5c5036dfb943..e626de33e735d 100644 +--- a/drivers/net/can/Kconfig ++++ b/drivers/net/can/Kconfig +@@ -185,10 +185,10 @@ config CAN_SLCAN + + config CAN_SUN4I + tristate "Allwinner A10 CAN controller" +- depends on MACH_SUN4I || MACH_SUN7I || COMPILE_TEST ++ depends on MACH_SUN4I || MACH_SUN7I || RISCV || COMPILE_TEST + help + Say Y here if you want to use CAN controller found on Allwinner +- A10/A20 SoCs. ++ A10/A20/D1 SoCs. + + To compile this driver as a module, choose M here: the module will + be called sun4i_can. +diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c +index 1f90fe6dbb8bb..c508a328e38d4 100644 +--- a/drivers/net/can/sun4i_can.c ++++ b/drivers/net/can/sun4i_can.c +@@ -91,6 +91,8 @@ + #define SUN4I_REG_BUF12_ADDR 0x0070 /* CAN Tx/Rx Buffer 12 */ + #define SUN4I_REG_ACPC_ADDR 0x0040 /* CAN Acceptance Code 0 */ + #define SUN4I_REG_ACPM_ADDR 0x0044 /* CAN Acceptance Mask 0 */ ++#define SUN4I_REG_ACPC_ADDR_D1 0x0028 /* CAN Acceptance Code 0 on the D1 */ ++#define SUN4I_REG_ACPM_ADDR_D1 0x002C /* CAN Acceptance Mask 0 on the D1 */ + #define SUN4I_REG_RBUF_RBACK_START_ADDR 0x0180 /* CAN transmit buffer start */ + #define SUN4I_REG_RBUF_RBACK_END_ADDR 0x01b0 /* CAN transmit buffer end */ + +@@ -779,6 +781,11 @@ static const struct sun4ican_quirks sun4ican_quirks_r40 = { + .acp_offset = 0, + }; + ++static const struct sun4ican_quirks sun4ican_quirks_d1 = { ++ .has_reset = true, ++ .acp_offset = (SUN4I_REG_ACPC_ADDR_D1 - SUN4I_REG_ACPC_ADDR), ++}; ++ + static const struct of_device_id sun4ican_of_match[] = { + { + .compatible = "allwinner,sun4i-a10-can", +@@ -789,6 +796,9 @@ static const struct of_device_id sun4ican_of_match[] = { + }, { + .compatible = "allwinner,sun8i-r40-can", + .data = &sun4ican_quirks_r40 ++ }, { ++ .compatible = "allwinner,sun20i-d1-can", ++ .data = &sun4ican_quirks_d1 + }, { + /* sentinel */ + }, +@@ -913,4 +923,4 @@ module_platform_driver(sun4i_can_driver); + MODULE_AUTHOR("Peter Chen "); + MODULE_AUTHOR("Gerhard Bertelsmann "); + MODULE_LICENSE("Dual BSD/GPL"); +-MODULE_DESCRIPTION("CAN driver for Allwinner SoCs (A10/A20)"); ++MODULE_DESCRIPTION("CAN driver for Allwinner SoCs (A10/A20/D1)"); +-- +2.40.1 + diff --git a/queue-6.5/crypto-lib-mpi-avoid-null-pointer-deref-in-mpi_cmp_u.patch b/queue-6.5/crypto-lib-mpi-avoid-null-pointer-deref-in-mpi_cmp_u.patch new file mode 100644 index 00000000000..0c8c1c5faff --- /dev/null +++ b/queue-6.5/crypto-lib-mpi-avoid-null-pointer-deref-in-mpi_cmp_u.patch @@ -0,0 +1,45 @@ +From cf50f7682532c293a2d4898c72221ec0b1cec56a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 4 Aug 2023 09:32:18 +0000 +Subject: crypto: lib/mpi - avoid null pointer deref in mpi_cmp_ui() + +From: Mark O'Donovan + +[ Upstream commit 9e47a758b70167c9301d2b44d2569f86c7796f2d ] + +During NVMeTCP Authentication a controller can trigger a kernel +oops by specifying the 8192 bit Diffie Hellman group and passing +a correctly sized, but zeroed Diffie Hellamn value. +mpi_cmp_ui() was detecting this if the second parameter was 0, +but 1 is passed from dh_is_pubkey_valid(). This causes the null +pointer u->d to be dereferenced towards the end of mpi_cmp_ui() + +Signed-off-by: Mark O'Donovan +Signed-off-by: Herbert Xu +Signed-off-by: Sasha Levin +--- + lib/mpi/mpi-cmp.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +diff --git a/lib/mpi/mpi-cmp.c b/lib/mpi/mpi-cmp.c +index c4cfa3ff05818..0835b6213235e 100644 +--- a/lib/mpi/mpi-cmp.c ++++ b/lib/mpi/mpi-cmp.c +@@ -25,8 +25,12 @@ int mpi_cmp_ui(MPI u, unsigned long v) + mpi_limb_t limb = v; + + mpi_normalize(u); +- if (!u->nlimbs && !limb) +- return 0; ++ if (u->nlimbs == 0) { ++ if (v == 0) ++ return 0; ++ else ++ return -1; ++ } + if (u->sign) + return -1; + if (u->nlimbs > 1) +-- +2.40.1 + diff --git a/queue-6.5/crypto-lrw-xts-replace-strlcpy-with-strscpy.patch b/queue-6.5/crypto-lrw-xts-replace-strlcpy-with-strscpy.patch new file mode 100644 index 00000000000..3028bf30ee1 --- /dev/null +++ b/queue-6.5/crypto-lrw-xts-replace-strlcpy-with-strscpy.patch @@ -0,0 +1,70 @@ +From 8f28a0d00ecaac41e3ac103e315f77ad187f8999 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 20 Jun 2023 20:08:32 +0000 +Subject: crypto: lrw,xts - Replace strlcpy with strscpy + +From: Azeem Shaikh + +[ Upstream commit babb80b3ecc6f40c962e13c654ebcd27f25ee327 ] + +strlcpy() reads the entire source buffer first. +This read may exceed the destination size limit. +This is both inefficient and can lead to linear read +overflows if a source string is not NUL-terminated [1]. +In an effort to remove strlcpy() completely [2], replace +strlcpy() here with strscpy(). + +Direct replacement is safe here since return value of -errno +is used to check for truncation instead of sizeof(dest). + +[1] https://www.kernel.org/doc/html/latest/process/deprecated.html#strlcpy +[2] https://github.com/KSPP/linux/issues/89 + +Signed-off-by: Azeem Shaikh +Reviewed-by: Kees Cook +Signed-off-by: Herbert Xu +Signed-off-by: Sasha Levin +--- + crypto/lrw.c | 6 +++--- + crypto/xts.c | 6 +++--- + 2 files changed, 6 insertions(+), 6 deletions(-) + +diff --git a/crypto/lrw.c b/crypto/lrw.c +index 1b0f76ba3eb5e..59260aefed280 100644 +--- a/crypto/lrw.c ++++ b/crypto/lrw.c +@@ -357,10 +357,10 @@ static int lrw_create(struct crypto_template *tmpl, struct rtattr **tb) + * cipher name. + */ + if (!strncmp(cipher_name, "ecb(", 4)) { +- unsigned len; ++ int len; + +- len = strlcpy(ecb_name, cipher_name + 4, sizeof(ecb_name)); +- if (len < 2 || len >= sizeof(ecb_name)) ++ len = strscpy(ecb_name, cipher_name + 4, sizeof(ecb_name)); ++ if (len < 2) + goto err_free_inst; + + if (ecb_name[len - 1] != ')') +diff --git a/crypto/xts.c b/crypto/xts.c +index 09be909a6a1aa..548b302c6c6a0 100644 +--- a/crypto/xts.c ++++ b/crypto/xts.c +@@ -396,10 +396,10 @@ static int xts_create(struct crypto_template *tmpl, struct rtattr **tb) + * cipher name. + */ + if (!strncmp(cipher_name, "ecb(", 4)) { +- unsigned len; ++ int len; + +- len = strlcpy(ctx->name, cipher_name + 4, sizeof(ctx->name)); +- if (len < 2 || len >= sizeof(ctx->name)) ++ len = strscpy(ctx->name, cipher_name + 4, sizeof(ctx->name)); ++ if (len < 2) + goto err_free_inst; + + if (ctx->name[len - 1] != ')') +-- +2.40.1 + diff --git a/queue-6.5/devlink-remove-reload-failed-checks-in-params-get-se.patch b/queue-6.5/devlink-remove-reload-failed-checks-in-params-get-se.patch new file mode 100644 index 00000000000..343880a7f0e --- /dev/null +++ b/queue-6.5/devlink-remove-reload-failed-checks-in-params-get-se.patch @@ -0,0 +1,68 @@ +From 092971e3bc31c372733fe0e60d7fed43c19827c8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 13 Jul 2023 11:44:19 +0200 +Subject: devlink: remove reload failed checks in params get/set callbacks + +From: Jiri Pirko + +[ Upstream commit 633d76ad01ad0321a1ace3e5cc4fed06753d7ac4 ] + +The checks in question were introduced by: +commit 6b4db2e528f6 ("devlink: Fix use-after-free after a failed reload"). +That fixed an issue of reload with mlxsw driver. + +Back then, that was a valid fix, because there was a limitation +in place that prevented drivers from registering/unregistering params +when devlink instance was registered. + +It was possible to do the fix differently by changing drivers to +register/unregister params in appropriate places making sure the ops +operate only on memory which is allocated and initialized. But that, +as a dependency, would require to remove the limitation mentioned above. + +Eventually, this limitation was lifted by: +commit 1d18bb1a4ddd ("devlink: allow registering parameters after the instance") + +Also, the alternative fix (which also fixed another issue) was done by: +commit 74cbc3c03c82 ("mlxsw: spectrum_acl_tcam: Move devlink param to TCAM code"). + +Therefore, the checks are no longer relevant. Each driver should make +sure to have the params registered only when the memory the ops +are working with is allocated and initialized. + +So remove the checks. + +Signed-off-by: Jiri Pirko +Reviewed-by: Ido Schimmel +Reviewed-by: Jakub Kicinski +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + net/devlink/leftover.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/net/devlink/leftover.c b/net/devlink/leftover.c +index bfed7929a904f..5277eb3c7d0a1 100644 +--- a/net/devlink/leftover.c ++++ b/net/devlink/leftover.c +@@ -3946,7 +3946,7 @@ static int devlink_param_get(struct devlink *devlink, + const struct devlink_param *param, + struct devlink_param_gset_ctx *ctx) + { +- if (!param->get || devlink->reload_failed) ++ if (!param->get) + return -EOPNOTSUPP; + return param->get(devlink, param->id, ctx); + } +@@ -3955,7 +3955,7 @@ static int devlink_param_set(struct devlink *devlink, + const struct devlink_param *param, + struct devlink_param_gset_ctx *ctx) + { +- if (!param->set || devlink->reload_failed) ++ if (!param->set) + return -EOPNOTSUPP; + return param->set(devlink, param->id, ctx); + } +-- +2.40.1 + diff --git a/queue-6.5/drm-amd-display-add-stream-overhead-in-bw-calculatio.patch b/queue-6.5/drm-amd-display-add-stream-overhead-in-bw-calculatio.patch new file mode 100644 index 00000000000..b6bec308d15 --- /dev/null +++ b/queue-6.5/drm-amd-display-add-stream-overhead-in-bw-calculatio.patch @@ -0,0 +1,114 @@ +From 2fc4e68e9746ea47bbab63d153532970277f9a6a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 10 Apr 2023 20:00:46 -0400 +Subject: drm/amd/display: Add stream overhead in BW calculations for 128b/132b + +From: George Shen + +[ Upstream commit 974764180838516f80a13257da67a1ec6afb87d4 ] + +[Why] +Current BW calculations do not account for the additional padding added +for uncompressed pixel-to-symbol packing. + +This results in X.Y being too low for 128b/132b SST streams in certain +scenarios. If X.Y is too low, end user can observe image corruption. + +[How] +Add function to calculate stream overhead to timing BW calculation for +128b/132b SST cases. + +Reviewed-by: Wenjing Liu +Acked-by: Alan Liu +Signed-off-by: George Shen +Tested-by: Daniel Wheeler +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/amd/display/dc/dc.h | 2 + + drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c | 42 +++++++++++++++++++++ + 2 files changed, 44 insertions(+) + +diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h +index 63948170fd6d9..3d4180f7ba349 100644 +--- a/drivers/gpu/drm/amd/display/dc/dc.h ++++ b/drivers/gpu/drm/amd/display/dc/dc.h +@@ -1409,6 +1409,8 @@ struct dc_plane_state *dc_get_surface_for_mpcc(struct dc *dc, + + uint32_t dc_get_opp_for_plane(struct dc *dc, struct dc_plane_state *plane); + ++void dc_set_disable_128b_132b_stream_overhead(bool disable); ++ + /* The function returns minimum bandwidth required to drive a given timing + * return - minimum required timing bandwidth in kbps. + */ +diff --git a/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c b/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c +index 58dd62cce4bb9..aed0d3dafa247 100644 +--- a/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c ++++ b/drivers/gpu/drm/amd/display/dc/dsc/dc_dsc.c +@@ -40,6 +40,8 @@ static bool dsc_policy_enable_dsc_when_not_needed; + + static bool dsc_policy_disable_dsc_stream_overhead; + ++static bool disable_128b_132b_stream_overhead; ++ + #ifndef MAX + #define MAX(X, Y) ((X) > (Y) ? (X) : (Y)) + #endif +@@ -47,6 +49,41 @@ static bool dsc_policy_disable_dsc_stream_overhead; + #define MIN(X, Y) ((X) < (Y) ? (X) : (Y)) + #endif + ++/* Need to account for padding due to pixel-to-symbol packing ++ * for uncompressed 128b/132b streams. ++ */ ++static uint32_t apply_128b_132b_stream_overhead( ++ const struct dc_crtc_timing *timing, const uint32_t kbps) ++{ ++ uint32_t total_kbps = kbps; ++ ++ if (disable_128b_132b_stream_overhead) ++ return kbps; ++ ++ if (!timing->flags.DSC) { ++ struct fixed31_32 bpp; ++ struct fixed31_32 overhead_factor; ++ ++ bpp = dc_fixpt_from_int(kbps); ++ bpp = dc_fixpt_div_int(bpp, timing->pix_clk_100hz / 10); ++ ++ /* Symbols_per_HActive = HActive * bpp / (4 lanes * 32-bit symbol size) ++ * Overhead_factor = ceil(Symbols_per_HActive) / Symbols_per_HActive ++ */ ++ overhead_factor = dc_fixpt_from_int(timing->h_addressable); ++ overhead_factor = dc_fixpt_mul(overhead_factor, bpp); ++ overhead_factor = dc_fixpt_div_int(overhead_factor, 128); ++ overhead_factor = dc_fixpt_div( ++ dc_fixpt_from_int(dc_fixpt_ceil(overhead_factor)), ++ overhead_factor); ++ ++ total_kbps = dc_fixpt_ceil( ++ dc_fixpt_mul_int(overhead_factor, total_kbps)); ++ } ++ ++ return total_kbps; ++} ++ + uint32_t dc_bandwidth_in_kbps_from_timing( + const struct dc_crtc_timing *timing) + { +@@ -1165,6 +1202,11 @@ void dc_dsc_policy_set_disable_dsc_stream_overhead(bool disable) + dsc_policy_disable_dsc_stream_overhead = disable; + } + ++void dc_set_disable_128b_132b_stream_overhead(bool disable) ++{ ++ disable_128b_132b_stream_overhead = disable; ++} ++ + void dc_dsc_get_default_config_option(const struct dc *dc, struct dc_dsc_config_options *options) + { + options->dsc_min_slice_height_override = dc->debug.dsc_min_slice_height_override; +-- +2.40.1 + diff --git a/queue-6.5/drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch b/queue-6.5/drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch new file mode 100644 index 00000000000..d3412a3e784 --- /dev/null +++ b/queue-6.5/drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch @@ -0,0 +1,42 @@ +From 09e9e5a0a89140c1a657101179b451dc0d487f7b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 24 Jul 2023 16:57:36 -0400 +Subject: drm/amd/display: Blocking invalid 420 modes on HDMI TMDS for DCN31 + +From: Leo Chen + +[ Upstream commit 026a71babf48efb6b9884a3a66fa31aec9e1ea54 ] + +[Why & How] +HDMI TMDS does not have ODM support. Filtering 420 modes that +exceed the 4096 FMT limitation on DCN31 will resolve +intermittent corruptions issues. + +Reviewed-by: Nicholas Kazlauskas +Acked-by: Tom Chung +Signed-off-by: Leo Chen +Tested-by: Daniel Wheeler +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + .../gpu/drm/amd/display/dc/dml/dcn31/display_mode_vba_31.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/amd/display/dc/dml/dcn31/display_mode_vba_31.c b/drivers/gpu/drm/amd/display/dc/dml/dcn31/display_mode_vba_31.c +index 43016c462251f..9d996d5fc3ffa 100644 +--- a/drivers/gpu/drm/amd/display/dc/dml/dcn31/display_mode_vba_31.c ++++ b/drivers/gpu/drm/amd/display/dc/dml/dcn31/display_mode_vba_31.c +@@ -4135,7 +4135,9 @@ void dml31_ModeSupportAndSystemConfigurationFull(struct display_mode_lib *mode_l + } + if (v->OutputFormat[k] == dm_420 && v->HActive[k] > DCN31_MAX_FMT_420_BUFFER_WIDTH + && v->ODMCombineEnablePerState[i][k] != dm_odm_combine_mode_4to1) { +- if (v->HActive[k] / 2 > DCN31_MAX_FMT_420_BUFFER_WIDTH) { ++ if (v->Output[k] == dm_hdmi) { ++ FMTBufferExceeded = true; ++ } else if (v->HActive[k] / 2 > DCN31_MAX_FMT_420_BUFFER_WIDTH) { + v->ODMCombineEnablePerState[i][k] = dm_odm_combine_mode_4to1; + v->PlaneRequiredDISPCLK = v->PlaneRequiredDISPCLKWithODMCombine4To1; + +-- +2.40.1 + diff --git a/queue-6.5/drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch-12335 b/queue-6.5/drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch-12335 new file mode 100644 index 00000000000..d0cd5dc862a --- /dev/null +++ b/queue-6.5/drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch-12335 @@ -0,0 +1,42 @@ +From 68f72fe6a747de97433d07fe89e0db9cdcce203a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 26 Jul 2023 22:44:13 -0400 +Subject: drm/amd/display: Blocking invalid 420 modes on HDMI TMDS for DCN314 + +From: Leo Chen + +[ Upstream commit 4c6107a653ccf361cb1b6ba35d558a1a5e6e57ac ] + +[Why & How] +HDMI TMDS does not have ODM support. Filtering 420 modes that +exceed the 4096 FMT limitation on DCN314 will resolve +intermittent corruptions issues. + +Reviewed-by: Nicholas Kazlauskas +Acked-by: Tom Chung +Signed-off-by: Leo Chen +Tested-by: Daniel Wheeler +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + .../gpu/drm/amd/display/dc/dml/dcn314/display_mode_vba_314.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/amd/display/dc/dml/dcn314/display_mode_vba_314.c b/drivers/gpu/drm/amd/display/dc/dml/dcn314/display_mode_vba_314.c +index 9010c47476e92..b763786bfcc85 100644 +--- a/drivers/gpu/drm/amd/display/dc/dml/dcn314/display_mode_vba_314.c ++++ b/drivers/gpu/drm/amd/display/dc/dml/dcn314/display_mode_vba_314.c +@@ -4227,7 +4227,9 @@ void dml314_ModeSupportAndSystemConfigurationFull(struct display_mode_lib *mode_ + } + if (v->OutputFormat[k] == dm_420 && v->HActive[k] > DCN314_MAX_FMT_420_BUFFER_WIDTH + && v->ODMCombineEnablePerState[i][k] != dm_odm_combine_mode_4to1) { +- if (v->HActive[k] / 2 > DCN314_MAX_FMT_420_BUFFER_WIDTH) { ++ if (v->Output[k] == dm_hdmi) { ++ FMTBufferExceeded = true; ++ } else if (v->HActive[k] / 2 > DCN314_MAX_FMT_420_BUFFER_WIDTH) { + v->ODMCombineEnablePerState[i][k] = dm_odm_combine_mode_4to1; + v->PlaneRequiredDISPCLK = v->PlaneRequiredDISPCLKWithODMCombine4To1; + +-- +2.40.1 + diff --git a/queue-6.5/drm-amd-display-fix-underflow-issue-on-175hz-timing.patch b/queue-6.5/drm-amd-display-fix-underflow-issue-on-175hz-timing.patch new file mode 100644 index 00000000000..b35dbb2b0f4 --- /dev/null +++ b/queue-6.5/drm-amd-display-fix-underflow-issue-on-175hz-timing.patch @@ -0,0 +1,66 @@ +From 4df09bdac63020e113948249cffcb72e21fa51f7 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 6 Jul 2023 16:17:03 -0400 +Subject: drm/amd/display: Fix underflow issue on 175hz timing + +From: Leo Ma + +[ Upstream commit 735688eb905db529efea0c78466fccc1461c3fde ] + +[Why] +Screen underflows happen on 175hz timing for 3 plane overlay case. + +[How] +Based on dst y prefetch value clamp to equ or oto for bandwidth +calculation. + +Reviewed-by: Dillon Varone +Acked-by: Alex Hung +Signed-off-by: Leo Ma +Tested-by: Daniel Wheeler +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + .../amd/display/dc/dml/dcn32/display_mode_vba_util_32.c | 7 ++++++- + 1 file changed, 6 insertions(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/amd/display/dc/dml/dcn32/display_mode_vba_util_32.c b/drivers/gpu/drm/amd/display/dc/dml/dcn32/display_mode_vba_util_32.c +index a50e7f4dce421..f74e5fc8218f5 100644 +--- a/drivers/gpu/drm/amd/display/dc/dml/dcn32/display_mode_vba_util_32.c ++++ b/drivers/gpu/drm/amd/display/dc/dml/dcn32/display_mode_vba_util_32.c +@@ -3459,6 +3459,7 @@ bool dml32_CalculatePrefetchSchedule( + double TimeForFetchingMetaPTE = 0; + double TimeForFetchingRowInVBlank = 0; + double LinesToRequestPrefetchPixelData = 0; ++ double LinesForPrefetchBandwidth = 0; + unsigned int HostVMDynamicLevelsTrips; + double trip_to_mem; + double Tvm_trips; +@@ -3888,11 +3889,15 @@ bool dml32_CalculatePrefetchSchedule( + TimeForFetchingMetaPTE = Tvm_oto; + TimeForFetchingRowInVBlank = Tr0_oto; + *PrefetchBandwidth = prefetch_bw_oto; ++ /* Clamp to oto for bandwidth calculation */ ++ LinesForPrefetchBandwidth = dst_y_prefetch_oto; + } else { + *DestinationLinesForPrefetch = dst_y_prefetch_equ; + TimeForFetchingMetaPTE = Tvm_equ; + TimeForFetchingRowInVBlank = Tr0_equ; + *PrefetchBandwidth = prefetch_bw_equ; ++ /* Clamp to equ for bandwidth calculation */ ++ LinesForPrefetchBandwidth = dst_y_prefetch_equ; + } + + *DestinationLinesToRequestVMInVBlank = dml_ceil(4.0 * TimeForFetchingMetaPTE / LineTime, 1.0) / 4.0; +@@ -3900,7 +3905,7 @@ bool dml32_CalculatePrefetchSchedule( + *DestinationLinesToRequestRowInVBlank = + dml_ceil(4.0 * TimeForFetchingRowInVBlank / LineTime, 1.0) / 4.0; + +- LinesToRequestPrefetchPixelData = *DestinationLinesForPrefetch - ++ LinesToRequestPrefetchPixelData = LinesForPrefetchBandwidth - + *DestinationLinesToRequestVMInVBlank - 2 * *DestinationLinesToRequestRowInVBlank; + + #ifdef __DML_VBA_DEBUG__ +-- +2.40.1 + diff --git a/queue-6.5/drm-amd-display-use-dtbclk-as-refclk-instead-of-dpre.patch b/queue-6.5/drm-amd-display-use-dtbclk-as-refclk-instead-of-dpre.patch new file mode 100644 index 00000000000..d5a26cb1026 --- /dev/null +++ b/queue-6.5/drm-amd-display-use-dtbclk-as-refclk-instead-of-dpre.patch @@ -0,0 +1,44 @@ +From 2264559251479851e027f5c248244491d8ef33ff Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 26 Jul 2023 10:40:48 -0400 +Subject: drm/amd/display: Use DTBCLK as refclk instead of DPREFCLK + +From: Austin Zheng + +[ Upstream commit 4a30cc2bd281fa176a68b5305cd3695d636152ad ] + +[Why] +Flash of corruption observed when UCLK switching after transitioning +from DTBCLK to DPREFCLK on subVP(DP) + subVP(HDMI) config +Scenario where DPREFCLK is required instead of DTBCLK is not expected + +[How] +Always set the DTBCLK source as DTBCLK0 + +Reviewed-by: Alvin Lee +Acked-by: Tom Chung +Signed-off-by: Austin Zheng +Tested-by: Daniel Wheeler +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c +index 61ceff6bc0b19..921f58c0c729b 100644 +--- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c ++++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c +@@ -281,7 +281,8 @@ static void dccg32_set_dpstreamclk( + struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg); + + /* set the dtbclk_p source */ +- dccg32_set_dtbclk_p_src(dccg, src, otg_inst); ++ /* always program refclk as DTBCLK. No use-case expected to require DPREFCLK as refclk */ ++ dccg32_set_dtbclk_p_src(dccg, DTBCLK0, otg_inst); + + /* enabled to select one of the DTBCLKs for pipe */ + switch (dp_hpo_inst) { +-- +2.40.1 + diff --git a/queue-6.5/drm-amd-display-use-max-memclk-variable-when-setting.patch b/queue-6.5/drm-amd-display-use-max-memclk-variable-when-setting.patch new file mode 100644 index 00000000000..2f654f743c3 --- /dev/null +++ b/queue-6.5/drm-amd-display-use-max-memclk-variable-when-setting.patch @@ -0,0 +1,42 @@ +From 7c62c1e05b73ca042f704993bd20b2133de8fa8a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 27 Jul 2023 14:23:13 -0400 +Subject: drm/amd/display: Use max memclk variable when setting max memclk + +From: Alvin Lee + +[ Upstream commit 2b1b838ea8e5437ef06a29818d16e9efdfaf0037 ] + +[Description] +In overclocking scenarios the max memclk could be higher +than the DC mode limit. However, for configs that don't +support MCLK switching we need to set the max memclk to +the overclocked max instead of the DC mode max or we +could result in underflow. + +Reviewed-by: Samson Tam +Acked-by: Tom Chung +Signed-off-by: Alvin Lee +Tested-by: Daniel Wheeler +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c +index cb992aca760dc..5fc78bf927bbc 100644 +--- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c ++++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn32/dcn32_clk_mgr.c +@@ -802,7 +802,7 @@ static void dcn32_set_hard_min_memclk(struct clk_mgr *clk_mgr_base, bool current + khz_to_mhz_ceil(clk_mgr_base->clks.dramclk_khz)); + else + dcn32_smu_set_hard_min_by_freq(clk_mgr, PPCLK_UCLK, +- clk_mgr_base->bw_params->clk_table.entries[clk_mgr_base->bw_params->clk_table.num_entries_per_clk.num_memclk_levels - 1].memclk_mhz); ++ clk_mgr_base->bw_params->max_memclk_mhz); + } else { + dcn32_smu_set_hard_min_by_freq(clk_mgr, PPCLK_UCLK, + clk_mgr_base->bw_params->clk_table.entries[0].memclk_mhz); +-- +2.40.1 + diff --git a/queue-6.5/drm-amdgpu-increase-soft-ih-ring-size.patch b/queue-6.5/drm-amdgpu-increase-soft-ih-ring-size.patch new file mode 100644 index 00000000000..21a35d69b5a --- /dev/null +++ b/queue-6.5/drm-amdgpu-increase-soft-ih-ring-size.patch @@ -0,0 +1,200 @@ +From fd3b49a620bb7ec27ff805d98db36b63f1420df9 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 7 Jul 2023 09:55:18 -0400 +Subject: drm/amdgpu: Increase soft IH ring size + +From: Philip Yang + +[ Upstream commit bf80d34b6c58ad1c4f76067ecd460a148eab9d39 ] + +Retry faults are delegated to soft IH ring and then processed by +deferred worker. Current soft IH ring size PAGE_SIZE can store 128 +entries, which may overflow and drop retry faults, causes HW stucks +because the retry fault is not recovered. + +Increase soft IH ring size to 8KB, enough to store 256 CAM entries +because we clear the CAM entry after handling the retry fault from soft +ring. + +Define macro IH_RING_SIZE and IH_SW_RING_SIZE to remove duplicate +constant. + +Show warning message if soft IH ring overflows with CAM enabled because +this should not happen. + +Signed-off-by: Philip Yang +Reviewed-by: Felix Kuehling +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/amd/amdgpu/amdgpu_ih.c | 8 ++++++-- + drivers/gpu/drm/amd/amdgpu/amdgpu_ih.h | 7 +++++-- + drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c | 2 +- + drivers/gpu/drm/amd/amdgpu/ih_v6_0.c | 4 ++-- + drivers/gpu/drm/amd/amdgpu/navi10_ih.c | 4 ++-- + drivers/gpu/drm/amd/amdgpu/vega10_ih.c | 4 ++-- + drivers/gpu/drm/amd/amdgpu/vega20_ih.c | 4 ++-- + 7 files changed, 20 insertions(+), 13 deletions(-) + +diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.c +index fceb3b384955a..f3b0aaf3ebc69 100644 +--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.c ++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.c +@@ -138,6 +138,7 @@ void amdgpu_ih_ring_fini(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih) + /** + * amdgpu_ih_ring_write - write IV to the ring buffer + * ++ * @adev: amdgpu_device pointer + * @ih: ih ring to write to + * @iv: the iv to write + * @num_dw: size of the iv in dw +@@ -145,8 +146,8 @@ void amdgpu_ih_ring_fini(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih) + * Writes an IV to the ring buffer using the CPU and increment the wptr. + * Used for testing and delegating IVs to a software ring. + */ +-void amdgpu_ih_ring_write(struct amdgpu_ih_ring *ih, const uint32_t *iv, +- unsigned int num_dw) ++void amdgpu_ih_ring_write(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih, ++ const uint32_t *iv, unsigned int num_dw) + { + uint32_t wptr = le32_to_cpu(*ih->wptr_cpu) >> 2; + unsigned int i; +@@ -161,6 +162,9 @@ void amdgpu_ih_ring_write(struct amdgpu_ih_ring *ih, const uint32_t *iv, + if (wptr != READ_ONCE(ih->rptr)) { + wmb(); + WRITE_ONCE(*ih->wptr_cpu, cpu_to_le32(wptr)); ++ } else if (adev->irq.retry_cam_enabled) { ++ dev_warn_once(adev->dev, "IH soft ring buffer overflow 0x%X, 0x%X\n", ++ wptr, ih->rptr); + } + } + +diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.h +index dd1c2eded6b9d..6c6184f0dbc17 100644 +--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.h ++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ih.h +@@ -27,6 +27,9 @@ + /* Maximum number of IVs processed at once */ + #define AMDGPU_IH_MAX_NUM_IVS 32 + ++#define IH_RING_SIZE (256 * 1024) ++#define IH_SW_RING_SIZE (8 * 1024) /* enough for 256 CAM entries */ ++ + struct amdgpu_device; + struct amdgpu_iv_entry; + +@@ -97,8 +100,8 @@ struct amdgpu_ih_funcs { + int amdgpu_ih_ring_init(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih, + unsigned ring_size, bool use_bus_addr); + void amdgpu_ih_ring_fini(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih); +-void amdgpu_ih_ring_write(struct amdgpu_ih_ring *ih, const uint32_t *iv, +- unsigned int num_dw); ++void amdgpu_ih_ring_write(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih, ++ const uint32_t *iv, unsigned int num_dw); + int amdgpu_ih_wait_on_checkpoint_process_ts(struct amdgpu_device *adev, + struct amdgpu_ih_ring *ih); + int amdgpu_ih_process(struct amdgpu_device *adev, struct amdgpu_ih_ring *ih); +diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c +index 5273decc5753b..fa6d0adcec206 100644 +--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c ++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c +@@ -493,7 +493,7 @@ void amdgpu_irq_delegate(struct amdgpu_device *adev, + struct amdgpu_iv_entry *entry, + unsigned int num_dw) + { +- amdgpu_ih_ring_write(&adev->irq.ih_soft, entry->iv_entry, num_dw); ++ amdgpu_ih_ring_write(adev, &adev->irq.ih_soft, entry->iv_entry, num_dw); + schedule_work(&adev->irq.ih_soft_work); + } + +diff --git a/drivers/gpu/drm/amd/amdgpu/ih_v6_0.c b/drivers/gpu/drm/amd/amdgpu/ih_v6_0.c +index b02e1cef78a76..980b241200803 100644 +--- a/drivers/gpu/drm/amd/amdgpu/ih_v6_0.c ++++ b/drivers/gpu/drm/amd/amdgpu/ih_v6_0.c +@@ -535,7 +535,7 @@ static int ih_v6_0_sw_init(void *handle) + * use bus address for ih ring by psp bl */ + use_bus_addr = + (adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) ? false : true; +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih, 256 * 1024, use_bus_addr); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih, IH_RING_SIZE, use_bus_addr); + if (r) + return r; + +@@ -548,7 +548,7 @@ static int ih_v6_0_sw_init(void *handle) + /* initialize ih control register offset */ + ih_v6_0_init_register_offset(adev); + +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, PAGE_SIZE, true); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, IH_SW_RING_SIZE, true); + if (r) + return r; + +diff --git a/drivers/gpu/drm/amd/amdgpu/navi10_ih.c b/drivers/gpu/drm/amd/amdgpu/navi10_ih.c +index eec13cb5bf758..b6a8478dabf43 100644 +--- a/drivers/gpu/drm/amd/amdgpu/navi10_ih.c ++++ b/drivers/gpu/drm/amd/amdgpu/navi10_ih.c +@@ -565,7 +565,7 @@ static int navi10_ih_sw_init(void *handle) + use_bus_addr = false; + else + use_bus_addr = true; +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih, 256 * 1024, use_bus_addr); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih, IH_RING_SIZE, use_bus_addr); + if (r) + return r; + +@@ -578,7 +578,7 @@ static int navi10_ih_sw_init(void *handle) + /* initialize ih control registers offset */ + navi10_ih_init_register_offset(adev); + +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, PAGE_SIZE, true); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, IH_SW_RING_SIZE, true); + if (r) + return r; + +diff --git a/drivers/gpu/drm/amd/amdgpu/vega10_ih.c b/drivers/gpu/drm/amd/amdgpu/vega10_ih.c +index 1e83db0c5438d..d364c6dd152c3 100644 +--- a/drivers/gpu/drm/amd/amdgpu/vega10_ih.c ++++ b/drivers/gpu/drm/amd/amdgpu/vega10_ih.c +@@ -485,7 +485,7 @@ static int vega10_ih_sw_init(void *handle) + if (r) + return r; + +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih, 256 * 1024, true); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih, IH_RING_SIZE, true); + if (r) + return r; + +@@ -510,7 +510,7 @@ static int vega10_ih_sw_init(void *handle) + /* initialize ih control registers offset */ + vega10_ih_init_register_offset(adev); + +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, PAGE_SIZE, true); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, IH_SW_RING_SIZE, true); + if (r) + return r; + +diff --git a/drivers/gpu/drm/amd/amdgpu/vega20_ih.c b/drivers/gpu/drm/amd/amdgpu/vega20_ih.c +index 4d719df376a72..544ee55a22da6 100644 +--- a/drivers/gpu/drm/amd/amdgpu/vega20_ih.c ++++ b/drivers/gpu/drm/amd/amdgpu/vega20_ih.c +@@ -539,7 +539,7 @@ static int vega20_ih_sw_init(void *handle) + (adev->ip_versions[OSSSYS_HWIP][0] == IP_VERSION(4, 4, 2))) + use_bus_addr = false; + +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih, 256 * 1024, use_bus_addr); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih, IH_RING_SIZE, use_bus_addr); + if (r) + return r; + +@@ -565,7 +565,7 @@ static int vega20_ih_sw_init(void *handle) + /* initialize ih control registers offset */ + vega20_ih_init_register_offset(adev); + +- r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, PAGE_SIZE, use_bus_addr); ++ r = amdgpu_ih_ring_init(adev, &adev->irq.ih_soft, IH_SW_RING_SIZE, use_bus_addr); + if (r) + return r; + +-- +2.40.1 + diff --git a/queue-6.5/drm-amdgpu-update-ring-scheduler-info-as-needed.patch b/queue-6.5/drm-amdgpu-update-ring-scheduler-info-as-needed.patch new file mode 100644 index 00000000000..d47becdf671 --- /dev/null +++ b/queue-6.5/drm-amdgpu-update-ring-scheduler-info-as-needed.patch @@ -0,0 +1,37 @@ +From d36c4abee346da3e302b698be5bb6442c69bf621 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 18 Jul 2023 17:41:45 +0530 +Subject: drm/amdgpu: Update ring scheduler info as needed + +From: Lijo Lazar + +[ Upstream commit 6cb209ed68e45c8e4b71d97a037ac6b7dbce9b50 ] + +Not all rings have scheduler associated. Only update scheduler data for +rings with scheduler. It could result in out of bound access as total +rings are more than those associated with particular IPs. + +Signed-off-by: Lijo Lazar +Reviewed-by: James Zhu +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/amd/amdgpu/aqua_vanjaram_reg_init.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/amd/amdgpu/aqua_vanjaram_reg_init.c b/drivers/gpu/drm/amd/amdgpu/aqua_vanjaram_reg_init.c +index 72b629a78c62c..d0fc62784e821 100644 +--- a/drivers/gpu/drm/amd/amdgpu/aqua_vanjaram_reg_init.c ++++ b/drivers/gpu/drm/amd/amdgpu/aqua_vanjaram_reg_init.c +@@ -134,7 +134,7 @@ static int aqua_vanjaram_xcp_sched_list_update( + + for (i = 0; i < AMDGPU_MAX_RINGS; i++) { + ring = adev->rings[i]; +- if (!ring || !ring->sched.ready) ++ if (!ring || !ring->sched.ready || ring->no_scheduler) + continue; + + aqua_vanjaram_xcp_gpu_sched_update(adev, ring, ring->xcp_id); +-- +2.40.1 + diff --git a/queue-6.5/drm-bridge-samsung-dsim-drain-command-transfer-fifo-.patch b/queue-6.5/drm-bridge-samsung-dsim-drain-command-transfer-fifo-.patch new file mode 100644 index 00000000000..bb0bdd279fc --- /dev/null +++ b/queue-6.5/drm-bridge-samsung-dsim-drain-command-transfer-fifo-.patch @@ -0,0 +1,41 @@ +From f596948fa4c365dcd5ac905f960bfeb06b537f62 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 15 Jun 2023 22:15:11 +0200 +Subject: drm: bridge: samsung-dsim: Drain command transfer FIFO before + transfer + +From: Marek Vasut + +[ Upstream commit 14806c6415820b1c4bc317655c40784d050a2edb ] + +Wait until the command transfer FIFO is empty before loading in the next +command. The previous behavior where the code waited until command transfer +FIFO was not full suffered from transfer corruption, where the last command +in the FIFO could be overwritten in case the FIFO indicates not full, but +also does not have enough space to store another transfer yet. + +Signed-off-by: Marek Vasut +Reviewed-by: Jagan Teki +Tested-by: Jagan Teki # imx8mm-icore +Link: https://patchwork.freedesktop.org/patch/msgid/20230615201511.565923-1-marex@denx.de +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/bridge/samsung-dsim.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/bridge/samsung-dsim.c b/drivers/gpu/drm/bridge/samsung-dsim.c +index 73ec60757dbcb..9e253af69c7a1 100644 +--- a/drivers/gpu/drm/bridge/samsung-dsim.c ++++ b/drivers/gpu/drm/bridge/samsung-dsim.c +@@ -1009,7 +1009,7 @@ static int samsung_dsim_wait_for_hdr_fifo(struct samsung_dsim *dsi) + do { + u32 reg = samsung_dsim_read(dsi, DSIM_FIFOCTRL_REG); + +- if (!(reg & DSIM_SFR_HEADER_FULL)) ++ if (reg & DSIM_SFR_HEADER_EMPTY) + return 0; + + if (!cond_resched()) +-- +2.40.1 + diff --git a/queue-6.5/drm-bridge-tc358762-instruct-dsi-host-to-generate-hs.patch b/queue-6.5/drm-bridge-tc358762-instruct-dsi-host-to-generate-hs.patch new file mode 100644 index 00000000000..37fca78d2b5 --- /dev/null +++ b/queue-6.5/drm-bridge-tc358762-instruct-dsi-host-to-generate-hs.patch @@ -0,0 +1,38 @@ +From b64c86d7842d48ce04dc6d2627efc973b8f7ae19 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 15 Jun 2023 22:19:00 +0200 +Subject: drm/bridge: tc358762: Instruct DSI host to generate HSE packets + +From: Marek Vasut + +[ Upstream commit 362fa8f6e6a05089872809f4465bab9d011d05b3 ] + +This bridge seems to need the HSE packet, otherwise the image is +shifted up and corrupted at the bottom. This makes the bridge +work with Samsung DSIM on i.MX8MM and i.MX8MP. + +Signed-off-by: Marek Vasut +Reviewed-by: Sam Ravnborg +Signed-off-by: Robert Foss +Link: https://patchwork.freedesktop.org/patch/msgid/20230615201902.566182-3-marex@denx.de +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/bridge/tc358762.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/gpu/drm/bridge/tc358762.c b/drivers/gpu/drm/bridge/tc358762.c +index 5641395fd310e..11445c50956e1 100644 +--- a/drivers/gpu/drm/bridge/tc358762.c ++++ b/drivers/gpu/drm/bridge/tc358762.c +@@ -231,7 +231,7 @@ static int tc358762_probe(struct mipi_dsi_device *dsi) + dsi->lanes = 1; + dsi->format = MIPI_DSI_FMT_RGB888; + dsi->mode_flags = MIPI_DSI_MODE_VIDEO | MIPI_DSI_MODE_VIDEO_SYNC_PULSE | +- MIPI_DSI_MODE_LPM; ++ MIPI_DSI_MODE_LPM | MIPI_DSI_MODE_VIDEO_HSE; + + ret = tc358762_parse_dt(ctx); + if (ret < 0) +-- +2.40.1 + diff --git a/queue-6.5/drm-edid-add-quirk-for-osvr-hdk-2.0.patch b/queue-6.5/drm-edid-add-quirk-for-osvr-hdk-2.0.patch new file mode 100644 index 00000000000..94640393004 --- /dev/null +++ b/queue-6.5/drm-edid-add-quirk-for-osvr-hdk-2.0.patch @@ -0,0 +1,40 @@ +From 63d43d875b36d570496512239700d3cb59551663 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 20 Jun 2023 23:19:03 -0700 +Subject: drm/edid: Add quirk for OSVR HDK 2.0 + +From: Ralph Campbell + +[ Upstream commit 98d4cb705bc00afd4a9a71cc1e84f7111682639a ] + +The OSVR virtual reality headset HDK 2.0 uses a different EDID +vendor and device identifier than the HDK 1.1 - 1.4 headsets. +Add the HDK 2.0 vendor and device identifier to the quirks table so +that window managers do not try to display the desktop screen on the +headset display. + +Closes: https://gitlab.freedesktop.org/drm/misc/-/issues/30 +Signed-off-by: Ralph Campbell +Tested-by: Ralph Campbell +Signed-off-by: Jani Nikula +Link: https://patchwork.freedesktop.org/patch/msgid/20230621061903.3422648-1-rcampbell@nvidia.com +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/drm_edid.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c +index 1f470968ed14b..9271e47d66572 100644 +--- a/drivers/gpu/drm/drm_edid.c ++++ b/drivers/gpu/drm/drm_edid.c +@@ -230,6 +230,7 @@ static const struct edid_quirk { + + /* OSVR HDK and HDK2 VR Headsets */ + EDID_QUIRK('S', 'V', 'R', 0x1019, EDID_QUIRK_NON_DESKTOP), ++ EDID_QUIRK('A', 'U', 'O', 0x1111, EDID_QUIRK_NON_DESKTOP), + }; + + /* +-- +2.40.1 + diff --git a/queue-6.5/drm-exynos-fix-a-possible-null-pointer-dereference-d.patch b/queue-6.5/drm-exynos-fix-a-possible-null-pointer-dereference-d.patch new file mode 100644 index 00000000000..3aac5ead981 --- /dev/null +++ b/queue-6.5/drm-exynos-fix-a-possible-null-pointer-dereference-d.patch @@ -0,0 +1,61 @@ +From 5909398d89ede573510295f6e0b6db5dedfd1c1c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 30 Jun 2023 10:19:06 +0800 +Subject: drm/exynos: fix a possible null-pointer dereference due to data race + in exynos_drm_crtc_atomic_disable() + +From: Tuo Li + +[ Upstream commit 2e63972a2de14482d0eae1a03a73e379f1c3f44c ] + +The variable crtc->state->event is often protected by the lock +crtc->dev->event_lock when is accessed. However, it is accessed as a +condition of an if statement in exynos_drm_crtc_atomic_disable() without +holding the lock: + + if (crtc->state->event && !crtc->state->active) + +However, if crtc->state->event is changed to NULL by another thread right +after the conditions of the if statement is checked to be true, a +null-pointer dereference can occur in drm_crtc_send_vblank_event(): + + e->pipe = pipe; + +To fix this possible null-pointer dereference caused by data race, the +spin lock coverage is extended to protect the if statement as well as the +function call to drm_crtc_send_vblank_event(). + +Reported-by: BassCheck +Link: https://sites.google.com/view/basscheck/home +Signed-off-by: Tuo Li +Reviewed-by: Krzysztof Kozlowski +Added relevant link. +Signed-off-by: Inki Dae +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/exynos/exynos_drm_crtc.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +diff --git a/drivers/gpu/drm/exynos/exynos_drm_crtc.c b/drivers/gpu/drm/exynos/exynos_drm_crtc.c +index 4153f302de7c4..d19e796c20613 100644 +--- a/drivers/gpu/drm/exynos/exynos_drm_crtc.c ++++ b/drivers/gpu/drm/exynos/exynos_drm_crtc.c +@@ -39,13 +39,12 @@ static void exynos_drm_crtc_atomic_disable(struct drm_crtc *crtc, + if (exynos_crtc->ops->atomic_disable) + exynos_crtc->ops->atomic_disable(exynos_crtc); + ++ spin_lock_irq(&crtc->dev->event_lock); + if (crtc->state->event && !crtc->state->active) { +- spin_lock_irq(&crtc->dev->event_lock); + drm_crtc_send_vblank_event(crtc, crtc->state->event); +- spin_unlock_irq(&crtc->dev->event_lock); +- + crtc->state->event = NULL; + } ++ spin_unlock_irq(&crtc->dev->event_lock); + } + + static int exynos_crtc_atomic_check(struct drm_crtc *crtc, +-- +2.40.1 + diff --git a/queue-6.5/drm-gm12u320-fix-the-timeout-usage-for-usb_bulk_msg.patch b/queue-6.5/drm-gm12u320-fix-the-timeout-usage-for-usb_bulk_msg.patch new file mode 100644 index 00000000000..15bf2751d05 --- /dev/null +++ b/queue-6.5/drm-gm12u320-fix-the-timeout-usage-for-usb_bulk_msg.patch @@ -0,0 +1,59 @@ +From 89147983e2128e96a42a596af1f0b52abdb1fa2d Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 4 Sep 2023 10:14:20 +0800 +Subject: drm: gm12u320: Fix the timeout usage for usb_bulk_msg() + +From: Jinjie Ruan + +[ Upstream commit 7583028d359db3cd0072badcc576b4f9455fd27a ] + +The timeout arg of usb_bulk_msg() is ms already, which has been converted +to jiffies by msecs_to_jiffies() in usb_start_wait_urb(). So fix the usage +by removing the redundant msecs_to_jiffies() in the macros. + +And as Hans suggested, also remove msecs_to_jiffies() for the IDLE_TIMEOUT +macro to make it consistent here and so change IDLE_TIMEOUT to +msecs_to_jiffies(IDLE_TIMEOUT) where it is used. + +Fixes: e4f86e437164 ("drm: Add Grain Media GM12U320 driver v2") +Signed-off-by: Jinjie Ruan +Suggested-by: Hans de Goede +Reviewed-by: Hans de Goede +Signed-off-by: Thomas Zimmermann +Link: https://patchwork.freedesktop.org/patch/msgid/20230904021421.1663892-1-ruanjinjie@huawei.com +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/tiny/gm12u320.c | 10 +++++----- + 1 file changed, 5 insertions(+), 5 deletions(-) + +diff --git a/drivers/gpu/drm/tiny/gm12u320.c b/drivers/gpu/drm/tiny/gm12u320.c +index c5bb683e440c5..0187539ff5eaa 100644 +--- a/drivers/gpu/drm/tiny/gm12u320.c ++++ b/drivers/gpu/drm/tiny/gm12u320.c +@@ -70,10 +70,10 @@ MODULE_PARM_DESC(eco_mode, "Turn on Eco mode (less bright, more silent)"); + #define READ_STATUS_SIZE 13 + #define MISC_VALUE_SIZE 4 + +-#define CMD_TIMEOUT msecs_to_jiffies(200) +-#define DATA_TIMEOUT msecs_to_jiffies(1000) +-#define IDLE_TIMEOUT msecs_to_jiffies(2000) +-#define FIRST_FRAME_TIMEOUT msecs_to_jiffies(2000) ++#define CMD_TIMEOUT 200 ++#define DATA_TIMEOUT 1000 ++#define IDLE_TIMEOUT 2000 ++#define FIRST_FRAME_TIMEOUT 2000 + + #define MISC_REQ_GET_SET_ECO_A 0xff + #define MISC_REQ_GET_SET_ECO_B 0x35 +@@ -389,7 +389,7 @@ static void gm12u320_fb_update_work(struct work_struct *work) + * switches back to showing its logo. + */ + queue_delayed_work(system_long_wq, &gm12u320->fb_update.work, +- IDLE_TIMEOUT); ++ msecs_to_jiffies(IDLE_TIMEOUT)); + + return; + err: +-- +2.40.1 + diff --git a/queue-6.5/drm-mediatek-dp-change-logging-to-dev-for-mtk_dp_aux.patch b/queue-6.5/drm-mediatek-dp-change-logging-to-dev-for-mtk_dp_aux.patch new file mode 100644 index 00000000000..4ed2efd0809 --- /dev/null +++ b/queue-6.5/drm-mediatek-dp-change-logging-to-dev-for-mtk_dp_aux.patch @@ -0,0 +1,65 @@ +From 16b726fd8e949d1a1030e5ebd7716243b5a3fdc8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 25 Jul 2023 09:32:26 +0200 +Subject: drm/mediatek: dp: Change logging to dev for mtk_dp_aux_transfer() + +From: AngeloGioacchino Del Regno + +[ Upstream commit fd70e2019bfbcb0ed90c5e23839bf510ce6acf8f ] + +Change logging from drm_{err,info}() to dev_{err,info}() in functions +mtk_dp_aux_transfer() and mtk_dp_aux_do_transfer(): this will be +essential to avoid getting NULL pointer kernel panics if any kind +of error happens during AUX transfers happening before the bridge +is attached. + +This may potentially start happening in a later commit implementing +aux-bus support, as AUX transfers will be triggered from the panel +driver (for EDID) before the mtk-dp bridge gets attached, and it's +done in preparation for the same. + +Signed-off-by: AngeloGioacchino Del Regno +Tested-by: Chen-Yu Tsai +Reviewed-by: CK Hu +Reviewed-by: Alexandre Mergnat +Link: https://patchwork.kernel.org/project/dri-devel/patch/20230725073234.55892-4-angelogioacchino.delregno@collabora.com/ +Signed-off-by: Chun-Kuang Hu +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/mediatek/mtk_dp.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +diff --git a/drivers/gpu/drm/mediatek/mtk_dp.c b/drivers/gpu/drm/mediatek/mtk_dp.c +index c58b775877a31..076aa54910571 100644 +--- a/drivers/gpu/drm/mediatek/mtk_dp.c ++++ b/drivers/gpu/drm/mediatek/mtk_dp.c +@@ -847,7 +847,7 @@ static int mtk_dp_aux_do_transfer(struct mtk_dp *mtk_dp, bool is_read, u8 cmd, + u32 phy_status = mtk_dp_read(mtk_dp, MTK_DP_AUX_P0_3628) & + AUX_RX_PHY_STATE_AUX_TX_P0_MASK; + if (phy_status != AUX_RX_PHY_STATE_AUX_TX_P0_RX_IDLE) { +- drm_err(mtk_dp->drm_dev, ++ dev_err(mtk_dp->dev, + "AUX Rx Aux hang, need SW reset\n"); + return -EIO; + } +@@ -2062,7 +2062,7 @@ static ssize_t mtk_dp_aux_transfer(struct drm_dp_aux *mtk_aux, + is_read = true; + break; + default: +- drm_err(mtk_aux->drm_dev, "invalid aux cmd = %d\n", ++ dev_err(mtk_dp->dev, "invalid aux cmd = %d\n", + msg->request); + ret = -EINVAL; + goto err; +@@ -2078,7 +2078,7 @@ static ssize_t mtk_dp_aux_transfer(struct drm_dp_aux *mtk_aux, + to_access, &msg->reply); + + if (ret) { +- drm_info(mtk_dp->drm_dev, ++ dev_info(mtk_dp->dev, + "Failed to do AUX transfer: %d\n", ret); + goto err; + } +-- +2.40.1 + diff --git a/queue-6.5/drm-msm-adreno-use-quirk-identify-hw_apriv.patch b/queue-6.5/drm-msm-adreno-use-quirk-identify-hw_apriv.patch new file mode 100644 index 00000000000..3d7eeaae29c --- /dev/null +++ b/queue-6.5/drm-msm-adreno-use-quirk-identify-hw_apriv.patch @@ -0,0 +1,87 @@ +From eb1bc3fd1565469ea560183057e85baa239dd78c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 27 Jul 2023 14:20:09 -0700 +Subject: drm/msm/adreno: Use quirk identify hw_apriv + +From: Rob Clark + +[ Upstream commit 459f9e26e7d49f80f587d7592ccb78e00ab458e4 ] + +Rather than just open coding a list of gpu-id matches. + +Signed-off-by: Rob Clark +Reviewed-by: Konrad Dybcio +Reviewed-by: Dmitry Baryshkov +Patchwork: https://patchwork.freedesktop.org/patch/549764/ +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/msm/adreno/a6xx_gpu.c | 3 +-- + drivers/gpu/drm/msm/adreno/adreno_device.c | 4 ++++ + drivers/gpu/drm/msm/adreno/adreno_gpu.h | 1 + + 3 files changed, 6 insertions(+), 2 deletions(-) + +diff --git a/drivers/gpu/drm/msm/adreno/a6xx_gpu.c b/drivers/gpu/drm/msm/adreno/a6xx_gpu.c +index a2513f7168238..f6c6147640173 100644 +--- a/drivers/gpu/drm/msm/adreno/a6xx_gpu.c ++++ b/drivers/gpu/drm/msm/adreno/a6xx_gpu.c +@@ -2489,8 +2489,7 @@ struct msm_gpu *a6xx_gpu_init(struct drm_device *dev) + /* Quirk data */ + adreno_gpu->info = info; + +- if (adreno_is_a650(adreno_gpu) || adreno_is_a660_family(adreno_gpu)) +- adreno_gpu->base.hw_apriv = true; ++ adreno_gpu->base.hw_apriv = !!(info->quirks & ADRENO_QUIRK_HAS_HW_APRIV); + + a6xx_llc_slices_init(pdev, a6xx_gpu); + +diff --git a/drivers/gpu/drm/msm/adreno/adreno_device.c b/drivers/gpu/drm/msm/adreno/adreno_device.c +index 6e3c1368c5e15..41bccf6009fb6 100644 +--- a/drivers/gpu/drm/msm/adreno/adreno_device.c ++++ b/drivers/gpu/drm/msm/adreno/adreno_device.c +@@ -325,6 +325,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_1M + SZ_128K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .zapfw = "a650_zap.mdt", + .hwcg = a650_hwcg, +@@ -339,6 +340,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_1M + SZ_512K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .zapfw = "a660_zap.mdt", + .hwcg = a660_hwcg, +@@ -351,6 +353,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_512K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .hwcg = a660_hwcg, + .address_space_size = SZ_16G, +@@ -375,6 +378,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_4M, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .zapfw = "a690_zap.mdt", + .hwcg = a690_hwcg, +diff --git a/drivers/gpu/drm/msm/adreno/adreno_gpu.h b/drivers/gpu/drm/msm/adreno/adreno_gpu.h +index 845019891ad19..a925e04a2283c 100644 +--- a/drivers/gpu/drm/msm/adreno/adreno_gpu.h ++++ b/drivers/gpu/drm/msm/adreno/adreno_gpu.h +@@ -32,6 +32,7 @@ enum { + #define ADRENO_QUIRK_TWO_PASS_USE_WFI BIT(0) + #define ADRENO_QUIRK_FAULT_DETECT_MASK BIT(1) + #define ADRENO_QUIRK_LMLOADKILL_DISABLE BIT(2) ++#define ADRENO_QUIRK_HAS_HW_APRIV BIT(3) + + struct adreno_rev { + uint8_t core; +-- +2.40.1 + diff --git a/queue-6.5/drm-msm-adreno-use-quirk-to-identify-cached-coherent.patch b/queue-6.5/drm-msm-adreno-use-quirk-to-identify-cached-coherent.patch new file mode 100644 index 00000000000..e2750311489 --- /dev/null +++ b/queue-6.5/drm-msm-adreno-use-quirk-to-identify-cached-coherent.patch @@ -0,0 +1,135 @@ +From c64a6b79ed4daacc215ec3a30f7231a340310e64 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 27 Jul 2023 14:20:10 -0700 +Subject: drm/msm/adreno: Use quirk to identify cached-coherent support + +From: Rob Clark + +[ Upstream commit 155668ef412fc82ff3172666831d95770141cdd6 ] + +It is better to explicitly list it. With the move to opaque chip-id's +for future devices, we should avoid trying to infer things like +generation from the numerical value. + +Signed-off-by: Rob Clark +Reviewed-by: Konrad Dybcio +Reviewed-by: Dmitry Baryshkov +Patchwork: https://patchwork.freedesktop.org/patch/549765/ +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/msm/adreno/adreno_device.c | 23 +++++++++++++++------- + drivers/gpu/drm/msm/adreno/adreno_gpu.h | 1 + + 2 files changed, 17 insertions(+), 7 deletions(-) + +diff --git a/drivers/gpu/drm/msm/adreno/adreno_device.c b/drivers/gpu/drm/msm/adreno/adreno_device.c +index 41bccf6009fb6..b2283faa173ac 100644 +--- a/drivers/gpu/drm/msm/adreno/adreno_device.c ++++ b/drivers/gpu/drm/msm/adreno/adreno_device.c +@@ -275,6 +275,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_512K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT, + .init = a6xx_gpu_init, + }, { + .rev = ADRENO_REV(6, 1, 9, ANY_ID), +@@ -286,6 +287,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_512K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT, + .init = a6xx_gpu_init, + .zapfw = "a615_zap.mdt", + .hwcg = a615_hwcg, +@@ -299,6 +301,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_1M, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT, + .init = a6xx_gpu_init, + .zapfw = "a630_zap.mdt", + .hwcg = a630_hwcg, +@@ -312,6 +315,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_1M, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT, + .init = a6xx_gpu_init, + .zapfw = "a640_zap.mdt", + .hwcg = a640_hwcg, +@@ -325,7 +329,8 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_1M + SZ_128K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, +- .quirks = ADRENO_QUIRK_HAS_HW_APRIV, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT | ++ ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .zapfw = "a650_zap.mdt", + .hwcg = a650_hwcg, +@@ -340,7 +345,8 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_1M + SZ_512K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, +- .quirks = ADRENO_QUIRK_HAS_HW_APRIV, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT | ++ ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .zapfw = "a660_zap.mdt", + .hwcg = a660_hwcg, +@@ -353,7 +359,8 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_512K, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, +- .quirks = ADRENO_QUIRK_HAS_HW_APRIV, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT | ++ ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .hwcg = a660_hwcg, + .address_space_size = SZ_16G, +@@ -367,6 +374,7 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_2M, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT, + .init = a6xx_gpu_init, + .zapfw = "a640_zap.mdt", + .hwcg = a640_hwcg, +@@ -378,7 +386,8 @@ static const struct adreno_info gpulist[] = { + }, + .gmem = SZ_4M, + .inactive_period = DRM_MSM_INACTIVE_PERIOD, +- .quirks = ADRENO_QUIRK_HAS_HW_APRIV, ++ .quirks = ADRENO_QUIRK_HAS_CACHED_COHERENT | ++ ADRENO_QUIRK_HAS_HW_APRIV, + .init = a6xx_gpu_init, + .zapfw = "a690_zap.mdt", + .hwcg = a690_hwcg, +@@ -590,9 +599,9 @@ static int adreno_bind(struct device *dev, struct device *master, void *data) + if (ret) + return ret; + +- if (config.rev.core >= 6) +- if (!adreno_has_gmu_wrapper(to_adreno_gpu(gpu))) +- priv->has_cached_coherent = true; ++ priv->has_cached_coherent = ++ !!(info->quirks & ADRENO_QUIRK_HAS_CACHED_COHERENT) && ++ !adreno_has_gmu_wrapper(to_adreno_gpu(gpu)); + + return 0; + } +diff --git a/drivers/gpu/drm/msm/adreno/adreno_gpu.h b/drivers/gpu/drm/msm/adreno/adreno_gpu.h +index a925e04a2283c..129771563f3fd 100644 +--- a/drivers/gpu/drm/msm/adreno/adreno_gpu.h ++++ b/drivers/gpu/drm/msm/adreno/adreno_gpu.h +@@ -33,6 +33,7 @@ enum { + #define ADRENO_QUIRK_FAULT_DETECT_MASK BIT(1) + #define ADRENO_QUIRK_LMLOADKILL_DISABLE BIT(2) + #define ADRENO_QUIRK_HAS_HW_APRIV BIT(3) ++#define ADRENO_QUIRK_HAS_CACHED_COHERENT BIT(4) + + struct adreno_rev { + uint8_t core; +-- +2.40.1 + diff --git a/queue-6.5/efi-unaccepted-use-acpi-reclaim-memory-for-unaccepte.patch b/queue-6.5/efi-unaccepted-use-acpi-reclaim-memory-for-unaccepte.patch new file mode 100644 index 00000000000..5f2d3947bff --- /dev/null +++ b/queue-6.5/efi-unaccepted-use-acpi-reclaim-memory-for-unaccepte.patch @@ -0,0 +1,55 @@ +From 9fc76127512229b74539276e0e7880beea85c0bf Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 16 Aug 2023 21:05:57 +0200 +Subject: efi/unaccepted: Use ACPI reclaim memory for unaccepted memory table + +From: Ard Biesheuvel + +[ Upstream commit e7761d827e99919c32400056a884e481ef008ec4 ] + +Kyril reports that crashkernels fail to work on confidential VMs that +rely on the unaccepted memory table, and this appears to be caused by +the fact that it is not considered part of the set of firmware tables +that the crashkernel needs to map. + +This is an oversight, and a result of the use of the EFI_LOADER_DATA +memory type for this table. The correct memory type to use for any +firmware table is EFI_ACPI_RECLAIM_MEMORY (including ones created by the +EFI stub), even though the name suggests that is it specific to ACPI. +ACPI reclaim means that the memory is used by the firmware to expose +information to the operating system, but that the memory region has no +special significance to the firmware itself, and the OS is free to +reclaim the memory and use it as ordinary memory if it is not interested +in the contents, or if it has already consumed them. In Linux, this +memory is never reclaimed, but it is always covered by the kernel direct +map and generally made accessible as ordinary memory. + +On x86, ACPI reclaim memory is translated into E820_ACPI, which the +kexec logic already recognizes as memory that the crashkernel may need +to to access, and so it will be mapped and accessible to the booting +crash kernel. + +Fixes: 745e3ed85f71 ("efi/libstub: Implement support for unaccepted memory") +Reported-by: Kirill A. Shutemov +Signed-off-by: Ard Biesheuvel +Signed-off-by: Sasha Levin +--- + drivers/firmware/efi/libstub/unaccepted_memory.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/firmware/efi/libstub/unaccepted_memory.c b/drivers/firmware/efi/libstub/unaccepted_memory.c +index ca61f4733ea58..9a655f30ba47d 100644 +--- a/drivers/firmware/efi/libstub/unaccepted_memory.c ++++ b/drivers/firmware/efi/libstub/unaccepted_memory.c +@@ -62,7 +62,7 @@ efi_status_t allocate_unaccepted_bitmap(__u32 nr_desc, + bitmap_size = DIV_ROUND_UP(unaccepted_end - unaccepted_start, + EFI_UNACCEPTED_UNIT_SIZE * BITS_PER_BYTE); + +- status = efi_bs_call(allocate_pool, EFI_LOADER_DATA, ++ status = efi_bs_call(allocate_pool, EFI_ACPI_RECLAIM_MEMORY, + sizeof(*unaccepted_table) + bitmap_size, + (void **)&unaccepted_table); + if (status != EFI_SUCCESS) { +-- +2.40.1 + diff --git a/queue-6.5/efivarfs-fix-statfs-on-efivarfs.patch b/queue-6.5/efivarfs-fix-statfs-on-efivarfs.patch new file mode 100644 index 00000000000..a4f812d3b9a --- /dev/null +++ b/queue-6.5/efivarfs-fix-statfs-on-efivarfs.patch @@ -0,0 +1,57 @@ +From 5b822d83e40e1b537c7d5f9aca1e6d45d235c0c6 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 10 Sep 2023 06:54:45 +0200 +Subject: efivarfs: fix statfs() on efivarfs + +From: Heinrich Schuchardt + +[ Upstream commit 79b83606abc778aa3cbee535b362ce905d0b9448 ] + +Some firmware (notably U-Boot) provides GetVariable() and +GetNextVariableName() but not QueryVariableInfo(). + +With commit d86ff3333cb1 ("efivarfs: expose used and total size") the +statfs syscall was broken for such firmware. + +If QueryVariableInfo() does not exist or returns EFI_UNSUPPORTED, just +report the file system size as 0 as statfs_simple() previously did. + +Fixes: d86ff3333cb1 ("efivarfs: expose used and total size") +Link: https://lore.kernel.org/all/20230910045445.41632-1-heinrich.schuchardt@canonical.com/ +Signed-off-by: Heinrich Schuchardt +[ardb: log warning on QueryVariableInfo() failure] +Reviewed-by: Ilias Apalodimas +Signed-off-by: Ard Biesheuvel +Signed-off-by: Sasha Levin +--- + fs/efivarfs/super.c | 14 ++++++++++---- + 1 file changed, 10 insertions(+), 4 deletions(-) + +diff --git a/fs/efivarfs/super.c b/fs/efivarfs/super.c +index e028fafa04f38..996271473609a 100644 +--- a/fs/efivarfs/super.c ++++ b/fs/efivarfs/super.c +@@ -32,10 +32,16 @@ static int efivarfs_statfs(struct dentry *dentry, struct kstatfs *buf) + u64 storage_space, remaining_space, max_variable_size; + efi_status_t status; + +- status = efivar_query_variable_info(attr, &storage_space, &remaining_space, +- &max_variable_size); +- if (status != EFI_SUCCESS) +- return efi_status_to_err(status); ++ /* Some UEFI firmware does not implement QueryVariableInfo() */ ++ storage_space = remaining_space = 0; ++ if (efi_rt_services_supported(EFI_RT_SUPPORTED_QUERY_VARIABLE_INFO)) { ++ status = efivar_query_variable_info(attr, &storage_space, ++ &remaining_space, ++ &max_variable_size); ++ if (status != EFI_SUCCESS && status != EFI_UNSUPPORTED) ++ pr_warn_ratelimited("query_variable_info() failed: 0x%lx\n", ++ status); ++ } + + /* + * This is not a normal filesystem, so no point in pretending it has a block +-- +2.40.1 + diff --git a/queue-6.5/ext2-fix-datatype-of-block-number-in-ext2_xattr_set2.patch b/queue-6.5/ext2-fix-datatype-of-block-number-in-ext2_xattr_set2.patch new file mode 100644 index 00000000000..11402aa2ed6 --- /dev/null +++ b/queue-6.5/ext2-fix-datatype-of-block-number-in-ext2_xattr_set2.patch @@ -0,0 +1,55 @@ +From 093427c9ed7b436520d43af315a7edc30a0826d5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 12:03:40 +0200 +Subject: ext2: fix datatype of block number in ext2_xattr_set2() + +From: Georg Ottinger + +[ Upstream commit e88076348425b7d0491c8c98d8732a7df8de7aa3 ] + +I run a small server that uses external hard drives for backups. The +backup software I use uses ext2 filesystems with 4KiB block size and +the server is running SELinux and therefore relies on xattr. I recently +upgraded the hard drives from 4TB to 12TB models. I noticed that after +transferring some TBs I got a filesystem error "Freeing blocks not in +datazone - block = 18446744071529317386, count = 1" and the backup +process stopped. Trying to fix the fs with e2fsck resulted in a +completely corrupted fs. The error probably came from ext2_free_blocks(), +and because of the large number 18e19 this problem immediately looked +like some kind of integer overflow. Whereas the 4TB fs was about 1e9 +blocks, the new 12TB is about 3e9 blocks. So, searching the ext2 code, +I came across the line in fs/ext2/xattr.c:745 where ext2_new_block() +is called and the resulting block number is stored in the variable block +as an int datatype. If a block with a block number greater than +INT32_MAX is returned, this variable overflows and the call to +sb_getblk() at line fs/ext2/xattr.c:750 fails, then the call to +ext2_free_blocks() produces the error. + +Signed-off-by: Georg Ottinger +Signed-off-by: Jan Kara +Message-Id: <20230815100340.22121-1-g.ottinger@gmx.at> +Signed-off-by: Sasha Levin +--- + fs/ext2/xattr.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/fs/ext2/xattr.c b/fs/ext2/xattr.c +index 8906ba479aafb..89517937d36c4 100644 +--- a/fs/ext2/xattr.c ++++ b/fs/ext2/xattr.c +@@ -742,10 +742,10 @@ ext2_xattr_set2(struct inode *inode, struct buffer_head *old_bh, + /* We need to allocate a new block */ + ext2_fsblk_t goal = ext2_group_first_block_no(sb, + EXT2_I(inode)->i_block_group); +- int block = ext2_new_block(inode, goal, &error); ++ ext2_fsblk_t block = ext2_new_block(inode, goal, &error); + if (error) + goto cleanup; +- ea_idebug(inode, "creating block %d", block); ++ ea_idebug(inode, "creating block %lu", block); + + new_bh = sb_getblk(sb, block); + if (unlikely(!new_bh)) { +-- +2.40.1 + diff --git a/queue-6.5/ext4-add-two-helper-functions-extent_logical_end-and.patch b/queue-6.5/ext4-add-two-helper-functions-extent_logical_end-and.patch new file mode 100644 index 00000000000..e5bc48638ff --- /dev/null +++ b/queue-6.5/ext4-add-two-helper-functions-extent_logical_end-and.patch @@ -0,0 +1,97 @@ +From fe6f11874433799f3964a59aae0283140898d017 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 24 Jul 2023 20:10:57 +0800 +Subject: ext4: add two helper functions extent_logical_end() and + pa_logical_end() + +From: Baokun Li + +[ Upstream commit 43bbddc067883d94de7a43d5756a295439fbe37d ] + +When we use lstart + len to calculate the end of free extent or prealloc +space, it may exceed the maximum value of 4294967295(0xffffffff) supported +by ext4_lblk_t and cause overflow, which may lead to various problems. + +Therefore, we add two helper functions, extent_logical_end() and +pa_logical_end(), to limit the type of end to loff_t, and also convert +lstart to loff_t for calculation to avoid overflow. + +Signed-off-by: Baokun Li +Reviewed-by: Ritesh Harjani (IBM) +Link: https://lore.kernel.org/r/20230724121059.11834-2-libaokun1@huawei.com +Signed-off-by: Theodore Ts'o +Signed-off-by: Sasha Levin +--- + fs/ext4/mballoc.c | 9 +++------ + fs/ext4/mballoc.h | 14 ++++++++++++++ + 2 files changed, 17 insertions(+), 6 deletions(-) + +diff --git a/fs/ext4/mballoc.c b/fs/ext4/mballoc.c +index a197ef71b7b02..627c813cf0759 100644 +--- a/fs/ext4/mballoc.c ++++ b/fs/ext4/mballoc.c +@@ -4433,7 +4433,7 @@ ext4_mb_normalize_request(struct ext4_allocation_context *ac, + + /* first, let's learn actual file size + * given current request is allocated */ +- size = ac->ac_o_ex.fe_logical + EXT4_C2B(sbi, ac->ac_o_ex.fe_len); ++ size = extent_logical_end(sbi, &ac->ac_o_ex); + size = size << bsbits; + if (size < i_size_read(ac->ac_inode)) + size = i_size_read(ac->ac_inode); +@@ -4767,7 +4767,6 @@ ext4_mb_use_preallocated(struct ext4_allocation_context *ac) + struct ext4_inode_info *ei = EXT4_I(ac->ac_inode); + struct ext4_locality_group *lg; + struct ext4_prealloc_space *tmp_pa = NULL, *cpa = NULL; +- loff_t tmp_pa_end; + struct rb_node *iter; + ext4_fsblk_t goal_block; + +@@ -4863,9 +4862,7 @@ ext4_mb_use_preallocated(struct ext4_allocation_context *ac) + * pa can possibly satisfy the request hence check if it overlaps + * original logical start and stop searching if it doesn't. + */ +- tmp_pa_end = (loff_t)tmp_pa->pa_lstart + EXT4_C2B(sbi, tmp_pa->pa_len); +- +- if (ac->ac_o_ex.fe_logical >= tmp_pa_end) { ++ if (ac->ac_o_ex.fe_logical >= pa_logical_end(sbi, tmp_pa)) { + spin_unlock(&tmp_pa->pa_lock); + goto try_group_pa; + } +@@ -5770,7 +5767,7 @@ static void ext4_mb_group_or_file(struct ext4_allocation_context *ac) + + group_pa_eligible = sbi->s_mb_group_prealloc > 0; + inode_pa_eligible = true; +- size = ac->ac_o_ex.fe_logical + EXT4_C2B(sbi, ac->ac_o_ex.fe_len); ++ size = extent_logical_end(sbi, &ac->ac_o_ex); + isize = (i_size_read(ac->ac_inode) + ac->ac_sb->s_blocksize - 1) + >> bsbits; + +diff --git a/fs/ext4/mballoc.h b/fs/ext4/mballoc.h +index df6b5e7c22741..d7aeb5da7d867 100644 +--- a/fs/ext4/mballoc.h ++++ b/fs/ext4/mballoc.h +@@ -233,6 +233,20 @@ static inline ext4_fsblk_t ext4_grp_offs_to_block(struct super_block *sb, + (fex->fe_start << EXT4_SB(sb)->s_cluster_bits); + } + ++static inline loff_t extent_logical_end(struct ext4_sb_info *sbi, ++ struct ext4_free_extent *fex) ++{ ++ /* Use loff_t to avoid end exceeding ext4_lblk_t max. */ ++ return (loff_t)fex->fe_logical + EXT4_C2B(sbi, fex->fe_len); ++} ++ ++static inline loff_t pa_logical_end(struct ext4_sb_info *sbi, ++ struct ext4_prealloc_space *pa) ++{ ++ /* Use loff_t to avoid end exceeding ext4_lblk_t max. */ ++ return (loff_t)pa->pa_lstart + EXT4_C2B(sbi, pa->pa_len); ++} ++ + typedef int (*ext4_mballoc_query_range_fn)( + struct super_block *sb, + ext4_group_t agno, +-- +2.40.1 + diff --git a/queue-6.5/ext4-avoid-overlapping-preallocations-due-to-overflo.patch b/queue-6.5/ext4-avoid-overlapping-preallocations-due-to-overflo.patch new file mode 100644 index 00000000000..0d006bf95e6 --- /dev/null +++ b/queue-6.5/ext4-avoid-overlapping-preallocations-due-to-overflo.patch @@ -0,0 +1,107 @@ +From 0452d65101de63b63569eeb8aed51334fb5c4008 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 24 Jul 2023 20:10:59 +0800 +Subject: ext4: avoid overlapping preallocations due to overflow + +From: Baokun Li + +[ Upstream commit bedc5d34632c21b5adb8ca7143d4c1f794507e4c ] + +Let's say we want to allocate 2 blocks starting from 4294966386, after +predicting the file size, start is aligned to 4294965248, len is changed +to 2048, then end = start + size = 0x100000000. Since end is of +type ext4_lblk_t, i.e. uint, end is truncated to 0. + +This causes (pa->pa_lstart >= end) to always hold when checking if the +current extent to be allocated crosses already preallocated blocks, so the +resulting ac_g_ex may cross already preallocated blocks. Hence we convert +the end type to loff_t and use pa_logical_end() to avoid overflow. + +Signed-off-by: Baokun Li +Reviewed-by: Ritesh Harjani (IBM) +Link: https://lore.kernel.org/r/20230724121059.11834-4-libaokun1@huawei.com +Signed-off-by: Theodore Ts'o +Signed-off-by: Sasha Levin +--- + fs/ext4/mballoc.c | 21 ++++++++++----------- + 1 file changed, 10 insertions(+), 11 deletions(-) + +diff --git a/fs/ext4/mballoc.c b/fs/ext4/mballoc.c +index 627c813cf0759..5c3055a32e57a 100644 +--- a/fs/ext4/mballoc.c ++++ b/fs/ext4/mballoc.c +@@ -4223,12 +4223,13 @@ ext4_mb_pa_rb_next_iter(ext4_lblk_t new_start, ext4_lblk_t cur_start, struct rb_ + + static inline void + ext4_mb_pa_assert_overlap(struct ext4_allocation_context *ac, +- ext4_lblk_t start, ext4_lblk_t end) ++ ext4_lblk_t start, loff_t end) + { + struct ext4_sb_info *sbi = EXT4_SB(ac->ac_sb); + struct ext4_inode_info *ei = EXT4_I(ac->ac_inode); + struct ext4_prealloc_space *tmp_pa; +- ext4_lblk_t tmp_pa_start, tmp_pa_end; ++ ext4_lblk_t tmp_pa_start; ++ loff_t tmp_pa_end; + struct rb_node *iter; + + read_lock(&ei->i_prealloc_lock); +@@ -4237,7 +4238,7 @@ ext4_mb_pa_assert_overlap(struct ext4_allocation_context *ac, + tmp_pa = rb_entry(iter, struct ext4_prealloc_space, + pa_node.inode_node); + tmp_pa_start = tmp_pa->pa_lstart; +- tmp_pa_end = tmp_pa->pa_lstart + EXT4_C2B(sbi, tmp_pa->pa_len); ++ tmp_pa_end = pa_logical_end(sbi, tmp_pa); + + spin_lock(&tmp_pa->pa_lock); + if (tmp_pa->pa_deleted == 0) +@@ -4259,14 +4260,14 @@ ext4_mb_pa_assert_overlap(struct ext4_allocation_context *ac, + */ + static inline void + ext4_mb_pa_adjust_overlap(struct ext4_allocation_context *ac, +- ext4_lblk_t *start, ext4_lblk_t *end) ++ ext4_lblk_t *start, loff_t *end) + { + struct ext4_inode_info *ei = EXT4_I(ac->ac_inode); + struct ext4_sb_info *sbi = EXT4_SB(ac->ac_sb); + struct ext4_prealloc_space *tmp_pa = NULL, *left_pa = NULL, *right_pa = NULL; + struct rb_node *iter; +- ext4_lblk_t new_start, new_end; +- ext4_lblk_t tmp_pa_start, tmp_pa_end, left_pa_end = -1, right_pa_start = -1; ++ ext4_lblk_t new_start, tmp_pa_start, right_pa_start = -1; ++ loff_t new_end, tmp_pa_end, left_pa_end = -1; + + new_start = *start; + new_end = *end; +@@ -4285,7 +4286,7 @@ ext4_mb_pa_adjust_overlap(struct ext4_allocation_context *ac, + tmp_pa = rb_entry(iter, struct ext4_prealloc_space, + pa_node.inode_node); + tmp_pa_start = tmp_pa->pa_lstart; +- tmp_pa_end = tmp_pa->pa_lstart + EXT4_C2B(sbi, tmp_pa->pa_len); ++ tmp_pa_end = pa_logical_end(sbi, tmp_pa); + + /* PA must not overlap original request */ + spin_lock(&tmp_pa->pa_lock); +@@ -4365,8 +4366,7 @@ ext4_mb_pa_adjust_overlap(struct ext4_allocation_context *ac, + } + + if (left_pa) { +- left_pa_end = +- left_pa->pa_lstart + EXT4_C2B(sbi, left_pa->pa_len); ++ left_pa_end = pa_logical_end(sbi, left_pa); + BUG_ON(left_pa_end > ac->ac_o_ex.fe_logical); + } + +@@ -4405,8 +4405,7 @@ ext4_mb_normalize_request(struct ext4_allocation_context *ac, + struct ext4_sb_info *sbi = EXT4_SB(ac->ac_sb); + struct ext4_super_block *es = sbi->s_es; + int bsbits, max; +- ext4_lblk_t end; +- loff_t size, start_off; ++ loff_t size, start_off, end; + loff_t orig_size __maybe_unused; + ext4_lblk_t start; + +-- +2.40.1 + diff --git a/queue-6.5/ext4-fix-bug-in-ext4_mb_new_inode_pa-due-to-overflow.patch b/queue-6.5/ext4-fix-bug-in-ext4_mb_new_inode_pa-due-to-overflow.patch new file mode 100644 index 00000000000..c2f319c5cac --- /dev/null +++ b/queue-6.5/ext4-fix-bug-in-ext4_mb_new_inode_pa-due-to-overflow.patch @@ -0,0 +1,122 @@ +From b519bdc661be04e28785821a7032a84f11ce5d36 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 24 Jul 2023 20:10:58 +0800 +Subject: ext4: fix BUG in ext4_mb_new_inode_pa() due to overflow + +From: Baokun Li + +[ Upstream commit bc056e7163ac7db945366de219745cf94f32a3e6 ] + +When we calculate the end position of ext4_free_extent, this position may +be exactly where ext4_lblk_t (i.e. uint) overflows. For example, if +ac_g_ex.fe_logical is 4294965248 and ac_orig_goal_len is 2048, then the +computed end is 0x100000000, which is 0. If ac->ac_o_ex.fe_logical is not +the first case of adjusting the best extent, that is, new_bex_end > 0, the +following BUG_ON will be triggered: + +========================================================= +kernel BUG at fs/ext4/mballoc.c:5116! +invalid opcode: 0000 [#1] PREEMPT SMP PTI +CPU: 3 PID: 673 Comm: xfs_io Tainted: G E 6.5.0-rc1+ #279 +RIP: 0010:ext4_mb_new_inode_pa+0xc5/0x430 +Call Trace: + + ext4_mb_use_best_found+0x203/0x2f0 + ext4_mb_try_best_found+0x163/0x240 + ext4_mb_regular_allocator+0x158/0x1550 + ext4_mb_new_blocks+0x86a/0xe10 + ext4_ext_map_blocks+0xb0c/0x13a0 + ext4_map_blocks+0x2cd/0x8f0 + ext4_iomap_begin+0x27b/0x400 + iomap_iter+0x222/0x3d0 + __iomap_dio_rw+0x243/0xcb0 + iomap_dio_rw+0x16/0x80 +========================================================= + +A simple reproducer demonstrating the problem: + + mkfs.ext4 -F /dev/sda -b 4096 100M + mount /dev/sda /tmp/test + fallocate -l1M /tmp/test/tmp + fallocate -l10M /tmp/test/file + fallocate -i -o 1M -l16777203M /tmp/test/file + fsstress -d /tmp/test -l 0 -n 100000 -p 8 & + sleep 10 && killall -9 fsstress + rm -f /tmp/test/tmp + xfs_io -c "open -ad /tmp/test/file" -c "pwrite -S 0xff 0 8192" + +We simply refactor the logic for adjusting the best extent by adding +a temporary ext4_free_extent ex and use extent_logical_end() to avoid +overflow, which also simplifies the code. + +Cc: stable@kernel.org # 6.4 +Fixes: 93cdf49f6eca ("ext4: Fix best extent lstart adjustment logic in ext4_mb_new_inode_pa()") +Signed-off-by: Baokun Li +Reviewed-by: Ritesh Harjani (IBM) +Link: https://lore.kernel.org/r/20230724121059.11834-3-libaokun1@huawei.com +Signed-off-by: Theodore Ts'o +Signed-off-by: Sasha Levin +--- + fs/ext4/mballoc.c | 31 ++++++++++++++----------------- + 1 file changed, 14 insertions(+), 17 deletions(-) + +diff --git a/fs/ext4/mballoc.c b/fs/ext4/mballoc.c +index 5c3055a32e57a..bd7557d8dec41 100644 +--- a/fs/ext4/mballoc.c ++++ b/fs/ext4/mballoc.c +@@ -5177,8 +5177,11 @@ ext4_mb_new_inode_pa(struct ext4_allocation_context *ac) + pa = ac->ac_pa; + + if (ac->ac_b_ex.fe_len < ac->ac_orig_goal_len) { +- int new_bex_start; +- int new_bex_end; ++ struct ext4_free_extent ex = { ++ .fe_logical = ac->ac_g_ex.fe_logical, ++ .fe_len = ac->ac_orig_goal_len, ++ }; ++ loff_t orig_goal_end = extent_logical_end(sbi, &ex); + + /* we can't allocate as much as normalizer wants. + * so, found space must get proper lstart +@@ -5197,29 +5200,23 @@ ext4_mb_new_inode_pa(struct ext4_allocation_context *ac) + * still cover original start + * 3. Else, keep the best ex at start of original request. + */ +- new_bex_end = ac->ac_g_ex.fe_logical + +- EXT4_C2B(sbi, ac->ac_orig_goal_len); +- new_bex_start = new_bex_end - EXT4_C2B(sbi, ac->ac_b_ex.fe_len); +- if (ac->ac_o_ex.fe_logical >= new_bex_start) +- goto adjust_bex; ++ ex.fe_len = ac->ac_b_ex.fe_len; + +- new_bex_start = ac->ac_g_ex.fe_logical; +- new_bex_end = +- new_bex_start + EXT4_C2B(sbi, ac->ac_b_ex.fe_len); +- if (ac->ac_o_ex.fe_logical < new_bex_end) ++ ex.fe_logical = orig_goal_end - EXT4_C2B(sbi, ex.fe_len); ++ if (ac->ac_o_ex.fe_logical >= ex.fe_logical) + goto adjust_bex; + +- new_bex_start = ac->ac_o_ex.fe_logical; +- new_bex_end = +- new_bex_start + EXT4_C2B(sbi, ac->ac_b_ex.fe_len); ++ ex.fe_logical = ac->ac_g_ex.fe_logical; ++ if (ac->ac_o_ex.fe_logical < extent_logical_end(sbi, &ex)) ++ goto adjust_bex; + ++ ex.fe_logical = ac->ac_o_ex.fe_logical; + adjust_bex: +- ac->ac_b_ex.fe_logical = new_bex_start; ++ ac->ac_b_ex.fe_logical = ex.fe_logical; + + BUG_ON(ac->ac_o_ex.fe_logical < ac->ac_b_ex.fe_logical); + BUG_ON(ac->ac_o_ex.fe_len > ac->ac_b_ex.fe_len); +- BUG_ON(new_bex_end > (ac->ac_g_ex.fe_logical + +- EXT4_C2B(sbi, ac->ac_orig_goal_len))); ++ BUG_ON(extent_logical_end(sbi, &ex) > orig_goal_end); + } + + pa->pa_lstart = ac->ac_b_ex.fe_logical; +-- +2.40.1 + diff --git a/queue-6.5/fix-nomenclature-for-usb-and-pci-wireless-devices.patch b/queue-6.5/fix-nomenclature-for-usb-and-pci-wireless-devices.patch new file mode 100644 index 00000000000..23d84fac0ff --- /dev/null +++ b/queue-6.5/fix-nomenclature-for-usb-and-pci-wireless-devices.patch @@ -0,0 +1,468 @@ +From b068db538d3ed9567c80c479b13942904789ac10 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 20:44:48 -0400 +Subject: Fix nomenclature for USB and PCI wireless devices + +From: Alan Stern + +[ Upstream commit 5d7cf67f72ae34d38e090bdfa673da4aefe4048e ] + +A mouse that uses a USB connection is called a "USB mouse" device (or +"USB mouse" for short), not a "mouse USB" device. By analogy, a WiFi +adapter that connects to the host computer via USB is a "USB wireless" +device, not a "wireless USB" device. (The latter term more properly +refers to a defunct Wireless USB specification, which described a +technology for sending USB protocol messages over an ultra wideband +radio link.) + +Similarly for a WiFi adapter card that plugs into a PCIe slot: It is a +"PCIe wireless" device, not a "wireless PCIe" device. + +Rephrase the text in the kernel source where the word ordering is +wrong. + +Signed-off-by: Alan Stern +Reviewed-by: Greg Kroah-Hartman +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/57da7c80-0e48-41b5-8427-884a02648f55@rowland.harvard.edu +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath10k/pci.c | 2 +- + drivers/net/wireless/ath/ath10k/usb.c | 2 +- + drivers/net/wireless/ath/ath11k/pci.c | 2 +- + drivers/net/wireless/ath/ath12k/pci.c | 2 +- + drivers/net/wireless/atmel/at76c50x-usb.c | 8 ++-- + .../wireless/intersil/orinoco/orinoco_usb.c | 12 ++--- + drivers/net/wireless/legacy/rndis_wlan.c | 2 +- + .../net/wireless/mediatek/mt76/mt7603/Kconfig | 2 +- + .../net/wireless/mediatek/mt76/mt7615/Kconfig | 2 +- + .../net/wireless/mediatek/mt76/mt76x0/Kconfig | 4 +- + .../net/wireless/mediatek/mt76/mt76x2/Kconfig | 4 +- + .../net/wireless/mediatek/mt76/mt7915/Kconfig | 2 +- + .../net/wireless/mediatek/mt76/mt7996/Kconfig | 2 +- + drivers/net/wireless/mediatek/mt7601u/Kconfig | 2 +- + drivers/net/wireless/purelifi/plfxlc/Kconfig | 2 +- + drivers/net/wireless/ralink/rt2x00/Kconfig | 2 +- + drivers/net/wireless/realtek/rtw88/pci.c | 2 +- + drivers/net/wireless/realtek/rtw88/usb.c | 2 +- + drivers/net/wireless/realtek/rtw89/pci.c | 2 +- + drivers/net/wireless/zydas/zd1201.c | 6 +-- + drivers/platform/x86/eeepc-laptop.c | 2 +- + drivers/staging/wlan-ng/prism2usb.c | 48 +++++++++---------- + 22 files changed, 57 insertions(+), 57 deletions(-) + +diff --git a/drivers/net/wireless/ath/ath10k/pci.c b/drivers/net/wireless/ath/ath10k/pci.c +index 9275a672f90cb..73463ded42045 100644 +--- a/drivers/net/wireless/ath/ath10k/pci.c ++++ b/drivers/net/wireless/ath/ath10k/pci.c +@@ -3817,7 +3817,7 @@ static void __exit ath10k_pci_exit(void) + module_exit(ath10k_pci_exit); + + MODULE_AUTHOR("Qualcomm Atheros"); +-MODULE_DESCRIPTION("Driver support for Qualcomm Atheros 802.11ac WLAN PCIe/AHB devices"); ++MODULE_DESCRIPTION("Driver support for Qualcomm Atheros PCIe/AHB 802.11ac WLAN devices"); + MODULE_LICENSE("Dual BSD/GPL"); + + /* QCA988x 2.0 firmware files */ +diff --git a/drivers/net/wireless/ath/ath10k/usb.c b/drivers/net/wireless/ath/ath10k/usb.c +index b0067af685b16..3c482baacec10 100644 +--- a/drivers/net/wireless/ath/ath10k/usb.c ++++ b/drivers/net/wireless/ath/ath10k/usb.c +@@ -1126,5 +1126,5 @@ static struct usb_driver ath10k_usb_driver = { + module_usb_driver(ath10k_usb_driver); + + MODULE_AUTHOR("Atheros Communications, Inc."); +-MODULE_DESCRIPTION("Driver support for Qualcomm Atheros 802.11ac WLAN USB devices"); ++MODULE_DESCRIPTION("Driver support for Qualcomm Atheros USB 802.11ac WLAN devices"); + MODULE_LICENSE("Dual BSD/GPL"); +diff --git a/drivers/net/wireless/ath/ath11k/pci.c b/drivers/net/wireless/ath/ath11k/pci.c +index ec40adc1cb235..a181563ec0851 100644 +--- a/drivers/net/wireless/ath/ath11k/pci.c ++++ b/drivers/net/wireless/ath/ath11k/pci.c +@@ -1036,7 +1036,7 @@ static void ath11k_pci_exit(void) + + module_exit(ath11k_pci_exit); + +-MODULE_DESCRIPTION("Driver support for Qualcomm Technologies 802.11ax WLAN PCIe devices"); ++MODULE_DESCRIPTION("Driver support for Qualcomm Technologies PCIe 802.11ax WLAN devices"); + MODULE_LICENSE("Dual BSD/GPL"); + + /* firmware files */ +diff --git a/drivers/net/wireless/ath/ath12k/pci.c b/drivers/net/wireless/ath/ath12k/pci.c +index e4f08a066ca10..fae5dfd6e9d70 100644 +--- a/drivers/net/wireless/ath/ath12k/pci.c ++++ b/drivers/net/wireless/ath/ath12k/pci.c +@@ -1411,5 +1411,5 @@ static void ath12k_pci_exit(void) + + module_exit(ath12k_pci_exit); + +-MODULE_DESCRIPTION("Driver support for Qualcomm Technologies 802.11be WLAN PCIe devices"); ++MODULE_DESCRIPTION("Driver support for Qualcomm Technologies PCIe 802.11be WLAN devices"); + MODULE_LICENSE("Dual BSD/GPL"); +diff --git a/drivers/net/wireless/atmel/at76c50x-usb.c b/drivers/net/wireless/atmel/at76c50x-usb.c +index 009bca34ece30..447b51cff8f96 100644 +--- a/drivers/net/wireless/atmel/at76c50x-usb.c ++++ b/drivers/net/wireless/atmel/at76c50x-usb.c +@@ -10,7 +10,7 @@ + * Copyright (c) 2007 Kalle Valo + * Copyright (c) 2010 Sebastian Smolorz + * +- * This file is part of the Berlios driver for WLAN USB devices based on the ++ * This file is part of the Berlios driver for USB WLAN devices based on the + * Atmel AT76C503A/505/505A. + * + * Some iw_handler code was taken from airo.c, (C) 1999 Benjamin Reed +@@ -143,7 +143,7 @@ static const struct usb_device_id dev_table[] = { + { USB_DEVICE(0x0cde, 0x0001), USB_DEVICE_DATA(BOARD_503_ISL3861) }, + /* Dynalink/Askey WLL013 (intersil) */ + { USB_DEVICE(0x069a, 0x0320), USB_DEVICE_DATA(BOARD_503_ISL3861) }, +- /* EZ connect 11Mpbs Wireless USB Adapter SMC2662W v1 */ ++ /* EZ connect 11Mpbs USB Wireless Adapter SMC2662W v1 */ + { USB_DEVICE(0x0d5c, 0xa001), USB_DEVICE_DATA(BOARD_503_ISL3861) }, + /* BenQ AWL300 */ + { USB_DEVICE(0x04a5, 0x9000), USB_DEVICE_DATA(BOARD_503_ISL3861) }, +@@ -195,7 +195,7 @@ static const struct usb_device_id dev_table[] = { + { USB_DEVICE(0x04a5, 0x9001), USB_DEVICE_DATA(BOARD_503) }, + /* 3Com 3CRSHEW696 */ + { USB_DEVICE(0x0506, 0x0a01), USB_DEVICE_DATA(BOARD_503) }, +- /* Siemens Santis ADSL WLAN USB adapter WLL 013 */ ++ /* Siemens Santis ADSL USB WLAN adapter WLL 013 */ + { USB_DEVICE(0x0681, 0x001b), USB_DEVICE_DATA(BOARD_503) }, + /* Belkin F5D6050, version 2 */ + { USB_DEVICE(0x050d, 0x0050), USB_DEVICE_DATA(BOARD_503) }, +@@ -238,7 +238,7 @@ static const struct usb_device_id dev_table[] = { + { USB_DEVICE(0x1915, 0x2233), USB_DEVICE_DATA(BOARD_505_2958) }, + /* Xterasys XN-2122B, IBlitzz BWU613B/BWU613SB */ + { USB_DEVICE(0x12fd, 0x1001), USB_DEVICE_DATA(BOARD_505_2958) }, +- /* Corega WLAN USB Stick 11 */ ++ /* Corega USB WLAN Stick 11 */ + { USB_DEVICE(0x07aa, 0x7613), USB_DEVICE_DATA(BOARD_505_2958) }, + /* Microstar MSI Box MS6978 */ + { USB_DEVICE(0x0db0, 0x1020), USB_DEVICE_DATA(BOARD_505_2958) }, +diff --git a/drivers/net/wireless/intersil/orinoco/orinoco_usb.c b/drivers/net/wireless/intersil/orinoco/orinoco_usb.c +index dd31929261ab9..866e0230df251 100644 +--- a/drivers/net/wireless/intersil/orinoco/orinoco_usb.c ++++ b/drivers/net/wireless/intersil/orinoco/orinoco_usb.c +@@ -129,18 +129,18 @@ MODULE_FIRMWARE("orinoco_ezusb_fw"); + + #define USB_AVAYA8_VENDOR_ID 0x0D98 + #define USB_AVAYAE_VENDOR_ID 0x0D9E +-#define USB_AVAYA_WIRELESS_ID 0x0300 /* Avaya Wireless USB Card */ ++#define USB_AVAYA_WIRELESS_ID 0x0300 /* Avaya USB Wireless Card */ + + #define USB_AGERE_VENDOR_ID 0x0D4E /* Agere Systems */ +-#define USB_AGERE_MODEL0801_ID 0x1000 /* Wireless USB Card Model 0801 */ +-#define USB_AGERE_MODEL0802_ID 0x1001 /* Wireless USB Card Model 0802 */ +-#define USB_AGERE_REBRANDED_ID 0x047A /* WLAN USB Card */ ++#define USB_AGERE_MODEL0801_ID 0x1000 /* USB Wireless Card Model 0801 */ ++#define USB_AGERE_MODEL0802_ID 0x1001 /* USB Wireless Card Model 0802 */ ++#define USB_AGERE_REBRANDED_ID 0x047A /* USB WLAN Card */ + + #define USB_ELSA_VENDOR_ID 0x05CC + #define USB_ELSA_AIRLANCER_ID 0x3100 /* ELSA AirLancer USB-11 */ + + #define USB_LEGEND_VENDOR_ID 0x0E7C +-#define USB_LEGEND_JOYNET_ID 0x0300 /* Joynet WLAN USB Card */ ++#define USB_LEGEND_JOYNET_ID 0x0300 /* Joynet USB WLAN Card */ + + #define USB_SAMSUNG_VENDOR_ID 0x04E8 + #define USB_SAMSUNG_SEW2001U1_ID 0x5002 /* Samsung SEW-2001u Card */ +@@ -154,7 +154,7 @@ MODULE_FIRMWARE("orinoco_ezusb_fw"); + #define USB_FUJITSU_E1100_ID 0x1002 /* connect2AIR WLAN E-1100 USB */ + + #define USB_2WIRE_VENDOR_ID 0x1630 +-#define USB_2WIRE_WIRELESS_ID 0xff81 /* 2Wire Wireless USB adapter */ ++#define USB_2WIRE_WIRELESS_ID 0xff81 /* 2Wire USB Wireless adapter */ + + + #define EZUSB_REQUEST_FW_TRANS 0xA0 +diff --git a/drivers/net/wireless/legacy/rndis_wlan.c b/drivers/net/wireless/legacy/rndis_wlan.c +index 712038d46bdb3..e7fea7ded6d5c 100644 +--- a/drivers/net/wireless/legacy/rndis_wlan.c ++++ b/drivers/net/wireless/legacy/rndis_wlan.c +@@ -1,6 +1,6 @@ + // SPDX-License-Identifier: GPL-2.0-or-later + /* +- * Driver for RNDIS based wireless USB devices. ++ * Driver for RNDIS based USB wireless devices. + * + * Copyright (C) 2007 by Bjorge Dijkstra + * Copyright (C) 2008-2009 by Jussi Kivilinna +diff --git a/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig b/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig +index 6a0080f1d91c7..dd16acfd9735d 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig ++++ b/drivers/net/wireless/mediatek/mt76/mt7603/Kconfig +@@ -5,7 +5,7 @@ config MT7603E + depends on MAC80211 + depends on PCI + help +- This adds support for MT7603E wireless PCIe devices and the WLAN core ++ This adds support for MT7603E PCIe wireless devices and the WLAN core + on MT7628/MT7688 SoC devices. This family supports IEEE 802.11n 2x2 + to 300Mbps PHY rate + +diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig b/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig +index 30fba36ff46bb..1ab1439143f41 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig ++++ b/drivers/net/wireless/mediatek/mt76/mt7615/Kconfig +@@ -11,7 +11,7 @@ config MT7615E + depends on MAC80211 + depends on PCI + help +- This adds support for MT7615-based wireless PCIe devices, ++ This adds support for MT7615-based PCIe wireless devices, + which support concurrent dual-band operation at both 5GHz + and 2.4GHz, IEEE 802.11ac 4x4:4SS 1733Mbps PHY rate, wave2 + MU-MIMO up to 4 users/group and 160MHz channels. +diff --git a/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig b/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig +index 7c88ed8b8f1e9..3ed888782a709 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig ++++ b/drivers/net/wireless/mediatek/mt76/mt76x0/Kconfig +@@ -10,7 +10,7 @@ config MT76x0U + depends on MAC80211 + depends on USB + help +- This adds support for MT7610U-based wireless USB 2.0 dongles, ++ This adds support for MT7610U-based USB 2.0 wireless dongles, + which comply with IEEE 802.11ac standards and support 1x1 + 433Mbps PHY rate. + +@@ -22,7 +22,7 @@ config MT76x0E + depends on MAC80211 + depends on PCI + help +- This adds support for MT7610/MT7630-based wireless PCIe devices, ++ This adds support for MT7610/MT7630-based PCIe wireless devices, + which comply with IEEE 802.11ac standards and support 1x1 + 433Mbps PHY rate. + +diff --git a/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig b/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig +index 5fd4973e32dfb..482a32b70ddfe 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig ++++ b/drivers/net/wireless/mediatek/mt76/mt76x2/Kconfig +@@ -9,7 +9,7 @@ config MT76x2E + depends on MAC80211 + depends on PCI + help +- This adds support for MT7612/MT7602/MT7662-based wireless PCIe ++ This adds support for MT7612/MT7602/MT7662-based PCIe wireless + devices, which comply with IEEE 802.11ac standards and support + 2SS to 866Mbit/s PHY rate. + +@@ -22,7 +22,7 @@ config MT76x2U + depends on MAC80211 + depends on USB + help +- This adds support for MT7612U-based wireless USB 3.0 dongles, ++ This adds support for MT7612U-based USB 3.0 wireless dongles, + which comply with IEEE 802.11ac standards and support 2SS to + 866Mbit/s PHY rate. + +diff --git a/drivers/net/wireless/mediatek/mt76/mt7915/Kconfig b/drivers/net/wireless/mediatek/mt76/mt7915/Kconfig +index d710726d47bfd..3337cdfed0109 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt7915/Kconfig ++++ b/drivers/net/wireless/mediatek/mt76/mt7915/Kconfig +@@ -7,7 +7,7 @@ config MT7915E + depends on PCI + select RELAY + help +- This adds support for MT7915-based wireless PCIe devices, ++ This adds support for MT7915-based PCIe wireless devices, + which support concurrent dual-band operation at both 5GHz + and 2.4GHz IEEE 802.11ax 4x4:4SS 1024-QAM, 160MHz channels, + OFDMA, spatial reuse and dual carrier modulation. +diff --git a/drivers/net/wireless/mediatek/mt76/mt7996/Kconfig b/drivers/net/wireless/mediatek/mt76/mt7996/Kconfig +index 1afa2f662e473..bb44d4a5e2dc9 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt7996/Kconfig ++++ b/drivers/net/wireless/mediatek/mt76/mt7996/Kconfig +@@ -7,7 +7,7 @@ config MT7996E + depends on MAC80211 + depends on PCI + help +- This adds support for MT7996-based wireless PCIe devices, ++ This adds support for MT7996-based PCIe wireless devices, + which support concurrent tri-band operation at 6GHz, 5GHz, + and 2.4GHz IEEE 802.11be 4x4:4SS 4096-QAM, 320MHz channels. + +diff --git a/drivers/net/wireless/mediatek/mt7601u/Kconfig b/drivers/net/wireless/mediatek/mt7601u/Kconfig +index 4a8b962806707..4880fc053d9d3 100644 +--- a/drivers/net/wireless/mediatek/mt7601u/Kconfig ++++ b/drivers/net/wireless/mediatek/mt7601u/Kconfig +@@ -4,4 +4,4 @@ config MT7601U + depends on MAC80211 + depends on USB + help +- This adds support for MT7601U-based wireless USB dongles. ++ This adds support for MT7601U-based USB wireless dongles. +diff --git a/drivers/net/wireless/purelifi/plfxlc/Kconfig b/drivers/net/wireless/purelifi/plfxlc/Kconfig +index 4e0be27a5e0eb..dd5fca480d7ef 100644 +--- a/drivers/net/wireless/purelifi/plfxlc/Kconfig ++++ b/drivers/net/wireless/purelifi/plfxlc/Kconfig +@@ -3,7 +3,7 @@ config PLFXLC + tristate "pureLiFi X, XL, XC device support" + depends on CFG80211 && MAC80211 && USB + help +- This option adds support for pureLiFi LiFi wireless USB ++ This option adds support for pureLiFi LiFi USB wireless + adapters. The pureLiFi X, XL, XC USB devices are based on + 802.11 OFDM PHY but uses light as the transmission medium. + The driver supports common 802.11 encryption/authentication +diff --git a/drivers/net/wireless/ralink/rt2x00/Kconfig b/drivers/net/wireless/ralink/rt2x00/Kconfig +index dcccc290a7f52..d1fd66d44a7ed 100644 +--- a/drivers/net/wireless/ralink/rt2x00/Kconfig ++++ b/drivers/net/wireless/ralink/rt2x00/Kconfig +@@ -170,7 +170,7 @@ config RT2800USB_RT35XX + config RT2800USB_RT3573 + bool "rt2800usb - Include support for rt3573 devices (EXPERIMENTAL)" + help +- This enables support for RT3573 chipset based wireless USB devices ++ This enables support for RT3573 chipset based USB wireless devices + in the rt2800usb driver. + + config RT2800USB_RT53XX +diff --git a/drivers/net/wireless/realtek/rtw88/pci.c b/drivers/net/wireless/realtek/rtw88/pci.c +index 44a8fff34cddf..2bfc0e822b8d0 100644 +--- a/drivers/net/wireless/realtek/rtw88/pci.c ++++ b/drivers/net/wireless/realtek/rtw88/pci.c +@@ -1828,5 +1828,5 @@ void rtw_pci_shutdown(struct pci_dev *pdev) + EXPORT_SYMBOL(rtw_pci_shutdown); + + MODULE_AUTHOR("Realtek Corporation"); +-MODULE_DESCRIPTION("Realtek 802.11ac wireless PCI driver"); ++MODULE_DESCRIPTION("Realtek PCI 802.11ac wireless driver"); + MODULE_LICENSE("Dual BSD/GPL"); +diff --git a/drivers/net/wireless/realtek/rtw88/usb.c b/drivers/net/wireless/realtek/rtw88/usb.c +index 875a61c9c80d4..c279a500b4bdb 100644 +--- a/drivers/net/wireless/realtek/rtw88/usb.c ++++ b/drivers/net/wireless/realtek/rtw88/usb.c +@@ -930,5 +930,5 @@ void rtw_usb_disconnect(struct usb_interface *intf) + EXPORT_SYMBOL(rtw_usb_disconnect); + + MODULE_AUTHOR("Realtek Corporation"); +-MODULE_DESCRIPTION("Realtek 802.11ac wireless USB driver"); ++MODULE_DESCRIPTION("Realtek USB 802.11ac wireless driver"); + MODULE_LICENSE("Dual BSD/GPL"); +diff --git a/drivers/net/wireless/realtek/rtw89/pci.c b/drivers/net/wireless/realtek/rtw89/pci.c +index 9402f1a0caea8..3a4bfc44142b6 100644 +--- a/drivers/net/wireless/realtek/rtw89/pci.c ++++ b/drivers/net/wireless/realtek/rtw89/pci.c +@@ -3939,5 +3939,5 @@ void rtw89_pci_remove(struct pci_dev *pdev) + EXPORT_SYMBOL(rtw89_pci_remove); + + MODULE_AUTHOR("Realtek Corporation"); +-MODULE_DESCRIPTION("Realtek 802.11ax wireless PCI driver"); ++MODULE_DESCRIPTION("Realtek PCI 802.11ax wireless driver"); + MODULE_LICENSE("Dual BSD/GPL"); +diff --git a/drivers/net/wireless/zydas/zd1201.c b/drivers/net/wireless/zydas/zd1201.c +index a85fe7e4c6d47..2814df1ecc78f 100644 +--- a/drivers/net/wireless/zydas/zd1201.c ++++ b/drivers/net/wireless/zydas/zd1201.c +@@ -1,6 +1,6 @@ + // SPDX-License-Identifier: GPL-2.0-only + /* +- * Driver for ZyDAS zd1201 based wireless USB devices. ++ * Driver for ZyDAS zd1201 based USB wireless devices. + * + * Copyright (c) 2004, 2005 Jeroen Vreeken (pe1rxq@amsat.org) + * +@@ -23,8 +23,8 @@ + #include "zd1201.h" + + static const struct usb_device_id zd1201_table[] = { +- {USB_DEVICE(0x0586, 0x3400)}, /* Peabird Wireless USB Adapter */ +- {USB_DEVICE(0x0ace, 0x1201)}, /* ZyDAS ZD1201 Wireless USB Adapter */ ++ {USB_DEVICE(0x0586, 0x3400)}, /* Peabird USB Wireless Adapter */ ++ {USB_DEVICE(0x0ace, 0x1201)}, /* ZyDAS ZD1201 USB Wireless Adapter */ + {USB_DEVICE(0x050d, 0x6051)}, /* Belkin F5D6051 usb adapter */ + {USB_DEVICE(0x0db0, 0x6823)}, /* MSI UB11B usb adapter */ + {USB_DEVICE(0x1044, 0x8004)}, /* Gigabyte GN-WLBZ101 */ +diff --git a/drivers/platform/x86/eeepc-laptop.c b/drivers/platform/x86/eeepc-laptop.c +index 62b71e8e3567a..ff1b70269ccbf 100644 +--- a/drivers/platform/x86/eeepc-laptop.c ++++ b/drivers/platform/x86/eeepc-laptop.c +@@ -1394,7 +1394,7 @@ static int eeepc_acpi_add(struct acpi_device *device) + * and machine-specific scripts find the fixed name convenient. But + * It's also good for us to exclude multiple instances because both + * our hwmon and our wlan rfkill subdevice use global ACPI objects +- * (the EC and the wlan PCI slot respectively). ++ * (the EC and the PCI wlan slot respectively). + */ + result = eeepc_platform_init(eeepc); + if (result) +diff --git a/drivers/staging/wlan-ng/prism2usb.c b/drivers/staging/wlan-ng/prism2usb.c +index 80e36d03c4e25..0e0ccef4871e9 100644 +--- a/drivers/staging/wlan-ng/prism2usb.c ++++ b/drivers/staging/wlan-ng/prism2usb.c +@@ -11,45 +11,45 @@ + + static const struct usb_device_id usb_prism_tbl[] = { + PRISM_DEV(0x04bb, 0x0922, "IOData AirPort WN-B11/USBS"), +- PRISM_DEV(0x07aa, 0x0012, "Corega Wireless LAN USB Stick-11"), +- PRISM_DEV(0x09aa, 0x3642, "Prism2.x 11Mbps WLAN USB Adapter"), +- PRISM_DEV(0x1668, 0x0408, "Actiontec Prism2.5 11Mbps WLAN USB Adapter"), +- PRISM_DEV(0x1668, 0x0421, "Actiontec Prism2.5 11Mbps WLAN USB Adapter"), +- PRISM_DEV(0x1915, 0x2236, "Linksys WUSB11v3.0 11Mbps WLAN USB Adapter"), +- PRISM_DEV(0x066b, 0x2212, "Linksys WUSB11v2.5 11Mbps WLAN USB Adapter"), +- PRISM_DEV(0x066b, 0x2213, "Linksys WUSB12v1.1 11Mbps WLAN USB Adapter"), ++ PRISM_DEV(0x07aa, 0x0012, "Corega USB Wireless LAN Stick-11"), ++ PRISM_DEV(0x09aa, 0x3642, "Prism2.x 11Mbps USB WLAN Adapter"), ++ PRISM_DEV(0x1668, 0x0408, "Actiontec Prism2.5 11Mbps USB WLAN Adapter"), ++ PRISM_DEV(0x1668, 0x0421, "Actiontec Prism2.5 11Mbps USB WLAN Adapter"), ++ PRISM_DEV(0x1915, 0x2236, "Linksys WUSB11v3.0 11Mbps USB WLAN Adapter"), ++ PRISM_DEV(0x066b, 0x2212, "Linksys WUSB11v2.5 11Mbps USB WLAN Adapter"), ++ PRISM_DEV(0x066b, 0x2213, "Linksys WUSB12v1.1 11Mbps USB WLAN Adapter"), + PRISM_DEV(0x0411, 0x0016, "Melco WLI-USB-S11 11Mbps WLAN Adapter"), +- PRISM_DEV(0x08de, 0x7a01, "PRISM25 IEEE 802.11 Mini USB Adapter"), +- PRISM_DEV(0x8086, 0x1111, "Intel PRO/Wireless 2011B LAN USB Adapter"), ++ PRISM_DEV(0x08de, 0x7a01, "PRISM25 USB IEEE 802.11 Mini Adapter"), ++ PRISM_DEV(0x8086, 0x1111, "Intel PRO/Wireless 2011B USB LAN Adapter"), + PRISM_DEV(0x0d8e, 0x7a01, "PRISM25 IEEE 802.11 Mini USB Adapter"), +- PRISM_DEV(0x045e, 0x006e, "Microsoft MN510 Wireless USB Adapter"), ++ PRISM_DEV(0x045e, 0x006e, "Microsoft MN510 USB Wireless Adapter"), + PRISM_DEV(0x0967, 0x0204, "Acer Warplink USB Adapter"), + PRISM_DEV(0x0cde, 0x0002, "Z-Com 725/726 Prism2.5 USB/USB Integrated"), +- PRISM_DEV(0x0cde, 0x0005, "Z-Com Xl735 Wireless 802.11b USB Adapter"), +- PRISM_DEV(0x413c, 0x8100, "Dell TrueMobile 1180 Wireless USB Adapter"), +- PRISM_DEV(0x0b3b, 0x1601, "ALLNET 0193 11Mbps WLAN USB Adapter"), +- PRISM_DEV(0x0b3b, 0x1602, "ZyXEL ZyAIR B200 Wireless USB Adapter"), +- PRISM_DEV(0x0baf, 0x00eb, "USRobotics USR1120 Wireless USB Adapter"), ++ PRISM_DEV(0x0cde, 0x0005, "Z-Com Xl735 USB Wireless 802.11b Adapter"), ++ PRISM_DEV(0x413c, 0x8100, "Dell TrueMobile 1180 USB Wireless Adapter"), ++ PRISM_DEV(0x0b3b, 0x1601, "ALLNET 0193 11Mbps USB WLAN Adapter"), ++ PRISM_DEV(0x0b3b, 0x1602, "ZyXEL ZyAIR B200 USB Wireless Adapter"), ++ PRISM_DEV(0x0baf, 0x00eb, "USRobotics USR1120 USB Wireless Adapter"), + PRISM_DEV(0x0411, 0x0027, "Melco WLI-USB-KS11G 11Mbps WLAN Adapter"), + PRISM_DEV(0x04f1, 0x3009, "JVC MP-XP7250 Builtin USB WLAN Adapter"), + PRISM_DEV(0x0846, 0x4110, "NetGear MA111"), + PRISM_DEV(0x03f3, 0x0020, "Adaptec AWN-8020 USB WLAN Adapter"), +- PRISM_DEV(0x2821, 0x3300, "ASUS-WL140 / Hawking HighDB Wireless USB Adapter"), +- PRISM_DEV(0x2001, 0x3700, "DWL-122 Wireless USB Adapter"), +- PRISM_DEV(0x2001, 0x3702, "DWL-120 Rev F Wireless USB Adapter"), ++ PRISM_DEV(0x2821, 0x3300, "ASUS-WL140 / Hawking HighDB USB Wireless Adapter"), ++ PRISM_DEV(0x2001, 0x3700, "DWL-122 USB Wireless Adapter"), ++ PRISM_DEV(0x2001, 0x3702, "DWL-120 Rev F USB Wireless Adapter"), + PRISM_DEV(0x50c2, 0x4013, "Averatec USB WLAN Adapter"), +- PRISM_DEV(0x2c02, 0x14ea, "Planex GW-US11H WLAN USB Adapter"), +- PRISM_DEV(0x124a, 0x168b, "Airvast PRISM3 WLAN USB Adapter"), ++ PRISM_DEV(0x2c02, 0x14ea, "Planex GW-US11H USB WLAN Adapter"), ++ PRISM_DEV(0x124a, 0x168b, "Airvast PRISM3 USB WLAN Adapter"), + PRISM_DEV(0x083a, 0x3503, "T-Sinus 111 USB WLAN Adapter"), + PRISM_DEV(0x0411, 0x0044, "Melco WLI-USB-KB11 11Mbps WLAN Adapter"), +- PRISM_DEV(0x1668, 0x6106, "ROPEX FreeLan 802.11b USB Adapter"), +- PRISM_DEV(0x124a, 0x4017, "Pheenet WL-503IA 802.11b USB Adapter"), ++ PRISM_DEV(0x1668, 0x6106, "ROPEX FreeLan USB 802.11b Adapter"), ++ PRISM_DEV(0x124a, 0x4017, "Pheenet WL-503IA USB 802.11b Adapter"), + PRISM_DEV(0x0bb2, 0x0302, "Ambit Microsystems Corp."), +- PRISM_DEV(0x9016, 0x182d, "Sitecom WL-022 802.11b USB Adapter"), ++ PRISM_DEV(0x9016, 0x182d, "Sitecom WL-022 USB 802.11b Adapter"), + PRISM_DEV(0x0543, 0x0f01, + "ViewSonic Airsync USB Adapter 11Mbps (Prism2.5)"), + PRISM_DEV(0x067c, 0x1022, +- "Siemens SpeedStream 1022 11Mbps WLAN USB Adapter"), ++ "Siemens SpeedStream 1022 11Mbps USB WLAN Adapter"), + PRISM_DEV(0x049f, 0x0033, + "Compaq/Intel W100 PRO/Wireless 11Mbps multiport WLAN Adapter"), + { } /* terminator */ +-- +2.40.1 + diff --git a/queue-6.5/fs-jfs-prevent-double-free-in-dbunmount-after-failed.patch b/queue-6.5/fs-jfs-prevent-double-free-in-dbunmount-after-failed.patch new file mode 100644 index 00000000000..3718b63516e --- /dev/null +++ b/queue-6.5/fs-jfs-prevent-double-free-in-dbunmount-after-failed.patch @@ -0,0 +1,121 @@ +From 338d5209852e83c75b5f9e17916adc5047960994 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 1 Jul 2023 17:05:42 +0300 +Subject: fs/jfs: prevent double-free in dbUnmount() after failed jfs_remount() + +From: Andrew Kanner + +[ Upstream commit cade5397e5461295f3cb87880534b6a07cafa427 ] + +Syzkaller reported the following issue: +================================================================== +BUG: KASAN: double-free in slab_free mm/slub.c:3787 [inline] +BUG: KASAN: double-free in __kmem_cache_free+0x71/0x110 mm/slub.c:3800 +Free of addr ffff888086408000 by task syz-executor.4/12750 +[...] +Call Trace: + +[...] + kasan_report_invalid_free+0xac/0xd0 mm/kasan/report.c:482 + ____kasan_slab_free+0xfb/0x120 + kasan_slab_free include/linux/kasan.h:177 [inline] + slab_free_hook mm/slub.c:1781 [inline] + slab_free_freelist_hook+0x12e/0x1a0 mm/slub.c:1807 + slab_free mm/slub.c:3787 [inline] + __kmem_cache_free+0x71/0x110 mm/slub.c:3800 + dbUnmount+0xf4/0x110 fs/jfs/jfs_dmap.c:264 + jfs_umount+0x248/0x3b0 fs/jfs/jfs_umount.c:87 + jfs_put_super+0x86/0x190 fs/jfs/super.c:194 + generic_shutdown_super+0x130/0x310 fs/super.c:492 + kill_block_super+0x79/0xd0 fs/super.c:1386 + deactivate_locked_super+0xa7/0xf0 fs/super.c:332 + cleanup_mnt+0x494/0x520 fs/namespace.c:1291 + task_work_run+0x243/0x300 kernel/task_work.c:179 + resume_user_mode_work include/linux/resume_user_mode.h:49 [inline] + exit_to_user_mode_loop+0x124/0x150 kernel/entry/common.c:171 + exit_to_user_mode_prepare+0xb2/0x140 kernel/entry/common.c:203 + __syscall_exit_to_user_mode_work kernel/entry/common.c:285 [inline] + syscall_exit_to_user_mode+0x26/0x60 kernel/entry/common.c:296 + do_syscall_64+0x49/0xb0 arch/x86/entry/common.c:86 + entry_SYSCALL_64_after_hwframe+0x63/0xcd +[...] + + +Allocated by task 13352: + kasan_save_stack mm/kasan/common.c:45 [inline] + kasan_set_track+0x3d/0x60 mm/kasan/common.c:52 + ____kasan_kmalloc mm/kasan/common.c:371 [inline] + __kasan_kmalloc+0x97/0xb0 mm/kasan/common.c:380 + kmalloc include/linux/slab.h:580 [inline] + dbMount+0x54/0x980 fs/jfs/jfs_dmap.c:164 + jfs_mount+0x1dd/0x830 fs/jfs/jfs_mount.c:121 + jfs_fill_super+0x590/0xc50 fs/jfs/super.c:556 + mount_bdev+0x26c/0x3a0 fs/super.c:1359 + legacy_get_tree+0xea/0x180 fs/fs_context.c:610 + vfs_get_tree+0x88/0x270 fs/super.c:1489 + do_new_mount+0x289/0xad0 fs/namespace.c:3145 + do_mount fs/namespace.c:3488 [inline] + __do_sys_mount fs/namespace.c:3697 [inline] + __se_sys_mount+0x2d3/0x3c0 fs/namespace.c:3674 + do_syscall_x64 arch/x86/entry/common.c:50 [inline] + do_syscall_64+0x3d/0xb0 arch/x86/entry/common.c:80 + entry_SYSCALL_64_after_hwframe+0x63/0xcd + +Freed by task 13352: + kasan_save_stack mm/kasan/common.c:45 [inline] + kasan_set_track+0x3d/0x60 mm/kasan/common.c:52 + kasan_save_free_info+0x27/0x40 mm/kasan/generic.c:518 + ____kasan_slab_free+0xd6/0x120 mm/kasan/common.c:236 + kasan_slab_free include/linux/kasan.h:177 [inline] + slab_free_hook mm/slub.c:1781 [inline] + slab_free_freelist_hook+0x12e/0x1a0 mm/slub.c:1807 + slab_free mm/slub.c:3787 [inline] + __kmem_cache_free+0x71/0x110 mm/slub.c:3800 + dbUnmount+0xf4/0x110 fs/jfs/jfs_dmap.c:264 + jfs_mount_rw+0x545/0x740 fs/jfs/jfs_mount.c:247 + jfs_remount+0x3db/0x710 fs/jfs/super.c:454 + reconfigure_super+0x3bc/0x7b0 fs/super.c:935 + vfs_fsconfig_locked fs/fsopen.c:254 [inline] + __do_sys_fsconfig fs/fsopen.c:439 [inline] + __se_sys_fsconfig+0xad5/0x1060 fs/fsopen.c:314 + do_syscall_x64 arch/x86/entry/common.c:50 [inline] + do_syscall_64+0x3d/0xb0 arch/x86/entry/common.c:80 + entry_SYSCALL_64_after_hwframe+0x63/0xcd +[...] + +JFS_SBI(ipbmap->i_sb)->bmap wasn't set to NULL after kfree() in +dbUnmount(). + +Syzkaller uses faultinject to reproduce this KASAN double-free +warning. The issue is triggered if either diMount() or dbMount() fail +in jfs_remount(), since diUnmount() or dbUnmount() already happened in +such a case - they will do double-free on next execution: jfs_umount +or jfs_remount. + +Tested on both upstream and jfs-next by syzkaller. + +Reported-and-tested-by: syzbot+6a93efb725385bc4b2e9@syzkaller.appspotmail.com +Closes: https://lore.kernel.org/all/000000000000471f2d05f1ce8bad@google.com/T/ +Link: https://syzkaller.appspot.com/bug?extid=6a93efb725385bc4b2e9 +Signed-off-by: Andrew Kanner +Signed-off-by: Dave Kleikamp +Signed-off-by: Sasha Levin +--- + fs/jfs/jfs_dmap.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/fs/jfs/jfs_dmap.c b/fs/jfs/jfs_dmap.c +index a14a0f18a4c40..88afd108c2dd2 100644 +--- a/fs/jfs/jfs_dmap.c ++++ b/fs/jfs/jfs_dmap.c +@@ -269,6 +269,7 @@ int dbUnmount(struct inode *ipbmap, int mounterror) + + /* free the memory for the in-memory bmap. */ + kfree(bmp); ++ JFS_SBI(ipbmap->i_sb)->bmap = NULL; + + return (0); + } +-- +2.40.1 + diff --git a/queue-6.5/hw_breakpoint-fix-single-stepping-when-using-bpf_ove.patch b/queue-6.5/hw_breakpoint-fix-single-stepping-when-using-bpf_ove.patch new file mode 100644 index 00000000000..67b22a23b10 --- /dev/null +++ b/queue-6.5/hw_breakpoint-fix-single-stepping-when-using-bpf_ove.patch @@ -0,0 +1,150 @@ +From 579f7fbb827f60efe1e46a663b5803d61b534523 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 5 Jun 2023 12:19:23 -0700 +Subject: hw_breakpoint: fix single-stepping when using bpf_overflow_handler + +From: Tomislav Novak + +[ Upstream commit d11a69873d9a7435fe6a48531e165ab80a8b1221 ] + +Arm platforms use is_default_overflow_handler() to determine if the +hw_breakpoint code should single-step over the breakpoint trigger or +let the custom handler deal with it. + +Since bpf_overflow_handler() currently isn't recognized as a default +handler, attaching a BPF program to a PERF_TYPE_BREAKPOINT event causes +it to keep firing (the instruction triggering the data abort exception +is never skipped). For example: + + # bpftrace -e 'watchpoint:0x10000:4:w { print("hit") }' -c ./test + Attaching 1 probe... + hit + hit + [...] + ^C + +(./test performs a single 4-byte store to 0x10000) + +This patch replaces the check with uses_default_overflow_handler(), +which accounts for the bpf_overflow_handler() case by also testing +if one of the perf_event_output functions gets invoked indirectly, +via orig_default_handler. + +Signed-off-by: Tomislav Novak +Tested-by: Samuel Gosselin # arm64 +Reviewed-by: Catalin Marinas +Acked-by: Alexei Starovoitov +Link: https://lore.kernel.org/linux-arm-kernel/20220923203644.2731604-1-tnovak@fb.com/ +Link: https://lore.kernel.org/r/20230605191923.1219974-1-tnovak@meta.com +Signed-off-by: Will Deacon +Signed-off-by: Sasha Levin +--- + arch/arm/kernel/hw_breakpoint.c | 8 ++++---- + arch/arm64/kernel/hw_breakpoint.c | 4 ++-- + include/linux/perf_event.h | 22 +++++++++++++++++++--- + 3 files changed, 25 insertions(+), 9 deletions(-) + +diff --git a/arch/arm/kernel/hw_breakpoint.c b/arch/arm/kernel/hw_breakpoint.c +index 054e9199f30db..dc0fb7a813715 100644 +--- a/arch/arm/kernel/hw_breakpoint.c ++++ b/arch/arm/kernel/hw_breakpoint.c +@@ -626,7 +626,7 @@ int hw_breakpoint_arch_parse(struct perf_event *bp, + hw->address &= ~alignment_mask; + hw->ctrl.len <<= offset; + +- if (is_default_overflow_handler(bp)) { ++ if (uses_default_overflow_handler(bp)) { + /* + * Mismatch breakpoints are required for single-stepping + * breakpoints. +@@ -798,7 +798,7 @@ static void watchpoint_handler(unsigned long addr, unsigned int fsr, + * Otherwise, insert a temporary mismatch breakpoint so that + * we can single-step over the watchpoint trigger. + */ +- if (!is_default_overflow_handler(wp)) ++ if (!uses_default_overflow_handler(wp)) + continue; + step: + enable_single_step(wp, instruction_pointer(regs)); +@@ -811,7 +811,7 @@ static void watchpoint_handler(unsigned long addr, unsigned int fsr, + info->trigger = addr; + pr_debug("watchpoint fired: address = 0x%x\n", info->trigger); + perf_bp_event(wp, regs); +- if (is_default_overflow_handler(wp)) ++ if (uses_default_overflow_handler(wp)) + enable_single_step(wp, instruction_pointer(regs)); + } + +@@ -886,7 +886,7 @@ static void breakpoint_handler(unsigned long unknown, struct pt_regs *regs) + info->trigger = addr; + pr_debug("breakpoint fired: address = 0x%x\n", addr); + perf_bp_event(bp, regs); +- if (is_default_overflow_handler(bp)) ++ if (uses_default_overflow_handler(bp)) + enable_single_step(bp, addr); + goto unlock; + } +diff --git a/arch/arm64/kernel/hw_breakpoint.c b/arch/arm64/kernel/hw_breakpoint.c +index db2a1861bb978..35225632d70ad 100644 +--- a/arch/arm64/kernel/hw_breakpoint.c ++++ b/arch/arm64/kernel/hw_breakpoint.c +@@ -654,7 +654,7 @@ static int breakpoint_handler(unsigned long unused, unsigned long esr, + perf_bp_event(bp, regs); + + /* Do we need to handle the stepping? */ +- if (is_default_overflow_handler(bp)) ++ if (uses_default_overflow_handler(bp)) + step = 1; + unlock: + rcu_read_unlock(); +@@ -733,7 +733,7 @@ static u64 get_distance_from_watchpoint(unsigned long addr, u64 val, + static int watchpoint_report(struct perf_event *wp, unsigned long addr, + struct pt_regs *regs) + { +- int step = is_default_overflow_handler(wp); ++ int step = uses_default_overflow_handler(wp); + struct arch_hw_breakpoint *info = counter_arch_bp(wp); + + info->trigger = addr; +diff --git a/include/linux/perf_event.h b/include/linux/perf_event.h +index 2166a69e3bf2e..e657916c9509c 100644 +--- a/include/linux/perf_event.h ++++ b/include/linux/perf_event.h +@@ -1316,15 +1316,31 @@ extern int perf_event_output(struct perf_event *event, + struct pt_regs *regs); + + static inline bool +-is_default_overflow_handler(struct perf_event *event) ++__is_default_overflow_handler(perf_overflow_handler_t overflow_handler) + { +- if (likely(event->overflow_handler == perf_event_output_forward)) ++ if (likely(overflow_handler == perf_event_output_forward)) + return true; +- if (unlikely(event->overflow_handler == perf_event_output_backward)) ++ if (unlikely(overflow_handler == perf_event_output_backward)) + return true; + return false; + } + ++#define is_default_overflow_handler(event) \ ++ __is_default_overflow_handler((event)->overflow_handler) ++ ++#ifdef CONFIG_BPF_SYSCALL ++static inline bool uses_default_overflow_handler(struct perf_event *event) ++{ ++ if (likely(is_default_overflow_handler(event))) ++ return true; ++ ++ return __is_default_overflow_handler(event->orig_overflow_handler); ++} ++#else ++#define uses_default_overflow_handler(event) \ ++ is_default_overflow_handler(event) ++#endif ++ + extern void + perf_event_header__init_id(struct perf_event_header *header, + struct perf_sample_data *data, +-- +2.40.1 + diff --git a/queue-6.5/ice-don-t-tx-before-switchdev-is-fully-configured.patch b/queue-6.5/ice-don-t-tx-before-switchdev-is-fully-configured.patch new file mode 100644 index 00000000000..a3bcd7bee6c --- /dev/null +++ b/queue-6.5/ice-don-t-tx-before-switchdev-is-fully-configured.patch @@ -0,0 +1,41 @@ +From ebb447d1c2e9383a5b770215de9817a45dd1120e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 12 Jul 2023 13:03:28 +0200 +Subject: ice: Don't tx before switchdev is fully configured + +From: Wojciech Drewek + +[ Upstream commit 7aa529a69e92b9aff585e569d5003f7c15d8d60b ] + +There is possibility that ice_eswitch_port_start_xmit might be +called while some resources are still not allocated which might +cause NULL pointer dereference. Fix this by checking if switchdev +configuration was finished. + +Reviewed-by: Paul Menzel +Reviewed-by: Simon Horman +Signed-off-by: Wojciech Drewek +Tested-by: Sujai Buvaneswaran +Signed-off-by: Tony Nguyen +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/ice/ice_eswitch.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/net/ethernet/intel/ice/ice_eswitch.c b/drivers/net/ethernet/intel/ice/ice_eswitch.c +index 8f232c41a89e3..459e32f6adb50 100644 +--- a/drivers/net/ethernet/intel/ice/ice_eswitch.c ++++ b/drivers/net/ethernet/intel/ice/ice_eswitch.c +@@ -331,6 +331,9 @@ ice_eswitch_port_start_xmit(struct sk_buff *skb, struct net_device *netdev) + np = netdev_priv(netdev); + vsi = np->vsi; + ++ if (!vsi || !ice_is_switchdev_running(vsi->back)) ++ return NETDEV_TX_BUSY; ++ + if (ice_is_reset_in_progress(vsi->back->state) || + test_bit(ICE_VF_DIS, vsi->back->state)) + return NETDEV_TX_BUSY; +-- +2.40.1 + diff --git a/queue-6.5/interconnect-fix-locking-for-runpm-vs-reclaim.patch b/queue-6.5/interconnect-fix-locking-for-runpm-vs-reclaim.patch new file mode 100644 index 00000000000..ab39f00a197 --- /dev/null +++ b/queue-6.5/interconnect-fix-locking-for-runpm-vs-reclaim.patch @@ -0,0 +1,249 @@ +From a9e87075c2d9991cdb110144660a7831a307dbf6 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 7 Aug 2023 10:11:40 -0700 +Subject: interconnect: Fix locking for runpm vs reclaim + +From: Rob Clark + +[ Upstream commit af42269c3523492d71ebbe11fefae2653e9cdc78 ] + +For cases where icc_bw_set() can be called in callbaths that could +deadlock against shrinker/reclaim, such as runpm resume, we need to +decouple the icc locking. Introduce a new icc_bw_lock for cases where +we need to serialize bw aggregation and update to decouple that from +paths that require memory allocation such as node/link creation/ +destruction. + +Fixes this lockdep splat: + + ====================================================== + WARNING: possible circular locking dependency detected + 6.2.0-rc8-debug+ #554 Not tainted + ------------------------------------------------------ + ring0/132 is trying to acquire lock: + ffffff80871916d0 (&gmu->lock){+.+.}-{3:3}, at: a6xx_pm_resume+0xf0/0x234 + + but task is already holding lock: + ffffffdb5aee57e8 (dma_fence_map){++++}-{0:0}, at: msm_job_run+0x68/0x150 + + which lock already depends on the new lock. + + the existing dependency chain (in reverse order) is: + + -> #4 (dma_fence_map){++++}-{0:0}: + __dma_fence_might_wait+0x74/0xc0 + dma_resv_lockdep+0x1f4/0x2f4 + do_one_initcall+0x104/0x2bc + kernel_init_freeable+0x344/0x34c + kernel_init+0x30/0x134 + ret_from_fork+0x10/0x20 + + -> #3 (mmu_notifier_invalidate_range_start){+.+.}-{0:0}: + fs_reclaim_acquire+0x80/0xa8 + slab_pre_alloc_hook.constprop.0+0x40/0x25c + __kmem_cache_alloc_node+0x60/0x1cc + __kmalloc+0xd8/0x100 + topology_parse_cpu_capacity+0x8c/0x178 + get_cpu_for_node+0x88/0xc4 + parse_cluster+0x1b0/0x28c + parse_cluster+0x8c/0x28c + init_cpu_topology+0x168/0x188 + smp_prepare_cpus+0x24/0xf8 + kernel_init_freeable+0x18c/0x34c + kernel_init+0x30/0x134 + ret_from_fork+0x10/0x20 + + -> #2 (fs_reclaim){+.+.}-{0:0}: + __fs_reclaim_acquire+0x3c/0x48 + fs_reclaim_acquire+0x54/0xa8 + slab_pre_alloc_hook.constprop.0+0x40/0x25c + __kmem_cache_alloc_node+0x60/0x1cc + __kmalloc+0xd8/0x100 + kzalloc.constprop.0+0x14/0x20 + icc_node_create_nolock+0x4c/0xc4 + icc_node_create+0x38/0x58 + qcom_icc_rpmh_probe+0x1b8/0x248 + platform_probe+0x70/0xc4 + really_probe+0x158/0x290 + __driver_probe_device+0xc8/0xe0 + driver_probe_device+0x44/0x100 + __driver_attach+0xf8/0x108 + bus_for_each_dev+0x78/0xc4 + driver_attach+0x2c/0x38 + bus_add_driver+0xd0/0x1d8 + driver_register+0xbc/0xf8 + __platform_driver_register+0x30/0x3c + qnoc_driver_init+0x24/0x30 + do_one_initcall+0x104/0x2bc + kernel_init_freeable+0x344/0x34c + kernel_init+0x30/0x134 + ret_from_fork+0x10/0x20 + + -> #1 (icc_lock){+.+.}-{3:3}: + __mutex_lock+0xcc/0x3c8 + mutex_lock_nested+0x30/0x44 + icc_set_bw+0x88/0x2b4 + _set_opp_bw+0x8c/0xd8 + _set_opp+0x19c/0x300 + dev_pm_opp_set_opp+0x84/0x94 + a6xx_gmu_resume+0x18c/0x804 + a6xx_pm_resume+0xf8/0x234 + adreno_runtime_resume+0x2c/0x38 + pm_generic_runtime_resume+0x30/0x44 + __rpm_callback+0x15c/0x174 + rpm_callback+0x78/0x7c + rpm_resume+0x318/0x524 + __pm_runtime_resume+0x78/0xbc + adreno_load_gpu+0xc4/0x17c + msm_open+0x50/0x120 + drm_file_alloc+0x17c/0x228 + drm_open_helper+0x74/0x118 + drm_open+0xa0/0x144 + drm_stub_open+0xd4/0xe4 + chrdev_open+0x1b8/0x1e4 + do_dentry_open+0x2f8/0x38c + vfs_open+0x34/0x40 + path_openat+0x64c/0x7b4 + do_filp_open+0x54/0xc4 + do_sys_openat2+0x9c/0x100 + do_sys_open+0x50/0x7c + __arm64_sys_openat+0x28/0x34 + invoke_syscall+0x8c/0x128 + el0_svc_common.constprop.0+0xa0/0x11c + do_el0_svc+0xac/0xbc + el0_svc+0x48/0xa0 + el0t_64_sync_handler+0xac/0x13c + el0t_64_sync+0x190/0x194 + + -> #0 (&gmu->lock){+.+.}-{3:3}: + __lock_acquire+0xe00/0x1060 + lock_acquire+0x1e0/0x2f8 + __mutex_lock+0xcc/0x3c8 + mutex_lock_nested+0x30/0x44 + a6xx_pm_resume+0xf0/0x234 + adreno_runtime_resume+0x2c/0x38 + pm_generic_runtime_resume+0x30/0x44 + __rpm_callback+0x15c/0x174 + rpm_callback+0x78/0x7c + rpm_resume+0x318/0x524 + __pm_runtime_resume+0x78/0xbc + pm_runtime_get_sync.isra.0+0x14/0x20 + msm_gpu_submit+0x58/0x178 + msm_job_run+0x78/0x150 + drm_sched_main+0x290/0x370 + kthread+0xf0/0x100 + ret_from_fork+0x10/0x20 + + other info that might help us debug this: + + Chain exists of: + &gmu->lock --> mmu_notifier_invalidate_range_start --> dma_fence_map + + Possible unsafe locking scenario: + + CPU0 CPU1 + ---- ---- + lock(dma_fence_map); + lock(mmu_notifier_invalidate_range_start); + lock(dma_fence_map); + lock(&gmu->lock); + + *** DEADLOCK *** + + 2 locks held by ring0/132: + #0: ffffff8087191170 (&gpu->lock){+.+.}-{3:3}, at: msm_job_run+0x64/0x150 + #1: ffffffdb5aee57e8 (dma_fence_map){++++}-{0:0}, at: msm_job_run+0x68/0x150 + + stack backtrace: + CPU: 7 PID: 132 Comm: ring0 Not tainted 6.2.0-rc8-debug+ #554 + Hardware name: Google Lazor (rev1 - 2) with LTE (DT) + Call trace: + dump_backtrace.part.0+0xb4/0xf8 + show_stack+0x20/0x38 + dump_stack_lvl+0x9c/0xd0 + dump_stack+0x18/0x34 + print_circular_bug+0x1b4/0x1f0 + check_noncircular+0x78/0xac + __lock_acquire+0xe00/0x1060 + lock_acquire+0x1e0/0x2f8 + __mutex_lock+0xcc/0x3c8 + mutex_lock_nested+0x30/0x44 + a6xx_pm_resume+0xf0/0x234 + adreno_runtime_resume+0x2c/0x38 + pm_generic_runtime_resume+0x30/0x44 + __rpm_callback+0x15c/0x174 + rpm_callback+0x78/0x7c + rpm_resume+0x318/0x524 + __pm_runtime_resume+0x78/0xbc + pm_runtime_get_sync.isra.0+0x14/0x20 + msm_gpu_submit+0x58/0x178 + msm_job_run+0x78/0x150 + drm_sched_main+0x290/0x370 + kthread+0xf0/0x100 + ret_from_fork+0x10/0x20 + +Signed-off-by: Rob Clark +Link: https://lore.kernel.org/r/20230807171148.210181-7-robdclark@gmail.com +Signed-off-by: Georgi Djakov +Signed-off-by: Sasha Levin +--- + drivers/interconnect/core.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +diff --git a/drivers/interconnect/core.c b/drivers/interconnect/core.c +index 5fac448c28fda..e15a92a79df1a 100644 +--- a/drivers/interconnect/core.c ++++ b/drivers/interconnect/core.c +@@ -28,6 +28,7 @@ static LIST_HEAD(icc_providers); + static int providers_count; + static bool synced_state; + static DEFINE_MUTEX(icc_lock); ++static DEFINE_MUTEX(icc_bw_lock); + static struct dentry *icc_debugfs_dir; + + static void icc_summary_show_one(struct seq_file *s, struct icc_node *n) +@@ -631,7 +632,7 @@ int icc_set_bw(struct icc_path *path, u32 avg_bw, u32 peak_bw) + if (WARN_ON(IS_ERR(path) || !path->num_nodes)) + return -EINVAL; + +- mutex_lock(&icc_lock); ++ mutex_lock(&icc_bw_lock); + + old_avg = path->reqs[0].avg_bw; + old_peak = path->reqs[0].peak_bw; +@@ -663,7 +664,7 @@ int icc_set_bw(struct icc_path *path, u32 avg_bw, u32 peak_bw) + apply_constraints(path); + } + +- mutex_unlock(&icc_lock); ++ mutex_unlock(&icc_bw_lock); + + trace_icc_set_bw_end(path, ret); + +@@ -872,6 +873,7 @@ void icc_node_add(struct icc_node *node, struct icc_provider *provider) + return; + + mutex_lock(&icc_lock); ++ mutex_lock(&icc_bw_lock); + + node->provider = provider; + list_add_tail(&node->node_list, &provider->nodes); +@@ -900,6 +902,7 @@ void icc_node_add(struct icc_node *node, struct icc_provider *provider) + node->avg_bw = 0; + node->peak_bw = 0; + ++ mutex_unlock(&icc_bw_lock); + mutex_unlock(&icc_lock); + } + EXPORT_SYMBOL_GPL(icc_node_add); +@@ -1025,6 +1028,7 @@ void icc_sync_state(struct device *dev) + return; + + mutex_lock(&icc_lock); ++ mutex_lock(&icc_bw_lock); + synced_state = true; + list_for_each_entry(p, &icc_providers, provider_list) { + dev_dbg(p->dev, "interconnect provider is in synced state\n"); +-- +2.40.1 + diff --git a/queue-6.5/io_uring-annotate-the-struct-io_kiocb-slab-for-appro.patch b/queue-6.5/io_uring-annotate-the-struct-io_kiocb-slab-for-appro.patch new file mode 100644 index 00000000000..b87e82a5118 --- /dev/null +++ b/queue-6.5/io_uring-annotate-the-struct-io_kiocb-slab-for-appro.patch @@ -0,0 +1,109 @@ +From 29f9b2894cfea72ed4c8c4b55307cae789094a8c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 2 Aug 2023 14:38:01 -0600 +Subject: io_uring: annotate the struct io_kiocb slab for appropriate user copy + +From: Jens Axboe + +[ Upstream commit b97f96e22f051d59d07a527dbd7d90408b661ca8 ] + +When compiling the kernel with clang and having HARDENED_USERCOPY +enabled, the liburing openat2.t test case fails during request setup: + +usercopy: Kernel memory overwrite attempt detected to SLUB object 'io_kiocb' (offset 24, size 24)! +------------[ cut here ]------------ +kernel BUG at mm/usercopy.c:102! +invalid opcode: 0000 [#1] PREEMPT SMP DEBUG_PAGEALLOC +CPU: 3 PID: 413 Comm: openat2.t Tainted: G N 6.4.3-g6995e2de6891-dirty #19 +Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.16.1-0-g3208b098f51a-prebuilt.qemu.org 04/01/2014 +RIP: 0010:usercopy_abort+0x84/0x90 +Code: ce 49 89 ce 48 c7 c3 68 48 98 82 48 0f 44 de 48 c7 c7 56 c6 94 82 4c 89 de 48 89 c1 41 52 41 56 53 e8 e0 51 c5 00 48 83 c4 18 <0f> 0b 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 44 00 00 55 41 57 41 56 +RSP: 0018:ffffc900016b3da0 EFLAGS: 00010296 +RAX: 0000000000000062 RBX: ffffffff82984868 RCX: 4e9b661ac6275b00 +RDX: ffff8881b90ec580 RSI: ffffffff82949a64 RDI: 00000000ffffffff +RBP: 0000000000000018 R08: 0000000000000000 R09: 0000000000000000 +R10: ffffc900016b3c88 R11: ffffc900016b3c30 R12: 00007ffe549659e0 +R13: ffff888119014000 R14: 0000000000000018 R15: 0000000000000018 +FS: 00007f862e3ca680(0000) GS:ffff8881b90c0000(0000) knlGS:0000000000000000 +CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 +CR2: 00005571483542a8 CR3: 0000000118c11000 CR4: 00000000003506e0 +Call Trace: + + ? __die_body+0x63/0xb0 + ? die+0x9d/0xc0 + ? do_trap+0xa7/0x180 + ? usercopy_abort+0x84/0x90 + ? do_error_trap+0xc6/0x110 + ? usercopy_abort+0x84/0x90 + ? handle_invalid_op+0x2c/0x40 + ? usercopy_abort+0x84/0x90 + ? exc_invalid_op+0x2f/0x40 + ? asm_exc_invalid_op+0x16/0x20 + ? usercopy_abort+0x84/0x90 + __check_heap_object+0xe2/0x110 + __check_object_size+0x142/0x3d0 + io_openat2_prep+0x68/0x140 + io_submit_sqes+0x28a/0x680 + __se_sys_io_uring_enter+0x120/0x580 + do_syscall_64+0x3d/0x80 + entry_SYSCALL_64_after_hwframe+0x46/0xb0 +RIP: 0033:0x55714834de26 +Code: ca 01 0f b6 82 d0 00 00 00 8b ba cc 00 00 00 45 31 c0 31 d2 41 b9 08 00 00 00 83 e0 01 c1 e0 04 41 09 c2 b8 aa 01 00 00 0f 05 66 0f 1f 84 00 00 00 00 00 89 30 eb 89 0f 1f 40 00 8b 00 a8 06 +RSP: 002b:00007ffe549659c8 EFLAGS: 00000246 ORIG_RAX: 00000000000001aa +RAX: ffffffffffffffda RBX: 00007ffe54965a50 RCX: 000055714834de26 +RDX: 0000000000000000 RSI: 0000000000000001 RDI: 0000000000000003 +RBP: 0000000000000000 R08: 0000000000000000 R09: 0000000000000008 +R10: 0000000000000000 R11: 0000000000000246 R12: 000055714834f057 +R13: 00007ffe54965a50 R14: 0000000000000001 R15: 0000557148351dd8 + +Modules linked in: +---[ end trace 0000000000000000 ]--- + +when it tries to copy struct open_how from userspace into the per-command +space in the io_kiocb. There's nothing wrong with the copy, but we're +missing the appropriate annotations for allowing user copies to/from the +io_kiocb slab. + +Allow copies in the per-command area, which is from the 'file' pointer to +when 'opcode' starts. We do have existing user copies there, but they are +not all annotated like the one that openat2_prep() uses, +copy_struct_from_user(). But in practice opcodes should be allowed to +copy data into their per-command area in the io_kiocb. + +Reported-by: Breno Leitao +Signed-off-by: Jens Axboe +Signed-off-by: Sasha Levin +--- + io_uring/io_uring.c | 16 ++++++++++++++-- + 1 file changed, 14 insertions(+), 2 deletions(-) + +diff --git a/io_uring/io_uring.c b/io_uring/io_uring.c +index 4e9217c1eb2e0..a1562f2cf3f3c 100644 +--- a/io_uring/io_uring.c ++++ b/io_uring/io_uring.c +@@ -4628,8 +4628,20 @@ static int __init io_uring_init(void) + + io_uring_optable_init(); + +- req_cachep = KMEM_CACHE(io_kiocb, SLAB_HWCACHE_ALIGN | SLAB_PANIC | +- SLAB_ACCOUNT | SLAB_TYPESAFE_BY_RCU); ++ /* ++ * Allow user copy in the per-command field, which starts after the ++ * file in io_kiocb and until the opcode field. The openat2 handling ++ * requires copying in user memory into the io_kiocb object in that ++ * range, and HARDENED_USERCOPY will complain if we haven't ++ * correctly annotated this range. ++ */ ++ req_cachep = kmem_cache_create_usercopy("io_kiocb", ++ sizeof(struct io_kiocb), 0, ++ SLAB_HWCACHE_ALIGN | SLAB_PANIC | ++ SLAB_ACCOUNT | SLAB_TYPESAFE_BY_RCU, ++ offsetof(struct io_kiocb, cmd.data), ++ sizeof_field(struct io_kiocb, cmd.data), NULL); ++ + return 0; + }; + __initcall(io_uring_init); +-- +2.40.1 + diff --git a/queue-6.5/iomap-fix-possible-overflow-condition-in-iomap_write.patch b/queue-6.5/iomap-fix-possible-overflow-condition-in-iomap_write.patch new file mode 100644 index 00000000000..66301d652ea --- /dev/null +++ b/queue-6.5/iomap-fix-possible-overflow-condition-in-iomap_write.patch @@ -0,0 +1,37 @@ +From 569ce80392aab7dff975ebb74e7e8fd5fabe69bf Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 10 Jul 2023 14:12:22 -0700 +Subject: iomap: Fix possible overflow condition in iomap_write_delalloc_scan + +From: Ritesh Harjani (IBM) + +[ Upstream commit eee2d2e6ea5550118170dbd5bb1316ceb38455fb ] + +folio_next_index() returns an unsigned long value which left shifted +by PAGE_SHIFT could possibly cause an overflow on 32-bit system. Instead +use folio_pos(folio) + folio_size(folio), which does this correctly. + +Suggested-by: Matthew Wilcox +Signed-off-by: Ritesh Harjani (IBM) +Reviewed-by: Darrick J. Wong +Signed-off-by: Sasha Levin +--- + fs/iomap/buffered-io.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/fs/iomap/buffered-io.c b/fs/iomap/buffered-io.c +index 7d2f70708f37d..794fda5bd9bc6 100644 +--- a/fs/iomap/buffered-io.c ++++ b/fs/iomap/buffered-io.c +@@ -927,7 +927,7 @@ static int iomap_write_delalloc_scan(struct inode *inode, + * the end of this data range, not the end of the folio. + */ + *punch_start_byte = min_t(loff_t, end_byte, +- folio_next_index(folio) << PAGE_SHIFT); ++ folio_pos(folio) + folio_size(folio)); + } + + /* move offset to start of next folio in range */ +-- +2.40.1 + diff --git a/queue-6.5/jfs-fix-invalid-free-of-jfs_ip-ipimap-i_imap-in-diun.patch b/queue-6.5/jfs-fix-invalid-free-of-jfs_ip-ipimap-i_imap-in-diun.patch new file mode 100644 index 00000000000..76e4797e614 --- /dev/null +++ b/queue-6.5/jfs-fix-invalid-free-of-jfs_ip-ipimap-i_imap-in-diun.patch @@ -0,0 +1,77 @@ +From 56206bcf32ec03c2406c114f067ef0e595bdbbbc Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 1 Dec 2022 20:46:28 +0800 +Subject: jfs: fix invalid free of JFS_IP(ipimap)->i_imap in diUnmount + +From: Liu Shixin via Jfs-discussion + +[ Upstream commit 6e2bda2c192d0244b5a78b787ef20aa10cb319b7 ] + +syzbot found an invalid-free in diUnmount: + +BUG: KASAN: double-free in slab_free mm/slub.c:3661 [inline] +BUG: KASAN: double-free in __kmem_cache_free+0x71/0x110 mm/slub.c:3674 +Free of addr ffff88806f410000 by task syz-executor131/3632 + + CPU: 0 PID: 3632 Comm: syz-executor131 Not tainted 6.1.0-rc7-syzkaller-00012-gca57f02295f1 #0 + Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 10/26/2022 + Call Trace: + + __dump_stack lib/dump_stack.c:88 [inline] + dump_stack_lvl+0x1b1/0x28e lib/dump_stack.c:106 + print_address_description+0x74/0x340 mm/kasan/report.c:284 + print_report+0x107/0x1f0 mm/kasan/report.c:395 + kasan_report_invalid_free+0xac/0xd0 mm/kasan/report.c:460 + ____kasan_slab_free+0xfb/0x120 + kasan_slab_free include/linux/kasan.h:177 [inline] + slab_free_hook mm/slub.c:1724 [inline] + slab_free_freelist_hook+0x12e/0x1a0 mm/slub.c:1750 + slab_free mm/slub.c:3661 [inline] + __kmem_cache_free+0x71/0x110 mm/slub.c:3674 + diUnmount+0xef/0x100 fs/jfs/jfs_imap.c:195 + jfs_umount+0x108/0x370 fs/jfs/jfs_umount.c:63 + jfs_put_super+0x86/0x190 fs/jfs/super.c:194 + generic_shutdown_super+0x130/0x310 fs/super.c:492 + kill_block_super+0x79/0xd0 fs/super.c:1428 + deactivate_locked_super+0xa7/0xf0 fs/super.c:332 + cleanup_mnt+0x494/0x520 fs/namespace.c:1186 + task_work_run+0x243/0x300 kernel/task_work.c:179 + exit_task_work include/linux/task_work.h:38 [inline] + do_exit+0x664/0x2070 kernel/exit.c:820 + do_group_exit+0x1fd/0x2b0 kernel/exit.c:950 + __do_sys_exit_group kernel/exit.c:961 [inline] + __se_sys_exit_group kernel/exit.c:959 [inline] + __x64_sys_exit_group+0x3b/0x40 kernel/exit.c:959 + do_syscall_x64 arch/x86/entry/common.c:50 [inline] + do_syscall_64+0x3d/0xb0 arch/x86/entry/common.c:80 + entry_SYSCALL_64_after_hwframe+0x63/0xcd +[...] + +JFS_IP(ipimap)->i_imap is not setting to NULL after free in diUnmount. +If jfs_remount() free JFS_IP(ipimap)->i_imap but then failed at diMount(). +JFS_IP(ipimap)->i_imap will be freed once again. +Fix this problem by setting JFS_IP(ipimap)->i_imap to NULL after free. + +Reported-by: syzbot+90a11e6b1e810785c6ff@syzkaller.appspotmail.com +Signed-off-by: Liu Shixin +Signed-off-by: Dave Kleikamp +Signed-off-by: Sasha Levin +--- + fs/jfs/jfs_imap.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/fs/jfs/jfs_imap.c b/fs/jfs/jfs_imap.c +index 390cbfce391fc..6fb28572cb2c6 100644 +--- a/fs/jfs/jfs_imap.c ++++ b/fs/jfs/jfs_imap.c +@@ -193,6 +193,7 @@ int diUnmount(struct inode *ipimap, int mounterror) + * free in-memory control structure + */ + kfree(imap); ++ JFS_IP(ipimap)->i_imap = NULL; + + return (0); + } +-- +2.40.1 + diff --git a/queue-6.5/kernel-fork-beware-of-__put_task_struct-calling-cont.patch b/queue-6.5/kernel-fork-beware-of-__put_task_struct-calling-cont.patch new file mode 100644 index 00000000000..24874665484 --- /dev/null +++ b/queue-6.5/kernel-fork-beware-of-__put_task_struct-calling-cont.patch @@ -0,0 +1,128 @@ +From 9a15cb505648355b783756191e373224ea5f7546 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 14 Jun 2023 09:23:21 -0300 +Subject: kernel/fork: beware of __put_task_struct() calling context + +From: Wander Lairson Costa + +[ Upstream commit d243b34459cea30cfe5f3a9b2feb44e7daff9938 ] + +Under PREEMPT_RT, __put_task_struct() indirectly acquires sleeping +locks. Therefore, it can't be called from an non-preemptible context. + +One practical example is splat inside inactive_task_timer(), which is +called in a interrupt context: + + CPU: 1 PID: 2848 Comm: life Kdump: loaded Tainted: G W --------- + Hardware name: HP ProLiant DL388p Gen8, BIOS P70 07/15/2012 + Call Trace: + dump_stack_lvl+0x57/0x7d + mark_lock_irq.cold+0x33/0xba + mark_lock+0x1e7/0x400 + mark_usage+0x11d/0x140 + __lock_acquire+0x30d/0x930 + lock_acquire.part.0+0x9c/0x210 + rt_spin_lock+0x27/0xe0 + refill_obj_stock+0x3d/0x3a0 + kmem_cache_free+0x357/0x560 + inactive_task_timer+0x1ad/0x340 + __run_hrtimer+0x8a/0x1a0 + __hrtimer_run_queues+0x91/0x130 + hrtimer_interrupt+0x10f/0x220 + __sysvec_apic_timer_interrupt+0x7b/0xd0 + sysvec_apic_timer_interrupt+0x4f/0xd0 + asm_sysvec_apic_timer_interrupt+0x12/0x20 + RIP: 0033:0x7fff196bf6f5 + +Instead of calling __put_task_struct() directly, we defer it using +call_rcu(). A more natural approach would use a workqueue, but since +in PREEMPT_RT, we can't allocate dynamic memory from atomic context, +the code would become more complex because we would need to put the +work_struct instance in the task_struct and initialize it when we +allocate a new task_struct. + +The issue is reproducible with stress-ng: + + while true; do + stress-ng --sched deadline --sched-period 1000000000 \ + --sched-runtime 800000000 --sched-deadline \ + 1000000000 --mmapfork 23 -t 20 + done + +Reported-by: Hu Chunyu +Suggested-by: Oleg Nesterov +Suggested-by: Valentin Schneider +Suggested-by: Peter Zijlstra +Signed-off-by: Wander Lairson Costa +Signed-off-by: Peter Zijlstra (Intel) +Link: https://lore.kernel.org/r/20230614122323.37957-2-wander@redhat.com +Signed-off-by: Sasha Levin +--- + include/linux/sched/task.h | 28 +++++++++++++++++++++++++++- + kernel/fork.c | 8 ++++++++ + 2 files changed, 35 insertions(+), 1 deletion(-) + +diff --git a/include/linux/sched/task.h b/include/linux/sched/task.h +index dd35ce28bb908..6b687c155fb6c 100644 +--- a/include/linux/sched/task.h ++++ b/include/linux/sched/task.h +@@ -118,10 +118,36 @@ static inline struct task_struct *get_task_struct(struct task_struct *t) + } + + extern void __put_task_struct(struct task_struct *t); ++extern void __put_task_struct_rcu_cb(struct rcu_head *rhp); + + static inline void put_task_struct(struct task_struct *t) + { +- if (refcount_dec_and_test(&t->usage)) ++ if (!refcount_dec_and_test(&t->usage)) ++ return; ++ ++ /* ++ * under PREEMPT_RT, we can't call put_task_struct ++ * in atomic context because it will indirectly ++ * acquire sleeping locks. ++ * ++ * call_rcu() will schedule delayed_put_task_struct_rcu() ++ * to be called in process context. ++ * ++ * __put_task_struct() is called when ++ * refcount_dec_and_test(&t->usage) succeeds. ++ * ++ * This means that it can't "conflict" with ++ * put_task_struct_rcu_user() which abuses ->rcu the same ++ * way; rcu_users has a reference so task->usage can't be ++ * zero after rcu_users 1 -> 0 transition. ++ * ++ * delayed_free_task() also uses ->rcu, but it is only called ++ * when it fails to fork a process. Therefore, there is no ++ * way it can conflict with put_task_struct(). ++ */ ++ if (IS_ENABLED(CONFIG_PREEMPT_RT) && !preemptible()) ++ call_rcu(&t->rcu, __put_task_struct_rcu_cb); ++ else + __put_task_struct(t); + } + +diff --git a/kernel/fork.c b/kernel/fork.c +index d2e12b6d2b180..f81149739eb9f 100644 +--- a/kernel/fork.c ++++ b/kernel/fork.c +@@ -985,6 +985,14 @@ void __put_task_struct(struct task_struct *tsk) + } + EXPORT_SYMBOL_GPL(__put_task_struct); + ++void __put_task_struct_rcu_cb(struct rcu_head *rhp) ++{ ++ struct task_struct *task = container_of(rhp, struct task_struct, rcu); ++ ++ __put_task_struct(task); ++} ++EXPORT_SYMBOL_GPL(__put_task_struct_rcu_cb); ++ + void __init __weak arch_task_cache_init(void) { } + + /* +-- +2.40.1 + diff --git a/queue-6.5/kobject-add-sanity-check-for-kset-kobj.ktype-in-kset.patch b/queue-6.5/kobject-add-sanity-check-for-kset-kobj.ktype-in-kset.patch new file mode 100644 index 00000000000..43373d8c6e6 --- /dev/null +++ b/queue-6.5/kobject-add-sanity-check-for-kset-kobj.ktype-in-kset.patch @@ -0,0 +1,60 @@ +From 739da96e344561b58bc8a6ef86e66d9489daf63e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 5 Aug 2023 16:41:13 +0800 +Subject: kobject: Add sanity check for kset->kobj.ktype in kset_register() + +From: Zhen Lei + +[ Upstream commit 4d0fe8c52bb3029d83e323c961221156ab98680b ] + +When I register a kset in the following way: + static struct kset my_kset; + kobject_set_name(&my_kset.kobj, "my_kset"); + ret = kset_register(&my_kset); + +A null pointer dereference exception is occurred: +[ 4453.568337] Unable to handle kernel NULL pointer dereference at \ +virtual address 0000000000000028 +... ... +[ 4453.810361] Call trace: +[ 4453.813062] kobject_get_ownership+0xc/0x34 +[ 4453.817493] kobject_add_internal+0x98/0x274 +[ 4453.822005] kset_register+0x5c/0xb4 +[ 4453.825820] my_kobj_init+0x44/0x1000 [my_kset] +... ... + +Because I didn't initialize my_kset.kobj.ktype. + +According to the description in Documentation/core-api/kobject.rst: + - A ktype is the type of object that embeds a kobject. Every structure + that embeds a kobject needs a corresponding ktype. + +So add sanity check to make sure kset->kobj.ktype is not NULL. + +Signed-off-by: Zhen Lei +Link: https://lore.kernel.org/r/20230805084114.1298-2-thunder.leizhen@huaweicloud.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + lib/kobject.c | 5 +++++ + 1 file changed, 5 insertions(+) + +diff --git a/lib/kobject.c b/lib/kobject.c +index 16d530f9c174b..4c7a990d6f120 100644 +--- a/lib/kobject.c ++++ b/lib/kobject.c +@@ -854,6 +854,11 @@ int kset_register(struct kset *k) + if (!k) + return -EINVAL; + ++ if (!k->kobj.ktype) { ++ pr_err("must have a ktype to be initialized properly!\n"); ++ return -EINVAL; ++ } ++ + kset_init(k); + err = kobject_add_internal(&k->kobj); + if (err) { +-- +2.40.1 + diff --git a/queue-6.5/kselftest-arm64-fix-a-memleak-in-zt_regs_run.patch b/queue-6.5/kselftest-arm64-fix-a-memleak-in-zt_regs_run.patch new file mode 100644 index 00000000000..9617a7b2aa9 --- /dev/null +++ b/queue-6.5/kselftest-arm64-fix-a-memleak-in-zt_regs_run.patch @@ -0,0 +1,34 @@ +From 159d05f1029d60bee18bba46d48b5bc20600d39c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 15:49:15 +0800 +Subject: kselftest/arm64: fix a memleak in zt_regs_run() + +From: Ding Xiang + +[ Upstream commit 46862da15e37efedb7d2d21e167f506c0b533772 ] + +If memcmp() does not return 0, "zeros" need to be freed to prevent memleak + +Signed-off-by: Ding Xiang +Link: https://lore.kernel.org/r/20230815074915.245528-1-dingxiang@cmss.chinamobile.com +Signed-off-by: Will Deacon +Signed-off-by: Sasha Levin +--- + tools/testing/selftests/arm64/signal/testcases/zt_regs.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/tools/testing/selftests/arm64/signal/testcases/zt_regs.c b/tools/testing/selftests/arm64/signal/testcases/zt_regs.c +index e1eb4d5c027ab..2e384d731618b 100644 +--- a/tools/testing/selftests/arm64/signal/testcases/zt_regs.c ++++ b/tools/testing/selftests/arm64/signal/testcases/zt_regs.c +@@ -65,6 +65,7 @@ int zt_regs_run(struct tdescr *td, siginfo_t *si, ucontext_t *uc) + if (memcmp(zeros, (char *)zt + ZT_SIG_REGS_OFFSET, + ZT_SIG_REGS_SIZE(zt->nregs)) != 0) { + fprintf(stderr, "ZT data invalid\n"); ++ free(zeros); + return 1; + } + +-- +2.40.1 + diff --git a/queue-6.5/libbpf-free-btf_vmlinux-when-closing-bpf_object.patch b/queue-6.5/libbpf-free-btf_vmlinux-when-closing-bpf_object.patch new file mode 100644 index 00000000000..4230689cdc3 --- /dev/null +++ b/queue-6.5/libbpf-free-btf_vmlinux-when-closing-bpf_object.patch @@ -0,0 +1,41 @@ +From 65c39a29590502dc02985d5f6452acf29b27ad04 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 22 Aug 2023 12:38:40 -0700 +Subject: libbpf: Free btf_vmlinux when closing bpf_object + +From: Hao Luo + +[ Upstream commit 29d67fdebc42af6466d1909c60fdd1ef4f3e5240 ] + +I hit a memory leak when testing bpf_program__set_attach_target(). +Basically, set_attach_target() may allocate btf_vmlinux, for example, +when setting attach target for bpf_iter programs. But btf_vmlinux +is freed only in bpf_object_load(), which means if we only open +bpf object but not load it, setting attach target may leak +btf_vmlinux. + +So let's free btf_vmlinux in bpf_object__close() anyway. + +Signed-off-by: Hao Luo +Signed-off-by: Andrii Nakryiko +Link: https://lore.kernel.org/bpf/20230822193840.1509809-1-haoluo@google.com +Signed-off-by: Sasha Levin +--- + tools/lib/bpf/libbpf.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/tools/lib/bpf/libbpf.c b/tools/lib/bpf/libbpf.c +index e07dff7eba600..13b5623b720f1 100644 +--- a/tools/lib/bpf/libbpf.c ++++ b/tools/lib/bpf/libbpf.c +@@ -8356,6 +8356,7 @@ void bpf_object__close(struct bpf_object *obj) + bpf_object__elf_finish(obj); + bpf_object_unload(obj); + btf__free(obj->btf); ++ btf__free(obj->btf_vmlinux); + btf_ext__free(obj->btf_ext); + + for (i = 0; i < obj->nr_maps; i++) +-- +2.40.1 + diff --git a/queue-6.5/locks-fix-kasan-use-after-free-in-trace_event_raw_ev.patch b/queue-6.5/locks-fix-kasan-use-after-free-in-trace_event_raw_ev.patch new file mode 100644 index 00000000000..165a8b0e0dc --- /dev/null +++ b/queue-6.5/locks-fix-kasan-use-after-free-in-trace_event_raw_ev.patch @@ -0,0 +1,88 @@ +From 9f7bb89950b68d2c402b0a85bf636a1087e6a4a9 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 21 Jul 2023 13:19:04 +0800 +Subject: locks: fix KASAN: use-after-free in + trace_event_raw_event_filelock_lock + +From: Will Shiu + +[ Upstream commit 74f6f5912693ce454384eaeec48705646a21c74f ] + +As following backtrace, the struct file_lock request , in posix_lock_inode +is free before ftrace function using. +Replace the ftrace function ahead free flow could fix the use-after-free +issue. + +[name:report&]=============================================== +BUG:KASAN: use-after-free in trace_event_raw_event_filelock_lock+0x80/0x12c +[name:report&]Read at addr f6ffff8025622620 by task NativeThread/16753 +[name:report_hw_tags&]Pointer tag: [f6], memory tag: [fe] +[name:report&] +BT: +Hardware name: MT6897 (DT) +Call trace: + dump_backtrace+0xf8/0x148 + show_stack+0x18/0x24 + dump_stack_lvl+0x60/0x7c + print_report+0x2c8/0xa08 + kasan_report+0xb0/0x120 + __do_kernel_fault+0xc8/0x248 + do_bad_area+0x30/0xdc + do_tag_check_fault+0x1c/0x30 + do_mem_abort+0x58/0xbc + el1_abort+0x3c/0x5c + el1h_64_sync_handler+0x54/0x90 + el1h_64_sync+0x68/0x6c + trace_event_raw_event_filelock_lock+0x80/0x12c + posix_lock_inode+0xd0c/0xd60 + do_lock_file_wait+0xb8/0x190 + fcntl_setlk+0x2d8/0x440 +... +[name:report&] +[name:report&]Allocated by task 16752: +... + slab_post_alloc_hook+0x74/0x340 + kmem_cache_alloc+0x1b0/0x2f0 + posix_lock_inode+0xb0/0xd60 +... + [name:report&] + [name:report&]Freed by task 16752: +... + kmem_cache_free+0x274/0x5b0 + locks_dispose_list+0x3c/0x148 + posix_lock_inode+0xc40/0xd60 + do_lock_file_wait+0xb8/0x190 + fcntl_setlk+0x2d8/0x440 + do_fcntl+0x150/0xc18 +... + +Signed-off-by: Will Shiu +Signed-off-by: Jeff Layton +Signed-off-by: Sasha Levin +--- + fs/locks.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/fs/locks.c b/fs/locks.c +index df8b26a425248..a552bdb6badc0 100644 +--- a/fs/locks.c ++++ b/fs/locks.c +@@ -1301,6 +1301,7 @@ static int posix_lock_inode(struct inode *inode, struct file_lock *request, + out: + spin_unlock(&ctx->flc_lock); + percpu_up_read(&file_rwsem); ++ trace_posix_lock_inode(inode, request, error); + /* + * Free any unused locks. + */ +@@ -1309,7 +1310,6 @@ static int posix_lock_inode(struct inode *inode, struct file_lock *request, + if (new_fl2) + locks_free_lock(new_fl2); + locks_dispose_list(&dispose); +- trace_posix_lock_inode(inode, request, error); + + return error; + } +-- +2.40.1 + diff --git a/queue-6.5/md-don-t-dereference-mddev-after-export_rdev.patch b/queue-6.5/md-don-t-dereference-mddev-after-export_rdev.patch new file mode 100644 index 00000000000..5cdda111283 --- /dev/null +++ b/queue-6.5/md-don-t-dereference-mddev-after-export_rdev.patch @@ -0,0 +1,111 @@ +From 9308ea378e77610f8a79dd345156bf4b01c0ada0 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 25 Aug 2023 10:55:31 +0800 +Subject: md: don't dereference mddev after export_rdev() + +From: Yu Kuai + +[ Upstream commit 7deac114be5fb25a4e865212ed0feaf5f85f2a28 ] + +Except for initial reference, mddev->kobject is referenced by +rdev->kobject, and if the last rdev is freed, there is no guarantee that +mddev is still valid. Hence mddev should not be used anymore after +export_rdev(). + +This problem can be triggered by following test for mdadm at very +low rate: + +New file: mdadm/tests/23rdev-lifetime + +devname=${dev0##*/} +devt=`cat /sys/block/$devname/dev` +pid="" +runtime=2 + +clean_up_test() { + pill -9 $pid + echo clear > /sys/block/md0/md/array_state +} + +trap 'clean_up_test' EXIT + +add_by_sysfs() { + while true; do + echo $devt > /sys/block/md0/md/new_dev + done +} + +remove_by_sysfs(){ + while true; do + echo remove > /sys/block/md0/md/dev-${devname}/state + done +} + +echo md0 > /sys/module/md_mod/parameters/new_array || die "create md0 failed" + +add_by_sysfs & +pid="$pid $!" + +remove_by_sysfs & +pid="$pid $!" + +sleep $runtime +exit 0 + +Test cmd: + +./test --save-logs --logdir=/tmp/ --keep-going --dev=loop --tests=23rdev-lifetime + +Test result: + +general protection fault, probably for non-canonical address 0x6b6b6b6b6b6b6bcb: 0000 [#4] PREEMPT SMP +CPU: 0 PID: 1292 Comm: test Tainted: G D W 6.5.0-rc2-00121-g01e55c376936 #562 +RIP: 0010:md_wakeup_thread+0x9e/0x320 [md_mod] +Call Trace: + + mddev_unlock+0x1b6/0x310 [md_mod] + rdev_attr_store+0xec/0x190 [md_mod] + sysfs_kf_write+0x52/0x70 + kernfs_fop_write_iter+0x19a/0x2a0 + vfs_write+0x3b5/0x770 + ksys_write+0x74/0x150 + __x64_sys_write+0x22/0x30 + do_syscall_64+0x40/0x90 + entry_SYSCALL_64_after_hwframe+0x63/0xcd + +Fix this problem by don't dereference mddev after export_rdev(). + +Fixes: 3ce94ce5d05a ("md: fix duplicate filename for rdev") +Signed-off-by: Yu Kuai +Signed-off-by: Song Liu +Link: https://lore.kernel.org/r/20230825025532.1523008-2-yukuai1@huaweicloud.com +Signed-off-by: Sasha Levin +--- + drivers/md/md.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +diff --git a/drivers/md/md.c b/drivers/md/md.c +index 2a4a3d3039fae..fba2809cd384a 100644 +--- a/drivers/md/md.c ++++ b/drivers/md/md.c +@@ -798,14 +798,14 @@ void mddev_unlock(struct mddev *mddev) + } else + mutex_unlock(&mddev->reconfig_mutex); + ++ md_wakeup_thread(mddev->thread); ++ wake_up(&mddev->sb_wait); ++ + list_for_each_entry_safe(rdev, tmp, &delete, same_set) { + list_del_init(&rdev->same_set); + kobject_del(&rdev->kobj); + export_rdev(rdev, mddev); + } +- +- md_wakeup_thread(mddev->thread); +- wake_up(&mddev->sb_wait); + } + EXPORT_SYMBOL_GPL(mddev_unlock); + +-- +2.40.1 + diff --git a/queue-6.5/md-fix-warning-for-holder-mismatch-from-export_rdev.patch b/queue-6.5/md-fix-warning-for-holder-mismatch-from-export_rdev.patch new file mode 100644 index 00000000000..c4d0d959109 --- /dev/null +++ b/queue-6.5/md-fix-warning-for-holder-mismatch-from-export_rdev.patch @@ -0,0 +1,155 @@ +From 3fdf3c8479dc83ac79470e580b1d2a8feca8b618 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 25 Aug 2023 10:55:32 +0800 +Subject: md: fix warning for holder mismatch from export_rdev() + +From: Yu Kuai + +[ Upstream commit 99892147f028d711f9d40fefad4f33632593864c ] + +Commit a1d767191096 ("md: use mddev->external to select holder in +export_rdev()") fix the problem that 'claim_rdev' is used for +blkdev_get_by_dev() while 'rdev' is used for blkdev_put(). + +However, if mddev->external is changed from 0 to 1, then 'rdev' is used +for blkdev_get_by_dev() while 'claim_rdev' is used for blkdev_put(). And +this problem can be reporduced reliably by following: + +New file: mdadm/tests/23rdev-lifetime + +devname=${dev0##*/} +devt=`cat /sys/block/$devname/dev` +pid="" +runtime=2 + +clean_up_test() { + pill -9 $pid + echo clear > /sys/block/md0/md/array_state +} + +trap 'clean_up_test' EXIT + +add_by_sysfs() { + while true; do + echo $devt > /sys/block/md0/md/new_dev + done +} + +remove_by_sysfs(){ + while true; do + echo remove > /sys/block/md0/md/dev-${devname}/state + done +} + +echo md0 > /sys/module/md_mod/parameters/new_array || die "create md0 failed" + +add_by_sysfs & +pid="$pid $!" + +remove_by_sysfs & +pid="$pid $!" + +sleep $runtime +exit 0 + +Test cmd: + +./test --save-logs --logdir=/tmp/ --keep-going --dev=loop --tests=23rdev-lifetime + +Test result: + +------------[ cut here ]------------ +WARNING: CPU: 0 PID: 960 at block/bdev.c:618 blkdev_put+0x27c/0x330 +Modules linked in: multipath md_mod loop +CPU: 0 PID: 960 Comm: test Not tainted 6.5.0-rc2-00121-g01e55c376936-dirty #50 +RIP: 0010:blkdev_put+0x27c/0x330 +Call Trace: + + export_rdev.isra.23+0x50/0xa0 [md_mod] + mddev_unlock+0x19d/0x300 [md_mod] + rdev_attr_store+0xec/0x190 [md_mod] + sysfs_kf_write+0x52/0x70 + kernfs_fop_write_iter+0x19a/0x2a0 + vfs_write+0x3b5/0x770 + ksys_write+0x74/0x150 + __x64_sys_write+0x22/0x30 + do_syscall_64+0x40/0x90 + entry_SYSCALL_64_after_hwframe+0x63/0xcd + +Fix the problem by recording if 'rdev' is used as holder. + +Fixes: a1d767191096 ("md: use mddev->external to select holder in export_rdev()") +Signed-off-by: Yu Kuai +Signed-off-by: Song Liu +Link: https://lore.kernel.org/r/20230825025532.1523008-3-yukuai1@huaweicloud.com +Signed-off-by: Sasha Levin +--- + drivers/md/md.c | 15 ++++++++++++--- + drivers/md/md.h | 3 +++ + 2 files changed, 15 insertions(+), 3 deletions(-) + +diff --git a/drivers/md/md.c b/drivers/md/md.c +index fba2809cd384a..06a8ccdb5135d 100644 +--- a/drivers/md/md.c ++++ b/drivers/md/md.c +@@ -2452,7 +2452,8 @@ static void export_rdev(struct md_rdev *rdev, struct mddev *mddev) + if (test_bit(AutoDetected, &rdev->flags)) + md_autodetect_dev(rdev->bdev->bd_dev); + #endif +- blkdev_put(rdev->bdev, mddev->external ? &claim_rdev : rdev); ++ blkdev_put(rdev->bdev, ++ test_bit(Holder, &rdev->flags) ? rdev : &claim_rdev); + rdev->bdev = NULL; + kobject_put(&rdev->kobj); + } +@@ -3632,6 +3633,7 @@ EXPORT_SYMBOL_GPL(md_rdev_init); + static struct md_rdev *md_import_device(dev_t newdev, int super_format, int super_minor) + { + struct md_rdev *rdev; ++ struct md_rdev *holder; + sector_t size; + int err; + +@@ -3646,8 +3648,15 @@ static struct md_rdev *md_import_device(dev_t newdev, int super_format, int supe + if (err) + goto out_clear_rdev; + ++ if (super_format == -2) { ++ holder = &claim_rdev; ++ } else { ++ holder = rdev; ++ set_bit(Holder, &rdev->flags); ++ } ++ + rdev->bdev = blkdev_get_by_dev(newdev, BLK_OPEN_READ | BLK_OPEN_WRITE, +- super_format == -2 ? &claim_rdev : rdev, NULL); ++ holder, NULL); + if (IS_ERR(rdev->bdev)) { + pr_warn("md: could not open device unknown-block(%u,%u).\n", + MAJOR(newdev), MINOR(newdev)); +@@ -3684,7 +3693,7 @@ static struct md_rdev *md_import_device(dev_t newdev, int super_format, int supe + return rdev; + + out_blkdev_put: +- blkdev_put(rdev->bdev, super_format == -2 ? &claim_rdev : rdev); ++ blkdev_put(rdev->bdev, holder); + out_clear_rdev: + md_rdev_clear(rdev); + out_free_rdev: +diff --git a/drivers/md/md.h b/drivers/md/md.h +index 1aef86bf3fc31..b0a0f5a5c7836 100644 +--- a/drivers/md/md.h ++++ b/drivers/md/md.h +@@ -211,6 +211,9 @@ enum flag_bits { + * check if there is collision between raid1 + * serial bios. + */ ++ Holder, /* rdev is used as holder while opening ++ * underlying disk exclusively. ++ */ + }; + + static inline int is_badblock(struct md_rdev *rdev, sector_t s, int sectors, +-- +2.40.1 + diff --git a/queue-6.5/md-raid1-fix-error-iso-c90-forbids-mixed-declaration.patch b/queue-6.5/md-raid1-fix-error-iso-c90-forbids-mixed-declaration.patch new file mode 100644 index 00000000000..41c50626090 --- /dev/null +++ b/queue-6.5/md-raid1-fix-error-iso-c90-forbids-mixed-declaration.patch @@ -0,0 +1,54 @@ +From 9401b654fb8fd3a84a73316b9d7af924f17c7046 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 11 Sep 2023 14:25:23 -0700 +Subject: md/raid1: fix error: ISO C90 forbids mixed declarations +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Nigel Croxon + +[ Upstream commit df203da47f4428bc286fc99318936416253a321c ] + +There is a compile error when this commit is added: +md: raid1: fix potential OOB in raid1_remove_disk() + +drivers/md/raid1.c: In function 'raid1_remove_disk': +drivers/md/raid1.c:1844:9: error: ISO C90 forbids mixed declarations +and code [-Werror=declaration-after-statement] +1844 |         struct raid1_info *p = conf->mirrors + number; +     |         ^~~~~~ + +That's because the new code was inserted before the struct. +The change is move the struct command above this commit. + +Fixes: 8b0472b50bcf ("md: raid1: fix potential OOB in raid1_remove_disk()") +Signed-off-by: Nigel Croxon +Signed-off-by: Song Liu +Link: https://lore.kernel.org/r/46d929d0-2aab-4cf2-b2bf-338963e8ba5a@redhat.com +Signed-off-by: Sasha Levin +--- + drivers/md/raid1.c | 3 +-- + 1 file changed, 1 insertion(+), 2 deletions(-) + +diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c +index 80aeee63dfb78..a60acd72210aa 100644 +--- a/drivers/md/raid1.c ++++ b/drivers/md/raid1.c +@@ -1829,12 +1829,11 @@ static int raid1_remove_disk(struct mddev *mddev, struct md_rdev *rdev) + struct r1conf *conf = mddev->private; + int err = 0; + int number = rdev->raid_disk; ++ struct raid1_info *p = conf->mirrors + number; + + if (unlikely(number >= conf->raid_disks)) + goto abort; + +- struct raid1_info *p = conf->mirrors + number; +- + if (rdev != p->rdev) + p = conf->mirrors + conf->raid_disks + number; + +-- +2.40.1 + diff --git a/queue-6.5/md-raid1-fix-potential-oob-in-raid1_remove_disk.patch b/queue-6.5/md-raid1-fix-potential-oob-in-raid1_remove_disk.patch new file mode 100644 index 00000000000..06af2801884 --- /dev/null +++ b/queue-6.5/md-raid1-fix-potential-oob-in-raid1_remove_disk.patch @@ -0,0 +1,46 @@ +From e5abf80d4ad8c4714a7d953ff7c7bae372883da2 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 22 Jul 2023 15:53:53 +0800 +Subject: md: raid1: fix potential OOB in raid1_remove_disk() + +From: Zhang Shurong + +[ Upstream commit 8b0472b50bcf0f19a5119b00a53b63579c8e1e4d ] + +If rddev->raid_disk is greater than mddev->raid_disks, there will be +an out-of-bounds in raid1_remove_disk(). We have already found +similar reports as follows: + +1) commit d17f744e883b ("md-raid10: fix KASAN warning") +2) commit 1ebc2cec0b7d ("dm raid: fix KASAN warning in raid5_remove_disk") + +Fix this bug by checking whether the "number" variable is +valid. + +Signed-off-by: Zhang Shurong +Reviewed-by: Yu Kuai +Link: https://lore.kernel.org/r/tencent_0D24426FAC6A21B69AC0C03CE4143A508F09@qq.com +Signed-off-by: Song Liu +Signed-off-by: Sasha Levin +--- + drivers/md/raid1.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c +index dd25832eb0452..80aeee63dfb78 100644 +--- a/drivers/md/raid1.c ++++ b/drivers/md/raid1.c +@@ -1829,6 +1829,10 @@ static int raid1_remove_disk(struct mddev *mddev, struct md_rdev *rdev) + struct r1conf *conf = mddev->private; + int err = 0; + int number = rdev->raid_disk; ++ ++ if (unlikely(number >= conf->raid_disks)) ++ goto abort; ++ + struct raid1_info *p = conf->mirrors + number; + + if (rdev != p->rdev) +-- +2.40.1 + diff --git a/queue-6.5/media-af9005-fix-null-ptr-deref-in-af9005_i2c_xfer.patch b/queue-6.5/media-af9005-fix-null-ptr-deref-in-af9005_i2c_xfer.patch new file mode 100644 index 00000000000..77186aaa5a1 --- /dev/null +++ b/queue-6.5/media-af9005-fix-null-ptr-deref-in-af9005_i2c_xfer.patch @@ -0,0 +1,52 @@ +From b0a266dd48cb8c69d58d5bcae24fc620660a44b1 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 8 Jul 2023 23:24:11 +0800 +Subject: media: af9005: Fix null-ptr-deref in af9005_i2c_xfer + +From: Zhang Shurong + +[ Upstream commit f4ee84f27625ce1fdf41e8483fa0561a1b837d10 ] + +In af9005_i2c_xfer, msg is controlled by user. When msg[i].buf +is null and msg[i].len is zero, former checks on msg[i].buf would be +passed. Malicious data finally reach af9005_i2c_xfer. If accessing +msg[i].buf[0] without sanity check, null ptr deref would happen. +We add check on msg[i].len to prevent crash. + +Similar commit: +commit 0ed554fd769a +("media: dvb-usb: az6027: fix null-ptr-deref in az6027_i2c_xfer()") + +Signed-off-by: Zhang Shurong +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/usb/dvb-usb/af9005.c | 5 +++++ + 1 file changed, 5 insertions(+) + +diff --git a/drivers/media/usb/dvb-usb/af9005.c b/drivers/media/usb/dvb-usb/af9005.c +index 0827bf3d4e8c7..13604e6acdb83 100644 +--- a/drivers/media/usb/dvb-usb/af9005.c ++++ b/drivers/media/usb/dvb-usb/af9005.c +@@ -422,6 +422,10 @@ static int af9005_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[], + if (ret == 0) + ret = 2; + } else { ++ if (msg[0].len < 2) { ++ ret = -EOPNOTSUPP; ++ goto unlock; ++ } + /* write one or more registers */ + reg = msg[0].buf[0]; + addr = msg[0].addr; +@@ -431,6 +435,7 @@ static int af9005_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[], + ret = 1; + } + ++unlock: + mutex_unlock(&d->i2c_mutex); + return ret; + } +-- +2.40.1 + diff --git a/queue-6.5/media-anysee-fix-null-ptr-deref-in-anysee_master_xfe.patch b/queue-6.5/media-anysee-fix-null-ptr-deref-in-anysee_master_xfe.patch new file mode 100644 index 00000000000..0fbff353259 --- /dev/null +++ b/queue-6.5/media-anysee-fix-null-ptr-deref-in-anysee_master_xfe.patch @@ -0,0 +1,43 @@ +From 749dd1e56f58cb5273a03a62c82d88ff88401d03 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 9 Jul 2023 00:02:20 +0800 +Subject: media: anysee: fix null-ptr-deref in anysee_master_xfer + +From: Zhang Shurong + +[ Upstream commit c30411266fd67ea3c02a05c157231654d5a3bdc9 ] + +In anysee_master_xfer, msg is controlled by user. When msg[i].buf +is null and msg[i].len is zero, former checks on msg[i].buf would be +passed. Malicious data finally reach anysee_master_xfer. If accessing +msg[i].buf[0] without sanity check, null ptr deref would happen. +We add check on msg[i].len to prevent crash. + +Similar commit: +commit 0ed554fd769a +("media: dvb-usb: az6027: fix null-ptr-deref in az6027_i2c_xfer()") + +Signed-off-by: Zhang Shurong +Signed-off-by: Hans Verkuil +[hverkuil: add spaces around +] +Signed-off-by: Sasha Levin +--- + drivers/media/usb/dvb-usb-v2/anysee.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/media/usb/dvb-usb-v2/anysee.c b/drivers/media/usb/dvb-usb-v2/anysee.c +index aa45b5d263f6b..a1235d0cce92f 100644 +--- a/drivers/media/usb/dvb-usb-v2/anysee.c ++++ b/drivers/media/usb/dvb-usb-v2/anysee.c +@@ -202,7 +202,7 @@ static int anysee_master_xfer(struct i2c_adapter *adap, struct i2c_msg *msg, + + while (i < num) { + if (num > i + 1 && (msg[i+1].flags & I2C_M_RD)) { +- if (msg[i].len > 2 || msg[i+1].len > 60) { ++ if (msg[i].len != 2 || msg[i + 1].len > 60) { + ret = -EOPNOTSUPP; + break; + } +-- +2.40.1 + diff --git a/queue-6.5/media-az6007-fix-null-ptr-deref-in-az6007_i2c_xfer.patch b/queue-6.5/media-az6007-fix-null-ptr-deref-in-az6007_i2c_xfer.patch new file mode 100644 index 00000000000..4e9b50932f2 --- /dev/null +++ b/queue-6.5/media-az6007-fix-null-ptr-deref-in-az6007_i2c_xfer.patch @@ -0,0 +1,55 @@ +From 4303f0e4febbc49f2a1d511ddf4a26dedf0c76fb Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 9 Jul 2023 00:28:17 +0800 +Subject: media: az6007: Fix null-ptr-deref in az6007_i2c_xfer() + +From: Zhang Shurong + +[ Upstream commit 1047f9343011f2cedc73c64829686206a7e9fc3f ] + +In az6007_i2c_xfer, msg is controlled by user. When msg[i].buf +is null and msg[i].len is zero, former checks on msg[i].buf would be +passed. Malicious data finally reach az6007_i2c_xfer. If accessing +msg[i].buf[0] without sanity check, null ptr deref would happen. +We add check on msg[i].len to prevent crash. + +Similar commit: +commit 0ed554fd769a +("media: dvb-usb: az6027: fix null-ptr-deref in az6027_i2c_xfer()") + +Signed-off-by: Zhang Shurong +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/usb/dvb-usb-v2/az6007.c | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/drivers/media/usb/dvb-usb-v2/az6007.c b/drivers/media/usb/dvb-usb-v2/az6007.c +index 2dcbb49d66dab..2410054ddb2c3 100644 +--- a/drivers/media/usb/dvb-usb-v2/az6007.c ++++ b/drivers/media/usb/dvb-usb-v2/az6007.c +@@ -788,6 +788,10 @@ static int az6007_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msgs[], + if (az6007_xfer_debug) + printk(KERN_DEBUG "az6007: I2C W addr=0x%x len=%d\n", + addr, msgs[i].len); ++ if (msgs[i].len < 1) { ++ ret = -EIO; ++ goto err; ++ } + req = AZ6007_I2C_WR; + index = msgs[i].buf[0]; + value = addr | (1 << 8); +@@ -802,6 +806,10 @@ static int az6007_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msgs[], + if (az6007_xfer_debug) + printk(KERN_DEBUG "az6007: I2C R addr=0x%x len=%d\n", + addr, msgs[i].len); ++ if (msgs[i].len < 1) { ++ ret = -EIO; ++ goto err; ++ } + req = AZ6007_I2C_RD; + index = msgs[i].buf[0]; + value = addr; +-- +2.40.1 + diff --git a/queue-6.5/media-dvb-usb-v2-af9035-fix-null-ptr-deref-in-af9035.patch b/queue-6.5/media-dvb-usb-v2-af9035-fix-null-ptr-deref-in-af9035.patch new file mode 100644 index 00000000000..ac59ff70531 --- /dev/null +++ b/queue-6.5/media-dvb-usb-v2-af9035-fix-null-ptr-deref-in-af9035.patch @@ -0,0 +1,64 @@ +From 31ec1ff1f4e0ca78943cfc77007c49a6113858ad Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 6 Jul 2023 00:06:54 +0800 +Subject: media: dvb-usb-v2: af9035: Fix null-ptr-deref in + af9035_i2c_master_xfer + +From: Zhang Shurong + +[ Upstream commit 7bf744f2de0a848fb1d717f5831b03db96feae89 ] + +In af9035_i2c_master_xfer, msg is controlled by user. When msg[i].buf +is null and msg[i].len is zero, former checks on msg[i].buf would be +passed. Malicious data finally reach af9035_i2c_master_xfer. If accessing +msg[i].buf[0] without sanity check, null ptr deref would happen. +We add check on msg[i].len to prevent crash. + +Similar commit: +commit 0ed554fd769a +("media: dvb-usb: az6027: fix null-ptr-deref in az6027_i2c_xfer()") + +Signed-off-by: Zhang Shurong +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/usb/dvb-usb-v2/af9035.c | 9 +++++---- + 1 file changed, 5 insertions(+), 4 deletions(-) + +diff --git a/drivers/media/usb/dvb-usb-v2/af9035.c b/drivers/media/usb/dvb-usb-v2/af9035.c +index 1e9c8d01523be..33a2aa8907e65 100644 +--- a/drivers/media/usb/dvb-usb-v2/af9035.c ++++ b/drivers/media/usb/dvb-usb-v2/af9035.c +@@ -322,6 +322,8 @@ static int af9035_i2c_master_xfer(struct i2c_adapter *adap, + ret = -EOPNOTSUPP; + } else if ((msg[0].addr == state->af9033_i2c_addr[0]) || + (msg[0].addr == state->af9033_i2c_addr[1])) { ++ if (msg[0].len < 3 || msg[1].len < 1) ++ return -EOPNOTSUPP; + /* demod access via firmware interface */ + u32 reg = msg[0].buf[0] << 16 | msg[0].buf[1] << 8 | + msg[0].buf[2]; +@@ -381,6 +383,8 @@ static int af9035_i2c_master_xfer(struct i2c_adapter *adap, + ret = -EOPNOTSUPP; + } else if ((msg[0].addr == state->af9033_i2c_addr[0]) || + (msg[0].addr == state->af9033_i2c_addr[1])) { ++ if (msg[0].len < 3) ++ return -EOPNOTSUPP; + /* demod access via firmware interface */ + u32 reg = msg[0].buf[0] << 16 | msg[0].buf[1] << 8 | + msg[0].buf[2]; +@@ -388,10 +392,7 @@ static int af9035_i2c_master_xfer(struct i2c_adapter *adap, + if (msg[0].addr == state->af9033_i2c_addr[1]) + reg |= 0x100000; + +- ret = (msg[0].len >= 3) ? af9035_wr_regs(d, reg, +- &msg[0].buf[3], +- msg[0].len - 3) +- : -EOPNOTSUPP; ++ ret = af9035_wr_regs(d, reg, &msg[0].buf[3], msg[0].len - 3); + } else { + /* I2C write */ + u8 buf[MAX_XFER_SIZE]; +-- +2.40.1 + diff --git a/queue-6.5/media-dvb-usb-v2-gl861-fix-null-ptr-deref-in-gl861_i.patch b/queue-6.5/media-dvb-usb-v2-gl861-fix-null-ptr-deref-in-gl861_i.patch new file mode 100644 index 00000000000..3e739ce1537 --- /dev/null +++ b/queue-6.5/media-dvb-usb-v2-gl861-fix-null-ptr-deref-in-gl861_i.patch @@ -0,0 +1,42 @@ +From 72bec26ec7596b865b08a3cde7fdf3091808ec48 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 10 Jul 2023 13:32:13 +0800 +Subject: media: dvb-usb-v2: gl861: Fix null-ptr-deref in gl861_i2c_master_xfer + +From: Zhang Shurong + +[ Upstream commit b97719a66970601cd3151a3e2020f4454a1c4ff6 ] + +In gl861_i2c_master_xfer, msg is controlled by user. When msg[i].buf +is null and msg[i].len is zero, former checks on msg[i].buf would be +passed. Malicious data finally reach gl861_i2c_master_xfer. If accessing +msg[i].buf[0] without sanity check, null ptr deref would happen. +We add check on msg[i].len to prevent crash. + +Similar commit: +commit 0ed554fd769a +("media: dvb-usb: az6027: fix null-ptr-deref in az6027_i2c_xfer()") + +Signed-off-by: Zhang Shurong +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/usb/dvb-usb-v2/gl861.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/media/usb/dvb-usb-v2/gl861.c b/drivers/media/usb/dvb-usb-v2/gl861.c +index 0c434259c36f1..c71e7b93476de 100644 +--- a/drivers/media/usb/dvb-usb-v2/gl861.c ++++ b/drivers/media/usb/dvb-usb-v2/gl861.c +@@ -120,7 +120,7 @@ static int gl861_i2c_master_xfer(struct i2c_adapter *adap, struct i2c_msg msg[], + } else if (num == 2 && !(msg[0].flags & I2C_M_RD) && + (msg[1].flags & I2C_M_RD)) { + /* I2C write + read */ +- if (msg[0].len > 1 || msg[1].len > sizeof(ctx->buf)) { ++ if (msg[0].len != 1 || msg[1].len > sizeof(ctx->buf)) { + ret = -EOPNOTSUPP; + goto err; + } +-- +2.40.1 + diff --git a/queue-6.5/media-dw2102-fix-null-ptr-deref-in-dw2102_i2c_transf.patch b/queue-6.5/media-dw2102-fix-null-ptr-deref-in-dw2102_i2c_transf.patch new file mode 100644 index 00000000000..38f63bef0d7 --- /dev/null +++ b/queue-6.5/media-dw2102-fix-null-ptr-deref-in-dw2102_i2c_transf.patch @@ -0,0 +1,98 @@ +From 9b4aeff70f8f1670985e10bb68bfa68a65ce0f3a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 8 Jul 2023 18:22:52 +0800 +Subject: media: dw2102: Fix null-ptr-deref in dw2102_i2c_transfer() + +From: Zhang Shurong + +[ Upstream commit 5ae544d94abc8ff77b1b9bf8774def3fa5689b5b ] + +In dw2102_i2c_transfer, msg is controlled by user. When msg[i].buf +is null and msg[i].len is zero, former checks on msg[i].buf would be +passed. Malicious data finally reach dw2102_i2c_transfer. If accessing +msg[i].buf[0] without sanity check, null ptr deref would happen. +We add check on msg[i].len to prevent crash. + +Similar commit: +commit 950e252cb469 +("[media] dw2102: limit messages to buffer size") + +Signed-off-by: Zhang Shurong +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/usb/dvb-usb/dw2102.c | 24 ++++++++++++++++++++++++ + 1 file changed, 24 insertions(+) + +diff --git a/drivers/media/usb/dvb-usb/dw2102.c b/drivers/media/usb/dvb-usb/dw2102.c +index 970b84c3f0b5a..b3bb1805829ad 100644 +--- a/drivers/media/usb/dvb-usb/dw2102.c ++++ b/drivers/media/usb/dvb-usb/dw2102.c +@@ -128,6 +128,10 @@ static int dw2102_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], + + switch (num) { + case 2: ++ if (msg[0].len < 1) { ++ num = -EOPNOTSUPP; ++ break; ++ } + /* read stv0299 register */ + value = msg[0].buf[0];/* register */ + for (i = 0; i < msg[1].len; i++) { +@@ -139,6 +143,10 @@ static int dw2102_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], + case 1: + switch (msg[0].addr) { + case 0x68: ++ if (msg[0].len < 2) { ++ num = -EOPNOTSUPP; ++ break; ++ } + /* write to stv0299 register */ + buf6[0] = 0x2a; + buf6[1] = msg[0].buf[0]; +@@ -148,6 +156,10 @@ static int dw2102_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], + break; + case 0x60: + if (msg[0].flags == 0) { ++ if (msg[0].len < 4) { ++ num = -EOPNOTSUPP; ++ break; ++ } + /* write to tuner pll */ + buf6[0] = 0x2c; + buf6[1] = 5; +@@ -159,6 +171,10 @@ static int dw2102_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], + dw210x_op_rw(d->udev, 0xb2, 0, 0, + buf6, 7, DW210X_WRITE_MSG); + } else { ++ if (msg[0].len < 1) { ++ num = -EOPNOTSUPP; ++ break; ++ } + /* read from tuner */ + dw210x_op_rw(d->udev, 0xb5, 0, 0, + buf6, 1, DW210X_READ_MSG); +@@ -166,12 +182,20 @@ static int dw2102_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], + } + break; + case (DW2102_RC_QUERY): ++ if (msg[0].len < 2) { ++ num = -EOPNOTSUPP; ++ break; ++ } + dw210x_op_rw(d->udev, 0xb8, 0, 0, + buf6, 2, DW210X_READ_MSG); + msg[0].buf[0] = buf6[0]; + msg[0].buf[1] = buf6[1]; + break; + case (DW2102_VOLTAGE_CTRL): ++ if (msg[0].len < 1) { ++ num = -EOPNOTSUPP; ++ break; ++ } + buf6[0] = 0x30; + buf6[1] = msg[0].buf[0]; + dw210x_op_rw(d->udev, 0xb2, 0, 0, +-- +2.40.1 + diff --git a/queue-6.5/media-mdp3-fix-resource-leaks-in-of_find_device_by_n.patch b/queue-6.5/media-mdp3-fix-resource-leaks-in-of_find_device_by_n.patch new file mode 100644 index 00000000000..11c3a197387 --- /dev/null +++ b/queue-6.5/media-mdp3-fix-resource-leaks-in-of_find_device_by_n.patch @@ -0,0 +1,40 @@ +From 5e45499931eac3712b3c4462cc73ff7ee418fbca Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 30 May 2023 18:17:18 +0800 +Subject: media: mdp3: Fix resource leaks in of_find_device_by_node + +From: Lu Hongfei + +[ Upstream commit 35ca8ce495366909b4c2e701d1356570dd40c4e2 ] + +Use put_device to release the object get through of_find_device_by_node, +avoiding resource leaks. + +Signed-off-by: Lu Hongfei +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/platform/mediatek/mdp3/mtk-mdp3-comp.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/drivers/media/platform/mediatek/mdp3/mtk-mdp3-comp.c b/drivers/media/platform/mediatek/mdp3/mtk-mdp3-comp.c +index a605e80c7dc36..b0ca2b3a8a739 100644 +--- a/drivers/media/platform/mediatek/mdp3/mtk-mdp3-comp.c ++++ b/drivers/media/platform/mediatek/mdp3/mtk-mdp3-comp.c +@@ -892,11 +892,13 @@ static int mdp_get_subsys_id(struct mdp_dev *mdp, struct device *dev, + ret = cmdq_dev_get_client_reg(&comp_pdev->dev, &cmdq_reg, index); + if (ret != 0) { + dev_err(&comp_pdev->dev, "cmdq_dev_get_subsys fail!\n"); ++ put_device(&comp_pdev->dev); + return -EINVAL; + } + + comp->subsys_id = cmdq_reg.subsys; + dev_dbg(&comp_pdev->dev, "subsys id=%d\n", cmdq_reg.subsys); ++ put_device(&comp_pdev->dev); + + return 0; + } +-- +2.40.1 + diff --git a/queue-6.5/media-pci-cx23885-replace-bug-with-error-return.patch b/queue-6.5/media-pci-cx23885-replace-bug-with-error-return.patch new file mode 100644 index 00000000000..62af0ac4759 --- /dev/null +++ b/queue-6.5/media-pci-cx23885-replace-bug-with-error-return.patch @@ -0,0 +1,36 @@ +From 741d4fafccfd036570b93e0afcd4056589ccdecf Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 21 Jul 2023 10:23:42 +0200 +Subject: media: pci: cx23885: replace BUG with error return + +From: Hans Verkuil + +[ Upstream commit 2e1796fd4904fdd6062a8e4589778ea899ea0c8d ] + +It was completely unnecessary to use BUG in buffer_prepare(). +Just replace it with an error return. This also fixes a smatch warning: + +drivers/media/pci/cx23885/cx23885-video.c:422 buffer_prepare() error: uninitialized symbol 'ret'. + +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/pci/cx23885/cx23885-video.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/media/pci/cx23885/cx23885-video.c b/drivers/media/pci/cx23885/cx23885-video.c +index 671fc0588e431..9af2c5596121c 100644 +--- a/drivers/media/pci/cx23885/cx23885-video.c ++++ b/drivers/media/pci/cx23885/cx23885-video.c +@@ -413,7 +413,7 @@ static int buffer_prepare(struct vb2_buffer *vb) + dev->height >> 1); + break; + default: +- BUG(); ++ return -EINVAL; /* should not happen */ + } + dprintk(2, "[%p/%d] buffer_init - %dx%d %dbpp 0x%08x - dma=0x%08lx\n", + buf, buf->vb.vb2_buf.index, +-- +2.40.1 + diff --git a/queue-6.5/media-pci-ipu3-cio2-initialise-timing-struct-to-avoi.patch b/queue-6.5/media-pci-ipu3-cio2-initialise-timing-struct-to-avoi.patch new file mode 100644 index 00000000000..4654760559b --- /dev/null +++ b/queue-6.5/media-pci-ipu3-cio2-initialise-timing-struct-to-avoi.patch @@ -0,0 +1,37 @@ +From b721d1c83c3b91e58c3d61fdd6edd8c6ff90e806 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 1 Aug 2023 10:14:30 +0300 +Subject: media: pci: ipu3-cio2: Initialise timing struct to avoid a compiler + warning + +From: Sakari Ailus + +[ Upstream commit 9d7531be3085a8f013cf173ccc4e72e3cf493538 ] + +Initialise timing struct in cio2_hw_init() to zero in order to avoid a +compiler warning. The warning was a false positive. + +Reported-by: Hans Verkuil +Signed-off-by: Sakari Ailus +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/pci/intel/ipu3/ipu3-cio2-main.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/media/pci/intel/ipu3/ipu3-cio2-main.c b/drivers/media/pci/intel/ipu3/ipu3-cio2-main.c +index dc09fbdb062b0..ca51776a961fb 100644 +--- a/drivers/media/pci/intel/ipu3/ipu3-cio2-main.c ++++ b/drivers/media/pci/intel/ipu3/ipu3-cio2-main.c +@@ -355,7 +355,7 @@ static int cio2_hw_init(struct cio2_device *cio2, struct cio2_queue *q) + void __iomem *const base = cio2->base; + u8 lanes, csi2bus = q->csi2.port; + u8 sensor_vc = SENSOR_VIR_CH_DFLT; +- struct cio2_csi2_timing timing; ++ struct cio2_csi2_timing timing = { 0 }; + int i, r; + + fmt = cio2_find_format(NULL, &q->subdev_fmt.code); +-- +2.40.1 + diff --git a/queue-6.5/media-tuners-qt1010-replace-bug_on-with-a-regular-er.patch b/queue-6.5/media-tuners-qt1010-replace-bug_on-with-a-regular-er.patch new file mode 100644 index 00000000000..ffca3961a8f --- /dev/null +++ b/queue-6.5/media-tuners-qt1010-replace-bug_on-with-a-regular-er.patch @@ -0,0 +1,46 @@ +From 0a85e2a7e80df5c260d26b445a83e076ea1804b8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 20 Jul 2023 08:20:51 +0200 +Subject: media: tuners: qt1010: replace BUG_ON with a regular error + +From: Hans Verkuil + +[ Upstream commit ee630b29ea44d1851bb6c903f400956604834463 ] + +BUG_ON is unnecessary here, and in addition it confuses smatch. +Replacing this with an error return help resolve this smatch +warning: + +drivers/media/tuners/qt1010.c:350 qt1010_init() error: buffer overflow 'i2c_data' 34 <= 34 + +Signed-off-by: Hans Verkuil +Signed-off-by: Sasha Levin +--- + drivers/media/tuners/qt1010.c | 11 ++++++----- + 1 file changed, 6 insertions(+), 5 deletions(-) + +diff --git a/drivers/media/tuners/qt1010.c b/drivers/media/tuners/qt1010.c +index 60931367b82ca..48fc79cd40273 100644 +--- a/drivers/media/tuners/qt1010.c ++++ b/drivers/media/tuners/qt1010.c +@@ -345,11 +345,12 @@ static int qt1010_init(struct dvb_frontend *fe) + else + valptr = &tmpval; + +- BUG_ON(i >= ARRAY_SIZE(i2c_data) - 1); +- +- err = qt1010_init_meas1(priv, i2c_data[i+1].reg, +- i2c_data[i].reg, +- i2c_data[i].val, valptr); ++ if (i >= ARRAY_SIZE(i2c_data) - 1) ++ err = -EIO; ++ else ++ err = qt1010_init_meas1(priv, i2c_data[i + 1].reg, ++ i2c_data[i].reg, ++ i2c_data[i].val, valptr); + i++; + break; + } +-- +2.40.1 + diff --git a/queue-6.5/misc-open-dice-make-open_dice-depend-on-has_iomem.patch b/queue-6.5/misc-open-dice-make-open_dice-depend-on-has_iomem.patch new file mode 100644 index 00000000000..1932b51ccbd --- /dev/null +++ b/queue-6.5/misc-open-dice-make-open_dice-depend-on-has_iomem.patch @@ -0,0 +1,52 @@ +From 63694d090b26fc6c4146bc75a8ec4dd4068d8be4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 7 Jul 2023 21:58:47 +0800 +Subject: misc: open-dice: make OPEN_DICE depend on HAS_IOMEM + +From: Baoquan He + +[ Upstream commit aefc8b57af7787c80686e49a5841e9289cb11f53 ] + +On s390 systems (aka mainframes), it has classic channel devices for +networking and permanent storage that are currently even more common +than PCI devices. Hence it could have a fully functional s390 kernel +with CONFIG_PCI=n, then the relevant iomem mapping functions +[including ioremap(), devm_ioremap(), etc.] are not available. + +Here let OPEN_DICE depend on HAS_IOMEM so that it won't be built +to cause below compiling error if PCI is unset: + +------ +ERROR: modpost: "devm_memremap" [drivers/misc/open-dice.ko] undefined! +ERROR: modpost: "devm_memunmap" [drivers/misc/open-dice.ko] undefined! +------ + +Reported-by: kernel test robot +Closes: https://lore.kernel.org/oe-kbuild-all/202306211329.ticOJCSv-lkp@intel.com/ +Signed-off-by: Baoquan He +Cc: Derek Kiernan +Cc: Dragan Cvetic +Cc: Arnd Bergmann +Cc: Greg Kroah-Hartman +Link: https://lore.kernel.org/r/20230707135852.24292-4-bhe@redhat.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/misc/Kconfig | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig +index 75e427f124b28..cadd4a820c033 100644 +--- a/drivers/misc/Kconfig ++++ b/drivers/misc/Kconfig +@@ -496,6 +496,7 @@ config HISI_HIKEY_USB + config OPEN_DICE + tristate "Open Profile for DICE driver" + depends on OF_RESERVED_MEM ++ depends on HAS_IOMEM + help + This driver exposes a DICE reserved memory region to userspace via + a character device. The memory region contains Compound Device +-- +2.40.1 + diff --git a/queue-6.5/mmc-sdhci-esdhc-imx-improve-esdhc_flag_err010450.patch b/queue-6.5/mmc-sdhci-esdhc-imx-improve-esdhc_flag_err010450.patch new file mode 100644 index 00000000000..eac81f10f9f --- /dev/null +++ b/queue-6.5/mmc-sdhci-esdhc-imx-improve-esdhc_flag_err010450.patch @@ -0,0 +1,54 @@ +From 40449789b4501c54edafec30f6c130a5d837fe03 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 11 Aug 2023 23:48:53 +0200 +Subject: mmc: sdhci-esdhc-imx: improve ESDHC_FLAG_ERR010450 + +From: Giulio Benetti + +[ Upstream commit 5ae4b0d8875caa44946e579420c7fd5740d58653 ] + +Errata ERR010450 only shows up if voltage is 1.8V, but if the device is +supplied by 3v3 the errata can be ignored. So let's check for if quirk +SDHCI_QUIRK2_NO_1_8_V is defined or not before limiting the frequency. + +Cc: Jim Reinhart +Cc: James Autry +Cc: Matthew Maron +Signed-off-by: Giulio Benetti +Acked-by: Haibo Chen +Acked-by: Adrian Hunter +Link: https://lore.kernel.org/r/20230811214853.8623-1-giulio.benetti@benettiengineering.com +Signed-off-by: Ulf Hansson +Signed-off-by: Sasha Levin +--- + drivers/mmc/host/sdhci-esdhc-imx.c | 7 ++++--- + 1 file changed, 4 insertions(+), 3 deletions(-) + +diff --git a/drivers/mmc/host/sdhci-esdhc-imx.c b/drivers/mmc/host/sdhci-esdhc-imx.c +index eebf94604a7fd..cddecc1e1ac2f 100644 +--- a/drivers/mmc/host/sdhci-esdhc-imx.c ++++ b/drivers/mmc/host/sdhci-esdhc-imx.c +@@ -171,8 +171,8 @@ + #define ESDHC_FLAG_HS400 BIT(9) + /* + * The IP has errata ERR010450 +- * uSDHC: Due to the I/O timing limit, for SDR mode, SD card clock can't +- * exceed 150MHz, for DDR mode, SD card clock can't exceed 45MHz. ++ * uSDHC: At 1.8V due to the I/O timing limit, for SDR mode, SD card ++ * clock can't exceed 150MHz, for DDR mode, SD card clock can't exceed 45MHz. + */ + #define ESDHC_FLAG_ERR010450 BIT(10) + /* The IP supports HS400ES mode */ +@@ -961,7 +961,8 @@ static inline void esdhc_pltfm_set_clock(struct sdhci_host *host, + | ESDHC_CLOCK_MASK); + sdhci_writel(host, temp, ESDHC_SYSTEM_CONTROL); + +- if (imx_data->socdata->flags & ESDHC_FLAG_ERR010450) { ++ if ((imx_data->socdata->flags & ESDHC_FLAG_ERR010450) && ++ (!(host->quirks2 & SDHCI_QUIRK2_NO_1_8_V))) { + unsigned int max_clock; + + max_clock = imx_data->is_ddr ? 45000000 : 150000000; +-- +2.40.1 + diff --git a/queue-6.5/mt76-mt7921-don-t-assume-adequate-headroom-for-sdio-.patch b/queue-6.5/mt76-mt7921-don-t-assume-adequate-headroom-for-sdio-.patch new file mode 100644 index 00000000000..bd632b5bb01 --- /dev/null +++ b/queue-6.5/mt76-mt7921-don-t-assume-adequate-headroom-for-sdio-.patch @@ -0,0 +1,78 @@ +From 702dcd436419b6e4a195d70042a0825d04fcbfc2 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 20 Apr 2023 15:24:51 -0400 +Subject: mt76: mt7921: don't assume adequate headroom for SDIO headers + +From: Matt Whitlock + +[ Upstream commit 98c4d0abf5c478db1ad126ff0c187dbb84c0803c ] + +mt7921_usb_sdio_tx_prepare_skb() calls mt7921_usb_sdio_write_txwi() and +mt7921_skb_add_usb_sdio_hdr(), both of which blindly assume that +adequate headroom will be available in the passed skb. This assumption +typically is satisfied when the skb was allocated in the net core for +transmission via the mt7921 netdev (although even that is only an +optimization and is not strictly guaranteed), but the assumption is +sometimes not satisfied when the skb originated in the receive path of +another netdev and was passed through to the mt7921, such as by the +bridge layer. Blindly prepending bytes to an skb is always wrong. + +This commit introduces a call to skb_cow_head() before the call to +mt7921_usb_sdio_write_txwi() in mt7921_usb_sdio_tx_prepare_skb() to +ensure that at least MT_SDIO_TXD_SIZE + MT_SDIO_HDR_SIZE bytes can be +pushed onto the skb. + +Without this fix, I can trivially cause kernel panics by bridging an +MT7921AU-based USB 802.11ax interface with an Ethernet interface on an +Intel Atom-based x86 system using its onboard RTL8169 PCI Ethernet +adapter and also on an ARM-based Raspberry Pi 1 using its onboard +SMSC9512 USB Ethernet adapter. Note that the panics do not occur in +every system configuration, as they occur only if the receiving netdev +leaves less headroom in its received skbs than the mt7921 needs for its +SDIO headers. + +Here is an example stack trace of this panic on Raspberry Pi OS Lite +2023-02-21 running kernel 6.1.24+ [1]: + + skb_panic from skb_push+0x44/0x48 + skb_push from mt7921_usb_sdio_tx_prepare_skb+0xd4/0x190 [mt7921_common] + mt7921_usb_sdio_tx_prepare_skb [mt7921_common] from mt76u_tx_queue_skb+0x94/0x1d0 [mt76_usb] + mt76u_tx_queue_skb [mt76_usb] from __mt76_tx_queue_skb+0x4c/0xc8 [mt76] + __mt76_tx_queue_skb [mt76] from mt76_txq_schedule.part.0+0x13c/0x398 [mt76] + mt76_txq_schedule.part.0 [mt76] from mt76_txq_schedule_all+0x24/0x30 [mt76] + mt76_txq_schedule_all [mt76] from mt7921_tx_worker+0x58/0xf4 [mt7921_common] + mt7921_tx_worker [mt7921_common] from __mt76_worker_fn+0x9c/0xec [mt76] + __mt76_worker_fn [mt76] from kthread+0xbc/0xe0 + kthread from ret_from_fork+0x14/0x34 + +After this fix, bridging the mt7921 interface works fine on both of my +previously problematic systems. + +[1] https://github.com/raspberrypi/firmware/tree/5c276f55a4b21345cd4d6200a504ee991851ff7a + +Link: https://github.com/openwrt/openwrt/issues/11796 +Signed-off-by: Matt Whitlock +Signed-off-by: Felix Fietkau +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/mediatek/mt76/mt7921/mac.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/drivers/net/wireless/mediatek/mt76/mt7921/mac.c b/drivers/net/wireless/mediatek/mt76/mt7921/mac.c +index 1675bf5204812..a671c601c5836 100644 +--- a/drivers/net/wireless/mediatek/mt76/mt7921/mac.c ++++ b/drivers/net/wireless/mediatek/mt76/mt7921/mac.c +@@ -1180,6 +1180,10 @@ int mt7921_usb_sdio_tx_prepare_skb(struct mt76_dev *mdev, void *txwi_ptr, + if (unlikely(tx_info->skb->len <= ETH_HLEN)) + return -EINVAL; + ++ err = skb_cow_head(skb, MT_SDIO_TXD_SIZE + MT_SDIO_HDR_SIZE); ++ if (err) ++ return err; ++ + if (!wcid) + wcid = &dev->mt76.global_wcid; + +-- +2.40.1 + diff --git a/queue-6.5/mtd-spi-nor-spansion-preserve-cfr2v-7-when-writing-m.patch b/queue-6.5/mtd-spi-nor-spansion-preserve-cfr2v-7-when-writing-m.patch new file mode 100644 index 00000000000..39f5d90ffb1 --- /dev/null +++ b/queue-6.5/mtd-spi-nor-spansion-preserve-cfr2v-7-when-writing-m.patch @@ -0,0 +1,66 @@ +From aa3b20d8aa0191e86db7e62f6c784bf670bdaa09 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 26 Jul 2023 10:52:48 +0300 +Subject: mtd: spi-nor: spansion: preserve CFR2V[7] when writing MEMLAT + +From: Takahiro Kuwano + +[ Upstream commit 1e611e104b9acb6310b8c684d5acee0e11ca7bd1 ] + +CFR2V[7] is assigned to Flash's address mode (3- or 4-ybte) and must not +be changed when writing MEMLAT (CFR2V[3:0]). CFR2V shall be used in a read, +update, write back fashion. + +Fixes: c3266af101f2 ("mtd: spi-nor: spansion: add support for Cypress Semper flash") +Signed-off-by: Takahiro Kuwano +Cc: stable@vger.kernel.org +Link: https://lore.kernel.org/r/20230726075257.12985-3-tudor.ambarus@linaro.org +Signed-off-by: Tudor Ambarus +Signed-off-by: Sasha Levin +--- + drivers/mtd/spi-nor/spansion.c | 14 +++++++++++++- + 1 file changed, 13 insertions(+), 1 deletion(-) + +diff --git a/drivers/mtd/spi-nor/spansion.c b/drivers/mtd/spi-nor/spansion.c +index 9edc1b7ac091a..4fbaa6fba45a6 100644 +--- a/drivers/mtd/spi-nor/spansion.c ++++ b/drivers/mtd/spi-nor/spansion.c +@@ -4,6 +4,7 @@ + * Copyright (C) 2014, Freescale Semiconductor, Inc. + */ + ++#include + #include + #include + +@@ -28,6 +29,7 @@ + #define SPINOR_REG_CYPRESS_CFR2 0x3 + #define SPINOR_REG_CYPRESS_CFR2V \ + (SPINOR_REG_CYPRESS_VREG + SPINOR_REG_CYPRESS_CFR2) ++#define SPINOR_REG_CYPRESS_CFR2_MEMLAT_MASK GENMASK(3, 0) + #define SPINOR_REG_CYPRESS_CFR2_MEMLAT_11_24 0xb + #define SPINOR_REG_CYPRESS_CFR2_ADRBYT BIT(7) + #define SPINOR_REG_CYPRESS_CFR3 0x4 +@@ -161,8 +163,18 @@ static int cypress_nor_octal_dtr_en(struct spi_nor *nor) + int ret; + u8 addr_mode_nbytes = nor->params->addr_mode_nbytes; + ++ op = (struct spi_mem_op) ++ CYPRESS_NOR_RD_ANY_REG_OP(addr_mode_nbytes, ++ SPINOR_REG_CYPRESS_CFR2V, 0, buf); ++ ++ ret = spi_nor_read_any_reg(nor, &op, nor->reg_proto); ++ if (ret) ++ return ret; ++ + /* Use 24 dummy cycles for memory array reads. */ +- *buf = SPINOR_REG_CYPRESS_CFR2_MEMLAT_11_24; ++ *buf &= ~SPINOR_REG_CYPRESS_CFR2_MEMLAT_MASK; ++ *buf |= FIELD_PREP(SPINOR_REG_CYPRESS_CFR2_MEMLAT_MASK, ++ SPINOR_REG_CYPRESS_CFR2_MEMLAT_11_24); + op = (struct spi_mem_op) + CYPRESS_NOR_WR_ANY_REG_OP(addr_mode_nbytes, + SPINOR_REG_CYPRESS_CFR2V, 1, buf); +-- +2.40.1 + diff --git a/queue-6.5/mtd-spi-nor-spansion-use-clpef-as-an-alternative-to-.patch b/queue-6.5/mtd-spi-nor-spansion-use-clpef-as-an-alternative-to-.patch new file mode 100644 index 00000000000..1a28c640a80 --- /dev/null +++ b/queue-6.5/mtd-spi-nor-spansion-use-clpef-as-an-alternative-to-.patch @@ -0,0 +1,486 @@ +From d6c419079b6cd3a26f6825c78481c7a78d7d7c81 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 26 Jul 2023 10:52:47 +0300 +Subject: mtd: spi-nor: spansion: use CLPEF as an alternative to CLSR + +From: Takahiro Kuwano + +[ Upstream commit d534fd9787d5925d9637752410e3ea92ca7f4cfa ] + +Infineon S28Hx (SEMPER Octal) and S25FS256T (SEMPER Nano) support Clear +Program and Erase Failure Flags (CLPEF, 82h) instead of CLSR(30h). +Introduce a new mfr_flag together with the infrastructure to allow +manufacturer private data in the core. With this we remove the need +to have if checks in the code at runtime and instead set the correct +opcodes at probe time. S25Hx (SEMPER QSPI) supports CLSR but it may +be disabled by CFR3x[2] while CLPEF is always available. Therefore, +the mfr_flag is also applied to S25Hx for safety. + +Signed-off-by: Takahiro Kuwano +Link: https://lore.kernel.org/r/20230726075257.12985-2-tudor.ambarus@linaro.org +Signed-off-by: Tudor Ambarus +Stable-dep-of: 1e611e104b9a ("mtd: spi-nor: spansion: preserve CFR2V[7] when writing MEMLAT") +Signed-off-by: Sasha Levin +--- + drivers/mtd/spi-nor/atmel.c | 8 +++- + drivers/mtd/spi-nor/core.c | 23 +++++++---- + drivers/mtd/spi-nor/core.h | 4 +- + drivers/mtd/spi-nor/issi.c | 4 +- + drivers/mtd/spi-nor/macronix.c | 4 +- + drivers/mtd/spi-nor/micron-st.c | 4 +- + drivers/mtd/spi-nor/spansion.c | 72 ++++++++++++++++++++++++++------- + drivers/mtd/spi-nor/sst.c | 8 +++- + drivers/mtd/spi-nor/winbond.c | 4 +- + drivers/mtd/spi-nor/xilinx.c | 4 +- + 10 files changed, 103 insertions(+), 32 deletions(-) + +diff --git a/drivers/mtd/spi-nor/atmel.c b/drivers/mtd/spi-nor/atmel.c +index 656dd80a0be79..58968c1e7d2f8 100644 +--- a/drivers/mtd/spi-nor/atmel.c ++++ b/drivers/mtd/spi-nor/atmel.c +@@ -48,9 +48,11 @@ static const struct spi_nor_locking_ops at25fs_nor_locking_ops = { + .is_locked = at25fs_nor_is_locked, + }; + +-static void at25fs_nor_late_init(struct spi_nor *nor) ++static int at25fs_nor_late_init(struct spi_nor *nor) + { + nor->params->locking_ops = &at25fs_nor_locking_ops; ++ ++ return 0; + } + + static const struct spi_nor_fixups at25fs_nor_fixups = { +@@ -149,9 +151,11 @@ static const struct spi_nor_locking_ops atmel_nor_global_protection_ops = { + .is_locked = atmel_nor_is_global_protected, + }; + +-static void atmel_nor_global_protection_late_init(struct spi_nor *nor) ++static int atmel_nor_global_protection_late_init(struct spi_nor *nor) + { + nor->params->locking_ops = &atmel_nor_global_protection_ops; ++ ++ return 0; + } + + static const struct spi_nor_fixups atmel_nor_global_protection_fixups = { +diff --git a/drivers/mtd/spi-nor/core.c b/drivers/mtd/spi-nor/core.c +index 55f4a902b8be9..72973cfb1d201 100644 +--- a/drivers/mtd/spi-nor/core.c ++++ b/drivers/mtd/spi-nor/core.c +@@ -2898,16 +2898,23 @@ static void spi_nor_init_fixup_flags(struct spi_nor *nor) + * SFDP standard, or where SFDP tables are not defined at all. + * Will replace the spi_nor_manufacturer_init_params() method. + */ +-static void spi_nor_late_init_params(struct spi_nor *nor) ++static int spi_nor_late_init_params(struct spi_nor *nor) + { + struct spi_nor_flash_parameter *params = nor->params; ++ int ret; + + if (nor->manufacturer && nor->manufacturer->fixups && +- nor->manufacturer->fixups->late_init) +- nor->manufacturer->fixups->late_init(nor); ++ nor->manufacturer->fixups->late_init) { ++ ret = nor->manufacturer->fixups->late_init(nor); ++ if (ret) ++ return ret; ++ } + +- if (nor->info->fixups && nor->info->fixups->late_init) +- nor->info->fixups->late_init(nor); ++ if (nor->info->fixups && nor->info->fixups->late_init) { ++ ret = nor->info->fixups->late_init(nor); ++ if (ret) ++ return ret; ++ } + + /* Default method kept for backward compatibility. */ + if (!params->set_4byte_addr_mode) +@@ -2925,6 +2932,8 @@ static void spi_nor_late_init_params(struct spi_nor *nor) + + if (nor->info->n_banks > 1) + params->bank_size = div64_u64(params->size, nor->info->n_banks); ++ ++ return 0; + } + + /** +@@ -3083,9 +3092,7 @@ static int spi_nor_init_params(struct spi_nor *nor) + spi_nor_init_params_deprecated(nor); + } + +- spi_nor_late_init_params(nor); +- +- return 0; ++ return spi_nor_late_init_params(nor); + } + + /** spi_nor_octal_dtr_enable() - enable Octal DTR I/O if needed +diff --git a/drivers/mtd/spi-nor/core.h b/drivers/mtd/spi-nor/core.h +index 4fb5ff09c63a9..2453bd5743ac9 100644 +--- a/drivers/mtd/spi-nor/core.h ++++ b/drivers/mtd/spi-nor/core.h +@@ -377,6 +377,7 @@ struct spi_nor_otp { + * than reading the status register to indicate they + * are ready for a new command + * @locking_ops: SPI NOR locking methods. ++ * @priv: flash's private data. + */ + struct spi_nor_flash_parameter { + u64 bank_size; +@@ -405,6 +406,7 @@ struct spi_nor_flash_parameter { + int (*ready)(struct spi_nor *nor); + + const struct spi_nor_locking_ops *locking_ops; ++ void *priv; + }; + + /** +@@ -431,7 +433,7 @@ struct spi_nor_fixups { + const struct sfdp_parameter_header *bfpt_header, + const struct sfdp_bfpt *bfpt); + int (*post_sfdp)(struct spi_nor *nor); +- void (*late_init)(struct spi_nor *nor); ++ int (*late_init)(struct spi_nor *nor); + }; + + /** +diff --git a/drivers/mtd/spi-nor/issi.c b/drivers/mtd/spi-nor/issi.c +index 400e2b42f45af..accdf7aa2bfde 100644 +--- a/drivers/mtd/spi-nor/issi.c ++++ b/drivers/mtd/spi-nor/issi.c +@@ -29,7 +29,7 @@ static const struct spi_nor_fixups is25lp256_fixups = { + .post_bfpt = is25lp256_post_bfpt_fixups, + }; + +-static void pm25lv_nor_late_init(struct spi_nor *nor) ++static int pm25lv_nor_late_init(struct spi_nor *nor) + { + struct spi_nor_erase_map *map = &nor->params->erase_map; + int i; +@@ -38,6 +38,8 @@ static void pm25lv_nor_late_init(struct spi_nor *nor) + for (i = 0; i < SNOR_ERASE_TYPE_MAX; i++) + if (map->erase_type[i].size == 4096) + map->erase_type[i].opcode = SPINOR_OP_BE_4K_PMC; ++ ++ return 0; + } + + static const struct spi_nor_fixups pm25lv_nor_fixups = { +diff --git a/drivers/mtd/spi-nor/macronix.c b/drivers/mtd/spi-nor/macronix.c +index 04888258e8914..eb149e517c1fe 100644 +--- a/drivers/mtd/spi-nor/macronix.c ++++ b/drivers/mtd/spi-nor/macronix.c +@@ -110,10 +110,12 @@ static void macronix_nor_default_init(struct spi_nor *nor) + nor->params->quad_enable = spi_nor_sr1_bit6_quad_enable; + } + +-static void macronix_nor_late_init(struct spi_nor *nor) ++static int macronix_nor_late_init(struct spi_nor *nor) + { + if (!nor->params->set_4byte_addr_mode) + nor->params->set_4byte_addr_mode = spi_nor_set_4byte_addr_mode_en4b_ex4b; ++ ++ return 0; + } + + static const struct spi_nor_fixups macronix_nor_fixups = { +diff --git a/drivers/mtd/spi-nor/micron-st.c b/drivers/mtd/spi-nor/micron-st.c +index 4b919756a2055..28c9c14a4b293 100644 +--- a/drivers/mtd/spi-nor/micron-st.c ++++ b/drivers/mtd/spi-nor/micron-st.c +@@ -429,7 +429,7 @@ static void micron_st_nor_default_init(struct spi_nor *nor) + nor->params->quad_enable = NULL; + } + +-static void micron_st_nor_late_init(struct spi_nor *nor) ++static int micron_st_nor_late_init(struct spi_nor *nor) + { + struct spi_nor_flash_parameter *params = nor->params; + +@@ -438,6 +438,8 @@ static void micron_st_nor_late_init(struct spi_nor *nor) + + if (!params->set_4byte_addr_mode) + params->set_4byte_addr_mode = spi_nor_set_4byte_addr_mode_wren_en4b_ex4b; ++ ++ return 0; + } + + static const struct spi_nor_fixups micron_st_nor_fixups = { +diff --git a/drivers/mtd/spi-nor/spansion.c b/drivers/mtd/spi-nor/spansion.c +index 15f9a80c10b9b..9edc1b7ac091a 100644 +--- a/drivers/mtd/spi-nor/spansion.c ++++ b/drivers/mtd/spi-nor/spansion.c +@@ -4,14 +4,17 @@ + * Copyright (C) 2014, Freescale Semiconductor, Inc. + */ + ++#include + #include + + #include "core.h" + + /* flash_info mfr_flag. Used to clear sticky prorietary SR bits. */ + #define USE_CLSR BIT(0) ++#define USE_CLPEF BIT(1) + + #define SPINOR_OP_CLSR 0x30 /* Clear status register 1 */ ++#define SPINOR_OP_CLPEF 0x82 /* Clear program/erase failure flags */ + #define SPINOR_OP_RD_ANY_REG 0x65 /* Read any register */ + #define SPINOR_OP_WR_ANY_REG 0x71 /* Write any register */ + #define SPINOR_REG_CYPRESS_VREG 0x00800000 +@@ -57,22 +60,32 @@ + SPI_MEM_OP_DUMMY(ndummy, 0), \ + SPI_MEM_OP_DATA_IN(1, buf, 0)) + +-#define SPANSION_CLSR_OP \ +- SPI_MEM_OP(SPI_MEM_OP_CMD(SPINOR_OP_CLSR, 0), \ ++#define SPANSION_OP(opcode) \ ++ SPI_MEM_OP(SPI_MEM_OP_CMD(opcode, 0), \ + SPI_MEM_OP_NO_ADDR, \ + SPI_MEM_OP_NO_DUMMY, \ + SPI_MEM_OP_NO_DATA) + ++/** ++ * struct spansion_nor_params - Spansion private parameters. ++ * @clsr: Clear Status Register or Clear Program and Erase Failure Flag ++ * opcode. ++ */ ++struct spansion_nor_params { ++ u8 clsr; ++}; ++ + /** + * spansion_nor_clear_sr() - Clear the Status Register. + * @nor: pointer to 'struct spi_nor'. + */ + static void spansion_nor_clear_sr(struct spi_nor *nor) + { ++ const struct spansion_nor_params *priv_params = nor->params->priv; + int ret; + + if (nor->spimem) { +- struct spi_mem_op op = SPANSION_CLSR_OP; ++ struct spi_mem_op op = SPANSION_OP(priv_params->clsr); + + spi_nor_spimem_setup_op(nor, &op, nor->reg_proto); + +@@ -528,9 +541,11 @@ static int s25fs256t_post_sfdp_fixup(struct spi_nor *nor) + return 0; + } + +-static void s25fs256t_late_init(struct spi_nor *nor) ++static int s25fs256t_late_init(struct spi_nor *nor) + { + cypress_nor_ecc_init(nor); ++ ++ return 0; + } + + static struct spi_nor_fixups s25fs256t_fixups = { +@@ -586,7 +601,7 @@ static int s25hx_t_post_sfdp_fixup(struct spi_nor *nor) + return cypress_nor_get_page_size(nor); + } + +-static void s25hx_t_late_init(struct spi_nor *nor) ++static int s25hx_t_late_init(struct spi_nor *nor) + { + struct spi_nor_flash_parameter *params = nor->params; + +@@ -598,6 +613,8 @@ static void s25hx_t_late_init(struct spi_nor *nor) + /* Replace ready() with multi die version */ + if (params->n_dice) + params->ready = cypress_nor_sr_ready_and_clear; ++ ++ return 0; + } + + static struct spi_nor_fixups s25hx_t_fixups = { +@@ -665,10 +682,12 @@ static int s28hx_t_post_bfpt_fixup(struct spi_nor *nor, + return 0; + } + +-static void s28hx_t_late_init(struct spi_nor *nor) ++static int s28hx_t_late_init(struct spi_nor *nor) + { + nor->params->octal_dtr_enable = cypress_nor_octal_dtr_enable; + cypress_nor_ecc_init(nor); ++ ++ return 0; + } + + static const struct spi_nor_fixups s28hx_t_fixups = { +@@ -792,47 +811,54 @@ static const struct flash_info spansion_nor_parts[] = { + FIXUP_FLAGS(SPI_NOR_4B_OPCODES) }, + { "s25fs256t", INFO6(0x342b19, 0x0f0890, 0, 0) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s25fs256t_fixups }, + { "s25hl512t", INFO6(0x342a1a, 0x0f0390, 256 * 1024, 256) + PARSE_SFDP +- MFR_FLAGS(USE_CLSR) ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s25hx_t_fixups }, + { "s25hl01gt", INFO6(0x342a1b, 0x0f0390, 256 * 1024, 512) + PARSE_SFDP +- MFR_FLAGS(USE_CLSR) ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s25hx_t_fixups }, + { "s25hl02gt", INFO6(0x342a1c, 0x0f0090, 0, 0) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + FLAGS(NO_CHIP_ERASE) + .fixups = &s25hx_t_fixups }, + { "s25hs512t", INFO6(0x342b1a, 0x0f0390, 256 * 1024, 256) + PARSE_SFDP +- MFR_FLAGS(USE_CLSR) ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s25hx_t_fixups }, + { "s25hs01gt", INFO6(0x342b1b, 0x0f0390, 256 * 1024, 512) + PARSE_SFDP +- MFR_FLAGS(USE_CLSR) ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s25hx_t_fixups }, + { "s25hs02gt", INFO6(0x342b1c, 0x0f0090, 0, 0) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + FLAGS(NO_CHIP_ERASE) + .fixups = &s25hx_t_fixups }, + { "cy15x104q", INFO6(0x042cc2, 0x7f7f7f, 512 * 1024, 1) + FLAGS(SPI_NOR_NO_ERASE) }, + { "s28hl512t", INFO(0x345a1a, 0, 256 * 1024, 256) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s28hx_t_fixups, + }, + { "s28hl01gt", INFO(0x345a1b, 0, 256 * 1024, 512) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s28hx_t_fixups, + }, + { "s28hs512t", INFO(0x345b1a, 0, 256 * 1024, 256) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s28hx_t_fixups, + }, + { "s28hs01gt", INFO(0x345b1b, 0, 256 * 1024, 512) + PARSE_SFDP ++ MFR_FLAGS(USE_CLPEF) + .fixups = &s28hx_t_fixups, + }, + }; +@@ -876,17 +902,35 @@ static int spansion_nor_sr_ready_and_clear(struct spi_nor *nor) + return !(nor->bouncebuf[0] & SR_WIP); + } + +-static void spansion_nor_late_init(struct spi_nor *nor) ++static int spansion_nor_late_init(struct spi_nor *nor) + { +- if (nor->params->size > SZ_16M) { ++ struct spi_nor_flash_parameter *params = nor->params; ++ struct spansion_nor_params *priv_params; ++ u8 mfr_flags = nor->info->mfr_flags; ++ ++ if (params->size > SZ_16M) { + nor->flags |= SNOR_F_4B_OPCODES; + /* No small sector erase for 4-byte command set */ + nor->erase_opcode = SPINOR_OP_SE; + nor->mtd.erasesize = nor->info->sector_size; + } + +- if (nor->info->mfr_flags & USE_CLSR) +- nor->params->ready = spansion_nor_sr_ready_and_clear; ++ if (mfr_flags & (USE_CLSR | USE_CLPEF)) { ++ priv_params = devm_kmalloc(nor->dev, sizeof(*priv_params), ++ GFP_KERNEL); ++ if (!priv_params) ++ return -ENOMEM; ++ ++ if (mfr_flags & USE_CLSR) ++ priv_params->clsr = SPINOR_OP_CLSR; ++ else if (mfr_flags & USE_CLPEF) ++ priv_params->clsr = SPINOR_OP_CLPEF; ++ ++ params->priv = priv_params; ++ params->ready = spansion_nor_sr_ready_and_clear; ++ } ++ ++ return 0; + } + + static const struct spi_nor_fixups spansion_nor_fixups = { +diff --git a/drivers/mtd/spi-nor/sst.c b/drivers/mtd/spi-nor/sst.c +index 688eb20c763e9..09fdc7023e09a 100644 +--- a/drivers/mtd/spi-nor/sst.c ++++ b/drivers/mtd/spi-nor/sst.c +@@ -49,9 +49,11 @@ static const struct spi_nor_locking_ops sst26vf_nor_locking_ops = { + .is_locked = sst26vf_nor_is_locked, + }; + +-static void sst26vf_nor_late_init(struct spi_nor *nor) ++static int sst26vf_nor_late_init(struct spi_nor *nor) + { + nor->params->locking_ops = &sst26vf_nor_locking_ops; ++ ++ return 0; + } + + static const struct spi_nor_fixups sst26vf_nor_fixups = { +@@ -203,10 +205,12 @@ static int sst_nor_write(struct mtd_info *mtd, loff_t to, size_t len, + return ret; + } + +-static void sst_nor_late_init(struct spi_nor *nor) ++static int sst_nor_late_init(struct spi_nor *nor) + { + if (nor->info->mfr_flags & SST_WRITE) + nor->mtd._write = sst_nor_write; ++ ++ return 0; + } + + static const struct spi_nor_fixups sst_nor_fixups = { +diff --git a/drivers/mtd/spi-nor/winbond.c b/drivers/mtd/spi-nor/winbond.c +index 63ba8e3a96f51..cd99c9a1c5688 100644 +--- a/drivers/mtd/spi-nor/winbond.c ++++ b/drivers/mtd/spi-nor/winbond.c +@@ -217,7 +217,7 @@ static const struct spi_nor_otp_ops winbond_nor_otp_ops = { + .is_locked = spi_nor_otp_is_locked_sr2, + }; + +-static void winbond_nor_late_init(struct spi_nor *nor) ++static int winbond_nor_late_init(struct spi_nor *nor) + { + struct spi_nor_flash_parameter *params = nor->params; + +@@ -233,6 +233,8 @@ static void winbond_nor_late_init(struct spi_nor *nor) + * from BFPT, if any. + */ + params->set_4byte_addr_mode = winbond_nor_set_4byte_addr_mode; ++ ++ return 0; + } + + static const struct spi_nor_fixups winbond_nor_fixups = { +diff --git a/drivers/mtd/spi-nor/xilinx.c b/drivers/mtd/spi-nor/xilinx.c +index 7175de8aa336a..00d53eae5ee83 100644 +--- a/drivers/mtd/spi-nor/xilinx.c ++++ b/drivers/mtd/spi-nor/xilinx.c +@@ -155,10 +155,12 @@ static int xilinx_nor_setup(struct spi_nor *nor, + return 0; + } + +-static void xilinx_nor_late_init(struct spi_nor *nor) ++static int xilinx_nor_late_init(struct spi_nor *nor) + { + nor->params->setup = xilinx_nor_setup; + nor->params->ready = xilinx_nor_sr_ready; ++ ++ return 0; + } + + static const struct spi_nor_fixups xilinx_nor_fixups = { +-- +2.40.1 + diff --git a/queue-6.5/net-ipv4-return-the-real-errno-instead-of-einval.patch b/queue-6.5/net-ipv4-return-the-real-errno-instead-of-einval.patch new file mode 100644 index 00000000000..eb5e4662e02 --- /dev/null +++ b/queue-6.5/net-ipv4-return-the-real-errno-instead-of-einval.patch @@ -0,0 +1,47 @@ +From 3fb1b967a90fe1e8fde581c49b4ace73fd51f847 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 7 Aug 2023 01:54:08 +0000 +Subject: net/ipv4: return the real errno instead of -EINVAL + +From: xu xin + +[ Upstream commit c67180efc507e04a87f22aa68bd7dd832db006b7 ] + +For now, No matter what error pointer ip_neigh_for_gw() returns, +ip_finish_output2() always return -EINVAL, which may mislead the upper +users. + +For exemple, an application uses sendto to send an UDP packet, but when the +neighbor table overflows, sendto() will get a value of -EINVAL, and it will +cause users to waste a lot of time checking parameters for errors. + +Return the real errno instead of -EINVAL. + +Signed-off-by: xu xin +Reviewed-by: Yang Yang +Cc: Si Hao +Reviewed-by: Kuniyuki Iwashima +Reviewed-by: Vadim Fedorenko +Link: https://lore.kernel.org/r/20230807015408.248237-1-xu.xin16@zte.com.cn +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/ipv4/ip_output.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/net/ipv4/ip_output.c b/net/ipv4/ip_output.c +index 6935d07a60c35..a8d2e8b1ff415 100644 +--- a/net/ipv4/ip_output.c ++++ b/net/ipv4/ip_output.c +@@ -236,7 +236,7 @@ static int ip_finish_output2(struct net *net, struct sock *sk, struct sk_buff *s + net_dbg_ratelimited("%s: No header cache and no neighbour!\n", + __func__); + kfree_skb_reason(skb, SKB_DROP_REASON_NEIGH_CREATEFAIL); +- return -EINVAL; ++ return PTR_ERR(neigh); + } + + static int ip_finish_output_gso(struct net *net, struct sock *sk, +-- +2.40.1 + diff --git a/queue-6.5/net-stmmac-use-per-queue-64-bit-statistics-where-nec.patch b/queue-6.5/net-stmmac-use-per-queue-64-bit-statistics-where-nec.patch new file mode 100644 index 00000000000..f2f0228296f --- /dev/null +++ b/queue-6.5/net-stmmac-use-per-queue-64-bit-statistics-where-nec.patch @@ -0,0 +1,1333 @@ +From 9c9cd57351a2f9c85963dce9d5185a261237b2d3 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 18 Jul 2023 00:06:30 +0800 +Subject: net: stmmac: use per-queue 64 bit statistics where necessary + +From: Jisheng Zhang + +[ Upstream commit 133466c3bbe171f826294161db203f7670bb30c8 ] + +Currently, there are two major issues with stmmac driver statistics +First of all, statistics in stmmac_extra_stats, stmmac_rxq_stats +and stmmac_txq_stats are 32 bit variables on 32 bit platforms. This +can cause some stats to overflow after several minutes of +high traffic, for example rx_pkt_n, tx_pkt_n and so on. + +Secondly, if HW supports multiqueues, there are frequent cacheline +ping pongs on some driver statistic vars, for example, normal_irq_n, +tx_pkt_n and so on. What's more, frequent cacheline ping pongs on +normal_irq_n happens in ISR, this makes the situation worse. + +To improve the driver, we convert those statistics to 64 bit, implement +ndo_get_stats64 and update .get_ethtool_stats implementation +accordingly. We also use per-queue statistics where necessary to remove +the cacheline ping pongs as much as possible to make multiqueue +operations faster. Those statistics which are not possible to overflow +and not frequently updated are kept as is. + +Signed-off-by: Jisheng Zhang +Link: https://lore.kernel.org/r/20230717160630.1892-3-jszhang@kernel.org +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/stmicro/stmmac/common.h | 39 ++-- + .../net/ethernet/stmicro/stmmac/dwmac-sun8i.c | 12 +- + .../ethernet/stmicro/stmmac/dwmac100_dma.c | 7 +- + .../ethernet/stmicro/stmmac/dwmac4_descs.c | 16 +- + .../net/ethernet/stmicro/stmmac/dwmac4_lib.c | 15 +- + .../net/ethernet/stmicro/stmmac/dwmac_lib.c | 12 +- + .../ethernet/stmicro/stmmac/dwxgmac2_descs.c | 6 +- + .../ethernet/stmicro/stmmac/dwxgmac2_dma.c | 14 +- + .../net/ethernet/stmicro/stmmac/enh_desc.c | 20 +- + drivers/net/ethernet/stmicro/stmmac/hwif.h | 12 +- + .../net/ethernet/stmicro/stmmac/norm_desc.c | 15 +- + drivers/net/ethernet/stmicro/stmmac/stmmac.h | 2 + + .../ethernet/stmicro/stmmac/stmmac_ethtool.c | 123 ++++++++--- + .../net/ethernet/stmicro/stmmac/stmmac_main.c | 200 ++++++++++++++---- + 14 files changed, 335 insertions(+), 158 deletions(-) + +diff --git a/drivers/net/ethernet/stmicro/stmmac/common.h b/drivers/net/ethernet/stmicro/stmmac/common.h +index 16e67c18b6f71..57f2137bbe9d9 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/common.h ++++ b/drivers/net/ethernet/stmicro/stmmac/common.h +@@ -59,13 +59,25 @@ + /* #define FRAME_FILTER_DEBUG */ + + struct stmmac_txq_stats { +- unsigned long tx_pkt_n; +- unsigned long tx_normal_irq_n; ++ u64 tx_bytes; ++ u64 tx_packets; ++ u64 tx_pkt_n; ++ u64 tx_normal_irq_n; ++ u64 napi_poll; ++ u64 tx_clean; ++ u64 tx_set_ic_bit; ++ u64 tx_tso_frames; ++ u64 tx_tso_nfrags; ++ struct u64_stats_sync syncp; + }; + + struct stmmac_rxq_stats { +- unsigned long rx_pkt_n; +- unsigned long rx_normal_irq_n; ++ u64 rx_bytes; ++ u64 rx_packets; ++ u64 rx_pkt_n; ++ u64 rx_normal_irq_n; ++ u64 napi_poll; ++ struct u64_stats_sync syncp; + }; + + /* Extra statistic and debug information exposed by ethtool */ +@@ -81,6 +93,7 @@ struct stmmac_extra_stats { + unsigned long tx_frame_flushed; + unsigned long tx_payload_error; + unsigned long tx_ip_header_error; ++ unsigned long tx_collision; + /* Receive errors */ + unsigned long rx_desc; + unsigned long sa_filter_fail; +@@ -113,14 +126,6 @@ struct stmmac_extra_stats { + /* Tx/Rx IRQ Events */ + unsigned long rx_early_irq; + unsigned long threshold; +- unsigned long tx_pkt_n; +- unsigned long rx_pkt_n; +- unsigned long normal_irq_n; +- unsigned long rx_normal_irq_n; +- unsigned long napi_poll; +- unsigned long tx_normal_irq_n; +- unsigned long tx_clean; +- unsigned long tx_set_ic_bit; + unsigned long irq_receive_pmt_irq_n; + /* MMC info */ + unsigned long mmc_tx_irq_n; +@@ -190,18 +195,16 @@ struct stmmac_extra_stats { + unsigned long mtl_rx_fifo_ctrl_active; + unsigned long mac_rx_frame_ctrl_fifo; + unsigned long mac_gmii_rx_proto_engine; +- /* TSO */ +- unsigned long tx_tso_frames; +- unsigned long tx_tso_nfrags; + /* EST */ + unsigned long mtl_est_cgce; + unsigned long mtl_est_hlbs; + unsigned long mtl_est_hlbf; + unsigned long mtl_est_btre; + unsigned long mtl_est_btrlm; +- /* per queue statistics */ +- struct stmmac_txq_stats txq_stats[MTL_MAX_TX_QUEUES]; +- struct stmmac_rxq_stats rxq_stats[MTL_MAX_RX_QUEUES]; ++ unsigned long rx_dropped; ++ unsigned long rx_errors; ++ unsigned long tx_dropped; ++ unsigned long tx_errors; + }; + + /* Safety Feature statistics exposed by ethtool */ +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c +index 1e714380d1250..b20f8ba34efd9 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c +@@ -440,8 +440,10 @@ static int sun8i_dwmac_dma_interrupt(struct stmmac_priv *priv, + struct stmmac_extra_stats *x, u32 chan, + u32 dir) + { +- u32 v; ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[chan]; ++ struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan]; + int ret = 0; ++ u32 v; + + v = readl(ioaddr + EMAC_INT_STA); + +@@ -452,7 +454,9 @@ static int sun8i_dwmac_dma_interrupt(struct stmmac_priv *priv, + + if (v & EMAC_TX_INT) { + ret |= handle_tx; +- x->tx_normal_irq_n++; ++ u64_stats_update_begin(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_normal_irq_n++; ++ u64_stats_update_end(&tx_q->txq_stats.syncp); + } + + if (v & EMAC_TX_DMA_STOP_INT) +@@ -474,7 +478,9 @@ static int sun8i_dwmac_dma_interrupt(struct stmmac_priv *priv, + + if (v & EMAC_RX_INT) { + ret |= handle_rx; +- x->rx_normal_irq_n++; ++ u64_stats_update_begin(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_normal_irq_n++; ++ u64_stats_update_end(&rx_q->rxq_stats.syncp); + } + + if (v & EMAC_RX_BUF_UA_INT) +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac100_dma.c b/drivers/net/ethernet/stmicro/stmmac/dwmac100_dma.c +index 1c32b1788f02e..dea270f60cc3e 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwmac100_dma.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwmac100_dma.c +@@ -82,29 +82,24 @@ static void dwmac100_dump_dma_regs(struct stmmac_priv *priv, + } + + /* DMA controller has two counters to track the number of the missed frames. */ +-static void dwmac100_dma_diagnostic_fr(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static void dwmac100_dma_diagnostic_fr(struct stmmac_extra_stats *x, + void __iomem *ioaddr) + { + u32 csr8 = readl(ioaddr + DMA_MISSED_FRAME_CTR); + + if (unlikely(csr8)) { + if (csr8 & DMA_MISSED_FRAME_OVE) { +- stats->rx_over_errors += 0x800; + x->rx_overflow_cntr += 0x800; + } else { + unsigned int ove_cntr; + ove_cntr = ((csr8 & DMA_MISSED_FRAME_OVE_CNTR) >> 17); +- stats->rx_over_errors += ove_cntr; + x->rx_overflow_cntr += ove_cntr; + } + + if (csr8 & DMA_MISSED_FRAME_OVE_M) { +- stats->rx_missed_errors += 0xffff; + x->rx_missed_cntr += 0xffff; + } else { + unsigned int miss_f = (csr8 & DMA_MISSED_FRAME_M_CNTR); +- stats->rx_missed_errors += miss_f; + x->rx_missed_cntr += miss_f; + } + } +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c +index 6a011d8633e8e..89a14084c6117 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c +@@ -13,8 +13,7 @@ + #include "dwmac4.h" + #include "dwmac4_descs.h" + +-static int dwmac4_wrback_get_tx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int dwmac4_wrback_get_tx_status(struct stmmac_extra_stats *x, + struct dma_desc *p, + void __iomem *ioaddr) + { +@@ -40,15 +39,13 @@ static int dwmac4_wrback_get_tx_status(struct net_device_stats *stats, + x->tx_frame_flushed++; + if (unlikely(tdes3 & TDES3_LOSS_CARRIER)) { + x->tx_losscarrier++; +- stats->tx_carrier_errors++; + } + if (unlikely(tdes3 & TDES3_NO_CARRIER)) { + x->tx_carrier++; +- stats->tx_carrier_errors++; + } + if (unlikely((tdes3 & TDES3_LATE_COLLISION) || + (tdes3 & TDES3_EXCESSIVE_COLLISION))) +- stats->collisions += ++ x->tx_collision += + (tdes3 & TDES3_COLLISION_COUNT_MASK) + >> TDES3_COLLISION_COUNT_SHIFT; + +@@ -73,8 +70,7 @@ static int dwmac4_wrback_get_tx_status(struct net_device_stats *stats, + return ret; + } + +-static int dwmac4_wrback_get_rx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int dwmac4_wrback_get_rx_status(struct stmmac_extra_stats *x, + struct dma_desc *p) + { + unsigned int rdes1 = le32_to_cpu(p->des1); +@@ -93,7 +89,7 @@ static int dwmac4_wrback_get_rx_status(struct net_device_stats *stats, + + if (unlikely(rdes3 & RDES3_ERROR_SUMMARY)) { + if (unlikely(rdes3 & RDES3_GIANT_PACKET)) +- stats->rx_length_errors++; ++ x->rx_length++; + if (unlikely(rdes3 & RDES3_OVERFLOW_ERROR)) + x->rx_gmac_overflow++; + +@@ -103,10 +99,8 @@ static int dwmac4_wrback_get_rx_status(struct net_device_stats *stats, + if (unlikely(rdes3 & RDES3_RECEIVE_ERROR)) + x->rx_mii++; + +- if (unlikely(rdes3 & RDES3_CRC_ERROR)) { ++ if (unlikely(rdes3 & RDES3_CRC_ERROR)) + x->rx_crc_errors++; +- stats->rx_crc_errors++; +- } + + if (unlikely(rdes3 & RDES3_DRIBBLE_ERROR)) + x->dribbling_bit++; +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_lib.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_lib.c +index 03ceb6a940732..980e5f8a37ec5 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_lib.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_lib.c +@@ -171,6 +171,8 @@ int dwmac4_dma_interrupt(struct stmmac_priv *priv, void __iomem *ioaddr, + const struct dwmac4_addrs *dwmac4_addrs = priv->plat->dwmac4_addrs; + u32 intr_status = readl(ioaddr + DMA_CHAN_STATUS(dwmac4_addrs, chan)); + u32 intr_en = readl(ioaddr + DMA_CHAN_INTR_ENA(dwmac4_addrs, chan)); ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[chan]; ++ struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan]; + int ret = 0; + + if (dir == DMA_DIR_RX) +@@ -198,18 +200,19 @@ int dwmac4_dma_interrupt(struct stmmac_priv *priv, void __iomem *ioaddr, + } + } + /* TX/RX NORMAL interrupts */ +- if (likely(intr_status & DMA_CHAN_STATUS_NIS)) +- x->normal_irq_n++; + if (likely(intr_status & DMA_CHAN_STATUS_RI)) { +- x->rx_normal_irq_n++; +- x->rxq_stats[chan].rx_normal_irq_n++; ++ u64_stats_update_begin(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_normal_irq_n++; ++ u64_stats_update_end(&rx_q->rxq_stats.syncp); + ret |= handle_rx; + } + if (likely(intr_status & DMA_CHAN_STATUS_TI)) { +- x->tx_normal_irq_n++; +- x->txq_stats[chan].tx_normal_irq_n++; ++ u64_stats_update_begin(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_normal_irq_n++; ++ u64_stats_update_end(&tx_q->txq_stats.syncp); + ret |= handle_tx; + } ++ + if (unlikely(intr_status & DMA_CHAN_STATUS_TBU)) + ret |= handle_tx; + if (unlikely(intr_status & DMA_CHAN_STATUS_ERI)) +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac_lib.c b/drivers/net/ethernet/stmicro/stmmac/dwmac_lib.c +index 0b6f999a83052..aaa09b16b016f 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwmac_lib.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwmac_lib.c +@@ -10,6 +10,7 @@ + #include + #include "common.h" + #include "dwmac_dma.h" ++#include "stmmac.h" + + #define GMAC_HI_REG_AE 0x80000000 + +@@ -161,6 +162,8 @@ static void show_rx_process_state(unsigned int status) + int dwmac_dma_interrupt(struct stmmac_priv *priv, void __iomem *ioaddr, + struct stmmac_extra_stats *x, u32 chan, u32 dir) + { ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[chan]; ++ struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan]; + int ret = 0; + /* read the status register (CSR5) */ + u32 intr_status = readl(ioaddr + DMA_STATUS); +@@ -208,17 +211,20 @@ int dwmac_dma_interrupt(struct stmmac_priv *priv, void __iomem *ioaddr, + } + /* TX/RX NORMAL interrupts */ + if (likely(intr_status & DMA_STATUS_NIS)) { +- x->normal_irq_n++; + if (likely(intr_status & DMA_STATUS_RI)) { + u32 value = readl(ioaddr + DMA_INTR_ENA); + /* to schedule NAPI on real RIE event. */ + if (likely(value & DMA_INTR_ENA_RIE)) { +- x->rx_normal_irq_n++; ++ u64_stats_update_begin(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_normal_irq_n++; ++ u64_stats_update_end(&rx_q->rxq_stats.syncp); + ret |= handle_rx; + } + } + if (likely(intr_status & DMA_STATUS_TI)) { +- x->tx_normal_irq_n++; ++ u64_stats_update_begin(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_normal_irq_n++; ++ u64_stats_update_end(&tx_q->txq_stats.syncp); + ret |= handle_tx; + } + if (unlikely(intr_status & DMA_STATUS_ERI)) +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_descs.c b/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_descs.c +index 13c347ee8be9c..fc82862a612c7 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_descs.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_descs.c +@@ -8,8 +8,7 @@ + #include "common.h" + #include "dwxgmac2.h" + +-static int dwxgmac2_get_tx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int dwxgmac2_get_tx_status(struct stmmac_extra_stats *x, + struct dma_desc *p, void __iomem *ioaddr) + { + unsigned int tdes3 = le32_to_cpu(p->des3); +@@ -23,8 +22,7 @@ static int dwxgmac2_get_tx_status(struct net_device_stats *stats, + return ret; + } + +-static int dwxgmac2_get_rx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int dwxgmac2_get_rx_status(struct stmmac_extra_stats *x, + struct dma_desc *p) + { + unsigned int rdes3 = le32_to_cpu(p->des3); +diff --git a/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_dma.c b/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_dma.c +index 070bd912580b7..3b5f8c595219b 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_dma.c ++++ b/drivers/net/ethernet/stmicro/stmmac/dwxgmac2_dma.c +@@ -337,6 +337,8 @@ static int dwxgmac2_dma_interrupt(struct stmmac_priv *priv, + struct stmmac_extra_stats *x, u32 chan, + u32 dir) + { ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[chan]; ++ struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[chan]; + u32 intr_status = readl(ioaddr + XGMAC_DMA_CH_STATUS(chan)); + u32 intr_en = readl(ioaddr + XGMAC_DMA_CH_INT_EN(chan)); + int ret = 0; +@@ -364,16 +366,16 @@ static int dwxgmac2_dma_interrupt(struct stmmac_priv *priv, + + /* TX/RX NORMAL interrupts */ + if (likely(intr_status & XGMAC_NIS)) { +- x->normal_irq_n++; +- + if (likely(intr_status & XGMAC_RI)) { +- x->rx_normal_irq_n++; +- x->rxq_stats[chan].rx_normal_irq_n++; ++ u64_stats_update_begin(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_normal_irq_n++; ++ u64_stats_update_end(&rx_q->rxq_stats.syncp); + ret |= handle_rx; + } + if (likely(intr_status & (XGMAC_TI | XGMAC_TBU))) { +- x->tx_normal_irq_n++; +- x->txq_stats[chan].tx_normal_irq_n++; ++ u64_stats_update_begin(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_normal_irq_n++; ++ u64_stats_update_end(&tx_q->txq_stats.syncp); + ret |= handle_tx; + } + } +diff --git a/drivers/net/ethernet/stmicro/stmmac/enh_desc.c b/drivers/net/ethernet/stmicro/stmmac/enh_desc.c +index a91d8f13a931d..937b7a0466fca 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/enh_desc.c ++++ b/drivers/net/ethernet/stmicro/stmmac/enh_desc.c +@@ -12,8 +12,7 @@ + #include "common.h" + #include "descs_com.h" + +-static int enh_desc_get_tx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int enh_desc_get_tx_status(struct stmmac_extra_stats *x, + struct dma_desc *p, void __iomem *ioaddr) + { + unsigned int tdes0 = le32_to_cpu(p->des0); +@@ -38,15 +37,13 @@ static int enh_desc_get_tx_status(struct net_device_stats *stats, + + if (unlikely(tdes0 & ETDES0_LOSS_CARRIER)) { + x->tx_losscarrier++; +- stats->tx_carrier_errors++; + } + if (unlikely(tdes0 & ETDES0_NO_CARRIER)) { + x->tx_carrier++; +- stats->tx_carrier_errors++; + } + if (unlikely((tdes0 & ETDES0_LATE_COLLISION) || + (tdes0 & ETDES0_EXCESSIVE_COLLISIONS))) +- stats->collisions += ++ x->tx_collision += + (tdes0 & ETDES0_COLLISION_COUNT_MASK) >> 3; + + if (unlikely(tdes0 & ETDES0_EXCESSIVE_DEFERRAL)) +@@ -117,8 +114,7 @@ static int enh_desc_coe_rdes0(int ipc_err, int type, int payload_err) + return ret; + } + +-static void enh_desc_get_ext_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static void enh_desc_get_ext_status(struct stmmac_extra_stats *x, + struct dma_extended_desc *p) + { + unsigned int rdes0 = le32_to_cpu(p->basic.des0); +@@ -182,8 +178,7 @@ static void enh_desc_get_ext_status(struct net_device_stats *stats, + } + } + +-static int enh_desc_get_rx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int enh_desc_get_rx_status(struct stmmac_extra_stats *x, + struct dma_desc *p) + { + unsigned int rdes0 = le32_to_cpu(p->des0); +@@ -193,14 +188,14 @@ static int enh_desc_get_rx_status(struct net_device_stats *stats, + return dma_own; + + if (unlikely(!(rdes0 & RDES0_LAST_DESCRIPTOR))) { +- stats->rx_length_errors++; ++ x->rx_length++; + return discard_frame; + } + + if (unlikely(rdes0 & RDES0_ERROR_SUMMARY)) { + if (unlikely(rdes0 & RDES0_DESCRIPTOR_ERROR)) { + x->rx_desc++; +- stats->rx_length_errors++; ++ x->rx_length++; + } + if (unlikely(rdes0 & RDES0_OVERFLOW_ERROR)) + x->rx_gmac_overflow++; +@@ -209,7 +204,7 @@ static int enh_desc_get_rx_status(struct net_device_stats *stats, + pr_err("\tIPC Csum Error/Giant frame\n"); + + if (unlikely(rdes0 & RDES0_COLLISION)) +- stats->collisions++; ++ x->rx_collision++; + if (unlikely(rdes0 & RDES0_RECEIVE_WATCHDOG)) + x->rx_watchdog++; + +@@ -218,7 +213,6 @@ static int enh_desc_get_rx_status(struct net_device_stats *stats, + + if (unlikely(rdes0 & RDES0_CRC_ERROR)) { + x->rx_crc_errors++; +- stats->rx_crc_errors++; + } + ret = discard_frame; + } +diff --git a/drivers/net/ethernet/stmicro/stmmac/hwif.h b/drivers/net/ethernet/stmicro/stmmac/hwif.h +index 6ee7cf07cfd76..652af8f6e75ff 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/hwif.h ++++ b/drivers/net/ethernet/stmicro/stmmac/hwif.h +@@ -57,8 +57,7 @@ struct stmmac_desc_ops { + /* Last tx segment reports the transmit status */ + int (*get_tx_ls)(struct dma_desc *p); + /* Return the transmit status looking at the TDES1 */ +- int (*tx_status)(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++ int (*tx_status)(struct stmmac_extra_stats *x, + struct dma_desc *p, void __iomem *ioaddr); + /* Get the buffer size from the descriptor */ + int (*get_tx_len)(struct dma_desc *p); +@@ -67,11 +66,9 @@ struct stmmac_desc_ops { + /* Get the receive frame size */ + int (*get_rx_frame_len)(struct dma_desc *p, int rx_coe_type); + /* Return the reception status looking at the RDES1 */ +- int (*rx_status)(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++ int (*rx_status)(struct stmmac_extra_stats *x, + struct dma_desc *p); +- void (*rx_extended_status)(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++ void (*rx_extended_status)(struct stmmac_extra_stats *x, + struct dma_extended_desc *p); + /* Set tx timestamp enable bit */ + void (*enable_tx_timestamp) (struct dma_desc *p); +@@ -191,8 +188,7 @@ struct stmmac_dma_ops { + void (*dma_tx_mode)(struct stmmac_priv *priv, void __iomem *ioaddr, + int mode, u32 channel, int fifosz, u8 qmode); + /* To track extra statistic (if supported) */ +- void (*dma_diagnostic_fr)(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++ void (*dma_diagnostic_fr)(struct stmmac_extra_stats *x, + void __iomem *ioaddr); + void (*enable_dma_transmission) (void __iomem *ioaddr); + void (*enable_dma_irq)(struct stmmac_priv *priv, void __iomem *ioaddr, +diff --git a/drivers/net/ethernet/stmicro/stmmac/norm_desc.c b/drivers/net/ethernet/stmicro/stmmac/norm_desc.c +index 350e6670a5766..68a7cfcb1d8f3 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/norm_desc.c ++++ b/drivers/net/ethernet/stmicro/stmmac/norm_desc.c +@@ -12,8 +12,7 @@ + #include "common.h" + #include "descs_com.h" + +-static int ndesc_get_tx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int ndesc_get_tx_status(struct stmmac_extra_stats *x, + struct dma_desc *p, void __iomem *ioaddr) + { + unsigned int tdes0 = le32_to_cpu(p->des0); +@@ -31,15 +30,12 @@ static int ndesc_get_tx_status(struct net_device_stats *stats, + if (unlikely(tdes0 & TDES0_ERROR_SUMMARY)) { + if (unlikely(tdes0 & TDES0_UNDERFLOW_ERROR)) { + x->tx_underflow++; +- stats->tx_fifo_errors++; + } + if (unlikely(tdes0 & TDES0_NO_CARRIER)) { + x->tx_carrier++; +- stats->tx_carrier_errors++; + } + if (unlikely(tdes0 & TDES0_LOSS_CARRIER)) { + x->tx_losscarrier++; +- stats->tx_carrier_errors++; + } + if (unlikely((tdes0 & TDES0_EXCESSIVE_DEFERRAL) || + (tdes0 & TDES0_EXCESSIVE_COLLISIONS) || +@@ -47,7 +43,7 @@ static int ndesc_get_tx_status(struct net_device_stats *stats, + unsigned int collisions; + + collisions = (tdes0 & TDES0_COLLISION_COUNT_MASK) >> 3; +- stats->collisions += collisions; ++ x->tx_collision += collisions; + } + ret = tx_err; + } +@@ -70,8 +66,7 @@ static int ndesc_get_tx_len(struct dma_desc *p) + * and, if required, updates the multicast statistics. + * In case of success, it returns good_frame because the GMAC device + * is supposed to be able to compute the csum in HW. */ +-static int ndesc_get_rx_status(struct net_device_stats *stats, +- struct stmmac_extra_stats *x, ++static int ndesc_get_rx_status(struct stmmac_extra_stats *x, + struct dma_desc *p) + { + int ret = good_frame; +@@ -81,7 +76,7 @@ static int ndesc_get_rx_status(struct net_device_stats *stats, + return dma_own; + + if (unlikely(!(rdes0 & RDES0_LAST_DESCRIPTOR))) { +- stats->rx_length_errors++; ++ x->rx_length++; + return discard_frame; + } + +@@ -96,11 +91,9 @@ static int ndesc_get_rx_status(struct net_device_stats *stats, + x->ipc_csum_error++; + if (unlikely(rdes0 & RDES0_COLLISION)) { + x->rx_collision++; +- stats->collisions++; + } + if (unlikely(rdes0 & RDES0_CRC_ERROR)) { + x->rx_crc_errors++; +- stats->rx_crc_errors++; + } + ret = discard_frame; + } +diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac.h b/drivers/net/ethernet/stmicro/stmmac/stmmac.h +index 07ea5ab0a60ba..4ce5eaaae5135 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/stmmac.h ++++ b/drivers/net/ethernet/stmicro/stmmac/stmmac.h +@@ -77,6 +77,7 @@ struct stmmac_tx_queue { + dma_addr_t dma_tx_phy; + dma_addr_t tx_tail_addr; + u32 mss; ++ struct stmmac_txq_stats txq_stats; + }; + + struct stmmac_rx_buffer { +@@ -121,6 +122,7 @@ struct stmmac_rx_queue { + unsigned int len; + unsigned int error; + } state; ++ struct stmmac_rxq_stats rxq_stats; + }; + + struct stmmac_channel { +diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c +index 2ae73ab842d45..b7ac7abecdd35 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c ++++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c +@@ -89,14 +89,6 @@ static const struct stmmac_stats stmmac_gstrings_stats[] = { + /* Tx/Rx IRQ Events */ + STMMAC_STAT(rx_early_irq), + STMMAC_STAT(threshold), +- STMMAC_STAT(tx_pkt_n), +- STMMAC_STAT(rx_pkt_n), +- STMMAC_STAT(normal_irq_n), +- STMMAC_STAT(rx_normal_irq_n), +- STMMAC_STAT(napi_poll), +- STMMAC_STAT(tx_normal_irq_n), +- STMMAC_STAT(tx_clean), +- STMMAC_STAT(tx_set_ic_bit), + STMMAC_STAT(irq_receive_pmt_irq_n), + /* MMC info */ + STMMAC_STAT(mmc_tx_irq_n), +@@ -163,9 +155,6 @@ static const struct stmmac_stats stmmac_gstrings_stats[] = { + STMMAC_STAT(mtl_rx_fifo_ctrl_active), + STMMAC_STAT(mac_rx_frame_ctrl_fifo), + STMMAC_STAT(mac_gmii_rx_proto_engine), +- /* TSO */ +- STMMAC_STAT(tx_tso_frames), +- STMMAC_STAT(tx_tso_nfrags), + /* EST */ + STMMAC_STAT(mtl_est_cgce), + STMMAC_STAT(mtl_est_hlbs), +@@ -175,6 +164,23 @@ static const struct stmmac_stats stmmac_gstrings_stats[] = { + }; + #define STMMAC_STATS_LEN ARRAY_SIZE(stmmac_gstrings_stats) + ++/* statistics collected in queue which will be summed up for all TX or RX ++ * queues, or summed up for both TX and RX queues(napi_poll, normal_irq_n). ++ */ ++static const char stmmac_qstats_string[][ETH_GSTRING_LEN] = { ++ "rx_pkt_n", ++ "rx_normal_irq_n", ++ "tx_pkt_n", ++ "tx_normal_irq_n", ++ "tx_clean", ++ "tx_set_ic_bit", ++ "tx_tso_frames", ++ "tx_tso_nfrags", ++ "normal_irq_n", ++ "napi_poll", ++}; ++#define STMMAC_QSTATS ARRAY_SIZE(stmmac_qstats_string) ++ + /* HW MAC Management counters (if supported) */ + #define STMMAC_MMC_STAT(m) \ + { #m, sizeof_field(struct stmmac_counters, m), \ +@@ -535,23 +541,44 @@ static void stmmac_get_per_qstats(struct stmmac_priv *priv, u64 *data) + { + u32 tx_cnt = priv->plat->tx_queues_to_use; + u32 rx_cnt = priv->plat->rx_queues_to_use; ++ unsigned int start; + int q, stat; ++ u64 *pos; + char *p; + ++ pos = data; + for (q = 0; q < tx_cnt; q++) { +- p = (char *)priv + offsetof(struct stmmac_priv, +- xstats.txq_stats[q].tx_pkt_n); ++ struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[q]; ++ struct stmmac_txq_stats snapshot; ++ ++ data = pos; ++ do { ++ start = u64_stats_fetch_begin(&tx_q->txq_stats.syncp); ++ snapshot = tx_q->txq_stats; ++ } while (u64_stats_fetch_retry(&tx_q->txq_stats.syncp, start)); ++ ++ p = (char *)&snapshot + offsetof(struct stmmac_txq_stats, tx_pkt_n); + for (stat = 0; stat < STMMAC_TXQ_STATS; stat++) { +- *data++ = (*(unsigned long *)p); +- p += sizeof(unsigned long); ++ *data++ += (*(u64 *)p); ++ p += sizeof(u64); + } + } ++ ++ pos = data; + for (q = 0; q < rx_cnt; q++) { +- p = (char *)priv + offsetof(struct stmmac_priv, +- xstats.rxq_stats[q].rx_pkt_n); ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[q]; ++ struct stmmac_rxq_stats snapshot; ++ ++ data = pos; ++ do { ++ start = u64_stats_fetch_begin(&rx_q->rxq_stats.syncp); ++ snapshot = rx_q->rxq_stats; ++ } while (u64_stats_fetch_retry(&rx_q->rxq_stats.syncp, start)); ++ ++ p = (char *)&snapshot + offsetof(struct stmmac_rxq_stats, rx_pkt_n); + for (stat = 0; stat < STMMAC_RXQ_STATS; stat++) { +- *data++ = (*(unsigned long *)p); +- p += sizeof(unsigned long); ++ *data++ += (*(u64 *)p); ++ p += sizeof(u64); + } + } + } +@@ -562,8 +589,10 @@ static void stmmac_get_ethtool_stats(struct net_device *dev, + struct stmmac_priv *priv = netdev_priv(dev); + u32 rx_queues_count = priv->plat->rx_queues_to_use; + u32 tx_queues_count = priv->plat->tx_queues_to_use; ++ u64 napi_poll = 0, normal_irq_n = 0; ++ int i, j = 0, pos, ret; + unsigned long count; +- int i, j = 0, ret; ++ unsigned int start; + + if (priv->dma_cap.asp) { + for (i = 0; i < STMMAC_SAFETY_FEAT_SIZE; i++) { +@@ -574,8 +603,7 @@ static void stmmac_get_ethtool_stats(struct net_device *dev, + } + + /* Update the DMA HW counters for dwmac10/100 */ +- ret = stmmac_dma_diagnostic_fr(priv, &dev->stats, (void *) &priv->xstats, +- priv->ioaddr); ++ ret = stmmac_dma_diagnostic_fr(priv, &priv->xstats, priv->ioaddr); + if (ret) { + /* If supported, for new GMAC chips expose the MMC counters */ + if (priv->dma_cap.rmon) { +@@ -606,6 +634,48 @@ static void stmmac_get_ethtool_stats(struct net_device *dev, + data[j++] = (stmmac_gstrings_stats[i].sizeof_stat == + sizeof(u64)) ? (*(u64 *)p) : (*(u32 *)p); + } ++ ++ pos = j; ++ for (i = 0; i < rx_queues_count; i++) { ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[i]; ++ struct stmmac_rxq_stats snapshot; ++ ++ j = pos; ++ do { ++ start = u64_stats_fetch_begin(&rx_q->rxq_stats.syncp); ++ snapshot = rx_q->rxq_stats; ++ } while (u64_stats_fetch_retry(&rx_q->rxq_stats.syncp, start)); ++ ++ data[j++] += snapshot.rx_pkt_n; ++ data[j++] += snapshot.rx_normal_irq_n; ++ normal_irq_n += snapshot.rx_normal_irq_n; ++ napi_poll += snapshot.napi_poll; ++ } ++ ++ pos = j; ++ for (i = 0; i < tx_queues_count; i++) { ++ struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[i]; ++ struct stmmac_txq_stats snapshot; ++ ++ j = pos; ++ do { ++ start = u64_stats_fetch_begin(&tx_q->txq_stats.syncp); ++ snapshot = tx_q->txq_stats; ++ } while (u64_stats_fetch_retry(&tx_q->txq_stats.syncp, start)); ++ ++ data[j++] += snapshot.tx_pkt_n; ++ data[j++] += snapshot.tx_normal_irq_n; ++ normal_irq_n += snapshot.tx_normal_irq_n; ++ data[j++] += snapshot.tx_clean; ++ data[j++] += snapshot.tx_set_ic_bit; ++ data[j++] += snapshot.tx_tso_frames; ++ data[j++] += snapshot.tx_tso_nfrags; ++ napi_poll += snapshot.napi_poll; ++ } ++ normal_irq_n += priv->xstats.rx_early_irq; ++ data[j++] = normal_irq_n; ++ data[j++] = napi_poll; ++ + stmmac_get_per_qstats(priv, &data[j]); + } + +@@ -618,7 +688,7 @@ static int stmmac_get_sset_count(struct net_device *netdev, int sset) + + switch (sset) { + case ETH_SS_STATS: +- len = STMMAC_STATS_LEN + ++ len = STMMAC_STATS_LEN + STMMAC_QSTATS + + STMMAC_TXQ_STATS * tx_cnt + + STMMAC_RXQ_STATS * rx_cnt; + +@@ -691,8 +761,11 @@ static void stmmac_get_strings(struct net_device *dev, u32 stringset, u8 *data) + p += ETH_GSTRING_LEN; + } + for (i = 0; i < STMMAC_STATS_LEN; i++) { +- memcpy(p, stmmac_gstrings_stats[i].stat_string, +- ETH_GSTRING_LEN); ++ memcpy(p, stmmac_gstrings_stats[i].stat_string, ETH_GSTRING_LEN); ++ p += ETH_GSTRING_LEN; ++ } ++ for (i = 0; i < STMMAC_QSTATS; i++) { ++ memcpy(p, stmmac_qstats_string[i], ETH_GSTRING_LEN); + p += ETH_GSTRING_LEN; + } + stmmac_get_qstats_string(priv, p); +diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +index 6931973028aef..def490a1e2120 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c ++++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +@@ -2432,6 +2432,8 @@ static bool stmmac_xdp_xmit_zc(struct stmmac_priv *priv, u32 queue, u32 budget) + struct dma_desc *tx_desc = NULL; + struct xdp_desc xdp_desc; + bool work_done = true; ++ u32 tx_set_ic_bit = 0; ++ unsigned long flags; + + /* Avoids TX time-out as we are sharing with slow path */ + txq_trans_cond_update(nq); +@@ -2492,7 +2494,7 @@ static bool stmmac_xdp_xmit_zc(struct stmmac_priv *priv, u32 queue, u32 budget) + if (set_ic) { + tx_q->tx_count_frames = 0; + stmmac_set_tx_ic(priv, tx_desc); +- priv->xstats.tx_set_ic_bit++; ++ tx_set_ic_bit++; + } + + stmmac_prepare_tx_desc(priv, tx_desc, 1, xdp_desc.len, +@@ -2504,6 +2506,9 @@ static bool stmmac_xdp_xmit_zc(struct stmmac_priv *priv, u32 queue, u32 budget) + tx_q->cur_tx = STMMAC_GET_ENTRY(tx_q->cur_tx, priv->dma_conf.dma_tx_size); + entry = tx_q->cur_tx; + } ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_set_ic_bit += tx_set_ic_bit; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); + + if (tx_desc) { + stmmac_flush_tx_descriptors(priv, queue); +@@ -2545,11 +2550,11 @@ static int stmmac_tx_clean(struct stmmac_priv *priv, int budget, u32 queue) + struct stmmac_tx_queue *tx_q = &priv->dma_conf.tx_queue[queue]; + unsigned int bytes_compl = 0, pkts_compl = 0; + unsigned int entry, xmits = 0, count = 0; ++ u32 tx_packets = 0, tx_errors = 0; ++ unsigned long flags; + + __netif_tx_lock_bh(netdev_get_tx_queue(priv->dev, queue)); + +- priv->xstats.tx_clean++; +- + tx_q->xsk_frames_done = 0; + + entry = tx_q->dirty_tx; +@@ -2580,8 +2585,7 @@ static int stmmac_tx_clean(struct stmmac_priv *priv, int budget, u32 queue) + else + p = tx_q->dma_tx + entry; + +- status = stmmac_tx_status(priv, &priv->dev->stats, +- &priv->xstats, p, priv->ioaddr); ++ status = stmmac_tx_status(priv, &priv->xstats, p, priv->ioaddr); + /* Check if the descriptor is owned by the DMA */ + if (unlikely(status & tx_dma_own)) + break; +@@ -2597,13 +2601,11 @@ static int stmmac_tx_clean(struct stmmac_priv *priv, int budget, u32 queue) + if (likely(!(status & tx_not_ls))) { + /* ... verify the status error condition */ + if (unlikely(status & tx_err)) { +- priv->dev->stats.tx_errors++; ++ tx_errors++; + if (unlikely(status & tx_err_bump_tc)) + stmmac_bump_dma_threshold(priv, queue); + } else { +- priv->dev->stats.tx_packets++; +- priv->xstats.tx_pkt_n++; +- priv->xstats.txq_stats[queue].tx_pkt_n++; ++ tx_packets++; + } + if (skb) + stmmac_get_tx_hwtstamp(priv, p, skb); +@@ -2705,6 +2707,14 @@ static int stmmac_tx_clean(struct stmmac_priv *priv, int budget, u32 queue) + if (tx_q->dirty_tx != tx_q->cur_tx) + stmmac_tx_timer_arm(priv, queue); + ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_packets += tx_packets; ++ tx_q->txq_stats.tx_pkt_n += tx_packets; ++ tx_q->txq_stats.tx_clean++; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); ++ ++ priv->xstats.tx_errors += tx_errors; ++ + __netif_tx_unlock_bh(netdev_get_tx_queue(priv->dev, queue)); + + /* Combine decisions from TX clean and XSK TX */ +@@ -2732,7 +2742,7 @@ static void stmmac_tx_err(struct stmmac_priv *priv, u32 chan) + tx_q->dma_tx_phy, chan); + stmmac_start_tx_dma(priv, chan); + +- priv->dev->stats.tx_errors++; ++ priv->xstats.tx_errors++; + netif_tx_wake_queue(netdev_get_tx_queue(priv->dev, chan)); + } + +@@ -4112,6 +4122,7 @@ static netdev_tx_t stmmac_tso_xmit(struct sk_buff *skb, struct net_device *dev) + struct stmmac_tx_queue *tx_q; + bool has_vlan, set_ic; + u8 proto_hdr_len, hdr; ++ unsigned long flags; + u32 pay_len, mss; + dma_addr_t des; + int i; +@@ -4260,7 +4271,6 @@ static netdev_tx_t stmmac_tso_xmit(struct sk_buff *skb, struct net_device *dev) + + tx_q->tx_count_frames = 0; + stmmac_set_tx_ic(priv, desc); +- priv->xstats.tx_set_ic_bit++; + } + + /* We've used all descriptors we need for this skb, however, +@@ -4276,9 +4286,13 @@ static netdev_tx_t stmmac_tso_xmit(struct sk_buff *skb, struct net_device *dev) + netif_tx_stop_queue(netdev_get_tx_queue(priv->dev, queue)); + } + +- dev->stats.tx_bytes += skb->len; +- priv->xstats.tx_tso_frames++; +- priv->xstats.tx_tso_nfrags += nfrags; ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_bytes += skb->len; ++ tx_q->txq_stats.tx_tso_frames++; ++ tx_q->txq_stats.tx_tso_nfrags += nfrags; ++ if (set_ic) ++ tx_q->txq_stats.tx_set_ic_bit++; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); + + if (priv->sarc_type) + stmmac_set_desc_sarc(priv, first, priv->sarc_type); +@@ -4328,7 +4342,7 @@ static netdev_tx_t stmmac_tso_xmit(struct sk_buff *skb, struct net_device *dev) + dma_map_err: + dev_err(priv->device, "Tx dma map failed\n"); + dev_kfree_skb(skb); +- priv->dev->stats.tx_dropped++; ++ priv->xstats.tx_dropped++; + return NETDEV_TX_OK; + } + +@@ -4354,6 +4368,7 @@ static netdev_tx_t stmmac_xmit(struct sk_buff *skb, struct net_device *dev) + struct stmmac_tx_queue *tx_q; + bool has_vlan, set_ic; + int entry, first_tx; ++ unsigned long flags; + dma_addr_t des; + + tx_q = &priv->dma_conf.tx_queue[queue]; +@@ -4482,7 +4497,6 @@ static netdev_tx_t stmmac_xmit(struct sk_buff *skb, struct net_device *dev) + + tx_q->tx_count_frames = 0; + stmmac_set_tx_ic(priv, desc); +- priv->xstats.tx_set_ic_bit++; + } + + /* We've used all descriptors we need for this skb, however, +@@ -4509,7 +4523,11 @@ static netdev_tx_t stmmac_xmit(struct sk_buff *skb, struct net_device *dev) + netif_tx_stop_queue(netdev_get_tx_queue(priv->dev, queue)); + } + +- dev->stats.tx_bytes += skb->len; ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_bytes += skb->len; ++ if (set_ic) ++ tx_q->txq_stats.tx_set_ic_bit++; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); + + if (priv->sarc_type) + stmmac_set_desc_sarc(priv, first, priv->sarc_type); +@@ -4571,7 +4589,7 @@ static netdev_tx_t stmmac_xmit(struct sk_buff *skb, struct net_device *dev) + dma_map_err: + netdev_err(priv->dev, "Tx DMA map failed\n"); + dev_kfree_skb(skb); +- priv->dev->stats.tx_dropped++; ++ priv->xstats.tx_dropped++; + return NETDEV_TX_OK; + } + +@@ -4772,9 +4790,12 @@ static int stmmac_xdp_xmit_xdpf(struct stmmac_priv *priv, int queue, + set_ic = false; + + if (set_ic) { ++ unsigned long flags; + tx_q->tx_count_frames = 0; + stmmac_set_tx_ic(priv, tx_desc); +- priv->xstats.tx_set_ic_bit++; ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.tx_set_ic_bit++; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); + } + + stmmac_enable_dma_transmission(priv, priv->ioaddr); +@@ -4919,16 +4940,18 @@ static void stmmac_dispatch_skb_zc(struct stmmac_priv *priv, u32 queue, + struct dma_desc *p, struct dma_desc *np, + struct xdp_buff *xdp) + { ++ struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue]; + struct stmmac_channel *ch = &priv->channel[queue]; + unsigned int len = xdp->data_end - xdp->data; + enum pkt_hash_types hash_type; + int coe = priv->hw->rx_csum; ++ unsigned long flags; + struct sk_buff *skb; + u32 hash; + + skb = stmmac_construct_skb_zc(ch, xdp); + if (!skb) { +- priv->dev->stats.rx_dropped++; ++ priv->xstats.rx_dropped++; + return; + } + +@@ -4947,8 +4970,10 @@ static void stmmac_dispatch_skb_zc(struct stmmac_priv *priv, u32 queue, + skb_record_rx_queue(skb, queue); + napi_gro_receive(&ch->rxtx_napi, skb); + +- priv->dev->stats.rx_packets++; +- priv->dev->stats.rx_bytes += len; ++ flags = u64_stats_update_begin_irqsave(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_pkt_n++; ++ rx_q->rxq_stats.rx_bytes += len; ++ u64_stats_update_end_irqrestore(&rx_q->rxq_stats.syncp, flags); + } + + static bool stmmac_rx_refill_zc(struct stmmac_priv *priv, u32 queue, u32 budget) +@@ -5025,9 +5050,11 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + unsigned int count = 0, error = 0, len = 0; + int dirty = stmmac_rx_dirty(priv, queue); + unsigned int next_entry = rx_q->cur_rx; ++ u32 rx_errors = 0, rx_dropped = 0; + unsigned int desc_size; + struct bpf_prog *prog; + bool failure = false; ++ unsigned long flags; + int xdp_status = 0; + int status = 0; + +@@ -5083,8 +5110,7 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + p = rx_q->dma_rx + entry; + + /* read the status of the incoming frame */ +- status = stmmac_rx_status(priv, &priv->dev->stats, +- &priv->xstats, p); ++ status = stmmac_rx_status(priv, &priv->xstats, p); + /* check if managed by the DMA otherwise go ahead */ + if (unlikely(status & dma_own)) + break; +@@ -5106,8 +5132,7 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + break; + + if (priv->extend_desc) +- stmmac_rx_extended_status(priv, &priv->dev->stats, +- &priv->xstats, ++ stmmac_rx_extended_status(priv, &priv->xstats, + rx_q->dma_erx + entry); + if (unlikely(status == discard_frame)) { + xsk_buff_free(buf->xdp); +@@ -5115,7 +5140,7 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + dirty++; + error = 1; + if (!priv->hwts_rx_en) +- priv->dev->stats.rx_errors++; ++ rx_errors++; + } + + if (unlikely(error && (status & rx_not_ls))) +@@ -5163,7 +5188,7 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + break; + case STMMAC_XDP_CONSUMED: + xsk_buff_free(buf->xdp); +- priv->dev->stats.rx_dropped++; ++ rx_dropped++; + break; + case STMMAC_XDP_TX: + case STMMAC_XDP_REDIRECT: +@@ -5184,8 +5209,12 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + + stmmac_finalize_xdp_rx(priv, xdp_status); + +- priv->xstats.rx_pkt_n += count; +- priv->xstats.rxq_stats[queue].rx_pkt_n += count; ++ flags = u64_stats_update_begin_irqsave(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_pkt_n += count; ++ u64_stats_update_end_irqrestore(&rx_q->rxq_stats.syncp, flags); ++ ++ priv->xstats.rx_dropped += rx_dropped; ++ priv->xstats.rx_errors += rx_errors; + + if (xsk_uses_need_wakeup(rx_q->xsk_pool)) { + if (failure || stmmac_rx_dirty(priv, queue) > 0) +@@ -5209,6 +5238,7 @@ static int stmmac_rx_zc(struct stmmac_priv *priv, int limit, u32 queue) + */ + static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + { ++ u32 rx_errors = 0, rx_dropped = 0, rx_bytes = 0, rx_packets = 0; + struct stmmac_rx_queue *rx_q = &priv->dma_conf.rx_queue[queue]; + struct stmmac_channel *ch = &priv->channel[queue]; + unsigned int count = 0, error = 0, len = 0; +@@ -5218,6 +5248,7 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + unsigned int desc_size; + struct sk_buff *skb = NULL; + struct stmmac_xdp_buff ctx; ++ unsigned long flags; + int xdp_status = 0; + int buf_sz; + +@@ -5273,8 +5304,7 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + p = rx_q->dma_rx + entry; + + /* read the status of the incoming frame */ +- status = stmmac_rx_status(priv, &priv->dev->stats, +- &priv->xstats, p); ++ status = stmmac_rx_status(priv, &priv->xstats, p); + /* check if managed by the DMA otherwise go ahead */ + if (unlikely(status & dma_own)) + break; +@@ -5291,14 +5321,13 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + prefetch(np); + + if (priv->extend_desc) +- stmmac_rx_extended_status(priv, &priv->dev->stats, +- &priv->xstats, rx_q->dma_erx + entry); ++ stmmac_rx_extended_status(priv, &priv->xstats, rx_q->dma_erx + entry); + if (unlikely(status == discard_frame)) { + page_pool_recycle_direct(rx_q->page_pool, buf->page); + buf->page = NULL; + error = 1; + if (!priv->hwts_rx_en) +- priv->dev->stats.rx_errors++; ++ rx_errors++; + } + + if (unlikely(error && (status & rx_not_ls))) +@@ -5366,7 +5395,7 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + virt_to_head_page(ctx.xdp.data), + sync_len, true); + buf->page = NULL; +- priv->dev->stats.rx_dropped++; ++ rx_dropped++; + + /* Clear skb as it was set as + * status by XDP program. +@@ -5395,7 +5424,7 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + + skb = napi_alloc_skb(&ch->rx_napi, buf1_len); + if (!skb) { +- priv->dev->stats.rx_dropped++; ++ rx_dropped++; + count++; + goto drain_data; + } +@@ -5455,8 +5484,8 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + napi_gro_receive(&ch->rx_napi, skb); + skb = NULL; + +- priv->dev->stats.rx_packets++; +- priv->dev->stats.rx_bytes += len; ++ rx_packets++; ++ rx_bytes += len; + count++; + } + +@@ -5471,8 +5500,14 @@ static int stmmac_rx(struct stmmac_priv *priv, int limit, u32 queue) + + stmmac_rx_refill(priv, queue); + +- priv->xstats.rx_pkt_n += count; +- priv->xstats.rxq_stats[queue].rx_pkt_n += count; ++ flags = u64_stats_update_begin_irqsave(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.rx_packets += rx_packets; ++ rx_q->rxq_stats.rx_bytes += rx_bytes; ++ rx_q->rxq_stats.rx_pkt_n += count; ++ u64_stats_update_end_irqrestore(&rx_q->rxq_stats.syncp, flags); ++ ++ priv->xstats.rx_dropped += rx_dropped; ++ priv->xstats.rx_errors += rx_errors; + + return count; + } +@@ -5482,10 +5517,15 @@ static int stmmac_napi_poll_rx(struct napi_struct *napi, int budget) + struct stmmac_channel *ch = + container_of(napi, struct stmmac_channel, rx_napi); + struct stmmac_priv *priv = ch->priv_data; ++ struct stmmac_rx_queue *rx_q; + u32 chan = ch->index; ++ unsigned long flags; + int work_done; + +- priv->xstats.napi_poll++; ++ rx_q = &priv->dma_conf.rx_queue[chan]; ++ flags = u64_stats_update_begin_irqsave(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.napi_poll++; ++ u64_stats_update_end_irqrestore(&rx_q->rxq_stats.syncp, flags); + + work_done = stmmac_rx(priv, budget, chan); + if (work_done < budget && napi_complete_done(napi, work_done)) { +@@ -5504,10 +5544,15 @@ static int stmmac_napi_poll_tx(struct napi_struct *napi, int budget) + struct stmmac_channel *ch = + container_of(napi, struct stmmac_channel, tx_napi); + struct stmmac_priv *priv = ch->priv_data; ++ struct stmmac_tx_queue *tx_q; + u32 chan = ch->index; ++ unsigned long flags; + int work_done; + +- priv->xstats.napi_poll++; ++ tx_q = &priv->dma_conf.tx_queue[chan]; ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.napi_poll++; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); + + work_done = stmmac_tx_clean(priv, budget, chan); + work_done = min(work_done, budget); +@@ -5529,9 +5574,20 @@ static int stmmac_napi_poll_rxtx(struct napi_struct *napi, int budget) + container_of(napi, struct stmmac_channel, rxtx_napi); + struct stmmac_priv *priv = ch->priv_data; + int rx_done, tx_done, rxtx_done; ++ struct stmmac_rx_queue *rx_q; ++ struct stmmac_tx_queue *tx_q; + u32 chan = ch->index; ++ unsigned long flags; ++ ++ rx_q = &priv->dma_conf.rx_queue[chan]; ++ flags = u64_stats_update_begin_irqsave(&rx_q->rxq_stats.syncp); ++ rx_q->rxq_stats.napi_poll++; ++ u64_stats_update_end_irqrestore(&rx_q->rxq_stats.syncp, flags); + +- priv->xstats.napi_poll++; ++ tx_q = &priv->dma_conf.tx_queue[chan]; ++ flags = u64_stats_update_begin_irqsave(&tx_q->txq_stats.syncp); ++ tx_q->txq_stats.napi_poll++; ++ u64_stats_update_end_irqrestore(&tx_q->txq_stats.syncp, flags); + + tx_done = stmmac_tx_clean(priv, budget, chan); + tx_done = min(tx_done, budget); +@@ -6790,6 +6846,56 @@ int stmmac_xsk_wakeup(struct net_device *dev, u32 queue, u32 flags) + return 0; + } + ++static void stmmac_get_stats64(struct net_device *dev, struct rtnl_link_stats64 *stats) ++{ ++ struct stmmac_priv *priv = netdev_priv(dev); ++ u32 tx_cnt = priv->plat->tx_queues_to_use; ++ u32 rx_cnt = priv->plat->rx_queues_to_use; ++ unsigned int start; ++ int q; ++ ++ for (q = 0; q < tx_cnt; q++) { ++ struct stmmac_txq_stats *txq_stats = &priv->dma_conf.tx_queue[q].txq_stats; ++ u64 tx_packets; ++ u64 tx_bytes; ++ ++ do { ++ start = u64_stats_fetch_begin(&txq_stats->syncp); ++ tx_packets = txq_stats->tx_packets; ++ tx_bytes = txq_stats->tx_bytes; ++ } while (u64_stats_fetch_retry(&txq_stats->syncp, start)); ++ ++ stats->tx_packets += tx_packets; ++ stats->tx_bytes += tx_bytes; ++ } ++ ++ for (q = 0; q < rx_cnt; q++) { ++ struct stmmac_rxq_stats *rxq_stats = &priv->dma_conf.rx_queue[q].rxq_stats; ++ u64 rx_packets; ++ u64 rx_bytes; ++ ++ do { ++ start = u64_stats_fetch_begin(&rxq_stats->syncp); ++ rx_packets = rxq_stats->rx_packets; ++ rx_bytes = rxq_stats->rx_bytes; ++ } while (u64_stats_fetch_retry(&rxq_stats->syncp, start)); ++ ++ stats->rx_packets += rx_packets; ++ stats->rx_bytes += rx_bytes; ++ } ++ ++ stats->rx_dropped = priv->xstats.rx_dropped; ++ stats->rx_errors = priv->xstats.rx_errors; ++ stats->tx_dropped = priv->xstats.tx_dropped; ++ stats->tx_errors = priv->xstats.tx_errors; ++ stats->tx_carrier_errors = priv->xstats.tx_losscarrier + priv->xstats.tx_carrier; ++ stats->collisions = priv->xstats.tx_collision + priv->xstats.rx_collision; ++ stats->rx_length_errors = priv->xstats.rx_length; ++ stats->rx_crc_errors = priv->xstats.rx_crc_errors; ++ stats->rx_over_errors = priv->xstats.rx_overflow_cntr; ++ stats->rx_missed_errors = priv->xstats.rx_missed_cntr; ++} ++ + static const struct net_device_ops stmmac_netdev_ops = { + .ndo_open = stmmac_open, + .ndo_start_xmit = stmmac_xmit, +@@ -6800,6 +6906,7 @@ static const struct net_device_ops stmmac_netdev_ops = { + .ndo_set_rx_mode = stmmac_set_rx_mode, + .ndo_tx_timeout = stmmac_tx_timeout, + .ndo_eth_ioctl = stmmac_ioctl, ++ .ndo_get_stats64 = stmmac_get_stats64, + .ndo_setup_tc = stmmac_setup_tc, + .ndo_select_queue = stmmac_select_queue, + #ifdef CONFIG_NET_POLL_CONTROLLER +@@ -7162,6 +7269,11 @@ int stmmac_dvr_probe(struct device *device, + priv->device = device; + priv->dev = ndev; + ++ for (i = 0; i < MTL_MAX_RX_QUEUES; i++) ++ u64_stats_init(&priv->dma_conf.rx_queue[i].rxq_stats.syncp); ++ for (i = 0; i < MTL_MAX_TX_QUEUES; i++) ++ u64_stats_init(&priv->dma_conf.tx_queue[i].txq_stats.syncp); ++ + stmmac_set_ethtool_ops(ndev); + priv->pause = pause; + priv->plat = plat_dat; +-- +2.40.1 + diff --git a/queue-6.5/net-use-sockaddr_storage-for-getsockopt-so_peername.patch b/queue-6.5/net-use-sockaddr_storage-for-getsockopt-so_peername.patch new file mode 100644 index 00000000000..c6dc8312665 --- /dev/null +++ b/queue-6.5/net-use-sockaddr_storage-for-getsockopt-so_peername.patch @@ -0,0 +1,63 @@ +From 8678c1ca9368c023232df7a3ff1a32ef29e4f693 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 28 Jul 2023 17:48:13 -0700 +Subject: net: Use sockaddr_storage for getsockopt(SO_PEERNAME). + +From: Kuniyuki Iwashima + +[ Upstream commit 8936bf53a091ad6a34b480c22002f1cb2422ab38 ] + +Commit df8fc4e934c1 ("kbuild: Enable -fstrict-flex-arrays=3") started +applying strict rules to standard string functions. + +It does not work well with conventional socket code around each protocol- +specific sockaddr_XXX struct, which is cast from sockaddr_storage and has +a bigger size than fortified functions expect. See these commits: + + commit 06d4c8a80836 ("af_unix: Fix fortify_panic() in unix_bind_bsd().") + commit ecb4534b6a1c ("af_unix: Terminate sun_path when bind()ing pathname socket.") + commit a0ade8404c3b ("af_packet: Fix warning of fortified memcpy() in packet_getname().") + +We must cast the protocol-specific address back to sockaddr_storage +to call such functions. + +However, in the case of getsockaddr(SO_PEERNAME), the rationale is a bit +unclear as the buffer is defined by char[128] which is the same size as +sockaddr_storage. + +Let's use sockaddr_storage explicitly. + +Signed-off-by: Kuniyuki Iwashima +Reviewed-by: Eric Dumazet +Reviewed-by: Willem de Bruijn +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + net/core/sock.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +diff --git a/net/core/sock.c b/net/core/sock.c +index 29c6cb030818b..eef27812013a4 100644 +--- a/net/core/sock.c ++++ b/net/core/sock.c +@@ -1824,14 +1824,14 @@ int sk_getsockopt(struct sock *sk, int level, int optname, + + case SO_PEERNAME: + { +- char address[128]; ++ struct sockaddr_storage address; + +- lv = sock->ops->getname(sock, (struct sockaddr *)address, 2); ++ lv = sock->ops->getname(sock, (struct sockaddr *)&address, 2); + if (lv < 0) + return -ENOTCONN; + if (lv < len) + return -EINVAL; +- if (copy_to_sockptr(optval, address, len)) ++ if (copy_to_sockptr(optval, &address, len)) + return -EFAULT; + goto lenout; + } +-- +2.40.1 + diff --git a/queue-6.5/netfilter-ebtables-fix-fortify-warnings-in-size_entr.patch b/queue-6.5/netfilter-ebtables-fix-fortify-warnings-in-size_entr.patch new file mode 100644 index 00000000000..b037c753f5f --- /dev/null +++ b/queue-6.5/netfilter-ebtables-fix-fortify-warnings-in-size_entr.patch @@ -0,0 +1,84 @@ +From 733f36435ce5ad1638c2f39ae16a938c1fce993e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 9 Aug 2023 15:45:03 +0800 +Subject: netfilter: ebtables: fix fortify warnings in size_entry_mwt() +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: GONG, Ruiqi + +[ Upstream commit a7ed3465daa240bdf01a5420f64336fee879c09d ] + +When compiling with gcc 13 and CONFIG_FORTIFY_SOURCE=y, the following +warning appears: + +In function ‘fortify_memcpy_chk’, + inlined from ‘size_entry_mwt’ at net/bridge/netfilter/ebtables.c:2118:2: +./include/linux/fortify-string.h:592:25: error: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Werror=attribute-warning] + 592 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The compiler is complaining: + +memcpy(&offsets[1], &entry->watchers_offset, + sizeof(offsets) - sizeof(offsets[0])); + +where memcpy reads beyong &entry->watchers_offset to copy +{watchers,target,next}_offset altogether into offsets[]. Silence the +warning by wrapping these three up via struct_group(). + +Signed-off-by: GONG, Ruiqi +Reviewed-by: Gustavo A. R. Silva +Reviewed-by: Kees Cook +Signed-off-by: Florian Westphal +Signed-off-by: Sasha Levin +--- + include/uapi/linux/netfilter_bridge/ebtables.h | 14 ++++++++------ + net/bridge/netfilter/ebtables.c | 3 +-- + 2 files changed, 9 insertions(+), 8 deletions(-) + +diff --git a/include/uapi/linux/netfilter_bridge/ebtables.h b/include/uapi/linux/netfilter_bridge/ebtables.h +index a494cf43a7552..b0caad82b6937 100644 +--- a/include/uapi/linux/netfilter_bridge/ebtables.h ++++ b/include/uapi/linux/netfilter_bridge/ebtables.h +@@ -182,12 +182,14 @@ struct ebt_entry { + unsigned char sourcemsk[ETH_ALEN]; + unsigned char destmac[ETH_ALEN]; + unsigned char destmsk[ETH_ALEN]; +- /* sizeof ebt_entry + matches */ +- unsigned int watchers_offset; +- /* sizeof ebt_entry + matches + watchers */ +- unsigned int target_offset; +- /* sizeof ebt_entry + matches + watchers + target */ +- unsigned int next_offset; ++ __struct_group(/* no tag */, offsets, /* no attrs */, ++ /* sizeof ebt_entry + matches */ ++ unsigned int watchers_offset; ++ /* sizeof ebt_entry + matches + watchers */ ++ unsigned int target_offset; ++ /* sizeof ebt_entry + matches + watchers + target */ ++ unsigned int next_offset; ++ ); + unsigned char elems[0] __attribute__ ((aligned (__alignof__(struct ebt_replace)))); + }; + +diff --git a/net/bridge/netfilter/ebtables.c b/net/bridge/netfilter/ebtables.c +index 757ec46fc45a0..aa23479b20b2a 100644 +--- a/net/bridge/netfilter/ebtables.c ++++ b/net/bridge/netfilter/ebtables.c +@@ -2115,8 +2115,7 @@ static int size_entry_mwt(const struct ebt_entry *entry, const unsigned char *ba + return ret; + + offsets[0] = sizeof(struct ebt_entry); /* matches come first */ +- memcpy(&offsets[1], &entry->watchers_offset, +- sizeof(offsets) - sizeof(offsets[0])); ++ memcpy(&offsets[1], &entry->offsets, sizeof(entry->offsets)); + + if (state->buf_kern_start) { + buf_start = state->buf_kern_start + state->buf_kern_offset; +-- +2.40.1 + diff --git a/queue-6.5/netlink-convert-nlk-flags-to-atomic-flags.patch b/queue-6.5/netlink-convert-nlk-flags-to-atomic-flags.patch new file mode 100644 index 00000000000..d2577933392 --- /dev/null +++ b/queue-6.5/netlink-convert-nlk-flags-to-atomic-flags.patch @@ -0,0 +1,351 @@ +From 0b5fa4a10e349e3cd05d0db3c9cd18de5ec49011 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 11 Aug 2023 07:22:26 +0000 +Subject: netlink: convert nlk->flags to atomic flags + +From: Eric Dumazet + +[ Upstream commit 8fe08d70a2b61b35a0a1235c78cf321e7528351f ] + +sk_diag_put_flags(), netlink_setsockopt(), netlink_getsockopt() +and others use nlk->flags without correct locking. + +Use set_bit(), clear_bit(), test_bit(), assign_bit() to remove +data-races. + +Reported-by: syzbot +Signed-off-by: Eric Dumazet +Reviewed-by: Simon Horman +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + net/netlink/af_netlink.c | 90 ++++++++++++++-------------------------- + net/netlink/af_netlink.h | 22 ++++++---- + net/netlink/diag.c | 10 ++--- + 3 files changed, 48 insertions(+), 74 deletions(-) + +diff --git a/net/netlink/af_netlink.c b/net/netlink/af_netlink.c +index 3836318737483..20082171f24a3 100644 +--- a/net/netlink/af_netlink.c ++++ b/net/netlink/af_netlink.c +@@ -84,7 +84,7 @@ struct listeners { + + static inline int netlink_is_kernel(struct sock *sk) + { +- return nlk_sk(sk)->flags & NETLINK_F_KERNEL_SOCKET; ++ return nlk_test_bit(KERNEL_SOCKET, sk); + } + + struct netlink_table *nl_table __read_mostly; +@@ -349,9 +349,7 @@ static void netlink_deliver_tap_kernel(struct sock *dst, struct sock *src, + + static void netlink_overrun(struct sock *sk) + { +- struct netlink_sock *nlk = nlk_sk(sk); +- +- if (!(nlk->flags & NETLINK_F_RECV_NO_ENOBUFS)) { ++ if (!nlk_test_bit(RECV_NO_ENOBUFS, sk)) { + if (!test_and_set_bit(NETLINK_S_CONGESTED, + &nlk_sk(sk)->state)) { + sk->sk_err = ENOBUFS; +@@ -1402,9 +1400,7 @@ EXPORT_SYMBOL_GPL(netlink_has_listeners); + + bool netlink_strict_get_check(struct sk_buff *skb) + { +- const struct netlink_sock *nlk = nlk_sk(NETLINK_CB(skb).sk); +- +- return nlk->flags & NETLINK_F_STRICT_CHK; ++ return nlk_test_bit(STRICT_CHK, NETLINK_CB(skb).sk); + } + EXPORT_SYMBOL_GPL(netlink_strict_get_check); + +@@ -1448,7 +1444,7 @@ static void do_one_broadcast(struct sock *sk, + return; + + if (!net_eq(sock_net(sk), p->net)) { +- if (!(nlk->flags & NETLINK_F_LISTEN_ALL_NSID)) ++ if (!nlk_test_bit(LISTEN_ALL_NSID, sk)) + return; + + if (!peernet_has_id(sock_net(sk), p->net)) +@@ -1481,7 +1477,7 @@ static void do_one_broadcast(struct sock *sk, + netlink_overrun(sk); + /* Clone failed. Notify ALL listeners. */ + p->failure = 1; +- if (nlk->flags & NETLINK_F_BROADCAST_SEND_ERROR) ++ if (nlk_test_bit(BROADCAST_SEND_ERROR, sk)) + p->delivery_failure = 1; + goto out; + } +@@ -1496,7 +1492,7 @@ static void do_one_broadcast(struct sock *sk, + val = netlink_broadcast_deliver(sk, p->skb2); + if (val < 0) { + netlink_overrun(sk); +- if (nlk->flags & NETLINK_F_BROADCAST_SEND_ERROR) ++ if (nlk_test_bit(BROADCAST_SEND_ERROR, sk)) + p->delivery_failure = 1; + } else { + p->congested |= val; +@@ -1576,7 +1572,7 @@ static int do_one_set_err(struct sock *sk, struct netlink_set_err_data *p) + !test_bit(p->group - 1, nlk->groups)) + goto out; + +- if (p->code == ENOBUFS && nlk->flags & NETLINK_F_RECV_NO_ENOBUFS) { ++ if (p->code == ENOBUFS && nlk_test_bit(RECV_NO_ENOBUFS, sk)) { + ret = 1; + goto out; + } +@@ -1643,7 +1639,7 @@ static int netlink_setsockopt(struct socket *sock, int level, int optname, + struct sock *sk = sock->sk; + struct netlink_sock *nlk = nlk_sk(sk); + unsigned int val = 0; +- int err; ++ int nr = -1; + + if (level != SOL_NETLINK) + return -ENOPROTOOPT; +@@ -1654,14 +1650,12 @@ static int netlink_setsockopt(struct socket *sock, int level, int optname, + + switch (optname) { + case NETLINK_PKTINFO: +- if (val) +- nlk->flags |= NETLINK_F_RECV_PKTINFO; +- else +- nlk->flags &= ~NETLINK_F_RECV_PKTINFO; +- err = 0; ++ nr = NETLINK_F_RECV_PKTINFO; + break; + case NETLINK_ADD_MEMBERSHIP: + case NETLINK_DROP_MEMBERSHIP: { ++ int err; ++ + if (!netlink_allowed(sock, NL_CFG_F_NONROOT_RECV)) + return -EPERM; + err = netlink_realloc_groups(sk); +@@ -1681,61 +1675,38 @@ static int netlink_setsockopt(struct socket *sock, int level, int optname, + if (optname == NETLINK_DROP_MEMBERSHIP && nlk->netlink_unbind) + nlk->netlink_unbind(sock_net(sk), val); + +- err = 0; + break; + } + case NETLINK_BROADCAST_ERROR: +- if (val) +- nlk->flags |= NETLINK_F_BROADCAST_SEND_ERROR; +- else +- nlk->flags &= ~NETLINK_F_BROADCAST_SEND_ERROR; +- err = 0; ++ nr = NETLINK_F_BROADCAST_SEND_ERROR; + break; + case NETLINK_NO_ENOBUFS: ++ assign_bit(NETLINK_F_RECV_NO_ENOBUFS, &nlk->flags, val); + if (val) { +- nlk->flags |= NETLINK_F_RECV_NO_ENOBUFS; + clear_bit(NETLINK_S_CONGESTED, &nlk->state); + wake_up_interruptible(&nlk->wait); +- } else { +- nlk->flags &= ~NETLINK_F_RECV_NO_ENOBUFS; + } +- err = 0; + break; + case NETLINK_LISTEN_ALL_NSID: + if (!ns_capable(sock_net(sk)->user_ns, CAP_NET_BROADCAST)) + return -EPERM; +- +- if (val) +- nlk->flags |= NETLINK_F_LISTEN_ALL_NSID; +- else +- nlk->flags &= ~NETLINK_F_LISTEN_ALL_NSID; +- err = 0; ++ nr = NETLINK_F_LISTEN_ALL_NSID; + break; + case NETLINK_CAP_ACK: +- if (val) +- nlk->flags |= NETLINK_F_CAP_ACK; +- else +- nlk->flags &= ~NETLINK_F_CAP_ACK; +- err = 0; ++ nr = NETLINK_F_CAP_ACK; + break; + case NETLINK_EXT_ACK: +- if (val) +- nlk->flags |= NETLINK_F_EXT_ACK; +- else +- nlk->flags &= ~NETLINK_F_EXT_ACK; +- err = 0; ++ nr = NETLINK_F_EXT_ACK; + break; + case NETLINK_GET_STRICT_CHK: +- if (val) +- nlk->flags |= NETLINK_F_STRICT_CHK; +- else +- nlk->flags &= ~NETLINK_F_STRICT_CHK; +- err = 0; ++ nr = NETLINK_F_STRICT_CHK; + break; + default: +- err = -ENOPROTOOPT; ++ return -ENOPROTOOPT; + } +- return err; ++ if (nr >= 0) ++ assign_bit(nr, &nlk->flags, val); ++ return 0; + } + + static int netlink_getsockopt(struct socket *sock, int level, int optname, +@@ -1802,7 +1773,7 @@ static int netlink_getsockopt(struct socket *sock, int level, int optname, + return -EINVAL; + + len = sizeof(int); +- val = nlk->flags & flag ? 1 : 0; ++ val = test_bit(flag, &nlk->flags); + + if (put_user(len, optlen) || + copy_to_user(optval, &val, len)) +@@ -1979,9 +1950,9 @@ static int netlink_recvmsg(struct socket *sock, struct msghdr *msg, size_t len, + msg->msg_namelen = sizeof(*addr); + } + +- if (nlk->flags & NETLINK_F_RECV_PKTINFO) ++ if (nlk_test_bit(RECV_PKTINFO, sk)) + netlink_cmsg_recv_pktinfo(msg, skb); +- if (nlk->flags & NETLINK_F_LISTEN_ALL_NSID) ++ if (nlk_test_bit(LISTEN_ALL_NSID, sk)) + netlink_cmsg_listen_all_nsid(sk, msg, skb); + + memset(&scm, 0, sizeof(scm)); +@@ -2058,7 +2029,7 @@ __netlink_kernel_create(struct net *net, int unit, struct module *module, + goto out_sock_release; + + nlk = nlk_sk(sk); +- nlk->flags |= NETLINK_F_KERNEL_SOCKET; ++ set_bit(NETLINK_F_KERNEL_SOCKET, &nlk->flags); + + netlink_table_grab(); + if (!nl_table[unit].registered) { +@@ -2192,7 +2163,7 @@ static int netlink_dump_done(struct netlink_sock *nlk, struct sk_buff *skb, + nl_dump_check_consistent(cb, nlh); + memcpy(nlmsg_data(nlh), &nlk->dump_done_errno, sizeof(nlk->dump_done_errno)); + +- if (extack->_msg && nlk->flags & NETLINK_F_EXT_ACK) { ++ if (extack->_msg && test_bit(NETLINK_F_EXT_ACK, &nlk->flags)) { + nlh->nlmsg_flags |= NLM_F_ACK_TLVS; + if (!nla_put_string(skb, NLMSGERR_ATTR_MSG, extack->_msg)) + nlmsg_end(skb, nlh); +@@ -2321,8 +2292,8 @@ int __netlink_dump_start(struct sock *ssk, struct sk_buff *skb, + const struct nlmsghdr *nlh, + struct netlink_dump_control *control) + { +- struct netlink_sock *nlk, *nlk2; + struct netlink_callback *cb; ++ struct netlink_sock *nlk; + struct sock *sk; + int ret; + +@@ -2357,8 +2328,7 @@ int __netlink_dump_start(struct sock *ssk, struct sk_buff *skb, + cb->min_dump_alloc = control->min_dump_alloc; + cb->skb = skb; + +- nlk2 = nlk_sk(NETLINK_CB(skb).sk); +- cb->strict_check = !!(nlk2->flags & NETLINK_F_STRICT_CHK); ++ cb->strict_check = nlk_test_bit(STRICT_CHK, NETLINK_CB(skb).sk); + + if (control->start) { + cb->extack = control->extack; +@@ -2402,7 +2372,7 @@ netlink_ack_tlv_len(struct netlink_sock *nlk, int err, + { + size_t tlvlen; + +- if (!extack || !(nlk->flags & NETLINK_F_EXT_ACK)) ++ if (!extack || !test_bit(NETLINK_F_EXT_ACK, &nlk->flags)) + return 0; + + tlvlen = 0; +@@ -2474,7 +2444,7 @@ void netlink_ack(struct sk_buff *in_skb, struct nlmsghdr *nlh, int err, + * requests to cap the error message, and get extra error data if + * requested. + */ +- if (err && !(nlk->flags & NETLINK_F_CAP_ACK)) ++ if (err && !test_bit(NETLINK_F_CAP_ACK, &nlk->flags)) + payload += nlmsg_len(nlh); + else + flags |= NLM_F_CAPPED; +diff --git a/net/netlink/af_netlink.h b/net/netlink/af_netlink.h +index 90a3198a9b7f7..3dbd38aef50a4 100644 +--- a/net/netlink/af_netlink.h ++++ b/net/netlink/af_netlink.h +@@ -8,14 +8,16 @@ + #include + + /* flags */ +-#define NETLINK_F_KERNEL_SOCKET 0x1 +-#define NETLINK_F_RECV_PKTINFO 0x2 +-#define NETLINK_F_BROADCAST_SEND_ERROR 0x4 +-#define NETLINK_F_RECV_NO_ENOBUFS 0x8 +-#define NETLINK_F_LISTEN_ALL_NSID 0x10 +-#define NETLINK_F_CAP_ACK 0x20 +-#define NETLINK_F_EXT_ACK 0x40 +-#define NETLINK_F_STRICT_CHK 0x80 ++enum { ++ NETLINK_F_KERNEL_SOCKET, ++ NETLINK_F_RECV_PKTINFO, ++ NETLINK_F_BROADCAST_SEND_ERROR, ++ NETLINK_F_RECV_NO_ENOBUFS, ++ NETLINK_F_LISTEN_ALL_NSID, ++ NETLINK_F_CAP_ACK, ++ NETLINK_F_EXT_ACK, ++ NETLINK_F_STRICT_CHK, ++}; + + #define NLGRPSZ(x) (ALIGN(x, sizeof(unsigned long) * 8) / 8) + #define NLGRPLONGS(x) (NLGRPSZ(x)/sizeof(unsigned long)) +@@ -23,10 +25,10 @@ + struct netlink_sock { + /* struct sock has to be the first member of netlink_sock */ + struct sock sk; ++ unsigned long flags; + u32 portid; + u32 dst_portid; + u32 dst_group; +- u32 flags; + u32 subscriptions; + u32 ngroups; + unsigned long *groups; +@@ -54,6 +56,8 @@ static inline struct netlink_sock *nlk_sk(struct sock *sk) + return container_of(sk, struct netlink_sock, sk); + } + ++#define nlk_test_bit(nr, sk) test_bit(NETLINK_F_##nr, &nlk_sk(sk)->flags) ++ + struct netlink_table { + struct rhashtable hash; + struct hlist_head mc_list; +diff --git a/net/netlink/diag.c b/net/netlink/diag.c +index e4f21b1067bcc..9c4f231be2757 100644 +--- a/net/netlink/diag.c ++++ b/net/netlink/diag.c +@@ -27,15 +27,15 @@ static int sk_diag_put_flags(struct sock *sk, struct sk_buff *skb) + + if (nlk->cb_running) + flags |= NDIAG_FLAG_CB_RUNNING; +- if (nlk->flags & NETLINK_F_RECV_PKTINFO) ++ if (nlk_test_bit(RECV_PKTINFO, sk)) + flags |= NDIAG_FLAG_PKTINFO; +- if (nlk->flags & NETLINK_F_BROADCAST_SEND_ERROR) ++ if (nlk_test_bit(BROADCAST_SEND_ERROR, sk)) + flags |= NDIAG_FLAG_BROADCAST_ERROR; +- if (nlk->flags & NETLINK_F_RECV_NO_ENOBUFS) ++ if (nlk_test_bit(RECV_NO_ENOBUFS, sk)) + flags |= NDIAG_FLAG_NO_ENOBUFS; +- if (nlk->flags & NETLINK_F_LISTEN_ALL_NSID) ++ if (nlk_test_bit(LISTEN_ALL_NSID, sk)) + flags |= NDIAG_FLAG_LISTEN_ALL_NSID; +- if (nlk->flags & NETLINK_F_CAP_ACK) ++ if (nlk_test_bit(CAP_ACK, sk)) + flags |= NDIAG_FLAG_CAP_ACK; + + return nla_put_u32(skb, NETLINK_DIAG_FLAGS, flags); +-- +2.40.1 + diff --git a/queue-6.5/nvmet-tcp-pass-iov_len-instead-of-sg-length-to-bvec_.patch b/queue-6.5/nvmet-tcp-pass-iov_len-instead-of-sg-length-to-bvec_.patch new file mode 100644 index 00000000000..4ade69cba1c --- /dev/null +++ b/queue-6.5/nvmet-tcp-pass-iov_len-instead-of-sg-length-to-bvec_.patch @@ -0,0 +1,39 @@ +From f04f081f064034112bd7c8b7618ec1c5eedd97f8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 9 Aug 2023 15:56:45 +0530 +Subject: nvmet-tcp: pass iov_len instead of sg->length to bvec_set_page() + +From: Varun Prakash + +[ Upstream commit 1f0bbf28940cf5edad90ab57b62aa8197bf5e836 ] + +iov_len is the valid data length, so pass iov_len instead of sg->length to +bvec_set_page(). + +Fixes: 5bfaba275ae6 ("nvmet-tcp: don't map pages which can't come from HIGHMEM") +Signed-off-by: Rakshana Sridhar +Signed-off-by: Varun Prakash +Reviewed-by: Sagi Grimberg +Reviewed-by: Christoph Hellwig +Signed-off-by: Keith Busch +Signed-off-by: Sasha Levin +--- + drivers/nvme/target/tcp.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/nvme/target/tcp.c b/drivers/nvme/target/tcp.c +index 868aa4de2e4c4..cd92d7ddf5ed1 100644 +--- a/drivers/nvme/target/tcp.c ++++ b/drivers/nvme/target/tcp.c +@@ -348,7 +348,7 @@ static void nvmet_tcp_build_pdu_iovec(struct nvmet_tcp_cmd *cmd) + while (length) { + u32 iov_len = min_t(u32, length, sg->length - sg_offset); + +- bvec_set_page(iov, sg_page(sg), sg->length, ++ bvec_set_page(iov, sg_page(sg), iov_len, + sg->offset + sg_offset); + + length -= iov_len; +-- +2.40.1 + diff --git a/queue-6.5/panic-reenable-preemption-in-warn-slowpath.patch b/queue-6.5/panic-reenable-preemption-in-warn-slowpath.patch new file mode 100644 index 00000000000..f9dc05648dd --- /dev/null +++ b/queue-6.5/panic-reenable-preemption-in-warn-slowpath.patch @@ -0,0 +1,59 @@ +From 35d7124bab0d893fe5a0e8b376a6295210db397c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 15 Sep 2023 09:55:39 +0200 +Subject: panic: Reenable preemption in WARN slowpath + +From: Lukas Wunner + +[ Upstream commit cccd32816506cbac3a4c65d9dff51b3125ef1a03 ] + +Commit: + + 5a5d7e9badd2 ("cpuidle: lib/bug: Disable rcu_is_watching() during WARN/BUG") + +amended warn_slowpath_fmt() to disable preemption until the WARN splat +has been emitted. + +However the commit neglected to reenable preemption in the !fmt codepath, +i.e. when a WARN splat is emitted without additional format string. + +One consequence is that users may see more splats than intended. E.g. a +WARN splat emitted in a work item results in at least two extra splats: + + BUG: workqueue leaked lock or atomic + (emitted by process_one_work()) + + BUG: scheduling while atomic + (emitted by worker_thread() -> schedule()) + +Ironically the point of the commit was to *avoid* extra splats. ;) + +Fix it. + +Fixes: 5a5d7e9badd2 ("cpuidle: lib/bug: Disable rcu_is_watching() during WARN/BUG") +Signed-off-by: Lukas Wunner +Signed-off-by: Ingo Molnar +Cc: Linus Torvalds +Cc: Thomas Gleixner +Cc: Paul E. McKenney +Link: https://lore.kernel.org/r/3ec48fde01e4ee6505f77908ba351bad200ae3d1.1694763684.git.lukas@wunner.de +Signed-off-by: Sasha Levin +--- + kernel/panic.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/kernel/panic.c b/kernel/panic.c +index 10effe40a3fa6..ea1c5fcb2d191 100644 +--- a/kernel/panic.c ++++ b/kernel/panic.c +@@ -697,6 +697,7 @@ void warn_slowpath_fmt(const char *file, int line, unsigned taint, + if (!fmt) { + __warn(file, line, __builtin_return_address(0), taint, + NULL, NULL); ++ warn_rcu_exit(rcu); + return; + } + +-- +2.40.1 + diff --git a/queue-6.5/pci-dwc-provide-deinit-callback-for-i.mx.patch b/queue-6.5/pci-dwc-provide-deinit-callback-for-i.mx.patch new file mode 100644 index 00000000000..cc7dd32e5f4 --- /dev/null +++ b/queue-6.5/pci-dwc-provide-deinit-callback-for-i.mx.patch @@ -0,0 +1,51 @@ +From 2ac0b1629babc6906ee0563344971d9bbf717ec4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 31 Jul 2023 12:55:01 +0100 +Subject: PCI: dwc: Provide deinit callback for i.MX + +From: Mark Brown + +[ Upstream commit fc8b24c28bec19fc0621d108b9ee81ddfdedb25a ] + +The i.MX integration for the DesignWare PCI controller has a _host_exit() +operation which undoes everything that the _host_init() operation does but +does not wire this up as the host_deinit callback for the core, or call it +in any path other than suspend. This means that if we ever unwind the +initial probe of the device, for example because it fails, the regulator +core complains that the regulators for the device were left enabled: + +imx6q-pcie 33800000.pcie: iATU: unroll T, 4 ob, 4 ib, align 64K, limit 16G +imx6q-pcie 33800000.pcie: Phy link never came up +imx6q-pcie 33800000.pcie: Phy link never came up +imx6q-pcie: probe of 33800000.pcie failed with error -110 +------------[ cut here ]------------ +WARNING: CPU: 2 PID: 46 at drivers/regulator/core.c:2396 _regulator_put+0x110/0x128 + +Wire up the callback so that the core can clean up after itself. + +Link: https://lore.kernel.org/r/20230731-pci-imx-regulator-cleanup-v2-1-fc8fa5c9893d@kernel.org +Tested-by: Fabio Estevam +Signed-off-by: Mark Brown +Signed-off-by: Lorenzo Pieralisi +Reviewed-by: Richard Zhu +Acked-by: Manivannan Sadhasivam +Signed-off-by: Sasha Levin +--- + drivers/pci/controller/dwc/pci-imx6.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/pci/controller/dwc/pci-imx6.c b/drivers/pci/controller/dwc/pci-imx6.c +index 27aaa2a6bf391..a18c20085e940 100644 +--- a/drivers/pci/controller/dwc/pci-imx6.c ++++ b/drivers/pci/controller/dwc/pci-imx6.c +@@ -1040,6 +1040,7 @@ static void imx6_pcie_host_exit(struct dw_pcie_rp *pp) + + static const struct dw_pcie_host_ops imx6_pcie_host_ops = { + .host_init = imx6_pcie_host_init, ++ .host_deinit = imx6_pcie_host_exit, + }; + + static const struct dw_pcie_ops dw_pcie_ops = { +-- +2.40.1 + diff --git a/queue-6.5/pci-fu740-set-the-number-of-msi-vectors.patch b/queue-6.5/pci-fu740-set-the-number-of-msi-vectors.patch new file mode 100644 index 00000000000..0c7c452f91f --- /dev/null +++ b/queue-6.5/pci-fu740-set-the-number-of-msi-vectors.patch @@ -0,0 +1,43 @@ +From 9b4e8bef06c9c1ca9f7c2ace5be3a84ffdb7c164 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 7 Aug 2023 05:56:21 +0000 +Subject: PCI: fu740: Set the number of MSI vectors + +From: Yong-Xuan Wang + +[ Upstream commit 551a60e1225e71fff8efd9390204c505b0870e0f ] + +The iMSI-RX module of the DW PCIe controller provides multiple sets of +MSI_CTRL_INT_i_* registers, and each set is capable of handling 32 MSI +interrupts. However, the fu740 PCIe controller driver only enabled one set +of MSI_CTRL_INT_i_* registers, as the total number of supported interrupts +was not specified. + +Set the supported number of MSI vectors to enable all the MSI_CTRL_INT_i_* +registers on the fu740 PCIe core, allowing the system to fully utilize the +available MSI interrupts. + +Link: https://lore.kernel.org/r/20230807055621.2431-1-yongxuan.wang@sifive.com +Signed-off-by: Yong-Xuan Wang +Signed-off-by: Lorenzo Pieralisi +Reviewed-by: Serge Semin +Signed-off-by: Sasha Levin +--- + drivers/pci/controller/dwc/pcie-fu740.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/pci/controller/dwc/pcie-fu740.c b/drivers/pci/controller/dwc/pcie-fu740.c +index 0c90583c078bf..1e9b44b8bba48 100644 +--- a/drivers/pci/controller/dwc/pcie-fu740.c ++++ b/drivers/pci/controller/dwc/pcie-fu740.c +@@ -299,6 +299,7 @@ static int fu740_pcie_probe(struct platform_device *pdev) + pci->dev = dev; + pci->ops = &dw_pcie_ops; + pci->pp.ops = &fu740_pcie_host_ops; ++ pci->pp.num_vectors = MAX_MSI_IRQS; + + /* SiFive specific region: mgmt */ + afp->mgmt_base = devm_platform_ioremap_resource_byname(pdev, "mgmt"); +-- +2.40.1 + diff --git a/queue-6.5/pci-vmd-disable-bridge-window-for-domain-reset.patch b/queue-6.5/pci-vmd-disable-bridge-window-for-domain-reset.patch new file mode 100644 index 00000000000..1e0175f7e99 --- /dev/null +++ b/queue-6.5/pci-vmd-disable-bridge-window-for-domain-reset.patch @@ -0,0 +1,93 @@ +From 337cbbca1309cf319efcb19aa03af7589e2b0506 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 10 Aug 2023 17:50:29 -0400 +Subject: PCI: vmd: Disable bridge window for domain reset + +From: Nirmal Patel + +[ Upstream commit f73eedc90bf73d48e8368e6b0b4ad76a7fffaef7 ] + +During domain reset process vmd_domain_reset() clears PCI +configuration space of VMD root ports. But certain platform +has observed following errors and failed to boot. + ... + DMAR: VT-d detected Invalidation Queue Error: Reason f + DMAR: VT-d detected Invalidation Time-out Error: SID ffff + DMAR: VT-d detected Invalidation Completion Error: SID ffff + DMAR: QI HEAD: UNKNOWN qw0 = 0x0, qw1 = 0x0 + DMAR: QI PRIOR: UNKNOWN qw0 = 0x0, qw1 = 0x0 + DMAR: Invalidation Time-out Error (ITE) cleared + +The root cause is that memset_io() clears prefetchable memory base/limit +registers and prefetchable base/limit 32 bits registers sequentially. +This seems to be enabling prefetchable memory if the device disabled +prefetchable memory originally. + +Here is an example (before memset_io()): + + PCI configuration space for 10000:00:00.0: + 86 80 30 20 06 00 10 00 04 00 04 06 00 00 01 00 + 00 00 00 00 00 00 00 00 00 01 01 00 00 00 00 20 + 00 00 00 00 01 00 01 00 ff ff ff ff 75 05 00 00 + ... + +So, prefetchable memory is ffffffff00000000-575000fffff, which is +disabled. When memset_io() clears prefetchable base 32 bits register, +the prefetchable memory becomes 0000000000000000-575000fffff, which is +enabled and incorrect. + +Here is the quote from section 7.5.1.3.9 of PCI Express Base 6.0 spec: + + The Prefetchable Memory Limit register must be programmed to a smaller + value than the Prefetchable Memory Base register if there is no + prefetchable memory on the secondary side of the bridge. + +This is believed to be the reason for the failure and in addition the +sequence of operation in vmd_domain_reset() is not following the PCIe +specs. + +Disable the bridge window by executing a sequence of operations +borrowed from pci_disable_bridge_window() and pci_setup_bridge_io(), +that comply with the PCI specifications. + +Link: https://lore.kernel.org/r/20230810215029.1177379-1-nirmal.patel@linux.intel.com +Signed-off-by: Nirmal Patel +Signed-off-by: Lorenzo Pieralisi +Signed-off-by: Sasha Levin +--- + drivers/pci/controller/vmd.c | 19 +++++++++++++++++-- + 1 file changed, 17 insertions(+), 2 deletions(-) + +diff --git a/drivers/pci/controller/vmd.c b/drivers/pci/controller/vmd.c +index e718a816d4814..ad56df98b8e63 100644 +--- a/drivers/pci/controller/vmd.c ++++ b/drivers/pci/controller/vmd.c +@@ -541,8 +541,23 @@ static void vmd_domain_reset(struct vmd_dev *vmd) + PCI_CLASS_BRIDGE_PCI)) + continue; + +- memset_io(base + PCI_IO_BASE, 0, +- PCI_ROM_ADDRESS1 - PCI_IO_BASE); ++ /* ++ * Temporarily disable the I/O range before updating ++ * PCI_IO_BASE. ++ */ ++ writel(0x0000ffff, base + PCI_IO_BASE_UPPER16); ++ /* Update lower 16 bits of I/O base/limit */ ++ writew(0x00f0, base + PCI_IO_BASE); ++ /* Update upper 16 bits of I/O base/limit */ ++ writel(0, base + PCI_IO_BASE_UPPER16); ++ ++ /* MMIO Base/Limit */ ++ writel(0x0000fff0, base + PCI_MEMORY_BASE); ++ ++ /* Prefetchable MMIO Base/Limit */ ++ writel(0, base + PCI_PREF_LIMIT_UPPER32); ++ writel(0x0000fff0, base + PCI_PREF_MEMORY_BASE); ++ writel(0xffffffff, base + PCI_PREF_BASE_UPPER32); + } + } + } +-- +2.40.1 + diff --git a/queue-6.5/perf-imx_ddr-speed-up-overflow-frequency-of-cycle.patch b/queue-6.5/perf-imx_ddr-speed-up-overflow-frequency-of-cycle.patch new file mode 100644 index 00000000000..30e423cd7cd --- /dev/null +++ b/queue-6.5/perf-imx_ddr-speed-up-overflow-frequency-of-cycle.patch @@ -0,0 +1,89 @@ +From 72baa53549bd042f2209d838f5b6024969b07c07 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 11 Aug 2023 09:54:37 +0800 +Subject: perf/imx_ddr: speed up overflow frequency of cycle + +From: Xu Yang + +[ Upstream commit e89ecd8368860bf05437eabd07d292c316221cfc ] + +For i.MX8MP, we cannot ensure that cycle counter overflow occurs at least +4 times as often as other events. Due to byte counters will count for any +event configured, it will overflow more often. And if byte counters +overflow that related counters would stop since they share the +COUNTER_CNTL. We can speed up cycle counter overflow frequency by setting +counter parameter (CP) field of cycle counter. In this way, we can avoid +stop counting byte counters when interrupt didn't come and the byte +counters can be fetched or updated from each cycle counter overflow +interrupt. + +Because we initialize CP filed to shorten counter0 overflow time, the cycle +counter will start couting from a fixed/base value each time. We need to +remove the base from the result too. Therefore, we could get precise result +from cycle counter. + +Signed-off-by: Xu Yang +Reviewed-by: Frank Li +Link: https://lore.kernel.org/r/20230811015438.1999307-1-xu.yang_2@nxp.com +Signed-off-by: Will Deacon +Signed-off-by: Sasha Levin +--- + drivers/perf/fsl_imx8_ddr_perf.c | 21 +++++++++++++++++++++ + 1 file changed, 21 insertions(+) + +diff --git a/drivers/perf/fsl_imx8_ddr_perf.c b/drivers/perf/fsl_imx8_ddr_perf.c +index c684aab407f86..e78b30521be25 100644 +--- a/drivers/perf/fsl_imx8_ddr_perf.c ++++ b/drivers/perf/fsl_imx8_ddr_perf.c +@@ -28,6 +28,8 @@ + #define CNTL_CLEAR_MASK 0xFFFFFFFD + #define CNTL_OVER_MASK 0xFFFFFFFE + ++#define CNTL_CP_SHIFT 16 ++#define CNTL_CP_MASK (0xFF << CNTL_CP_SHIFT) + #define CNTL_CSV_SHIFT 24 + #define CNTL_CSV_MASK (0xFFU << CNTL_CSV_SHIFT) + +@@ -35,6 +37,8 @@ + #define EVENT_CYCLES_COUNTER 0 + #define NUM_COUNTERS 4 + ++/* For removing bias if cycle counter CNTL.CP is set to 0xf0 */ ++#define CYCLES_COUNTER_MASK 0x0FFFFFFF + #define AXI_MASKING_REVERT 0xffff0000 /* AXI_MASKING(MSB 16bits) + AXI_ID(LSB 16bits) */ + + #define to_ddr_pmu(p) container_of(p, struct ddr_pmu, pmu) +@@ -428,6 +432,17 @@ static void ddr_perf_counter_enable(struct ddr_pmu *pmu, int config, + writel(0, pmu->base + reg); + val = CNTL_EN | CNTL_CLEAR; + val |= FIELD_PREP(CNTL_CSV_MASK, config); ++ ++ /* ++ * On i.MX8MP we need to bias the cycle counter to overflow more often. ++ * We do this by initializing bits [23:16] of the counter value via the ++ * COUNTER_CTRL Counter Parameter (CP) field. ++ */ ++ if (pmu->devtype_data->quirks & DDR_CAP_AXI_ID_FILTER_ENHANCED) { ++ if (counter == EVENT_CYCLES_COUNTER) ++ val |= FIELD_PREP(CNTL_CP_MASK, 0xf0); ++ } ++ + writel(val, pmu->base + reg); + } else { + /* Disable counter */ +@@ -467,6 +482,12 @@ static void ddr_perf_event_update(struct perf_event *event) + int ret; + + new_raw_count = ddr_perf_read_counter(pmu, counter); ++ /* Remove the bias applied in ddr_perf_counter_enable(). */ ++ if (pmu->devtype_data->quirks & DDR_CAP_AXI_ID_FILTER_ENHANCED) { ++ if (counter == EVENT_CYCLES_COUNTER) ++ new_raw_count &= CYCLES_COUNTER_MASK; ++ } ++ + local64_add(new_raw_count, &event->count); + + /* +-- +2.40.1 + diff --git a/queue-6.5/perf-smmuv3-enable-hisilicon-erratum-162001900-quirk.patch b/queue-6.5/perf-smmuv3-enable-hisilicon-erratum-162001900-quirk.patch new file mode 100644 index 00000000000..1bef1a587bb --- /dev/null +++ b/queue-6.5/perf-smmuv3-enable-hisilicon-erratum-162001900-quirk.patch @@ -0,0 +1,160 @@ +From 781b6d82d38d8aa676d5ddf4e27cc0587d05c220 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 14 Aug 2023 20:40:12 +0800 +Subject: perf/smmuv3: Enable HiSilicon Erratum 162001900 quirk for HIP08/09 + +From: Yicong Yang + +[ Upstream commit 0242737dc4eb9f6e9a5ea594b3f93efa0b12f28d ] + +Some HiSilicon SMMU PMCG suffers the erratum 162001900 that the PMU +disable control sometimes fail to disable the counters. This will lead +to error or inaccurate data since before we enable the counters the +counter's still counting for the event used in last perf session. + +This patch tries to fix this by hardening the global disable process. +Before disable the PMU, writing an invalid event type (0xffff) to +focibly stop the counters. Correspondingly restore each events on +pmu::pmu_enable(). + +Signed-off-by: Yicong Yang +Link: https://lore.kernel.org/r/20230814124012.58013-1-yangyicong@huawei.com +Signed-off-by: Will Deacon +Signed-off-by: Sasha Levin +--- + Documentation/arch/arm64/silicon-errata.rst | 3 ++ + drivers/acpi/arm64/iort.c | 5 ++- + drivers/perf/arm_smmuv3_pmu.c | 46 ++++++++++++++++++++- + include/linux/acpi_iort.h | 1 + + 4 files changed, 53 insertions(+), 2 deletions(-) + +diff --git a/Documentation/arch/arm64/silicon-errata.rst b/Documentation/arch/arm64/silicon-errata.rst +index bedd3a1d7b423..0ac452333eb4f 100644 +--- a/Documentation/arch/arm64/silicon-errata.rst ++++ b/Documentation/arch/arm64/silicon-errata.rst +@@ -198,6 +198,9 @@ stable kernels. + +----------------+-----------------+-----------------+-----------------------------+ + | Hisilicon | Hip08 SMMU PMCG | #162001800 | N/A | + +----------------+-----------------+-----------------+-----------------------------+ ++| Hisilicon | Hip08 SMMU PMCG | #162001900 | N/A | ++| | Hip09 SMMU PMCG | | | +++----------------+-----------------+-----------------+-----------------------------+ + +----------------+-----------------+-----------------+-----------------------------+ + | Qualcomm Tech. | Kryo/Falkor v1 | E1003 | QCOM_FALKOR_ERRATUM_1003 | + +----------------+-----------------+-----------------+-----------------------------+ +diff --git a/drivers/acpi/arm64/iort.c b/drivers/acpi/arm64/iort.c +index 56d887323ae52..6496ff5a6ba20 100644 +--- a/drivers/acpi/arm64/iort.c ++++ b/drivers/acpi/arm64/iort.c +@@ -1708,7 +1708,10 @@ static void __init arm_smmu_v3_pmcg_init_resources(struct resource *res, + static struct acpi_platform_list pmcg_plat_info[] __initdata = { + /* HiSilicon Hip08 Platform */ + {"HISI ", "HIP08 ", 0, ACPI_SIG_IORT, greater_than_or_equal, +- "Erratum #162001800", IORT_SMMU_V3_PMCG_HISI_HIP08}, ++ "Erratum #162001800, Erratum #162001900", IORT_SMMU_V3_PMCG_HISI_HIP08}, ++ /* HiSilicon Hip09 Platform */ ++ {"HISI ", "HIP09 ", 0, ACPI_SIG_IORT, greater_than_or_equal, ++ "Erratum #162001900", IORT_SMMU_V3_PMCG_HISI_HIP09}, + { } + }; + +diff --git a/drivers/perf/arm_smmuv3_pmu.c b/drivers/perf/arm_smmuv3_pmu.c +index 25a269d431e45..0e17c57ddb876 100644 +--- a/drivers/perf/arm_smmuv3_pmu.c ++++ b/drivers/perf/arm_smmuv3_pmu.c +@@ -115,6 +115,7 @@ + #define SMMU_PMCG_PA_SHIFT 12 + + #define SMMU_PMCG_EVCNTR_RDONLY BIT(0) ++#define SMMU_PMCG_HARDEN_DISABLE BIT(1) + + static int cpuhp_state_num; + +@@ -159,6 +160,20 @@ static inline void smmu_pmu_enable(struct pmu *pmu) + writel(SMMU_PMCG_CR_ENABLE, smmu_pmu->reg_base + SMMU_PMCG_CR); + } + ++static int smmu_pmu_apply_event_filter(struct smmu_pmu *smmu_pmu, ++ struct perf_event *event, int idx); ++ ++static inline void smmu_pmu_enable_quirk_hip08_09(struct pmu *pmu) ++{ ++ struct smmu_pmu *smmu_pmu = to_smmu_pmu(pmu); ++ unsigned int idx; ++ ++ for_each_set_bit(idx, smmu_pmu->used_counters, smmu_pmu->num_counters) ++ smmu_pmu_apply_event_filter(smmu_pmu, smmu_pmu->events[idx], idx); ++ ++ smmu_pmu_enable(pmu); ++} ++ + static inline void smmu_pmu_disable(struct pmu *pmu) + { + struct smmu_pmu *smmu_pmu = to_smmu_pmu(pmu); +@@ -167,6 +182,22 @@ static inline void smmu_pmu_disable(struct pmu *pmu) + writel(0, smmu_pmu->reg_base + SMMU_PMCG_IRQ_CTRL); + } + ++static inline void smmu_pmu_disable_quirk_hip08_09(struct pmu *pmu) ++{ ++ struct smmu_pmu *smmu_pmu = to_smmu_pmu(pmu); ++ unsigned int idx; ++ ++ /* ++ * The global disable of PMU sometimes fail to stop the counting. ++ * Harden this by writing an invalid event type to each used counter ++ * to forcibly stop counting. ++ */ ++ for_each_set_bit(idx, smmu_pmu->used_counters, smmu_pmu->num_counters) ++ writel(0xffff, smmu_pmu->reg_base + SMMU_PMCG_EVTYPER(idx)); ++ ++ smmu_pmu_disable(pmu); ++} ++ + static inline void smmu_pmu_counter_set_value(struct smmu_pmu *smmu_pmu, + u32 idx, u64 value) + { +@@ -765,7 +796,10 @@ static void smmu_pmu_get_acpi_options(struct smmu_pmu *smmu_pmu) + switch (model) { + case IORT_SMMU_V3_PMCG_HISI_HIP08: + /* HiSilicon Erratum 162001800 */ +- smmu_pmu->options |= SMMU_PMCG_EVCNTR_RDONLY; ++ smmu_pmu->options |= SMMU_PMCG_EVCNTR_RDONLY | SMMU_PMCG_HARDEN_DISABLE; ++ break; ++ case IORT_SMMU_V3_PMCG_HISI_HIP09: ++ smmu_pmu->options |= SMMU_PMCG_HARDEN_DISABLE; + break; + } + +@@ -890,6 +924,16 @@ static int smmu_pmu_probe(struct platform_device *pdev) + if (!dev->of_node) + smmu_pmu_get_acpi_options(smmu_pmu); + ++ /* ++ * For platforms suffer this quirk, the PMU disable sometimes fails to ++ * stop the counters. This will leads to inaccurate or error counting. ++ * Forcibly disable the counters with these quirk handler. ++ */ ++ if (smmu_pmu->options & SMMU_PMCG_HARDEN_DISABLE) { ++ smmu_pmu->pmu.pmu_enable = smmu_pmu_enable_quirk_hip08_09; ++ smmu_pmu->pmu.pmu_disable = smmu_pmu_disable_quirk_hip08_09; ++ } ++ + /* Pick one CPU to be the preferred one to use */ + smmu_pmu->on_cpu = raw_smp_processor_id(); + WARN_ON(irq_set_affinity(smmu_pmu->irq, cpumask_of(smmu_pmu->on_cpu))); +diff --git a/include/linux/acpi_iort.h b/include/linux/acpi_iort.h +index ee7cb6aaff718..1cb65592c95dd 100644 +--- a/include/linux/acpi_iort.h ++++ b/include/linux/acpi_iort.h +@@ -21,6 +21,7 @@ + */ + #define IORT_SMMU_V3_PMCG_GENERIC 0x00000000 /* Generic SMMUv3 PMCG */ + #define IORT_SMMU_V3_PMCG_HISI_HIP08 0x00000001 /* HiSilicon HIP08 PMCG */ ++#define IORT_SMMU_V3_PMCG_HISI_HIP09 0x00000002 /* HiSilicon HIP09 PMCG */ + + int iort_register_domain_token(int trans_id, phys_addr_t base, + struct fwnode_handle *fw_node); +-- +2.40.1 + diff --git a/queue-6.5/platform-chrome-cros_ec_lpc-remove-ec-panic-shutdown.patch b/queue-6.5/platform-chrome-cros_ec_lpc-remove-ec-panic-shutdown.patch new file mode 100644 index 00000000000..8a8bee8339a --- /dev/null +++ b/queue-6.5/platform-chrome-cros_ec_lpc-remove-ec-panic-shutdown.patch @@ -0,0 +1,42 @@ +From 421b4b968ee5f038f65df467765b3cd796731065 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 2 Aug 2023 17:58:48 +0000 +Subject: platform/chrome: cros_ec_lpc: Remove EC panic shutdown timeout + +From: Rob Barnes + +[ Upstream commit f2d4dced9a584612b25adb559c1350243d2bb544 ] + +Remove the 1 second timeout applied to hw_protection_shutdown after an +EC panic. On some platforms this 1 second timeout is insufficient to +allow the filesystem to fully sync. Independently the EC will force a +full system reset after a short period. So this backup timeout is +unnecessary. + +Signed-off-by: Rob Barnes +Reviewed-by: Guenter Roeck +Link: https://lore.kernel.org/r/20230802175847.1.Ie9fc53b6a1f4c6661c5376286a50e0cf51b3e961@changeid +Signed-off-by: Tzung-Bi Shih +Signed-off-by: Sasha Levin +--- + drivers/platform/chrome/cros_ec_lpc.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/drivers/platform/chrome/cros_ec_lpc.c b/drivers/platform/chrome/cros_ec_lpc.c +index 500a61b093e47..356572452898d 100644 +--- a/drivers/platform/chrome/cros_ec_lpc.c ++++ b/drivers/platform/chrome/cros_ec_lpc.c +@@ -327,8 +327,8 @@ static void cros_ec_lpc_acpi_notify(acpi_handle device, u32 value, void *data) + dev_emerg(ec_dev->dev, "CrOS EC Panic Reported. Shutdown is imminent!"); + blocking_notifier_call_chain(&ec_dev->panic_notifier, 0, ec_dev); + kobject_uevent_env(&ec_dev->dev->kobj, KOBJ_CHANGE, (char **)env); +- /* Begin orderly shutdown. Force shutdown after 1 second. */ +- hw_protection_shutdown("CrOS EC Panic", 1000); ++ /* Begin orderly shutdown. EC will force reset after a short period. */ ++ hw_protection_shutdown("CrOS EC Panic", -1); + /* Do not query for other events after a panic is reported */ + return; + } +-- +2.40.1 + diff --git a/queue-6.5/pm-hibernate-fix-the-exclusive-get-block-device-in-t.patch b/queue-6.5/pm-hibernate-fix-the-exclusive-get-block-device-in-t.patch new file mode 100644 index 00000000000..13993aa0743 --- /dev/null +++ b/queue-6.5/pm-hibernate-fix-the-exclusive-get-block-device-in-t.patch @@ -0,0 +1,87 @@ +From 2750b0f1d2bc30185cc1c6d1a6ade999dc0190e2 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 6 Sep 2023 12:18:52 +0800 +Subject: PM: hibernate: Fix the exclusive get block device in test_resume mode + +From: Chen Yu + +[ Upstream commit 148b6f4cc3920e563094540fe1a12d00d3bbccae ] + +Commit 5904de0d735b ("PM: hibernate: Do not get block device exclusively +in test_resume mode") fixes a hibernation issue under test_resume mode. +That commit is supposed to open the block device in non-exclusive mode +when in test_resume. However the code does the opposite, which is against +its description. + +In summary, the swap device is only opened exclusively by swsusp_check() +with its corresponding *close(), and must be in non test_resume mode. +This is to avoid the race condition that different processes scribble the +device at the same time. All the other cases should use non-exclusive mode. + +Fix it by really disabling exclusive mode under test_resume. + +Fixes: 5904de0d735b ("PM: hibernate: Do not get block device exclusively in test_resume mode") +Closes: https://lore.kernel.org/lkml/000000000000761f5f0603324129@google.com/ +Reported-by: Pengfei Xu +Signed-off-by: Chen Yu +Tested-by: Chenzhou Feng +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Sasha Levin +--- + kernel/power/hibernate.c | 12 ++++++------ + 1 file changed, 6 insertions(+), 6 deletions(-) + +diff --git a/kernel/power/hibernate.c b/kernel/power/hibernate.c +index 2b4a946a6ff5c..8d35b9f9aaa3f 100644 +--- a/kernel/power/hibernate.c ++++ b/kernel/power/hibernate.c +@@ -786,9 +786,9 @@ int hibernate(void) + unlock_device_hotplug(); + if (snapshot_test) { + pm_pr_dbg("Checking hibernation image\n"); +- error = swsusp_check(snapshot_test); ++ error = swsusp_check(false); + if (!error) +- error = load_image_and_restore(snapshot_test); ++ error = load_image_and_restore(false); + } + thaw_processes(); + +@@ -945,14 +945,14 @@ static int software_resume(void) + pm_pr_dbg("Looking for hibernation image.\n"); + + mutex_lock(&system_transition_mutex); +- error = swsusp_check(false); ++ error = swsusp_check(true); + if (error) + goto Unlock; + + /* The snapshot device should not be opened while we're running */ + if (!hibernate_acquire()) { + error = -EBUSY; +- swsusp_close(false); ++ swsusp_close(true); + goto Unlock; + } + +@@ -973,7 +973,7 @@ static int software_resume(void) + goto Close_Finish; + } + +- error = load_image_and_restore(false); ++ error = load_image_and_restore(true); + thaw_processes(); + Finish: + pm_notifier_call_chain(PM_POST_RESTORE); +@@ -987,7 +987,7 @@ static int software_resume(void) + pm_pr_dbg("Hibernation image not present or could not be loaded.\n"); + return error; + Close_Finish: +- swsusp_close(false); ++ swsusp_close(true); + goto Finish; + } + +-- +2.40.1 + diff --git a/queue-6.5/powerpc-pseries-fix-possible-memory-leak-in-ibmebus_.patch b/queue-6.5/powerpc-pseries-fix-possible-memory-leak-in-ibmebus_.patch new file mode 100644 index 00000000000..4a48a0bdbfc --- /dev/null +++ b/queue-6.5/powerpc-pseries-fix-possible-memory-leak-in-ibmebus_.patch @@ -0,0 +1,39 @@ +From 304692699edacc1c2a8f47908b7312a876e1cf9c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 10 Nov 2022 09:19:29 +0800 +Subject: powerpc/pseries: fix possible memory leak in ibmebus_bus_init() + +From: ruanjinjie + +[ Upstream commit afda85b963c12947e298ad85d757e333aa40fd74 ] + +If device_register() returns error in ibmebus_bus_init(), name of kobject +which is allocated in dev_set_name() called in device_add() is leaked. + +As comment of device_add() says, it should call put_device() to drop +the reference count that was set in device_initialize() when it fails, +so the name can be freed in kobject_cleanup(). + +Signed-off-by: ruanjinjie +Signed-off-by: Michael Ellerman +Link: https://msgid.link/20221110011929.3709774-1-ruanjinjie@huawei.com +Signed-off-by: Sasha Levin +--- + arch/powerpc/platforms/pseries/ibmebus.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/arch/powerpc/platforms/pseries/ibmebus.c b/arch/powerpc/platforms/pseries/ibmebus.c +index 44703f13985bf..969cb9fc960f8 100644 +--- a/arch/powerpc/platforms/pseries/ibmebus.c ++++ b/arch/powerpc/platforms/pseries/ibmebus.c +@@ -460,6 +460,7 @@ static int __init ibmebus_bus_init(void) + if (err) { + printk(KERN_WARNING "%s: device_register returned %i\n", + __func__, err); ++ put_device(&ibmebus_bus_device); + bus_unregister(&ibmebus_bus_type); + + return err; +-- +2.40.1 + diff --git a/queue-6.5/printk-consolidate-console-deferred-printing.patch b/queue-6.5/printk-consolidate-console-deferred-printing.patch new file mode 100644 index 00000000000..a5af497983d --- /dev/null +++ b/queue-6.5/printk-consolidate-console-deferred-printing.patch @@ -0,0 +1,126 @@ +From a2103cfe353b3db0dec0519b1722bfd31e177dc1 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 17 Jul 2023 21:52:05 +0206 +Subject: printk: Consolidate console deferred printing + +From: John Ogness + +[ Upstream commit 696ffaf50e1f8dbc66223ff614473f945f5fb8d8 ] + +Printing to consoles can be deferred for several reasons: + +- explicitly with printk_deferred() +- printk() in NMI context +- recursive printk() calls + +The current implementation is not consistent. For printk_deferred(), +irq work is scheduled twice. For NMI und recursive, panic CPU +suppression and caller delays are not properly enforced. + +Correct these inconsistencies by consolidating the deferred printing +code so that vprintk_deferred() is the top-level function for +deferred printing and vprintk_emit() will perform whichever irq_work +queueing is appropriate. + +Also add kerneldoc for wake_up_klogd() and defer_console_output() to +clarify their differences and appropriate usage. + +Signed-off-by: John Ogness +Reviewed-by: Sergey Senozhatsky +Reviewed-by: Petr Mladek +Signed-off-by: Petr Mladek +Link: https://lore.kernel.org/r/20230717194607.145135-6-john.ogness@linutronix.de +Signed-off-by: Sasha Levin +--- + kernel/printk/printk.c | 35 ++++++++++++++++++++++++++++------- + kernel/printk/printk_safe.c | 9 ++------- + 2 files changed, 30 insertions(+), 14 deletions(-) + +diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c +index 88770561c4350..d5e29fad84234 100644 +--- a/kernel/printk/printk.c ++++ b/kernel/printk/printk.c +@@ -2308,7 +2308,11 @@ asmlinkage int vprintk_emit(int facility, int level, + preempt_enable(); + } + +- wake_up_klogd(); ++ if (in_sched) ++ defer_console_output(); ++ else ++ wake_up_klogd(); ++ + return printed_len; + } + EXPORT_SYMBOL(vprintk_emit); +@@ -3843,11 +3847,33 @@ static void __wake_up_klogd(int val) + preempt_enable(); + } + ++/** ++ * wake_up_klogd - Wake kernel logging daemon ++ * ++ * Use this function when new records have been added to the ringbuffer ++ * and the console printing of those records has already occurred or is ++ * known to be handled by some other context. This function will only ++ * wake the logging daemon. ++ * ++ * Context: Any context. ++ */ + void wake_up_klogd(void) + { + __wake_up_klogd(PRINTK_PENDING_WAKEUP); + } + ++/** ++ * defer_console_output - Wake kernel logging daemon and trigger ++ * console printing in a deferred context ++ * ++ * Use this function when new records have been added to the ringbuffer, ++ * this context is responsible for console printing those records, but ++ * the current context is not allowed to perform the console printing. ++ * Trigger an irq_work context to perform the console printing. This ++ * function also wakes the logging daemon. ++ * ++ * Context: Any context. ++ */ + void defer_console_output(void) + { + /* +@@ -3864,12 +3890,7 @@ void printk_trigger_flush(void) + + int vprintk_deferred(const char *fmt, va_list args) + { +- int r; +- +- r = vprintk_emit(0, LOGLEVEL_SCHED, NULL, fmt, args); +- defer_console_output(); +- +- return r; ++ return vprintk_emit(0, LOGLEVEL_SCHED, NULL, fmt, args); + } + + int _printk_deferred(const char *fmt, ...) +diff --git a/kernel/printk/printk_safe.c b/kernel/printk/printk_safe.c +index ef0f9a2044da1..6d10927a07d83 100644 +--- a/kernel/printk/printk_safe.c ++++ b/kernel/printk/printk_safe.c +@@ -38,13 +38,8 @@ asmlinkage int vprintk(const char *fmt, va_list args) + * Use the main logbuf even in NMI. But avoid calling console + * drivers that might have their own locks. + */ +- if (this_cpu_read(printk_context) || in_nmi()) { +- int len; +- +- len = vprintk_store(0, LOGLEVEL_DEFAULT, NULL, fmt, args); +- defer_console_output(); +- return len; +- } ++ if (this_cpu_read(printk_context) || in_nmi()) ++ return vprintk_deferred(fmt, args); + + /* No obstacles. */ + return vprintk_default(fmt, args); +-- +2.40.1 + diff --git a/queue-6.5/printk-do-not-take-console-lock-for-console_flush_on.patch b/queue-6.5/printk-do-not-take-console-lock-for-console_flush_on.patch new file mode 100644 index 00000000000..e1b3da8213e --- /dev/null +++ b/queue-6.5/printk-do-not-take-console-lock-for-console_flush_on.patch @@ -0,0 +1,96 @@ +From db1b38358ec5d28707b80f56b35362d520760a06 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 17 Jul 2023 21:52:04 +0206 +Subject: printk: Do not take console lock for console_flush_on_panic() + +From: John Ogness + +[ Upstream commit eacb04ff3c5b8662a65f380ae450250698448cff ] + +Currently console_flush_on_panic() will attempt to acquire the +console lock when flushing the buffer on panic. If it fails to +acquire the lock, it continues anyway because this is the last +chance to get any pending records printed. + +The reason why the console lock was attempted at all was to +prevent any other CPUs from acquiring the console lock for +printing while the panic CPU was printing. But as of the +previous commit, non-panic CPUs will no longer attempt to +acquire the console lock in a panic situation. Therefore it is +no longer strictly necessary for a panic CPU to acquire the +console lock. + +Avoiding taking the console lock when flushing in panic has +the additional benefit of avoiding possible deadlocks due to +semaphore usage in NMI context (semaphores are not NMI-safe) +and avoiding possible deadlocks if another CPU accesses the +semaphore and is stopped while holding one of the semaphore's +internal spinlocks. + +Signed-off-by: John Ogness +Reviewed-by: Sergey Senozhatsky +Reviewed-by: Petr Mladek +Signed-off-by: Petr Mladek +Link: https://lore.kernel.org/r/20230717194607.145135-5-john.ogness@linutronix.de +Signed-off-by: Sasha Levin +--- + kernel/printk/printk.c | 28 +++++++++++++++++++--------- + 1 file changed, 19 insertions(+), 9 deletions(-) + +diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c +index 591c11888200d..88770561c4350 100644 +--- a/kernel/printk/printk.c ++++ b/kernel/printk/printk.c +@@ -3120,14 +3120,24 @@ void console_unblank(void) + */ + void console_flush_on_panic(enum con_flush_mode mode) + { ++ bool handover; ++ u64 next_seq; ++ + /* +- * If someone else is holding the console lock, trylock will fail +- * and may_schedule may be set. Ignore and proceed to unlock so +- * that messages are flushed out. As this can be called from any +- * context and we don't want to get preempted while flushing, +- * ensure may_schedule is cleared. ++ * Ignore the console lock and flush out the messages. Attempting a ++ * trylock would not be useful because: ++ * ++ * - if it is contended, it must be ignored anyway ++ * - console_lock() and console_trylock() block and fail ++ * respectively in panic for non-panic CPUs ++ * - semaphores are not NMI-safe ++ */ ++ ++ /* ++ * If another context is holding the console lock, ++ * @console_may_schedule might be set. Clear it so that ++ * this context does not call cond_resched() while flushing. + */ +- console_trylock(); + console_may_schedule = 0; + + if (mode == CONSOLE_REPLAY_ALL) { +@@ -3140,15 +3150,15 @@ void console_flush_on_panic(enum con_flush_mode mode) + cookie = console_srcu_read_lock(); + for_each_console_srcu(c) { + /* +- * If the above console_trylock() failed, this is an +- * unsynchronized assignment. But in that case, the ++ * This is an unsynchronized assignment, but the + * kernel is in "hope and pray" mode anyway. + */ + c->seq = seq; + } + console_srcu_read_unlock(cookie); + } +- console_unlock(); ++ ++ console_flush_all(false, &next_seq, &handover); + } + + /* +-- +2.40.1 + diff --git a/queue-6.5/printk-keep-non-panic-cpus-out-of-console-lock.patch b/queue-6.5/printk-keep-non-panic-cpus-out-of-console-lock.patch new file mode 100644 index 00000000000..4e4fabb1978 --- /dev/null +++ b/queue-6.5/printk-keep-non-panic-cpus-out-of-console-lock.patch @@ -0,0 +1,108 @@ +From f237a5fc598b7ff2d6376a32d787b89377349332 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 17 Jul 2023 21:52:03 +0206 +Subject: printk: Keep non-panic-CPUs out of console lock + +From: John Ogness + +[ Upstream commit 51a1d258e50e03a0216bf42b6af9ff34ec402ac1 ] + +When in a panic situation, non-panic CPUs should avoid holding the +console lock so as not to contend with the panic CPU. This is already +implemented with abandon_console_lock_in_panic(), which is checked +after each printed line. However, non-panic CPUs should also avoid +trying to acquire the console lock during a panic. + +Modify console_trylock() to fail and console_lock() to block() when +called from a non-panic CPU during a panic. + +Signed-off-by: John Ogness +Reviewed-by: Sergey Senozhatsky +Reviewed-by: Petr Mladek +Signed-off-by: Petr Mladek +Link: https://lore.kernel.org/r/20230717194607.145135-4-john.ogness@linutronix.de +Signed-off-by: Sasha Levin +--- + kernel/printk/printk.c | 45 ++++++++++++++++++++++++------------------ + 1 file changed, 26 insertions(+), 19 deletions(-) + +diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c +index 7d3f30eb35862..591c11888200d 100644 +--- a/kernel/printk/printk.c ++++ b/kernel/printk/printk.c +@@ -2585,6 +2585,25 @@ static int console_cpu_notify(unsigned int cpu) + return 0; + } + ++/* ++ * Return true when this CPU should unlock console_sem without pushing all ++ * messages to the console. This reduces the chance that the console is ++ * locked when the panic CPU tries to use it. ++ */ ++static bool abandon_console_lock_in_panic(void) ++{ ++ if (!panic_in_progress()) ++ return false; ++ ++ /* ++ * We can use raw_smp_processor_id() here because it is impossible for ++ * the task to be migrated to the panic_cpu, or away from it. If ++ * panic_cpu has already been set, and we're not currently executing on ++ * that CPU, then we never will be. ++ */ ++ return atomic_read(&panic_cpu) != raw_smp_processor_id(); ++} ++ + /** + * console_lock - block the console subsystem from printing + * +@@ -2597,6 +2616,10 @@ void console_lock(void) + { + might_sleep(); + ++ /* On panic, the console_lock must be left to the panic cpu. */ ++ while (abandon_console_lock_in_panic()) ++ msleep(1000); ++ + down_console_sem(); + if (console_suspended) + return; +@@ -2615,6 +2638,9 @@ EXPORT_SYMBOL(console_lock); + */ + int console_trylock(void) + { ++ /* On panic, the console_lock must be left to the panic cpu. */ ++ if (abandon_console_lock_in_panic()) ++ return 0; + if (down_trylock_console_sem()) + return 0; + if (console_suspended) { +@@ -2633,25 +2659,6 @@ int is_console_locked(void) + } + EXPORT_SYMBOL(is_console_locked); + +-/* +- * Return true when this CPU should unlock console_sem without pushing all +- * messages to the console. This reduces the chance that the console is +- * locked when the panic CPU tries to use it. +- */ +-static bool abandon_console_lock_in_panic(void) +-{ +- if (!panic_in_progress()) +- return false; +- +- /* +- * We can use raw_smp_processor_id() here because it is impossible for +- * the task to be migrated to the panic_cpu, or away from it. If +- * panic_cpu has already been set, and we're not currently executing on +- * that CPU, then we never will be. +- */ +- return atomic_read(&panic_cpu) != raw_smp_processor_id(); +-} +- + /* + * Check if the given console is currently capable and allowed to print + * records. +-- +2.40.1 + diff --git a/queue-6.5/printk-reduce-console_unblank-usage-in-unsafe-scenar.patch b/queue-6.5/printk-reduce-console_unblank-usage-in-unsafe-scenar.patch new file mode 100644 index 00000000000..f5e899b3217 --- /dev/null +++ b/queue-6.5/printk-reduce-console_unblank-usage-in-unsafe-scenar.patch @@ -0,0 +1,102 @@ +From 2c4830d767254f7e42841303c7c91dbea51f2da9 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 17 Jul 2023 21:52:02 +0206 +Subject: printk: Reduce console_unblank() usage in unsafe scenarios + +From: John Ogness + +[ Upstream commit 7b23a66db55ed0a55b020e913f0d6f6d52a1ad2c ] + +A semaphore is not NMI-safe, even when using down_trylock(). Both +down_trylock() and up() are using internal spinlocks and up() +might even call wake_up_process(). + +In the panic() code path it gets even worse because the internal +spinlocks of the semaphore may have been taken by a CPU that has +been stopped. + +To reduce the risk of deadlocks caused by the console semaphore in +the panic path, make the following changes: + +- First check if any consoles have implemented the unblank() + callback. If not, then there is no reason to take the console + semaphore anyway. (This check is also useful for the non-panic + path since the locking/unlocking of the console lock can be + quite expensive due to console printing.) + +- If the panic path is in NMI context, bail out without attempting + to take the console semaphore or calling any unblank() callbacks. + Bailing out is acceptable because console_unblank() would already + bail out if the console semaphore is contended. The alternative of + ignoring the console semaphore and calling the unblank() callbacks + anyway is a bad idea because these callbacks are also not NMI-safe. + +If consoles with unblank() callbacks exist and console_unblank() is +called from a non-NMI panic context, it will still attempt a +down_trylock(). This could still result in a deadlock if one of the +stopped CPUs is holding the semaphore internal spinlock. But this +is a risk that the kernel has been (and continues to be) willing +to take. + +Signed-off-by: John Ogness +Reviewed-by: Sergey Senozhatsky +Reviewed-by: Petr Mladek +Signed-off-by: Petr Mladek +Link: https://lore.kernel.org/r/20230717194607.145135-3-john.ogness@linutronix.de +Signed-off-by: Sasha Levin +--- + kernel/printk/printk.c | 28 ++++++++++++++++++++++++++++ + 1 file changed, 28 insertions(+) + +diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c +index 357a4d18f6387..7d3f30eb35862 100644 +--- a/kernel/printk/printk.c ++++ b/kernel/printk/printk.c +@@ -3045,9 +3045,27 @@ EXPORT_SYMBOL(console_conditional_schedule); + + void console_unblank(void) + { ++ bool found_unblank = false; + struct console *c; + int cookie; + ++ /* ++ * First check if there are any consoles implementing the unblank() ++ * callback. If not, there is no reason to continue and take the ++ * console lock, which in particular can be dangerous if ++ * @oops_in_progress is set. ++ */ ++ cookie = console_srcu_read_lock(); ++ for_each_console_srcu(c) { ++ if ((console_srcu_read_flags(c) & CON_ENABLED) && c->unblank) { ++ found_unblank = true; ++ break; ++ } ++ } ++ console_srcu_read_unlock(cookie); ++ if (!found_unblank) ++ return; ++ + /* + * Stop console printing because the unblank() callback may + * assume the console is not within its write() callback. +@@ -3056,6 +3074,16 @@ void console_unblank(void) + * In that case, attempt a trylock as best-effort. + */ + if (oops_in_progress) { ++ /* Semaphores are not NMI-safe. */ ++ if (in_nmi()) ++ return; ++ ++ /* ++ * Attempting to trylock the console lock can deadlock ++ * if another CPU was stopped while modifying the ++ * semaphore. "Hope and pray" that this is not the ++ * current situation. ++ */ + if (down_trylock_console_sem() != 0) + return; + } else +-- +2.40.1 + diff --git a/queue-6.5/printk-rename-abandon_console_lock_in_panic-to-other.patch b/queue-6.5/printk-rename-abandon_console_lock_in_panic-to-other.patch new file mode 100644 index 00000000000..4e4a8081f7a --- /dev/null +++ b/queue-6.5/printk-rename-abandon_console_lock_in_panic-to-other.patch @@ -0,0 +1,90 @@ +From e0733272398ba3fb0554624d185834193787a23f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 17 Jul 2023 21:52:07 +0206 +Subject: printk: Rename abandon_console_lock_in_panic() to + other_cpu_in_panic() + +From: John Ogness + +[ Upstream commit 132a90d1527fedba2d95085c951ccf00dbbebe41 ] + +Currently abandon_console_lock_in_panic() is only used to determine if +the current CPU should immediately release the console lock because +another CPU is in panic. However, later this function will be used by +the CPU to immediately release other resources in this situation. + +Rename the function to other_cpu_in_panic(), which is a better +description and does not assume it is related to the console lock. + +Signed-off-by: John Ogness +Reviewed-by: Sergey Senozhatsky +Reviewed-by: Petr Mladek +Signed-off-by: Petr Mladek +Link: https://lore.kernel.org/r/20230717194607.145135-8-john.ogness@linutronix.de +Signed-off-by: Sasha Levin +--- + kernel/printk/internal.h | 2 ++ + kernel/printk/printk.c | 15 ++++++++------- + 2 files changed, 10 insertions(+), 7 deletions(-) + +diff --git a/kernel/printk/internal.h b/kernel/printk/internal.h +index 2a17704136f1d..7d4979d5c3ce6 100644 +--- a/kernel/printk/internal.h ++++ b/kernel/printk/internal.h +@@ -103,3 +103,5 @@ struct printk_message { + u64 seq; + unsigned long dropped; + }; ++ ++bool other_cpu_in_panic(void); +diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c +index d5e29fad84234..08a9419046b65 100644 +--- a/kernel/printk/printk.c ++++ b/kernel/printk/printk.c +@@ -2590,11 +2590,12 @@ static int console_cpu_notify(unsigned int cpu) + } + + /* +- * Return true when this CPU should unlock console_sem without pushing all +- * messages to the console. This reduces the chance that the console is +- * locked when the panic CPU tries to use it. ++ * Return true if a panic is in progress on a remote CPU. ++ * ++ * On true, the local CPU should immediately release any printing resources ++ * that may be needed by the panic CPU. + */ +-static bool abandon_console_lock_in_panic(void) ++bool other_cpu_in_panic(void) + { + if (!panic_in_progress()) + return false; +@@ -2621,7 +2622,7 @@ void console_lock(void) + might_sleep(); + + /* On panic, the console_lock must be left to the panic cpu. */ +- while (abandon_console_lock_in_panic()) ++ while (other_cpu_in_panic()) + msleep(1000); + + down_console_sem(); +@@ -2643,7 +2644,7 @@ EXPORT_SYMBOL(console_lock); + int console_trylock(void) + { + /* On panic, the console_lock must be left to the panic cpu. */ +- if (abandon_console_lock_in_panic()) ++ if (other_cpu_in_panic()) + return 0; + if (down_trylock_console_sem()) + return 0; +@@ -2959,7 +2960,7 @@ static bool console_flush_all(bool do_cond_resched, u64 *next_seq, bool *handove + any_progress = true; + + /* Allow panic_cpu to take over the consoles safely. */ +- if (abandon_console_lock_in_panic()) ++ if (other_cpu_in_panic()) + goto abandon; + + if (do_cond_resched) +-- +2.40.1 + diff --git a/queue-6.5/rcuscale-move-rcu_scale_writer-schedule_timeout_unin.patch b/queue-6.5/rcuscale-move-rcu_scale_writer-schedule_timeout_unin.patch new file mode 100644 index 00000000000..6644c559953 --- /dev/null +++ b/queue-6.5/rcuscale-move-rcu_scale_writer-schedule_timeout_unin.patch @@ -0,0 +1,71 @@ +From 54d05d1c09eec3c64dddd55ba9c59e432e3df95f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 16 Jun 2023 15:39:26 +0800 +Subject: rcuscale: Move rcu_scale_writer() schedule_timeout_uninterruptible() + to _idle() + +From: Zqiang + +[ Upstream commit e60c122a1614b4f65b29a7bef9d83b9fd30e937a ] + +The rcuscale.holdoff module parameter can be used to delay the start +of rcu_scale_writer() kthread. However, the hung-task timeout will +trigger when the timeout specified by rcuscale.holdoff is greater than +hung_task_timeout_secs: + +runqemu kvm nographic slirp qemuparams="-smp 4 -m 2048M" +bootparams="rcuscale.shutdown=0 rcuscale.holdoff=300" + +[ 247.071753] INFO: task rcu_scale_write:59 blocked for more than 122 seconds. +[ 247.072529] Not tainted 6.4.0-rc1-00134-gb9ed6de8d4ff #7 +[ 247.073400] "echo 0 > /proc/sys/kernel/hung_task_timeout_secs" disables this message. +[ 247.074331] task:rcu_scale_write state:D stack:30144 pid:59 ppid:2 flags:0x00004000 +[ 247.075346] Call Trace: +[ 247.075660] +[ 247.075965] __schedule+0x635/0x1280 +[ 247.076448] ? __pfx___schedule+0x10/0x10 +[ 247.076967] ? schedule_timeout+0x2dc/0x4d0 +[ 247.077471] ? __pfx_lock_release+0x10/0x10 +[ 247.078018] ? enqueue_timer+0xe2/0x220 +[ 247.078522] schedule+0x84/0x120 +[ 247.078957] schedule_timeout+0x2e1/0x4d0 +[ 247.079447] ? __pfx_schedule_timeout+0x10/0x10 +[ 247.080032] ? __pfx_rcu_scale_writer+0x10/0x10 +[ 247.080591] ? __pfx_process_timeout+0x10/0x10 +[ 247.081163] ? __pfx_sched_set_fifo_low+0x10/0x10 +[ 247.081760] ? __pfx_rcu_scale_writer+0x10/0x10 +[ 247.082287] rcu_scale_writer+0x6b1/0x7f0 +[ 247.082773] ? mark_held_locks+0x29/0xa0 +[ 247.083252] ? __pfx_rcu_scale_writer+0x10/0x10 +[ 247.083865] ? __pfx_rcu_scale_writer+0x10/0x10 +[ 247.084412] kthread+0x179/0x1c0 +[ 247.084759] ? __pfx_kthread+0x10/0x10 +[ 247.085098] ret_from_fork+0x2c/0x50 +[ 247.085433] + +This commit therefore replaces schedule_timeout_uninterruptible() with +schedule_timeout_idle(). + +Signed-off-by: Zqiang +Signed-off-by: Paul E. McKenney +Signed-off-by: Sasha Levin +--- + kernel/rcu/rcuscale.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/kernel/rcu/rcuscale.c b/kernel/rcu/rcuscale.c +index d1221731c7cfd..35aab6cbba583 100644 +--- a/kernel/rcu/rcuscale.c ++++ b/kernel/rcu/rcuscale.c +@@ -424,7 +424,7 @@ rcu_scale_writer(void *arg) + sched_set_fifo_low(current); + + if (holdoff) +- schedule_timeout_uninterruptible(holdoff * HZ); ++ schedule_timeout_idle(holdoff * HZ); + + /* + * Wait until rcu_end_inkernel_boot() is called for normal GP tests +-- +2.40.1 + diff --git a/queue-6.5/revert-wifi-mac80211_hwsim-check-the-return-value-of.patch b/queue-6.5/revert-wifi-mac80211_hwsim-check-the-return-value-of.patch new file mode 100644 index 00000000000..61d47f74d92 --- /dev/null +++ b/queue-6.5/revert-wifi-mac80211_hwsim-check-the-return-value-of.patch @@ -0,0 +1,39 @@ +From 431054e59d25a9f16b85e925de89370c738ac94a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 22 Aug 2023 14:17:21 +0200 +Subject: Revert "wifi: mac80211_hwsim: check the return value of nla_put_u32" + +From: Johannes Berg + +[ Upstream commit 1b78dd34560e9962f8e917fe4adde6f2ab0eb89f ] + +This reverts commit b970ac68e0c4 ("wifi: mac80211_hwsim: check the +return value of nla_put_u32") since it introduced a memory leak in +the error path, which seems worse than sending an incomplete skb, +and the put can't fail anyway since the SKB was just allocated. + +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/virtual/mac80211_hwsim.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +diff --git a/drivers/net/wireless/virtual/mac80211_hwsim.c b/drivers/net/wireless/virtual/mac80211_hwsim.c +index dd516cec41973..23307c8baea21 100644 +--- a/drivers/net/wireless/virtual/mac80211_hwsim.c ++++ b/drivers/net/wireless/virtual/mac80211_hwsim.c +@@ -582,9 +582,8 @@ static int mac80211_hwsim_vendor_cmd_test(struct wiphy *wiphy, + */ + + /* Add vendor data */ +- err = nla_put_u32(skb, QCA_WLAN_VENDOR_ATTR_TEST, val + 1); +- if (err) +- return err; ++ nla_put_u32(skb, QCA_WLAN_VENDOR_ATTR_TEST, val + 1); ++ + /* Send the event - this will call nla_nest_end() */ + cfg80211_vendor_event(skb, GFP_KERNEL); + } +-- +2.40.1 + diff --git a/queue-6.5/riscv-kexec-align-the-kexeced-kernel-entry.patch b/queue-6.5/riscv-kexec-align-the-kexeced-kernel-entry.patch new file mode 100644 index 00000000000..ea1325b13d8 --- /dev/null +++ b/queue-6.5/riscv-kexec-align-the-kexeced-kernel-entry.patch @@ -0,0 +1,47 @@ +From f3a721f8d050c391aec90297e1160583866d3b8b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 6 Sep 2023 17:58:17 +0800 +Subject: riscv: kexec: Align the kexeced kernel entry + +From: Song Shuai + +[ Upstream commit 1bfb2b618d52e59a4ef1896b46c4698ad2be66b7 ] + +The current riscv boot protocol requires 2MB alignment for RV64 +and 4MB alignment for RV32. + +In KEXEC_FILE path, the elf_find_pbase() function should align +the kexeced kernel entry according to the requirement, otherwise +the kexeced kernel would silently BUG at the setup_vm(). + +Fixes: 8acea455fafa ("RISC-V: Support for kexec_file on panic") +Signed-off-by: Song Shuai +Link: https://lore.kernel.org/r/20230906095817.364390-1-songshuaishuai@tinylab.org +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/kernel/elf_kexec.c | 8 +++++++- + 1 file changed, 7 insertions(+), 1 deletion(-) + +diff --git a/arch/riscv/kernel/elf_kexec.c b/arch/riscv/kernel/elf_kexec.c +index c08bb5c3b3857..b3b96ff46d193 100644 +--- a/arch/riscv/kernel/elf_kexec.c ++++ b/arch/riscv/kernel/elf_kexec.c +@@ -98,7 +98,13 @@ static int elf_find_pbase(struct kimage *image, unsigned long kernel_len, + kbuf.image = image; + kbuf.buf_min = lowest_paddr; + kbuf.buf_max = ULONG_MAX; +- kbuf.buf_align = PAGE_SIZE; ++ ++ /* ++ * Current riscv boot protocol requires 2MB alignment for ++ * RV64 and 4MB alignment for RV32 ++ * ++ */ ++ kbuf.buf_align = PMD_SIZE; + kbuf.mem = KEXEC_BUF_MEM_UNKNOWN; + kbuf.memsz = ALIGN(kernel_len, PAGE_SIZE); + kbuf.top_down = false; +-- +2.40.1 + diff --git a/queue-6.5/s390-boot-cleanup-number-of-page-table-levels-setup.patch b/queue-6.5/s390-boot-cleanup-number-of-page-table-levels-setup.patch new file mode 100644 index 00000000000..8d7fa45e1d8 --- /dev/null +++ b/queue-6.5/s390-boot-cleanup-number-of-page-table-levels-setup.patch @@ -0,0 +1,63 @@ +From 1433000ff520b2e2411103591369e6afcbda459b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 6 Jul 2023 12:28:17 +0200 +Subject: s390/boot: cleanup number of page table levels setup + +From: Alexander Gordeev + +[ Upstream commit 8ddccc8a7d06f7ea4d8579970c95609d1b1de77b ] + +The separate vmalloc area size check against _REGION2_SIZE +is needed in case user provided insanely large value using +vmalloc= kernel command line parameter. That could lead to +overflow and selecting 3 page table levels instead of 4. + +Use size_add() for the overflow check and get rid of the +extra vmalloc area check. + +With the current values of CONFIG_MAX_PHYSMEM_BITS and +PAGES_PER_SECTION the sum of maximal possible size of +identity mapping and vmemmap area (derived from these +macros) plus modules area size MODULES_LEN can not +overflow. Thus, that sum is used as first addend while +vmalloc area size is second addend for size_add(). + +Suggested-by: Heiko Carstens +Acked-by: Heiko Carstens +Signed-off-by: Alexander Gordeev +Signed-off-by: Heiko Carstens +Signed-off-by: Sasha Levin +--- + arch/s390/boot/startup.c | 9 ++++----- + 1 file changed, 4 insertions(+), 5 deletions(-) + +diff --git a/arch/s390/boot/startup.c b/arch/s390/boot/startup.c +index 64bd7ac3e35d1..f8d0550e5d2af 100644 +--- a/arch/s390/boot/startup.c ++++ b/arch/s390/boot/startup.c +@@ -176,6 +176,7 @@ static unsigned long setup_kernel_memory_layout(void) + unsigned long asce_limit; + unsigned long rte_size; + unsigned long pages; ++ unsigned long vsize; + unsigned long vmax; + + pages = ident_map_size / PAGE_SIZE; +@@ -183,11 +184,9 @@ static unsigned long setup_kernel_memory_layout(void) + vmemmap_size = SECTION_ALIGN_UP(pages) * sizeof(struct page); + + /* choose kernel address space layout: 4 or 3 levels. */ +- vmemmap_start = round_up(ident_map_size, _REGION3_SIZE); +- if (IS_ENABLED(CONFIG_KASAN) || +- vmalloc_size > _REGION2_SIZE || +- vmemmap_start + vmemmap_size + vmalloc_size + MODULES_LEN > +- _REGION2_SIZE) { ++ vsize = round_up(ident_map_size, _REGION3_SIZE) + vmemmap_size + MODULES_LEN; ++ vsize = size_add(vsize, vmalloc_size); ++ if (IS_ENABLED(CONFIG_KASAN) || (vsize > _REGION2_SIZE)) { + asce_limit = _REGION1_SIZE; + rte_size = _REGION2_SIZE; + } else { +-- +2.40.1 + diff --git a/queue-6.5/samples-hw_breakpoint-fix-building-without-module-un.patch b/queue-6.5/samples-hw_breakpoint-fix-building-without-module-un.patch new file mode 100644 index 00000000000..b42c4f2ba8f --- /dev/null +++ b/queue-6.5/samples-hw_breakpoint-fix-building-without-module-un.patch @@ -0,0 +1,48 @@ +From 6ab63f0c5a10d7d362d09a97120c021ddd4e8cb0 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 25 Jul 2023 10:25:36 +0200 +Subject: samples/hw_breakpoint: fix building without module unloading + +From: Arnd Bergmann + +[ Upstream commit b9080468caeddc58a91edd1c3a7d212ea82b0d1d ] + +__symbol_put() is really meant as an internal helper and is not available +when module unloading is disabled, unlike the previously used symbol_put(): + +samples/hw_breakpoint/data_breakpoint.c: In function 'hw_break_module_exit': +samples/hw_breakpoint/data_breakpoint.c:73:9: error: implicit declaration of function '__symbol_put'; did you mean '__symbol_get'? [-Werror=implicit-function-declaration] + +The hw_break_module_exit() function is not actually used when module +unloading is disabled, but it still causes the build failure for an +undefined identifier. Enclose this one call in an appropriate #ifdef to +clarify what the requirement is. Leaving out the entire exit function +would also work but feels less clar in this case. + +Fixes: 910e230d5f1bb ("samples/hw_breakpoint: Fix kernel BUG 'invalid opcode: 0000'") +Fixes: d8a84d33a4954 ("samples/hw_breakpoint: drop use of kallsyms_lookup_name()") +Signed-off-by: Arnd Bergmann +Reviewed-by: Petr Mladek +Signed-off-by: Luis Chamberlain +Signed-off-by: Sasha Levin +--- + samples/hw_breakpoint/data_breakpoint.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/samples/hw_breakpoint/data_breakpoint.c b/samples/hw_breakpoint/data_breakpoint.c +index 9debd128b2ab8..b99322f188e59 100644 +--- a/samples/hw_breakpoint/data_breakpoint.c ++++ b/samples/hw_breakpoint/data_breakpoint.c +@@ -70,7 +70,9 @@ static int __init hw_break_module_init(void) + static void __exit hw_break_module_exit(void) + { + unregister_wide_hw_breakpoint(sample_hbp); ++#ifdef CONFIG_MODULE_UNLOAD + __symbol_put(ksym_name); ++#endif + printk(KERN_INFO "HW Breakpoint for %s write uninstalled\n", ksym_name); + } + +-- +2.40.1 + diff --git a/queue-6.5/samples-hw_breakpoint-fix-kernel-bug-invalid-opcode-.patch b/queue-6.5/samples-hw_breakpoint-fix-kernel-bug-invalid-opcode-.patch new file mode 100644 index 00000000000..79eddbc4f30 --- /dev/null +++ b/queue-6.5/samples-hw_breakpoint-fix-kernel-bug-invalid-opcode-.patch @@ -0,0 +1,77 @@ +From d0694ef523e8b25720156bf2d051e2f1aac11600 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 16 Apr 2023 23:05:17 +0800 +Subject: samples/hw_breakpoint: Fix kernel BUG 'invalid opcode: 0000' + +From: Rong Tao + +[ Upstream commit 910e230d5f1bb72c54532e94fbb1705095c7bab6 ] + +Macro symbol_put() is defined as __symbol_put(__stringify(x)) + + ksym_name = "jiffies" + symbol_put(ksym_name) + +will be resolved as + + __symbol_put("ksym_name") + +which is clearly wrong. So symbol_put must be replaced with __symbol_put. + +When we uninstall hw_breakpoint.ko (rmmod), a kernel bug occurs with the +following error: + +[11381.854152] kernel BUG at kernel/module/main.c:779! +[11381.854159] invalid opcode: 0000 [#2] PREEMPT SMP PTI +[11381.854163] CPU: 8 PID: 59623 Comm: rmmod Tainted: G D OE 6.2.9-200.fc37.x86_64 #1 +[11381.854167] Hardware name: To Be Filled By O.E.M. To Be Filled By O.E.M./B360M-HDV, BIOS P3.20 10/23/2018 +[11381.854169] RIP: 0010:__symbol_put+0xa2/0xb0 +[11381.854175] Code: 00 e8 92 d2 f7 ff 65 8b 05 c3 2f e6 78 85 c0 74 1b 48 8b 44 24 30 65 48 2b 04 25 28 00 00 00 75 12 48 83 c4 38 c3 cc cc cc cc <0f> 0b 0f 1f 44 00 00 eb de e8 c0 df d8 00 90 90 90 90 90 90 90 90 +[11381.854178] RSP: 0018:ffffad8ec6ae7dd0 EFLAGS: 00010246 +[11381.854181] RAX: 0000000000000000 RBX: ffffffffc1fd1240 RCX: 000000000000000c +[11381.854184] RDX: 000000000000006b RSI: ffffffffc02bf7c7 RDI: ffffffffc1fd001c +[11381.854186] RBP: 000055a38b76e7c8 R08: ffffffff871ccfe0 R09: 0000000000000000 +[11381.854188] R10: 0000000000000000 R11: 0000000000000000 R12: 0000000000000000 +[11381.854190] R13: 0000000000000000 R14: 0000000000000000 R15: 0000000000000000 +[11381.854192] FS: 00007fbf7c62c740(0000) GS:ffff8c5badc00000(0000) knlGS:0000000000000000 +[11381.854195] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 +[11381.854197] CR2: 000055a38b7793f8 CR3: 0000000363e1e001 CR4: 00000000003726e0 +[11381.854200] DR0: ffffffffb3407980 DR1: 0000000000000000 DR2: 0000000000000000 +[11381.854202] DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400 +[11381.854204] Call Trace: +[11381.854207] +[11381.854212] s_module_exit+0xc/0xff0 [symbol_getput] +[11381.854219] __do_sys_delete_module.constprop.0+0x198/0x2f0 +[11381.854225] do_syscall_64+0x58/0x80 +[11381.854231] ? exit_to_user_mode_prepare+0x180/0x1f0 +[11381.854237] ? syscall_exit_to_user_mode+0x17/0x40 +[11381.854241] ? do_syscall_64+0x67/0x80 +[11381.854245] ? syscall_exit_to_user_mode+0x17/0x40 +[11381.854248] ? do_syscall_64+0x67/0x80 +[11381.854252] ? exc_page_fault+0x70/0x170 +[11381.854256] entry_SYSCALL_64_after_hwframe+0x72/0xdc + +Signed-off-by: Rong Tao +Reviewed-by: Petr Mladek +Signed-off-by: Luis Chamberlain +Signed-off-by: Sasha Levin +--- + samples/hw_breakpoint/data_breakpoint.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/samples/hw_breakpoint/data_breakpoint.c b/samples/hw_breakpoint/data_breakpoint.c +index 418c46fe5ffc3..9debd128b2ab8 100644 +--- a/samples/hw_breakpoint/data_breakpoint.c ++++ b/samples/hw_breakpoint/data_breakpoint.c +@@ -70,7 +70,7 @@ static int __init hw_break_module_init(void) + static void __exit hw_break_module_exit(void) + { + unregister_wide_hw_breakpoint(sample_hbp); +- symbol_put(ksym_name); ++ __symbol_put(ksym_name); + printk(KERN_INFO "HW Breakpoint for %s write uninstalled\n", ksym_name); + } + +-- +2.40.1 + diff --git a/queue-6.5/scftorture-forgive-memory-allocation-failure-if-kasa.patch b/queue-6.5/scftorture-forgive-memory-allocation-failure-if-kasa.patch new file mode 100644 index 00000000000..ab05980464d --- /dev/null +++ b/queue-6.5/scftorture-forgive-memory-allocation-failure-if-kasa.patch @@ -0,0 +1,49 @@ +From 6a7aad339ae004003f8a3665493477c18b05ae45 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 15 May 2023 19:00:10 -0700 +Subject: scftorture: Forgive memory-allocation failure if KASAN + +From: Paul E. McKenney + +[ Upstream commit 013608cd0812bdb21fc26d39ed8fdd2fc76e8b9b ] + +Kernels built with CONFIG_KASAN=y quarantine newly freed memory in order +to better detect use-after-free errors. However, this can exhaust memory +more quickly in allocator-heavy tests, which can result in spurious +scftorture failure. This commit therefore forgives memory-allocation +failure in kernels built with CONFIG_KASAN=y, but continues counting +the errors for use in detailed test-result analyses. + +Signed-off-by: Paul E. McKenney +Signed-off-by: Sasha Levin +--- + kernel/scftorture.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +diff --git a/kernel/scftorture.c b/kernel/scftorture.c +index 5d113aa59e773..83c33ba0ca7e0 100644 +--- a/kernel/scftorture.c ++++ b/kernel/scftorture.c +@@ -171,7 +171,8 @@ static void scf_torture_stats_print(void) + scfs.n_all_wait += scf_stats_p[i].n_all_wait; + } + if (atomic_read(&n_errs) || atomic_read(&n_mb_in_errs) || +- atomic_read(&n_mb_out_errs) || atomic_read(&n_alloc_errs)) ++ atomic_read(&n_mb_out_errs) || ++ (!IS_ENABLED(CONFIG_KASAN) && atomic_read(&n_alloc_errs))) + bangstr = "!!! "; + pr_alert("%s %sscf_invoked_count %s: %lld resched: %lld single: %lld/%lld single_ofl: %lld/%lld single_rpc: %lld single_rpc_ofl: %lld many: %lld/%lld all: %lld/%lld ", + SCFTORT_FLAG, bangstr, isdone ? "VER" : "ver", invoked_count, scfs.n_resched, +@@ -323,7 +324,8 @@ static void scftorture_invoke_one(struct scf_statistics *scfp, struct torture_ra + preempt_disable(); + if (scfsp->scfs_prim == SCF_PRIM_SINGLE || scfsp->scfs_wait) { + scfcp = kmalloc(sizeof(*scfcp), GFP_ATOMIC); +- if (WARN_ON_ONCE(!scfcp)) { ++ if (!scfcp) { ++ WARN_ON_ONCE(!IS_ENABLED(CONFIG_KASAN)); + atomic_inc(&n_alloc_errs); + } else { + scfcp->scfc_cpu = -1; +-- +2.40.1 + diff --git a/queue-6.5/scsi-lpfc-abort-outstanding-els-cmds-when-mailbox-ti.patch b/queue-6.5/scsi-lpfc-abort-outstanding-els-cmds-when-mailbox-ti.patch new file mode 100644 index 00000000000..b6bb34250c6 --- /dev/null +++ b/queue-6.5/scsi-lpfc-abort-outstanding-els-cmds-when-mailbox-ti.patch @@ -0,0 +1,196 @@ +From 2187bc313549c1073deb3830fb7e7874e8677da1 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 12 Jul 2023 11:05:18 -0700 +Subject: scsi: lpfc: Abort outstanding ELS cmds when mailbox timeout error is + detected + +From: Justin Tee + +[ Upstream commit 089ea22e374aa20043e72243c47b5867d5419d38 ] + +A mailbox timeout error usually indicates something has gone wrong, and a +follow up reset of the HBA is a typical recovery mechanism. Introduce a +MBX_TMO_ERR flag to detect such cases and have lpfc_els_flush_cmd abort ELS +commands if the MBX_TMO_ERR flag condition was set. This ensures all of +the registered SGL resources meant for ELS traffic are not leaked after an +HBA reset. + +Signed-off-by: Justin Tee +Link: https://lore.kernel.org/r/20230712180522.112722-9-justintee8345@gmail.com +Signed-off-by: Martin K. Petersen +Signed-off-by: Sasha Levin +--- + drivers/scsi/lpfc/lpfc.h | 1 + + drivers/scsi/lpfc/lpfc_els.c | 25 ++++++++++++++++++------- + drivers/scsi/lpfc/lpfc_init.c | 20 +++++++++++++++++--- + drivers/scsi/lpfc/lpfc_sli.c | 8 +++++++- + 4 files changed, 43 insertions(+), 11 deletions(-) + +diff --git a/drivers/scsi/lpfc/lpfc.h b/drivers/scsi/lpfc/lpfc.h +index 9a89636843693..e8d7eeeb21856 100644 +--- a/drivers/scsi/lpfc/lpfc.h ++++ b/drivers/scsi/lpfc/lpfc.h +@@ -872,6 +872,7 @@ enum lpfc_irq_chann_mode { + enum lpfc_hba_bit_flags { + FABRIC_COMANDS_BLOCKED, + HBA_PCI_ERR, ++ MBX_TMO_ERR, + }; + + struct lpfc_hba { +diff --git a/drivers/scsi/lpfc/lpfc_els.c b/drivers/scsi/lpfc/lpfc_els.c +index 2bad9954c355f..6f6ef5235ee3b 100644 +--- a/drivers/scsi/lpfc/lpfc_els.c ++++ b/drivers/scsi/lpfc/lpfc_els.c +@@ -9588,11 +9588,13 @@ void + lpfc_els_flush_cmd(struct lpfc_vport *vport) + { + LIST_HEAD(abort_list); ++ LIST_HEAD(cancel_list); + struct lpfc_hba *phba = vport->phba; + struct lpfc_sli_ring *pring; + struct lpfc_iocbq *tmp_iocb, *piocb; + u32 ulp_command; + unsigned long iflags = 0; ++ bool mbx_tmo_err; + + lpfc_fabric_abort_vport(vport); + +@@ -9614,15 +9616,16 @@ lpfc_els_flush_cmd(struct lpfc_vport *vport) + if (phba->sli_rev == LPFC_SLI_REV4) + spin_lock(&pring->ring_lock); + ++ mbx_tmo_err = test_bit(MBX_TMO_ERR, &phba->bit_flags); + /* First we need to issue aborts to outstanding cmds on txcmpl */ + list_for_each_entry_safe(piocb, tmp_iocb, &pring->txcmplq, list) { +- if (piocb->cmd_flag & LPFC_IO_LIBDFC) ++ if (piocb->cmd_flag & LPFC_IO_LIBDFC && !mbx_tmo_err) + continue; + + if (piocb->vport != vport) + continue; + +- if (piocb->cmd_flag & LPFC_DRIVER_ABORTED) ++ if (piocb->cmd_flag & LPFC_DRIVER_ABORTED && !mbx_tmo_err) + continue; + + /* On the ELS ring we can have ELS_REQUESTs or +@@ -9641,8 +9644,8 @@ lpfc_els_flush_cmd(struct lpfc_vport *vport) + */ + if (phba->link_state == LPFC_LINK_DOWN) + piocb->cmd_cmpl = lpfc_cmpl_els_link_down; +- } +- if (ulp_command == CMD_GEN_REQUEST64_CR) ++ } else if (ulp_command == CMD_GEN_REQUEST64_CR || ++ mbx_tmo_err) + list_add_tail(&piocb->dlist, &abort_list); + } + +@@ -9654,11 +9657,19 @@ lpfc_els_flush_cmd(struct lpfc_vport *vport) + list_for_each_entry_safe(piocb, tmp_iocb, &abort_list, dlist) { + spin_lock_irqsave(&phba->hbalock, iflags); + list_del_init(&piocb->dlist); +- lpfc_sli_issue_abort_iotag(phba, pring, piocb, NULL); ++ if (mbx_tmo_err) ++ list_move_tail(&piocb->list, &cancel_list); ++ else ++ lpfc_sli_issue_abort_iotag(phba, pring, piocb, NULL); ++ + spin_unlock_irqrestore(&phba->hbalock, iflags); + } +- /* Make sure HBA is alive */ +- lpfc_issue_hb_tmo(phba); ++ if (!list_empty(&cancel_list)) ++ lpfc_sli_cancel_iocbs(phba, &cancel_list, IOSTAT_LOCAL_REJECT, ++ IOERR_SLI_ABORTED); ++ else ++ /* Make sure HBA is alive */ ++ lpfc_issue_hb_tmo(phba); + + if (!list_empty(&abort_list)) + lpfc_printf_vlog(vport, KERN_ERR, LOG_TRACE_EVENT, +diff --git a/drivers/scsi/lpfc/lpfc_init.c b/drivers/scsi/lpfc/lpfc_init.c +index 3221a934066bb..ce9e4cdd6004c 100644 +--- a/drivers/scsi/lpfc/lpfc_init.c ++++ b/drivers/scsi/lpfc/lpfc_init.c +@@ -7550,6 +7550,8 @@ lpfc_disable_pci_dev(struct lpfc_hba *phba) + void + lpfc_reset_hba(struct lpfc_hba *phba) + { ++ int rc = 0; ++ + /* If resets are disabled then set error state and return. */ + if (!phba->cfg_enable_hba_reset) { + phba->link_state = LPFC_HBA_ERROR; +@@ -7560,13 +7562,25 @@ lpfc_reset_hba(struct lpfc_hba *phba) + if (phba->sli.sli_flag & LPFC_SLI_ACTIVE) { + lpfc_offline_prep(phba, LPFC_MBX_WAIT); + } else { ++ if (test_bit(MBX_TMO_ERR, &phba->bit_flags)) { ++ /* Perform a PCI function reset to start from clean */ ++ rc = lpfc_pci_function_reset(phba); ++ lpfc_els_flush_all_cmd(phba); ++ } + lpfc_offline_prep(phba, LPFC_MBX_NO_WAIT); + lpfc_sli_flush_io_rings(phba); + } + lpfc_offline(phba); +- lpfc_sli_brdrestart(phba); +- lpfc_online(phba); +- lpfc_unblock_mgmt_io(phba); ++ clear_bit(MBX_TMO_ERR, &phba->bit_flags); ++ if (unlikely(rc)) { ++ lpfc_printf_log(phba, KERN_ERR, LOG_SLI, ++ "8888 PCI function reset failed rc %x\n", ++ rc); ++ } else { ++ lpfc_sli_brdrestart(phba); ++ lpfc_online(phba); ++ lpfc_unblock_mgmt_io(phba); ++ } + } + + /** +diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c +index 58d10f8f75a78..4dfadf254a727 100644 +--- a/drivers/scsi/lpfc/lpfc_sli.c ++++ b/drivers/scsi/lpfc/lpfc_sli.c +@@ -3935,6 +3935,8 @@ void lpfc_poll_eratt(struct timer_list *t) + uint64_t sli_intr, cnt; + + phba = from_timer(phba, t, eratt_poll); ++ if (!(phba->hba_flag & HBA_SETUP)) ++ return; + + /* Here we will also keep track of interrupts per sec of the hba */ + sli_intr = phba->sli.slistat.sli_intr; +@@ -7693,7 +7695,9 @@ lpfc_sli4_repost_sgl_list(struct lpfc_hba *phba, + spin_unlock_irq(&phba->hbalock); + } else { + lpfc_printf_log(phba, KERN_ERR, LOG_TRACE_EVENT, +- "3161 Failure to post sgl to port.\n"); ++ "3161 Failure to post sgl to port,status %x " ++ "blkcnt %d totalcnt %d postcnt %d\n", ++ status, block_cnt, total_cnt, post_cnt); + return -EIO; + } + +@@ -8478,6 +8482,7 @@ lpfc_sli4_hba_setup(struct lpfc_hba *phba) + spin_unlock_irq(&phba->hbalock); + } + } ++ phba->hba_flag &= ~HBA_SETUP; + + lpfc_sli4_dip(phba); + +@@ -9282,6 +9287,7 @@ lpfc_mbox_timeout_handler(struct lpfc_hba *phba) + * would get IOCB_ERROR from lpfc_sli_issue_iocb, allowing + * it to fail all outstanding SCSI IO. + */ ++ set_bit(MBX_TMO_ERR, &phba->bit_flags); + spin_lock_irq(&phba->pport->work_port_lock); + phba->pport->work_port_events &= ~WORKER_MBOX_TMO; + spin_unlock_irq(&phba->pport->work_port_lock); +-- +2.40.1 + diff --git a/queue-6.5/scsi-lpfc-fix-the-null-vs-is_err-bug-for-debugfs_cre.patch b/queue-6.5/scsi-lpfc-fix-the-null-vs-is_err-bug-for-debugfs_cre.patch new file mode 100644 index 00000000000..45077c8603f --- /dev/null +++ b/queue-6.5/scsi-lpfc-fix-the-null-vs-is_err-bug-for-debugfs_cre.patch @@ -0,0 +1,97 @@ +From 2d9a9d4edb3f6718aa424da11c619550542c9889 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 6 Sep 2023 11:08:09 +0800 +Subject: scsi: lpfc: Fix the NULL vs IS_ERR() bug for debugfs_create_file() + +From: Jinjie Ruan + +[ Upstream commit 7dcc683db3639eadd11bf0d59a09088a43de5e22 ] + +Since debugfs_create_file() returns ERR_PTR and never NULL, use IS_ERR() to +check the return value. + +Fixes: 2fcbc569b9f5 ("scsi: lpfc: Make debugfs ktime stats generic for NVME and SCSI") +Fixes: 4c47efc140fa ("scsi: lpfc: Move SCSI and NVME Stats to hardware queue structures") +Fixes: 6a828b0f6192 ("scsi: lpfc: Support non-uniform allocation of MSIX vectors to hardware queues") +Fixes: 95bfc6d8ad86 ("scsi: lpfc: Make FW logging dynamically configurable") +Fixes: 9f77870870d8 ("scsi: lpfc: Add debugfs support for cm framework buffers") +Fixes: c490850a0947 ("scsi: lpfc: Adapt partitioned XRI lists to efficient sharing") +Signed-off-by: Jinjie Ruan +Link: https://lore.kernel.org/r/20230906030809.2847970-1-ruanjinjie@huawei.com +Reviewed-by: Justin Tee +Signed-off-by: Martin K. Petersen +Signed-off-by: Sasha Levin +--- + drivers/scsi/lpfc/lpfc_debugfs.c | 14 +++++++------- + 1 file changed, 7 insertions(+), 7 deletions(-) + +diff --git a/drivers/scsi/lpfc/lpfc_debugfs.c b/drivers/scsi/lpfc/lpfc_debugfs.c +index 7f9b221e7c34a..ea9b42225e629 100644 +--- a/drivers/scsi/lpfc/lpfc_debugfs.c ++++ b/drivers/scsi/lpfc/lpfc_debugfs.c +@@ -6073,7 +6073,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + phba->hba_debugfs_root, + phba, + &lpfc_debugfs_op_multixripools); +- if (!phba->debug_multixri_pools) { ++ if (IS_ERR(phba->debug_multixri_pools)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "0527 Cannot create debugfs multixripools\n"); + goto debug_failed; +@@ -6085,7 +6085,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + debugfs_create_file(name, S_IFREG | 0644, + phba->hba_debugfs_root, + phba, &lpfc_cgn_buffer_op); +- if (!phba->debug_cgn_buffer) { ++ if (IS_ERR(phba->debug_cgn_buffer)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "6527 Cannot create debugfs " + "cgn_buffer\n"); +@@ -6098,7 +6098,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + debugfs_create_file(name, S_IFREG | 0644, + phba->hba_debugfs_root, + phba, &lpfc_rx_monitor_op); +- if (!phba->debug_rx_monitor) { ++ if (IS_ERR(phba->debug_rx_monitor)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "6528 Cannot create debugfs " + "rx_monitor\n"); +@@ -6111,7 +6111,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + debugfs_create_file(name, 0644, + phba->hba_debugfs_root, + phba, &lpfc_debugfs_ras_log); +- if (!phba->debug_ras_log) { ++ if (IS_ERR(phba->debug_ras_log)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "6148 Cannot create debugfs" + " ras_log\n"); +@@ -6132,7 +6132,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + debugfs_create_file(name, S_IFREG | 0644, + phba->hba_debugfs_root, + phba, &lpfc_debugfs_op_lockstat); +- if (!phba->debug_lockstat) { ++ if (IS_ERR(phba->debug_lockstat)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "4610 Can't create debugfs lockstat\n"); + goto debug_failed; +@@ -6358,7 +6358,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + debugfs_create_file(name, 0644, + vport->vport_debugfs_root, + vport, &lpfc_debugfs_op_scsistat); +- if (!vport->debug_scsistat) { ++ if (IS_ERR(vport->debug_scsistat)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "4611 Cannot create debugfs scsistat\n"); + goto debug_failed; +@@ -6369,7 +6369,7 @@ lpfc_debugfs_initialize(struct lpfc_vport *vport) + debugfs_create_file(name, 0644, + vport->vport_debugfs_root, + vport, &lpfc_debugfs_op_ioktime); +- if (!vport->debug_ioktime) { ++ if (IS_ERR(vport->debug_ioktime)) { + lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT, + "0815 Cannot create debugfs ioktime\n"); + goto debug_failed; +-- +2.40.1 + diff --git a/queue-6.5/scsi-qla2xxx-fix-null-vs-is_err-bug-for-debugfs_crea.patch b/queue-6.5/scsi-qla2xxx-fix-null-vs-is_err-bug-for-debugfs_crea.patch new file mode 100644 index 00000000000..8c2f04f2f23 --- /dev/null +++ b/queue-6.5/scsi-qla2xxx-fix-null-vs-is_err-bug-for-debugfs_crea.patch @@ -0,0 +1,54 @@ +From 9f0205633022384a4bbf6775d1395d311b28f4ac Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 31 Aug 2023 22:09:29 +0800 +Subject: scsi: qla2xxx: Fix NULL vs IS_ERR() bug for debugfs_create_dir() + +From: Jinjie Ruan + +[ Upstream commit d0b0822e32dbae80bbcb3cc86f34d28539d913df ] + +Since both debugfs_create_dir() and debugfs_create_file() return ERR_PTR +and never NULL, use IS_ERR() instead of checking for NULL. + +Fixes: 1e98fb0f9208 ("scsi: qla2xxx: Setup debugfs entries for remote ports") +Signed-off-by: Jinjie Ruan +Link: https://lore.kernel.org/r/20230831140930.3166359-1-ruanjinjie@huawei.com +Signed-off-by: Martin K. Petersen +Signed-off-by: Sasha Levin +--- + drivers/scsi/qla2xxx/qla_dfs.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +diff --git a/drivers/scsi/qla2xxx/qla_dfs.c b/drivers/scsi/qla2xxx/qla_dfs.c +index f060e593685de..a7a364760b800 100644 +--- a/drivers/scsi/qla2xxx/qla_dfs.c ++++ b/drivers/scsi/qla2xxx/qla_dfs.c +@@ -116,7 +116,7 @@ qla2x00_dfs_create_rport(scsi_qla_host_t *vha, struct fc_port *fp) + + sprintf(wwn, "pn-%016llx", wwn_to_u64(fp->port_name)); + fp->dfs_rport_dir = debugfs_create_dir(wwn, vha->dfs_rport_root); +- if (!fp->dfs_rport_dir) ++ if (IS_ERR(fp->dfs_rport_dir)) + return; + if (NVME_TARGET(vha->hw, fp)) + debugfs_create_file("dev_loss_tmo", 0600, fp->dfs_rport_dir, +@@ -708,14 +708,14 @@ qla2x00_dfs_setup(scsi_qla_host_t *vha) + if (IS_QLA27XX(ha) || IS_QLA83XX(ha) || IS_QLA28XX(ha)) { + ha->tgt.dfs_naqp = debugfs_create_file("naqp", + 0400, ha->dfs_dir, vha, &dfs_naqp_ops); +- if (!ha->tgt.dfs_naqp) { ++ if (IS_ERR(ha->tgt.dfs_naqp)) { + ql_log(ql_log_warn, vha, 0xd011, + "Unable to create debugFS naqp node.\n"); + goto out; + } + } + vha->dfs_rport_root = debugfs_create_dir("rports", ha->dfs_dir); +- if (!vha->dfs_rport_root) { ++ if (IS_ERR(vha->dfs_rport_root)) { + ql_log(ql_log_warn, vha, 0xd012, + "Unable to create debugFS rports node.\n"); + goto out; +-- +2.40.1 + diff --git a/queue-6.5/scsi-target-core-fix-target_cmd_counter-leak.patch b/queue-6.5/scsi-target-core-fix-target_cmd_counter-leak.patch new file mode 100644 index 00000000000..9740449f27a --- /dev/null +++ b/queue-6.5/scsi-target-core-fix-target_cmd_counter-leak.patch @@ -0,0 +1,56 @@ +From 3fb20f5d58c67804613e5be3f859b43ca86c60f4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 31 Aug 2023 20:34:59 +0200 +Subject: scsi: target: core: Fix target_cmd_counter leak + +From: David Disseldorp + +[ Upstream commit d14e3e553e05cb763964c991fe6acb0a6a1c6f9c ] + +The target_cmd_counter struct allocated via target_alloc_cmd_counter() is +never freed, resulting in leaks across various transport types, e.g.: + + unreferenced object 0xffff88801f920120 (size 96): + comm "sh", pid 102, jiffies 4294892535 (age 713.412s) + hex dump (first 32 bytes): + 07 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ + 00 00 00 00 00 00 00 00 38 01 92 1f 80 88 ff ff ........8....... + backtrace: + [<00000000e58a6252>] kmalloc_trace+0x11/0x20 + [<0000000043af4b2f>] target_alloc_cmd_counter+0x17/0x90 [target_core_mod] + [<000000007da2dfa7>] target_setup_session+0x2d/0x140 [target_core_mod] + [<0000000068feef86>] tcm_loop_tpg_nexus_store+0x19b/0x350 [tcm_loop] + [<000000006a80e021>] configfs_write_iter+0xb1/0x120 + [<00000000e9f4d860>] vfs_write+0x2e4/0x3c0 + [<000000008143433b>] ksys_write+0x80/0xb0 + [<00000000a7df29b2>] do_syscall_64+0x42/0x90 + [<0000000053f45fb8>] entry_SYSCALL_64_after_hwframe+0x6e/0xd8 + +Free the structure alongside the corresponding iscsit_conn / se_sess +parent. + +Signed-off-by: David Disseldorp +Link: https://lore.kernel.org/r/20230831183459.6938-1-ddiss@suse.de +Fixes: becd9be6069e ("scsi: target: Move sess cmd counter to new struct") +Reviewed-by: Mike Christie +Signed-off-by: Martin K. Petersen +Signed-off-by: Sasha Levin +--- + drivers/target/target_core_transport.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/target/target_core_transport.c b/drivers/target/target_core_transport.c +index 687adc9e086ca..0686882bcbda3 100644 +--- a/drivers/target/target_core_transport.c ++++ b/drivers/target/target_core_transport.c +@@ -264,6 +264,7 @@ void target_free_cmd_counter(struct target_cmd_counter *cmd_cnt) + percpu_ref_put(&cmd_cnt->refcnt); + + percpu_ref_exit(&cmd_cnt->refcnt); ++ kfree(cmd_cnt); + } + EXPORT_SYMBOL_GPL(target_free_cmd_counter); + +-- +2.40.1 + diff --git a/queue-6.5/scsi-target-iscsi-fix-buffer-overflow-in-lio_target_.patch b/queue-6.5/scsi-target-iscsi-fix-buffer-overflow-in-lio_target_.patch new file mode 100644 index 00000000000..7a1f4886b51 --- /dev/null +++ b/queue-6.5/scsi-target-iscsi-fix-buffer-overflow-in-lio_target_.patch @@ -0,0 +1,163 @@ +From 57ba3e34f49f8c3b0ff1ba194aa0f5c037344c4d Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 22 Jul 2023 18:26:37 +0300 +Subject: scsi: target: iscsi: Fix buffer overflow in + lio_target_nacl_info_show() + +From: Konstantin Shelekhin + +[ Upstream commit 801f287c93ff95582b0a2d2163f12870a2f076d4 ] + +The function lio_target_nacl_info_show() uses sprintf() in a loop to print +details for every iSCSI connection in a session without checking for the +buffer length. With enough iSCSI connections it's possible to overflow the +buffer provided by configfs and corrupt the memory. + +This patch replaces sprintf() with sysfs_emit_at() that checks for buffer +boundries. + +Signed-off-by: Konstantin Shelekhin +Link: https://lore.kernel.org/r/20230722152657.168859-2-k.shelekhin@yadro.com +Signed-off-by: Martin K. Petersen +Signed-off-by: Sasha Levin +--- + drivers/target/iscsi/iscsi_target_configfs.c | 54 ++++++++++---------- + 1 file changed, 27 insertions(+), 27 deletions(-) + +diff --git a/drivers/target/iscsi/iscsi_target_configfs.c b/drivers/target/iscsi/iscsi_target_configfs.c +index 5d0f51822414e..c142a67dc7cc2 100644 +--- a/drivers/target/iscsi/iscsi_target_configfs.c ++++ b/drivers/target/iscsi/iscsi_target_configfs.c +@@ -533,102 +533,102 @@ static ssize_t lio_target_nacl_info_show(struct config_item *item, char *page) + spin_lock_bh(&se_nacl->nacl_sess_lock); + se_sess = se_nacl->nacl_sess; + if (!se_sess) { +- rb += sprintf(page+rb, "No active iSCSI Session for Initiator" ++ rb += sysfs_emit_at(page, rb, "No active iSCSI Session for Initiator" + " Endpoint: %s\n", se_nacl->initiatorname); + } else { + sess = se_sess->fabric_sess_ptr; + +- rb += sprintf(page+rb, "InitiatorName: %s\n", ++ rb += sysfs_emit_at(page, rb, "InitiatorName: %s\n", + sess->sess_ops->InitiatorName); +- rb += sprintf(page+rb, "InitiatorAlias: %s\n", ++ rb += sysfs_emit_at(page, rb, "InitiatorAlias: %s\n", + sess->sess_ops->InitiatorAlias); + +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "LIO Session ID: %u ISID: 0x%6ph TSIH: %hu ", + sess->sid, sess->isid, sess->tsih); +- rb += sprintf(page+rb, "SessionType: %s\n", ++ rb += sysfs_emit_at(page, rb, "SessionType: %s\n", + (sess->sess_ops->SessionType) ? + "Discovery" : "Normal"); +- rb += sprintf(page+rb, "Session State: "); ++ rb += sysfs_emit_at(page, rb, "Session State: "); + switch (sess->session_state) { + case TARG_SESS_STATE_FREE: +- rb += sprintf(page+rb, "TARG_SESS_FREE\n"); ++ rb += sysfs_emit_at(page, rb, "TARG_SESS_FREE\n"); + break; + case TARG_SESS_STATE_ACTIVE: +- rb += sprintf(page+rb, "TARG_SESS_STATE_ACTIVE\n"); ++ rb += sysfs_emit_at(page, rb, "TARG_SESS_STATE_ACTIVE\n"); + break; + case TARG_SESS_STATE_LOGGED_IN: +- rb += sprintf(page+rb, "TARG_SESS_STATE_LOGGED_IN\n"); ++ rb += sysfs_emit_at(page, rb, "TARG_SESS_STATE_LOGGED_IN\n"); + break; + case TARG_SESS_STATE_FAILED: +- rb += sprintf(page+rb, "TARG_SESS_STATE_FAILED\n"); ++ rb += sysfs_emit_at(page, rb, "TARG_SESS_STATE_FAILED\n"); + break; + case TARG_SESS_STATE_IN_CONTINUE: +- rb += sprintf(page+rb, "TARG_SESS_STATE_IN_CONTINUE\n"); ++ rb += sysfs_emit_at(page, rb, "TARG_SESS_STATE_IN_CONTINUE\n"); + break; + default: +- rb += sprintf(page+rb, "ERROR: Unknown Session" ++ rb += sysfs_emit_at(page, rb, "ERROR: Unknown Session" + " State!\n"); + break; + } + +- rb += sprintf(page+rb, "---------------------[iSCSI Session" ++ rb += sysfs_emit_at(page, rb, "---------------------[iSCSI Session" + " Values]-----------------------\n"); +- rb += sprintf(page+rb, " CmdSN/WR : CmdSN/WC : ExpCmdSN" ++ rb += sysfs_emit_at(page, rb, " CmdSN/WR : CmdSN/WC : ExpCmdSN" + " : MaxCmdSN : ITT : TTT\n"); + max_cmd_sn = (u32) atomic_read(&sess->max_cmd_sn); +- rb += sprintf(page+rb, " 0x%08x 0x%08x 0x%08x 0x%08x" ++ rb += sysfs_emit_at(page, rb, " 0x%08x 0x%08x 0x%08x 0x%08x" + " 0x%08x 0x%08x\n", + sess->cmdsn_window, + (max_cmd_sn - sess->exp_cmd_sn) + 1, + sess->exp_cmd_sn, max_cmd_sn, + sess->init_task_tag, sess->targ_xfer_tag); +- rb += sprintf(page+rb, "----------------------[iSCSI" ++ rb += sysfs_emit_at(page, rb, "----------------------[iSCSI" + " Connections]-------------------------\n"); + + spin_lock(&sess->conn_lock); + list_for_each_entry(conn, &sess->sess_conn_list, conn_list) { +- rb += sprintf(page+rb, "CID: %hu Connection" ++ rb += sysfs_emit_at(page, rb, "CID: %hu Connection" + " State: ", conn->cid); + switch (conn->conn_state) { + case TARG_CONN_STATE_FREE: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_FREE\n"); + break; + case TARG_CONN_STATE_XPT_UP: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_XPT_UP\n"); + break; + case TARG_CONN_STATE_IN_LOGIN: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_IN_LOGIN\n"); + break; + case TARG_CONN_STATE_LOGGED_IN: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_LOGGED_IN\n"); + break; + case TARG_CONN_STATE_IN_LOGOUT: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_IN_LOGOUT\n"); + break; + case TARG_CONN_STATE_LOGOUT_REQUESTED: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_LOGOUT_REQUESTED\n"); + break; + case TARG_CONN_STATE_CLEANUP_WAIT: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "TARG_CONN_STATE_CLEANUP_WAIT\n"); + break; + default: +- rb += sprintf(page+rb, ++ rb += sysfs_emit_at(page, rb, + "ERROR: Unknown Connection State!\n"); + break; + } + +- rb += sprintf(page+rb, " Address %pISc %s", &conn->login_sockaddr, ++ rb += sysfs_emit_at(page, rb, " Address %pISc %s", &conn->login_sockaddr, + (conn->network_transport == ISCSI_TCP) ? + "TCP" : "SCTP"); +- rb += sprintf(page+rb, " StatSN: 0x%08x\n", ++ rb += sysfs_emit_at(page, rb, " StatSN: 0x%08x\n", + conn->stat_sn); + } + spin_unlock(&sess->conn_lock); +-- +2.40.1 + diff --git a/queue-6.5/selftests-nolibc-fix-up-kernel-parameters-support.patch b/queue-6.5/selftests-nolibc-fix-up-kernel-parameters-support.patch new file mode 100644 index 00000000000..3371cfae501 --- /dev/null +++ b/queue-6.5/selftests-nolibc-fix-up-kernel-parameters-support.patch @@ -0,0 +1,105 @@ +From 4c21f60f069e19e2bc7cea87f9e40c4c7846fd1a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 8 Jul 2023 02:32:05 +0800 +Subject: selftests/nolibc: fix up kernel parameters support +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Zhangjin Wu + +[ Upstream commit c388c9920da2679f62bec48d00ca9e80e9d0a364 ] + +kernel parameters allow pass two types of strings, one type is like +'noapic', another type is like 'panic=5', the first type is passed as +arguments of the init program, the second type is passed as environment +variables of the init program. + +when users pass kernel parameters like this: + + noapic NOLIBC_TEST=syscall + +our nolibc-test program will use the test setting from argv[1] and +ignore the one from NOLIBC_TEST environment variable, and at last, it +will print the following line and ignore the whole test setting. + + Ignoring unknown test name 'noapic' + +reversing the parsing order does solve the above issue: + + test = getenv("NOLIBC_TEST"); + if (test) + test = argv[1]; + +but it still doesn't work with such kernel parameters (without +NOLIBC_TEST environment variable): + + noapic FOO=bar + +To support all of the potential kernel parameters, let's verify the test +setting from both of argv[1] and NOLIBC_TEST environment variable. + +Reviewed-by: Thomas Weißschuh +Signed-off-by: Zhangjin Wu +Signed-off-by: Willy Tarreau +Signed-off-by: Sasha Levin +--- + tools/testing/selftests/nolibc/nolibc-test.c | 33 ++++++++++++++++++-- + 1 file changed, 31 insertions(+), 2 deletions(-) + +diff --git a/tools/testing/selftests/nolibc/nolibc-test.c b/tools/testing/selftests/nolibc/nolibc-test.c +index 486334981e601..55628a25df0a3 100644 +--- a/tools/testing/selftests/nolibc/nolibc-test.c ++++ b/tools/testing/selftests/nolibc/nolibc-test.c +@@ -939,6 +939,35 @@ static const struct test test_names[] = { + { 0 } + }; + ++int is_setting_valid(char *test) ++{ ++ int idx, len, test_len, valid = 0; ++ char delimiter; ++ ++ if (!test) ++ return valid; ++ ++ test_len = strlen(test); ++ ++ for (idx = 0; test_names[idx].name; idx++) { ++ len = strlen(test_names[idx].name); ++ if (test_len < len) ++ continue; ++ ++ if (strncmp(test, test_names[idx].name, len) != 0) ++ continue; ++ ++ delimiter = test[len]; ++ if (delimiter != ':' && delimiter != ',' && delimiter != '\0') ++ continue; ++ ++ valid = 1; ++ break; ++ } ++ ++ return valid; ++} ++ + int main(int argc, char **argv, char **envp) + { + int min = 0; +@@ -964,10 +993,10 @@ int main(int argc, char **argv, char **envp) + * syscall:5-15[:.*],stdlib:8-10 + */ + test = argv[1]; +- if (!test) ++ if (!is_setting_valid(test)) + test = getenv("NOLIBC_TEST"); + +- if (test) { ++ if (is_setting_valid(test)) { + char *comma, *colon, *dash, *value; + + do { +-- +2.40.1 + diff --git a/queue-6.5/selftests-nolibc-prevent-out-of-bounds-access-in-exp.patch b/queue-6.5/selftests-nolibc-prevent-out-of-bounds-access-in-exp.patch new file mode 100644 index 00000000000..928f92f23a0 --- /dev/null +++ b/queue-6.5/selftests-nolibc-prevent-out-of-bounds-access-in-exp.patch @@ -0,0 +1,46 @@ +From a3989fb1685f3d178bc255e9303e651ddabc332b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 3 Aug 2023 09:28:56 +0200 +Subject: selftests/nolibc: prevent out of bounds access in expect_vfprintf +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Thomas Weißschuh + +[ Upstream commit 9c5e490093e83e165022e0311bd7df5aa06cc860 ] + +If read() fails and returns -1 (or returns garbage for some other +reason) buf would be accessed out of bounds. +Only use the return value of read() after it has been validated. + +Signed-off-by: Thomas Weißschuh +Signed-off-by: Willy Tarreau +Signed-off-by: Sasha Levin +--- + tools/testing/selftests/nolibc/nolibc-test.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/tools/testing/selftests/nolibc/nolibc-test.c b/tools/testing/selftests/nolibc/nolibc-test.c +index 55628a25df0a3..8e7750e2eb97c 100644 +--- a/tools/testing/selftests/nolibc/nolibc-test.c ++++ b/tools/testing/selftests/nolibc/nolibc-test.c +@@ -769,7 +769,6 @@ static int expect_vfprintf(int llen, size_t c, const char *expected, const char + lseek(fd, 0, SEEK_SET); + + r = read(fd, buf, sizeof(buf) - 1); +- buf[r] = '\0'; + + fclose(memfile); + +@@ -779,6 +778,7 @@ static int expect_vfprintf(int llen, size_t c, const char *expected, const char + return 1; + } + ++ buf[r] = '\0'; + llen += printf(" \"%s\" = \"%s\"", expected, buf); + ret = strncmp(expected, buf, c); + +-- +2.40.1 + diff --git a/queue-6.5/selftests-tracing-fix-to-unmount-tracefs-for-recover.patch b/queue-6.5/selftests-tracing-fix-to-unmount-tracefs-for-recover.patch new file mode 100644 index 00000000000..6404d556757 --- /dev/null +++ b/queue-6.5/selftests-tracing-fix-to-unmount-tracefs-for-recover.patch @@ -0,0 +1,65 @@ +From 5d4aabb99b46d389364bd8693b0bbc08a801898a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 12 Sep 2023 10:10:39 +0900 +Subject: selftests: tracing: Fix to unmount tracefs for recovering environment + +From: Masami Hiramatsu (Google) + +[ Upstream commit 7e021da80f48582171029714f8a487347f29dddb ] + +Fix to unmount the tracefs if the ftracetest mounted it for recovering +system environment. If the tracefs is already mounted, this does nothing. + +Suggested-by: Mark Brown +Link: https://lore.kernel.org/all/29fce076-746c-4650-8358-b4e0fa215cf7@sirena.org.uk/ +Fixes: cbd965bde74c ("ftrace/selftests: Return the skip code when tracing directory not configured in kernel") +Signed-off-by: Masami Hiramatsu (Google) +Reviewed-by: Steven Rostedt (Google) +Reviewed-by: Mark Brown +Signed-off-by: Shuah Khan +Signed-off-by: Sasha Levin +--- + tools/testing/selftests/ftrace/ftracetest | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/tools/testing/selftests/ftrace/ftracetest b/tools/testing/selftests/ftrace/ftracetest +index cb5f18c06593d..d68264a5f3f03 100755 +--- a/tools/testing/selftests/ftrace/ftracetest ++++ b/tools/testing/selftests/ftrace/ftracetest +@@ -31,6 +31,9 @@ err_ret=1 + # kselftest skip code is 4 + err_skip=4 + ++# umount required ++UMOUNT_DIR="" ++ + # cgroup RT scheduling prevents chrt commands from succeeding, which + # induces failures in test wakeup tests. Disable for the duration of + # the tests. +@@ -45,6 +48,9 @@ setup() { + + cleanup() { + echo $sched_rt_runtime_orig > $sched_rt_runtime ++ if [ -n "${UMOUNT_DIR}" ]; then ++ umount ${UMOUNT_DIR} ||: ++ fi + } + + errexit() { # message +@@ -160,11 +166,13 @@ if [ -z "$TRACING_DIR" ]; then + mount -t tracefs nodev /sys/kernel/tracing || + errexit "Failed to mount /sys/kernel/tracing" + TRACING_DIR="/sys/kernel/tracing" ++ UMOUNT_DIR=${TRACING_DIR} + # If debugfs exists, then so does /sys/kernel/debug + elif [ -d "/sys/kernel/debug" ]; then + mount -t debugfs nodev /sys/kernel/debug || + errexit "Failed to mount /sys/kernel/debug" + TRACING_DIR="/sys/kernel/debug/tracing" ++ UMOUNT_DIR=${TRACING_DIR} + else + err_ret=$err_skip + errexit "debugfs and tracefs are not configured in this kernel" +-- +2.40.1 + diff --git a/queue-6.5/serial-cpm_uart-avoid-suspicious-locking.patch b/queue-6.5/serial-cpm_uart-avoid-suspicious-locking.patch new file mode 100644 index 00000000000..6ff43aaf121 --- /dev/null +++ b/queue-6.5/serial-cpm_uart-avoid-suspicious-locking.patch @@ -0,0 +1,80 @@ +From 272efdde02cb231ef30d291cc97c413a200381d0 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 3 Aug 2023 15:56:42 +0200 +Subject: serial: cpm_uart: Avoid suspicious locking + +From: Christophe Leroy + +[ Upstream commit 36ef11d311f405e55ad8e848c19b212ff71ef536 ] + + CHECK drivers/tty/serial/cpm_uart/cpm_uart_core.c +drivers/tty/serial/cpm_uart/cpm_uart_core.c:1271:39: warning: context imbalance in 'cpm_uart_console_write' - unexpected unlock + +Allthough 'nolock' is not expected to change, sparse find the following +form suspicious: + + if (unlikely(nolock)) { + local_irq_save(flags); + } else { + spin_lock_irqsave(&pinfo->port.lock, flags); + } + + cpm_uart_early_write(pinfo, s, count, true); + + if (unlikely(nolock)) { + local_irq_restore(flags); + } else { + spin_unlock_irqrestore(&pinfo->port.lock, flags); + } + +Rewrite it a more obvious form: + + if (unlikely(oops_in_progress)) { + local_irq_save(flags); + cpm_uart_early_write(pinfo, s, count, true); + local_irq_restore(flags); + } else { + spin_lock_irqsave(&pinfo->port.lock, flags); + cpm_uart_early_write(pinfo, s, count, true); + spin_unlock_irqrestore(&pinfo->port.lock, flags); + } + +Signed-off-by: Christophe Leroy +Link: https://lore.kernel.org/r/f7da5cdc9287960185829cfef681a7d8614efa1f.1691068700.git.christophe.leroy@csgroup.eu +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/tty/serial/cpm_uart/cpm_uart_core.c | 13 ++++--------- + 1 file changed, 4 insertions(+), 9 deletions(-) + +diff --git a/drivers/tty/serial/cpm_uart/cpm_uart_core.c b/drivers/tty/serial/cpm_uart/cpm_uart_core.c +index 66afa9bea6bfe..71366a4cea22c 100644 +--- a/drivers/tty/serial/cpm_uart/cpm_uart_core.c ++++ b/drivers/tty/serial/cpm_uart/cpm_uart_core.c +@@ -1255,19 +1255,14 @@ static void cpm_uart_console_write(struct console *co, const char *s, + { + struct uart_cpm_port *pinfo = &cpm_uart_ports[co->index]; + unsigned long flags; +- int nolock = oops_in_progress; + +- if (unlikely(nolock)) { ++ if (unlikely(oops_in_progress)) { + local_irq_save(flags); +- } else { +- spin_lock_irqsave(&pinfo->port.lock, flags); +- } +- +- cpm_uart_early_write(pinfo, s, count, true); +- +- if (unlikely(nolock)) { ++ cpm_uart_early_write(pinfo, s, count, true); + local_irq_restore(flags); + } else { ++ spin_lock_irqsave(&pinfo->port.lock, flags); ++ cpm_uart_early_write(pinfo, s, count, true); + spin_unlock_irqrestore(&pinfo->port.lock, flags); + } + } +-- +2.40.1 + diff --git a/queue-6.5/series b/queue-6.5/series new file mode 100644 index 00000000000..69e080f454a --- /dev/null +++ b/queue-6.5/series @@ -0,0 +1,166 @@ +iomap-fix-possible-overflow-condition-in-iomap_write.patch +autofs-fix-memory-leak-of-waitqueues-in-autofs_catat.patch +btrfs-handle-errors-properly-in-update_inline_extent.patch +btrfs-output-extra-debug-info-if-we-failed-to-find-a.patch +locks-fix-kasan-use-after-free-in-trace_event_raw_ev.patch +acpica-add-aml_no_operand_resolve-flag-to-timer.patch +kernel-fork-beware-of-__put_task_struct-calling-cont.patch +rcuscale-move-rcu_scale_writer-schedule_timeout_unin.patch +scftorture-forgive-memory-allocation-failure-if-kasa.patch +acpi-video-add-backlight-native-dmi-quirk-for-lenovo.patch +platform-chrome-cros_ec_lpc-remove-ec-panic-shutdown.patch +x86-amd_nb-add-pci-ids-for-amd-family-1ah-based-mode.patch +perf-smmuv3-enable-hisilicon-erratum-162001900-quirk.patch +s390-boot-cleanup-number-of-page-table-levels-setup.patch +kselftest-arm64-fix-a-memleak-in-zt_regs_run.patch +perf-imx_ddr-speed-up-overflow-frequency-of-cycle.patch +acpi-video-add-backlight-native-dmi-quirk-for-apple-.patch +hw_breakpoint-fix-single-stepping-when-using-bpf_ove.patch +acpi-x86-s2idle-catch-multiple-acpi_type_package-obj.patch +selftests-nolibc-fix-up-kernel-parameters-support.patch +selftests-nolibc-prevent-out-of-bounds-access-in-exp.patch +spi-sun6i-add-quirk-for-dual-and-quad-spi-modes-supp.patch +devlink-remove-reload-failed-checks-in-params-get-se.patch +crypto-lrw-xts-replace-strlcpy-with-strscpy.patch +net-stmmac-use-per-queue-64-bit-statistics-where-nec.patch +ice-don-t-tx-before-switchdev-is-fully-configured.patch +wifi-ath9k-fix-fortify-warnings.patch +wifi-ath9k-fix-printk-specifier.patch +wifi-rtw88-delete-timer-and-free-skb-queue-when-unlo.patch +wifi-mwifiex-fix-fortify-warning.patch +mt76-mt7921-don-t-assume-adequate-headroom-for-sdio-.patch +wifi-wil6210-fix-fortify-warnings.patch +can-sun4i_can-add-acceptance-register-quirk.patch +can-sun4i_can-add-support-for-the-allwinner-d1.patch +net-use-sockaddr_storage-for-getsockopt-so_peername.patch +wifi-ath12k-fix-a-null-pointer-dereference-in-ath12k.patch +wifi-ath12k-avoid-array-overflow-of-hw-mode-for-pref.patch +net-ipv4-return-the-real-errno-instead-of-einval.patch +crypto-lib-mpi-avoid-null-pointer-deref-in-mpi_cmp_u.patch +bluetooth-btusb-add-device-0489-e0f5-as-mt7922-devic.patch +bluetooth-btusb-add-a-new-vid-pid-0489-e0f6-for-mt79.patch +bluetooth-btusb-add-new-vid-pid-0489-e102-for-mt7922.patch +bluetooth-btusb-add-new-vid-pid-04ca-3804-for-mt7922.patch +bluetooth-fix-hci_suspend_sync-crash.patch +bluetooth-btusb-add-support-for-another-mediatek-792.patch +netlink-convert-nlk-flags-to-atomic-flags.patch +tpm_tis-resend-command-to-recover-from-data-transfer.patch +mmc-sdhci-esdhc-imx-improve-esdhc_flag_err010450.patch +alx-fix-oob-read-compiler-warning.patch +wifi-iwlwifi-pcie-avoid-a-warning-in-case-prepare-ca.patch +wifi-mac80211-check-s1g-action-frame-size.patch +netfilter-ebtables-fix-fortify-warnings-in-size_entr.patch +wifi-cfg80211-reject-auth-assoc-to-ap-with-our-addre.patch +wifi-cfg80211-ocb-don-t-leave-if-not-joined.patch +wifi-mac80211-check-for-station-first-in-client-prob.patch +wifi-mac80211_hwsim-drop-short-frames.patch +revert-wifi-mac80211_hwsim-check-the-return-value-of.patch +libbpf-free-btf_vmlinux-when-closing-bpf_object.patch +wifi-ath12k-fix-memory-leak-in-rx_desc-and-tx_desc.patch +wifi-ath12k-add-check-max-message-length-while-scann.patch +fix-nomenclature-for-usb-and-pci-wireless-devices.patch +bpf-consider-non-owning-refs-trusted.patch +bpf-consider-non-owning-refs-to-refcounted-nodes-rcu.patch +drm-bridge-tc358762-instruct-dsi-host-to-generate-hs.patch +drm-edid-add-quirk-for-osvr-hdk-2.0.patch +drm-bridge-samsung-dsim-drain-command-transfer-fifo-.patch +arm64-dts-qcom-sm6125-pdx201-correct-ramoops-pmsg-si.patch +arm64-dts-qcom-sm6125-sprout-correct-ramoops-pmsg-si.patch +arm64-dts-qcom-sm6350-correct-ramoops-pmsg-size.patch +arm64-dts-qcom-sm8150-kumano-correct-ramoops-pmsg-si.patch +arm64-dts-qcom-sm8250-edo-correct-ramoops-pmsg-size.patch +drm-amdgpu-increase-soft-ih-ring-size.patch +drm-amd-display-add-stream-overhead-in-bw-calculatio.patch +samples-hw_breakpoint-fix-kernel-bug-invalid-opcode-.patch +drm-amdgpu-update-ring-scheduler-info-as-needed.patch +drm-amd-display-fix-underflow-issue-on-175hz-timing.patch +asoc-sof-topology-simplify-code-to-prevent-static-an.patch +asoc-intel-sof_sdw-update-bt-offload-config-for-soun.patch +alsa-hda-intel-dsp-cfg-add-lunarlake-support.patch +drm-amd-display-use-dtbclk-as-refclk-instead-of-dpre.patch +drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch +drm-amd-display-blocking-invalid-420-modes-on-hdmi-t.patch-12335 +drm-amd-display-use-max-memclk-variable-when-setting.patch +drm-msm-adreno-use-quirk-identify-hw_apriv.patch +drm-msm-adreno-use-quirk-to-identify-cached-coherent.patch +drm-exynos-fix-a-possible-null-pointer-dereference-d.patch +io_uring-annotate-the-struct-io_kiocb-slab-for-appro.patch +drm-mediatek-dp-change-logging-to-dev-for-mtk_dp_aux.patch +bus-ti-sysc-configure-uart-quirks-for-k3-soc.patch +arm64-dts-qcom-sc8280xp-x13s-add-camera-activity-led.patch +md-raid1-fix-potential-oob-in-raid1_remove_disk.patch +ext2-fix-datatype-of-block-number-in-ext2_xattr_set2.patch +blk-mq-fix-tags-leak-when-shrink-nr_hw_queues.patch +asoc-sof-amd-clear-panic-mask-status-when-panic-occu.patch +x86-bring-back-rep-movsq-for-user-access-on-cpus-wit.patch +fs-jfs-prevent-double-free-in-dbunmount-after-failed.patch +jfs-fix-invalid-free-of-jfs_ip-ipimap-i_imap-in-diun.patch +ext4-add-two-helper-functions-extent_logical_end-and.patch +ext4-avoid-overlapping-preallocations-due-to-overflo.patch +pci-dwc-provide-deinit-callback-for-i.mx.patch +arm-9317-1-kexec-make-smp-stop-calls-asynchronous.patch +powerpc-pseries-fix-possible-memory-leak-in-ibmebus_.patch +pci-vmd-disable-bridge-window-for-domain-reset.patch +pci-fu740-set-the-number-of-msi-vectors.patch +media-mdp3-fix-resource-leaks-in-of_find_device_by_n.patch +media-dvb-usb-v2-af9035-fix-null-ptr-deref-in-af9035.patch +media-dw2102-fix-null-ptr-deref-in-dw2102_i2c_transf.patch +media-af9005-fix-null-ptr-deref-in-af9005_i2c_xfer.patch +media-anysee-fix-null-ptr-deref-in-anysee_master_xfe.patch +media-az6007-fix-null-ptr-deref-in-az6007_i2c_xfer.patch +media-dvb-usb-v2-gl861-fix-null-ptr-deref-in-gl861_i.patch +scsi-lpfc-abort-outstanding-els-cmds-when-mailbox-ti.patch +media-tuners-qt1010-replace-bug_on-with-a-regular-er.patch +media-pci-cx23885-replace-bug-with-error-return.patch +usb-cdns3-put-the-cdns-set-active-part-outside-the-s.patch +usb-typec-intel_pmc_mux-add-new-acpi-id-for-lunar-la.patch +usb-gadget-fsl_qe_udc-validate-endpoint-index-for-ch.patch +tools-iio-iio_generic_buffer-fix-some-integer-type-a.patch +scsi-target-iscsi-fix-buffer-overflow-in-lio_target_.patch +serial-cpm_uart-avoid-suspicious-locking.patch +misc-open-dice-make-open_dice-depend-on-has_iomem.patch +usb-dwc3-dwc3-octeon-verify-clock-divider.patch +usb-ehci-add-workaround-for-chipidea-portsc.pec-bug.patch +usb-chipidea-add-workaround-for-chipidea-pec-bug.patch +media-pci-ipu3-cio2-initialise-timing-struct-to-avoi.patch +kobject-add-sanity-check-for-kset-kobj.ktype-in-kset.patch +interconnect-fix-locking-for-runpm-vs-reclaim.patch +usb-typec-qcom-pmic-typec-register-drm_bridge.patch +printk-reduce-console_unblank-usage-in-unsafe-scenar.patch +printk-keep-non-panic-cpus-out-of-console-lock.patch +printk-do-not-take-console-lock-for-console_flush_on.patch +printk-consolidate-console-deferred-printing.patch +printk-rename-abandon_console_lock_in_panic-to-other.patch +ext4-fix-bug-in-ext4_mb_new_inode_pa-due-to-overflow.patch +btrfs-introduce-struct-to-consolidate-extent-buffer-.patch +btrfs-zoned-introduce-block-group-context-to-btrfs_e.patch +btrfs-zoned-return-int-from-btrfs_check_meta_write_p.patch +btrfs-zoned-defer-advancing-meta-write-pointer.patch +btrfs-zoned-activate-metadata-block-group-on-write-t.patch +mtd-spi-nor-spansion-use-clpef-as-an-alternative-to-.patch +mtd-spi-nor-spansion-preserve-cfr2v-7-when-writing-m.patch +btrfs-add-a-helper-to-read-the-superblock-metadata_u.patch +btrfs-compare-the-correct-fsid-metadata_uuid-in-btrf.patch +nvmet-tcp-pass-iov_len-instead-of-sg-length-to-bvec_.patch +drm-gm12u320-fix-the-timeout-usage-for-usb_bulk_msg.patch +scsi-qla2xxx-fix-null-vs-is_err-bug-for-debugfs_crea.patch +md-don-t-dereference-mddev-after-export_rdev.patch +md-fix-warning-for-holder-mismatch-from-export_rdev.patch +efi-unaccepted-use-acpi-reclaim-memory-for-unaccepte.patch +efivarfs-fix-statfs-on-efivarfs.patch +pm-hibernate-fix-the-exclusive-get-block-device-in-t.patch +selftests-tracing-fix-to-unmount-tracefs-for-recover.patch +x86-ibt-suppress-spurious-endbr.patch +x86-ibt-avoid-duplicate-endbr-in-__put_user_nocheck.patch +riscv-kexec-align-the-kexeced-kernel-entry.patch +x86-sched-restore-the-sd_asym_packing-flag-in-the-di.patch +scsi-target-core-fix-target_cmd_counter-leak.patch +scsi-lpfc-fix-the-null-vs-is_err-bug-for-debugfs_cre.patch +panic-reenable-preemption-in-warn-slowpath.patch +ata-libata-remove-references-to-non-existing-error_h.patch +ata-libata-core-fetch-sense-data-for-successful-comm.patch +x86-boot-compressed-reserve-more-memory-for-page-tab.patch +x86-purgatory-remove-lto-flags.patch +samples-hw_breakpoint-fix-building-without-module-un.patch +blk-mq-fix-tags-uaf-when-shrinking-q-nr_hw_queues.patch +md-raid1-fix-error-iso-c90-forbids-mixed-declaration.patch diff --git a/queue-6.5/spi-sun6i-add-quirk-for-dual-and-quad-spi-modes-supp.patch b/queue-6.5/spi-sun6i-add-quirk-for-dual-and-quad-spi-modes-supp.patch new file mode 100644 index 00000000000..7281cdf30d2 --- /dev/null +++ b/queue-6.5/spi-sun6i-add-quirk-for-dual-and-quad-spi-modes-supp.patch @@ -0,0 +1,98 @@ +From 4644734b897324ef4c9a73b90d83c4b9b41b33bb Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 24 Jun 2023 16:16:22 +0300 +Subject: spi: sun6i: add quirk for dual and quad SPI modes support + +From: Maksim Kiselev + +[ Upstream commit 0605d9fb411f3337482976842a3901d6c125d298 ] + +New Allwinner's SPI controllers can support dual and quad SPI modes. +To enable one of these modes, we should set the corresponding bit in +the SUN6I_BURST_CTL_CNT_REG register. DRM (28 bits) for dual mode and +Quad_EN (29 bits) for quad transmission. + +Signed-off-by: Maksim Kiselev +Link: https://lore.kernel.org/r/20230624131632.2972546-2-bigunclemax@gmail.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + drivers/spi/spi-sun6i.c | 29 +++++++++++++++++++++++++---- + 1 file changed, 25 insertions(+), 4 deletions(-) + +diff --git a/drivers/spi/spi-sun6i.c b/drivers/spi/spi-sun6i.c +index 30d541612253e..cec2747235abf 100644 +--- a/drivers/spi/spi-sun6i.c ++++ b/drivers/spi/spi-sun6i.c +@@ -83,6 +83,9 @@ + #define SUN6I_XMIT_CNT_REG 0x34 + + #define SUN6I_BURST_CTL_CNT_REG 0x38 ++#define SUN6I_BURST_CTL_CNT_STC_MASK GENMASK(23, 0) ++#define SUN6I_BURST_CTL_CNT_DRM BIT(28) ++#define SUN6I_BURST_CTL_CNT_QUAD_EN BIT(29) + + #define SUN6I_TXDATA_REG 0x200 + #define SUN6I_RXDATA_REG 0x300 +@@ -90,6 +93,7 @@ + struct sun6i_spi_cfg { + unsigned long fifo_depth; + bool has_clk_ctl; ++ u32 mode_bits; + }; + + struct sun6i_spi { +@@ -266,7 +270,7 @@ static int sun6i_spi_transfer_one(struct spi_master *master, + unsigned int div, div_cdr1, div_cdr2, timeout; + unsigned int start, end, tx_time; + unsigned int trig_level; +- unsigned int tx_len = 0, rx_len = 0; ++ unsigned int tx_len = 0, rx_len = 0, nbits = 0; + bool use_dma; + int ret = 0; + u32 reg; +@@ -418,13 +422,29 @@ static int sun6i_spi_transfer_one(struct spi_master *master, + sun6i_spi_write(sspi, SUN6I_GBL_CTL_REG, reg); + + /* Setup the transfer now... */ +- if (sspi->tx_buf) ++ if (sspi->tx_buf) { + tx_len = tfr->len; ++ nbits = tfr->tx_nbits; ++ } else if (tfr->rx_buf) { ++ nbits = tfr->rx_nbits; ++ } ++ ++ switch (nbits) { ++ case SPI_NBITS_DUAL: ++ reg = SUN6I_BURST_CTL_CNT_DRM; ++ break; ++ case SPI_NBITS_QUAD: ++ reg = SUN6I_BURST_CTL_CNT_QUAD_EN; ++ break; ++ case SPI_NBITS_SINGLE: ++ default: ++ reg = FIELD_PREP(SUN6I_BURST_CTL_CNT_STC_MASK, tx_len); ++ } + + /* Setup the counters */ ++ sun6i_spi_write(sspi, SUN6I_BURST_CTL_CNT_REG, reg); + sun6i_spi_write(sspi, SUN6I_BURST_CNT_REG, tfr->len); + sun6i_spi_write(sspi, SUN6I_XMIT_CNT_REG, tx_len); +- sun6i_spi_write(sspi, SUN6I_BURST_CTL_CNT_REG, tx_len); + + if (!use_dma) { + /* Fill the TX FIFO */ +@@ -623,7 +643,8 @@ static int sun6i_spi_probe(struct platform_device *pdev) + master->set_cs = sun6i_spi_set_cs; + master->transfer_one = sun6i_spi_transfer_one; + master->num_chipselect = 4; +- master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_CS_HIGH | SPI_LSB_FIRST; ++ master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_CS_HIGH | SPI_LSB_FIRST | ++ sspi->cfg->mode_bits; + master->bits_per_word_mask = SPI_BPW_MASK(8); + master->dev.of_node = pdev->dev.of_node; + master->auto_runtime_pm = true; +-- +2.40.1 + diff --git a/queue-6.5/tools-iio-iio_generic_buffer-fix-some-integer-type-a.patch b/queue-6.5/tools-iio-iio_generic_buffer-fix-some-integer-type-a.patch new file mode 100644 index 00000000000..c75b829b744 --- /dev/null +++ b/queue-6.5/tools-iio-iio_generic_buffer-fix-some-integer-type-a.patch @@ -0,0 +1,73 @@ +From ee6d5c7e36ccb6bc23f4381b41a21d933504bc3b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 25 Jul 2023 09:24:07 +0000 +Subject: tools: iio: iio_generic_buffer: Fix some integer type and calculation + +From: Chenyuan Mi + +[ Upstream commit 49d736313d0975ddeb156f4f59801da833f78b30 ] + +In function size_from_channelarray(), the return value 'bytes' is defined +as int type. However, the calcution of 'bytes' in this function is designed +to use the unsigned int type. So it is necessary to change 'bytes' type to +unsigned int to avoid integer overflow. + +The size_from_channelarray() is called in main() function, its return value +is directly multipled by 'buf_len' and then used as the malloc() parameter. +The 'buf_len' is completely controllable by user, thus a multiplication +overflow may occur here. This could allocate an unexpected small area. + +Signed-off-by: Chenyuan Mi +Link: https://lore.kernel.org/r/20230725092407.62545-1-michenyuan@huawei.com +Signed-off-by: Jonathan Cameron +Signed-off-by: Sasha Levin +--- + tools/iio/iio_generic_buffer.c | 17 +++++++++++++---- + 1 file changed, 13 insertions(+), 4 deletions(-) + +diff --git a/tools/iio/iio_generic_buffer.c b/tools/iio/iio_generic_buffer.c +index f8deae4e26a15..44bbf80f0cfdd 100644 +--- a/tools/iio/iio_generic_buffer.c ++++ b/tools/iio/iio_generic_buffer.c +@@ -51,9 +51,9 @@ enum autochan { + * Has the side effect of filling the channels[i].location values used + * in processing the buffer output. + **/ +-static int size_from_channelarray(struct iio_channel_info *channels, int num_channels) ++static unsigned int size_from_channelarray(struct iio_channel_info *channels, int num_channels) + { +- int bytes = 0; ++ unsigned int bytes = 0; + int i = 0; + + while (i < num_channels) { +@@ -348,7 +348,7 @@ int main(int argc, char **argv) + ssize_t read_size; + int dev_num = -1, trig_num = -1; + char *buffer_access = NULL; +- int scan_size; ++ unsigned int scan_size; + int noevents = 0; + int notrigger = 0; + char *dummy; +@@ -674,7 +674,16 @@ int main(int argc, char **argv) + } + + scan_size = size_from_channelarray(channels, num_channels); +- data = malloc(scan_size * buf_len); ++ ++ size_t total_buf_len = scan_size * buf_len; ++ ++ if (scan_size > 0 && total_buf_len / scan_size != buf_len) { ++ ret = -EFAULT; ++ perror("Integer overflow happened when calculate scan_size * buf_len"); ++ goto error; ++ } ++ ++ data = malloc(total_buf_len); + if (!data) { + ret = -ENOMEM; + goto error; +-- +2.40.1 + diff --git a/queue-6.5/tpm_tis-resend-command-to-recover-from-data-transfer.patch b/queue-6.5/tpm_tis-resend-command-to-recover-from-data-transfer.patch new file mode 100644 index 00000000000..8c900fe255e --- /dev/null +++ b/queue-6.5/tpm_tis-resend-command-to-recover-from-data-transfer.patch @@ -0,0 +1,49 @@ +From 08b9f8fe19af7f3a6cc7d0d930745a8918bcca90 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 13 Jun 2023 20:02:59 +0200 +Subject: tpm_tis: Resend command to recover from data transfer errors + +From: Alexander Steffen + +[ Upstream commit 280db21e153d8810ce3b93640c63ae922bcb9e8e ] + +Similar to the transmission of TPM responses, also the transmission of TPM +commands may become corrupted. Instead of aborting when detecting such +issues, try resending the command again. + +Signed-off-by: Alexander Steffen +Reviewed-by: Jarkko Sakkinen +Signed-off-by: Jarkko Sakkinen +Signed-off-by: Sasha Levin +--- + drivers/char/tpm/tpm_tis_core.c | 13 ++++++++++--- + 1 file changed, 10 insertions(+), 3 deletions(-) + +diff --git a/drivers/char/tpm/tpm_tis_core.c b/drivers/char/tpm/tpm_tis_core.c +index b95963095729a..f4c4c027b062d 100644 +--- a/drivers/char/tpm/tpm_tis_core.c ++++ b/drivers/char/tpm/tpm_tis_core.c +@@ -512,10 +512,17 @@ static int tpm_tis_send_main(struct tpm_chip *chip, const u8 *buf, size_t len) + int rc; + u32 ordinal; + unsigned long dur; ++ unsigned int try; + +- rc = tpm_tis_send_data(chip, buf, len); +- if (rc < 0) +- return rc; ++ for (try = 0; try < TPM_RETRY; try++) { ++ rc = tpm_tis_send_data(chip, buf, len); ++ if (rc >= 0) ++ /* Data transfer done successfully */ ++ break; ++ else if (rc != -EIO) ++ /* Data transfer failed, not recoverable */ ++ return rc; ++ } + + rc = tpm_tis_verify_crc(priv, len, buf); + if (rc < 0) { +-- +2.40.1 + diff --git a/queue-6.5/usb-cdns3-put-the-cdns-set-active-part-outside-the-s.patch b/queue-6.5/usb-cdns3-put-the-cdns-set-active-part-outside-the-s.patch new file mode 100644 index 00000000000..e377a78508e --- /dev/null +++ b/queue-6.5/usb-cdns3-put-the-cdns-set-active-part-outside-the-s.patch @@ -0,0 +1,143 @@ +From 7530cd38b37f333d155564308e174038f9b91e1e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 16 Jun 2023 10:19:51 +0800 +Subject: usb: cdns3: Put the cdns set active part outside the spin lock + +From: Xiaolei Wang + +[ Upstream commit 2319b9c87fe243327285f2fefd7374ffd75a65fc ] + +The device may be scheduled during the resume process, +so this cannot appear in atomic operations. Since +pm_runtime_set_active will resume suppliers, put set +active outside the spin lock, which is only used to +protect the struct cdns data structure, otherwise the +kernel will report the following warning: + + BUG: sleeping function called from invalid context at drivers/base/power/runtime.c:1163 + in_atomic(): 1, irqs_disabled(): 0, non_block: 0, pid: 651, name: sh + preempt_count: 1, expected: 0 + RCU nest depth: 0, expected: 0 + CPU: 0 PID: 651 Comm: sh Tainted: G WC 6.1.20 #1 + Hardware name: Freescale i.MX8QM MEK (DT) + Call trace: + dump_backtrace.part.0+0xe0/0xf0 + show_stack+0x18/0x30 + dump_stack_lvl+0x64/0x80 + dump_stack+0x1c/0x38 + __might_resched+0x1fc/0x240 + __might_sleep+0x68/0xc0 + __pm_runtime_resume+0x9c/0xe0 + rpm_get_suppliers+0x68/0x1b0 + __pm_runtime_set_status+0x298/0x560 + cdns_resume+0xb0/0x1c0 + cdns3_controller_resume.isra.0+0x1e0/0x250 + cdns3_plat_resume+0x28/0x40 + +Signed-off-by: Xiaolei Wang +Acked-by: Peter Chen +Link: https://lore.kernel.org/r/20230616021952.1025854-1-xiaolei.wang@windriver.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/usb/cdns3/cdns3-plat.c | 3 ++- + drivers/usb/cdns3/cdnsp-pci.c | 3 ++- + drivers/usb/cdns3/core.c | 15 +++++++++++---- + drivers/usb/cdns3/core.h | 7 +++++-- + 4 files changed, 20 insertions(+), 8 deletions(-) + +diff --git a/drivers/usb/cdns3/cdns3-plat.c b/drivers/usb/cdns3/cdns3-plat.c +index 884e2301237f4..1168dbeed2ce0 100644 +--- a/drivers/usb/cdns3/cdns3-plat.c ++++ b/drivers/usb/cdns3/cdns3-plat.c +@@ -255,9 +255,10 @@ static int cdns3_controller_resume(struct device *dev, pm_message_t msg) + cdns3_set_platform_suspend(cdns->dev, false, false); + + spin_lock_irqsave(&cdns->lock, flags); +- cdns_resume(cdns, !PMSG_IS_AUTO(msg)); ++ cdns_resume(cdns); + cdns->in_lpm = false; + spin_unlock_irqrestore(&cdns->lock, flags); ++ cdns_set_active(cdns, !PMSG_IS_AUTO(msg)); + if (cdns->wakeup_pending) { + cdns->wakeup_pending = false; + enable_irq(cdns->wakeup_irq); +diff --git a/drivers/usb/cdns3/cdnsp-pci.c b/drivers/usb/cdns3/cdnsp-pci.c +index 7b151f5af3ccb..0725668ffea4c 100644 +--- a/drivers/usb/cdns3/cdnsp-pci.c ++++ b/drivers/usb/cdns3/cdnsp-pci.c +@@ -208,8 +208,9 @@ static int __maybe_unused cdnsp_pci_resume(struct device *dev) + int ret; + + spin_lock_irqsave(&cdns->lock, flags); +- ret = cdns_resume(cdns, 1); ++ ret = cdns_resume(cdns); + spin_unlock_irqrestore(&cdns->lock, flags); ++ cdns_set_active(cdns, 1); + + return ret; + } +diff --git a/drivers/usb/cdns3/core.c b/drivers/usb/cdns3/core.c +index dbcdf3b24b477..7b20d2d5c262e 100644 +--- a/drivers/usb/cdns3/core.c ++++ b/drivers/usb/cdns3/core.c +@@ -522,9 +522,8 @@ int cdns_suspend(struct cdns *cdns) + } + EXPORT_SYMBOL_GPL(cdns_suspend); + +-int cdns_resume(struct cdns *cdns, u8 set_active) ++int cdns_resume(struct cdns *cdns) + { +- struct device *dev = cdns->dev; + enum usb_role real_role; + bool role_changed = false; + int ret = 0; +@@ -556,15 +555,23 @@ int cdns_resume(struct cdns *cdns, u8 set_active) + if (cdns->roles[cdns->role]->resume) + cdns->roles[cdns->role]->resume(cdns, cdns_power_is_lost(cdns)); + ++ return 0; ++} ++EXPORT_SYMBOL_GPL(cdns_resume); ++ ++void cdns_set_active(struct cdns *cdns, u8 set_active) ++{ ++ struct device *dev = cdns->dev; ++ + if (set_active) { + pm_runtime_disable(dev); + pm_runtime_set_active(dev); + pm_runtime_enable(dev); + } + +- return 0; ++ return; + } +-EXPORT_SYMBOL_GPL(cdns_resume); ++EXPORT_SYMBOL_GPL(cdns_set_active); + #endif /* CONFIG_PM_SLEEP */ + + MODULE_AUTHOR("Peter Chen "); +diff --git a/drivers/usb/cdns3/core.h b/drivers/usb/cdns3/core.h +index 2d332a788871e..4a4dbc2c15615 100644 +--- a/drivers/usb/cdns3/core.h ++++ b/drivers/usb/cdns3/core.h +@@ -125,10 +125,13 @@ int cdns_init(struct cdns *cdns); + int cdns_remove(struct cdns *cdns); + + #ifdef CONFIG_PM_SLEEP +-int cdns_resume(struct cdns *cdns, u8 set_active); ++int cdns_resume(struct cdns *cdns); + int cdns_suspend(struct cdns *cdns); ++void cdns_set_active(struct cdns *cdns, u8 set_active); + #else /* CONFIG_PM_SLEEP */ +-static inline int cdns_resume(struct cdns *cdns, u8 set_active) ++static inline int cdns_resume(struct cdns *cdns) ++{ return 0; } ++static inline int cdns_set_active(struct cdns *cdns, u8 set_active) + { return 0; } + static inline int cdns_suspend(struct cdns *cdns) + { return 0; } +-- +2.40.1 + diff --git a/queue-6.5/usb-chipidea-add-workaround-for-chipidea-pec-bug.patch b/queue-6.5/usb-chipidea-add-workaround-for-chipidea-pec-bug.patch new file mode 100644 index 00000000000..33e270ffa1b --- /dev/null +++ b/queue-6.5/usb-chipidea-add-workaround-for-chipidea-pec-bug.patch @@ -0,0 +1,106 @@ +From fd22c29a6aceaa005f02937a140584046887c4c0 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 9 Aug 2023 10:44:32 +0800 +Subject: usb: chipidea: add workaround for chipidea PEC bug + +From: Xu Yang + +[ Upstream commit 12e6ac69cc7e7d3367599ae26a92a0f9a18bc728 ] + +Some NXP processors using ChipIdea USB IP have a bug when frame babble is +detected. + +Issue description: +In USB camera test, our controller is host in HS mode. In ISOC IN, when +device sends data across the micro frame, it causes the babble in host +controller. This will clear the PE bit. In spec, it also requires to set +the PEC bit and then set the PCI bit. Without the PCI interrupt, the +software does not know the PE is cleared. + +This will add a flag CI_HDRC_HAS_PORTSC_PEC_MISSED to some impacted +platform datas. And the ehci host driver will assert PEC by SW when +specific conditions are satisfied. + +Signed-off-by: Xu Yang +Link: https://lore.kernel.org/r/20230809024432.535160-2-xu.yang_2@nxp.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/usb/chipidea/ci.h | 1 + + drivers/usb/chipidea/ci_hdrc_imx.c | 4 +++- + drivers/usb/chipidea/core.c | 2 ++ + drivers/usb/chipidea/host.c | 1 + + include/linux/usb/chipidea.h | 1 + + 5 files changed, 8 insertions(+), 1 deletion(-) + +diff --git a/drivers/usb/chipidea/ci.h b/drivers/usb/chipidea/ci.h +index f210b7489fd5b..78cfbe621272c 100644 +--- a/drivers/usb/chipidea/ci.h ++++ b/drivers/usb/chipidea/ci.h +@@ -257,6 +257,7 @@ struct ci_hdrc { + bool id_event; + bool b_sess_valid_event; + bool imx28_write_fix; ++ bool has_portsc_pec_bug; + bool supports_runtime_pm; + bool in_lpm; + bool wakeup_int; +diff --git a/drivers/usb/chipidea/ci_hdrc_imx.c b/drivers/usb/chipidea/ci_hdrc_imx.c +index 873539f9a2c0a..a96d8af935382 100644 +--- a/drivers/usb/chipidea/ci_hdrc_imx.c ++++ b/drivers/usb/chipidea/ci_hdrc_imx.c +@@ -67,11 +67,13 @@ static const struct ci_hdrc_imx_platform_flag imx7d_usb_data = { + + static const struct ci_hdrc_imx_platform_flag imx7ulp_usb_data = { + .flags = CI_HDRC_SUPPORTS_RUNTIME_PM | ++ CI_HDRC_HAS_PORTSC_PEC_MISSED | + CI_HDRC_PMQOS, + }; + + static const struct ci_hdrc_imx_platform_flag imx8ulp_usb_data = { +- .flags = CI_HDRC_SUPPORTS_RUNTIME_PM, ++ .flags = CI_HDRC_SUPPORTS_RUNTIME_PM | ++ CI_HDRC_HAS_PORTSC_PEC_MISSED, + }; + + static const struct of_device_id ci_hdrc_imx_dt_ids[] = { +diff --git a/drivers/usb/chipidea/core.c b/drivers/usb/chipidea/core.c +index 51994d655b821..500286a4576b5 100644 +--- a/drivers/usb/chipidea/core.c ++++ b/drivers/usb/chipidea/core.c +@@ -1045,6 +1045,8 @@ static int ci_hdrc_probe(struct platform_device *pdev) + CI_HDRC_IMX28_WRITE_FIX); + ci->supports_runtime_pm = !!(ci->platdata->flags & + CI_HDRC_SUPPORTS_RUNTIME_PM); ++ ci->has_portsc_pec_bug = !!(ci->platdata->flags & ++ CI_HDRC_HAS_PORTSC_PEC_MISSED); + platform_set_drvdata(pdev, ci); + + ret = hw_device_init(ci, base); +diff --git a/drivers/usb/chipidea/host.c b/drivers/usb/chipidea/host.c +index ebe7400243b12..08af26b762a2d 100644 +--- a/drivers/usb/chipidea/host.c ++++ b/drivers/usb/chipidea/host.c +@@ -151,6 +151,7 @@ static int host_start(struct ci_hdrc *ci) + ehci->has_hostpc = ci->hw_bank.lpm; + ehci->has_tdi_phy_lpm = ci->hw_bank.lpm; + ehci->imx28_write_fix = ci->imx28_write_fix; ++ ehci->has_ci_pec_bug = ci->has_portsc_pec_bug; + + priv = (struct ehci_ci_priv *)ehci->priv; + priv->reg_vbus = NULL; +diff --git a/include/linux/usb/chipidea.h b/include/linux/usb/chipidea.h +index ee38835ed77cc..0b4f2d5faa080 100644 +--- a/include/linux/usb/chipidea.h ++++ b/include/linux/usb/chipidea.h +@@ -63,6 +63,7 @@ struct ci_hdrc_platform_data { + #define CI_HDRC_IMX_IS_HSIC BIT(14) + #define CI_HDRC_PMQOS BIT(15) + #define CI_HDRC_PHY_VBUS_CONTROL BIT(16) ++#define CI_HDRC_HAS_PORTSC_PEC_MISSED BIT(17) + enum usb_dr_mode dr_mode; + #define CI_HDRC_CONTROLLER_RESET_EVENT 0 + #define CI_HDRC_CONTROLLER_STOPPED_EVENT 1 +-- +2.40.1 + diff --git a/queue-6.5/usb-dwc3-dwc3-octeon-verify-clock-divider.patch b/queue-6.5/usb-dwc3-dwc3-octeon-verify-clock-divider.patch new file mode 100644 index 00000000000..0ccf5945171 --- /dev/null +++ b/queue-6.5/usb-dwc3-dwc3-octeon-verify-clock-divider.patch @@ -0,0 +1,57 @@ +From c151f6712e0b82f9f120a8da356633024f4459e0 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 11:37:50 +0200 +Subject: usb: dwc3: dwc3-octeon: Verify clock divider + +From: Ladislav Michl + +[ Upstream commit fb57f829beefd4b3746f1b23d51e80ed5d4bb87b ] + +Although valid USB clock divider will be calculated for all valid +Octeon core frequencies, make code formally correct limiting +divider not to be greater that 7 so it fits into H_CLKDIV_SEL +field. + +Signed-off-by: Ladislav Michl +Reported-by: Linux Kernel Functional Testing +Closes: https://qa-reports.linaro.org/lkft/linux-next-master/build/next-20230808/testrun/18882876/suite/build/test/gcc-8-cavium_octeon_defconfig/log +Acked-by: Thinh Nguyen +Link: https://lore.kernel.org/r/ZNIM7tlBNdHFzXZG@lenoch +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + arch/mips/cavium-octeon/octeon-usb.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +diff --git a/arch/mips/cavium-octeon/octeon-usb.c b/arch/mips/cavium-octeon/octeon-usb.c +index 2add435ad0387..165e032d08647 100644 +--- a/arch/mips/cavium-octeon/octeon-usb.c ++++ b/arch/mips/cavium-octeon/octeon-usb.c +@@ -243,11 +243,11 @@ static int dwc3_octeon_get_divider(void) + while (div < ARRAY_SIZE(clk_div)) { + uint64_t rate = octeon_get_io_clock_rate() / clk_div[div]; + if (rate <= 300000000 && rate >= 150000000) +- break; ++ return div; + div++; + } + +- return div; ++ return -EINVAL; + } + + static int dwc3_octeon_config_power(struct device *dev, void __iomem *base) +@@ -374,6 +374,10 @@ static int dwc3_octeon_clocks_start(struct device *dev, void __iomem *base) + + /* Step 4b: Select controller clock frequency. */ + div = dwc3_octeon_get_divider(); ++ if (div < 0) { ++ dev_err(dev, "clock divider invalid\n"); ++ return div; ++ } + val = dwc3_octeon_readq(uctl_ctl_reg); + val &= ~USBDRD_UCTL_CTL_H_CLKDIV_SEL; + val |= FIELD_PREP(USBDRD_UCTL_CTL_H_CLKDIV_SEL, div); +-- +2.40.1 + diff --git a/queue-6.5/usb-ehci-add-workaround-for-chipidea-portsc.pec-bug.patch b/queue-6.5/usb-ehci-add-workaround-for-chipidea-portsc.pec-bug.patch new file mode 100644 index 00000000000..f0889bcfdf1 --- /dev/null +++ b/queue-6.5/usb-ehci-add-workaround-for-chipidea-portsc.pec-bug.patch @@ -0,0 +1,119 @@ +From db01f2024c550498aea86c5d5948d105331e151d Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 9 Aug 2023 10:44:31 +0800 +Subject: usb: ehci: add workaround for chipidea PORTSC.PEC bug + +From: Xu Yang + +[ Upstream commit dda4b60ed70bd670eefda081f70c0cb20bbeb1fa ] + +Some NXP processor using chipidea IP has a bug when frame babble is +detected. + +As per 4.15.1.1.1 Serial Bus Babble: + A babble condition also exists if IN transaction is in progress at +High-speed SOF2 point. This is called frame babble. The host controller +must disable the port to which the frame babble is detected. + +The USB controller has disabled the port (PE cleared) and has asserted +USBERRINT when frame babble is detected, but PEC is not asserted. +Therefore, the SW isn't aware that port has been disabled. Then the +SW keeps sending packets to this port, but all of the transfers will +fail. + +This workaround will firstly assert PCD by SW when USBERRINT is detected +and then judge whether port change has really occurred or not by polling +roothub status. Because the PEC doesn't get asserted in our case, this +patch will also assert it by SW when specific conditions are satisfied. + +Signed-off-by: Xu Yang +Acked-by: Peter Chen +Link: https://lore.kernel.org/r/20230809024432.535160-1-xu.yang_2@nxp.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/usb/host/ehci-hcd.c | 8 ++++++-- + drivers/usb/host/ehci-hub.c | 10 +++++++++- + drivers/usb/host/ehci.h | 10 ++++++++++ + 3 files changed, 25 insertions(+), 3 deletions(-) + +diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c +index a1930db0da1c3..802bfafb1012b 100644 +--- a/drivers/usb/host/ehci-hcd.c ++++ b/drivers/usb/host/ehci-hcd.c +@@ -755,10 +755,14 @@ static irqreturn_t ehci_irq (struct usb_hcd *hcd) + + /* normal [4.15.1.2] or error [4.15.1.1] completion */ + if (likely ((status & (STS_INT|STS_ERR)) != 0)) { +- if (likely ((status & STS_ERR) == 0)) ++ if (likely ((status & STS_ERR) == 0)) { + INCR(ehci->stats.normal); +- else ++ } else { ++ /* Force to check port status */ ++ if (ehci->has_ci_pec_bug) ++ status |= STS_PCD; + INCR(ehci->stats.error); ++ } + bh = 1; + } + +diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c +index efe30e3be22f7..1aee392e84927 100644 +--- a/drivers/usb/host/ehci-hub.c ++++ b/drivers/usb/host/ehci-hub.c +@@ -674,7 +674,8 @@ ehci_hub_status_data (struct usb_hcd *hcd, char *buf) + + if ((temp & mask) != 0 || test_bit(i, &ehci->port_c_suspend) + || (ehci->reset_done[i] && time_after_eq( +- jiffies, ehci->reset_done[i]))) { ++ jiffies, ehci->reset_done[i])) ++ || ehci_has_ci_pec_bug(ehci, temp)) { + if (i < 7) + buf [0] |= 1 << (i + 1); + else +@@ -875,6 +876,13 @@ int ehci_hub_control( + if (temp & PORT_PEC) + status |= USB_PORT_STAT_C_ENABLE << 16; + ++ if (ehci_has_ci_pec_bug(ehci, temp)) { ++ status |= USB_PORT_STAT_C_ENABLE << 16; ++ ehci_info(ehci, ++ "PE is cleared by HW port:%d PORTSC:%08x\n", ++ wIndex + 1, temp); ++ } ++ + if ((temp & PORT_OCC) && (!ignore_oc && !ehci->spurious_oc)){ + status |= USB_PORT_STAT_C_OVERCURRENT << 16; + +diff --git a/drivers/usb/host/ehci.h b/drivers/usb/host/ehci.h +index c5c7f87825493..1441e34007961 100644 +--- a/drivers/usb/host/ehci.h ++++ b/drivers/usb/host/ehci.h +@@ -207,6 +207,7 @@ struct ehci_hcd { /* one per controller */ + unsigned has_fsl_port_bug:1; /* FreeScale */ + unsigned has_fsl_hs_errata:1; /* Freescale HS quirk */ + unsigned has_fsl_susp_errata:1; /* NXP SUSP quirk */ ++ unsigned has_ci_pec_bug:1; /* ChipIdea PEC bug */ + unsigned big_endian_mmio:1; + unsigned big_endian_desc:1; + unsigned big_endian_capbase:1; +@@ -707,6 +708,15 @@ ehci_port_speed(struct ehci_hcd *ehci, unsigned int portsc) + */ + #define ehci_has_fsl_susp_errata(e) ((e)->has_fsl_susp_errata) + ++/* ++ * Some Freescale/NXP processors using ChipIdea IP have a bug in which ++ * disabling the port (PE is cleared) does not cause PEC to be asserted ++ * when frame babble is detected. ++ */ ++#define ehci_has_ci_pec_bug(e, portsc) \ ++ ((e)->has_ci_pec_bug && ((e)->command & CMD_PSE) \ ++ && !(portsc & PORT_PEC) && !(portsc & PORT_PE)) ++ + /* + * While most USB host controllers implement their registers in + * little-endian format, a minority (celleb companion chip) implement +-- +2.40.1 + diff --git a/queue-6.5/usb-gadget-fsl_qe_udc-validate-endpoint-index-for-ch.patch b/queue-6.5/usb-gadget-fsl_qe_udc-validate-endpoint-index-for-ch.patch new file mode 100644 index 00000000000..7d3da93344d --- /dev/null +++ b/queue-6.5/usb-gadget-fsl_qe_udc-validate-endpoint-index-for-ch.patch @@ -0,0 +1,37 @@ +From 251c693d6b5e96f5cf78bb657d62de06a268d908 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Jun 2023 16:15:11 +0800 +Subject: usb: gadget: fsl_qe_udc: validate endpoint index for ch9 udc + +From: Ma Ke + +[ Upstream commit ce9daa2efc0872a9a68ea51dc8000df05893ef2e ] + +We should verify the bound of the array to assure that host +may not manipulate the index to point past endpoint array. + +Signed-off-by: Ma Ke +Acked-by: Li Yang +Link: https://lore.kernel.org/r/20230628081511.186850-1-make_ruc2021@163.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/usb/gadget/udc/fsl_qe_udc.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/drivers/usb/gadget/udc/fsl_qe_udc.c b/drivers/usb/gadget/udc/fsl_qe_udc.c +index 9c5dc1c1a68ea..4aae86b47edfc 100644 +--- a/drivers/usb/gadget/udc/fsl_qe_udc.c ++++ b/drivers/usb/gadget/udc/fsl_qe_udc.c +@@ -1959,6 +1959,8 @@ static void ch9getstatus(struct qe_udc *udc, u8 request_type, u16 value, + } else if ((request_type & USB_RECIP_MASK) == USB_RECIP_ENDPOINT) { + /* Get endpoint status */ + int pipe = index & USB_ENDPOINT_NUMBER_MASK; ++ if (pipe >= USB_MAX_ENDPOINTS) ++ goto stall; + struct qe_ep *target_ep = &udc->eps[pipe]; + u16 usep; + +-- +2.40.1 + diff --git a/queue-6.5/usb-typec-intel_pmc_mux-add-new-acpi-id-for-lunar-la.patch b/queue-6.5/usb-typec-intel_pmc_mux-add-new-acpi-id-for-lunar-la.patch new file mode 100644 index 00000000000..4f984e898f6 --- /dev/null +++ b/queue-6.5/usb-typec-intel_pmc_mux-add-new-acpi-id-for-lunar-la.patch @@ -0,0 +1,99 @@ +From 0fb2fe8692397b97c94ea4e6b285d9f8e72a5682 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 4 Jul 2023 13:35:09 +0530 +Subject: usb: typec: intel_pmc_mux: Add new ACPI ID for Lunar Lake IOM device + +From: Madhu M + +[ Upstream commit e032368e8cb15ab1f11b92f078caa9bae995b8fe ] + +Intel Lunar Lake IOM has a different IOM port status offset and size +than Intel MTL. + +Intel Lunar Lake is the first platform to extend IOM port status +from 32bit to 64bit by adding DDI port number into IOM port status. + +Added IOM_PORT_STATUS_REGS macro for using platform specific IOM port +status offset and size. + +Reviewed-by: Andy Shevchenko +Acked-by: Heikki Krogerus +Signed-off-by: Madhu M +Link: https://lore.kernel.org/r/20230704080509.14251-1-madhu.m@intel.com +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/usb/typec/mux/intel_pmc_mux.c | 25 ++++++++++++++++++++----- + 1 file changed, 20 insertions(+), 5 deletions(-) + +diff --git a/drivers/usb/typec/mux/intel_pmc_mux.c b/drivers/usb/typec/mux/intel_pmc_mux.c +index 5e8edf3881c0d..61a88f68b458c 100644 +--- a/drivers/usb/typec/mux/intel_pmc_mux.c ++++ b/drivers/usb/typec/mux/intel_pmc_mux.c +@@ -117,6 +117,16 @@ enum { + IOM_PORT_STATUS_DHPD_HPD_STATUS_SHIFT) & \ + IOM_PORT_STATUS_DHPD_HPD_STATUS_ASSERT) + ++/* IOM port status register */ ++#define IOM_PORT_STATUS_REGS(_offset_, _size_) ((_offset_) | (_size_)) ++#define IOM_PORT_STATUS_REGS_SZ_MASK BIT(0) ++#define IOM_PORT_STATUS_REGS_SZ_4 0 ++#define IOM_PORT_STATUS_REGS_SZ_8 1 ++#define IOM_PORT_STATUS_REGS_OFFSET(_d_) \ ++ ((_d_) & ~IOM_PORT_STATUS_REGS_SZ_MASK) ++#define IOM_PORT_STATUS_REGS_SIZE(_d_) \ ++ (4 << ((_d_) & IOM_PORT_STATUS_REGS_SZ_MASK)) ++ + struct pmc_usb; + + struct pmc_usb_port { +@@ -145,6 +155,7 @@ struct pmc_usb { + struct acpi_device *iom_adev; + void __iomem *iom_base; + u32 iom_port_status_offset; ++ u8 iom_port_status_size; + + struct dentry *dentry; + }; +@@ -160,7 +171,7 @@ static void update_port_status(struct pmc_usb_port *port) + + port->iom_status = readl(port->pmc->iom_base + + port->pmc->iom_port_status_offset + +- port_num * sizeof(u32)); ++ port_num * port->pmc->iom_port_status_size); + } + + static int sbu_orientation(struct pmc_usb_port *port) +@@ -589,13 +600,16 @@ static int pmc_usb_register_port(struct pmc_usb *pmc, int index, + /* IOM ACPI IDs and IOM_PORT_STATUS_OFFSET */ + static const struct acpi_device_id iom_acpi_ids[] = { + /* TigerLake */ +- { "INTC1072", 0x560, }, ++ { "INTC1072", IOM_PORT_STATUS_REGS(0x560, IOM_PORT_STATUS_REGS_SZ_4) }, + + /* AlderLake */ +- { "INTC1079", 0x160, }, ++ { "INTC1079", IOM_PORT_STATUS_REGS(0x160, IOM_PORT_STATUS_REGS_SZ_4) }, + + /* Meteor Lake */ +- { "INTC107A", 0x160, }, ++ { "INTC107A", IOM_PORT_STATUS_REGS(0x160, IOM_PORT_STATUS_REGS_SZ_4) }, ++ ++ /* Lunar Lake */ ++ { "INTC10EA", IOM_PORT_STATUS_REGS(0x150, IOM_PORT_STATUS_REGS_SZ_8) }, + {} + }; + +@@ -615,7 +629,8 @@ static int pmc_usb_probe_iom(struct pmc_usb *pmc) + if (!adev) + return -ENODEV; + +- pmc->iom_port_status_offset = (u32)dev_id->driver_data; ++ pmc->iom_port_status_offset = IOM_PORT_STATUS_REGS_OFFSET(dev_id->driver_data); ++ pmc->iom_port_status_size = IOM_PORT_STATUS_REGS_SIZE(dev_id->driver_data); + + INIT_LIST_HEAD(&resource_list); + ret = acpi_dev_get_memory_resources(adev, &resource_list); +-- +2.40.1 + diff --git a/queue-6.5/usb-typec-qcom-pmic-typec-register-drm_bridge.patch b/queue-6.5/usb-typec-qcom-pmic-typec-register-drm_bridge.patch new file mode 100644 index 00000000000..cdbd595689f --- /dev/null +++ b/queue-6.5/usb-typec-qcom-pmic-typec-register-drm_bridge.patch @@ -0,0 +1,107 @@ +From bd7f8ea50c3c99cd27b9f1a041071552dbb1a901 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 17 Aug 2023 18:08:24 +0300 +Subject: usb: typec: qcom-pmic-typec: register drm_bridge + +From: Dmitry Baryshkov + +[ Upstream commit 4b3cd783808bb327d931bbb1324d6c367443b721 ] + +The current approach to handling DP on bridge-enabled platforms requires +a chain of DP bridges up to the USB-C connector. Register a last DRM +bridge for such chain. + +Acked-by: Bryan O'Donoghue +Signed-off-by: Dmitry Baryshkov +Link: https://lore.kernel.org/r/20230817150824.14371-3-dmitry.baryshkov@linaro.org +Signed-off-by: Greg Kroah-Hartman +Signed-off-by: Sasha Levin +--- + drivers/usb/typec/tcpm/Kconfig | 1 + + drivers/usb/typec/tcpm/qcom/qcom_pmic_typec.c | 37 +++++++++++++++++++ + 2 files changed, 38 insertions(+) + +diff --git a/drivers/usb/typec/tcpm/Kconfig b/drivers/usb/typec/tcpm/Kconfig +index 5d393f520fc2f..0b2993fef564b 100644 +--- a/drivers/usb/typec/tcpm/Kconfig ++++ b/drivers/usb/typec/tcpm/Kconfig +@@ -79,6 +79,7 @@ config TYPEC_WCOVE + config TYPEC_QCOM_PMIC + tristate "Qualcomm PMIC USB Type-C Port Controller Manager driver" + depends on ARCH_QCOM || COMPILE_TEST ++ depends on DRM || DRM=n + help + A Type-C port and Power Delivery driver which aggregates two + discrete pieces of silicon in the PM8150b PMIC block: the +diff --git a/drivers/usb/typec/tcpm/qcom/qcom_pmic_typec.c b/drivers/usb/typec/tcpm/qcom/qcom_pmic_typec.c +index 9b467a346114e..273b4811b4ac8 100644 +--- a/drivers/usb/typec/tcpm/qcom/qcom_pmic_typec.c ++++ b/drivers/usb/typec/tcpm/qcom/qcom_pmic_typec.c +@@ -17,6 +17,9 @@ + #include + #include + #include ++ ++#include ++ + #include "qcom_pmic_typec_pdphy.h" + #include "qcom_pmic_typec_port.h" + +@@ -33,6 +36,7 @@ struct pmic_typec { + struct pmic_typec_port *pmic_typec_port; + bool vbus_enabled; + struct mutex lock; /* VBUS state serialization */ ++ struct drm_bridge bridge; + }; + + #define tcpc_to_tcpm(_tcpc_) container_of(_tcpc_, struct pmic_typec, tcpc) +@@ -146,6 +150,35 @@ static int qcom_pmic_typec_init(struct tcpc_dev *tcpc) + return 0; + } + ++#if IS_ENABLED(CONFIG_DRM) ++static int qcom_pmic_typec_attach(struct drm_bridge *bridge, ++ enum drm_bridge_attach_flags flags) ++{ ++ return flags & DRM_BRIDGE_ATTACH_NO_CONNECTOR ? 0 : -EINVAL; ++} ++ ++static const struct drm_bridge_funcs qcom_pmic_typec_bridge_funcs = { ++ .attach = qcom_pmic_typec_attach, ++}; ++ ++static int qcom_pmic_typec_init_drm(struct pmic_typec *tcpm) ++{ ++ tcpm->bridge.funcs = &qcom_pmic_typec_bridge_funcs; ++#ifdef CONFIG_OF ++ tcpm->bridge.of_node = of_get_child_by_name(tcpm->dev->of_node, "connector"); ++#endif ++ tcpm->bridge.ops = DRM_BRIDGE_OP_HPD; ++ tcpm->bridge.type = DRM_MODE_CONNECTOR_DisplayPort; ++ ++ return devm_drm_bridge_add(tcpm->dev, &tcpm->bridge); ++} ++#else ++static int qcom_pmic_typec_init_drm(struct pmic_typec *tcpm) ++{ ++ return 0; ++} ++#endif ++ + static int qcom_pmic_typec_probe(struct platform_device *pdev) + { + struct pmic_typec *tcpm; +@@ -208,6 +241,10 @@ static int qcom_pmic_typec_probe(struct platform_device *pdev) + mutex_init(&tcpm->lock); + platform_set_drvdata(pdev, tcpm); + ++ ret = qcom_pmic_typec_init_drm(tcpm); ++ if (ret) ++ return ret; ++ + tcpm->tcpc.fwnode = device_get_named_child_node(tcpm->dev, "connector"); + if (!tcpm->tcpc.fwnode) + return -EINVAL; +-- +2.40.1 + diff --git a/queue-6.5/wifi-ath12k-add-check-max-message-length-while-scann.patch b/queue-6.5/wifi-ath12k-add-check-max-message-length-while-scann.patch new file mode 100644 index 00000000000..1374a268b5a --- /dev/null +++ b/queue-6.5/wifi-ath12k-add-check-max-message-length-while-scann.patch @@ -0,0 +1,76 @@ +From ae409df4868f312ba06c50f648de1026482f6658 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 9 Aug 2023 04:16:57 -0400 +Subject: wifi: ath12k: add check max message length while scanning with + extraie + +From: Wen Gong + +[ Upstream commit 2f5124e86ae74b7ba24c9ae2644107b750cbf38f ] + +Currently the extraie length is directly used to allocate skb buffer. When +the length of skb is greater than the max message length which firmware +supports, error will happen in firmware side. + +Hence add check for the skb length and drop extraie when overflow and +print a message. + +Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0-03427-QCAHMTSWPL_V1.0_V2.0_SILICONZ-1.15378.4 + +Signed-off-by: Wen Gong +Reviewed-by: Jeff Johnson +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230809081657.13858-1-quic_wgong@quicinc.com +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath12k/wmi.c | 20 +++++++++++++------- + 1 file changed, 13 insertions(+), 7 deletions(-) + +diff --git a/drivers/net/wireless/ath/ath12k/wmi.c b/drivers/net/wireless/ath/ath12k/wmi.c +index 4f378f06e946e..eebc5a65ce3b4 100644 +--- a/drivers/net/wireless/ath/ath12k/wmi.c ++++ b/drivers/net/wireless/ath/ath12k/wmi.c +@@ -2162,12 +2162,6 @@ int ath12k_wmi_send_scan_start_cmd(struct ath12k *ar, + if (arg->num_bssid) + len += sizeof(*bssid) * arg->num_bssid; + +- len += TLV_HDR_SIZE; +- if (arg->extraie.len) +- extraie_len_with_pad = +- roundup(arg->extraie.len, sizeof(u32)); +- len += extraie_len_with_pad; +- + if (arg->num_hint_bssid) + len += TLV_HDR_SIZE + + arg->num_hint_bssid * sizeof(*hint_bssid); +@@ -2176,6 +2170,18 @@ int ath12k_wmi_send_scan_start_cmd(struct ath12k *ar, + len += TLV_HDR_SIZE + + arg->num_hint_s_ssid * sizeof(*s_ssid); + ++ len += TLV_HDR_SIZE; ++ if (arg->extraie.len) ++ extraie_len_with_pad = ++ roundup(arg->extraie.len, sizeof(u32)); ++ if (extraie_len_with_pad <= (wmi->wmi_ab->max_msg_len[ar->pdev_idx] - len)) { ++ len += extraie_len_with_pad; ++ } else { ++ ath12k_warn(ar->ab, "discard large size %d bytes extraie for scan start\n", ++ arg->extraie.len); ++ extraie_len_with_pad = 0; ++ } ++ + skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len); + if (!skb) + return -ENOMEM; +@@ -2265,7 +2271,7 @@ int ath12k_wmi_send_scan_start_cmd(struct ath12k *ar, + tlv->header = ath12k_wmi_tlv_hdr(WMI_TAG_ARRAY_BYTE, len); + ptr += TLV_HDR_SIZE; + +- if (arg->extraie.len) ++ if (extraie_len_with_pad) + memcpy(ptr, arg->extraie.ptr, + arg->extraie.len); + +-- +2.40.1 + diff --git a/queue-6.5/wifi-ath12k-avoid-array-overflow-of-hw-mode-for-pref.patch b/queue-6.5/wifi-ath12k-avoid-array-overflow-of-hw-mode-for-pref.patch new file mode 100644 index 00000000000..49e1a960630 --- /dev/null +++ b/queue-6.5/wifi-ath12k-avoid-array-overflow-of-hw-mode-for-pref.patch @@ -0,0 +1,61 @@ +From 24367c49d9dc0f7e6f89bec54df2672b10a8f9d5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 14 Jul 2023 03:24:05 -0400 +Subject: wifi: ath12k: avoid array overflow of hw mode for preferred_hw_mode + +From: Wen Gong + +[ Upstream commit 1e9b1363e2de1552ee4e3d74ac8bb43a194f1cb4 ] + +Currently ath12k define WMI_HOST_HW_MODE_DBS_OR_SBS=5 as max hw mode +for enum wmi_host_hw_mode_config_type, it is also same for the array +ath12k_hw_mode_pri_map. + +When tested with new version firmware/board data which support new +hw mode eMLSR mode with hw mode value 8, it leads overflow usage for +array ath12k_hw_mode_pri_map in function ath12k_wmi_hw_mode_caps(), +and then lead preferred_hw_mode changed to 8, and finally function +ath12k_pull_mac_phy_cap_svc_ready_ext() select the capability of hw +mode 8, but the capability of eMLSR mode report from firmware does +not support 2.4 GHz band for WCN7850, so finally 2.4 GHz band is +disabled. + +Skip the hw mode which exceeds WMI_HOST_HW_MODE_MAX in function +ath12k_wmi_hw_mode_caps() helps to avoid array overflow, then the 2.4 +GHz band will not be disabled. + +This is to keep compatibility with newer version firmware/board data +files, this change is still needed after ath12k add eMLSR hw mode 8 in +array ath12k_hw_mode_pri_map and enum wmi_host_hw_mode_config_type, +because more hw mode maybe added in next firmware/board data version +e.g hw mode 9, then it will also lead new array overflow without this +change. + +Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0-03427-QCAHMTSWPL_V1.0_V2.0_SILICONZ-1.15378.4 + +Signed-off-by: Wen Gong +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230714072405.28705-1-quic_wgong@quicinc.com +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath12k/wmi.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/drivers/net/wireless/ath/ath12k/wmi.c b/drivers/net/wireless/ath/ath12k/wmi.c +index 4928e4e916603..4f378f06e946e 100644 +--- a/drivers/net/wireless/ath/ath12k/wmi.c ++++ b/drivers/net/wireless/ath/ath12k/wmi.c +@@ -3704,6 +3704,10 @@ static int ath12k_wmi_hw_mode_caps(struct ath12k_base *soc, + for (i = 0 ; i < svc_rdy_ext->n_hw_mode_caps; i++) { + hw_mode_caps = &svc_rdy_ext->hw_mode_caps[i]; + mode = le32_to_cpu(hw_mode_caps->hw_mode_id); ++ ++ if (mode >= WMI_HOST_HW_MODE_MAX) ++ continue; ++ + pref = soc->wmi_ab.preferred_hw_mode; + + if (ath12k_hw_mode_pri_map[mode] < ath12k_hw_mode_pri_map[pref]) { +-- +2.40.1 + diff --git a/queue-6.5/wifi-ath12k-fix-a-null-pointer-dereference-in-ath12k.patch b/queue-6.5/wifi-ath12k-fix-a-null-pointer-dereference-in-ath12k.patch new file mode 100644 index 00000000000..322d348bef8 --- /dev/null +++ b/queue-6.5/wifi-ath12k-fix-a-null-pointer-dereference-in-ath12k.patch @@ -0,0 +1,48 @@ +From cff630f8b0eb8208b2a9ae0cad76d96868161c56 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 26 Jul 2023 05:26:25 -0400 +Subject: wifi: ath12k: Fix a NULL pointer dereference in + ath12k_mac_op_hw_scan() + +From: Wen Gong + +[ Upstream commit 8ad314da54c6dd223a6b6cc85019160aa842f659 ] + +In ath12k_mac_op_hw_scan(), the return value of kzalloc() is directly +used in memcpy(), which may lead to a NULL pointer dereference on +failure of kzalloc(). + +Fix this bug by adding a check of arg.extraie.ptr. + +Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0-03427-QCAHMTSWPL_V1.0_V2.0_SILICONZ-1.15378.4 + +Signed-off-by: Wen Gong +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230726092625.3350-1-quic_wgong@quicinc.com +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath12k/mac.c | 7 +++++-- + 1 file changed, 5 insertions(+), 2 deletions(-) + +diff --git a/drivers/net/wireless/ath/ath12k/mac.c b/drivers/net/wireless/ath/ath12k/mac.c +index 45d88e35fc2eb..d165b24094ad5 100644 +--- a/drivers/net/wireless/ath/ath12k/mac.c ++++ b/drivers/net/wireless/ath/ath12k/mac.c +@@ -2755,9 +2755,12 @@ static int ath12k_mac_op_hw_scan(struct ieee80211_hw *hw, + arg.scan_id = ATH12K_SCAN_ID; + + if (req->ie_len) { ++ arg.extraie.ptr = kmemdup(req->ie, req->ie_len, GFP_KERNEL); ++ if (!arg.extraie.ptr) { ++ ret = -ENOMEM; ++ goto exit; ++ } + arg.extraie.len = req->ie_len; +- arg.extraie.ptr = kzalloc(req->ie_len, GFP_KERNEL); +- memcpy(arg.extraie.ptr, req->ie, req->ie_len); + } + + if (req->n_ssids) { +-- +2.40.1 + diff --git a/queue-6.5/wifi-ath12k-fix-memory-leak-in-rx_desc-and-tx_desc.patch b/queue-6.5/wifi-ath12k-fix-memory-leak-in-rx_desc-and-tx_desc.patch new file mode 100644 index 00000000000..e89c0bbadf0 --- /dev/null +++ b/queue-6.5/wifi-ath12k-fix-memory-leak-in-rx_desc-and-tx_desc.patch @@ -0,0 +1,117 @@ +From 89224cd238fb6f54b8c9e1849fcaf10ed4fb5225 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 22 Aug 2023 16:42:23 +0300 +Subject: wifi: ath12k: Fix memory leak in rx_desc and tx_desc + +From: Rajat Soni + +[ Upstream commit afb522b36e76acaa9f8fc06d0a9742d841c47c16 ] + +Currently when ath12k_dp_cc_desc_init() is called we allocate +memory to rx_descs and tx_descs. In ath12k_dp_cc_cleanup(), during +descriptor cleanup rx_descs and tx_descs memory is not freed. + +This is cause of memory leak. These allocated memory should be +freed in ath12k_dp_cc_cleanup. + +In ath12k_dp_cc_desc_init(), we can save base address of rx_descs +and tx_descs. In ath12k_dp_cc_cleanup(), we can free rx_descs and +tx_descs memory using their base address. + +Tested-on: QCN9274 hw2.0 PCI WLAN.WBE.1.0.1-00029-QCAHKSWPL_SILICONZ-1 + +Signed-off-by: Rajat Soni +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230718053510.30894-1-quic_rajson@quicinc.com +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath12k/dp.c | 30 +++++++++++++++++++++++++++- + drivers/net/wireless/ath/ath12k/dp.h | 2 ++ + 2 files changed, 31 insertions(+), 1 deletion(-) + +diff --git a/drivers/net/wireless/ath/ath12k/dp.c b/drivers/net/wireless/ath/ath12k/dp.c +index ae1645d0f42a2..f933896f2a68d 100644 +--- a/drivers/net/wireless/ath/ath12k/dp.c ++++ b/drivers/net/wireless/ath/ath12k/dp.c +@@ -1129,6 +1129,7 @@ static void ath12k_dp_cc_cleanup(struct ath12k_base *ab) + struct ath12k_dp *dp = &ab->dp; + struct sk_buff *skb; + int i; ++ u32 pool_id, tx_spt_page; + + if (!dp->spt_info) + return; +@@ -1148,6 +1149,14 @@ static void ath12k_dp_cc_cleanup(struct ath12k_base *ab) + dev_kfree_skb_any(skb); + } + ++ for (i = 0; i < ATH12K_NUM_RX_SPT_PAGES; i++) { ++ if (!dp->spt_info->rxbaddr[i]) ++ continue; ++ ++ kfree(dp->spt_info->rxbaddr[i]); ++ dp->spt_info->rxbaddr[i] = NULL; ++ } ++ + spin_unlock_bh(&dp->rx_desc_lock); + + /* TX Descriptor cleanup */ +@@ -1170,6 +1179,21 @@ static void ath12k_dp_cc_cleanup(struct ath12k_base *ab) + spin_unlock_bh(&dp->tx_desc_lock[i]); + } + ++ for (pool_id = 0; pool_id < ATH12K_HW_MAX_QUEUES; pool_id++) { ++ spin_lock_bh(&dp->tx_desc_lock[pool_id]); ++ ++ for (i = 0; i < ATH12K_TX_SPT_PAGES_PER_POOL; i++) { ++ tx_spt_page = i + pool_id * ATH12K_TX_SPT_PAGES_PER_POOL; ++ if (!dp->spt_info->txbaddr[tx_spt_page]) ++ continue; ++ ++ kfree(dp->spt_info->txbaddr[tx_spt_page]); ++ dp->spt_info->txbaddr[tx_spt_page] = NULL; ++ } ++ ++ spin_unlock_bh(&dp->tx_desc_lock[pool_id]); ++ } ++ + /* unmap SPT pages */ + for (i = 0; i < dp->num_spt_pages; i++) { + if (!dp->spt_info[i].vaddr) +@@ -1343,6 +1367,8 @@ static int ath12k_dp_cc_desc_init(struct ath12k_base *ab) + return -ENOMEM; + } + ++ dp->spt_info->rxbaddr[i] = &rx_descs[0]; ++ + for (j = 0; j < ATH12K_MAX_SPT_ENTRIES; j++) { + rx_descs[j].cookie = ath12k_dp_cc_cookie_gen(i, j); + rx_descs[j].magic = ATH12K_DP_RX_DESC_MAGIC; +@@ -1368,8 +1394,10 @@ static int ath12k_dp_cc_desc_init(struct ath12k_base *ab) + return -ENOMEM; + } + ++ tx_spt_page = i + pool_id * ATH12K_TX_SPT_PAGES_PER_POOL; ++ dp->spt_info->txbaddr[tx_spt_page] = &tx_descs[0]; ++ + for (j = 0; j < ATH12K_MAX_SPT_ENTRIES; j++) { +- tx_spt_page = i + pool_id * ATH12K_TX_SPT_PAGES_PER_POOL; + ppt_idx = ATH12K_NUM_RX_SPT_PAGES + tx_spt_page; + tx_descs[j].desc_id = ath12k_dp_cc_cookie_gen(ppt_idx, j); + tx_descs[j].pool_id = pool_id; +diff --git a/drivers/net/wireless/ath/ath12k/dp.h b/drivers/net/wireless/ath/ath12k/dp.h +index 7c5dafce5a68d..9aeda0321cd75 100644 +--- a/drivers/net/wireless/ath/ath12k/dp.h ++++ b/drivers/net/wireless/ath/ath12k/dp.h +@@ -289,6 +289,8 @@ struct ath12k_tx_desc_info { + struct ath12k_spt_info { + dma_addr_t paddr; + u64 *vaddr; ++ struct ath12k_rx_desc_info *rxbaddr[ATH12K_NUM_RX_SPT_PAGES]; ++ struct ath12k_tx_desc_info *txbaddr[ATH12K_NUM_TX_SPT_PAGES]; + }; + + struct ath12k_reo_queue_ref { +-- +2.40.1 + diff --git a/queue-6.5/wifi-ath9k-fix-fortify-warnings.patch b/queue-6.5/wifi-ath9k-fix-fortify-warnings.patch new file mode 100644 index 00000000000..0b303550119 --- /dev/null +++ b/queue-6.5/wifi-ath9k-fix-fortify-warnings.patch @@ -0,0 +1,97 @@ +From 8f1b9a2e9e5b3a20703319de84e8f52b31e198aa Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 24 Jul 2023 13:11:07 +0300 +Subject: wifi: ath9k: fix fortify warnings +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Dmitry Antipov + +[ Upstream commit 810e41cebb6c6e394f2068f839e1a3fc745a5dcc ] + +When compiling with gcc 13.1 and CONFIG_FORTIFY_SOURCE=y, +I've noticed the following: + +In function ‘fortify_memcpy_chk’, + inlined from ‘ath_tx_complete_aggr’ at drivers/net/wireless/ath/ath9k/xmit.c:556:4, + inlined from ‘ath_tx_process_buffer’ at drivers/net/wireless/ath/ath9k/xmit.c:773:3: +./include/linux/fortify-string.h:529:25: warning: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Wattribute-warning] + 529 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +In function ‘fortify_memcpy_chk’, + inlined from ‘ath_tx_count_frames’ at drivers/net/wireless/ath/ath9k/xmit.c:473:3, + inlined from ‘ath_tx_complete_aggr’ at drivers/net/wireless/ath/ath9k/xmit.c:572:2, + inlined from ‘ath_tx_process_buffer’ at drivers/net/wireless/ath/ath9k/xmit.c:773:3: +./include/linux/fortify-string.h:529:25: warning: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Wattribute-warning] + 529 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +In both cases, the compiler complains on: + +memcpy(ba, &ts->ba_low, WME_BA_BMP_SIZE >> 3); + +which is the legal way to copy both 'ba_low' and following 'ba_high' +members of 'struct ath_tx_status' at once (that is, issue one 8-byte +'memcpy()' for two 4-byte fields). Since the fortification logic seems +interprets this trick as an attempt to overread 4-byte 'ba_low', silence +relevant warnings by using the convenient 'struct_group()' quirk. + +Suggested-by: Johannes Berg +Signed-off-by: Dmitry Antipov +Acked-by: Toke Høiland-Jørgensen +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230620080855.396851-2-dmantipov@yandex.ru +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath9k/mac.h | 6 ++++-- + drivers/net/wireless/ath/ath9k/xmit.c | 4 ++-- + 2 files changed, 6 insertions(+), 4 deletions(-) + +diff --git a/drivers/net/wireless/ath/ath9k/mac.h b/drivers/net/wireless/ath/ath9k/mac.h +index af44b33814ddc..f03d792732da7 100644 +--- a/drivers/net/wireless/ath/ath9k/mac.h ++++ b/drivers/net/wireless/ath/ath9k/mac.h +@@ -115,8 +115,10 @@ struct ath_tx_status { + u8 qid; + u16 desc_id; + u8 tid; +- u32 ba_low; +- u32 ba_high; ++ struct_group(ba, ++ u32 ba_low; ++ u32 ba_high; ++ ); + u32 evm0; + u32 evm1; + u32 evm2; +diff --git a/drivers/net/wireless/ath/ath9k/xmit.c b/drivers/net/wireless/ath/ath9k/xmit.c +index f6f2ab7a63ffc..42058368e6373 100644 +--- a/drivers/net/wireless/ath/ath9k/xmit.c ++++ b/drivers/net/wireless/ath/ath9k/xmit.c +@@ -468,7 +468,7 @@ static void ath_tx_count_frames(struct ath_softc *sc, struct ath_buf *bf, + isaggr = bf_isaggr(bf); + if (isaggr) { + seq_st = ts->ts_seqnum; +- memcpy(ba, &ts->ba_low, WME_BA_BMP_SIZE >> 3); ++ memcpy(ba, &ts->ba, WME_BA_BMP_SIZE >> 3); + } + + while (bf) { +@@ -551,7 +551,7 @@ static void ath_tx_complete_aggr(struct ath_softc *sc, struct ath_txq *txq, + if (isaggr && txok) { + if (ts->ts_flags & ATH9K_TX_BA) { + seq_st = ts->ts_seqnum; +- memcpy(ba, &ts->ba_low, WME_BA_BMP_SIZE >> 3); ++ memcpy(ba, &ts->ba, WME_BA_BMP_SIZE >> 3); + } else { + /* + * AR5416 can become deaf/mute when BA +-- +2.40.1 + diff --git a/queue-6.5/wifi-ath9k-fix-printk-specifier.patch b/queue-6.5/wifi-ath9k-fix-printk-specifier.patch new file mode 100644 index 00000000000..0463ad063ca --- /dev/null +++ b/queue-6.5/wifi-ath9k-fix-printk-specifier.patch @@ -0,0 +1,68 @@ +From e3e20f1ab24fe7ef989193b82cfdeb1741196298 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 23 Jul 2023 12:04:02 +0800 +Subject: wifi: ath9k: fix printk specifier +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Dongliang Mu + +[ Upstream commit 061115fbfb2ce5870c9a004d68dc63138c07c782 ] + +Smatch reports: + +ath_pci_probe() warn: argument 4 to %lx specifier is cast from pointer +ath_ahb_probe() warn: argument 4 to %lx specifier is cast from pointer + +Fix it by modifying %lx to %p in the printk format string. + +Note that with this change, the pointer address will be printed as a +hashed value by default. This is appropriate because the kernel +should not leak kernel pointers to user space in an informational +message. If someone wants to see the real address for debugging +purposes, this can be achieved with the no_hash_pointers kernel option. + +Signed-off-by: Dongliang Mu +Acked-by: Toke Høiland-Jørgensen +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230723040403.296723-1-dzm91@hust.edu.cn +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/ath9k/ahb.c | 4 ++-- + drivers/net/wireless/ath/ath9k/pci.c | 4 ++-- + 2 files changed, 4 insertions(+), 4 deletions(-) + +diff --git a/drivers/net/wireless/ath/ath9k/ahb.c b/drivers/net/wireless/ath/ath9k/ahb.c +index 9cd12b20b18d8..9bfaadfa6c009 100644 +--- a/drivers/net/wireless/ath/ath9k/ahb.c ++++ b/drivers/net/wireless/ath/ath9k/ahb.c +@@ -132,8 +132,8 @@ static int ath_ahb_probe(struct platform_device *pdev) + + ah = sc->sc_ah; + ath9k_hw_name(ah, hw_name, sizeof(hw_name)); +- wiphy_info(hw->wiphy, "%s mem=0x%lx, irq=%d\n", +- hw_name, (unsigned long)mem, irq); ++ wiphy_info(hw->wiphy, "%s mem=0x%p, irq=%d\n", ++ hw_name, mem, irq); + + return 0; + +diff --git a/drivers/net/wireless/ath/ath9k/pci.c b/drivers/net/wireless/ath/ath9k/pci.c +index a09f9d223f3de..0633589b85c23 100644 +--- a/drivers/net/wireless/ath/ath9k/pci.c ++++ b/drivers/net/wireless/ath/ath9k/pci.c +@@ -988,8 +988,8 @@ static int ath_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id) + sc->sc_ah->msi_reg = 0; + + ath9k_hw_name(sc->sc_ah, hw_name, sizeof(hw_name)); +- wiphy_info(hw->wiphy, "%s mem=0x%lx, irq=%d\n", +- hw_name, (unsigned long)sc->mem, pdev->irq); ++ wiphy_info(hw->wiphy, "%s mem=0x%p, irq=%d\n", ++ hw_name, sc->mem, pdev->irq); + + return 0; + +-- +2.40.1 + diff --git a/queue-6.5/wifi-cfg80211-ocb-don-t-leave-if-not-joined.patch b/queue-6.5/wifi-cfg80211-ocb-don-t-leave-if-not-joined.patch new file mode 100644 index 00000000000..e6325118366 --- /dev/null +++ b/queue-6.5/wifi-cfg80211-ocb-don-t-leave-if-not-joined.patch @@ -0,0 +1,37 @@ +From da23de484fdcc386620940a6227cda54c6266b5d Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 18:32:03 +0200 +Subject: wifi: cfg80211: ocb: don't leave if not joined + +From: Johannes Berg + +[ Upstream commit abc76cf552e13cfa88a204b362a86b0e08e95228 ] + +If there's no OCB state, don't ask the driver/mac80211 to +leave, since that's just confusing. Since set/clear the +chandef state, that's a simple check. + +Reported-by: syzbot+09d1cd2f71e6dd3bfd2c@syzkaller.appspotmail.com +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + net/wireless/ocb.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/net/wireless/ocb.c b/net/wireless/ocb.c +index 27a1732264f95..29afaf3da54f3 100644 +--- a/net/wireless/ocb.c ++++ b/net/wireless/ocb.c +@@ -68,6 +68,9 @@ int __cfg80211_leave_ocb(struct cfg80211_registered_device *rdev, + if (!rdev->ops->leave_ocb) + return -EOPNOTSUPP; + ++ if (!wdev->u.ocb.chandef.chan) ++ return -ENOTCONN; ++ + err = rdev_leave_ocb(rdev, dev); + if (!err) + memset(&wdev->u.ocb.chandef, 0, sizeof(wdev->u.ocb.chandef)); +-- +2.40.1 + diff --git a/queue-6.5/wifi-cfg80211-reject-auth-assoc-to-ap-with-our-addre.patch b/queue-6.5/wifi-cfg80211-reject-auth-assoc-to-ap-with-our-addre.patch new file mode 100644 index 00000000000..e2c148ba1cf --- /dev/null +++ b/queue-6.5/wifi-cfg80211-reject-auth-assoc-to-ap-with-our-addre.patch @@ -0,0 +1,61 @@ +From f3fce875eacacae0d406c2bc8c83e87b23f5d855 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 18:09:00 +0200 +Subject: wifi: cfg80211: reject auth/assoc to AP with our address + +From: Johannes Berg + +[ Upstream commit 5d4e04bf3a0f098bd9033de3a5291810fa14c7a6 ] + +If the AP uses our own address as its MLD address or BSSID, then +clearly something's wrong. Reject such connections so we don't +try and fail later. + +Reported-by: syzbot+2676771ed06a6df166ad@syzkaller.appspotmail.com +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + net/wireless/mlme.c | 13 +++++++++++++ + 1 file changed, 13 insertions(+) + +diff --git a/net/wireless/mlme.c b/net/wireless/mlme.c +index ac059cefbeb39..775cac4d61006 100644 +--- a/net/wireless/mlme.c ++++ b/net/wireless/mlme.c +@@ -281,6 +281,11 @@ int cfg80211_mlme_auth(struct cfg80211_registered_device *rdev, + ether_addr_equal(req->bss->bssid, wdev->u.client.connected_addr)) + return -EALREADY; + ++ if (ether_addr_equal(req->bss->bssid, dev->dev_addr) || ++ (req->link_id >= 0 && ++ ether_addr_equal(req->ap_mld_addr, dev->dev_addr))) ++ return -EINVAL; ++ + return rdev_auth(rdev, dev, req); + } + +@@ -335,6 +340,9 @@ int cfg80211_mlme_assoc(struct cfg80211_registered_device *rdev, + if (req->links[i].bss == req->links[j].bss) + return -EINVAL; + } ++ ++ if (ether_addr_equal(req->links[i].bss->bssid, dev->dev_addr)) ++ return -EINVAL; + } + + if (wdev->connected && +@@ -342,6 +350,11 @@ int cfg80211_mlme_assoc(struct cfg80211_registered_device *rdev, + !ether_addr_equal(wdev->u.client.connected_addr, req->prev_bssid))) + return -EALREADY; + ++ if ((req->bss && ether_addr_equal(req->bss->bssid, dev->dev_addr)) || ++ (req->link_id >= 0 && ++ ether_addr_equal(req->ap_mld_addr, dev->dev_addr))) ++ return -EINVAL; ++ + cfg80211_oper_and_ht_capa(&req->ht_capa_mask, + rdev->wiphy.ht_capa_mod_mask); + cfg80211_oper_and_vht_capa(&req->vht_capa_mask, +-- +2.40.1 + diff --git a/queue-6.5/wifi-iwlwifi-pcie-avoid-a-warning-in-case-prepare-ca.patch b/queue-6.5/wifi-iwlwifi-pcie-avoid-a-warning-in-case-prepare-ca.patch new file mode 100644 index 00000000000..588c0b13ab6 --- /dev/null +++ b/queue-6.5/wifi-iwlwifi-pcie-avoid-a-warning-in-case-prepare-ca.patch @@ -0,0 +1,72 @@ +From 482475fe2d37a43a2dab551a5d5c70222e78f683 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 22 Aug 2023 10:33:15 +0300 +Subject: wifi: iwlwifi: pcie: avoid a warning in case prepare card failed + +From: Avraham Stern + +[ Upstream commit 057381ddac0593c6e4ca8f58732830d8542b9c4e ] + +In case CSME holds the NIC and SAP connection is already established, +iwl_pcie_prepare_card_hw() during iwl_pci_probe() will fail +(which is fine since CSME will release the nic later when asked with +a SAP message). In this case tring to grab nic access to read the +crf ids will fail with a warning. +Avoid the warning by only trying to read the crf ids in case prepare +card succeeded. + +Signed-off-by: Avraham Stern +Signed-off-by: Gregory Greenman +Link: https://lore.kernel.org/r/20230822103048.9b026fa7b97e.I12bea7e6eef54eeeaf916b68d71583e92ff310fd@changeid +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/intel/iwlwifi/pcie/drv.c | 11 +---------- + 1 file changed, 1 insertion(+), 10 deletions(-) + +diff --git a/drivers/net/wireless/intel/iwlwifi/pcie/drv.c b/drivers/net/wireless/intel/iwlwifi/pcie/drv.c +index 73c1fb3c0c5ec..bc83d2ba55c67 100644 +--- a/drivers/net/wireless/intel/iwlwifi/pcie/drv.c ++++ b/drivers/net/wireless/intel/iwlwifi/pcie/drv.c +@@ -1132,12 +1132,6 @@ static int get_crf_id(struct iwl_trans *iwl_trans) + else + sd_reg_ver_addr = SD_REG_VER; + +- if (!iwl_trans_grab_nic_access(iwl_trans)) { +- IWL_ERR(iwl_trans, "Failed to grab nic access before reading crf id\n"); +- ret = -EIO; +- goto out; +- } +- + /* Enable access to peripheral registers */ + val = iwl_read_umac_prph_no_grab(iwl_trans, WFPM_CTRL_REG); + val |= ENABLE_WFPM; +@@ -1157,9 +1151,6 @@ static int get_crf_id(struct iwl_trans *iwl_trans) + iwl_trans->hw_crf_id, iwl_trans->hw_cnv_id, + iwl_trans->hw_wfpm_id); + +- iwl_trans_release_nic_access(iwl_trans); +- +-out: + return ret; + } + +@@ -1351,6 +1342,7 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) + if (ret) + goto out_free_trans; + if (iwl_trans_grab_nic_access(iwl_trans)) { ++ get_crf_id(iwl_trans); + /* all good */ + iwl_trans_release_nic_access(iwl_trans); + } else { +@@ -1360,7 +1352,6 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) + } + + iwl_trans->hw_rf_id = iwl_read32(iwl_trans, CSR_HW_RF_ID); +- get_crf_id(iwl_trans); + + /* + * The RF_ID is set to zero in blank OTP so read version to +-- +2.40.1 + diff --git a/queue-6.5/wifi-mac80211-check-for-station-first-in-client-prob.patch b/queue-6.5/wifi-mac80211-check-for-station-first-in-client-prob.patch new file mode 100644 index 00000000000..b71af7ce62a --- /dev/null +++ b/queue-6.5/wifi-mac80211-check-for-station-first-in-client-prob.patch @@ -0,0 +1,59 @@ +From 8a8c62d5a8d5a05a40e143438726004b01b4d9d2 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 18:41:32 +0200 +Subject: wifi: mac80211: check for station first in client probe + +From: Johannes Berg + +[ Upstream commit 67dfa589aa8806c7959cbca2f4613b8d41c75a06 ] + +When probing a client, first check if we have it, and then +check for the channel context, otherwise you can trigger +the warning there easily by probing when the AP isn't even +started yet. Since a client existing means the AP is also +operating, we can then keep the warning. + +Also simplify the moved code a bit. + +Reported-by: syzbot+999fac712d84878a7379@syzkaller.appspotmail.com +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + net/mac80211/cfg.c | 15 ++++++++------- + 1 file changed, 8 insertions(+), 7 deletions(-) + +diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c +index d354b32a20f8f..45e7a5d9c7d94 100644 +--- a/net/mac80211/cfg.c ++++ b/net/mac80211/cfg.c +@@ -4133,19 +4133,20 @@ static int ieee80211_probe_client(struct wiphy *wiphy, struct net_device *dev, + mutex_lock(&local->mtx); + + rcu_read_lock(); ++ sta = sta_info_get_bss(sdata, peer); ++ if (!sta) { ++ ret = -ENOLINK; ++ goto unlock; ++ } ++ ++ qos = sta->sta.wme; ++ + chanctx_conf = rcu_dereference(sdata->vif.bss_conf.chanctx_conf); + if (WARN_ON(!chanctx_conf)) { + ret = -EINVAL; + goto unlock; + } + band = chanctx_conf->def.chan->band; +- sta = sta_info_get_bss(sdata, peer); +- if (sta) { +- qos = sta->sta.wme; +- } else { +- ret = -ENOLINK; +- goto unlock; +- } + + if (qos) { + fc = cpu_to_le16(IEEE80211_FTYPE_DATA | +-- +2.40.1 + diff --git a/queue-6.5/wifi-mac80211-check-s1g-action-frame-size.patch b/queue-6.5/wifi-mac80211-check-s1g-action-frame-size.patch new file mode 100644 index 00000000000..2843aff6442 --- /dev/null +++ b/queue-6.5/wifi-mac80211-check-s1g-action-frame-size.patch @@ -0,0 +1,37 @@ +From 7f7f4659ca96cef28a401bf2d2046a8b87af4da5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 17:51:05 +0200 +Subject: wifi: mac80211: check S1G action frame size + +From: Johannes Berg + +[ Upstream commit 19e4a47ee74718a22e963e8a647c8c3bfe8bb05c ] + +Before checking the action code, check that it even +exists in the frame. + +Reported-by: syzbot+be9c824e6f269d608288@syzkaller.appspotmail.com +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + net/mac80211/rx.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c +index 0af2599c17e8d..e751cda5eef69 100644 +--- a/net/mac80211/rx.c ++++ b/net/mac80211/rx.c +@@ -3734,6 +3734,10 @@ ieee80211_rx_h_action(struct ieee80211_rx_data *rx) + break; + goto queue; + case WLAN_CATEGORY_S1G: ++ if (len < offsetofend(typeof(*mgmt), ++ u.action.u.s1g.action_code)) ++ break; ++ + switch (mgmt->u.action.u.s1g.action_code) { + case WLAN_S1G_TWT_SETUP: + case WLAN_S1G_TWT_TEARDOWN: +-- +2.40.1 + diff --git a/queue-6.5/wifi-mac80211_hwsim-drop-short-frames.patch b/queue-6.5/wifi-mac80211_hwsim-drop-short-frames.patch new file mode 100644 index 00000000000..d2250f61cb4 --- /dev/null +++ b/queue-6.5/wifi-mac80211_hwsim-drop-short-frames.patch @@ -0,0 +1,49 @@ +From a0887212b95d8db71a244327cef38cf4dcb79d93 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 15 Aug 2023 21:28:01 +0200 +Subject: wifi: mac80211_hwsim: drop short frames + +From: Johannes Berg + +[ Upstream commit fba360a047d5eeeb9d4b7c3a9b1c8308980ce9a6 ] + +While technically some control frames like ACK are shorter and +end after Address 1, such frames shouldn't be forwarded through +wmediumd or similar userspace, so require the full 3-address +header to avoid accessing invalid memory if shorter frames are +passed in. + +Reported-by: syzbot+b2645b5bf1512b81fa22@syzkaller.appspotmail.com +Reviewed-by: Jeff Johnson +Signed-off-by: Johannes Berg +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/virtual/mac80211_hwsim.c | 7 ++++--- + 1 file changed, 4 insertions(+), 3 deletions(-) + +diff --git a/drivers/net/wireless/virtual/mac80211_hwsim.c b/drivers/net/wireless/virtual/mac80211_hwsim.c +index f446fd0e8cd0d..dd516cec41973 100644 +--- a/drivers/net/wireless/virtual/mac80211_hwsim.c ++++ b/drivers/net/wireless/virtual/mac80211_hwsim.c +@@ -5626,14 +5626,15 @@ static int hwsim_cloned_frame_received_nl(struct sk_buff *skb_2, + frame_data_len = nla_len(info->attrs[HWSIM_ATTR_FRAME]); + frame_data = (void *)nla_data(info->attrs[HWSIM_ATTR_FRAME]); + ++ if (frame_data_len < sizeof(struct ieee80211_hdr_3addr) || ++ frame_data_len > IEEE80211_MAX_DATA_LEN) ++ goto err; ++ + /* Allocate new skb here */ + skb = alloc_skb(frame_data_len, GFP_KERNEL); + if (skb == NULL) + goto err; + +- if (frame_data_len > IEEE80211_MAX_DATA_LEN) +- goto err; +- + /* Copy the data */ + skb_put_data(skb, frame_data, frame_data_len); + +-- +2.40.1 + diff --git a/queue-6.5/wifi-mwifiex-fix-fortify-warning.patch b/queue-6.5/wifi-mwifiex-fix-fortify-warning.patch new file mode 100644 index 00000000000..d15dc1b7344 --- /dev/null +++ b/queue-6.5/wifi-mwifiex-fix-fortify-warning.patch @@ -0,0 +1,87 @@ +From 35b4a45ebb534c963be720ff8be8c5cd238e0604 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 29 Jun 2023 11:51:01 +0300 +Subject: wifi: mwifiex: fix fortify warning +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Dmitry Antipov + +[ Upstream commit dcce94b80a954a8968ff29fafcfb066d6197fa9a ] + +When compiling with gcc 13.1 and CONFIG_FORTIFY_SOURCE=y, +I've noticed the following: + +In function ‘fortify_memcpy_chk’, + inlined from ‘mwifiex_construct_tdls_action_frame’ at drivers/net/wireless/marvell/mwifiex/tdls.c:765:3, + inlined from ‘mwifiex_send_tdls_action_frame’ at drivers/net/wireless/marvell/mwifiex/tdls.c:856:6: +./include/linux/fortify-string.h:529:25: warning: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Wattribute-warning] + 529 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The compiler actually complains on: + +memmove(pos + ETH_ALEN, &mgmt->u.action.category, + sizeof(mgmt->u.action.u.tdls_discover_resp)); + +and it happens because the fortification logic interprets this +as an attempt to overread 1-byte 'u.action.category' member of +'struct ieee80211_mgmt'. To silence this warning, it's enough +to pass an address of 'u.action' itself instead of an address +of its first member. + +This also fixes an improper usage of 'sizeof()'. Since 'skb' is +extended with 'sizeof(mgmt->u.action.u.tdls_discover_resp) + 1' +bytes (where 1 is actually 'sizeof(mgmt->u.action.category)'), +I assume that the same number of bytes should be copied. + +Suggested-by: Brian Norris +Signed-off-by: Dmitry Antipov +Reviewed-by: Brian Norris +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230629085115.180499-2-dmantipov@yandex.ru +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/marvell/mwifiex/tdls.c | 9 ++++++--- + 1 file changed, 6 insertions(+), 3 deletions(-) + +diff --git a/drivers/net/wireless/marvell/mwifiex/tdls.c b/drivers/net/wireless/marvell/mwifiex/tdls.c +index 97bb87c3676bb..6c60621b6cccb 100644 +--- a/drivers/net/wireless/marvell/mwifiex/tdls.c ++++ b/drivers/net/wireless/marvell/mwifiex/tdls.c +@@ -735,6 +735,7 @@ mwifiex_construct_tdls_action_frame(struct mwifiex_private *priv, + int ret; + u16 capab; + struct ieee80211_ht_cap *ht_cap; ++ unsigned int extra; + u8 radio, *pos; + + capab = priv->curr_bss_params.bss_descriptor.cap_info_bitmap; +@@ -753,7 +754,10 @@ mwifiex_construct_tdls_action_frame(struct mwifiex_private *priv, + + switch (action_code) { + case WLAN_PUB_ACTION_TDLS_DISCOVER_RES: +- skb_put(skb, sizeof(mgmt->u.action.u.tdls_discover_resp) + 1); ++ /* See the layout of 'struct ieee80211_mgmt'. */ ++ extra = sizeof(mgmt->u.action.u.tdls_discover_resp) + ++ sizeof(mgmt->u.action.category); ++ skb_put(skb, extra); + mgmt->u.action.category = WLAN_CATEGORY_PUBLIC; + mgmt->u.action.u.tdls_discover_resp.action_code = + WLAN_PUB_ACTION_TDLS_DISCOVER_RES; +@@ -762,8 +766,7 @@ mwifiex_construct_tdls_action_frame(struct mwifiex_private *priv, + mgmt->u.action.u.tdls_discover_resp.capability = + cpu_to_le16(capab); + /* move back for addr4 */ +- memmove(pos + ETH_ALEN, &mgmt->u.action.category, +- sizeof(mgmt->u.action.u.tdls_discover_resp)); ++ memmove(pos + ETH_ALEN, &mgmt->u.action, extra); + /* init address 4 */ + eth_broadcast_addr(pos); + +-- +2.40.1 + diff --git a/queue-6.5/wifi-rtw88-delete-timer-and-free-skb-queue-when-unlo.patch b/queue-6.5/wifi-rtw88-delete-timer-and-free-skb-queue-when-unlo.patch new file mode 100644 index 00000000000..4563a8c2ef6 --- /dev/null +++ b/queue-6.5/wifi-rtw88-delete-timer-and-free-skb-queue-when-unlo.patch @@ -0,0 +1,44 @@ +From 737b7dd1f54acbfd8c49fcecaf4d1b4786ff663b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Jun 2023 10:23:15 +0300 +Subject: wifi: rtw88: delete timer and free skb queue when unloading + +From: Dmitry Antipov + +[ Upstream commit 634fcbcaa4062db39aeb5ac6ed1bc1feb8dd5216 ] + +Fix possible crash and memory leak on driver unload by deleting +TX purge timer and freeing C2H queue in 'rtw_core_deinit()', +shrink critical section in the latter by freeing COEX queue +out of TX report lock scope. + +Reviewed-by: Ping-Ke Shih +Signed-off-by: Dmitry Antipov +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230628072327.167196-1-dmantipov@yandex.ru +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/realtek/rtw88/main.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/drivers/net/wireless/realtek/rtw88/main.c b/drivers/net/wireless/realtek/rtw88/main.c +index c853e2f2d448f..c2ddb4d382af5 100644 +--- a/drivers/net/wireless/realtek/rtw88/main.c ++++ b/drivers/net/wireless/realtek/rtw88/main.c +@@ -2183,10 +2183,12 @@ void rtw_core_deinit(struct rtw_dev *rtwdev) + release_firmware(wow_fw->firmware); + + destroy_workqueue(rtwdev->tx_wq); ++ timer_delete_sync(&rtwdev->tx_report.purge_timer); + spin_lock_irqsave(&rtwdev->tx_report.q_lock, flags); + skb_queue_purge(&rtwdev->tx_report.queue); +- skb_queue_purge(&rtwdev->coex.queue); + spin_unlock_irqrestore(&rtwdev->tx_report.q_lock, flags); ++ skb_queue_purge(&rtwdev->coex.queue); ++ skb_queue_purge(&rtwdev->c2h_queue); + + list_for_each_entry_safe(rsvd_pkt, tmp, &rtwdev->rsvd_page_list, + build_list) { +-- +2.40.1 + diff --git a/queue-6.5/wifi-wil6210-fix-fortify-warnings.patch b/queue-6.5/wifi-wil6210-fix-fortify-warnings.patch new file mode 100644 index 00000000000..a92bdf7f6e4 --- /dev/null +++ b/queue-6.5/wifi-wil6210-fix-fortify-warnings.patch @@ -0,0 +1,127 @@ +From 21f2efbca8041458beb0daac19b6aea1ff0bbcb4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Jun 2023 12:36:55 +0300 +Subject: wifi: wil6210: fix fortify warnings +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Dmitry Antipov + +[ Upstream commit 1ad8237e971630c66a1a6194491e0837b64d00e0 ] + +When compiling with gcc 13.1 and CONFIG_FORTIFY_SOURCE=y, +I've noticed the following: + +In function ‘fortify_memcpy_chk’, + inlined from ‘wil_rx_crypto_check_edma’ at drivers/net/wireless/ath/wil6210/txrx_edma.c:566:2: +./include/linux/fortify-string.h:529:25: warning: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Wattribute-warning] + 529 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +where the compiler complains on: + +const u8 *pn; +... +pn = (u8 *)&st->ext.pn_15_0; +... +memcpy(cc->pn, pn, IEEE80211_GCMP_PN_LEN); + +and: + +In function ‘fortify_memcpy_chk’, + inlined from ‘wil_rx_crypto_check’ at drivers/net/wireless/ath/wil6210/txrx.c:684:2: +./include/linux/fortify-string.h:529:25: warning: call to ‘__read_overflow2_field’ +declared with attribute warning: detected read beyond size of field (2nd parameter); +maybe use struct_group()? [-Wattribute-warning] + 529 | __read_overflow2_field(q_size_field, size); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +where the compiler complains on: + +const u8 *pn = (u8 *)&d->mac.pn_15_0; +... +memcpy(cc->pn, pn, IEEE80211_GCMP_PN_LEN); + +In both cases, the fortification logic interprets 'memcpy()' as 6-byte +overread of 2-byte field 'pn_15_0' of 'struct wil_rx_status_extension' +and 'pn_15_0' of 'struct vring_rx_mac', respectively. To silence +these warnings, last two fields of the aforementioned structures +are grouped using 'struct_group_attr(pn, __packed' quirk. + +Signed-off-by: Dmitry Antipov +Signed-off-by: Kalle Valo +Link: https://lore.kernel.org/r/20230621093711.80118-1-dmantipov@yandex.ru +Signed-off-by: Sasha Levin +--- + drivers/net/wireless/ath/wil6210/txrx.c | 2 +- + drivers/net/wireless/ath/wil6210/txrx.h | 6 ++++-- + drivers/net/wireless/ath/wil6210/txrx_edma.c | 2 +- + drivers/net/wireless/ath/wil6210/txrx_edma.h | 6 ++++-- + 4 files changed, 10 insertions(+), 6 deletions(-) + +diff --git a/drivers/net/wireless/ath/wil6210/txrx.c b/drivers/net/wireless/ath/wil6210/txrx.c +index 237cbd5c5060b..f29ac6de71399 100644 +--- a/drivers/net/wireless/ath/wil6210/txrx.c ++++ b/drivers/net/wireless/ath/wil6210/txrx.c +@@ -666,7 +666,7 @@ static int wil_rx_crypto_check(struct wil6210_priv *wil, struct sk_buff *skb) + struct wil_tid_crypto_rx *c = mc ? &s->group_crypto_rx : + &s->tid_crypto_rx[tid]; + struct wil_tid_crypto_rx_single *cc = &c->key_id[key_id]; +- const u8 *pn = (u8 *)&d->mac.pn_15_0; ++ const u8 *pn = (u8 *)&d->mac.pn; + + if (!cc->key_set) { + wil_err_ratelimited(wil, +diff --git a/drivers/net/wireless/ath/wil6210/txrx.h b/drivers/net/wireless/ath/wil6210/txrx.h +index 1ae1bec1b97f1..689f68d89a440 100644 +--- a/drivers/net/wireless/ath/wil6210/txrx.h ++++ b/drivers/net/wireless/ath/wil6210/txrx.h +@@ -343,8 +343,10 @@ struct vring_rx_mac { + u32 d0; + u32 d1; + u16 w4; +- u16 pn_15_0; +- u32 pn_47_16; ++ struct_group_attr(pn, __packed, ++ u16 pn_15_0; ++ u32 pn_47_16; ++ ); + } __packed; + + /* Rx descriptor - DMA part +diff --git a/drivers/net/wireless/ath/wil6210/txrx_edma.c b/drivers/net/wireless/ath/wil6210/txrx_edma.c +index 201c8c35e0c9e..1ba1f21ebea26 100644 +--- a/drivers/net/wireless/ath/wil6210/txrx_edma.c ++++ b/drivers/net/wireless/ath/wil6210/txrx_edma.c +@@ -548,7 +548,7 @@ static int wil_rx_crypto_check_edma(struct wil6210_priv *wil, + s = &wil->sta[cid]; + c = mc ? &s->group_crypto_rx : &s->tid_crypto_rx[tid]; + cc = &c->key_id[key_id]; +- pn = (u8 *)&st->ext.pn_15_0; ++ pn = (u8 *)&st->ext.pn; + + if (!cc->key_set) { + wil_err_ratelimited(wil, +diff --git a/drivers/net/wireless/ath/wil6210/txrx_edma.h b/drivers/net/wireless/ath/wil6210/txrx_edma.h +index c736f7413a35f..ee90e225bb050 100644 +--- a/drivers/net/wireless/ath/wil6210/txrx_edma.h ++++ b/drivers/net/wireless/ath/wil6210/txrx_edma.h +@@ -330,8 +330,10 @@ struct wil_rx_status_extension { + u32 d0; + u32 d1; + __le16 seq_num; /* only lower 12 bits */ +- u16 pn_15_0; +- u32 pn_47_16; ++ struct_group_attr(pn, __packed, ++ u16 pn_15_0; ++ u32 pn_47_16; ++ ); + } __packed; + + struct wil_rx_status_extended { +-- +2.40.1 + diff --git a/queue-6.5/x86-amd_nb-add-pci-ids-for-amd-family-1ah-based-mode.patch b/queue-6.5/x86-amd_nb-add-pci-ids-for-amd-family-1ah-based-mode.patch new file mode 100644 index 00000000000..2ab63fe3a8a --- /dev/null +++ b/queue-6.5/x86-amd_nb-add-pci-ids-for-amd-family-1ah-based-mode.patch @@ -0,0 +1,88 @@ +From 62267dfba8f2fd09e19c2dc1cc61379f5de6c2c3 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 8 Aug 2023 22:52:42 -0500 +Subject: x86/amd_nb: Add PCI IDs for AMD Family 1Ah-based models + +From: Avadhut Naik + +[ Upstream commit c64016609b6f66b753b5f37929a191477fa584c0 ] + +Add new PCI Device IDs required to support AMD's new Family 1Ah-based +models 00h-1Fh, 20h and 40h-4Fh. + + [ bp: Zap a useless sentence. ] + +Co-developed-by: Mario Limonciello +Signed-off-by: Mario Limonciello +Signed-off-by: Avadhut Naik +Signed-off-by: Borislav Petkov (AMD) +Link: https://lore.kernel.org/r/20230809035244.2722455-2-avadhut.naik@amd.com +Signed-off-by: Sasha Levin +--- + arch/x86/kernel/amd_nb.c | 8 ++++++++ + include/linux/pci_ids.h | 2 ++ + 2 files changed, 10 insertions(+) + +diff --git a/arch/x86/kernel/amd_nb.c b/arch/x86/kernel/amd_nb.c +index 035a3db5330b0..356de955e78dd 100644 +--- a/arch/x86/kernel/amd_nb.c ++++ b/arch/x86/kernel/amd_nb.c +@@ -24,6 +24,8 @@ + #define PCI_DEVICE_ID_AMD_19H_M40H_ROOT 0x14b5 + #define PCI_DEVICE_ID_AMD_19H_M60H_ROOT 0x14d8 + #define PCI_DEVICE_ID_AMD_19H_M70H_ROOT 0x14e8 ++#define PCI_DEVICE_ID_AMD_1AH_M00H_ROOT 0x153a ++#define PCI_DEVICE_ID_AMD_1AH_M20H_ROOT 0x1507 + #define PCI_DEVICE_ID_AMD_MI200_ROOT 0x14bb + + #define PCI_DEVICE_ID_AMD_17H_DF_F4 0x1464 +@@ -39,6 +41,7 @@ + #define PCI_DEVICE_ID_AMD_19H_M60H_DF_F4 0x14e4 + #define PCI_DEVICE_ID_AMD_19H_M70H_DF_F4 0x14f4 + #define PCI_DEVICE_ID_AMD_19H_M78H_DF_F4 0x12fc ++#define PCI_DEVICE_ID_AMD_1AH_M00H_DF_F4 0x12c4 + #define PCI_DEVICE_ID_AMD_MI200_DF_F4 0x14d4 + + /* Protect the PCI config register pairs used for SMN. */ +@@ -56,6 +59,8 @@ static const struct pci_device_id amd_root_ids[] = { + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M40H_ROOT) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M60H_ROOT) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M70H_ROOT) }, ++ { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_1AH_M00H_ROOT) }, ++ { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_1AH_M20H_ROOT) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_MI200_ROOT) }, + {} + }; +@@ -85,6 +90,8 @@ static const struct pci_device_id amd_nb_misc_ids[] = { + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M60H_DF_F3) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M70H_DF_F3) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M78H_DF_F3) }, ++ { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_1AH_M00H_DF_F3) }, ++ { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_1AH_M20H_DF_F3) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_MI200_DF_F3) }, + {} + }; +@@ -106,6 +113,7 @@ static const struct pci_device_id amd_nb_link_ids[] = { + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M40H_DF_F4) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_19H_M50H_DF_F4) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_CNB17H_F4) }, ++ { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_1AH_M00H_DF_F4) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_MI200_DF_F4) }, + {} + }; +diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h +index 2dc75df1437fb..8f9a459e16718 100644 +--- a/include/linux/pci_ids.h ++++ b/include/linux/pci_ids.h +@@ -576,6 +576,8 @@ + #define PCI_DEVICE_ID_AMD_19H_M60H_DF_F3 0x14e3 + #define PCI_DEVICE_ID_AMD_19H_M70H_DF_F3 0x14f3 + #define PCI_DEVICE_ID_AMD_19H_M78H_DF_F3 0x12fb ++#define PCI_DEVICE_ID_AMD_1AH_M00H_DF_F3 0x12c3 ++#define PCI_DEVICE_ID_AMD_1AH_M20H_DF_F3 0x16fb + #define PCI_DEVICE_ID_AMD_MI200_DF_F3 0x14d3 + #define PCI_DEVICE_ID_AMD_CNB17H_F3 0x1703 + #define PCI_DEVICE_ID_AMD_LANCE 0x2000 +-- +2.40.1 + diff --git a/queue-6.5/x86-boot-compressed-reserve-more-memory-for-page-tab.patch b/queue-6.5/x86-boot-compressed-reserve-more-memory-for-page-tab.patch new file mode 100644 index 00000000000..9618ccf6fc5 --- /dev/null +++ b/queue-6.5/x86-boot-compressed-reserve-more-memory-for-page-tab.patch @@ -0,0 +1,123 @@ +From 5b8bba4dc3e5f5487fbd315502e7c6d606fa24ee Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 15 Sep 2023 10:02:21 +0300 +Subject: x86/boot/compressed: Reserve more memory for page tables + +From: Kirill A. Shutemov + +[ Upstream commit f530ee95b72e77b09c141c4b1a4b94d1199ffbd9 ] + +The decompressor has a hard limit on the number of page tables it can +allocate. This limit is defined at compile-time and will cause boot +failure if it is reached. + +The kernel is very strict and calculates the limit precisely for the +worst-case scenario based on the current configuration. However, it is +easy to forget to adjust the limit when a new use-case arises. The +worst-case scenario is rarely encountered during sanity checks. + +In the case of enabling 5-level paging, a use-case was overlooked. The +limit needs to be increased by one to accommodate the additional level. +This oversight went unnoticed until Aaron attempted to run the kernel +via kexec with 5-level paging and unaccepted memory enabled. + +Update wost-case calculations to include 5-level paging. + +To address this issue, let's allocate some extra space for page tables. +128K should be sufficient for any use-case. The logic can be simplified +by using a single value for all kernel configurations. + +[ Also add a warning, should this memory run low - by Dave Hansen. ] + +Fixes: 34bbb0009f3b ("x86/boot/compressed: Enable 5-level paging during decompression stage") +Reported-by: Aaron Lu +Signed-off-by: Kirill A. Shutemov +Signed-off-by: Ingo Molnar +Link: https://lore.kernel.org/r/20230915070221.10266-1-kirill.shutemov@linux.intel.com +Signed-off-by: Sasha Levin +--- + arch/x86/boot/compressed/ident_map_64.c | 8 +++++ + arch/x86/include/asm/boot.h | 45 +++++++++++++++++-------- + 2 files changed, 39 insertions(+), 14 deletions(-) + +diff --git a/arch/x86/boot/compressed/ident_map_64.c b/arch/x86/boot/compressed/ident_map_64.c +index bcc956c17872b..08f93b0401bbd 100644 +--- a/arch/x86/boot/compressed/ident_map_64.c ++++ b/arch/x86/boot/compressed/ident_map_64.c +@@ -59,6 +59,14 @@ static void *alloc_pgt_page(void *context) + return NULL; + } + ++ /* Consumed more tables than expected? */ ++ if (pages->pgt_buf_offset == BOOT_PGT_SIZE_WARN) { ++ debug_putstr("pgt_buf running low in " __FILE__ "\n"); ++ debug_putstr("Need to raise BOOT_PGT_SIZE?\n"); ++ debug_putaddr(pages->pgt_buf_offset); ++ debug_putaddr(pages->pgt_buf_size); ++ } ++ + entry = pages->pgt_buf + pages->pgt_buf_offset; + pages->pgt_buf_offset += PAGE_SIZE; + +diff --git a/arch/x86/include/asm/boot.h b/arch/x86/include/asm/boot.h +index 9191280d9ea31..215d37f7dde8a 100644 +--- a/arch/x86/include/asm/boot.h ++++ b/arch/x86/include/asm/boot.h +@@ -40,23 +40,40 @@ + #ifdef CONFIG_X86_64 + # define BOOT_STACK_SIZE 0x4000 + ++/* ++ * Used by decompressor's startup_32() to allocate page tables for identity ++ * mapping of the 4G of RAM in 4-level paging mode: ++ * - 1 level4 table; ++ * - 1 level3 table; ++ * - 4 level2 table that maps everything with 2M pages; ++ * ++ * The additional level5 table needed for 5-level paging is allocated from ++ * trampoline_32bit memory. ++ */ + # define BOOT_INIT_PGT_SIZE (6*4096) +-# ifdef CONFIG_RANDOMIZE_BASE ++ + /* +- * Assuming all cross the 512GB boundary: +- * 1 page for level4 +- * (2+2)*4 pages for kernel, param, cmd_line, and randomized kernel +- * 2 pages for first 2M (video RAM: CONFIG_X86_VERBOSE_BOOTUP). +- * Total is 19 pages. ++ * Total number of page tables kernel_add_identity_map() can allocate, ++ * including page tables consumed by startup_32(). ++ * ++ * Worst-case scenario: ++ * - 5-level paging needs 1 level5 table; ++ * - KASLR needs to map kernel, boot_params, cmdline and randomized kernel, ++ * assuming all of them cross 256T boundary: ++ * + 4*2 level4 table; ++ * + 4*2 level3 table; ++ * + 4*2 level2 table; ++ * - X86_VERBOSE_BOOTUP needs to map the first 2M (video RAM): ++ * + 1 level4 table; ++ * + 1 level3 table; ++ * + 1 level2 table; ++ * Total: 28 tables ++ * ++ * Add 4 spare table in case decompressor touches anything beyond what is ++ * accounted above. Warn if it happens. + */ +-# ifdef CONFIG_X86_VERBOSE_BOOTUP +-# define BOOT_PGT_SIZE (19*4096) +-# else /* !CONFIG_X86_VERBOSE_BOOTUP */ +-# define BOOT_PGT_SIZE (17*4096) +-# endif +-# else /* !CONFIG_RANDOMIZE_BASE */ +-# define BOOT_PGT_SIZE BOOT_INIT_PGT_SIZE +-# endif ++# define BOOT_PGT_SIZE_WARN (28*4096) ++# define BOOT_PGT_SIZE (32*4096) + + #else /* !CONFIG_X86_64 */ + # define BOOT_STACK_SIZE 0x1000 +-- +2.40.1 + diff --git a/queue-6.5/x86-bring-back-rep-movsq-for-user-access-on-cpus-wit.patch b/queue-6.5/x86-bring-back-rep-movsq-for-user-access-on-cpus-wit.patch new file mode 100644 index 00000000000..9b803aff56d --- /dev/null +++ b/queue-6.5/x86-bring-back-rep-movsq-for-user-access-on-cpus-wit.patch @@ -0,0 +1,140 @@ +From a0dbcc380f71bc780c75cd497608850941f98d41 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 30 Aug 2023 16:03:15 +0200 +Subject: x86: bring back rep movsq for user access on CPUs without ERMS + +From: Mateusz Guzik + +[ Upstream commit ca96b162bfd21a5d55e3cd6099e4ee357a0eeb68 ] + +Intel CPUs ship with ERMS for over a decade, but this is not true for +AMD. In particular one reasonably recent uarch (EPYC 7R13) does not +have it (or at least the bit is inactive when running on the Amazon EC2 +cloud -- I found rather conflicting information about AMD CPUs vs the +extension). + +Hand-rolled mov loops executing in this case are quite pessimal compared +to rep movsq for bigger sizes. While the upper limit depends on uarch, +everyone is well south of 1KB AFAICS and sizes bigger than that are +common. + +While technically ancient CPUs may be suffering from rep usage, gcc has +been emitting it for years all over kernel code, so I don't think this +is a legitimate concern. + +Sample result from read1_processes from will-it-scale (4KB reads/s): + + before: 1507021 + after: 1721828 (+14%) + +Note that the cutoff point for rep usage is set to 64 bytes, which is +way too conservative but I'm sticking to what was done in 47ee3f1dd93b +("x86: re-introduce support for ERMS copies for user space accesses"). +That is to say *some* copies will now go slower, which is fixable but +beyond the scope of this patch. + +Signed-off-by: Mateusz Guzik +Signed-off-by: Linus Torvalds +Signed-off-by: Sasha Levin +--- + arch/x86/include/asm/uaccess_64.h | 2 +- + arch/x86/lib/copy_user_64.S | 57 +++++++------------------------ + 2 files changed, 14 insertions(+), 45 deletions(-) + +diff --git a/arch/x86/include/asm/uaccess_64.h b/arch/x86/include/asm/uaccess_64.h +index 81b826d3b7530..f2c02e4469ccc 100644 +--- a/arch/x86/include/asm/uaccess_64.h ++++ b/arch/x86/include/asm/uaccess_64.h +@@ -116,7 +116,7 @@ copy_user_generic(void *to, const void *from, unsigned long len) + "2:\n" + _ASM_EXTABLE_UA(1b, 2b) + :"+c" (len), "+D" (to), "+S" (from), ASM_CALL_CONSTRAINT +- : : "memory", "rax", "r8", "r9", "r10", "r11"); ++ : : "memory", "rax"); + clac(); + return len; + } +diff --git a/arch/x86/lib/copy_user_64.S b/arch/x86/lib/copy_user_64.S +index 01c5de4c279b8..0a81aafed7f88 100644 +--- a/arch/x86/lib/copy_user_64.S ++++ b/arch/x86/lib/copy_user_64.S +@@ -27,7 +27,7 @@ + * NOTE! The calling convention is very intentionally the same as + * for 'rep movs', so that we can rewrite the function call with + * just a plain 'rep movs' on machines that have FSRM. But to make +- * it simpler for us, we can clobber rsi/rdi and rax/r8-r11 freely. ++ * it simpler for us, we can clobber rsi/rdi and rax freely. + */ + SYM_FUNC_START(rep_movs_alternative) + cmpq $64,%rcx +@@ -68,55 +68,24 @@ SYM_FUNC_START(rep_movs_alternative) + _ASM_EXTABLE_UA( 3b, .Lcopy_user_tail) + + .Llarge: +-0: ALTERNATIVE "jmp .Lunrolled", "rep movsb", X86_FEATURE_ERMS ++0: ALTERNATIVE "jmp .Llarge_movsq", "rep movsb", X86_FEATURE_ERMS + 1: RET + +- _ASM_EXTABLE_UA( 0b, 1b) ++ _ASM_EXTABLE_UA( 0b, 1b) + +- .p2align 4 +-.Lunrolled: +-10: movq (%rsi),%r8 +-11: movq 8(%rsi),%r9 +-12: movq 16(%rsi),%r10 +-13: movq 24(%rsi),%r11 +-14: movq %r8,(%rdi) +-15: movq %r9,8(%rdi) +-16: movq %r10,16(%rdi) +-17: movq %r11,24(%rdi) +-20: movq 32(%rsi),%r8 +-21: movq 40(%rsi),%r9 +-22: movq 48(%rsi),%r10 +-23: movq 56(%rsi),%r11 +-24: movq %r8,32(%rdi) +-25: movq %r9,40(%rdi) +-26: movq %r10,48(%rdi) +-27: movq %r11,56(%rdi) +- addq $64,%rsi +- addq $64,%rdi +- subq $64,%rcx +- cmpq $64,%rcx +- jae .Lunrolled +- cmpl $8,%ecx +- jae .Lword ++.Llarge_movsq: ++ movq %rcx,%rax ++ shrq $3,%rcx ++ andl $7,%eax ++0: rep movsq ++ movl %eax,%ecx + testl %ecx,%ecx + jne .Lcopy_user_tail + RET + +- _ASM_EXTABLE_UA(10b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(11b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(12b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(13b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(14b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(15b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(16b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(17b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(20b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(21b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(22b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(23b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(24b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(25b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(26b, .Lcopy_user_tail) +- _ASM_EXTABLE_UA(27b, .Lcopy_user_tail) ++1: leaq (%rax,%rcx,8),%rcx ++ jmp .Lcopy_user_tail ++ ++ _ASM_EXTABLE_UA( 0b, 1b) + SYM_FUNC_END(rep_movs_alternative) + EXPORT_SYMBOL(rep_movs_alternative) +-- +2.40.1 + diff --git a/queue-6.5/x86-ibt-avoid-duplicate-endbr-in-__put_user_nocheck.patch b/queue-6.5/x86-ibt-avoid-duplicate-endbr-in-__put_user_nocheck.patch new file mode 100644 index 00000000000..8faf9ffd20d --- /dev/null +++ b/queue-6.5/x86-ibt-avoid-duplicate-endbr-in-__put_user_nocheck.patch @@ -0,0 +1,64 @@ +From 7d2238c090feb2c330f6af0df0506538e4b488e1 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 2 Aug 2023 12:55:47 +0200 +Subject: x86/ibt: Avoid duplicate ENDBR in __put_user_nocheck*() + +From: Peter Zijlstra + +[ Upstream commit 7575e5a35267983dcbeb1e0d3a49d21ae3cf0b82 ] + +Commit cb855971d717 ("x86/putuser: Provide room for padding") changed +__put_user_nocheck_*() into proper functions but failed to note that +SYM_FUNC_START() already provides ENDBR, rendering the explicit ENDBR +superfluous. + +Fixes: cb855971d717 ("x86/putuser: Provide room for padding") +Reported-by: David Kaplan +Reviewed-by: Andrew Cooper +Signed-off-by: Peter Zijlstra (Intel) +Signed-off-by: Ingo Molnar +Link: https://lore.kernel.org/r/20230802110323.086971726@infradead.org +Signed-off-by: Sasha Levin +--- + arch/x86/lib/putuser.S | 4 ---- + 1 file changed, 4 deletions(-) + +diff --git a/arch/x86/lib/putuser.S b/arch/x86/lib/putuser.S +index 1451e0c4ae22a..235bbda6fc823 100644 +--- a/arch/x86/lib/putuser.S ++++ b/arch/x86/lib/putuser.S +@@ -56,7 +56,6 @@ SYM_FUNC_END(__put_user_1) + EXPORT_SYMBOL(__put_user_1) + + SYM_FUNC_START(__put_user_nocheck_1) +- ENDBR + ASM_STAC + 2: movb %al,(%_ASM_CX) + xor %ecx,%ecx +@@ -76,7 +75,6 @@ SYM_FUNC_END(__put_user_2) + EXPORT_SYMBOL(__put_user_2) + + SYM_FUNC_START(__put_user_nocheck_2) +- ENDBR + ASM_STAC + 4: movw %ax,(%_ASM_CX) + xor %ecx,%ecx +@@ -96,7 +94,6 @@ SYM_FUNC_END(__put_user_4) + EXPORT_SYMBOL(__put_user_4) + + SYM_FUNC_START(__put_user_nocheck_4) +- ENDBR + ASM_STAC + 6: movl %eax,(%_ASM_CX) + xor %ecx,%ecx +@@ -119,7 +116,6 @@ SYM_FUNC_END(__put_user_8) + EXPORT_SYMBOL(__put_user_8) + + SYM_FUNC_START(__put_user_nocheck_8) +- ENDBR + ASM_STAC + 9: mov %_ASM_AX,(%_ASM_CX) + #ifdef CONFIG_X86_32 +-- +2.40.1 + diff --git a/queue-6.5/x86-ibt-suppress-spurious-endbr.patch b/queue-6.5/x86-ibt-suppress-spurious-endbr.patch new file mode 100644 index 00000000000..0006c6e6a33 --- /dev/null +++ b/queue-6.5/x86-ibt-suppress-spurious-endbr.patch @@ -0,0 +1,70 @@ +From a60926a3232694d9a0d1ec9e2a8542febfde6377 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 2 Aug 2023 12:55:46 +0200 +Subject: x86/ibt: Suppress spurious ENDBR + +From: Peter Zijlstra + +[ Upstream commit 25e73b7e3f72a25aa30cbb2eecb49036e0acf066 ] + +It was reported that under certain circumstances GCC emits ENDBR +instructions for _THIS_IP_ usage. Specifically, when it appears at the +start of a basic block -- but not elsewhere. + +Since _THIS_IP_ is never used for control flow, these ENDBR +instructions are completely superfluous. Override the _THIS_IP_ +definition for x86_64 to avoid this. + +Less ENDBR instructions is better. + +Fixes: 156ff4a544ae ("x86/ibt: Base IBT bits") +Reported-by: David Kaplan +Reviewed-by: Andrew Cooper +Signed-off-by: Peter Zijlstra (Intel) +Signed-off-by: Ingo Molnar +Link: https://lore.kernel.org/r/20230802110323.016197440@infradead.org +Signed-off-by: Sasha Levin +--- + arch/x86/include/asm/linkage.h | 8 ++++++++ + include/linux/instruction_pointer.h | 5 +++++ + 2 files changed, 13 insertions(+) + +diff --git a/arch/x86/include/asm/linkage.h b/arch/x86/include/asm/linkage.h +index 97a3de7892d3f..5ff49fd67732e 100644 +--- a/arch/x86/include/asm/linkage.h ++++ b/arch/x86/include/asm/linkage.h +@@ -8,6 +8,14 @@ + #undef notrace + #define notrace __attribute__((no_instrument_function)) + ++#ifdef CONFIG_64BIT ++/* ++ * The generic version tends to create spurious ENDBR instructions under ++ * certain conditions. ++ */ ++#define _THIS_IP_ ({ unsigned long __here; asm ("lea 0(%%rip), %0" : "=r" (__here)); __here; }) ++#endif ++ + #ifdef CONFIG_X86_32 + #define asmlinkage CPP_ASMLINKAGE __attribute__((regparm(0))) + #endif /* CONFIG_X86_32 */ +diff --git a/include/linux/instruction_pointer.h b/include/linux/instruction_pointer.h +index cda1f706eaeb1..aa0b3ffea9353 100644 +--- a/include/linux/instruction_pointer.h ++++ b/include/linux/instruction_pointer.h +@@ -2,7 +2,12 @@ + #ifndef _LINUX_INSTRUCTION_POINTER_H + #define _LINUX_INSTRUCTION_POINTER_H + ++#include ++ + #define _RET_IP_ (unsigned long)__builtin_return_address(0) ++ ++#ifndef _THIS_IP_ + #define _THIS_IP_ ({ __label__ __here; __here: (unsigned long)&&__here; }) ++#endif + + #endif /* _LINUX_INSTRUCTION_POINTER_H */ +-- +2.40.1 + diff --git a/queue-6.5/x86-purgatory-remove-lto-flags.patch b/queue-6.5/x86-purgatory-remove-lto-flags.patch new file mode 100644 index 00000000000..2325bf77ad9 --- /dev/null +++ b/queue-6.5/x86-purgatory-remove-lto-flags.patch @@ -0,0 +1,63 @@ +From b9c6c5360df5c9632ed07e9fd54b981d9900bd84 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 14 Sep 2023 10:01:38 -0700 +Subject: x86/purgatory: Remove LTO flags + +From: Song Liu + +[ Upstream commit 75b2f7e4c9e0fd750a5a27ca9736d1daa7a3762a ] + +-flto* implies -ffunction-sections. With LTO enabled, ld.lld generates +multiple .text sections for purgatory.ro: + + $ readelf -S purgatory.ro | grep " .text" + [ 1] .text PROGBITS 0000000000000000 00000040 + [ 7] .text.purgatory PROGBITS 0000000000000000 000020e0 + [ 9] .text.warn PROGBITS 0000000000000000 000021c0 + [13] .text.sha256_upda PROGBITS 0000000000000000 000022f0 + [15] .text.sha224_upda PROGBITS 0000000000000000 00002be0 + [17] .text.sha256_fina PROGBITS 0000000000000000 00002bf0 + [19] .text.sha224_fina PROGBITS 0000000000000000 00002cc0 + +This causes WARNING from kexec_purgatory_setup_sechdrs(): + + WARNING: CPU: 26 PID: 110894 at kernel/kexec_file.c:919 + kexec_load_purgatory+0x37f/0x390 + +Fix this by disabling LTO for purgatory. + +[ AFAICT, x86 is the only arch that supports LTO and purgatory. ] + +We could also fix this with an explicit linker script to rejoin .text.* +sections back into .text. However, given the benefit of LTOing purgatory +is small, simply disable the production of more .text.* sections for now. + +Fixes: b33fff07e3e3 ("x86, build: allow LTO to be selected") +Signed-off-by: Song Liu +Signed-off-by: Ingo Molnar +Reviewed-by: Nick Desaulniers +Reviewed-by: Sami Tolvanen +Link: https://lore.kernel.org/r/20230914170138.995606-1-song@kernel.org +Signed-off-by: Sasha Levin +--- + arch/x86/purgatory/Makefile | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/arch/x86/purgatory/Makefile b/arch/x86/purgatory/Makefile +index c2a29be35c01b..08aa0f25f12a0 100644 +--- a/arch/x86/purgatory/Makefile ++++ b/arch/x86/purgatory/Makefile +@@ -19,6 +19,10 @@ CFLAGS_sha256.o := -D__DISABLE_EXPORTS -D__NO_FORTIFY + # optimization flags. + KBUILD_CFLAGS := $(filter-out -fprofile-sample-use=% -fprofile-use=%,$(KBUILD_CFLAGS)) + ++# When LTO is enabled, llvm emits many text sections, which is not supported ++# by kexec. Remove -flto=* flags. ++KBUILD_CFLAGS := $(filter-out $(CC_FLAGS_LTO),$(KBUILD_CFLAGS)) ++ + # When linking purgatory.ro with -r unresolved symbols are not checked, + # also link a purgatory.chk binary without -r to check for unresolved symbols. + PURGATORY_LDFLAGS := -e purgatory_start -z nodefaultlib +-- +2.40.1 + diff --git a/queue-6.5/x86-sched-restore-the-sd_asym_packing-flag-in-the-di.patch b/queue-6.5/x86-sched-restore-the-sd_asym_packing-flag-in-the-di.patch new file mode 100644 index 00000000000..a3bd3306f7a --- /dev/null +++ b/queue-6.5/x86-sched-restore-the-sd_asym_packing-flag-in-the-di.patch @@ -0,0 +1,70 @@ +From 9f54b64afe19c51fe0c08de919d7e227a26365d9 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 14 Aug 2023 20:57:47 -0700 +Subject: x86/sched: Restore the SD_ASYM_PACKING flag in the DIE domain + +From: Ricardo Neri + +[ Upstream commit 108af4b4bd3813610701379a58538e3339b162e4 ] + +Commit 8f2d6c41e5a6 ("x86/sched: Rewrite topology setup") dropped the +SD_ASYM_PACKING flag in the DIE domain added in commit 044f0e27dec6 +("x86/sched: Add the SD_ASYM_PACKING flag to the die domain of hybrid +processors"). Restore it on hybrid processors. + +The die-level domain does not depend on any build configuration and now +x86_sched_itmt_flags() is always needed. Remove the build dependency on +CONFIG_SCHED_[SMT|CLUSTER|MC]. + +Fixes: 8f2d6c41e5a6 ("x86/sched: Rewrite topology setup") +Signed-off-by: Ricardo Neri +Signed-off-by: Peter Zijlstra (Intel) +Signed-off-by: Ingo Molnar +Reviewed-by: Chen Yu +Tested-by: Caleb Callaway +Link: https://lkml.kernel.org/r/20230815035747.11529-1-ricardo.neri-calderon@linux.intel.com +Signed-off-by: Sasha Levin +--- + arch/x86/kernel/smpboot.c | 12 +++++++++--- + 1 file changed, 9 insertions(+), 3 deletions(-) + +diff --git a/arch/x86/kernel/smpboot.c b/arch/x86/kernel/smpboot.c +index 7d82f0bd449c7..747b83a373a2d 100644 +--- a/arch/x86/kernel/smpboot.c ++++ b/arch/x86/kernel/smpboot.c +@@ -587,7 +587,6 @@ static bool match_llc(struct cpuinfo_x86 *c, struct cpuinfo_x86 *o) + } + + +-#if defined(CONFIG_SCHED_SMT) || defined(CONFIG_SCHED_CLUSTER) || defined(CONFIG_SCHED_MC) + static inline int x86_sched_itmt_flags(void) + { + return sysctl_sched_itmt_enabled ? SD_ASYM_PACKING : 0; +@@ -611,7 +610,14 @@ static int x86_cluster_flags(void) + return cpu_cluster_flags() | x86_sched_itmt_flags(); + } + #endif +-#endif ++ ++static int x86_die_flags(void) ++{ ++ if (cpu_feature_enabled(X86_FEATURE_HYBRID_CPU)) ++ return x86_sched_itmt_flags(); ++ ++ return 0; ++} + + /* + * Set if a package/die has multiple NUMA nodes inside. +@@ -653,7 +659,7 @@ static void __init build_sched_topology(void) + */ + if (!x86_has_numa_in_package) { + x86_topology[i++] = (struct sched_domain_topology_level){ +- cpu_cpu_mask, SD_INIT_NAME(DIE) ++ cpu_cpu_mask, x86_die_flags, SD_INIT_NAME(DIE) + }; + } + +-- +2.40.1 +