diff options
author | Dmitry Baryshkov <dbaryshkov@gmail.com> | 2008-09-24 23:36:23 +0200 |
---|---|---|
committer | Samuel Ortiz <samuel@sortiz.org> | 2008-10-19 22:54:09 +0200 |
commit | 1c1b6ffce5737d764cc474b9bd6677bb9a344094 (patch) | |
tree | b637110fe6282769104b72d08b3864ed1538bf96 | |
parent | 80e74a805f0a6662b9b8de519439afd06ac35427 (diff) | |
download | op-kernel-dev-1c1b6ffce5737d764cc474b9bd6677bb9a344094.zip op-kernel-dev-1c1b6ffce5737d764cc474b9bd6677bb9a344094.tar.gz |
mfd: provide and use setup hook for tc6393xb
Instead of using bitfields for initial gpio setup,
provide generic setup/teardown hooks that can be used
to set the gpio states, register child devices, etc.
Signed-off-by: Dmitry Baryshkov <dbaryshkov@gmail.com>
Signed-off-by: Samuel Ortiz <sameo@openedhand.com>
-rw-r--r-- | arch/arm/mach-pxa/include/mach/tosa.h | 2 | ||||
-rw-r--r-- | arch/arm/mach-pxa/tosa.c | 35 | ||||
-rw-r--r-- | drivers/mfd/tc6393xb.c | 21 | ||||
-rw-r--r-- | include/linux/mfd/tc6393xb.h | 4 |
4 files changed, 45 insertions, 17 deletions
diff --git a/arch/arm/mach-pxa/include/mach/tosa.h b/arch/arm/mach-pxa/include/mach/tosa.h index a72803f..8bce6d8 100644 --- a/arch/arm/mach-pxa/include/mach/tosa.h +++ b/arch/arm/mach-pxa/include/mach/tosa.h @@ -59,8 +59,6 @@ * TC6393XB GPIOs */ #define TOSA_TC6393XB_GPIO_BASE (NR_BUILTIN_GPIO + 2 * 12) -#define TOSA_TC6393XB_GPIO(i) (TOSA_TC6393XB_GPIO_BASE + (i)) -#define TOSA_TC6393XB_GPIO_BIT(gpio) (1 << (gpio - TOSA_TC6393XB_GPIO_BASE)) #define TOSA_GPIO_TG_ON (TOSA_TC6393XB_GPIO_BASE + 0) #define TOSA_GPIO_L_MUTE (TOSA_TC6393XB_GPIO_BASE + 1) diff --git a/arch/arm/mach-pxa/tosa.c b/arch/arm/mach-pxa/tosa.c index 130e37e..fac846b 100644 --- a/arch/arm/mach-pxa/tosa.c +++ b/arch/arm/mach-pxa/tosa.c @@ -706,16 +706,39 @@ static struct tmio_nand_data tosa_tc6393xb_nand_config = { .badblock_pattern = &tosa_tc6393xb_nand_bbt, }; -static struct tc6393xb_platform_data tosa_tc6393xb_setup = { +static int tosa_tc6393xb_setup(struct platform_device *dev) +{ + int rc; + + rc = gpio_request(TOSA_GPIO_CARD_VCC_ON, "CARD_VCC_ON"); + if (rc) + goto err_req; + + rc = gpio_direction_output(TOSA_GPIO_CARD_VCC_ON, 1); + if (rc) + goto err_dir; + + return rc; + +err_dir: + gpio_free(TOSA_GPIO_CARD_VCC_ON); +err_req: + return rc; +} + +static void tosa_tc6393xb_teardown(struct platform_device *dev) +{ + gpio_free(TOSA_GPIO_CARD_VCC_ON); +} + +static struct tc6393xb_platform_data tosa_tc6393xb_data = { .scr_pll2cr = 0x0cc1, .scr_gper = 0x3300, - .scr_gpo_dsr = - TOSA_TC6393XB_GPIO_BIT(TOSA_GPIO_CARD_VCC_ON), - .scr_gpo_doecr = - TOSA_TC6393XB_GPIO_BIT(TOSA_GPIO_CARD_VCC_ON), .irq_base = IRQ_BOARD_START, .gpio_base = TOSA_TC6393XB_GPIO_BASE, + .setup = tosa_tc6393xb_setup, + .teardown = tosa_tc6393xb_teardown, .enable = tosa_tc6393xb_enable, .disable = tosa_tc6393xb_disable, @@ -730,7 +753,7 @@ static struct platform_device tc6393xb_device = { .name = "tc6393xb", .id = -1, .dev = { - .platform_data = &tosa_tc6393xb_setup, + .platform_data = &tosa_tc6393xb_data, }, .num_resources = ARRAY_SIZE(tc6393xb_resources), .resource = tc6393xb_resources, diff --git a/drivers/mfd/tc6393xb.c b/drivers/mfd/tc6393xb.c index e4c1c78..83dc703 100644 --- a/drivers/mfd/tc6393xb.c +++ b/drivers/mfd/tc6393xb.c @@ -460,13 +460,6 @@ static int __devinit tc6393xb_probe(struct platform_device *dev) tc6393xb->suspend_state.fer = 0; - for (i = 0; i < 3; i++) { - tc6393xb->suspend_state.gpo_dsr[i] = - (tcpd->scr_gpo_dsr >> (8 * i)) & 0xff; - tc6393xb->suspend_state.gpo_doecr[i] = - (tcpd->scr_gpo_doecr >> (8 * i)) & 0xff; - } - tc6393xb->suspend_state.ccr = SCR_CCR_UNK1 | SCR_CCR_HCLK_48; @@ -488,6 +481,12 @@ static int __devinit tc6393xb_probe(struct platform_device *dev) tc6393xb_attach_irq(dev); + if (tcpd->setup) { + ret = tcpd->setup(dev); + if (ret) + goto err_setup; + } + tc6393xb_cells[TC6393XB_CELL_NAND].driver_data = tcpd->nand_data; tc6393xb_cells[TC6393XB_CELL_NAND].platform_data = &tc6393xb_cells[TC6393XB_CELL_NAND]; @@ -506,6 +505,10 @@ static int __devinit tc6393xb_probe(struct platform_device *dev) if (!ret) return 0; + if (tcpd->teardown) + tcpd->teardown(dev); + +err_setup: tc6393xb_detach_irq(dev); err_gpio_add: @@ -535,6 +538,10 @@ static int __devexit tc6393xb_remove(struct platform_device *dev) int ret; mfd_remove_devices(&dev->dev); + + if (tcpd->teardown) + tcpd->teardown(dev); + tc6393xb_detach_irq(dev); if (tc6393xb->gpio.base != -1) { diff --git a/include/linux/mfd/tc6393xb.h b/include/linux/mfd/tc6393xb.h index fec7b3f..1fa8206 100644 --- a/include/linux/mfd/tc6393xb.h +++ b/include/linux/mfd/tc6393xb.h @@ -21,8 +21,6 @@ struct tc6393xb_platform_data { u16 scr_pll2cr; /* PLL2 Control */ u16 scr_gper; /* GP Enable */ - u32 scr_gpo_doecr; /* GPO Data OE Control */ - u32 scr_gpo_dsr; /* GPO Data Set */ int (*enable)(struct platform_device *dev); int (*disable)(struct platform_device *dev); @@ -31,6 +29,8 @@ struct tc6393xb_platform_data { int irq_base; /* base for subdevice irqs */ int gpio_base; + int (*setup)(struct platform_device *dev); + void (*teardown)(struct platform_device *dev); struct tmio_nand_data *nand_data; }; |