[U-Boot] [U-BOOT] nand merge problem

Scott Wood scottwood at freescale.com
Mon Jun 1 18:54:28 CEST 2009


On Sun, May 31, 2009 at 04:09:35PM +0800, xiangfu wrote:
> static void jz_hwcontrol(struct mtd_info *mtd, int cmd, unsigned int ctrl)
> {
> 	struct nand_chip *this = (struct nand_chip *)(mtd->priv);
>         unsigned int nandaddr = (unsigned int)this->IO_ADDR_W;
> 	if (ctrl & NAND_CTRL_CHANGE) {
> 		if (ctrl & NAND_CLE)
> 			nandaddr = nandaddr | 0x00008000;
>                 else
>                         nandaddr = nandaddr & ~0x00008000;
> 			
> 		if (ctrl & NAND_ALE)
> 			this->IO_ADDR_W = (void __iomem *)((unsigned long)(this->IO_ADDR_W) |
> 0x00010000);
> 		else
> 			this->IO_ADDR_W = (void __iomem *)((unsigned long)(this->IO_ADDR_W) &
> ~0x00010000);
> 		if (ctrl & NAND_NCE) {
> 			this->IO_ADDR_W = this->IO_ADDR_R = (void __iomem *)NAND_DATA_PORT1;
> 			REG_EMC_NFCSR |= EMC_NFCSR_NFCE1;
> 		} else {
> 			REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE1;
>                         REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE2;
>                         REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE3;
>                         REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE4;
> 		}
> 	}
> 
> 	this->IO_ADDR_W = (void __iomem *)nandaddr;
>         if (cmd != NAND_CMD_NONE)
>                 writeb(cmd, this->IO_ADDR_W);
> }

Try something like this instead:

static void jz_hwcontrol(struct mtd_info *mtd, int cmd, unsigned int ctrl)
{
	struct nand_chip *this = mtd->priv;
	unsigned long nandaddr = (unsigned long)this->IO_ADDR_W;

	if (ctrl & NAND_CTRL_CHANGE) {
		/* Change this to use I/O accessors. */
		if (ctrl & NAND_NCE) {
			REG_EMC_NFCSR |= EMC_NFCSR_NFCE1; 
		} else {
			/*
			 * Why set only one bit when NCE is high, but clear
			 * four when low?  Why clear separate bits in the same
			 * register one at a time?
			 */
			REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE1;
			REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE2;
			REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE3;
			REG_EMC_NFCSR &= ~EMC_NFCSR_NFCE4;
		}
	}

	if (cmd == NAND_CMD_NONE)
		return;

	if (ctrl & NAND_CLE)
		nandaddr |= 0x00008000;
	else /* must be ALE */
		nandaddr |= 0x00010000;

	writeb(cmd, (uint8_t *)nandaddr);
}

-Scott


More information about the U-Boot mailing list