]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
OMAPDSS: DSI: split DSI memory map to smaller blocks
authorTomi Valkeinen <tomi.valkeinen@ti.com>
Tue, 17 Dec 2013 11:53:28 +0000 (13:53 +0200)
committerTomi Valkeinen <tomi.valkeinen@ti.com>
Mon, 13 Jan 2014 10:19:54 +0000 (12:19 +0200)
DSI contains three separate blocks: protocol engine, PHY and PLL. At the
moment, all these are memory mapped in one big chunk. We need to split
that memory map into smaller pieces so that we can add proper 'reg'
properties into the DT data for each block.

This patch changes the driver to map the blocks separately. It first
tries to get the memory resource using name, used when booting with DT,
and if that fails, it gets the memory resource by ID, in which case the
driver gets the big chunk from platform data. That big chunk is then
split into the smaller blocks manually.

After DSS DT code has been merged and the old platform code removed, we
can clean up the memory resource management.

Instead of changing the driver in all the places where a register is
read or written, this patch takes a shortcut: it adds an additional
number to the struct which represents the register index. This number is
used to decide which base address to use. In the future we should
consider other approaches.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@ti.com>
drivers/video/omap2/dss/dsi.c

index 1cd3e47fd43f9e0dd5d7053fc82a750eaf409918..f6f8d93c4be941c8c192dfe8ca4aa7ecf3180dda 100644 (file)
 
 #define DSI_CATCH_MISSING_TE
 
-struct dsi_reg { u16 idx; };
+struct dsi_reg { u16 module; u16 idx; };
 
-#define DSI_REG(idx)           ((const struct dsi_reg) { idx })
+#define DSI_REG(mod, idx)              ((const struct dsi_reg) { mod, idx })
 
-#define DSI_SZ_REGS            SZ_1K
 /* DSI Protocol Engine */
 
-#define DSI_REVISION                   DSI_REG(0x0000)
-#define DSI_SYSCONFIG                  DSI_REG(0x0010)
-#define DSI_SYSSTATUS                  DSI_REG(0x0014)
-#define DSI_IRQSTATUS                  DSI_REG(0x0018)
-#define DSI_IRQENABLE                  DSI_REG(0x001C)
-#define DSI_CTRL                       DSI_REG(0x0040)
-#define DSI_GNQ                                DSI_REG(0x0044)
-#define DSI_COMPLEXIO_CFG1             DSI_REG(0x0048)
-#define DSI_COMPLEXIO_IRQ_STATUS       DSI_REG(0x004C)
-#define DSI_COMPLEXIO_IRQ_ENABLE       DSI_REG(0x0050)
-#define DSI_CLK_CTRL                   DSI_REG(0x0054)
-#define DSI_TIMING1                    DSI_REG(0x0058)
-#define DSI_TIMING2                    DSI_REG(0x005C)
-#define DSI_VM_TIMING1                 DSI_REG(0x0060)
-#define DSI_VM_TIMING2                 DSI_REG(0x0064)
-#define DSI_VM_TIMING3                 DSI_REG(0x0068)
-#define DSI_CLK_TIMING                 DSI_REG(0x006C)
-#define DSI_TX_FIFO_VC_SIZE            DSI_REG(0x0070)
-#define DSI_RX_FIFO_VC_SIZE            DSI_REG(0x0074)
-#define DSI_COMPLEXIO_CFG2             DSI_REG(0x0078)
-#define DSI_RX_FIFO_VC_FULLNESS                DSI_REG(0x007C)
-#define DSI_VM_TIMING4                 DSI_REG(0x0080)
-#define DSI_TX_FIFO_VC_EMPTINESS       DSI_REG(0x0084)
-#define DSI_VM_TIMING5                 DSI_REG(0x0088)
-#define DSI_VM_TIMING6                 DSI_REG(0x008C)
-#define DSI_VM_TIMING7                 DSI_REG(0x0090)
-#define DSI_STOPCLK_TIMING             DSI_REG(0x0094)
-#define DSI_VC_CTRL(n)                 DSI_REG(0x0100 + (n * 0x20))
-#define DSI_VC_TE(n)                   DSI_REG(0x0104 + (n * 0x20))
-#define DSI_VC_LONG_PACKET_HEADER(n)   DSI_REG(0x0108 + (n * 0x20))
-#define DSI_VC_LONG_PACKET_PAYLOAD(n)  DSI_REG(0x010C + (n * 0x20))
-#define DSI_VC_SHORT_PACKET_HEADER(n)  DSI_REG(0x0110 + (n * 0x20))
-#define DSI_VC_IRQSTATUS(n)            DSI_REG(0x0118 + (n * 0x20))
-#define DSI_VC_IRQENABLE(n)            DSI_REG(0x011C + (n * 0x20))
+#define DSI_PROTO                      0
+#define DSI_PROTO_SZ                   0x200
+
+#define DSI_REVISION                   DSI_REG(DSI_PROTO, 0x0000)
+#define DSI_SYSCONFIG                  DSI_REG(DSI_PROTO, 0x0010)
+#define DSI_SYSSTATUS                  DSI_REG(DSI_PROTO, 0x0014)
+#define DSI_IRQSTATUS                  DSI_REG(DSI_PROTO, 0x0018)
+#define DSI_IRQENABLE                  DSI_REG(DSI_PROTO, 0x001C)
+#define DSI_CTRL                       DSI_REG(DSI_PROTO, 0x0040)
+#define DSI_GNQ                                DSI_REG(DSI_PROTO, 0x0044)
+#define DSI_COMPLEXIO_CFG1             DSI_REG(DSI_PROTO, 0x0048)
+#define DSI_COMPLEXIO_IRQ_STATUS       DSI_REG(DSI_PROTO, 0x004C)
+#define DSI_COMPLEXIO_IRQ_ENABLE       DSI_REG(DSI_PROTO, 0x0050)
+#define DSI_CLK_CTRL                   DSI_REG(DSI_PROTO, 0x0054)
+#define DSI_TIMING1                    DSI_REG(DSI_PROTO, 0x0058)
+#define DSI_TIMING2                    DSI_REG(DSI_PROTO, 0x005C)
+#define DSI_VM_TIMING1                 DSI_REG(DSI_PROTO, 0x0060)
+#define DSI_VM_TIMING2                 DSI_REG(DSI_PROTO, 0x0064)
+#define DSI_VM_TIMING3                 DSI_REG(DSI_PROTO, 0x0068)
+#define DSI_CLK_TIMING                 DSI_REG(DSI_PROTO, 0x006C)
+#define DSI_TX_FIFO_VC_SIZE            DSI_REG(DSI_PROTO, 0x0070)
+#define DSI_RX_FIFO_VC_SIZE            DSI_REG(DSI_PROTO, 0x0074)
+#define DSI_COMPLEXIO_CFG2             DSI_REG(DSI_PROTO, 0x0078)
+#define DSI_RX_FIFO_VC_FULLNESS                DSI_REG(DSI_PROTO, 0x007C)
+#define DSI_VM_TIMING4                 DSI_REG(DSI_PROTO, 0x0080)
+#define DSI_TX_FIFO_VC_EMPTINESS       DSI_REG(DSI_PROTO, 0x0084)
+#define DSI_VM_TIMING5                 DSI_REG(DSI_PROTO, 0x0088)
+#define DSI_VM_TIMING6                 DSI_REG(DSI_PROTO, 0x008C)
+#define DSI_VM_TIMING7                 DSI_REG(DSI_PROTO, 0x0090)
+#define DSI_STOPCLK_TIMING             DSI_REG(DSI_PROTO, 0x0094)
+#define DSI_VC_CTRL(n)                 DSI_REG(DSI_PROTO, 0x0100 + (n * 0x20))
+#define DSI_VC_TE(n)                   DSI_REG(DSI_PROTO, 0x0104 + (n * 0x20))
+#define DSI_VC_LONG_PACKET_HEADER(n)   DSI_REG(DSI_PROTO, 0x0108 + (n * 0x20))
+#define DSI_VC_LONG_PACKET_PAYLOAD(n)  DSI_REG(DSI_PROTO, 0x010C + (n * 0x20))
+#define DSI_VC_SHORT_PACKET_HEADER(n)  DSI_REG(DSI_PROTO, 0x0110 + (n * 0x20))
+#define DSI_VC_IRQSTATUS(n)            DSI_REG(DSI_PROTO, 0x0118 + (n * 0x20))
+#define DSI_VC_IRQENABLE(n)            DSI_REG(DSI_PROTO, 0x011C + (n * 0x20))
 
 /* DSIPHY_SCP */
 
-#define DSI_DSIPHY_CFG0                        DSI_REG(0x200 + 0x0000)
-#define DSI_DSIPHY_CFG1                        DSI_REG(0x200 + 0x0004)
-#define DSI_DSIPHY_CFG2                        DSI_REG(0x200 + 0x0008)
-#define DSI_DSIPHY_CFG5                        DSI_REG(0x200 + 0x0014)
-#define DSI_DSIPHY_CFG10               DSI_REG(0x200 + 0x0028)
+#define DSI_PHY                                1
+#define DSI_PHY_OFFSET                 0x200
+#define DSI_PHY_SZ                     0x40
+
+#define DSI_DSIPHY_CFG0                        DSI_REG(DSI_PHY, 0x0000)
+#define DSI_DSIPHY_CFG1                        DSI_REG(DSI_PHY, 0x0004)
+#define DSI_DSIPHY_CFG2                        DSI_REG(DSI_PHY, 0x0008)
+#define DSI_DSIPHY_CFG5                        DSI_REG(DSI_PHY, 0x0014)
+#define DSI_DSIPHY_CFG10               DSI_REG(DSI_PHY, 0x0028)
 
 /* DSI_PLL_CTRL_SCP */
 
-#define DSI_PLL_CONTROL                        DSI_REG(0x300 + 0x0000)
-#define DSI_PLL_STATUS                 DSI_REG(0x300 + 0x0004)
-#define DSI_PLL_GO                     DSI_REG(0x300 + 0x0008)
-#define DSI_PLL_CONFIGURATION1         DSI_REG(0x300 + 0x000C)
-#define DSI_PLL_CONFIGURATION2         DSI_REG(0x300 + 0x0010)
+#define DSI_PLL                                2
+#define DSI_PLL_OFFSET                 0x300
+#define DSI_PLL_SZ                     0x20
+
+#define DSI_PLL_CONTROL                        DSI_REG(DSI_PLL, 0x0000)
+#define DSI_PLL_STATUS                 DSI_REG(DSI_PLL, 0x0004)
+#define DSI_PLL_GO                     DSI_REG(DSI_PLL, 0x0008)
+#define DSI_PLL_CONFIGURATION1         DSI_REG(DSI_PLL, 0x000C)
+#define DSI_PLL_CONFIGURATION2         DSI_REG(DSI_PLL, 0x0010)
 
 #define REG_GET(dsidev, idx, start, end) \
        FLD_GET(dsi_read_reg(dsidev, idx), start, end)
@@ -277,7 +287,9 @@ struct dsi_clk_calc_ctx {
 
 struct dsi_data {
        struct platform_device *pdev;
-       void __iomem    *base;
+       void __iomem *proto_base;
+       void __iomem *phy_base;
+       void __iomem *pll_base;
 
        int module_id;
 
@@ -414,16 +426,32 @@ static inline void dsi_write_reg(struct platform_device *dsidev,
                const struct dsi_reg idx, u32 val)
 {
        struct dsi_data *dsi = dsi_get_dsidrv_data(dsidev);
+       void __iomem *base;
+
+       switch(idx.module) {
+               case DSI_PROTO: base = dsi->proto_base; break;
+               case DSI_PHY: base = dsi->phy_base; break;
+               case DSI_PLL: base = dsi->pll_base; break;
+               default: return;
+       }
 
-       __raw_writel(val, dsi->base + idx.idx);
+       __raw_writel(val, base + idx.idx);
 }
 
 static inline u32 dsi_read_reg(struct platform_device *dsidev,
                const struct dsi_reg idx)
 {
        struct dsi_data *dsi = dsi_get_dsidrv_data(dsidev);
+       void __iomem *base;
 
-       return __raw_readl(dsi->base + idx.idx);
+       switch(idx.module) {
+               case DSI_PROTO: base = dsi->proto_base; break;
+               case DSI_PHY: base = dsi->phy_base; break;
+               case DSI_PLL: base = dsi->pll_base; break;
+               default: return 0;
+       }
+
+       return __raw_readl(base + idx.idx);
 }
 
 static void dsi_bus_lock(struct omap_dss_device *dssdev)
@@ -5346,8 +5374,9 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
 {
        u32 rev;
        int r, i;
-       struct resource *dsi_mem;
        struct dsi_data *dsi;
+       struct resource *res;
+       struct resource temp_res;
 
        dsi = devm_kzalloc(&dsidev->dev, sizeof(*dsi), GFP_KERNEL);
        if (!dsi)
@@ -5377,16 +5406,64 @@ static int omap_dsihw_probe(struct platform_device *dsidev)
        dsi->te_timer.function = dsi_te_timeout;
        dsi->te_timer.data = 0;
 #endif
-       dsi_mem = platform_get_resource(dsi->pdev, IORESOURCE_MEM, 0);
-       if (!dsi_mem) {
-               DSSERR("can't get IORESOURCE_MEM DSI\n");
-               return -EINVAL;
+
+       res = platform_get_resource_byname(dsidev, IORESOURCE_MEM, "proto");
+       if (!res) {
+               res = platform_get_resource(dsidev, IORESOURCE_MEM, 0);
+               if (!res) {
+                       DSSERR("can't get IORESOURCE_MEM DSI\n");
+                       return -EINVAL;
+               }
+
+               temp_res.start = res->start;
+               temp_res.end = temp_res.start + DSI_PROTO_SZ - 1;
+               res = &temp_res;
+       }
+
+       dsi->proto_base = devm_ioremap(&dsidev->dev, res->start,
+               resource_size(res));
+       if (!dsi->proto_base) {
+               DSSERR("can't ioremap DSI protocol engine\n");
+               return -ENOMEM;
+       }
+
+       res = platform_get_resource_byname(dsidev, IORESOURCE_MEM, "phy");
+       if (!res) {
+               res = platform_get_resource(dsidev, IORESOURCE_MEM, 0);
+               if (!res) {
+                       DSSERR("can't get IORESOURCE_MEM DSI\n");
+                       return -EINVAL;
+               }
+
+               temp_res.start = res->start + DSI_PHY_OFFSET;
+               temp_res.end = temp_res.start + DSI_PHY_SZ - 1;
+               res = &temp_res;
+       }
+
+       dsi->phy_base = devm_ioremap(&dsidev->dev, res->start,
+               resource_size(res));
+       if (!dsi->proto_base) {
+               DSSERR("can't ioremap DSI PHY\n");
+               return -ENOMEM;
+       }
+
+       res = platform_get_resource_byname(dsidev, IORESOURCE_MEM, "pll");
+       if (!res) {
+               res = platform_get_resource(dsidev, IORESOURCE_MEM, 0);
+               if (!res) {
+                       DSSERR("can't get IORESOURCE_MEM DSI\n");
+                       return -EINVAL;
+               }
+
+               temp_res.start = res->start + DSI_PLL_OFFSET;
+               temp_res.end = temp_res.start + DSI_PLL_SZ - 1;
+               res = &temp_res;
        }
 
-       dsi->base = devm_ioremap(&dsidev->dev, dsi_mem->start,
-                                resource_size(dsi_mem));
-       if (!dsi->base) {
-               DSSERR("can't ioremap DSI\n");
+       dsi->pll_base = devm_ioremap(&dsidev->dev, res->start,
+               resource_size(res));
+       if (!dsi->proto_base) {
+               DSSERR("can't ioremap DSI PLL\n");
                return -ENOMEM;
        }