This patch mainly adds support for mt8192 Multimedia IOMMU and SMI.
mt8192 also is MTK IOMMU gen2 which uses ARM Short-Descriptor translation
table format. The M4U-SMI HW diagram is as below:
EMI
|
M4U
|
------------
SMI Common
------------
|
+-------+------+------+----------------------+-------+
| | | | ...... | |
| | | | | |
larb0 larb1 larb2 larb4 ...... larb19 larb20
disp0 disp1 mdp vdec IPE IPE
All the connections are HW fixed, SW can NOT adjust it.
Comparing with the preview SoC, this patchset mainly adds two new functions:
a) add iova 34 bits support.
b) add multi domains support since several HW has the special iova
region requirement.
change note:
v6:a) base on v5.11-rc1. and tlb v4:
https://lore.kernel.org/linux-mediatek/20210107122909.16317-1-yong.wu@mediatek.com/T/#t
b) Remove the "domain id" definition in the binding header file.
Get the domain from dev->dma_range_map.
After this, Change many codes flow.
c) the patchset adds a new common file(mtk_smi-larb-port.h).
This version changes that name into mtk-memory-port.h which reflect
its file path. This only changes the file name. no other change.
thus I keep all the Reviewed-by Tags.
(another reason is that we will add some iommu ports unrelated with
smi-larb)
d) Refactor the power-domain flow suggestted by Tomasz.
e) Some other small fix. use different oas for different soc; Change the
macro for 34bit iova tlb flush.
v5: https://lore.kernel.org/linux-iommu/20201209080102.26626-1-yong.wu@mediatek.com/
a) Add a new patch for the header guard for smi-larb-port.h in [5/27].
b) Add a new patch for error handle for iommu_device_sysfs_add and
iommu_device_register[15/27].
c) Add a flag for the iova "ias == 34" case. the previous SoC still keep
32bits to save 16KB*3 lvl1 pgtable memory[13/27].
d) Add include <linux/bitfield.h> for FIELD_GET build fail.
e) In PM power domain patch, add a checking "pm_runtime_enabled" when call
pm_runtime_get_sync for non power-domain case. and add a pm_runtime_put_noidle
while pm_runtime_get_sync fail case.
v4: https://lore.kernel.org/linux-iommu/20201111123838.15682-1-yong.wu@mediatek.com/
a) rebase on v5.10-rc1
b) Move the smi part to a independent patchset.
c) Improve v7s code from Robin and Will.
d) Add a mediatek iommu entry patch in MAINTAIN.
v3: https://lore.kernel.org/linux-iommu/20200930070647.10188-1-yong.wu@mediatek.com/
a) Fix DT schema issue commented from Rob.
b) Fix a v7s issue. Use "_lvl" instead of "_l" in the macro(ARM_V7S_PTES_PER_LVL) since
it is called in ARM_V7S_LVL_IDX which has already used "_l".
c) Fix a PM suspend issue: Avoid pm suspend in pm runtime case.
v2: https://lore.kernel.org/linux-iommu/20200905080920.13396-1-yong.wu@mediatek.com/
a) Convert IOMMU/SMI dt-binding to DT schema.
b) Fix some comment from Pi-Hsun and Nicolas. like use
generic_iommu_put_resv_regions.
c) Reword some comment, like add how to use domain-id.
v1: https://lore.kernel.org/linux-iommu/20200711064846.16007-1-yong.wu@mediatek.com/
Yong Wu (33):
dt-bindings: iommu: mediatek: Convert IOMMU to DT schema
dt-bindings: memory: mediatek: Add a common memory header file
dt-bindings: memory: mediatek: Extend LARB_NR_MAX to 32
dt-bindings: memory: mediatek: Rename header guard for SMI header file
dt-bindings: mediatek: Add binding for mt8192 IOMMU
of/device: Move dma_range_map before of_iommu_configure
iommu: Avoid reallocate default domain for a group
iommu/mediatek: Use the common mtk-memory-port.h
iommu/io-pgtable-arm-v7s: Use ias to check the valid iova in unmap
iommu/io-pgtable-arm-v7s: Extend PA34 for MediaTek
iommu/io-pgtable-arm-v7s: Clarify LVL_SHIFT/BITS macro
iommu/io-pgtable-arm-v7s: Add cfg as a param in some macros
iommu/io-pgtable-arm-v7s: Quad lvl1 pgtable for MediaTek
iommu/mediatek: Add a flag for iova 34bits case
iommu/mediatek: Update oas for v7s
iommu/mediatek: Move hw_init into attach_device
iommu/mediatek: Add error handle for mtk_iommu_probe
iommu/mediatek: Add device link for smi-common and m4u
iommu/mediatek: Add pm runtime callback
iommu/mediatek: Add power-domain operation
iommu/mediatek: Support up to 34bit iova in tlb flush
iommu/mediatek: Support report iova 34bit translation fault in ISR
iommu/mediatek: Adjust the structure
iommu/mediatek: Move domain_finalise into attach_device
iommu/mediatek: Move geometry.aperture updating into domain_finalise
iommu/mediatek: Add iova_region structure
iommu/mediatek: Add get_domain_id from dev->dma_range_map
iommu/mediatek: Support for multi domains
iommu/mediatek: Add iova reserved function
iommu/mediatek: Support master use iova over 32bit
iommu/mediatek: Remove unnecessary check in attach_device
iommu/mediatek: Add mt8192 support
MAINTAINERS: Add entry for MediaTek IOMMU
.../bindings/iommu/mediatek,iommu.txt | 105 -----
.../bindings/iommu/mediatek,iommu.yaml | 183 +++++++++
MAINTAINERS | 9 +
drivers/iommu/io-pgtable-arm-v7s.c | 56 +--
drivers/iommu/iommu.c | 3 +-
drivers/iommu/mtk_iommu.c | 366 ++++++++++++++----
drivers/iommu/mtk_iommu.h | 12 +-
drivers/memory/mtk-smi.c | 8 +
drivers/of/device.c | 3 +-
include/dt-bindings/memory/mt2701-larb-port.h | 4 +-
include/dt-bindings/memory/mt2712-larb-port.h | 6 +-
include/dt-bindings/memory/mt6779-larb-port.h | 6 +-
include/dt-bindings/memory/mt8167-larb-port.h | 6 +-
include/dt-bindings/memory/mt8173-larb-port.h | 6 +-
include/dt-bindings/memory/mt8183-larb-port.h | 6 +-
include/dt-bindings/memory/mt8192-larb-port.h | 243 ++++++++++++
include/dt-bindings/memory/mtk-memory-port.h | 15 +
include/linux/io-pgtable.h | 4 +-
include/soc/mediatek/smi.h | 3 +-
19 files changed, 810 insertions(+), 234 deletions(-)
delete mode 100644 Documentation/devicetree/bindings/iommu/mediatek,iommu.txt
create mode 100644 Documentation/devicetree/bindings/iommu/mediatek,iommu.yaml
create mode 100644 include/dt-bindings/memory/mt8192-larb-port.h
create mode 100644 include/dt-bindings/memory/mtk-memory-port.h
--
2.18.0
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
@@ -1,105 +0,0 @@-* Mediatek IOMMU Architecture Implementation-- Some Mediatek SOCs contain a Multimedia Memory Management Unit (M4U), and-this M4U have two generations of HW architecture. Generation one uses flat-pagetable, and only supports 4K size page mapping. Generation two uses the-ARM Short-Descriptor translation table format for address translation.-- About the M4U Hardware Block Diagram, please check below:-- EMI (External Memory Interface)- |- m4u (Multimedia Memory Management Unit)- |- +--------+- | |- gals0-rx gals1-rx (Global Async Local Sync rx)- | |- | |- gals0-tx gals1-tx (Global Async Local Sync tx)- | | Some SoCs may have GALS.- +--------+- |- SMI Common(Smart Multimedia Interface Common)- |- +----------------+-------- | |- | gals-rx There may be GALS in some larbs.- | |- | |- | gals-tx- | |- SMI larb0 SMI larb1 ... SoCs have several SMI local arbiter(larb).- (display) (vdec)- | |- | |- +-----+-----+ +----+----+- | | | | | |- | | |... | | | ... There are different ports in each larb.- | | | | | |-OVL0 RDMA0 WDMA0 MC PP VLD-- As above, The Multimedia HW will go through SMI and M4U while it-access EMI. SMI is a bridge between m4u and the Multimedia HW. It contain-smi local arbiter and smi common. It will control whether the Multimedia-HW should go though the m4u for translation or bypass it and talk-directly with EMI. And also SMI help control the power domain and clocks for-each local arbiter.- Normally we specify a local arbiter(larb) for each multimedia HW-like display, video decode, and camera. And there are different ports-in each larb. Take a example, There are many ports like MC, PP, VLD in the-video decode local arbiter, all these ports are according to the video HW.- In some SoCs, there may be a GALS(Global Async Local Sync) module between-smi-common and m4u, and additional GALS module between smi-larb and-smi-common. GALS can been seen as a "asynchronous fifo" which could help-synchronize for the modules in different clock frequency.--Required properties:-- compatible : must be one of the following string:- "mediatek,mt2701-m4u" for mt2701 which uses generation one m4u HW.- "mediatek,mt2712-m4u" for mt2712 which uses generation two m4u HW.- "mediatek,mt6779-m4u" for mt6779 which uses generation two m4u HW.- "mediatek,mt7623-m4u", "mediatek,mt2701-m4u" for mt7623 which uses- generation one m4u HW.- "mediatek,mt8167-m4u" for mt8167 which uses generation two m4u HW.- "mediatek,mt8173-m4u" for mt8173 which uses generation two m4u HW.- "mediatek,mt8183-m4u" for mt8183 which uses generation two m4u HW.-- reg : m4u register base and size.-- interrupts : the interrupt of m4u.-- clocks : must contain one entry for each clock-names.-- clock-names : Only 1 optional clock:- - "bclk": the block clock of m4u.- Here is the list which require this "bclk":- - mt2701, mt2712, mt7623 and mt8173.- Note that m4u use the EMI clock which always has been enabled before kernel- if there is no this "bclk".-- mediatek,larbs : List of phandle to the local arbiters in the current Socs.- Refer to bindings/memory-controllers/mediatek,smi-larb.txt. It must sort- according to the local arbiter index, like larb0, larb1, larb2...-- iommu-cells : must be 1. This is the mtk_m4u_id according to the HW.- Specifies the mtk_m4u_id as defined in- dt-binding/memory/mt2701-larb-port.h for mt2701, mt7623- dt-binding/memory/mt2712-larb-port.h for mt2712,- dt-binding/memory/mt6779-larb-port.h for mt6779,- dt-binding/memory/mt8167-larb-port.h for mt8167,- dt-binding/memory/mt8173-larb-port.h for mt8173, and- dt-binding/memory/mt8183-larb-port.h for mt8183.--Example:- iommu: iommu@10205000 {- compatible = "mediatek,mt8173-m4u";- reg = <0 0x10205000 0 0x1000>;- interrupts = <GIC_SPI 139 IRQ_TYPE_LEVEL_LOW>;- clocks = <&infracfg CLK_INFRA_M4U>;- clock-names = "bclk";- mediatek,larbs = <&larb0 &larb1 &larb2 &larb3 &larb4 &larb5>;- #iommu-cells = <1>;- };--Example for a client device:- display {- compatible = "mediatek,mt8173-disp";- iommus = <&iommu M4U_PORT_DISP_OVL0>,- <&iommu M4U_PORT_DISP_RDMA0>;- ...- };
@@ -0,0 +1,167 @@+# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)+%YAML1.2+---+$id:http://devicetree.org/schemas/iommu/mediatek,iommu.yaml#+$schema:http://devicetree.org/meta-schemas/core.yaml#++title:MediaTek IOMMU Architecture Implementation++maintainers:+-Yong Wu <yong.wu@mediatek.com>++description:|++Some MediaTek SOCs contain a Multimedia Memory Management Unit (M4U), and+this M4U have two generations of HW architecture. Generation one uses flat+pagetable, and only supports 4K size page mapping. Generation two uses the+ARM Short-Descriptor translation table format for address translation.++About the M4U Hardware Block Diagram, please check below:++EMI (External Memory Interface)+|+m4u (Multimedia Memory Management Unit)+|++--------++| |+gals0-rx gals1-rx (Global Async Local Sync rx)+| |+| |+gals0-tx gals1-tx (Global Async Local Sync tx)+| | Some SoCs may have GALS.++--------++|+SMI Common(Smart Multimedia Interface Common)+|++----------------+-------+| |+| gals-rx There may be GALS in some larbs.+| |+| |+| gals-tx+| |+SMI larb0 SMI larb1 ... SoCs have several SMI local arbiter(larb).+(display) (vdec)+| |+| |++-----+-----+ +----+----++| | | | | |+| | |... | | | ... There are different ports in each larb.+| | | | | |+OVL0 RDMA0 WDMA0 MC PP VLD++As above, The Multimedia HW will go through SMI and M4U while it+access EMI. SMI is a bridge between m4u and the Multimedia HW. It contain+smi local arbiter and smi common. It will control whether the Multimedia+HW should go though the m4u for translation or bypass it and talk+directly with EMI. And also SMI help control the power domain and clocks for+each local arbiter.++Normally we specify a local arbiter(larb) for each multimedia HW+like display, video decode, and camera. And there are different ports+in each larb. Take a example, There are many ports like MC, PP, VLD in the+video decode local arbiter, all these ports are according to the video HW.++In some SoCs, there may be a GALS(Global Async Local Sync) module between+smi-common and m4u, and additional GALS module between smi-larb and+smi-common. GALS can been seen as a "asynchronous fifo" which could help+synchronize for the modules in different clock frequency.++properties:+compatible:+oneOf:+-enum:+-mediatek,mt2701-m4u# generation one+-mediatek,mt2712-m4u# generation two+-mediatek,mt6779-m4u# generation two+-mediatek,mt8167-m4u# generation two+-mediatek,mt8173-m4u# generation two+-mediatek,mt8183-m4u# generation two++-description:mt7623 generation one+items:+-const:mediatek,mt7623-m4u+-const:mediatek,mt2701-m4u++reg:+maxItems:1++interrupts:+maxItems:1++clocks:+items:+-description:bclk is the block clock.++clock-names:+items:+-const:bclk++mediatek,larbs:+$ref:/schemas/types.yaml#/definitions/phandle-array+minItems:1+maxItems:16+description:|+List of phandle to the local arbiters in the current Socs.+Refer to bindings/memory-controllers/mediatek,smi-larb.yaml. It must sort+according to the local arbiter index, like larb0, larb1, larb2...++'#iommu-cells':+const:1+description:|+This is the mtk_m4u_id according to the HW. Specifies the mtk_m4u_id as+defined in+dt-binding/memory/mt2701-larb-port.h for mt2701 and mt7623,+dt-binding/memory/mt2712-larb-port.h for mt2712,+dt-binding/memory/mt6779-larb-port.h for mt6779,+dt-binding/memory/mt8167-larb-port.h for mt8167,+dt-binding/memory/mt8173-larb-port.h for mt8173,+dt-binding/memory/mt8183-larb-port.h for mt8183.++required:+-compatible+-reg+-interrupts+-mediatek,larbs+-'#iommu-cells'++allOf:+-if:+properties:+compatible:+contains:+enum:+-mediatek,mt2701-m4u+-mediatek,mt2712-m4u+-mediatek,mt8173-m4u++then:+required:+-clocks++additionalProperties:false++examples:+-|+#include <dt-bindings/clock/mt8173-clk.h>+#include <dt-bindings/interrupt-controller/arm-gic.h>++iommu:iommu@10205000 {+compatible = "mediatek,mt8173-m4u";+reg = <0x10205000 0x1000>;+interrupts = <GIC_SPI 139 IRQ_TYPE_LEVEL_LOW>;+clocks = <&infracfg CLK_INFRA_M4U>;+clock-names = "bclk";+mediatek,larbs = <&larb0 &larb1 &larb2+&larb3&larb4&larb5>;+#iommu-cells = <1>;+};++-|+#include <dt-bindings/memory/mt8173-larb-port.h>++/* Example for a client device */+display {+compatible = "mediatek,mt8173-disp";+iommus = <&iommu M4U_PORT_DISP_OVL0>,+<&iommu M4U_PORT_DISP_RDMA0>;+};
--
2.18.0
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
Extend the max larb number definition as mt8192 has larb_nr over 16.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Acked-by: Rob Herring <robh@kernel.org>
Acked-by: Krzysztof Kozlowski <krzk@kernel.org>
---
Documentation/devicetree/bindings/iommu/mediatek,iommu.yaml | 2 +-
include/dt-bindings/memory/mtk-memory-port.h | 4 ++--
2 files changed, 3 insertions(+), 3 deletions(-)
@@ -99,7 +99,7 @@ properties:mediatek,larbs:$ref:/schemas/types.yaml#/definitions/phandle-arrayminItems:1-maxItems:16+maxItems:32description:|List of phandle to the local arbiters in the current Socs.Refer to bindings/memory-controllers/mediatek,smi-larb.yaml. It must sort
@@ -115,7 +116,11 @@ properties:dt-binding/memory/mt6779-larb-port.h for mt6779,dt-binding/memory/mt8167-larb-port.h for mt8167,dt-binding/memory/mt8173-larb-port.h for mt8173,-dt-binding/memory/mt8183-larb-port.h for mt8183.+dt-binding/memory/mt8183-larb-port.h for mt8183,+dt-binding/memory/mt8192-larb-port.h for mt8192.++power-domains:+maxItems:1required:-compatible
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
From: Rob Herring <robh@kernel.org> Date: 2021-01-14 19:28:32
On Mon, Jan 11, 2021 at 07:18:47PM +0800, Yong Wu wrote:
quoted hunk
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -170,9 +170,11 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,dev_dbg(dev,"device is%sdma coherent\n",coherent?" ":" not ");+dev->dma_range_map=map;iommu=of_iommu_configure(dev,np,id);if(PTR_ERR(iommu)==-EPROBE_DEFER){kfree(map);+dev->dma_range_map=NULL;
Not really going to matter, but you should probably clear dma_range_map
before what it points to is freed.
With that,
Reviewed-by: Rob Herring <robh@kernel.org>
On Thu, 2021-01-14 at 13:27 -0600, Rob Herring wrote:
On Mon, Jan 11, 2021 at 07:18:47PM +0800, Yong Wu wrote:
quoted
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -170,9 +170,11 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,dev_dbg(dev,"device is%sdma coherent\n",coherent?" ":" not ");+dev->dma_range_map=map;iommu=of_iommu_configure(dev,np,id);if(PTR_ERR(iommu)==-EPROBE_DEFER){kfree(map);+dev->dma_range_map=NULL;
Not really going to matter, but you should probably clear dma_range_map
before what it points to is freed.
With that,
Reviewed-by: Rob Herring <robh@kernel.org>
Thanks for the review. I will move it before "kfree(map)" in next
version.
From: Robin Murphy <robin.murphy@arm.com> Date: 2021-01-18 15:52:22
On 2021-01-15 05:30, Yong Wu wrote:
On Thu, 2021-01-14 at 13:27 -0600, Rob Herring wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:47PM +0800, Yong Wu wrote:
quoted
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -170,9 +170,11 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,dev_dbg(dev,"device is%sdma coherent\n",coherent?" ":" not ");+dev->dma_range_map=map;iommu=of_iommu_configure(dev,np,id);if(PTR_ERR(iommu)==-EPROBE_DEFER){kfree(map);+dev->dma_range_map=NULL;
Not really going to matter, but you should probably clear dma_range_map
before what it points to is freed.
With that,
Reviewed-by: Rob Herring <robh@kernel.org>
Thanks for the review. I will move it before "kfree(map)" in next
version.
Paul noticed that we already have a bug in assigning to this
unconditionally[1] - I'd totally forgotten about this series when I
theorised about IOMMU drivers wanting the information earlier, but
sweeping my inbox now only goes to show I was right to think of it :)
We should really get something in as a fix independent of this series,
taking both angles into account.
Robin.
[1]
https://lore.kernel.org/linux-arm-kernel/5c7946f3-b56e-da00-a750-be097c7ceb32@arm.com/
From: Paul Kocialkowski <hidden> Date: 2021-01-19 09:41:23
Hi,
On Mon 18 Jan 21, 15:49, Robin Murphy wrote:
On 2021-01-15 05:30, Yong Wu wrote:
quoted
On Thu, 2021-01-14 at 13:27 -0600, Rob Herring wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:47PM +0800, Yong Wu wrote:
quoted
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -170,9 +170,11 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,dev_dbg(dev,"device is%sdma coherent\n",coherent?" ":" not ");+dev->dma_range_map=map;iommu=of_iommu_configure(dev,np,id);if(PTR_ERR(iommu)==-EPROBE_DEFER){kfree(map);+dev->dma_range_map=NULL;
Not really going to matter, but you should probably clear dma_range_map
before what it points to is freed.
With that,
Reviewed-by: Rob Herring <robh@kernel.org>
Thanks for the review. I will move it before "kfree(map)" in next
version.
Paul noticed that we already have a bug in assigning to this
unconditionally[1] - I'd totally forgotten about this series when I
theorised about IOMMU drivers wanting the information earlier, but sweeping
my inbox now only goes to show I was right to think of it :)
We should really get something in as a fix independent of this series,
taking both angles into account.
Okay, I can also fix this while fixing my case. So we'd go for setting
dev->dma_range_map = map; under the if (!ret).
Then I think the error case for of_iommu_configure should be to set
dev->dma_range_map = NULL; only if map != NULL (otherwise we'd be overwriting
and leaking the previously-set map).
I think a comment to remind that dev->dma_range_map can be set prior to this
function would be useful too.
What do you think?
Cheers,
Paul
On Mon, 2021-01-18 at 15:49 +0000, Robin Murphy wrote:
On 2021-01-15 05:30, Yong Wu wrote:
quoted
On Thu, 2021-01-14 at 13:27 -0600, Rob Herring wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:47PM +0800, Yong Wu wrote:
quoted
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -170,9 +170,11 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,dev_dbg(dev,"device is%sdma coherent\n",coherent?" ":" not ");+dev->dma_range_map=map;iommu=of_iommu_configure(dev,np,id);if(PTR_ERR(iommu)==-EPROBE_DEFER){kfree(map);+dev->dma_range_map=NULL;
Not really going to matter, but you should probably clear dma_range_map
before what it points to is freed.
With that,
Reviewed-by: Rob Herring <robh@kernel.org>
Thanks for the review. I will move it before "kfree(map)" in next
version.
Paul noticed that we already have a bug in assigning to this
unconditionally[1] - I'd totally forgotten about this series when I
theorised about IOMMU drivers wanting the information earlier, but
sweeping my inbox now only goes to show I was right to think of it :)
We should really get something in as a fix independent of this series,
taking both angles into account.
Thanks this info. Following your suggestion, Move this into the "if (!
ret)". Then it is like this:
@@ -181,7 +185,6 @@ int of_dma_configure_id(struct device *dev, struct
device_node *np,
arch_setup_dma_ops(dev, dma_start, size, iommu, coherent);
- dev->dma_range_map = map;
return 0;
}
EXPORT_SYMBOL_GPL(of_dma_configure_id);
If this is ok, I will send this as a independent patch.
From: Paul Kocialkowski <hidden> Date: 2021-01-19 10:10:57
Hi,
On Tue 19 Jan 21, 17:20, Yong Wu wrote:
On Mon, 2021-01-18 at 15:49 +0000, Robin Murphy wrote:
quoted
On 2021-01-15 05:30, Yong Wu wrote:
quoted
On Thu, 2021-01-14 at 13:27 -0600, Rob Herring wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:47PM +0800, Yong Wu wrote:
quoted
"dev->dma_range_map" contains the devices' dma_ranges information,
This patch moves dma_range_map before of_iommu_configure. The iommu
driver may need to know the dma_address requirements of its iommu
consumer devices.
CC: Rob Herring <robh+dt@kernel.org>
CC: Frank Rowand <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/of/device.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -170,9 +170,11 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,dev_dbg(dev,"device is%sdma coherent\n",coherent?" ":" not ");+dev->dma_range_map=map;iommu=of_iommu_configure(dev,np,id);if(PTR_ERR(iommu)==-EPROBE_DEFER){kfree(map);+dev->dma_range_map=NULL;
Not really going to matter, but you should probably clear dma_range_map
before what it points to is freed.
With that,
Reviewed-by: Rob Herring <robh@kernel.org>
Thanks for the review. I will move it before "kfree(map)" in next
version.
Paul noticed that we already have a bug in assigning to this
unconditionally[1] - I'd totally forgotten about this series when I
theorised about IOMMU drivers wanting the information earlier, but
sweeping my inbox now only goes to show I was right to think of it :)
We should really get something in as a fix independent of this series,
taking both angles into account.
Thanks this info. Following your suggestion, Move this into the "if (!
ret)". Then it is like this:
@@ -181,7 +185,6 @@ int of_dma_configure_id(struct device *dev, struct
device_node *np,
arch_setup_dma_ops(dev, dma_start, size, iommu, coherent);
- dev->dma_range_map = map;
return 0;
}
EXPORT_SYMBOL_GPL(of_dma_configure_id);
If this is ok, I will send this as a independent patch.
With the suggested changes, this looks good to me!
Thanks,
Paul
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
From: Will Deacon <will@kernel.org> Date: 2021-01-27 03:45:06
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted hunk
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
Will
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
On Tue, 2021-01-26 at 22:23 +0000, Will Deacon wrote:
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
oh. sorry, I overlooked this. the current code is enough.
I will remove this patch. and send the next version in this week.
Thanks very much.
From: Will Deacon <will@kernel.org> Date: 2021-01-28 21:11:41
On Wed, Jan 27, 2021 at 05:39:16PM +0800, Yong Wu wrote:
On Tue, 2021-01-26 at 22:23 +0000, Will Deacon wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
oh. sorry, I overlooked this. the current code is enough.
I will remove this patch. and send the next version in this week.
Thanks very much.
Actually, looking at this again, if we're dropping this patch and patch 6
just needs the kfree() moving about, then there's no need to repost. The
issue that Robin and Paul are discussing can be handled separately.
Will
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
From: Will Deacon <will@kernel.org> Date: 2021-01-28 21:15:38
On Thu, Jan 28, 2021 at 09:10:20PM +0000, Will Deacon wrote:
On Wed, Jan 27, 2021 at 05:39:16PM +0800, Yong Wu wrote:
quoted
On Tue, 2021-01-26 at 22:23 +0000, Will Deacon wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
oh. sorry, I overlooked this. the current code is enough.
I will remove this patch. and send the next version in this week.
Thanks very much.
Actually, looking at this again, if we're dropping this patch and patch 6
just needs the kfree() moving about, then there's no need to repost. The
issue that Robin and Paul are discussing can be handled separately.
From: Robin Murphy <robin.murphy@arm.com> Date: 2021-01-29 00:05:08
On 2021-01-28 21:14, Will Deacon wrote:
On Thu, Jan 28, 2021 at 09:10:20PM +0000, Will Deacon wrote:
quoted
On Wed, Jan 27, 2021 at 05:39:16PM +0800, Yong Wu wrote:
quoted
On Tue, 2021-01-26 at 22:23 +0000, Will Deacon wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
oh. sorry, I overlooked this. the current code is enough.
I will remove this patch. and send the next version in this week.
Thanks very much.
Actually, looking at this again, if we're dropping this patch and patch 6
just needs the kfree() moving about, then there's no need to repost. The
issue that Robin and Paul are discussing can be handled separately.
FWIW patch #6 gets dropped as well now, since Rob has applied the
standalone fix (89c7cb1608ac).
Robin.
On Thu, 2021-01-28 at 21:14 +0000, Will Deacon wrote:
On Thu, Jan 28, 2021 at 09:10:20PM +0000, Will Deacon wrote:
quoted
On Wed, Jan 27, 2021 at 05:39:16PM +0800, Yong Wu wrote:
quoted
On Tue, 2021-01-26 at 22:23 +0000, Will Deacon wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
oh. sorry, I overlooked this. the current code is enough.
I will remove this patch. and send the next version in this week.
Thanks very much.
Actually, looking at this again, if we're dropping this patch and patch 6
just needs the kfree() moving about, then there's no need to repost. The
issue that Robin and Paul are discussing can be handled separately.
After confirm with Tomasz, He still need some time to take a look at v6.
thus I need wait some time to send v7 after his feedback.
Thanks for your comment. and Thanks Tomasz for the review.
From: Will Deacon <will@kernel.org> Date: 2021-01-29 08:48:59
On Fri, Jan 29, 2021 at 09:52:42AM +0800, Yong Wu wrote:
On Thu, 2021-01-28 at 21:14 +0000, Will Deacon wrote:
quoted
On Thu, Jan 28, 2021 at 09:10:20PM +0000, Will Deacon wrote:
quoted
On Wed, Jan 27, 2021 at 05:39:16PM +0800, Yong Wu wrote:
quoted
On Tue, 2021-01-26 at 22:23 +0000, Will Deacon wrote:
quoted
On Mon, Jan 11, 2021 at 07:18:48PM +0800, Yong Wu wrote:
quoted
If group->default_domain exists, avoid reallocate it.
In some iommu drivers, there may be several devices share a group. Avoid
realloc the default domain for this case.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
@@ -266,7 +266,8 @@ int iommu_probe_device(struct device *dev)*supportdefaultdomains,sothereturnvalueisnotyet*checked.*/-iommu_alloc_default_domain(group,dev);+if(!group->default_domain)+iommu_alloc_default_domain(group,dev);
I don't really get what this achieves, since iommu_alloc_default_domain()
looks like this:
static int iommu_alloc_default_domain(struct iommu_group *group,
struct device *dev)
{
unsigned int type;
if (group->default_domain)
return 0;
...
in which case, it should be fine?
oh. sorry, I overlooked this. the current code is enough.
I will remove this patch. and send the next version in this week.
Thanks very much.
Actually, looking at this again, if we're dropping this patch and patch 6
just needs the kfree() moving about, then there's no need to repost. The
issue that Robin and Paul are discussing can be handled separately.
After confirm with Tomasz, He still need some time to take a look at v6.
thus I need wait some time to send v7 after his feedback.
Thanks for your comment. and Thanks Tomasz for the review.
Ok, but please be aware that I'm planning to send my queue to Joerg on
Monday, so if it doesn't show up today then it will miss 5.12.
Will
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
Use the ias for the valid iova checking in arm_v7s_unmap. This is a
preparing patch for supporting iova 34bit for MediaTek.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Reviewed-by: Robin Murphy <robin.murphy@arm.com>
---
drivers/iommu/io-pgtable-arm-v7s.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
The current _ARM_V7S_LVL_BITS/ARM_V7S_LVL_SHIFT use a formula to calculate
the corresponding value for level1 and level2 to pretend the code sane.
Actually their level1 and level2 values are different from each other.
This patch only clarify the two macro. No functional change.
Suggested-by: Robin Murphy <robin.murphy@arm.com>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Reviewed-by: Robin Murphy <robin.murphy@arm.com>
---
drivers/iommu/io-pgtable-arm-v7s.c | 8 +++-----
1 file changed, 3 insertions(+), 5 deletions(-)
Add "cfg" as a parameter for some macros. This is a preparing patch for
mediatek extend the lvl1 pgtable. No functional change.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Acked-by: Will Deacon <will@kernel.org>
Reviewed-by: Robin Murphy <robin.murphy@arm.com>
---
drivers/iommu/io-pgtable-arm-v7s.c | 36 +++++++++++++++---------------
1 file changed, 18 insertions(+), 18 deletions(-)
@@ -283,7 +283,7 @@ static void __arm_v7s_free_table(void *table, int lvl,{structio_pgtable_cfg*cfg=&data->iop.cfg;structdevice*dev=cfg->iommu_dev;-size_tsize=ARM_V7S_TABLE_SIZE(lvl);+size_tsize=ARM_V7S_TABLE_SIZE(lvl,cfg);if(!cfg->coherent_walk)dma_unmap_single(dev,__arm_v7s_dma_addr(table),size,
@@ -427,7 +427,7 @@ static int arm_v7s_init_pte(struct arm_v7s_io_pgtable *data,arm_v7s_iopte*tblp;size_tsz=ARM_V7S_BLOCK_SIZE(lvl);-tblp=ptep-ARM_V7S_LVL_IDX(iova,lvl);+tblp=ptep-ARM_V7S_LVL_IDX(iova,lvl,cfg);if(WARN_ON(__arm_v7s_unmap(data,NULL,iova+i*sz,sz,lvl,tblp)!=sz))return-EINVAL;
@@ -480,7 +480,7 @@ static int __arm_v7s_map(struct arm_v7s_io_pgtable *data, unsigned long iova,intnum_entries=size>>ARM_V7S_LVL_SHIFT(lvl);/* Find our entry at the current level */-ptep+=ARM_V7S_LVL_IDX(iova,lvl);+ptep+=ARM_V7S_LVL_IDX(iova,lvl,cfg);/* If we can install a leaf entry at this level, then do so */if(num_entries)
@@ -112,9 +112,10 @@#define ARM_V7S_TEX_MASK 0x7#define ARM_V7S_ATTR_TEX(val) (((val) & ARM_V7S_TEX_MASK) << ARM_V7S_TEX_SHIFT)-/* MediaTek extend the two bits for PA 32bit/33bit */+/* MediaTek extend the bits below for PA 32bit/33bit/34bit */#define ARM_V7S_ATTR_MTK_PA_BIT32 BIT(9)#define ARM_V7S_ATTR_MTK_PA_BIT33 BIT(4)+#define ARM_V7S_ATTR_MTK_PA_BIT34 BIT(5)/* *well, except for TEX on level 2 large pages, of course :( */#define ARM_V7S_CONT_PAGE_TEX_SHIFT 6
@@ -194,6 +195,8 @@ static arm_v7s_iopte paddr_to_iopte(phys_addr_t paddr, int lvl,pte|=ARM_V7S_ATTR_MTK_PA_BIT32;if(paddr&BIT_ULL(33))pte|=ARM_V7S_ATTR_MTK_PA_BIT33;+if(paddr&BIT_ULL(34))+pte|=ARM_V7S_ATTR_MTK_PA_BIT34;returnpte;}
@@ -218,6 +221,8 @@ static phys_addr_t iopte_to_paddr(arm_v7s_iopte pte, int lvl,paddr|=BIT_ULL(32);if(pte&ARM_V7S_ATTR_MTK_PA_BIT33)paddr|=BIT_ULL(33);+if(pte&ARM_V7S_ATTR_MTK_PA_BIT34)+paddr|=BIT_ULL(34);returnpaddr;}
Add a HW flag for if the HW support 34bit IOVA. the previous SoC
still use 32bit. normally the lvl1 pgtable size is 16KB when ias == 32.
if ias == 34, lvl1 pgtable size is 16KB * 4. The purpose of this patch
is to save 16KB*3 continuous memory for the previous SoC.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
The standard input iova bits is 32. MediaTek quad the lvl1 pagetable
(4 * lvl1). No change for lvl2 pagetable. Then the iova bits can reach
34bit.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Reviewed-by: Robin Murphy <robin.murphy@arm.com>
---
drivers/iommu/io-pgtable-arm-v7s.c | 7 ++++---
1 file changed, 4 insertions(+), 3 deletions(-)
This patch only updates oas in different SoCs.
If the SoC supports 4GB-mode and current dram size is 4GB, the oas is 33.
otherwise, it's still 32. In the lastest SoC, the oas is 35bits.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
In the original code, we lack the error handle. This patch adds them.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 23 +++++++++++++++++++----
1 file changed, 19 insertions(+), 4 deletions(-)
In the lastest SoC, M4U has its special power domain. thus, If the engine
begin to work, it should help enable the power for M4U firstly.
Currently if the engine work, it always enable the power/clocks for
smi-larbs/smi-common. This patch adds device_link for smi-common and M4U.
then, if smi-common power is enabled, the M4U power also is powered on
automatically.
Normally M4U connect with several smi-larbs and their smi-common always
are the same, In this patch it get smi-common dev from the last smi-larb
device, then add the device_link.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 27 ++++++++++++++++++++++++---
drivers/iommu/mtk_iommu.h | 1 +
2 files changed, 25 insertions(+), 3 deletions(-)
@@ -633,6 +634,9 @@ static int mtk_iommu_probe(struct platform_device *pdev){structmtk_iommu_data*data;structdevice*dev=&pdev->dev;+structdevice_node*larbnode,*smicomm_node;+structplatform_device*plarbdev;+structdevice_link*link;structresource*res;resource_size_tioaddr;structcomponent_match*match=NULL;
@@ -699,8 +703,6 @@ static int mtk_iommu_probe(struct platform_device *pdev)returnlarb_nr;for(i=0;i<larb_nr;i++){-structdevice_node*larbnode;-structplatform_device*plarbdev;u32id;larbnode=of_parse_phandle(dev->of_node,"mediatek,larbs",i);
@@ -727,12 +729,28 @@ static int mtk_iommu_probe(struct platform_device *pdev)compare_of,larbnode);}+/* Get smi-common dev from the last larb. */+smicomm_node=of_parse_phandle(larbnode,"mediatek,smi",0);+if(!smicomm_node)+return-EINVAL;++plarbdev=of_find_device_by_node(smicomm_node);+of_node_put(smicomm_node);+data->smicomm_dev=&plarbdev->dev;++link=device_link_add(data->smicomm_dev,dev,+DL_FLAG_STATELESS|DL_FLAG_PM_RUNTIME);+if(!link){+dev_err(dev,"Unable link %s.\n",dev_name(data->smicomm_dev));+return-EINVAL;+}+platform_set_drvdata(pdev,data);ret=iommu_device_sysfs_add(&data->iommu,dev,NULL,"mtk-iommu.%pa",&ioaddr);if(ret)-returnret;+gotoout_link_remove;iommu_device_set_ops(&data->iommu,&mtk_iommu_ops);iommu_device_set_fwnode(&data->iommu,&pdev->dev.of_node->fwnode);
@@ -762,6 +780,8 @@ static int mtk_iommu_probe(struct platform_device *pdev)iommu_device_unregister(&data->iommu);out_sysfs_remove:iommu_device_sysfs_remove(&data->iommu);+out_link_remove:+device_link_remove(data->smicomm_dev,dev);returnret;}
@@ -776,6 +796,7 @@ static int mtk_iommu_remove(struct platform_device *pdev)bus_set_iommu(&platform_bus_type,NULL);clk_disable_unprepare(data->bclk);+device_link_remove(data->smicomm_dev,&pdev->dev);devm_free_irq(&pdev->dev,data->irq,data);component_master_del(&pdev->dev,&mtk_iommu_com_ops);return0;
In attach device, it will update the pagetable base address register.
Move the hw_init function also here. Then it only need call
pm_runtime_get/put one time here if m4u has power domain.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 13 +++++++------
1 file changed, 7 insertions(+), 6 deletions(-)
@@ -364,12 +366,15 @@ static int mtk_iommu_attach_device(struct iommu_domain *domain,{structmtk_iommu_data*data=dev_iommu_priv_get(dev);structmtk_iommu_domain*dom=to_mtk_domain(domain);+intret;if(!data)return-ENODEV;-/* Update the pgtable base address register of the M4U HW */-if(!data->m4u_dom){+if(!data->m4u_dom){/* Initialize the M4U HW */+ret=mtk_iommu_hw_init(data);+if(ret)+returnret;data->m4u_dom=dom;writel(dom->cfg.arm_v7s_cfg.ttbr&MMU_PT_ADDR_MASK,data->base+REG_MMU_PT_BASE_ADDR);
@@ -724,10 +729,6 @@ static int mtk_iommu_probe(struct platform_device *pdev)platform_set_drvdata(pdev,data);-ret=mtk_iommu_hw_init(data);-if(ret)-returnret;-ret=iommu_device_sysfs_add(&data->iommu,dev,NULL,"mtk-iommu.%pa",&ioaddr);if(ret)
--
2.18.0
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
In pm runtime case, all the registers backup/restore and bclk are
controlled in the pm_runtime callback, Rename the original
suspend/resume to the runtime_suspend/resume.
Use pm_runtime_force_suspend/resume as the normal suspend/resume.
iommu should suspend after iommu consumer devices, thus use _LATE_.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 8 +++++---
1 file changed, 5 insertions(+), 3 deletions(-)
In the previous SoC, the M4U HW is in the EMI power domain which is
always on. the latest M4U is in the display power domain which may be
turned on/off, thus we have to add pm_runtime interface for it.
When the engine work, the engine always enable the power and clocks for
smi-larb/smi-common, then the M4U's power will always be powered on
automatically via the device link with smi-common.
Note: we don't enable the M4U power in iommu_map/unmap for tlb flush.
If its power already is on, of course it is ok. if the power is off,
the main tlb will be reset while M4U power on, thus the tlb flush while
m4u power off is unnecessary, just skip it.
Therefore, we increase the ref_count for pm when pm status is ACTIVE,
otherwise, skip it. Meanwhile, the tlb_flush_range is called so often,
thus, update pm ref_count while the SoC has power-domain to avoid touch the
dev->power.lock. and the tlb_flush_all only is called when boot, so no
need check if the SoC has power-domain to keep code clean.
There will be one case that pm runctime status is not expected when tlb
flush. After boot, the display may call dma_alloc_attrs before it call
pm_runtime_get(disp-dev), then the m4u's pm status is not active inside
the dma_alloc_attrs. Since it only happens after boot, the tlb is clean
at that time, I also think this is ok.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 39 ++++++++++++++++++++++++++++++++++-----
1 file changed, 34 insertions(+), 5 deletions(-)
@@ -219,6 +230,9 @@ static void mtk_iommu_tlb_flush_range_sync(unsigned long iova, size_t size,/* Clear the CPE status */writel_relaxed(0,data->base+REG_MMU_CPE_DONE);spin_unlock_irqrestore(&data->tlb_lock,flags);++if(has_pm)+pm_runtime_put(data->dev);}}
@@ -367,18 +381,27 @@ static int mtk_iommu_attach_device(struct iommu_domain *domain,{structmtk_iommu_data*data=dev_iommu_priv_get(dev);structmtk_iommu_domain*dom=to_mtk_domain(domain);+structdevice*m4udev=data->dev;intret;if(!data)return-ENODEV;if(!data->m4u_dom){/* Initialize the M4U HW */+ret=pm_runtime_resume_and_get(m4udev);+if(ret<0)+returnret;+ret=mtk_iommu_hw_init(data);-if(ret)+if(ret){+pm_runtime_put(m4udev);returnret;+}data->m4u_dom=dom;writel(dom->cfg.arm_v7s_cfg.ttbr&MMU_PT_ADDR_MASK,data->base+REG_MMU_PT_BASE_ADDR);++pm_runtime_put(m4udev);}mtk_iommu_config(data,dev,true);
@@ -738,11 +761,13 @@ static int mtk_iommu_probe(struct platform_device *pdev)of_node_put(smicomm_node);data->smicomm_dev=&plarbdev->dev;+pm_runtime_enable(dev);+link=device_link_add(data->smicomm_dev,dev,DL_FLAG_STATELESS|DL_FLAG_PM_RUNTIME);if(!link){dev_err(dev,"Unable link %s.\n",dev_name(data->smicomm_dev));-return-EINVAL;+gotoout_runtime_disable;}platform_set_drvdata(pdev,data);
@@ -782,6 +807,8 @@ static int mtk_iommu_probe(struct platform_device *pdev)iommu_device_sysfs_remove(&data->iommu);out_link_remove:device_link_remove(data->smicomm_dev,dev);+out_runtime_disable:+pm_runtime_disable(dev);returnret;}
@@ -797,6 +824,7 @@ static int mtk_iommu_remove(struct platform_device *pdev)clk_disable_unprepare(data->bclk);device_link_remove(data->smicomm_dev,&pdev->dev);+pm_runtime_disable(&pdev->dev);devm_free_irq(&pdev->dev,data->irq,data);component_master_del(&pdev->dev,&mtk_iommu_com_ops);return0;
@@ -828,6 +856,9 @@ static int __maybe_unused mtk_iommu_runtime_resume(struct device *dev)void__iomem*base=data->base;intret;+/* Avoid first resume to affect the default value of registers below. */+if(!m4u_dom)+return0;ret=clk_prepare_enable(data->bclk);if(ret){dev_err(data->dev,"Failed to enable clk(%d) in resume\n",ret);
@@ -841,9 +872,7 @@ static int __maybe_unused mtk_iommu_runtime_resume(struct device *dev)writel_relaxed(reg->int_main_control,base+REG_MMU_INT_MAIN_CONTROL);writel_relaxed(reg->ivrp_paddr,base+REG_MMU_IVRP_PADDR);writel_relaxed(reg->vld_pa_rng,base+REG_MMU_VLD_PA_RNG);-if(m4u_dom)-writel(m4u_dom->cfg.arm_v7s_cfg.ttbr&MMU_PT_ADDR_MASK,-base+REG_MMU_PT_BASE_ADDR);+writel(m4u_dom->cfg.arm_v7s_cfg.ttbr&MMU_PT_ADDR_MASK,base+REG_MMU_PT_BASE_ADDR);return0;}
--
2.18.0
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
If the iova is 34bit, the iova[32][33] is the bit0/1 in the tlb flush
register. Add a new macro for this.
In the macro, since (iova + size - 1) may be end with 0xfff, then the
bit0/1 always is 1, thus add a mask.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 10 ++++++++--
1 file changed, 8 insertions(+), 2 deletions(-)
@@ -351,6 +352,7 @@ static int mtk_iommu_domain_finalise(struct mtk_iommu_domain *dom)return-EINVAL;}+dom->data=data;/* Update our support page sizes bitmap */dom->domain.pgsize_bitmap=dom->cfg.pgsize_bitmap;return0;
@@ -442,10 +444,9 @@ static int mtk_iommu_map(struct iommu_domain *domain, unsigned long iova,phys_addr_tpaddr,size_tsize,intprot,gfp_tgfp){structmtk_iommu_domain*dom=to_mtk_domain(domain);-structmtk_iommu_data*data=mtk_iommu_get_m4u_data();/* The "4GB mode" M4U physically can not use the lower remap of Dram. */-if(data->enable_4GB)+if(dom->data->enable_4GB)paddr|=BIT_ULL(32);/* Synchronize with the tlb_lock */
Currently domain_alloc only has a parameter(type), We have no chance to
input some special data. This patch moves the domain_finalise into
attach_device which has the device information, then could update
the domain's geometry.aperture ranges for each a device.
Strictly, I should use the data from mtk_iommu_get_m4u_data as the
parameter of mtk_iommu_domain_finalise in this patch. but dom->data
only is used in tlb ops in which the data is get from the m4u_list, thus
it is ok here.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 31 ++++++++++++-------------------
1 file changed, 12 insertions(+), 19 deletions(-)
If the iova is over 32bit, the fault status register bit is a little
different.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 17 +++++++++++++++--
1 file changed, 15 insertions(+), 2 deletions(-)
Add a new structure for the iova_region. Each a region will be a
independent iommu domain.
For the previous SoC, there is single iova region(0~4G). For the SoC
that need support multi-domains, there will be several regions.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 19 +++++++++++++++++++
drivers/iommu/mtk_iommu.h | 5 +++++
2 files changed, 24 insertions(+)
Move the domain geometry.aperture updating into domain_finalise.
This is a preparing patch for updating the domain region. We know the
detailed iova region in the attach_device.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 7 ++++---
1 file changed, 4 insertions(+), 3 deletions(-)
Add a new interface _get_domain_id from dev->dma_range_map,
The iommu consumer device will use dma-ranges in dtsi node to indicate
its dma address region requirement. In this iommu driver, we will get
the requirement and decide which iova domain it should locate.
In the lastest SoC, there will be several iova-regions(domains), we will
compare and calculate which domain is right. If the start/end of device
requirement equal some region. it is best fit of course. If it is inside
some region, it is also ok. the iova requirement of a device should not
be inside two or more regions.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 42 ++++++++++++++++++++++++++++++++++++++-
1 file changed, 41 insertions(+), 1 deletion(-)
@@ -314,6 +315,36 @@ static irqreturn_t mtk_iommu_isr(int irq, void *dev_id)returnIRQ_HANDLED;}+staticintmtk_iommu_get_domain_id(structdevice*dev,+conststructmtk_iommu_plat_data*plat_data)+{+conststructmtk_iommu_iova_region*rgn=plat_data->iova_region;+conststructbus_dma_region*dma_rgn=dev->dma_range_map;+inti,candidate=-1;+dma_addr_tdma_end;++if(!dma_rgn||plat_data->iova_region_nr==1)+return0;++dma_end=dma_rgn->dma_start+dma_rgn->size-1;+for(i=0;i<plat_data->iova_region_nr;i++,rgn++){+/* Best fit. */+if(dma_rgn->dma_start==rgn->iova_base&&+dma_end==rgn->iova_base+rgn->size-1)+returni;+/* ok if it is inside this region. */+if(dma_rgn->dma_start>=rgn->iova_base&&+dma_end<rgn->iova_base+rgn->size)+candidate=i;+}++if(candidate>=0)+returncandidate;+dev_err(dev,"Can NOT find the iommu domain id(%pad 0x%llx).\n",+&dma_rgn->dma_start,dma_rgn->size);+return-EINVAL;+}+staticvoidmtk_iommu_config(structmtk_iommu_data*data,structdevice*dev,boolenable){
@@ -400,11 +431,15 @@ static int mtk_iommu_attach_device(struct iommu_domain *domain,structmtk_iommu_data*data=dev_iommu_priv_get(dev);structmtk_iommu_domain*dom=to_mtk_domain(domain);structdevice*m4udev=data->dev;-intret;+intret,domid;if(!data)return-ENODEV;+domid=mtk_iommu_get_domain_id(dev,data->plat_data);+if(domid<0)+returndomid;+if(!dom->data){if(mtk_iommu_domain_finalise(dom,data))return-ENODEV;
@@ -534,10 +569,15 @@ static void mtk_iommu_release_device(struct device *dev)staticstructiommu_group*mtk_iommu_device_group(structdevice*dev){structmtk_iommu_data*data=mtk_iommu_get_m4u_data();+intdomid;if(!data)returnERR_PTR(-ENODEV);+domid=mtk_iommu_get_domain_id(dev,data->plat_data);+if(domid<0)+returnERR_PTR(domid);+/* All the client devices are in the same m4u iommu-group */if(!data->m4u_group){data->m4u_group=iommu_group_alloc();
--
2.18.0
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
Some HW IP(ex: CCU) require the special iova range. That means the iova
got from dma_alloc_attrs for that devices must locate in his special range.
In this patch, we prepare a iommu group(domain) for each a iova range
requirement.
Meanwhile we still use one pagetable which support 16GB iova.
After this patch, If the iova range of a master is over 4G, the master
should:
a) Declare its special dma-ranges in its dtsi node. For example, If we
preassign the iova 4G-8G for vcodec, then the vcodec dtsi node should
add this:
/*
* iova start at 0x1_0000_0000, pa still start at 0x4000_0000
* size is 0x1_0000_0000.
*/
dma-ranges = <0x1 0x0 0x0 0x40000000 0x1 0x0>; /* 4G ~ 8G */
Note: we don't have a actual bus concept here. the master doesn't have its
special parent node, thus this dma-ranges can only be put in the master's
node.
b) Update the dma_mask:
dma_set_mask_and_coherent(dev, DMA_BIT_MASK(33));
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 37 ++++++++++++++++++++++++++-----------
drivers/iommu/mtk_iommu.h | 4 +++-
2 files changed, 29 insertions(+), 12 deletions(-)
@@ -369,8 +369,19 @@ static void mtk_iommu_config(struct mtk_iommu_data *data,}staticintmtk_iommu_domain_finalise(structmtk_iommu_domain*dom,-structmtk_iommu_data*data)+structmtk_iommu_data*data,+unsignedintdomid){+conststructmtk_iommu_iova_region*region;++/* Use the exist domain as there is only one pgtable here. */+if(data->m4u_dom){+dom->iop=data->m4u_dom->iop;+dom->cfg=data->m4u_dom->cfg;+dom->domain.pgsize_bitmap=data->m4u_dom->cfg.pgsize_bitmap;+gotoupdate_iova_region;+}+dom->cfg=(structio_pgtable_cfg){.quirks=IO_PGTABLE_QUIRK_ARM_NS|IO_PGTABLE_QUIRK_NO_PERMS|
@@ -394,8 +405,11 @@ static int mtk_iommu_domain_finalise(struct mtk_iommu_domain *dom,/* Update our support page sizes bitmap */dom->domain.pgsize_bitmap=dom->cfg.pgsize_bitmap;-dom->domain.geometry.aperture_start=0;-dom->domain.geometry.aperture_end=DMA_BIT_MASK(32);+update_iova_region:+/* Update the iova region for this domain */+region=data->plat_data->iova_region+domid;+dom->domain.geometry.aperture_start=region->iova_base;+dom->domain.geometry.aperture_end=region->iova_base+region->size-1;dom->domain.geometry.force_aperture=true;return0;}
@@ -441,7 +455,7 @@ static int mtk_iommu_attach_device(struct iommu_domain *domain,returndomid;if(!dom->data){-if(mtk_iommu_domain_finalise(dom,data))+if(mtk_iommu_domain_finalise(dom,data,domid))return-ENODEV;dom->data=data;}
@@ -578,15 +593,15 @@ static struct iommu_group *mtk_iommu_device_group(struct device *dev)if(domid<0)returnERR_PTR(domid);-/* All the client devices are in the same m4u iommu-group */-if(!data->m4u_group){-data->m4u_group=iommu_group_alloc();-if(IS_ERR(data->m4u_group))-dev_err(dev,"Failed to allocate M4U IOMMU group\n");+group=data->m4u_group[domid];+if(!group){+group=iommu_group_alloc();+if(!IS_ERR(group))+data->m4u_group[domid]=group;}else{-iommu_group_ref_get(data->m4u_group);+iommu_group_ref_get(group);}-returndata->m4u_group;+returngroup;}staticintmtk_iommu_of_xlate(structdevice*dev,structof_phandle_args*args)
For multiple iommu_domains, we need to reserve some iova regions. Take a
example, If the default iova region is 0 ~ 4G, but the 0x4000_0000 ~
0x43ff_ffff is only for the special CCU0 domain. Thus we should exclude
this region for the default iova region.
Signed-off-by: Anan sun <redacted>
Signed-off-by: Chao Hao <redacted>
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 31 +++++++++++++++++++++++++++++++
1 file changed, 31 insertions(+)
@@ -626,6 +626,35 @@ static int mtk_iommu_of_xlate(struct device *dev, struct of_phandle_args *args)returniommu_fwspec_add_ids(dev,args->args,1);}+staticvoidmtk_iommu_get_resv_regions(structdevice*dev,+structlist_head*head)+{+structmtk_iommu_data*data=dev_iommu_priv_get(dev);+unsignedintdomid=mtk_iommu_get_domain_id(dev,data->plat_data),i;+conststructmtk_iommu_iova_region*resv,*curdom;+structiommu_resv_region*region;+intprot=IOMMU_WRITE|IOMMU_READ;++if(domid<0)+return;+curdom=data->plat_data->iova_region+domid;+for(i=0;i<data->plat_data->iova_region_nr;i++){+resv=data->plat_data->iova_region+i;++/* Only reserve when the region is inside the current domain */+if(resv->iova_base<=curdom->iova_base||+resv->iova_base+resv->size>=curdom->iova_base+curdom->size)+continue;++region=iommu_alloc_resv_region(resv->iova_base,resv->size,+prot,IOMMU_RESV_RESERVED);+if(!region)+return;++list_add_tail(®ion->list,head);+}+}+staticconststructiommu_opsmtk_iommu_ops={.domain_alloc=mtk_iommu_domain_alloc,.domain_free=mtk_iommu_domain_free,
After extending v7s, our pagetable already support iova reach
16GB(34bit). the master got the iova via dma_alloc_attrs may reach
34bits, but its HW register still is 32bit. then how to set the
bit32/bit33 iova? this depend on a SMI larb setting(bank_sel).
we separate whole 16GB iova to four banks:
bank: 0: 0~4G; 1: 4~8G; 2: 8-12G; 3: 12-16G;
The bank number is (iova >> 32).
We will preassign which bank the larbs belong to. currently we don't
have a interface for master to adjust its bank number.
Each a bank is a iova_region which is a independent iommu-domain.
the iova range for each iommu-domain can't cross 4G.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Acked-by: Krzysztof Kozlowski <krzk@kernel.org> #for memory part
---
drivers/iommu/mtk_iommu.c | 18 ++++++++++++------
drivers/memory/mtk-smi.c | 7 +++++++
include/soc/mediatek/smi.h | 1 +
3 files changed, 20 insertions(+), 6 deletions(-)
@@ -345,21 +345,27 @@ static int mtk_iommu_get_domain_id(struct device *dev,return-EINVAL;}-staticvoidmtk_iommu_config(structmtk_iommu_data*data,-structdevice*dev,boolenable)+staticvoidmtk_iommu_config(structmtk_iommu_data*data,structdevice*dev,+boolenable,unsignedintdomid){structmtk_smi_larb_iommu*larb_mmu;unsignedintlarbid,portid;structiommu_fwspec*fwspec=dev_iommu_fwspec_get(dev);+conststructmtk_iommu_iova_region*region;inti;for(i=0;i<fwspec->num_ids;++i){larbid=MTK_M4U_TO_LARB(fwspec->ids[i]);portid=MTK_M4U_TO_PORT(fwspec->ids[i]);+larb_mmu=&data->larb_imu[larbid];-dev_dbg(dev,"%s iommu port: %d\n",-enable?"enable":"disable",portid);+region=data->plat_data->iova_region+domid;+larb_mmu->bank[portid]=upper_32_bits(region->iova_base);++dev_dbg(dev,"%s iommu for larb(%s) port %d dom %d bank %d.\n",+enable?"enable":"disable",dev_name(larb_mmu->dev),+portid,domid,larb_mmu->bank[portid]);if(enable)larb_mmu->mmu|=MTK_SMI_MMU_EN(portid);
@@ -477,7 +483,7 @@ static int mtk_iommu_attach_device(struct iommu_domain *domain,pm_runtime_put(m4udev);}-mtk_iommu_config(data,dev,true);+mtk_iommu_config(data,dev,true,domid);return0;}
This priv_data is set in the of_xlate. if of_xlate failed, it should
not enter attach_device. remove the unnecessary check.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
---
drivers/iommu/mtk_iommu.c | 6 ------
1 file changed, 6 deletions(-)
I am the author of MediaTek iommu driver, and will to maintain and
develop it further.
Add myself to cover these items.
Signed-off-by: Yong Wu <yong.wu@mediatek.com>
Reviewed-by: Chun-Kuang Hu <chunkuang.hu@kernel.org>
---
MAINTAINERS | 9 +++++++++
1 file changed, 9 insertions(+)
From: Will Deacon <will@kernel.org> Date: 2021-01-27 03:45:07
On Mon, Jan 11, 2021 at 07:18:41PM +0800, Yong Wu wrote:
This patch mainly adds support for mt8192 Multimedia IOMMU and SMI.
mt8192 also is MTK IOMMU gen2 which uses ARM Short-Descriptor translation
table format. The M4U-SMI HW diagram is as below:
EMI
|
M4U
|
------------
SMI Common
------------
|
+-------+------+------+----------------------+-------+
| | | | ...... | |
| | | | | |
larb0 larb1 larb2 larb4 ...... larb19 larb20
disp0 disp1 mdp vdec IPE IPE
All the connections are HW fixed, SW can NOT adjust it.
Comparing with the preview SoC, this patchset mainly adds two new functions:
a) add iova 34 bits support.
b) add multi domains support since several HW has the special iova
region requirement.
This is looking good and I'd really like to see it merged, especially as it
has changes to the io-pgtable code. Please could you post a new version ASAP
to address the comments on patches 6 and 7?
Will
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
From: Tomasz Figa <tfiga@chromium.org> Date: 2021-01-29 11:29:47
Hi Yong,
On Mon, Jan 11, 2021 at 07:18:41PM +0800, Yong Wu wrote:
This patch mainly adds support for mt8192 Multimedia IOMMU and SMI.
mt8192 also is MTK IOMMU gen2 which uses ARM Short-Descriptor translation
table format. The M4U-SMI HW diagram is as below:
EMI
|
M4U
|
------------
SMI Common
------------
|
+-------+------+------+----------------------+-------+
| | | | ...... | |
| | | | | |
larb0 larb1 larb2 larb4 ...... larb19 larb20
disp0 disp1 mdp vdec IPE IPE
All the connections are HW fixed, SW can NOT adjust it.
Comparing with the preview SoC, this patchset mainly adds two new functions:
a) add iova 34 bits support.
b) add multi domains support since several HW has the special iova
region requirement.
change note:
v6:a) base on v5.11-rc1. and tlb v4:
https://lore.kernel.org/linux-mediatek/20210107122909.16317-1-yong.wu@mediatek.com/T/#t
b) Remove the "domain id" definition in the binding header file.
Get the domain from dev->dma_range_map.
After this, Change many codes flow.
c) the patchset adds a new common file(mtk_smi-larb-port.h).
This version changes that name into mtk-memory-port.h which reflect
its file path. This only changes the file name. no other change.
thus I keep all the Reviewed-by Tags.
(another reason is that we will add some iommu ports unrelated with
smi-larb)
d) Refactor the power-domain flow suggestted by Tomasz.
e) Some other small fix. use different oas for different soc; Change the
macro for 34bit iova tlb flush.
Thanks for the fixes.
I still think the concept of dma-ranges is not quire right for the
problem we need to solve here, but it certainly works for the time being
and it's possible to remove it in a follow up patch, so I'm fine with
merging this as is.
Reviewed-by: Tomasz Figa <tfiga@chromium.org>
I'll comment on my suggestion for a replacement for the dma-ranges that
doesn't need hardcoding arbitrary address ranges in DT in a separate
reply.
Best regards,
Tomasz
_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
From: Will Deacon <will@kernel.org> Date: 2021-02-01 15:20:03
On Mon, Jan 11, 2021 at 07:18:41PM +0800, Yong Wu wrote:
This patch mainly adds support for mt8192 Multimedia IOMMU and SMI.
mt8192 also is MTK IOMMU gen2 which uses ARM Short-Descriptor translation
table format. The M4U-SMI HW diagram is as below:
EMI
|
M4U
|
------------
SMI Common
------------
|
+-------+------+------+----------------------+-------+
| | | | ...... | |
| | | | | |
larb0 larb1 larb2 larb4 ...... larb19 larb20
disp0 disp1 mdp vdec IPE IPE
All the connections are HW fixed, SW can NOT adjust it.
Comparing with the preview SoC, this patchset mainly adds two new functions:
a) add iova 34 bits support.
b) add multi domains support since several HW has the special iova
region requirement.
change note:
v6:a) base on v5.11-rc1. and tlb v4:
https://lore.kernel.org/linux-mediatek/20210107122909.16317-1-yong.wu@mediatek.com/T/#t