--- /dev/null
+From ca35a5363c00b56f05f5bb5427c4acdb9bced452 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 23 Feb 2024 13:15:02 +0000
+Subject: afs: Fix endless loop in directory parsing
+
+From: David Howells <dhowells@redhat.com>
+
+[ 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 <dhowells@redhat.com>
+Link: https://lore.kernel.org/r/786185.1708694102@warthog.procyon.org.uk
+Reviewed-by: Marc Dionne <marc.dionne@auristor.com>
+cc: Marc Dionne <marc.dionne@auristor.com>
+cc: Markus Suvanto <markus.suvanto@gmail.com>
+cc: linux-afs@lists.infradead.org
+Signed-off-by: Christian Brauner <brauner@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 9c8de20152b61440b805ef9bed510686ab8ec783 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 21 Feb 2024 10:21:56 +0100
+Subject: ALSA: Drop leftover snd-rtctimer stuff from Makefile
+
+From: Takashi Iwai <tiwai@suse.de>
+
+[ 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 <tiwai@suse.de>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 996b75cb975241da5638351d1d1b152a9fa3e8fb Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 29 Jan 2024 16:27:23 +0000
+Subject: ASoC: cs35l56: cs35l56_component_remove() must clean up wm_adsp
+
+From: Richard Fitzgerald <rf@opensource.cirrus.com>
+
+[ Upstream commit cd38ccbecdace1469b4e0cfb3ddeec72a3fad226 ]
+
+cs35l56_component_remove() must call wm_adsp_power_down() and
+wm_adsp2_component_remove().
+
+Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 64888a4b48409566fd30fbc6e4bdb477f6444913 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 29 Jan 2024 16:27:22 +0000
+Subject: ASoC: cs35l56: cs35l56_component_remove() must clear
+ cs35l56->component
+
+From: Richard Fitzgerald <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From ff65344b3059886efc7e90115671f45f98c70f05 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 29 Jan 2024 16:27:24 +0000
+Subject: ASoC: cs35l56: Don't add the same register patch multiple times
+
+From: Richard Fitzgerald <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From b88820d41009c9e2aea29dc45f579ad2a7958349 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 8 Feb 2024 12:37:42 +0000
+Subject: ASoC: cs35l56: Fix deadlock in ASP1 mixer register initialization
+
+From: Richard Fitzgerald <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 61fc6a1399ea9c1542d227ad99daec38cec15cb5 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 29 Jan 2024 16:27:29 +0000
+Subject: ASoC: cs35l56: Fix for initializing ASP1 mixer registers
+
+From: Richard Fitzgerald <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From b3fa559a6a5c72bf612369dc11fc5d9e25ab9e6a Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Stable-dep-of: eba2eb2495f4 ("ASoC: soc-card: Fix missing locking in snd_soc_card_get_kcontrol()")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 5132dca9cf4b6afd0f56d1725e01b21d4042fecf Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 16 Feb 2024 14:05:35 +0000
+Subject: ASoC: cs35l56: Must clear HALO_STATE before issuing SYSTEM_RESET
+
+From: Richard Fitzgerald <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 4c623874ce1ea5c86f873465027938745133f321 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 21 Feb 2024 13:48:04 +0000
+Subject: ASoC: qcom: Fix uninitialized pointer dmactl
+
+From: Colin Ian King <colin.i.king@gmail.com>
+
+[ 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 <colin.i.king@gmail.com>
+Link: https://msgid.link/r/20240221134804.3475989-1-colin.i.king@gmail.com
+Signed-off-by: Mark Brown <broonie@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 1d53ba904339062a97e8a23fec31153a40bdfa86 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <rf@opensource.cirrus.com>
+
+[ 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 <rf@opensource.cirrus.com>
+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 <broonie@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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 <kuninori.morimoto.gx@renesas.com>
+ //
++
++#include <linux/lockdep.h>
++#include <linux/rwsem.h>
+ #include <sound/soc.h>
+ #include <sound/jack.h>
+
+@@ -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
+
--- /dev/null
+From ee53fa2f2987d9361f55da3a18fb3e19384cd2ef Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 4 Jan 2024 11:56:32 +0000
+Subject: Bluetooth: Avoid potential use-after-free in hci_error_reset
+
+From: Ying Hsu <yinghsu@chromium.org>
+
+[ 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 <HASH:3b4a6>]
+ ? init_wait_entry+0x31/0x31
+ __hci_cmd_sync+0x16/0x20 [bluetooth <HASH:3b4a 6>]
+ hci_error_reset+0x4f/0xa4 [bluetooth <HASH:3b4a 6>]
+ 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 <yinghsu@chromium.org>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 33e4f5171519954127bd2a7902b04e8d53942190 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 25 Jan 2024 14:50:28 +0800
+Subject: Bluetooth: Enforce validation on max value of connection interval
+
+From: Kai-Heng Feng <kai.heng.feng@canonical.com>
+
+[ 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 <kai.heng.feng@canonical.com>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 96509a6f93096aa7c78a459940744081e7f28787 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <luiz.von.dentz@intel.com>
+
+[ 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 <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From f410dcb58db1060bb11efcb2485f5b99845b3239 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 9 Jan 2024 19:03:23 +0800
+Subject: Bluetooth: hci_event: Fix wrongly recorded wakeup BD_ADDR
+
+From: Zijun Hu <quic_zijuhu@quicinc.com>
+
+[ 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 <quic_zijuhu@quicinc.com>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From a7b27cb2dd411e1ac3d78acac5b7d3c8ec9ae2ae Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <quic_janathot@quicinc.com>
+
+[ 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 <quic_janathot@quicinc.com>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From c5f458ba17654cf85cee883a554545cc9c1b3b97 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <verdre@v0yd.nl>
+
+[ 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 <verdre@v0yd.nl>
+Reviewed-by: Simon Horman <horms@kernel.org>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 93d9bfb68307a2f5273f7afd522aecf9be046f6f Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <luiz.von.dentz@intel.com>
+
+[ 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 <clancy.shang@quectel.com>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Reviewed-by: Paul Menzel <pmenzel@molgen.mpg.de>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From e1e597fd65dd3a453e4796d1d52485a6ea5a47fb Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 26 Jan 2024 17:00:24 +0800
+Subject: Bluetooth: qca: Fix triggering coredump implementation
+
+From: Zijun Hu <quic_zijuhu@quicinc.com>
+
+[ 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 <quic_zijuhu@quicinc.com>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 55f55dc4ed083192cc0663a71ce05ad20c48a0ab Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 19 Jan 2024 17:45:30 +0800
+Subject: Bluetooth: qca: Fix wrong event type for patch config command
+
+From: Zijun Hu <quic_zijuhu@quicinc.com>
+
+[ 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 <quic_zijuhu@quicinc.com>
+Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From f430064a1aecf85073b05659b6c979df273dce4c Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 22 Feb 2024 12:29:26 +0000
+Subject: btrfs: fix race between ordered extent completion and fiemap
+
+From: Filipe Manana <fdmanana@suse.com>
+
+[ 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] <TASK>
+ [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 <wangyugui@e16-tech.com>
+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 <josef@toxicpanda.com>
+Signed-off-by: Filipe Manana <fdmanana@suse.com>
+Signed-off-by: David Sterba <dsterba@suse.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From e82b178e30639aa1fb0d8c3799b50e8c956360ef Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <dsmythies@telus.net>
+
+[ 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 <dsmythies@telus.net>
+Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 5b8ca818c16cc39bfa611b471dd19750a8e0f184 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 20:00:01 +0300
+Subject: drivers: perf: added capabilities for legacy PMU
+
+From: Vadim Shakirov <vadim.shakirov@syntacore.com>
+
+[ 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 <atishp@rivosinc.com>
+Signed-off-by: Vadim Shakirov <vadim.shakirov@syntacore.com>
+Reviewed-by: Atish Patra <atishp@rivosinc.com>
+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 <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 88daa58cb9af1e3bf945eaf0395f2e2f63eec394 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 20:00:02 +0300
+Subject: drivers: perf: ctr_get_width function for legacy is not defined
+
+From: Vadim Shakirov <vadim.shakirov@syntacore.com>
+
+[ 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 <vadim.shakirov@syntacore.com>
+Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
+Reviewed-by: Atish Patra <atishp@rivosinc.com>
+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 <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From e8ade91757eaf66bd2dcbc6e07ec3ed9c6942129 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 20 Feb 2024 09:14:25 +0530
+Subject: drm/amd/display: Prevent potential buffer overflow in
+ map_hw_resources
+
+From: Srinivasan Shanmugam <srinivasan.shanmugam@amd.com>
+
+[ 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 <Rodrigo.Siqueira@amd.com>
+Cc: Roman Li <roman.li@amd.com>
+Cc: Qingqing Zhuo <Qingqing.Zhuo@amd.com>
+Cc: Aurabindo Pillai <aurabindo.pillai@amd.com>
+Cc: Tom Chung <chiahsuan.chung@amd.com>
+Signed-off-by: Srinivasan Shanmugam <srinivasan.shanmugam@amd.com>
+Suggested-by: Roman Li <roman.li@amd.com>
+Reviewed-by: Roman Li <roman.li@amd.com>
+Reviewed-by: Rodrigo Siqueira <Rodrigo.Siqueira@amd.com>
+Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From b7b9f288fd236d73ce52962cfd0e0e69bb113777 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 29 Feb 2024 21:52:05 +0530
+Subject: drm/nouveau: keep DMA buffers required for suspend/resume
+
+From: Sid Pranjale <sidpranjale127@protonmail.com>
+
+[ 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 <sidpranjale127@protonmail.com>
+Signed-off-by: Dave Airlie <airlied@redhat.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 41774432d4719db0e112a37cc21785491f471eda Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 23 Feb 2024 16:03:33 +0100
+Subject: drm/tegra: Remove existing framebuffer only if we support display
+
+From: Thierry Reding <treding@nvidia.com>
+
+[ 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 <treding@nvidia.com>
+Reviewed-by: Thomas Zimmermann <tzimmermann@suse.de>
+Reviewed-by: Javier Martinez Canillas <javierm@redhat.com>
+Signed-off-by: Robert Foss <rfoss@kernel.org>
+Link: https://patchwork.freedesktop.org/patch/msgid/20240223150333.1401582-1-thierry.reding@gmail.com
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 9e35afa49051c9e41195cf71d7fa0522d20b56a5 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 12 Feb 2024 12:24:40 +0100
+Subject: efi/capsule-loader: fix incorrect allocation size
+
+From: Arnd Bergmann <arnd@arndb.de>
+
+[ 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 <arnd@arndb.de>
+Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 448f55667a5b74c06527e0109983b31ceed77e8a Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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) <jirislaby@kernel.org>
+
+[ 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:
+ <TASK>
+ 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) <jirislaby@kernel.org>
+Fixes: a5a923038d70 ("fbdev: fbcon: Properly revert changes when vc_resize() failed")
+Reported-and-tested-by: Ubisectech Sirius <bugreport@ubisectech.com>
+Cc: Ubisectech Sirius <bugreport@ubisectech.com>
+Cc: Daniel Vetter <daniel@ffwll.ch>
+Cc: Helge Deller <deller@gmx.de>
+Cc: linux-fbdev@vger.kernel.org
+Cc: dri-devel@lists.freedesktop.org
+Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
+Link: https://patchwork.freedesktop.org/patch/msgid/20240208114411.14604-1-jirislaby@kernel.org
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 5c8245088ad0df3ac2a5537447f93cbbc6c9809f Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 22 Feb 2024 03:05:16 +0200
+Subject: gpu: host1x: Skip reset assert on Tegra186
+
+From: Mikko Perttunen <mperttunen@nvidia.com>
+
+[ 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 <mperttunen@nvidia.com>
+Reviewed-by: Jon Hunter <jonathanh@nvidia.com>
+Tested-by: Jon Hunter <jonathanh@nvidia.com>
+Signed-off-by: Thierry Reding <treding@nvidia.com>
+Link: https://patchwork.freedesktop.org/patch/msgid/20240222010517.1573931-1-cyndis@kapsi.fi
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From befdcd7b1038490850b477ac8ec7107c95aafa8e Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 25 Jan 2024 15:40:55 +0200
+Subject: ice: fix connection state of DPLL and out pin
+
+From: Yochai Hagvi <yochai.hagvi@intel.com>
+
+[ 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 <wojciech.drewek@intel.com>
+Reviewed-by: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+Signed-off-by: Yochai Hagvi <yochai.hagvi@intel.com>
+Tested-by: Sunitha Mekala <sunithax.d.mekala@intel.com> (A Contingent worker at Intel)
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 160b34bf4b12b3c847f80a7ebee8e33526b8476b Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 9 Feb 2024 22:24:30 +0100
+Subject: ice: fix dpll and dpll_pin data access on PF reset
+
+From: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+
+[ 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/<ice PF>/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 <aleksandr.loktionov@intel.com>
+Reviewed-by: Przemek Kitszel <przemyslaw.kitszel@intel.com>
+Signed-off-by: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+Tested-by: Pucha Himasekhar Reddy <himasekharx.reddy.pucha@intel.com> (A Contingent worker at Intel)
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 91f1db083c45cb941925ed4a5fe3c6c82c4e9f62 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 8 Feb 2024 23:56:31 +0100
+Subject: ice: fix dpll input pin phase_adjust value updates
+
+From: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+
+[ 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 <alan.brady@intel.com>
+Signed-off-by: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+Tested-by: Pucha Himasekhar Reddy <himasekharx.reddy.pucha@intel.com> (A Contingent worker at Intel)
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 0bb0fce0377540fdaa274ee5275616baa8ba08a3 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 9 Feb 2024 22:24:31 +0100
+Subject: ice: fix dpll periodic work data updates on PF reset
+
+From: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+
+[ 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/<ice PF>/device/reset
+
+Fixes: d7999f5ea64b ("ice: implement dpll interface to control cgu")
+Reviewed-by: Igor Bagnucki <igor.bagnucki@intel.com>
+Signed-off-by: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+Tested-by: Pucha Himasekhar Reddy <himasekharx.reddy.pucha@intel.com> (A Contingent worker at Intel)
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From a0739457a8e786c7e828ffc785a96e61bd240cfc Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 9 Feb 2024 22:24:32 +0100
+Subject: ice: fix pin phase adjust updates on PF reset
+
+From: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+
+[ 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/<ice PF>/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 <igor.bagnucki@intel.com>
+Signed-off-by: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+Tested-by: Pucha Himasekhar Reddy <himasekharx.reddy.pucha@intel.com> (A Contingent worker at Intel)
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 9be10aaf1ae1109ec4f230c6ee3644ea8fba086a Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 10:49:41 -0800
+Subject: igb: extend PTP timestamp adjustments to i211
+
+From: Oleksij Rempel <o.rempel@pengutronix.de>
+
+[ 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 <o.rempel@pengutronix.de>
+Reviewed-by: Jacob Keller <jacob.e.keller@intel.com>
+Tested-by: Pucha Himasekhar Reddy <himasekharx.reddy.pucha@intel.com> (A Contingent worker at Intel)
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Link: https://lore.kernel.org/r/20240227184942.362710-1-anthony.l.nguyen@intel.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From f90703eef697ccb6048feef85527bfb010b7ebb5 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 22 Feb 2024 12:17:47 +0000
+Subject: ipv6: fix potential "struct net" leak in inet6_rtm_getaddr()
+
+From: Eric Dumazet <edumazet@google.com>
+
+[ 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 <edumazet@google.com>
+Cc: Christian Brauner <brauner@kernel.org>
+Cc: David Ahern <dsahern@kernel.org>
+Reviewed-by: David Ahern <dsahern@kernel.org>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From e62c3afd4d996756cbe8b18020d37804020dbb0f Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <o.rempel@pengutronix.de>
+
+[ 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 <o.rempel@pengutronix.de>
+Link: https://lore.kernel.org/r/20240222123839.2816561-1-o.rempel@pengutronix.de
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From cb7ce9ff64112709b11201100ab111e34b08b40c Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 8 Nov 2023 09:07:01 -0600
+Subject: mtd: spinand: gigadevice: Fix the get ecc status issue
+
+From: Han Xu <han.xu@nxp.com>
+
+[ 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 <han.xu@nxp.com>
+Signed-off-by: Miquel Raynal <miquel.raynal@bootlin.com>
+Link: https://lore.kernel.org/linux-mtd/20231108150701.593912-1-han.xu@nxp.com
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 995a89a9b6509e2bb83ccea6e303c03130516f20 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <vladimir.oltean@nxp.com>
+
+[ 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 <vladimir.oltean@nxp.com>
+Reviewed-by: Sean Anderson <sean.anderson@seco.com>
+Acked-by: Madalin Bucur <madalin.bucur@oss.nxp.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ .../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
+
--- /dev/null
+From 3ac0aa74f7963638ddc5b835b0209fb0ede6670b Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <lukma@denx.de>
+
+[ 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 <lukma@denx.de>
+Reviewed-by: Jiri Pirko <jiri@nvidia.com>
+Link: https://lore.kernel.org/r/20240228085644.3618044-1-lukma@denx.de
+Signed-off-by: Paolo Abeni <pabeni@redhat.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 9abae2f181bf9fbcd17ae6ae3b8d19af8d541d2a Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 20 Feb 2024 14:56:02 +0100
+Subject: net: ip_tunnel: prevent perpetual headroom growth
+
+From: Florian Westphal <fw@strlen.de>
+
+[ 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 <fw@strlen.de>
+Reviewed-by: Simon Horman <horms@kernel.org>
+Link: https://lore.kernel.org/r/20240220135606.4939-1-fw@strlen.de
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 5762a118bace98a4ff085e5a515559fd835d79dc Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 26 Feb 2024 12:08:20 +0100
+Subject: net: lan78xx: fix "softirq work is pending" error
+
+From: Oleksij Rempel <o.rempel@pengutronix.de>
+
+[ 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 <o.rempel@pengutronix.de>
+Link: https://lore.kernel.org/r/20240226110820.2113584-1-o.rempel@pengutronix.de
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From bd15896818a126d1192be3bd0e5ca1b02643b0ec Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 20 Feb 2024 16:10:53 +0800
+Subject: net: mctp: take ownership of skb in mctp_local_output
+
+From: Jeremy Kerr <jk@codeconstruct.com.au>
+
+[ 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 <jk@codeconstruct.com.au>
+Reviewed-by: Simon Horman <horms@kernel.org>
+Link: https://lore.kernel.org/r/20240220081053.1439104-1-jk@codeconstruct.com.au
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From b6da1cced14e133c063c76c0283309bb82170a99 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Sun, 25 Feb 2024 00:20:06 +0100
+Subject: net: usb: dm9601: fix wrong return value in dm9601_mdio_read
+
+From: Javier Carrasco <javier.carrasco.cruz@gmail.com>
+
+[ 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 <javier.carrasco.cruz@gmail.com>
+Reviewed-by: Simon Horman <horms@kernel.org>
+Reviewed-by: Peter Korsgaard <peter@korsgaard.com>
+Link: https://lore.kernel.org/r/20240225-dm9601_ret_err-v1-1-02c1d959ea59@gmail.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 8e96197e7b8c759784033f32811e36f95ea4330b Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <kuba@kernel.org>
+
+[ 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 <tglx@linutronix.de>
+Reported-by: syzbot+039399a9b96297ddedca@syzkaller.appspotmail.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Reviewed-by: Toke Høiland-Jørgensen <toke@redhat.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 468bd7513ce5d6d7460c0abe9d92338c793cdac4 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 16:17:51 +0100
+Subject: netfilter: bridge: confirm multicast packets before passing them up
+ the stack
+
+From: Florian Westphal <fw@strlen.de>
+
+[ 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 <pablo@netfilter.org>
+Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2")
+Closes: https://bugzilla.kernel.org/show_bug.cgi?id=217777
+Signed-off-by: Florian Westphal <fw@strlen.de>
+Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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 <linux/sysctl.h>
+ #endif
+
++#if IS_ENABLED(CONFIG_NF_CONNTRACK)
++#include <net/netfilter/nf_conntrack_core.h>
++#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
+
--- /dev/null
+From 5b2d37a6a27367e3ce1c08dc720eff43aaee06f7 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 22 Feb 2024 10:33:08 +0000
+Subject: netfilter: nf_tables: allow NFPROTO_INET in
+ nft_(match/target)_validate()
+
+From: Ignat Korchagin <ignat@cloudflare.com>
+
+[ 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 <jgriege@cloudflare.com>
+Signed-off-by: Ignat Korchagin <ignat@cloudflare.com>
+Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From fc3abc2aae27399a812bfdc6ed5ab7d5de6b38a4 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 21 Feb 2024 18:27:33 +0100
+Subject: netlink: add nla be16/32 types to minlen array
+
+From: Florian Westphal <fw@strlen.de>
+
+[ 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 <xrivendell7@gmail.com>
+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 <fw@strlen.de>
+Link: https://lore.kernel.org/r/20240221172740.5092-1-fw@strlen.de
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 5fceda5f8ecbf764076b1a5676277c287434968c Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 21 Feb 2024 16:40:48 +0900
+Subject: netlink: Fix kernel-infoleak-after-free in __skb_datagram_iter
+
+From: Ryosuke Yasuoka <ryasuoka@redhat.com>
+
+[ 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 <ryasuoka@redhat.com>
+Reviewed-by: Eric Dumazet <edumazet@google.com>
+Link: https://lore.kernel.org/r/20240221074053.1794118-1-ryasuoka@redhat.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From b96037b42f4017c20a6c8fd7db8ff99c1b3ab56d Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 23 Feb 2024 21:24:35 -0800
+Subject: of: property: fw_devlink: Fix stupid bug in remote-endpoint parsing
+
+From: Saravana Kannan <saravanak@google.com>
+
+[ 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 <luca.ceresoli@bootlin.com>
+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 <saravanak@google.com>
+Reviewed-by: Herve Codina <herve.codina@bootlin.com>
+Reviewed-by: Luca Ceresoli <luca.ceresoli@bootlin.com>
+Tested-by: Luca Ceresoli <luca.ceresoli@bootlin.com>
+Link: https://lore.kernel.org/r/20240224052436.3552333-1-saravanak@google.com
+Signed-off-by: Rob Herring <robh@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 04d17b0776530d22bbf8b3aba2c4714d783a37f3 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Thu, 15 Feb 2024 16:51:33 +0100
+Subject: power: supply: bq27xxx-i2c: Do not free non existing IRQ
+
+From: Hans de Goede <hdegoede@redhat.com>
+
+[ 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 <hdegoede@redhat.com>
+Link: https://lore.kernel.org/r/20240215155133.70537-1-hdegoede@redhat.com
+Signed-off-by: Sebastian Reichel <sebastian.reichel@collabora.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 6ddf0b71069fb7abb2c06246e52d4ca3680cf262 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 21:50:15 +0100
+Subject: Revert "riscv: mm: support Svnapot in huge vmap"
+
+From: Alexandre Ghiti <alexghiti@rivosinc.com>
+
+[ 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 <alexghiti@rivosinc.com>
+Link: https://lore.kernel.org/r/20240227205016.121901-2-alexghiti@rivosinc.com
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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 <linux/pgtable.h>
++#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
+
--- /dev/null
+From 075a553251f56d2bf42d0d704021f1ec7d5f8f66 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <conor@kernel.org>
+
+[ 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 <conor.dooley@microchip.com>
+Signed-off-by: Conor Dooley <conor.dooley@microchip.com>
+Acked-by: Guo Ren <guoren@kernel.org>
+Link: https://lore.kernel.org/r/20240223-tidings-shabby-607f086cb4d7@spud
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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 <asm/hwprobe.h>
+ #include <asm/patch.h>
+ #include <asm/processor.h>
++#include <asm/sbi.h>
+ #include <asm/vector.h>
+
+ #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
+
--- /dev/null
+From f86f0306db3981584614ec008467dc05eae0669d Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Sun, 11 Feb 2024 09:36:40 +0100
+Subject: riscv: Fix build error if !CONFIG_ARCH_ENABLE_HUGEPAGE_MIGRATION
+
+From: Alexandre Ghiti <alexghiti@rivosinc.com>
+
+[ 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 <lkp@intel.com>
+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 <alexghiti@rivosinc.com>
+Link: https://lore.kernel.org/r/20240211083640.756583-1-alexghiti@rivosinc.com
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From d3b6b151aee397d8322d393a5392560cb8543f61 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 21:50:16 +0100
+Subject: riscv: Fix pte_leaf_size() for NAPOT
+
+From: Alexandre Ghiti <alexghiti@rivosinc.com>
+
+[ 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 <alexghiti@rivosinc.com>
+Link: https://lore.kernel.org/r/20240227205016.121901-3-alexghiti@rivosinc.com
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 481d3401bf550153c9a552f712017a12a7618232 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 21 Feb 2024 11:02:31 +0800
+Subject: riscv: mm: fix NOCACHE_THEAD does not set bit[61] correctly
+
+From: Yangyu Chen <cyy@cyyself.name>
+
+[ 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 <cyy@cyyself.name>
+Reviewed-by: Guo Ren <guoren@kernel.org>
+Reviewed-by: Jisheng Zhang <jszhang@kernel.org>
+Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
+Link: https://lore.kernel.org/r/tencent_E19FA1A095768063102E654C6FC858A32F06@qq.com
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 3be8cc95fa189d09ad7cf1f0cd8619c3256d582c Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <dvlachos@ics.forth.gr>
+
+[ 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 <alexghiti@rivosinc.com>
+Signed-off-by: Dimitris Vlachos <dvlachos@ics.forth.gr>
+Reported-by: Dimitris Vlachos <dvlachos@ics.forth.gr>
+Closes: https://lore.kernel.org/linux-riscv/20240202135030.42265-1-csd4492@csd.uoc.gr
+Fixes: d95f1a542c3d ("RISC-V: Implement sparsemem")
+Reviewed-by: Alexandre Ghiti <alexghiti@rivosinc.com>
+Link: https://lore.kernel.org/r/20240229191723.32779-1-dvlachos@ics.forth.gr
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 185539bb0b6782c24520bf1c5ef4fd7e124ed827 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 20 Dec 2023 01:50:43 +0800
+Subject: riscv: tlb: fix __p*d_free_tlb()
+
+From: Jisheng Zhang <jszhang@kernel.org>
+
+[ 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 <jszhang@kernel.org>
+Fixes: c5e9b2c2ae82 ("riscv: Improve tlb_flush()")
+Link: https://lore.kernel.org/r/20231219175046.2496-2-jszhang@kernel.org
+Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 4c169ea53c1f036161929019d5364c33ba0ec168 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Feb 2024 20:11:28 +0800
+Subject: rtnetlink: fix error logic of IFLA_BRIDGE_FLAGS writing back
+
+From: Lin Ma <linma@zju.edu.cn>
+
+[ 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 <linma@zju.edu.cn>
+Acked-by: Nikolay Aleksandrov <razor@blackwall.org>
+Link: https://lore.kernel.org/r/20240227121128.608110-1-linma@zju.edu.cn
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
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
--- /dev/null
+From 401c42fc8d0b2faa3a307fe60087c33015e7a561 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <theo.lebrun@bootlin.com>
+
+[ 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 <d-gole@ti.com>
+Signed-off-by: Théo Lebrun <theo.lebrun@bootlin.com>
+Link: https://msgid.link/r/20240222-cdns-qspi-pm-fix-v4-1-6b6af8bcbf59@bootlin.com
+Signed-off-by: Mark Brown <broonie@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 2d34ae58d5afe88d58b8dc5489cad4ffb319cc7b Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+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 <theo.lebrun@bootlin.com>
+
+[ 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 <theo.lebrun@bootlin.com>
+Link: https://msgid.link/r/20240222-cdns-qspi-pm-fix-v4-2-6b6af8bcbf59@bootlin.com
+Signed-off-by: Mark Brown <broonie@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 9ec36d8c21e7e96a4065dd440d8f027edd73d6db Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 26 Feb 2024 17:42:32 +0100
+Subject: stmmac: Clear variable when destroying workqueue
+
+From: Jakub Raczynski <j.raczynski@samsung.com>
+
+[ 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
+ <Skipping backtrace for watchdog timeout>
+[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 <j.raczynski@samsung.com>
+Reviewed-by: Jiri Pirko <jiri@nvidia.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 03e9f590f26218cbe1c817338e5616a632b4c6e8 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 28 Feb 2024 23:43:57 +0100
+Subject: tls: decrement decrypt_pending if no async completion will be called
+
+From: Sabrina Dubroca <sd@queasysnail.net>
+
+[ 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 <sd@queasysnail.net>
+Link: https://lore.kernel.org/r/c56d5fc35543891d5319f834f25622360e1bfbec.1709132643.git.sd@queasysnail.net
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 8ec2e65fc9e163fdad06989ce7c62548954b7a3e Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 28 Feb 2024 23:43:58 +0100
+Subject: tls: fix peeking with sync+async decryption
+
+From: Sabrina Dubroca <sd@queasysnail.net>
+
+[ 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 <sd@queasysnail.net>
+Link: https://lore.kernel.org/r/1b132d2b2b99296bfde54e8a67672d90d6d16e71.1709132643.git.sd@queasysnail.net
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 4867fcabeff59551e125bbc057c72e230550a1ad Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 28 Feb 2024 23:44:00 +0100
+Subject: tls: fix use-after-free on failed backlog decryption
+
+From: Sabrina Dubroca <sd@queasysnail.net>
+
+[ 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 <sd@queasysnail.net>
+Link: https://lore.kernel.org/r/4755dd8d9bebdefaa19ce1439b833d6199d4364c.1709132643.git.sd@queasysnail.net
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 10b947c0cc5b738af12fb78443520b235d9ab1a7 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Wed, 28 Feb 2024 23:43:59 +0100
+Subject: tls: separate no-async decryption request handling from async
+
+From: Sabrina Dubroca <sd@queasysnail.net>
+
+[ 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 <sd@queasysnail.net>
+Link: https://lore.kernel.org/r/47bde5f649707610eaef9f0d679519966fc31061.1709132643.git.sd@queasysnail.net
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Stable-dep-of: 13114dc55430 ("tls: fix use-after-free on failed backlog decryption")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From c3a370fe39d2215dfb4ab7a72e558308de7e59b8 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 26 Feb 2024 13:40:18 -0800
+Subject: tools: ynl: fix handling of multiple mcast groups
+
+From: Jakub Kicinski <kuba@kernel.org>
+
+[ 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 <donald.hunter@gmail.com>
+Acked-by: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+Link: https://lore.kernel.org/r/20240226214019.1255242-1-kuba@kernel.org
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 840674561910430eb8f271402d54b75241f48956 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 20 Feb 2024 11:12:07 +0800
+Subject: tun: Fix xdp_rxq_info's queue_index when detaching
+
+From: Yunjian Wang <wangyunjian@huawei.com>
+
+[ 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 <wangyunjian@huawei.com>
+Link: https://lore.kernel.org/r/1708398727-46308-1-git-send-email-wangyunjian@huawei.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From 18cfadcc879fb50e326f73c2feb3478f0dd9cfde Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Mon, 26 Feb 2024 13:49:21 +0100
+Subject: uapi: in6: replace temporary label with rfc9486
+
+From: Justin Iurman <justin.iurman@uliege.be>
+
+[ 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 <justin.iurman@uliege.be>
+Reviewed-by: Simon Horman <horms@kernel.org>
+Link: https://lore.kernel.org/r/20240226124921.9097-1-justin.iurman@uliege.be
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+
--- /dev/null
+From e26ac7caef1ec277cdfa40d9bd396173c26c0e1f Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 23 Feb 2024 15:59:08 -0800
+Subject: veth: try harder when allocating queue memory
+
+From: Jakub Kicinski <kuba@kernel.org>
+
+[ 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 <shankerwangmiao@gmail.com>
+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 <kuba@kernel.org>
+Reviewed-by: Eric Dumazet <edumazet@google.com>
+Link: https://lore.kernel.org/r/20240223235908.693010-1-kuba@kernel.org
+Signed-off-by: Paolo Abeni <pabeni@redhat.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ 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
+