1 Index: linux-2.6.18/drivers/mtd/nand/tmio.c
2 ===================================================================
3 --- /dev/null 1970-01-01 00:00:00.000000000 +0000
4 +++ linux-2.6.18/drivers/mtd/nand/tmio.c 2006-09-20 17:01:43.000000000 +0200
7 + * A device driver for NAND flash connected to a Toshiba Mobile IO
8 + * controller. This is known to work with the following variants:
9 + * TC6393XB revision 3
11 + * Maintainer: Chris Humbert <mahadri+mtd@drigon.com>
13 + * Copyright (C) 2005 Chris Humbert
14 + * Copyright (C) 2005 Dirk Opfer
15 + * Copyright (C) 2004 SHARP
16 + * Copyright (C) 2002 Lineo Japan, Inc.
17 + * Copyright (C) Ian Molton and Sebastian Carlier
19 + * Based on Sharp's NAND driver, sharp_sl_tc6393.c
21 + * This program is free software; you can redistribute it and/or modify
22 + * it under the terms of the GNU General Public License version 2 as
23 + * published by the Free Software Foundation.
26 +#include <linux/module.h>
27 +#include <linux/types.h>
28 +#include <linux/delay.h>
29 +#include <linux/wait.h>
30 +#include <linux/ioport.h>
31 +#include <linux/mtd/mtd.h>
32 +#include <linux/mtd/nand.h>
33 +#include <linux/mtd/nand_ecc.h>
34 +#include <linux/mtd/partitions.h>
36 +#include <asm/hardware/tmio.h>
38 +#include <linux/interrupt.h>
40 +#define mtd_printk(level, mtd, format, arg...) \
41 + printk (level "%s: " format, mtd->name, ## arg)
42 +#define mtd_warn(mtd, format, arg...) \
43 + mtd_printk (KERN_WARNING, mtd, format, ## arg)
45 +/*--------------------------------------------------------------------------*/
47 +/* tmio_nfcr.mode Register Command List */
48 +#define FCR_MODE_DATA 0x94 // Data Data_Mode
49 +#define FCR_MODE_COMMAND 0x95 // Data Command_Mode
50 +#define FCR_MODE_ADDRESS 0x96 // Data Address_Mode
52 +#define FCR_MODE_HWECC_CALC 0xB4 // HW-ECC Data
53 +#define FCR_MODE_HWECC_RESULT 0xD4 // HW-ECC Calculation Result Read_Mode
54 +#define FCR_MODE_HWECC_RESET 0xF4 // HW-ECC Reset
56 +#define FCR_MODE_POWER_ON 0x0C // Power Supply ON to SSFDC card
57 +#define FCR_MODE_POWER_OFF 0x08 // Power Supply OFF to SSFDC card
59 +#define FCR_MODE_LED_OFF 0x00 // LED OFF
60 +#define FCR_MODE_LED_ON 0x04 // LED ON
62 +#define FCR_MODE_EJECT_ON 0x68 // Ejection Demand from Penguin is Advanced
63 +#define FCR_MODE_EJECT_OFF 0x08 // Ejection Demand from Penguin is Not Advanced
65 +#define FCR_MODE_LOCK 0x6C // Operates By Lock_Mode. Ejection Switch is Invalid
66 +#define FCR_MODE_UNLOCK 0x0C // Operates By UnLock_Mode.Ejection Switch is Effective
68 +#define FCR_MODE_CONTROLLER_ID 0x40 // Controller ID Read
69 +#define FCR_MODE_STANDBY 0x00 // SSFDC card Changes Standby State
71 +#define FCR_MODE_WE 0x80
72 +#define FCR_MODE_ECC1 0x40
73 +#define FCR_MODE_ECC0 0x20
74 +#define FCR_MODE_CE 0x10
75 +#define FCR_MODE_PCNT1 0x08
76 +#define FCR_MODE_PCNT0 0x04
77 +#define FCR_MODE_ALE 0x02
78 +#define FCR_MODE_CLE 0x01
80 +#define FCR_STATUS_BUSY 0x80
83 + * NAND Flash Host Controller Configuration Register
87 + u16 command; /* 0x04 Command */
89 + u16 base[2]; /* 0x10 NAND Flash Control Reg Base Addr*/
91 + u8 intp; /* 0x3d Interrupt Pin */
93 + u8 inte; /* 0x48 Interrupt Enable */
95 + u8 ec; /* 0x4a Event Control */
97 + u8 icc; /* 0x4c Internal Clock Control */
99 + u8 eccc; /* 0x5b ECC Control */
101 + u8 nftc; /* 0x60 NAND Flash Transaction Control */
102 + u8 nfm; /* 0x61 NAND Flash Monitor */
103 + u8 nfpsc; /* 0x62 NAND Flash Power Supply Control */
104 + u8 nfdc; /* 0x63 NAND Flash Detect Control */
106 +} __attribute__ ((packed));
109 + * NAND Flash Control Register
113 + u8 u8; /* 0x00 Data Register */
116 +} __attribute__ ((packed));
117 + u8 mode; /* 0x04 Mode Register */
118 + u8 status; /* 0x05 Status Register */
119 + u8 isr; /* 0x06 Interrupt Status Register */
120 + u8 imr; /* 0x07 Interrupt Mask Register */
121 +} __attribute__ ((packed));
124 + struct mtd_info mtd;
125 + struct nand_chip chip;
127 + struct tmio_nfhccr __iomem * ccr;
128 + struct tmio_nfcr __iomem * fcr;
132 + /* for tmio_nand_read_byte */
134 + unsigned read_good:1;
137 +#define mtd_to_tmio(m) container_of(m, struct tmio_nand, mtd)
139 +/*--------------------------------------------------------------------------*/
141 +static void tmio_nand_hwcontrol (struct mtd_info *mtd, int cmd)
143 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
144 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
145 + u8 mode = ioread8 (&fcr->mode);
148 + case NAND_CTL_SETCLE: mode |= FCR_MODE_CLE; break;
149 + case NAND_CTL_CLRCLE: mode &= ~FCR_MODE_CLE; break;
151 + case NAND_CTL_SETALE: mode |= FCR_MODE_ALE; break;
152 + case NAND_CTL_CLRALE: mode &= ~FCR_MODE_ALE; break;
154 + case NAND_CTL_SETNCE: mode = FCR_MODE_DATA; break;
155 + case NAND_CTL_CLRNCE: mode = FCR_MODE_STANDBY; break;
158 + iowrite8 (mode, &fcr->mode);
159 + tmio->read_good = 0;
162 +static int tmio_nand_dev_ready (struct mtd_info* mtd)
164 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
165 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
167 + return !(ioread8 (&fcr->status) & FCR_STATUS_BUSY);
170 +static irqreturn_t tmio_irq (int irq, void *__tmio, struct pt_regs * r)
172 + struct tmio_nand* tmio = __tmio;
173 + struct nand_chip* this = &tmio->chip;
174 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
176 + /* disable RDYREQ interrupt */
177 + iowrite8 (0x00, &fcr->imr);
179 + if (unlikely (!waitqueue_active (&this->wq)))
180 + printk (KERN_WARNING TMIO_NAME_NAND ": spurious interrupt\n");
182 + wake_up (&this->wq);
183 + return IRQ_HANDLED;
187 + * The TMIO core has a RDYREQ interrupt on the posedge of #SMRB.
188 + * This interrupt is normally disabled, but for long operations like
189 + * erase and write, we enable it to wake us up. The irq handler
190 + * disables the interrupt.
193 +tmio_nand_wait (struct mtd_info *mtd, struct nand_chip *this, int state)
195 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
196 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
199 + /* enable RDYREQ interrupt */
200 + iowrite8 (0x0f, &fcr->isr);
201 + iowrite8 (0x81, &fcr->imr);
203 + timeout = wait_event_timeout (this->wq,
204 + this->state != state || tmio_nand_dev_ready (mtd),
205 + msecs_to_jiffies (state == FL_ERASING ? 400 : 20));
207 + if (this->state != state)
210 + if (unlikely (!tmio_nand_dev_ready (mtd))) {
211 + iowrite8 (0x00, &fcr->imr);
212 + mtd_warn (mtd, "still busy with %s after %d ms\n",
213 + state == FL_ERASING ? "erase" : "program",
214 + state == FL_ERASING ? 400 : 20);
216 + } else if (unlikely (!timeout)) {
217 + iowrite8 (0x00, &fcr->imr);
218 + mtd_warn (mtd, "timeout waiting for interrupt\n");
221 + this->cmdfunc (mtd, NAND_CMD_STATUS, -1, -1);
222 + return this->read_byte (mtd);
226 + * The TMIO controller combines two 8-bit data bytes into one 16-bit
227 + * word. This function separates them so nand_base.c works as expected,
228 + * especially its NAND_CMD_READID routines.
230 + * To prevent stale data from being read, tmio_nand_hwcontrol() clears
233 +static u_char tmio_nand_read_byte (struct mtd_info *mtd)
235 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
236 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
239 + if (tmio->read_good--)
242 + data = ioread16 (&fcr->u16);
243 + tmio->read = data >> 8;
248 + * The TMIO controller converts an 8-bit NAND interface to a 16-bit
249 + * bus interface, so all data reads and writes must be 16-bit wide.
250 + * Thus, we implement 16-bit versions of the read, write, and verify
251 + * buffer functions.
254 +tmio_nand_write_buf (struct mtd_info *mtd, const u_char *buf, int len)
256 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
257 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
259 + iowrite16_rep (&fcr->u16, buf, len >> 1);
262 +static void tmio_nand_read_buf (struct mtd_info *mtd, u_char *buf, int len)
264 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
265 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
267 + ioread16_rep (&fcr->u16, buf, len >> 1);
271 +tmio_nand_verify_buf (struct mtd_info *mtd, const u_char *buf, int len)
273 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
274 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
275 + u16* p = (u16*) buf;
277 + for (len >>= 1; len; len--)
278 + if (*(p++) != ioread16 (&fcr->u16))
283 +static void tmio_nand_enable_hwecc (struct mtd_info* mtd, int mode)
285 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
286 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
288 + iowrite8 (FCR_MODE_HWECC_RESET, &fcr->mode);
289 + ioread8 (&fcr->u8); /* dummy read */
290 + iowrite8 (FCR_MODE_HWECC_CALC, &fcr->mode);
293 +static int tmio_nand_calculate_ecc (struct mtd_info* mtd, const u_char* dat,
296 + struct tmio_nand* tmio = mtd_to_tmio (mtd);
297 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
300 + iowrite8 (FCR_MODE_HWECC_RESULT, &fcr->mode);
302 + ecc = ioread16 (&fcr->u16);
303 + ecc_code[1] = ecc; // 000-255 LP7-0
304 + ecc_code[0] = ecc >> 8; // 000-255 LP15-8
305 + ecc = ioread16 (&fcr->u16);
306 + ecc_code[2] = ecc; // 000-255 CP5-0,11b
307 + ecc_code[4] = ecc >> 8; // 256-511 LP7-0
308 + ecc = ioread16 (&fcr->u16);
309 + ecc_code[3] = ecc; // 256-511 LP15-8
310 + ecc_code[5] = ecc >> 8; // 256-511 CP5-0,11b
312 + iowrite8 (FCR_MODE_DATA, &fcr->mode);
316 +static void tmio_hw_init (struct device *dev, struct tmio_nand *tmio)
318 + struct resource* nfcr = tmio_resource_control (dev);
319 + struct tmio_device* tdev = dev_to_tdev (dev);
320 + struct tmio_nfhccr __iomem * ccr = tmio->ccr;
321 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
322 + unsigned long base;
324 + /* (89h) SMD Buffer ON By TC6393XB SystemConfig gpibfc1 */
325 + tdev->ops->clock (dev, 1);
326 + tdev->ops->function (dev, 1);
328 + /* (4Ch) CLKRUN Enable 1st spcrunc */
329 + iowrite8 (0x81, &ccr->icc);
331 + /* (10h)BaseAddress 0x1000 spba.spba2 */
332 + base = nfcr->start - tdev->iomem->start;
333 + iowrite16 (base, ccr->base + 0);
334 + iowrite16 (base >> 16, ccr->base + 1);
336 + /* (04h)Command Register I/O spcmd */
337 + iowrite8 (0x02, &ccr->command);
339 + /* (62h) Power Supply Control ssmpwc */
340 + /* HardPowerOFF - SuspendOFF - PowerSupplyWait_4MS */
341 + iowrite8 (0x02, &ccr->nfpsc);
343 + /* (63h) Detect Control ssmdtc */
344 + iowrite8 (0x02, &ccr->nfdc);
346 + /* Interrupt status register clear sintst */
347 + iowrite8 (0x0f, &fcr->isr);
349 + /* After power supply, Media are reset smode */
350 + iowrite8 (FCR_MODE_POWER_ON, &fcr->mode);
351 + iowrite8 (FCR_MODE_COMMAND, &fcr->mode);
352 + iowrite8 (NAND_CMD_RESET, &fcr->u8);
354 + /* Standby Mode smode */
355 + iowrite8 (FCR_MODE_STANDBY, &fcr->mode);
360 +static void tmio_hw_stop (struct device *dev, struct tmio_nand *tmio)
362 + struct tmio_device* tdev = dev_to_tdev (dev);
363 + struct tmio_nfcr __iomem * fcr = tmio->fcr;
365 + iowrite8 (FCR_MODE_POWER_OFF, &fcr->mode);
366 + tdev->ops->function (dev, 0);
367 + tdev->ops->clock (dev, 0);
370 +/*--------------------------------------------------------------------------*/
372 +#ifdef CONFIG_MTD_PARTITIONS
373 +static const char *part_probes[] = { "cmdlinepart", NULL };
376 +static int tmio_probe (struct device *dev)
378 + struct tmio_device* tdev = dev_to_tdev (dev);
379 + struct tmio_nand_platform_data* tnpd = dev->platform_data;
380 + struct resource* ccr = tmio_resource_config (dev);
381 + struct resource* fcr = tmio_resource_control (dev);
382 + struct resource* irq = tmio_resource_irq (dev);
383 + struct tmio_nand* tmio;
384 + struct mtd_info* mtd;
385 + struct nand_chip* this;
386 + struct mtd_partition* parts;
393 + retval = request_resource (tdev->iomem, ccr);
395 + goto err_request_ccr;
397 + retval = request_resource (tdev->iomem, fcr);
399 + goto err_request_fcr;
401 + tmio = kzalloc (sizeof *tmio, GFP_KERNEL);
407 + dev_set_drvdata (dev, tmio);
409 + this = &tmio->chip;
411 + mtd->name = TMIO_NAME_NAND;
413 + tmio->ccr = ioremap (ccr->start, ccr->end - ccr->start + 1);
416 + goto err_iomap_ccr;
419 + tmio->fcr = ioremap (fcr->start, fcr->end - fcr->start + 1);
422 + goto err_iomap_fcr;
425 + tmio_hw_init (dev, tmio);
427 + /* Set address of NAND IO lines */
428 + this->IO_ADDR_R = tmio->fcr;
429 + this->IO_ADDR_W = tmio->fcr;
431 + /* Set address of hardware control function */
432 + this->hwcontrol = tmio_nand_hwcontrol;
433 + this->dev_ready = tmio_nand_dev_ready;
434 + this->read_byte = tmio_nand_read_byte;
435 + this->write_buf = tmio_nand_write_buf;
436 + this->read_buf = tmio_nand_read_buf;
437 + this->verify_buf = tmio_nand_verify_buf;
439 + /* set eccmode using hardware ECC */
440 + this->eccmode = NAND_ECC_HW6_512;
441 + this->enable_hwecc = tmio_nand_enable_hwecc;
442 + this->calculate_ecc = tmio_nand_calculate_ecc;
443 + this->correct_data = nand_correct_data;
444 + this->badblock_pattern = tnpd->badblock_pattern;
446 + /* 15 us command delay time */
447 + this->chip_delay = 15;
450 + retval = request_irq (irq->start, &tmio_irq,
451 + SA_INTERRUPT, irq->name, tmio);
453 + tmio->irq = irq->start;
454 + this->waitfunc = tmio_nand_wait;
456 + mtd_warn (mtd, "request_irq error %d\n", retval);
459 + /* Scan to find existence of the device */
460 + if (nand_scan (mtd, 1)) {
465 + /* Register the partitions */
466 +#ifdef CONFIG_MTD_PARTITIONS
467 + nbparts = parse_mtd_partitions (mtd, part_probes, &parts, 0);
469 + if (nbparts <= 0) {
470 + parts = tnpd->partition;
471 + nbparts = tnpd->num_partitions;
474 + add_mtd_partitions (mtd, parts, nbparts);
479 + free_irq (tmio->irq, tmio);
480 + tmio_hw_stop (dev, tmio);
481 + iounmap (tmio->fcr);
483 + iounmap (tmio->ccr);
487 + release_resource (fcr);
489 + release_resource (ccr);
494 +static int tmio_remove (struct device *dev)
496 + struct tmio_nand* tmio = dev_get_drvdata (dev);
498 + nand_release (&tmio->mtd);
500 + free_irq (tmio->irq, tmio);
501 + tmio_hw_stop (dev, tmio);
502 + iounmap (tmio->fcr);
503 + iounmap (tmio->ccr);
505 + release_resource (tmio_resource_control (dev));
506 + release_resource (tmio_resource_config (dev));
511 +static int tmio_suspend (struct device *dev, pm_message_t state)
513 + tmio_hw_stop (dev, dev_get_drvdata (dev));
517 +static int tmio_resume (struct device *dev)
519 + tmio_hw_init (dev, dev_get_drvdata (dev));
524 +static struct device_driver tmio_driver = {
525 + .name = TMIO_NAME_NAND,
526 + .bus = &tmio_bus_type,
527 + .probe = tmio_probe,
528 + .remove = tmio_remove,
530 + .suspend = tmio_suspend,
531 + .resume = tmio_resume,
535 +static int __init tmio_init (void) {
536 + return driver_register (&tmio_driver);
539 +static void __exit tmio_exit (void) {
540 + driver_unregister (&tmio_driver);
543 +module_init (tmio_init);
544 +module_exit (tmio_exit);
546 +MODULE_LICENSE ("GPL");
547 +MODULE_AUTHOR ("Dirk Opfer, Chris Humbert");
548 +MODULE_DESCRIPTION ("NAND flash driver on Toshiba Mobile IO controller");
549 Index: linux-2.6.18/drivers/mtd/nand/Kconfig
550 ===================================================================
551 --- linux-2.6.18.orig/drivers/mtd/nand/Kconfig 2006-09-20 05:42:06.000000000 +0200
552 +++ linux-2.6.18/drivers/mtd/nand/Kconfig 2006-09-20 17:01:43.000000000 +0200
555 Support for NAND flash on Amstrad E3 (Delta).
557 +config MTD_NAND_TMIO
558 + tristate "NAND Flash device on Toshiba Mobile IO Controller"
559 + depends on MTD_NAND && TOSHIBA_TC6393XB
561 + Support for NAND flash connected to a Toshiba Mobile IO
562 + Controller in some PDAs, including the Sharp SL6000x.
565 tristate "NAND Flash device on TOTO board"
566 depends on ARCH_OMAP && MTD_NAND && BROKEN
567 Index: linux-2.6.18/drivers/mtd/nand/Makefile
568 ===================================================================
569 --- linux-2.6.18.orig/drivers/mtd/nand/Makefile 2006-09-20 05:42:06.000000000 +0200
570 +++ linux-2.6.18/drivers/mtd/nand/Makefile 2006-09-20 17:03:43.000000000 +0200
572 obj-$(CONFIG_MTD_NAND_NANDSIM) += nandsim.o
573 obj-$(CONFIG_MTD_NAND_CS553X) += cs553x_nand.o
574 obj-$(CONFIG_MTD_NAND_NDFC) += ndfc.o
575 +obj-$(CONFIG_MTD_NAND_TMIO) += tmio.o
577 nand-objs = nand_base.o nand_bbt.o