diff mbox series

[2/4] imx: imx8mp: disable fused IP for UltraLite

Message ID 20220214125525.26954-2-peng.fan@oss.nxp.com
State Superseded
Delegated to: Stefano Babic
Headers show
Series [1/4] imx: imx8mp: detect i.MX8MP UltraLite when get cpu rev | expand

Commit Message

Peng Fan (OSS) Feb. 14, 2022, 12:55 p.m. UTC
From: Peng Fan <peng.fan@nxp.com>

Beside the fused modules on iMX8MP Lite, this part has also fused
GPU3D/2D, LVDS and MIPI DSI.
So we have to disable them for kernel and also disable MIPI DSI
in u-boot DTS for splash screen at runtime.

Signed-off-by: Ye Li <ye.li@nxp.com>
Signed-off-by: Peng Fan <peng.fan@nxp.com>
---
 arch/arm/mach-imx/imx8m/soc.c | 147 ++++++++++++++++++++++++++++++++--
 1 file changed, 142 insertions(+), 5 deletions(-)

Comments

Teresa Remmet Feb. 18, 2022, 9:59 a.m. UTC | #1
Hello Peng,

Am Montag, dem 14.02.2022 um 20:55 +0800 schrieb Peng Fan (OSS):
> From: Peng Fan <peng.fan@nxp.com>
> 
> Beside the fused modules on iMX8MP Lite, this part has also fused
> GPU3D/2D, LVDS and MIPI DSI.
> So we have to disable them for kernel and also disable MIPI DSI
> in u-boot DTS for splash screen at runtime.
> 
> Signed-off-by: Ye Li <ye.li@nxp.com>
> Signed-off-by: Peng Fan <peng.fan@nxp.com>
> ---
>  arch/arm/mach-imx/imx8m/soc.c | 147
> ++++++++++++++++++++++++++++++++--
>  1 file changed, 142 insertions(+), 5 deletions(-)
> 
> diff --git a/arch/arm/mach-imx/imx8m/soc.c b/arch/arm/mach-
> imx/imx8m/soc.c
> index e2d21bf6b8..91ff7eca59 100644
> --- a/arch/arm/mach-imx/imx8m/soc.c
> +++ b/arch/arm/mach-imx/imx8m/soc.c
> @@ -905,6 +905,90 @@ static int low_drive_gpu_freq(void *blob)
>  }
>  #endif
>  
> 

[...]

>  
> +#ifdef CONFIG_OF_BOARD_FIXUP
> +#ifndef CONFIG_SPL_BUILD
> +int board_fix_fdt(void *fdt)

I stumbled over this already in the NXP U-Boot. We 
implemented there on top our own board_fix_fdt() callback on board
level. So this caused a conflict. This will be a issue for upstream
also when a imx8m* board tries to use it. 
Is there not any other way to solve this than implementing board
callbacks on soc level?

Regards,
Teresa   

> +{
> +	if (is_imx8mpul()) {
> +		int i = 0;
> +		int nodeoff, ret;
> +		const char *status = "disabled";
> +		static const char * const dsi_nodes[] = {
> +			"/soc@0/bus@32c00000/mipi_dsi@32e60000",
> +			"/soc@0/bus@32c00000/lcd-controller@32e80000",
> +			"/dsi-host"
> +		};
> +
> +		for (i = 0; i < ARRAY_SIZE(dsi_nodes); i++) {
> +			nodeoff = fdt_path_offset(fdt, dsi_nodes[i]);
> +			if (nodeoff > 0) {
> +set_status:
> +				ret = fdt_setprop(fdt, nodeoff,
> "status", status,
> +						  strlen(status) + 1);
> +				if (ret == -FDT_ERR_NOSPACE) {
> +					ret = fdt_increase_size(fdt,
> 512);
> +					if (!ret)
> +						goto set_status;
> +				}
> +			}
> +		}
> +	}
> +
> +	return 0;
> +}
> +#endif
> +#endif
> +
>  #if !CONFIG_IS_ENABLED(SYSRESET)
>  void reset_cpu(void)
>  {
diff mbox series

Patch

diff --git a/arch/arm/mach-imx/imx8m/soc.c b/arch/arm/mach-imx/imx8m/soc.c
index e2d21bf6b8..91ff7eca59 100644
--- a/arch/arm/mach-imx/imx8m/soc.c
+++ b/arch/arm/mach-imx/imx8m/soc.c
@@ -905,6 +905,90 @@  static int low_drive_gpu_freq(void *blob)
 }
 #endif
 
