diff options
author | Prabhakar Kushwaha <prabhakar@freescale.com> | 2013-04-04 18:44:06 +0000 |
---|---|---|
committer | Scott Wood <scottwood@freescale.com> | 2013-05-22 16:53:42 -0500 |
commit | a1b81ab26fbbdcbaa6e2a096397c75415181c298 (patch) | |
tree | bda14d8f39dc1c41ad70e2ed8bed0b12cbd4af7f /drivers/mtd/nand | |
parent | 453db36863668df08078838029d988b72f0ee994 (diff) |
nand/fsl_ifc: Convert to self-init
Convert NAND IFC driver to support CONFIG_SYS_NAND_SELF_INIT.
Signed-off-by: Prabhakar Kushwaha <prabhakar@freescale.com>
Diffstat (limited to 'drivers/mtd/nand')
-rw-r--r-- | drivers/mtd/nand/fsl_ifc_nand.c | 42 |
1 files changed, 37 insertions, 5 deletions
diff --git a/drivers/mtd/nand/fsl_ifc_nand.c b/drivers/mtd/nand/fsl_ifc_nand.c index b13d8a9303..49cfb33569 100644 --- a/drivers/mtd/nand/fsl_ifc_nand.c +++ b/drivers/mtd/nand/fsl_ifc_nand.c @@ -21,6 +21,7 @@ #include <common.h> #include <malloc.h> +#include <nand.h> #include <linux/mtd/mtd.h> #include <linux/mtd/nand.h> @@ -41,7 +42,6 @@ struct fsl_ifc_ctrl; /* mtd information per set */ struct fsl_ifc_mtd { - struct mtd_info mtd; struct nand_chip chip; struct fsl_ifc_ctrl *ctrl; @@ -794,11 +794,14 @@ static void fsl_ifc_sram_init(void) out_be32(&ifc_ctrl->regs->csor_cs[cs].csor_ext, csor_ext); } -int board_nand_init(struct nand_chip *nand) +static int fsl_ifc_chip_init(int devnum, u8 *addr) { + struct mtd_info *mtd = &nand_info[devnum]; + struct nand_chip *nand; struct fsl_ifc_mtd *priv; struct nand_ecclayout *layout; uint32_t cspr = 0, csor = 0, ver = 0; + int ret; if (!ifc_ctrl) { fsl_ifc_ctrl_init(); @@ -811,18 +814,18 @@ int board_nand_init(struct nand_chip *nand) return -ENOMEM; priv->ctrl = ifc_ctrl; - priv->vbase = nand->IO_ADDR_R; + priv->vbase = addr; /* Find which chip select it is connected to. */ for (priv->bank = 0; priv->bank < MAX_BANKS; priv->bank++) { - phys_addr_t base_addr = virt_to_phys(nand->IO_ADDR_R); + phys_addr_t phys_addr = virt_to_phys(addr); cspr = in_be32(&ifc_ctrl->regs->cspr_cs[priv->bank].cspr); csor = in_be32(&ifc_ctrl->regs->csor_cs[priv->bank].csor); if ((cspr & CSPR_V) && (cspr & CSPR_MSEL) == CSPR_MSEL_NAND && - (cspr & CSPR_BA) == CSPR_PHYS_ADDR(base_addr)) { + (cspr & CSPR_BA) == CSPR_PHYS_ADDR(phys_addr)) { ifc_ctrl->cs_nand = priv->bank << IFC_NAND_CSEL_SHIFT; break; } @@ -835,6 +838,9 @@ int board_nand_init(struct nand_chip *nand) return -ENODEV; } + nand = &priv->chip; + mtd->priv = nand; + ifc_ctrl->chips[priv->bank] = priv; /* fill in nand_chip structure */ @@ -921,5 +927,31 @@ int board_nand_init(struct nand_chip *nand) if (ver == FSL_IFC_V1_1_0) fsl_ifc_sram_init(); + ret = nand_scan_ident(mtd, 1, NULL); + if (ret) + return ret; + + ret = nand_scan_tail(mtd); + if (ret) + return ret; + + ret = nand_register(devnum); + if (ret) + return ret; return 0; } + +#ifndef CONFIG_SYS_NAND_BASE_LIST +#define CONFIG_SYS_NAND_BASE_LIST { CONFIG_SYS_NAND_BASE } +#endif + +static unsigned long base_address[CONFIG_SYS_MAX_NAND_DEVICE] = + CONFIG_SYS_NAND_BASE_LIST; + +void board_nand_init(void) +{ + int i; + + for (i = 0; i < CONFIG_SYS_MAX_NAND_DEVICE; i++) + fsl_ifc_chip_init(i, (u8 *)base_address[i]); +} |