Linux Sound subsystem development
 help / color / mirror / Atom feed
* [PATCH 0/8] Reword the SDCA HID code
@ 2026-08-05 12:41 Charles Keepax
  2026-08-05 12:41 ` [PATCH 1/8] ASoC: SDCA: Tidy up error message Charles Keepax
                   ` (9 more replies)
  0 siblings, 10 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:41 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

This series reworks the SDCA HID code, the primary goals being to no
longer store runtime HID data in the DisCo data structures and remove
the need to pass the soundwire device into the ACPI parsing code.

To achieve this the HID device registration is moved to the IRQ work
flow rather than the ACPI work flow.

Also a few small issues are fixed up along the way, some formatting,
some missing cleanup/docs.

Thanks,
Charles

Charles Keepax (8):
  ASoC: SDCA: Tidy up error message
  ASoC: SDCA: Remove unused dev pointer argument
  ASoC: SDCA: Move HID registration to IRQ time
  ASoC: SDCA: Move HID descriptors to function
  ASoC: SDCA: Update HID DisCo parsing
  ASoC: SDCA: Add missing destroy for HID device
  ASoC: SDCA: Add missing HID kernel doc
  ASoC: SDCA: Pass swft table through sdca_dev_register()

 include/sound/sdca_asoc.h             |   8 +-
 include/sound/sdca_function.h         |  24 ++--
 include/sound/sdca_hid.h              |  11 +-
 sound/soc/codecs/rt766-sdca.c         |  26 +++-
 sound/soc/codecs/rt766-sdca.h         |   2 +
 sound/soc/codecs/tac5xx2-sdw.c        |   6 +-
 sound/soc/codecs/tas2783-sdw.c        |   2 +-
 sound/soc/sdca/sdca_asoc.c            |  13 +-
 sound/soc/sdca/sdca_class_function.c  |   2 +-
 sound/soc/sdca/sdca_function_device.c |   7 +-
 sound/soc/sdca/sdca_functions.c       | 180 +++++++++++++++-----------
 sound/soc/sdca/sdca_hid.c             |  48 ++++---
 sound/soc/sdca/sdca_interrupts.c      |   6 +
 13 files changed, 211 insertions(+), 124 deletions(-)

-- 
2.47.3


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [PATCH 1/8] ASoC: SDCA: Tidy up error message
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
@ 2026-08-05 12:41 ` Charles Keepax
  2026-08-05 12:41 ` [PATCH 2/8] ASoC: SDCA: Remove unused dev pointer argument Charles Keepax
                   ` (8 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:41 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

Bring the entity_pde_event() error message slightly more in line with
the other SDCA error messages.

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 sound/soc/sdca/sdca_asoc.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/sound/soc/sdca/sdca_asoc.c b/sound/soc/sdca/sdca_asoc.c
index 9a6c0036b7be3..03486d1c1b2f3 100644
--- a/sound/soc/sdca/sdca_asoc.c
+++ b/sound/soc/sdca/sdca_asoc.c
@@ -458,7 +458,7 @@ static int entity_pde_event(struct snd_soc_dapm_widget *widget,
 					   entity->pde.max_delay,
 					   entity->pde.num_max_delay);
 	if (ret)
-		dev_err(component->dev, "%s: PDE transition %x -> %x failed, err=%d\n",
+		dev_err(component->dev, "%s: pde transition %x -> %x failed: %d\n",
 			entity->label, from, to, ret);
 
 	return ret;
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 2/8] ASoC: SDCA: Remove unused dev pointer argument
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
  2026-08-05 12:41 ` [PATCH 1/8] ASoC: SDCA: Tidy up error message Charles Keepax
@ 2026-08-05 12:41 ` Charles Keepax
  2026-08-05 12:42 ` [PATCH 3/8] ASoC: SDCA: Move HID registration to IRQ time Charles Keepax
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:41 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

Remove the now unused device pointer from
sdca_asoc_pde_poll_actual_ps().

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 include/sound/sdca_asoc.h      |  8 ++++----
 sound/soc/codecs/rt766-sdca.c  |  2 +-
 sound/soc/codecs/tac5xx2-sdw.c |  4 ++--
 sound/soc/sdca/sdca_asoc.c     | 11 +++++------
 4 files changed, 12 insertions(+), 13 deletions(-)

diff --git a/include/sound/sdca_asoc.h b/include/sound/sdca_asoc.h
index d3024c3b38b9c..599a72f335153 100644
--- a/include/sound/sdca_asoc.h
+++ b/include/sound/sdca_asoc.h
@@ -107,9 +107,9 @@ int sdca_asoc_q78_put_volsw(struct snd_kcontrol *kcontrol,
 			    struct snd_ctl_elem_value *ucontrol);
 int sdca_asoc_q78_get_volsw(struct snd_kcontrol *kcontrol,
 			    struct snd_ctl_elem_value *ucontrol);
-int sdca_asoc_pde_poll_actual_ps(struct device *dev, struct regmap *regmap,
+int sdca_asoc_pde_poll_actual_ps(struct regmap *regmap,
 				 int function_id, int entity_id,
-			    int from_ps, int to_ps,
-			    const struct sdca_pde_delay *pde_delays,
-			    int num_delays);
+				 int from_ps, int to_ps,
+				 const struct sdca_pde_delay *pde_delays,
+				 int num_delays);
 #endif // __SDCA_ASOC_H__
diff --git a/sound/soc/codecs/rt766-sdca.c b/sound/soc/codecs/rt766-sdca.c
index 49ee9cef5c541..4c5acd950d70f 100644
--- a/sound/soc/codecs/rt766-sdca.c
+++ b/sound/soc/codecs/rt766-sdca.c
@@ -616,7 +616,7 @@ static int rt766_sdca_pde_event(struct snd_soc_dapm_widget *w,
 		return -EINVAL;
 	}
 
