All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jonathan Cameron <Jonathan.Cameron@Huawei.com>
To: Dan Williams <dan.j.williams@intel.com>
Cc: <linux-cxl@vger.kernel.org>, Dave Jiang <dave.jiang@intel.com>
Subject: Re: [PATCH] cxl/hdm: Limit emulation to the number of range registers
Date: Thu, 30 Mar 2023 18:02:32 +0100	[thread overview]
Message-ID: <20230330180232.00004c84@Huawei.com> (raw)
In-Reply-To: <168012574932.221280.15944705098679646436.stgit@dwillia2-xfh.jf.intel.com>

On Wed, 29 Mar 2023 14:35:49 -0700
Dan Williams <dan.j.williams@intel.com> wrote:

> Recall that range register emulation seeks to treat the 2 potential
> range registers as Linux CXL "decoder" objects. The number of range
> registers can be 1 or 2, while HDM decoder ranges can include more than
> 2.
> 
> Be careful not to confuse DVSEC range count with HDM capability decoder
> count. Commit to range register earlier in devm_cxl_setup_hdm().
> Otherwise, a device with more HDM decoders than range registers can set
> @cxlhdm->decoder_count to an invalid value.
> 
> Avoid introducing a forward declaration by just moving the definition of
> should_emulate_decoders() earlier in the file. should_emulate_decoders()
> is unchanged.
> 
> Tested-by: Dave Jiang <dave.jiang@intel.com>
> Fixes: d7a2153762c7 ("cxl/hdm: Add emulation when HDM decoders are not committed")
> Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Seems reasonable.

Reviewed-by: Jonathan Cameron <Jonathan.Cameron@huawei.com>

> ---
>  drivers/cxl/core/hdm.c |   82 +++++++++++++++++++++++++++---------------------
>  1 file changed, 46 insertions(+), 36 deletions(-)
> 
> diff --git a/drivers/cxl/core/hdm.c b/drivers/cxl/core/hdm.c
> index cc123996b1a4..9884b6d4d930 100644
> --- a/drivers/cxl/core/hdm.c
> +++ b/drivers/cxl/core/hdm.c
> @@ -101,6 +101,42 @@ static int map_hdm_decoder_regs(struct cxl_port *port, void __iomem *crb,
>  				      BIT(CXL_CM_CAP_CAP_ID_HDM));
>  }
>  
> +static bool should_emulate_decoders(struct cxl_endpoint_dvsec_info *info)
> +{
> +	struct cxl_hdm *cxlhdm;
> +	void __iomem *hdm;
> +	u32 ctrl;
> +	int i;
> +
> +	if (!info)
> +		return false;
> +
> +	cxlhdm = dev_get_drvdata(&info->port->dev);
> +	hdm = cxlhdm->regs.hdm_decoder;
> +
> +	if (!hdm)
> +		return true;
> +
> +	/*
> +	 * If HDM decoders are present and the driver is in control of
> +	 * Mem_Enable skip DVSEC based emulation
> +	 */
> +	if (!info->mem_enabled)
> +		return false;
> +
> +	/*
> +	 * If any decoders are committed already, there should not be any
> +	 * emulated DVSEC decoders.
> +	 */
> +	for (i = 0; i < cxlhdm->decoder_count; i++) {
> +		ctrl = readl(hdm + CXL_HDM_DECODER0_CTRL_OFFSET(i));
> +		if (FIELD_GET(CXL_HDM_DECODER0_CTRL_COMMITTED, ctrl))
> +			return false;
> +	}
> +
> +	return true;
> +}
> +
>  /**
>   * devm_cxl_setup_hdm - map HDM decoder component registers
>   * @port: cxl_port to map
> @@ -140,6 +176,16 @@ struct cxl_hdm *devm_cxl_setup_hdm(struct cxl_port *port,
>  		return ERR_PTR(-ENXIO);
>  	}
>  
> +	/*
> +	 * Now that the hdm capability is parsed, decide if range
> +	 * register emulation is needed and fixup cxlhdm accordingly.
> +	 */
> +	if (should_emulate_decoders(info)) {
> +		dev_dbg(dev, "Fallback map %d range register%s\n", info->ranges,
> +			info->ranges > 1 ? "s" : "");
> +		cxlhdm->decoder_count = info->ranges;
> +	}
> +
>  	return cxlhdm;
>  }
>  EXPORT_SYMBOL_NS_GPL(devm_cxl_setup_hdm, CXL);
> @@ -717,42 +763,6 @@ static int cxl_setup_hdm_decoder_from_dvsec(struct cxl_port *port,
>  	return 0;
>  }
>  
> -static bool should_emulate_decoders(struct cxl_endpoint_dvsec_info *info)
> -{
> -	struct cxl_hdm *cxlhdm;
> -	void __iomem *hdm;
> -	u32 ctrl;
> -	int i;
> -
> -	if (!info)
> -		return false;
> -
> -	cxlhdm = dev_get_drvdata(&info->port->dev);
> -	hdm = cxlhdm->regs.hdm_decoder;
> -
> -	if (!hdm)
> -		return true;
> -
> -	/*
> -	 * If HDM decoders are present and the driver is in control of
> -	 * Mem_Enable skip DVSEC based emulation
> -	 */
> -	if (!info->mem_enabled)
> -		return false;
> -
> -	/*
> -	 * If any decoders are committed already, there should not be any
> -	 * emulated DVSEC decoders.
> -	 */
> -	for (i = 0; i < cxlhdm->decoder_count; i++) {
> -		ctrl = readl(hdm + CXL_HDM_DECODER0_CTRL_OFFSET(i));
> -		if (FIELD_GET(CXL_HDM_DECODER0_CTRL_COMMITTED, ctrl))
> -			return false;
> -	}
> -
> -	return true;
> -}
> -
>  static int init_hdm_decoder(struct cxl_port *port, struct cxl_decoder *cxld,
>  			    int *target_map, void __iomem *hdm, int which,
>  			    u64 *dpa_base, struct cxl_endpoint_dvsec_info *info)
> 


      parent reply	other threads:[~2023-03-30 17:02 UTC|newest]

Thread overview: 3+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-03-29 21:35 [PATCH] cxl/hdm: Limit emulation to the number of range registers Dan Williams
2023-03-30  0:00 ` Dave Jiang
2023-03-30 17:02 ` Jonathan Cameron [this message]

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=20230330180232.00004c84@Huawei.com \
    --to=jonathan.cameron@huawei.com \
    --cc=dan.j.williams@intel.com \
    --cc=dave.jiang@intel.com \
    --cc=linux-cxl@vger.kernel.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.