+static bool check_remote_endpoint(void *blob, const char *ep1, const char *ep2)
+{
+	int lookup_node;
+	int nodeoff;
+
+	nodeoff = fdt_path_offset(blob, ep1);
+	if (nodeoff) {
+		lookup_node = fdtdec_lookup_phandle(blob, nodeoff, "remote-endpoint");
+		nodeoff = fdt_path_offset(blob, ep2);
+
+		if (nodeoff > 0 && nodeoff == lookup_node)
+			return true;
+	}
+
+	return false;
+}
+
+int disable_dsi_lcdif_nodes(void *blob)
+{
+	int ret;
+
+	static const char * const dsi_path_8mp[] = {
+		"/soc@0/bus@32c00000/mipi_dsi@32e60000"
+	};
+
+	static const char * const lcdif_path_8mp[] = {
+		"/soc@0/bus@32c00000/lcd-controller@32e80000"
+	};
+
+	static const char * const lcdif_ep_path_8mp[] = {
+		"/soc@0/bus@32c00000/lcd-controller@32e80000/port@0/endpoint"
+	};
+	static const char * const dsi_ep_path_8mp[] = {
+		"/soc@0/bus@32c00000/mipi_dsi@32e60000/port@0/endpoint"
+	};
+
+	ret = disable_fdt_nodes(blob, dsi_path_8mp, ARRAY_SIZE(dsi_path_8mp));
+	if (ret)
+		return ret;
+
+	if (check_remote_endpoint(blob, dsi_ep_path_8mp[0], lcdif_ep_path_8mp[0])) {
+		/* Disable lcdif node */
+		return disable_fdt_nodes(blob, lcdif_path_8mp, ARRAY_SIZE(lcdif_path_8mp));
+	}
+
+	return 0;
+}
+
+int disable_lvds_lcdif_nodes(void *blob)
+{
+	int ret, i;
+
+	static const char * const ldb_path_8mp[] = {
+		"/soc@0/bus@32c00000/ldb@32ec005c",
+		"/soc@0/bus@32c00000/phy@32ec0128"
+	};
+
+	static const char * const lcdif_path_8mp[] = {
+		"/soc@0/bus@32c00000/lcd-controller@32e90000"
+	};
+
+	static const char * const lcdif_ep_path_8mp[] = {
+		"/soc@0/bus@32c00000/lcd-controller@32e90000/port@0/endpoint@0",
+		"/soc@0/bus@32c00000/lcd-controller@32e90000/port@0/endpoint@1"
+	};
+	static const char * const ldb_ep_path_8mp[] = {
+		"/soc@0/bus@32c00000/ldb@32ec005c/lvds-channel@0/port@0/endpoint",
+		"/soc@0/bus@32c00000/ldb@32ec005c/lvds-channel@1/port@0/endpoint"
+	};
+
+	ret = disable_fdt_nodes(blob, ldb_path_8mp, ARRAY_SIZE(ldb_path_8mp));
+	if (ret)
+		return ret;
+
+	for (i = 0; i < ARRAY_SIZE(ldb_ep_path_8mp); i++) {
+		if (check_remote_endpoint(blob, ldb_ep_path_8mp[i], lcdif_ep_path_8mp[i])) {
+			/* Disable lcdif node */
+			return disable_fdt_nodes(blob, lcdif_path_8mp, ARRAY_SIZE(lcdif_path_8mp));
+		}
+	}
+
+	return 0;
+}
+
 int disable_gpu_nodes(void *blob)
 {
 	static const char * const nodes_path_8mn[] = {
@@ -912,7 +996,15 @@  int disable_gpu_nodes(void *blob)
 		"/soc@/gpu@38000000"
 	};
 
-	return disable_fdt_nodes(blob, nodes_path_8mn, ARRAY_SIZE(nodes_path_8mn));
+	static const char * const nodes_path_8mp[] = {
+		"/gpu3d@38000000",
+		"/gpu2d@38008000"
+	};
+
+	if (is_imx8mp())
+		return disable_fdt_nodes(blob, nodes_path_8mp, ARRAY_SIZE(nodes_path_8mp));
+	else
+		return disable_fdt_nodes(blob, nodes_path_8mn, ARRAY_SIZE(nodes_path_8mn));
 }
 
 int disable_npu_nodes(void *blob)
@@ -1168,16 +1260,27 @@  usb_modify_speed:
 		disable_cpu_nodes(blob, 3);
 
 #elif defined(CONFIG_IMX8MP)
-	if (is_imx8mpl())
+	if (is_imx8mpul()) {
+		/* Disable GPU */
+		disable_gpu_nodes(blob);
+
+		/* Disable DSI */
+		disable_dsi_lcdif_nodes(blob);
+
+		/* Disable LVDS */
+		disable_lvds_lcdif_nodes(blob);
+	}
+
+	if (is_imx8mpul() || is_imx8mpl())
 		disable_vpu_nodes(blob);
 
-	if (is_imx8mpl() || is_imx8mp6())
+	if (is_imx8mpul() || is_imx8mpl() || is_imx8mp6())
 		disable_npu_nodes(blob);
 
-	if (is_imx8mpl())
+	if (is_imx8mpul() || is_imx8mpl())
 		disable_isp_nodes(blob);
 
-	if (is_imx8mpl() || is_imx8mp6())
+	if (is_imx8mpul() || is_imx8mpl() || is_imx8mp6())
 		disable_dsp_nodes(blob);
 
 	if (is_imx8mpd())
@@ -1188,6 +1291,40 @@  usb_modify_speed:
 }
 #endif
 
+#ifdef CONFIG_OF_BOARD_FIXUP
+#ifndef CONFIG_SPL_BUILD
+int board_fix_fdt(void *fdt)
+{
+	if (is_imx8mpul()) {
+		int i = 0;
+		int nodeoff, ret;
+		const char *status = "disabled";
+		static const char * const dsi_nodes[] = {
+			"/soc@0/bus@32c00000/mipi_dsi@32e60000",
+			"/soc@0/bus@32c00000/lcd-controller@32e80000",
+			"/dsi-host"
+		};
+
+		for (i = 0; i < ARRAY_SIZE(dsi_nodes); i++) {
+			nodeoff = fdt_path_offset(fdt, dsi_nodes[i]);
+			if (nodeoff > 0) {
+set_status:
+				ret = fdt_setprop(fdt, nodeoff, "status", status,
+						  strlen(status) + 1);
+				if (ret == -FDT_ERR_NOSPACE) {
+					ret = fdt_increase_size(fdt, 512);
+					if (!ret)
+						goto set_status;
+				}
+			}
+		}
+	}
+
+	return 0;
+}
+#endif
+#endif
+
 #if !CONFIG_IS_ENABLED(SYSRESET)
 void reset_cpu(void)
 {