-	ret = sdca_asoc_pde_poll_actual_ps(component->dev, rt766->regmap,
+	ret = sdca_asoc_pde_poll_actual_ps(rt766->regmap,
 				   func_num,
 				   pde_num,
 				   from_ps, to_ps,
diff --git a/sound/soc/codecs/tac5xx2-sdw.c b/sound/soc/codecs/tac5xx2-sdw.c
index ace06f5ab58c1..ea0408b71713b 100644
--- a/sound/soc/codecs/tac5xx2-sdw.c
+++ b/sound/soc/codecs/tac5xx2-sdw.c
@@ -800,7 +800,7 @@ static int tac_sdw_hw_params(struct snd_pcm_substream *substream,
 		return ret;
 	}
 
-	ret = sdca_asoc_pde_poll_actual_ps(tac_dev->dev, tac_dev->regmap, function_id, pde_entity,
+	ret = sdca_asoc_pde_poll_actual_ps(tac_dev->regmap, function_id, pde_entity,
 					   SDCA_PDE_PS3, SDCA_PDE_PS0, NULL, 0);
 	if (ret)
 		dev_err(tac_dev->dev, "failed to transition func %d, pde %d from PS3 -> PS0, err=%d\n",
@@ -847,7 +847,7 @@ static int tac_sdw_pcm_hw_free(struct snd_pcm_substream *substream,
 		return ret;
 	}
 
-	ret = sdca_asoc_pde_poll_actual_ps(tac_dev->dev, tac_dev->regmap, function_id,
+	ret = sdca_asoc_pde_poll_actual_ps(tac_dev->regmap, function_id,
 					   pde_entity, SDCA_PDE_PS0, SDCA_PDE_PS3,
 					   NULL, 0);
 	if (ret)
diff --git a/sound/soc/sdca/sdca_asoc.c b/sound/soc/sdca/sdca_asoc.c
index 03486d1c1b2f3..ce2e7c2707657 100644
--- a/sound/soc/sdca/sdca_asoc.c
+++ b/sound/soc/sdca/sdca_asoc.c
@@ -364,7 +364,6 @@ static int entity_parse_ot(struct device *dev,
 
 /**
  * sdca_asoc_pde_poll_actual_ps - Verify PDE power state reached target state
- * @dev: Pointer to the device for error logging.
  * @regmap: Register map for reading ACTUAL_PS register.
  * @function_id: SDCA function identifier.
  * @entity_id: SDCA entity identifier for the power domain.
@@ -389,11 +388,11 @@ static int entity_parse_ot(struct device *dev,
  * polling times out before reaching the target state, or a negative error code if
  * a register read fails.
  */
-int sdca_asoc_pde_poll_actual_ps(struct device *dev, struct regmap *regmap,
+int sdca_asoc_pde_poll_actual_ps(struct regmap *regmap,
 				 int function_id, int entity_id,
-			    int from_ps, int to_ps,
-			    const struct sdca_pde_delay *pde_delays,
-			    int num_delays)
+				 int from_ps, int to_ps,
+				 const struct sdca_pde_delay *pde_delays,
+				 int num_delays)
 {
 	static const int polls = 100;
 	static const int default_poll_us = 1000;
@@ -451,7 +450,7 @@ static int entity_pde_event(struct snd_soc_dapm_widget *widget,
 		return 0;
 	}
 
-	ret = sdca_asoc_pde_poll_actual_ps(component->dev, component->regmap,
+	ret = sdca_asoc_pde_poll_actual_ps(component->regmap,
 					   SDW_SDCA_CTL_FUNC(widget->reg),
 					   SDW_SDCA_CTL_ENT(widget->reg),
 					   from, to,
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 3/8] ASoC: SDCA: Move HID registration to IRQ time
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
  2026-08-05 12:41 ` [PATCH 1/8] ASoC: SDCA: Tidy up error message Charles Keepax
  2026-08-05 12:41 ` [PATCH 2/8] ASoC: SDCA: Remove unused dev pointer argument Charles Keepax
@ 2026-08-05 12:42 ` Charles Keepax
  2026-08-05 12:42 ` [PATCH 4/8] ASoC: SDCA: Move HID descriptors to function Charles Keepax
                   ` (6 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:42 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

Currently, the SDCA code registers the HID device whilst parsing
the DisCo information. This necessitates storing the HID device
in the DisCo structs, which are intended to only store the parsed
DisCo. Having the HID device registered so early in the process
also causes some issues with cleaning up.

Update the code to register the HID device as the IRQs are handled,
this alleviates the previous concerns and brings the support inline
with the other SDCA event handling.

As part of this move the naming for the SDCA HID is also updated,
it saves some complexity around the passing of the SoundWire device
to include this in this patch. Update to using the dev_name for
the phys, which is more consistent with other HID users, and use
the actual function name/address for the HID name itself.

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 include/sound/sdca_function.h    |  2 --
 include/sound/sdca_hid.h         |  6 ++----
 sound/soc/codecs/rt766-sdca.c    | 22 +++++++++++++++++++---
 sound/soc/codecs/rt766-sdca.h    |  2 ++
 sound/soc/sdca/sdca_functions.c  | 24 ++++++------------------
 sound/soc/sdca/sdca_hid.c        | 21 ++++++++++-----------
 sound/soc/sdca/sdca_interrupts.c |  4 ++++
 7 files changed, 43 insertions(+), 38 deletions(-)

diff --git a/include/sound/sdca_function.h b/include/sound/sdca_function.h
index fb931ae735a27..35799a9771454 100644
--- a/include/sound/sdca_function.h
+++ b/include/sound/sdca_function.h
@@ -1116,7 +1116,6 @@ struct sdca_entity_ge {
 
 /**
  * struct sdca_entity_hide - information specific to HIDE Entities
- * @hid: HID device structure
  * @num_hidtx_ids: number of HIDTx Report ID
  * @num_hidrx_ids: number of HIDRx Report ID
  * @hidtx_ids: HIDTx Report ID
@@ -1131,7 +1130,6 @@ struct sdca_entity_ge {
  * @hid_desc: HID descriptor for the HIDE Entity
  */
 struct sdca_entity_hide {
-	struct hid_device *hid;
 	unsigned int *hidtx_ids;
 	unsigned int *hidrx_ids;
 	int num_hidtx_ids;
diff --git a/include/sound/sdca_hid.h b/include/sound/sdca_hid.h
index 18bebbe428c9f..83d1c7768133b 100644
--- a/include/sound/sdca_hid.h
+++ b/include/sound/sdca_hid.h
@@ -16,14 +16,12 @@ struct sdca_interrupt;
 
 #if IS_ENABLED(CONFIG_SND_SOC_SDCA_HID)
 
-int sdca_add_hid_device(struct device *dev, struct sdw_slave *sdw,
-			struct sdca_entity *entity);
+int sdca_add_hid_device(struct sdca_interrupt *interrupt);
 int sdca_hid_process_report(struct sdca_interrupt *interrupt);
 
 #else
 
-static inline int sdca_add_hid_device(struct device *dev, struct sdw_slave *sdw,
-				      struct sdca_entity *entity)
+static inline int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 {
 	return 0;
 }
diff --git a/sound/soc/codecs/rt766-sdca.c b/sound/soc/codecs/rt766-sdca.c
index 4c5acd950d70f..54ed0c42fba2f 100644
--- a/sound/soc/codecs/rt766-sdca.c
+++ b/sound/soc/codecs/rt766-sdca.c
@@ -22,6 +22,7 @@
 #include <sound/sdca.h>
 #include <sound/sdca_asoc.h>
 #include <sound/sdca_function.h>
+#include <sound/sdca_hid.h>
 #include <sound/sdca_regmap.h>
 #include <sound/sdca_interrupts.h>
 #include <linux/slab.h>
@@ -33,7 +34,6 @@
 static int rt766_sdca_btn_detect(struct sdca_interrupt *interrupt)
 {
 	struct rt766_sdca_priv *rt766 = interrupt->priv;
-	struct sdca_entity *ent_hid = interrupt->entity;
 	unsigned char *buf = NULL;
 	unsigned int offset, owner, length;
 	unsigned int det_mode, idx, val;
@@ -85,8 +85,8 @@ static int rt766_sdca_btn_detect(struct sdca_interrupt *interrupt)
 			buf[idx] = val & 0xff;
 		}
 
-		if (ent_hid)
-			hid_input_report(ent_hid->hide.hid, HID_INPUT_REPORT,
+		if (rt766->hid)
+			hid_input_report(rt766->hid, HID_INPUT_REPORT,
 				buf, length, 1);
 	}
 
@@ -191,6 +191,13 @@ static irqreturn_t rt766_sdca_irq_jd_handler(int irq, void *data)
 	return IRQ_HANDLED;
 }
 
+static void rt766_sdca_destroy_hid_device(struct sdca_interrupt *interrupt)
+{
+	struct rt766_sdca_priv *rt766 = interrupt->priv;
+
+	hid_destroy_device(rt766->hid);
+}
+
 static int rt766_sdca_irq_ctl(struct rt766_sdca_priv *rt766,
 							  struct sdca_function_data *function,
 							  struct snd_soc_component *component,
@@ -231,6 +238,15 @@ static int rt766_sdca_irq_ctl(struct rt766_sdca_priv *rt766,
 				if (ret)
 					return ret;
 
+				if (handler == rt766_sdca_irq_btn_handler) {
+					ret = sdca_add_hid_device(interrupt);
+					if (ret)
+						return ret;
+
+					interrupt->free_priv = rt766_sdca_destroy_hid_device;
+					rt766->hid = interrupt->priv;
+				}
+
 				interrupt->priv = rt766;
 				ret = sdca_irq_request(dev, info, irq, interrupt->name,
 								handler, interrupt);
diff --git a/sound/soc/codecs/rt766-sdca.h b/sound/soc/codecs/rt766-sdca.h
index 5acdb83a42fb8..de4064007eb9b 100644
--- a/sound/soc/codecs/rt766-sdca.h
+++ b/sound/soc/codecs/rt766-sdca.h
@@ -8,6 +8,7 @@
 #ifndef __RT766_H__
 #define __RT766_H__
 
+#include <linux/hid.h>
 #include <linux/pm.h>
 #include <linux/regmap.h>
 #include <linux/soundwire/sdw.h>
@@ -41,6 +42,7 @@ struct  rt766_sdca_priv {
 	struct sdca_function_data *sa_func_data;
 	struct sdca_function_data *hid_func_data;
 	struct sdca_interrupt_info *irq_info;
+	struct hid_device *hid;
 };
 
 /* vendor registers */
diff --git a/sound/soc/sdca/sdca_functions.c b/sound/soc/sdca/sdca_functions.c
index cdf1e68d60ac5..e9b449b670332 100644
--- a/sound/soc/sdca/sdca_functions.c
+++ b/sound/soc/sdca/sdca_functions.c
@@ -18,7 +18,6 @@
 #include <linux/types.h>
 #include <sound/sdca.h>
 #include <sound/sdca_function.h>
-#include <sound/sdca_hid.h>
 
 /*
  * Should be long enough to encompass all the MIPI DisCo properties.
@@ -1366,8 +1365,7 @@ static int find_sdca_entity_ge(struct device *dev,
 }
 
 static int
-find_sdca_entity_hide(struct device *dev, struct sdw_slave *sdw,
-		      struct fwnode_handle *function_node,
+find_sdca_entity_hide(struct device *dev, struct fwnode_handle *function_node,
 		      struct fwnode_handle *entity_node, struct sdca_entity *entity)
 {
 	struct sdca_entity_hide *hide = &entity->hide;
@@ -1440,13 +1438,6 @@ find_sdca_entity_hide(struct device *dev, struct sdw_slave *sdw,
 			hide->hid_report_desc = report_desc;
 			fwnode_property_read_u8_array(function_node, "mipi-sdca-report-descriptor",
 						      report_desc, nval);
-
-			/* add HID device */
-			ret = sdca_add_hid_device(dev, sdw, entity);
-			if (ret) {
-				dev_err(dev, "%pfwP: failed to add HID device: %d\n", entity_node, ret);
-				return ret;
-			}
 		}
 	}
 
@@ -1475,8 +1466,7 @@ static int find_sdca_entity_xu(struct device *dev,
 	return 0;
 }
 
-static int find_sdca_entity(struct device *dev, struct sdw_slave *sdw,
-			    struct sdca_function_data *function,
+static int find_sdca_entity(struct device *dev, struct sdca_function_data *function,
 			    struct fwnode_handle *function_node,
 			    struct fwnode_handle *entity_node,
 			    struct sdca_entity *entity)
@@ -1528,8 +1518,7 @@ static int find_sdca_entity(struct device *dev, struct sdw_slave *sdw,
 		ret = find_sdca_entity_ge(dev, entity_node, entity);
 		break;
 	case SDCA_ENTITY_TYPE_HIDE:
-		ret = find_sdca_entity_hide(dev, sdw, function_node,
-					    entity_node, entity);
+		ret = find_sdca_entity_hide(dev, function_node, entity_node, entity);
 		break;
 	default:
 		break;
@@ -1544,8 +1533,7 @@ static int find_sdca_entity(struct device *dev, struct sdw_slave *sdw,
 	return 0;
 }
 
-static int find_sdca_entities(struct device *dev, struct sdw_slave *sdw,
-			      struct fwnode_handle *function_node,
+static int find_sdca_entities(struct device *dev, struct fwnode_handle *function_node,
 			      struct sdca_function_data *function)
 {
 	struct sdca_entity *entities;
@@ -1596,7 +1584,7 @@ static int find_sdca_entities(struct device *dev, struct sdw_slave *sdw,
 			return -EINVAL;
 		}
 
-		ret = find_sdca_entity(dev, sdw, function, function_node,
+		ret = find_sdca_entity(dev, function, function_node,
 				       entity_node, &entities[i]);
 		fwnode_handle_put(entity_node);
 		if (ret)
@@ -2214,7 +2202,7 @@ int sdca_parse_function(struct device *dev, struct sdw_slave *sdw,
 	if (ret)
 		return ret;
 
-	ret = find_sdca_entities(dev, sdw, node, function);
+	ret = find_sdca_entities(dev, node, function);
 	if (ret)
 		return ret;
 
diff --git a/sound/soc/sdca/sdca_hid.c b/sound/soc/sdca/sdca_hid.c
index abbd56a3d2971..ea511c6f9798e 100644
--- a/sound/soc/sdca/sdca_hid.c
+++ b/sound/soc/sdca/sdca_hid.c
@@ -14,6 +14,7 @@
 #include <linux/module.h>
 #include <linux/property.h>
 #include <linux/soundwire/sdw.h>
+#include <linux/string.h>
 #include <linux/types.h>
 #include <sound/sdca.h>
 #include <sound/sdca_function.h>
@@ -85,10 +86,11 @@ static const struct hid_ll_driver sdw_hid_driver = {
 	.raw_request = sdwhid_raw_request,
 };
 
-int sdca_add_hid_device(struct device *dev, struct sdw_slave *sdw,
-			struct sdca_entity *entity)
+int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 {
-	struct sdw_bus *bus = sdw->bus;
+	struct device *dev = interrupt->dev;
+	struct sdca_function_data *function = interrupt->function;
+	struct sdca_entity *entity = interrupt->entity;
 	struct hid_device *hid;
 	int ret;
 
@@ -102,12 +104,9 @@ int sdca_add_hid_device(struct device *dev, struct sdw_slave *sdw,
 	hid->bus = BUS_SDW;
 	hid->version = le16_to_cpu(entity->hide.hid_desc.bcdHID);
 
-	snprintf(hid->name, sizeof(hid->name),
-		 "HID sdw:%01x:%01x:%04x:%04x:%02x",
-		 bus->controller_id, bus->link_id, sdw->id.mfg_id,
-		 sdw->id.part_id, sdw->id.class_id);
-
-	snprintf(hid->phys, sizeof(hid->phys), "%s", dev->bus->name);
+	strscpy(hid->phys, dev_name(dev));
+	snprintf(hid->name, sizeof(hid->name), "SDCA %s:%02x",
+		 function->desc->name, function->desc->adr);
 
 	hid->driver_data = entity;
 
@@ -118,7 +117,7 @@ int sdca_add_hid_device(struct device *dev, struct sdw_slave *sdw,
 		return ret;
 	}
 
-	entity->hide.hid = hid;
+	interrupt->priv = hid;
 
 	return 0;
 }
@@ -133,7 +132,7 @@ EXPORT_SYMBOL_NS(sdca_add_hid_device, "SND_SOC_SDCA");
 int sdca_hid_process_report(struct sdca_interrupt *interrupt)
 {
 	struct device *dev = interrupt->dev;
-	struct hid_device *hid = interrupt->entity->hide.hid;
+	struct hid_device *hid = interrupt->priv;
 	void *val __free(kfree) = NULL;
 	int len, ret;
 
diff --git a/sound/soc/sdca/sdca_interrupts.c b/sound/soc/sdca/sdca_interrupts.c
index 42fbd3af8a754..71037189a057c 100644
--- a/sound/soc/sdca/sdca_interrupts.c
+++ b/sound/soc/sdca/sdca_interrupts.c
@@ -487,6 +487,10 @@ int sdca_irq_populate_early(struct device *dev, struct regmap *regmap,
 				}
 				break;
 			case SDCA_CTL_TYPE_S(HIDE, HIDTX_CURRENTOWNER):
+				ret = sdca_add_hid_device(interrupt);
+				if (ret)
+					return ret;
+
 				interrupt->handler = hid_handler;
 				break;
 			default:
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 4/8] ASoC: SDCA: Move HID descriptors to function
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (2 preceding siblings ...)
  2026-08-05 12:42 ` [PATCH 3/8] ASoC: SDCA: Move HID registration to IRQ time Charles Keepax
@ 2026-08-05 12:42 ` Charles Keepax
  2026-08-05 12:42 ` [PATCH 5/8] ASoC: SDCA: Update HID DisCo parsing Charles Keepax
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:42 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

The HID descriptors are defined at the function level in DisCo
and as such it makes more sense to parse and store them at
that level in the SDCA code. This shouldn't really make much
practical difference but is conceptually better and avoids
passing the function node down to the entity parsing code.

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 include/sound/sdca_function.h   | 19 ++++++++--
 sound/soc/sdca/sdca_functions.c | 65 ++++++++++++++++++++++-----------
 sound/soc/sdca/sdca_hid.c       | 11 +++---
 3 files changed, 63 insertions(+), 32 deletions(-)

diff --git a/include/sound/sdca_function.h b/include/sound/sdca_function.h
index 35799a9771454..72441ed5eba49 100644
--- a/include/sound/sdca_function.h
+++ b/include/sound/sdca_function.h
@@ -1126,8 +1126,6 @@ struct sdca_entity_ge {
  * within this Device
  * @max_delay: the maximum time in microseconds allowed for the Device
  * to change the ownership from Device to Host
- * @hid_report_desc: HID Report Descriptor for the HIDE Entity
- * @hid_desc: HID descriptor for the HIDE Entity
  */
 struct sdca_entity_hide {
 	unsigned int *hidtx_ids;
@@ -1137,8 +1135,6 @@ struct sdca_entity_hide {
 	unsigned int af_number_list[SDCA_MAX_FUNCTION_COUNT];
 	unsigned int hide_reside_function_num;
 	unsigned int max_delay;
-	unsigned char *hid_report_desc;
-	struct hid_descriptor hid_desc;
 };
 
 /**
@@ -1399,6 +1395,16 @@ struct sdca_fdl_data {
 	int num_sets;
 };
 
+/**
+ * struct sdca_function_hid - information about a function's HID descriptors
+ * @report_desc: HID Report Descriptor for the HID Function
+ * @desc: HID descriptor for the HID Function
+ */
+struct sdca_function_hid {
+	unsigned char *report_desc;
+	struct hid_descriptor desc;
+};
+
 /**
  * struct sdca_function_data - top-level information for one SDCA function
  * @desc: Pointer to short descriptor from initial parsing.
@@ -1413,6 +1419,7 @@ struct sdca_fdl_data {
  * @reset_max_delay: Maximum Function reset delay in microseconds, before an
  * error should be reported.
  * @fdl_data: FDL data for this Function, if available.
+ * @hid: HID data for this Function, if available.
  */
 struct sdca_function_data {
 	struct sdca_function_desc *desc;
@@ -1428,6 +1435,10 @@ struct sdca_function_data {
 	unsigned int reset_max_delay;
 
 	struct sdca_fdl_data fdl_data;
+
+	union {
+		struct sdca_function_hid hid;
+	};
 };
 
 static inline u32 sdca_range(struct sdca_control_range *range,
diff --git a/sound/soc/sdca/sdca_functions.c b/sound/soc/sdca/sdca_functions.c
index e9b449b670332..e49acfe49e289 100644
--- a/sound/soc/sdca/sdca_functions.c
+++ b/sound/soc/sdca/sdca_functions.c
@@ -1364,14 +1364,13 @@ static int find_sdca_entity_ge(struct device *dev,
 	return -EINVAL;
 }
 
-static int
-find_sdca_entity_hide(struct device *dev, struct fwnode_handle *function_node,
-		      struct fwnode_handle *entity_node, struct sdca_entity *entity)
+static int find_sdca_entity_hide(struct device *dev,
+				 struct fwnode_handle *entity_node,
+				 struct sdca_entity *entity)
 {
 	struct sdca_entity_hide *hide = &entity->hide;
 	unsigned int delay, *af_list = hide->af_number_list;
 	int nval, ret;
-	unsigned char *report_desc = NULL;
 
 	ret = fwnode_property_read_u32(entity_node,
 				       "mipi-sdca-RxUMP-ownership-transition-max-delay", &delay);
@@ -1424,23 +1423,6 @@ find_sdca_entity_hide(struct device *dev, struct fwnode_handle *function_node,
 	fwnode_property_read_u32_array(entity_node,
 				       "mipi-sdca-hide-related-audio-function-list", af_list, nval);
 
-	nval = fwnode_property_count_u8(function_node, "mipi-sdca-hid-descriptor");
-	if (nval)
-		fwnode_property_read_u8_array(function_node, "mipi-sdca-hid-descriptor",
-					      (u8 *)&hide->hid_desc, nval);
-
-	if (hide->hid_desc.bNumDescriptors) {
-		nval = fwnode_property_count_u8(function_node, "mipi-sdca-report-descriptor");
-		if (nval) {
-			report_desc = devm_kzalloc(dev, nval, GFP_KERNEL);
-			if (!report_desc)
-				return -ENOMEM;
-			hide->hid_report_desc = report_desc;
-			fwnode_property_read_u8_array(function_node, "mipi-sdca-report-descriptor",
-						      report_desc, nval);
-		}
-	}
-
 	return 0;
 }
 
@@ -1518,7 +1500,7 @@ static int find_sdca_entity(struct device *dev, struct sdca_function_data *funct
 		ret = find_sdca_entity_ge(dev, entity_node, entity);
 		break;
 	case SDCA_ENTITY_TYPE_HIDE:
-		ret = find_sdca_entity_hide(dev, function_node, entity_node, entity);
+		ret = find_sdca_entity_hide(dev, entity_node, entity);
 		break;
 	default:
 		break;
@@ -2167,6 +2149,35 @@ static int find_sdca_filesets(struct device *dev, struct sdw_slave *sdw,
 	return 0;
 }
 
+static int find_sdca_hid(struct device *dev, struct fwnode_handle *function_node,
+			 struct sdca_function_data *function)
+{
+	int nval;
+
+	nval = fwnode_property_count_u8(function_node, "mipi-sdca-hid-descriptor");
+	if (nval)
+		fwnode_property_read_u8_array(function_node, "mipi-sdca-hid-descriptor",
+					      (u8 *)&function->hid.desc, nval);
+
+	if (function->hid.desc.bNumDescriptors) {
+		nval = fwnode_property_count_u8(function_node, "mipi-sdca-report-descriptor");
+		if (nval) {
+			unsigned char *report_desc;
+
+			report_desc = devm_kzalloc(dev, nval, GFP_KERNEL);
+			if (!report_desc)
+				return -ENOMEM;
+
+			function->hid.report_desc = report_desc;
+			fwnode_property_read_u8_array(function_node,
+						      "mipi-sdca-report-descriptor",
+						      report_desc, nval);
+		}
+	}
+
+	return 0;
+}
+
 /**
  * sdca_parse_function - parse ACPI DisCo for a Function
  * @dev: Pointer to device against which function data will be allocated.
@@ -2218,6 +2229,16 @@ int sdca_parse_function(struct device *dev, struct sdw_slave *sdw,
 	if (ret)
 		return ret;
 
+	switch (function->desc->type) {
+	case SDCA_FUNCTION_TYPE_HID:
+		ret = find_sdca_hid(dev, node, function);
+		if (ret)
+			return ret;
+		break;
+	default:
+		break;
+	}
+
 	return 0;
 }
 EXPORT_SYMBOL_NS(sdca_parse_function, "SND_SOC_SDCA");
diff --git a/sound/soc/sdca/sdca_hid.c b/sound/soc/sdca/sdca_hid.c
index ea511c6f9798e..5000d73657b41 100644
--- a/sound/soc/sdca/sdca_hid.c
+++ b/sound/soc/sdca/sdca_hid.c
@@ -24,18 +24,18 @@
 
 static int sdwhid_parse(struct hid_device *hid)
 {
-	struct sdca_entity *entity = hid->driver_data;
+	struct sdca_function_data *function = hid->driver_data;
 	unsigned int rsize;
 	int ret;
 
-	rsize = le16_to_cpu(entity->hide.hid_desc.rpt_desc.wDescriptorLength);
+	rsize = le16_to_cpu(function->hid.desc.rpt_desc.wDescriptorLength);
 
 	if (!rsize || rsize > HID_MAX_DESCRIPTOR_SIZE) {
 		dev_err(&hid->dev, "invalid size of report descriptor (%u)\n", rsize);
 		return -EINVAL;
 	}
 
-	ret = hid_parse_report(hid, entity->hide.hid_report_desc, rsize);
+	ret = hid_parse_report(hid, function->hid.report_desc, rsize);
 
 	if (!ret)
 		return 0;
@@ -90,7 +90,6 @@ int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 {
 	struct device *dev = interrupt->dev;
 	struct sdca_function_data *function = interrupt->function;
-	struct sdca_entity *entity = interrupt->entity;
 	struct hid_device *hid;
 	int ret;
 
@@ -102,13 +101,13 @@ int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 
 	hid->dev.parent = dev;
 	hid->bus = BUS_SDW;
-	hid->version = le16_to_cpu(entity->hide.hid_desc.bcdHID);
+	hid->version = le16_to_cpu(function->hid.desc.bcdHID);
 
 	strscpy(hid->phys, dev_name(dev));
 	snprintf(hid->name, sizeof(hid->name), "SDCA %s:%02x",
 		 function->desc->name, function->desc->adr);
 
-	hid->driver_data = entity;
+	hid->driver_data = function;
 
 	ret = hid_add_device(hid);
 	if (ret && ret != -ENODEV) {
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 5/8] ASoC: SDCA: Update HID DisCo parsing
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (3 preceding siblings ...)
  2026-08-05 12:42 ` [PATCH 4/8] ASoC: SDCA: Move HID descriptors to function Charles Keepax
@ 2026-08-05 12:42 ` Charles Keepax
  2026-08-05 12:42 ` [PATCH 6/8] ASoC: SDCA: Add missing destroy for HID device Charles Keepax
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:42 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

Add more error checking on the parsing of the HID DisCo and bring
the code more inline with the rest of the DisCo parsing.

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 sound/soc/sdca/sdca_functions.c | 119 ++++++++++++++++++++------------
 1 file changed, 74 insertions(+), 45 deletions(-)

diff --git a/sound/soc/sdca/sdca_functions.c b/sound/soc/sdca/sdca_functions.c
index e49acfe49e289..1196cc09389ae 100644
--- a/sound/soc/sdca/sdca_functions.c
+++ b/sound/soc/sdca/sdca_functions.c
@@ -7,6 +7,7 @@
  */
 
 #include <linux/acpi.h>
+#include <linux/array_size.h>
 #include <linux/byteorder/generic.h>
 #include <linux/cleanup.h>
 #include <linux/device.h>
@@ -1369,59 +1370,71 @@ static int find_sdca_entity_hide(struct device *dev,
 				 struct sdca_entity *entity)
 {
 	struct sdca_entity_hide *hide = &entity->hide;
-	unsigned int delay, *af_list = hide->af_number_list;
-	int nval, ret;
+	int num_reports, ret;
+	unsigned int delay;
 
 	ret = fwnode_property_read_u32(entity_node,
-				       "mipi-sdca-RxUMP-ownership-transition-max-delay", &delay);
+				       "mipi-sdca-RxUMP-ownership-transition-max-delay",
+				       &delay);
 	if (!ret)
 		hide->max_delay = delay;
 
-	nval = fwnode_property_count_u32(entity_node, "mipi-sdca-HIDTx-supported-report-ids");
-	if (nval > 0) {
-		hide->num_hidtx_ids = nval;
+	num_reports = fwnode_property_count_u32(entity_node,
+						"mipi-sdca-HIDTx-supported-report-ids");
+	if (num_reports < 0 && num_reports != -EINVAL) {
+		dev_err(dev, "%pfwP: failed to read hid tx ids: %d\n",
+			entity_node, num_reports);
+		return num_reports;
+	} else if (num_reports > 0) {
+		hide->num_hidtx_ids = num_reports;
 		hide->hidtx_ids = devm_kcalloc(dev, hide->num_hidtx_ids,
 					       sizeof(*hide->hidtx_ids), GFP_KERNEL);
 		if (!hide->hidtx_ids)
 			return -ENOMEM;
 
-		ret = fwnode_property_read_u32_array(entity_node,
-						     "mipi-sdca-HIDTx-supported-report-ids",
-						     hide->hidtx_ids,
-						     hide->num_hidtx_ids);
-		if (ret < 0)
-			return ret;
+		fwnode_property_read_u32_array(entity_node,
+					       "mipi-sdca-HIDTx-supported-report-ids",
+					       hide->hidtx_ids, hide->num_hidtx_ids);
 	}
 
-	nval = fwnode_property_count_u32(entity_node, "mipi-sdca-HIDRx-supported-report-ids");
-	if (nval > 0) {
-		hide->num_hidrx_ids = nval;
+	num_reports = fwnode_property_count_u32(entity_node,
+						"mipi-sdca-HIDRx-supported-report-ids");
+	if (num_reports < 0 && num_reports != -EINVAL) {
+		dev_err(dev, "%pfwP: failed to read hid rx ids: %d\n",
+			entity_node, num_reports);
+		return num_reports;
+	} else if (num_reports > 0) {
+		hide->num_hidrx_ids = num_reports;
 		hide->hidrx_ids = devm_kcalloc(dev, hide->num_hidrx_ids,
 					       sizeof(*hide->hidrx_ids), GFP_KERNEL);
 		if (!hide->hidrx_ids)
 			return -ENOMEM;
 
-		ret = fwnode_property_read_u32_array(entity_node,
-						     "mipi-sdca-HIDRx-supported-report-ids",
-						     hide->hidrx_ids,
-						     hide->num_hidrx_ids);
-		if (ret < 0)
-			return ret;
+		fwnode_property_read_u32_array(entity_node,
+					       "mipi-sdca-HIDRx-supported-report-ids",
+					       hide->hidrx_ids, hide->num_hidrx_ids);
 	}
 
-	nval = fwnode_property_count_u32(entity_node, "mipi-sdca-hide-related-audio-function-list");
-	if (nval <= 0) {
+	/*
+	 * FIXME: This should probably link to the actual sdca_function_data pointer,
+	 * but updating to do so should probably wait until we have a user.
+	 */
+	num_reports = fwnode_property_count_u32(entity_node,
+						"mipi-sdca-hide-related-audio-function-list");
+	if (num_reports <= 0) {
 		dev_err(dev, "%pfwP: audio function numbers list missing: %d\n",
-			entity_node, nval);
+			entity_node, num_reports);
 		return -EINVAL;
-	} else if (nval > SDCA_MAX_FUNCTION_COUNT) {
-		dev_err(dev, "%pfwP: maximum number of audio function exceeded\n", entity_node);
+	} else if (num_reports > ARRAY_SIZE(hide->af_number_list)) {
+		dev_err(dev, "%pfwP: maximum number of audio function exceeded\n",
+			entity_node);
 		return -EINVAL;
 	}
 
-	hide->hide_reside_function_num = nval;
+	hide->hide_reside_function_num = num_reports;
 	fwnode_property_read_u32_array(entity_node,
-				       "mipi-sdca-hide-related-audio-function-list", af_list, nval);
+				       "mipi-sdca-hide-related-audio-function-list",
+				       hide->af_number_list, num_reports);
 
 	return 0;
 }
@@ -2152,29 +2165,45 @@ static int find_sdca_filesets(struct device *dev, struct sdw_slave *sdw,
 static int find_sdca_hid(struct device *dev, struct fwnode_handle *function_node,
 			 struct sdca_function_data *function)
 {
-	int nval;
+	int num_desc;
 
-	nval = fwnode_property_count_u8(function_node, "mipi-sdca-hid-descriptor");
-	if (nval)
-		fwnode_property_read_u8_array(function_node, "mipi-sdca-hid-descriptor",
-					      (u8 *)&function->hid.desc, nval);
+	num_desc = fwnode_property_count_u8(function_node, "mipi-sdca-hid-descriptor");
+	if (!num_desc) {
+		return 0;
+	} else if (num_desc < 0) {
+		dev_err(dev, "%pfwP: failed to read hid descriptor: %d\n",
+			function_node, num_desc);
+		return num_desc;
+	} else if (num_desc > sizeof(function->hid.desc)) {
+		dev_err(dev, "%pfwP: hid descriptor too large: %d\n",
+			function_node, num_desc);
+		return -EINVAL;
+	}
 
-	if (function->hid.desc.bNumDescriptors) {
-		nval = fwnode_property_count_u8(function_node, "mipi-sdca-report-descriptor");
-		if (nval) {
-			unsigned char *report_desc;
+	fwnode_property_read_u8_array(function_node, "mipi-sdca-hid-descriptor",
+				      (u8 *)&function->hid.desc, num_desc);
 
-			report_desc = devm_kzalloc(dev, nval, GFP_KERNEL);
-			if (!report_desc)
-				return -ENOMEM;
+	if (!function->hid.desc.bNumDescriptors)
+		return 0;
 
-			function->hid.report_desc = report_desc;
-			fwnode_property_read_u8_array(function_node,
-						      "mipi-sdca-report-descriptor",
-						      report_desc, nval);
-		}
+	num_desc = fwnode_property_count_u8(function_node, "mipi-sdca-report-descriptor");
+	if (num_desc <= 0) {
+		dev_err(dev, "%pfwP: failed to read report descriptor: %d\n",
+			function_node, num_desc);
+
+		if (!num_desc)
+			return -EINVAL;
+
+		return num_desc;
 	}
 
+	function->hid.report_desc = devm_kzalloc(dev, num_desc, GFP_KERNEL);
+	if (!function->hid.report_desc)
+		return -ENOMEM;
+
+	fwnode_property_read_u8_array(function_node, "mipi-sdca-report-descriptor",
+				      function->hid.report_desc, num_desc);
+
 	return 0;
 }
 
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 6/8] ASoC: SDCA: Add missing destroy for HID device
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (4 preceding siblings ...)
  2026-08-05 12:42 ` [PATCH 5/8] ASoC: SDCA: Update HID DisCo parsing Charles Keepax
@ 2026-08-05 12:42 ` Charles Keepax
  2026-08-05 12:42 ` [PATCH 7/8] ASoC: SDCA: Add missing HID kernel doc Charles Keepax
                   ` (3 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:42 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

The SDCA code is currently missing a cleanup for HID devices when the
drivers are unbound. Add the missing HID cleanup as part of the IRQ
cleanup to mirror when the HID device is created.

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 include/sound/sdca_hid.h         |  5 +++++
 sound/soc/sdca/sdca_hid.c        | 12 ++++++++++++
 sound/soc/sdca/sdca_interrupts.c |  2 ++
 3 files changed, 19 insertions(+)

diff --git a/include/sound/sdca_hid.h b/include/sound/sdca_hid.h
index 83d1c7768133b..848081df3e4ec 100644
--- a/include/sound/sdca_hid.h
+++ b/include/sound/sdca_hid.h
@@ -17,6 +17,7 @@ struct sdca_interrupt;
 #if IS_ENABLED(CONFIG_SND_SOC_SDCA_HID)
 
 int sdca_add_hid_device(struct sdca_interrupt *interrupt);
+void sdca_destroy_hid_device(struct sdca_interrupt *interrupt);
 int sdca_hid_process_report(struct sdca_interrupt *interrupt);
 
 #else
@@ -26,6 +27,10 @@ static inline int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 	return 0;
 }
 
+static inline void sdca_destroy_hid_device(struct sdca_interrupt *interrupt)
+{
+}
+
 static inline int sdca_hid_process_report(struct sdca_interrupt *interrupt)
 {
 	return 0;
diff --git a/sound/soc/sdca/sdca_hid.c b/sound/soc/sdca/sdca_hid.c
index 5000d73657b41..514f895bd90de 100644
--- a/sound/soc/sdca/sdca_hid.c
+++ b/sound/soc/sdca/sdca_hid.c
@@ -122,6 +122,18 @@ int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 }
 EXPORT_SYMBOL_NS(sdca_add_hid_device, "SND_SOC_SDCA");
 
+/**
+ * sdca_destroy_hid_device - destroy the HID device
+ * @interrupt: Pointer to the SDCA interrupt information structure.
+ */
+void sdca_destroy_hid_device(struct sdca_interrupt *interrupt)
+{
+	struct hid_device *hid = interrupt->priv;
+
+	hid_destroy_device(hid);
+}
+EXPORT_SYMBOL_NS(sdca_destroy_hid_device, "SND_SOC_SDCA");
+
 /**
  * sdca_hid_process_report - read a HID event from the device and report
  * @interrupt: Pointer to the SDCA interrupt information structure.
diff --git a/sound/soc/sdca/sdca_interrupts.c b/sound/soc/sdca/sdca_interrupts.c
index 71037189a057c..7aebc721a847f 100644
--- a/sound/soc/sdca/sdca_interrupts.c
+++ b/sound/soc/sdca/sdca_interrupts.c
@@ -487,6 +487,8 @@ int sdca_irq_populate_early(struct device *dev, struct regmap *regmap,
 				}
 				break;
 			case SDCA_CTL_TYPE_S(HIDE, HIDTX_CURRENTOWNER):
+				interrupt->free_priv = sdca_destroy_hid_device;
+
 				ret = sdca_add_hid_device(interrupt);
 				if (ret)
 					return ret;
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 7/8] ASoC: SDCA: Add missing HID kernel doc
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (5 preceding siblings ...)
  2026-08-05 12:42 ` [PATCH 6/8] ASoC: SDCA: Add missing destroy for HID device Charles Keepax
@ 2026-08-05 12:42 ` Charles Keepax
  2026-08-05 12:42 ` [PATCH 8/8] ASoC: SDCA: Pass swft table through sdca_dev_register() Charles Keepax
                   ` (2 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:42 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

Add missing kernel doc for the function sdca_add_hid_device()

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 sound/soc/sdca/sdca_hid.c | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/sound/soc/sdca/sdca_hid.c b/sound/soc/sdca/sdca_hid.c
index 514f895bd90de..bee1b83c05f21 100644
--- a/sound/soc/sdca/sdca_hid.c
+++ b/sound/soc/sdca/sdca_hid.c
@@ -86,6 +86,12 @@ static const struct hid_ll_driver sdw_hid_driver = {
 	.raw_request = sdwhid_raw_request,
 };
 
+/**
+ * sdca_add_hid_device - create a new SDCA HID device
+ * @interrupt: Pointer to the SDCA interrupt information structure.
+ *
+ * Return: Zero on success, and a negative error code on failure.
+ */
 int sdca_add_hid_device(struct sdca_interrupt *interrupt)
 {
 	struct device *dev = interrupt->dev;
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* [PATCH 8/8] ASoC: SDCA: Pass swft table through sdca_dev_register()
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (6 preceding siblings ...)
  2026-08-05 12:42 ` [PATCH 7/8] ASoC: SDCA: Add missing HID kernel doc Charles Keepax
@ 2026-08-05 12:42 ` Charles Keepax
  2026-08-06  8:57 ` [PATCH 0/8] Reword the SDCA HID code Pierre-Louis Bossart
  2026-08-06 12:42 ` Mark Brown
  9 siblings, 0 replies; 11+ messages in thread
From: Charles Keepax @ 2026-08-05 12:42 UTC (permalink / raw)
  To: broonie
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

Rather than passing the SoundWire slave into find_sdca_filesets(),
stash the swift table whilst processing sdca_dev_register(). This
allows us to completely remove the passing of the sdw_slave into
the ACPI parsing code.

Signed-off-by: Charles Keepax <ckeepax@opensource.cirrus.com>
---
 include/sound/sdca_function.h         |  3 +--
 sound/soc/codecs/rt766-sdca.c         |  2 +-
 sound/soc/codecs/tac5xx2-sdw.c        |  2 +-
 sound/soc/codecs/tas2783-sdw.c        |  2 +-
 sound/soc/sdca/sdca_class_function.c  |  2 +-
 sound/soc/sdca/sdca_function_device.c |  7 +++++--
 sound/soc/sdca/sdca_functions.c       | 10 +++-------
 7 files changed, 13 insertions(+), 15 deletions(-)

diff --git a/include/sound/sdca_function.h b/include/sound/sdca_function.h
index 72441ed5eba49..f65a1d6784e81 100644
--- a/include/sound/sdca_function.h
+++ b/include/sound/sdca_function.h
@@ -1460,8 +1460,7 @@ static inline u32 sdca_range_search(struct sdca_control_range *range,
 	return 0;
 }
 
-int sdca_parse_function(struct device *dev, struct sdw_slave *sdw,
-			struct sdca_function_data *function);
+int sdca_parse_function(struct device *dev, struct sdca_function_data *function);
 
 const char *sdca_find_terminal_name(enum sdca_terminal_type type);
 
diff --git a/sound/soc/codecs/rt766-sdca.c b/sound/soc/codecs/rt766-sdca.c
index 54ed0c42fba2f..64d763b96a061 100644
--- a/sound/soc/codecs/rt766-sdca.c
+++ b/sound/soc/codecs/rt766-sdca.c
@@ -1201,7 +1201,7 @@ int rt766_sdca_init(struct device *dev, struct regmap *regmap, struct sdw_slave
 		}
 
 		func_data_ptr->desc = &slave->sdca_data.function[i];
-		ret = sdca_parse_function(dev, slave, func_data_ptr);
+		ret = sdca_parse_function(dev, func_data_ptr);
 		if (ret) {
 			devm_kfree(dev, func_data_ptr);
 			goto _free_dai_drv_;
diff --git a/sound/soc/codecs/tac5xx2-sdw.c b/sound/soc/codecs/tac5xx2-sdw.c
index ea0408b71713b..fdb6213d13603 100644
--- a/sound/soc/codecs/tac5xx2-sdw.c
+++ b/sound/soc/codecs/tac5xx2-sdw.c
@@ -1940,7 +1940,7 @@ static s32 tac_sdw_probe(struct sdw_slave *peripheral,
 						     "failed to allocate %s function data",
 						     func_name);
 			function_data->desc = &peripheral->sdca_data.function[i];
-			ret = sdca_parse_function(dev, peripheral, function_data);
+			ret = sdca_parse_function(dev, function_data);
 			if (!ret)
 				*func_ptr = function_data;
 			else
diff --git a/sound/soc/codecs/tas2783-sdw.c b/sound/soc/codecs/tas2783-sdw.c
index 34f17e063fa3e..94f11e3b0c207 100644
--- a/sound/soc/codecs/tas2783-sdw.c
+++ b/sound/soc/codecs/tas2783-sdw.c
@@ -1348,7 +1348,7 @@ static s32 tas_sdw_probe(struct sdw_slave *peripheral,
 		function_data->desc = &peripheral->sdca_data.function[i];
 
 		/* Parse the function */
-		ret = sdca_parse_function(dev, peripheral, function_data);
+		ret = sdca_parse_function(dev, function_data);
 		if (!ret)
 			tas_dev->sa_func_data = function_data;
 		else
diff --git a/sound/soc/sdca/sdca_class_function.c b/sound/soc/sdca/sdca_class_function.c
index 2fb2b043c979c..cc7045dc26e6b 100644
--- a/sound/soc/sdca/sdca_class_function.c
+++ b/sound/soc/sdca/sdca_class_function.c
@@ -329,7 +329,7 @@ static int class_function_probe(struct auxiliary_device *auxdev,
 	drv->core = core;
 	drv->function = &sdev->function;
 
-	ret = sdca_parse_function(dev, core->sdw, drv->function);
+	ret = sdca_parse_function(dev, drv->function);
 	if (ret)
 		return ret;
 
diff --git a/sound/soc/sdca/sdca_function_device.c b/sound/soc/sdca/sdca_function_device.c
index b5ca98283a889..54604872ae0d8 100644
--- a/sound/soc/sdca/sdca_function_device.c
+++ b/sound/soc/sdca/sdca_function_device.c
@@ -32,7 +32,8 @@ static void sdca_dev_release(struct device *dev)
 
 /* alloc, init and add link devices */
 static struct sdca_dev *sdca_dev_register(struct device *parent,
-					  struct sdca_function_desc *function_desc)
+					  struct sdca_function_desc *function_desc,
+					  struct acpi_table_swft *swft)
 {
 	struct sdca_dev *sdev;
 	struct auxiliary_device *auxdev;
@@ -50,6 +51,7 @@ static struct sdca_dev *sdca_dev_register(struct device *parent,
 	auxdev->dev.release = sdca_dev_release;
 
 	sdev->function.desc = function_desc;
+	sdev->function.fdl_data.swft = swft;
 
 	rc = ida_alloc(&sdca_function_ida, GFP_KERNEL);
 	if (rc < 0) {
@@ -99,7 +101,8 @@ int sdca_dev_register_functions(struct sdw_slave *slave)
 		struct sdca_dev *func_dev;
 
 		func_dev = sdca_dev_register(&slave->dev,
-					     &sdca_data->function[i]);
+					     &sdca_data->function[i],
+					     sdca_data->swft);
 		if (IS_ERR(func_dev)) {
 			ret = PTR_ERR(func_dev);
 			/*
diff --git a/sound/soc/sdca/sdca_functions.c b/sound/soc/sdca/sdca_functions.c
index 1196cc09389ae..e01d91eb3cc81 100644
--- a/sound/soc/sdca/sdca_functions.c
+++ b/sound/soc/sdca/sdca_functions.c
@@ -2072,8 +2072,7 @@ static int find_sdca_clusters(struct device *dev,
 	return 0;
 }
 
-static int find_sdca_filesets(struct device *dev, struct sdw_slave *sdw,
-			      struct fwnode_handle *function_node,
+static int find_sdca_filesets(struct device *dev, struct fwnode_handle *function_node,
 			      struct sdca_function_data *function)
 {
 	static const int mult_fileset = 3;
@@ -2155,7 +2154,6 @@ static int find_sdca_filesets(struct device *dev, struct sdw_slave *sdw,
 		set->files = files;
 	}
 
-	function->fdl_data.swft = sdw->sdca_data.swft;
 	function->fdl_data.num_sets = num_sets;
 	function->fdl_data.sets = sets;
 
@@ -2210,13 +2208,11 @@ static int find_sdca_hid(struct device *dev, struct fwnode_handle *function_node
 /**
  * sdca_parse_function - parse ACPI DisCo for a Function
  * @dev: Pointer to device against which function data will be allocated.
- * @sdw: SoundWire slave device to be processed.
  * @function: Pointer to the Function information, to be populated.
  *
  * Return: Returns 0 for success.
  */
-int sdca_parse_function(struct device *dev, struct sdw_slave *sdw,
-			struct sdca_function_data *function)
+int sdca_parse_function(struct device *dev, struct sdca_function_data *function)
 {
 	struct fwnode_handle *node = function->desc->node;
 	u32 tmp;
@@ -2254,7 +2250,7 @@ int sdca_parse_function(struct device *dev, struct sdw_slave *sdw,
 	if (ret < 0)
 		return ret;
 
-	ret = find_sdca_filesets(dev, sdw, node, function);
+	ret = find_sdca_filesets(dev, node, function);
 	if (ret)
 		return ret;
 
-- 
2.47.3


^ permalink raw reply related	[flat|nested] 11+ messages in thread

* Re: [PATCH 0/8] Reword the SDCA HID code
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (7 preceding siblings ...)
  2026-08-05 12:42 ` [PATCH 8/8] ASoC: SDCA: Pass swft table through sdca_dev_register() Charles Keepax
@ 2026-08-06  8:57 ` Pierre-Louis Bossart
  2026-08-06 12:42 ` Mark Brown
  9 siblings, 0 replies; 11+ messages in thread
From: Pierre-Louis Bossart @ 2026-08-06  8:57 UTC (permalink / raw)
  To: Charles Keepax, broonie
  Cc: lgirdwood, yung-chuan.liao, shenghao-ding, kevin-lu, baojun.xu,
	sen, niranjan.hy, oder_chiou, shumingf, linux-sound, linux-kernel,
	patches

On 8/5/26 14:41, Charles Keepax wrote:
> This series reworks the SDCA HID code, the primary goals being to no
> longer store runtime HID data in the DisCo data structures and remove
> the need to pass the soundwire device into the ACPI parsing code.
> 
> To achieve this the HID device registration is moved to the IRQ work
> flow rather than the ACPI work flow.
> 
> Also a few small issues are fixed up along the way, some formatting,
> some missing cleanup/docs.
> 
> Thanks,
> Charles
> 
> Charles Keepax (8):
>   ASoC: SDCA: Tidy up error message
>   ASoC: SDCA: Remove unused dev pointer argument
>   ASoC: SDCA: Move HID registration to IRQ time
>   ASoC: SDCA: Move HID descriptors to function
>   ASoC: SDCA: Update HID DisCo parsing
>   ASoC: SDCA: Add missing destroy for HID device
>   ASoC: SDCA: Add missing HID kernel doc
>   ASoC: SDCA: Pass swft table through sdca_dev_register()


LGTM

Reviewed-by: Pierre-Louis Bossart <pierre-louis.bossart@linux.dev>


^ permalink raw reply	[flat|nested] 11+ messages in thread

* Re: [PATCH 0/8] Reword the SDCA HID code
  2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
                   ` (8 preceding siblings ...)
  2026-08-06  8:57 ` [PATCH 0/8] Reword the SDCA HID code Pierre-Louis Bossart
@ 2026-08-06 12:42 ` Mark Brown
  9 siblings, 0 replies; 11+ messages in thread
From: Mark Brown @ 2026-08-06 12:42 UTC (permalink / raw)
  To: Charles Keepax
  Cc: lgirdwood, yung-chuan.liao, pierre-louis.bossart, shenghao-ding,
	kevin-lu, baojun.xu, sen, niranjan.hy, oder_chiou, shumingf,
	linux-sound, linux-kernel, patches

On Wed, 05 Aug 2026 13:41:57 +0100, Charles Keepax wrote:
> Reword the SDCA HID code
> 
> This series reworks the SDCA HID code, the primary goals being to no
> longer store runtime HID data in the DisCo data structures and remove
> the need to pass the soundwire device into the ACPI parsing code.
> 
> To achieve this the HID device registration is moved to the IRQ work
> flow rather than the ACPI work flow.
> 
> [...]

Applied to

   https://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound.git for-7.3

Thanks!

[1/8] ASoC: SDCA: Tidy up error message
      https://git.kernel.org/broonie/sound/c/6a236928b43c
[2/8] ASoC: SDCA: Remove unused dev pointer argument
      https://git.kernel.org/broonie/sound/c/3dcc74d51b22
[3/8] ASoC: SDCA: Move HID registration to IRQ time
      https://git.kernel.org/broonie/sound/c/c03f0b9a7d99
[4/8] ASoC: SDCA: Move HID descriptors to function
      https://git.kernel.org/broonie/sound/c/f3243b79026e
[5/8] ASoC: SDCA: Update HID DisCo parsing
      https://git.kernel.org/broonie/sound/c/01dba3e93486
[6/8] ASoC: SDCA: Add missing destroy for HID device
      https://git.kernel.org/broonie/sound/c/df1fd5d8ab40
[7/8] ASoC: SDCA: Add missing HID kernel doc
      https://git.kernel.org/broonie/sound/c/3ede9e98ca1c
[8/8] ASoC: SDCA: Pass swft table through sdca_dev_register()
      https://git.kernel.org/broonie/sound/c/a50e530e05fa

All being well this means that it will be integrated into the linux-next
tree (usually sometime in the next 24 hours) and sent to Linus during
the next merge window (or sooner if it is a bug fix), however if
problems are discovered then the patch may be dropped or reverted.

You may get further e-mails resulting from automated or manual testing
and review of the tree, please engage with people reporting problems and
send followup patches addressing any issues that are reported if needed.

If any updates are required or you are submitting further changes they
should be sent as incremental updates against current git, existing
patches will not be replaced.

Please add any relevant lists and maintainers to the CCs when replying
to this mail.

Thanks,
Mark


^ permalink raw reply	[flat|nested] 11+ messages in thread

end of thread, other threads:[~2026-08-06 17:58 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-08-05 12:41 [PATCH 0/8] Reword the SDCA HID code Charles Keepax
2026-08-05 12:41 ` [PATCH 1/8] ASoC: SDCA: Tidy up error message Charles Keepax
2026-08-05 12:41 ` [PATCH 2/8] ASoC: SDCA: Remove unused dev pointer argument Charles Keepax
2026-08-05 12:42 ` [PATCH 3/8] ASoC: SDCA: Move HID registration to IRQ time Charles Keepax
2026-08-05 12:42 ` [PATCH 4/8] ASoC: SDCA: Move HID descriptors to function Charles Keepax
2026-08-05 12:42 ` [PATCH 5/8] ASoC: SDCA: Update HID DisCo parsing Charles Keepax
2026-08-05 12:42 ` [PATCH 6/8] ASoC: SDCA: Add missing destroy for HID device Charles Keepax
2026-08-05 12:42 ` [PATCH 7/8] ASoC: SDCA: Add missing HID kernel doc Charles Keepax
2026-08-05 12:42 ` [PATCH 8/8] ASoC: SDCA: Pass swft table through sdca_dev_register() Charles Keepax
2026-08-06  8:57 ` [PATCH 0/8] Reword the SDCA HID code Pierre-Louis Bossart
2026-08-06 12:42 ` Mark Brown

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox