diff mbox series

[v8,07/10] PCI: qcom: Handle MSIs routed to multiple GIC interrupts

Message ID 20220512104545.2204523-8-dmitry.baryshkov@linaro.org (mailing list archive)
State Superseded
Delegated to: Lorenzo Pieralisi
Headers show
Series PCI: qcom: Fix higher MSI vectors handling | expand

Commit Message

Dmitry Baryshkov May 12, 2022, 10:45 a.m. UTC
On some of Qualcomm platforms each group of 32 MSI vectors is routed to the
separate GIC interrupt. Thus, to receive higher MSI vectors properly,
declare that the host should use split MSI IRQ handling on these
platforms.

Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
---
 drivers/pci/controller/dwc/pcie-qcom.c | 12 ++++++++++++
 1 file changed, 12 insertions(+)

Comments

Johan Hovold May 13, 2022, 12:42 p.m. UTC | #1
On Thu, May 12, 2022 at 01:45:42PM +0300, Dmitry Baryshkov wrote:
> On some of Qualcomm platforms each group of 32 MSI vectors is routed to the
> separate GIC interrupt. Thus, to receive higher MSI vectors properly,
> declare that the host should use split MSI IRQ handling on these
> platforms.
> 
> Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
> ---
>  drivers/pci/controller/dwc/pcie-qcom.c | 12 ++++++++++++
>  1 file changed, 12 insertions(+)
> 
> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
> index 2e5464edc36e..f79752d1d680 100644
> --- a/drivers/pci/controller/dwc/pcie-qcom.c
> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
> @@ -194,6 +194,7 @@ struct qcom_pcie_ops {
>  
>  struct qcom_pcie_cfg {
>  	const struct qcom_pcie_ops *ops;
> +	unsigned int has_split_msi_irq:1;
>  	unsigned int pipe_clk_need_muxing:1;
>  	unsigned int has_tbu_clk:1;
>  	unsigned int has_ddrss_sf_tbu_clk:1;

> @@ -1592,6 +1599,11 @@ static int qcom_pcie_probe(struct platform_device *pdev)
>  
>  	pcie->cfg = pcie_cfg;
>  
> +	if (pcie->cfg->has_split_msi_irq) {
> +		pp->num_vectors = MAX_MSI_IRQS;
> +		pp->has_split_msi_irq = true;
> +	}

If all qcom platform that can support more than 32 MSI require multiple
IRQs, how about adding num_vectors to the config instead and set
pp->has_split_msi_irq when cfg->num_vectors is set (or unconditionally
if you remove the corresponding warning you just added to the dwc host
code)?

At least some sc8280xp seem to only support 128 MSI (using 4 IRQs).

> +
>  	pcie->reset = devm_gpiod_get_optional(dev, "perst", GPIOD_OUT_HIGH);
>  	if (IS_ERR(pcie->reset)) {
>  		ret = PTR_ERR(pcie->reset);

Johan
Dmitry Baryshkov May 13, 2022, 12:48 p.m. UTC | #2
On 13/05/2022 15:42, Johan Hovold wrote:
> On Thu, May 12, 2022 at 01:45:42PM +0300, Dmitry Baryshkov wrote:
>> On some of Qualcomm platforms each group of 32 MSI vectors is routed to the
>> separate GIC interrupt. Thus, to receive higher MSI vectors properly,
>> declare that the host should use split MSI IRQ handling on these
>> platforms.
>>
>> Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
>> ---
>>   drivers/pci/controller/dwc/pcie-qcom.c | 12 ++++++++++++
>>   1 file changed, 12 insertions(+)
>>
>> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
>> index 2e5464edc36e..f79752d1d680 100644
>> --- a/drivers/pci/controller/dwc/pcie-qcom.c
>> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
>> @@ -194,6 +194,7 @@ struct qcom_pcie_ops {
>>   
>>   struct qcom_pcie_cfg {
>>   	const struct qcom_pcie_ops *ops;
>> +	unsigned int has_split_msi_irq:1;
>>   	unsigned int pipe_clk_need_muxing:1;
>>   	unsigned int has_tbu_clk:1;
>>   	unsigned int has_ddrss_sf_tbu_clk:1;
> 
>> @@ -1592,6 +1599,11 @@ static int qcom_pcie_probe(struct platform_device *pdev)
>>   
>>   	pcie->cfg = pcie_cfg;
>>   
>> +	if (pcie->cfg->has_split_msi_irq) {
>> +		pp->num_vectors = MAX_MSI_IRQS;
>> +		pp->has_split_msi_irq = true;
>> +	}
> 
> If all qcom platform that can support more than 32 MSI require multiple
> IRQs, how about adding num_vectors to the config instead and set
> pp->has_split_msi_irq when cfg->num_vectors is set (or unconditionally
> if you remove the corresponding warning you just added to the dwc host
> code)?
> 
> At least some sc8280xp seem to only support 128 MSI (using 4 IRQs).

Nice idea, let's do this.

> 
>> +
>>   	pcie->reset = devm_gpiod_get_optional(dev, "perst", GPIOD_OUT_HIGH);
>>   	if (IS_ERR(pcie->reset)) {
>>   		ret = PTR_ERR(pcie->reset);
> 
> Johan
Johan Hovold May 13, 2022, 12:57 p.m. UTC | #3
On Fri, May 13, 2022 at 03:48:09PM +0300, Dmitry Baryshkov wrote:
> On 13/05/2022 15:42, Johan Hovold wrote:

> > If all qcom platform that can support more than 32 MSI require multiple
> > IRQs, how about adding num_vectors to the config instead and set
> > pp->has_split_msi_irq when cfg->num_vectors is set (or unconditionally
> > if you remove the corresponding warning you just added to the dwc host
> > code)?
> > 
> > At least some sc8280xp seem to only support 128 MSI (using 4 IRQs).
> 
> Nice idea, let's do this.

If at all possible it would be even better to just infer it from the
devicetree to avoid having to describe things in two places, though.

Johan
diff mbox series

Patch

diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
index 2e5464edc36e..f79752d1d680 100644
--- a/drivers/pci/controller/dwc/pcie-qcom.c
+++ b/drivers/pci/controller/dwc/pcie-qcom.c
@@ -194,6 +194,7 @@  struct qcom_pcie_ops {
 
 struct qcom_pcie_cfg {
 	const struct qcom_pcie_ops *ops;
+	unsigned int has_split_msi_irq:1;
 	unsigned int pipe_clk_need_muxing:1;
 	unsigned int has_tbu_clk:1;
 	unsigned int has_ddrss_sf_tbu_clk:1;
@@ -1502,6 +1503,7 @@  static const struct qcom_pcie_cfg ipq8064_cfg = {
 
 static const struct qcom_pcie_cfg msm8996_cfg = {
 	.ops = &ops_2_3_2,
+	.has_split_msi_irq = true,
 };
 
 static const struct qcom_pcie_cfg ipq8074_cfg = {
@@ -1514,6 +1516,7 @@  static const struct qcom_pcie_cfg ipq4019_cfg = {
 
 static const struct qcom_pcie_cfg sdm845_cfg = {
 	.ops = &ops_2_7_0,
+	.has_split_msi_irq = true,
 	.has_tbu_clk = true,
 };
 
@@ -1526,12 +1529,14 @@  static const struct qcom_pcie_cfg sm8150_cfg = {
 
 static const struct qcom_pcie_cfg sm8250_cfg = {
 	.ops = &ops_1_9_0,
+	.has_split_msi_irq = true,
 	.has_tbu_clk = true,
 	.has_ddrss_sf_tbu_clk = true,
 };
 
 static const struct qcom_pcie_cfg sm8450_pcie0_cfg = {
 	.ops = &ops_1_9_0,
+	.has_split_msi_irq = true,
 	.has_ddrss_sf_tbu_clk = true,
 	.pipe_clk_need_muxing = true,
 	.has_aggre0_clk = true,
@@ -1540,6 +1545,7 @@  static const struct qcom_pcie_cfg sm8450_pcie0_cfg = {
 
 static const struct qcom_pcie_cfg sm8450_pcie1_cfg = {
 	.ops = &ops_1_9_0,
+	.has_split_msi_irq = true,
 	.has_ddrss_sf_tbu_clk = true,
 	.pipe_clk_need_muxing = true,
 	.has_aggre1_clk = true,
@@ -1547,6 +1553,7 @@  static const struct qcom_pcie_cfg sm8450_pcie1_cfg = {
 
 static const struct qcom_pcie_cfg sc7280_cfg = {
 	.ops = &ops_1_9_0,
+	.has_split_msi_irq = true,
 	.has_tbu_clk = true,
 	.pipe_clk_need_muxing = true,
 };
@@ -1592,6 +1599,11 @@  static int qcom_pcie_probe(struct platform_device *pdev)
 
 	pcie->cfg = pcie_cfg;
 
+	if (pcie->cfg->has_split_msi_irq) {
+		pp->num_vectors = MAX_MSI_IRQS;
+		pp->has_split_msi_irq = true;
+	}
+
 	pcie->reset = devm_gpiod_get_optional(dev, "perst", GPIOD_OUT_HIGH);
 	if (IS_ERR(pcie->reset)) {
 		ret = PTR_ERR(pcie->reset);