Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge branch 'icc-imx8mp' into icc-next

This patchset is to support i.MX8MP NoC settings, i.MX8MP NoC initial
value after power up is invalid, need set a valid value after related
power domain up.

This patchset also includes two patch[1,2] during my development to enable
the ICC feature for i.MX8MP.

I not include ddrc DVFS in this patchset, ths patchset is only to
support NoC value mode/priority/ext_control being set to a valid value
that suggested by i.MX Chip Design Team. The value is same as NXP
downstream one inside Arm Trusted Firmware:
https://source.codeaurora.org/external/imx/imx-atf/tree/plat/imx/imx8m/i/gpc.c?h=lf_v2.4#n97

Link: https://lore.kernel.org/r/20220703091132.1412063-1-peng.fan@oss.nxp.com
Signed-off-by: Georgi Djakov <djakov@kernel.org>

+496 -23
+4 -2
Documentation/devicetree/bindings/interconnect/fsl,imx8m-noc.yaml
··· 26 26 oneOf: 27 27 - items: 28 28 - enum: 29 - - fsl,imx8mn-nic 30 29 - fsl,imx8mm-nic 30 + - fsl,imx8mn-nic 31 + - fsl,imx8mp-nic 31 32 - fsl,imx8mq-nic 32 33 - const: fsl,imx8m-nic 33 34 - items: 34 35 - enum: 35 - - fsl,imx8mn-noc 36 36 - fsl,imx8mm-noc 37 + - fsl,imx8mn-noc 38 + - fsl,imx8mp-noc 37 39 - fsl,imx8mq-noc 38 40 - const: fsl,imx8m-noc 39 41 - const: fsl,imx8m-nic
+1
drivers/devfreq/imx-bus.c
··· 145 145 { .compatible = "fsl,imx8mq-noc", .data = "imx8mq-interconnect", }, 146 146 { .compatible = "fsl,imx8mm-noc", .data = "imx8mm-interconnect", }, 147 147 { .compatible = "fsl,imx8mn-noc", .data = "imx8mn-interconnect", }, 148 + { .compatible = "fsl,imx8mp-noc", .data = "imx8mp-interconnect", }, 148 149 { .compatible = "fsl,imx8m-noc", }, 149 150 { .compatible = "fsl,imx8m-nic", }, 150 151 { /* sentinel */ },
+42
drivers/interconnect/bulk.c
··· 115 115 icc_disable(paths[num_paths].path); 116 116 } 117 117 EXPORT_SYMBOL_GPL(icc_bulk_disable); 118 + 119 + struct icc_bulk_devres { 120 + struct icc_bulk_data *paths; 121 + int num_paths; 122 + }; 123 + 124 + static void devm_icc_bulk_release(struct device *dev, void *res) 125 + { 126 + struct icc_bulk_devres *devres = res; 127 + 128 + icc_bulk_put(devres->num_paths, devres->paths); 129 + } 130 + 131 + /** 132 + * devm_of_icc_bulk_get() - resource managed of_icc_bulk_get 133 + * @dev: the device requesting the path 134 + * @num_paths: the number of icc_bulk_data 135 + * @paths: the table with the paths we want to get 136 + * 137 + * Returns 0 on success or negative errno otherwise. 138 + */ 139 + int devm_of_icc_bulk_get(struct device *dev, int num_paths, struct icc_bulk_data *paths) 140 + { 141 + struct icc_bulk_devres *devres; 142 + int ret; 143 + 144 + devres = devres_alloc(devm_icc_bulk_release, sizeof(*devres), GFP_KERNEL); 145 + if (!devres) 146 + return -ENOMEM; 147 + 148 + ret = of_icc_bulk_get(dev, num_paths, paths); 149 + if (!ret) { 150 + devres->paths = paths; 151 + devres->num_paths = num_paths; 152 + devres_add(dev, devres); 153 + } else { 154 + devres_free(devres); 155 + } 156 + 157 + return ret; 158 + } 159 + EXPORT_SYMBOL_GPL(devm_of_icc_bulk_get);
+4
drivers/interconnect/imx/Kconfig
··· 15 15 config INTERCONNECT_IMX8MQ 16 16 tristate "i.MX8MQ interconnect driver" 17 17 depends on INTERCONNECT_IMX 18 + 19 + config INTERCONNECT_IMX8MP 20 + tristate "i.MX8MP interconnect driver" 21 + depends on INTERCONNECT_IMX
+2
drivers/interconnect/imx/Makefile
··· 2 2 imx8mm-interconnect-objs := imx8mm.o 3 3 imx8mq-interconnect-objs := imx8mq.o 4 4 imx8mn-interconnect-objs := imx8mn.o 5 + imx8mp-interconnect-objs := imx8mp.o 5 6 6 7 obj-$(CONFIG_INTERCONNECT_IMX) += imx-interconnect.o 7 8 obj-$(CONFIG_INTERCONNECT_IMX8MM) += imx8mm-interconnect.o 8 9 obj-$(CONFIG_INTERCONNECT_IMX8MQ) += imx8mq-interconnect.o 9 10 obj-$(CONFIG_INTERCONNECT_IMX8MN) += imx8mn-interconnect.o 11 + obj-$(CONFIG_INTERCONNECT_IMX8MP) += imx8mp-interconnect.o
+67 -17
drivers/interconnect/imx/imx.c
··· 10 10 11 11 #include <linux/device.h> 12 12 #include <linux/interconnect-provider.h> 13 + #include <linux/io.h> 13 14 #include <linux/module.h> 14 15 #include <linux/of.h> 15 16 #include <linux/of_platform.h> ··· 22 21 /* private icc_node data */ 23 22 struct imx_icc_node { 24 23 const struct imx_icc_node_desc *desc; 24 + const struct imx_icc_noc_setting *setting; 25 25 struct device *qos_dev; 26 26 struct dev_pm_qos_request qos_req; 27 + struct imx_icc_provider *imx_provider; 27 28 }; 28 29 29 30 static int imx_icc_get_bw(struct icc_node *node, u32 *avg, u32 *peak) ··· 40 37 { 41 38 struct device *dev = node->provider->dev; 42 39 struct imx_icc_node *node_data = node->data; 40 + void __iomem *base; 41 + u32 prio; 43 42 u64 freq; 43 + 44 + if (node_data->setting && node->peak_bw) { 45 + base = node_data->setting->reg + node_data->imx_provider->noc_base; 46 + if (node_data->setting->mode == IMX_NOC_MODE_FIXED) { 47 + prio = node_data->setting->prio_level; 48 + prio = PRIORITY_COMP_MARK | (prio << 8) | prio; 49 + writel(prio, base + IMX_NOC_PRIO_REG); 50 + writel(node_data->setting->mode, base + IMX_NOC_MODE_REG); 51 + writel(node_data->setting->ext_control, base + IMX_NOC_EXT_CTL_REG); 52 + dev_dbg(dev, "%s: mode: 0x%x, prio: 0x%x, ext_control: 0x%x\n", 53 + node_data->desc->name, node_data->setting->mode, prio, 54 + node_data->setting->ext_control); 55 + } else if (node_data->setting->mode == IMX_NOC_MODE_UNCONFIGURED) { 56 + dev_dbg(dev, "%s: mode not unconfigured\n", node_data->desc->name); 57 + } else { 58 + dev_info(dev, "%s: mode: %d not supported\n", 59 + node_data->desc->name, node_data->setting->mode); 60 + return -EOPNOTSUPP; 61 + } 62 + } 44 63 45 64 if (!node_data->qos_dev) 46 65 return 0; ··· 86 61 87 62 static int imx_icc_set(struct icc_node *src, struct icc_node *dst) 88 63 { 64 + int ret; 65 + 66 + ret = imx_icc_node_set(src); 67 + if (ret) 68 + return ret; 69 + 89 70 return imx_icc_node_set(dst); 90 71 } 91 72 ··· 159 128 DEV_PM_QOS_MIN_FREQUENCY, 0); 160 129 } 161 130 162 - static struct icc_node *imx_icc_node_add(struct icc_provider *provider, 163 - const struct imx_icc_node_desc *node_desc) 131 + static struct icc_node *imx_icc_node_add(struct imx_icc_provider *imx_provider, 132 + const struct imx_icc_node_desc *node_desc, 133 + const struct imx_icc_noc_setting *setting) 164 134 { 135 + struct icc_provider *provider = &imx_provider->provider; 165 136 struct device *dev = provider->dev; 166 137 struct imx_icc_node *node_data; 167 138 struct icc_node *node; ··· 190 157 node->name = node_desc->name; 191 158 node->data = node_data; 192 159 node_data->desc = node_desc; 160 + node_data->setting = setting; 161 + node_data->imx_provider = imx_provider; 193 162 icc_node_add(node, provider); 194 163 195 164 if (node_desc->adj) { ··· 213 178 imx_icc_node_destroy(node); 214 179 } 215 180 216 - static int imx_icc_register_nodes(struct icc_provider *provider, 181 + static int imx_icc_register_nodes(struct imx_icc_provider *imx_provider, 217 182 const struct imx_icc_node_desc *descs, 218 - int count) 183 + int count, 184 + const struct imx_icc_noc_setting *settings) 219 185 { 186 + struct icc_provider *provider = &imx_provider->provider; 220 187 struct icc_onecell_data *provider_data = provider->data; 221 188 int ret; 222 189 int i; ··· 228 191 const struct imx_icc_node_desc *node_desc = &descs[i]; 229 192 size_t j; 230 193 231 - node = imx_icc_node_add(provider, node_desc); 194 + node = imx_icc_node_add(imx_provider, node_desc, 195 + settings ? &settings[node_desc->id] : NULL); 232 196 if (IS_ERR(node)) { 233 197 ret = dev_err_probe(provider->dev, PTR_ERR(node), 234 198 "failed to add %s\n", node_desc->name); ··· 267 229 } 268 230 269 231 int imx_icc_register(struct platform_device *pdev, 270 - struct imx_icc_node_desc *nodes, int nodes_count) 232 + struct imx_icc_node_desc *nodes, int nodes_count, 233 + struct imx_icc_noc_setting *settings) 271 234 { 272 235 struct device *dev = &pdev->dev; 273 236 struct icc_onecell_data *data; 237 + struct imx_icc_provider *imx_provider; 274 238 struct icc_provider *provider; 275 - int max_node_id; 239 + int num_nodes; 276 240 int ret; 277 241 278 242 /* icc_onecell_data is indexed by node_id, unlike nodes param */ 279 - max_node_id = get_max_node_id(nodes, nodes_count); 280 - data = devm_kzalloc(dev, struct_size(data, nodes, max_node_id), 243 + num_nodes = get_max_node_id(nodes, nodes_count) + 1; 244 + data = devm_kzalloc(dev, struct_size(data, nodes, num_nodes), 281 245 GFP_KERNEL); 282 246 if (!data) 283 247 return -ENOMEM; 284 - data->num_nodes = max_node_id; 248 + data->num_nodes = num_nodes; 285 249 286 - provider = devm_kzalloc(dev, sizeof(*provider), GFP_KERNEL); 287 - if (!provider) 250 + imx_provider = devm_kzalloc(dev, sizeof(*imx_provider), GFP_KERNEL); 251 + if (!imx_provider) 288 252 return -ENOMEM; 253 + provider = &imx_provider->provider; 289 254 provider->set = imx_icc_set; 290 255 provider->get_bw = imx_icc_get_bw; 291 256 provider->aggregate = icc_std_aggregate; 292 257 provider->xlate = of_icc_xlate_onecell; 293 258 provider->data = data; 294 259 provider->dev = dev->parent; 295 - platform_set_drvdata(pdev, provider); 260 + platform_set_drvdata(pdev, imx_provider); 261 + 262 + if (settings) { 263 + imx_provider->noc_base = devm_of_iomap(dev, provider->dev->of_node, 0, NULL); 264 + if (IS_ERR(imx_provider->noc_base)) { 265 + ret = PTR_ERR(imx_provider->noc_base); 266 + dev_err(dev, "Error mapping NoC: %d\n", ret); 267 + return ret; 268 + } 269 + } 296 270 297 271 ret = icc_provider_add(provider); 298 272 if (ret) { ··· 312 262 return ret; 313 263 } 314 264 315 - ret = imx_icc_register_nodes(provider, nodes, nodes_count); 265 + ret = imx_icc_register_nodes(imx_provider, nodes, nodes_count, settings); 316 266 if (ret) 317 267 goto provider_del; 318 268 ··· 326 276 327 277 int imx_icc_unregister(struct platform_device *pdev) 328 278 { 329 - struct icc_provider *provider = platform_get_drvdata(pdev); 279 + struct imx_icc_provider *imx_provider = platform_get_drvdata(pdev); 330 280 331 - imx_icc_unregister_nodes(provider); 281 + imx_icc_unregister_nodes(&imx_provider->provider); 332 282 333 - return icc_provider_del(provider); 283 + return icc_provider_del(&imx_provider->provider); 334 284 } 335 285 EXPORT_SYMBOL_GPL(imx_icc_unregister); 336 286
+48 -1
drivers/interconnect/imx/imx.h
··· 10 10 #ifndef __DRIVERS_INTERCONNECT_IMX_H 11 11 #define __DRIVERS_INTERCONNECT_IMX_H 12 12 13 + #include <linux/interconnect-provider.h> 13 14 #include <linux/kernel.h> 14 15 15 16 #define IMX_ICC_MAX_LINKS 4 17 + 18 + /* 19 + * High throughput priority level in Regulator mode 20 + * Read Priority in Fixed/Limiter mode 21 + */ 22 + #define PRIORITY0_SHIFT 0 23 + /* 24 + * Low throughput priority level in Regulator mode 25 + * Write Priority in Fixed/Limiter mode 26 + */ 27 + #define PRIORITY1_SHIFT 8 28 + #define PRIORITY_MASK 0x7 29 + 30 + #define PRIORITY_COMP_MARK BIT(31) /* Must set */ 31 + 32 + #define IMX_NOC_MODE_FIXED 0 33 + #define IMX_NOC_MODE_LIMITER 1 34 + #define IMX_NOC_MODE_BYPASS 2 35 + #define IMX_NOC_MODE_REGULATOR 3 36 + #define IMX_NOC_MODE_UNCONFIGURED 0xFF 37 + 38 + #define IMX_NOC_PRIO_REG 0x8 39 + #define IMX_NOC_MODE_REG 0xC 40 + #define IMX_NOC_BANDWIDTH_REG 0x10 41 + #define IMX_NOC_SATURATION 0x14 42 + #define IMX_NOC_EXT_CTL_REG 0x18 43 + 44 + struct imx_icc_provider { 45 + void __iomem *noc_base; 46 + struct icc_provider provider; 47 + }; 16 48 17 49 /* 18 50 * struct imx_icc_node_adj - Describe a dynamic adjustable node ··· 70 38 const struct imx_icc_node_adj_desc *adj; 71 39 }; 72 40 41 + /* 42 + * struct imx_icc_noc_setting - Describe an interconnect node setting 43 + * @reg: register offset inside the NoC 44 + * @prio_level: priority level 45 + * @mode: functional mode 46 + * @ext_control: external input control 47 + */ 48 + struct imx_icc_noc_setting { 49 + u32 reg; 50 + u32 prio_level; 51 + u32 mode; 52 + u32 ext_control; 53 + }; 54 + 73 55 #define DEFINE_BUS_INTERCONNECT(_name, _id, _adj, ...) \ 74 56 { \ 75 57 .id = _id, \ ··· 101 55 102 56 int imx_icc_register(struct platform_device *pdev, 103 57 struct imx_icc_node_desc *nodes, 104 - int nodes_count); 58 + int nodes_count, 59 + struct imx_icc_noc_setting *noc_settings); 105 60 int imx_icc_unregister(struct platform_device *pdev); 106 61 107 62 #endif /* __DRIVERS_INTERCONNECT_IMX_H */
+1 -1
drivers/interconnect/imx/imx8mm.c
··· 83 83 84 84 static int imx8mm_icc_probe(struct platform_device *pdev) 85 85 { 86 - return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes)); 86 + return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes), NULL); 87 87 } 88 88 89 89 static int imx8mm_icc_remove(struct platform_device *pdev)
+1 -1
drivers/interconnect/imx/imx8mn.c
··· 72 72 73 73 static int imx8mn_icc_probe(struct platform_device *pdev) 74 74 { 75 - return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes)); 75 + return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes), NULL); 76 76 } 77 77 78 78 static int imx8mn_icc_remove(struct platform_device *pdev)
+259
drivers/interconnect/imx/imx8mp.c
··· 1 + // SPDX-License-Identifier: GPL-2.0 2 + /* 3 + * Interconnect framework driver for i.MX8MP SoC 4 + * 5 + * Copyright 2022 NXP 6 + * Peng Fan <peng.fan@nxp.com> 7 + */ 8 + 9 + #include <linux/module.h> 10 + #include <linux/of_device.h> 11 + #include <linux/platform_device.h> 12 + #include <dt-bindings/interconnect/fsl,imx8mp.h> 13 + 14 + #include "imx.h" 15 + 16 + static const struct imx_icc_node_adj_desc imx8mp_noc_adj = { 17 + .bw_mul = 1, 18 + .bw_div = 16, 19 + .main_noc = true, 20 + }; 21 + 22 + static struct imx_icc_noc_setting noc_setting_nodes[] = { 23 + [IMX8MP_ICM_MLMIX] = { 24 + .reg = 0x180, 25 + .mode = IMX_NOC_MODE_FIXED, 26 + .prio_level = 3, 27 + }, 28 + [IMX8MP_ICM_DSP] = { 29 + .reg = 0x200, 30 + .mode = IMX_NOC_MODE_FIXED, 31 + .prio_level = 3, 32 + }, 33 + [IMX8MP_ICM_SDMA2PER] = { 34 + .reg = 0x280, 35 + .mode = IMX_NOC_MODE_FIXED, 36 + .prio_level = 4, 37 + }, 38 + [IMX8MP_ICM_SDMA2BURST] = { 39 + .reg = 0x300, 40 + .mode = IMX_NOC_MODE_FIXED, 41 + .prio_level = 4, 42 + }, 43 + [IMX8MP_ICM_SDMA3PER] = { 44 + .reg = 0x380, 45 + .mode = IMX_NOC_MODE_FIXED, 46 + .prio_level = 4, 47 + }, 48 + [IMX8MP_ICM_SDMA3BURST] = { 49 + .reg = 0x400, 50 + .mode = IMX_NOC_MODE_FIXED, 51 + .prio_level = 4, 52 + }, 53 + [IMX8MP_ICM_EDMA] = { 54 + .reg = 0x480, 55 + .mode = IMX_NOC_MODE_FIXED, 56 + .prio_level = 4, 57 + }, 58 + [IMX8MP_ICM_GPU3D] = { 59 + .reg = 0x500, 60 + .mode = IMX_NOC_MODE_FIXED, 61 + .prio_level = 3, 62 + }, 63 + [IMX8MP_ICM_GPU2D] = { 64 + .reg = 0x580, 65 + .mode = IMX_NOC_MODE_FIXED, 66 + .prio_level = 3, 67 + }, 68 + [IMX8MP_ICM_HRV] = { 69 + .reg = 0x600, 70 + .mode = IMX_NOC_MODE_FIXED, 71 + .prio_level = 2, 72 + .ext_control = 1, 73 + }, 74 + [IMX8MP_ICM_LCDIF_HDMI] = { 75 + .reg = 0x680, 76 + .mode = IMX_NOC_MODE_FIXED, 77 + .prio_level = 2, 78 + .ext_control = 1, 79 + }, 80 + [IMX8MP_ICM_HDCP] = { 81 + .reg = 0x700, 82 + .mode = IMX_NOC_MODE_FIXED, 83 + .prio_level = 5, 84 + }, 85 + [IMX8MP_ICM_NOC_PCIE] = { 86 + .reg = 0x780, 87 + .mode = IMX_NOC_MODE_FIXED, 88 + .prio_level = 3, 89 + }, 90 + [IMX8MP_ICM_USB1] = { 91 + .reg = 0x800, 92 + .mode = IMX_NOC_MODE_FIXED, 93 + .prio_level = 3, 94 + }, 95 + [IMX8MP_ICM_USB2] = { 96 + .reg = 0x880, 97 + .mode = IMX_NOC_MODE_FIXED, 98 + .prio_level = 3, 99 + }, 100 + [IMX8MP_ICM_PCIE] = { 101 + .reg = 0x900, 102 + .mode = IMX_NOC_MODE_FIXED, 103 + .prio_level = 3, 104 + }, 105 + [IMX8MP_ICM_LCDIF_RD] = { 106 + .reg = 0x980, 107 + .mode = IMX_NOC_MODE_FIXED, 108 + .prio_level = 2, 109 + .ext_control = 1, 110 + }, 111 + [IMX8MP_ICM_LCDIF_WR] = { 112 + .reg = 0xa00, 113 + .mode = IMX_NOC_MODE_FIXED, 114 + .prio_level = 2, 115 + .ext_control = 1, 116 + }, 117 + [IMX8MP_ICM_ISI0] = { 118 + .reg = 0xa80, 119 + .mode = IMX_NOC_MODE_FIXED, 120 + .prio_level = 2, 121 + .ext_control = 1, 122 + }, 123 + [IMX8MP_ICM_ISI1] = { 124 + .reg = 0xb00, 125 + .mode = IMX_NOC_MODE_FIXED, 126 + .prio_level = 2, 127 + .ext_control = 1, 128 + }, 129 + [IMX8MP_ICM_ISI2] = { 130 + .reg = 0xb80, 131 + .mode = IMX_NOC_MODE_FIXED, 132 + .prio_level = 2, 133 + .ext_control = 1, 134 + }, 135 + [IMX8MP_ICM_ISP0] = { 136 + .reg = 0xc00, 137 + .mode = IMX_NOC_MODE_FIXED, 138 + .prio_level = 7, 139 + }, 140 + [IMX8MP_ICM_ISP1] = { 141 + .reg = 0xc80, 142 + .mode = IMX_NOC_MODE_FIXED, 143 + .prio_level = 7, 144 + }, 145 + [IMX8MP_ICM_DWE] = { 146 + .reg = 0xd00, 147 + .mode = IMX_NOC_MODE_FIXED, 148 + .prio_level = 7, 149 + }, 150 + [IMX8MP_ICM_VPU_G1] = { 151 + .reg = 0xd80, 152 + .mode = IMX_NOC_MODE_FIXED, 153 + .prio_level = 3, 154 + }, 155 + [IMX8MP_ICM_VPU_G2] = { 156 + .reg = 0xe00, 157 + .mode = IMX_NOC_MODE_FIXED, 158 + .prio_level = 3, 159 + }, 160 + [IMX8MP_ICM_VPU_H1] = { 161 + .reg = 0xe80, 162 + .mode = IMX_NOC_MODE_FIXED, 163 + .prio_level = 3, 164 + }, 165 + [IMX8MP_ICN_MEDIA] = { 166 + .mode = IMX_NOC_MODE_UNCONFIGURED, 167 + }, 168 + [IMX8MP_ICN_VIDEO] = { 169 + .mode = IMX_NOC_MODE_UNCONFIGURED, 170 + }, 171 + [IMX8MP_ICN_AUDIO] = { 172 + .mode = IMX_NOC_MODE_UNCONFIGURED, 173 + }, 174 + [IMX8MP_ICN_HDMI] = { 175 + .mode = IMX_NOC_MODE_UNCONFIGURED, 176 + }, 177 + [IMX8MP_ICN_GPU] = { 178 + .mode = IMX_NOC_MODE_UNCONFIGURED, 179 + }, 180 + [IMX8MP_ICN_HSIO] = { 181 + .mode = IMX_NOC_MODE_UNCONFIGURED, 182 + }, 183 + }; 184 + 185 + /* Describe bus masters, slaves and connections between them */ 186 + static struct imx_icc_node_desc nodes[] = { 187 + DEFINE_BUS_INTERCONNECT("NOC", IMX8MP_ICN_NOC, &imx8mp_noc_adj, 188 + IMX8MP_ICS_DRAM, IMX8MP_ICN_MAIN), 189 + 190 + DEFINE_BUS_SLAVE("OCRAM", IMX8MP_ICS_OCRAM, NULL), 191 + DEFINE_BUS_SLAVE("DRAM", IMX8MP_ICS_DRAM, NULL), 192 + DEFINE_BUS_MASTER("A53", IMX8MP_ICM_A53, IMX8MP_ICN_NOC), 193 + DEFINE_BUS_MASTER("SUPERMIX", IMX8MP_ICM_SUPERMIX, IMX8MP_ICN_NOC), 194 + DEFINE_BUS_MASTER("GIC", IMX8MP_ICM_GIC, IMX8MP_ICN_NOC), 195 + DEFINE_BUS_MASTER("MLMIX", IMX8MP_ICM_MLMIX, IMX8MP_ICN_NOC), 196 + 197 + DEFINE_BUS_INTERCONNECT("NOC_AUDIO", IMX8MP_ICN_AUDIO, NULL, IMX8MP_ICN_NOC), 198 + DEFINE_BUS_MASTER("DSP", IMX8MP_ICM_DSP, IMX8MP_ICN_AUDIO), 199 + DEFINE_BUS_MASTER("SDMA2PER", IMX8MP_ICM_SDMA2PER, IMX8MP_ICN_AUDIO), 200 + DEFINE_BUS_MASTER("SDMA2BURST", IMX8MP_ICM_SDMA2BURST, IMX8MP_ICN_AUDIO), 201 + DEFINE_BUS_MASTER("SDMA3PER", IMX8MP_ICM_SDMA3PER, IMX8MP_ICN_AUDIO), 202 + DEFINE_BUS_MASTER("SDMA3BURST", IMX8MP_ICM_SDMA3BURST, IMX8MP_ICN_AUDIO), 203 + DEFINE_BUS_MASTER("EDMA", IMX8MP_ICM_EDMA, IMX8MP_ICN_AUDIO), 204 + 205 + DEFINE_BUS_INTERCONNECT("NOC_GPU", IMX8MP_ICN_GPU, NULL, IMX8MP_ICN_NOC), 206 + DEFINE_BUS_MASTER("GPU 2D", IMX8MP_ICM_GPU2D, IMX8MP_ICN_GPU), 207 + DEFINE_BUS_MASTER("GPU 3D", IMX8MP_ICM_GPU3D, IMX8MP_ICN_GPU), 208 + 209 + DEFINE_BUS_INTERCONNECT("NOC_HDMI", IMX8MP_ICN_HDMI, NULL, IMX8MP_ICN_NOC), 210 + DEFINE_BUS_MASTER("HRV", IMX8MP_ICM_HRV, IMX8MP_ICN_HDMI), 211 + DEFINE_BUS_MASTER("LCDIF_HDMI", IMX8MP_ICM_LCDIF_HDMI, IMX8MP_ICN_HDMI), 212 + DEFINE_BUS_MASTER("HDCP", IMX8MP_ICM_HDCP, IMX8MP_ICN_HDMI), 213 + 214 + DEFINE_BUS_INTERCONNECT("NOC_HSIO", IMX8MP_ICN_HSIO, NULL, IMX8MP_ICN_NOC), 215 + DEFINE_BUS_MASTER("NOC_PCIE", IMX8MP_ICM_NOC_PCIE, IMX8MP_ICN_HSIO), 216 + DEFINE_BUS_MASTER("USB1", IMX8MP_ICM_USB1, IMX8MP_ICN_HSIO), 217 + DEFINE_BUS_MASTER("USB2", IMX8MP_ICM_USB2, IMX8MP_ICN_HSIO), 218 + DEFINE_BUS_MASTER("PCIE", IMX8MP_ICM_PCIE, IMX8MP_ICN_HSIO), 219 + 220 + DEFINE_BUS_INTERCONNECT("NOC_MEDIA", IMX8MP_ICN_MEDIA, NULL, IMX8MP_ICN_NOC), 221 + DEFINE_BUS_MASTER("LCDIF_RD", IMX8MP_ICM_LCDIF_RD, IMX8MP_ICN_MEDIA), 222 + DEFINE_BUS_MASTER("LCDIF_WR", IMX8MP_ICM_LCDIF_WR, IMX8MP_ICN_MEDIA), 223 + DEFINE_BUS_MASTER("ISI0", IMX8MP_ICM_ISI0, IMX8MP_ICN_MEDIA), 224 + DEFINE_BUS_MASTER("ISI1", IMX8MP_ICM_ISI1, IMX8MP_ICN_MEDIA), 225 + DEFINE_BUS_MASTER("ISI2", IMX8MP_ICM_ISI2, IMX8MP_ICN_MEDIA), 226 + DEFINE_BUS_MASTER("ISP0", IMX8MP_ICM_ISP0, IMX8MP_ICN_MEDIA), 227 + DEFINE_BUS_MASTER("ISP1", IMX8MP_ICM_ISP1, IMX8MP_ICN_MEDIA), 228 + DEFINE_BUS_MASTER("DWE", IMX8MP_ICM_DWE, IMX8MP_ICN_MEDIA), 229 + 230 + DEFINE_BUS_INTERCONNECT("NOC_VIDEO", IMX8MP_ICN_VIDEO, NULL, IMX8MP_ICN_NOC), 231 + DEFINE_BUS_MASTER("VPU G1", IMX8MP_ICM_VPU_G1, IMX8MP_ICN_VIDEO), 232 + DEFINE_BUS_MASTER("VPU G2", IMX8MP_ICM_VPU_G2, IMX8MP_ICN_VIDEO), 233 + DEFINE_BUS_MASTER("VPU H1", IMX8MP_ICM_VPU_H1, IMX8MP_ICN_VIDEO), 234 + DEFINE_BUS_INTERCONNECT("PL301_MAIN", IMX8MP_ICN_MAIN, NULL, 235 + IMX8MP_ICN_NOC, IMX8MP_ICS_OCRAM), 236 + }; 237 + 238 + static int imx8mp_icc_probe(struct platform_device *pdev) 239 + { 240 + return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes), noc_setting_nodes); 241 + } 242 + 243 + static int imx8mp_icc_remove(struct platform_device *pdev) 244 + { 245 + return imx_icc_unregister(pdev); 246 + } 247 + 248 + static struct platform_driver imx8mp_icc_driver = { 249 + .probe = imx8mp_icc_probe, 250 + .remove = imx8mp_icc_remove, 251 + .driver = { 252 + .name = "imx8mp-interconnect", 253 + }, 254 + }; 255 + 256 + module_platform_driver(imx8mp_icc_driver); 257 + MODULE_AUTHOR("Peng Fan <peng.fan@nxp.com>"); 258 + MODULE_LICENSE("GPL"); 259 + MODULE_ALIAS("platform:imx8mp-interconnect");
+1 -1
drivers/interconnect/imx/imx8mq.c
··· 82 82 83 83 static int imx8mq_icc_probe(struct platform_device *pdev) 84 84 { 85 - return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes)); 85 + return imx_icc_register(pdev, nodes, ARRAY_SIZE(nodes), NULL); 86 86 } 87 87 88 88 static int imx8mq_icc_remove(struct platform_device *pdev)
+59
include/dt-bindings/interconnect/fsl,imx8mp.h
··· 1 + /* SPDX-License-Identifier: GPL-2.0 OR MIT */ 2 + /* 3 + * Interconnect framework driver for i.MX SoC 4 + * 5 + * Copyright 2022 NXP 6 + * Peng Fan <peng.fan@nxp.com> 7 + */ 8 + 9 + #ifndef __DT_BINDINGS_INTERCONNECT_IMX8MP_H 10 + #define __DT_BINDINGS_INTERCONNECT_IMX8MP_H 11 + 12 + #define IMX8MP_ICN_NOC 0 13 + #define IMX8MP_ICN_MAIN 1 14 + #define IMX8MP_ICS_DRAM 2 15 + #define IMX8MP_ICS_OCRAM 3 16 + #define IMX8MP_ICM_A53 4 17 + #define IMX8MP_ICM_SUPERMIX 5 18 + #define IMX8MP_ICM_GIC 6 19 + #define IMX8MP_ICM_MLMIX 7 20 + 21 + #define IMX8MP_ICN_AUDIO 8 22 + #define IMX8MP_ICM_DSP 9 23 + #define IMX8MP_ICM_SDMA2PER 10 24 + #define IMX8MP_ICM_SDMA2BURST 11 25 + #define IMX8MP_ICM_SDMA3PER 12 26 + #define IMX8MP_ICM_SDMA3BURST 13 27 + #define IMX8MP_ICM_EDMA 14 28 + 29 + #define IMX8MP_ICN_GPU 15 30 + #define IMX8MP_ICM_GPU2D 16 31 + #define IMX8MP_ICM_GPU3D 17 32 + 33 + #define IMX8MP_ICN_HDMI 18 34 + #define IMX8MP_ICM_HRV 19 35 + #define IMX8MP_ICM_LCDIF_HDMI 20 36 + #define IMX8MP_ICM_HDCP 21 37 + 38 + #define IMX8MP_ICN_HSIO 22 39 + #define IMX8MP_ICM_NOC_PCIE 23 40 + #define IMX8MP_ICM_USB1 24 41 + #define IMX8MP_ICM_USB2 25 42 + #define IMX8MP_ICM_PCIE 26 43 + 44 + #define IMX8MP_ICN_MEDIA 27 45 + #define IMX8MP_ICM_LCDIF_RD 28 46 + #define IMX8MP_ICM_LCDIF_WR 29 47 + #define IMX8MP_ICM_ISI0 30 48 + #define IMX8MP_ICM_ISI1 31 49 + #define IMX8MP_ICM_ISI2 32 50 + #define IMX8MP_ICM_ISP0 33 51 + #define IMX8MP_ICM_ISP1 34 52 + #define IMX8MP_ICM_DWE 35 53 + 54 + #define IMX8MP_ICN_VIDEO 36 55 + #define IMX8MP_ICM_VPU_G1 37 56 + #define IMX8MP_ICM_VPU_G2 38 57 + #define IMX8MP_ICM_VPU_H1 39 58 + 59 + #endif /* __DT_BINDINGS_INTERCONNECT_IMX8MP_H */
+7
include/linux/interconnect.h
··· 44 44 const int dst_id); 45 45 struct icc_path *of_icc_get(struct device *dev, const char *name); 46 46 struct icc_path *devm_of_icc_get(struct device *dev, const char *name); 47 + int devm_of_icc_bulk_get(struct device *dev, int num_paths, struct icc_bulk_data *paths); 47 48 struct icc_path *of_icc_get_by_index(struct device *dev, int idx); 48 49 void icc_put(struct icc_path *path); 49 50 int icc_enable(struct icc_path *path); ··· 113 112 } 114 113 115 114 static inline int of_icc_bulk_get(struct device *dev, int num_paths, struct icc_bulk_data *paths) 115 + { 116 + return 0; 117 + } 118 + 119 + static inline int devm_of_icc_bulk_get(struct device *dev, int num_paths, 120 + struct icc_bulk_data *paths) 116 121 { 117 122 return 0; 118 123 }