All of lore.kernel.org
 help / color / mirror / Atom feed
From: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
To: Bhaumik Bhatt <bbhatt@codeaurora.org>
Cc: linux-arm-msm@vger.kernel.org, hemantk@codeaurora.org,
	jhugo@codeaurora.org, linux-kernel@vger.kernel.org,
	loic.poulain@linaro.org
Subject: Re: [PATCH v5 3/9] bus: mhi: core: Improvements to the channel handling state machine
Date: Thu, 21 Jan 2021 20:13:02 +0530	[thread overview]
Message-ID: <20210121144302.GA5473@work> (raw)
In-Reply-To: <1610139297-36435-4-git-send-email-bbhatt@codeaurora.org>

On Fri, Jan 08, 2021 at 12:54:51PM -0800, Bhaumik Bhatt wrote:
> Improve the channel handling state machine such that all commands
> go through a common function and validation process to ensure
> that the state machine is not violated in any way and adheres to
> the MHI specification.
> 
> Signed-off-by: Bhaumik Bhatt <bbhatt@codeaurora.org>
> Reviewed-by: Hemant Kumar <hemantk@codeaurora.org>
> ---
>  drivers/bus/mhi/core/init.c     |   6 ++
>  drivers/bus/mhi/core/internal.h |  12 +++
>  drivers/bus/mhi/core/main.c     | 166 +++++++++++++++++++++++-----------------
>  3 files changed, 114 insertions(+), 70 deletions(-)
> 
> diff --git a/drivers/bus/mhi/core/init.c b/drivers/bus/mhi/core/init.c
> index 03c5786..482b365 100644
> --- a/drivers/bus/mhi/core/init.c
> +++ b/drivers/bus/mhi/core/init.c
> @@ -54,6 +54,12 @@ const char * const mhi_state_str[MHI_STATE_MAX] = {
>  	[MHI_STATE_SYS_ERR] = "SYS_ERR",
>  };
>  
> +const char * const mhi_ch_state_type_str[MHI_CH_STATE_TYPE_MAX] = {
> +	[MHI_CH_STATE_TYPE_RESET] = "RESET",
> +	[MHI_CH_STATE_TYPE_STOP] = "STOP",
> +	[MHI_CH_STATE_TYPE_START] = "START",
> +};
> +
>  static const char * const mhi_pm_state_str[] = {
>  	[MHI_PM_STATE_DISABLE] = "DISABLE",
>  	[MHI_PM_STATE_POR] = "POR",
> diff --git a/drivers/bus/mhi/core/internal.h b/drivers/bus/mhi/core/internal.h
> index 6f80ec3..7e3aac1 100644
> --- a/drivers/bus/mhi/core/internal.h
> +++ b/drivers/bus/mhi/core/internal.h
> @@ -369,6 +369,18 @@ enum mhi_ch_state {
>  	MHI_CH_STATE_ERROR = 0x5,
>  };
>  
> +enum mhi_ch_state_type {
> +	MHI_CH_STATE_TYPE_RESET,
> +	MHI_CH_STATE_TYPE_STOP,
> +	MHI_CH_STATE_TYPE_START,
> +	MHI_CH_STATE_TYPE_MAX,
> +};
> +
> +extern const char * const mhi_ch_state_type_str[MHI_CH_STATE_TYPE_MAX];
> +#define TO_CH_STATE_TYPE_STR(state) (((state) >= MHI_CH_STATE_TYPE_MAX) ? \
> +				     "INVALID_STATE" : \
> +				     mhi_ch_state_type_str[(state)])
> +
>  #define MHI_INVALID_BRSTMODE(mode) (mode != MHI_DB_BRST_DISABLE && \
>  				    mode != MHI_DB_BRST_ENABLE)
>  
> diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
> index c22d7df..081fdf0 100644
> --- a/drivers/bus/mhi/core/main.c
> +++ b/drivers/bus/mhi/core/main.c
> @@ -1250,56 +1250,118 @@ int mhi_send_cmd(struct mhi_controller *mhi_cntrl,
>  	return 0;
>  }
>  
> -static void __mhi_unprepare_channel(struct mhi_controller *mhi_cntrl,
> -				    struct mhi_chan *mhi_chan)
> +static int mhi_update_channel_state(struct mhi_controller *mhi_cntrl,
> +				    struct mhi_chan *mhi_chan,
> +				    enum mhi_ch_state_type to_state)
>  {
> -	int ret;
>  	struct device *dev = &mhi_cntrl->mhi_dev->dev;
> +	enum mhi_cmd_type cmd = MHI_CMD_NOP;
> +	int ret = -EIO;
> +
> +	dev_dbg(dev, "Updating channel %s(%d) state to: %s\n", mhi_chan->name,
> +		mhi_chan->chan, TO_CH_STATE_TYPE_STR(to_state));

Instead of explicitly using the channel name and its id, you should be
able to use `mhi_chan->mhi_dev->dev` so that dev_dbg() can provide that
information for you. For instance,

mhi0_IPCR: Updating channel state to RESET

Do it for all instances below.

> +
> +	switch (to_state) {
> +	case MHI_CH_STATE_TYPE_RESET:
> +		write_lock_irq(&mhi_chan->lock);
> +		if (mhi_chan->ch_state != MHI_CH_STATE_STOP &&
> +		    mhi_chan->ch_state != MHI_CH_STATE_ENABLED &&
> +		    mhi_chan->ch_state != MHI_CH_STATE_SUSPENDED) {
> +			write_unlock_irq(&mhi_chan->lock);
> +			goto exit_invalid_state;
> +		}
> +		mhi_chan->ch_state = MHI_CH_STATE_DISABLED;
> +		write_unlock_irq(&mhi_chan->lock);
>  
> -	dev_dbg(dev, "Entered: unprepare channel:%d\n", mhi_chan->chan);
> +		cmd = MHI_CMD_RESET_CHAN;
> +		break;
> +	case MHI_CH_STATE_TYPE_STOP:
> +		if (mhi_chan->ch_state != MHI_CH_STATE_ENABLED)
> +			goto exit_invalid_state;
>  
> -	/* no more processing events for this channel */
> -	mutex_lock(&mhi_chan->mutex);
> -	write_lock_irq(&mhi_chan->lock);
> -	if (mhi_chan->ch_state != MHI_CH_STATE_ENABLED &&
> -	    mhi_chan->ch_state != MHI_CH_STATE_SUSPENDED) {
> -		write_unlock_irq(&mhi_chan->lock);
> -		mutex_unlock(&mhi_chan->mutex);
> -		return;
> +		cmd = MHI_CMD_STOP_CHAN;
> +		break;
> +	case MHI_CH_STATE_TYPE_START:
> +		if (mhi_chan->ch_state != MHI_CH_STATE_STOP &&
> +		    mhi_chan->ch_state != MHI_CH_STATE_DISABLED)
> +			goto exit_invalid_state;
> +
> +		cmd = MHI_CMD_START_CHAN;
> +		break;
> +	default:
> +		goto exit_invalid_state;
>  	}
>  
> -	mhi_chan->ch_state = MHI_CH_STATE_DISABLED;
> -	write_unlock_irq(&mhi_chan->lock);
> +	/* bring host and device out of suspended states */
> +	ret = mhi_device_get_sync(mhi_cntrl->mhi_dev);

You are sneaking in a change here. Please add it to the commit description.

> +	if (ret)
> +		return ret;
> +	mhi_cntrl->runtime_get(mhi_cntrl);
>  
>  	reinit_completion(&mhi_chan->completion);
> -	read_lock_bh(&mhi_cntrl->pm_lock);
> -	if (MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state)) {
> -		read_unlock_bh(&mhi_cntrl->pm_lock);
> -		goto error_invalid_state;
> +	ret = mhi_send_cmd(mhi_cntrl, mhi_chan, cmd);
> +	if (ret) {
> +		dev_err(dev, "Failed to send %s(%d) %s command\n",
> +			mhi_chan->name, mhi_chan->chan,
> +			TO_CH_STATE_TYPE_STR(to_state));
> +		goto exit_command_failure;
>  	}
>  
> -	mhi_cntrl->wake_toggle(mhi_cntrl);
> -	read_unlock_bh(&mhi_cntrl->pm_lock);
> +	ret = wait_for_completion_timeout(&mhi_chan->completion,
> +				       msecs_to_jiffies(mhi_cntrl->timeout_ms));
> +	if (!ret || mhi_chan->ccs != MHI_EV_CC_SUCCESS) {
> +		dev_err(dev, "Failed to receive %s(%d) %s command completion\n",
> +			mhi_chan->name, mhi_chan->chan,
> +			TO_CH_STATE_TYPE_STR(to_state));
> +		ret = -EIO;
> +		goto exit_command_failure;
> +	}
>  
> -	mhi_cntrl->runtime_get(mhi_cntrl);
> +	ret = 0;
> +
> +	if (to_state != MHI_CH_STATE_TYPE_RESET) {
> +		write_lock_irq(&mhi_chan->lock);
> +		mhi_chan->ch_state = (to_state == MHI_CH_STATE_TYPE_START) ?
> +				      MHI_CH_STATE_ENABLED : MHI_CH_STATE_STOP;
> +		write_unlock_irq(&mhi_chan->lock);
> +	}
> +
> +	dev_dbg(dev, "Channel %s(%d) state change to %s successful\n",
> +		mhi_chan->name, mhi_chan->chan, TO_CH_STATE_TYPE_STR(to_state));
> +
> +exit_command_failure:
>  	mhi_cntrl->runtime_put(mhi_cntrl);
> -	ret = mhi_send_cmd(mhi_cntrl, mhi_chan, MHI_CMD_RESET_CHAN);
> -	if (ret)
> -		goto error_invalid_state;
> +	mhi_device_put(mhi_cntrl->mhi_dev);
>  
> -	/* even if it fails we will still reset */
> -	ret = wait_for_completion_timeout(&mhi_chan->completion,
> -				msecs_to_jiffies(mhi_cntrl->timeout_ms));
> -	if (!ret || mhi_chan->ccs != MHI_EV_CC_SUCCESS)
> -		dev_err(dev,
> -			"Failed to receive cmd completion, still resetting\n");
> +	return ret;
> +

This is not a recommended way to handle error paths. There should be a
single return for all error paths. Please fix it.

> +exit_invalid_state:
> +	dev_err(dev, "Channel %s(%d) update to %s not allowed\n",
> +		mhi_chan->name, mhi_chan->chan, TO_CH_STATE_TYPE_STR(to_state));
> +
> +	return -EINVAL;
> +}
> +
> +static void __mhi_unprepare_channel(struct mhi_controller *mhi_cntrl,
> +				    struct mhi_chan *mhi_chan)
> +{
> +	int ret;
> +	struct device *dev = &mhi_cntrl->mhi_dev->dev;
> +
> +	/* no more processing events for this channel */

Move this comment below.

Thanks,
Mani

  reply	other threads:[~2021-01-21 14:44 UTC|newest]

Thread overview: 21+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-01-08 20:54 [PATCH v5 0/9] Updates to MHI channel handling Bhaumik Bhatt
2021-01-08 20:54 ` [PATCH v5 1/9] bus: mhi: core: Allow sending the STOP channel command Bhaumik Bhatt
2021-01-21 11:25   ` Manivannan Sadhasivam
2021-01-08 20:54 ` [PATCH v5 2/9] bus: mhi: core: Allow channel to be disabled from stopped state Bhaumik Bhatt
2021-01-21 11:35   ` Manivannan Sadhasivam
2021-01-08 20:54 ` [PATCH v5 3/9] bus: mhi: core: Improvements to the channel handling state machine Bhaumik Bhatt
2021-01-21 14:43   ` Manivannan Sadhasivam [this message]
2021-01-08 20:54 ` [PATCH v5 4/9] bus: mhi: core: Clear configuration from channel context during reset Bhaumik Bhatt
2021-01-21 14:47   ` Manivannan Sadhasivam
2021-01-08 20:54 ` [PATCH v5 5/9] bus: mhi: core: Add support to stop or start channel data transfers Bhaumik Bhatt
2021-01-21 14:50   ` Manivannan Sadhasivam
2021-02-04 20:25     ` Bhaumik Bhatt
2021-01-08 20:54 ` [PATCH v5 6/9] bus: mhi: core: Check channel execution environment before issuing reset Bhaumik Bhatt
2021-01-21 15:12   ` Manivannan Sadhasivam
2021-02-04 20:23     ` Bhaumik Bhatt
2021-01-08 20:54 ` [PATCH v5 7/9] bus: mhi: core: Remove __ prefix for MHI channel unprepare function Bhaumik Bhatt
2021-01-08 20:54 ` [PATCH v5 8/9] bus: mhi: Improve documentation on channel transfer setup APIs Bhaumik Bhatt
2021-01-08 20:54 ` [PATCH v5 9/9] bus: mhi: core: Do not clear channel context more than once Bhaumik Bhatt
2021-01-09  4:39   ` Hemant Kumar
2021-01-21 15:15   ` Manivannan Sadhasivam
2021-01-09  7:38 [PATCH v5 3/9] bus: mhi: core: Improvements to the channel handling state machine kernel test robot

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=20210121144302.GA5473@work \
    --to=manivannan.sadhasivam@linaro.org \
    --cc=bbhatt@codeaurora.org \
    --cc=hemantk@codeaurora.org \
    --cc=jhugo@codeaurora.org \
    --cc=linux-arm-msm@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=loic.poulain@linaro.org \
    /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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.