1 drivers/mtd/nand/Kconfig | 7
2 drivers/mtd/nand/Makefile | 1
3 drivers/mtd/nand/tmio.c | 554 ++++++++++++++++++++++++++++++++++++++++++++++
4 3 files changed, 562 insertions(+)
6 Index: git/drivers/mtd/nand/tmio.c
7 ===================================================================
8 --- /dev/null 1970-01-01 00:00:00.000000000 +0000
9 +++ git/drivers/mtd/nand/tmio.c 2006-11-07 23:31:12.000000000 +0000
12 + * A device driver for NAND flash connected to a Toshiba Mobile IO
13 + * controller. This is known to work with the following variants:
14 + * TC6393XB revision 3
16 + * Maintainer: Chris Humbert <mahadri+mtd@drigon.com>
18 + * Copyright (C) 2005 Chris Humbert
19 + * Copyright (C) 2005 Dirk Opfer
20 + * Copyright (C) 2004 SHARP
21 + * Copyright (C) 2002 Lineo Japan, Inc.
22 + * Copyright (C) Ian Molton and Sebastian Carlier
24 + * Based on Sharp's NAND driver, sharp_sl_tc6393.c
26 + * This program is free software; you can redistribute it and/or modify
27 + * it under the terms of the GNU General Public License version 2 as
28 + * published by the Free Software Foundation.
31 +#include <linux/module.h>
32 +#include <linux/types.h>
33 +#include <linux/delay.h>
34 +#include <linux/wait.h>
35 +#include <linux/ioport.h>
36 +#include <linux/mtd/mtd.h>
37 +#include <linux/mtd/nand.h>
38 +#include <linux/mtd/nand_ecc.h>
39 +#include <linux/mtd/partitions.h>
41 +#include <asm/hardware/tmio.h>
43 +#include <linux/interrupt.h>
45 +#define mtd_printk(level, mtd, format, arg...) \
46 + printk (level "%s: " format, mtd->name, ## arg)
47 +#define mtd_warn(mtd, format, arg...) \
48 + mtd_printk (KERN_WARNING, mtd, format, ## arg)
50 +/*--------------------------------------------------------------------------*/
52 +/* tmio_nfcr.mode Register Command List */
53 +#define FCR_MODE_DATA 0x94 // Data Data_Mode
54 +#define FCR_MODE_COMMAND 0x95 // Data Command_Mode
55 +#define FCR_MODE_ADDRESS 0x96 // Data Address_Mode
57 +#define FCR_MODE_HWECC_CALC 0xB4 // HW-ECC Data
58 +#define FCR_MODE_HWECC_RESULT 0xD4 // HW-ECC Calculation Result Read_Mode
59 +#define FCR_MODE_HWECC_RESET 0xF4 // HW-ECC Reset
61 +#define FCR_MODE_POWER_ON 0x0C // Power Supply ON to SSFDC card
62 +#define FCR_MODE_POWER_OFF 0x08 // Power Supply OFF to SSFDC card
64 +#define FCR_MODE_LED_OFF 0x00 // LED OFF
65 +#define FCR_MODE_LED_ON 0x04 // LED ON
67 +#define FCR_MODE_EJECT_ON 0x68 // Ejection Demand from Penguin is Advanced
68 +#define FCR_MODE_EJECT_OFF 0x08 // Ejection Demand from Penguin is Not Advanced
70 +#define FCR_MODE_LOCK 0x6C // Operates By Lock_Mode. Ejection Switch is Invalid
71 +#define FCR_MODE_UNLOCK 0x0C // Operates By UnLock_Mode.Ejection Switch is Effective
73 +#define FCR_MODE_CONTROLLER_ID 0x40 // Controller ID Read
74 +#define FCR_MODE_STANDBY 0x00 // SSFDC card Changes Standby State
76 +#define FCR_MODE_WE 0x80
77 +#define FCR_MODE_ECC1 0x40
78 +#define FCR_MODE_ECC0 0x20
79 +#define FCR_MODE_CE 0x10
80 +#define FCR_MODE_PCNT1 0x08
81 +#define FCR_MODE_PCNT0 0x04
82 +#define FCR_MODE_ALE 0x02
83 +#define FCR_MODE_CLE 0x01
85 +#define FCR_STATUS_BUSY 0x80
88 + * NAND Flash Host Controller Configuration Register
92 + u16 command; /* 0x04 Command */
94 + u16 base[2]; /* 0x10 NAND Flash Control Reg Base Addr*/
96 + u8 intp; /* 0x3d Interrupt Pin */
98 + u8 inte; /* 0x48 Interrupt Enable */
100 + u8 ec; /* 0x4a Event Control */
102 + u8 icc; /* 0x4c Internal Clock Control */
104 + u8 eccc; /* 0x5b ECC Control */
106 + u8 nftc; /* 0x60 NAND Flash Transaction Control */
107 + u8 nfm; /* 0x61 NAND Flash Monitor */
108 + u8 nfpsc; /* 0x62 NAND Flash Power Supply Control */
109 + u8 nfdc; /* 0x63 NAND Flash Detect Control */
111 +} __attribute__ ((packed));
114 + * NAND Flash Control Register
118 + u8 u8; /* 0x00 Data Register */
121 +} __attribute__ ((packed));
122 + u8 mode; /* 0x04 Mode Register */
123 + u8 status; /* 0x05 Status Register */
124 + u8 isr; /* 0x06 Interrupt Status Register */
125 + u8 imr; /* 0x07 Interrupt Mask Register */
126 +} __attribute__ ((packed));
129 + struct mtd_info mtd;
130 + struct nand_chip chip;
132 + struct tmio_nfhccr __iomem * ccr;
133 + struct tmio_nfcr __iomem * fcr;
137 + /* for tmio_nand_read_byte */
139 + unsigned read_good:1;
142 +#define mtd_to_tmio(m) container_of(m, struct tmio_nand, mtd)
144 +/*--------------------------------------------------------------------------*/
146 +static void tmio_nand_hwcontrol(struct mtd_info *mtd, int cmd,
149 + struct tmio_nand *tmio = mtd_to_tmio (mtd);
150 + struct tmio_nfcr __iomem *fcr = tmio->fcr;
151 + struct nand_chip *chip = mtd->priv;
153 + if (ctrl & NAND_CTRL_CHANGE) {
156 + if (ctrl & NAND_NCE) {
157 + mode = FCR_MODE_DATA;
159 + if (ctrl & NAND_CLE)
160 + mode |= FCR_MODE_CLE;
162 + mode &= ~FCR_MODE_CLE;
164 + if (ctrl & NAND_ALE)
165 + mode |= FCR_MODE_ALE;
167 + mode &= ~FCR_MODE_ALE;
169 + mode = FCR_MODE_STANDBY;
172 + iowrite8 (mode, &fcr->mode);
173 + tmio->read_good = 0;
176 + if (cmd != NAND_CMD_NONE)
177 + writeb(cmd, chip->IO_ADDR_W);
180 +static int tmio_nand_dev_ready (struct mtd_info* mtd)
182 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
183 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
185 + return !(ioread8 (&fcr->status) & FCR_STATUS_BUSY);
188 +static irqreturn_t tmio_irq (int irq, void *__tmio)
190 + struct tmio_nand* tmio = __tmio;
191 + struct nand_chip* this = &tmio->chip;
192 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
194 + /* disable RDYREQ interrupt */
195 + iowrite8 (0x00, &fcr->imr);
197 + if (unlikely (!waitqueue_active (&this->controller->wq)))
198 + printk (KERN_WARNING TMIO_NAME_NAND ": spurious interrupt\n");
200 + wake_up (&this->controller->wq);
201 + return IRQ_HANDLED;
205 + * The TMIO core has a RDYREQ interrupt on the posedge of #SMRB.
206 + * This interrupt is normally disabled, but for long operations like
207 + * erase and write, we enable it to wake us up. The irq handler
208 + * disables the interrupt.
211 +tmio_nand_wait (struct mtd_info *mtd, struct nand_chip *this)
213 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
214 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
217 + /* enable RDYREQ interrupt */
218 + iowrite8 (0x0f, &fcr->isr);
219 + iowrite8 (0x81, &fcr->imr);
221 + timeout = wait_event_timeout (this->controller->wq, tmio_nand_dev_ready (mtd),
222 + msecs_to_jiffies (this->state == FL_ERASING ? 400 : 20));
224 + if (unlikely (!tmio_nand_dev_ready (mtd))) {
225 + iowrite8 (0x00, &fcr->imr);
226 + mtd_warn (mtd, "still busy with %s after %d ms\n",
227 + this->state == FL_ERASING ? "erase" : "program",
228 + this->state == FL_ERASING ? 400 : 20);
230 + } else if (unlikely (!timeout)) {
231 + iowrite8 (0x00, &fcr->imr);
232 + mtd_warn (mtd, "timeout waiting for interrupt\n");
235 + this->cmdfunc (mtd, NAND_CMD_STATUS, -1, -1);
236 + return this->read_byte (mtd);
240 + * The TMIO controller combines two 8-bit data bytes into one 16-bit
241 + * word. This function separates them so nand_base.c works as expected,
242 + * especially its NAND_CMD_READID routines.
244 + * To prevent stale data from being read, tmio_nand_hwcontrol() clears
247 +static u_char tmio_nand_read_byte (struct mtd_info *mtd)
249 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
250 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
253 + if (tmio->read_good--)
256 + data = ioread16 (&fcr->u16);
257 + tmio->read = data >> 8;
262 + * The TMIO controller converts an 8-bit NAND interface to a 16-bit
263 + * bus interface, so all data reads and writes must be 16-bit wide.
264 + * Thus, we implement 16-bit versions of the read, write, and verify
265 + * buffer functions.
268 +tmio_nand_write_buf (struct mtd_info *mtd, const u_char *buf, int len)
270 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
271 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
273 + iowrite16_rep (&fcr->u16, buf, len >> 1);
276 +static void tmio_nand_read_buf (struct mtd_info *mtd, u_char *buf, int len)
278 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
279 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
281 + ioread16_rep (&fcr->u16, buf, len >> 1);
285 +tmio_nand_verify_buf (struct mtd_info *mtd, const u_char *buf, int len)
287 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
288 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
289 + u16* p = (u16*) buf;
291 + for (len >>= 1; len; len--)
292 + if (*(p++) != ioread16 (&fcr->u16))
297 +static void tmio_nand_enable_hwecc (struct mtd_info* mtd, int mode)
299 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
300 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
302 + iowrite8 (FCR_MODE_HWECC_RESET, &fcr->mode);
303 + ioread8 (&fcr->u8); /* dummy read */
304 + iowrite8 (FCR_MODE_HWECC_CALC, &fcr->mode);
307 +static int tmio_nand_calculate_ecc (struct mtd_info* mtd, const u_char* dat,
310 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
311 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
314 + iowrite8 (FCR_MODE_HWECC_RESULT, &fcr->mode);
316 + ecc = ioread16 (&fcr->u16);
317 + ecc_code[1] = ecc; // 000-255 LP7-0
318 + ecc_code[0] = ecc >> 8; // 000-255 LP15-8
319 + ecc = ioread16 (&fcr->u16);
320 + ecc_code[2] = ecc; // 000-255 CP5-0,11b
321 + ecc_code[4] = ecc >> 8; // 256-511 LP7-0
322 + ecc = ioread16 (&fcr->u16);
323 + ecc_code[3] = ecc; // 256-511 LP15-8
324 + ecc_code[5] = ecc >> 8; // 256-511 CP5-0,11b
326 + iowrite8 (FCR_MODE_DATA, &fcr->mode);
330 +static void tmio_hw_init (struct device *dev, struct tmio_nand *tmio)
332 + struct resource* nfcr = tmio_resource_control (dev);
333 + struct tmio_device* tdev = dev_to_tdev (dev);
334 + struct tmio_nfhccr __iomem * ccr = tmio->ccr;
335 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
336 + unsigned long base;
338 + /* (89h) SMD Buffer ON By TC6393XB SystemConfig gpibfc1 */
339 + tdev->ops->clock (dev, 1);
340 + tdev->ops->function (dev, 1);
342 + /* (4Ch) CLKRUN Enable 1st spcrunc */
343 + iowrite8 (0x81, &ccr->icc);
345 + /* (10h)BaseAddress 0x1000 spba.spba2 */
346 + base = nfcr->start - tdev->iomem->start;
347 + iowrite16 (base, ccr->base + 0);
348 + iowrite16 (base >> 16, ccr->base + 1);
350 + /* (04h)Command Register I/O spcmd */
351 + iowrite8 (0x02, &ccr->command);
353 + /* (62h) Power Supply Control ssmpwc */
354 + /* HardPowerOFF - SuspendOFF - PowerSupplyWait_4MS */
355 + iowrite8 (0x02, &ccr->nfpsc);
357 + /* (63h) Detect Control ssmdtc */
358 + iowrite8 (0x02, &ccr->nfdc);
360 + /* Interrupt status register clear sintst */
361 + iowrite8 (0x0f, &fcr->isr);
363 + /* After power supply, Media are reset smode */
364 + iowrite8 (FCR_MODE_POWER_ON, &fcr->mode);
365 + iowrite8 (FCR_MODE_COMMAND, &fcr->mode);
366 + iowrite8 (NAND_CMD_RESET, &fcr->u8);
368 + /* Standby Mode smode */
369 + iowrite8 (FCR_MODE_STANDBY, &fcr->mode);
374 +static void tmio_hw_stop (struct device *dev, struct tmio_nand *tmio)
376 + struct tmio_device* tdev = dev_to_tdev (dev);
377 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
379 + iowrite8 (FCR_MODE_POWER_OFF, &fcr->mode);
380 + tdev->ops->function (dev, 0);
381 + tdev->ops->clock (dev, 0);
384 +/*--------------------------------------------------------------------------*/
386 +#ifdef CONFIG_MTD_PARTITIONS
387 +static const char *part_probes[] = { "cmdlinepart", NULL };
390 +static int tmio_probe (struct device *dev)
392 + struct tmio_device* tdev = dev_to_tdev (dev);
393 + struct tmio_nand_platform_data* tnpd = dev->platform_data;
394 + struct resource* ccr = tmio_resource_config (dev);
395 + struct resource* fcr = tmio_resource_control (dev);
396 + struct resource* irq = tmio_resource_irq (dev);
397 + struct tmio_nand* tmio;
398 + struct mtd_info* mtd;
399 + struct nand_chip* this;
400 + struct mtd_partition* parts;
407 + retval = request_resource (tdev->iomem, ccr);
409 + goto err_request_ccr;
411 + retval = request_resource (tdev->iomem, fcr);
413 + goto err_request_fcr;
415 + tmio = kzalloc (sizeof *tmio, GFP_KERNEL);
421 + dev_set_drvdata (dev, tmio);
423 + this = &tmio->chip;
425 + mtd->name = TMIO_NAME_NAND;
427 + tmio->ccr = ioremap (ccr->start, ccr->end - ccr->start + 1);
430 + goto err_iomap_ccr;
433 + tmio->fcr = ioremap (fcr->start, fcr->end - fcr->start + 1);
436 + goto err_iomap_fcr;
439 + tmio_hw_init (dev, tmio);
441 + /* Set address of NAND IO lines */
442 + this->IO_ADDR_R = tmio->fcr;
443 + this->IO_ADDR_W = tmio->fcr;
445 + /* Set address of hardware control function */
446 + this->cmd_ctrl = tmio_nand_hwcontrol;
447 + this->dev_ready = tmio_nand_dev_ready;
448 + this->read_byte = tmio_nand_read_byte;
449 + this->write_buf = tmio_nand_write_buf;
450 + this->read_buf = tmio_nand_read_buf;
451 + this->verify_buf = tmio_nand_verify_buf;
453 + /* set eccmode using hardware ECC */
454 + this->ecc.mode = NAND_ECC_HW;
455 + this->ecc.size = 512;
456 + this->ecc.bytes = 6;
457 + this->ecc.hwctl = tmio_nand_enable_hwecc;
458 + this->ecc.calculate = tmio_nand_calculate_ecc;
459 + this->ecc.correct = nand_correct_data;
460 + this->badblock_pattern = tnpd->badblock_pattern;
462 + /* 15 us command delay time */
463 + this->chip_delay = 15;
466 + retval = request_irq (irq->start, &tmio_irq,
467 + SA_INTERRUPT, irq->name, tmio);
469 + tmio->irq = irq->start;
470 + this->waitfunc = tmio_nand_wait;
472 + mtd_warn (mtd, "request_irq error %d\n", retval);
475 + /* Scan to find existence of the device */
476 + if (nand_scan (mtd, 1)) {
481 + /* Register the partitions */
482 +#ifdef CONFIG_MTD_PARTITIONS
483 + nbparts = parse_mtd_partitions (mtd, part_probes, &parts, 0);
485 + if (nbparts <= 0) {
486 + parts = tnpd->partition;
487 + nbparts = tnpd->num_partitions;
490 + add_mtd_partitions (mtd, parts, nbparts);
495 + free_irq (tmio->irq, tmio);
496 + tmio_hw_stop (dev, tmio);
497 + iounmap (tmio->fcr);
499 + iounmap (tmio->ccr);
503 + release_resource (fcr);
505 + release_resource (ccr);
510 +static int tmio_remove (struct device *dev)
512 + struct tmio_nand* tmio = dev_get_drvdata (dev);
514 + nand_release (&tmio->mtd);
516 + free_irq (tmio->irq, tmio);
517 + tmio_hw_stop (dev, tmio);
518 + iounmap (tmio->fcr);
519 + iounmap (tmio->ccr);
521 + release_resource (tmio_resource_control (dev));
522 + release_resource (tmio_resource_config (dev));
527 +static int tmio_suspend (struct device *dev, pm_message_t state)
529 + tmio_hw_stop (dev, dev_get_drvdata (dev));
533 +static int tmio_resume (struct device *dev)
535 + tmio_hw_init (dev, dev_get_drvdata (dev));
540 +static struct device_driver tmio_driver = {
541 + .name = TMIO_NAME_NAND,
542 + .bus = &tmio_bus_type,
543 + .probe = tmio_probe,
544 + .remove = tmio_remove,
546 + .suspend = tmio_suspend,
547 + .resume = tmio_resume,
551 +static int __init tmio_init (void) {
552 + return driver_register (&tmio_driver);
555 +static void __exit tmio_exit (void) {
556 + driver_unregister (&tmio_driver);
559 +module_init (tmio_init);
560 +module_exit (tmio_exit);
562 +MODULE_LICENSE ("GPL");
563 +MODULE_AUTHOR ("Dirk Opfer, Chris Humbert");
564 +MODULE_DESCRIPTION ("NAND flash driver on Toshiba Mobile IO controller");
565 Index: git/drivers/mtd/nand/Kconfig
566 ===================================================================
567 --- git.orig/drivers/mtd/nand/Kconfig 2006-10-31 16:09:03.000000000 +0000
568 +++ git/drivers/mtd/nand/Kconfig 2006-11-07 22:13:09.000000000 +0000
569 @@ -63,6 +63,13 @@ config MTD_NAND_AMS_DELTA
571 Support for NAND flash on Amstrad E3 (Delta).
573 +config MTD_NAND_TMIO
574 + tristate "NAND Flash device on Toshiba Mobile IO Controller"
575 + depends on MTD_NAND && TOSHIBA_TC6393XB
577 + Support for NAND flash connected to a Toshiba Mobile IO
578 + Controller in some PDAs, including the Sharp SL6000x.
581 tristate "NAND Flash device on TOTO board"
582 depends on ARCH_OMAP && MTD_NAND && BROKEN
583 Index: git/drivers/mtd/nand/Makefile
584 ===================================================================
585 --- git.orig/drivers/mtd/nand/Makefile 2006-10-31 16:09:03.000000000 +0000
586 +++ git/drivers/mtd/nand/Makefile 2006-11-07 22:13:09.000000000 +0000
587 @@ -22,5 +22,6 @@ obj-$(CONFIG_MTD_NAND_TS7250) += ts7250
588 obj-$(CONFIG_MTD_NAND_NANDSIM) += nandsim.o
589 obj-$(CONFIG_MTD_NAND_CS553X) += cs553x_nand.o
590 obj-$(CONFIG_MTD_NAND_NDFC) += ndfc.o
591 +obj-$(CONFIG_MTD_NAND_TMIO) += tmio.o
593 nand-objs = nand_base.o nand_bbt.o