2022-04-06 14:39:45

by Ashish Mhetre

[permalink] [raw]
Subject: [Patch v6 0/4] memory: tegra: Add MC channels and error logging

From tegra186 onward, memory controllers support multiple channels.
Add memory controller channels in device tree and add support to map
address spaces of these channels in tegra MC driver.
When memory controller interrupt occurs, registers from these channels
are required to be read in order to get error information.
Add error logging support from tegra186 onward for memory controller
interrupts.

Ashish Mhetre (4):
memory: tegra: Add memory controller channels support
memory: tegra: Add MC error logging on tegra186 onward
dt-bindings: memory: Update reg maxitems for tegra186
arm64: tegra: Add memory controller channels

---
Changes in v6:
- Added reg-names for each reg item of memory controller node
- Added logging for interrupts on multiple memory controller channels
- Added clearing interrupt support for global intstatus
- Updated DT binding documentation to work with existing DTS as well
- Updated function to get MC channels
- Updated variable names

Changes in v5:
- Updated patch sequence such that driver patches are before DT patches
- Fixed DT ABI break from v4
- Fixed smatch bug
- Updated description in DT binding documentation
- Updated variable names

Changes in v4:
- Added memory controller channels support
- Added newlines after every break statement of all switch cases
- Fixed compile error with W=1 build
- Fixed the interrupt mask bit logic

Changes in v3:
- Removed unnecessary ifdefs
- Grouped newly added MC registers with existing MC registers
- Removed unnecessary initialization of variables
- Updated code to use newly added field 'has_addr_hi_reg' instead of ifdefs

Changes in v2:
- Updated patch subject and commit message
- Removed separate irq handlers
- Updated tegra30_mc_handle_irq to be used for tegra186 onwards as well

.../nvidia,tegra186-mc.yaml | 14 +-
arch/arm64/boot/dts/nvidia/tegra186.dtsi | 7 +-
arch/arm64/boot/dts/nvidia/tegra194.dtsi | 21 ++-
arch/arm64/boot/dts/nvidia/tegra234.dtsi | 21 ++-
drivers/memory/tegra/mc.c | 120 +++++++++++++++---
drivers/memory/tegra/mc.h | 37 +++++-
drivers/memory/tegra/tegra186.c | 98 ++++++++++++++
drivers/memory/tegra/tegra194.c | 45 +++++++
drivers/memory/tegra/tegra234.c | 64 ++++++++++
include/soc/tegra/mc.h | 12 ++
10 files changed, 412 insertions(+), 27 deletions(-)

--
2.17.1


2022-04-06 14:42:40

by Ashish Mhetre

[permalink] [raw]
Subject: [Patch v6 1/4] memory: tegra: Add memory controller channels support

From tegra186 onwards, memory controller support multiple channels.
Add support for mapping address spaces of these channels.
Make sure that number of channels are as expected on each SOC.
During error interrupts from memory controller, appropriate registers
from these channels need to be accessed for logging error info.

Signed-off-by: Ashish Mhetre <[email protected]>
---
drivers/memory/tegra/mc.c | 6 ++++
drivers/memory/tegra/tegra186.c | 54 +++++++++++++++++++++++++++++++++
drivers/memory/tegra/tegra194.c | 1 +
drivers/memory/tegra/tegra234.c | 1 +
include/soc/tegra/mc.h | 7 +++++
5 files changed, 69 insertions(+)

diff --git a/drivers/memory/tegra/mc.c b/drivers/memory/tegra/mc.c
index bf3abb6d8354..3cda1d9ad32a 100644
--- a/drivers/memory/tegra/mc.c
+++ b/drivers/memory/tegra/mc.c
@@ -749,6 +749,12 @@ static int tegra_mc_probe(struct platform_device *pdev)
if (IS_ERR(mc->regs))
return PTR_ERR(mc->regs);

+ if (mc->soc->ops && mc->soc->ops->map_regs) {
+ err = mc->soc->ops->map_regs(mc, pdev);
+ if (err < 0)
+ return err;
+ }
+
mc->debugfs.root = debugfs_create_dir("mc", NULL);

