mirror of
git://nv-tegra.nvidia.com/linux-nv-oot.git
synced 2025-12-22 17:25:35 +03:00
ethernet: Get VM IRQ config sequence from nvidia,vm-irq-id
Ethernet driver expect the VM IRQ configuration. The VM IRQ
is provided with the property "interrupt" which have multiple
VM irq numbers and their configurations via the vm irq
configuration node which is referred by property
"nvidia,vm-irq-config".
The vm irq configuration node have the configuration of
all VM IRQ and each configuration is separated with the
child node like below.
ethernet@6800000 {
nvidia,vm-irq-config = <&mgbe_vm_irq_config>;
}
mgbe_vm_irq_config: mgbe-vm-irq-config {
nvidia,num-vm-irqs = <5>;
vm_irq1 {
nvidia,num-vm-channels = <2>;
nvidia,vm-channels = <0 1>;
nvidia,vm-num = <0>;
nvidia,vm-irq-id = <0>;
};
vm_irq2 {
nvidia,num-vm-channels = <2>;
nvidia,vm-channels = <2 3>;
nvidia,vm-num = <1>;
nvidia,vm-irq-id = <1>;
};
vm_irq3 {
nvidia,num-vm-channels = <2>;
nvidia,vm-channels = <4 5>;
nvidia,vm-num = <2>;
nvidia,vm-irq-id = <2>;
};
vm_irq4 {
nvidia,num-vm-channels = <2>;
nvidia,vm-channels = <6 7>;
nvidia,vm-num = <3>;
nvidia,vm-irq-id = <3>;
};
vm_irq5 {
nvidia,num-vm-channels = <2>;
nvidia,vm-channels = <8 9>;
nvidia,vm-num = <4>;
nvidia,vm-irq-id = <4>;
};
};
};
The child 1(vm_irq1) is link with the VM IRQ 1 listed in
interrupt property, next child which is vm_irq2 is link
with the 2nd VM irq. So, the order of VM configuration
child must be in same order as VM IRQ provided in the
property interrupt.
If the irq configuration order i..e child order is not
matching with VM irq number then there is interrupt issue.
Now, if the VM IRQ config child nodes are provided in base
DT file in same order then the ethernet works fine.
But when applying via overlay, it does not work.
This is because of overlay technique. The overlay logic is
such that it iterates all child node in overlay and
apply the child as first child of target node.
Hence the child sequence provided in overlay fragment
is applied in reverse order in target node. This causes
the irq configuration order not matching with VM IRQs.
To address the overlay issue, read the sequence of
interrupt in property "interrupt" from the newly added property
"nvidia,vm-irq-id" of each child. This way child node
sequence does not matter, and sequence is identified
by property.
Bug 3956724
Change-Id: I5c08edcd8a7e8d3112618dd23050d8b5c10ddc59
Signed-off-by: Revanth Kumar Uppala <ruppala@nvidia.com>
Reviewed-on: https://git-master.nvidia.com/r/c/linux-nv-oot/+/2855639
Reviewed-by: Bhadram Varka <vbhadram@nvidia.com>
Reviewed-by: Narayan Reddy <narayanr@nvidia.com>
Reviewed-by: Laxman Dewangan <ldewangan@nvidia.com>
GVS: Gerrit_Virtual_Submit <buildbot_gerritrpt@nvidia.com>
This commit is contained in:
committed by
mobile promotions
parent
354ef0dbe0
commit
2172c01a6d
@@ -4374,7 +4374,7 @@ static int ether_get_vm_irq_data(struct platform_device *pdev,
|
|||||||
struct osi_core_priv_data *osi_core = pdata->osi_core;
|
struct osi_core_priv_data *osi_core = pdata->osi_core;
|
||||||
struct device_node *vm_node, *temp;
|
struct device_node *vm_node, *temp;
|
||||||
unsigned int i, j, node = 0;
|
unsigned int i, j, node = 0;
|
||||||
int ret = 0;
|
int vm_irq_id, child_id, ret =0;
|
||||||
|
|
||||||
vm_node = of_parse_phandle(pdev->dev.of_node,
|
vm_node = of_parse_phandle(pdev->dev.of_node,
|
||||||
"nvidia,vm-irq-config", 0);
|
"nvidia,vm-irq-config", 0);
|
||||||
@@ -4414,10 +4414,24 @@ static int ether_get_vm_irq_data(struct platform_device *pdev,
|
|||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
child_id = 0;
|
||||||
for_each_child_of_node(vm_node, temp) {
|
for_each_child_of_node(vm_node, temp) {
|
||||||
if (node == osi_core->num_vm_irqs)
|
ret = of_property_read_u32(temp, "nvidia,vm-irq-id", &vm_irq_id);
|
||||||
|
if (ret != 0) {
|
||||||
|
vm_irq_id = child_id;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (vm_irq_id >= osi_core->num_vm_irqs)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
node = vm_irq_id;
|
||||||
|
|
||||||
|
ret = of_property_read_u32(temp, "nvidia,vm-num", &osi_core->irq_data[node].vm_num);
|
||||||
|
if (ret != 0) {
|
||||||
|
dev_err(&pdev->dev, "failed to read VM Number\n");
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
ret = of_property_read_u32(temp, "nvidia,num-vm-channels",
|
ret = of_property_read_u32(temp, "nvidia,num-vm-channels",
|
||||||
&osi_core->irq_data[node].num_vm_chans);
|
&osi_core->irq_data[node].num_vm_chans);
|
||||||
if (ret != 0) {
|
if (ret != 0) {
|
||||||
@@ -4433,21 +4447,15 @@ static int ether_get_vm_irq_data(struct platform_device *pdev,
|
|||||||
dev_err(&pdev->dev, "failed to get VM channels\n");
|
dev_err(&pdev->dev, "failed to get VM channels\n");
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
child_id++;
|
||||||
ret = of_property_read_u32(temp, "nvidia,vm-num",
|
|
||||||
&osi_core->irq_data[node].vm_num);
|
|
||||||
if (ret != 0) {
|
|
||||||
dev_err(&pdev->dev, "failed to read VM Number\n");
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (node = 0; node < osi_core->num_vm_irqs; node++) {
|
||||||
ether_set_vm_irq_chan_mask(&pdata->vm_irq_data[node],
|
ether_set_vm_irq_chan_mask(&pdata->vm_irq_data[node],
|
||||||
osi_core->irq_data[node].num_vm_chans,
|
osi_core->irq_data[node].num_vm_chans,
|
||||||
osi_core->irq_data[node].vm_chans);
|
osi_core->irq_data[node].vm_chans);
|
||||||
|
|
||||||
pdata->vm_irq_data[node].pdata = pdata;
|
pdata->vm_irq_data[node].pdata = pdata;
|
||||||
|
|
||||||
node++;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
for (i = 0, j = 1; i < osi_core->num_vm_irqs; i++, j++) {
|
for (i = 0, j = 1; i < osi_core->num_vm_irqs; i++, j++) {
|
||||||
|
|||||||
Reference in New Issue
Block a user