Linux Sound subsystem development
 help / color / mirror / Atom feed
From: Pierre-Louis Bossart <pierre-louis.bossart@linux.dev>
To: Bard Liao <yung-chuan.liao@linux.intel.com>,
	linux-sound@vger.kernel.org, vkoul@kernel.org
Cc: vinod.koul@linaro.org, linux-kernel@vger.kernel.org,
	peter.ujfalusi@linux.intel.com, bard.liao@intel.com
Subject: Re: [PATCH 1/2] soundwire: bus: add CLOCK_STOP_MODE1 support back
Date: Tue, 30 Jun 2026 11:42:49 +0200	[thread overview]
Message-ID: <ca8eb233-0e40-4900-aaca-69b8fe783f06@linux.dev> (raw)
In-Reply-To: <20260629144450.2096823-2-yung-chuan.liao@linux.intel.com>

On 6/29/26 16:44, Bard Liao wrote:
> CLOCK_STOP_MODE1 is used when the Peripheral might have entered a deeper
> power-saving mode that does not retain state while the Clock is stopped.
> It is useful when the device is more power consumption sensitive. Add it
> back to allow the Peripheral use CLOCK_STOP_MODE1.
> 
> Signed-off-by: Bard Liao <yung-chuan.liao@linux.intel.com>
> Reviewed-by: Péter Ujfalusi <peter.ujfalusi@linux.intel.com>

This patch looks fine with the understanding that the DisCo property is defined on a system-by-system basis and isn't a codec property extracted from a datasheet.

If it was a codec property, this could be problematic in some cases. For example in a latency-constrained environment, the host could require peripherals to use the clock-stop mode0 to restart faster, even if this means writing-off power saving that the peripheral supports.

In other words, if the OEMs use a copy-pasted DisCo definition this could be problematic, and at some point we may have to discard the codec property. For now it's fine, so here's my

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

