ftp://ftp.kernel.org/pub/linux/kernel/v2.6/linux-2.6.6.tar.bz2
[linux-2.6.git] / drivers / char / nwflash.c
1 /*
2  * Flash memory interface rev.5 driver for the Intel
3  * Flash chips used on the NetWinder.
4  *
5  * 20/08/2000   RMK     use __ioremap to map flash into virtual memory
6  *                      make a few more places use "volatile"
7  * 22/05/2001   RMK     - Lock read against write
8  *                      - merge printk level changes (with mods) from Alan Cox.
9  *                      - use *ppos as the file position, not file->f_pos.
10  *                      - fix check for out of range pos and r/w size
11  *
12  * Please note that we are tampering with the only flash chip in the
13  * machine, which contains the bootup code.  We therefore have the
14  * power to convert these machines into doorstops...
15  */
16
17 #include <linux/module.h>
18 #include <linux/types.h>
19 #include <linux/fs.h>
20 #include <linux/errno.h>
21 #include <linux/mm.h>
22 #include <linux/delay.h>
23 #include <linux/proc_fs.h>
24 #include <linux/sched.h>
25 #include <linux/miscdevice.h>
26 #include <linux/spinlock.h>
27 #include <linux/rwsem.h>
28 #include <linux/init.h>
29 #include <linux/smp_lock.h>
30
31 #include <asm/hardware/dec21285.h>
32 #include <asm/io.h>
33 #include <asm/leds.h>
34 #include <asm/mach-types.h>
35 #include <asm/system.h>
36 #include <asm/uaccess.h>
37
38 /*****************************************************************************/
39 #include <asm/nwflash.h>
40
41 #define NWFLASH_VERSION "6.4"
42
43 static void kick_open(void);
44 static int get_flash_id(void);
45 static int erase_block(int nBlock);
46 static int write_block(unsigned long p, const char *buf, int count);
47 static int flash_ioctl(struct inode *inodep, struct file *filep, unsigned int cmd, unsigned long arg);
48 static ssize_t flash_read(struct file *file, char *buf, size_t count, loff_t * ppos);
49 static ssize_t flash_write(struct file *file, const char *buf, size_t count, loff_t * ppos);
50 static loff_t flash_llseek(struct file *file, loff_t offset, int orig);
51
52 #define KFLASH_SIZE     1024*1024       //1 Meg
53 #define KFLASH_SIZE4    4*1024*1024     //4 Meg
54 #define KFLASH_ID       0x89A6          //Intel flash
55 #define KFLASH_ID4      0xB0D4          //Intel flash 4Meg
56
57 static int flashdebug;          //if set - we will display progress msgs
58
59 static int gbWriteEnable;
60 static int gbWriteBase64Enable;
61 static volatile unsigned char *FLASH_BASE;
62 static int gbFlashSize = KFLASH_SIZE;
63 static DECLARE_MUTEX(nwflash_sem);
64
65 extern spinlock_t gpio_lock;
66
67 /*
68  * the delay routine - it is often required to let the flash "breeze"...
69  */
70 void flash_wait(int timeout)
71 {
72         current->state = TASK_INTERRUPTIBLE;
73         schedule_timeout(timeout);
74 }
75
76 static int get_flash_id(void)
77 {
78         volatile unsigned int c1, c2;
79
80         /*
81          * try to get flash chip ID
82          */
83         kick_open();
84         c2 = inb(0x80);
85         *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0x90;
86         udelay(15);
87         c1 = *(volatile unsigned char *) FLASH_BASE;
88         c2 = inb(0x80);
89
90         /*
91          * on 4 Meg flash the second byte is actually at offset 2...
92          */
93         if (c1 == 0xB0)
94                 c2 = *(volatile unsigned char *) (FLASH_BASE + 2);
95         else
96                 c2 = *(volatile unsigned char *) (FLASH_BASE + 1);
97
98         c2 += (c1 << 8);
99
100         /*
101          * set it back to read mode
102          */
103         *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0xFF;
104
105         if (c2 == KFLASH_ID4)
106                 gbFlashSize = KFLASH_SIZE4;
107
108         return c2;
109 }
110
111 static int flash_ioctl(struct inode *inodep, struct file *filep, unsigned int cmd, unsigned long arg)
112 {
113         switch (cmd) {
114         case CMD_WRITE_DISABLE:
115                 gbWriteBase64Enable = 0;
116                 gbWriteEnable = 0;
117                 break;
118
119         case CMD_WRITE_ENABLE:
120                 gbWriteEnable = 1;
121                 break;
122
123         case CMD_WRITE_BASE64K_ENABLE:
124                 gbWriteBase64Enable = 1;
125                 break;
126
127         default:
128                 gbWriteBase64Enable = 0;
129                 gbWriteEnable = 0;
130                 return -EINVAL;
131         }
132         return 0;
133 }
134
135 static ssize_t flash_read(struct file *file, char *buf, size_t size, loff_t * ppos)
136 {
137         unsigned long p = *ppos;
138         unsigned int count = size;
139         int ret = 0;
140
141         if (flashdebug)
142                 printk(KERN_DEBUG "flash_read: flash_read: offset=0x%lX, buffer=%p, count=0x%X.\n",
143                        p, buf, count);
144
145         if (count)
146                 ret = -ENXIO;
147
148         if (p < gbFlashSize) {
149                 if (count > gbFlashSize - p)
150                         count = gbFlashSize - p;
151
152                 /*
153                  * We now lock against reads and writes. --rmk
154                  */
155                 if (down_interruptible(&nwflash_sem))
156                         return -ERESTARTSYS;
157
158                 ret = copy_to_user(buf, (void *)(FLASH_BASE + p), count);
159                 if (ret == 0) {
160                         ret = count;
161                         *ppos += count;
162                 } else
163                         ret = -EFAULT;
164                 up(&nwflash_sem);
165         }
166         return ret;
167 }
168
169 static ssize_t flash_write(struct file *file, const char *buf, size_t size, loff_t * ppos)
170 {
171         unsigned long p = *ppos;
172         unsigned int count = size;
173         int written;
174         int nBlock, temp, rc;
175         int i, j;
176
177         if (flashdebug)
178                 printk("flash_write: offset=0x%lX, buffer=0x%p, count=0x%X.\n",
179                        p, buf, count);
180
181         if (!gbWriteEnable)
182                 return -EINVAL;
183
184         if (p < 64 * 1024 && (!gbWriteBase64Enable))
185                 return -EINVAL;
186
187         /*
188          * check for out of range pos or count
189          */
190         if (p >= gbFlashSize)
191                 return count ? -ENXIO : 0;
192
193         if (count > gbFlashSize - p)
194                 count = gbFlashSize - p;
195                         
196         if (verify_area(VERIFY_READ, buf, count))
197                 return -EFAULT;
198
199         /*
200          * We now lock against reads and writes. --rmk
201          */
202         if (down_interruptible(&nwflash_sem))
203                 return -ERESTARTSYS;
204
205         written = 0;
206
207         leds_event(led_claim);
208         leds_event(led_green_on);
209
210         nBlock = (int) p >> 16; //block # of 64K bytes
211
212         /*
213          * # of 64K blocks to erase and write
214          */
215         temp = ((int) (p + count) >> 16) - nBlock + 1;
216
217         /*
218          * write ends at exactly 64k boundary?
219          */
220         if (((int) (p + count) & 0xFFFF) == 0)
221                 temp -= 1;
222
223         if (flashdebug)
224                 printk(KERN_DEBUG "flash_write: writing %d block(s) "
225                         "starting at %d.\n", temp, nBlock);
226
227         for (; temp; temp--, nBlock++) {
228                 if (flashdebug)
229                         printk(KERN_DEBUG "flash_write: erasing block %d.\n", nBlock);
230
231                 /*
232                  * first we have to erase the block(s), where we will write...
233                  */
234                 i = 0;
235                 j = 0;
236           RetryBlock:
237                 do {
238                         rc = erase_block(nBlock);
239                         i++;
240                 } while (rc && i < 10);
241
242                 if (rc) {
243                         printk(KERN_ERR "flash_write: erase error %x\n", rc);
244                         break;
245                 }
246                 if (flashdebug)
247                         printk(KERN_DEBUG "flash_write: writing offset %lX, from buf "
248                                 "%p, bytes left %X.\n", p, buf, count - written);
249
250                 /*
251                  * write_block will limit write to space left in this block
252                  */
253                 rc = write_block(p, buf, count - written);
254                 j++;
255
256                 /*
257                  * if somehow write verify failed? Can't happen??
258                  */
259                 if (!rc) {
260                         /*
261                          * retry up to 10 times
262                          */
263                         if (j < 10)
264                                 goto RetryBlock;
265                         else
266                                 /*
267                                  * else quit with error...
268                                  */
269                                 rc = -1;
270
271                 }
272                 if (rc < 0) {
273                         printk(KERN_ERR "flash_write: write error %X\n", rc);
274                         break;
275                 }
276                 p += rc;
277                 buf += rc;
278                 written += rc;
279                 *ppos += rc;
280
281                 if (flashdebug)
282                         printk(KERN_DEBUG "flash_write: written 0x%X bytes OK.\n", written);
283         }
284
285         /*
286          * restore reg on exit
287          */
288         leds_event(led_release);
289
290         up(&nwflash_sem);
291
292         return written;
293 }
294
295
296 /*
297  * The memory devices use the full 32/64 bits of the offset, and so we cannot
298  * check against negative addresses: they are ok. The return value is weird,
299  * though, in that case (0).
300  *
301  * also note that seeking relative to the "end of file" isn't supported:
302  * it has no meaning, so it returns -EINVAL.
303  */
304 static loff_t flash_llseek(struct file *file, loff_t offset, int orig)
305 {
306         loff_t ret;
307
308         lock_kernel();
309         if (flashdebug)
310                 printk(KERN_DEBUG "flash_llseek: offset=0x%X, orig=0x%X.\n",
311                        (unsigned int) offset, orig);
312
313         switch (orig) {
314         case 0:
315                 if (offset < 0) {
316                         ret = -EINVAL;
317                         break;
318                 }
319
320                 if ((unsigned int) offset > gbFlashSize) {
321                         ret = -EINVAL;
322                         break;
323                 }
324
325                 file->f_pos = (unsigned int) offset;
326                 ret = file->f_pos;
327                 break;
328         case 1:
329                 if ((file->f_pos + offset) > gbFlashSize) {
330                         ret = -EINVAL;
331                         break;
332                 }
333                 if ((file->f_pos + offset) < 0) {
334                         ret = -EINVAL;
335                         break;
336                 }
337                 file->f_pos += offset;
338                 ret = file->f_pos;
339                 break;
340         default:
341                 ret = -EINVAL;
342         }
343         unlock_kernel();
344         return ret;
345 }
346
347
348 /*
349  * assume that main Write routine did the parameter checking...
350  * so just go ahead and erase, what requested!
351  */
352
353 static int erase_block(int nBlock)
354 {
355         volatile unsigned int c1;
356         volatile unsigned char *pWritePtr;
357         unsigned long timeout;
358         int temp, temp1;
359
360         /*
361          * orange LED == erase
362          */
363         leds_event(led_amber_on);
364
365         /*
366          * reset footbridge to the correct offset 0 (...0..3)
367          */
368         *CSR_ROMWRITEREG = 0;
369
370         /*
371          * dummy ROM read
372          */
373         c1 = *(volatile unsigned char *) (FLASH_BASE + 0x8000);
374
375         kick_open();
376         /*
377          * reset status if old errors
378          */
379         *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0x50;
380
381         /*
382          * erase a block...
383          * aim at the middle of a current block...
384          */
385         pWritePtr = (unsigned char *) ((unsigned int) (FLASH_BASE + 0x8000 + (nBlock << 16)));
386         /*
387          * dummy read
388          */
389         c1 = *pWritePtr;
390
391         kick_open();
392         /*
393          * erase
394          */
395         *(volatile unsigned char *) pWritePtr = 0x20;
396
397         /*
398          * confirm
399          */
400         *(volatile unsigned char *) pWritePtr = 0xD0;
401
402         /*
403          * wait 10 ms
404          */
405         flash_wait(HZ / 100);
406
407         /*
408          * wait while erasing in process (up to 10 sec)
409          */
410         timeout = jiffies + 10 * HZ;
411         c1 = 0;
412         while (!(c1 & 0x80) && time_before(jiffies, timeout)) {
413                 flash_wait(HZ / 100);
414                 /*
415                  * read any address
416                  */
417                 c1 = *(volatile unsigned char *) (pWritePtr);
418                 //              printk("Flash_erase: status=%X.\n",c1);
419         }
420
421         /*
422          * set flash for normal read access
423          */
424         kick_open();
425 //      *(volatile unsigned char*)(FLASH_BASE+0x8000) = 0xFF;
426         *(volatile unsigned char *) pWritePtr = 0xFF;   //back to normal operation
427
428         /*
429          * check if erase errors were reported
430          */
431         if (c1 & 0x20) {
432                 printk(KERN_ERR "flash_erase: err at %p\n", pWritePtr);
433
434                 /*
435                  * reset error
436                  */
437                 *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0x50;
438                 return -2;
439         }
440
441         /*
442          * just to make sure - verify if erased OK...
443          */
444         flash_wait(HZ / 100);
445
446         pWritePtr = (unsigned char *) ((unsigned int) (FLASH_BASE + (nBlock << 16)));
447
448         for (temp = 0; temp < 16 * 1024; temp++, pWritePtr += 4) {
449                 if ((temp1 = *(volatile unsigned int *) pWritePtr) != 0xFFFFFFFF) {
450                         printk(KERN_ERR "flash_erase: verify err at %p = %X\n",
451                                pWritePtr, temp1);
452                         return -1;
453                 }
454         }
455
456         return 0;
457
458 }
459
460 /*
461  * write_block will limit number of bytes written to the space in this block
462  */
463 static int write_block(unsigned long p, const char *buf, int count)
464 {
465         volatile unsigned int c1;
466         volatile unsigned int c2;
467         unsigned char *pWritePtr;
468         unsigned int uAddress;
469         unsigned int offset;
470         unsigned long timeout;
471         unsigned long timeout1;
472
473         /*
474          * red LED == write
475          */
476         leds_event(led_amber_off);
477         leds_event(led_red_on);
478
479         pWritePtr = (unsigned char *) ((unsigned int) (FLASH_BASE + p));
480
481         /*
482          * check if write will end in this block....
483          */
484         offset = p & 0xFFFF;
485
486         if (offset + count > 0x10000)
487                 count = 0x10000 - offset;
488
489         /*
490          * wait up to 30 sec for this block
491          */
492         timeout = jiffies + 30 * HZ;
493
494         for (offset = 0; offset < count; offset++, pWritePtr++) {
495                 uAddress = (unsigned int) pWritePtr;
496                 uAddress &= 0xFFFFFFFC;
497                 if (__get_user(c2, buf + offset))
498                         return -EFAULT;
499
500           WriteRetry:
501                 /*
502                  * dummy read
503                  */
504                 c1 = *(volatile unsigned char *) (FLASH_BASE + 0x8000);
505
506                 /*
507                  * kick open the write gate
508                  */
509                 kick_open();
510
511                 /*
512                  * program footbridge to the correct offset...0..3
513                  */
514                 *CSR_ROMWRITEREG = (unsigned int) pWritePtr & 3;
515
516                 /*
517                  * write cmd
518                  */
519                 *(volatile unsigned char *) (uAddress) = 0x40;
520
521                 /*
522                  * data to write
523                  */
524                 *(volatile unsigned char *) (uAddress) = c2;
525
526                 /*
527                  * get status
528                  */
529                 *(volatile unsigned char *) (FLASH_BASE + 0x10000) = 0x70;
530
531                 c1 = 0;
532
533                 /*
534                  * wait up to 1 sec for this byte
535                  */
536                 timeout1 = jiffies + 1 * HZ;
537
538                 /*
539                  * while not ready...
540                  */
541                 while (!(c1 & 0x80) && time_before(jiffies, timeout1))
542                         c1 = *(volatile unsigned char *) (FLASH_BASE + 0x8000);
543
544                 /*
545                  * if timeout getting status
546                  */
547                 if (time_after_eq(jiffies, timeout1)) {
548                         kick_open();
549                         /*
550                          * reset err
551                          */
552                         *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0x50;
553
554                         goto WriteRetry;
555                 }
556                 /*
557                  * switch on read access, as a default flash operation mode
558                  */
559                 kick_open();
560                 /*
561                  * read access
562                  */
563                 *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0xFF;
564
565                 /*
566                  * if hardware reports an error writing, and not timeout - 
567                  * reset the chip and retry
568                  */
569                 if (c1 & 0x10) {
570                         kick_open();
571                         /*
572                          * reset err
573                          */
574                         *(volatile unsigned char *) (FLASH_BASE + 0x8000) = 0x50;
575
576                         /*
577                          * before timeout?
578                          */
579                         if (time_before(jiffies, timeout)) {
580                                 if (flashdebug)
581                                         printk(KERN_DEBUG "write_block: Retrying write at 0x%X)n",
582                                                pWritePtr - FLASH_BASE);
583
584                                 /*
585                                  * no LED == waiting
586                                  */
587                                 leds_event(led_amber_off);
588                                 /*
589                                  * wait couple ms
590                                  */
591                                 flash_wait(HZ / 100);
592                                 /*
593                                  * red LED == write
594                                  */
595                                 leds_event(led_red_on);
596
597                                 goto WriteRetry;
598                         } else {
599                                 printk(KERN_ERR "write_block: timeout at 0x%X\n",
600                                        pWritePtr - FLASH_BASE);
601                                 /*
602                                  * return error -2
603                                  */
604                                 return -2;
605
606                         }
607                 }
608         }
609
610         /*
611          * green LED == read/verify
612          */
613         leds_event(led_amber_off);
614         leds_event(led_green_on);
615
616         flash_wait(HZ / 100);
617
618         pWritePtr = (unsigned char *) ((unsigned int) (FLASH_BASE + p));
619
620         for (offset = 0; offset < count; offset++) {
621                 char c, c1;
622                 if (__get_user(c, buf))
623                         return -EFAULT;
624                 buf++;
625                 if ((c1 = *pWritePtr++) != c) {
626                         printk(KERN_ERR "write_block: verify error at 0x%X (%02X!=%02X)\n",
627                                pWritePtr - FLASH_BASE, c1, c);
628                         return 0;
629                 }
630         }
631
632         return count;
633 }
634
635
636 static void kick_open(void)
637 {
638         unsigned long flags;
639
640         /*
641          * we want to write a bit pattern XXX1 to Xilinx to enable
642          * the write gate, which will be open for about the next 2ms.
643          */
644         spin_lock_irqsave(&gpio_lock, flags);
645         cpld_modify(1, 1);
646         spin_unlock_irqrestore(&gpio_lock, flags);
647
648         /*
649          * let the ISA bus to catch on...
650          */
651         udelay(25);
652 }
653
654 static struct file_operations flash_fops =
655 {
656         .owner          = THIS_MODULE,
657         .llseek         = flash_llseek,
658         .read           = flash_read,
659         .write          = flash_write,
660         .ioctl          = flash_ioctl,
661 };
662
663 static struct miscdevice flash_miscdev =
664 {
665         FLASH_MINOR,
666         "nwflash",
667         &flash_fops
668 };
669
670 static int __init nwflash_init(void)
671 {
672         int ret = -ENODEV;
673
674         if (machine_is_netwinder()) {
675                 int id;
676
677                 FLASH_BASE = ioremap(DC21285_FLASH, KFLASH_SIZE4);
678                 if (!FLASH_BASE)
679                         goto out;
680
681                 id = get_flash_id();
682                 if ((id != KFLASH_ID) && (id != KFLASH_ID4)) {
683                         ret = -ENXIO;
684                         iounmap((void *)FLASH_BASE);
685                         printk("Flash: incorrect ID 0x%04X.\n", id);
686                         goto out;
687                 }
688
689                 printk("Flash ROM driver v.%s, flash device ID 0x%04X, size %d Mb.\n",
690                        NWFLASH_VERSION, id, gbFlashSize / (1024 * 1024));
691
692                 ret = misc_register(&flash_miscdev);
693                 if (ret < 0) {
694                         iounmap((void *)FLASH_BASE);
695                 }
696         }
697 out:
698         return ret;
699 }
700
701 static void __exit nwflash_exit(void)
702 {
703         misc_deregister(&flash_miscdev);
704         iounmap((void *)FLASH_BASE);
705 }
706
707 MODULE_LICENSE("GPL");
708
709 MODULE_PARM(flashdebug, "i");
710
711 module_init(nwflash_init);
712 module_exit(nwflash_exit);