]> git.ipfire.org Git - people/ms/u-boot.git/blame - drivers/mtd/nand/diskonchip.c
Update MTD to that of Linux 2.6.22.1
[people/ms/u-boot.git] / drivers / mtd / nand / diskonchip.c
CommitLineData
ac7eb8a3 1/*
932394ac
WD
2 * drivers/mtd/nand/diskonchip.c
3 *
4 * (C) 2003 Red Hat, Inc.
5 * (C) 2004 Dan Brown <dan_brown@ieee.org>
6 * (C) 2004 Kalev Lember <kalev@smartlink.ee>
7 *
8 * Author: David Woodhouse <dwmw2@infradead.org>
9 * Additional Diskonchip 2000 and Millennium support by Dan Brown <dan_brown@ieee.org>
10 * Diskonchip Millennium Plus support by Kalev Lember <kalev@smartlink.ee>
ac7eb8a3 11 *
932394ac 12 * Error correction code lifted from the old docecc code
ac7eb8a3 13 * Author: Fabrice Bellard (fabrice.bellard@netgem.com)
932394ac
WD
14 * Copyright (C) 2000 Netgem S.A.
15 * converted to the generic Reed-Solomon library by Thomas Gleixner <tglx@linutronix.de>
ac7eb8a3 16 *
932394ac
WD
17 * Interface to generic NAND code for M-Systems DiskOnChip devices
18 *
cfa460ad 19 * $Id: diskonchip.c,v 1.55 2005/11/07 11:14:30 gleixner Exp $
932394ac
WD
20 */
21
038ccac5 22#include <common.h>
addb2e16 23
6db39708 24#if !defined(CFG_NAND_LEGACY)
addb2e16 25
932394ac
WD
26#include <linux/kernel.h>
27#include <linux/init.h>
28#include <linux/sched.h>
29#include <linux/delay.h>
30#include <linux/rslib.h>
31#include <linux/moduleparam.h>
32#include <asm/io.h>
33
34#include <linux/mtd/mtd.h>
35#include <linux/mtd/nand.h>
36#include <linux/mtd/doc2000.h>
37#include <linux/mtd/compatmac.h>
38#include <linux/mtd/partitions.h>
39#include <linux/mtd/inftl.h>
40
41/* Where to look for the devices? */
cfa460ad
WJ
42#ifndef CONFIG_MTD_NAND_DISKONCHIP_PROBE_ADDRESS
43#define CONFIG_MTD_NAND_DISKONCHIP_PROBE_ADDRESS 0
932394ac
WD
44#endif
45
46static unsigned long __initdata doc_locations[] = {
47#if defined (__alpha__) || defined(__i386__) || defined(__x86_64__)
cfa460ad 48#ifdef CONFIG_MTD_NAND_DISKONCHIP_PROBE_HIGH
ac7eb8a3 49 0xfffc8000, 0xfffca000, 0xfffcc000, 0xfffce000,
932394ac 50 0xfffd0000, 0xfffd2000, 0xfffd4000, 0xfffd6000,
ac7eb8a3
WD
51 0xfffd8000, 0xfffda000, 0xfffdc000, 0xfffde000,
52 0xfffe0000, 0xfffe2000, 0xfffe4000, 0xfffe6000,
932394ac
WD
53 0xfffe8000, 0xfffea000, 0xfffec000, 0xfffee000,
54#else /* CONFIG_MTD_DOCPROBE_HIGH */
ac7eb8a3 55 0xc8000, 0xca000, 0xcc000, 0xce000,
932394ac 56 0xd0000, 0xd2000, 0xd4000, 0xd6000,
ac7eb8a3
WD
57 0xd8000, 0xda000, 0xdc000, 0xde000,
58 0xe0000, 0xe2000, 0xe4000, 0xe6000,
932394ac
WD
59 0xe8000, 0xea000, 0xec000, 0xee000,
60#endif /* CONFIG_MTD_DOCPROBE_HIGH */
61#elif defined(__PPC__)
62 0xe4000000,
63#elif defined(CONFIG_MOMENCO_OCELOT)
64 0x2f000000,
ac7eb8a3 65 0xff000000,
932394ac 66#elif defined(CONFIG_MOMENCO_OCELOT_G) || defined (CONFIG_MOMENCO_OCELOT_C)
ac7eb8a3 67 0xff000000,
cfa460ad 68#else
932394ac
WD
69#warning Unknown architecture for DiskOnChip. No default probe locations defined
70#endif
71 0xffffffff };
72
73static struct mtd_info *doclist = NULL;
74
75struct doc_priv {
76 void __iomem *virtadr;
77 unsigned long physadr;
78 u_char ChipID;
79 u_char CDSNControl;
cfa460ad 80 int chips_per_floor; /* The number of chips detected on each floor */
932394ac
WD
81 int curfloor;
82 int curchip;
83 int mh0_page;
84 int mh1_page;
85 struct mtd_info *nextdoc;
86};
87
932394ac
WD
88/* This is the syndrome computed by the HW ecc generator upon reading an empty
89 page, one with all 0xff for data and stored ecc code. */
90static u_char empty_read_syndrome[6] = { 0x26, 0xff, 0x6d, 0x47, 0x73, 0x7a };
cfa460ad 91
932394ac
WD
92/* This is the ecc value computed by the HW ecc generator upon writing an empty
93 page, one with all 0xff for data. */
94static u_char empty_write_ecc[6] = { 0x4b, 0x00, 0xe2, 0x0e, 0x93, 0xf7 };
95
96#define INFTL_BBT_RESERVED_BLOCKS 4
97
98#define DoC_is_MillenniumPlus(doc) ((doc)->ChipID == DOC_ChipID_DocMilPlus16 || (doc)->ChipID == DOC_ChipID_DocMilPlus32)
99#define DoC_is_Millennium(doc) ((doc)->ChipID == DOC_ChipID_DocMil)
100#define DoC_is_2000(doc) ((doc)->ChipID == DOC_ChipID_Doc2k)
101
cfa460ad
WJ
102static void doc200x_hwcontrol(struct mtd_info *mtd, int cmd,
103 unsigned int bitmask);
932394ac
WD
104static void doc200x_select_chip(struct mtd_info *mtd, int chip);
105
cfa460ad 106static int debug = 0;
932394ac
WD
107module_param(debug, int, 0);
108
cfa460ad 109static int try_dword = 1;
932394ac
WD
110module_param(try_dword, int, 0);
111
cfa460ad 112static int no_ecc_failures = 0;
932394ac
WD
113module_param(no_ecc_failures, int, 0);
114
cfa460ad 115static int no_autopart = 0;
932394ac 116module_param(no_autopart, int, 0);
932394ac 117
cfa460ad
WJ
118static int show_firmware_partition = 0;
119module_param(show_firmware_partition, int, 0);
120
121#ifdef CONFIG_MTD_NAND_DISKONCHIP_BBTWRITE
122static int inftl_bbt_write = 1;
932394ac 123#else
cfa460ad 124static int inftl_bbt_write = 0;
932394ac
WD
125#endif
126module_param(inftl_bbt_write, int, 0);
127
cfa460ad 128static unsigned long doc_config_location = CONFIG_MTD_NAND_DISKONCHIP_PROBE_ADDRESS;
932394ac
WD
129module_param(doc_config_location, ulong, 0);
130MODULE_PARM_DESC(doc_config_location, "Physical memory address at which to probe for DiskOnChip");
131
932394ac
WD
132/* Sector size for HW ECC */
133#define SECTOR_SIZE 512
134/* The sector bytes are packed into NB_DATA 10 bit words */
135#define NB_DATA (((SECTOR_SIZE + 1) * 8 + 6) / 10)
136/* Number of roots */
137#define NROOTS 4
138/* First consective root */
139#define FCR 510
140/* Number of symbols */
141#define NN 1023
142
143/* the Reed Solomon control structure */
144static struct rs_control *rs_decoder;
145
ac7eb8a3 146/*
932394ac
WD
147 * The HW decoder in the DoC ASIC's provides us a error syndrome,
148 * which we must convert to a standard syndrom usable by the generic
149 * Reed-Solomon library code.
150 *
151 * Fabrice Bellard figured this out in the old docecc code. I added
152 * some comments, improved a minor bit and converted it to make use
153 * of the generic Reed-Solomon libary. tglx
154 */
cfa460ad 155static int doc_ecc_decode(struct rs_control *rs, uint8_t *data, uint8_t *ecc)
932394ac
WD
156{
157 int i, j, nerr, errpos[8];
158 uint8_t parity;
159 uint16_t ds[4], s[5], tmp, errval[8], syn[4];
160
161 /* Convert the ecc bytes into words */
162 ds[0] = ((ecc[4] & 0xff) >> 0) | ((ecc[5] & 0x03) << 8);
163 ds[1] = ((ecc[5] & 0xfc) >> 2) | ((ecc[2] & 0x0f) << 6);
164 ds[2] = ((ecc[2] & 0xf0) >> 4) | ((ecc[3] & 0x3f) << 4);
165 ds[3] = ((ecc[3] & 0xc0) >> 6) | ((ecc[0] & 0xff) << 2);
166 parity = ecc[1];
167
168 /* Initialize the syndrom buffer */
169 for (i = 0; i < NROOTS; i++)
170 s[i] = ds[0];
ac7eb8a3
WD
171 /*
172 * Evaluate
932394ac
WD
173 * s[i] = ds[3]x^3 + ds[2]x^2 + ds[1]x^1 + ds[0]
174 * where x = alpha^(FCR + i)
175 */
cfa460ad
WJ
176 for (j = 1; j < NROOTS; j++) {
177 if (ds[j] == 0)
932394ac
WD
178 continue;
179 tmp = rs->index_of[ds[j]];
cfa460ad 180 for (i = 0; i < NROOTS; i++)
932394ac
WD
181 s[i] ^= rs->alpha_to[rs_modnn(rs, tmp + (FCR + i) * j)];
182 }
183
184 /* Calc s[i] = s[i] / alpha^(v + i) */
185 for (i = 0; i < NROOTS; i++) {
186 if (syn[i])
53677ef1 187 syn[i] = rs_modnn(rs, rs->index_of[s[i]] + (NN - FCR - i));
932394ac
WD
188 }
189 /* Call the decoder library */
190 nerr = decode_rs16(rs, NULL, NULL, 1019, syn, 0, errpos, 0, errval);
191
192 /* Incorrectable errors ? */
193 if (nerr < 0)
194 return nerr;
195
ac7eb8a3 196 /*
932394ac
WD
197 * Correct the errors. The bitpositions are a bit of magic,
198 * but they are given by the design of the de/encoder circuit
199 * in the DoC ASIC's.
200 */
cfa460ad 201 for (i = 0; i < nerr; i++) {
932394ac
WD
202 int index, bitpos, pos = 1015 - errpos[i];
203 uint8_t val;
204 if (pos >= NB_DATA && pos < 1019)
205 continue;
206 if (pos < NB_DATA) {
207 /* extract bit position (MSB first) */
208 pos = 10 * (NB_DATA - 1 - pos) - 6;
209 /* now correct the following 10 bits. At most two bytes
210 can be modified since pos is even */
211 index = (pos >> 3) ^ 1;
212 bitpos = pos & 7;
cfa460ad 213 if ((index >= 0 && index < SECTOR_SIZE) || index == (SECTOR_SIZE + 1)) {
932394ac
WD
214 val = (uint8_t) (errval[i] >> (2 + bitpos));
215 parity ^= val;
216 if (index < SECTOR_SIZE)
217 data[index] ^= val;
218 }
219 index = ((pos >> 3) + 1) ^ 1;
220 bitpos = (bitpos + 10) & 7;
221 if (bitpos == 0)
222 bitpos = 8;
cfa460ad
WJ
223 if ((index >= 0 && index < SECTOR_SIZE) || index == (SECTOR_SIZE + 1)) {
224 val = (uint8_t) (errval[i] << (8 - bitpos));
932394ac
WD
225 parity ^= val;
226 if (index < SECTOR_SIZE)
227 data[index] ^= val;
228 }
229 }
230 }
231 /* If the parity is wrong, no rescue possible */
232 return parity ? -1 : nerr;
233}
234
235static void DoC_Delay(struct doc_priv *doc, unsigned short cycles)
236{
237 volatile char dummy;
238 int i;
ac7eb8a3 239
932394ac
WD
240 for (i = 0; i < cycles; i++) {
241 if (DoC_is_Millennium(doc))
242 dummy = ReadDOC(doc->virtadr, NOP);
243 else if (DoC_is_MillenniumPlus(doc))
244 dummy = ReadDOC(doc->virtadr, Mplus_NOP);
245 else
246 dummy = ReadDOC(doc->virtadr, DOCStatus);
247 }
ac7eb8a3 248
932394ac
WD
249}
250
251#define CDSN_CTRL_FR_B_MASK (CDSN_CTRL_FR_B0 | CDSN_CTRL_FR_B1)
252
253/* DOC_WaitReady: Wait for RDY line to be asserted by the flash chip */
254static int _DoC_WaitReady(struct doc_priv *doc)
255{
ac7eb8a3 256 void __iomem *docptr = doc->virtadr;
932394ac
WD
257 unsigned long timeo = jiffies + (HZ * 10);
258
cfa460ad
WJ
259 if (debug)
260 printk("_DoC_WaitReady...\n");
932394ac
WD
261 /* Out-of-line routine to wait for chip response */
262 if (DoC_is_MillenniumPlus(doc)) {
263 while ((ReadDOC(docptr, Mplus_FlashControl) & CDSN_CTRL_FR_B_MASK) != CDSN_CTRL_FR_B_MASK) {
264 if (time_after(jiffies, timeo)) {
265 printk("_DoC_WaitReady timed out.\n");
266 return -EIO;
267 }
268 udelay(1);
269 cond_resched();
270 }
271 } else {
272 while (!(ReadDOC(docptr, CDSNControl) & CDSN_CTRL_FR_B)) {
273 if (time_after(jiffies, timeo)) {
274 printk("_DoC_WaitReady timed out.\n");
275 return -EIO;
276 }
277 udelay(1);
278 cond_resched();
279 }
280 }
281
282 return 0;
283}
284
285static inline int DoC_WaitReady(struct doc_priv *doc)
286{
ac7eb8a3 287 void __iomem *docptr = doc->virtadr;
932394ac
WD
288 int ret = 0;
289
290 if (DoC_is_MillenniumPlus(doc)) {
291 DoC_Delay(doc, 4);
292
293 if ((ReadDOC(docptr, Mplus_FlashControl) & CDSN_CTRL_FR_B_MASK) != CDSN_CTRL_FR_B_MASK)
294 /* Call the out-of-line routine to wait */
295 ret = _DoC_WaitReady(doc);
296 } else {
297 DoC_Delay(doc, 4);
298
299 if (!(ReadDOC(docptr, CDSNControl) & CDSN_CTRL_FR_B))
300 /* Call the out-of-line routine to wait */
301 ret = _DoC_WaitReady(doc);
302 DoC_Delay(doc, 2);
303 }
304
cfa460ad
WJ
305 if (debug)
306 printk("DoC_WaitReady OK\n");
932394ac
WD
307 return ret;
308}
309
310static void doc2000_write_byte(struct mtd_info *mtd, u_char datum)
311{
312 struct nand_chip *this = mtd->priv;
313 struct doc_priv *doc = this->priv;
ac7eb8a3 314 void __iomem *docptr = doc->virtadr;
932394ac 315
cfa460ad
WJ
316 if (debug)
317 printk("write_byte %02x\n", datum);
932394ac
WD
318 WriteDOC(datum, docptr, CDSNSlowIO);
319 WriteDOC(datum, docptr, 2k_CDSN_IO);
320}
321
322static u_char doc2000_read_byte(struct mtd_info *mtd)
323{
324 struct nand_chip *this = mtd->priv;
325 struct doc_priv *doc = this->priv;
ac7eb8a3 326 void __iomem *docptr = doc->virtadr;
932394ac
WD
327 u_char ret;
328
329 ReadDOC(docptr, CDSNSlowIO);
330 DoC_Delay(doc, 2);
331 ret = ReadDOC(docptr, 2k_CDSN_IO);
cfa460ad
WJ
332 if (debug)
333 printk("read_byte returns %02x\n", ret);
932394ac
WD
334 return ret;
335}
336
cfa460ad 337static void doc2000_writebuf(struct mtd_info *mtd, const u_char *buf, int len)
932394ac
WD
338{
339 struct nand_chip *this = mtd->priv;
340 struct doc_priv *doc = this->priv;
ac7eb8a3 341 void __iomem *docptr = doc->virtadr;
932394ac 342 int i;
cfa460ad
WJ
343 if (debug)
344 printk("writebuf of %d bytes: ", len);
345 for (i = 0; i < len; i++) {
932394ac
WD
346 WriteDOC_(buf[i], docptr, DoC_2k_CDSN_IO + i);
347 if (debug && i < 16)
348 printk("%02x ", buf[i]);
349 }
cfa460ad
WJ
350 if (debug)
351 printk("\n");
932394ac
WD
352}
353
cfa460ad 354static void doc2000_readbuf(struct mtd_info *mtd, u_char *buf, int len)
932394ac
WD
355{
356 struct nand_chip *this = mtd->priv;
357 struct doc_priv *doc = this->priv;
ac7eb8a3 358 void __iomem *docptr = doc->virtadr;
53677ef1 359 int i;
932394ac 360
cfa460ad
WJ
361 if (debug)
362 printk("readbuf of %d bytes: ", len);
932394ac 363
cfa460ad 364 for (i = 0; i < len; i++) {
932394ac
WD
365 buf[i] = ReadDOC(docptr, 2k_CDSN_IO + i);
366 }
367}
368
ac7eb8a3 369static void doc2000_readbuf_dword(struct mtd_info *mtd,
932394ac
WD
370 u_char *buf, int len)
371{
372 struct nand_chip *this = mtd->priv;
373 struct doc_priv *doc = this->priv;
ac7eb8a3 374 void __iomem *docptr = doc->virtadr;
53677ef1 375 int i;
932394ac 376
cfa460ad
WJ
377 if (debug)
378 printk("readbuf_dword of %d bytes: ", len);
932394ac 379
cfa460ad
WJ
380 if (unlikely((((unsigned long)buf) | len) & 3)) {
381 for (i = 0; i < len; i++) {
382 *(uint8_t *) (&buf[i]) = ReadDOC(docptr, 2k_CDSN_IO + i);
932394ac
WD
383 }
384 } else {
cfa460ad
WJ
385 for (i = 0; i < len; i += 4) {
386 *(uint32_t*) (&buf[i]) = readl(docptr + DoC_2k_CDSN_IO + i);
932394ac
WD
387 }
388 }
389}
390
cfa460ad 391static int doc2000_verifybuf(struct mtd_info *mtd, const u_char *buf, int len)
932394ac
WD
392{
393 struct nand_chip *this = mtd->priv;
394 struct doc_priv *doc = this->priv;
ac7eb8a3 395 void __iomem *docptr = doc->virtadr;
932394ac
WD
396 int i;
397
cfa460ad 398 for (i = 0; i < len; i++)
932394ac
WD
399 if (buf[i] != ReadDOC(docptr, 2k_CDSN_IO))
400 return -EFAULT;
401 return 0;
402}
403
404static uint16_t __init doc200x_ident_chip(struct mtd_info *mtd, int nr)
405{
406 struct nand_chip *this = mtd->priv;
407 struct doc_priv *doc = this->priv;
408 uint16_t ret;
409
410 doc200x_select_chip(mtd, nr);
cfa460ad
WJ
411 doc200x_hwcontrol(mtd, NAND_CMD_READID,
412 NAND_CTRL_CLE | NAND_CTRL_CHANGE);
413 doc200x_hwcontrol(mtd, 0, NAND_CTRL_ALE | NAND_CTRL_CHANGE);
414 doc200x_hwcontrol(mtd, NAND_CMD_NONE, NAND_NCE | NAND_CTRL_CHANGE);
415
416 /* We cant' use dev_ready here, but at least we wait for the
417 * command to complete
418 */
419 udelay(50);
932394ac
WD
420
421 ret = this->read_byte(mtd) << 8;
422 ret |= this->read_byte(mtd);
423
424 if (doc->ChipID == DOC_ChipID_Doc2k && try_dword && !nr) {
425 /* First chip probe. See if we get same results by 32-bit access */
426 union {
427 uint32_t dword;
428 uint8_t byte[4];
429 } ident;
430 void __iomem *docptr = doc->virtadr;
431
cfa460ad
WJ
432 doc200x_hwcontrol(mtd, NAND_CMD_READID,
433 NAND_CTRL_CLE | NAND_CTRL_CHANGE);
434 doc200x_hwcontrol(mtd, 0, NAND_CTRL_ALE | NAND_CTRL_CHANGE);
435 doc200x_hwcontrol(mtd, NAND_CMD_NONE,
436 NAND_NCE | NAND_CTRL_CHANGE);
437
438 udelay(50);
932394ac
WD
439
440 ident.dword = readl(docptr + DoC_2k_CDSN_IO);
441 if (((ident.byte[0] << 8) | ident.byte[1]) == ret) {
442 printk(KERN_INFO "DiskOnChip 2000 responds to DWORD access\n");
443 this->read_buf = &doc2000_readbuf_dword;
444 }
445 }
ac7eb8a3 446
932394ac
WD
447 return ret;
448}
449
450static void __init doc2000_count_chips(struct mtd_info *mtd)
451{
452 struct nand_chip *this = mtd->priv;
453 struct doc_priv *doc = this->priv;
454 uint16_t mfrid;
455 int i;
456
457 /* Max 4 chips per floor on DiskOnChip 2000 */
458 doc->chips_per_floor = 4;
459
460 /* Find out what the first chip is */
461 mfrid = doc200x_ident_chip(mtd, 0);
462
463 /* Find how many chips in each floor. */
464 for (i = 1; i < 4; i++) {
465 if (doc200x_ident_chip(mtd, i) != mfrid)
466 break;
467 }
468 doc->chips_per_floor = i;
469 printk(KERN_DEBUG "Detected %d chips per floor.\n", i);
470}
471
cfa460ad 472static int doc200x_wait(struct mtd_info *mtd, struct nand_chip *this)
932394ac
WD
473{
474 struct doc_priv *doc = this->priv;
475
476 int status;
ac7eb8a3 477
932394ac
WD
478 DoC_WaitReady(doc);
479 this->cmdfunc(mtd, NAND_CMD_STATUS, -1, -1);
480 DoC_WaitReady(doc);
481 status = (int)this->read_byte(mtd);
482
483 return status;
484}
485
486static void doc2001_write_byte(struct mtd_info *mtd, u_char datum)
487{
488 struct nand_chip *this = mtd->priv;
489 struct doc_priv *doc = this->priv;
ac7eb8a3 490 void __iomem *docptr = doc->virtadr;
932394ac
WD
491
492 WriteDOC(datum, docptr, CDSNSlowIO);
493 WriteDOC(datum, docptr, Mil_CDSN_IO);
494 WriteDOC(datum, docptr, WritePipeTerm);
495}
496
497static u_char doc2001_read_byte(struct mtd_info *mtd)
498{
499 struct nand_chip *this = mtd->priv;
500 struct doc_priv *doc = this->priv;
ac7eb8a3 501 void __iomem *docptr = doc->virtadr;
932394ac 502
cfa460ad 503 //ReadDOC(docptr, CDSNSlowIO);
932394ac
WD
504 /* 11.4.5 -- delay twice to allow extended length cycle */
505 DoC_Delay(doc, 2);
506 ReadDOC(docptr, ReadPipeInit);
cfa460ad 507 //return ReadDOC(docptr, Mil_CDSN_IO);
932394ac
WD
508 return ReadDOC(docptr, LastDataRead);
509}
510
cfa460ad 511static void doc2001_writebuf(struct mtd_info *mtd, const u_char *buf, int len)
932394ac
WD
512{
513 struct nand_chip *this = mtd->priv;
514 struct doc_priv *doc = this->priv;
ac7eb8a3 515 void __iomem *docptr = doc->virtadr;
932394ac
WD
516 int i;
517
cfa460ad 518 for (i = 0; i < len; i++)
932394ac
WD
519 WriteDOC_(buf[i], docptr, DoC_Mil_CDSN_IO + i);
520 /* Terminate write pipeline */
521 WriteDOC(0x00, docptr, WritePipeTerm);
522}
523
cfa460ad 524static void doc2001_readbuf(struct mtd_info *mtd, u_char *buf, int len)
932394ac
WD
525{
526 struct nand_chip *this = mtd->priv;
527 struct doc_priv *doc = this->priv;
ac7eb8a3 528 void __iomem *docptr = doc->virtadr;
932394ac
WD
529 int i;
530
531 /* Start read pipeline */
532 ReadDOC(docptr, ReadPipeInit);
533
cfa460ad 534 for (i = 0; i < len - 1; i++)
932394ac
WD
535 buf[i] = ReadDOC(docptr, Mil_CDSN_IO + (i & 0xff));
536
537 /* Terminate read pipeline */
538 buf[i] = ReadDOC(docptr, LastDataRead);
539}
540
cfa460ad 541static int doc2001_verifybuf(struct mtd_info *mtd, const u_char *buf, int len)
932394ac
WD
542{
543 struct nand_chip *this = mtd->priv;
544 struct doc_priv *doc = this->priv;
ac7eb8a3 545 void __iomem *docptr = doc->virtadr;
932394ac
WD
546 int i;
547
548 /* Start read pipeline */
549 ReadDOC(docptr, ReadPipeInit);
550
cfa460ad 551 for (i = 0; i < len - 1; i++)
932394ac
WD
552 if (buf[i] != ReadDOC(docptr, Mil_CDSN_IO)) {
553 ReadDOC(docptr, LastDataRead);
554 return i;
555 }
556 if (buf[i] != ReadDOC(docptr, LastDataRead))
557 return i;
558 return 0;
559}
560
561static u_char doc2001plus_read_byte(struct mtd_info *mtd)
562{
563 struct nand_chip *this = mtd->priv;
564 struct doc_priv *doc = this->priv;
ac7eb8a3 565 void __iomem *docptr = doc->virtadr;
932394ac
WD
566 u_char ret;
567
ac7eb8a3
WD
568 ReadDOC(docptr, Mplus_ReadPipeInit);
569 ReadDOC(docptr, Mplus_ReadPipeInit);
570 ret = ReadDOC(docptr, Mplus_LastDataRead);
cfa460ad
WJ
571 if (debug)
572 printk("read_byte returns %02x\n", ret);
932394ac
WD
573 return ret;
574}
575
cfa460ad 576static void doc2001plus_writebuf(struct mtd_info *mtd, const u_char *buf, int len)
932394ac
WD
577{
578 struct nand_chip *this = mtd->priv;
579 struct doc_priv *doc = this->priv;
ac7eb8a3 580 void __iomem *docptr = doc->virtadr;
932394ac
WD
581 int i;
582
cfa460ad
WJ
583 if (debug)
584 printk("writebuf of %d bytes: ", len);
585 for (i = 0; i < len; i++) {
932394ac
WD
586 WriteDOC_(buf[i], docptr, DoC_Mil_CDSN_IO + i);
587 if (debug && i < 16)
588 printk("%02x ", buf[i]);
589 }
cfa460ad
WJ
590 if (debug)
591 printk("\n");
932394ac
WD
592}
593
cfa460ad 594static void doc2001plus_readbuf(struct mtd_info *mtd, u_char *buf, int len)
932394ac
WD
595{
596 struct nand_chip *this = mtd->priv;
597 struct doc_priv *doc = this->priv;
ac7eb8a3 598 void __iomem *docptr = doc->virtadr;
932394ac
WD
599 int i;
600
cfa460ad
WJ
601 if (debug)
602 printk("readbuf of %d bytes: ", len);
932394ac
WD
603
604 /* Start read pipeline */
605 ReadDOC(docptr, Mplus_ReadPipeInit);
606 ReadDOC(docptr, Mplus_ReadPipeInit);
607
cfa460ad 608 for (i = 0; i < len - 2; i++) {
932394ac
WD
609 buf[i] = ReadDOC(docptr, Mil_CDSN_IO);
610 if (debug && i < 16)
611 printk("%02x ", buf[i]);
612 }
613
614 /* Terminate read pipeline */
cfa460ad 615 buf[len - 2] = ReadDOC(docptr, Mplus_LastDataRead);
932394ac 616 if (debug && i < 16)
cfa460ad
WJ
617 printk("%02x ", buf[len - 2]);
618 buf[len - 1] = ReadDOC(docptr, Mplus_LastDataRead);
932394ac 619 if (debug && i < 16)
cfa460ad
WJ
620 printk("%02x ", buf[len - 1]);
621 if (debug)
622 printk("\n");
932394ac
WD
623}
624
cfa460ad 625static int doc2001plus_verifybuf(struct mtd_info *mtd, const u_char *buf, int len)
932394ac
WD
626{
627 struct nand_chip *this = mtd->priv;
628 struct doc_priv *doc = this->priv;
ac7eb8a3 629 void __iomem *docptr = doc->virtadr;
932394ac
WD
630 int i;
631
cfa460ad
WJ
632 if (debug)
633 printk("verifybuf of %d bytes: ", len);
932394ac
WD
634
635 /* Start read pipeline */
636 ReadDOC(docptr, Mplus_ReadPipeInit);
637 ReadDOC(docptr, Mplus_ReadPipeInit);
638
cfa460ad 639 for (i = 0; i < len - 2; i++)
932394ac
WD
640 if (buf[i] != ReadDOC(docptr, Mil_CDSN_IO)) {
641 ReadDOC(docptr, Mplus_LastDataRead);
642 ReadDOC(docptr, Mplus_LastDataRead);
643 return i;
644 }
cfa460ad
WJ
645 if (buf[len - 2] != ReadDOC(docptr, Mplus_LastDataRead))
646 return len - 2;
647 if (buf[len - 1] != ReadDOC(docptr, Mplus_LastDataRead))
648 return len - 1;
932394ac
WD
649 return 0;
650}
651
652static void doc2001plus_select_chip(struct mtd_info *mtd, int chip)
653{
654 struct nand_chip *this = mtd->priv;
655 struct doc_priv *doc = this->priv;
ac7eb8a3 656 void __iomem *docptr = doc->virtadr;
932394ac
WD
657 int floor = 0;
658
cfa460ad
WJ
659 if (debug)
660 printk("select chip (%d)\n", chip);
932394ac
WD
661
662 if (chip == -1) {
663 /* Disable flash internally */
664 WriteDOC(0, docptr, Mplus_FlashSelect);
665 return;
666 }
667
668 floor = chip / doc->chips_per_floor;
cfa460ad 669 chip -= (floor * doc->chips_per_floor);
932394ac
WD
670
671 /* Assert ChipEnable and deassert WriteProtect */
672 WriteDOC((DOC_FLASH_CE), docptr, Mplus_FlashSelect);
673 this->cmdfunc(mtd, NAND_CMD_RESET, -1, -1);
674
675 doc->curchip = chip;
676 doc->curfloor = floor;
677}
678
679static void doc200x_select_chip(struct mtd_info *mtd, int chip)
680{
681 struct nand_chip *this = mtd->priv;
682 struct doc_priv *doc = this->priv;
ac7eb8a3 683 void __iomem *docptr = doc->virtadr;
932394ac
WD
684 int floor = 0;
685
cfa460ad
WJ
686 if (debug)
687 printk("select chip (%d)\n", chip);
932394ac
WD
688
689 if (chip == -1)
690 return;
691
692 floor = chip / doc->chips_per_floor;
cfa460ad 693 chip -= (floor * doc->chips_per_floor);
932394ac
WD
694
695 /* 11.4.4 -- deassert CE before changing chip */
cfa460ad 696 doc200x_hwcontrol(mtd, NAND_CMD_NONE, 0 | NAND_CTRL_CHANGE);
932394ac
WD
697
698 WriteDOC(floor, docptr, FloorSelect);
699 WriteDOC(chip, docptr, CDSNDeviceSelect);
700
cfa460ad 701 doc200x_hwcontrol(mtd, NAND_CMD_NONE, NAND_NCE | NAND_CTRL_CHANGE);
932394ac
WD
702
703 doc->curchip = chip;
704 doc->curfloor = floor;
705}
706
cfa460ad
WJ
707#define CDSN_CTRL_MSK (CDSN_CTRL_CE | CDSN_CTRL_CLE | CDSN_CTRL_ALE)
708
709static void doc200x_hwcontrol(struct mtd_info *mtd, int cmd,
710 unsigned int ctrl)
932394ac
WD
711{
712 struct nand_chip *this = mtd->priv;
713 struct doc_priv *doc = this->priv;
ac7eb8a3 714 void __iomem *docptr = doc->virtadr;
932394ac 715
cfa460ad
WJ
716 if (ctrl & NAND_CTRL_CHANGE) {
717 doc->CDSNControl &= ~CDSN_CTRL_MSK;
718 doc->CDSNControl |= ctrl & CDSN_CTRL_MSK;
719 if (debug)
720 printk("hwcontrol(%d): %02x\n", cmd, doc->CDSNControl);
721 WriteDOC(doc->CDSNControl, docptr, CDSNControl);
722 /* 11.4.3 -- 4 NOPs after CSDNControl write */
723 DoC_Delay(doc, 4);
724 }
725 if (cmd != NAND_CMD_NONE) {
726 if (DoC_is_2000(doc))
727 doc2000_write_byte(mtd, cmd);
728 else
729 doc2001_write_byte(mtd, cmd);
932394ac 730 }
932394ac
WD
731}
732
cfa460ad 733static void doc2001plus_command(struct mtd_info *mtd, unsigned command, int column, int page_addr)
932394ac
WD
734{
735 struct nand_chip *this = mtd->priv;
736 struct doc_priv *doc = this->priv;
ac7eb8a3 737 void __iomem *docptr = doc->virtadr;
932394ac
WD
738
739 /*
740 * Must terminate write pipeline before sending any commands
741 * to the device.
742 */
743 if (command == NAND_CMD_PAGEPROG) {
744 WriteDOC(0x00, docptr, Mplus_WritePipeTerm);
745 WriteDOC(0x00, docptr, Mplus_WritePipeTerm);
746 }
747
748 /*
749 * Write out the command to the device.
750 */
751 if (command == NAND_CMD_SEQIN) {
752 int readcmd;
753
cfa460ad 754 if (column >= mtd->writesize) {
932394ac 755 /* OOB area */
cfa460ad 756 column -= mtd->writesize;
932394ac
WD
757 readcmd = NAND_CMD_READOOB;
758 } else if (column < 256) {
759 /* First 256 bytes --> READ0 */
760 readcmd = NAND_CMD_READ0;
761 } else {
762 column -= 256;
763 readcmd = NAND_CMD_READ1;
764 }
765 WriteDOC(readcmd, docptr, Mplus_FlashCmd);
766 }
767 WriteDOC(command, docptr, Mplus_FlashCmd);
768 WriteDOC(0, docptr, Mplus_WritePipeTerm);
769 WriteDOC(0, docptr, Mplus_WritePipeTerm);
770
771 if (column != -1 || page_addr != -1) {
772 /* Serially input address */
773 if (column != -1) {
774 /* Adjust columns for 16 bit buswidth */
775 if (this->options & NAND_BUSWIDTH_16)
776 column >>= 1;
777 WriteDOC(column, docptr, Mplus_FlashAddress);
778 }
779 if (page_addr != -1) {
cfa460ad
WJ
780 WriteDOC((unsigned char)(page_addr & 0xff), docptr, Mplus_FlashAddress);
781 WriteDOC((unsigned char)((page_addr >> 8) & 0xff), docptr, Mplus_FlashAddress);
932394ac
WD
782 /* One more address cycle for higher density devices */
783 if (this->chipsize & 0x0c000000) {
cfa460ad 784 WriteDOC((unsigned char)((page_addr >> 16) & 0x0f), docptr, Mplus_FlashAddress);
932394ac
WD
785 printk("high density\n");
786 }
787 }
788 WriteDOC(0, docptr, Mplus_WritePipeTerm);
789 WriteDOC(0, docptr, Mplus_WritePipeTerm);
790 /* deassert ALE */
cfa460ad
WJ
791 if (command == NAND_CMD_READ0 || command == NAND_CMD_READ1 ||
792 command == NAND_CMD_READOOB || command == NAND_CMD_READID)
932394ac
WD
793 WriteDOC(0, docptr, Mplus_FlashControl);
794 }
795
ac7eb8a3 796 /*
932394ac
WD
797 * program and erase have their own busy handlers
798 * status and sequential in needs no delay
cfa460ad 799 */
932394ac
WD
800 switch (command) {
801
802 case NAND_CMD_PAGEPROG:
803 case NAND_CMD_ERASE1:
804 case NAND_CMD_ERASE2:
805 case NAND_CMD_SEQIN:
806 case NAND_CMD_STATUS:
807 return;
808
809 case NAND_CMD_RESET:
810 if (this->dev_ready)
811 break;
812 udelay(this->chip_delay);
813 WriteDOC(NAND_CMD_STATUS, docptr, Mplus_FlashCmd);
814 WriteDOC(0, docptr, Mplus_WritePipeTerm);
815 WriteDOC(0, docptr, Mplus_WritePipeTerm);
cfa460ad 816 while (!(this->read_byte(mtd) & 0x40)) ;
932394ac
WD
817 return;
818
cfa460ad 819 /* This applies to read commands */
932394ac 820 default:
ac7eb8a3 821 /*
932394ac
WD
822 * If we don't have access to the busy pin, we apply the given
823 * command delay
cfa460ad 824 */
932394ac 825 if (!this->dev_ready) {
cfa460ad 826 udelay(this->chip_delay);
932394ac
WD
827 return;
828 }
829 }
830
831 /* Apply this short delay always to ensure that we do wait tWB in
832 * any case on any machine. */
cfa460ad 833 ndelay(100);
932394ac 834 /* wait until command is processed */
cfa460ad 835 while (!this->dev_ready(mtd)) ;
932394ac
WD
836}
837
838static int doc200x_dev_ready(struct mtd_info *mtd)
839{
840 struct nand_chip *this = mtd->priv;
841 struct doc_priv *doc = this->priv;
ac7eb8a3 842 void __iomem *docptr = doc->virtadr;
932394ac
WD
843
844 if (DoC_is_MillenniumPlus(doc)) {
845 /* 11.4.2 -- must NOP four times before checking FR/B# */
846 DoC_Delay(doc, 4);
847 if ((ReadDOC(docptr, Mplus_FlashControl) & CDSN_CTRL_FR_B_MASK) != CDSN_CTRL_FR_B_MASK) {
cfa460ad 848 if (debug)
932394ac
WD
849 printk("not ready\n");
850 return 0;
851 }
cfa460ad
WJ
852 if (debug)
853 printk("was ready\n");
932394ac
WD
854 return 1;
855 } else {
856 /* 11.4.2 -- must NOP four times before checking FR/B# */
857 DoC_Delay(doc, 4);
858 if (!(ReadDOC(docptr, CDSNControl) & CDSN_CTRL_FR_B)) {
cfa460ad 859 if (debug)
932394ac
WD
860 printk("not ready\n");
861 return 0;
862 }
863 /* 11.4.2 -- Must NOP twice if it's ready */
864 DoC_Delay(doc, 2);
cfa460ad
WJ
865 if (debug)
866 printk("was ready\n");
932394ac
WD
867 return 1;
868 }
869}
870
871static int doc200x_block_bad(struct mtd_info *mtd, loff_t ofs, int getchip)
872{
873 /* This is our last resort if we couldn't find or create a BBT. Just
874 pretend all blocks are good. */
875 return 0;
876}
877
878static void doc200x_enable_hwecc(struct mtd_info *mtd, int mode)
879{
880 struct nand_chip *this = mtd->priv;
881 struct doc_priv *doc = this->priv;
ac7eb8a3 882 void __iomem *docptr = doc->virtadr;
932394ac
WD
883
884 /* Prime the ECC engine */
cfa460ad 885 switch (mode) {
932394ac
WD
886 case NAND_ECC_READ:
887 WriteDOC(DOC_ECC_RESET, docptr, ECCConf);
888 WriteDOC(DOC_ECC_EN, docptr, ECCConf);
889 break;
890 case NAND_ECC_WRITE:
891 WriteDOC(DOC_ECC_RESET, docptr, ECCConf);
892 WriteDOC(DOC_ECC_EN | DOC_ECC_RW, docptr, ECCConf);
893 break;
894 }
895}
896
897static void doc2001plus_enable_hwecc(struct mtd_info *mtd, int mode)
898{
899 struct nand_chip *this = mtd->priv;
900 struct doc_priv *doc = this->priv;
ac7eb8a3 901 void __iomem *docptr = doc->virtadr;
932394ac
WD
902
903 /* Prime the ECC engine */
cfa460ad 904 switch (mode) {
932394ac
WD
905 case NAND_ECC_READ:
906 WriteDOC(DOC_ECC_RESET, docptr, Mplus_ECCConf);
907 WriteDOC(DOC_ECC_EN, docptr, Mplus_ECCConf);
908 break;
909 case NAND_ECC_WRITE:
910 WriteDOC(DOC_ECC_RESET, docptr, Mplus_ECCConf);
911 WriteDOC(DOC_ECC_EN | DOC_ECC_RW, docptr, Mplus_ECCConf);
912 break;
913 }
914}
915
916/* This code is only called on write */
cfa460ad 917static int doc200x_calculate_ecc(struct mtd_info *mtd, const u_char *dat, unsigned char *ecc_code)
932394ac
WD
918{
919 struct nand_chip *this = mtd->priv;
920 struct doc_priv *doc = this->priv;
ac7eb8a3 921 void __iomem *docptr = doc->virtadr;
932394ac
WD
922 int i;
923 int emptymatch = 1;
924
925 /* flush the pipeline */
926 if (DoC_is_2000(doc)) {
927 WriteDOC(doc->CDSNControl & ~CDSN_CTRL_FLASH_IO, docptr, CDSNControl);
928 WriteDOC(0, docptr, 2k_CDSN_IO);
929 WriteDOC(0, docptr, 2k_CDSN_IO);
930 WriteDOC(0, docptr, 2k_CDSN_IO);
931 WriteDOC(doc->CDSNControl, docptr, CDSNControl);
932 } else if (DoC_is_MillenniumPlus(doc)) {
933 WriteDOC(0, docptr, Mplus_NOP);
934 WriteDOC(0, docptr, Mplus_NOP);
935 WriteDOC(0, docptr, Mplus_NOP);
936 } else {
937 WriteDOC(0, docptr, NOP);
938 WriteDOC(0, docptr, NOP);
939 WriteDOC(0, docptr, NOP);
940 }
941
942 for (i = 0; i < 6; i++) {
943 if (DoC_is_MillenniumPlus(doc))
944 ecc_code[i] = ReadDOC_(docptr, DoC_Mplus_ECCSyndrome0 + i);
ac7eb8a3 945 else
932394ac
WD
946 ecc_code[i] = ReadDOC_(docptr, DoC_ECCSyndrome0 + i);
947 if (ecc_code[i] != empty_write_ecc[i])
948 emptymatch = 0;
949 }
950 if (DoC_is_MillenniumPlus(doc))
951 WriteDOC(DOC_ECC_DIS, docptr, Mplus_ECCConf);
952 else
953 WriteDOC(DOC_ECC_DIS, docptr, ECCConf);
954#if 0
955 /* If emptymatch=1, we might have an all-0xff data buffer. Check. */
956 if (emptymatch) {
957 /* Note: this somewhat expensive test should not be triggered
958 often. It could be optimized away by examining the data in
959 the writebuf routine, and remembering the result. */
960 for (i = 0; i < 512; i++) {
cfa460ad
WJ
961 if (dat[i] == 0xff)
962 continue;
932394ac
WD
963 emptymatch = 0;
964 break;
965 }
966 }
967 /* If emptymatch still =1, we do have an all-0xff data buffer.
968 Return all-0xff ecc value instead of the computed one, so
969 it'll look just like a freshly-erased page. */
cfa460ad
WJ
970 if (emptymatch)
971 memset(ecc_code, 0xff, 6);
932394ac
WD
972#endif
973 return 0;
974}
975
cfa460ad
WJ
976static int doc200x_correct_data(struct mtd_info *mtd, u_char *dat,
977 u_char *read_ecc, u_char *isnull)
932394ac
WD
978{
979 int i, ret = 0;
980 struct nand_chip *this = mtd->priv;
981 struct doc_priv *doc = this->priv;
ac7eb8a3 982 void __iomem *docptr = doc->virtadr;
cfa460ad 983 uint8_t calc_ecc[6];
932394ac
WD
984 volatile u_char dummy;
985 int emptymatch = 1;
ac7eb8a3 986
932394ac
WD
987 /* flush the pipeline */
988 if (DoC_is_2000(doc)) {
989 dummy = ReadDOC(docptr, 2k_ECCStatus);
990 dummy = ReadDOC(docptr, 2k_ECCStatus);
991 dummy = ReadDOC(docptr, 2k_ECCStatus);
992 } else if (DoC_is_MillenniumPlus(doc)) {
993 dummy = ReadDOC(docptr, Mplus_ECCConf);
994 dummy = ReadDOC(docptr, Mplus_ECCConf);
995 dummy = ReadDOC(docptr, Mplus_ECCConf);
996 } else {
997 dummy = ReadDOC(docptr, ECCConf);
998 dummy = ReadDOC(docptr, ECCConf);
999 dummy = ReadDOC(docptr, ECCConf);
1000 }
ac7eb8a3 1001
932394ac
WD
1002 /* Error occured ? */
1003 if (dummy & 0x80) {
1004 for (i = 0; i < 6; i++) {
1005 if (DoC_is_MillenniumPlus(doc))
1006 calc_ecc[i] = ReadDOC_(docptr, DoC_Mplus_ECCSyndrome0 + i);
1007 else
1008 calc_ecc[i] = ReadDOC_(docptr, DoC_ECCSyndrome0 + i);
1009 if (calc_ecc[i] != empty_read_syndrome[i])
1010 emptymatch = 0;
1011 }
1012 /* If emptymatch=1, the read syndrome is consistent with an
1013 all-0xff data and stored ecc block. Check the stored ecc. */
1014 if (emptymatch) {
1015 for (i = 0; i < 6; i++) {
cfa460ad
WJ
1016 if (read_ecc[i] == 0xff)
1017 continue;
932394ac
WD
1018 emptymatch = 0;
1019 break;
1020 }
1021 }
1022 /* If emptymatch still =1, check the data block. */
1023 if (emptymatch) {
cfa460ad
WJ
1024 /* Note: this somewhat expensive test should not be triggered
1025 often. It could be optimized away by examining the data in
1026 the readbuf routine, and remembering the result. */
932394ac 1027 for (i = 0; i < 512; i++) {
cfa460ad
WJ
1028 if (dat[i] == 0xff)
1029 continue;
932394ac
WD
1030 emptymatch = 0;
1031 break;
1032 }
1033 }
1034 /* If emptymatch still =1, this is almost certainly a freshly-
1035 erased block, in which case the ECC will not come out right.
1036 We'll suppress the error and tell the caller everything's
1037 OK. Because it is. */
cfa460ad
WJ
1038 if (!emptymatch)
1039 ret = doc_ecc_decode(rs_decoder, dat, calc_ecc);
932394ac
WD
1040 if (ret > 0)
1041 printk(KERN_ERR "doc200x_correct_data corrected %d errors\n", ret);
ac7eb8a3 1042 }
932394ac
WD
1043 if (DoC_is_MillenniumPlus(doc))
1044 WriteDOC(DOC_ECC_DIS, docptr, Mplus_ECCConf);
1045 else
1046 WriteDOC(DOC_ECC_DIS, docptr, ECCConf);
1047 if (no_ecc_failures && (ret == -1)) {
1048 printk(KERN_ERR "suppressing ECC failure\n");
1049 ret = 0;
1050 }
1051 return ret;
1052}
ac7eb8a3 1053
cfa460ad
WJ
1054//u_char mydatabuf[528];
1055
1056/* The strange out-of-order .oobfree list below is a (possibly unneeded)
1057 * attempt to retain compatibility. It used to read:
1058 * .oobfree = { {8, 8} }
1059 * Since that leaves two bytes unusable, it was changed. But the following
1060 * scheme might affect existing jffs2 installs by moving the cleanmarker:
1061 * .oobfree = { {6, 10} }
1062 * jffs2 seems to handle the above gracefully, but the current scheme seems
1063 * safer. The only problem with it is that any code that parses oobfree must
1064 * be able to handle out-of-order segments.
1065 */
1066static struct nand_ecclayout doc200x_oobinfo = {
ac7eb8a3
WD
1067 .eccbytes = 6,
1068 .eccpos = {0, 1, 2, 3, 4, 5},
cfa460ad 1069 .oobfree = {{8, 8}, {6, 2}}
932394ac 1070};
ac7eb8a3 1071
932394ac
WD
1072/* Find the (I)NFTL Media Header, and optionally also the mirror media header.
1073 On sucessful return, buf will contain a copy of the media header for
1074 further processing. id is the string to scan for, and will presumably be
1075 either "ANAND" or "BNAND". If findmirror=1, also look for the mirror media
1076 header. The page #s of the found media headers are placed in mh0_page and
1077 mh1_page in the DOC private structure. */
cfa460ad 1078static int __init find_media_headers(struct mtd_info *mtd, u_char *buf, const char *id, int findmirror)
932394ac
WD
1079{
1080 struct nand_chip *this = mtd->priv;
1081 struct doc_priv *doc = this->priv;
cfa460ad 1082 unsigned offs;
932394ac
WD
1083 int ret;
1084 size_t retlen;
1085
cfa460ad
WJ
1086 for (offs = 0; offs < mtd->size; offs += mtd->erasesize) {
1087 ret = mtd->read(mtd, offs, mtd->writesize, &retlen, buf);
1088 if (retlen != mtd->writesize)
1089 continue;
932394ac 1090 if (ret) {
cfa460ad 1091 printk(KERN_WARNING "ECC error scanning DOC at 0x%x\n", offs);
932394ac 1092 }
cfa460ad
WJ
1093 if (memcmp(buf, id, 6))
1094 continue;
932394ac
WD
1095 printk(KERN_INFO "Found DiskOnChip %s Media Header at 0x%x\n", id, offs);
1096 if (doc->mh0_page == -1) {
1097 doc->mh0_page = offs >> this->page_shift;
cfa460ad
WJ
1098 if (!findmirror)
1099 return 1;
932394ac
WD
1100 continue;
1101 }
1102 doc->mh1_page = offs >> this->page_shift;
1103 return 2;
1104 }
1105 if (doc->mh0_page == -1) {
1106 printk(KERN_WARNING "DiskOnChip %s Media Header not found.\n", id);
1107 return 0;
1108 }
1109 /* Only one mediaheader was found. We want buf to contain a
1110 mediaheader on return, so we'll have to re-read the one we found. */
1111 offs = doc->mh0_page << this->page_shift;
cfa460ad
WJ
1112 ret = mtd->read(mtd, offs, mtd->writesize, &retlen, buf);
1113 if (retlen != mtd->writesize) {
932394ac
WD
1114 /* Insanity. Give up. */
1115 printk(KERN_ERR "Read DiskOnChip Media Header once, but can't reread it???\n");
1116 return 0;
1117 }
1118 return 1;
1119}
1120
cfa460ad 1121static inline int __init nftl_partscan(struct mtd_info *mtd, struct mtd_partition *parts)
932394ac
WD
1122{
1123 struct nand_chip *this = mtd->priv;
1124 struct doc_priv *doc = this->priv;
1125 int ret = 0;
1126 u_char *buf;
1127 struct NFTLMediaHeader *mh;
1128 const unsigned psize = 1 << this->page_shift;
cfa460ad 1129 int numparts = 0;
932394ac
WD
1130 unsigned blocks, maxblocks;
1131 int offs, numheaders;
1132
cfa460ad 1133 buf = kmalloc(mtd->writesize, GFP_KERNEL);
932394ac
WD
1134 if (!buf) {
1135 printk(KERN_ERR "DiskOnChip mediaheader kmalloc failed!\n");
1136 return 0;
1137 }
cfa460ad
WJ
1138 if (!(numheaders = find_media_headers(mtd, buf, "ANAND", 1)))
1139 goto out;
1140 mh = (struct NFTLMediaHeader *)buf;
1141
1142 mh->NumEraseUnits = le16_to_cpu(mh->NumEraseUnits);
1143 mh->FirstPhysicalEUN = le16_to_cpu(mh->FirstPhysicalEUN);
1144 mh->FormattedSize = le32_to_cpu(mh->FormattedSize);
932394ac 1145
932394ac
WD
1146 printk(KERN_INFO " DataOrgID = %s\n"
1147 " NumEraseUnits = %d\n"
1148 " FirstPhysicalEUN = %d\n"
1149 " FormattedSize = %d\n"
1150 " UnitSizeFactor = %d\n",
1151 mh->DataOrgID, mh->NumEraseUnits,
1152 mh->FirstPhysicalEUN, mh->FormattedSize,
1153 mh->UnitSizeFactor);
932394ac
WD
1154
1155 blocks = mtd->size >> this->phys_erase_shift;
1156 maxblocks = min(32768U, mtd->erasesize - psize);
1157
1158 if (mh->UnitSizeFactor == 0x00) {
1159 /* Auto-determine UnitSizeFactor. The constraints are:
1160 - There can be at most 32768 virtual blocks.
1161 - There can be at most (virtual block size - page size)
cfa460ad
WJ
1162 virtual blocks (because MediaHeader+BBT must fit in 1).
1163 */
932394ac
WD
1164 mh->UnitSizeFactor = 0xff;
1165 while (blocks > maxblocks) {
1166 blocks >>= 1;
1167 maxblocks = min(32768U, (maxblocks << 1) + psize);
1168 mh->UnitSizeFactor--;
1169 }
1170 printk(KERN_WARNING "UnitSizeFactor=0x00 detected. Correct value is assumed to be 0x%02x.\n", mh->UnitSizeFactor);
1171 }
1172
1173 /* NOTE: The lines below modify internal variables of the NAND and MTD
1174 layers; variables with have already been configured by nand_scan.
1175 Unfortunately, we didn't know before this point what these values
1176 should be. Thus, this code is somewhat dependant on the exact
1177 implementation of the NAND layer. */
1178 if (mh->UnitSizeFactor != 0xff) {
1179 this->bbt_erase_shift += (0xff - mh->UnitSizeFactor);
1180 mtd->erasesize <<= (0xff - mh->UnitSizeFactor);
1181 printk(KERN_INFO "Setting virtual erase size to %d\n", mtd->erasesize);
1182 blocks = mtd->size >> this->bbt_erase_shift;
1183 maxblocks = min(32768U, mtd->erasesize - psize);
1184 }
1185
1186 if (blocks > maxblocks) {
1187 printk(KERN_ERR "UnitSizeFactor of 0x%02x is inconsistent with device size. Aborting.\n", mh->UnitSizeFactor);
1188 goto out;
1189 }
1190
1191 /* Skip past the media headers. */
1192 offs = max(doc->mh0_page, doc->mh1_page);
1193 offs <<= this->page_shift;
1194 offs += mtd->erasesize;
1195
cfa460ad
WJ
1196 if (show_firmware_partition == 1) {
1197 parts[0].name = " DiskOnChip Firmware / Media Header partition";
1198 parts[0].offset = 0;
1199 parts[0].size = offs;
1200 numparts = 1;
1201 }
1202
1203 parts[numparts].name = " DiskOnChip BDTL partition";
1204 parts[numparts].offset = offs;
1205 parts[numparts].size = (mh->NumEraseUnits - numheaders) << this->bbt_erase_shift;
932394ac 1206
cfa460ad
WJ
1207 offs += parts[numparts].size;
1208 numparts++;
932394ac 1209
932394ac 1210 if (offs < mtd->size) {
cfa460ad
WJ
1211 parts[numparts].name = " DiskOnChip Remainder partition";
1212 parts[numparts].offset = offs;
1213 parts[numparts].size = mtd->size - offs;
1214 numparts++;
932394ac 1215 }
cfa460ad
WJ
1216
1217 ret = numparts;
1218 out:
932394ac
WD
1219 kfree(buf);
1220 return ret;
1221}
1222
1223/* This is a stripped-down copy of the code in inftlmount.c */
cfa460ad 1224static inline int __init inftl_partscan(struct mtd_info *mtd, struct mtd_partition *parts)
932394ac
WD
1225{
1226 struct nand_chip *this = mtd->priv;
1227 struct doc_priv *doc = this->priv;
1228 int ret = 0;
1229 u_char *buf;
1230 struct INFTLMediaHeader *mh;
1231 struct INFTLPartition *ip;
1232 int numparts = 0;
1233 int blocks;
1234 int vshift, lastvunit = 0;
1235 int i;
1236 int end = mtd->size;
1237
1238 if (inftl_bbt_write)
1239 end -= (INFTL_BBT_RESERVED_BLOCKS << this->phys_erase_shift);
1240
cfa460ad 1241 buf = kmalloc(mtd->writesize, GFP_KERNEL);
932394ac
WD
1242 if (!buf) {
1243 printk(KERN_ERR "DiskOnChip mediaheader kmalloc failed!\n");
1244 return 0;
1245 }
1246
cfa460ad
WJ
1247 if (!find_media_headers(mtd, buf, "BNAND", 0))
1248 goto out;
932394ac 1249 doc->mh1_page = doc->mh0_page + (4096 >> this->page_shift);
cfa460ad 1250 mh = (struct INFTLMediaHeader *)buf;
932394ac
WD
1251
1252 mh->NoOfBootImageBlocks = le32_to_cpu(mh->NoOfBootImageBlocks);
1253 mh->NoOfBinaryPartitions = le32_to_cpu(mh->NoOfBinaryPartitions);
1254 mh->NoOfBDTLPartitions = le32_to_cpu(mh->NoOfBDTLPartitions);
1255 mh->BlockMultiplierBits = le32_to_cpu(mh->BlockMultiplierBits);
1256 mh->FormatFlags = le32_to_cpu(mh->FormatFlags);
1257 mh->PercentUsed = le32_to_cpu(mh->PercentUsed);
ac7eb8a3 1258
932394ac
WD
1259 printk(KERN_INFO " bootRecordID = %s\n"
1260 " NoOfBootImageBlocks = %d\n"
1261 " NoOfBinaryPartitions = %d\n"
1262 " NoOfBDTLPartitions = %d\n"
1263 " BlockMultiplerBits = %d\n"
1264 " FormatFlgs = %d\n"
1265 " OsakVersion = %d.%d.%d.%d\n"
1266 " PercentUsed = %d\n",
1267 mh->bootRecordID, mh->NoOfBootImageBlocks,
1268 mh->NoOfBinaryPartitions,
1269 mh->NoOfBDTLPartitions,
1270 mh->BlockMultiplierBits, mh->FormatFlags,
1271 ((unsigned char *) &mh->OsakVersion)[0] & 0xf,
1272 ((unsigned char *) &mh->OsakVersion)[1] & 0xf,
1273 ((unsigned char *) &mh->OsakVersion)[2] & 0xf,
1274 ((unsigned char *) &mh->OsakVersion)[3] & 0xf,
1275 mh->PercentUsed);
932394ac
WD
1276
1277 vshift = this->phys_erase_shift + mh->BlockMultiplierBits;
1278
1279 blocks = mtd->size >> vshift;
1280 if (blocks > 32768) {
1281 printk(KERN_ERR "BlockMultiplierBits=%d is inconsistent with device size. Aborting.\n", mh->BlockMultiplierBits);
1282 goto out;
1283 }
1284
1285 blocks = doc->chips_per_floor << (this->chip_shift - this->phys_erase_shift);
1286 if (inftl_bbt_write && (blocks > mtd->erasesize)) {
1287 printk(KERN_ERR "Writeable BBTs spanning more than one erase block are not yet supported. FIX ME!\n");
1288 goto out;
1289 }
1290
1291 /* Scan the partitions */
1292 for (i = 0; (i < 4); i++) {
1293 ip = &(mh->Partitions[i]);
1294 ip->virtualUnits = le32_to_cpu(ip->virtualUnits);
1295 ip->firstUnit = le32_to_cpu(ip->firstUnit);
1296 ip->lastUnit = le32_to_cpu(ip->lastUnit);
1297 ip->flags = le32_to_cpu(ip->flags);
1298 ip->spareUnits = le32_to_cpu(ip->spareUnits);
1299 ip->Reserved0 = le32_to_cpu(ip->Reserved0);
1300
932394ac
WD
1301 printk(KERN_INFO " PARTITION[%d] ->\n"
1302 " virtualUnits = %d\n"
1303 " firstUnit = %d\n"
1304 " lastUnit = %d\n"
1305 " flags = 0x%x\n"
1306 " spareUnits = %d\n",
1307 i, ip->virtualUnits, ip->firstUnit,
1308 ip->lastUnit, ip->flags,
1309 ip->spareUnits);
932394ac 1310
cfa460ad
WJ
1311 if ((show_firmware_partition == 1) &&
1312 (i == 0) && (ip->firstUnit > 0)) {
932394ac
WD
1313 parts[0].name = " DiskOnChip IPL / Media Header partition";
1314 parts[0].offset = 0;
1315 parts[0].size = mtd->erasesize * ip->firstUnit;
1316 numparts = 1;
1317 }
932394ac
WD
1318
1319 if (ip->flags & INFTL_BINARY)
1320 parts[numparts].name = " DiskOnChip BDK partition";
1321 else
1322 parts[numparts].name = " DiskOnChip BDTL partition";
1323 parts[numparts].offset = ip->firstUnit << vshift;
1324 parts[numparts].size = (1 + ip->lastUnit - ip->firstUnit) << vshift;
1325 numparts++;
cfa460ad
WJ
1326 if (ip->lastUnit > lastvunit)
1327 lastvunit = ip->lastUnit;
1328 if (ip->flags & INFTL_LAST)
1329 break;
932394ac
WD
1330 }
1331 lastvunit++;
1332 if ((lastvunit << vshift) < end) {
1333 parts[numparts].name = " DiskOnChip Remainder partition";
1334 parts[numparts].offset = lastvunit << vshift;
1335 parts[numparts].size = end - parts[numparts].offset;
1336 numparts++;
1337 }
1338 ret = numparts;
cfa460ad 1339 out:
932394ac
WD
1340 kfree(buf);
1341 return ret;
1342}
1343
1344static int __init nftl_scan_bbt(struct mtd_info *mtd)
1345{
1346 int ret, numparts;
1347 struct nand_chip *this = mtd->priv;
1348 struct doc_priv *doc = this->priv;
1349 struct mtd_partition parts[2];
1350
cfa460ad 1351 memset((char *)parts, 0, sizeof(parts));
932394ac
WD
1352 /* On NFTL, we have to find the media headers before we can read the
1353 BBTs, since they're stored in the media header eraseblocks. */
1354 numparts = nftl_partscan(mtd, parts);
cfa460ad
WJ
1355 if (!numparts)
1356 return -EIO;
932394ac
WD
1357 this->bbt_td->options = NAND_BBT_ABSPAGE | NAND_BBT_8BIT |
1358 NAND_BBT_SAVECONTENT | NAND_BBT_WRITE |
1359 NAND_BBT_VERSION;
1360 this->bbt_td->veroffs = 7;
1361 this->bbt_td->pages[0] = doc->mh0_page + 1;
1362 if (doc->mh1_page != -1) {
1363 this->bbt_md->options = NAND_BBT_ABSPAGE | NAND_BBT_8BIT |
1364 NAND_BBT_SAVECONTENT | NAND_BBT_WRITE |
1365 NAND_BBT_VERSION;
1366 this->bbt_md->veroffs = 7;
1367 this->bbt_md->pages[0] = doc->mh1_page + 1;
1368 } else {
1369 this->bbt_md = NULL;
1370 }
1371
1372 /* It's safe to set bd=NULL below because NAND_BBT_CREATE is not set.
1373 At least as nand_bbt.c is currently written. */
1374 if ((ret = nand_scan_bbt(mtd, NULL)))
1375 return ret;
1376 add_mtd_device(mtd);
1377#ifdef CONFIG_MTD_PARTITIONS
1378 if (!no_autopart)
1379 add_mtd_partitions(mtd, parts, numparts);
1380#endif
1381 return 0;
1382}
1383
1384static int __init inftl_scan_bbt(struct mtd_info *mtd)
1385{
1386 int ret, numparts;
1387 struct nand_chip *this = mtd->priv;
1388 struct doc_priv *doc = this->priv;
1389 struct mtd_partition parts[5];
1390
1391 if (this->numchips > doc->chips_per_floor) {
1392 printk(KERN_ERR "Multi-floor INFTL devices not yet supported.\n");
1393 return -EIO;
1394 }
1395
1396 if (DoC_is_MillenniumPlus(doc)) {
1397 this->bbt_td->options = NAND_BBT_2BIT | NAND_BBT_ABSPAGE;
1398 if (inftl_bbt_write)
1399 this->bbt_td->options |= NAND_BBT_WRITE;
1400 this->bbt_td->pages[0] = 2;
1401 this->bbt_md = NULL;
1402 } else {
cfa460ad 1403 this->bbt_td->options = NAND_BBT_LASTBLOCK | NAND_BBT_8BIT | NAND_BBT_VERSION;
932394ac
WD
1404 if (inftl_bbt_write)
1405 this->bbt_td->options |= NAND_BBT_WRITE;
1406 this->bbt_td->offs = 8;
1407 this->bbt_td->len = 8;
1408 this->bbt_td->veroffs = 7;
1409 this->bbt_td->maxblocks = INFTL_BBT_RESERVED_BLOCKS;
1410 this->bbt_td->reserved_block_code = 0x01;
1411 this->bbt_td->pattern = "MSYS_BBT";
1412
cfa460ad 1413 this->bbt_md->options = NAND_BBT_LASTBLOCK | NAND_BBT_8BIT | NAND_BBT_VERSION;
932394ac
WD
1414 if (inftl_bbt_write)
1415 this->bbt_md->options |= NAND_BBT_WRITE;
1416 this->bbt_md->offs = 8;
1417 this->bbt_md->len = 8;
1418 this->bbt_md->veroffs = 7;
1419 this->bbt_md->maxblocks = INFTL_BBT_RESERVED_BLOCKS;
1420 this->bbt_md->reserved_block_code = 0x01;
1421 this->bbt_md->pattern = "TBB_SYSM";
1422 }
1423
1424 /* It's safe to set bd=NULL below because NAND_BBT_CREATE is not set.
1425 At least as nand_bbt.c is currently written. */
1426 if ((ret = nand_scan_bbt(mtd, NULL)))
1427 return ret;
cfa460ad 1428 memset((char *)parts, 0, sizeof(parts));
932394ac
WD
1429 numparts = inftl_partscan(mtd, parts);
1430 /* At least for now, require the INFTL Media Header. We could probably
1431 do without it for non-INFTL use, since all it gives us is
1432 autopartitioning, but I want to give it more thought. */
cfa460ad
WJ
1433 if (!numparts)
1434 return -EIO;
932394ac
WD
1435 add_mtd_device(mtd);
1436#ifdef CONFIG_MTD_PARTITIONS
1437 if (!no_autopart)
1438 add_mtd_partitions(mtd, parts, numparts);
1439#endif
1440 return 0;
1441}
1442
1443static inline int __init doc2000_init(struct mtd_info *mtd)
1444{
1445 struct nand_chip *this = mtd->priv;
1446 struct doc_priv *doc = this->priv;
1447
932394ac
WD
1448 this->read_byte = doc2000_read_byte;
1449 this->write_buf = doc2000_writebuf;
1450 this->read_buf = doc2000_readbuf;
1451 this->verify_buf = doc2000_verifybuf;
1452 this->scan_bbt = nftl_scan_bbt;
1453
1454 doc->CDSNControl = CDSN_CTRL_FLASH_IO | CDSN_CTRL_ECC_IO;
1455 doc2000_count_chips(mtd);
1456 mtd->name = "DiskOnChip 2000 (NFTL Model)";
1457 return (4 * doc->chips_per_floor);
1458}
1459
1460static inline int __init doc2001_init(struct mtd_info *mtd)
1461{
1462 struct nand_chip *this = mtd->priv;
1463 struct doc_priv *doc = this->priv;
1464
932394ac
WD
1465 this->read_byte = doc2001_read_byte;
1466 this->write_buf = doc2001_writebuf;
1467 this->read_buf = doc2001_readbuf;
1468 this->verify_buf = doc2001_verifybuf;
1469
1470 ReadDOC(doc->virtadr, ChipID);
1471 ReadDOC(doc->virtadr, ChipID);
1472 ReadDOC(doc->virtadr, ChipID);
1473 if (ReadDOC(doc->virtadr, ChipID) != DOC_ChipID_DocMil) {
1474 /* It's not a Millennium; it's one of the newer
ac7eb8a3 1475 DiskOnChip 2000 units with a similar ASIC.
932394ac
WD
1476 Treat it like a Millennium, except that it
1477 can have multiple chips. */
1478 doc2000_count_chips(mtd);
1479 mtd->name = "DiskOnChip 2000 (INFTL Model)";
1480 this->scan_bbt = inftl_scan_bbt;
1481 return (4 * doc->chips_per_floor);
1482 } else {
1483 /* Bog-standard Millennium */
1484 doc->chips_per_floor = 1;
1485 mtd->name = "DiskOnChip Millennium";
1486 this->scan_bbt = nftl_scan_bbt;
1487 return 1;
1488 }
1489}
1490
1491static inline int __init doc2001plus_init(struct mtd_info *mtd)
1492{
1493 struct nand_chip *this = mtd->priv;
1494 struct doc_priv *doc = this->priv;
1495
932394ac
WD
1496 this->read_byte = doc2001plus_read_byte;
1497 this->write_buf = doc2001plus_writebuf;
1498 this->read_buf = doc2001plus_readbuf;
1499 this->verify_buf = doc2001plus_verifybuf;
1500 this->scan_bbt = inftl_scan_bbt;
cfa460ad 1501 this->cmd_ctrl = NULL;
932394ac
WD
1502 this->select_chip = doc2001plus_select_chip;
1503 this->cmdfunc = doc2001plus_command;
cfa460ad 1504 this->ecc.hwctl = doc2001plus_enable_hwecc;
932394ac
WD
1505
1506 doc->chips_per_floor = 1;
1507 mtd->name = "DiskOnChip Millennium Plus";
1508
1509 return 1;
1510}
1511
cfa460ad 1512static int __init doc_probe(unsigned long physadr)
932394ac
WD
1513{
1514 unsigned char ChipID;
1515 struct mtd_info *mtd;
1516 struct nand_chip *nand;
1517 struct doc_priv *doc;
1518 void __iomem *virtadr;
1519 unsigned char save_control;
1520 unsigned char tmp, tmpb, tmpc;
1521 int reg, len, numchips;
1522 int ret = 0;
1523
1524 virtadr = ioremap(physadr, DOC_IOREMAP_LEN);
1525 if (!virtadr) {
1526 printk(KERN_ERR "Diskonchip ioremap failed: 0x%x bytes at 0x%lx\n", DOC_IOREMAP_LEN, physadr);
1527 return -EIO;
1528 }
1529
1530 /* It's not possible to cleanly detect the DiskOnChip - the
1531 * bootup procedure will put the device into reset mode, and
1532 * it's not possible to talk to it without actually writing
1533 * to the DOCControl register. So we store the current contents
1534 * of the DOCControl register's location, in case we later decide
1535 * that it's not a DiskOnChip, and want to put it back how we
ac7eb8a3 1536 * found it.
932394ac
WD
1537 */
1538 save_control = ReadDOC(virtadr, DOCControl);
1539
1540 /* Reset the DiskOnChip ASIC */
cfa460ad
WJ
1541 WriteDOC(DOC_MODE_CLR_ERR | DOC_MODE_MDWREN | DOC_MODE_RESET, virtadr, DOCControl);
1542 WriteDOC(DOC_MODE_CLR_ERR | DOC_MODE_MDWREN | DOC_MODE_RESET, virtadr, DOCControl);
932394ac
WD
1543
1544 /* Enable the DiskOnChip ASIC */
cfa460ad
WJ
1545 WriteDOC(DOC_MODE_CLR_ERR | DOC_MODE_MDWREN | DOC_MODE_NORMAL, virtadr, DOCControl);
1546 WriteDOC(DOC_MODE_CLR_ERR | DOC_MODE_MDWREN | DOC_MODE_NORMAL, virtadr, DOCControl);
932394ac
WD
1547
1548 ChipID = ReadDOC(virtadr, ChipID);
1549
cfa460ad 1550 switch (ChipID) {
932394ac
WD
1551 case DOC_ChipID_Doc2k:
1552 reg = DoC_2k_ECCStatus;
1553 break;
1554 case DOC_ChipID_DocMil:
1555 reg = DoC_ECCConf;
1556 break;
1557 case DOC_ChipID_DocMilPlus16:
1558 case DOC_ChipID_DocMilPlus32:
1559 case 0:
1560 /* Possible Millennium Plus, need to do more checks */
1561 /* Possibly release from power down mode */
1562 for (tmp = 0; (tmp < 4); tmp++)
1563 ReadDOC(virtadr, Mplus_Power);
1564
1565 /* Reset the Millennium Plus ASIC */
cfa460ad 1566 tmp = DOC_MODE_RESET | DOC_MODE_MDWREN | DOC_MODE_RST_LAT | DOC_MODE_BDECT;
932394ac
WD
1567 WriteDOC(tmp, virtadr, Mplus_DOCControl);
1568 WriteDOC(~tmp, virtadr, Mplus_CtrlConfirm);
1569
1570 mdelay(1);
1571 /* Enable the Millennium Plus ASIC */
cfa460ad 1572 tmp = DOC_MODE_NORMAL | DOC_MODE_MDWREN | DOC_MODE_RST_LAT | DOC_MODE_BDECT;
932394ac
WD
1573 WriteDOC(tmp, virtadr, Mplus_DOCControl);
1574 WriteDOC(~tmp, virtadr, Mplus_CtrlConfirm);
1575 mdelay(1);
1576
1577 ChipID = ReadDOC(virtadr, ChipID);
1578
1579 switch (ChipID) {
1580 case DOC_ChipID_DocMilPlus16:
1581 reg = DoC_Mplus_Toggle;
1582 break;
1583 case DOC_ChipID_DocMilPlus32:
1584 printk(KERN_ERR "DiskOnChip Millennium Plus 32MB is not supported, ignoring.\n");
1585 default:
1586 ret = -ENODEV;
1587 goto notfound;
1588 }
1589 break;
1590
1591 default:
1592 ret = -ENODEV;
1593 goto notfound;
1594 }
1595 /* Check the TOGGLE bit in the ECC register */
cfa460ad 1596 tmp = ReadDOC_(virtadr, reg) & DOC_TOGGLE_BIT;
932394ac
WD
1597 tmpb = ReadDOC_(virtadr, reg) & DOC_TOGGLE_BIT;
1598 tmpc = ReadDOC_(virtadr, reg) & DOC_TOGGLE_BIT;
1599 if ((tmp == tmpb) || (tmp != tmpc)) {
1600 printk(KERN_WARNING "Possible DiskOnChip at 0x%lx failed TOGGLE test, dropping.\n", physadr);
1601 ret = -ENODEV;
1602 goto notfound;
1603 }
1604
1605 for (mtd = doclist; mtd; mtd = doc->nextdoc) {
1606 unsigned char oldval;
1607 unsigned char newval;
1608 nand = mtd->priv;
1609 doc = nand->priv;
1610 /* Use the alias resolution register to determine if this is
1611 in fact the same DOC aliased to a new address. If writes
1612 to one chip's alias resolution register change the value on
1613 the other chip, they're the same chip. */
1614 if (ChipID == DOC_ChipID_DocMilPlus16) {
1615 oldval = ReadDOC(doc->virtadr, Mplus_AliasResolution);
1616 newval = ReadDOC(virtadr, Mplus_AliasResolution);
1617 } else {
1618 oldval = ReadDOC(doc->virtadr, AliasResolution);
1619 newval = ReadDOC(virtadr, AliasResolution);
1620 }
1621 if (oldval != newval)
1622 continue;
1623 if (ChipID == DOC_ChipID_DocMilPlus16) {
1624 WriteDOC(~newval, virtadr, Mplus_AliasResolution);
1625 oldval = ReadDOC(doc->virtadr, Mplus_AliasResolution);
cfa460ad 1626 WriteDOC(newval, virtadr, Mplus_AliasResolution); // restore it
932394ac
WD
1627 } else {
1628 WriteDOC(~newval, virtadr, AliasResolution);
1629 oldval = ReadDOC(doc->virtadr, AliasResolution);
cfa460ad 1630 WriteDOC(newval, virtadr, AliasResolution); // restore it
932394ac
WD
1631 }
1632 newval = ~newval;
1633 if (oldval == newval) {
1634 printk(KERN_DEBUG "Found alias of DOC at 0x%lx to 0x%lx\n", doc->physadr, physadr);
1635 goto notfound;
1636 }
1637 }
1638
1639 printk(KERN_NOTICE "DiskOnChip found at 0x%lx\n", physadr);
1640
1641 len = sizeof(struct mtd_info) +
cfa460ad
WJ
1642 sizeof(struct nand_chip) + sizeof(struct doc_priv) + (2 * sizeof(struct nand_bbt_descr));
1643 mtd = kzalloc(len, GFP_KERNEL);
932394ac
WD
1644 if (!mtd) {
1645 printk(KERN_ERR "DiskOnChip kmalloc (%d bytes) failed!\n", len);
1646 ret = -ENOMEM;
1647 goto fail;
1648 }
932394ac
WD
1649
1650 nand = (struct nand_chip *) (mtd + 1);
1651 doc = (struct doc_priv *) (nand + 1);
1652 nand->bbt_td = (struct nand_bbt_descr *) (doc + 1);
1653 nand->bbt_md = nand->bbt_td + 1;
1654
1655 mtd->priv = nand;
1656 mtd->owner = THIS_MODULE;
1657
1658 nand->priv = doc;
1659 nand->select_chip = doc200x_select_chip;
cfa460ad 1660 nand->cmd_ctrl = doc200x_hwcontrol;
932394ac
WD
1661 nand->dev_ready = doc200x_dev_ready;
1662 nand->waitfunc = doc200x_wait;
1663 nand->block_bad = doc200x_block_bad;
cfa460ad
WJ
1664 nand->ecc.hwctl = doc200x_enable_hwecc;
1665 nand->ecc.calculate = doc200x_calculate_ecc;
1666 nand->ecc.correct = doc200x_correct_data;
932394ac 1667
cfa460ad
WJ
1668 nand->ecc.layout = &doc200x_oobinfo;
1669 nand->ecc.mode = NAND_ECC_HW_SYNDROME;
1670 nand->ecc.size = 512;
1671 nand->ecc.bytes = 6;
1672 nand->options = NAND_USE_FLASH_BBT;
932394ac
WD
1673
1674 doc->physadr = physadr;
1675 doc->virtadr = virtadr;
1676 doc->ChipID = ChipID;
1677 doc->curfloor = -1;
1678 doc->curchip = -1;
1679 doc->mh0_page = -1;
1680 doc->mh1_page = -1;
1681 doc->nextdoc = doclist;
1682
1683 if (ChipID == DOC_ChipID_Doc2k)
1684 numchips = doc2000_init(mtd);
1685 else if (ChipID == DOC_ChipID_DocMilPlus16)
1686 numchips = doc2001plus_init(mtd);
1687 else
1688 numchips = doc2001_init(mtd);
1689
1690 if ((ret = nand_scan(mtd, numchips))) {
1691 /* DBB note: i believe nand_release is necessary here, as
1692 buffers may have been allocated in nand_base. Check with
1693 Thomas. FIX ME! */
1694 /* nand_release will call del_mtd_device, but we haven't yet
1695 added it. This is handled without incident by
1696 del_mtd_device, as far as I can tell. */
1697 nand_release(mtd);
1698 kfree(mtd);
1699 goto fail;
1700 }
1701
1702 /* Success! */
1703 doclist = mtd;
1704 return 0;
1705
cfa460ad 1706 notfound:
932394ac
WD
1707 /* Put back the contents of the DOCControl register, in case it's not
1708 actually a DiskOnChip. */
1709 WriteDOC(save_control, virtadr, DOCControl);
cfa460ad 1710 fail:
932394ac
WD
1711 iounmap(virtadr);
1712 return ret;
1713}
1714
1715static void release_nanddoc(void)
1716{
53677ef1 1717 struct mtd_info *mtd, *nextmtd;
932394ac
WD
1718 struct nand_chip *nand;
1719 struct doc_priv *doc;
1720
1721 for (mtd = doclist; mtd; mtd = nextmtd) {
1722 nand = mtd->priv;
1723 doc = nand->priv;
1724
1725 nextmtd = doc->nextdoc;
1726 nand_release(mtd);
1727 iounmap(doc->virtadr);
1728 kfree(mtd);
1729 }
1730}
1731
1732static int __init init_nanddoc(void)
1733{
1734 int i, ret = 0;
1735
1736 /* We could create the decoder on demand, if memory is a concern.
ac7eb8a3 1737 * This way we have it handy, if an error happens
932394ac
WD
1738 *
1739 * Symbolsize is 10 (bits)
1740 * Primitve polynomial is x^10+x^3+1
1741 * first consecutive root is 510
1742 * primitve element to generate roots = 1
1743 * generator polinomial degree = 4
1744 */
1745 rs_decoder = init_rs(10, 0x409, FCR, 1, NROOTS);
53677ef1 1746 if (!rs_decoder) {
cfa460ad 1747 printk(KERN_ERR "DiskOnChip: Could not create a RS decoder\n");
932394ac
WD
1748 return -ENOMEM;
1749 }
1750
1751 if (doc_config_location) {
1752 printk(KERN_INFO "Using configured DiskOnChip probe address 0x%lx\n", doc_config_location);
1753 ret = doc_probe(doc_config_location);
1754 if (ret < 0)
1755 goto outerr;
1756 } else {
cfa460ad 1757 for (i = 0; (doc_locations[i] != 0xffffffff); i++) {
932394ac
WD
1758 doc_probe(doc_locations[i]);
1759 }
1760 }
1761 /* No banner message any more. Print a message if no DiskOnChip
1762 found, so the user knows we at least tried. */
1763 if (!doclist) {
1764 printk(KERN_INFO "No valid DiskOnChip devices found\n");
1765 ret = -ENODEV;
1766 goto outerr;
1767 }
1768 return 0;
cfa460ad 1769 outerr:
932394ac
WD
1770 free_rs(rs_decoder);
1771 return ret;
1772}
1773
1774static void __exit cleanup_nanddoc(void)
1775{
1776 /* Cleanup the nand/DoC resources */
1777 release_nanddoc();
1778
1779 /* Free the reed solomon resources */
1780 if (rs_decoder) {
1781 free_rs(rs_decoder);
1782 }
1783}
1784
1785module_init(init_nanddoc);
1786module_exit(cleanup_nanddoc);
1787
1788MODULE_LICENSE("GPL");
1789MODULE_AUTHOR("David Woodhouse <dwmw2@infradead.org>");
1790MODULE_DESCRIPTION("M-Systems DiskOnChip 2000, Millennium and Millennium Plus device driver\n");
6db39708 1791#endif