> ---
>  drivers/soundwire/bus.c       | 45 +++++++++++++++++++----------------
>  include/linux/soundwire/sdw.h |  4 ++++
>  2 files changed, 29 insertions(+), 20 deletions(-)
> 
> diff --git a/drivers/soundwire/bus.c b/drivers/soundwire/bus.c
> index 0490777fa406..21d8d6d7147a 100644
> --- a/drivers/soundwire/bus.c
> +++ b/drivers/soundwire/bus.c
> @@ -956,8 +956,22 @@ static void sdw_modify_slave_status(struct sdw_slave *slave,
>  	mutex_unlock(&bus->bus_lock);
>  }
>  
> +static enum sdw_clk_stop_mode sdw_get_clk_stop_mode(struct sdw_slave *slave)
> +{
> +	struct device *dev = &slave->dev;
> +	struct sdw_driver *drv = drv_to_sdw_driver(dev->driver);
> +
> +	/*
> +	 * Query for clock stop mode if Slave implements
> +	 * ops->get_clk_stop_mode, else read from property.
> +	 */
> +	if (drv->ops && drv->ops->get_clk_stop_mode)
> +		return drv->ops->get_clk_stop_mode(slave);
> +
> +	return slave->prop.clk_stop_mode1 ? SDW_CLK_STOP_MODE1 : SDW_CLK_STOP_MODE0;
> +}
> +
>  static int sdw_slave_clk_stop_callback(struct sdw_slave *slave,
> -				       enum sdw_clk_stop_mode mode,
>  				       enum sdw_clk_stop_type type)
>  {
>  	int ret = 0;
> @@ -969,7 +983,7 @@ static int sdw_slave_clk_stop_callback(struct sdw_slave *slave,
>  		struct sdw_driver *drv = drv_to_sdw_driver(dev->driver);
>  
>  		if (drv->ops && drv->ops->clk_stop)
> -			ret = drv->ops->clk_stop(slave, mode, type);
> +			ret = drv->ops->clk_stop(slave, slave->clk_stop_mode, type);
>  	}
>  
>  	mutex_unlock(&slave->sdw_dev_lock);
> @@ -978,7 +992,6 @@ static int sdw_slave_clk_stop_callback(struct sdw_slave *slave,
>  }
>  
>  static int sdw_slave_clk_stop_prepare(struct sdw_slave *slave,
> -				      enum sdw_clk_stop_mode mode,
>  				      bool prepare)
>  {
>  	bool wake_en;
> @@ -990,7 +1003,7 @@ static int sdw_slave_clk_stop_prepare(struct sdw_slave *slave,
>  	if (prepare) {
>  		val = SDW_SCP_SYSTEMCTRL_CLK_STP_PREP;
>  
> -		if (mode == SDW_CLK_STOP_MODE1)
> +		if (slave->clk_stop_mode == SDW_CLK_STOP_MODE1)
>  			val |= SDW_SCP_SYSTEMCTRL_CLK_STP_MODE1;
>  
>  		if (wake_en)
> @@ -1078,9 +1091,9 @@ int sdw_bus_prep_clk_stop(struct sdw_bus *bus)
>  		/* Identify if Slave(s) are available on Bus */
>  		is_slave = true;
>  
> -		ret = sdw_slave_clk_stop_callback(slave,
> -						  SDW_CLK_STOP_MODE0,
> -						  SDW_CLK_PRE_PREPARE);
> +		slave->clk_stop_mode = sdw_get_clk_stop_mode(slave);
> +
> +		ret = sdw_slave_clk_stop_callback(slave, SDW_CLK_PRE_PREPARE);
>  		if (ret < 0 && ret != -ENODATA) {
>  			dev_err(&slave->dev, "clock stop pre-prepare cb failed:%d\n", ret);
>  			return ret;
> @@ -1090,9 +1103,7 @@ int sdw_bus_prep_clk_stop(struct sdw_bus *bus)
>  		if (!slave->prop.simple_clk_stop_capable) {
>  			simple_clk_stop = false;
>  
> -			ret = sdw_slave_clk_stop_prepare(slave,
> -							 SDW_CLK_STOP_MODE0,
> -							 true);
> +			ret = sdw_slave_clk_stop_prepare(slave, true);
>  			if (ret < 0 && ret != -ENODATA) {
>  				dev_err(&slave->dev, "clock stop prepare failed:%d\n", ret);
>  				return ret;
> @@ -1130,9 +1141,7 @@ int sdw_bus_prep_clk_stop(struct sdw_bus *bus)
>  		    slave->status != SDW_SLAVE_ALERT)
>  			continue;
>  
> -		ret = sdw_slave_clk_stop_callback(slave,
> -						  SDW_CLK_STOP_MODE0,
> -						  SDW_CLK_POST_PREPARE);
> +		ret = sdw_slave_clk_stop_callback(slave, SDW_CLK_POST_PREPARE);
>  
>  		if (ret < 0 && ret != -ENODATA) {
>  			dev_err(&slave->dev, "clock stop post-prepare cb failed:%d\n", ret);
> @@ -1204,8 +1213,7 @@ int sdw_bus_exit_clk_stop(struct sdw_bus *bus)
>  		/* Identify if Slave(s) are available on Bus */
>  		is_slave = true;
>  
> -		ret = sdw_slave_clk_stop_callback(slave, SDW_CLK_STOP_MODE0,
> -						  SDW_CLK_PRE_DEPREPARE);
> +		ret = sdw_slave_clk_stop_callback(slave, SDW_CLK_PRE_DEPREPARE);
>  		if (ret < 0)
>  			dev_warn(&slave->dev, "clock stop pre-deprepare cb failed:%d\n", ret);
>  
> @@ -1213,9 +1221,7 @@ int sdw_bus_exit_clk_stop(struct sdw_bus *bus)
>  		if (!slave->prop.simple_clk_stop_capable) {
>  			simple_clk_stop = false;
>  
> -			ret = sdw_slave_clk_stop_prepare(slave, SDW_CLK_STOP_MODE0,
> -							 false);
> -
> +			ret = sdw_slave_clk_stop_prepare(slave, false);
>  			if (ret < 0)
>  				dev_warn(&slave->dev, "clock stop deprepare failed:%d\n", ret);
>  		}
> @@ -1243,8 +1249,7 @@ int sdw_bus_exit_clk_stop(struct sdw_bus *bus)
>  		    slave->status != SDW_SLAVE_ALERT)
>  			continue;
>  
> -		ret = sdw_slave_clk_stop_callback(slave, SDW_CLK_STOP_MODE0,
> -						  SDW_CLK_POST_DEPREPARE);
> +		ret = sdw_slave_clk_stop_callback(slave, SDW_CLK_POST_DEPREPARE);
>  		if (ret < 0)
>  			dev_warn(&slave->dev, "clock stop post-deprepare cb failed:%d\n", ret);
>  	}
> diff --git a/include/linux/soundwire/sdw.h b/include/linux/soundwire/sdw.h
> index b484784e2690..c1d2fc69bed5 100644
> --- a/include/linux/soundwire/sdw.h
> +++ b/include/linux/soundwire/sdw.h
> @@ -612,6 +612,7 @@ struct sdw_bus_params {
>   * @update_status: Update Slave status
>   * @bus_config: Update the bus config for Slave
>   * @port_prep: Prepare the port with parameters
> + * @get_clk_stop_mode: Get the clock stop mode of the Slave
>   * @clk_stop: handle imp-def sequences before and after prepare and de-prepare
>   */
>  struct sdw_slave_ops {
> @@ -625,6 +626,7 @@ struct sdw_slave_ops {
>  	int (*port_prep)(struct sdw_slave *slave,
>  			 struct sdw_prepare_ch *prepare_ch,
>  			 enum sdw_port_prep_ops pre_ops);
> +	enum sdw_clk_stop_mode (*get_clk_stop_mode)(struct sdw_slave *slave);
>  	int (*clk_stop)(struct sdw_slave *slave,
>  			enum sdw_clk_stop_mode mode,
>  			enum sdw_clk_stop_type type);
> @@ -643,6 +645,7 @@ struct sdw_slave_ops {
>   * @node: node for bus list
>   * @port_ready: Port ready completion flag for each Slave port
>   * @m_port_map: static Master port map for each Slave port
> + * @clk_stop_mode: The clock stop mode of the Slave
>   * @dev_num: Current Device Number, values can be 0 or dev_num_sticky
>   * @dev_num_sticky: one-time static Device Number assigned by Bus
>   * @probed: boolean tracking driver state
> @@ -677,6 +680,7 @@ struct sdw_slave {
>  	struct list_head node;
>  	struct completion port_ready[SDW_MAX_PORTS];
>  	unsigned int m_port_map[SDW_MAX_PORTS];
> +	enum sdw_clk_stop_mode clk_stop_mode;
>  	u16 dev_num;
>  	u16 dev_num_sticky;
>  	bool probed;


  reply	other threads:[~2026-06-30  9:44 UTC|newest]

Thread overview: 16+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-06-29 14:44 [PATCH 0/2] soundwire: bus: re-enable CLOCK_STOP_MODE1 support Bard Liao
2026-06-29 14:44 ` [PATCH 1/2] soundwire: bus: add CLOCK_STOP_MODE1 support back Bard Liao
2026-06-30  9:42   ` Pierre-Louis Bossart [this message]
2026-06-29 14:44 ` [PATCH 2/2] soundwire: Intel: stop sdw clock in system suspend Bard Liao
2026-06-30  9:33   ` Pierre-Louis Bossart
2026-06-30 10:35     ` Liao, Bard
2026-06-30 10:51       ` Richard Fitzgerald
2026-06-30 12:36         ` Pierre-Louis Bossart
2026-06-30 12:50           ` Richard Fitzgerald
2026-07-01 11:55             ` Pierre-Louis Bossart
2026-07-01 12:00               ` Pierre-Louis Bossart
2026-07-01 12:30                 ` Liao, Bard
2026-07-01 12:36                 ` Richard Fitzgerald
2026-07-01 12:15               ` Richard Fitzgerald
2026-07-01 14:09                 ` Pierre-Louis Bossart
2026-07-01 14:59                   ` Richard Fitzgerald

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=ca8eb233-0e40-4900-aaca-69b8fe783f06@linux.dev \
    --to=pierre-louis.bossart@linux.dev \
    --cc=bard.liao@intel.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-sound@vger.kernel.org \
    --cc=peter.ujfalusi@linux.intel.com \
    --cc=vinod.koul@linaro.org \
    --cc=vkoul@kernel.org \
    --cc=yung-chuan.liao@linux.intel.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox