From e93569c12e14a5a1b5e6c7dfff03bf36801aae02 Mon Sep 17 00:00:00 2001 From: Gabor Juhos Date: Mon, 19 Mar 2012 15:56:59 +0000 Subject: [PATCH] ar71xx: add platform data for the RB750 NAND driver SVN-Revision: 31022 --- .../ar71xx/files/arch/mips/ath79/mach-rb750.c | 24 ++++++++-- .../mips/include/asm/mach-ath79/mach-rb750.h | 11 ++++- .../files/drivers/mtd/nand/rb750_nand.c | 46 +++++++++++-------- 3 files changed, 55 insertions(+), 26 deletions(-) diff --git a/target/linux/ar71xx/files/arch/mips/ath79/mach-rb750.c b/target/linux/ar71xx/files/arch/mips/ath79/mach-rb750.c index 976617bb36..bcd961e1bd 100644 --- a/target/linux/ar71xx/files/arch/mips/ath79/mach-rb750.c +++ b/target/linux/ar71xx/files/arch/mips/ath79/mach-rb750.c @@ -1,5 +1,5 @@ /* - * MikroTik RouterBOARD 750 support + * MikroTik RouterBOARD 750/750GL support * * Copyright (C) 2010-2012 Gabor Juhos * @@ -59,9 +59,13 @@ static struct platform_device rb750_leds_device = { } }; +static struct rb7xx_nand_platform_data rb750_nand_data; static struct platform_device rb750_nand_device = { .name = "rb750-nand", .id = -1, + .dev = { + .platform_data = &rb750_nand_data, + } }; int rb750_latch_change(u32 mask_clr, u32 mask_set) @@ -113,19 +117,24 @@ unlock: } EXPORT_SYMBOL_GPL(rb750_latch_change); -void rb750_nand_pins_enable(void) +static void rb750_nand_enable_pins(void) { + rb750_latch_change(RB750_LVC573_LE, 0); ath79_gpio_function_setup(AR724X_GPIO_FUNC_JTAG_DISABLE, AR724X_GPIO_FUNC_SPI_EN); } -EXPORT_SYMBOL_GPL(rb750_nand_pins_enable); -void rb750_nand_pins_disable(void) +static void rb750_nand_disable_pins(void) { ath79_gpio_function_setup(AR724X_GPIO_FUNC_SPI_EN, AR724X_GPIO_FUNC_JTAG_DISABLE); + rb750_latch_change(0, RB750_LVC573_LE); +} + +static void rb750_nand_latch_change(u32 clear, u32 set) +{ + rb750_latch_change(clear, set); } -EXPORT_SYMBOL_GPL(rb750_nand_pins_disable); static void __init rb750_setup(void) { @@ -147,6 +156,11 @@ static void __init rb750_setup(void) ath79_register_eth(0); platform_device_register(&rb750_leds_device); + + rb750_nand_data.nce_line = RB750_NAND_NCE; + rb750_nand_data.enable_pins = rb750_nand_enable_pins; + rb750_nand_data.disable_pins = rb750_nand_disable_pins; + rb750_nand_data.latch_change = rb750_nand_latch_change; platform_device_register(&rb750_nand_device); } diff --git a/target/linux/ar71xx/files/arch/mips/include/asm/mach-ath79/mach-rb750.h b/target/linux/ar71xx/files/arch/mips/include/asm/mach-ath79/mach-rb750.h index 3e6fc50c55..9509fca71e 100644 --- a/target/linux/ar71xx/files/arch/mips/include/asm/mach-ath79/mach-rb750.h +++ b/target/linux/ar71xx/files/arch/mips/include/asm/mach-ath79/mach-rb750.h @@ -43,6 +43,7 @@ #define RB750_LED_PORT3 BIT(RB750_GPIO_LED_PORT3) #define RB750_LED_PORT4 BIT(RB750_GPIO_LED_PORT4) #define RB750_LED_PORT5 BIT(RB750_GPIO_LED_PORT5) +#define RB750_NAND_NCE BIT(RB750_GPIO_NAND_NCE) #define RB750_LVC573_LE BIT(RB750_GPIO_LVC573_LE) @@ -61,8 +62,14 @@ struct rb750_led_platform_data { struct rb750_led_data *leds; }; +struct rb7xx_nand_platform_data { + u32 nce_line; + + void (*enable_pins)(void); + void (*disable_pins)(void); + void (*latch_change)(u32, u32); +}; + int rb750_latch_change(u32 mask_clr, u32 mask_set); -void rb750_nand_pins_enable(void); -void rb750_nand_pins_disable(void); #endif /* _MACH_RB750_H */ \ No newline at end of file diff --git a/target/linux/ar71xx/files/drivers/mtd/nand/rb750_nand.c b/target/linux/ar71xx/files/drivers/mtd/nand/rb750_nand.c index f97e6e6c69..251e182208 100644 --- a/target/linux/ar71xx/files/drivers/mtd/nand/rb750_nand.c +++ b/target/linux/ar71xx/files/drivers/mtd/nand/rb750_nand.c @@ -31,20 +31,24 @@ #define RB750_NAND_NRE BIT(RB750_GPIO_NAND_NRE) #define RB750_NAND_NWE BIT(RB750_GPIO_NAND_NWE) #define RB750_NAND_RDY BIT(RB750_GPIO_NAND_RDY) -#define RB750_NAND_NCE BIT(RB750_GPIO_NAND_NCE) #define RB750_NAND_DATA_SHIFT 1 #define RB750_NAND_DATA_BITS (0xff << RB750_NAND_DATA_SHIFT) #define RB750_NAND_INPUT_BITS (RB750_NAND_DATA_BITS | RB750_NAND_RDY) #define RB750_NAND_OUTPUT_BITS (RB750_NAND_ALE | RB750_NAND_CLE | \ - RB750_NAND_NRE | RB750_NAND_NWE | \ - RB750_NAND_NCE) + RB750_NAND_NRE | RB750_NAND_NWE) struct rb750_nand_info { struct nand_chip chip; struct mtd_info mtd; + struct rb7xx_nand_platform_data *pdata; }; +static inline struct rb750_nand_info *mtd_to_rbinfo(struct mtd_info *mtd) +{ + return container_of(mtd, struct rb750_nand_info, mtd); +} + /* * We need to use the OLD Yaffs-1 OOB layout, otherwise the RB bootloader * will not be able to find the kernel that we load. @@ -138,16 +142,12 @@ static int rb750_nand_read_verify(u8 *read_buf, unsigned len, static void rb750_nand_select_chip(struct mtd_info *mtd, int chip) { + struct rb750_nand_info *rbinfo = mtd_to_rbinfo(mtd); void __iomem *base = ath79_gpio_base; - u32 func; u32 t; - func = __raw_readl(base + AR71XX_GPIO_REG_FUNC); if (chip >= 0) { - /* disable latch */ - rb750_latch_change(RB750_LVC573_LE, 0); - - rb750_nand_pins_enable(); + rbinfo->pdata->enable_pins(); /* set input mode for data lines */ t = __raw_readl(base + AR71XX_GPIO_REG_OE); @@ -161,10 +161,12 @@ static void rb750_nand_select_chip(struct mtd_info *mtd, int chip) (void) __raw_readl(base + AR71XX_GPIO_REG_SET); /* activate CE line */ - __raw_writel(RB750_NAND_NCE, base + AR71XX_GPIO_REG_CLEAR); + __raw_writel(rbinfo->pdata->nce_line, + base + AR71XX_GPIO_REG_CLEAR); } else { /* deactivate CE line */ - __raw_writel(RB750_NAND_NCE, base + AR71XX_GPIO_REG_SET); + __raw_writel(rbinfo->pdata->nce_line, + base + AR71XX_GPIO_REG_SET); /* flush write */ (void) __raw_readl(base + AR71XX_GPIO_REG_SET); @@ -172,10 +174,7 @@ static void rb750_nand_select_chip(struct mtd_info *mtd, int chip) __raw_writel(t | RB750_NAND_IO0 | RB750_NAND_RDY, base + AR71XX_GPIO_REG_OE); - rb750_nand_pins_disable(); - - /* enable latch */ - rb750_latch_change(0, RB750_LVC573_LE); + rbinfo->pdata->disable_pins(); } } @@ -232,7 +231,7 @@ static int rb750_nand_verify_buf(struct mtd_info *mtd, const u8 *buf, int len) return rb750_nand_read_verify(NULL, len, buf); } -static void __init rb750_nand_gpio_init(void) +static void __init rb750_nand_gpio_init(struct rb750_nand_info *info) { void __iomem *base = ath79_gpio_base; u32 out; @@ -253,19 +252,24 @@ static void __init rb750_nand_gpio_init(void) /* setup output lines */ t = __raw_readl(base + AR71XX_GPIO_REG_OE); - __raw_writel(t | RB750_NAND_OUTPUT_BITS, base + AR71XX_GPIO_REG_OE); + t |= RB750_NAND_OUTPUT_BITS; + t |= info->pdata->nce_line; + __raw_writel(t, base + AR71XX_GPIO_REG_OE); - rb750_latch_change(~out & RB750_NAND_IO0, out & RB750_NAND_IO0); + info->pdata->latch_change(~out & RB750_NAND_IO0, out & RB750_NAND_IO0); } static int __devinit rb750_nand_probe(struct platform_device *pdev) { struct rb750_nand_info *info; + struct rb7xx_nand_platform_data *pdata; int ret; printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); - rb750_nand_gpio_init(); + pdata = pdev->dev.platform_data; + if (!pdata) + return -EINVAL; info = kzalloc(sizeof(*info), GFP_KERNEL); if (!info) @@ -287,8 +291,12 @@ static int __devinit rb750_nand_probe(struct platform_device *pdev) info->chip.ecc.mode = NAND_ECC_SOFT; info->chip.options |= NAND_NO_AUTOINCR; + info->pdata = pdata; + platform_set_drvdata(pdev, info); + rb750_nand_gpio_init(info); + ret = nand_scan_ident(&info->mtd, 1, NULL); if (ret) { ret = -ENXIO; -- 2.30.2