[PATCH 2/2] OMAP: DSS2: Fix omap_dss_probe() error path

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



From: Jani Nikula <ext-jani.1.nikula@xxxxxxxxx>

Perform graceful cleanup on errors instead of just bailing out.

Signed-off-by: Jani Nikula <ext-jani.1.nikula@xxxxxxxxx>
---
 drivers/video/omap2/dss/core.c |   54 ++++++++++++++++++++++++++++++---------
 1 files changed, 41 insertions(+), 13 deletions(-)

diff --git a/drivers/video/omap2/dss/core.c b/drivers/video/omap2/dss/core.c
index 92ee067..b3a498f 100644
--- a/drivers/video/omap2/dss/core.c
+++ b/drivers/video/omap2/dss/core.c
@@ -507,7 +507,7 @@ static int omap_dss_probe(struct platform_device *pdev)
 
 	r = dss_get_clocks();
 	if (r)
-		goto fail0;
+		goto err_clocks;
 
 	dss_clk_enable_all_no_ctx();
 
@@ -523,57 +523,64 @@ static int omap_dss_probe(struct platform_device *pdev)
 	r = dss_init(skip_init);
 	if (r) {
 		DSSERR("Failed to initialize DSS\n");
-		goto fail0;
+		goto err_dss;
 	}
 
 	r = rfbi_init();
 	if (r) {
 		DSSERR("Failed to initialize rfbi\n");
-		goto fail0;
+		goto err_rfbi;
 	}
 
 	r = dpi_init(pdev);
 	if (r) {
 		DSSERR("Failed to initialize dpi\n");
-		goto fail0;
+		goto err_dpi;
 	}
 
 	r = dispc_init();
 	if (r) {
 		DSSERR("Failed to initialize dispc\n");
-		goto fail0;
+		goto err_dispc;
 	}
 
 	r = venc_init(pdev);
 	if (r) {
 		DSSERR("Failed to initialize venc\n");
-		goto fail0;
+		goto err_venc;
 	}
 
 	if (cpu_is_omap34xx()) {
 		r = sdi_init(skip_init);
 		if (r) {
 			DSSERR("Failed to initialize SDI\n");
-			goto fail0;
+			goto err_sdi;
 		}
 
 		r = dsi_init(pdev);
 		if (r) {
 			DSSERR("Failed to initialize DSI\n");
-			goto fail0;
+			goto err_dsi;
 		}
 	}
 
 	r = dss_initialize_debugfs();
 	if (r)
-		goto fail0;
+		goto err_debugfs;
 
 	for (i = 0; i < pdata->num_devices; ++i) {
 		struct omap_dss_device *dssdev = pdata->devices[i];
 
 		r = omap_dss_register_device(dssdev);
-		if (r)
-			DSSERR("device reg failed %d\n", i);
+		if (r) {
+			DSSERR("device %d %s register failed %d\n", i,
+				dssdev->name ?: "unnamed", r);
+
+			while (--i >= 0)
+				omap_dss_unregister_device(pdata->devices[i]);
+
+			goto err_register;
+		}
 
 		if (def_disp_name && strcmp(def_disp_name, dssdev->name) == 0)
 			pdata->default_device = dssdev;
@@ -583,8 +590,29 @@ static int omap_dss_probe(struct platform_device *pdev)
 
 	return 0;
 
-	/* XXX fail correctly */
-fail0:
+err_register:
+	dss_uninitialize_debugfs();
+err_debugfs:
+	if (cpu_is_omap34xx())
+		dsi_exit();
+err_dsi:
+	if (cpu_is_omap34xx())
+		sdi_exit();
+err_sdi:
+	venc_exit();
+err_venc:
+	dispc_exit();
+err_dispc:
+	dpi_exit();
+err_dpi:
+	rfbi_exit();
+err_rfbi:
+	dss_exit();
+err_dss:
+	dss_clk_disable_all_no_ctx();
+	dss_put_clocks();
+err_clocks:
+
 	return r;
 }
 
-- 
1.6.5.2

--
To unsubscribe from this list: send the line "unsubscribe linux-omap" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Arm (vger)]     [ARM Kernel]     [ARM MSM]     [Linux Tegra]     [Linux WPAN Networking]     [Linux Wireless Networking]     [Maemo Users]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite Trails]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux