/*
 * Copyright (C) 2012-2015 Freescale Semiconductor, Inc. All Rights Reserved.
 */
/*
 * The code contained herein is licensed under the GNU General Public
 * License. You may obtain a copy of the GNU General Public License
 * Version 2 or later at the following locations:
 *
 * http://www.opensource.org/licenses/gpl-license.html
 * http://www.gnu.org/copyleft/gpl.html
 */

#include <linux/clk.h>
#include <linux/err.h>
#include <linux/init.h>
#include <linux/io.h>
#include <linux/mfd/syscon.h>
#include <linux/mfd/syscon/imx6q-iomuxc-gpr.h>
#include <linux/module.h>
#include <linux/of_device.h>
#include <linux/platform_device.h>
#include <linux/regmap.h>
#include <linux/types.h>
#include <video/of_videomode.h>
#include <video/videomode.h>
#include "mxc_dispdrv.h"

#define DRIVER_NAME	"ldb"

#define LDB_BGREF_RMODE_INT		(0x1 << 15)

#define LDB_DI1_VS_POL_ACT_LOW		(0x1 << 10)
#define LDB_DI0_VS_POL_ACT_LOW		(0x1 << 9)

#define LDB_BIT_MAP_CH1_JEIDA		(0x1 << 8)
#define LDB_BIT_MAP_CH0_JEIDA		(0x1 << 6)

#define LDB_DATA_WIDTH_CH1_24		(0x1 << 7)
#define LDB_DATA_WIDTH_CH0_24		(0x1 << 5)

#define LDB_CH1_MODE_MASK		(0x3 << 2)
#define LDB_CH1_MODE_EN_TO_DI1		(0x3 << 2)
#define LDB_CH1_MODE_EN_TO_DI0		(0x1 << 2)
#define LDB_CH0_MODE_MASK		(0x3 << 0)
#define LDB_CH0_MODE_EN_TO_DI1		(0x3 << 0)
#define LDB_CH0_MODE_EN_TO_DI0		(0x1 << 0)

#define LDB_SPLIT_MODE_EN		(0x1 << 4)

#define INVALID_BUS_REG			(~0UL)

struct crtc_mux {
	enum crtc crtc;
	u32 val;
};

struct bus_mux {
	int reg;
	int shift;
	int mask;
	int crtc_mux_num;
	const struct crtc_mux *crtcs;
};

struct ldb_info {
	bool split_cap;
	bool dual_cap;
	bool ext_bgref_cap;
	bool clk_fixup;
	int ctrl_reg;
	int bus_mux_num;
	const struct bus_mux *buses;
};

struct ldb_data;

struct ldb_chan {
	struct ldb_data *ldb;
	struct fb_info *fbi;
	struct videomode vm;
	enum crtc crtc;
	int chno;
	bool is_used;
	bool online;
};

struct ldb_data {
	struct regmap *regmap;
	struct device *dev;
	struct mxc_dispdrv_handle *mddh;
	struct ldb_chan chan[2];
	int bus_mux_num;
	const struct bus_mux *buses;
	int primary_chno;
	int ctrl_reg;
	u32 ctrl;
	bool spl_mode;
	bool dual_mode;
	bool clk_fixup;
	struct clk *di_clk[4];
	struct clk *ldb_di_clk[2];
	struct clk *div_3_5_clk[2];
	struct clk *div_7_clk[2];
	struct clk *div_sel_clk[2];
};

static const struct crtc_mux imx6q_lvds0_crtc_mux[] = {
	{
		.crtc = CRTC_IPU1_DI0,
		.val = IMX6Q_GPR3_LVDS0_MUX_CTL_IPU1_DI0,
	}, {
		.crtc = CRTC_IPU1_DI1,
		.val = IMX6Q_GPR3_LVDS0_MUX_CTL_IPU1_DI1,
	}, {
		.crtc = CRTC_IPU2_DI0,
		.val = IMX6Q_GPR3_LVDS0_MUX_CTL_IPU2_DI0,
	}, {
		.crtc = CRTC_IPU2_DI1,
		.val = IMX6Q_GPR3_LVDS0_MUX_CTL_IPU2_DI1,
	}
};

static const struct crtc_mux imx6q_lvds1_crtc_mux[] = {
	{
		.crtc = CRTC_IPU1_DI0,
		.val = IMX6Q_GPR3_LVDS1_MUX_CTL_IPU1_DI0,
	}, {
		.crtc = CRTC_IPU1_DI1,
		.val = IMX6Q_GPR3_LVDS1_MUX_CTL_IPU1_DI1,
	}, {
		.crtc = CRTC_IPU2_DI0,
		.val = IMX6Q_GPR3_LVDS1_MUX_CTL_IPU2_DI0,
	}, {
		.crtc = CRTC_IPU2_DI1,
		.val = IMX6Q_GPR3_LVDS1_MUX_CTL_IPU2_DI1,
	}
};

static const struct bus_mux imx6q_ldb_buses[] = {
	{
		.reg = IOMUXC_GPR3,
		.shift = 6,
		.mask = IMX6Q_GPR3_LVDS0_MUX_CTL_MASK,
		.crtc_mux_num = ARRAY_SIZE(imx6q_lvds0_crtc_mux),
		.crtcs = imx6q_lvds0_crtc_mux,
	}, {
		.reg = IOMUXC_GPR3,
		.shift = 8,
		.mask = IMX6Q_GPR3_LVDS1_MUX_CTL_MASK,
		.crtc_mux_num = ARRAY_SIZE(imx6q_lvds1_crtc_mux),
		.crtcs = imx6q_lvds1_crtc_mux,
	}
};

static const struct ldb_info imx6q_ldb_info = {
	.split_cap = true,
	.dual_cap = true,
	.ext_bgref_cap = false,
	.clk_fixup = false,
	.ctrl_reg = IOMUXC_GPR2,
	.bus_mux_num = ARRAY_SIZE(imx6q_ldb_buses),
	.buses = imx6q_ldb_buses,
};

static const struct ldb_info imx6qp_ldb_info = {
	.split_cap = true,
	.dual_cap = true,
	.ext_bgref_cap = false,
	.clk_fixup = true,
	.ctrl_reg = IOMUXC_GPR2,
	.bus_mux_num = ARRAY_SIZE(imx6q_ldb_buses),
	.buses = imx6q_ldb_buses,
};

static const struct crtc_mux imx6dl_lvds0_crtc_mux[] = {
	{
		.crtc = CRTC_IPU1_DI0,
		.val = IMX6DL_GPR3_LVDS0_MUX_CTL_IPU1_DI0,
	}, {
		.crtc = CRTC_IPU1_DI1,
		.val = IMX6DL_GPR3_LVDS0_MUX_CTL_IPU1_DI1,
	}, {
		.crtc = CRTC_LCDIF1,
		.val = IMX6DL_GPR3_LVDS0_MUX_CTL_LCDIF,
	}
};

static const struct crtc_mux imx6dl_lvds1_crtc_mux[] = {
	{
		.crtc = CRTC_IPU1_DI0,
		.val = IMX6DL_GPR3_LVDS1_MUX_CTL_IPU1_DI0,
	}, {
		.crtc = CRTC_IPU1_DI1,
		.val = IMX6DL_GPR3_LVDS1_MUX_CTL_IPU1_DI1,
	}, {
		.crtc = CRTC_LCDIF1,
		.val = IMX6DL_GPR3_LVDS1_MUX_CTL_LCDIF,
	}
};

static const struct bus_mux imx6dl_ldb_buses[] = {
	{
		.reg = IOMUXC_GPR3,
		.shift = 6,
		.mask = IMX6DL_GPR3_LVDS0_MUX_CTL_MASK,
		.crtc_mux_num = ARRAY_SIZE(imx6dl_lvds0_crtc_mux),
		.crtcs = imx6dl_lvds0_crtc_mux,
	}, {
		.reg = IOMUXC_GPR3,
		.shift = 8,
		.mask = IMX6DL_GPR3_LVDS1_MUX_CTL_MASK,
		.crtc_mux_num = ARRAY_SIZE(imx6dl_lvds1_crtc_mux),
		.crtcs = imx6dl_lvds1_crtc_mux,
	}
};

static const struct ldb_info imx6dl_ldb_info = {
	.split_cap = true,
	.dual_cap = true,
	.ext_bgref_cap = false,
	.clk_fixup = false,
	.ctrl_reg = IOMUXC_GPR2,
	.bus_mux_num = ARRAY_SIZE(imx6dl_ldb_buses),
	.buses = imx6dl_ldb_buses,
};

static const struct crtc_mux imx6sx_lvds_crtc_mux[] = {
	{
		.crtc = CRTC_LCDIF1,
		.val = IMX6SX_GPR5_DISP_MUX_LDB_CTRL_LCDIF1,
	}, {
		.crtc = CRTC_LCDIF2,
		.val = IMX6SX_GPR5_DISP_MUX_LDB_CTRL_LCDIF2,
	}
};

static const struct bus_mux imx6sx_ldb_buses[] = {
	{
		.reg = IOMUXC_GPR5,
		.shift = 3,
		.mask = IMX6SX_GPR5_DISP_MUX_LDB_CTRL_MASK,
		.crtc_mux_num = ARRAY_SIZE(imx6sx_lvds_crtc_mux),
		.crtcs = imx6sx_lvds_crtc_mux,
	}
};

static const struct ldb_info imx6sx_ldb_info = {
	.split_cap = false,
	.dual_cap = false,
	.ext_bgref_cap = false,
	.clk_fixup = false,
	.ctrl_reg = IOMUXC_GPR6,
	.bus_mux_num = ARRAY_SIZE(imx6sx_ldb_buses),
	.buses = imx6sx_ldb_buses,
};

static const struct crtc_mux imx53_lvds0_crtc_mux[] = {
	{ .crtc = CRTC_IPU1_DI0, },
};

static const struct crtc_mux imx53_lvds1_crtc_mux[] = {
	{ .crtc = CRTC_IPU1_DI1, }
};

static const struct bus_mux imx53_ldb_buses[] = {
	{
		.reg = INVALID_BUS_REG,
		.crtc_mux_num = ARRAY_SIZE(imx53_lvds0_crtc_mux),
		.crtcs = imx53_lvds0_crtc_mux,
	}, {
		.reg = INVALID_BUS_REG,
		.crtc_mux_num = ARRAY_SIZE(imx53_lvds1_crtc_mux),
		.crtcs = imx53_lvds1_crtc_mux,
	}
};

static const struct ldb_info imx53_ldb_info = {
	.split_cap = true,
	.dual_cap = false,
	.ext_bgref_cap = true,
	.clk_fixup = false,
	.ctrl_reg = IOMUXC_GPR2,
	.bus_mux_num = ARRAY_SIZE(imx53_ldb_buses),
	.buses = imx53_ldb_buses,
};

static const struct of_device_id ldb_dt_ids[] = {
	{ .compatible = "fsl,imx6qp-ldb", .data = &imx6qp_ldb_info, },
	{ .compatible = "fsl,imx6q-ldb", .data = &imx6q_ldb_info, },
	{ .compatible = "fsl,imx6dl-ldb", .data = &imx6dl_ldb_info, },
	{ .compatible = "fsl,imx6sx-ldb", .data = &imx6sx_ldb_info, },
	{ .compatible = "fsl,imx53-ldb", .data = &imx53_ldb_info, },
	{ /* sentinel */ }
};
MODULE_DEVICE_TABLE(of, ldb_dt_ids);

static int ldb_init(struct mxc_dispdrv_handle *mddh,
		    struct mxc_dispdrv_setting *setting)
{
	struct ldb_data *ldb = mxc_dispdrv_getdata(mddh);
	struct device *dev = ldb->dev;
	struct fb_info *fbi = setting->fbi;
	struct ldb_chan *chan;
	struct fb_videomode fb_vm;
	int chno;

	chno = ldb->chan[ldb->primary_chno].is_used ?
		!ldb->primary_chno : ldb->primary_chno;

	chan = &ldb->chan[chno];

	if (chan->is_used) {
		dev_err(dev, "LVDS channel%d is already used\n", chno);
		return -EBUSY;
	}
	if (!chan->online) {
		dev_err(dev, "LVDS channel%d is not online\n", chno);
		return -ENODEV;
	}

	chan->is_used = true;

	chan->fbi = fbi;

	fb_videomode_from_videomode(&chan->vm, &fb_vm);
	fb_videomode_to_var(&fbi->var, &fb_vm);

	setting->crtc = chan->crtc;

	return 0;
}

static int get_di_clk_id(struct ldb_chan chan, int *id)
{
	struct ldb_data *ldb = chan.ldb;
	int i = 0, chno = chan.chno, mask, shift;
	enum crtc crtc;
	u32 val;

	/* no pre-muxing, such as mx53 */
	if (ldb->buses[chno].reg == INVALID_BUS_REG) {
		*id = chno;
		return 0;
	}

	for (; i < ldb->buses[chno].crtc_mux_num; i++) {
		crtc = ldb->buses[chno].crtcs[i].crtc;
		val  = ldb->buses[chno].crtcs[i].val;
		mask = ldb->buses[chno].mask;
		shift = ldb->buses[chno].shift;
		if (chan.crtc == crtc) {
			*id = (val & mask) >> shift;
			return 0;
		}
	}

	return -EINVAL;
}

static int get_mux_val(struct bus_mux bus_mux, enum crtc crtc,
		       u32 *mux_val)
{
	int i = 0;

	for (; i < bus_mux.crtc_mux_num; i++)
		if (bus_mux.crtcs[i].crtc == crtc) {
			*mux_val = bus_mux.crtcs[i].val;
			return 0;
		}

	return -EINVAL;
}

static int find_ldb_chno(struct ldb_data *ldb,
			 struct fb_info *fbi, int *chno)
{
	struct device *dev = ldb->dev;
	int i = 0;

	for (; i < 2; i++)
		if (ldb->chan[i].fbi == fbi) {
			*chno = ldb->chan[i].chno;
			return 0;
		}
	dev_err(dev, "failed to find channel number\n");
	return -EINVAL;
}

static void ldb_disable(struct mxc_dispdrv_handle *mddh,
			struct fb_info *fbi);

static int ldb_setup(struct mxc_dispdrv_handle *mddh,
		     struct fb_info *fbi)
{
	struct ldb_data *ldb = mxc_dispdrv_getdata(mddh);
	struct ldb_chan chan;
	struct device *dev = ldb->dev;
	struct clk *ldb_di_parent, *ldb_di_sel, *ldb_di_sel_parent;
	struct clk *other_ldb_di_sel = NULL;
	struct bus_mux bus_mux;
	int ret = 0, id = 0, chno, other_chno;
	unsigned long serial_clk;
	u32 mux_val;

	ret = find_ldb_chno(ldb, fbi, &chno);
	if (ret < 0)
		return ret;

	other_chno = chno ? 0 : 1;

	chan = ldb->chan[chno];

	bus_mux = ldb->buses[chno];

	ret = get_di_clk_id(chan, &id);
	if (ret < 0) {
		dev_err(dev, "failed to get ch%d di clk id\n",
			chan.chno);
		return ret;
	}

	ret = get_mux_val(bus_mux, chan.crtc, &mux_val);
	if (ret < 0) {
		dev_err(dev, "failed to get ch%d mux val\n",
			chan.chno);
		return ret;
	}


	if (ldb->clk_fixup) {
		/*
		 * ldb_di_sel_parent(plls) -> ldb_di_sel -> ldb_di[chno] ->
		 *
		 *     -> div_3_5[chno] ->
		 * -> |                   |-> div_sel[chno] -> di[id]
		 *     ->  div_7[chno] ->
		 */
		clk_set_parent(ldb->di_clk[id], ldb->div_sel_clk[chno]);
	} else {
		/*
		 * ldb_di_sel_parent(plls) -> ldb_di_sel ->
		 *
		 *     -> div_3_5[chno] ->
		 * -> |                   |-> div_sel[chno] ->
		 *     ->  div_7[chno] ->
		 *
		 * -> ldb_di[chno] -> di[id]
		 */
		clk_set_parent(ldb->di_clk[id], ldb->ldb_di_clk[chno]);
	}
	ldb_di_parent = ldb->spl_mode ? ldb->div_3_5_clk[chno] :
			ldb->div_7_clk[chno];
	clk_set_parent(ldb->div_sel_clk[chno], ldb_di_parent);
	ldb_di_sel = clk_get_parent(ldb_di_parent);
	ldb_di_sel_parent = clk_get_parent(ldb_di_sel);
	serial_clk = ldb->spl_mode ? chan.vm.pixelclock * 7 / 2 :
			chan.vm.pixelclock * 7;
	clk_set_rate(ldb_di_sel_parent, serial_clk);

	/*
	 * split mode or dual mode:
	 * clock tree for the other channel
	 */
	if (ldb->spl_mode) {
		clk_set_parent(ldb->div_sel_clk[other_chno],
			       ldb->div_3_5_clk[other_chno]);
		other_ldb_di_sel =
			clk_get_parent(ldb->div_3_5_clk[other_chno]);;
	}

	if (ldb->dual_mode) {
		clk_set_parent(ldb->div_sel_clk[other_chno],
			       ldb->div_7_clk[other_chno]);
		other_ldb_di_sel =
			clk_get_parent(ldb->div_7_clk[other_chno]);;
	}

	if (ldb->spl_mode || ldb->dual_mode)
		clk_set_parent(other_ldb_di_sel, ldb_di_sel_parent);

	if (!(chan.fbi->var.sync & FB_SYNC_VERT_HIGH_ACT)) {
		if (ldb->spl_mode && bus_mux.reg == INVALID_BUS_REG)
			/* no pre-muxing, such as mx53 */
			ldb->ctrl |= (id == 0 ? LDB_DI0_VS_POL_ACT_LOW :
					LDB_DI1_VS_POL_ACT_LOW);
		else
			ldb->ctrl |= (chno == 0 ? LDB_DI0_VS_POL_ACT_LOW :
					LDB_DI1_VS_POL_ACT_LOW);
	}

	if (bus_mux.reg != INVALID_BUS_REG)
		regmap_update_bits(ldb->regmap, bus_mux.reg,
				   bus_mux.mask, mux_val);

	regmap_write(ldb->regmap, ldb->ctrl_reg, ldb->ctrl);

	/* disable channel for correct sequence */
	ldb_disable(mddh, fbi);

	return ret;
}

static int ldb_enable(struct mxc_dispdrv_handle *mddh,
		      struct fb_info *fbi)
{
	struct ldb_data *ldb = mxc_dispdrv_getdata(mddh);
	struct ldb_chan chan;
	struct device *dev = ldb->dev;
	struct bus_mux bus_mux;
	int ret = 0, id = 0, chno, other_chno;

	ret = find_ldb_chno(ldb, fbi, &chno);
	if (ret < 0)
		return ret;

	chan = ldb->chan[chno];

	bus_mux = ldb->buses[chno];

	if (ldb->spl_mode || ldb->dual_mode) {
		other_chno = chno ? 0 : 1;
		clk_prepare_enable(ldb->ldb_di_clk[other_chno]);
	}

	if ((ldb->spl_mode || ldb->dual_mode) &&
	    bus_mux.reg == INVALID_BUS_REG) {
		/* no pre-muxing, such as mx53 */
		ret = get_di_clk_id(chan, &id);
		if (ret < 0) {
			dev_err(dev, "failed to get ch%d di clk id\n",
				chan.chno);
			return ret;
		}

		ldb->ctrl |= id ?
			(LDB_CH0_MODE_EN_TO_DI1 | LDB_CH1_MODE_EN_TO_DI1) :
			(LDB_CH0_MODE_EN_TO_DI0 | LDB_CH1_MODE_EN_TO_DI0);
	} else {
		if (ldb->spl_mode || ldb->dual_mode)
			ldb->ctrl |= LDB_CH0_MODE_EN_TO_DI0 |
				     LDB_CH1_MODE_EN_TO_DI0;
		else
			ldb->ctrl |= chno ? LDB_CH1_MODE_EN_TO_DI1 :
					    LDB_CH0_MODE_EN_TO_DI0;
	}

	regmap_write(ldb->regmap, ldb->ctrl_reg, ldb->ctrl);
	return 0;
}

static void ldb_disable(struct mxc_dispdrv_handle *mddh,
		       struct fb_info *fbi)
{
	struct ldb_data *ldb = mxc_dispdrv_getdata(mddh);
	int ret, chno, other_chno;

	ret = find_ldb_chno(ldb, fbi, &chno);
	if (ret < 0)
		return;

	if (ldb->spl_mode || ldb->dual_mode) {
		ldb->ctrl &= ~(LDB_CH1_MODE_MASK | LDB_CH0_MODE_MASK);
		other_chno = chno ? 0 : 1;
		clk_disable_unprepare(ldb->ldb_di_clk[other_chno]);
	} else {
		ldb->ctrl &= ~(chno ? LDB_CH1_MODE_MASK :
				      LDB_CH0_MODE_MASK);
	}

	regmap_write(ldb->regmap, ldb->ctrl_reg, ldb->ctrl);
	return;
}

static struct mxc_dispdrv_driver ldb_drv = {
	.name		= DRIVER_NAME,
	.init		= ldb_init,
	.setup		= ldb_setup,
	.enable		= ldb_enable,
	.disable	= ldb_disable
};

enum {
	LVDS_BIT_MAP_SPWG,
	LVDS_BIT_MAP_JEIDA,
};

static const char *ldb_bit_mappings[] = {
	[LVDS_BIT_MAP_SPWG] = "spwg",
	[LVDS_BIT_MAP_JEIDA] = "jeida",
};

static int of_get_data_mapping(struct device_node *np)
{
	const char *bm;
	int ret, i;

	ret = of_property_read_string(np, "fsl,data-mapping", &bm);
	if (ret < 0)
		return ret;

	for (i = 0; i < ARRAY_SIZE(ldb_bit_mappings); i++)
		if (!strcasecmp(bm, ldb_bit_mappings[i]))
			return i;

	return -EINVAL;
}

static const char *ldb_crtc_mappings[] = {
	[CRTC_IPU_DI0] = "ipu-di0",
	[CRTC_IPU_DI1] = "ipu-di1",
	[CRTC_IPU1_DI0] = "ipu1-di0",
	[CRTC_IPU1_DI1] = "ipu1-di1",
	[CRTC_IPU2_DI0] = "ipu2-di0",
	[CRTC_IPU2_DI1] = "ipu2-di1",
	[CRTC_LCDIF] = "lcdif",
	[CRTC_LCDIF1] = "lcdif1",
	[CRTC_LCDIF2] = "lcdif2",
};

static enum crtc of_get_crtc_mapping(struct device_node *np)
{
	const char *cm;
	enum crtc i;
	int ret;

	ret = of_property_read_string(np, "crtc", &cm);
	if (ret < 0)
		return ret;

	for (i = 0; i < ARRAY_SIZE(ldb_crtc_mappings); i++)
		if (!strcasecmp(cm, ldb_crtc_mappings[i])) {
			switch (i) {
			case CRTC_IPU_DI0:
				i = CRTC_IPU1_DI0;
				break;
			case CRTC_IPU_DI1:
				i = CRTC_IPU1_DI1;
				break;
			case CRTC_LCDIF:
				i = CRTC_LCDIF1;
				break;
			default:
				break;
			}
			return i;
		}

	return -EINVAL;
}

static int mux_count(struct ldb_data *ldb)
{
	int i, j, count = 0;
	bool should_count[CRTC_MAX];
	enum crtc crtc;

	for (i = 0; i < CRTC_MAX; i++)
		should_count[i] = true;

	for (i = 0; i < ldb->bus_mux_num; i++) {
		for (j = 0; j < ldb->buses[i].crtc_mux_num; j++) {
			crtc = ldb->buses[i].crtcs[j].crtc;
			if (should_count[crtc]) {
				count++;
				should_count[crtc] = false;
			}
		}
	}

	return count;
}

static bool is_valid_crtc(struct ldb_data *ldb, enum crtc crtc,
			  int chno)
{
	int i = 0;

	if (chno > ldb->bus_mux_num - 1)
		return false;

	for (; i < ldb->buses[chno].crtc_mux_num; i++)
		if (ldb->buses[chno].crtcs[i].crtc == crtc)
			return true;

	return false;
}

static int ldb_probe(struct platform_device *pdev)
{
	struct device *dev = &pdev->dev;
	const struct of_device_id *of_id =
			of_match_device(ldb_dt_ids, dev);
	const struct ldb_info *ldb_info =
			(const struct ldb_info *)of_id->data;
	struct device_node *np = dev->of_node, *child;
	struct ldb_data *ldb;
	bool ext_ref;
	int i, data_width, mapping, child_count = 0;
	char clkname[16];

	ldb = devm_kzalloc(dev, sizeof(*ldb), GFP_KERNEL);
	if (!ldb)
		return -ENOMEM;

	ldb->regmap = syscon_regmap_lookup_by_phandle(np, "gpr");
	if (IS_ERR(ldb->regmap)) {
		dev_err(dev, "failed to get parent regmap\n");
		return PTR_ERR(ldb->regmap);
	}

	ldb->dev = dev;
	ldb->bus_mux_num = ldb_info->bus_mux_num;
	ldb->buses = ldb_info->buses;
	ldb->ctrl_reg = ldb_info->ctrl_reg;
	ldb->clk_fixup = ldb_info->clk_fixup;
	ldb->primary_chno = -1;

	ext_ref = of_property_read_bool(np, "ext-ref");
	if (!ext_ref && ldb_info->ext_bgref_cap)
		ldb->ctrl |= LDB_BGREF_RMODE_INT;

	ldb->spl_mode = of_property_read_bool(np, "split-mode");
	if (ldb->spl_mode) {
		if (ldb_info->split_cap) {
			ldb->ctrl |= LDB_SPLIT_MODE_EN;
			dev_info(dev, "split mode\n");
		} else {
			dev_err(dev, "cannot support split mode\n");
			return -EINVAL;
		}
	}

	ldb->dual_mode = of_property_read_bool(np, "dual-mode");
	if (ldb->dual_mode) {
		if (ldb_info->dual_cap) {
			dev_info(dev, "dual mode\n");
		} else {
			dev_err(dev, "cannot support dual mode\n");
			return -EINVAL;
		}
	}

	if (ldb->dual_mode && ldb->spl_mode) {
		dev_err(dev, "cannot support dual mode and split mode "
				"simultaneously\n");
		return -EINVAL;
	}

	for (i = 0; i < mux_count(ldb); i++) {
		sprintf(clkname, "di%d_sel", i);
		ldb->di_clk[i] = devm_clk_get(dev, clkname);
		if (IS_ERR(ldb->di_clk[i])) {
			dev_err(dev, "failed to get clk %s\n", clkname);
			return PTR_ERR(ldb->di_clk[i]);
		}
	}

	for_each_child_of_node(np, child) {
		struct ldb_chan *chan;
		enum crtc crtc;
		bool is_primary;
		int ret;

		ret = of_property_read_u32(child, "reg", &i);
		if (ret || i < 0 || i > 1 || i >= ldb->bus_mux_num) {
			dev_err(dev, "wrong LVDS channel number\n");
			return -EINVAL;
		}

		if ((ldb->spl_mode || ldb->dual_mode) && i > 0) {
			dev_warn(dev, "split mode or dual mode, ignoring "
				"second output\n");
			continue;
		}

		if (!of_device_is_available(child))
			continue;

		if (++child_count > ldb->bus_mux_num) {
			dev_err(dev, "too many LVDS channels\n");
			return -EINVAL;
		}

		chan = &ldb->chan[i];
		chan->chno = i;
		chan->ldb = ldb;
		chan->online = true;

		is_primary = of_property_read_bool(child, "primary");

		if (ldb->bus_mux_num == 1 || (ldb->primary_chno == -1 &&
		    (is_primary || ldb->spl_mode || ldb->dual_mode)))
			ldb->primary_chno = chan->chno;

		ret = of_property_read_u32(child, "fsl,data-width",
					   &data_width);
		if (ret || (data_width != 18 && data_width != 24)) {
			dev_err(dev, "data width not specified or invalid\n");
			return -EINVAL;
		}

		mapping = of_get_data_mapping(child);
		switch (mapping) {
		case LVDS_BIT_MAP_SPWG:
			if (data_width == 24) {
				if (i == 0 || ldb->spl_mode || ldb->dual_mode)
					ldb->ctrl |= LDB_DATA_WIDTH_CH0_24;
				if (i == 1 || ldb->spl_mode || ldb->dual_mode)
					ldb->ctrl |= LDB_DATA_WIDTH_CH1_24;
			}
			break;
		case LVDS_BIT_MAP_JEIDA:
			if (data_width == 18) {
				dev_err(dev, "JEIDA only support 24bit\n");
				return -EINVAL;
			}
			if (i == 0 || ldb->spl_mode || ldb->dual_mode)
				ldb->ctrl |= LDB_DATA_WIDTH_CH0_24 |
					     LDB_BIT_MAP_CH0_JEIDA;
			if (i == 1 || ldb->spl_mode || ldb->dual_mode)
				ldb->ctrl |= LDB_DATA_WIDTH_CH1_24 |
					     LDB_BIT_MAP_CH1_JEIDA;
			break;
		default:
			dev_err(dev, "data mapping not specified or invalid\n");
			return -EINVAL;
		}

		crtc = of_get_crtc_mapping(child);
		if (is_valid_crtc(ldb, crtc, chan->chno)) {
			ldb->chan[i].crtc = crtc;
		} else {
			dev_err(dev, "crtc not specified or invalid\n");
			return -EINVAL;
		}

		ret = of_get_videomode(child, &chan->vm, 0);
		if (ret)
			return -EINVAL;

		sprintf(clkname, "ldb_di%d", i);
		ldb->ldb_di_clk[i] = devm_clk_get(dev, clkname);
		if (IS_ERR(ldb->ldb_di_clk[i])) {
			dev_err(dev, "failed to get clk %s\n", clkname);
			return PTR_ERR(ldb->ldb_di_clk[i]);
		}

		sprintf(clkname, "ldb_di%d_div_3_5", i);
		ldb->div_3_5_clk[i] = devm_clk_get(dev, clkname);
		if (IS_ERR(ldb->div_3_5_clk[i])) {
			dev_err(dev, "failed to get clk %s\n", clkname);
			return PTR_ERR(ldb->div_3_5_clk[i]);
		}

		sprintf(clkname, "ldb_di%d_div_7", i);
		ldb->div_7_clk[i] = devm_clk_get(dev, clkname);
		if (IS_ERR(ldb->div_7_clk[i])) {
			dev_err(dev, "failed to get clk %s\n", clkname);
			return PTR_ERR(ldb->div_7_clk[i]);
		}

		sprintf(clkname, "ldb_di%d_div_sel", i);
		ldb->div_sel_clk[i] = devm_clk_get(dev, clkname);
		if (IS_ERR(ldb->div_sel_clk[i])) {
			dev_err(dev, "failed to get clk %s\n", clkname);
			return PTR_ERR(ldb->div_sel_clk[i]);
		}
	}

	if (child_count == 0) {
		dev_err(dev, "failed to find valid LVDS channel\n");
		return -EINVAL;
	}

	if (ldb->primary_chno == -1) {
		dev_err(dev, "failed to know primary channel\n");
		return -EINVAL;
	}

	ldb->mddh = mxc_dispdrv_register(&ldb_drv);
	mxc_dispdrv_setdata(ldb->mddh, ldb);
	dev_set_drvdata(&pdev->dev, ldb);

	return 0;
}

static int ldb_remove(struct platform_device *pdev)
{
	struct ldb_data *ldb = dev_get_drvdata(&pdev->dev);

	mxc_dispdrv_puthandle(ldb->mddh);
	mxc_dispdrv_unregister(ldb->mddh);
	return 0;
}

static struct platform_driver ldb_driver = {
	.driver = {
		.name = DRIVER_NAME,
		.of_match_table	= ldb_dt_ids,
	},
	.probe = ldb_probe,
	.remove = ldb_remove,
};

module_platform_driver(ldb_driver);

MODULE_AUTHOR("Freescale Semiconductor, Inc.");
MODULE_DESCRIPTION("LDB driver");
MODULE_LICENSE("GPL");
MODULE_ALIAS("platform:" DRIVER_NAME);