if (mc->soc->ops && mc->soc->ops->probe) {
diff --git a/drivers/memory/tegra/tegra186.c b/drivers/memory/tegra/tegra186.c
index 3d153881abc1..2ca8ce349188 100644
--- a/drivers/memory/tegra/tegra186.c
+++ b/drivers/memory/tegra/tegra186.c
@@ -139,11 +139,64 @@ static int tegra186_mc_probe_device(struct tegra_mc *mc, struct device *dev)
return 0;
}

+static int tegra186_mc_map_regs(struct tegra_mc *mc,
+ struct platform_device *pdev)
+{
+ struct device_node *np = pdev->dev.parent->of_node;
+ int num_dt_channels, reg_cells = 0;
+ int i, ret;
+ u32 val;
+
+ ret = of_property_read_u32(np, "#address-cells", &val);
+ if (ret) {
+ dev_err(&pdev->dev, "missing #address-cells property\n");
+ return ret;
+ }
+
+ reg_cells = val;
+
+ ret = of_property_read_u32(np, "#size-cells", &val);
+ if (ret) {
+ dev_err(&pdev->dev, "missing #size-cells property\n");
+ return ret;
+ }
+
+ reg_cells += val;
+
+ num_dt_channels = of_property_count_elems_of_size(pdev->dev.of_node, "reg",
+ reg_cells * sizeof(u32));
+ /*
+ * On tegra186 onwards, memory controller support multiple channels.
+ * Apart from regular memory controller channels, there is one broadcast
+ * channel and one for stream-id registers.
+ */
+ if (num_dt_channels < mc->soc->num_channels + 2) {
+ dev_warn(&pdev->dev, "MC channels are missing, please update memory controller DT node with MC channels\n");
+ return 0;
+ }
+
+ mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev, "mc-broadcast");
+ if (IS_ERR(mc->bcast_ch_regs))
+ return PTR_ERR(mc->bcast_ch_regs);
+
+ for (i = 0; i < mc->soc->num_channels; i++) {
+ char name[4];
+
+ sprintf(name, "mc%u", i);
+ mc->ch_regs[i] = devm_platform_ioremap_resource_byname(pdev, name);
+ if (IS_ERR(mc->ch_regs[i]))
+ return PTR_ERR(mc->ch_regs[i]);
+ }
+
+ return 0;
+}
+
const struct tegra_mc_ops tegra186_mc_ops = {
.probe = tegra186_mc_probe,
.remove = tegra186_mc_remove,
.resume = tegra186_mc_resume,
.probe_device = tegra186_mc_probe_device,
+ .map_regs = tegra186_mc_map_regs,
};

#if defined(CONFIG_ARCH_TEGRA_186_SOC)
@@ -875,6 +928,7 @@ const struct tegra_mc_soc tegra186_mc_soc = {
.num_clients = ARRAY_SIZE(tegra186_mc_clients),
.clients = tegra186_mc_clients,
.num_address_bits = 40,
+ .num_channels = 4,
.ops = &tegra186_mc_ops,
};
#endif
diff --git a/drivers/memory/tegra/tegra194.c b/drivers/memory/tegra/tegra194.c
index cab998b8bd5c..94001174deaf 100644
--- a/drivers/memory/tegra/tegra194.c
+++ b/drivers/memory/tegra/tegra194.c
@@ -1347,5 +1347,6 @@ const struct tegra_mc_soc tegra194_mc_soc = {
.num_clients = ARRAY_SIZE(tegra194_mc_clients),
.clients = tegra194_mc_clients,
.num_address_bits = 40,
+ .num_channels = 16,
.ops = &tegra186_mc_ops,
};
diff --git a/drivers/memory/tegra/tegra234.c b/drivers/memory/tegra/tegra234.c
index e22824a79f45..6335a132be2d 100644
--- a/drivers/memory/tegra/tegra234.c
+++ b/drivers/memory/tegra/tegra234.c
@@ -97,5 +97,6 @@ const struct tegra_mc_soc tegra234_mc_soc = {
.num_clients = ARRAY_SIZE(tegra234_mc_clients),
.clients = tegra234_mc_clients,
.num_address_bits = 40,
+ .num_channels = 16,
.ops = &tegra186_mc_ops,
};
diff --git a/include/soc/tegra/mc.h b/include/soc/tegra/mc.h
index 1066b1194a5a..c3c121fbfbb7 100644
--- a/include/soc/tegra/mc.h
+++ b/include/soc/tegra/mc.h
@@ -13,6 +13,9 @@
#include <linux/irq.h>
#include <linux/reset-controller.h>
#include <linux/types.h>
+#include <linux/platform_device.h>
+
+#define MC_MAX_CHANNELS 16

struct clk;
struct device;
@@ -181,6 +184,7 @@ struct tegra_mc_ops {
int (*resume)(struct tegra_mc *mc);
irqreturn_t (*handle_irq)(int irq, void *data);
int (*probe_device)(struct tegra_mc *mc, struct device *dev);
+ int (*map_regs)(struct tegra_mc *mc, struct platform_device *pdev);
};

struct tegra_mc_soc {
@@ -194,6 +198,7 @@ struct tegra_mc_soc {
unsigned int atom_size;

u8 client_id_mask;
+ u8 num_channels;

const struct tegra_smmu_soc *smmu;

@@ -212,6 +217,8 @@ struct tegra_mc {
struct tegra_smmu *smmu;
struct gart_device *gart;
void __iomem *regs;
+ void __iomem *bcast_ch_regs;
+ void __iomem *ch_regs[MC_MAX_CHANNELS];
struct clk *clk;
int irq;

--
2.17.1

2022-04-11 10:24:24

by Dmitry Osipenko

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support


On 4/11/22 09:05, Ashish Mhetre wrote:
>
>
> On 4/10/2022 7:48 PM, Dmitry Osipenko wrote:
>> External email: Use caution opening links or attachments
>>
>>
>> 06.04.2022 08:24, Ashish Mhetre пишет:
>>> +     num_dt_channels =
>>> of_property_count_elems_of_size(pdev->dev.of_node, "reg",
>>> +                                                       reg_cells *
>>> sizeof(u32));
>>> +     /*
>>> +      * On tegra186 onwards, memory controller support multiple
>>> channels.
>>> +      * Apart from regular memory controller channels, there is one
>>> broadcast
>>> +      * channel and one for stream-id registers.
>>> +      */
>>> +     if (num_dt_channels < mc->soc->num_channels + 2) {
>>> +             dev_warn(&pdev->dev, "MC channels are missing, please
>>> update memory controller DT node with MC channels\n");
>>> +             return 0;
>>> +     }
>>> +
>>> +     mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>> "mc-broadcast");
>>> +     if (IS_ERR(mc->bcast_ch_regs))
>>> +             return PTR_ERR(mc->bcast_ch_regs);
>>
>> Looks to me that you don't need to use of_property_count_elems_of_size()
>> and could only check the "mc-broadcast" presence to decide whether this
>> is an older DT.
>>
> Now that we are using reg-names in new DT, yes it'd be fine to just
> check mc-broadcast to decide it's a new or old DT.
>
>> mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>> "broadcast");
>> if (IS_ERR(mc->bcast_ch_regs)) {
>>          dev_warn(&pdev->dev, "Broadcast channel is missing, please
>> update your
>> device-tree\n");
>>          return PTR_ERR(mc->bcast_ch_regs);
>> }
>
> return 0;
>
> to avoid DT ABI break, right?

Yes, it should be "return 0".

2022-04-11 10:50:33

by Dmitry Osipenko

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support

06.04.2022 08:24, Ashish Mhetre пишет:
> + num_dt_channels = of_property_count_elems_of_size(pdev->dev.of_node, "reg",
> + reg_cells * sizeof(u32));
> + /*
> + * On tegra186 onwards, memory controller support multiple channels.
> + * Apart from regular memory controller channels, there is one broadcast
> + * channel and one for stream-id registers.
> + */
> + if (num_dt_channels < mc->soc->num_channels + 2) {
> + dev_warn(&pdev->dev, "MC channels are missing, please update memory controller DT node with MC channels\n");
> + return 0;
> + }
> +
> + mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev, "mc-broadcast");
> + if (IS_ERR(mc->bcast_ch_regs))
> + return PTR_ERR(mc->bcast_ch_regs);

Looks to me that you don't need to use of_property_count_elems_of_size()
and could only check the "mc-broadcast" presence to decide whether this
is an older DT.

mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
"broadcast");
if (IS_ERR(mc->bcast_ch_regs)) {
dev_warn(&pdev->dev, "Broadcast channel is missing, please update your
device-tree\n");
return PTR_ERR(mc->bcast_ch_regs);
}

2022-04-11 15:09:28

by Dmitry Osipenko

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support

On 4/11/22 10:28, Ashish Mhetre wrote:
>
>
> On 4/11/2022 12:03 PM, Dmitry Osipenko wrote:
>> External email: Use caution opening links or attachments
>>
>>
>> On 4/11/22 09:05, Ashish Mhetre wrote:
>>>
>>>
>>> On 4/10/2022 7:48 PM, Dmitry Osipenko wrote:
>>>> External email: Use caution opening links or attachments
>>>>
>>>>
>>>> 06.04.2022 08:24, Ashish Mhetre пишет:
>>>>> +     num_dt_channels =
>>>>> of_property_count_elems_of_size(pdev->dev.of_node, "reg",
>>>>> +                                                       reg_cells *
>>>>> sizeof(u32));
>>>>> +     /*
>>>>> +      * On tegra186 onwards, memory controller support multiple
>>>>> channels.
>>>>> +      * Apart from regular memory controller channels, there is one
>>>>> broadcast
>>>>> +      * channel and one for stream-id registers.
>>>>> +      */
>>>>> +     if (num_dt_channels < mc->soc->num_channels + 2) {
>>>>> +             dev_warn(&pdev->dev, "MC channels are missing, please
>>>>> update memory controller DT node with MC channels\n");
>>>>> +             return 0;
>>>>> +     }
>>>>> +
>>>>> +     mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>>>> "mc-broadcast");
>>>>> +     if (IS_ERR(mc->bcast_ch_regs))
>>>>> +             return PTR_ERR(mc->bcast_ch_regs);
>>>>
>>>> Looks to me that you don't need to use
>>>> of_property_count_elems_of_size()
>>>> and could only check the "mc-broadcast" presence to decide whether this
>>>> is an older DT.
>>>>
>>> Now that we are using reg-names in new DT, yes it'd be fine to just
>>> check mc-broadcast to decide it's a new or old DT.
>>>
>>>> mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>>> "broadcast");
>>>> if (IS_ERR(mc->bcast_ch_regs)) {
>>>>           dev_warn(&pdev->dev, "Broadcast channel is missing, please
>>>> update your
>>>> device-tree\n");
>>>>           return PTR_ERR(mc->bcast_ch_regs);
>>>> }
>>>
>>> return 0;
>>>
>>> to avoid DT ABI break, right?
>>
>> Yes, it should be "return 0".
>
> But if we "return 0" from here, then what about the case when ioremap()
> actually fails with new DT i.e. when broadcast reg is present in DT?
> In that case error should be returned and probe should be failed, right?

You should check for the -ENOENT.

2022-04-11 16:27:37

by Dmitry Osipenko

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support

06.04.2022 08:24, Ashish Mhetre пишет:
> diff --git a/include/soc/tegra/mc.h b/include/soc/tegra/mc.h
> index 1066b1194a5a..c3c121fbfbb7 100644
> --- a/include/soc/tegra/mc.h
> +++ b/include/soc/tegra/mc.h
> @@ -13,6 +13,9 @@
> #include <linux/irq.h>
> #include <linux/reset-controller.h>
> #include <linux/types.h>
> +#include <linux/platform_device.h>
> +
> +#define MC_MAX_CHANNELS 16
>
> struct clk;
> struct device;
> @@ -181,6 +184,7 @@ struct tegra_mc_ops {
> int (*resume)(struct tegra_mc *mc);
> irqreturn_t (*handle_irq)(int irq, void *data);
> int (*probe_device)(struct tegra_mc *mc, struct device *dev);
> + int (*map_regs)(struct tegra_mc *mc, struct platform_device *pdev);
> };
>
> struct tegra_mc_soc {
> @@ -194,6 +198,7 @@ struct tegra_mc_soc {
> unsigned int atom_size;
>
> u8 client_id_mask;
> + u8 num_channels;
>
> const struct tegra_smmu_soc *smmu;
>
> @@ -212,6 +217,8 @@ struct tegra_mc {
> struct tegra_smmu *smmu;
> struct gart_device *gart;
> void __iomem *regs;
> + void __iomem *bcast_ch_regs;
> + void __iomem *ch_regs[MC_MAX_CHANNELS];

Why not to allocate ch_regs at runtime?

2022-04-11 19:04:47

by Dmitry Osipenko

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support

06.04.2022 08:24, Ashish Mhetre пишет:
> diff --git a/include/soc/tegra/mc.h b/include/soc/tegra/mc.h
> index 1066b1194a5a..c3c121fbfbb7 100644
> --- a/include/soc/tegra/mc.h
> +++ b/include/soc/tegra/mc.h
> @@ -13,6 +13,9 @@
> #include <linux/irq.h>
> #include <linux/reset-controller.h>
> #include <linux/types.h>
> +#include <linux/platform_device.h>
> +
> +#define MC_MAX_CHANNELS 16
>
> struct clk;
> struct device;
> @@ -181,6 +184,7 @@ struct tegra_mc_ops {
> int (*resume)(struct tegra_mc *mc);
> irqreturn_t (*handle_irq)(int irq, void *data);
> int (*probe_device)(struct tegra_mc *mc, struct device *dev);
> + int (*map_regs)(struct tegra_mc *mc, struct platform_device *pdev);

Use to_platform_device(mc->dev) instead of passing the pdev argument.

2022-04-11 21:38:01

by Ashish Mhetre

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support



On 4/10/2022 8:31 PM, Dmitry Osipenko wrote:
> External email: Use caution opening links or attachments
>
>
> 06.04.2022 08:24, Ashish Mhetre пишет:
>> diff --git a/include/soc/tegra/mc.h b/include/soc/tegra/mc.h
>> index 1066b1194a5a..c3c121fbfbb7 100644
>> --- a/include/soc/tegra/mc.h
>> +++ b/include/soc/tegra/mc.h
>> @@ -13,6 +13,9 @@
>> #include <linux/irq.h>
>> #include <linux/reset-controller.h>
>> #include <linux/types.h>
>> +#include <linux/platform_device.h>
>> +
>> +#define MC_MAX_CHANNELS 16
>>
>> struct clk;
>> struct device;
>> @@ -181,6 +184,7 @@ struct tegra_mc_ops {
>> int (*resume)(struct tegra_mc *mc);
>> irqreturn_t (*handle_irq)(int irq, void *data);
>> int (*probe_device)(struct tegra_mc *mc, struct device *dev);
>> + int (*map_regs)(struct tegra_mc *mc, struct platform_device *pdev);
>
> Use to_platform_device(mc->dev) instead of passing the pdev argument.

Okay, I'll update in v7.

2022-04-12 00:48:56

by Ashish Mhetre

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support



On 4/10/2022 8:34 PM, Dmitry Osipenko wrote:
> External email: Use caution opening links or attachments
>
>
> 06.04.2022 08:24, Ashish Mhetre пишет:
>> diff --git a/include/soc/tegra/mc.h b/include/soc/tegra/mc.h
>> index 1066b1194a5a..c3c121fbfbb7 100644
>> --- a/include/soc/tegra/mc.h
>> +++ b/include/soc/tegra/mc.h
>> @@ -13,6 +13,9 @@
>> #include <linux/irq.h>
>> #include <linux/reset-controller.h>
>> #include <linux/types.h>
>> +#include <linux/platform_device.h>
>> +
>> +#define MC_MAX_CHANNELS 16
>>
>> struct clk;
>> struct device;
>> @@ -181,6 +184,7 @@ struct tegra_mc_ops {
>> int (*resume)(struct tegra_mc *mc);
>> irqreturn_t (*handle_irq)(int irq, void *data);
>> int (*probe_device)(struct tegra_mc *mc, struct device *dev);
>> + int (*map_regs)(struct tegra_mc *mc, struct platform_device *pdev);
>> };
>>
>> struct tegra_mc_soc {
>> @@ -194,6 +198,7 @@ struct tegra_mc_soc {
>> unsigned int atom_size;
>>
>> u8 client_id_mask;
>> + u8 num_channels;
>>
>> const struct tegra_smmu_soc *smmu;
>>
>> @@ -212,6 +217,8 @@ struct tegra_mc {
>> struct tegra_smmu *smmu;
>> struct gart_device *gart;
>> void __iomem *regs;
>> + void __iomem *bcast_ch_regs;
>> + void __iomem *ch_regs[MC_MAX_CHANNELS];
>
> Why not to allocate ch_regs at runtime?

Yes, we can do that. I'll make necessary changes in v7.

2022-04-12 07:34:14

by Ashish Mhetre

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support



On 4/10/2022 7:48 PM, Dmitry Osipenko wrote:
> External email: Use caution opening links or attachments
>
>
> 06.04.2022 08:24, Ashish Mhetre пишет:
>> + num_dt_channels = of_property_count_elems_of_size(pdev->dev.of_node, "reg",
>> + reg_cells * sizeof(u32));
>> + /*
>> + * On tegra186 onwards, memory controller support multiple channels.
>> + * Apart from regular memory controller channels, there is one broadcast
>> + * channel and one for stream-id registers.
>> + */
>> + if (num_dt_channels < mc->soc->num_channels + 2) {
>> + dev_warn(&pdev->dev, "MC channels are missing, please update memory controller DT node with MC channels\n");
>> + return 0;
>> + }
>> +
>> + mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev, "mc-broadcast");
>> + if (IS_ERR(mc->bcast_ch_regs))
>> + return PTR_ERR(mc->bcast_ch_regs);
>
> Looks to me that you don't need to use of_property_count_elems_of_size()
> and could only check the "mc-broadcast" presence to decide whether this
> is an older DT.
>
Now that we are using reg-names in new DT, yes it'd be fine to just
check mc-broadcast to decide it's a new or old DT.

> mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
> "broadcast");
> if (IS_ERR(mc->bcast_ch_regs)) {
> dev_warn(&pdev->dev, "Broadcast channel is missing, please update your
> device-tree\n");
> return PTR_ERR(mc->bcast_ch_regs);
> }

return 0;

to avoid DT ABI break, right?

2022-04-12 07:42:54

by Ashish Mhetre

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support



On 4/11/2022 12:03 PM, Dmitry Osipenko wrote:
> External email: Use caution opening links or attachments
>
>
> On 4/11/22 09:05, Ashish Mhetre wrote:
>>
>>
>> On 4/10/2022 7:48 PM, Dmitry Osipenko wrote:
>>> External email: Use caution opening links or attachments
>>>
>>>
>>> 06.04.2022 08:24, Ashish Mhetre пишет:
>>>> + num_dt_channels =
>>>> of_property_count_elems_of_size(pdev->dev.of_node, "reg",
>>>> + reg_cells *
>>>> sizeof(u32));
>>>> + /*
>>>> + * On tegra186 onwards, memory controller support multiple
>>>> channels.
>>>> + * Apart from regular memory controller channels, there is one
>>>> broadcast
>>>> + * channel and one for stream-id registers.
>>>> + */
>>>> + if (num_dt_channels < mc->soc->num_channels + 2) {
>>>> + dev_warn(&pdev->dev, "MC channels are missing, please
>>>> update memory controller DT node with MC channels\n");
>>>> + return 0;
>>>> + }
>>>> +
>>>> + mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>>> "mc-broadcast");
>>>> + if (IS_ERR(mc->bcast_ch_regs))
>>>> + return PTR_ERR(mc->bcast_ch_regs);
>>>
>>> Looks to me that you don't need to use of_property_count_elems_of_size()
>>> and could only check the "mc-broadcast" presence to decide whether this
>>> is an older DT.
>>>
>> Now that we are using reg-names in new DT, yes it'd be fine to just
>> check mc-broadcast to decide it's a new or old DT.
>>
>>> mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>> "broadcast");
>>> if (IS_ERR(mc->bcast_ch_regs)) {
>>> dev_warn(&pdev->dev, "Broadcast channel is missing, please
>>> update your
>>> device-tree\n");
>>> return PTR_ERR(mc->bcast_ch_regs);
>>> }
>>
>> return 0;
>>
>> to avoid DT ABI break, right?
>
> Yes, it should be "return 0".

But if we "return 0" from here, then what about the case when ioremap()
actually fails with new DT i.e. when broadcast reg is present in DT?
In that case error should be returned and probe should be failed, right?

2022-04-12 12:32:43

by Dmitry Osipenko

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support


On 4/11/22 12:18, Ashish Mhetre wrote:
>
>
> On 4/11/2022 1:05 PM, Dmitry Osipenko wrote:
>> External email: Use caution opening links or attachments
>>
>>
>> On 4/11/22 10:28, Ashish Mhetre wrote:
>>>
>>>
>>> On 4/11/2022 12:03 PM, Dmitry Osipenko wrote:
>>>> External email: Use caution opening links or attachments
>>>>
>>>>
>>>> On 4/11/22 09:05, Ashish Mhetre wrote:
>>>>>
>>>>>
>>>>> On 4/10/2022 7:48 PM, Dmitry Osipenko wrote:
>>>>>> External email: Use caution opening links or attachments
>>>>>>
>>>>>>
>>>>>> 06.04.2022 08:24, Ashish Mhetre пишет:
>>>>>>> +     num_dt_channels =
>>>>>>> of_property_count_elems_of_size(pdev->dev.of_node, "reg",
>>>>>>> +                                                       reg_cells *
>>>>>>> sizeof(u32));
>>>>>>> +     /*
>>>>>>> +      * On tegra186 onwards, memory controller support multiple
>>>>>>> channels.
>>>>>>> +      * Apart from regular memory controller channels, there is one
>>>>>>> broadcast
>>>>>>> +      * channel and one for stream-id registers.
>>>>>>> +      */
>>>>>>> +     if (num_dt_channels < mc->soc->num_channels + 2) {
>>>>>>> +             dev_warn(&pdev->dev, "MC channels are missing, please
>>>>>>> update memory controller DT node with MC channels\n");
>>>>>>> +             return 0;
>>>>>>> +     }
>>>>>>> +
>>>>>>> +     mc->bcast_ch_regs =
>>>>>>> devm_platform_ioremap_resource_byname(pdev,
>>>>>>> "mc-broadcast");
>>>>>>> +     if (IS_ERR(mc->bcast_ch_regs))
>>>>>>> +             return PTR_ERR(mc->bcast_ch_regs);
>>>>>>
>>>>>> Looks to me that you don't need to use
>>>>>> of_property_count_elems_of_size()
>>>>>> and could only check the "mc-broadcast" presence to decide whether
>>>>>> this
>>>>>> is an older DT.
>>>>>>
>>>>> Now that we are using reg-names in new DT, yes it'd be fine to just
>>>>> check mc-broadcast to decide it's a new or old DT.
>>>>>
>>>>>> mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>>>>> "broadcast");
>>>>>> if (IS_ERR(mc->bcast_ch_regs)) {
>>>>>>            dev_warn(&pdev->dev, "Broadcast channel is missing, please
>>>>>> update your
>>>>>> device-tree\n");
>>>>>>            return PTR_ERR(mc->bcast_ch_regs);
>>>>>> }
>>>>>
>>>>> return 0;
>>>>>
>>>>> to avoid DT ABI break, right?
>>>>
>>>> Yes, it should be "return 0".
>>>
>>> But if we "return 0" from here, then what about the case when ioremap()
>>> actually fails with new DT i.e. when broadcast reg is present in DT?
>>> In that case error should be returned and probe should be failed, right?
>>
>> You should check for the -ENOENT.
>
> I checked __devm_ioremap_resource(), it returns -EINVAL if given
> resource is not present. So should we check for -EINVAL instead?

Yes

2022-04-12 20:08:17

by Ashish Mhetre

[permalink] [raw]
Subject: Re: [Patch v6 1/4] memory: tegra: Add memory controller channels support



On 4/11/2022 1:05 PM, Dmitry Osipenko wrote:
> External email: Use caution opening links or attachments
>
>
> On 4/11/22 10:28, Ashish Mhetre wrote:
>>
>>
>> On 4/11/2022 12:03 PM, Dmitry Osipenko wrote:
>>> External email: Use caution opening links or attachments
>>>
>>>
>>> On 4/11/22 09:05, Ashish Mhetre wrote:
>>>>
>>>>
>>>> On 4/10/2022 7:48 PM, Dmitry Osipenko wrote:
>>>>> External email: Use caution opening links or attachments
>>>>>
>>>>>
>>>>> 06.04.2022 08:24, Ashish Mhetre пишет:
>>>>>> + num_dt_channels =
>>>>>> of_property_count_elems_of_size(pdev->dev.of_node, "reg",
>>>>>> + reg_cells *
>>>>>> sizeof(u32));
>>>>>> + /*
>>>>>> + * On tegra186 onwards, memory controller support multiple
>>>>>> channels.
>>>>>> + * Apart from regular memory controller channels, there is one
>>>>>> broadcast
>>>>>> + * channel and one for stream-id registers.
>>>>>> + */
>>>>>> + if (num_dt_channels < mc->soc->num_channels + 2) {
>>>>>> + dev_warn(&pdev->dev, "MC channels are missing, please
>>>>>> update memory controller DT node with MC channels\n");
>>>>>> + return 0;
>>>>>> + }
>>>>>> +
>>>>>> + mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>>>>> "mc-broadcast");
>>>>>> + if (IS_ERR(mc->bcast_ch_regs))
>>>>>> + return PTR_ERR(mc->bcast_ch_regs);
>>>>>
>>>>> Looks to me that you don't need to use
>>>>> of_property_count_elems_of_size()
>>>>> and could only check the "mc-broadcast" presence to decide whether this
>>>>> is an older DT.
>>>>>
>>>> Now that we are using reg-names in new DT, yes it'd be fine to just
>>>> check mc-broadcast to decide it's a new or old DT.
>>>>
>>>>> mc->bcast_ch_regs = devm_platform_ioremap_resource_byname(pdev,
>>>>> "broadcast");
>>>>> if (IS_ERR(mc->bcast_ch_regs)) {
>>>>> dev_warn(&pdev->dev, "Broadcast channel is missing, please
>>>>> update your
>>>>> device-tree\n");
>>>>> return PTR_ERR(mc->bcast_ch_regs);
>>>>> }
>>>>
>>>> return 0;
>>>>
>>>> to avoid DT ABI break, right?
>>>
>>> Yes, it should be "return 0".
>>
>> But if we "return 0" from here, then what about the case when ioremap()
>> actually fails with new DT i.e. when broadcast reg is present in DT?
>> In that case error should be returned and probe should be failed, right?
>
> You should check for the -ENOENT.

I checked __devm_ioremap_resource(), it returns -EINVAL if given
resource is not present. So should we check for -EINVAL instead?