From: Sasha Levin Date: Sun, 3 Mar 2024 15:56:42 +0000 (-0500) Subject: Fixes for 6.7 X-Git-Tag: v4.19.309~92^2~6 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=dbc0ba14eb81edbb5987d91aabebd9a2bf37c240;p=thirdparty%2Fkernel%2Fstable-queue.git Fixes for 6.7 Signed-off-by: Sasha Levin --- diff --git a/queue-6.7/afs-fix-endless-loop-in-directory-parsing.patch b/queue-6.7/afs-fix-endless-loop-in-directory-parsing.patch new file mode 100644 index 00000000000..38c429a379b --- /dev/null +++ b/queue-6.7/afs-fix-endless-loop-in-directory-parsing.patch @@ -0,0 +1,68 @@ +From ca35a5363c00b56f05f5bb5427c4acdb9bced452 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 23 Feb 2024 13:15:02 +0000 +Subject: afs: Fix endless loop in directory parsing + +From: David Howells + +[ Upstream commit 5f7a07646655fb4108da527565dcdc80124b14c4 ] + +If a directory has a block with only ".__afsXXXX" files in it (from +uncompleted silly-rename), these .__afsXXXX files are skipped but without +advancing the file position in the dir_context. This leads to +afs_dir_iterate() repeating the block again and again. + +Fix this by making the code that skips the .__afsXXXX file also manually +advance the file position. + +The symptoms are a soft lookup: + + watchdog: BUG: soft lockup - CPU#3 stuck for 52s! [check:5737] + ... + RIP: 0010:afs_dir_iterate_block+0x39/0x1fd + ... + ? watchdog_timer_fn+0x1a6/0x213 + ... + ? asm_sysvec_apic_timer_interrupt+0x16/0x20 + ? afs_dir_iterate_block+0x39/0x1fd + afs_dir_iterate+0x10a/0x148 + afs_readdir+0x30/0x4a + iterate_dir+0x93/0xd3 + __do_sys_getdents64+0x6b/0xd4 + +This is almost certainly the actual fix for: + + https://bugzilla.kernel.org/show_bug.cgi?id=218496 + +Fixes: 57e9d49c5452 ("afs: Hide silly-rename files from userspace") +Signed-off-by: David Howells +Link: https://lore.kernel.org/r/786185.1708694102@warthog.procyon.org.uk +Reviewed-by: Marc Dionne +cc: Marc Dionne +cc: Markus Suvanto +cc: linux-afs@lists.infradead.org +Signed-off-by: Christian Brauner +Signed-off-by: Sasha Levin +--- + fs/afs/dir.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/fs/afs/dir.c b/fs/afs/dir.c +index 9140780be5a43..c097da6e9c5b2 100644 +--- a/fs/afs/dir.c ++++ b/fs/afs/dir.c +@@ -479,8 +479,10 @@ static int afs_dir_iterate_block(struct afs_vnode *dvnode, + dire->u.name[0] == '.' && + ctx->actor != afs_lookup_filldir && + ctx->actor != afs_lookup_one_filldir && +- memcmp(dire->u.name, ".__afs", 6) == 0) ++ memcmp(dire->u.name, ".__afs", 6) == 0) { ++ ctx->pos = blkoff + next * sizeof(union afs_xdr_dirent); + continue; ++ } + + /* found the next entry */ + if (!dir_emit(ctx, dire->u.name, nlen, +-- +2.43.0 + diff --git a/queue-6.7/alsa-drop-leftover-snd-rtctimer-stuff-from-makefile.patch b/queue-6.7/alsa-drop-leftover-snd-rtctimer-stuff-from-makefile.patch new file mode 100644 index 00000000000..3ed42c66166 --- /dev/null +++ b/queue-6.7/alsa-drop-leftover-snd-rtctimer-stuff-from-makefile.patch @@ -0,0 +1,35 @@ +From 9c8de20152b61440b805ef9bed510686ab8ec783 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 10:21:56 +0100 +Subject: ALSA: Drop leftover snd-rtctimer stuff from Makefile + +From: Takashi Iwai + +[ Upstream commit 4df49712eb54141be00a9312547436d55677f092 ] + +We forgot to remove the line for snd-rtctimer from Makefile while +dropping the functionality. Get rid of the stale line. + +Fixes: 34ce71a96dcb ("ALSA: timer: remove legacy rtctimer") +Link: https://lore.kernel.org/r/20240221092156.28695-1-tiwai@suse.de +Signed-off-by: Takashi Iwai +Signed-off-by: Sasha Levin +--- + sound/core/Makefile | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/sound/core/Makefile b/sound/core/Makefile +index a6b444ee28326..f6526b3371375 100644 +--- a/sound/core/Makefile ++++ b/sound/core/Makefile +@@ -32,7 +32,6 @@ snd-ump-objs := ump.o + snd-ump-$(CONFIG_SND_UMP_LEGACY_RAWMIDI) += ump_convert.o + snd-timer-objs := timer.o + snd-hrtimer-objs := hrtimer.o +-snd-rtctimer-objs := rtctimer.o + snd-hwdep-objs := hwdep.o + snd-seq-device-objs := seq_device.o + +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-cs35l56_component_remove-must-clean-up-.patch b/queue-6.7/asoc-cs35l56-cs35l56_component_remove-must-clean-up-.patch new file mode 100644 index 00000000000..197ff6396b3 --- /dev/null +++ b/queue-6.7/asoc-cs35l56-cs35l56_component_remove-must-clean-up-.patch @@ -0,0 +1,41 @@ +From 996b75cb975241da5638351d1d1b152a9fa3e8fb Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 29 Jan 2024 16:27:23 +0000 +Subject: ASoC: cs35l56: cs35l56_component_remove() must clean up wm_adsp + +From: Richard Fitzgerald + +[ Upstream commit cd38ccbecdace1469b4e0cfb3ddeec72a3fad226 ] + +cs35l56_component_remove() must call wm_adsp_power_down() and +wm_adsp2_component_remove(). + +Signed-off-by: Richard Fitzgerald +Fixes: e49611252900 ("ASoC: cs35l56: Add driver for Cirrus Logic CS35L56") +Link: https://msgid.link/r/20240129162737.497-5-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()") +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56.c | 5 +++++ + 1 file changed, 5 insertions(+) + +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index 09944db4db30d..491da77112c34 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -810,6 +810,11 @@ static void cs35l56_component_remove(struct snd_soc_component *component) + + cancel_work_sync(&cs35l56->dsp_work); + ++ if (cs35l56->dsp.cs_dsp.booted) ++ wm_adsp_power_down(&cs35l56->dsp); ++ ++ wm_adsp2_component_remove(&cs35l56->dsp, component); ++ + cs35l56->component = NULL; + } + +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-cs35l56_component_remove-must-clear-cs3.patch b/queue-6.7/asoc-cs35l56-cs35l56_component_remove-must-clear-cs3.patch new file mode 100644 index 00000000000..e3afa9cd8c7 --- /dev/null +++ b/queue-6.7/asoc-cs35l56-cs35l56_component_remove-must-clear-cs3.patch @@ -0,0 +1,42 @@ +From 64888a4b48409566fd30fbc6e4bdb477f6444913 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 29 Jan 2024 16:27:22 +0000 +Subject: ASoC: cs35l56: cs35l56_component_remove() must clear + cs35l56->component + +From: Richard Fitzgerald + +[ Upstream commit ae861c466ee57e15a29d97629e1c564e3f714a4f ] + +The cs35l56->component pointer is used by the suspend-resume handling to +know whether the driver is fully instantiated. This is to prevent it +queuing dsp_work which would result in calling wm_adsp when the driver +is not an instantiated ASoC component. So this pointer must be cleared +by cs35l56_component_remove(). + +Signed-off-by: Richard Fitzgerald +Fixes: e49611252900 ("ASoC: cs35l56: Add driver for Cirrus Logic CS35L56") +Link: https://msgid.link/r/20240129162737.497-4-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()") +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index 45b4de3eff94f..09944db4db30d 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -809,6 +809,8 @@ static void cs35l56_component_remove(struct snd_soc_component *component) + struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); + + cancel_work_sync(&cs35l56->dsp_work); ++ ++ cs35l56->component = NULL; + } + + static int cs35l56_set_bias_level(struct snd_soc_component *component, +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-don-t-add-the-same-register-patch-multi.patch b/queue-6.7/asoc-cs35l56-don-t-add-the-same-register-patch-multi.patch new file mode 100644 index 00000000000..e16a6926a31 --- /dev/null +++ b/queue-6.7/asoc-cs35l56-don-t-add-the-same-register-patch-multi.patch @@ -0,0 +1,55 @@ +From ff65344b3059886efc7e90115671f45f98c70f05 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 29 Jan 2024 16:27:24 +0000 +Subject: ASoC: cs35l56: Don't add the same register patch multiple times + +From: Richard Fitzgerald + +[ Upstream commit 07687cd0539f8185b6ba0c0afba8473517116d6a ] + +Move the call to cs35l56_set_patch() earlier in cs35l56_init() so +that it only adds the register patch on first-time initialization. + +The call was after the post_soft_reset label, so every time this +function was run to re-initialize the hardware after a reset it would +call regmap_register_patch() and add the same reg_sequence again. + +Signed-off-by: Richard Fitzgerald +Fixes: 898673b905b9 ("ASoC: cs35l56: Move shared data into a common data structure") +Link: https://msgid.link/r/20240129162737.497-6-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()") +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56.c | 8 ++++---- + 1 file changed, 4 insertions(+), 4 deletions(-) + +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index 491da77112c34..ea5d2b2eb82a0 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -1159,6 +1159,10 @@ int cs35l56_init(struct cs35l56_private *cs35l56) + if (ret < 0) + return ret; + ++ ret = cs35l56_set_patch(&cs35l56->base); ++ if (ret) ++ return ret; ++ + /* Populate the DSP information with the revision and security state */ + cs35l56->dsp.part = devm_kasprintf(cs35l56->base.dev, GFP_KERNEL, "cs35l56%s-%02x", + cs35l56->base.secured ? "s" : "", cs35l56->base.rev); +@@ -1197,10 +1201,6 @@ int cs35l56_init(struct cs35l56_private *cs35l56) + if (ret) + return ret; + +- ret = cs35l56_set_patch(&cs35l56->base); +- if (ret) +- return ret; +- + /* Registers could be dirty after soft reset or SoundWire enumeration */ + regcache_sync(cs35l56->base.regmap); + +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-fix-deadlock-in-asp1-mixer-register-ini.patch b/queue-6.7/asoc-cs35l56-fix-deadlock-in-asp1-mixer-register-ini.patch new file mode 100644 index 00000000000..9e56b1e753c --- /dev/null +++ b/queue-6.7/asoc-cs35l56-fix-deadlock-in-asp1-mixer-register-ini.patch @@ -0,0 +1,301 @@ +From b88820d41009c9e2aea29dc45f579ad2a7958349 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 8 Feb 2024 12:37:42 +0000 +Subject: ASoC: cs35l56: Fix deadlock in ASP1 mixer register initialization + +From: Richard Fitzgerald + +[ Upstream commit c14f09f010cc569ae7e2f6ef02374f6bfef9917e ] + +Rewrite the handling of ASP1 TX mixer mux initialization to prevent a +deadlock during component_remove(). + +The firmware can overwrite the ASP1 TX mixer registers with +system-specific settings. This is mainly for hardware that uses the +ASP as a chip-to-chip link controlled by the firmware. Because of this +the driver cannot know the starting state of the ASP1 mixer muxes until +the firmware has been downloaded and rebooted. + +The original workaround for this was to queue a work function from the +dsp_work() job. This work then read the register values (populating the +regmap cache the first time around) and then called +snd_soc_dapm_mux_update_power(). The problem with this is that it was +ultimately triggered by cs35l56_component_probe() queueing dsp_work, +which meant that it would be running in parallel with the rest of the +ASoC component and card initialization. To prevent accessing DAPM before +it was fully initialized the work function took the card mutex. But this +would deadlock if cs35l56_component_remove() was called before the work job +had completed, because ASoC calls component_remove() with the card mutex +held. + +This new version removes the work function. Instead the regmap cache and +DAPM mux widgets are initialized the first time any of the associated ALSA +controls is read or written. + +Signed-off-by: Richard Fitzgerald +Fixes: 07f7d6e7a124 ("ASoC: cs35l56: Fix for initializing ASP1 mixer registers") +Link: https://lore.kernel.org/r/20240208123742.1278104-1-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()") +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56.c | 153 +++++++++++++++++-------------------- + sound/soc/codecs/cs35l56.h | 2 +- + 2 files changed, 73 insertions(+), 82 deletions(-) + +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index f05fab577f037..aaeed4992d846 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -68,63 +68,7 @@ static const char * const cs35l56_asp1_mux_control_names[] = { + "ASP1 TX1 Source", "ASP1 TX2 Source", "ASP1 TX3 Source", "ASP1 TX4 Source" + }; + +-static int cs35l56_dspwait_asp1tx_get(struct snd_kcontrol *kcontrol, +- struct snd_ctl_elem_value *ucontrol) +-{ +- struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol); +- struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); +- struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; +- int index = e->shift_l; +- unsigned int addr, val; +- int ret; +- +- /* Wait for mux to be initialized */ +- cs35l56_wait_dsp_ready(cs35l56); +- flush_work(&cs35l56->mux_init_work); +- +- addr = cs35l56_asp1_mixer_regs[index]; +- ret = regmap_read(cs35l56->base.regmap, addr, &val); +- if (ret) +- return ret; +- +- val &= CS35L56_ASP_TXn_SRC_MASK; +- ucontrol->value.enumerated.item[0] = snd_soc_enum_val_to_item(e, val); +- +- return 0; +-} +- +-static int cs35l56_dspwait_asp1tx_put(struct snd_kcontrol *kcontrol, +- struct snd_ctl_elem_value *ucontrol) +-{ +- struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol); +- struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); +- struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); +- struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; +- int item = ucontrol->value.enumerated.item[0]; +- int index = e->shift_l; +- unsigned int addr, val; +- bool changed; +- int ret; +- +- /* Wait for mux to be initialized */ +- cs35l56_wait_dsp_ready(cs35l56); +- flush_work(&cs35l56->mux_init_work); +- +- addr = cs35l56_asp1_mixer_regs[index]; +- val = snd_soc_enum_item_to_val(e, item); +- +- ret = regmap_update_bits_check(cs35l56->base.regmap, addr, +- CS35L56_ASP_TXn_SRC_MASK, val, &changed); +- if (!ret) +- return ret; +- +- if (changed) +- snd_soc_dapm_mux_update_power(dapm, kcontrol, item, e, NULL); +- +- return changed; +-} +- +-static void cs35l56_mark_asp1_mixer_widgets_dirty(struct cs35l56_private *cs35l56) ++static int cs35l56_sync_asp1_mixer_widgets_with_firmware(struct cs35l56_private *cs35l56) + { + struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(cs35l56->component); + const char *prefix = cs35l56->component->name_prefix; +@@ -135,13 +79,19 @@ static void cs35l56_mark_asp1_mixer_widgets_dirty(struct cs35l56_private *cs35l5 + unsigned int val[4]; + int i, item, ret; + ++ if (cs35l56->asp1_mixer_widgets_initialized) ++ return 0; ++ + /* + * Resume so we can read the registers from silicon if the regmap + * cache has not yet been populated. + */ + ret = pm_runtime_resume_and_get(cs35l56->base.dev); + if (ret < 0) +- return; ++ return ret; ++ ++ /* Wait for firmware download and reboot */ ++ cs35l56_wait_dsp_ready(cs35l56); + + ret = regmap_bulk_read(cs35l56->base.regmap, CS35L56_ASP1TX1_INPUT, + val, ARRAY_SIZE(val)); +@@ -151,12 +101,9 @@ static void cs35l56_mark_asp1_mixer_widgets_dirty(struct cs35l56_private *cs35l5 + + if (ret) { + dev_err(cs35l56->base.dev, "Failed to read ASP1 mixer regs: %d\n", ret); +- return; ++ return ret; + } + +- snd_soc_card_mutex_lock(dapm->card); +- WARN_ON(!dapm->card->instantiated); +- + for (i = 0; i < ARRAY_SIZE(cs35l56_asp1_mux_control_names); ++i) { + name = cs35l56_asp1_mux_control_names[i]; + +@@ -176,16 +123,65 @@ static void cs35l56_mark_asp1_mixer_widgets_dirty(struct cs35l56_private *cs35l5 + snd_soc_dapm_mux_update_power(dapm, kcontrol, item, e, NULL); + } + +- snd_soc_card_mutex_unlock(dapm->card); ++ cs35l56->asp1_mixer_widgets_initialized = true; ++ ++ return 0; + } + +-static void cs35l56_mux_init_work(struct work_struct *work) ++static int cs35l56_dspwait_asp1tx_get(struct snd_kcontrol *kcontrol, ++ struct snd_ctl_elem_value *ucontrol) + { +- struct cs35l56_private *cs35l56 = container_of(work, +- struct cs35l56_private, +- mux_init_work); ++ struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol); ++ struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); ++ struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; ++ int index = e->shift_l; ++ unsigned int addr, val; ++ int ret; + +- cs35l56_mark_asp1_mixer_widgets_dirty(cs35l56); ++ ret = cs35l56_sync_asp1_mixer_widgets_with_firmware(cs35l56); ++ if (ret) ++ return ret; ++ ++ addr = cs35l56_asp1_mixer_regs[index]; ++ ret = regmap_read(cs35l56->base.regmap, addr, &val); ++ if (ret) ++ return ret; ++ ++ val &= CS35L56_ASP_TXn_SRC_MASK; ++ ucontrol->value.enumerated.item[0] = snd_soc_enum_val_to_item(e, val); ++ ++ return 0; ++} ++ ++static int cs35l56_dspwait_asp1tx_put(struct snd_kcontrol *kcontrol, ++ struct snd_ctl_elem_value *ucontrol) ++{ ++ struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol); ++ struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); ++ struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); ++ struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; ++ int item = ucontrol->value.enumerated.item[0]; ++ int index = e->shift_l; ++ unsigned int addr, val; ++ bool changed; ++ int ret; ++ ++ ret = cs35l56_sync_asp1_mixer_widgets_with_firmware(cs35l56); ++ if (ret) ++ return ret; ++ ++ addr = cs35l56_asp1_mixer_regs[index]; ++ val = snd_soc_enum_item_to_val(e, item); ++ ++ ret = regmap_update_bits_check(cs35l56->base.regmap, addr, ++ CS35L56_ASP_TXn_SRC_MASK, val, &changed); ++ if (!ret) ++ return ret; ++ ++ if (changed) ++ snd_soc_dapm_mux_update_power(dapm, kcontrol, item, e, NULL); ++ ++ return changed; + } + + static DECLARE_TLV_DB_SCALE(vol_tlv, -10000, 25, 0); +@@ -909,14 +905,6 @@ static void cs35l56_dsp_work(struct work_struct *work) + else + cs35l56_patch(cs35l56); + +- +- /* +- * Set starting value of ASP1 mux widgets. Updating a mux takes +- * the DAPM mutex. Post this to a separate job so that DAPM +- * power-up can wait for dsp_work to complete without deadlocking +- * on the DAPM mutex. +- */ +- queue_work(cs35l56->dsp_wq, &cs35l56->mux_init_work); + err: + pm_runtime_mark_last_busy(cs35l56->base.dev); + pm_runtime_put_autosuspend(cs35l56->base.dev); +@@ -953,6 +941,13 @@ static int cs35l56_component_probe(struct snd_soc_component *component) + debugfs_create_bool("can_hibernate", 0444, debugfs_root, &cs35l56->base.can_hibernate); + debugfs_create_bool("fw_patched", 0444, debugfs_root, &cs35l56->base.fw_patched); + ++ /* ++ * The widgets for the ASP1TX mixer can't be initialized ++ * until the firmware has been downloaded and rebooted. ++ */ ++ regcache_drop_region(cs35l56->base.regmap, CS35L56_ASP1TX1_INPUT, CS35L56_ASP1TX4_INPUT); ++ cs35l56->asp1_mixer_widgets_initialized = false; ++ + queue_work(cs35l56->dsp_wq, &cs35l56->dsp_work); + + return 0; +@@ -963,7 +958,6 @@ static void cs35l56_component_remove(struct snd_soc_component *component) + struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); + + cancel_work_sync(&cs35l56->dsp_work); +- cancel_work_sync(&cs35l56->mux_init_work); + + if (cs35l56->dsp.cs_dsp.booted) + wm_adsp_power_down(&cs35l56->dsp); +@@ -1034,10 +1028,8 @@ int cs35l56_system_suspend(struct device *dev) + + dev_dbg(dev, "system_suspend\n"); + +- if (cs35l56->component) { ++ if (cs35l56->component) + flush_work(&cs35l56->dsp_work); +- cancel_work_sync(&cs35l56->mux_init_work); +- } + + /* + * The interrupt line is normally shared, but after we start suspending +@@ -1188,7 +1180,6 @@ static int cs35l56_dsp_init(struct cs35l56_private *cs35l56) + return -ENOMEM; + + INIT_WORK(&cs35l56->dsp_work, cs35l56_dsp_work); +- INIT_WORK(&cs35l56->mux_init_work, cs35l56_mux_init_work); + + dsp = &cs35l56->dsp; + cs35l56_init_cs_dsp(&cs35l56->base, &dsp->cs_dsp); +diff --git a/sound/soc/codecs/cs35l56.h b/sound/soc/codecs/cs35l56.h +index dc2fe4c91e67b..d9fbf568a1958 100644 +--- a/sound/soc/codecs/cs35l56.h ++++ b/sound/soc/codecs/cs35l56.h +@@ -34,7 +34,6 @@ struct cs35l56_private { + struct wm_adsp dsp; /* must be first member */ + struct cs35l56_base base; + struct work_struct dsp_work; +- struct work_struct mux_init_work; + struct workqueue_struct *dsp_wq; + struct snd_soc_component *component; + struct regulator_bulk_data supplies[CS35L56_NUM_BULK_SUPPLIES]; +@@ -51,6 +50,7 @@ struct cs35l56_private { + u8 asp_slot_count; + bool tdm_mode; + bool sysclk_set; ++ bool asp1_mixer_widgets_initialized; + u8 old_sdw_clock_scale; + }; + +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-fix-for-initializing-asp1-mixer-registe.patch b/queue-6.7/asoc-cs35l56-fix-for-initializing-asp1-mixer-registe.patch new file mode 100644 index 00000000000..e99e3ca0158 --- /dev/null +++ b/queue-6.7/asoc-cs35l56-fix-for-initializing-asp1-mixer-registe.patch @@ -0,0 +1,333 @@ +From 61fc6a1399ea9c1542d227ad99daec38cec15cb5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 29 Jan 2024 16:27:29 +0000 +Subject: ASoC: cs35l56: Fix for initializing ASP1 mixer registers + +From: Richard Fitzgerald + +[ Upstream commit 07f7d6e7a124d3e4de36771e2a4926d0e31c2258 ] + +Defer initializing the state of the ASP1 mixer registers until +the firmware has been downloaded and rebooted. + +On a SoundWire system the ASP is free for use as a chip-to-chip +interconnect. This can be either for the firmware on multiple +CS35L56 to share reference audio; or as a bridge to another +device. If it is a firmware interconnect it is owned by the +firmware and the Linux driver should avoid writing the registers. +However, if it is a bridge then Linux may take over and handle +it as a normal codec-to-codec link. Even if the ASP is used +as a firmware-firmware interconnect it is useful to have +ALSA controls for the ASP mixer. They are at least useful for +debugging. + +CS35L56 is designed for SDCA and a generic SDCA driver would +know nothing about these chip-specific registers. So if the +ASP is being used on a SoundWire system the firmware sets up the +ASP mixer registers. This means that we can't assume the default +state of these registers. But we don't know the initial state +that the firmware set them to until after the firmware has been +downloaded and booted, which can take several seconds when +downloading multiple amps. + +DAPM normally reads the initial state of mux registers during +probe() but this would mean blocking probe() for several seconds +until the firmware has initialized them. To avoid this, the +mixer muxes are set SND_SOC_NOPM to prevent DAPM trying to read +the register state. Custom get/set callbacks are implemented for +ALSA control access, and these can safely block waiting for the +firmware download. + +After the firmware download has completed, the state of the +mux registers is known so a work job is queued to call +snd_soc_dapm_mux_update_power() on each of the mux widgets. + +Backport note: +This won't apply cleanly to kernels older than v6.6. + +Signed-off-by: Richard Fitzgerald +Fixes: e49611252900 ("ASoC: cs35l56: Add driver for Cirrus Logic CS35L56") +Link: https://msgid.link/r/20240129162737.497-11-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()") +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56-shared.c | 7 +- + sound/soc/codecs/cs35l56.c | 172 +++++++++++++++++++++++++++--- + sound/soc/codecs/cs35l56.h | 1 + + 3 files changed, 163 insertions(+), 17 deletions(-) + +diff --git a/sound/soc/codecs/cs35l56-shared.c b/sound/soc/codecs/cs35l56-shared.c +index fc99bc92aeace..2eb397724b4ba 100644 +--- a/sound/soc/codecs/cs35l56-shared.c ++++ b/sound/soc/codecs/cs35l56-shared.c +@@ -34,10 +34,9 @@ static const struct reg_default cs35l56_reg_defaults[] = { + { CS35L56_ASP1_FRAME_CONTROL5, 0x00020100 }, + { CS35L56_ASP1_DATA_CONTROL1, 0x00000018 }, + { CS35L56_ASP1_DATA_CONTROL5, 0x00000018 }, +- { CS35L56_ASP1TX1_INPUT, 0x00000018 }, +- { CS35L56_ASP1TX2_INPUT, 0x00000019 }, +- { CS35L56_ASP1TX3_INPUT, 0x00000020 }, +- { CS35L56_ASP1TX4_INPUT, 0x00000028 }, ++ ++ /* no defaults for ASP1TX mixer */ ++ + { CS35L56_SWIRE_DP3_CH1_INPUT, 0x00000018 }, + { CS35L56_SWIRE_DP3_CH2_INPUT, 0x00000019 }, + { CS35L56_SWIRE_DP3_CH3_INPUT, 0x00000029 }, +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index ea5d2b2eb82a0..30f4b9e9cc94c 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -59,6 +59,135 @@ static int cs35l56_dspwait_put_volsw(struct snd_kcontrol *kcontrol, + return snd_soc_put_volsw(kcontrol, ucontrol); + } + ++static const unsigned short cs35l56_asp1_mixer_regs[] = { ++ CS35L56_ASP1TX1_INPUT, CS35L56_ASP1TX2_INPUT, ++ CS35L56_ASP1TX3_INPUT, CS35L56_ASP1TX4_INPUT, ++}; ++ ++static const char * const cs35l56_asp1_mux_control_names[] = { ++ "ASP1 TX1 Source", "ASP1 TX2 Source", "ASP1 TX3 Source", "ASP1 TX4 Source" ++}; ++ ++static int cs35l56_dspwait_asp1tx_get(struct snd_kcontrol *kcontrol, ++ struct snd_ctl_elem_value *ucontrol) ++{ ++ struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol); ++ struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); ++ struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; ++ int index = e->shift_l; ++ unsigned int addr, val; ++ int ret; ++ ++ /* Wait for mux to be initialized */ ++ cs35l56_wait_dsp_ready(cs35l56); ++ flush_work(&cs35l56->mux_init_work); ++ ++ addr = cs35l56_asp1_mixer_regs[index]; ++ ret = regmap_read(cs35l56->base.regmap, addr, &val); ++ if (ret) ++ return ret; ++ ++ val &= CS35L56_ASP_TXn_SRC_MASK; ++ ucontrol->value.enumerated.item[0] = snd_soc_enum_val_to_item(e, val); ++ ++ return 0; ++} ++ ++static int cs35l56_dspwait_asp1tx_put(struct snd_kcontrol *kcontrol, ++ struct snd_ctl_elem_value *ucontrol) ++{ ++ struct snd_soc_component *component = snd_soc_dapm_kcontrol_component(kcontrol); ++ struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); ++ struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); ++ struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; ++ int item = ucontrol->value.enumerated.item[0]; ++ int index = e->shift_l; ++ unsigned int addr, val; ++ bool changed; ++ int ret; ++ ++ /* Wait for mux to be initialized */ ++ cs35l56_wait_dsp_ready(cs35l56); ++ flush_work(&cs35l56->mux_init_work); ++ ++ addr = cs35l56_asp1_mixer_regs[index]; ++ val = snd_soc_enum_item_to_val(e, item); ++ ++ ret = regmap_update_bits_check(cs35l56->base.regmap, addr, ++ CS35L56_ASP_TXn_SRC_MASK, val, &changed); ++ if (!ret) ++ return ret; ++ ++ if (changed) ++ snd_soc_dapm_mux_update_power(dapm, kcontrol, item, e, NULL); ++ ++ return changed; ++} ++ ++static void cs35l56_mark_asp1_mixer_widgets_dirty(struct cs35l56_private *cs35l56) ++{ ++ struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(cs35l56->component); ++ const char *prefix = cs35l56->component->name_prefix; ++ char full_name[SNDRV_CTL_ELEM_ID_NAME_MAXLEN]; ++ const char *name; ++ struct snd_kcontrol *kcontrol; ++ struct soc_enum *e; ++ unsigned int val[4]; ++ int i, item, ret; ++ ++ /* ++ * Resume so we can read the registers from silicon if the regmap ++ * cache has not yet been populated. ++ */ ++ ret = pm_runtime_resume_and_get(cs35l56->base.dev); ++ if (ret < 0) ++ return; ++ ++ ret = regmap_bulk_read(cs35l56->base.regmap, CS35L56_ASP1TX1_INPUT, ++ val, ARRAY_SIZE(val)); ++ ++ pm_runtime_mark_last_busy(cs35l56->base.dev); ++ pm_runtime_put_autosuspend(cs35l56->base.dev); ++ ++ if (ret) { ++ dev_err(cs35l56->base.dev, "Failed to read ASP1 mixer regs: %d\n", ret); ++ return; ++ } ++ ++ snd_soc_card_mutex_lock(dapm->card); ++ WARN_ON(!dapm->card->instantiated); ++ ++ for (i = 0; i < ARRAY_SIZE(cs35l56_asp1_mux_control_names); ++i) { ++ name = cs35l56_asp1_mux_control_names[i]; ++ ++ if (prefix) { ++ snprintf(full_name, sizeof(full_name), "%s %s", prefix, name); ++ name = full_name; ++ } ++ ++ kcontrol = snd_soc_card_get_kcontrol(dapm->card, name); ++ if (!kcontrol) { ++ dev_warn(cs35l56->base.dev, "Could not find control %s\n", name); ++ continue; ++ } ++ ++ e = (struct soc_enum *)kcontrol->private_value; ++ item = snd_soc_enum_val_to_item(e, val[i] & CS35L56_ASP_TXn_SRC_MASK); ++ snd_soc_dapm_mux_update_power(dapm, kcontrol, item, e, NULL); ++ } ++ ++ snd_soc_card_mutex_unlock(dapm->card); ++} ++ ++static void cs35l56_mux_init_work(struct work_struct *work) ++{ ++ struct cs35l56_private *cs35l56 = container_of(work, ++ struct cs35l56_private, ++ mux_init_work); ++ ++ cs35l56_mark_asp1_mixer_widgets_dirty(cs35l56); ++} ++ + static DECLARE_TLV_DB_SCALE(vol_tlv, -10000, 25, 0); + + static const struct snd_kcontrol_new cs35l56_controls[] = { +@@ -77,40 +206,44 @@ static const struct snd_kcontrol_new cs35l56_controls[] = { + }; + + static SOC_VALUE_ENUM_SINGLE_DECL(cs35l56_asp1tx1_enum, +- CS35L56_ASP1TX1_INPUT, +- 0, CS35L56_ASP_TXn_SRC_MASK, ++ SND_SOC_NOPM, ++ 0, 0, + cs35l56_tx_input_texts, + cs35l56_tx_input_values); + + static const struct snd_kcontrol_new asp1_tx1_mux = +- SOC_DAPM_ENUM("ASP1TX1 SRC", cs35l56_asp1tx1_enum); ++ SOC_DAPM_ENUM_EXT("ASP1TX1 SRC", cs35l56_asp1tx1_enum, ++ cs35l56_dspwait_asp1tx_get, cs35l56_dspwait_asp1tx_put); + + static SOC_VALUE_ENUM_SINGLE_DECL(cs35l56_asp1tx2_enum, +- CS35L56_ASP1TX2_INPUT, +- 0, CS35L56_ASP_TXn_SRC_MASK, ++ SND_SOC_NOPM, ++ 1, 0, + cs35l56_tx_input_texts, + cs35l56_tx_input_values); + + static const struct snd_kcontrol_new asp1_tx2_mux = +- SOC_DAPM_ENUM("ASP1TX2 SRC", cs35l56_asp1tx2_enum); ++ SOC_DAPM_ENUM_EXT("ASP1TX2 SRC", cs35l56_asp1tx2_enum, ++ cs35l56_dspwait_asp1tx_get, cs35l56_dspwait_asp1tx_put); + + static SOC_VALUE_ENUM_SINGLE_DECL(cs35l56_asp1tx3_enum, +- CS35L56_ASP1TX3_INPUT, +- 0, CS35L56_ASP_TXn_SRC_MASK, ++ SND_SOC_NOPM, ++ 2, 0, + cs35l56_tx_input_texts, + cs35l56_tx_input_values); + + static const struct snd_kcontrol_new asp1_tx3_mux = +- SOC_DAPM_ENUM("ASP1TX3 SRC", cs35l56_asp1tx3_enum); ++ SOC_DAPM_ENUM_EXT("ASP1TX3 SRC", cs35l56_asp1tx3_enum, ++ cs35l56_dspwait_asp1tx_get, cs35l56_dspwait_asp1tx_put); + + static SOC_VALUE_ENUM_SINGLE_DECL(cs35l56_asp1tx4_enum, +- CS35L56_ASP1TX4_INPUT, +- 0, CS35L56_ASP_TXn_SRC_MASK, ++ SND_SOC_NOPM, ++ 3, 0, + cs35l56_tx_input_texts, + cs35l56_tx_input_values); + + static const struct snd_kcontrol_new asp1_tx4_mux = +- SOC_DAPM_ENUM("ASP1TX4 SRC", cs35l56_asp1tx4_enum); ++ SOC_DAPM_ENUM_EXT("ASP1TX4 SRC", cs35l56_asp1tx4_enum, ++ cs35l56_dspwait_asp1tx_get, cs35l56_dspwait_asp1tx_put); + + static SOC_VALUE_ENUM_SINGLE_DECL(cs35l56_sdw1tx1_enum, + CS35L56_SWIRE_DP3_CH1_INPUT, +@@ -764,6 +897,15 @@ static void cs35l56_dsp_work(struct work_struct *work) + else + cs35l56_patch(cs35l56); + ++ ++ /* ++ * Set starting value of ASP1 mux widgets. Updating a mux takes ++ * the DAPM mutex. Post this to a separate job so that DAPM ++ * power-up can wait for dsp_work to complete without deadlocking ++ * on the DAPM mutex. ++ */ ++ queue_work(cs35l56->dsp_wq, &cs35l56->mux_init_work); ++ + pm_runtime_mark_last_busy(cs35l56->base.dev); + pm_runtime_put_autosuspend(cs35l56->base.dev); + } +@@ -809,6 +951,7 @@ static void cs35l56_component_remove(struct snd_soc_component *component) + struct cs35l56_private *cs35l56 = snd_soc_component_get_drvdata(component); + + cancel_work_sync(&cs35l56->dsp_work); ++ cancel_work_sync(&cs35l56->mux_init_work); + + if (cs35l56->dsp.cs_dsp.booted) + wm_adsp_power_down(&cs35l56->dsp); +@@ -876,8 +1019,10 @@ int cs35l56_system_suspend(struct device *dev) + + dev_dbg(dev, "system_suspend\n"); + +- if (cs35l56->component) ++ if (cs35l56->component) { + flush_work(&cs35l56->dsp_work); ++ cancel_work_sync(&cs35l56->mux_init_work); ++ } + + /* + * The interrupt line is normally shared, but after we start suspending +@@ -1028,6 +1173,7 @@ static int cs35l56_dsp_init(struct cs35l56_private *cs35l56) + return -ENOMEM; + + INIT_WORK(&cs35l56->dsp_work, cs35l56_dsp_work); ++ INIT_WORK(&cs35l56->mux_init_work, cs35l56_mux_init_work); + + dsp = &cs35l56->dsp; + cs35l56_init_cs_dsp(&cs35l56->base, &dsp->cs_dsp); +diff --git a/sound/soc/codecs/cs35l56.h b/sound/soc/codecs/cs35l56.h +index 8159c3e217d93..dc2fe4c91e67b 100644 +--- a/sound/soc/codecs/cs35l56.h ++++ b/sound/soc/codecs/cs35l56.h +@@ -34,6 +34,7 @@ struct cs35l56_private { + struct wm_adsp dsp; /* must be first member */ + struct cs35l56_base base; + struct work_struct dsp_work; ++ struct work_struct mux_init_work; + struct workqueue_struct *dsp_wq; + struct snd_soc_component *component; + struct regulator_bulk_data supplies[CS35L56_NUM_BULK_SUPPLIES]; +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-fix-misuse-of-wm_adsp-part-string-for-s.patch b/queue-6.7/asoc-cs35l56-fix-misuse-of-wm_adsp-part-string-for-s.patch new file mode 100644 index 00000000000..d00af8035f0 --- /dev/null +++ b/queue-6.7/asoc-cs35l56-fix-misuse-of-wm_adsp-part-string-for-s.patch @@ -0,0 +1,101 @@ +From b3fa559a6a5c72bf612369dc11fc5d9e25ab9e6a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 29 Jan 2024 16:27:30 +0000 +Subject: ASoC: cs35l56: Fix misuse of wm_adsp 'part' string for silicon + revision + +From: Richard Fitzgerald + +[ Upstream commit f6c967941c5d6fa526fdd64733a8d86bf2bfab31 ] + +Put the silicon revision and secured flag in the wm_adsp fwf_name +string instead of including them in the part string. + +This changes the format of the firmware name string from + + cs35l56[s]-rev-misc[-system_name] + +to + cs35l56-rev[-s]-misc[-system_name] + +No firmware files have been published, so this doesn't cause a +compatibility break. + +Silicon revision and secured flag are included in the firmware +filename to pick a firmware compatible with the part. These strings +were being added to the part string, but that is a misuse of the +string. The correct place for these is the fwf_name string, which +is specifically intended to select between multiple firmware files +for the same part. + +Backport note: +This won't apply to kernels older than v6.6. + +Signed-off-by: Richard Fitzgerald +Fixes: 608f1b0dbdde ("ASoC: cs35l56: Move DSP part string generation so that it is done only once") +Link: https://msgid.link/r/20240129162737.497-12-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()") +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56.c | 23 ++++++++++++++++------- + 1 file changed, 16 insertions(+), 7 deletions(-) + +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index 30f4b9e9cc94c..f05fab577f037 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -886,6 +886,18 @@ static void cs35l56_dsp_work(struct work_struct *work) + + pm_runtime_get_sync(cs35l56->base.dev); + ++ /* Populate fw file qualifier with the revision and security state */ ++ if (!cs35l56->dsp.fwf_name) { ++ cs35l56->dsp.fwf_name = kasprintf(GFP_KERNEL, "%02x%s-dsp1", ++ cs35l56->base.rev, ++ cs35l56->base.secured ? "-s" : ""); ++ if (!cs35l56->dsp.fwf_name) ++ goto err; ++ } ++ ++ dev_dbg(cs35l56->base.dev, "DSP fwf name: '%s' system name: '%s'\n", ++ cs35l56->dsp.fwf_name, cs35l56->dsp.system_name); ++ + /* + * When the device is running in secure mode the firmware files can + * only contain insecure tunings and therefore we do not need to +@@ -905,7 +917,7 @@ static void cs35l56_dsp_work(struct work_struct *work) + * on the DAPM mutex. + */ + queue_work(cs35l56->dsp_wq, &cs35l56->mux_init_work); +- ++err: + pm_runtime_mark_last_busy(cs35l56->base.dev); + pm_runtime_put_autosuspend(cs35l56->base.dev); + } +@@ -958,6 +970,9 @@ static void cs35l56_component_remove(struct snd_soc_component *component) + + wm_adsp2_component_remove(&cs35l56->dsp, component); + ++ kfree(cs35l56->dsp.fwf_name); ++ cs35l56->dsp.fwf_name = NULL; ++ + cs35l56->component = NULL; + } + +@@ -1309,12 +1324,6 @@ int cs35l56_init(struct cs35l56_private *cs35l56) + if (ret) + return ret; + +- /* Populate the DSP information with the revision and security state */ +- cs35l56->dsp.part = devm_kasprintf(cs35l56->base.dev, GFP_KERNEL, "cs35l56%s-%02x", +- cs35l56->base.secured ? "s" : "", cs35l56->base.rev); +- if (!cs35l56->dsp.part) +- return -ENOMEM; +- + if (!cs35l56->base.reset_gpio) { + dev_dbg(cs35l56->base.dev, "No reset gpio: using soft reset\n"); + cs35l56->soft_resetting = true; +-- +2.43.0 + diff --git a/queue-6.7/asoc-cs35l56-must-clear-halo_state-before-issuing-sy.patch b/queue-6.7/asoc-cs35l56-must-clear-halo_state-before-issuing-sy.patch new file mode 100644 index 00000000000..8b72691681a --- /dev/null +++ b/queue-6.7/asoc-cs35l56-must-clear-halo_state-before-issuing-sy.patch @@ -0,0 +1,44 @@ +From 5132dca9cf4b6afd0f56d1725e01b21d4042fecf Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 16 Feb 2024 14:05:35 +0000 +Subject: ASoC: cs35l56: Must clear HALO_STATE before issuing SYSTEM_RESET + +From: Richard Fitzgerald + +[ Upstream commit e33625c84b75e4f078d7f9bf58f01fe71ab99642 ] + +The driver must write 0 to HALO_STATE before sending the SYSTEM_RESET +command to the firmware. + +HALO_STATE is in DSP memory, which is preserved across a soft reset. +The SYSTEM_RESET command does not change the value of HALO_STATE. +There is period of time while the CS35L56 is resetting, before the +firmware has started to boot, where a read of HALO_STATE will return +the value it had before the SYSTEM_RESET. If the driver does not +clear HALO_STATE, this would return BOOT_DONE status even though the +firmware has not booted. + +Signed-off-by: Richard Fitzgerald +Fixes: 8a731fd37f8b ("ASoC: cs35l56: Move utility functions to shared file") +Link: https://msgid.link/r/20240216140535.1434933-1-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + sound/soc/codecs/cs35l56-shared.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/sound/soc/codecs/cs35l56-shared.c b/sound/soc/codecs/cs35l56-shared.c +index 953ba066bab1e..fc99bc92aeace 100644 +--- a/sound/soc/codecs/cs35l56-shared.c ++++ b/sound/soc/codecs/cs35l56-shared.c +@@ -286,6 +286,7 @@ void cs35l56_wait_min_reset_pulse(void) + EXPORT_SYMBOL_NS_GPL(cs35l56_wait_min_reset_pulse, SND_SOC_CS35L56_SHARED); + + static const struct reg_sequence cs35l56_system_reset_seq[] = { ++ REG_SEQ0(CS35L56_DSP1_HALO_STATE, 0), + REG_SEQ0(CS35L56_DSP_VIRTUAL1_MBOX_1, CS35L56_MBOX_CMD_SYSTEM_RESET), + }; + +-- +2.43.0 + diff --git a/queue-6.7/asoc-qcom-fix-uninitialized-pointer-dmactl.patch b/queue-6.7/asoc-qcom-fix-uninitialized-pointer-dmactl.patch new file mode 100644 index 00000000000..4e512306cbd --- /dev/null +++ b/queue-6.7/asoc-qcom-fix-uninitialized-pointer-dmactl.patch @@ -0,0 +1,46 @@ +From 4c623874ce1ea5c86f873465027938745133f321 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 13:48:04 +0000 +Subject: ASoC: qcom: Fix uninitialized pointer dmactl + +From: Colin Ian King + +[ Upstream commit 1382d8b55129875b2e07c4d2a7ebc790183769ee ] + +In the case where __lpass_get_dmactl_handle is called and the driver +id dai_id is invalid the pointer dmactl is not being assigned a value, +and dmactl contains a garbage value since it has not been initialized +and so the null check may not work. Fix this to initialize dmactl to +NULL. One could argue that modern compilers will set this to zero, but +it is useful to keep this initialized as per the same way in functions +__lpass_platform_codec_intf_init and lpass_cdc_dma_daiops_hw_params. + +Cleans up clang scan build warning: +sound/soc/qcom/lpass-cdc-dma.c:275:7: warning: Branch condition +evaluates to a garbage value [core.uninitialized.Branch] + +Fixes: b81af585ea54 ("ASoC: qcom: Add lpass CPU driver for codec dma control") +Signed-off-by: Colin Ian King +Link: https://msgid.link/r/20240221134804.3475989-1-colin.i.king@gmail.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + sound/soc/qcom/lpass-cdc-dma.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/sound/soc/qcom/lpass-cdc-dma.c b/sound/soc/qcom/lpass-cdc-dma.c +index 48b03e60e3a3d..8106c586f68a4 100644 +--- a/sound/soc/qcom/lpass-cdc-dma.c ++++ b/sound/soc/qcom/lpass-cdc-dma.c +@@ -259,7 +259,7 @@ static int lpass_cdc_dma_daiops_trigger(struct snd_pcm_substream *substream, + int cmd, struct snd_soc_dai *dai) + { + struct snd_soc_pcm_runtime *soc_runtime = snd_soc_substream_to_rtd(substream); +- struct lpaif_dmactl *dmactl; ++ struct lpaif_dmactl *dmactl = NULL; + int ret = 0, id; + + switch (cmd) { +-- +2.43.0 + diff --git a/queue-6.7/asoc-soc-card-fix-missing-locking-in-snd_soc_card_ge.patch b/queue-6.7/asoc-soc-card-fix-missing-locking-in-snd_soc_card_ge.patch new file mode 100644 index 00000000000..a426e3c53df --- /dev/null +++ b/queue-6.7/asoc-soc-card-fix-missing-locking-in-snd_soc_card_ge.patch @@ -0,0 +1,227 @@ +From 1d53ba904339062a97e8a23fec31153a40bdfa86 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 12:37:10 +0000 +Subject: ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol() + +From: Richard Fitzgerald + +[ Upstream commit eba2eb2495f47690400331c722868902784e59de ] + +snd_soc_card_get_kcontrol() must be holding a read lock on +card->controls_rwsem while walking the controls list. + +Compare with snd_ctl_find_numid(). + +The existing function is renamed snd_soc_card_get_kcontrol_locked() +so that it can be called from contexts that are already holding +card->controls_rwsem (for example, control get/put functions). + +There are few direct or indirect callers of +snd_soc_card_get_kcontrol(), and most are safe. Three require +changes, which have been included in this patch: + +codecs/cs35l45.c: + cs35l45_activate_ctl() is called from a control put() function so + is changed to call snd_soc_card_get_kcontrol_locked(). + +codecs/cs35l56.c: + cs35l56_sync_asp1_mixer_widgets_with_firmware() is called from + control get()/put() functions so is changed to call + snd_soc_card_get_kcontrol_locked(). + +fsl/fsl_xcvr.c: + fsl_xcvr_activate_ctl() is called from three places, one of which + already holds card->controls_rwsem: + 1. fsl_xcvr_mode_put(), a control put function, which will + already be holding card->controls_rwsem. + 2. fsl_xcvr_startup(), a DAI startup function. + 3. fsl_xcvr_shutdown(), a DAI shutdown function. + + To fix this, fsl_xcvr_activate_ctl() has been changed to call + snd_soc_card_get_kcontrol_locked() so that it is safe to call + directly from fsl_xcvr_mode_put(). + The fsl_xcvr_startup() and fsl_xcvr_shutdown() functions have been + changed to take a read lock on card->controls_rsem() around calls + to fsl_xcvr_activate_ctl(). While this is not very elegant, it + keeps the change small, to avoid this patch creating a large + collateral churn in fsl/fsl_xcvr.c. + +Analysis of other callers of snd_soc_card_get_kcontrol() is that +they do not need any changes, they are not holding card->controls_rwsem +when they call snd_soc_card_get_kcontrol(). + +Direct callers of snd_soc_card_get_kcontrol(): + fsl/fsl_spdif.c: fsl_spdif_dai_probe() - DAI probe function + fsl/fsl_micfil.c: voice_detected_fn() - IRQ handler + +Indirect callers via soc_component_notify_control(): + codecs/cs42l43: cs42l43_mic_shutter() - IRQ handler + codecs/cs42l43: cs42l43_spk_shutter() - IRQ handler + codecs/ak4118.c: ak4118_irq_handler() - IRQ handler + codecs/wm_adsp.c: wm_adsp_write_ctl() - not currently used + +Indirect callers via snd_soc_limit_volume(): + qcom/sc8280xp.c: sc8280xp_snd_init() - DAIlink init function + ti/rx51.c: rx51_aic34_init() - DAI init function + +I don't have hardware to test the fsl/*, qcom/sc828xp.c, ti/rx51.c +and ak4118.c changes. + +Backport note: +The fsl/, qcom/, cs35l45, cs35l56 and cs42l43 callers were added +since the Fixes commit so won't all be present on older kernels. + +Signed-off-by: Richard Fitzgerald +Fixes: 209c6cdfd283 ("ASoC: soc-card: move snd_soc_card_get_kcontrol() to soc-card") +Link: https://lore.kernel.org/r/20240221123710.690224-1-rf@opensource.cirrus.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + include/sound/soc-card.h | 2 ++ + sound/soc/codecs/cs35l45.c | 2 +- + sound/soc/codecs/cs35l56.c | 2 +- + sound/soc/fsl/fsl_xcvr.c | 12 +++++++++++- + sound/soc/soc-card.c | 24 ++++++++++++++++++++++-- + 5 files changed, 37 insertions(+), 5 deletions(-) + +diff --git a/include/sound/soc-card.h b/include/sound/soc-card.h +index ecc02e955279f..1f4c39922d825 100644 +--- a/include/sound/soc-card.h ++++ b/include/sound/soc-card.h +@@ -30,6 +30,8 @@ static inline void snd_soc_card_mutex_unlock(struct snd_soc_card *card) + + struct snd_kcontrol *snd_soc_card_get_kcontrol(struct snd_soc_card *soc_card, + const char *name); ++struct snd_kcontrol *snd_soc_card_get_kcontrol_locked(struct snd_soc_card *soc_card, ++ const char *name); + int snd_soc_card_jack_new(struct snd_soc_card *card, const char *id, int type, + struct snd_soc_jack *jack); + int snd_soc_card_jack_new_pins(struct snd_soc_card *card, const char *id, +diff --git a/sound/soc/codecs/cs35l45.c b/sound/soc/codecs/cs35l45.c +index 44c221745c3b2..2392c6effed85 100644 +--- a/sound/soc/codecs/cs35l45.c ++++ b/sound/soc/codecs/cs35l45.c +@@ -184,7 +184,7 @@ static int cs35l45_activate_ctl(struct snd_soc_component *component, + else + snprintf(name, SNDRV_CTL_ELEM_ID_NAME_MAXLEN, "%s", ctl_name); + +- kcontrol = snd_soc_card_get_kcontrol(component->card, name); ++ kcontrol = snd_soc_card_get_kcontrol_locked(component->card, name); + if (!kcontrol) { + dev_err(component->dev, "Can't find kcontrol %s\n", name); + return -EINVAL; +diff --git a/sound/soc/codecs/cs35l56.c b/sound/soc/codecs/cs35l56.c +index aaeed4992d846..8e596f5ce8b2a 100644 +--- a/sound/soc/codecs/cs35l56.c ++++ b/sound/soc/codecs/cs35l56.c +@@ -112,7 +112,7 @@ static int cs35l56_sync_asp1_mixer_widgets_with_firmware(struct cs35l56_private + name = full_name; + } + +- kcontrol = snd_soc_card_get_kcontrol(dapm->card, name); ++ kcontrol = snd_soc_card_get_kcontrol_locked(dapm->card, name); + if (!kcontrol) { + dev_warn(cs35l56->base.dev, "Could not find control %s\n", name); + continue; +diff --git a/sound/soc/fsl/fsl_xcvr.c b/sound/soc/fsl/fsl_xcvr.c +index f0fb33d719c25..c46f64557a7ff 100644 +--- a/sound/soc/fsl/fsl_xcvr.c ++++ b/sound/soc/fsl/fsl_xcvr.c +@@ -174,7 +174,9 @@ static int fsl_xcvr_activate_ctl(struct snd_soc_dai *dai, const char *name, + struct snd_kcontrol *kctl; + bool enabled; + +- kctl = snd_soc_card_get_kcontrol(card, name); ++ lockdep_assert_held(&card->snd_card->controls_rwsem); ++ ++ kctl = snd_soc_card_get_kcontrol_locked(card, name); + if (kctl == NULL) + return -ENOENT; + +@@ -576,10 +578,14 @@ static int fsl_xcvr_startup(struct snd_pcm_substream *substream, + xcvr->streams |= BIT(substream->stream); + + if (!xcvr->soc_data->spdif_only) { ++ struct snd_soc_card *card = dai->component->card; ++ + /* Disable XCVR controls if there is stream started */ ++ down_read(&card->snd_card->controls_rwsem); + fsl_xcvr_activate_ctl(dai, fsl_xcvr_mode_kctl.name, false); + fsl_xcvr_activate_ctl(dai, fsl_xcvr_arc_mode_kctl.name, false); + fsl_xcvr_activate_ctl(dai, fsl_xcvr_earc_capds_kctl.name, false); ++ up_read(&card->snd_card->controls_rwsem); + } + + return 0; +@@ -598,11 +604,15 @@ static void fsl_xcvr_shutdown(struct snd_pcm_substream *substream, + /* Enable XCVR controls if there is no stream started */ + if (!xcvr->streams) { + if (!xcvr->soc_data->spdif_only) { ++ struct snd_soc_card *card = dai->component->card; ++ ++ down_read(&card->snd_card->controls_rwsem); + fsl_xcvr_activate_ctl(dai, fsl_xcvr_mode_kctl.name, true); + fsl_xcvr_activate_ctl(dai, fsl_xcvr_arc_mode_kctl.name, + (xcvr->mode == FSL_XCVR_MODE_ARC)); + fsl_xcvr_activate_ctl(dai, fsl_xcvr_earc_capds_kctl.name, + (xcvr->mode == FSL_XCVR_MODE_EARC)); ++ up_read(&card->snd_card->controls_rwsem); + } + ret = regmap_update_bits(xcvr->regmap, FSL_XCVR_EXT_IER0, + FSL_XCVR_IRQ_EARC_ALL, 0); +diff --git a/sound/soc/soc-card.c b/sound/soc/soc-card.c +index 285ab4c9c7168..8a2f163da6bc9 100644 +--- a/sound/soc/soc-card.c ++++ b/sound/soc/soc-card.c +@@ -5,6 +5,9 @@ + // Copyright (C) 2019 Renesas Electronics Corp. + // Kuninori Morimoto + // ++ ++#include ++#include + #include + #include + +@@ -26,12 +29,15 @@ static inline int _soc_card_ret(struct snd_soc_card *card, + return ret; + } + +-struct snd_kcontrol *snd_soc_card_get_kcontrol(struct snd_soc_card *soc_card, +- const char *name) ++struct snd_kcontrol *snd_soc_card_get_kcontrol_locked(struct snd_soc_card *soc_card, ++ const char *name) + { + struct snd_card *card = soc_card->snd_card; + struct snd_kcontrol *kctl; + ++ /* must be held read or write */ ++ lockdep_assert_held(&card->controls_rwsem); ++ + if (unlikely(!name)) + return NULL; + +@@ -40,6 +46,20 @@ struct snd_kcontrol *snd_soc_card_get_kcontrol(struct snd_soc_card *soc_card, + return kctl; + return NULL; + } ++EXPORT_SYMBOL_GPL(snd_soc_card_get_kcontrol_locked); ++ ++struct snd_kcontrol *snd_soc_card_get_kcontrol(struct snd_soc_card *soc_card, ++ const char *name) ++{ ++ struct snd_card *card = soc_card->snd_card; ++ struct snd_kcontrol *kctl; ++ ++ down_read(&card->controls_rwsem); ++ kctl = snd_soc_card_get_kcontrol_locked(soc_card, name); ++ up_read(&card->controls_rwsem); ++ ++ return kctl; ++} + EXPORT_SYMBOL_GPL(snd_soc_card_get_kcontrol); + + static int jack_new(struct snd_soc_card *card, const char *id, int type, +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-avoid-potential-use-after-free-in-hci_erro.patch b/queue-6.7/bluetooth-avoid-potential-use-after-free-in-hci_erro.patch new file mode 100644 index 00000000000..665b0efe177 --- /dev/null +++ b/queue-6.7/bluetooth-avoid-potential-use-after-free-in-hci_erro.patch @@ -0,0 +1,66 @@ +From ee53fa2f2987d9361f55da3a18fb3e19384cd2ef Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 4 Jan 2024 11:56:32 +0000 +Subject: Bluetooth: Avoid potential use-after-free in hci_error_reset + +From: Ying Hsu + +[ Upstream commit 2449007d3f73b2842c9734f45f0aadb522daf592 ] + +While handling the HCI_EV_HARDWARE_ERROR event, if the underlying +BT controller is not responding, the GPIO reset mechanism would +free the hci_dev and lead to a use-after-free in hci_error_reset. + +Here's the call trace observed on a ChromeOS device with Intel AX201: + queue_work_on+0x3e/0x6c + __hci_cmd_sync_sk+0x2ee/0x4c0 [bluetooth ] + ? init_wait_entry+0x31/0x31 + __hci_cmd_sync+0x16/0x20 [bluetooth ] + hci_error_reset+0x4f/0xa4 [bluetooth ] + process_one_work+0x1d8/0x33f + worker_thread+0x21b/0x373 + kthread+0x13a/0x152 + ? pr_cont_work+0x54/0x54 + ? kthread_blkcg+0x31/0x31 + ret_from_fork+0x1f/0x30 + +This patch holds the reference count on the hci_dev while processing +a HCI_EV_HARDWARE_ERROR event to avoid potential crash. + +Fixes: c7741d16a57c ("Bluetooth: Perform a power cycle when receiving hardware error event") +Signed-off-by: Ying Hsu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_core.c | 7 ++++--- + 1 file changed, 4 insertions(+), 3 deletions(-) + +diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c +index 65601aa52e0d8..2821a42cefdc6 100644 +--- a/net/bluetooth/hci_core.c ++++ b/net/bluetooth/hci_core.c +@@ -1049,6 +1049,7 @@ static void hci_error_reset(struct work_struct *work) + { + struct hci_dev *hdev = container_of(work, struct hci_dev, error_reset); + ++ hci_dev_hold(hdev); + BT_DBG("%s", hdev->name); + + if (hdev->hw_error) +@@ -1056,10 +1057,10 @@ static void hci_error_reset(struct work_struct *work) + else + bt_dev_err(hdev, "hardware error 0x%2.2x", hdev->hw_error_code); + +- if (hci_dev_do_close(hdev)) +- return; ++ if (!hci_dev_do_close(hdev)) ++ hci_dev_do_open(hdev); + +- hci_dev_do_open(hdev); ++ hci_dev_put(hdev); + } + + void hci_uuids_clear(struct hci_dev *hdev) +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-enforce-validation-on-max-value-of-connect.patch b/queue-6.7/bluetooth-enforce-validation-on-max-value-of-connect.patch new file mode 100644 index 00000000000..b2725db30b0 --- /dev/null +++ b/queue-6.7/bluetooth-enforce-validation-on-max-value-of-connect.patch @@ -0,0 +1,68 @@ +From 33e4f5171519954127bd2a7902b04e8d53942190 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 25 Jan 2024 14:50:28 +0800 +Subject: Bluetooth: Enforce validation on max value of connection interval + +From: Kai-Heng Feng + +[ Upstream commit e4b019515f950b4e6e5b74b2e1bb03a90cb33039 ] + +Right now Linux BT stack cannot pass test case "GAP/CONN/CPUP/BV-05-C +'Connection Parameter Update Procedure Invalid Parameters Central +Responder'" in Bluetooth Test Suite revision GAP.TS.p44. [0] + +That was revoled by commit c49a8682fc5d ("Bluetooth: validate BLE +connection interval updates"), but later got reverted due to devices +like keyboards and mice may require low connection interval. + +So only validate the max value connection interval to pass the Test +Suite, and let devices to request low connection interval if needed. + +[0] https://www.bluetooth.org/docman/handlers/DownloadDoc.ashx?doc_id=229869 + +Fixes: 68d19d7d9957 ("Revert "Bluetooth: validate BLE connection interval updates"") +Signed-off-by: Kai-Heng Feng +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_event.c | 4 ++++ + net/bluetooth/l2cap_core.c | 8 +++++++- + 2 files changed, 11 insertions(+), 1 deletion(-) + +diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c +index 613f2fd0bcc1e..2a5f5a7d2412b 100644 +--- a/net/bluetooth/hci_event.c ++++ b/net/bluetooth/hci_event.c +@@ -6797,6 +6797,10 @@ static void hci_le_remote_conn_param_req_evt(struct hci_dev *hdev, void *data, + return send_conn_param_neg_reply(hdev, handle, + HCI_ERROR_UNKNOWN_CONN_ID); + ++ if (max > hcon->le_conn_max_interval) ++ return send_conn_param_neg_reply(hdev, handle, ++ HCI_ERROR_INVALID_LL_PARAMS); ++ + if (hci_check_conn_params(min, max, latency, timeout)) + return send_conn_param_neg_reply(hdev, handle, + HCI_ERROR_INVALID_LL_PARAMS); +diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c +index 60298975d5c45..656f49b299d20 100644 +--- a/net/bluetooth/l2cap_core.c ++++ b/net/bluetooth/l2cap_core.c +@@ -5613,7 +5613,13 @@ static inline int l2cap_conn_param_update_req(struct l2cap_conn *conn, + + memset(&rsp, 0, sizeof(rsp)); + +- err = hci_check_conn_params(min, max, latency, to_multiplier); ++ if (max > hcon->le_conn_max_interval) { ++ BT_DBG("requested connection interval exceeds current bounds."); ++ err = -EINVAL; ++ } else { ++ err = hci_check_conn_params(min, max, latency, to_multiplier); ++ } ++ + if (err) + rsp.result = cpu_to_le16(L2CAP_CONN_PARAM_REJECTED); + else +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-hci_event-fix-handling-of-hci_ev_io_capa_r.patch b/queue-6.7/bluetooth-hci_event-fix-handling-of-hci_ev_io_capa_r.patch new file mode 100644 index 00000000000..a19284a5ea2 --- /dev/null +++ b/queue-6.7/bluetooth-hci_event-fix-handling-of-hci_ev_io_capa_r.patch @@ -0,0 +1,42 @@ +From 96509a6f93096aa7c78a459940744081e7f28787 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 22 Jan 2024 09:02:47 -0500 +Subject: Bluetooth: hci_event: Fix handling of HCI_EV_IO_CAPA_REQUEST + +From: Luiz Augusto von Dentz + +[ Upstream commit 7e74aa53a68bf60f6019bd5d9a9a1406ec4d4865 ] + +If we received HCI_EV_IO_CAPA_REQUEST while +HCI_OP_READ_REMOTE_EXT_FEATURES is yet to be responded assume the remote +does support SSP since otherwise this event shouldn't be generated. + +Link: https://lore.kernel.org/linux-bluetooth/CABBYNZ+9UdG1cMZVmdtN3U2aS16AKMCyTARZZyFX7xTEDWcMOw@mail.gmail.com/T/#t +Fixes: c7f59461f5a7 ("Bluetooth: Fix a refcnt underflow problem for hci_conn") +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_event.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c +index 22b22c264c2a5..613f2fd0bcc1e 100644 +--- a/net/bluetooth/hci_event.c ++++ b/net/bluetooth/hci_event.c +@@ -5329,9 +5329,12 @@ static void hci_io_capa_request_evt(struct hci_dev *hdev, void *data, + hci_dev_lock(hdev); + + conn = hci_conn_hash_lookup_ba(hdev, ACL_LINK, &ev->bdaddr); +- if (!conn || !hci_conn_ssp_enabled(conn)) ++ if (!conn || !hci_dev_test_flag(hdev, HCI_SSP_ENABLED)) + goto unlock; + ++ /* Assume remote supports SSP since it has triggered this event */ ++ set_bit(HCI_CONN_SSP_ENABLED, &conn->flags); ++ + hci_conn_hold(conn); + + if (!hci_dev_test_flag(hdev, HCI_MGMT)) +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-hci_event-fix-wrongly-recorded-wakeup-bd_a.patch b/queue-6.7/bluetooth-hci_event-fix-wrongly-recorded-wakeup-bd_a.patch new file mode 100644 index 00000000000..76174c952bb --- /dev/null +++ b/queue-6.7/bluetooth-hci_event-fix-wrongly-recorded-wakeup-bd_a.patch @@ -0,0 +1,42 @@ +From f410dcb58db1060bb11efcb2485f5b99845b3239 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 9 Jan 2024 19:03:23 +0800 +Subject: Bluetooth: hci_event: Fix wrongly recorded wakeup BD_ADDR + +From: Zijun Hu + +[ Upstream commit 61a5ab72edea7ebc3ad2c6beea29d966f528ebfb ] + +hci_store_wake_reason() wrongly parses event HCI_Connection_Request +as HCI_Connection_Complete and HCI_Connection_Complete as +HCI_Connection_Request, so causes recording wakeup BD_ADDR error and +potential stability issue, fix it by using the correct field. + +Fixes: 2f20216c1d6f ("Bluetooth: Emit controller suspend and resume events") +Signed-off-by: Zijun Hu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_event.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c +index ef8c3bed73617..22b22c264c2a5 100644 +--- a/net/bluetooth/hci_event.c ++++ b/net/bluetooth/hci_event.c +@@ -7420,10 +7420,10 @@ static void hci_store_wake_reason(struct hci_dev *hdev, u8 event, + * keep track of the bdaddr of the connection event that woke us up. + */ + if (event == HCI_EV_CONN_REQUEST) { +- bacpy(&hdev->wake_addr, &conn_complete->bdaddr); ++ bacpy(&hdev->wake_addr, &conn_request->bdaddr); + hdev->wake_addr_type = BDADDR_BREDR; + } else if (event == HCI_EV_CONN_COMPLETE) { +- bacpy(&hdev->wake_addr, &conn_request->bdaddr); ++ bacpy(&hdev->wake_addr, &conn_complete->bdaddr); + hdev->wake_addr_type = BDADDR_BREDR; + } else if (event == HCI_EV_LE_META) { + struct hci_ev_le_meta *le_ev = (void *)skb->data; +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-hci_qca-set-bda-quirk-bit-if-fwnode-exists.patch b/queue-6.7/bluetooth-hci_qca-set-bda-quirk-bit-if-fwnode-exists.patch new file mode 100644 index 00000000000..3d15e2b5bcf --- /dev/null +++ b/queue-6.7/bluetooth-hci_qca-set-bda-quirk-bit-if-fwnode-exists.patch @@ -0,0 +1,62 @@ +From a7b27cb2dd411e1ac3d78acac5b7d3c8ec9ae2ae Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 24 Jan 2024 20:00:42 +0530 +Subject: Bluetooth: hci_qca: Set BDA quirk bit if fwnode exists in DT + +From: Janaki Ramaiah Thota + +[ Upstream commit 7dcd3e014aa7faeeaf4047190b22d8a19a0db696 ] + +BT adapter going into UNCONFIGURED state during BT turn ON when +devicetree has no local-bd-address node. + +Bluetooth will not work out of the box on such devices, to avoid this +problem, added check to set HCI_QUIRK_USE_BDADDR_PROPERTY based on +local-bd-address node entry. + +When this quirk is not set, the public Bluetooth address read by host +from controller though HCI Read BD Address command is +considered as valid. + +Fixes: e668eb1e1578 ("Bluetooth: hci_core: Don't stop BT if the BD address missing in dts") +Signed-off-by: Janaki Ramaiah Thota +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/hci_qca.c | 13 ++++++++++++- + 1 file changed, 12 insertions(+), 1 deletion(-) + +diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c +index 35f74f209d1fc..cc6dabf6884d7 100644 +--- a/drivers/bluetooth/hci_qca.c ++++ b/drivers/bluetooth/hci_qca.c +@@ -7,6 +7,7 @@ + * + * Copyright (C) 2007 Texas Instruments, Inc. + * Copyright (c) 2010, 2012, 2018 The Linux Foundation. All rights reserved. ++ * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved. + * + * Acknowledgements: + * This file is based on hci_ll.c, which was... +@@ -1886,7 +1887,17 @@ static int qca_setup(struct hci_uart *hu) + case QCA_WCN6750: + case QCA_WCN6855: + case QCA_WCN7850: +- set_bit(HCI_QUIRK_USE_BDADDR_PROPERTY, &hdev->quirks); ++ ++ /* Set BDA quirk bit for reading BDA value from fwnode property ++ * only if that property exist in DT. ++ */ ++ if (fwnode_property_present(dev_fwnode(hdev->dev.parent), "local-bd-address")) { ++ set_bit(HCI_QUIRK_USE_BDADDR_PROPERTY, &hdev->quirks); ++ bt_dev_info(hdev, "setting quirk bit to read BDA from fwnode later"); ++ } else { ++ bt_dev_dbg(hdev, "local-bd-address` is not present in the devicetree so not setting quirk bit for BDA"); ++ } ++ + hci_set_aosp_capable(hdev); + + ret = qca_read_soc_version(hdev, &ver, soc_type); +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-hci_sync-check-the-correct-flag-before-sta.patch b/queue-6.7/bluetooth-hci_sync-check-the-correct-flag-before-sta.patch new file mode 100644 index 00000000000..c5753403555 --- /dev/null +++ b/queue-6.7/bluetooth-hci_sync-check-the-correct-flag-before-sta.patch @@ -0,0 +1,49 @@ +From c5f458ba17654cf85cee883a554545cc9c1b3b97 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 2 Jan 2024 19:08:08 +0100 +Subject: Bluetooth: hci_sync: Check the correct flag before starting a scan +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Jonas Dreßler + +[ Upstream commit 6b3899be24b16ff8ee0cb25f0bd59b01b15ba1d1 ] + +There's a very confusing mistake in the code starting a HCI inquiry: We're +calling hci_dev_test_flag() to test for HCI_INQUIRY, but hci_dev_test_flag() +checks hdev->dev_flags instead of hdev->flags. HCI_INQUIRY is a bit that's +set on hdev->flags, not on hdev->dev_flags though. + +HCI_INQUIRY equals the integer 7, and in hdev->dev_flags, 7 means +HCI_BONDABLE, so we were actually checking for HCI_BONDABLE here. + +The mistake is only present in the synchronous code for starting an inquiry, +not in the async one. Also devices are typically bondable while doing an +inquiry, so that might be the reason why nobody noticed it so far. + +Fixes: abfeea476c68 ("Bluetooth: hci_sync: Convert MGMT_OP_START_DISCOVERY") +Signed-off-by: Jonas Dreßler +Reviewed-by: Simon Horman +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_sync.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/net/bluetooth/hci_sync.c b/net/bluetooth/hci_sync.c +index 97284d9b2a2e3..39ccbb1be24c3 100644 +--- a/net/bluetooth/hci_sync.c ++++ b/net/bluetooth/hci_sync.c +@@ -5629,7 +5629,7 @@ static int hci_inquiry_sync(struct hci_dev *hdev, u8 length) + + bt_dev_dbg(hdev, ""); + +- if (hci_dev_test_flag(hdev, HCI_INQUIRY)) ++ if (test_bit(HCI_INQUIRY, &hdev->flags)) + return 0; + + hci_dev_lock(hdev); +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-hci_sync-fix-accept_list-when-attempting-t.patch b/queue-6.7/bluetooth-hci_sync-fix-accept_list-when-attempting-t.patch new file mode 100644 index 00000000000..cab3741d7cd --- /dev/null +++ b/queue-6.7/bluetooth-hci_sync-fix-accept_list-when-attempting-t.patch @@ -0,0 +1,42 @@ +From 93d9bfb68307a2f5273f7afd522aecf9be046f6f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 5 Jan 2024 10:43:26 -0500 +Subject: Bluetooth: hci_sync: Fix accept_list when attempting to suspend + +From: Luiz Augusto von Dentz + +[ Upstream commit e5469adb2a7e930d96813316592302d9f8f1df4e ] + +During suspend, only wakeable devices can be in acceptlist, so if the +device was previously added it needs to be removed otherwise the device +can end up waking up the system prematurely. + +Fixes: 3b42055388c3 ("Bluetooth: hci_sync: Fix attempting to suspend with unfiltered passive scan") +Signed-off-by: Clancy Shang +Signed-off-by: Luiz Augusto von Dentz +Reviewed-by: Paul Menzel +Signed-off-by: Sasha Levin +--- + net/bluetooth/hci_sync.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/net/bluetooth/hci_sync.c b/net/bluetooth/hci_sync.c +index 39ccbb1be24c3..b90ee68bba1d6 100644 +--- a/net/bluetooth/hci_sync.c ++++ b/net/bluetooth/hci_sync.c +@@ -2274,8 +2274,11 @@ static int hci_le_add_accept_list_sync(struct hci_dev *hdev, + + /* During suspend, only wakeable devices can be in acceptlist */ + if (hdev->suspended && +- !(params->flags & HCI_CONN_FLAG_REMOTE_WAKEUP)) ++ !(params->flags & HCI_CONN_FLAG_REMOTE_WAKEUP)) { ++ hci_le_del_accept_list_sync(hdev, ¶ms->addr, ++ params->addr_type); + return 0; ++ } + + /* Select filter policy to accept all advertising */ + if (*num_entries >= hdev->le_accept_list_size) +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-qca-fix-triggering-coredump-implementation.patch b/queue-6.7/bluetooth-qca-fix-triggering-coredump-implementation.patch new file mode 100644 index 00000000000..8b3f0da1801 --- /dev/null +++ b/queue-6.7/bluetooth-qca-fix-triggering-coredump-implementation.patch @@ -0,0 +1,47 @@ +From e1e597fd65dd3a453e4796d1d52485a6ea5a47fb Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 26 Jan 2024 17:00:24 +0800 +Subject: Bluetooth: qca: Fix triggering coredump implementation + +From: Zijun Hu + +[ Upstream commit 6abf9dd26bb1699c17d601b9a292577d01827c0e ] + +hci_coredump_qca() uses __hci_cmd_sync() to send a vendor-specific command +to trigger firmware coredump, but the command does not have any event as +its sync response, so it is not suitable to use __hci_cmd_sync(), fixed by +using __hci_cmd_send(). + +Fixes: 06d3fdfcdf5c ("Bluetooth: hci_qca: Add qcom devcoredump support") +Signed-off-by: Zijun Hu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/hci_qca.c | 9 ++++----- + 1 file changed, 4 insertions(+), 5 deletions(-) + +diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c +index cc6dabf6884d7..a65de7309da4c 100644 +--- a/drivers/bluetooth/hci_qca.c ++++ b/drivers/bluetooth/hci_qca.c +@@ -1807,13 +1807,12 @@ static int qca_power_on(struct hci_dev *hdev) + + static void hci_coredump_qca(struct hci_dev *hdev) + { ++ int err; + static const u8 param[] = { 0x26 }; +- struct sk_buff *skb; + +- skb = __hci_cmd_sync(hdev, 0xfc0c, 1, param, HCI_CMD_TIMEOUT); +- if (IS_ERR(skb)) +- bt_dev_err(hdev, "%s: trigger crash failed (%ld)", __func__, PTR_ERR(skb)); +- kfree_skb(skb); ++ err = __hci_cmd_send(hdev, 0xfc0c, 1, param); ++ if (err < 0) ++ bt_dev_err(hdev, "%s: trigger crash failed (%d)", __func__, err); + } + + static int qca_setup(struct hci_uart *hu) +-- +2.43.0 + diff --git a/queue-6.7/bluetooth-qca-fix-wrong-event-type-for-patch-config-.patch b/queue-6.7/bluetooth-qca-fix-wrong-event-type-for-patch-config-.patch new file mode 100644 index 00000000000..e855238d07f --- /dev/null +++ b/queue-6.7/bluetooth-qca-fix-wrong-event-type-for-patch-config-.patch @@ -0,0 +1,45 @@ +From 55f55dc4ed083192cc0663a71ce05ad20c48a0ab Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 19 Jan 2024 17:45:30 +0800 +Subject: Bluetooth: qca: Fix wrong event type for patch config command + +From: Zijun Hu + +[ Upstream commit c0dbc56077ae759f2dd602c7561480bc2b1b712c ] + +Vendor-specific command patch config has HCI_Command_Complete event as +response, but qca_send_patch_config_cmd() wrongly expects vendor-specific +event for the command, fixed by using right event type. + +Btmon log for the vendor-specific command are shown below: +< HCI Command: Vendor (0x3f|0x0000) plen 5 + 28 01 00 00 00 +> HCI Event: Command Complete (0x0e) plen 5 + Vendor (0x3f|0x0000) ncmd 1 + Status: Success (0x00) + 28 + +Fixes: 4fac8a7ac80b ("Bluetooth: btqca: sequential validation") +Signed-off-by: Zijun Hu +Signed-off-by: Luiz Augusto von Dentz +Signed-off-by: Sasha Levin +--- + drivers/bluetooth/btqca.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c +index fdb0fae88d1c5..b40b32fa7f1c3 100644 +--- a/drivers/bluetooth/btqca.c ++++ b/drivers/bluetooth/btqca.c +@@ -152,7 +152,7 @@ static int qca_send_patch_config_cmd(struct hci_dev *hdev) + bt_dev_dbg(hdev, "QCA Patch config"); + + skb = __hci_cmd_sync_ev(hdev, EDL_PATCH_CMD_OPCODE, sizeof(cmd), +- cmd, HCI_EV_VENDOR, HCI_INIT_TIMEOUT); ++ cmd, 0, HCI_INIT_TIMEOUT); + if (IS_ERR(skb)) { + err = PTR_ERR(skb); + bt_dev_err(hdev, "Sending QCA Patch config failed (%d)", err); +-- +2.43.0 + diff --git a/queue-6.7/btrfs-fix-race-between-ordered-extent-completion-and.patch b/queue-6.7/btrfs-fix-race-between-ordered-extent-completion-and.patch new file mode 100644 index 00000000000..c1eac4d23ab --- /dev/null +++ b/queue-6.7/btrfs-fix-race-between-ordered-extent-completion-and.patch @@ -0,0 +1,268 @@ +From f430064a1aecf85073b05659b6c979df273dce4c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 12:29:26 +0000 +Subject: btrfs: fix race between ordered extent completion and fiemap + +From: Filipe Manana + +[ Upstream commit a1a4a9ca77f143c00fce69c1239887ff8b813bec ] + +For fiemap we recently stopped locking the target extent range for the +whole duration of the fiemap call, in order to avoid a deadlock in a +scenario where the fiemap buffer happens to be a memory mapped range of +the same file. This use case is very unlikely to be useful in practice but +it may be triggered by fuzz testing (syzbot, etc). + +However by not locking the target extent range for the whole duration of +the fiemap call we can race with an ordered extent. This happens like +this: + +1) The fiemap task finishes processing a file extent item that covers + the file range [512K, 1M[, and that file extent item is the last item + in the leaf currently being processed; + +2) And ordered extent for the file range [768K, 2M[, in COW mode, + completes (btrfs_finish_one_ordered()) and the file extent item + covering the range [512K, 1M[ is trimmed to cover the range + [512K, 768K[ and then a new file extent item for the range [768K, 2M[ + is inserted in the inode's subvolume tree; + +3) The fiemap task calls fiemap_next_leaf_item(), which then calls + btrfs_next_leaf() to find the next leaf / item. This finds that the + the next key following the one we previously processed (its type is + BTRFS_EXTENT_DATA_KEY and its offset is 512K), is the key corresponding + to the new file extent item inserted by the ordered extent, which has + a type of BTRFS_EXTENT_DATA_KEY and an offset of 768K; + +4) Later the fiemap code ends up at emit_fiemap_extent() and triggers + the warning: + + if (cache->offset + cache->len > offset) { + WARN_ON(1); + return -EINVAL; + } + + Since we get 1M > 768K, because the previously emitted entry for the + old extent covering the file range [512K, 1M[ ends at an offset that + is greater than the new extent's start offset (768K). This makes fiemap + fail with -EINVAL besides triggering the warning that produces a stack + trace like the following: + + [1621.677651] ------------[ cut here ]------------ + [1621.677656] WARNING: CPU: 1 PID: 204366 at fs/btrfs/extent_io.c:2492 emit_fiemap_extent+0x84/0x90 [btrfs] + [1621.677899] Modules linked in: btrfs blake2b_generic (...) + [1621.677951] CPU: 1 PID: 204366 Comm: pool Not tainted 6.8.0-rc5-btrfs-next-151+ #1 + [1621.677954] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.16.2-0-gea1b7a073390-prebuilt.qemu.org 04/01/2014 + [1621.677956] RIP: 0010:emit_fiemap_extent+0x84/0x90 [btrfs] + [1621.678033] Code: 2b 4c 89 63 (...) + [1621.678035] RSP: 0018:ffffab16089ffd20 EFLAGS: 00010206 + [1621.678037] RAX: 00000000004fa000 RBX: ffffab16089ffe08 RCX: 0000000000009000 + [1621.678039] RDX: 00000000004f9000 RSI: 00000000004f1000 RDI: ffffab16089ffe90 + [1621.678040] RBP: 00000000004f9000 R08: 0000000000001000 R09: 0000000000000000 + [1621.678041] R10: 0000000000000000 R11: 0000000000001000 R12: 0000000041d78000 + [1621.678043] R13: 0000000000001000 R14: 0000000000000000 R15: ffff9434f0b17850 + [1621.678044] FS: 00007fa6e20006c0(0000) GS:ffff943bdfa40000(0000) knlGS:0000000000000000 + [1621.678046] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 + [1621.678048] CR2: 00007fa6b0801000 CR3: 000000012d404002 CR4: 0000000000370ef0 + [1621.678053] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 + [1621.678055] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 + [1621.678056] Call Trace: + [1621.678074] + [1621.678076] ? __warn+0x80/0x130 + [1621.678082] ? emit_fiemap_extent+0x84/0x90 [btrfs] + [1621.678159] ? report_bug+0x1f4/0x200 + [1621.678164] ? handle_bug+0x42/0x70 + [1621.678167] ? exc_invalid_op+0x14/0x70 + [1621.678170] ? asm_exc_invalid_op+0x16/0x20 + [1621.678178] ? emit_fiemap_extent+0x84/0x90 [btrfs] + [1621.678253] extent_fiemap+0x766/0xa30 [btrfs] + [1621.678339] btrfs_fiemap+0x45/0x80 [btrfs] + [1621.678420] do_vfs_ioctl+0x1e4/0x870 + [1621.678431] __x64_sys_ioctl+0x6a/0xc0 + [1621.678434] do_syscall_64+0x52/0x120 + [1621.678445] entry_SYSCALL_64_after_hwframe+0x6e/0x76 + +There's also another case where before calling btrfs_next_leaf() we are +processing a hole or a prealloc extent and we had several delalloc ranges +within that hole or prealloc extent. In that case if the ordered extents +complete before we find the next key, we may end up finding an extent item +with an offset smaller than (or equals to) the offset in cache->offset. + +So fix this by changing emit_fiemap_extent() to address these three +scenarios like this: + +1) For the first case, steps listed above, adjust the length of the + previously cached extent so that it does not overlap with the current + extent, emit the previous one and cache the current file extent item; + +2) For the second case where he had a hole or prealloc extent with + multiple delalloc ranges inside the hole or prealloc extent's range, + and the current file extent item has an offset that matches the offset + in the fiemap cache, just discard what we have in the fiemap cache and + assign the current file extent item to the cache, since it's more up + to date; + +3) For the third case where he had a hole or prealloc extent with + multiple delalloc ranges inside the hole or prealloc extent's range + and the offset of the file extent item we just found is smaller than + what we have in the cache, just skip the current file extent item + if its range end at or behind the cached extent's end, because we may + have emitted (to the fiemap user space buffer) delalloc ranges that + overlap with the current file extent item's range. If the file extent + item's range goes beyond the end offset of the cached extent, just + emit the cached extent and cache a subrange of the file extent item, + that goes from the end offset of the cached extent to the end offset + of the file extent item. + +Dealing with those cases in those ways makes everything consistent by +reflecting the current state of file extent items in the btree and +without emitting extents that have overlapping ranges (which would be +confusing and violating expectations). + +This issue could be triggered often with test case generic/561, and was +also hit and reported by Wang Yugui. + +Reported-by: Wang Yugui +Link: https://lore.kernel.org/linux-btrfs/20240223104619.701F.409509F4@e16-tech.com/ +Fixes: b0ad381fa769 ("btrfs: fix deadlock with fiemap and extent locking") +Reviewed-by: Josef Bacik +Signed-off-by: Filipe Manana +Signed-off-by: David Sterba +Signed-off-by: Sasha Levin +--- + fs/btrfs/extent_io.c | 103 ++++++++++++++++++++++++++++++++++++++++--- + 1 file changed, 96 insertions(+), 7 deletions(-) + +diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c +index 197b41d02735b..3f795f105a645 100644 +--- a/fs/btrfs/extent_io.c ++++ b/fs/btrfs/extent_io.c +@@ -2436,6 +2436,7 @@ static int emit_fiemap_extent(struct fiemap_extent_info *fieinfo, + struct fiemap_cache *cache, + u64 offset, u64 phys, u64 len, u32 flags) + { ++ u64 cache_end; + int ret = 0; + + /* Set at the end of extent_fiemap(). */ +@@ -2445,15 +2446,102 @@ static int emit_fiemap_extent(struct fiemap_extent_info *fieinfo, + goto assign; + + /* +- * Sanity check, extent_fiemap() should have ensured that new +- * fiemap extent won't overlap with cached one. +- * Not recoverable. ++ * When iterating the extents of the inode, at extent_fiemap(), we may ++ * find an extent that starts at an offset behind the end offset of the ++ * previous extent we processed. This happens if fiemap is called ++ * without FIEMAP_FLAG_SYNC and there are ordered extents completing ++ * while we call btrfs_next_leaf() (through fiemap_next_leaf_item()). + * +- * NOTE: Physical address can overlap, due to compression ++ * For example we are in leaf X processing its last item, which is the ++ * file extent item for file range [512K, 1M[, and after ++ * btrfs_next_leaf() releases the path, there's an ordered extent that ++ * completes for the file range [768K, 2M[, and that results in trimming ++ * the file extent item so that it now corresponds to the file range ++ * [512K, 768K[ and a new file extent item is inserted for the file ++ * range [768K, 2M[, which may end up as the last item of leaf X or as ++ * the first item of the next leaf - in either case btrfs_next_leaf() ++ * will leave us with a path pointing to the new extent item, for the ++ * file range [768K, 2M[, since that's the first key that follows the ++ * last one we processed. So in order not to report overlapping extents ++ * to user space, we trim the length of the previously cached extent and ++ * emit it. ++ * ++ * Upon calling btrfs_next_leaf() we may also find an extent with an ++ * offset smaller than or equals to cache->offset, and this happens ++ * when we had a hole or prealloc extent with several delalloc ranges in ++ * it, but after btrfs_next_leaf() released the path, delalloc was ++ * flushed and the resulting ordered extents were completed, so we can ++ * now have found a file extent item for an offset that is smaller than ++ * or equals to what we have in cache->offset. We deal with this as ++ * described below. + */ +- if (cache->offset + cache->len > offset) { +- WARN_ON(1); +- return -EINVAL; ++ cache_end = cache->offset + cache->len; ++ if (cache_end > offset) { ++ if (offset == cache->offset) { ++ /* ++ * We cached a dealloc range (found in the io tree) for ++ * a hole or prealloc extent and we have now found a ++ * file extent item for the same offset. What we have ++ * now is more recent and up to date, so discard what ++ * we had in the cache and use what we have just found. ++ */ ++ goto assign; ++ } else if (offset > cache->offset) { ++ /* ++ * The extent range we previously found ends after the ++ * offset of the file extent item we found and that ++ * offset falls somewhere in the middle of that previous ++ * extent range. So adjust the range we previously found ++ * to end at the offset of the file extent item we have ++ * just found, since this extent is more up to date. ++ * Emit that adjusted range and cache the file extent ++ * item we have just found. This corresponds to the case ++ * where a previously found file extent item was split ++ * due to an ordered extent completing. ++ */ ++ cache->len = offset - cache->offset; ++ goto emit; ++ } else { ++ const u64 range_end = offset + len; ++ ++ /* ++ * The offset of the file extent item we have just found ++ * is behind the cached offset. This means we were ++ * processing a hole or prealloc extent for which we ++ * have found delalloc ranges (in the io tree), so what ++ * we have in the cache is the last delalloc range we ++ * found while the file extent item we found can be ++ * either for a whole delalloc range we previously ++ * emmitted or only a part of that range. ++ * ++ * We have two cases here: ++ * ++ * 1) The file extent item's range ends at or behind the ++ * cached extent's end. In this case just ignore the ++ * current file extent item because we don't want to ++ * overlap with previous ranges that may have been ++ * emmitted already; ++ * ++ * 2) The file extent item starts behind the currently ++ * cached extent but its end offset goes beyond the ++ * end offset of the cached extent. We don't want to ++ * overlap with a previous range that may have been ++ * emmitted already, so we emit the currently cached ++ * extent and then partially store the current file ++ * extent item's range in the cache, for the subrange ++ * going the cached extent's end to the end of the ++ * file extent item. ++ */ ++ if (range_end <= cache_end) ++ return 0; ++ ++ if (!(flags & (FIEMAP_EXTENT_ENCODED | FIEMAP_EXTENT_DELALLOC))) ++ phys += cache_end - offset; ++ ++ offset = cache_end; ++ len = range_end - cache_end; ++ goto emit; ++ } + } + + /* +@@ -2473,6 +2561,7 @@ static int emit_fiemap_extent(struct fiemap_extent_info *fieinfo, + return 0; + } + ++emit: + /* Not mergeable, need to submit cached one */ + ret = fiemap_fill_next_extent(fieinfo, cache->offset, cache->phys, + cache->len, cache->flags); +-- +2.43.0 + diff --git a/queue-6.7/cpufreq-intel_pstate-fix-pstate-limits-enforcement-f.patch b/queue-6.7/cpufreq-intel_pstate-fix-pstate-limits-enforcement-f.patch new file mode 100644 index 00000000000..429db49781b --- /dev/null +++ b/queue-6.7/cpufreq-intel_pstate-fix-pstate-limits-enforcement-f.patch @@ -0,0 +1,42 @@ +From e82b178e30639aa1fb0d8c3799b50e8c956360ef Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sat, 17 Feb 2024 13:30:10 -0800 +Subject: cpufreq: intel_pstate: fix pstate limits enforcement for adjust_perf + call back + +From: Doug Smythies + +[ Upstream commit f0a0fc10abb062d122db5ac4ed42f6d1ca342649 ] + +There is a loophole in pstate limit clamping for the intel_cpufreq CPU +frequency scaling driver (intel_pstate in passive mode), schedutil CPU +frequency scaling governor, HWP (HardWare Pstate) control enabled, when +the adjust_perf call back path is used. + +Fix it. + +Fixes: a365ab6b9dfb cpufreq: intel_pstate: Implement the ->adjust_perf() callback +Signed-off-by: Doug Smythies +Signed-off-by: Rafael J. Wysocki +Signed-off-by: Sasha Levin +--- + drivers/cpufreq/intel_pstate.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/cpufreq/intel_pstate.c b/drivers/cpufreq/intel_pstate.c +index f5c69fa230d9b..357e01a272743 100644 +--- a/drivers/cpufreq/intel_pstate.c ++++ b/drivers/cpufreq/intel_pstate.c +@@ -2983,6 +2983,9 @@ static void intel_cpufreq_adjust_perf(unsigned int cpunum, + if (min_pstate < cpu->min_perf_ratio) + min_pstate = cpu->min_perf_ratio; + ++ if (min_pstate > cpu->max_perf_ratio) ++ min_pstate = cpu->max_perf_ratio; ++ + max_pstate = min(cap_pstate, cpu->max_perf_ratio); + if (max_pstate < min_pstate) + max_pstate = min_pstate; +-- +2.43.0 + diff --git a/queue-6.7/drivers-perf-added-capabilities-for-legacy-pmu.patch b/queue-6.7/drivers-perf-added-capabilities-for-legacy-pmu.patch new file mode 100644 index 00000000000..59dcedc049f --- /dev/null +++ b/queue-6.7/drivers-perf-added-capabilities-for-legacy-pmu.patch @@ -0,0 +1,43 @@ +From 5b8ca818c16cc39bfa611b471dd19750a8e0f184 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 20:00:01 +0300 +Subject: drivers: perf: added capabilities for legacy PMU + +From: Vadim Shakirov + +[ Upstream commit 65730fe8f4fb039683d76fa8ea7e8d18a53c6cc6 ] + +Added the PERF_PMU_CAP_NO_INTERRUPT flag because the legacy pmu driver +does not provide sampling capabilities + +Added the PERF_PMU_CAP_NO_EXCLUDE flag because the legacy pmu driver +does not provide the ability to disable counter incrementation in +different privilege modes + +Suggested-by: Atish Patra +Signed-off-by: Vadim Shakirov +Reviewed-by: Atish Patra +Fixes: 9b3e150e310e ("RISC-V: Add a simple platform driver for RISC-V legacy perf") +Link: https://lore.kernel.org/r/20240227170002.188671-2-vadim.shakirov@syntacore.com +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + drivers/perf/riscv_pmu_legacy.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/drivers/perf/riscv_pmu_legacy.c b/drivers/perf/riscv_pmu_legacy.c +index 79fdd667922e8..a85fc9a15f039 100644 +--- a/drivers/perf/riscv_pmu_legacy.c ++++ b/drivers/perf/riscv_pmu_legacy.c +@@ -117,6 +117,8 @@ static void pmu_legacy_init(struct riscv_pmu *pmu) + pmu->event_mapped = pmu_legacy_event_mapped; + pmu->event_unmapped = pmu_legacy_event_unmapped; + pmu->csr_index = pmu_legacy_csr_index; ++ pmu->pmu.capabilities |= PERF_PMU_CAP_NO_INTERRUPT; ++ pmu->pmu.capabilities |= PERF_PMU_CAP_NO_EXCLUDE; + + perf_pmu_register(&pmu->pmu, "cpu", PERF_TYPE_RAW); + } +-- +2.43.0 + diff --git a/queue-6.7/drivers-perf-ctr_get_width-function-for-legacy-is-no.patch b/queue-6.7/drivers-perf-ctr_get_width-function-for-legacy-is-no.patch new file mode 100644 index 00000000000..0b290c7252c --- /dev/null +++ b/queue-6.7/drivers-perf-ctr_get_width-function-for-legacy-is-no.patch @@ -0,0 +1,112 @@ +From 88daa58cb9af1e3bf945eaf0395f2e2f63eec394 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 20:00:02 +0300 +Subject: drivers: perf: ctr_get_width function for legacy is not defined + +From: Vadim Shakirov + +[ Upstream commit 682dc133f83e0194796e6ea72eb642df1c03dfbe ] + +With parameters CONFIG_RISCV_PMU_LEGACY=y and CONFIG_RISCV_PMU_SBI=n +linux kernel crashes when you try perf record: + +$ perf record ls +[ 46.749286] Unable to handle kernel NULL pointer dereference at virtual address 0000000000000000 +[ 46.750199] Oops [#1] +[ 46.750342] Modules linked in: +[ 46.750608] CPU: 0 PID: 107 Comm: perf-exec Not tainted 6.6.0 #2 +[ 46.750906] Hardware name: riscv-virtio,qemu (DT) +[ 46.751184] epc : 0x0 +[ 46.751430] ra : arch_perf_update_userpage+0x54/0x13e +[ 46.751680] epc : 0000000000000000 ra : ffffffff8072ee52 sp : ff2000000022b8f0 +[ 46.751958] gp : ffffffff81505988 tp : ff6000000290d400 t0 : ff2000000022b9c0 +[ 46.752229] t1 : 0000000000000001 t2 : 0000000000000003 s0 : ff2000000022b930 +[ 46.752451] s1 : ff600000028fb000 a0 : 0000000000000000 a1 : ff600000028fb000 +[ 46.752673] a2 : 0000000ae2751268 a3 : 00000000004fb708 a4 : 0000000000000004 +[ 46.752895] a5 : 0000000000000000 a6 : 000000000017ffe3 a7 : 00000000000000d2 +[ 46.753117] s2 : ff600000028fb000 s3 : 0000000ae2751268 s4 : 0000000000000000 +[ 46.753338] s5 : ffffffff8153e290 s6 : ff600000863b9000 s7 : ff60000002961078 +[ 46.753562] s8 : ff60000002961048 s9 : ff60000002961058 s10: 0000000000000001 +[ 46.753783] s11: 0000000000000018 t3 : ffffffffffffffff t4 : ffffffffffffffff +[ 46.754005] t5 : ff6000000292270c t6 : ff2000000022bb30 +[ 46.754179] status: 0000000200000100 badaddr: 0000000000000000 cause: 000000000000000c +[ 46.754653] Code: Unable to access instruction at 0xffffffffffffffec. +[ 46.754939] ---[ end trace 0000000000000000 ]--- +[ 46.755131] note: perf-exec[107] exited with irqs disabled +[ 46.755546] note: perf-exec[107] exited with preempt_count 4 + +This happens because in the legacy case the ctr_get_width function was not +defined, but it is used in arch_perf_update_userpage. + +Also remove extra check in riscv_pmu_ctr_get_width_mask + +Signed-off-by: Vadim Shakirov +Reviewed-by: Alexandre Ghiti +Reviewed-by: Atish Patra +Fixes: cc4c07c89aad ("drivers: perf: Implement perf event mmap support in the SBI backend") +Link: https://lore.kernel.org/r/20240227170002.188671-3-vadim.shakirov@syntacore.com +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + drivers/perf/riscv_pmu.c | 18 +++++------------- + drivers/perf/riscv_pmu_legacy.c | 8 +++++++- + 2 files changed, 12 insertions(+), 14 deletions(-) + +diff --git a/drivers/perf/riscv_pmu.c b/drivers/perf/riscv_pmu.c +index 0dda70e1ef90a..c78a6fd6c57f6 100644 +--- a/drivers/perf/riscv_pmu.c ++++ b/drivers/perf/riscv_pmu.c +@@ -150,19 +150,11 @@ u64 riscv_pmu_ctr_get_width_mask(struct perf_event *event) + struct riscv_pmu *rvpmu = to_riscv_pmu(event->pmu); + struct hw_perf_event *hwc = &event->hw; + +- if (!rvpmu->ctr_get_width) +- /** +- * If the pmu driver doesn't support counter width, set it to default +- * maximum allowed by the specification. +- */ +- cwidth = 63; +- else { +- if (hwc->idx == -1) +- /* Handle init case where idx is not initialized yet */ +- cwidth = rvpmu->ctr_get_width(0); +- else +- cwidth = rvpmu->ctr_get_width(hwc->idx); +- } ++ if (hwc->idx == -1) ++ /* Handle init case where idx is not initialized yet */ ++ cwidth = rvpmu->ctr_get_width(0); ++ else ++ cwidth = rvpmu->ctr_get_width(hwc->idx); + + return GENMASK_ULL(cwidth, 0); + } +diff --git a/drivers/perf/riscv_pmu_legacy.c b/drivers/perf/riscv_pmu_legacy.c +index a85fc9a15f039..fa0bccf4edf2e 100644 +--- a/drivers/perf/riscv_pmu_legacy.c ++++ b/drivers/perf/riscv_pmu_legacy.c +@@ -37,6 +37,12 @@ static int pmu_legacy_event_map(struct perf_event *event, u64 *config) + return pmu_legacy_ctr_get_idx(event); + } + ++/* cycle & instret are always 64 bit, one bit less according to SBI spec */ ++static int pmu_legacy_ctr_get_width(int idx) ++{ ++ return 63; ++} ++ + static u64 pmu_legacy_read_ctr(struct perf_event *event) + { + struct hw_perf_event *hwc = &event->hw; +@@ -111,7 +117,7 @@ static void pmu_legacy_init(struct riscv_pmu *pmu) + pmu->ctr_stop = NULL; + pmu->event_map = pmu_legacy_event_map; + pmu->ctr_get_idx = pmu_legacy_ctr_get_idx; +- pmu->ctr_get_width = NULL; ++ pmu->ctr_get_width = pmu_legacy_ctr_get_width; + pmu->ctr_clear_idx = NULL; + pmu->ctr_read = pmu_legacy_read_ctr; + pmu->event_mapped = pmu_legacy_event_mapped; +-- +2.43.0 + diff --git a/queue-6.7/drm-amd-display-prevent-potential-buffer-overflow-in.patch b/queue-6.7/drm-amd-display-prevent-potential-buffer-overflow-in.patch new file mode 100644 index 00000000000..427fad74472 --- /dev/null +++ b/queue-6.7/drm-amd-display-prevent-potential-buffer-overflow-in.patch @@ -0,0 +1,59 @@ +From e8ade91757eaf66bd2dcbc6e07ec3ed9c6942129 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 20 Feb 2024 09:14:25 +0530 +Subject: drm/amd/display: Prevent potential buffer overflow in + map_hw_resources + +From: Srinivasan Shanmugam + +[ Upstream commit 0f8ca019544a252d1afb468ce840c6dcbac73af4 ] + +Adds a check in the map_hw_resources function to prevent a potential +buffer overflow. The function was accessing arrays using an index that +could potentially be greater than the size of the arrays, leading to a +buffer overflow. + +Adds a check to ensure that the index is within the bounds of the +arrays. If the index is out of bounds, an error message is printed and +break it will continue execution with just ignoring extra data early to +prevent the buffer overflow. + +Reported by smatch: +drivers/gpu/drm/amd/amdgpu/../display/dc/dml2/dml2_wrapper.c:79 map_hw_resources() error: buffer overflow 'dml2->v20.scratch.dml_to_dc_pipe_mapping.disp_cfg_to_stream_id' 6 <= 7 +drivers/gpu/drm/amd/amdgpu/../display/dc/dml2/dml2_wrapper.c:81 map_hw_resources() error: buffer overflow 'dml2->v20.scratch.dml_to_dc_pipe_mapping.disp_cfg_to_plane_id' 6 <= 7 + +Fixes: 7966f319c66d ("drm/amd/display: Introduce DML2") +Cc: Rodrigo Siqueira +Cc: Roman Li +Cc: Qingqing Zhuo +Cc: Aurabindo Pillai +Cc: Tom Chung +Signed-off-by: Srinivasan Shanmugam +Suggested-by: Roman Li +Reviewed-by: Roman Li +Reviewed-by: Rodrigo Siqueira +Signed-off-by: Alex Deucher +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/amd/display/dc/dml2/dml2_wrapper.c | 5 +++++ + 1 file changed, 5 insertions(+) + +diff --git a/drivers/gpu/drm/amd/display/dc/dml2/dml2_wrapper.c b/drivers/gpu/drm/amd/display/dc/dml2/dml2_wrapper.c +index 8f231418870f2..c62b61ac45d27 100644 +--- a/drivers/gpu/drm/amd/display/dc/dml2/dml2_wrapper.c ++++ b/drivers/gpu/drm/amd/display/dc/dml2/dml2_wrapper.c +@@ -76,6 +76,11 @@ static void map_hw_resources(struct dml2_context *dml2, + in_out_display_cfg->hw.DLGRefClkFreqMHz = 50; + } + for (j = 0; j < mode_support_info->DPPPerSurface[i]; j++) { ++ if (i >= __DML2_WRAPPER_MAX_STREAMS_PLANES__) { ++ dml_print("DML::%s: Index out of bounds: i=%d, __DML2_WRAPPER_MAX_STREAMS_PLANES__=%d\n", ++ __func__, i, __DML2_WRAPPER_MAX_STREAMS_PLANES__); ++ break; ++ } + dml2->v20.scratch.dml_to_dc_pipe_mapping.dml_pipe_idx_to_stream_id[num_pipes] = dml2->v20.scratch.dml_to_dc_pipe_mapping.disp_cfg_to_stream_id[i]; + dml2->v20.scratch.dml_to_dc_pipe_mapping.dml_pipe_idx_to_stream_id_valid[num_pipes] = true; + dml2->v20.scratch.dml_to_dc_pipe_mapping.dml_pipe_idx_to_plane_id[num_pipes] = dml2->v20.scratch.dml_to_dc_pipe_mapping.disp_cfg_to_plane_id[i]; +-- +2.43.0 + diff --git a/queue-6.7/drm-nouveau-keep-dma-buffers-required-for-suspend-re.patch b/queue-6.7/drm-nouveau-keep-dma-buffers-required-for-suspend-re.patch new file mode 100644 index 00000000000..047e6a46005 --- /dev/null +++ b/queue-6.7/drm-nouveau-keep-dma-buffers-required-for-suspend-re.patch @@ -0,0 +1,47 @@ +From b7b9f288fd236d73ce52962cfd0e0e69bb113777 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 29 Feb 2024 21:52:05 +0530 +Subject: drm/nouveau: keep DMA buffers required for suspend/resume + +From: Sid Pranjale + +[ Upstream commit f6ecfdad359a01c7fd8a3bcfde3ef0acdf107e6e ] + +Nouveau deallocates a few buffers post GPU init which are required for GPU suspend/resume to function correctly. +This is likely not as big an issue on systems where the NVGPU is the only GPU, but on multi-GPU set ups it leads to a regression where the kernel module errors and results in a system-wide rendering freeze. + +This commit addresses that regression by moving the two buffers required for suspend and resume to be deallocated at driver unload instead of post init. + +Fixes: 042b5f83841fb ("drm/nouveau: fix several DMA buffer leaks") +Signed-off-by: Sid Pranjale +Signed-off-by: Dave Airlie +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/nouveau/nvkm/subdev/gsp/r535.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gsp/r535.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gsp/r535.c +index a41735ab60683..d66fc3570642b 100644 +--- a/drivers/gpu/drm/nouveau/nvkm/subdev/gsp/r535.c ++++ b/drivers/gpu/drm/nouveau/nvkm/subdev/gsp/r535.c +@@ -1054,8 +1054,6 @@ r535_gsp_postinit(struct nvkm_gsp *gsp) + /* Release the DMA buffers that were needed only for boot and init */ + nvkm_gsp_mem_dtor(gsp, &gsp->boot.fw); + nvkm_gsp_mem_dtor(gsp, &gsp->libos); +- nvkm_gsp_mem_dtor(gsp, &gsp->rmargs); +- nvkm_gsp_mem_dtor(gsp, &gsp->wpr_meta); + + return ret; + } +@@ -2163,6 +2161,8 @@ r535_gsp_dtor(struct nvkm_gsp *gsp) + + r535_gsp_dtor_fws(gsp); + ++ nvkm_gsp_mem_dtor(gsp, &gsp->rmargs); ++ nvkm_gsp_mem_dtor(gsp, &gsp->wpr_meta); + nvkm_gsp_mem_dtor(gsp, &gsp->shm.mem); + nvkm_gsp_mem_dtor(gsp, &gsp->loginit); + nvkm_gsp_mem_dtor(gsp, &gsp->logintr); +-- +2.43.0 + diff --git a/queue-6.7/drm-tegra-remove-existing-framebuffer-only-if-we-sup.patch b/queue-6.7/drm-tegra-remove-existing-framebuffer-only-if-we-sup.patch new file mode 100644 index 00000000000..fa481d07b8c --- /dev/null +++ b/queue-6.7/drm-tegra-remove-existing-framebuffer-only-if-we-sup.patch @@ -0,0 +1,63 @@ +From 41774432d4719db0e112a37cc21785491f471eda Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 23 Feb 2024 16:03:33 +0100 +Subject: drm/tegra: Remove existing framebuffer only if we support display + +From: Thierry Reding + +[ Upstream commit 86bf8cfda6d2a6720fa2e6e676c98f0882c9d3d7 ] + +Tegra DRM doesn't support display on Tegra234 and later, so make sure +not to remove any existing framebuffers in that case. + +v2: - add comments explaining how this situation can come about + - clear DRIVER_MODESET and DRIVER_ATOMIC feature bits + +Fixes: 6848c291a54f ("drm/aperture: Convert drivers to aperture interfaces") +Signed-off-by: Thierry Reding +Reviewed-by: Thomas Zimmermann +Reviewed-by: Javier Martinez Canillas +Signed-off-by: Robert Foss +Link: https://patchwork.freedesktop.org/patch/msgid/20240223150333.1401582-1-thierry.reding@gmail.com +Signed-off-by: Sasha Levin +--- + drivers/gpu/drm/tegra/drm.c | 23 ++++++++++++++++++++--- + 1 file changed, 20 insertions(+), 3 deletions(-) + +diff --git a/drivers/gpu/drm/tegra/drm.c b/drivers/gpu/drm/tegra/drm.c +index ff36171c8fb70..373bcd79257e0 100644 +--- a/drivers/gpu/drm/tegra/drm.c ++++ b/drivers/gpu/drm/tegra/drm.c +@@ -1242,9 +1242,26 @@ static int host1x_drm_probe(struct host1x_device *dev) + + drm_mode_config_reset(drm); + +- err = drm_aperture_remove_framebuffers(&tegra_drm_driver); +- if (err < 0) +- goto hub; ++ /* ++ * Only take over from a potential firmware framebuffer if any CRTCs ++ * have been registered. This must not be a fatal error because there ++ * are other accelerators that are exposed via this driver. ++ * ++ * Another case where this happens is on Tegra234 where the display ++ * hardware is no longer part of the host1x complex, so this driver ++ * will not expose any modesetting features. ++ */ ++ if (drm->mode_config.num_crtc > 0) { ++ err = drm_aperture_remove_framebuffers(&tegra_drm_driver); ++ if (err < 0) ++ goto hub; ++ } else { ++ /* ++ * Indicate to userspace that this doesn't expose any display ++ * capabilities. ++ */ ++ drm->driver_features &= ~(DRIVER_MODESET | DRIVER_ATOMIC); ++ } + + err = drm_dev_register(drm, 0); + if (err < 0) +-- +2.43.0 + diff --git a/queue-6.7/efi-capsule-loader-fix-incorrect-allocation-size.patch b/queue-6.7/efi-capsule-loader-fix-incorrect-allocation-size.patch new file mode 100644 index 00000000000..bb821e63758 --- /dev/null +++ b/queue-6.7/efi-capsule-loader-fix-incorrect-allocation-size.patch @@ -0,0 +1,43 @@ +From 9e35afa49051c9e41195cf71d7fa0522d20b56a5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 12 Feb 2024 12:24:40 +0100 +Subject: efi/capsule-loader: fix incorrect allocation size + +From: Arnd Bergmann + +[ Upstream commit fccfa646ef3628097d59f7d9c1a3e84d4b6bb45e ] + +gcc-14 notices that the allocation with sizeof(void) on 32-bit architectures +is not enough for a 64-bit phys_addr_t: + +drivers/firmware/efi/capsule-loader.c: In function 'efi_capsule_open': +drivers/firmware/efi/capsule-loader.c:295:24: error: allocation of insufficient size '4' for type 'phys_addr_t' {aka 'long long unsigned int'} with size '8' [-Werror=alloc-size] + 295 | cap_info->phys = kzalloc(sizeof(void *), GFP_KERNEL); + | ^ + +Use the correct type instead here. + +Fixes: f24c4d478013 ("efi/capsule-loader: Reinstate virtual capsule mapping") +Signed-off-by: Arnd Bergmann +Signed-off-by: Ard Biesheuvel +Signed-off-by: Sasha Levin +--- + drivers/firmware/efi/capsule-loader.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/firmware/efi/capsule-loader.c b/drivers/firmware/efi/capsule-loader.c +index 3e8d4b51a8140..97bafb5f70389 100644 +--- a/drivers/firmware/efi/capsule-loader.c ++++ b/drivers/firmware/efi/capsule-loader.c +@@ -292,7 +292,7 @@ static int efi_capsule_open(struct inode *inode, struct file *file) + return -ENOMEM; + } + +- cap_info->phys = kzalloc(sizeof(void *), GFP_KERNEL); ++ cap_info->phys = kzalloc(sizeof(phys_addr_t), GFP_KERNEL); + if (!cap_info->phys) { + kfree(cap_info->pages); + kfree(cap_info); +-- +2.43.0 + diff --git a/queue-6.7/fbcon-always-restore-the-old-font-data-in-fbcon_do_s.patch b/queue-6.7/fbcon-always-restore-the-old-font-data-in-fbcon_do_s.patch new file mode 100644 index 00000000000..f2357eca9fd --- /dev/null +++ b/queue-6.7/fbcon-always-restore-the-old-font-data-in-fbcon_do_s.patch @@ -0,0 +1,95 @@ +From 448f55667a5b74c06527e0109983b31ceed77e8a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 8 Feb 2024 12:44:11 +0100 +Subject: fbcon: always restore the old font data in fbcon_do_set_font() + +From: Jiri Slaby (SUSE) + +[ Upstream commit 00d6a284fcf3fad1b7e1b5bc3cd87cbfb60ce03f ] + +Commit a5a923038d70 (fbdev: fbcon: Properly revert changes when +vc_resize() failed) started restoring old font data upon failure (of +vc_resize()). But it performs so only for user fonts. It means that the +"system"/internal fonts are not restored at all. So in result, the very +first call to fbcon_do_set_font() performs no restore at all upon +failing vc_resize(). + +This can be reproduced by Syzkaller to crash the system on the next +invocation of font_get(). It's rather hard to hit the allocation failure +in vc_resize() on the first font_set(), but not impossible. Esp. if +fault injection is used to aid the execution/failure. It was +demonstrated by Sirius: + BUG: unable to handle page fault for address: fffffffffffffff8 + #PF: supervisor read access in kernel mode + #PF: error_code(0x0000) - not-present page + PGD cb7b067 P4D cb7b067 PUD cb7d067 PMD 0 + Oops: 0000 [#1] PREEMPT SMP KASAN + CPU: 1 PID: 8007 Comm: poc Not tainted 6.7.0-g9d1694dc91ce #20 + Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.15.0-1 04/01/2014 + RIP: 0010:fbcon_get_font+0x229/0x800 drivers/video/fbdev/core/fbcon.c:2286 + Call Trace: + + con_font_get drivers/tty/vt/vt.c:4558 [inline] + con_font_op+0x1fc/0xf20 drivers/tty/vt/vt.c:4673 + vt_k_ioctl drivers/tty/vt/vt_ioctl.c:474 [inline] + vt_ioctl+0x632/0x2ec0 drivers/tty/vt/vt_ioctl.c:752 + tty_ioctl+0x6f8/0x1570 drivers/tty/tty_io.c:2803 + vfs_ioctl fs/ioctl.c:51 [inline] + ... + +So restore the font data in any case, not only for user fonts. Note the +later 'if' is now protected by 'old_userfont' and not 'old_data' as the +latter is always set now. (And it is supposed to be non-NULL. Otherwise +we would see the bug above again.) + +Signed-off-by: Jiri Slaby (SUSE) +Fixes: a5a923038d70 ("fbdev: fbcon: Properly revert changes when vc_resize() failed") +Reported-and-tested-by: Ubisectech Sirius +Cc: Ubisectech Sirius +Cc: Daniel Vetter +Cc: Helge Deller +Cc: linux-fbdev@vger.kernel.org +Cc: dri-devel@lists.freedesktop.org +Signed-off-by: Daniel Vetter +Link: https://patchwork.freedesktop.org/patch/msgid/20240208114411.14604-1-jirislaby@kernel.org +Signed-off-by: Sasha Levin +--- + drivers/video/fbdev/core/fbcon.c | 8 +++----- + 1 file changed, 3 insertions(+), 5 deletions(-) + +diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c +index 63af6ab034b5f..e6c45d585482f 100644 +--- a/drivers/video/fbdev/core/fbcon.c ++++ b/drivers/video/fbdev/core/fbcon.c +@@ -2400,11 +2400,9 @@ static int fbcon_do_set_font(struct vc_data *vc, int w, int h, int charcount, + struct fbcon_ops *ops = info->fbcon_par; + struct fbcon_display *p = &fb_display[vc->vc_num]; + int resize, ret, old_userfont, old_width, old_height, old_charcount; +- char *old_data = NULL; ++ u8 *old_data = vc->vc_font.data; + + resize = (w != vc->vc_font.width) || (h != vc->vc_font.height); +- if (p->userfont) +- old_data = vc->vc_font.data; + vc->vc_font.data = (void *)(p->fontdata = data); + old_userfont = p->userfont; + if ((p->userfont = userfont)) +@@ -2438,13 +2436,13 @@ static int fbcon_do_set_font(struct vc_data *vc, int w, int h, int charcount, + update_screen(vc); + } + +- if (old_data && (--REFCOUNT(old_data) == 0)) ++ if (old_userfont && (--REFCOUNT(old_data) == 0)) + kfree(old_data - FONT_EXTRA_WORDS * sizeof(int)); + return 0; + + err_out: + p->fontdata = old_data; +- vc->vc_font.data = (void *)old_data; ++ vc->vc_font.data = old_data; + + if (userfont) { + p->userfont = old_userfont; +-- +2.43.0 + diff --git a/queue-6.7/gpu-host1x-skip-reset-assert-on-tegra186.patch b/queue-6.7/gpu-host1x-skip-reset-assert-on-tegra186.patch new file mode 100644 index 00000000000..19423902226 --- /dev/null +++ b/queue-6.7/gpu-host1x-skip-reset-assert-on-tegra186.patch @@ -0,0 +1,84 @@ +From 5c8245088ad0df3ac2a5537447f93cbbc6c9809f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 03:05:16 +0200 +Subject: gpu: host1x: Skip reset assert on Tegra186 + +From: Mikko Perttunen + +[ Upstream commit 1fa8d07ae1a5fa4e87de42c338e8fc27f46d8bb6 ] + +On Tegra186, secure world applications may need to access host1x +during suspend/resume, and rely on the kernel to keep Host1x out +of reset during the suspend cycle. As such, as a quirk, +skip asserting Host1x's reset on Tegra186. + +We don't need to keep the clocks enabled, as BPMP ensures the clock +stays on while Host1x is being used. On newer SoC's, the reset line +is inaccessible, so there is no need for the quirk. + +Fixes: b7c00cdf6df5 ("gpu: host1x: Enable system suspend callbacks") +Signed-off-by: Mikko Perttunen +Reviewed-by: Jon Hunter +Tested-by: Jon Hunter +Signed-off-by: Thierry Reding +Link: https://patchwork.freedesktop.org/patch/msgid/20240222010517.1573931-1-cyndis@kapsi.fi +Signed-off-by: Sasha Levin +--- + drivers/gpu/host1x/dev.c | 15 +++++++++------ + drivers/gpu/host1x/dev.h | 6 ++++++ + 2 files changed, 15 insertions(+), 6 deletions(-) + +diff --git a/drivers/gpu/host1x/dev.c b/drivers/gpu/host1x/dev.c +index 42fd504abbcda..89983d7d73ca1 100644 +--- a/drivers/gpu/host1x/dev.c ++++ b/drivers/gpu/host1x/dev.c +@@ -169,6 +169,7 @@ static const struct host1x_info host1x06_info = { + .num_sid_entries = ARRAY_SIZE(tegra186_sid_table), + .sid_table = tegra186_sid_table, + .reserve_vblank_syncpts = false, ++ .skip_reset_assert = true, + }; + + static const struct host1x_sid_entry tegra194_sid_table[] = { +@@ -680,13 +681,15 @@ static int __maybe_unused host1x_runtime_suspend(struct device *dev) + host1x_intr_stop(host); + host1x_syncpt_save(host); + +- err = reset_control_bulk_assert(host->nresets, host->resets); +- if (err) { +- dev_err(dev, "failed to assert reset: %d\n", err); +- goto resume_host1x; +- } ++ if (!host->info->skip_reset_assert) { ++ err = reset_control_bulk_assert(host->nresets, host->resets); ++ if (err) { ++ dev_err(dev, "failed to assert reset: %d\n", err); ++ goto resume_host1x; ++ } + +- usleep_range(1000, 2000); ++ usleep_range(1000, 2000); ++ } + + clk_disable_unprepare(host->clk); + reset_control_bulk_release(host->nresets, host->resets); +diff --git a/drivers/gpu/host1x/dev.h b/drivers/gpu/host1x/dev.h +index c8e302de76257..925a118db23f5 100644 +--- a/drivers/gpu/host1x/dev.h ++++ b/drivers/gpu/host1x/dev.h +@@ -116,6 +116,12 @@ struct host1x_info { + * the display driver disables VBLANK increments. + */ + bool reserve_vblank_syncpts; ++ /* ++ * On Tegra186, secure world applications may require access to ++ * host1x during suspend/resume. To allow this, we need to leave ++ * host1x not in reset. ++ */ ++ bool skip_reset_assert; + }; + + struct host1x { +-- +2.43.0 + diff --git a/queue-6.7/ice-fix-connection-state-of-dpll-and-out-pin.patch b/queue-6.7/ice-fix-connection-state-of-dpll-and-out-pin.patch new file mode 100644 index 00000000000..3239faf5055 --- /dev/null +++ b/queue-6.7/ice-fix-connection-state-of-dpll-and-out-pin.patch @@ -0,0 +1,147 @@ +From befdcd7b1038490850b477ac8ec7107c95aafa8e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 25 Jan 2024 15:40:55 +0200 +Subject: ice: fix connection state of DPLL and out pin + +From: Yochai Hagvi + +[ Upstream commit e8335ef57c6816d81b24173ba88cc9b3f043687f ] + +Fix the connection state between source DPLL and output pin, updating the +attribute 'state' of 'parent_device'. Previously, the connection state +was broken, and didn't reflect the correct state. + +When 'state_on_dpll_set' is called with the value +'DPLL_PIN_STATE_CONNECTED' (1), the output pin will switch to the given +DPLL, and the state of the given DPLL will be set to connected. +E.g.: + --do pin-set --json '{"id":2, "parent-device":{"parent-id":1, + "state": 1 }}' +This command will connect DPLL device with id 1 to output pin with id 2. + +When 'state_on_dpll_set' is called with the value +'DPLL_PIN_STATE_DISCONNECTED' (2) and the given DPLL is currently +connected, then the output pin will be disabled. +E.g: + --do pin-set --json '{"id":2, "parent-device":{"parent-id":1, + "state": 2 }}' +This command will disable output pin with id 2 if DPLL device with ID 1 is +connected to it; otherwise, the command is ignored. + +Fixes: d7999f5ea64b ("ice: implement dpll interface to control cgu") +Reviewed-by: Wojciech Drewek +Reviewed-by: Arkadiusz Kubalewski +Signed-off-by: Yochai Hagvi +Tested-by: Sunitha Mekala (A Contingent worker at Intel) +Signed-off-by: Tony Nguyen +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/ice/ice_dpll.c | 43 +++++++++++++++++------ + 1 file changed, 32 insertions(+), 11 deletions(-) + +diff --git a/drivers/net/ethernet/intel/ice/ice_dpll.c b/drivers/net/ethernet/intel/ice/ice_dpll.c +index 86b180cb32a02..0f836adc0e587 100644 +--- a/drivers/net/ethernet/intel/ice/ice_dpll.c ++++ b/drivers/net/ethernet/intel/ice/ice_dpll.c +@@ -254,6 +254,7 @@ ice_dpll_output_frequency_get(const struct dpll_pin *pin, void *pin_priv, + * ice_dpll_pin_enable - enable a pin on dplls + * @hw: board private hw structure + * @pin: pointer to a pin ++ * @dpll_idx: dpll index to connect to output pin + * @pin_type: type of pin being enabled + * @extack: error reporting + * +@@ -266,7 +267,7 @@ ice_dpll_output_frequency_get(const struct dpll_pin *pin, void *pin_priv, + */ + static int + ice_dpll_pin_enable(struct ice_hw *hw, struct ice_dpll_pin *pin, +- enum ice_dpll_pin_type pin_type, ++ u8 dpll_idx, enum ice_dpll_pin_type pin_type, + struct netlink_ext_ack *extack) + { + u8 flags = 0; +@@ -280,10 +281,12 @@ ice_dpll_pin_enable(struct ice_hw *hw, struct ice_dpll_pin *pin, + ret = ice_aq_set_input_pin_cfg(hw, pin->idx, 0, flags, 0, 0); + break; + case ICE_DPLL_PIN_TYPE_OUTPUT: ++ flags = ICE_AQC_SET_CGU_OUT_CFG_UPDATE_SRC_SEL; + if (pin->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN) + flags |= ICE_AQC_SET_CGU_OUT_CFG_ESYNC_EN; + flags |= ICE_AQC_SET_CGU_OUT_CFG_OUT_EN; +- ret = ice_aq_set_output_pin_cfg(hw, pin->idx, flags, 0, 0, 0); ++ ret = ice_aq_set_output_pin_cfg(hw, pin->idx, flags, dpll_idx, ++ 0, 0); + break; + default: + return -EINVAL; +@@ -398,14 +401,27 @@ ice_dpll_pin_state_update(struct ice_pf *pf, struct ice_dpll_pin *pin, + break; + case ICE_DPLL_PIN_TYPE_OUTPUT: + ret = ice_aq_get_output_pin_cfg(&pf->hw, pin->idx, +- &pin->flags[0], NULL, ++ &pin->flags[0], &parent, + &pin->freq, NULL); + if (ret) + goto err; +- if (ICE_AQC_SET_CGU_OUT_CFG_OUT_EN & pin->flags[0]) +- pin->state[0] = DPLL_PIN_STATE_CONNECTED; +- else +- pin->state[0] = DPLL_PIN_STATE_DISCONNECTED; ++ ++ parent &= ICE_AQC_GET_CGU_OUT_CFG_DPLL_SRC_SEL; ++ if (ICE_AQC_SET_CGU_OUT_CFG_OUT_EN & pin->flags[0]) { ++ pin->state[pf->dplls.eec.dpll_idx] = ++ parent == pf->dplls.eec.dpll_idx ? ++ DPLL_PIN_STATE_CONNECTED : ++ DPLL_PIN_STATE_DISCONNECTED; ++ pin->state[pf->dplls.pps.dpll_idx] = ++ parent == pf->dplls.pps.dpll_idx ? ++ DPLL_PIN_STATE_CONNECTED : ++ DPLL_PIN_STATE_DISCONNECTED; ++ } else { ++ pin->state[pf->dplls.eec.dpll_idx] = ++ DPLL_PIN_STATE_DISCONNECTED; ++ pin->state[pf->dplls.pps.dpll_idx] = ++ DPLL_PIN_STATE_DISCONNECTED; ++ } + break; + case ICE_DPLL_PIN_TYPE_RCLK_INPUT: + for (parent = 0; parent < pf->dplls.rclk.num_parents; +@@ -595,7 +611,8 @@ ice_dpll_pin_state_set(const struct dpll_pin *pin, void *pin_priv, + + mutex_lock(&pf->dplls.lock); + if (enable) +- ret = ice_dpll_pin_enable(&pf->hw, p, pin_type, extack); ++ ret = ice_dpll_pin_enable(&pf->hw, p, d->dpll_idx, pin_type, ++ extack); + else + ret = ice_dpll_pin_disable(&pf->hw, p, pin_type, extack); + if (!ret) +@@ -628,6 +645,11 @@ ice_dpll_output_state_set(const struct dpll_pin *pin, void *pin_priv, + struct netlink_ext_ack *extack) + { + bool enable = state == DPLL_PIN_STATE_CONNECTED; ++ struct ice_dpll_pin *p = pin_priv; ++ struct ice_dpll *d = dpll_priv; ++ ++ if (!enable && p->state[d->dpll_idx] == DPLL_PIN_STATE_DISCONNECTED) ++ return 0; + + return ice_dpll_pin_state_set(pin, pin_priv, dpll, dpll_priv, enable, + extack, ICE_DPLL_PIN_TYPE_OUTPUT); +@@ -694,10 +716,9 @@ ice_dpll_pin_state_get(const struct dpll_pin *pin, void *pin_priv, + ret = ice_dpll_pin_state_update(pf, p, pin_type, extack); + if (ret) + goto unlock; +- if (pin_type == ICE_DPLL_PIN_TYPE_INPUT) ++ if (pin_type == ICE_DPLL_PIN_TYPE_INPUT || ++ pin_type == ICE_DPLL_PIN_TYPE_OUTPUT) + *state = p->state[d->dpll_idx]; +- else if (pin_type == ICE_DPLL_PIN_TYPE_OUTPUT) +- *state = p->state[0]; + ret = 0; + unlock: + mutex_unlock(&pf->dplls.lock); +-- +2.43.0 + diff --git a/queue-6.7/ice-fix-dpll-and-dpll_pin-data-access-on-pf-reset.patch b/queue-6.7/ice-fix-dpll-and-dpll_pin-data-access-on-pf-reset.patch new file mode 100644 index 00000000000..50288a75749 --- /dev/null +++ b/queue-6.7/ice-fix-dpll-and-dpll_pin-data-access-on-pf-reset.patch @@ -0,0 +1,140 @@ +From 160b34bf4b12b3c847f80a7ebee8e33526b8476b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 9 Feb 2024 22:24:30 +0100 +Subject: ice: fix dpll and dpll_pin data access on PF reset + +From: Arkadiusz Kubalewski + +[ Upstream commit fc7fd1a10a9d2d38378b42e9a508da4c68018453 ] + +Do not allow to acquire data or alter configuration of dpll and pins +through firmware if PF reset is in progress, this would cause confusing +netlink extack errors as the firmware cannot respond or process the +request properly during the reset time. + +Return (-EBUSY) and extack error for the user who tries access/modify +the config of dpll/pin through firmware during the reset time. + +The PF reset and kernel access to dpll data are both asynchronous. It is +not possible to guard all the possible reset paths with any determinictic +approach. I.e., it is possible that reset starts after reset check is +performed (or if the reset would be checked after mutex is locked), but at +the same time it is not possible to wait for dpll mutex unlock in the +reset flow. +This is best effort solution to at least give a clue to the user +what is happening in most of the cases, knowing that there are possible +race conditions where the user could see a different error received +from firmware due to reset unexpectedly starting. + +Test by looping execution of below steps until netlink error appears: +- perform PF reset +$ echo 1 > /sys/class/net//device/reset +- i.e. try to alter/read dpll/pin config: +$ ./tools/net/ynl/cli.py --spec Documentation/netlink/specs/dpll.yaml \ + --dump pin-get + +Fixes: d7999f5ea64b ("ice: implement dpll interface to control cgu") +Reviewed-by: Aleksandr Loktionov +Reviewed-by: Przemek Kitszel +Signed-off-by: Arkadiusz Kubalewski +Tested-by: Pucha Himasekhar Reddy (A Contingent worker at Intel) +Signed-off-by: Tony Nguyen +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/ice/ice_dpll.c | 38 +++++++++++++++++++++++ + 1 file changed, 38 insertions(+) + +diff --git a/drivers/net/ethernet/intel/ice/ice_dpll.c b/drivers/net/ethernet/intel/ice/ice_dpll.c +index 10a469060d322..9c8be237c7e50 100644 +--- a/drivers/net/ethernet/intel/ice/ice_dpll.c ++++ b/drivers/net/ethernet/intel/ice/ice_dpll.c +@@ -30,6 +30,26 @@ static const char * const pin_type_name[] = { + [ICE_DPLL_PIN_TYPE_RCLK_INPUT] = "rclk-input", + }; + ++/** ++ * ice_dpll_is_reset - check if reset is in progress ++ * @pf: private board structure ++ * @extack: error reporting ++ * ++ * If reset is in progress, fill extack with error. ++ * ++ * Return: ++ * * false - no reset in progress ++ * * true - reset in progress ++ */ ++static bool ice_dpll_is_reset(struct ice_pf *pf, struct netlink_ext_ack *extack) ++{ ++ if (ice_is_reset_in_progress(pf->state)) { ++ NL_SET_ERR_MSG(extack, "PF reset in progress"); ++ return true; ++ } ++ return false; ++} ++ + /** + * ice_dpll_pin_freq_set - set pin's frequency + * @pf: private board structure +@@ -109,6 +129,9 @@ ice_dpll_frequency_set(const struct dpll_pin *pin, void *pin_priv, + struct ice_pf *pf = d->pf; + int ret; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + ret = ice_dpll_pin_freq_set(pf, p, pin_type, frequency, extack); + mutex_unlock(&pf->dplls.lock); +@@ -609,6 +632,9 @@ ice_dpll_pin_state_set(const struct dpll_pin *pin, void *pin_priv, + struct ice_pf *pf = d->pf; + int ret; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + if (enable) + ret = ice_dpll_pin_enable(&pf->hw, p, d->dpll_idx, pin_type, +@@ -712,6 +738,9 @@ ice_dpll_pin_state_get(const struct dpll_pin *pin, void *pin_priv, + struct ice_pf *pf = d->pf; + int ret; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + ret = ice_dpll_pin_state_update(pf, p, pin_type, extack); + if (ret) +@@ -836,6 +865,9 @@ ice_dpll_input_prio_set(const struct dpll_pin *pin, void *pin_priv, + struct ice_pf *pf = d->pf; + int ret; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + ret = ice_dpll_hw_input_prio_set(pf, d, p, prio, extack); + mutex_unlock(&pf->dplls.lock); +@@ -1115,6 +1147,9 @@ ice_dpll_rclk_state_on_pin_set(const struct dpll_pin *pin, void *pin_priv, + int ret = -EINVAL; + u32 hw_idx; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + hw_idx = parent->idx - pf->dplls.base_rclk_idx; + if (hw_idx >= pf->dplls.num_inputs) +@@ -1169,6 +1204,9 @@ ice_dpll_rclk_state_on_pin_get(const struct dpll_pin *pin, void *pin_priv, + int ret = -EINVAL; + u32 hw_idx; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + hw_idx = parent->idx - pf->dplls.base_rclk_idx; + if (hw_idx >= pf->dplls.num_inputs) +-- +2.43.0 + diff --git a/queue-6.7/ice-fix-dpll-input-pin-phase_adjust-value-updates.patch b/queue-6.7/ice-fix-dpll-input-pin-phase_adjust-value-updates.patch new file mode 100644 index 00000000000..d85894999d1 --- /dev/null +++ b/queue-6.7/ice-fix-dpll-input-pin-phase_adjust-value-updates.patch @@ -0,0 +1,45 @@ +From 91f1db083c45cb941925ed4a5fe3c6c82c4e9f62 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 8 Feb 2024 23:56:31 +0100 +Subject: ice: fix dpll input pin phase_adjust value updates + +From: Arkadiusz Kubalewski + +[ Upstream commit 3b14430c65b4f510b2a310ca4f18ed6ca7184b00 ] + +The value of phase_adjust for input pin shall be updated in +ice_dpll_pin_state_update(..). Fix by adding proper argument to the +firmware query function call - a pin's struct field pointer where the +phase_adjust value during driver runtime is stored. + +Previously the phase_adjust used to misinform user about actual +phase_adjust value. I.e., if phase_adjust was set to a non zero value and +if driver was reloaded, the user would see the value equal 0, which is +not correct - the actual value is equal to value set before driver reload. + +Fixes: 90e1c90750d7 ("ice: dpll: implement phase related callbacks") +Reviewed-by: Alan Brady +Signed-off-by: Arkadiusz Kubalewski +Tested-by: Pucha Himasekhar Reddy (A Contingent worker at Intel) +Signed-off-by: Tony Nguyen +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/ice/ice_dpll.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/net/ethernet/intel/ice/ice_dpll.c b/drivers/net/ethernet/intel/ice/ice_dpll.c +index 0f836adc0e587..10a469060d322 100644 +--- a/drivers/net/ethernet/intel/ice/ice_dpll.c ++++ b/drivers/net/ethernet/intel/ice/ice_dpll.c +@@ -373,7 +373,7 @@ ice_dpll_pin_state_update(struct ice_pf *pf, struct ice_dpll_pin *pin, + case ICE_DPLL_PIN_TYPE_INPUT: + ret = ice_aq_get_input_pin_cfg(&pf->hw, pin->idx, NULL, NULL, + NULL, &pin->flags[0], +- &pin->freq, NULL); ++ &pin->freq, &pin->phase_adjust); + if (ret) + goto err; + if (ICE_AQC_GET_CGU_IN_CFG_FLG2_INPUT_EN & pin->flags[0]) { +-- +2.43.0 + diff --git a/queue-6.7/ice-fix-dpll-periodic-work-data-updates-on-pf-reset.patch b/queue-6.7/ice-fix-dpll-periodic-work-data-updates-on-pf-reset.patch new file mode 100644 index 00000000000..1dbb9cf48a0 --- /dev/null +++ b/queue-6.7/ice-fix-dpll-periodic-work-data-updates-on-pf-reset.patch @@ -0,0 +1,55 @@ +From 0bb0fce0377540fdaa274ee5275616baa8ba08a3 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 9 Feb 2024 22:24:31 +0100 +Subject: ice: fix dpll periodic work data updates on PF reset + +From: Arkadiusz Kubalewski + +[ Upstream commit 9a8385fe14bcb250a3889e744dc54e9c411d8400 ] + +Do not allow dpll periodic work function to acquire data from firmware +if PF reset is in progress. Acquiring data will cause dmesg errors as the +firmware cannot respond or process the request properly during the reset +time. + +Test by looping execution of below step until dmesg error appears: +- perform PF reset +$ echo 1 > /sys/class/net//device/reset + +Fixes: d7999f5ea64b ("ice: implement dpll interface to control cgu") +Reviewed-by: Igor Bagnucki +Signed-off-by: Arkadiusz Kubalewski +Tested-by: Pucha Himasekhar Reddy (A Contingent worker at Intel) +Signed-off-by: Tony Nguyen +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/ice/ice_dpll.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/drivers/net/ethernet/intel/ice/ice_dpll.c b/drivers/net/ethernet/intel/ice/ice_dpll.c +index 9c8be237c7e50..bcb9b9c13aabc 100644 +--- a/drivers/net/ethernet/intel/ice/ice_dpll.c ++++ b/drivers/net/ethernet/intel/ice/ice_dpll.c +@@ -1390,8 +1390,10 @@ static void ice_dpll_periodic_work(struct kthread_work *work) + struct ice_pf *pf = container_of(d, struct ice_pf, dplls); + struct ice_dpll *de = &pf->dplls.eec; + struct ice_dpll *dp = &pf->dplls.pps; +- int ret; ++ int ret = 0; + ++ if (ice_is_reset_in_progress(pf->state)) ++ goto resched; + mutex_lock(&pf->dplls.lock); + ret = ice_dpll_update_state(pf, de, false); + if (!ret) +@@ -1411,6 +1413,7 @@ static void ice_dpll_periodic_work(struct kthread_work *work) + ice_dpll_notify_changes(de); + ice_dpll_notify_changes(dp); + ++resched: + /* Run twice a second or reschedule if update failed */ + kthread_queue_delayed_work(d->kworker, &d->work, + ret ? msecs_to_jiffies(10) : +-- +2.43.0 + diff --git a/queue-6.7/ice-fix-pin-phase-adjust-updates-on-pf-reset.patch b/queue-6.7/ice-fix-pin-phase-adjust-updates-on-pf-reset.patch new file mode 100644 index 00000000000..3c1e8bbeed1 --- /dev/null +++ b/queue-6.7/ice-fix-pin-phase-adjust-updates-on-pf-reset.patch @@ -0,0 +1,50 @@ +From a0739457a8e786c7e828ffc785a96e61bd240cfc Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 9 Feb 2024 22:24:32 +0100 +Subject: ice: fix pin phase adjust updates on PF reset + +From: Arkadiusz Kubalewski + +[ Upstream commit ee89921da471edcb4b1e67f5bbfedddf39749782 ] + +Do not allow to set phase adjust value for a pin if PF reset is in +progress, this would cause confusing netlink extack errors as the firmware +cannot process the request properly during the reset time. + +Return (-EBUSY) and report extack error for the user who tries configure +pin phase adjust during the reset time. + +Test by looping execution of below steps until netlink error appears: +- perform PF reset +$ echo 1 > /sys/class/net//device/reset +- change pin phase adjust value: +$ ./tools/net/ynl/cli.py --spec Documentation/netlink/specs/dpll.yaml \ + --do pin-set --json '{"id":0, "phase-adjust":1000}' + +Fixes: 90e1c90750d7 ("ice: dpll: implement phase related callbacks") +Reviewed-by: Igor Bagnucki +Signed-off-by: Arkadiusz Kubalewski +Tested-by: Pucha Himasekhar Reddy (A Contingent worker at Intel) +Signed-off-by: Tony Nguyen +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/ice/ice_dpll.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/drivers/net/ethernet/intel/ice/ice_dpll.c b/drivers/net/ethernet/intel/ice/ice_dpll.c +index bcb9b9c13aabc..2b657d43c769d 100644 +--- a/drivers/net/ethernet/intel/ice/ice_dpll.c ++++ b/drivers/net/ethernet/intel/ice/ice_dpll.c +@@ -988,6 +988,9 @@ ice_dpll_pin_phase_adjust_set(const struct dpll_pin *pin, void *pin_priv, + u8 flag, flags_en = 0; + int ret; + ++ if (ice_dpll_is_reset(pf, extack)) ++ return -EBUSY; ++ + mutex_lock(&pf->dplls.lock); + switch (type) { + case ICE_DPLL_PIN_TYPE_INPUT: +-- +2.43.0 + diff --git a/queue-6.7/igb-extend-ptp-timestamp-adjustments-to-i211.patch b/queue-6.7/igb-extend-ptp-timestamp-adjustments-to-i211.patch new file mode 100644 index 00000000000..9665a3e1e34 --- /dev/null +++ b/queue-6.7/igb-extend-ptp-timestamp-adjustments-to-i211.patch @@ -0,0 +1,62 @@ +From 9be10aaf1ae1109ec4f230c6ee3644ea8fba086a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 10:49:41 -0800 +Subject: igb: extend PTP timestamp adjustments to i211 + +From: Oleksij Rempel + +[ Upstream commit 0bb7b09392eb74b152719ae87b1ba5e4bf910ef0 ] + +The i211 requires the same PTP timestamp adjustments as the i210, +according to its datasheet. To ensure consistent timestamping across +different platforms, this change extends the existing adjustments to +include the i211. + +The adjustment result are tested and comparable for i210 and i211 based +systems. + +Fixes: 3f544d2a4d5c ("igb: adjust PTP timestamps for Tx/Rx latency") +Signed-off-by: Oleksij Rempel +Reviewed-by: Jacob Keller +Tested-by: Pucha Himasekhar Reddy (A Contingent worker at Intel) +Signed-off-by: Tony Nguyen +Link: https://lore.kernel.org/r/20240227184942.362710-1-anthony.l.nguyen@intel.com +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/intel/igb/igb_ptp.c | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/drivers/net/ethernet/intel/igb/igb_ptp.c b/drivers/net/ethernet/intel/igb/igb_ptp.c +index 319c544b9f04c..f945705561200 100644 +--- a/drivers/net/ethernet/intel/igb/igb_ptp.c ++++ b/drivers/net/ethernet/intel/igb/igb_ptp.c +@@ -957,7 +957,7 @@ static void igb_ptp_tx_hwtstamp(struct igb_adapter *adapter) + + igb_ptp_systim_to_hwtstamp(adapter, &shhwtstamps, regval); + /* adjust timestamp for the TX latency based on link speed */ +- if (adapter->hw.mac.type == e1000_i210) { ++ if (hw->mac.type == e1000_i210 || hw->mac.type == e1000_i211) { + switch (adapter->link_speed) { + case SPEED_10: + adjust = IGB_I210_TX_LATENCY_10; +@@ -1003,6 +1003,7 @@ int igb_ptp_rx_pktstamp(struct igb_q_vector *q_vector, void *va, + ktime_t *timestamp) + { + struct igb_adapter *adapter = q_vector->adapter; ++ struct e1000_hw *hw = &adapter->hw; + struct skb_shared_hwtstamps ts; + __le64 *regval = (__le64 *)va; + int adjust = 0; +@@ -1022,7 +1023,7 @@ int igb_ptp_rx_pktstamp(struct igb_q_vector *q_vector, void *va, + igb_ptp_systim_to_hwtstamp(adapter, &ts, le64_to_cpu(regval[1])); + + /* adjust timestamp for the RX latency based on link speed */ +- if (adapter->hw.mac.type == e1000_i210) { ++ if (hw->mac.type == e1000_i210 || hw->mac.type == e1000_i211) { + switch (adapter->link_speed) { + case SPEED_10: + adjust = IGB_I210_RX_LATENCY_10; +-- +2.43.0 + diff --git a/queue-6.7/ipv6-fix-potential-struct-net-leak-in-inet6_rtm_geta.patch b/queue-6.7/ipv6-fix-potential-struct-net-leak-in-inet6_rtm_geta.patch new file mode 100644 index 00000000000..1cc42fdd4a2 --- /dev/null +++ b/queue-6.7/ipv6-fix-potential-struct-net-leak-in-inet6_rtm_geta.patch @@ -0,0 +1,45 @@ +From f90703eef697ccb6048feef85527bfb010b7ebb5 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 12:17:47 +0000 +Subject: ipv6: fix potential "struct net" leak in inet6_rtm_getaddr() + +From: Eric Dumazet + +[ Upstream commit 10bfd453da64a057bcfd1a49fb6b271c48653cdb ] + +It seems that if userspace provides a correct IFA_TARGET_NETNSID value +but no IFA_ADDRESS and IFA_LOCAL attributes, inet6_rtm_getaddr() +returns -EINVAL with an elevated "struct net" refcount. + +Fixes: 6ecf4c37eb3e ("ipv6: enable IFA_TARGET_NETNSID for RTM_GETADDR") +Signed-off-by: Eric Dumazet +Cc: Christian Brauner +Cc: David Ahern +Reviewed-by: David Ahern +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + net/ipv6/addrconf.c | 7 ++++--- + 1 file changed, 4 insertions(+), 3 deletions(-) + +diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c +index 5a839c5fb1a5a..055230b669cf2 100644 +--- a/net/ipv6/addrconf.c ++++ b/net/ipv6/addrconf.c +@@ -5509,9 +5509,10 @@ static int inet6_rtm_getaddr(struct sk_buff *in_skb, struct nlmsghdr *nlh, + } + + addr = extract_addr(tb[IFA_ADDRESS], tb[IFA_LOCAL], &peer); +- if (!addr) +- return -EINVAL; +- ++ if (!addr) { ++ err = -EINVAL; ++ goto errout; ++ } + ifm = nlmsg_data(nlh); + if (ifm->ifa_index) + dev = dev_get_by_index(tgt_net, ifm->ifa_index); +-- +2.43.0 + diff --git a/queue-6.7/lan78xx-enable-auto-speed-configuration-for-lan7850-.patch b/queue-6.7/lan78xx-enable-auto-speed-configuration-for-lan7850-.patch new file mode 100644 index 00000000000..30514d28967 --- /dev/null +++ b/queue-6.7/lan78xx-enable-auto-speed-configuration-for-lan7850-.patch @@ -0,0 +1,45 @@ +From e62c3afd4d996756cbe8b18020d37804020dbb0f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 13:38:38 +0100 +Subject: lan78xx: enable auto speed configuration for LAN7850 if no EEPROM is + detected + +From: Oleksij Rempel + +[ Upstream commit 0e67899abfbfdea0c3c0ed3fd263ffc601c5c157 ] + +Same as LAN7800, LAN7850 can be used without EEPROM. If EEPROM is not +present or not flashed, LAN7850 will fail to sync the speed detected by the PHY +with the MAC. In case link speed is 100Mbit, it will accidentally work, +otherwise no data can be transferred. + +Better way would be to implement link_up callback, or set auto speed +configuration unconditionally. But this changes would be more intrusive. +So, for now, set it only if no EEPROM is found. + +Fixes: e69647a19c87 ("lan78xx: Set ASD in MAC_CR when EEE is enabled.") +Signed-off-by: Oleksij Rempel +Link: https://lore.kernel.org/r/20240222123839.2816561-1-o.rempel@pengutronix.de +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + drivers/net/usb/lan78xx.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +diff --git a/drivers/net/usb/lan78xx.c b/drivers/net/usb/lan78xx.c +index 5add4145d9fc1..2e6d423f3a016 100644 +--- a/drivers/net/usb/lan78xx.c ++++ b/drivers/net/usb/lan78xx.c +@@ -3035,7 +3035,8 @@ static int lan78xx_reset(struct lan78xx_net *dev) + if (dev->chipid == ID_REV_CHIP_ID_7801_) + buf &= ~MAC_CR_GMII_EN_; + +- if (dev->chipid == ID_REV_CHIP_ID_7800_) { ++ if (dev->chipid == ID_REV_CHIP_ID_7800_ || ++ dev->chipid == ID_REV_CHIP_ID_7850_) { + ret = lan78xx_read_raw_eeprom(dev, 0, 1, &sig); + if (!ret && sig != EEPROM_INDICATOR) { + /* Implies there is no external eeprom. Set mac speed */ +-- +2.43.0 + diff --git a/queue-6.7/mtd-spinand-gigadevice-fix-the-get-ecc-status-issue.patch b/queue-6.7/mtd-spinand-gigadevice-fix-the-get-ecc-status-issue.patch new file mode 100644 index 00000000000..0adf1072a51 --- /dev/null +++ b/queue-6.7/mtd-spinand-gigadevice-fix-the-get-ecc-status-issue.patch @@ -0,0 +1,63 @@ +From cb7ce9ff64112709b11201100ab111e34b08b40c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 8 Nov 2023 09:07:01 -0600 +Subject: mtd: spinand: gigadevice: Fix the get ecc status issue + +From: Han Xu + +[ Upstream commit 59950610c0c00c7a06d8a75d2ee5d73dba4274cf ] + +Some GigaDevice ecc_get_status functions use on-stack buffer for +spi_mem_op causes spi_mem_check_op failing, fix the issue by using +spinand scratchbuf. + +Fixes: c40c7a990a46 ("mtd: spinand: Add support for GigaDevice GD5F1GQ4UExxG") +Signed-off-by: Han Xu +Signed-off-by: Miquel Raynal +Link: https://lore.kernel.org/linux-mtd/20231108150701.593912-1-han.xu@nxp.com +Signed-off-by: Sasha Levin +--- + drivers/mtd/nand/spi/gigadevice.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +diff --git a/drivers/mtd/nand/spi/gigadevice.c b/drivers/mtd/nand/spi/gigadevice.c +index 987710e09441a..6023cba748bb8 100644 +--- a/drivers/mtd/nand/spi/gigadevice.c ++++ b/drivers/mtd/nand/spi/gigadevice.c +@@ -186,7 +186,7 @@ static int gd5fxgq4uexxg_ecc_get_status(struct spinand_device *spinand, + { + u8 status2; + struct spi_mem_op op = SPINAND_GET_FEATURE_OP(GD5FXGQXXEXXG_REG_STATUS2, +- &status2); ++ spinand->scratchbuf); + int ret; + + switch (status & STATUS_ECC_MASK) { +@@ -207,6 +207,7 @@ static int gd5fxgq4uexxg_ecc_get_status(struct spinand_device *spinand, + * report the maximum of 4 in this case + */ + /* bits sorted this way (3...0): ECCS1,ECCS0,ECCSE1,ECCSE0 */ ++ status2 = *(spinand->scratchbuf); + return ((status & STATUS_ECC_MASK) >> 2) | + ((status2 & STATUS_ECC_MASK) >> 4); + +@@ -228,7 +229,7 @@ static int gd5fxgq5xexxg_ecc_get_status(struct spinand_device *spinand, + { + u8 status2; + struct spi_mem_op op = SPINAND_GET_FEATURE_OP(GD5FXGQXXEXXG_REG_STATUS2, +- &status2); ++ spinand->scratchbuf); + int ret; + + switch (status & STATUS_ECC_MASK) { +@@ -248,6 +249,7 @@ static int gd5fxgq5xexxg_ecc_get_status(struct spinand_device *spinand, + * 1 ... 4 bits are flipped (and corrected) + */ + /* bits sorted this way (1...0): ECCSE1, ECCSE0 */ ++ status2 = *(spinand->scratchbuf); + return ((status2 & STATUS_ECC_MASK) >> 4) + 1; + + case STATUS_ECC_UNCOR_ERROR: +-- +2.43.0 + diff --git a/queue-6.7/net-dpaa-fman_memac-accept-phy-interface-type-10gbas.patch b/queue-6.7/net-dpaa-fman_memac-accept-phy-interface-type-10gbas.patch new file mode 100644 index 00000000000..d1ff178fee5 --- /dev/null +++ b/queue-6.7/net-dpaa-fman_memac-accept-phy-interface-type-10gbas.patch @@ -0,0 +1,131 @@ +From 995a89a9b6509e2bb83ccea6e303c03130516f20 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 00:34:42 +0200 +Subject: net: dpaa: fman_memac: accept phy-interface-type = "10gbase-r" in the + device tree + +From: Vladimir Oltean + +[ Upstream commit 734f06db599f66d6a159c78abfdbadfea3b7d43b ] + +Since commit 5d93cfcf7360 ("net: dpaa: Convert to phylink"), we support +the "10gbase-r" phy-mode through a driver-based conversion of "xgmii", +but we still don't actually support it when the device tree specifies +"10gbase-r" proper. + +This is because boards such as LS1046A-RDB do not define pcs-handle-names +(for whatever reason) in the ethernet@f0000 device tree node, and the +code enters through this code path: + + err = of_property_match_string(mac_node, "pcs-handle-names", "xfi"); + // code takes neither branch and falls through + if (err >= 0) { + (...) + } else if (err != -EINVAL && err != -ENODATA) { + goto _return_fm_mac_free; + } + + (...) + + /* For compatibility, if pcs-handle-names is missing, we assume this + * phy is the first one in pcsphy-handle + */ + err = of_property_match_string(mac_node, "pcs-handle-names", "sgmii"); + if (err == -EINVAL || err == -ENODATA) + pcs = memac_pcs_create(mac_node, 0); // code takes this branch + else if (err < 0) + goto _return_fm_mac_free; + else + pcs = memac_pcs_create(mac_node, err); + + // A default PCS is created and saved in "pcs" + + // This determination fails and mistakenly saves the default PCS + // memac->sgmii_pcs instead of memac->xfi_pcs, because at this + // stage, mac_dev->phy_if == PHY_INTERFACE_MODE_10GBASER. + if (err && mac_dev->phy_if == PHY_INTERFACE_MODE_XGMII) + memac->xfi_pcs = pcs; + else + memac->sgmii_pcs = pcs; + +In other words, in the absence of pcs-handle-names, the default +xfi_pcs assignment logic only works when in the device tree we have +PHY_INTERFACE_MODE_XGMII. + +By reversing the order between the fallback xfi_pcs assignment and the +"xgmii" overwrite with "10gbase-r", we are able to support both values +in the device tree, with identical behavior. + +Currently, it is impossible to make the s/xgmii/10gbase-r/ device tree +conversion, because it would break forward compatibility (new device +tree with old kernel). The only way to modify existing device trees to +phy-interface-mode = "10gbase-r" is to fix stable kernels to accept this +value and handle it properly. + +One reason why the conversion is desirable is because with pre-phylink +kernels, the Aquantia PHY driver used to warn about the improper use +of PHY_INTERFACE_MODE_XGMII [1]. It is best to have a single (latest) +device tree that works with all supported stable kernel versions. + +Note that the blamed commit does not constitute a regression per se. +Older stable kernels like 6.1 still do not work with "10gbase-r", but +for a different reason. That is a battle for another time. + +[1] https://lore.kernel.org/netdev/20240214-ls1046-dts-use-10gbase-r-v1-1-8c2d68547393@concurrent-rt.com/ + +Fixes: 5d93cfcf7360 ("net: dpaa: Convert to phylink") +Signed-off-by: Vladimir Oltean +Reviewed-by: Sean Anderson +Acked-by: Madalin Bucur +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + .../net/ethernet/freescale/fman/fman_memac.c | 18 +++++++++--------- + 1 file changed, 9 insertions(+), 9 deletions(-) + +diff --git a/drivers/net/ethernet/freescale/fman/fman_memac.c b/drivers/net/ethernet/freescale/fman/fman_memac.c +index 9ba15d3183d75..758535adc9ff5 100644 +--- a/drivers/net/ethernet/freescale/fman/fman_memac.c ++++ b/drivers/net/ethernet/freescale/fman/fman_memac.c +@@ -1073,6 +1073,14 @@ int memac_initialization(struct mac_device *mac_dev, + unsigned long capabilities; + unsigned long *supported; + ++ /* The internal connection to the serdes is XGMII, but this isn't ++ * really correct for the phy mode (which is the external connection). ++ * However, this is how all older device trees say that they want ++ * 10GBASE-R (aka XFI), so just convert it for them. ++ */ ++ if (mac_dev->phy_if == PHY_INTERFACE_MODE_XGMII) ++ mac_dev->phy_if = PHY_INTERFACE_MODE_10GBASER; ++ + mac_dev->phylink_ops = &memac_mac_ops; + mac_dev->set_promisc = memac_set_promiscuous; + mac_dev->change_addr = memac_modify_mac_address; +@@ -1139,7 +1147,7 @@ int memac_initialization(struct mac_device *mac_dev, + * (and therefore that xfi_pcs cannot be set). If we are defaulting to + * XGMII, assume this is for XFI. Otherwise, assume it is for SGMII. + */ +- if (err && mac_dev->phy_if == PHY_INTERFACE_MODE_XGMII) ++ if (err && mac_dev->phy_if == PHY_INTERFACE_MODE_10GBASER) + memac->xfi_pcs = pcs; + else + memac->sgmii_pcs = pcs; +@@ -1153,14 +1161,6 @@ int memac_initialization(struct mac_device *mac_dev, + goto _return_fm_mac_free; + } + +- /* The internal connection to the serdes is XGMII, but this isn't +- * really correct for the phy mode (which is the external connection). +- * However, this is how all older device trees say that they want +- * 10GBASE-R (aka XFI), so just convert it for them. +- */ +- if (mac_dev->phy_if == PHY_INTERFACE_MODE_XGMII) +- mac_dev->phy_if = PHY_INTERFACE_MODE_10GBASER; +- + /* TODO: The following interface modes are supported by (some) hardware + * but not by this driver: + * - 1000BASE-KX +-- +2.43.0 + diff --git a/queue-6.7/net-hsr-use-correct-offset-for-hsr-tlv-values-in-sup.patch b/queue-6.7/net-hsr-use-correct-offset-for-hsr-tlv-values-in-sup.patch new file mode 100644 index 00000000000..2f61a80307c --- /dev/null +++ b/queue-6.7/net-hsr-use-correct-offset-for-hsr-tlv-values-in-sup.patch @@ -0,0 +1,54 @@ +From 3ac0aa74f7963638ddc5b835b0209fb0ede6670b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Feb 2024 09:56:44 +0100 +Subject: net: hsr: Use correct offset for HSR TLV values in supervisory HSR + frames + +From: Lukasz Majewski + +[ Upstream commit 51dd4ee0372228ffb0f7709fa7aa0678d4199d06 ] + +Current HSR implementation uses following supervisory frame (even for +HSRv1 the HSR tag is not is not present): + +00000000: 01 15 4e 00 01 2d XX YY ZZ 94 77 10 88 fb 00 01 +00000010: 7e 1c 17 06 XX YY ZZ 94 77 10 1e 06 XX YY ZZ 94 +00000020: 77 10 00 00 00 00 00 00 00 00 00 00 00 00 00 00 +00000030: 00 00 00 00 00 00 00 00 00 00 00 00 + +The current code adds extra two bytes (i.e. sizeof(struct hsr_sup_tlv)) +when offset for skb_pull() is calculated. +This is wrong, as both 'struct hsrv1_ethhdr_sp' and 'hsrv0_ethhdr_sp' +already have 'struct hsr_sup_tag' defined in them, so there is no need +for adding extra two bytes. + +This code was working correctly as with no RedBox support, the check for +HSR_TLV_EOT (0x00) was off by two bytes, which were corresponding to +zeroed padded bytes for minimal packet size. + +Fixes: eafaa88b3eb7 ("net: hsr: Add support for redbox supervision frames") +Signed-off-by: Lukasz Majewski +Reviewed-by: Jiri Pirko +Link: https://lore.kernel.org/r/20240228085644.3618044-1-lukma@denx.de +Signed-off-by: Paolo Abeni +Signed-off-by: Sasha Levin +--- + net/hsr/hsr_forward.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/net/hsr/hsr_forward.c b/net/hsr/hsr_forward.c +index 80cdc6f6b34c9..0323ab5023c69 100644 +--- a/net/hsr/hsr_forward.c ++++ b/net/hsr/hsr_forward.c +@@ -83,7 +83,7 @@ static bool is_supervision_frame(struct hsr_priv *hsr, struct sk_buff *skb) + return false; + + /* Get next tlv */ +- total_length += sizeof(struct hsr_sup_tlv) + hsr_sup_tag->tlv.HSR_TLV_length; ++ total_length += hsr_sup_tag->tlv.HSR_TLV_length; + if (!pskb_may_pull(skb, total_length)) + return false; + skb_pull(skb, total_length); +-- +2.43.0 + diff --git a/queue-6.7/net-ip_tunnel-prevent-perpetual-headroom-growth.patch b/queue-6.7/net-ip_tunnel-prevent-perpetual-headroom-growth.patch new file mode 100644 index 00000000000..dfbc5985b84 --- /dev/null +++ b/queue-6.7/net-ip_tunnel-prevent-perpetual-headroom-growth.patch @@ -0,0 +1,181 @@ +From 9abae2f181bf9fbcd17ae6ae3b8d19af8d541d2a Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 20 Feb 2024 14:56:02 +0100 +Subject: net: ip_tunnel: prevent perpetual headroom growth + +From: Florian Westphal + +[ Upstream commit 5ae1e9922bbdbaeb9cfbe91085ab75927488ac0f ] + +syzkaller triggered following kasan splat: +BUG: KASAN: use-after-free in __skb_flow_dissect+0x19d1/0x7a50 net/core/flow_dissector.c:1170 +Read of size 1 at addr ffff88812fb4000e by task syz-executor183/5191 +[..] + kasan_report+0xda/0x110 mm/kasan/report.c:588 + __skb_flow_dissect+0x19d1/0x7a50 net/core/flow_dissector.c:1170 + skb_flow_dissect_flow_keys include/linux/skbuff.h:1514 [inline] + ___skb_get_hash net/core/flow_dissector.c:1791 [inline] + __skb_get_hash+0xc7/0x540 net/core/flow_dissector.c:1856 + skb_get_hash include/linux/skbuff.h:1556 [inline] + ip_tunnel_xmit+0x1855/0x33c0 net/ipv4/ip_tunnel.c:748 + ipip_tunnel_xmit+0x3cc/0x4e0 net/ipv4/ipip.c:308 + __netdev_start_xmit include/linux/netdevice.h:4940 [inline] + netdev_start_xmit include/linux/netdevice.h:4954 [inline] + xmit_one net/core/dev.c:3548 [inline] + dev_hard_start_xmit+0x13d/0x6d0 net/core/dev.c:3564 + __dev_queue_xmit+0x7c1/0x3d60 net/core/dev.c:4349 + dev_queue_xmit include/linux/netdevice.h:3134 [inline] + neigh_connected_output+0x42c/0x5d0 net/core/neighbour.c:1592 + ... + ip_finish_output2+0x833/0x2550 net/ipv4/ip_output.c:235 + ip_finish_output+0x31/0x310 net/ipv4/ip_output.c:323 + .. + iptunnel_xmit+0x5b4/0x9b0 net/ipv4/ip_tunnel_core.c:82 + ip_tunnel_xmit+0x1dbc/0x33c0 net/ipv4/ip_tunnel.c:831 + ipgre_xmit+0x4a1/0x980 net/ipv4/ip_gre.c:665 + __netdev_start_xmit include/linux/netdevice.h:4940 [inline] + netdev_start_xmit include/linux/netdevice.h:4954 [inline] + xmit_one net/core/dev.c:3548 [inline] + dev_hard_start_xmit+0x13d/0x6d0 net/core/dev.c:3564 + ... + +The splat occurs because skb->data points past skb->head allocated area. +This is because neigh layer does: + __skb_pull(skb, skb_network_offset(skb)); + +... but skb_network_offset() returns a negative offset and __skb_pull() +arg is unsigned. IOW, we skb->data gets "adjusted" by a huge value. + +The negative value is returned because skb->head and skb->data distance is +more than 64k and skb->network_header (u16) has wrapped around. + +The bug is in the ip_tunnel infrastructure, which can cause +dev->needed_headroom to increment ad infinitum. + +The syzkaller reproducer consists of packets getting routed via a gre +tunnel, and route of gre encapsulated packets pointing at another (ipip) +tunnel. The ipip encapsulation finds gre0 as next output device. + +This results in the following pattern: + +1). First packet is to be sent out via gre0. +Route lookup found an output device, ipip0. + +2). +ip_tunnel_xmit for gre0 bumps gre0->needed_headroom based on the future +output device, rt.dev->needed_headroom (ipip0). + +3). +ip output / start_xmit moves skb on to ipip0. which runs the same +code path again (xmit recursion). + +4). +Routing step for the post-gre0-encap packet finds gre0 as output device +to use for ipip0 encapsulated packet. + +tunl0->needed_headroom is then incremented based on the (already bumped) +gre0 device headroom. + +This repeats for every future packet: + +gre0->needed_headroom gets inflated because previous packets' ipip0 step +incremented rt->dev (gre0) headroom, and ipip0 incremented because gre0 +needed_headroom was increased. + +For each subsequent packet, gre/ipip0->needed_headroom grows until +post-expand-head reallocations result in a skb->head/data distance of +more than 64k. + +Once that happens, skb->network_header (u16) wraps around when +pskb_expand_head tries to make sure that skb_network_offset() is unchanged +after the headroom expansion/reallocation. + +After this skb_network_offset(skb) returns a different (and negative) +result post headroom expansion. + +The next trip to neigh layer (or anything else that would __skb_pull the +network header) makes skb->data point to a memory location outside +skb->head area. + +v2: Cap the needed_headroom update to an arbitarily chosen upperlimit to +prevent perpetual increase instead of dropping the headroom increment +completely. + +Reported-and-tested-by: syzbot+bfde3bef047a81b8fde6@syzkaller.appspotmail.com +Closes: https://groups.google.com/g/syzkaller-bugs/c/fL9G6GtWskY/m/VKk_PR5FBAAJ +Fixes: 243aad830e8a ("ip_gre: include route header_len in max_headroom calculation") +Signed-off-by: Florian Westphal +Reviewed-by: Simon Horman +Link: https://lore.kernel.org/r/20240220135606.4939-1-fw@strlen.de +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/ipv4/ip_tunnel.c | 28 +++++++++++++++++++++------- + 1 file changed, 21 insertions(+), 7 deletions(-) + +diff --git a/net/ipv4/ip_tunnel.c b/net/ipv4/ip_tunnel.c +index beeae624c412d..2d29fce7c5606 100644 +--- a/net/ipv4/ip_tunnel.c ++++ b/net/ipv4/ip_tunnel.c +@@ -554,6 +554,20 @@ static int tnl_update_pmtu(struct net_device *dev, struct sk_buff *skb, + return 0; + } + ++static void ip_tunnel_adj_headroom(struct net_device *dev, unsigned int headroom) ++{ ++ /* we must cap headroom to some upperlimit, else pskb_expand_head ++ * will overflow header offsets in skb_headers_offset_update(). ++ */ ++ static const unsigned int max_allowed = 512; ++ ++ if (headroom > max_allowed) ++ headroom = max_allowed; ++ ++ if (headroom > READ_ONCE(dev->needed_headroom)) ++ WRITE_ONCE(dev->needed_headroom, headroom); ++} ++ + void ip_md_tunnel_xmit(struct sk_buff *skb, struct net_device *dev, + u8 proto, int tunnel_hlen) + { +@@ -632,13 +646,13 @@ void ip_md_tunnel_xmit(struct sk_buff *skb, struct net_device *dev, + } + + headroom += LL_RESERVED_SPACE(rt->dst.dev) + rt->dst.header_len; +- if (headroom > READ_ONCE(dev->needed_headroom)) +- WRITE_ONCE(dev->needed_headroom, headroom); +- +- if (skb_cow_head(skb, READ_ONCE(dev->needed_headroom))) { ++ if (skb_cow_head(skb, headroom)) { + ip_rt_put(rt); + goto tx_dropped; + } ++ ++ ip_tunnel_adj_headroom(dev, headroom); ++ + iptunnel_xmit(NULL, rt, skb, fl4.saddr, fl4.daddr, proto, tos, ttl, + df, !net_eq(tunnel->net, dev_net(dev))); + return; +@@ -818,16 +832,16 @@ void ip_tunnel_xmit(struct sk_buff *skb, struct net_device *dev, + + max_headroom = LL_RESERVED_SPACE(rt->dst.dev) + sizeof(struct iphdr) + + rt->dst.header_len + ip_encap_hlen(&tunnel->encap); +- if (max_headroom > READ_ONCE(dev->needed_headroom)) +- WRITE_ONCE(dev->needed_headroom, max_headroom); + +- if (skb_cow_head(skb, READ_ONCE(dev->needed_headroom))) { ++ if (skb_cow_head(skb, max_headroom)) { + ip_rt_put(rt); + DEV_STATS_INC(dev, tx_dropped); + kfree_skb(skb); + return; + } + ++ ip_tunnel_adj_headroom(dev, max_headroom); ++ + iptunnel_xmit(NULL, rt, skb, fl4.saddr, fl4.daddr, protocol, tos, ttl, + df, !net_eq(tunnel->net, dev_net(dev))); + return; +-- +2.43.0 + diff --git a/queue-6.7/net-lan78xx-fix-softirq-work-is-pending-error.patch b/queue-6.7/net-lan78xx-fix-softirq-work-is-pending-error.patch new file mode 100644 index 00000000000..d1c9b1b802b --- /dev/null +++ b/queue-6.7/net-lan78xx-fix-softirq-work-is-pending-error.patch @@ -0,0 +1,39 @@ +From 5762a118bace98a4ff085e5a515559fd835d79dc Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 26 Feb 2024 12:08:20 +0100 +Subject: net: lan78xx: fix "softirq work is pending" error + +From: Oleksij Rempel + +[ Upstream commit e3d5d70cb483df8296dd44e9ae3b6355ef86494c ] + +Disable BH around the call to napi_schedule() to avoid following +error: +NOHZ tick-stop error: local softirq work is pending, handler #08!!! + +Fixes: ec4c7e12396b ("lan78xx: Introduce NAPI polling support") +Signed-off-by: Oleksij Rempel +Link: https://lore.kernel.org/r/20240226110820.2113584-1-o.rempel@pengutronix.de +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + drivers/net/usb/lan78xx.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/drivers/net/usb/lan78xx.c b/drivers/net/usb/lan78xx.c +index 2e6d423f3a016..a2dde84499fdd 100644 +--- a/drivers/net/usb/lan78xx.c ++++ b/drivers/net/usb/lan78xx.c +@@ -1501,7 +1501,9 @@ static int lan78xx_link_reset(struct lan78xx_net *dev) + + lan78xx_rx_urb_submit_all(dev); + ++ local_bh_disable(); + napi_schedule(&dev->napi); ++ local_bh_enable(); + } + + return 0; +-- +2.43.0 + diff --git a/queue-6.7/net-mctp-take-ownership-of-skb-in-mctp_local_output.patch b/queue-6.7/net-mctp-take-ownership-of-skb-in-mctp_local_output.patch new file mode 100644 index 00000000000..0e8ce7089fe --- /dev/null +++ b/queue-6.7/net-mctp-take-ownership-of-skb-in-mctp_local_output.patch @@ -0,0 +1,83 @@ +From bd15896818a126d1192be3bd0e5ca1b02643b0ec Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 20 Feb 2024 16:10:53 +0800 +Subject: net: mctp: take ownership of skb in mctp_local_output + +From: Jeremy Kerr + +[ Upstream commit 3773d65ae5154ed7df404b050fd7387a36ab5ef3 ] + +Currently, mctp_local_output only takes ownership of skb on success, and +we may leak an skb if mctp_local_output fails in specific states; the +skb ownership isn't transferred until the actual output routing occurs. + +Instead, make mctp_local_output free the skb on all error paths up to +the route action, so it always consumes the passed skb. + +Fixes: 833ef3b91de6 ("mctp: Populate socket implementation") +Signed-off-by: Jeremy Kerr +Reviewed-by: Simon Horman +Link: https://lore.kernel.org/r/20240220081053.1439104-1-jk@codeconstruct.com.au +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + include/net/mctp.h | 1 + + net/mctp/route.c | 10 ++++++++-- + 2 files changed, 9 insertions(+), 2 deletions(-) + +diff --git a/include/net/mctp.h b/include/net/mctp.h +index da86e106c91d5..2bff5f47ce82f 100644 +--- a/include/net/mctp.h ++++ b/include/net/mctp.h +@@ -249,6 +249,7 @@ struct mctp_route { + struct mctp_route *mctp_route_lookup(struct net *net, unsigned int dnet, + mctp_eid_t daddr); + ++/* always takes ownership of skb */ + int mctp_local_output(struct sock *sk, struct mctp_route *rt, + struct sk_buff *skb, mctp_eid_t daddr, u8 req_tag); + +diff --git a/net/mctp/route.c b/net/mctp/route.c +index 6218dcd07e184..ceee44ea09d97 100644 +--- a/net/mctp/route.c ++++ b/net/mctp/route.c +@@ -888,7 +888,7 @@ int mctp_local_output(struct sock *sk, struct mctp_route *rt, + dev = dev_get_by_index_rcu(sock_net(sk), cb->ifindex); + if (!dev) { + rcu_read_unlock(); +- return rc; ++ goto out_free; + } + rt->dev = __mctp_dev_get(dev); + rcu_read_unlock(); +@@ -903,7 +903,8 @@ int mctp_local_output(struct sock *sk, struct mctp_route *rt, + rt->mtu = 0; + + } else { +- return -EINVAL; ++ rc = -EINVAL; ++ goto out_free; + } + + spin_lock_irqsave(&rt->dev->addrs_lock, flags); +@@ -966,12 +967,17 @@ int mctp_local_output(struct sock *sk, struct mctp_route *rt, + rc = mctp_do_fragment_route(rt, skb, mtu, tag); + } + ++ /* route output functions consume the skb, even on error */ ++ skb = NULL; ++ + out_release: + if (!ext_rt) + mctp_route_release(rt); + + mctp_dev_put(tmp_rt.dev); + ++out_free: ++ kfree_skb(skb); + return rc; + } + +-- +2.43.0 + diff --git a/queue-6.7/net-usb-dm9601-fix-wrong-return-value-in-dm9601_mdio.patch b/queue-6.7/net-usb-dm9601-fix-wrong-return-value-in-dm9601_mdio.patch new file mode 100644 index 00000000000..480e8dcc9f1 --- /dev/null +++ b/queue-6.7/net-usb-dm9601-fix-wrong-return-value-in-dm9601_mdio.patch @@ -0,0 +1,49 @@ +From b6da1cced14e133c063c76c0283309bb82170a99 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 25 Feb 2024 00:20:06 +0100 +Subject: net: usb: dm9601: fix wrong return value in dm9601_mdio_read + +From: Javier Carrasco + +[ Upstream commit c68b2c9eba38ec3f60f4894b189090febf4d8d22 ] + +The MII code does not check the return value of mdio_read (among +others), and therefore no error code should be sent. A previous fix to +the use of an uninitialized variable propagates negative error codes, +that might lead to wrong operations by the MII library. + +An example of such issues is the use of mii_nway_restart by the dm9601 +driver. The mii_nway_restart function does not check the value returned +by mdio_read, which in this case might be a negative number which could +contain the exact bit the function checks (BMCR_ANENABLE = 0x1000). + +Return zero in case of error, as it is common practice in users of +mdio_read to avoid wrong uses of the return value. + +Fixes: 8f8abb863fa5 ("net: usb: dm9601: fix uninitialized variable use in dm9601_mdio_read") +Signed-off-by: Javier Carrasco +Reviewed-by: Simon Horman +Reviewed-by: Peter Korsgaard +Link: https://lore.kernel.org/r/20240225-dm9601_ret_err-v1-1-02c1d959ea59@gmail.com +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + drivers/net/usb/dm9601.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/net/usb/dm9601.c b/drivers/net/usb/dm9601.c +index 99ec1d4a972db..8b6d6a1b3c2ec 100644 +--- a/drivers/net/usb/dm9601.c ++++ b/drivers/net/usb/dm9601.c +@@ -232,7 +232,7 @@ static int dm9601_mdio_read(struct net_device *netdev, int phy_id, int loc) + err = dm_read_shared_word(dev, 1, loc, &res); + if (err < 0) { + netdev_err(dev->net, "MDIO read error: %d\n", err); +- return err; ++ return 0; + } + + netdev_dbg(dev->net, +-- +2.43.0 + diff --git a/queue-6.7/net-veth-clear-gro-when-clearing-xdp-even-when-down.patch b/queue-6.7/net-veth-clear-gro-when-clearing-xdp-even-when-down.patch new file mode 100644 index 00000000000..105ad6791c2 --- /dev/null +++ b/queue-6.7/net-veth-clear-gro-when-clearing-xdp-even-when-down.patch @@ -0,0 +1,121 @@ +From 8e96197e7b8c759784033f32811e36f95ea4330b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 15:12:10 -0800 +Subject: net: veth: clear GRO when clearing XDP even when down +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Jakub Kicinski + +[ Upstream commit fe9f801355f0b47668419f30f1fac1cf4539e736 ] + +veth sets NETIF_F_GRO automatically when XDP is enabled, +because both features use the same NAPI machinery. + +The logic to clear NETIF_F_GRO sits in veth_disable_xdp() which +is called both on ndo_stop and when XDP is turned off. +To avoid the flag from being cleared when the device is brought +down, the clearing is skipped when IFF_UP is not set. +Bringing the device down should indeed not modify its features. + +Unfortunately, this means that clearing is also skipped when +XDP is disabled _while_ the device is down. And there's nothing +on the open path to bring the device features back into sync. +IOW if user enables XDP, disables it and then brings the device +up we'll end up with a stray GRO flag set but no NAPI instances. + +We don't depend on the GRO flag on the datapath, so the datapath +won't crash. We will crash (or hang), however, next time features +are sync'ed (either by user via ethtool or peer changing its config). +The GRO flag will go away, and veth will try to disable the NAPIs. +But the open path never created them since XDP was off, the GRO flag +was a stray. If NAPI was initialized before we'll hang in napi_disable(). +If it never was we'll crash trying to stop uninitialized hrtimer. + +Move the GRO flag updates to the XDP enable / disable paths, +instead of mixing them with the ndo_open / ndo_close paths. + +Fixes: d3256efd8e8b ("veth: allow enabling NAPI even without XDP") +Reported-by: Thomas Gleixner +Reported-by: syzbot+039399a9b96297ddedca@syzkaller.appspotmail.com +Signed-off-by: Jakub Kicinski +Reviewed-by: Toke Høiland-Jørgensen +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + drivers/net/veth.c | 35 +++++++++++++++++------------------ + 1 file changed, 17 insertions(+), 18 deletions(-) + +diff --git a/drivers/net/veth.c b/drivers/net/veth.c +index 977861c46b1fe..bf4da315ae01c 100644 +--- a/drivers/net/veth.c ++++ b/drivers/net/veth.c +@@ -1208,14 +1208,6 @@ static int veth_enable_xdp(struct net_device *dev) + veth_disable_xdp_range(dev, 0, dev->real_num_rx_queues, true); + return err; + } +- +- if (!veth_gro_requested(dev)) { +- /* user-space did not require GRO, but adding XDP +- * is supposed to get GRO working +- */ +- dev->features |= NETIF_F_GRO; +- netdev_features_change(dev); +- } + } + } + +@@ -1235,18 +1227,9 @@ static void veth_disable_xdp(struct net_device *dev) + for (i = 0; i < dev->real_num_rx_queues; i++) + rcu_assign_pointer(priv->rq[i].xdp_prog, NULL); + +- if (!netif_running(dev) || !veth_gro_requested(dev)) { ++ if (!netif_running(dev) || !veth_gro_requested(dev)) + veth_napi_del(dev); + +- /* if user-space did not require GRO, since adding XDP +- * enabled it, clear it now +- */ +- if (!veth_gro_requested(dev) && netif_running(dev)) { +- dev->features &= ~NETIF_F_GRO; +- netdev_features_change(dev); +- } +- } +- + veth_disable_xdp_range(dev, 0, dev->real_num_rx_queues, false); + } + +@@ -1654,6 +1637,14 @@ static int veth_xdp_set(struct net_device *dev, struct bpf_prog *prog, + } + + if (!old_prog) { ++ if (!veth_gro_requested(dev)) { ++ /* user-space did not require GRO, but adding ++ * XDP is supposed to get GRO working ++ */ ++ dev->features |= NETIF_F_GRO; ++ netdev_features_change(dev); ++ } ++ + peer->hw_features &= ~NETIF_F_GSO_SOFTWARE; + peer->max_mtu = max_mtu; + } +@@ -1669,6 +1660,14 @@ static int veth_xdp_set(struct net_device *dev, struct bpf_prog *prog, + if (dev->flags & IFF_UP) + veth_disable_xdp(dev); + ++ /* if user-space did not require GRO, since adding XDP ++ * enabled it, clear it now ++ */ ++ if (!veth_gro_requested(dev)) { ++ dev->features &= ~NETIF_F_GRO; ++ netdev_features_change(dev); ++ } ++ + if (peer) { + peer->hw_features |= NETIF_F_GSO_SOFTWARE; + peer->max_mtu = ETH_MAX_MTU; +-- +2.43.0 + diff --git a/queue-6.7/netfilter-bridge-confirm-multicast-packets-before-pa.patch b/queue-6.7/netfilter-bridge-confirm-multicast-packets-before-pa.patch new file mode 100644 index 00000000000..faf0c412b2b --- /dev/null +++ b/queue-6.7/netfilter-bridge-confirm-multicast-packets-before-pa.patch @@ -0,0 +1,282 @@ +From 468bd7513ce5d6d7460c0abe9d92338c793cdac4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 16:17:51 +0100 +Subject: netfilter: bridge: confirm multicast packets before passing them up + the stack + +From: Florian Westphal + +[ Upstream commit 62e7151ae3eb465e0ab52a20c941ff33bb6332e9 ] + +conntrack nf_confirm logic cannot handle cloned skbs referencing +the same nf_conn entry, which will happen for multicast (broadcast) +frames on bridges. + + Example: + macvlan0 + | + br0 + / \ + ethX ethY + + ethX (or Y) receives a L2 multicast or broadcast packet containing + an IP packet, flow is not yet in conntrack table. + + 1. skb passes through bridge and fake-ip (br_netfilter)Prerouting. + -> skb->_nfct now references a unconfirmed entry + 2. skb is broad/mcast packet. bridge now passes clones out on each bridge + interface. + 3. skb gets passed up the stack. + 4. In macvlan case, macvlan driver retains clone(s) of the mcast skb + and schedules a work queue to send them out on the lower devices. + + The clone skb->_nfct is not a copy, it is the same entry as the + original skb. The macvlan rx handler then returns RX_HANDLER_PASS. + 5. Normal conntrack hooks (in NF_INET_LOCAL_IN) confirm the orig skb. + +The Macvlan broadcast worker and normal confirm path will race. + +This race will not happen if step 2 already confirmed a clone. In that +case later steps perform skb_clone() with skb->_nfct already confirmed (in +hash table). This works fine. + +But such confirmation won't happen when eb/ip/nftables rules dropped the +packets before they reached the nf_confirm step in postrouting. + +Pablo points out that nf_conntrack_bridge doesn't allow use of stateful +nat, so we can safely discard the nf_conn entry and let inet call +conntrack again. + +This doesn't work for bridge netfilter: skb could have a nat +transformation. Also bridge nf prevents re-invocation of inet prerouting +via 'sabotage_in' hook. + +Work around this problem by explicit confirmation of the entry at LOCAL_IN +time, before upper layer has a chance to clone the unconfirmed entry. + +The downside is that this disables NAT and conntrack helpers. + +Alternative fix would be to add locking to all code parts that deal with +unconfirmed packets, but even if that could be done in a sane way this +opens up other problems, for example: + +-m physdev --physdev-out eth0 -j SNAT --snat-to 1.2.3.4 +-m physdev --physdev-out eth1 -j SNAT --snat-to 1.2.3.5 + +For multicast case, only one of such conflicting mappings will be +created, conntrack only handles 1:1 NAT mappings. + +Users should set create a setup that explicitly marks such traffic +NOTRACK (conntrack bypass) to avoid this, but we cannot auto-bypass +them, ruleset might have accept rules for untracked traffic already, +so user-visible behaviour would change. + +Suggested-by: Pablo Neira Ayuso +Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2") +Closes: https://bugzilla.kernel.org/show_bug.cgi?id=217777 +Signed-off-by: Florian Westphal +Signed-off-by: Pablo Neira Ayuso +Signed-off-by: Sasha Levin +--- + include/linux/netfilter.h | 1 + + net/bridge/br_netfilter_hooks.c | 96 ++++++++++++++++++++++ + net/bridge/netfilter/nf_conntrack_bridge.c | 30 +++++++ + net/netfilter/nf_conntrack_core.c | 1 + + 4 files changed, 128 insertions(+) + +diff --git a/include/linux/netfilter.h b/include/linux/netfilter.h +index 80900d9109920..ce660d51549b4 100644 +--- a/include/linux/netfilter.h ++++ b/include/linux/netfilter.h +@@ -474,6 +474,7 @@ struct nf_ct_hook { + const struct sk_buff *); + void (*attach)(struct sk_buff *nskb, const struct sk_buff *skb); + void (*set_closing)(struct nf_conntrack *nfct); ++ int (*confirm)(struct sk_buff *skb); + }; + extern const struct nf_ct_hook __rcu *nf_ct_hook; + +diff --git a/net/bridge/br_netfilter_hooks.c b/net/bridge/br_netfilter_hooks.c +index ed17208907578..35e10c5a766d5 100644 +--- a/net/bridge/br_netfilter_hooks.c ++++ b/net/bridge/br_netfilter_hooks.c +@@ -43,6 +43,10 @@ + #include + #endif + ++#if IS_ENABLED(CONFIG_NF_CONNTRACK) ++#include ++#endif ++ + static unsigned int brnf_net_id __read_mostly; + + struct brnf_net { +@@ -553,6 +557,90 @@ static unsigned int br_nf_pre_routing(void *priv, + return NF_STOLEN; + } + ++#if IS_ENABLED(CONFIG_NF_CONNTRACK) ++/* conntracks' nf_confirm logic cannot handle cloned skbs referencing ++ * the same nf_conn entry, which will happen for multicast (broadcast) ++ * Frames on bridges. ++ * ++ * Example: ++ * macvlan0 ++ * br0 ++ * ethX ethY ++ * ++ * ethX (or Y) receives multicast or broadcast packet containing ++ * an IP packet, not yet in conntrack table. ++ * ++ * 1. skb passes through bridge and fake-ip (br_netfilter)Prerouting. ++ * -> skb->_nfct now references a unconfirmed entry ++ * 2. skb is broad/mcast packet. bridge now passes clones out on each bridge ++ * interface. ++ * 3. skb gets passed up the stack. ++ * 4. In macvlan case, macvlan driver retains clone(s) of the mcast skb ++ * and schedules a work queue to send them out on the lower devices. ++ * ++ * The clone skb->_nfct is not a copy, it is the same entry as the ++ * original skb. The macvlan rx handler then returns RX_HANDLER_PASS. ++ * 5. Normal conntrack hooks (in NF_INET_LOCAL_IN) confirm the orig skb. ++ * ++ * The Macvlan broadcast worker and normal confirm path will race. ++ * ++ * This race will not happen if step 2 already confirmed a clone. In that ++ * case later steps perform skb_clone() with skb->_nfct already confirmed (in ++ * hash table). This works fine. ++ * ++ * But such confirmation won't happen when eb/ip/nftables rules dropped the ++ * packets before they reached the nf_confirm step in postrouting. ++ * ++ * Work around this problem by explicit confirmation of the entry at ++ * LOCAL_IN time, before upper layer has a chance to clone the unconfirmed ++ * entry. ++ * ++ */ ++static unsigned int br_nf_local_in(void *priv, ++ struct sk_buff *skb, ++ const struct nf_hook_state *state) ++{ ++ struct nf_conntrack *nfct = skb_nfct(skb); ++ const struct nf_ct_hook *ct_hook; ++ struct nf_conn *ct; ++ int ret; ++ ++ if (!nfct || skb->pkt_type == PACKET_HOST) ++ return NF_ACCEPT; ++ ++ ct = container_of(nfct, struct nf_conn, ct_general); ++ if (likely(nf_ct_is_confirmed(ct))) ++ return NF_ACCEPT; ++ ++ WARN_ON_ONCE(skb_shared(skb)); ++ WARN_ON_ONCE(refcount_read(&nfct->use) != 1); ++ ++ /* We can't call nf_confirm here, it would create a dependency ++ * on nf_conntrack module. ++ */ ++ ct_hook = rcu_dereference(nf_ct_hook); ++ if (!ct_hook) { ++ skb->_nfct = 0ul; ++ nf_conntrack_put(nfct); ++ return NF_ACCEPT; ++ } ++ ++ nf_bridge_pull_encap_header(skb); ++ ret = ct_hook->confirm(skb); ++ switch (ret & NF_VERDICT_MASK) { ++ case NF_STOLEN: ++ return NF_STOLEN; ++ default: ++ nf_bridge_push_encap_header(skb); ++ break; ++ } ++ ++ ct = container_of(nfct, struct nf_conn, ct_general); ++ WARN_ON_ONCE(!nf_ct_is_confirmed(ct)); ++ ++ return ret; ++} ++#endif + + /* PF_BRIDGE/FORWARD *************************************************/ + static int br_nf_forward_finish(struct net *net, struct sock *sk, struct sk_buff *skb) +@@ -964,6 +1052,14 @@ static const struct nf_hook_ops br_nf_ops[] = { + .hooknum = NF_BR_PRE_ROUTING, + .priority = NF_BR_PRI_BRNF, + }, ++#if IS_ENABLED(CONFIG_NF_CONNTRACK) ++ { ++ .hook = br_nf_local_in, ++ .pf = NFPROTO_BRIDGE, ++ .hooknum = NF_BR_LOCAL_IN, ++ .priority = NF_BR_PRI_LAST, ++ }, ++#endif + { + .hook = br_nf_forward, + .pf = NFPROTO_BRIDGE, +diff --git a/net/bridge/netfilter/nf_conntrack_bridge.c b/net/bridge/netfilter/nf_conntrack_bridge.c +index abb090f94ed26..6f877e31709ba 100644 +--- a/net/bridge/netfilter/nf_conntrack_bridge.c ++++ b/net/bridge/netfilter/nf_conntrack_bridge.c +@@ -291,6 +291,30 @@ static unsigned int nf_ct_bridge_pre(void *priv, struct sk_buff *skb, + return nf_conntrack_in(skb, &bridge_state); + } + ++static unsigned int nf_ct_bridge_in(void *priv, struct sk_buff *skb, ++ const struct nf_hook_state *state) ++{ ++ enum ip_conntrack_info ctinfo; ++ struct nf_conn *ct; ++ ++ if (skb->pkt_type == PACKET_HOST) ++ return NF_ACCEPT; ++ ++ /* nf_conntrack_confirm() cannot handle concurrent clones, ++ * this happens for broad/multicast frames with e.g. macvlan on top ++ * of the bridge device. ++ */ ++ ct = nf_ct_get(skb, &ctinfo); ++ if (!ct || nf_ct_is_confirmed(ct) || nf_ct_is_template(ct)) ++ return NF_ACCEPT; ++ ++ /* let inet prerouting call conntrack again */ ++ skb->_nfct = 0; ++ nf_ct_put(ct); ++ ++ return NF_ACCEPT; ++} ++ + static void nf_ct_bridge_frag_save(struct sk_buff *skb, + struct nf_bridge_frag_data *data) + { +@@ -385,6 +409,12 @@ static struct nf_hook_ops nf_ct_bridge_hook_ops[] __read_mostly = { + .hooknum = NF_BR_PRE_ROUTING, + .priority = NF_IP_PRI_CONNTRACK, + }, ++ { ++ .hook = nf_ct_bridge_in, ++ .pf = NFPROTO_BRIDGE, ++ .hooknum = NF_BR_LOCAL_IN, ++ .priority = NF_IP_PRI_CONNTRACK_CONFIRM, ++ }, + { + .hook = nf_ct_bridge_post, + .pf = NFPROTO_BRIDGE, +diff --git a/net/netfilter/nf_conntrack_core.c b/net/netfilter/nf_conntrack_core.c +index 2e5f3864d353a..5b876fa7f9af9 100644 +--- a/net/netfilter/nf_conntrack_core.c ++++ b/net/netfilter/nf_conntrack_core.c +@@ -2756,6 +2756,7 @@ static const struct nf_ct_hook nf_conntrack_hook = { + .get_tuple_skb = nf_conntrack_get_tuple_skb, + .attach = nf_conntrack_attach, + .set_closing = nf_conntrack_set_closing, ++ .confirm = __nf_conntrack_confirm, + }; + + void nf_conntrack_init_end(void) +-- +2.43.0 + diff --git a/queue-6.7/netfilter-nf_tables-allow-nfproto_inet-in-nft_-match.patch b/queue-6.7/netfilter-nf_tables-allow-nfproto_inet-in-nft_-match.patch new file mode 100644 index 00000000000..d8a3b53b6fd --- /dev/null +++ b/queue-6.7/netfilter-nf_tables-allow-nfproto_inet-in-nft_-match.patch @@ -0,0 +1,108 @@ +From 5b2d37a6a27367e3ce1c08dc720eff43aaee06f7 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 10:33:08 +0000 +Subject: netfilter: nf_tables: allow NFPROTO_INET in + nft_(match/target)_validate() + +From: Ignat Korchagin + +[ Upstream commit 7e0f122c65912740327e4c54472acaa5f85868cb ] + +Commit d0009effa886 ("netfilter: nf_tables: validate NFPROTO_* family") added +some validation of NFPROTO_* families in the nft_compat module, but it broke +the ability to use legacy iptables modules in dual-stack nftables. + +While with legacy iptables one had to independently manage IPv4 and IPv6 +tables, with nftables it is possible to have dual-stack tables sharing the +rules. Moreover, it was possible to use rules based on legacy iptables +match/target modules in dual-stack nftables. + +As an example, the program from [2] creates an INET dual-stack family table +using an xt_bpf based rule, which looks like the following (the actual output +was generated with a patched nft tool as the current nft tool does not parse +dual stack tables with legacy match rules, so consider it for illustrative +purposes only): + +table inet testfw { + chain input { + type filter hook prerouting priority filter; policy accept; + bytecode counter packets 0 bytes 0 accept + } +} + +After d0009effa886 ("netfilter: nf_tables: validate NFPROTO_* family") we get +EOPNOTSUPP for the above program. + +Fix this by allowing NFPROTO_INET for nft_(match/target)_validate(), but also +restrict the functions to classic iptables hooks. + +Changes in v3: + * clarify that upstream nft will not display such configuration properly and + that the output was generated with a patched nft tool + * remove example program from commit description and link to it instead + * no code changes otherwise + +Changes in v2: + * restrict nft_(match/target)_validate() to classic iptables hooks + * rewrite example program to use unmodified libnftnl + +Fixes: d0009effa886 ("netfilter: nf_tables: validate NFPROTO_* family") +Link: https://lore.kernel.org/all/Zc1PfoWN38UuFJRI@calendula/T/#mc947262582c90fec044c7a3398cc92fac7afea72 [1] +Link: https://lore.kernel.org/all/20240220145509.53357-1-ignat@cloudflare.com/ [2] +Reported-by: Jordan Griege +Signed-off-by: Ignat Korchagin +Signed-off-by: Pablo Neira Ayuso +Signed-off-by: Sasha Levin +--- + net/netfilter/nft_compat.c | 20 ++++++++++++++++++++ + 1 file changed, 20 insertions(+) + +diff --git a/net/netfilter/nft_compat.c b/net/netfilter/nft_compat.c +index 1f9474fefe849..d3d11dede5450 100644 +--- a/net/netfilter/nft_compat.c ++++ b/net/netfilter/nft_compat.c +@@ -359,10 +359,20 @@ static int nft_target_validate(const struct nft_ctx *ctx, + + if (ctx->family != NFPROTO_IPV4 && + ctx->family != NFPROTO_IPV6 && ++ ctx->family != NFPROTO_INET && + ctx->family != NFPROTO_BRIDGE && + ctx->family != NFPROTO_ARP) + return -EOPNOTSUPP; + ++ ret = nft_chain_validate_hooks(ctx->chain, ++ (1 << NF_INET_PRE_ROUTING) | ++ (1 << NF_INET_LOCAL_IN) | ++ (1 << NF_INET_FORWARD) | ++ (1 << NF_INET_LOCAL_OUT) | ++ (1 << NF_INET_POST_ROUTING)); ++ if (ret) ++ return ret; ++ + if (nft_is_base_chain(ctx->chain)) { + const struct nft_base_chain *basechain = + nft_base_chain(ctx->chain); +@@ -610,10 +620,20 @@ static int nft_match_validate(const struct nft_ctx *ctx, + + if (ctx->family != NFPROTO_IPV4 && + ctx->family != NFPROTO_IPV6 && ++ ctx->family != NFPROTO_INET && + ctx->family != NFPROTO_BRIDGE && + ctx->family != NFPROTO_ARP) + return -EOPNOTSUPP; + ++ ret = nft_chain_validate_hooks(ctx->chain, ++ (1 << NF_INET_PRE_ROUTING) | ++ (1 << NF_INET_LOCAL_IN) | ++ (1 << NF_INET_FORWARD) | ++ (1 << NF_INET_LOCAL_OUT) | ++ (1 << NF_INET_POST_ROUTING)); ++ if (ret) ++ return ret; ++ + if (nft_is_base_chain(ctx->chain)) { + const struct nft_base_chain *basechain = + nft_base_chain(ctx->chain); +-- +2.43.0 + diff --git a/queue-6.7/netlink-add-nla-be16-32-types-to-minlen-array.patch b/queue-6.7/netlink-add-nla-be16-32-types-to-minlen-array.patch new file mode 100644 index 00000000000..e534db073b2 --- /dev/null +++ b/queue-6.7/netlink-add-nla-be16-32-types-to-minlen-array.patch @@ -0,0 +1,65 @@ +From fc3abc2aae27399a812bfdc6ed5ab7d5de6b38a4 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 18:27:33 +0100 +Subject: netlink: add nla be16/32 types to minlen array + +From: Florian Westphal + +[ Upstream commit 9a0d18853c280f6a0ee99f91619f2442a17a323a ] + +BUG: KMSAN: uninit-value in nla_validate_range_unsigned lib/nlattr.c:222 [inline] +BUG: KMSAN: uninit-value in nla_validate_int_range lib/nlattr.c:336 [inline] +BUG: KMSAN: uninit-value in validate_nla lib/nlattr.c:575 [inline] +BUG: KMSAN: uninit-value in __nla_validate_parse+0x2e20/0x45c0 lib/nlattr.c:631 + nla_validate_range_unsigned lib/nlattr.c:222 [inline] + nla_validate_int_range lib/nlattr.c:336 [inline] + validate_nla lib/nlattr.c:575 [inline] +... + +The message in question matches this policy: + + [NFTA_TARGET_REV] = NLA_POLICY_MAX(NLA_BE32, 255), + +but because NLA_BE32 size in minlen array is 0, the validation +code will read past the malformed (too small) attribute. + +Note: Other attributes, e.g. BITFIELD32, SINT, UINT.. are also missing: +those likely should be added too. + +Reported-by: syzbot+3f497b07aa3baf2fb4d0@syzkaller.appspotmail.com +Reported-by: xingwei lee +Closes: https://lore.kernel.org/all/CABOYnLzFYHSnvTyS6zGa-udNX55+izqkOt2sB9WDqUcEGW6n8w@mail.gmail.com/raw +Fixes: ecaf75ffd5f5 ("netlink: introduce bigendian integer types") +Signed-off-by: Florian Westphal +Link: https://lore.kernel.org/r/20240221172740.5092-1-fw@strlen.de +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + lib/nlattr.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/lib/nlattr.c b/lib/nlattr.c +index dc15e7888fc1f..0319e811bb10a 100644 +--- a/lib/nlattr.c ++++ b/lib/nlattr.c +@@ -30,6 +30,8 @@ static const u8 nla_attr_len[NLA_TYPE_MAX+1] = { + [NLA_S16] = sizeof(s16), + [NLA_S32] = sizeof(s32), + [NLA_S64] = sizeof(s64), ++ [NLA_BE16] = sizeof(__be16), ++ [NLA_BE32] = sizeof(__be32), + }; + + static const u8 nla_attr_minlen[NLA_TYPE_MAX+1] = { +@@ -43,6 +45,8 @@ static const u8 nla_attr_minlen[NLA_TYPE_MAX+1] = { + [NLA_S16] = sizeof(s16), + [NLA_S32] = sizeof(s32), + [NLA_S64] = sizeof(s64), ++ [NLA_BE16] = sizeof(__be16), ++ [NLA_BE32] = sizeof(__be32), + }; + + /* +-- +2.43.0 + diff --git a/queue-6.7/netlink-fix-kernel-infoleak-after-free-in-__skb_data.patch b/queue-6.7/netlink-fix-kernel-infoleak-after-free-in-__skb_data.patch new file mode 100644 index 00000000000..fd9e44d38d0 --- /dev/null +++ b/queue-6.7/netlink-fix-kernel-infoleak-after-free-in-__skb_data.patch @@ -0,0 +1,134 @@ +From 5fceda5f8ecbf764076b1a5676277c287434968c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 16:40:48 +0900 +Subject: netlink: Fix kernel-infoleak-after-free in __skb_datagram_iter + +From: Ryosuke Yasuoka + +[ Upstream commit 661779e1fcafe1b74b3f3fe8e980c1e207fea1fd ] + +syzbot reported the following uninit-value access issue [1]: + +netlink_to_full_skb() creates a new `skb` and puts the `skb->data` +passed as a 1st arg of netlink_to_full_skb() onto new `skb`. The data +size is specified as `len` and passed to skb_put_data(). This `len` +is based on `skb->end` that is not data offset but buffer offset. The +`skb->end` contains data and tailroom. Since the tailroom is not +initialized when the new `skb` created, KMSAN detects uninitialized +memory area when copying the data. + +This patch resolved this issue by correct the len from `skb->end` to +`skb->len`, which is the actual data offset. + +BUG: KMSAN: kernel-infoleak-after-free in instrument_copy_to_user include/linux/instrumented.h:114 [inline] +BUG: KMSAN: kernel-infoleak-after-free in copy_to_user_iter lib/iov_iter.c:24 [inline] +BUG: KMSAN: kernel-infoleak-after-free in iterate_ubuf include/linux/iov_iter.h:29 [inline] +BUG: KMSAN: kernel-infoleak-after-free in iterate_and_advance2 include/linux/iov_iter.h:245 [inline] +BUG: KMSAN: kernel-infoleak-after-free in iterate_and_advance include/linux/iov_iter.h:271 [inline] +BUG: KMSAN: kernel-infoleak-after-free in _copy_to_iter+0x364/0x2520 lib/iov_iter.c:186 + instrument_copy_to_user include/linux/instrumented.h:114 [inline] + copy_to_user_iter lib/iov_iter.c:24 [inline] + iterate_ubuf include/linux/iov_iter.h:29 [inline] + iterate_and_advance2 include/linux/iov_iter.h:245 [inline] + iterate_and_advance include/linux/iov_iter.h:271 [inline] + _copy_to_iter+0x364/0x2520 lib/iov_iter.c:186 + copy_to_iter include/linux/uio.h:197 [inline] + simple_copy_to_iter+0x68/0xa0 net/core/datagram.c:532 + __skb_datagram_iter+0x123/0xdc0 net/core/datagram.c:420 + skb_copy_datagram_iter+0x5c/0x200 net/core/datagram.c:546 + skb_copy_datagram_msg include/linux/skbuff.h:3960 [inline] + packet_recvmsg+0xd9c/0x2000 net/packet/af_packet.c:3482 + sock_recvmsg_nosec net/socket.c:1044 [inline] + sock_recvmsg net/socket.c:1066 [inline] + sock_read_iter+0x467/0x580 net/socket.c:1136 + call_read_iter include/linux/fs.h:2014 [inline] + new_sync_read fs/read_write.c:389 [inline] + vfs_read+0x8f6/0xe00 fs/read_write.c:470 + ksys_read+0x20f/0x4c0 fs/read_write.c:613 + __do_sys_read fs/read_write.c:623 [inline] + __se_sys_read fs/read_write.c:621 [inline] + __x64_sys_read+0x93/0xd0 fs/read_write.c:621 + do_syscall_x64 arch/x86/entry/common.c:52 [inline] + do_syscall_64+0x44/0x110 arch/x86/entry/common.c:83 + entry_SYSCALL_64_after_hwframe+0x63/0x6b + +Uninit was stored to memory at: + skb_put_data include/linux/skbuff.h:2622 [inline] + netlink_to_full_skb net/netlink/af_netlink.c:181 [inline] + __netlink_deliver_tap_skb net/netlink/af_netlink.c:298 [inline] + __netlink_deliver_tap+0x5be/0xc90 net/netlink/af_netlink.c:325 + netlink_deliver_tap net/netlink/af_netlink.c:338 [inline] + netlink_deliver_tap_kernel net/netlink/af_netlink.c:347 [inline] + netlink_unicast_kernel net/netlink/af_netlink.c:1341 [inline] + netlink_unicast+0x10f1/0x1250 net/netlink/af_netlink.c:1368 + netlink_sendmsg+0x1238/0x13d0 net/netlink/af_netlink.c:1910 + sock_sendmsg_nosec net/socket.c:730 [inline] + __sock_sendmsg net/socket.c:745 [inline] + ____sys_sendmsg+0x9c2/0xd60 net/socket.c:2584 + ___sys_sendmsg+0x28d/0x3c0 net/socket.c:2638 + __sys_sendmsg net/socket.c:2667 [inline] + __do_sys_sendmsg net/socket.c:2676 [inline] + __se_sys_sendmsg net/socket.c:2674 [inline] + __x64_sys_sendmsg+0x307/0x490 net/socket.c:2674 + do_syscall_x64 arch/x86/entry/common.c:52 [inline] + do_syscall_64+0x44/0x110 arch/x86/entry/common.c:83 + entry_SYSCALL_64_after_hwframe+0x63/0x6b + +Uninit was created at: + free_pages_prepare mm/page_alloc.c:1087 [inline] + free_unref_page_prepare+0xb0/0xa40 mm/page_alloc.c:2347 + free_unref_page_list+0xeb/0x1100 mm/page_alloc.c:2533 + release_pages+0x23d3/0x2410 mm/swap.c:1042 + free_pages_and_swap_cache+0xd9/0xf0 mm/swap_state.c:316 + tlb_batch_pages_flush mm/mmu_gather.c:98 [inline] + tlb_flush_mmu_free mm/mmu_gather.c:293 [inline] + tlb_flush_mmu+0x6f5/0x980 mm/mmu_gather.c:300 + tlb_finish_mmu+0x101/0x260 mm/mmu_gather.c:392 + exit_mmap+0x49e/0xd30 mm/mmap.c:3321 + __mmput+0x13f/0x530 kernel/fork.c:1349 + mmput+0x8a/0xa0 kernel/fork.c:1371 + exit_mm+0x1b8/0x360 kernel/exit.c:567 + do_exit+0xd57/0x4080 kernel/exit.c:858 + do_group_exit+0x2fd/0x390 kernel/exit.c:1021 + __do_sys_exit_group kernel/exit.c:1032 [inline] + __se_sys_exit_group kernel/exit.c:1030 [inline] + __x64_sys_exit_group+0x3c/0x50 kernel/exit.c:1030 + do_syscall_x64 arch/x86/entry/common.c:52 [inline] + do_syscall_64+0x44/0x110 arch/x86/entry/common.c:83 + entry_SYSCALL_64_after_hwframe+0x63/0x6b + +Bytes 3852-3903 of 3904 are uninitialized +Memory access of size 3904 starts at ffff88812ea1e000 +Data copied to user address 0000000020003280 + +CPU: 1 PID: 5043 Comm: syz-executor297 Not tainted 6.7.0-rc5-syzkaller-00047-g5bd7ef53ffe5 #0 +Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 11/10/2023 + +Fixes: 1853c9496460 ("netlink, mmap: transform mmap skb into full skb on taps") +Reported-and-tested-by: syzbot+34ad5fab48f7bf510349@syzkaller.appspotmail.com +Closes: https://syzkaller.appspot.com/bug?extid=34ad5fab48f7bf510349 [1] +Signed-off-by: Ryosuke Yasuoka +Reviewed-by: Eric Dumazet +Link: https://lore.kernel.org/r/20240221074053.1794118-1-ryasuoka@redhat.com +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/netlink/af_netlink.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/net/netlink/af_netlink.c b/net/netlink/af_netlink.c +index d9107b545d360..6ae782efb1ee3 100644 +--- a/net/netlink/af_netlink.c ++++ b/net/netlink/af_netlink.c +@@ -167,7 +167,7 @@ static inline u32 netlink_group_mask(u32 group) + static struct sk_buff *netlink_to_full_skb(const struct sk_buff *skb, + gfp_t gfp_mask) + { +- unsigned int len = skb_end_offset(skb); ++ unsigned int len = skb->len; + struct sk_buff *new; + + new = alloc_skb(len, gfp_mask); +-- +2.43.0 + diff --git a/queue-6.7/of-property-fw_devlink-fix-stupid-bug-in-remote-endp.patch b/queue-6.7/of-property-fw_devlink-fix-stupid-bug-in-remote-endp.patch new file mode 100644 index 00000000000..556e00d2994 --- /dev/null +++ b/queue-6.7/of-property-fw_devlink-fix-stupid-bug-in-remote-endp.patch @@ -0,0 +1,44 @@ +From b96037b42f4017c20a6c8fd7db8ff99c1b3ab56d Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 23 Feb 2024 21:24:35 -0800 +Subject: of: property: fw_devlink: Fix stupid bug in remote-endpoint parsing + +From: Saravana Kannan + +[ Upstream commit 7cb50f6c9fbaa1c0b80100b8971bf13db5d75d06 ] + +Introduced a stupid bug in commit 782bfd03c3ae ("of: property: Improve +finding the supplier of a remote-endpoint property") due to a last minute +incorrect edit of "index !=0" into "!index". This patch fixes it to be +"index > 0" to match the comment right next to it. + +Reported-by: Luca Ceresoli +Link: https://lore.kernel.org/lkml/20240223171849.10f9901d@booty/ +Fixes: 782bfd03c3ae ("of: property: Improve finding the supplier of a remote-endpoint property") +Signed-off-by: Saravana Kannan +Reviewed-by: Herve Codina +Reviewed-by: Luca Ceresoli +Tested-by: Luca Ceresoli +Link: https://lore.kernel.org/r/20240224052436.3552333-1-saravanak@google.com +Signed-off-by: Rob Herring +Signed-off-by: Sasha Levin +--- + drivers/of/property.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/drivers/of/property.c b/drivers/of/property.c +index 885ee040ee2b3..15d1156843256 100644 +--- a/drivers/of/property.c ++++ b/drivers/of/property.c +@@ -1303,7 +1303,7 @@ static struct device_node *parse_remote_endpoint(struct device_node *np, + int index) + { + /* Return NULL for index > 0 to signify end of remote-endpoints. */ +- if (!index || strcmp(prop_name, "remote-endpoint")) ++ if (index > 0 || strcmp(prop_name, "remote-endpoint")) + return NULL; + + return of_graph_get_remote_port_parent(np); +-- +2.43.0 + diff --git a/queue-6.7/power-supply-bq27xxx-i2c-do-not-free-non-existing-ir.patch b/queue-6.7/power-supply-bq27xxx-i2c-do-not-free-non-existing-ir.patch new file mode 100644 index 00000000000..ecc027c9b47 --- /dev/null +++ b/queue-6.7/power-supply-bq27xxx-i2c-do-not-free-non-existing-ir.patch @@ -0,0 +1,51 @@ +From 04d17b0776530d22bbf8b3aba2c4714d783a37f3 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 15 Feb 2024 16:51:33 +0100 +Subject: power: supply: bq27xxx-i2c: Do not free non existing IRQ + +From: Hans de Goede + +[ Upstream commit 2df70149e73e79783bcbc7db4fa51ecef0e2022c ] + +The bq27xxx i2c-client may not have an IRQ, in which case +client->irq will be 0. bq27xxx_battery_i2c_probe() already has +an if (client->irq) check wrapping the request_threaded_irq(). + +But bq27xxx_battery_i2c_remove() unconditionally calls +free_irq(client->irq) leading to: + +[ 190.310742] ------------[ cut here ]------------ +[ 190.310843] Trying to free already-free IRQ 0 +[ 190.310861] WARNING: CPU: 2 PID: 1304 at kernel/irq/manage.c:1893 free_irq+0x1b8/0x310 + +Followed by a backtrace when unbinding the driver. Add +an if (client->irq) to bq27xxx_battery_i2c_remove() mirroring +probe() to fix this. + +Fixes: 444ff00734f3 ("power: supply: bq27xxx: Fix I2C IRQ race on remove") +Signed-off-by: Hans de Goede +Link: https://lore.kernel.org/r/20240215155133.70537-1-hdegoede@redhat.com +Signed-off-by: Sebastian Reichel +Signed-off-by: Sasha Levin +--- + drivers/power/supply/bq27xxx_battery_i2c.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/drivers/power/supply/bq27xxx_battery_i2c.c b/drivers/power/supply/bq27xxx_battery_i2c.c +index 9b5475590518f..886e0a8e2abd1 100644 +--- a/drivers/power/supply/bq27xxx_battery_i2c.c ++++ b/drivers/power/supply/bq27xxx_battery_i2c.c +@@ -209,7 +209,9 @@ static void bq27xxx_battery_i2c_remove(struct i2c_client *client) + { + struct bq27xxx_device_info *di = i2c_get_clientdata(client); + +- free_irq(client->irq, di); ++ if (client->irq) ++ free_irq(client->irq, di); ++ + bq27xxx_battery_teardown(di); + + mutex_lock(&battery_mutex); +-- +2.43.0 + diff --git a/queue-6.7/revert-riscv-mm-support-svnapot-in-huge-vmap.patch b/queue-6.7/revert-riscv-mm-support-svnapot-in-huge-vmap.patch new file mode 100644 index 00000000000..0bebd045091 --- /dev/null +++ b/queue-6.7/revert-riscv-mm-support-svnapot-in-huge-vmap.patch @@ -0,0 +1,120 @@ +From 6ddf0b71069fb7abb2c06246e52d4ca3680cf262 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 21:50:15 +0100 +Subject: Revert "riscv: mm: support Svnapot in huge vmap" + +From: Alexandre Ghiti + +[ Upstream commit 16ab4646c9057e0528b985ad772e3cb88c613db2 ] + +This reverts commit ce173474cf19fe7fbe8f0fc74e3c81ec9c3d9807. + +We cannot correctly deal with NAPOT mappings in vmalloc/vmap because if +some part of a NAPOT mapping is unmapped, the remaining mapping is not +updated accordingly. For example: + +ptr = vmalloc_huge(64 * 1024, GFP_KERNEL); +vunmap_range((unsigned long)(ptr + PAGE_SIZE), + (unsigned long)(ptr + 64 * 1024)); + +leads to the following kernel page table dump: + +0xffff8f8000ef0000-0xffff8f8000ef1000 0x00000001033c0000 4K PTE N .. .. D A G . . W R V + +Meaning the first entry which was not unmapped still has the N bit set, +which, if accessed first and cached in the TLB, could allow access to the +unmapped range. + +That's because the logic to break the NAPOT mapping does not exist and +likely won't. Indeed, to break a NAPOT mapping, we first have to clear +the whole mapping, flush the TLB and then set the new mapping ("break- +before-make" equivalent). That works fine in userspace since we can handle +any pagefault occurring on the remaining mapping but we can't handle a kernel +pagefault on such mapping. + +So fix this by reverting the commit that introduced the vmap/vmalloc +support. + +Fixes: ce173474cf19 ("riscv: mm: support Svnapot in huge vmap") +Signed-off-by: Alexandre Ghiti +Link: https://lore.kernel.org/r/20240227205016.121901-2-alexghiti@rivosinc.com +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/include/asm/vmalloc.h | 61 +------------------------------- + 1 file changed, 1 insertion(+), 60 deletions(-) + +diff --git a/arch/riscv/include/asm/vmalloc.h b/arch/riscv/include/asm/vmalloc.h +index 924d01b56c9a1..51f6dfe19745a 100644 +--- a/arch/riscv/include/asm/vmalloc.h ++++ b/arch/riscv/include/asm/vmalloc.h +@@ -19,65 +19,6 @@ static inline bool arch_vmap_pmd_supported(pgprot_t prot) + return true; + } + +-#ifdef CONFIG_RISCV_ISA_SVNAPOT +-#include ++#endif + +-#define arch_vmap_pte_range_map_size arch_vmap_pte_range_map_size +-static inline unsigned long arch_vmap_pte_range_map_size(unsigned long addr, unsigned long end, +- u64 pfn, unsigned int max_page_shift) +-{ +- unsigned long map_size = PAGE_SIZE; +- unsigned long size, order; +- +- if (!has_svnapot()) +- return map_size; +- +- for_each_napot_order_rev(order) { +- if (napot_cont_shift(order) > max_page_shift) +- continue; +- +- size = napot_cont_size(order); +- if (end - addr < size) +- continue; +- +- if (!IS_ALIGNED(addr, size)) +- continue; +- +- if (!IS_ALIGNED(PFN_PHYS(pfn), size)) +- continue; +- +- map_size = size; +- break; +- } +- +- return map_size; +-} +- +-#define arch_vmap_pte_supported_shift arch_vmap_pte_supported_shift +-static inline int arch_vmap_pte_supported_shift(unsigned long size) +-{ +- int shift = PAGE_SHIFT; +- unsigned long order; +- +- if (!has_svnapot()) +- return shift; +- +- WARN_ON_ONCE(size >= PMD_SIZE); +- +- for_each_napot_order_rev(order) { +- if (napot_cont_size(order) > size) +- continue; +- +- if (!IS_ALIGNED(size, napot_cont_size(order))) +- continue; +- +- shift = napot_cont_shift(order); +- break; +- } +- +- return shift; +-} +- +-#endif /* CONFIG_RISCV_ISA_SVNAPOT */ +-#endif /* CONFIG_HAVE_ARCH_HUGE_VMAP */ + #endif /* _ASM_RISCV_VMALLOC_H */ +-- +2.43.0 + diff --git a/queue-6.7/risc-v-ignore-v-from-the-riscv-isa-dt-property-on-ol.patch b/queue-6.7/risc-v-ignore-v-from-the-riscv-isa-dt-property-on-ol.patch new file mode 100644 index 00000000000..d5895e04025 --- /dev/null +++ b/queue-6.7/risc-v-ignore-v-from-the-riscv-isa-dt-property-on-ol.patch @@ -0,0 +1,71 @@ +From 075a553251f56d2bf42d0d704021f1ec7d5f8f66 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 23 Feb 2024 11:31:31 +0000 +Subject: RISC-V: Ignore V from the riscv,isa DT property on older T-Head CPUs + +From: Conor Dooley + +[ Upstream commit d82f32202e0df7bf40d4b67c8a4ff9cea32df4d9 ] + +Before attempting to support the pre-ratification version of vector +found on older T-Head CPUs, disallow "v" in riscv,isa on these +platforms. The deprecated property has no clear way to communicate +the specific version of vector that is supported and much of the vendor +provided software puts "v" in the isa string. riscv,isa-extensions +should be used instead. This should not be too much of a burden for +these systems, as the vendor shipped devicetrees and firmware do not +work with a mainline kernel and will require updating. + +We can limit this restriction to only ignore v in riscv,isa on CPUs +that report T-Head's vendor ID and a zero marchid. Newer T-Head CPUs +that support the ratified version of vector should report non-zero +marchid, according to Guo Ren [1]. + +Link: https://lore.kernel.org/linux-riscv/CAJF2gTRy5eK73=d6s7CVy9m9pB8p4rAoMHM3cZFwzg=AuF7TDA@mail.gmail.com/ [1] +Fixes: dc6667a4e7e3 ("riscv: Extending cpufeature.c to detect V-extension") +Co-developed-by: Conor Dooley +Signed-off-by: Conor Dooley +Acked-by: Guo Ren +Link: https://lore.kernel.org/r/20240223-tidings-shabby-607f086cb4d7@spud +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/kernel/cpufeature.c | 15 +++++++++++++++ + 1 file changed, 15 insertions(+) + +diff --git a/arch/riscv/kernel/cpufeature.c b/arch/riscv/kernel/cpufeature.c +index b3785ffc15703..92a26f8b18450 100644 +--- a/arch/riscv/kernel/cpufeature.c ++++ b/arch/riscv/kernel/cpufeature.c +@@ -22,6 +22,7 @@ + #include + #include + #include ++#include + #include + + #include "copy-unaligned.h" +@@ -401,6 +402,20 @@ static void __init riscv_fill_hwcap_from_isa_string(unsigned long *isa2hwcap) + set_bit(RISCV_ISA_EXT_ZIHPM, isainfo->isa); + } + ++ /* ++ * "V" in ISA strings is ambiguous in practice: it should mean ++ * just the standard V-1.0 but vendors aren't well behaved. ++ * Many vendors with T-Head CPU cores which implement the 0.7.1 ++ * version of the vector specification put "v" into their DTs. ++ * CPU cores with the ratified spec will contain non-zero ++ * marchid. ++ */ ++ if (acpi_disabled && riscv_cached_mvendorid(cpu) == THEAD_VENDOR_ID && ++ riscv_cached_marchid(cpu) == 0x0) { ++ this_hwcap &= ~isa2hwcap[RISCV_ISA_EXT_v]; ++ clear_bit(RISCV_ISA_EXT_v, isainfo->isa); ++ } ++ + /* + * All "okay" hart should have same isa. Set HWCAP based on + * common capabilities of every "okay" hart, in case they don't +-- +2.43.0 + diff --git a/queue-6.7/riscv-fix-build-error-if-config_arch_enable_hugepage.patch b/queue-6.7/riscv-fix-build-error-if-config_arch_enable_hugepage.patch new file mode 100644 index 00000000000..dc8dc1a8ba6 --- /dev/null +++ b/queue-6.7/riscv-fix-build-error-if-config_arch_enable_hugepage.patch @@ -0,0 +1,72 @@ +From f86f0306db3981584614ec008467dc05eae0669d Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Sun, 11 Feb 2024 09:36:40 +0100 +Subject: riscv: Fix build error if !CONFIG_ARCH_ENABLE_HUGEPAGE_MIGRATION + +From: Alexandre Ghiti + +[ Upstream commit fc325b1a915f6d0c821bfcea21fb3f1354c4323b ] + +The new riscv specific arch_hugetlb_migration_supported() must be +guarded with a #ifdef CONFIG_ARCH_ENABLE_HUGEPAGE_MIGRATION to avoid +the following build error: + +In file included from include/linux/hugetlb.h:851, + from kernel/fork.c:52: +>> arch/riscv/include/asm/hugetlb.h:15:42: error: static declaration of 'arch_hugetlb_migration_supported' follows non-static declaration + 15 | #define arch_hugetlb_migration_supported arch_hugetlb_migration_supported + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + include/linux/hugetlb.h:916:20: note: in expansion of macro 'arch_hugetlb_migration_supported' + 916 | static inline bool arch_hugetlb_migration_supported(struct hstate *h) + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + arch/riscv/include/asm/hugetlb.h:14:6: note: previous declaration of 'arch_hugetlb_migration_supported' with type 'bool(struct hstate *)' {aka '_Bool(struct hstate *)'} + 14 | bool arch_hugetlb_migration_supported(struct hstate *h); + | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Reported-by: kernel test robot +Closes: https://lore.kernel.org/oe-kbuild-all/202402110258.CV51JlEI-lkp@intel.com/ +Fixes: ce68c035457b ("riscv: Fix arch_hugetlb_migration_supported() for NAPOT") +Signed-off-by: Alexandre Ghiti +Link: https://lore.kernel.org/r/20240211083640.756583-1-alexghiti@rivosinc.com +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/include/asm/hugetlb.h | 2 ++ + arch/riscv/mm/hugetlbpage.c | 2 ++ + 2 files changed, 4 insertions(+) + +diff --git a/arch/riscv/include/asm/hugetlb.h b/arch/riscv/include/asm/hugetlb.h +index 20f9c3ba23414..22deb7a2a6ec4 100644 +--- a/arch/riscv/include/asm/hugetlb.h ++++ b/arch/riscv/include/asm/hugetlb.h +@@ -11,8 +11,10 @@ static inline void arch_clear_hugepage_flags(struct page *page) + } + #define arch_clear_hugepage_flags arch_clear_hugepage_flags + ++#ifdef CONFIG_ARCH_ENABLE_HUGEPAGE_MIGRATION + bool arch_hugetlb_migration_supported(struct hstate *h); + #define arch_hugetlb_migration_supported arch_hugetlb_migration_supported ++#endif + + #ifdef CONFIG_RISCV_ISA_SVNAPOT + #define __HAVE_ARCH_HUGE_PTE_CLEAR +diff --git a/arch/riscv/mm/hugetlbpage.c b/arch/riscv/mm/hugetlbpage.c +index e7b69281875b2..fbe918801667d 100644 +--- a/arch/riscv/mm/hugetlbpage.c ++++ b/arch/riscv/mm/hugetlbpage.c +@@ -426,10 +426,12 @@ bool __init arch_hugetlb_valid_size(unsigned long size) + return __hugetlb_valid_size(size); + } + ++#ifdef CONFIG_ARCH_ENABLE_HUGEPAGE_MIGRATION + bool arch_hugetlb_migration_supported(struct hstate *h) + { + return __hugetlb_valid_size(huge_page_size(h)); + } ++#endif + + #ifdef CONFIG_CONTIG_ALLOC + static __init int gigantic_pages_init(void) +-- +2.43.0 + diff --git a/queue-6.7/riscv-fix-pte_leaf_size-for-napot.patch b/queue-6.7/riscv-fix-pte_leaf_size-for-napot.patch new file mode 100644 index 00000000000..5cbf964fa17 --- /dev/null +++ b/queue-6.7/riscv-fix-pte_leaf_size-for-napot.patch @@ -0,0 +1,38 @@ +From d3b6b151aee397d8322d393a5392560cb8543f61 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 21:50:16 +0100 +Subject: riscv: Fix pte_leaf_size() for NAPOT + +From: Alexandre Ghiti + +[ Upstream commit e0fe5ab4192c171c111976dbe90bbd37d3976be0 ] + +pte_leaf_size() must be reimplemented to add support for NAPOT mappings. + +Fixes: 82a1a1f3bfb6 ("riscv: mm: support Svnapot in hugetlb page") +Signed-off-by: Alexandre Ghiti +Link: https://lore.kernel.org/r/20240227205016.121901-3-alexghiti@rivosinc.com +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/include/asm/pgtable.h | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h +index 74ffb2178f545..ec8468ddad4a0 100644 +--- a/arch/riscv/include/asm/pgtable.h ++++ b/arch/riscv/include/asm/pgtable.h +@@ -439,6 +439,10 @@ static inline pte_t pte_mkhuge(pte_t pte) + return pte; + } + ++#define pte_leaf_size(pte) (pte_napot(pte) ? \ ++ napot_cont_size(napot_cont_order(pte)) :\ ++ PAGE_SIZE) ++ + #ifdef CONFIG_NUMA_BALANCING + /* + * See the comment in include/asm-generic/pgtable.h +-- +2.43.0 + diff --git a/queue-6.7/riscv-mm-fix-nocache_thead-does-not-set-bit-61-corre.patch b/queue-6.7/riscv-mm-fix-nocache_thead-does-not-set-bit-61-corre.patch new file mode 100644 index 00000000000..e66d2952bb8 --- /dev/null +++ b/queue-6.7/riscv-mm-fix-nocache_thead-does-not-set-bit-61-corre.patch @@ -0,0 +1,43 @@ +From 481d3401bf550153c9a552f712017a12a7618232 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 21 Feb 2024 11:02:31 +0800 +Subject: riscv: mm: fix NOCACHE_THEAD does not set bit[61] correctly + +From: Yangyu Chen + +[ Upstream commit c21f014818600ae017f97ee087e7c136b1916aa7 ] + +Previous commit dbfbda3bd6bf ("riscv: mm: update T-Head memory type +definitions") from patch [1] missed a `<` for bit shifting, result in +bit(61) does not set in _PAGE_NOCACHE_THEAD and leaves bit(0) set instead. +This patch get this fixed. + +Link: https://lore.kernel.org/linux-riscv/20230912072510.2510-1-jszhang@kernel.org/ [1] +Fixes: dbfbda3bd6bf ("riscv: mm: update T-Head memory type definitions") +Signed-off-by: Yangyu Chen +Reviewed-by: Guo Ren +Reviewed-by: Jisheng Zhang +Reviewed-by: Alexandre Ghiti +Link: https://lore.kernel.org/r/tencent_E19FA1A095768063102E654C6FC858A32F06@qq.com +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/include/asm/pgtable-64.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/riscv/include/asm/pgtable-64.h b/arch/riscv/include/asm/pgtable-64.h +index 9a2c780a11e95..783837bbd8783 100644 +--- a/arch/riscv/include/asm/pgtable-64.h ++++ b/arch/riscv/include/asm/pgtable-64.h +@@ -136,7 +136,7 @@ enum napot_cont_order { + * 10010 - IO Strongly-ordered, Non-cacheable, Non-bufferable, Shareable, Non-trustable + */ + #define _PAGE_PMA_THEAD ((1UL << 62) | (1UL << 61) | (1UL << 60)) +-#define _PAGE_NOCACHE_THEAD ((1UL < 61) | (1UL << 60)) ++#define _PAGE_NOCACHE_THEAD ((1UL << 61) | (1UL << 60)) + #define _PAGE_IO_THEAD ((1UL << 63) | (1UL << 60)) + #define _PAGE_MTMASK_THEAD (_PAGE_PMA_THEAD | _PAGE_IO_THEAD | (1UL << 59)) + +-- +2.43.0 + diff --git a/queue-6.7/riscv-sparse-memory-vmemmap-out-of-bounds-fix.patch b/queue-6.7/riscv-sparse-memory-vmemmap-out-of-bounds-fix.patch new file mode 100644 index 00000000000..9f723f0096c --- /dev/null +++ b/queue-6.7/riscv-sparse-memory-vmemmap-out-of-bounds-fix.patch @@ -0,0 +1,50 @@ +From 3be8cc95fa189d09ad7cf1f0cd8619c3256d582c Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 29 Feb 2024 21:17:23 +0200 +Subject: riscv: Sparse-Memory/vmemmap out-of-bounds fix +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Dimitris Vlachos + +[ Upstream commit a11dd49dcb9376776193e15641f84fcc1e5980c9 ] + +Offset vmemmap so that the first page of vmemmap will be mapped +to the first page of physical memory in order to ensure that +vmemmap’s bounds will be respected during +pfn_to_page()/page_to_pfn() operations. +The conversion macros will produce correct SV39/48/57 addresses +for every possible/valid DRAM_BASE inside the physical memory limits. + +v2:Address Alex's comments + +Suggested-by: Alexandre Ghiti +Signed-off-by: Dimitris Vlachos +Reported-by: Dimitris Vlachos +Closes: https://lore.kernel.org/linux-riscv/20240202135030.42265-1-csd4492@csd.uoc.gr +Fixes: d95f1a542c3d ("RISC-V: Implement sparsemem") +Reviewed-by: Alexandre Ghiti +Link: https://lore.kernel.org/r/20240229191723.32779-1-dvlachos@ics.forth.gr +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/include/asm/pgtable.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h +index ec8468ddad4a0..76b131e7bbcad 100644 +--- a/arch/riscv/include/asm/pgtable.h ++++ b/arch/riscv/include/asm/pgtable.h +@@ -84,7 +84,7 @@ + * Define vmemmap for pfn_to_page & page_to_pfn calls. Needed if kernel + * is configured with CONFIG_SPARSEMEM_VMEMMAP enabled. + */ +-#define vmemmap ((struct page *)VMEMMAP_START) ++#define vmemmap ((struct page *)VMEMMAP_START - (phys_ram_base >> PAGE_SHIFT)) + + #define PCI_IO_SIZE SZ_16M + #define PCI_IO_END VMEMMAP_START +-- +2.43.0 + diff --git a/queue-6.7/riscv-tlb-fix-__p-d_free_tlb.patch b/queue-6.7/riscv-tlb-fix-__p-d_free_tlb.patch new file mode 100644 index 00000000000..2216f4a7dfa --- /dev/null +++ b/queue-6.7/riscv-tlb-fix-__p-d_free_tlb.patch @@ -0,0 +1,71 @@ +From 185539bb0b6782c24520bf1c5ef4fd7e124ed827 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 20 Dec 2023 01:50:43 +0800 +Subject: riscv: tlb: fix __p*d_free_tlb() + +From: Jisheng Zhang + +[ Upstream commit 8246601a7d391ce8207408149d65732f28af81a1 ] + +If non-leaf PTEs I.E pmd, pud or p4d is modified, a sfence.vma is +a must for safe, imagine if an implementation caches the non-leaf +translation in TLB, although I didn't meet this HW so far, but it's +possible in theory. + +Signed-off-by: Jisheng Zhang +Fixes: c5e9b2c2ae82 ("riscv: Improve tlb_flush()") +Link: https://lore.kernel.org/r/20231219175046.2496-2-jszhang@kernel.org +Signed-off-by: Palmer Dabbelt +Signed-off-by: Sasha Levin +--- + arch/riscv/include/asm/pgalloc.h | 20 +++++++++++++++++--- + 1 file changed, 17 insertions(+), 3 deletions(-) + +diff --git a/arch/riscv/include/asm/pgalloc.h b/arch/riscv/include/asm/pgalloc.h +index d169a4f41a2e7..c80bb9990d32e 100644 +--- a/arch/riscv/include/asm/pgalloc.h ++++ b/arch/riscv/include/asm/pgalloc.h +@@ -95,7 +95,13 @@ static inline void pud_free(struct mm_struct *mm, pud_t *pud) + __pud_free(mm, pud); + } + +-#define __pud_free_tlb(tlb, pud, addr) pud_free((tlb)->mm, pud) ++#define __pud_free_tlb(tlb, pud, addr) \ ++do { \ ++ if (pgtable_l4_enabled) { \ ++ pagetable_pud_dtor(virt_to_ptdesc(pud)); \ ++ tlb_remove_page_ptdesc((tlb), virt_to_ptdesc(pud)); \ ++ } \ ++} while (0) + + #define p4d_alloc_one p4d_alloc_one + static inline p4d_t *p4d_alloc_one(struct mm_struct *mm, unsigned long addr) +@@ -124,7 +130,11 @@ static inline void p4d_free(struct mm_struct *mm, p4d_t *p4d) + __p4d_free(mm, p4d); + } + +-#define __p4d_free_tlb(tlb, p4d, addr) p4d_free((tlb)->mm, p4d) ++#define __p4d_free_tlb(tlb, p4d, addr) \ ++do { \ ++ if (pgtable_l5_enabled) \ ++ tlb_remove_page_ptdesc((tlb), virt_to_ptdesc(p4d)); \ ++} while (0) + #endif /* __PAGETABLE_PMD_FOLDED */ + + static inline void sync_kernel_mappings(pgd_t *pgd) +@@ -149,7 +159,11 @@ static inline pgd_t *pgd_alloc(struct mm_struct *mm) + + #ifndef __PAGETABLE_PMD_FOLDED + +-#define __pmd_free_tlb(tlb, pmd, addr) pmd_free((tlb)->mm, pmd) ++#define __pmd_free_tlb(tlb, pmd, addr) \ ++do { \ ++ pagetable_pmd_dtor(virt_to_ptdesc(pmd)); \ ++ tlb_remove_page_ptdesc((tlb), virt_to_ptdesc(pmd)); \ ++} while (0) + + #endif /* __PAGETABLE_PMD_FOLDED */ + +-- +2.43.0 + diff --git a/queue-6.7/rtnetlink-fix-error-logic-of-ifla_bridge_flags-writi.patch b/queue-6.7/rtnetlink-fix-error-logic-of-ifla_bridge_flags-writi.patch new file mode 100644 index 00000000000..fb97513df37 --- /dev/null +++ b/queue-6.7/rtnetlink-fix-error-logic-of-ifla_bridge_flags-writi.patch @@ -0,0 +1,83 @@ +From 4c169ea53c1f036161929019d5364c33ba0ec168 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 27 Feb 2024 20:11:28 +0800 +Subject: rtnetlink: fix error logic of IFLA_BRIDGE_FLAGS writing back + +From: Lin Ma + +[ Upstream commit 743ad091fb46e622f1b690385bb15e3cd3daf874 ] + +In the commit d73ef2d69c0d ("rtnetlink: let rtnl_bridge_setlink checks +IFLA_BRIDGE_MODE length"), an adjustment was made to the old loop logic +in the function `rtnl_bridge_setlink` to enable the loop to also check +the length of the IFLA_BRIDGE_MODE attribute. However, this adjustment +removed the `break` statement and led to an error logic of the flags +writing back at the end of this function. + +if (have_flags) + memcpy(nla_data(attr), &flags, sizeof(flags)); + // attr should point to IFLA_BRIDGE_FLAGS NLA !!! + +Before the mentioned commit, the `attr` is granted to be IFLA_BRIDGE_FLAGS. +However, this is not necessarily true fow now as the updated loop will let +the attr point to the last NLA, even an invalid NLA which could cause +overflow writes. + +This patch introduces a new variable `br_flag` to save the NLA pointer +that points to IFLA_BRIDGE_FLAGS and uses it to resolve the mentioned +error logic. + +Fixes: d73ef2d69c0d ("rtnetlink: let rtnl_bridge_setlink checks IFLA_BRIDGE_MODE length") +Signed-off-by: Lin Ma +Acked-by: Nikolay Aleksandrov +Link: https://lore.kernel.org/r/20240227121128.608110-1-linma@zju.edu.cn +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/core/rtnetlink.c | 11 +++++------ + 1 file changed, 5 insertions(+), 6 deletions(-) + +diff --git a/net/core/rtnetlink.c b/net/core/rtnetlink.c +index bf4c3f65ad99c..8f9cd6b7926e3 100644 +--- a/net/core/rtnetlink.c ++++ b/net/core/rtnetlink.c +@@ -5164,10 +5164,9 @@ static int rtnl_bridge_setlink(struct sk_buff *skb, struct nlmsghdr *nlh, + struct net *net = sock_net(skb->sk); + struct ifinfomsg *ifm; + struct net_device *dev; +- struct nlattr *br_spec, *attr = NULL; ++ struct nlattr *br_spec, *attr, *br_flags_attr = NULL; + int rem, err = -EOPNOTSUPP; + u16 flags = 0; +- bool have_flags = false; + + if (nlmsg_len(nlh) < sizeof(*ifm)) + return -EINVAL; +@@ -5185,11 +5184,11 @@ static int rtnl_bridge_setlink(struct sk_buff *skb, struct nlmsghdr *nlh, + br_spec = nlmsg_find_attr(nlh, sizeof(struct ifinfomsg), IFLA_AF_SPEC); + if (br_spec) { + nla_for_each_nested(attr, br_spec, rem) { +- if (nla_type(attr) == IFLA_BRIDGE_FLAGS && !have_flags) { ++ if (nla_type(attr) == IFLA_BRIDGE_FLAGS && !br_flags_attr) { + if (nla_len(attr) < sizeof(flags)) + return -EINVAL; + +- have_flags = true; ++ br_flags_attr = attr; + flags = nla_get_u16(attr); + } + +@@ -5233,8 +5232,8 @@ static int rtnl_bridge_setlink(struct sk_buff *skb, struct nlmsghdr *nlh, + } + } + +- if (have_flags) +- memcpy(nla_data(attr), &flags, sizeof(flags)); ++ if (br_flags_attr) ++ memcpy(nla_data(br_flags_attr), &flags, sizeof(flags)); + out: + return err; + } +-- +2.43.0 + diff --git a/queue-6.7/series b/queue-6.7/series index c786fde6fb4..62260304a01 100644 --- a/queue-6.7/series +++ b/queue-6.7/series @@ -1 +1,72 @@ btrfs-fix-deadlock-with-fiemap-and-extent-locking.patch +mtd-spinand-gigadevice-fix-the-get-ecc-status-issue.patch +ice-fix-connection-state-of-dpll-and-out-pin.patch +ice-fix-dpll-input-pin-phase_adjust-value-updates.patch +ice-fix-dpll-and-dpll_pin-data-access-on-pf-reset.patch +ice-fix-dpll-periodic-work-data-updates-on-pf-reset.patch +ice-fix-pin-phase-adjust-updates-on-pf-reset.patch +spi-cadence-qspi-fix-pointer-reference-in-runtime-pm.patch +spi-cadence-qspi-remove-system-wide-suspend-helper-c.patch +netlink-fix-kernel-infoleak-after-free-in-__skb_data.patch +netlink-add-nla-be16-32-types-to-minlen-array.patch +net-ip_tunnel-prevent-perpetual-headroom-growth.patch +net-mctp-take-ownership-of-skb-in-mctp_local_output.patch +net-dpaa-fman_memac-accept-phy-interface-type-10gbas.patch +tun-fix-xdp_rxq_info-s-queue_index-when-detaching.patch +cpufreq-intel_pstate-fix-pstate-limits-enforcement-f.patch +net-veth-clear-gro-when-clearing-xdp-even-when-down.patch +ipv6-fix-potential-struct-net-leak-in-inet6_rtm_geta.patch +lan78xx-enable-auto-speed-configuration-for-lan7850-.patch +veth-try-harder-when-allocating-queue-memory.patch +net-usb-dm9601-fix-wrong-return-value-in-dm9601_mdio.patch +net-lan78xx-fix-softirq-work-is-pending-error.patch +uapi-in6-replace-temporary-label-with-rfc9486.patch +stmmac-clear-variable-when-destroying-workqueue.patch +bluetooth-hci_sync-check-the-correct-flag-before-sta.patch +bluetooth-avoid-potential-use-after-free-in-hci_erro.patch +bluetooth-hci_sync-fix-accept_list-when-attempting-t.patch +bluetooth-hci_event-fix-wrongly-recorded-wakeup-bd_a.patch +bluetooth-hci_event-fix-handling-of-hci_ev_io_capa_r.patch +bluetooth-enforce-validation-on-max-value-of-connect.patch +bluetooth-qca-fix-wrong-event-type-for-patch-config-.patch +bluetooth-hci_qca-set-bda-quirk-bit-if-fwnode-exists.patch +bluetooth-qca-fix-triggering-coredump-implementation.patch +netfilter-nf_tables-allow-nfproto_inet-in-nft_-match.patch +netfilter-bridge-confirm-multicast-packets-before-pa.patch +tools-ynl-fix-handling-of-multiple-mcast-groups.patch +rtnetlink-fix-error-logic-of-ifla_bridge_flags-writi.patch +igb-extend-ptp-timestamp-adjustments-to-i211.patch +net-hsr-use-correct-offset-for-hsr-tlv-values-in-sup.patch +tls-decrement-decrypt_pending-if-no-async-completion.patch +tls-fix-peeking-with-sync-async-decryption.patch +tls-separate-no-async-decryption-request-handling-fr.patch +tls-fix-use-after-free-on-failed-backlog-decryption.patch +riscv-tlb-fix-__p-d_free_tlb.patch +efi-capsule-loader-fix-incorrect-allocation-size.patch +power-supply-bq27xxx-i2c-do-not-free-non-existing-ir.patch +asoc-cs35l56-must-clear-halo_state-before-issuing-sy.patch +alsa-drop-leftover-snd-rtctimer-stuff-from-makefile.patch +asoc-qcom-fix-uninitialized-pointer-dmactl.patch +gpu-host1x-skip-reset-assert-on-tegra186.patch +riscv-mm-fix-nocache_thead-does-not-set-bit-61-corre.patch +riscv-fix-build-error-if-config_arch_enable_hugepage.patch +asoc-cs35l56-cs35l56_component_remove-must-clear-cs3.patch +asoc-cs35l56-cs35l56_component_remove-must-clean-up-.patch +asoc-cs35l56-don-t-add-the-same-register-patch-multi.patch +asoc-cs35l56-fix-for-initializing-asp1-mixer-registe.patch +asoc-cs35l56-fix-misuse-of-wm_adsp-part-string-for-s.patch +asoc-cs35l56-fix-deadlock-in-asp1-mixer-register-ini.patch +asoc-soc-card-fix-missing-locking-in-snd_soc_card_ge.patch +risc-v-ignore-v-from-the-riscv-isa-dt-property-on-ol.patch +drm-tegra-remove-existing-framebuffer-only-if-we-sup.patch +fbcon-always-restore-the-old-font-data-in-fbcon_do_s.patch +afs-fix-endless-loop-in-directory-parsing.patch +drm-amd-display-prevent-potential-buffer-overflow-in.patch +drivers-perf-added-capabilities-for-legacy-pmu.patch +drivers-perf-ctr_get_width-function-for-legacy-is-no.patch +revert-riscv-mm-support-svnapot-in-huge-vmap.patch +riscv-fix-pte_leaf_size-for-napot.patch +riscv-sparse-memory-vmemmap-out-of-bounds-fix.patch +btrfs-fix-race-between-ordered-extent-completion-and.patch +drm-nouveau-keep-dma-buffers-required-for-suspend-re.patch +of-property-fw_devlink-fix-stupid-bug-in-remote-endp.patch diff --git a/queue-6.7/spi-cadence-qspi-fix-pointer-reference-in-runtime-pm.patch b/queue-6.7/spi-cadence-qspi-fix-pointer-reference-in-runtime-pm.patch new file mode 100644 index 00000000000..f8458425512 --- /dev/null +++ b/queue-6.7/spi-cadence-qspi-fix-pointer-reference-in-runtime-pm.patch @@ -0,0 +1,65 @@ +From 401c42fc8d0b2faa3a307fe60087c33015e7a561 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 11:12:29 +0100 +Subject: spi: cadence-qspi: fix pointer reference in runtime PM hooks +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Théo Lebrun + +[ Upstream commit 32ce3bb57b6b402de2aec1012511e7ac4e7449dc ] + +dev_get_drvdata() gets used to acquire the pointer to cqspi and the SPI +controller. Neither embed the other; this lead to memory corruption. + +On a given platform (Mobileye EyeQ5) the memory corruption is hidden +inside cqspi->f_pdata. Also, this uninitialised memory is used as a +mutex (ctlr->bus_lock_mutex) by spi_controller_suspend(). + +Fixes: 2087e85bb66e ("spi: cadence-quadspi: fix suspend-resume implementations") +Reviewed-by: Dhruva Gole +Signed-off-by: Théo Lebrun +Link: https://msgid.link/r/20240222-cdns-qspi-pm-fix-v4-1-6b6af8bcbf59@bootlin.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + drivers/spi/spi-cadence-quadspi.c | 6 ++---- + 1 file changed, 2 insertions(+), 4 deletions(-) + +diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-quadspi.c +index f94e0d370d466..0d184d65dce76 100644 +--- a/drivers/spi/spi-cadence-quadspi.c ++++ b/drivers/spi/spi-cadence-quadspi.c +@@ -1930,10 +1930,9 @@ static void cqspi_remove(struct platform_device *pdev) + static int cqspi_suspend(struct device *dev) + { + struct cqspi_st *cqspi = dev_get_drvdata(dev); +- struct spi_controller *host = dev_get_drvdata(dev); + int ret; + +- ret = spi_controller_suspend(host); ++ ret = spi_controller_suspend(cqspi->host); + cqspi_controller_enable(cqspi, 0); + + clk_disable_unprepare(cqspi->clk); +@@ -1944,7 +1943,6 @@ static int cqspi_suspend(struct device *dev) + static int cqspi_resume(struct device *dev) + { + struct cqspi_st *cqspi = dev_get_drvdata(dev); +- struct spi_controller *host = dev_get_drvdata(dev); + + clk_prepare_enable(cqspi->clk); + cqspi_wait_idle(cqspi); +@@ -1953,7 +1951,7 @@ static int cqspi_resume(struct device *dev) + cqspi->current_cs = -1; + cqspi->sclk = 0; + +- return spi_controller_resume(host); ++ return spi_controller_resume(cqspi->host); + } + + static DEFINE_RUNTIME_DEV_PM_OPS(cqspi_dev_pm_ops, cqspi_suspend, +-- +2.43.0 + diff --git a/queue-6.7/spi-cadence-qspi-remove-system-wide-suspend-helper-c.patch b/queue-6.7/spi-cadence-qspi-remove-system-wide-suspend-helper-c.patch new file mode 100644 index 00000000000..425de321402 --- /dev/null +++ b/queue-6.7/spi-cadence-qspi-remove-system-wide-suspend-helper-c.patch @@ -0,0 +1,89 @@ +From 2d34ae58d5afe88d58b8dc5489cad4ffb319cc7b Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Thu, 22 Feb 2024 11:12:30 +0100 +Subject: spi: cadence-qspi: remove system-wide suspend helper calls from + runtime PM hooks +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +From: Théo Lebrun + +[ Upstream commit 959043afe53ae80633e810416cee6076da6e91c6 ] + +The ->runtime_suspend() and ->runtime_resume() callbacks are not +expected to call spi_controller_suspend() and spi_controller_resume(). +Remove calls to those in the cadence-qspi driver. + +Those helpers have two roles currently: + - They stop/start the queue, including dealing with the kworker. + - They toggle the SPI controller SPI_CONTROLLER_SUSPENDED flag. It + requires acquiring ctlr->bus_lock_mutex. + +Step one is irrelevant because cadence-qspi is not queued. Step two +however has two implications: + - A deadlock occurs, because ->runtime_resume() is called in a context + where the lock is already taken (in the ->exec_op() callback, where + the usage count is incremented). + - It would disallow all operations once the device is auto-suspended. + +Here is a brief call tree highlighting the mutex deadlock: + +spi_mem_exec_op() + ... + spi_mem_access_start() + mutex_lock(&ctlr->bus_lock_mutex) + + cqspi_exec_mem_op() + pm_runtime_resume_and_get() + cqspi_resume() + spi_controller_resume() + mutex_lock(&ctlr->bus_lock_mutex) + ... + + spi_mem_access_end() + mutex_unlock(&ctlr->bus_lock_mutex) + ... + +Fixes: 0578a6dbfe75 ("spi: spi-cadence-quadspi: add runtime pm support") +Signed-off-by: Théo Lebrun +Link: https://msgid.link/r/20240222-cdns-qspi-pm-fix-v4-2-6b6af8bcbf59@bootlin.com +Signed-off-by: Mark Brown +Signed-off-by: Sasha Levin +--- + drivers/spi/spi-cadence-quadspi.c | 9 ++------- + 1 file changed, 2 insertions(+), 7 deletions(-) + +diff --git a/drivers/spi/spi-cadence-quadspi.c b/drivers/spi/spi-cadence-quadspi.c +index 0d184d65dce76..731775d34d393 100644 +--- a/drivers/spi/spi-cadence-quadspi.c ++++ b/drivers/spi/spi-cadence-quadspi.c +@@ -1930,14 +1930,10 @@ static void cqspi_remove(struct platform_device *pdev) + static int cqspi_suspend(struct device *dev) + { + struct cqspi_st *cqspi = dev_get_drvdata(dev); +- int ret; + +- ret = spi_controller_suspend(cqspi->host); + cqspi_controller_enable(cqspi, 0); +- + clk_disable_unprepare(cqspi->clk); +- +- return ret; ++ return 0; + } + + static int cqspi_resume(struct device *dev) +@@ -1950,8 +1946,7 @@ static int cqspi_resume(struct device *dev) + + cqspi->current_cs = -1; + cqspi->sclk = 0; +- +- return spi_controller_resume(cqspi->host); ++ return 0; + } + + static DEFINE_RUNTIME_DEV_PM_OPS(cqspi_dev_pm_ops, cqspi_suspend, +-- +2.43.0 + diff --git a/queue-6.7/stmmac-clear-variable-when-destroying-workqueue.patch b/queue-6.7/stmmac-clear-variable-when-destroying-workqueue.patch new file mode 100644 index 00000000000..ee36406d864 --- /dev/null +++ b/queue-6.7/stmmac-clear-variable-when-destroying-workqueue.patch @@ -0,0 +1,83 @@ +From 9ec36d8c21e7e96a4065dd440d8f027edd73d6db Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 26 Feb 2024 17:42:32 +0100 +Subject: stmmac: Clear variable when destroying workqueue + +From: Jakub Raczynski + +[ Upstream commit 8af411bbba1f457c33734795f024d0ef26d0963f ] + +Currently when suspending driver and stopping workqueue it is checked whether +workqueue is not NULL and if so, it is destroyed. +Function destroy_workqueue() does drain queue and does clear variable, but +it does not set workqueue variable to NULL. This can cause kernel/module +panic if code attempts to clear workqueue that was not initialized. + +This scenario is possible when resuming suspended driver in stmmac_resume(), +because there is no handling for failed stmmac_hw_setup(), +which can fail and return if DMA engine has failed to initialize, +and workqueue is initialized after DMA engine. +Should DMA engine fail to initialize, resume will proceed normally, +but interface won't work and TX queue will eventually timeout, +causing 'Reset adapter' error. +This then does destroy workqueue during reset process. +And since workqueue is initialized after DMA engine and can be skipped, +it will cause kernel/module panic. + +To secure against this possible crash, set workqueue variable to NULL when +destroying workqueue. + +Log/backtrace from crash goes as follows: +[88.031977]------------[ cut here ]------------ +[88.031985]NETDEV WATCHDOG: eth0 (sxgmac): transmit queue 1 timed out +[88.032017]WARNING: CPU: 0 PID: 0 at net/sched/sch_generic.c:477 dev_watchdog+0x390/0x398 + +[88.032251]---[ end trace e70de432e4d5c2c0 ]--- +[88.032282]sxgmac 16d88000.ethernet eth0: Reset adapter. +[88.036359]------------[ cut here ]------------ +[88.036519]Call trace: +[88.036523] flush_workqueue+0x3e4/0x430 +[88.036528] drain_workqueue+0xc4/0x160 +[88.036533] destroy_workqueue+0x40/0x270 +[88.036537] stmmac_fpe_stop_wq+0x4c/0x70 +[88.036541] stmmac_release+0x278/0x280 +[88.036546] __dev_close_many+0xcc/0x158 +[88.036551] dev_close_many+0xbc/0x190 +[88.036555] dev_close.part.0+0x70/0xc0 +[88.036560] dev_close+0x24/0x30 +[88.036564] stmmac_service_task+0x110/0x140 +[88.036569] process_one_work+0x1d8/0x4a0 +[88.036573] worker_thread+0x54/0x408 +[88.036578] kthread+0x164/0x170 +[88.036583] ret_from_fork+0x10/0x20 +[88.036588]---[ end trace e70de432e4d5c2c1 ]--- +[88.036597]Unable to handle kernel NULL pointer dereference at virtual address 0000000000000004 + +Fixes: 5a5586112b929 ("net: stmmac: support FPE link partner hand-shaking procedure") +Signed-off-by: Jakub Raczynski +Reviewed-by: Jiri Pirko +Signed-off-by: David S. Miller +Signed-off-by: Sasha Levin +--- + drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +index e9a1b60ebb503..de4d769195174 100644 +--- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c ++++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +@@ -3942,8 +3942,10 @@ static void stmmac_fpe_stop_wq(struct stmmac_priv *priv) + { + set_bit(__FPE_REMOVING, &priv->fpe_task_state); + +- if (priv->fpe_wq) ++ if (priv->fpe_wq) { + destroy_workqueue(priv->fpe_wq); ++ priv->fpe_wq = NULL; ++ } + + netdev_info(priv->dev, "FPE workqueue stop"); + } +-- +2.43.0 + diff --git a/queue-6.7/tls-decrement-decrypt_pending-if-no-async-completion.patch b/queue-6.7/tls-decrement-decrypt_pending-if-no-async-completion.patch new file mode 100644 index 00000000000..be8e1b87548 --- /dev/null +++ b/queue-6.7/tls-decrement-decrypt_pending-if-no-async-completion.patch @@ -0,0 +1,42 @@ +From 03e9f590f26218cbe1c817338e5616a632b4c6e8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Feb 2024 23:43:57 +0100 +Subject: tls: decrement decrypt_pending if no async completion will be called + +From: Sabrina Dubroca + +[ Upstream commit f7fa16d49837f947ee59492958f9e6f0e51d9a78 ] + +With mixed sync/async decryption, or failures of crypto_aead_decrypt, +we increment decrypt_pending but we never do the corresponding +decrement since tls_decrypt_done will not be called. In this case, we +should decrement decrypt_pending immediately to avoid getting stuck. + +For example, the prequeue prequeue test gets stuck with mixed +modes (one async decrypt + one sync decrypt). + +Fixes: 94524d8fc965 ("net/tls: Add support for async decryption of tls records") +Signed-off-by: Sabrina Dubroca +Link: https://lore.kernel.org/r/c56d5fc35543891d5319f834f25622360e1bfbec.1709132643.git.sd@queasysnail.net +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/tls/tls_sw.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/net/tls/tls_sw.c b/net/tls/tls_sw.c +index de96959336c48..9f23ba321efe6 100644 +--- a/net/tls/tls_sw.c ++++ b/net/tls/tls_sw.c +@@ -289,6 +289,8 @@ static int tls_do_decryption(struct sock *sk, + return 0; + + ret = crypto_wait_req(ret, &ctx->async_wait); ++ } else if (darg->async) { ++ atomic_dec(&ctx->decrypt_pending); + } + darg->async = false; + +-- +2.43.0 + diff --git a/queue-6.7/tls-fix-peeking-with-sync-async-decryption.patch b/queue-6.7/tls-fix-peeking-with-sync-async-decryption.patch new file mode 100644 index 00000000000..fc1d09344bf --- /dev/null +++ b/queue-6.7/tls-fix-peeking-with-sync-async-decryption.patch @@ -0,0 +1,72 @@ +From 8ec2e65fc9e163fdad06989ce7c62548954b7a3e Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Feb 2024 23:43:58 +0100 +Subject: tls: fix peeking with sync+async decryption + +From: Sabrina Dubroca + +[ Upstream commit 6caaf104423d809b49a67ee6500191d063b40dc6 ] + +If we peek from 2 records with a currently empty rx_list, and the +first record is decrypted synchronously but the second record is +decrypted async, the following happens: + 1. decrypt record 1 (sync) + 2. copy from record 1 to the userspace's msg + 3. queue the decrypted record to rx_list for future read(!PEEK) + 4. decrypt record 2 (async) + 5. queue record 2 to rx_list + 6. call process_rx_list to copy data from the 2nd record + +We currently pass copied=0 as skip offset to process_rx_list, so we +end up copying once again from the first record. We should skip over +the data we've already copied. + +Seen with selftest tls.12_aes_gcm.recv_peek_large_buf_mult_recs + +Fixes: 692d7b5d1f91 ("tls: Fix recvmsg() to be able to peek across multiple records") +Signed-off-by: Sabrina Dubroca +Link: https://lore.kernel.org/r/1b132d2b2b99296bfde54e8a67672d90d6d16e71.1709132643.git.sd@queasysnail.net +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/tls/tls_sw.c | 9 ++++++--- + 1 file changed, 6 insertions(+), 3 deletions(-) + +diff --git a/net/tls/tls_sw.c b/net/tls/tls_sw.c +index 9f23ba321efe6..1394fc44f3788 100644 +--- a/net/tls/tls_sw.c ++++ b/net/tls/tls_sw.c +@@ -1950,6 +1950,7 @@ int tls_sw_recvmsg(struct sock *sk, + struct strp_msg *rxm; + struct tls_msg *tlm; + ssize_t copied = 0; ++ ssize_t peeked = 0; + bool async = false; + int target, err; + bool is_kvec = iov_iter_is_kvec(&msg->msg_iter); +@@ -2097,8 +2098,10 @@ int tls_sw_recvmsg(struct sock *sk, + if (err < 0) + goto put_on_rx_list_err; + +- if (is_peek) ++ if (is_peek) { ++ peeked += chunk; + goto put_on_rx_list; ++ } + + if (partially_consumed) { + rxm->offset += chunk; +@@ -2137,8 +2140,8 @@ int tls_sw_recvmsg(struct sock *sk, + + /* Drain records from the rx_list & copy if required */ + if (is_peek || is_kvec) +- err = process_rx_list(ctx, msg, &control, copied, +- decrypted, is_peek, NULL); ++ err = process_rx_list(ctx, msg, &control, copied + peeked, ++ decrypted - peeked, is_peek, NULL); + else + err = process_rx_list(ctx, msg, &control, 0, + async_copy_bytes, is_peek, NULL); +-- +2.43.0 + diff --git a/queue-6.7/tls-fix-use-after-free-on-failed-backlog-decryption.patch b/queue-6.7/tls-fix-use-after-free-on-failed-backlog-decryption.patch new file mode 100644 index 00000000000..69f1e95c837 --- /dev/null +++ b/queue-6.7/tls-fix-use-after-free-on-failed-backlog-decryption.patch @@ -0,0 +1,94 @@ +From 4867fcabeff59551e125bbc057c72e230550a1ad Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Feb 2024 23:44:00 +0100 +Subject: tls: fix use-after-free on failed backlog decryption + +From: Sabrina Dubroca + +[ Upstream commit 13114dc5543069f7b97991e3b79937b6da05f5b0 ] + +When the decrypt request goes to the backlog and crypto_aead_decrypt +returns -EBUSY, tls_do_decryption will wait until all async +decryptions have completed. If one of them fails, tls_do_decryption +will return -EBADMSG and tls_decrypt_sg jumps to the error path, +releasing all the pages. But the pages have been passed to the async +callback, and have already been released by tls_decrypt_done. + +The only true async case is when crypto_aead_decrypt returns + -EINPROGRESS. With -EBUSY, we already waited so we can tell +tls_sw_recvmsg that the data is available for immediate copy, but we +need to notify tls_decrypt_sg (via the new ->async_done flag) that the +memory has already been released. + +Fixes: 859054147318 ("net: tls: handle backlogging of crypto requests") +Signed-off-by: Sabrina Dubroca +Link: https://lore.kernel.org/r/4755dd8d9bebdefaa19ce1439b833d6199d4364c.1709132643.git.sd@queasysnail.net +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + net/tls/tls_sw.c | 24 +++++++++++++++++------- + 1 file changed, 17 insertions(+), 7 deletions(-) + +diff --git a/net/tls/tls_sw.c b/net/tls/tls_sw.c +index 1fd37fe13ffd8..211f57164cb61 100644 +--- a/net/tls/tls_sw.c ++++ b/net/tls/tls_sw.c +@@ -52,6 +52,7 @@ struct tls_decrypt_arg { + struct_group(inargs, + bool zc; + bool async; ++ bool async_done; + u8 tail; + ); + +@@ -286,15 +287,18 @@ static int tls_do_decryption(struct sock *sk, + } + + ret = crypto_aead_decrypt(aead_req); ++ if (ret == -EINPROGRESS) ++ return 0; ++ + if (ret == -EBUSY) { + ret = tls_decrypt_async_wait(ctx); +- ret = ret ?: -EINPROGRESS; +- } +- if (ret == -EINPROGRESS) { +- return 0; +- } else if (darg->async) { +- atomic_dec(&ctx->decrypt_pending); ++ darg->async_done = true; ++ /* all completions have run, we're not doing async anymore */ ++ darg->async = false; ++ return ret; + } ++ ++ atomic_dec(&ctx->decrypt_pending); + darg->async = false; + + return ret; +@@ -1593,8 +1597,11 @@ static int tls_decrypt_sg(struct sock *sk, struct iov_iter *out_iov, + /* Prepare and submit AEAD request */ + err = tls_do_decryption(sk, sgin, sgout, dctx->iv, + data_len + prot->tail_size, aead_req, darg); +- if (err) ++ if (err) { ++ if (darg->async_done) ++ goto exit_free_skb; + goto exit_free_pages; ++ } + + darg->skb = clear_skb ?: tls_strp_msg(ctx); + clear_skb = NULL; +@@ -1606,6 +1613,9 @@ static int tls_decrypt_sg(struct sock *sk, struct iov_iter *out_iov, + return err; + } + ++ if (unlikely(darg->async_done)) ++ return 0; ++ + if (prot->tail_size) + darg->tail = dctx->tail; + +-- +2.43.0 + diff --git a/queue-6.7/tls-separate-no-async-decryption-request-handling-fr.patch b/queue-6.7/tls-separate-no-async-decryption-request-handling-fr.patch new file mode 100644 index 00000000000..c949b60b30d --- /dev/null +++ b/queue-6.7/tls-separate-no-async-decryption-request-handling-fr.patch @@ -0,0 +1,64 @@ +From 10b947c0cc5b738af12fb78443520b235d9ab1a7 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Wed, 28 Feb 2024 23:43:59 +0100 +Subject: tls: separate no-async decryption request handling from async + +From: Sabrina Dubroca + +[ Upstream commit 41532b785e9d79636b3815a64ddf6a096647d011 ] + +If we're not doing async, the handling is much simpler. There's no +reference counting, we just need to wait for the completion to wake us +up and return its result. + +We should preferably also use a separate crypto_wait. I'm not seeing a +UAF as I did in the past, I think aec7961916f3 ("tls: fix race between +async notify and socket close") took care of it. + +This will make the next fix easier. + +Signed-off-by: Sabrina Dubroca +Link: https://lore.kernel.org/r/47bde5f649707610eaef9f0d679519966fc31061.1709132643.git.sd@queasysnail.net +Signed-off-by: Jakub Kicinski +Stable-dep-of: 13114dc55430 ("tls: fix use-after-free on failed backlog decryption") +Signed-off-by: Sasha Levin +--- + net/tls/tls_sw.c | 13 ++++++++----- + 1 file changed, 8 insertions(+), 5 deletions(-) + +diff --git a/net/tls/tls_sw.c b/net/tls/tls_sw.c +index 1394fc44f3788..1fd37fe13ffd8 100644 +--- a/net/tls/tls_sw.c ++++ b/net/tls/tls_sw.c +@@ -274,9 +274,15 @@ static int tls_do_decryption(struct sock *sk, + DEBUG_NET_WARN_ON_ONCE(atomic_read(&ctx->decrypt_pending) < 1); + atomic_inc(&ctx->decrypt_pending); + } else { ++ DECLARE_CRYPTO_WAIT(wait); ++ + aead_request_set_callback(aead_req, + CRYPTO_TFM_REQ_MAY_BACKLOG, +- crypto_req_done, &ctx->async_wait); ++ crypto_req_done, &wait); ++ ret = crypto_aead_decrypt(aead_req); ++ if (ret == -EINPROGRESS || ret == -EBUSY) ++ ret = crypto_wait_req(ret, &wait); ++ return ret; + } + + ret = crypto_aead_decrypt(aead_req); +@@ -285,10 +291,7 @@ static int tls_do_decryption(struct sock *sk, + ret = ret ?: -EINPROGRESS; + } + if (ret == -EINPROGRESS) { +- if (darg->async) +- return 0; +- +- ret = crypto_wait_req(ret, &ctx->async_wait); ++ return 0; + } else if (darg->async) { + atomic_dec(&ctx->decrypt_pending); + } +-- +2.43.0 + diff --git a/queue-6.7/tools-ynl-fix-handling-of-multiple-mcast-groups.patch b/queue-6.7/tools-ynl-fix-handling-of-multiple-mcast-groups.patch new file mode 100644 index 00000000000..191ac38ea4f --- /dev/null +++ b/queue-6.7/tools-ynl-fix-handling-of-multiple-mcast-groups.patch @@ -0,0 +1,48 @@ +From c3a370fe39d2215dfb4ab7a72e558308de7e59b8 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 26 Feb 2024 13:40:18 -0800 +Subject: tools: ynl: fix handling of multiple mcast groups + +From: Jakub Kicinski + +[ Upstream commit b6c65eb20ffa8e3bd89f551427dbeee2876d72ca ] + +We never increment the group number iterator, so all groups +get recorded into index 0 of the mcast_groups[] array. + +As a result YNL can only handle using the last group. +For example using the "netdev" sample on kernel with +page pool commands results in: + + $ ./samples/netdev + YNL: Multicast group 'mgmt' not found + +Most families have only one multicast group, so this hasn't +been noticed. Plus perhaps developers usually test the last +group which would have worked. + +Fixes: 86878f14d71a ("tools: ynl: user space helpers") +Reviewed-by: Donald Hunter +Acked-by: Nicolas Dichtel +Link: https://lore.kernel.org/r/20240226214019.1255242-1-kuba@kernel.org +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + tools/net/ynl/lib/ynl.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/tools/net/ynl/lib/ynl.c b/tools/net/ynl/lib/ynl.c +index 591f5f50ddaab..2aa19004fa0cf 100644 +--- a/tools/net/ynl/lib/ynl.c ++++ b/tools/net/ynl/lib/ynl.c +@@ -519,6 +519,7 @@ ynl_get_family_info_mcast(struct ynl_sock *ys, const struct nlattr *mcasts) + ys->mcast_groups[i].name[GENL_NAMSIZ - 1] = 0; + } + } ++ i++; + } + + return 0; +-- +2.43.0 + diff --git a/queue-6.7/tun-fix-xdp_rxq_info-s-queue_index-when-detaching.patch b/queue-6.7/tun-fix-xdp_rxq_info-s-queue_index-when-detaching.patch new file mode 100644 index 00000000000..f9c71d0ac78 --- /dev/null +++ b/queue-6.7/tun-fix-xdp_rxq_info-s-queue_index-when-detaching.patch @@ -0,0 +1,36 @@ +From 840674561910430eb8f271402d54b75241f48956 Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Tue, 20 Feb 2024 11:12:07 +0800 +Subject: tun: Fix xdp_rxq_info's queue_index when detaching + +From: Yunjian Wang + +[ Upstream commit 2a770cdc4382b457ca3d43d03f0f0064f905a0d0 ] + +When a queue(tfile) is detached, we only update tfile's queue_index, +but do not update xdp_rxq_info's queue_index. This patch fixes it. + +Fixes: 8bf5c4ee1889 ("tun: setup xdp_rxq_info") +Signed-off-by: Yunjian Wang +Link: https://lore.kernel.org/r/1708398727-46308-1-git-send-email-wangyunjian@huawei.com +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + drivers/net/tun.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/net/tun.c b/drivers/net/tun.c +index 4a4f8c8e79fa1..8f95a562b8d0c 100644 +--- a/drivers/net/tun.c ++++ b/drivers/net/tun.c +@@ -653,6 +653,7 @@ static void __tun_detach(struct tun_file *tfile, bool clean) + tun->tfiles[tun->numqueues - 1]); + ntfile = rtnl_dereference(tun->tfiles[index]); + ntfile->queue_index = index; ++ ntfile->xdp_rxq.queue_index = index; + rcu_assign_pointer(tun->tfiles[tun->numqueues - 1], + NULL); + +-- +2.43.0 + diff --git a/queue-6.7/uapi-in6-replace-temporary-label-with-rfc9486.patch b/queue-6.7/uapi-in6-replace-temporary-label-with-rfc9486.patch new file mode 100644 index 00000000000..f52586d143c --- /dev/null +++ b/queue-6.7/uapi-in6-replace-temporary-label-with-rfc9486.patch @@ -0,0 +1,39 @@ +From 18cfadcc879fb50e326f73c2feb3478f0dd9cfde Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Mon, 26 Feb 2024 13:49:21 +0100 +Subject: uapi: in6: replace temporary label with rfc9486 + +From: Justin Iurman + +[ Upstream commit 6a2008641920a9c6fe1abbeb9acbec463215d505 ] + +Not really a fix per se, but IPV6_TLV_IOAM is still tagged as "TEMPORARY +IANA allocation for IOAM", while RFC 9486 is available for some time +now. Just update the reference. + +Fixes: 9ee11f0fff20 ("ipv6: ioam: Data plane support for Pre-allocated Trace") +Signed-off-by: Justin Iurman +Reviewed-by: Simon Horman +Link: https://lore.kernel.org/r/20240226124921.9097-1-justin.iurman@uliege.be +Signed-off-by: Jakub Kicinski +Signed-off-by: Sasha Levin +--- + include/uapi/linux/in6.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/include/uapi/linux/in6.h b/include/uapi/linux/in6.h +index c4c53a9ab9595..ff8d21f9e95b7 100644 +--- a/include/uapi/linux/in6.h ++++ b/include/uapi/linux/in6.h +@@ -145,7 +145,7 @@ struct in6_flowlabel_req { + #define IPV6_TLV_PADN 1 + #define IPV6_TLV_ROUTERALERT 5 + #define IPV6_TLV_CALIPSO 7 /* RFC 5570 */ +-#define IPV6_TLV_IOAM 49 /* TEMPORARY IANA allocation for IOAM */ ++#define IPV6_TLV_IOAM 49 /* RFC 9486 */ + #define IPV6_TLV_JUMBO 194 + #define IPV6_TLV_HAO 201 /* home address option */ + +-- +2.43.0 + diff --git a/queue-6.7/veth-try-harder-when-allocating-queue-memory.patch b/queue-6.7/veth-try-harder-when-allocating-queue-memory.patch new file mode 100644 index 00000000000..ec2f96e6a63 --- /dev/null +++ b/queue-6.7/veth-try-harder-when-allocating-queue-memory.patch @@ -0,0 +1,55 @@ +From e26ac7caef1ec277cdfa40d9bd396173c26c0e1f Mon Sep 17 00:00:00 2001 +From: Sasha Levin +Date: Fri, 23 Feb 2024 15:59:08 -0800 +Subject: veth: try harder when allocating queue memory + +From: Jakub Kicinski + +[ Upstream commit 1ce7d306ea63f3e379557c79abd88052e0483813 ] + +struct veth_rq is pretty large, 832B total without debug +options enabled. Since commit under Fixes we try to pre-allocate +enough queues for every possible CPU. Miao Wang reports that +this may lead to order-5 allocations which will fail in production. + +Let the allocation fallback to vmalloc() and try harder. +These are the same flags we pass to netdev queue allocation. + +Reported-and-tested-by: Miao Wang +Fixes: 9d3684c24a52 ("veth: create by default nr_possible_cpus queues") +Link: https://lore.kernel.org/all/5F52CAE2-2FB7-4712-95F1-3312FBBFA8DD@gmail.com/ +Signed-off-by: Jakub Kicinski +Reviewed-by: Eric Dumazet +Link: https://lore.kernel.org/r/20240223235908.693010-1-kuba@kernel.org +Signed-off-by: Paolo Abeni +Signed-off-by: Sasha Levin +--- + drivers/net/veth.c | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/drivers/net/veth.c b/drivers/net/veth.c +index bf4da315ae01c..a2e80278eb2f9 100644 +--- a/drivers/net/veth.c ++++ b/drivers/net/veth.c +@@ -1461,7 +1461,8 @@ static int veth_alloc_queues(struct net_device *dev) + struct veth_priv *priv = netdev_priv(dev); + int i; + +- priv->rq = kcalloc(dev->num_rx_queues, sizeof(*priv->rq), GFP_KERNEL_ACCOUNT); ++ priv->rq = kvcalloc(dev->num_rx_queues, sizeof(*priv->rq), ++ GFP_KERNEL_ACCOUNT | __GFP_RETRY_MAYFAIL); + if (!priv->rq) + return -ENOMEM; + +@@ -1477,7 +1478,7 @@ static void veth_free_queues(struct net_device *dev) + { + struct veth_priv *priv = netdev_priv(dev); + +- kfree(priv->rq); ++ kvfree(priv->rq); + } + + static int veth_dev_init(struct net_device *dev) +-- +2.43.0 +