#include <linux/of_gpio.h>
 #include <linux/of_irq.h>
 #include <linux/pinctrl/consumer.h>
+#include <linux/of_graph.h>
 #include <linux/regulator/consumer.h>
 #include <linux/spinlock.h>
 #include <video/mipi_display.h>
        msm_host->format = dsi->format;
        msm_host->mode_flags = dsi->mode_flags;
 
-       msm_host->panel_node = dsi->dev.of_node;
+       WARN_ON(dsi->dev.of_node != msm_host->panel_node);
 
        /* Some gpios defined in panel DT need to be controlled by host */
        ret = dsi_host_init_panel_gpios(msm_host, &dsi->dev);
        .transfer = dsi_host_transfer,
 };
 
+static int dsi_host_parse_dt(struct msm_dsi_host *msm_host)
+{
+       struct device *dev = &msm_host->pdev->dev;
+       struct device_node *np = dev->of_node;
+       struct device_node *endpoint, *panel_node;
+       int ret;
+
+       ret = of_property_read_u32(np, "qcom,dsi-host-index", &msm_host->id);
+       if (ret) {
+               dev_err(dev, "%s: host index not specified, ret=%d\n",
+                       __func__, ret);
+               return ret;
+       }
+
+       /*
+        * Get the first endpoint node. In our case, dsi has one output port
+        * to which the panel is connected. Don't return an error if a port
+        * isn't defined. It's possible that there is nothing connected to
+        * the dsi output.
+        */
+       endpoint = of_graph_get_next_endpoint(np, NULL);
+       if (!endpoint) {
+               dev_dbg(dev, "%s: no endpoint\n", __func__);
+               return 0;
+       }
+
+       /* Get panel node from the output port's endpoint data */
+       panel_node = of_graph_get_remote_port_parent(endpoint);
+       if (!panel_node) {
+               dev_err(dev, "%s: no valid device\n", __func__);
+               of_node_put(endpoint);
+               return -ENODEV;
+       }
+
+       of_node_put(endpoint);
+       of_node_put(panel_node);
+
+       msm_host->panel_node = panel_node;
+
+       return 0;
+}
+
 int msm_dsi_host_init(struct msm_dsi *msm_dsi)
 {
        struct msm_dsi_host *msm_host = NULL;
                goto fail;
        }
 
-       ret = of_property_read_u32(pdev->dev.of_node,
-                               "qcom,dsi-host-index", &msm_host->id);
+       msm_host->pdev = pdev;
+
+       ret = dsi_host_parse_dt(msm_host);
        if (ret) {
-               dev_err(&pdev->dev,
-                       "%s: host index not specified, ret=%d\n",
-                       __func__, ret);
+               pr_err("%s: failed to parse dt\n", __func__);
                goto fail;
        }
-       msm_host->pdev = pdev;
 
        ret = dsi_clk_init(msm_host);
        if (ret) {
 int msm_dsi_host_register(struct mipi_dsi_host *host, bool check_defer)
 {
        struct msm_dsi_host *msm_host = to_msm_dsi_host(host);
-       struct device_node *node;
        int ret;
 
        /* Register mipi dsi host */
                 * It makes sure panel is connected when fbcon detects
                 * connector status and gets the proper display mode to
                 * create framebuffer.
+                * Don't try to defer if there is nothing connected to the dsi
+                * output
                 */
-               if (check_defer) {
-                       node = of_get_child_by_name(msm_host->pdev->dev.of_node,
-                                                       "panel");
-                       if (node) {
-                               if (!of_drm_find_panel(node)) {
-                                       of_node_put(node);
-                                       return -EPROBE_DEFER;
-                               }
-
-                               of_node_put(node);
-                       }
+               if (check_defer && msm_host->panel_node) {
+                       if (!of_drm_find_panel(msm_host->panel_node))
+                               return -EPROBE_DEFER;
                }
        }