1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23#include <linux/kernel.h>
24#include <linux/module.h>
25#include <linux/moduleparam.h>
26#include <linux/slab.h>
27#include <linux/init.h>
28#include <linux/sched.h>
29#include <linux/delay.h>
30#include <linux/interrupt.h>
31#include <linux/jiffies.h>
32#include <linux/mtd/mtd.h>
33#include <linux/mtd/onenand.h>
34#include <linux/mtd/partitions.h>
35
36#include <asm/io.h>
37
38
39
40
41
42#define MB_ERASE_MIN_BLK_COUNT 2
43#define MB_ERASE_MAX_BLK_COUNT 64
44
45
46static int flex_bdry[MAX_DIES * 2] = { -1, 0, -1, 0 };
47
48module_param_array(flex_bdry, int, NULL, 0400);
49MODULE_PARM_DESC(flex_bdry, "SLC Boundary information for Flex-OneNAND"
50 "Syntax:flex_bdry=DIE_BDRY,LOCK,..."
51 "DIE_BDRY: SLC boundary of the die"
52 "LOCK: Locking information for SLC boundary"
53 " : 0->Set boundary in unlocked status"
54 " : 1->Set boundary in locked status");
55
56
57static int otp;
58
59module_param(otp, int, 0400);
60MODULE_PARM_DESC(otp, "Corresponding behaviour of OneNAND in OTP"
61 "Syntax : otp=LOCK_TYPE"
62 "LOCK_TYPE : Keys issued, for specific OTP Lock type"
63 " : 0 -> Default (No Blocks Locked)"
64 " : 1 -> OTP Block lock"
65 " : 2 -> 1st Block lock"
66 " : 3 -> BOTH OTP Block and 1st Block lock");
67
68
69
70
71
72static struct nand_ecclayout onenand_oob_128 = {
73 .eccbytes = 64,
74 .eccpos = {
75 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
76 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
77 38, 39, 40, 41, 42, 43, 44, 45, 46, 47,
78 54, 55, 56, 57, 58, 59, 60, 61, 62, 63,
79 70, 71, 72, 73, 74, 75, 76, 77, 78, 79,
80 86, 87, 88, 89, 90, 91, 92, 93, 94, 95,
81 102, 103, 104, 105
82 },
83 .oobfree = {
84 {2, 4}, {18, 4}, {34, 4}, {50, 4},
85 {66, 4}, {82, 4}, {98, 4}, {114, 4}
86 }
87};
88
89
90
91
92static struct nand_ecclayout onenand_oob_64 = {
93 .eccbytes = 20,
94 .eccpos = {
95 8, 9, 10, 11, 12,
96 24, 25, 26, 27, 28,
97 40, 41, 42, 43, 44,
98 56, 57, 58, 59, 60,
99 },
100 .oobfree = {
101 {2, 3}, {14, 2}, {18, 3}, {30, 2},
102 {34, 3}, {46, 2}, {50, 3}, {62, 2}
103 }
104};
105
106
107
108
109static struct nand_ecclayout onenand_oob_32 = {
110 .eccbytes = 10,
111 .eccpos = {
112 8, 9, 10, 11, 12,
113 24, 25, 26, 27, 28,
114 },
115 .oobfree = { {2, 3}, {14, 2}, {18, 3}, {30, 2} }
116};
117
118static const unsigned char ffchars[] = {
119 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
120 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
121 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
122 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
123 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
124 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
125 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
126 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
127 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
128 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
129 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
130 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
131 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
132 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
133 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
134 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
135};
136
137
138
139
140
141
142
143static unsigned short onenand_readw(void __iomem *addr)
144{
145 return readw(addr);
146}
147
148
149
150
151
152
153
154
155static void onenand_writew(unsigned short value, void __iomem *addr)
156{
157 writew(value, addr);
158}
159
160
161
162
163
164
165
166
167
168static int onenand_block_address(struct onenand_chip *this, int block)
169{
170
171 if (block & this->density_mask)
172 return ONENAND_DDP_CHIP1 | (block ^ this->density_mask);
173
174 return block;
175}
176
177
178
179
180
181
182
183
184
185static int onenand_bufferram_address(struct onenand_chip *this, int block)
186{
187
188 if (block & this->density_mask)
189 return ONENAND_DDP_CHIP1;
190
191 return ONENAND_DDP_CHIP0;
192}
193
194
195
196
197
198
199
200
201
202static int onenand_page_address(int page, int sector)
203{
204
205 int fpa, fsa;
206
207 fpa = page & ONENAND_FPA_MASK;
208 fsa = sector & ONENAND_FSA_MASK;
209
210 return ((fpa << ONENAND_FPA_SHIFT) | fsa);
211}
212
213
214
215
216
217
218
219
220
221
222static int onenand_buffer_address(int dataram1, int sectors, int count)
223{
224 int bsa, bsc;
225
226
227 bsa = sectors & ONENAND_BSA_MASK;
228
229 if (dataram1)
230 bsa |= ONENAND_BSA_DATARAM1;
231 else
232 bsa |= ONENAND_BSA_DATARAM0;
233
234
235 bsc = count & ONENAND_BSC_MASK;
236
237 return ((bsa << ONENAND_BSA_SHIFT) | bsc);
238}
239
240
241
242
243
244
245static unsigned flexonenand_block(struct onenand_chip *this, loff_t addr)
246{
247 unsigned boundary, blk, die = 0;
248
249 if (ONENAND_IS_DDP(this) && addr >= this->diesize[0]) {
250 die = 1;
251 addr -= this->diesize[0];
252 }
253
254 boundary = this->boundary[die];
255
256 blk = addr >> (this->erase_shift - 1);
257 if (blk > boundary)
258 blk = (blk + boundary + 1) >> 1;
259
260 blk += die ? this->density_mask : 0;
261 return blk;
262}
263
264inline unsigned onenand_block(struct onenand_chip *this, loff_t addr)
265{
266 if (!FLEXONENAND(this))
267 return addr >> this->erase_shift;
268 return flexonenand_block(this, addr);
269}
270
271
272
273
274
275
276
277
278static loff_t flexonenand_addr(struct onenand_chip *this, int block)
279{
280 loff_t ofs = 0;
281 int die = 0, boundary;
282
283 if (ONENAND_IS_DDP(this) && block >= this->density_mask) {
284 block -= this->density_mask;
285 die = 1;
286 ofs = this->diesize[0];
287 }
288
289 boundary = this->boundary[die];
290 ofs += (loff_t)block << (this->erase_shift - 1);
291 if (block > (boundary + 1))
292 ofs += (loff_t)(block - boundary - 1) << (this->erase_shift - 1);
293 return ofs;
294}
295
296loff_t onenand_addr(struct onenand_chip *this, int block)
297{
298 if (!FLEXONENAND(this))
299 return (loff_t)block << this->erase_shift;
300 return flexonenand_addr(this, block);
301}
302EXPORT_SYMBOL(onenand_addr);
303
304
305
306
307
308
309
310static inline int onenand_get_density(int dev_id)
311{
312 int density = dev_id >> ONENAND_DEVICE_DENSITY_SHIFT;
313 return (density & ONENAND_DEVICE_DENSITY_MASK);
314}
315
316
317
318
319
320
321int flexonenand_region(struct mtd_info *mtd, loff_t addr)
322{
323 int i;
324
325 for (i = 0; i < mtd->numeraseregions; i++)
326 if (addr < mtd->eraseregions[i].offset)
327 break;
328 return i - 1;
329}
330EXPORT_SYMBOL(flexonenand_region);
331
332
333
334
335
336
337
338
339
340
341
342static int onenand_command(struct mtd_info *mtd, int cmd, loff_t addr, size_t len)
343{
344 struct onenand_chip *this = mtd->priv;
345 int value, block, page;
346
347
348 switch (cmd) {
349 case ONENAND_CMD_UNLOCK:
350 case ONENAND_CMD_LOCK:
351 case ONENAND_CMD_LOCK_TIGHT:
352 case ONENAND_CMD_UNLOCK_ALL:
353 block = -1;
354 page = -1;
355 break;
356
357 case FLEXONENAND_CMD_PI_ACCESS:
358
359 block = addr * this->density_mask;
360 page = -1;
361 break;
362
363 case ONENAND_CMD_ERASE:
364 case ONENAND_CMD_MULTIBLOCK_ERASE:
365 case ONENAND_CMD_ERASE_VERIFY:
366 case ONENAND_CMD_BUFFERRAM:
367 case ONENAND_CMD_OTP_ACCESS:
368 block = onenand_block(this, addr);
369 page = -1;
370 break;
371
372 case FLEXONENAND_CMD_READ_PI:
373 cmd = ONENAND_CMD_READ;
374 block = addr * this->density_mask;
375 page = 0;
376 break;
377
378 default:
379 block = onenand_block(this, addr);
380 if (FLEXONENAND(this))
381 page = (int) (addr - onenand_addr(this, block))>>\
382 this->page_shift;
383 else
384 page = (int) (addr >> this->page_shift);
385 if (ONENAND_IS_2PLANE(this)) {
386
387 block &= ~1;
388
389 if (addr & this->writesize)
390 block++;
391 page >>= 1;
392 }
393 page &= this->page_mask;
394 break;
395 }
396
397
398 if (cmd == ONENAND_CMD_BUFFERRAM) {
399
400 value = onenand_bufferram_address(this, block);
401 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS2);
402
403 if (ONENAND_IS_2PLANE(this) || ONENAND_IS_4KB_PAGE(this))
404
405 ONENAND_SET_BUFFERRAM0(this);
406 else
407
408 ONENAND_SET_NEXT_BUFFERRAM(this);
409
410 return 0;
411 }
412
413 if (block != -1) {
414
415 value = onenand_block_address(this, block);
416 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS1);
417
418
419 value = onenand_bufferram_address(this, block);
420 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS2);
421 }
422
423 if (page != -1) {
424
425 int sectors = 0, count = 0;
426 int dataram;
427
428 switch (cmd) {
429 case FLEXONENAND_CMD_RECOVER_LSB:
430 case ONENAND_CMD_READ:
431 case ONENAND_CMD_READOOB:
432 if (ONENAND_IS_4KB_PAGE(this))
433
434 dataram = ONENAND_SET_BUFFERRAM0(this);
435 else
436 dataram = ONENAND_SET_NEXT_BUFFERRAM(this);
437 break;
438
439 default:
440 if (ONENAND_IS_2PLANE(this) && cmd == ONENAND_CMD_PROG)
441 cmd = ONENAND_CMD_2X_PROG;
442 dataram = ONENAND_CURRENT_BUFFERRAM(this);
443 break;
444 }
445
446
447 value = onenand_page_address(page, sectors);
448 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS8);
449
450
451 value = onenand_buffer_address(dataram, sectors, count);
452 this->write_word(value, this->base + ONENAND_REG_START_BUFFER);
453 }
454
455
456 this->write_word(ONENAND_INT_CLEAR, this->base + ONENAND_REG_INTERRUPT);
457
458
459 this->write_word(cmd, this->base + ONENAND_REG_COMMAND);
460
461 return 0;
462}
463
464
465
466
467
468static inline int onenand_read_ecc(struct onenand_chip *this)
469{
470 int ecc, i, result = 0;
471
472 if (!FLEXONENAND(this) && !ONENAND_IS_4KB_PAGE(this))
473 return this->read_word(this->base + ONENAND_REG_ECC_STATUS);
474
475 for (i = 0; i < 4; i++) {
476 ecc = this->read_word(this->base + ONENAND_REG_ECC_STATUS + i*2);
477 if (likely(!ecc))
478 continue;
479 if (ecc & FLEXONENAND_UNCORRECTABLE_ERROR)
480 return ONENAND_ECC_2BIT_ALL;
481 else
482 result = ONENAND_ECC_1BIT_ALL;
483 }
484
485 return result;
486}
487
488
489
490
491
492
493
494
495
496
497static int onenand_wait(struct mtd_info *mtd, int state)
498{
499 struct onenand_chip * this = mtd->priv;
500 unsigned long timeout;
501 unsigned int flags = ONENAND_INT_MASTER;
502 unsigned int interrupt = 0;
503 unsigned int ctrl;
504
505
506 timeout = jiffies + msecs_to_jiffies(20);
507 while (time_before(jiffies, timeout)) {
508 interrupt = this->read_word(this->base + ONENAND_REG_INTERRUPT);
509
510 if (interrupt & flags)
511 break;
512
513 if (state != FL_READING && state != FL_PREPARING_ERASE)
514 cond_resched();
515 }
516
517 interrupt = this->read_word(this->base + ONENAND_REG_INTERRUPT);
518
519 ctrl = this->read_word(this->base + ONENAND_REG_CTRL_STATUS);
520
521
522
523
524
525
526 if (interrupt & ONENAND_INT_READ) {
527 int ecc = onenand_read_ecc(this);
528 if (ecc) {
529 if (ecc & ONENAND_ECC_2BIT_ALL) {
530 printk(KERN_ERR "%s: ECC error = 0x%04x\n",
531 __func__, ecc);
532 mtd->ecc_stats.failed++;
533 return -EBADMSG;
534 } else if (ecc & ONENAND_ECC_1BIT_ALL) {
535 printk(KERN_DEBUG "%s: correctable ECC error = 0x%04x\n",
536 __func__, ecc);
537 mtd->ecc_stats.corrected++;
538 }
539 }
540 } else if (state == FL_READING) {
541 printk(KERN_ERR "%s: read timeout! ctrl=0x%04x intr=0x%04x\n",
542 __func__, ctrl, interrupt);
543 return -EIO;
544 }
545
546 if (state == FL_PREPARING_ERASE && !(interrupt & ONENAND_INT_ERASE)) {
547 printk(KERN_ERR "%s: mb erase timeout! ctrl=0x%04x intr=0x%04x\n",
548 __func__, ctrl, interrupt);
549 return -EIO;
550 }
551
552 if (!(interrupt & ONENAND_INT_MASTER)) {
553 printk(KERN_ERR "%s: timeout! ctrl=0x%04x intr=0x%04x\n",
554 __func__, ctrl, interrupt);
555 return -EIO;
556 }
557
558
559 if (ctrl & ONENAND_CTRL_ERROR) {
560 printk(KERN_ERR "%s: controller error = 0x%04x\n",
561 __func__, ctrl);
562 if (ctrl & ONENAND_CTRL_LOCK)
563 printk(KERN_ERR "%s: it's locked error.\n", __func__);
564 return -EIO;
565 }
566
567 return 0;
568}
569
570
571
572
573
574
575
576
577static irqreturn_t onenand_interrupt(int irq, void *data)
578{
579 struct onenand_chip *this = data;
580
581
582 if (!this->complete.done)
583 complete(&this->complete);
584
585 return IRQ_HANDLED;
586}
587
588
589
590
591
592
593
594
595static int onenand_interrupt_wait(struct mtd_info *mtd, int state)
596{
597 struct onenand_chip *this = mtd->priv;
598
599 wait_for_completion(&this->complete);
600
601 return onenand_wait(mtd, state);
602}
603
604
605
606
607
608
609
610
611static int onenand_try_interrupt_wait(struct mtd_info *mtd, int state)
612{
613 struct onenand_chip *this = mtd->priv;
614 unsigned long remain, timeout;
615
616
617 this->wait = onenand_interrupt_wait;
618
619 timeout = msecs_to_jiffies(100);
620 remain = wait_for_completion_timeout(&this->complete, timeout);
621 if (!remain) {
622 printk(KERN_INFO "OneNAND: There's no interrupt. "
623 "We use the normal wait\n");
624
625
626 free_irq(this->irq, this);
627
628 this->wait = onenand_wait;
629 }
630
631 return onenand_wait(mtd, state);
632}
633
634
635
636
637
638
639
640
641
642static void onenand_setup_wait(struct mtd_info *mtd)
643{
644 struct onenand_chip *this = mtd->priv;
645 int syscfg;
646
647 init_completion(&this->complete);
648
649 if (this->irq <= 0) {
650 this->wait = onenand_wait;
651 return;
652 }
653
654 if (request_irq(this->irq, &onenand_interrupt,
655 IRQF_SHARED, "onenand", this)) {
656
657 this->wait = onenand_wait;
658 return;
659 }
660
661
662 syscfg = this->read_word(this->base + ONENAND_REG_SYS_CFG1);
663 syscfg |= ONENAND_SYS_CFG1_IOBE;
664 this->write_word(syscfg, this->base + ONENAND_REG_SYS_CFG1);
665
666 this->wait = onenand_try_interrupt_wait;
667}
668
669
670
671
672
673
674
675
676
677static inline int onenand_bufferram_offset(struct mtd_info *mtd, int area)
678{
679 struct onenand_chip *this = mtd->priv;
680
681 if (ONENAND_CURRENT_BUFFERRAM(this)) {
682
683 if (area == ONENAND_DATARAM)
684 return this->writesize;
685 if (area == ONENAND_SPARERAM)
686 return mtd->oobsize;
687 }
688
689 return 0;
690}
691
692
693
694
695
696
697
698
699
700
701
702static int onenand_read_bufferram(struct mtd_info *mtd, int area,
703 unsigned char *buffer, int offset, size_t count)
704{
705 struct onenand_chip *this = mtd->priv;
706 void __iomem *bufferram;
707
708 bufferram = this->base + area;
709
710 bufferram += onenand_bufferram_offset(mtd, area);
711
712 if (ONENAND_CHECK_BYTE_ACCESS(count)) {
713 unsigned short word;
714
715
716 count--;
717
718
719 word = this->read_word(bufferram + offset + count);
720 buffer[count] = (word & 0xff);
721 }
722
723 memcpy(buffer, bufferram + offset, count);
724
725 return 0;
726}
727
728
729
730
731
732
733
734
735
736
737
738static int onenand_sync_read_bufferram(struct mtd_info *mtd, int area,
739 unsigned char *buffer, int offset, size_t count)
740{
741 struct onenand_chip *this = mtd->priv;
742 void __iomem *bufferram;
743
744 bufferram = this->base + area;
745
746 bufferram += onenand_bufferram_offset(mtd, area);
747
748 this->mmcontrol(mtd, ONENAND_SYS_CFG1_SYNC_READ);
749
750 if (ONENAND_CHECK_BYTE_ACCESS(count)) {
751 unsigned short word;
752
753
754 count--;
755
756
757 word = this->read_word(bufferram + offset + count);
758 buffer[count] = (word & 0xff);
759 }
760
761 memcpy(buffer, bufferram + offset, count);
762
763 this->mmcontrol(mtd, 0);
764
765 return 0;
766}
767
768
769
770
771
772
773
774
775
776
777
778static int onenand_write_bufferram(struct mtd_info *mtd, int area,
779 const unsigned char *buffer, int offset, size_t count)
780{
781 struct onenand_chip *this = mtd->priv;
782 void __iomem *bufferram;
783
784 bufferram = this->base + area;
785
786 bufferram += onenand_bufferram_offset(mtd, area);
787
788 if (ONENAND_CHECK_BYTE_ACCESS(count)) {
789 unsigned short word;
790 int byte_offset;
791
792
793 count--;
794
795
796 byte_offset = offset + count;
797
798
799 word = this->read_word(bufferram + byte_offset);
800 word = (word & ~0xff) | buffer[count];
801 this->write_word(word, bufferram + byte_offset);
802 }
803
804 memcpy(bufferram + offset, buffer, count);
805
806 return 0;
807}
808
809
810
811
812
813
814
815
816
817static int onenand_get_2x_blockpage(struct mtd_info *mtd, loff_t addr)
818{
819 struct onenand_chip *this = mtd->priv;
820 int blockpage, block, page;
821
822
823 block = (int) (addr >> this->erase_shift) & ~1;
824
825 if (addr & this->writesize)
826 block++;
827 page = (int) (addr >> (this->page_shift + 1)) & this->page_mask;
828 blockpage = (block << 7) | page;
829
830 return blockpage;
831}
832
833
834
835
836
837
838
839
840
841static int onenand_check_bufferram(struct mtd_info *mtd, loff_t addr)
842{
843 struct onenand_chip *this = mtd->priv;
844 int blockpage, found = 0;
845 unsigned int i;
846
847 if (ONENAND_IS_2PLANE(this))
848 blockpage = onenand_get_2x_blockpage(mtd, addr);
849 else
850 blockpage = (int) (addr >> this->page_shift);
851
852
853 i = ONENAND_CURRENT_BUFFERRAM(this);
854 if (this->bufferram[i].blockpage == blockpage)
855 found = 1;
856 else {
857
858 i = ONENAND_NEXT_BUFFERRAM(this);
859 if (this->bufferram[i].blockpage == blockpage) {
860 ONENAND_SET_NEXT_BUFFERRAM(this);
861 found = 1;
862 }
863 }
864
865 if (found && ONENAND_IS_DDP(this)) {
866
867 int block = onenand_block(this, addr);
868 int value = onenand_bufferram_address(this, block);
869 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS2);
870 }
871
872 return found;
873}
874
875
876
877
878
879
880
881
882
883static void onenand_update_bufferram(struct mtd_info *mtd, loff_t addr,
884 int valid)
885{
886 struct onenand_chip *this = mtd->priv;
887 int blockpage;
888 unsigned int i;
889
890 if (ONENAND_IS_2PLANE(this))
891 blockpage = onenand_get_2x_blockpage(mtd, addr);
892 else
893 blockpage = (int) (addr >> this->page_shift);
894
895
896 i = ONENAND_NEXT_BUFFERRAM(this);
897 if (this->bufferram[i].blockpage == blockpage)
898 this->bufferram[i].blockpage = -1;
899
900
901 i = ONENAND_CURRENT_BUFFERRAM(this);
902 if (valid)
903 this->bufferram[i].blockpage = blockpage;
904 else
905 this->bufferram[i].blockpage = -1;
906}
907
908
909
910
911
912
913
914
915
916static void onenand_invalidate_bufferram(struct mtd_info *mtd, loff_t addr,
917 unsigned int len)
918{
919 struct onenand_chip *this = mtd->priv;
920 int i;
921 loff_t end_addr = addr + len;
922
923
924 for (i = 0; i < MAX_BUFFERRAM; i++) {
925 loff_t buf_addr = this->bufferram[i].blockpage << this->page_shift;
926 if (buf_addr >= addr && buf_addr < end_addr)
927 this->bufferram[i].blockpage = -1;
928 }
929}
930
931
932
933
934
935
936
937
938static int onenand_get_device(struct mtd_info *mtd, int new_state)
939{
940 struct onenand_chip *this = mtd->priv;
941 DECLARE_WAITQUEUE(wait, current);
942
943
944
945
946 while (1) {
947 spin_lock(&this->chip_lock);
948 if (this->state == FL_READY) {
949 this->state = new_state;
950 spin_unlock(&this->chip_lock);
951 if (new_state != FL_PM_SUSPENDED && this->enable)
952 this->enable(mtd);
953 break;
954 }
955 if (new_state == FL_PM_SUSPENDED) {
956 spin_unlock(&this->chip_lock);
957 return (this->state == FL_PM_SUSPENDED) ? 0 : -EAGAIN;
958 }
959 set_current_state(TASK_UNINTERRUPTIBLE);
960 add_wait_queue(&this->wq, &wait);
961 spin_unlock(&this->chip_lock);
962 schedule();
963 remove_wait_queue(&this->wq, &wait);
964 }
965
966 return 0;
967}
968
969
970
971
972
973
974
975static void onenand_release_device(struct mtd_info *mtd)
976{
977 struct onenand_chip *this = mtd->priv;
978
979 if (this->state != FL_PM_SUSPENDED && this->disable)
980 this->disable(mtd);
981
982 spin_lock(&this->chip_lock);
983 this->state = FL_READY;
984 wake_up(&this->wq);
985 spin_unlock(&this->chip_lock);
986}
987
988
989
990
991
992
993
994
995static int onenand_transfer_auto_oob(struct mtd_info *mtd, uint8_t *buf, int column,
996 int thislen)
997{
998 struct onenand_chip *this = mtd->priv;
999 struct nand_oobfree *free;
1000 int readcol = column;
1001 int readend = column + thislen;
1002 int lastgap = 0;
1003 unsigned int i;
1004 uint8_t *oob_buf = this->oob_buf;
1005
1006 free = this->ecclayout->oobfree;
1007 for (i = 0; i < MTD_MAX_OOBFREE_ENTRIES && free->length; i++, free++) {
1008 if (readcol >= lastgap)
1009 readcol += free->offset - lastgap;
1010 if (readend >= lastgap)
1011 readend += free->offset - lastgap;
1012 lastgap = free->offset + free->length;
1013 }
1014 this->read_bufferram(mtd, ONENAND_SPARERAM, oob_buf, 0, mtd->oobsize);
1015 free = this->ecclayout->oobfree;
1016 for (i = 0; i < MTD_MAX_OOBFREE_ENTRIES && free->length; i++, free++) {
1017 int free_end = free->offset + free->length;
1018 if (free->offset < readend && free_end > readcol) {
1019 int st = max_t(int,free->offset,readcol);
1020 int ed = min_t(int,free_end,readend);
1021 int n = ed - st;
1022 memcpy(buf, oob_buf + st, n);
1023 buf += n;
1024 } else if (column == 0)
1025 break;
1026 }
1027 return 0;
1028}
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043static int onenand_recover_lsb(struct mtd_info *mtd, loff_t addr, int status)
1044{
1045 struct onenand_chip *this = mtd->priv;
1046 int i;
1047
1048
1049 if (!FLEXONENAND(this))
1050 return status;
1051
1052
1053 if (status != -EBADMSG && status != ONENAND_BBT_READ_ECC_ERROR)
1054 return status;
1055
1056
1057 i = flexonenand_region(mtd, addr);
1058 if (mtd->eraseregions[i].erasesize < (1 << this->erase_shift))
1059 return status;
1060
1061
1062
1063
1064 printk(KERN_INFO "%s: Attempting to recover from uncorrectable read\n",
1065 __func__);
1066 mtd->ecc_stats.failed--;
1067
1068
1069 this->command(mtd, FLEXONENAND_CMD_RECOVER_LSB, addr, this->writesize);
1070 return this->wait(mtd, FL_READING);
1071}
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082static int onenand_mlc_read_ops_nolock(struct mtd_info *mtd, loff_t from,
1083 struct mtd_oob_ops *ops)
1084{
1085 struct onenand_chip *this = mtd->priv;
1086 struct mtd_ecc_stats stats;
1087 size_t len = ops->len;
1088 size_t ooblen = ops->ooblen;
1089 u_char *buf = ops->datbuf;
1090 u_char *oobbuf = ops->oobbuf;
1091 int read = 0, column, thislen;
1092 int oobread = 0, oobcolumn, thisooblen, oobsize;
1093 int ret = 0;
1094 int writesize = this->writesize;
1095
1096 DEBUG(MTD_DEBUG_LEVEL3, "%s: from = 0x%08x, len = %i\n",
1097 __func__, (unsigned int) from, (int) len);
1098
1099 if (ops->mode == MTD_OOB_AUTO)
1100 oobsize = this->ecclayout->oobavail;
1101 else
1102 oobsize = mtd->oobsize;
1103
1104 oobcolumn = from & (mtd->oobsize - 1);
1105
1106
1107 if (from + len > mtd->size) {
1108 printk(KERN_ERR "%s: Attempt read beyond end of device\n",
1109 __func__);
1110 ops->retlen = 0;
1111 ops->oobretlen = 0;
1112 return -EINVAL;
1113 }
1114
1115 stats = mtd->ecc_stats;
1116
1117 while (read < len) {
1118 cond_resched();
1119
1120 thislen = min_t(int, writesize, len - read);
1121
1122 column = from & (writesize - 1);
1123 if (column + thislen > writesize)
1124 thislen = writesize - column;
1125
1126 if (!onenand_check_bufferram(mtd, from)) {
1127 this->command(mtd, ONENAND_CMD_READ, from, writesize);
1128
1129 ret = this->wait(mtd, FL_READING);
1130 if (unlikely(ret))
1131 ret = onenand_recover_lsb(mtd, from, ret);
1132 onenand_update_bufferram(mtd, from, !ret);
1133 if (ret == -EBADMSG)
1134 ret = 0;
1135 if (ret)
1136 break;
1137 }
1138
1139 this->read_bufferram(mtd, ONENAND_DATARAM, buf, column, thislen);
1140 if (oobbuf) {
1141 thisooblen = oobsize - oobcolumn;
1142 thisooblen = min_t(int, thisooblen, ooblen - oobread);
1143
1144 if (ops->mode == MTD_OOB_AUTO)
1145 onenand_transfer_auto_oob(mtd, oobbuf, oobcolumn, thisooblen);
1146 else
1147 this->read_bufferram(mtd, ONENAND_SPARERAM, oobbuf, oobcolumn, thisooblen);
1148 oobread += thisooblen;
1149 oobbuf += thisooblen;
1150 oobcolumn = 0;
1151 }
1152
1153 read += thislen;
1154 if (read == len)
1155 break;
1156
1157 from += thislen;
1158 buf += thislen;
1159 }
1160
1161
1162
1163
1164
1165
1166 ops->retlen = read;
1167 ops->oobretlen = oobread;
1168
1169 if (ret)
1170 return ret;
1171
1172 if (mtd->ecc_stats.failed - stats.failed)
1173 return -EBADMSG;
1174
1175 return mtd->ecc_stats.corrected - stats.corrected ? -EUCLEAN : 0;
1176}
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186static int onenand_read_ops_nolock(struct mtd_info *mtd, loff_t from,
1187 struct mtd_oob_ops *ops)
1188{
1189 struct onenand_chip *this = mtd->priv;
1190 struct mtd_ecc_stats stats;
1191 size_t len = ops->len;
1192 size_t ooblen = ops->ooblen;
1193 u_char *buf = ops->datbuf;
1194 u_char *oobbuf = ops->oobbuf;
1195 int read = 0, column, thislen;
1196 int oobread = 0, oobcolumn, thisooblen, oobsize;
1197 int ret = 0, boundary = 0;
1198 int writesize = this->writesize;
1199
1200 DEBUG(MTD_DEBUG_LEVEL3, "%s: from = 0x%08x, len = %i\n",
1201 __func__, (unsigned int) from, (int) len);
1202
1203 if (ops->mode == MTD_OOB_AUTO)
1204 oobsize = this->ecclayout->oobavail;
1205 else
1206 oobsize = mtd->oobsize;
1207
1208 oobcolumn = from & (mtd->oobsize - 1);
1209
1210
1211 if ((from + len) > mtd->size) {
1212 printk(KERN_ERR "%s: Attempt read beyond end of device\n",
1213 __func__);
1214 ops->retlen = 0;
1215 ops->oobretlen = 0;
1216 return -EINVAL;
1217 }
1218
1219 stats = mtd->ecc_stats;
1220
1221
1222
1223
1224 if (read < len) {
1225 if (!onenand_check_bufferram(mtd, from)) {
1226 this->command(mtd, ONENAND_CMD_READ, from, writesize);
1227 ret = this->wait(mtd, FL_READING);
1228 onenand_update_bufferram(mtd, from, !ret);
1229 if (ret == -EBADMSG)
1230 ret = 0;
1231 }
1232 }
1233
1234 thislen = min_t(int, writesize, len - read);
1235 column = from & (writesize - 1);
1236 if (column + thislen > writesize)
1237 thislen = writesize - column;
1238
1239 while (!ret) {
1240
1241 from += thislen;
1242 if (read + thislen < len) {
1243 this->command(mtd, ONENAND_CMD_READ, from, writesize);
1244
1245
1246
1247
1248
1249 if (ONENAND_IS_DDP(this) &&
1250 unlikely(from == (this->chipsize >> 1))) {
1251 this->write_word(ONENAND_DDP_CHIP0, this->base + ONENAND_REG_START_ADDRESS2);
1252 boundary = 1;
1253 } else
1254 boundary = 0;
1255 ONENAND_SET_PREV_BUFFERRAM(this);
1256 }
1257
1258 this->read_bufferram(mtd, ONENAND_DATARAM, buf, column, thislen);
1259
1260
1261 if (oobbuf) {
1262 thisooblen = oobsize - oobcolumn;
1263 thisooblen = min_t(int, thisooblen, ooblen - oobread);
1264
1265 if (ops->mode == MTD_OOB_AUTO)
1266 onenand_transfer_auto_oob(mtd, oobbuf, oobcolumn, thisooblen);
1267 else
1268 this->read_bufferram(mtd, ONENAND_SPARERAM, oobbuf, oobcolumn, thisooblen);
1269 oobread += thisooblen;
1270 oobbuf += thisooblen;
1271 oobcolumn = 0;
1272 }
1273
1274
1275 read += thislen;
1276 if (read == len)
1277 break;
1278
1279 if (unlikely(boundary))
1280 this->write_word(ONENAND_DDP_CHIP1, this->base + ONENAND_REG_START_ADDRESS2);
1281 ONENAND_SET_NEXT_BUFFERRAM(this);
1282 buf += thislen;
1283 thislen = min_t(int, writesize, len - read);
1284 column = 0;
1285 cond_resched();
1286
1287 ret = this->wait(mtd, FL_READING);
1288 onenand_update_bufferram(mtd, from, !ret);
1289 if (ret == -EBADMSG)
1290 ret = 0;
1291 }
1292
1293
1294
1295
1296
1297
1298 ops->retlen = read;
1299 ops->oobretlen = oobread;
1300
1301 if (ret)
1302 return ret;
1303
1304 if (mtd->ecc_stats.failed - stats.failed)
1305 return -EBADMSG;
1306
1307 return mtd->ecc_stats.corrected - stats.corrected ? -EUCLEAN : 0;
1308}
1309
1310
1311
1312
1313
1314
1315
1316
1317
1318static int onenand_read_oob_nolock(struct mtd_info *mtd, loff_t from,
1319 struct mtd_oob_ops *ops)
1320{
1321 struct onenand_chip *this = mtd->priv;
1322 struct mtd_ecc_stats stats;
1323 int read = 0, thislen, column, oobsize;
1324 size_t len = ops->ooblen;
1325 mtd_oob_mode_t mode = ops->mode;
1326 u_char *buf = ops->oobbuf;
1327 int ret = 0, readcmd;
1328
1329 from += ops->ooboffs;
1330
1331 DEBUG(MTD_DEBUG_LEVEL3, "%s: from = 0x%08x, len = %i\n",
1332 __func__, (unsigned int) from, (int) len);
1333
1334
1335 ops->oobretlen = 0;
1336
1337 if (mode == MTD_OOB_AUTO)
1338 oobsize = this->ecclayout->oobavail;
1339 else
1340 oobsize = mtd->oobsize;
1341
1342 column = from & (mtd->oobsize - 1);
1343
1344 if (unlikely(column >= oobsize)) {
1345 printk(KERN_ERR "%s: Attempted to start read outside oob\n",
1346 __func__);
1347 return -EINVAL;
1348 }
1349
1350
1351 if (unlikely(from >= mtd->size ||
1352 column + len > ((mtd->size >> this->page_shift) -
1353 (from >> this->page_shift)) * oobsize)) {
1354 printk(KERN_ERR "%s: Attempted to read beyond end of device\n",
1355 __func__);
1356 return -EINVAL;
1357 }
1358
1359 stats = mtd->ecc_stats;
1360
1361 readcmd = ONENAND_IS_4KB_PAGE(this) ? ONENAND_CMD_READ : ONENAND_CMD_READOOB;
1362
1363 while (read < len) {
1364 cond_resched();
1365
1366 thislen = oobsize - column;
1367 thislen = min_t(int, thislen, len);
1368
1369 this->command(mtd, readcmd, from, mtd->oobsize);
1370
1371 onenand_update_bufferram(mtd, from, 0);
1372
1373 ret = this->wait(mtd, FL_READING);
1374 if (unlikely(ret))
1375 ret = onenand_recover_lsb(mtd, from, ret);
1376
1377 if (ret && ret != -EBADMSG) {
1378 printk(KERN_ERR "%s: read failed = 0x%x\n",
1379 __func__, ret);
1380 break;
1381 }
1382
1383 if (mode == MTD_OOB_AUTO)
1384 onenand_transfer_auto_oob(mtd, buf, column, thislen);
1385 else
1386 this->read_bufferram(mtd, ONENAND_SPARERAM, buf, column, thislen);
1387
1388 read += thislen;
1389
1390 if (read == len)
1391 break;
1392
1393 buf += thislen;
1394
1395
1396 if (read < len) {
1397
1398 from += mtd->writesize;
1399 column = 0;
1400 }
1401 }
1402
1403 ops->oobretlen = read;
1404
1405 if (ret)
1406 return ret;
1407
1408 if (mtd->ecc_stats.failed - stats.failed)
1409 return -EBADMSG;
1410
1411 return 0;
1412}
1413
1414
1415
1416
1417
1418
1419
1420
1421
1422
1423
1424static int onenand_read(struct mtd_info *mtd, loff_t from, size_t len,
1425 size_t *retlen, u_char *buf)
1426{
1427 struct onenand_chip *this = mtd->priv;
1428 struct mtd_oob_ops ops = {
1429 .len = len,
1430 .ooblen = 0,
1431 .datbuf = buf,
1432 .oobbuf = NULL,
1433 };
1434 int ret;
1435
1436 onenand_get_device(mtd, FL_READING);
1437 ret = ONENAND_IS_4KB_PAGE(this) ?
1438 onenand_mlc_read_ops_nolock(mtd, from, &ops) :
1439 onenand_read_ops_nolock(mtd, from, &ops);
1440 onenand_release_device(mtd);
1441
1442 *retlen = ops.retlen;
1443 return ret;
1444}
1445
1446
1447
1448
1449
1450
1451
1452
1453
1454static int onenand_read_oob(struct mtd_info *mtd, loff_t from,
1455 struct mtd_oob_ops *ops)
1456{
1457 struct onenand_chip *this = mtd->priv;
1458 int ret;
1459
1460 switch (ops->mode) {
1461 case MTD_OOB_PLACE:
1462 case MTD_OOB_AUTO:
1463 break;
1464 case MTD_OOB_RAW:
1465
1466 default:
1467 return -EINVAL;
1468 }
1469
1470 onenand_get_device(mtd, FL_READING);
1471 if (ops->datbuf)
1472 ret = ONENAND_IS_4KB_PAGE(this) ?
1473 onenand_mlc_read_ops_nolock(mtd, from, ops) :
1474 onenand_read_ops_nolock(mtd, from, ops);
1475 else
1476 ret = onenand_read_oob_nolock(mtd, from, ops);
1477 onenand_release_device(mtd);
1478
1479 return ret;
1480}
1481
1482
1483
1484
1485
1486
1487
1488
1489static int onenand_bbt_wait(struct mtd_info *mtd, int state)
1490{
1491 struct onenand_chip *this = mtd->priv;
1492 unsigned long timeout;
1493 unsigned int interrupt, ctrl, ecc, addr1, addr8;
1494
1495
1496 timeout = jiffies + msecs_to_jiffies(20);
1497 while (time_before(jiffies, timeout)) {
1498 interrupt = this->read_word(this->base + ONENAND_REG_INTERRUPT);
1499 if (interrupt & ONENAND_INT_MASTER)
1500 break;
1501 }
1502
1503 interrupt = this->read_word(this->base + ONENAND_REG_INTERRUPT);
1504 ctrl = this->read_word(this->base + ONENAND_REG_CTRL_STATUS);
1505 addr1 = this->read_word(this->base + ONENAND_REG_START_ADDRESS1);
1506 addr8 = this->read_word(this->base + ONENAND_REG_START_ADDRESS8);
1507
1508 if (interrupt & ONENAND_INT_READ) {
1509 ecc = onenand_read_ecc(this);
1510 if (ecc & ONENAND_ECC_2BIT_ALL) {
1511 printk(KERN_DEBUG "%s: ecc 0x%04x ctrl 0x%04x "
1512 "intr 0x%04x addr1 %#x addr8 %#x\n",
1513 __func__, ecc, ctrl, interrupt, addr1, addr8);
1514 return ONENAND_BBT_READ_ECC_ERROR;
1515 }
1516 } else {
1517 printk(KERN_ERR "%s: read timeout! ctrl 0x%04x "
1518 "intr 0x%04x addr1 %#x addr8 %#x\n",
1519 __func__, ctrl, interrupt, addr1, addr8);
1520 return ONENAND_BBT_READ_FATAL_ERROR;
1521 }
1522
1523
1524 if (ctrl & ONENAND_CTRL_ERROR) {
1525 printk(KERN_DEBUG "%s: ctrl 0x%04x intr 0x%04x addr1 %#x "
1526 "addr8 %#x\n", __func__, ctrl, interrupt, addr1, addr8);
1527 return ONENAND_BBT_READ_ERROR;
1528 }
1529
1530 return 0;
1531}
1532
1533
1534
1535
1536
1537
1538
1539
1540
1541int onenand_bbt_read_oob(struct mtd_info *mtd, loff_t from,
1542 struct mtd_oob_ops *ops)
1543{
1544 struct onenand_chip *this = mtd->priv;
1545 int read = 0, thislen, column;
1546 int ret = 0, readcmd;
1547 size_t len = ops->ooblen;
1548 u_char *buf = ops->oobbuf;
1549
1550 DEBUG(MTD_DEBUG_LEVEL3, "%s: from = 0x%08x, len = %zi\n",
1551 __func__, (unsigned int) from, len);
1552
1553
1554 ops->oobretlen = 0;
1555
1556
1557 if (unlikely((from + len) > mtd->size)) {
1558 printk(KERN_ERR "%s: Attempt read beyond end of device\n",
1559 __func__);
1560 return ONENAND_BBT_READ_FATAL_ERROR;
1561 }
1562
1563
1564 onenand_get_device(mtd, FL_READING);
1565
1566 column = from & (mtd->oobsize - 1);
1567
1568 readcmd = ONENAND_IS_4KB_PAGE(this) ? ONENAND_CMD_READ : ONENAND_CMD_READOOB;
1569
1570 while (read < len) {
1571 cond_resched();
1572
1573 thislen = mtd->oobsize - column;
1574 thislen = min_t(int, thislen, len);
1575
1576 this->command(mtd, readcmd, from, mtd->oobsize);
1577
1578 onenand_update_bufferram(mtd, from, 0);
1579
1580 ret = this->bbt_wait(mtd, FL_READING);
1581 if (unlikely(ret))
1582 ret = onenand_recover_lsb(mtd, from, ret);
1583
1584 if (ret)
1585 break;
1586
1587 this->read_bufferram(mtd, ONENAND_SPARERAM, buf, column, thislen);
1588 read += thislen;
1589 if (read == len)
1590 break;
1591
1592 buf += thislen;
1593
1594
1595 if (read < len) {
1596
1597 from += this->writesize;
1598 column = 0;
1599 }
1600 }
1601
1602
1603 onenand_release_device(mtd);
1604
1605 ops->oobretlen = read;
1606 return ret;
1607}
1608
1609#ifdef CONFIG_MTD_ONENAND_VERIFY_WRITE
1610
1611
1612
1613
1614
1615
1616static int onenand_verify_oob(struct mtd_info *mtd, const u_char *buf, loff_t to)
1617{
1618 struct onenand_chip *this = mtd->priv;
1619 u_char *oob_buf = this->oob_buf;
1620 int status, i, readcmd;
1621
1622 readcmd = ONENAND_IS_4KB_PAGE(this) ? ONENAND_CMD_READ : ONENAND_CMD_READOOB;
1623
1624 this->command(mtd, readcmd, to, mtd->oobsize);
1625 onenand_update_bufferram(mtd, to, 0);
1626 status = this->wait(mtd, FL_READING);
1627 if (status)
1628 return status;
1629
1630 this->read_bufferram(mtd, ONENAND_SPARERAM, oob_buf, 0, mtd->oobsize);
1631 for (i = 0; i < mtd->oobsize; i++)
1632 if (buf[i] != 0xFF && buf[i] != oob_buf[i])
1633 return -EBADMSG;
1634
1635 return 0;
1636}
1637
1638
1639
1640
1641
1642
1643
1644
1645static int onenand_verify(struct mtd_info *mtd, const u_char *buf, loff_t addr, size_t len)
1646{
1647 struct onenand_chip *this = mtd->priv;
1648 int ret = 0;
1649 int thislen, column;
1650
1651 column = addr & (this->writesize - 1);
1652
1653 while (len != 0) {
1654 thislen = min_t(int, this->writesize - column, len);
1655
1656 this->command(mtd, ONENAND_CMD_READ, addr, this->writesize);
1657
1658 onenand_update_bufferram(mtd, addr, 0);
1659
1660 ret = this->wait(mtd, FL_READING);
1661 if (ret)
1662 return ret;
1663
1664 onenand_update_bufferram(mtd, addr, 1);
1665
1666 this->read_bufferram(mtd, ONENAND_DATARAM, this->verify_buf, 0, mtd->writesize);
1667
1668 if (memcmp(buf, this->verify_buf + column, thislen))
1669 return -EBADMSG;
1670
1671 len -= thislen;
1672 buf += thislen;
1673 addr += thislen;
1674 column = 0;
1675 }
1676
1677 return 0;
1678}
1679#else
1680#define onenand_verify(...) (0)
1681#define onenand_verify_oob(...) (0)
1682#endif
1683
1684#define NOTALIGNED(x) ((x & (this->subpagesize - 1)) != 0)
1685
1686static void onenand_panic_wait(struct mtd_info *mtd)
1687{
1688 struct onenand_chip *this = mtd->priv;
1689 unsigned int interrupt;
1690 int i;
1691
1692 for (i = 0; i < 2000; i++) {
1693 interrupt = this->read_word(this->base + ONENAND_REG_INTERRUPT);
1694 if (interrupt & ONENAND_INT_MASTER)
1695 break;
1696 udelay(10);
1697 }
1698}
1699
1700
1701
1702
1703
1704
1705
1706
1707
1708
1709
1710static int onenand_panic_write(struct mtd_info *mtd, loff_t to, size_t len,
1711 size_t *retlen, const u_char *buf)
1712{
1713 struct onenand_chip *this = mtd->priv;
1714 int column, subpage;
1715 int written = 0;
1716 int ret = 0;
1717
1718 if (this->state == FL_PM_SUSPENDED)
1719 return -EBUSY;
1720
1721
1722 onenand_panic_wait(mtd);
1723
1724 DEBUG(MTD_DEBUG_LEVEL3, "%s: to = 0x%08x, len = %i\n",
1725 __func__, (unsigned int) to, (int) len);
1726
1727
1728 *retlen = 0;
1729
1730
1731 if (unlikely((to + len) > mtd->size)) {
1732 printk(KERN_ERR "%s: Attempt write to past end of device\n",
1733 __func__);
1734 return -EINVAL;
1735 }
1736
1737
1738 if (unlikely(NOTALIGNED(to) || NOTALIGNED(len))) {
1739 printk(KERN_ERR "%s: Attempt to write not page aligned data\n",
1740 __func__);
1741 return -EINVAL;
1742 }
1743
1744 column = to & (mtd->writesize - 1);
1745
1746
1747 while (written < len) {
1748 int thislen = min_t(int, mtd->writesize - column, len - written);
1749 u_char *wbuf = (u_char *) buf;
1750
1751 this->command(mtd, ONENAND_CMD_BUFFERRAM, to, thislen);
1752
1753
1754 subpage = thislen < mtd->writesize;
1755 if (subpage) {
1756 memset(this->page_buf, 0xff, mtd->writesize);
1757 memcpy(this->page_buf + column, buf, thislen);
1758 wbuf = this->page_buf;
1759 }
1760
1761 this->write_bufferram(mtd, ONENAND_DATARAM, wbuf, 0, mtd->writesize);
1762 this->write_bufferram(mtd, ONENAND_SPARERAM, ffchars, 0, mtd->oobsize);
1763
1764 this->command(mtd, ONENAND_CMD_PROG, to, mtd->writesize);
1765
1766 onenand_panic_wait(mtd);
1767
1768
1769 onenand_update_bufferram(mtd, to, !ret && !subpage);
1770 if (ONENAND_IS_2PLANE(this)) {
1771 ONENAND_SET_BUFFERRAM1(this);
1772 onenand_update_bufferram(mtd, to + this->writesize, !ret && !subpage);
1773 }
1774
1775 if (ret) {
1776 printk(KERN_ERR "%s: write failed %d\n", __func__, ret);
1777 break;
1778 }
1779
1780 written += thislen;
1781
1782 if (written == len)
1783 break;
1784
1785 column = 0;
1786 to += thislen;
1787 buf += thislen;
1788 }
1789
1790 *retlen = written;
1791 return ret;
1792}
1793
1794
1795
1796
1797
1798
1799
1800
1801
1802static int onenand_fill_auto_oob(struct mtd_info *mtd, u_char *oob_buf,
1803 const u_char *buf, int column, int thislen)
1804{
1805 struct onenand_chip *this = mtd->priv;
1806 struct nand_oobfree *free;
1807 int writecol = column;
1808 int writeend = column + thislen;
1809 int lastgap = 0;
1810 unsigned int i;
1811
1812 free = this->ecclayout->oobfree;
1813 for (i = 0; i < MTD_MAX_OOBFREE_ENTRIES && free->length; i++, free++) {
1814 if (writecol >= lastgap)
1815 writecol += free->offset - lastgap;
1816 if (writeend >= lastgap)
1817 writeend += free->offset - lastgap;
1818 lastgap = free->offset + free->length;
1819 }
1820 free = this->ecclayout->oobfree;
1821 for (i = 0; i < MTD_MAX_OOBFREE_ENTRIES && free->length; i++, free++) {
1822 int free_end = free->offset + free->length;
1823 if (free->offset < writeend && free_end > writecol) {
1824 int st = max_t(int,free->offset,writecol);
1825 int ed = min_t(int,free_end,writeend);
1826 int n = ed - st;
1827 memcpy(oob_buf + st, buf, n);
1828 buf += n;
1829 } else if (column == 0)
1830 break;
1831 }
1832 return 0;
1833}
1834
1835
1836
1837
1838
1839
1840
1841
1842
1843static int onenand_write_ops_nolock(struct mtd_info *mtd, loff_t to,
1844 struct mtd_oob_ops *ops)
1845{
1846 struct onenand_chip *this = mtd->priv;
1847 int written = 0, column, thislen = 0, subpage = 0;
1848 int prev = 0, prevlen = 0, prev_subpage = 0, first = 1;
1849 int oobwritten = 0, oobcolumn, thisooblen, oobsize;
1850 size_t len = ops->len;
1851 size_t ooblen = ops->ooblen;
1852 const u_char *buf = ops->datbuf;
1853 const u_char *oob = ops->oobbuf;
1854 u_char *oobbuf;
1855 int ret = 0, cmd;
1856
1857 DEBUG(MTD_DEBUG_LEVEL3, "%s: to = 0x%08x, len = %i\n",
1858 __func__, (unsigned int) to, (int) len);
1859
1860
1861 ops->retlen = 0;
1862 ops->oobretlen = 0;
1863
1864
1865 if (unlikely((to + len) > mtd->size)) {
1866 printk(KERN_ERR "%s: Attempt write to past end of device\n",
1867 __func__);
1868 return -EINVAL;
1869 }
1870
1871
1872 if (unlikely(NOTALIGNED(to) || NOTALIGNED(len))) {
1873 printk(KERN_ERR "%s: Attempt to write not page aligned data\n",
1874 __func__);
1875 return -EINVAL;
1876 }
1877
1878
1879 if (!len)
1880 return 0;
1881
1882 if (ops->mode == MTD_OOB_AUTO)
1883 oobsize = this->ecclayout->oobavail;
1884 else
1885 oobsize = mtd->oobsize;
1886
1887 oobcolumn = to & (mtd->oobsize - 1);
1888
1889 column = to & (mtd->writesize - 1);
1890
1891
1892 while (1) {
1893 if (written < len) {
1894 u_char *wbuf = (u_char *) buf;
1895
1896 thislen = min_t(int, mtd->writesize - column, len - written);
1897 thisooblen = min_t(int, oobsize - oobcolumn, ooblen - oobwritten);
1898
1899 cond_resched();
1900
1901 this->command(mtd, ONENAND_CMD_BUFFERRAM, to, thislen);
1902
1903
1904 subpage = thislen < mtd->writesize;
1905 if (subpage) {
1906 memset(this->page_buf, 0xff, mtd->writesize);
1907 memcpy(this->page_buf + column, buf, thislen);
1908 wbuf = this->page_buf;
1909 }
1910
1911 this->write_bufferram(mtd, ONENAND_DATARAM, wbuf, 0, mtd->writesize);
1912
1913 if (oob) {
1914 oobbuf = this->oob_buf;
1915
1916
1917
1918 memset(oobbuf, 0xff, mtd->oobsize);
1919 if (ops->mode == MTD_OOB_AUTO)
1920 onenand_fill_auto_oob(mtd, oobbuf, oob, oobcolumn, thisooblen);
1921 else
1922 memcpy(oobbuf + oobcolumn, oob, thisooblen);
1923
1924 oobwritten += thisooblen;
1925 oob += thisooblen;
1926 oobcolumn = 0;
1927 } else
1928 oobbuf = (u_char *) ffchars;
1929
1930 this->write_bufferram(mtd, ONENAND_SPARERAM, oobbuf, 0, mtd->oobsize);
1931 } else
1932 ONENAND_SET_NEXT_BUFFERRAM(this);
1933
1934
1935
1936
1937
1938 if (!ONENAND_IS_2PLANE(this) && !ONENAND_IS_4KB_PAGE(this) && !first) {
1939 ONENAND_SET_PREV_BUFFERRAM(this);
1940
1941 ret = this->wait(mtd, FL_WRITING);
1942
1943
1944 onenand_update_bufferram(mtd, prev, !ret && !prev_subpage);
1945 if (ret) {
1946 written -= prevlen;
1947 printk(KERN_ERR "%s: write failed %d\n",
1948 __func__, ret);
1949 break;
1950 }
1951
1952 if (written == len) {
1953
1954 ret = onenand_verify(mtd, buf - len, to - len, len);
1955 if (ret)
1956 printk(KERN_ERR "%s: verify failed %d\n",
1957 __func__, ret);
1958 break;
1959 }
1960
1961 ONENAND_SET_NEXT_BUFFERRAM(this);
1962 }
1963
1964 this->ongoing = 0;
1965 cmd = ONENAND_CMD_PROG;
1966
1967
1968 if (ONENAND_IS_CACHE_PROGRAM(this) &&
1969 likely(onenand_block(this, to) != 0) &&
1970 ONENAND_IS_4KB_PAGE(this) &&
1971 ((written + thislen) < len)) {
1972 cmd = ONENAND_CMD_2X_CACHE_PROG;
1973 this->ongoing = 1;
1974 }
1975
1976 this->command(mtd, cmd, to, mtd->writesize);
1977
1978
1979
1980
1981 if (ONENAND_IS_2PLANE(this) || ONENAND_IS_4KB_PAGE(this)) {
1982 ret = this->wait(mtd, FL_WRITING);
1983
1984
1985 onenand_update_bufferram(mtd, to, !ret && !subpage);
1986 if (ret) {
1987 printk(KERN_ERR "%s: write failed %d\n",
1988 __func__, ret);
1989 break;
1990 }
1991
1992
1993 ret = onenand_verify(mtd, buf, to, thislen);
1994 if (ret) {
1995 printk(KERN_ERR "%s: verify failed %d\n",
1996 __func__, ret);
1997 break;
1998 }
1999
2000 written += thislen;
2001
2002 if (written == len)
2003 break;
2004
2005 } else
2006 written += thislen;
2007
2008 column = 0;
2009 prev_subpage = subpage;
2010 prev = to;
2011 prevlen = thislen;
2012 to += thislen;
2013 buf += thislen;
2014 first = 0;
2015 }
2016
2017
2018 if (written != len)
2019 onenand_invalidate_bufferram(mtd, 0, -1);
2020
2021 ops->retlen = written;
2022 ops->oobretlen = oobwritten;
2023
2024 return ret;
2025}
2026
2027
2028
2029
2030
2031
2032
2033
2034
2035
2036
2037
2038
2039static int onenand_write_oob_nolock(struct mtd_info *mtd, loff_t to,
2040 struct mtd_oob_ops *ops)
2041{
2042 struct onenand_chip *this = mtd->priv;
2043 int column, ret = 0, oobsize;
2044 int written = 0, oobcmd;
2045 u_char *oobbuf;
2046 size_t len = ops->ooblen;
2047 const u_char *buf = ops->oobbuf;
2048 mtd_oob_mode_t mode = ops->mode;
2049
2050 to += ops->ooboffs;
2051
2052 DEBUG(MTD_DEBUG_LEVEL3, "%s: to = 0x%08x, len = %i\n",
2053 __func__, (unsigned int) to, (int) len);
2054
2055
2056 ops->oobretlen = 0;
2057
2058 if (mode == MTD_OOB_AUTO)
2059 oobsize = this->ecclayout->oobavail;
2060 else
2061 oobsize = mtd->oobsize;
2062
2063 column = to & (mtd->oobsize - 1);
2064
2065 if (unlikely(column >= oobsize)) {
2066 printk(KERN_ERR "%s: Attempted to start write outside oob\n",
2067 __func__);
2068 return -EINVAL;
2069 }
2070
2071
2072 if (unlikely(column + len > oobsize)) {
2073 printk(KERN_ERR "%s: Attempt to write past end of page\n",
2074 __func__);
2075 return -EINVAL;
2076 }
2077
2078
2079 if (unlikely(to >= mtd->size ||
2080 column + len > ((mtd->size >> this->page_shift) -
2081 (to >> this->page_shift)) * oobsize)) {
2082 printk(KERN_ERR "%s: Attempted to write past end of device\n",
2083 __func__);
2084 return -EINVAL;
2085 }
2086
2087 oobbuf = this->oob_buf;
2088
2089 oobcmd = ONENAND_IS_4KB_PAGE(this) ? ONENAND_CMD_PROG : ONENAND_CMD_PROGOOB;
2090
2091
2092 while (written < len) {
2093 int thislen = min_t(int, oobsize, len - written);
2094
2095 cond_resched();
2096
2097 this->command(mtd, ONENAND_CMD_BUFFERRAM, to, mtd->oobsize);
2098
2099
2100
2101 memset(oobbuf, 0xff, mtd->oobsize);
2102 if (mode == MTD_OOB_AUTO)
2103 onenand_fill_auto_oob(mtd, oobbuf, buf, column, thislen);
2104 else
2105 memcpy(oobbuf + column, buf, thislen);
2106 this->write_bufferram(mtd, ONENAND_SPARERAM, oobbuf, 0, mtd->oobsize);
2107
2108 if (ONENAND_IS_4KB_PAGE(this)) {
2109
2110 memset(this->page_buf, 0xff, mtd->writesize);
2111 this->write_bufferram(mtd, ONENAND_DATARAM,
2112 this->page_buf, 0, mtd->writesize);
2113 }
2114
2115 this->command(mtd, oobcmd, to, mtd->oobsize);
2116
2117 onenand_update_bufferram(mtd, to, 0);
2118 if (ONENAND_IS_2PLANE(this)) {
2119 ONENAND_SET_BUFFERRAM1(this);
2120 onenand_update_bufferram(mtd, to + this->writesize, 0);
2121 }
2122
2123 ret = this->wait(mtd, FL_WRITING);
2124 if (ret) {
2125 printk(KERN_ERR "%s: write failed %d\n", __func__, ret);
2126 break;
2127 }
2128
2129 ret = onenand_verify_oob(mtd, oobbuf, to);
2130 if (ret) {
2131 printk(KERN_ERR "%s: verify failed %d\n",
2132 __func__, ret);
2133 break;
2134 }
2135
2136 written += thislen;
2137 if (written == len)
2138 break;
2139
2140 to += mtd->writesize;
2141 buf += thislen;
2142 column = 0;
2143 }
2144
2145 ops->oobretlen = written;
2146
2147 return ret;
2148}
2149
2150
2151
2152
2153
2154
2155
2156
2157
2158
2159
2160static int onenand_write(struct mtd_info *mtd, loff_t to, size_t len,
2161 size_t *retlen, const u_char *buf)
2162{
2163 struct mtd_oob_ops ops = {
2164 .len = len,
2165 .ooblen = 0,
2166 .datbuf = (u_char *) buf,
2167 .oobbuf = NULL,
2168 };
2169 int ret;
2170
2171 onenand_get_device(mtd, FL_WRITING);
2172 ret = onenand_write_ops_nolock(mtd, to, &ops);
2173 onenand_release_device(mtd);
2174
2175 *retlen = ops.retlen;
2176 return ret;
2177}
2178
2179
2180
2181
2182
2183
2184
2185static int onenand_write_oob(struct mtd_info *mtd, loff_t to,
2186 struct mtd_oob_ops *ops)
2187{
2188 int ret;
2189
2190 switch (ops->mode) {
2191 case MTD_OOB_PLACE:
2192 case MTD_OOB_AUTO:
2193 break;
2194 case MTD_OOB_RAW:
2195
2196 default:
2197 return -EINVAL;
2198 }
2199
2200 onenand_get_device(mtd, FL_WRITING);
2201 if (ops->datbuf)
2202 ret = onenand_write_ops_nolock(mtd, to, ops);
2203 else
2204 ret = onenand_write_oob_nolock(mtd, to, ops);
2205 onenand_release_device(mtd);
2206
2207 return ret;
2208}
2209
2210
2211
2212
2213
2214
2215
2216
2217
2218
2219static int onenand_block_isbad_nolock(struct mtd_info *mtd, loff_t ofs, int allowbbt)
2220{
2221 struct onenand_chip *this = mtd->priv;
2222 struct bbm_info *bbm = this->bbm;
2223
2224
2225 return bbm->isbad_bbt(mtd, ofs, allowbbt);
2226}
2227
2228
2229static int onenand_multiblock_erase_verify(struct mtd_info *mtd,
2230 struct erase_info *instr)
2231{
2232 struct onenand_chip *this = mtd->priv;
2233 loff_t addr = instr->addr;
2234 int len = instr->len;
2235 unsigned int block_size = (1 << this->erase_shift);
2236 int ret = 0;
2237
2238 while (len) {
2239 this->command(mtd, ONENAND_CMD_ERASE_VERIFY, addr, block_size);
2240 ret = this->wait(mtd, FL_VERIFYING_ERASE);
2241 if (ret) {
2242 printk(KERN_ERR "%s: Failed verify, block %d\n",
2243 __func__, onenand_block(this, addr));
2244 instr->state = MTD_ERASE_FAILED;
2245 instr->fail_addr = addr;
2246 return -1;
2247 }
2248 len -= block_size;
2249 addr += block_size;
2250 }
2251 return 0;
2252}
2253
2254
2255
2256
2257
2258
2259
2260
2261
2262static int onenand_multiblock_erase(struct mtd_info *mtd,
2263 struct erase_info *instr,
2264 unsigned int block_size)
2265{
2266 struct onenand_chip *this = mtd->priv;
2267 loff_t addr = instr->addr;
2268 int len = instr->len;
2269 int eb_count = 0;
2270 int ret = 0;
2271 int bdry_block = 0;
2272
2273 instr->state = MTD_ERASING;
2274
2275 if (ONENAND_IS_DDP(this)) {
2276 loff_t bdry_addr = this->chipsize >> 1;
2277 if (addr < bdry_addr && (addr + len) > bdry_addr)
2278 bdry_block = bdry_addr >> this->erase_shift;
2279 }
2280
2281
2282 while (len) {
2283
2284 if (onenand_block_isbad_nolock(mtd, addr, 0)) {
2285 printk(KERN_WARNING "%s: attempt to erase a bad block "
2286 "at addr 0x%012llx\n",
2287 __func__, (unsigned long long) addr);
2288 instr->state = MTD_ERASE_FAILED;
2289 return -EIO;
2290 }
2291 len -= block_size;
2292 addr += block_size;
2293 }
2294
2295 len = instr->len;
2296 addr = instr->addr;
2297
2298
2299 while (len) {
2300 struct erase_info verify_instr = *instr;
2301 int max_eb_count = MB_ERASE_MAX_BLK_COUNT;
2302
2303 verify_instr.addr = addr;
2304 verify_instr.len = 0;
2305
2306
2307 if (bdry_block) {
2308 int this_block = (addr >> this->erase_shift);
2309
2310 if (this_block < bdry_block) {
2311 max_eb_count = min(max_eb_count,
2312 (bdry_block - this_block));
2313 }
2314 }
2315
2316 eb_count = 0;
2317
2318 while (len > block_size && eb_count < (max_eb_count - 1)) {
2319 this->command(mtd, ONENAND_CMD_MULTIBLOCK_ERASE,
2320 addr, block_size);
2321 onenand_invalidate_bufferram(mtd, addr, block_size);
2322
2323 ret = this->wait(mtd, FL_PREPARING_ERASE);
2324 if (ret) {
2325 printk(KERN_ERR "%s: Failed multiblock erase, "
2326 "block %d\n", __func__,
2327 onenand_block(this, addr));
2328 instr->state = MTD_ERASE_FAILED;
2329 instr->fail_addr = MTD_FAIL_ADDR_UNKNOWN;
2330 return -EIO;
2331 }
2332
2333 len -= block_size;
2334 addr += block_size;
2335 eb_count++;
2336 }
2337
2338
2339 cond_resched();
2340 this->command(mtd, ONENAND_CMD_ERASE, addr, block_size);
2341 onenand_invalidate_bufferram(mtd, addr, block_size);
2342
2343 ret = this->wait(mtd, FL_ERASING);
2344
2345 if (ret) {
2346 printk(KERN_ERR "%s: Failed erase, block %d\n",
2347 __func__, onenand_block(this, addr));
2348 instr->state = MTD_ERASE_FAILED;
2349 instr->fail_addr = MTD_FAIL_ADDR_UNKNOWN;
2350 return -EIO;
2351 }
2352
2353 len -= block_size;
2354 addr += block_size;
2355 eb_count++;
2356
2357
2358 verify_instr.len = eb_count * block_size;
2359 if (onenand_multiblock_erase_verify(mtd, &verify_instr)) {
2360 instr->state = verify_instr.state;
2361 instr->fail_addr = verify_instr.fail_addr;
2362 return -EIO;
2363 }
2364
2365 }
2366 return 0;
2367}
2368
2369
2370
2371
2372
2373
2374
2375
2376
2377
2378
2379static int onenand_block_by_block_erase(struct mtd_info *mtd,
2380 struct erase_info *instr,
2381 struct mtd_erase_region_info *region,
2382 unsigned int block_size)
2383{
2384 struct onenand_chip *this = mtd->priv;
2385 loff_t addr = instr->addr;
2386 int len = instr->len;
2387 loff_t region_end = 0;
2388 int ret = 0;
2389
2390 if (region) {
2391
2392 region_end = region->offset + region->erasesize * region->numblocks;
2393 }
2394
2395 instr->state = MTD_ERASING;
2396
2397
2398 while (len) {
2399 cond_resched();
2400
2401
2402 if (onenand_block_isbad_nolock(mtd, addr, 0)) {
2403 printk(KERN_WARNING "%s: attempt to erase a bad block "
2404 "at addr 0x%012llx\n",
2405 __func__, (unsigned long long) addr);
2406 instr->state = MTD_ERASE_FAILED;
2407 return -EIO;
2408 }
2409
2410 this->command(mtd, ONENAND_CMD_ERASE, addr, block_size);
2411
2412 onenand_invalidate_bufferram(mtd, addr, block_size);
2413
2414 ret = this->wait(mtd, FL_ERASING);
2415
2416 if (ret) {
2417 printk(KERN_ERR "%s: Failed erase, block %d\n",
2418 __func__, onenand_block(this, addr));
2419 instr->state = MTD_ERASE_FAILED;
2420 instr->fail_addr = addr;
2421 return -EIO;
2422 }
2423
2424 len -= block_size;
2425 addr += block_size;
2426
2427 if (addr == region_end) {
2428 if (!len)
2429 break;
2430 region++;
2431
2432 block_size = region->erasesize;
2433 region_end = region->offset + region->erasesize * region->numblocks;
2434
2435 if (len & (block_size - 1)) {
2436
2437 printk(KERN_ERR "%s: Unaligned address\n",
2438 __func__);
2439 return -EIO;
2440 }
2441 }
2442 }
2443 return 0;
2444}
2445
2446
2447
2448
2449
2450
2451
2452
2453static int onenand_erase(struct mtd_info *mtd, struct erase_info *instr)
2454{
2455 struct onenand_chip *this = mtd->priv;
2456 unsigned int block_size;
2457 loff_t addr = instr->addr;
2458 loff_t len = instr->len;
2459 int ret = 0;
2460 struct mtd_erase_region_info *region = NULL;
2461 loff_t region_offset = 0;
2462
2463 DEBUG(MTD_DEBUG_LEVEL3, "%s: start=0x%012llx, len=%llu\n", __func__,
2464 (unsigned long long) instr->addr, (unsigned long long) instr->len);
2465
2466
2467 if (unlikely((len + addr) > mtd->size)) {
2468 printk(KERN_ERR "%s: Erase past end of device\n", __func__);
2469 return -EINVAL;
2470 }
2471
2472 if (FLEXONENAND(this)) {
2473
2474 int i = flexonenand_region(mtd, addr);
2475
2476 region = &mtd->eraseregions[i];
2477 block_size = region->erasesize;
2478
2479
2480
2481
2482 region_offset = region->offset;
2483 } else
2484 block_size = 1 << this->erase_shift;
2485
2486
2487 if (unlikely((addr - region_offset) & (block_size - 1))) {
2488 printk(KERN_ERR "%s: Unaligned address\n", __func__);
2489 return -EINVAL;
2490 }
2491
2492
2493 if (unlikely(len & (block_size - 1))) {
2494 printk(KERN_ERR "%s: Length not block aligned\n", __func__);
2495 return -EINVAL;
2496 }
2497
2498 instr->fail_addr = MTD_FAIL_ADDR_UNKNOWN;
2499
2500
2501 onenand_get_device(mtd, FL_ERASING);
2502
2503 if (ONENAND_IS_4KB_PAGE(this) || region ||
2504 instr->len < MB_ERASE_MIN_BLK_COUNT * block_size) {
2505
2506 ret = onenand_block_by_block_erase(mtd, instr,
2507 region, block_size);
2508 } else {
2509 ret = onenand_multiblock_erase(mtd, instr, block_size);
2510 }
2511
2512
2513 onenand_release_device(mtd);
2514
2515
2516 if (!ret) {
2517 instr->state = MTD_ERASE_DONE;
2518 mtd_erase_callback(instr);
2519 }
2520
2521 return ret;
2522}
2523
2524
2525
2526
2527
2528
2529
2530static void onenand_sync(struct mtd_info *mtd)
2531{
2532 DEBUG(MTD_DEBUG_LEVEL3, "%s: called\n", __func__);
2533
2534
2535 onenand_get_device(mtd, FL_SYNCING);
2536
2537
2538 onenand_release_device(mtd);
2539}
2540
2541
2542
2543
2544
2545
2546
2547
2548static int onenand_block_isbad(struct mtd_info *mtd, loff_t ofs)
2549{
2550 int ret;
2551
2552
2553 if (ofs > mtd->size)
2554 return -EINVAL;
2555
2556 onenand_get_device(mtd, FL_READING);
2557 ret = onenand_block_isbad_nolock(mtd, ofs, 0);
2558 onenand_release_device(mtd);
2559 return ret;
2560}
2561
2562
2563
2564
2565
2566
2567
2568
2569
2570static int onenand_default_block_markbad(struct mtd_info *mtd, loff_t ofs)
2571{
2572 struct onenand_chip *this = mtd->priv;
2573 struct bbm_info *bbm = this->bbm;
2574 u_char buf[2] = {0, 0};
2575 struct mtd_oob_ops ops = {
2576 .mode = MTD_OOB_PLACE,
2577 .ooblen = 2,
2578 .oobbuf = buf,
2579 .ooboffs = 0,
2580 };
2581 int block;
2582
2583
2584 block = onenand_block(this, ofs);
2585 if (bbm->bbt)
2586 bbm->bbt[block >> 2] |= 0x01 << ((block & 0x03) << 1);
2587
2588
2589 ofs += mtd->oobsize + (bbm->badblockpos & ~0x01);
2590
2591
2592
2593
2594 return onenand_write_oob_nolock(mtd, ofs, &ops);
2595}
2596
2597
2598
2599
2600
2601
2602
2603
2604static int onenand_block_markbad(struct mtd_info *mtd, loff_t ofs)
2605{
2606 struct onenand_chip *this = mtd->priv;
2607 int ret;
2608
2609 ret = onenand_block_isbad(mtd, ofs);
2610 if (ret) {
2611
2612 if (ret > 0)
2613 return 0;
2614 return ret;
2615 }
2616
2617 onenand_get_device(mtd, FL_WRITING);
2618 ret = this->block_markbad(mtd, ofs);
2619 onenand_release_device(mtd);
2620 return ret;
2621}
2622
2623
2624
2625
2626
2627
2628
2629
2630
2631
2632static int onenand_do_lock_cmd(struct mtd_info *mtd, loff_t ofs, size_t len, int cmd)
2633{
2634 struct onenand_chip *this = mtd->priv;
2635 int start, end, block, value, status;
2636 int wp_status_mask;
2637
2638 start = onenand_block(this, ofs);
2639 end = onenand_block(this, ofs + len) - 1;
2640
2641 if (cmd == ONENAND_CMD_LOCK)
2642 wp_status_mask = ONENAND_WP_LS;
2643 else
2644 wp_status_mask = ONENAND_WP_US;
2645
2646
2647 if (this->options & ONENAND_HAS_CONT_LOCK) {
2648
2649 this->write_word(start, this->base + ONENAND_REG_START_BLOCK_ADDRESS);
2650
2651 this->write_word(end, this->base + ONENAND_REG_END_BLOCK_ADDRESS);
2652
2653 this->command(mtd, cmd, 0, 0);
2654
2655
2656 this->wait(mtd, FL_LOCKING);
2657
2658
2659 while (this->read_word(this->base + ONENAND_REG_CTRL_STATUS)
2660 & ONENAND_CTRL_ONGO)
2661 continue;
2662
2663
2664 status = this->read_word(this->base + ONENAND_REG_WP_STATUS);
2665 if (!(status & wp_status_mask))
2666 printk(KERN_ERR "%s: wp status = 0x%x\n",
2667 __func__, status);
2668
2669 return 0;
2670 }
2671
2672
2673 for (block = start; block < end + 1; block++) {
2674
2675 value = onenand_block_address(this, block);
2676 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS1);
2677
2678 value = onenand_bufferram_address(this, block);
2679 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS2);
2680
2681 this->write_word(block, this->base + ONENAND_REG_START_BLOCK_ADDRESS);
2682
2683 this->command(mtd, cmd, 0, 0);
2684
2685
2686 this->wait(mtd, FL_LOCKING);
2687
2688
2689 while (this->read_word(this->base + ONENAND_REG_CTRL_STATUS)
2690 & ONENAND_CTRL_ONGO)
2691 continue;
2692
2693
2694 status = this->read_word(this->base + ONENAND_REG_WP_STATUS);
2695 if (!(status & wp_status_mask))
2696 printk(KERN_ERR "%s: block = %d, wp status = 0x%x\n",
2697 __func__, block, status);
2698 }
2699
2700 return 0;
2701}
2702
2703
2704
2705
2706
2707
2708
2709
2710
2711static int onenand_lock(struct mtd_info *mtd, loff_t ofs, uint64_t len)
2712{
2713 int ret;
2714
2715 onenand_get_device(mtd, FL_LOCKING);
2716 ret = onenand_do_lock_cmd(mtd, ofs, len, ONENAND_CMD_LOCK);
2717 onenand_release_device(mtd);
2718 return ret;
2719}
2720
2721
2722
2723
2724
2725
2726
2727
2728
2729static int onenand_unlock(struct mtd_info *mtd, loff_t ofs, uint64_t len)
2730{
2731 int ret;
2732
2733 onenand_get_device(mtd, FL_LOCKING);
2734 ret = onenand_do_lock_cmd(mtd, ofs, len, ONENAND_CMD_UNLOCK);
2735 onenand_release_device(mtd);
2736 return ret;
2737}
2738
2739
2740
2741
2742
2743
2744
2745static int onenand_check_lock_status(struct onenand_chip *this)
2746{
2747 unsigned int value, block, status;
2748 unsigned int end;
2749
2750 end = this->chipsize >> this->erase_shift;
2751 for (block = 0; block < end; block++) {
2752
2753 value = onenand_block_address(this, block);
2754 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS1);
2755
2756 value = onenand_bufferram_address(this, block);
2757 this->write_word(value, this->base + ONENAND_REG_START_ADDRESS2);
2758
2759 this->write_word(block, this->base + ONENAND_REG_START_BLOCK_ADDRESS);
2760
2761
2762 status = this->read_word(this->base + ONENAND_REG_WP_STATUS);
2763 if (!(status & ONENAND_WP_US)) {
2764 printk(KERN_ERR "%s: block = %d, wp status = 0x%x\n",
2765 __func__, block, status);
2766 return 0;
2767 }
2768 }
2769
2770 return 1;
2771}
2772
2773
2774
2775
2776
2777
2778
2779static void onenand_unlock_all(struct mtd_info *mtd)
2780{
2781 struct onenand_chip *this = mtd->priv;
2782 loff_t ofs = 0;
2783 loff_t len = mtd->size;
2784
2785 if (this->options & ONENAND_HAS_UNLOCK_ALL) {
2786
2787 this->write_word(0, this->base + ONENAND_REG_START_BLOCK_ADDRESS);
2788
2789 this->command(mtd, ONENAND_CMD_UNLOCK_ALL, 0, 0);
2790
2791
2792 this->wait(mtd, FL_LOCKING);
2793
2794
2795 while (this->read_word(this->base + ONENAND_REG_CTRL_STATUS)
2796 & ONENAND_CTRL_ONGO)
2797 continue;
2798
2799
2800 if (this->options & ONENAND_SKIP_UNLOCK_CHECK)
2801 return;
2802
2803
2804 if (onenand_check_lock_status(this))
2805 return;
2806
2807
2808 if (ONENAND_IS_DDP(this) && !FLEXONENAND(this)) {
2809
2810 ofs = this->chipsize >> 1;
2811 len = this->chipsize >> 1;
2812 }
2813 }
2814
2815 onenand_do_lock_cmd(mtd, ofs, len, ONENAND_CMD_UNLOCK);
2816}
2817
2818#ifdef CONFIG_MTD_ONENAND_OTP
2819
2820
2821
2822
2823
2824
2825
2826
2827static int onenand_otp_command(struct mtd_info *mtd, int cmd, loff_t addr,
2828 size_t len)
2829{
2830 struct onenand_chip *this = mtd->priv;
2831 int value, block, page;
2832
2833
2834 switch (cmd) {
2835 case ONENAND_CMD_OTP_ACCESS:
2836 block = (int) (addr >> this->erase_shift);
2837 page = -1;
2838 break;
2839
2840 default:
2841 block = (int) (addr >> this->erase_shift);
2842 page = (int) (addr >> this->page_shift);
2843
2844 if (ONENAND_IS_2PLANE(this)) {
2845
2846 block &= ~1;
2847
2848 if (addr & this->writesize)
2849 block++;
2850 page >>= 1;
2851 }
2852 page &= this->page_mask;
2853 break;
2854 }
2855
2856 if (block != -1) {
2857
2858 value = onenand_block_address(this, block);
2859 this->write_word(value, this->base +
2860 ONENAND_REG_START_ADDRESS1);
2861 }
2862
2863 if (page != -1) {
2864
2865 int sectors = 4, count = 4;
2866 int dataram;
2867
2868 switch (cmd) {
2869 default:
2870 if (ONENAND_IS_2PLANE(this) && cmd == ONENAND_CMD_PROG)
2871 cmd = ONENAND_CMD_2X_PROG;
2872 dataram = ONENAND_CURRENT_BUFFERRAM(this);
2873 break;
2874 }
2875
2876
2877 value = onenand_page_address(page, sectors);
2878 this->write_word(value, this->base +
2879 ONENAND_REG_START_ADDRESS8);
2880
2881
2882 value = onenand_buffer_address(dataram, sectors, count);
2883 this->write_word(value, this->base + ONENAND_REG_START_BUFFER);
2884 }
2885
2886
2887 this->write_word(ONENAND_INT_CLEAR, this->base + ONENAND_REG_INTERRUPT);
2888
2889
2890 this->write_word(cmd, this->base + ONENAND_REG_COMMAND);
2891
2892 return 0;
2893}
2894
2895
2896
2897
2898
2899
2900
2901
2902
2903
2904
2905static int onenand_otp_write_oob_nolock(struct mtd_info *mtd, loff_t to,
2906 struct mtd_oob_ops *ops)
2907{
2908 struct onenand_chip *this = mtd->priv;
2909 int column, ret = 0, oobsize;
2910 int written = 0;
2911 u_char *oobbuf;
2912 size_t len = ops->ooblen;
2913 const u_char *buf = ops->oobbuf;
2914 int block, value, status;
2915
2916 to += ops->ooboffs;
2917
2918
2919 ops->oobretlen = 0;
2920
2921 oobsize = mtd->oobsize;
2922
2923 column = to & (mtd->oobsize - 1);
2924
2925 oobbuf = this->oob_buf;
2926
2927
2928 while (written < len) {
2929 int thislen = min_t(int, oobsize, len - written);
2930
2931 cond_resched();
2932
2933 block = (int) (to >> this->erase_shift);
2934
2935
2936
2937
2938
2939 value = onenand_block_address(this, block);
2940 this->write_word(value, this->base +
2941 ONENAND_REG_START_ADDRESS1);
2942
2943
2944
2945
2946
2947
2948 value = onenand_bufferram_address(this, block);
2949 this->write_word(value, this->base +
2950 ONENAND_REG_START_ADDRESS2);
2951 ONENAND_SET_NEXT_BUFFERRAM(this);
2952
2953
2954
2955
2956 this->command(mtd, ONENAND_CMD_OTP_ACCESS, 0, 0);
2957 this->wait(mtd, FL_OTPING);
2958
2959
2960
2961 memcpy(oobbuf + column, buf, thislen);
2962
2963
2964
2965
2966
2967
2968
2969 this->write_bufferram(mtd, ONENAND_SPARERAM,
2970 oobbuf, 0, mtd->oobsize);
2971
2972 onenand_otp_command(mtd, ONENAND_CMD_PROGOOB, to, mtd->oobsize);
2973 onenand_update_bufferram(mtd, to, 0);
2974 if (ONENAND_IS_2PLANE(this)) {
2975 ONENAND_SET_BUFFERRAM1(this);
2976 onenand_update_bufferram(mtd, to + this->writesize, 0);
2977 }
2978
2979 ret = this->wait(mtd, FL_WRITING);
2980 if (ret) {
2981 printk(KERN_ERR "%s: write failed %d\n", __func__, ret);
2982 break;
2983 }
2984
2985
2986 this->command(mtd, ONENAND_CMD_RESET, 0, 0);
2987 this->wait(mtd, FL_RESETING);
2988
2989 status = this->read_word(this->base + ONENAND_REG_CTRL_STATUS);
2990 status &= 0x60;
2991
2992 if (status == 0x60) {
2993 printk(KERN_DEBUG "\nBLOCK\tSTATUS\n");
2994 printk(KERN_DEBUG "1st Block\tLOCKED\n");
2995 printk(KERN_DEBUG "OTP Block\tLOCKED\n");
2996 } else if (status == 0x20) {
2997 printk(KERN_DEBUG "\nBLOCK\tSTATUS\n");
2998 printk(KERN_DEBUG "1st Block\tLOCKED\n");
2999 printk(KERN_DEBUG "OTP Block\tUN-LOCKED\n");
3000 } else if (status == 0x40) {
3001 printk(KERN_DEBUG "\nBLOCK\tSTATUS\n");
3002 printk(KERN_DEBUG "1st Block\tUN-LOCKED\n");
3003 printk(KERN_DEBUG "OTP Block\tLOCKED\n");
3004 } else {
3005 printk(KERN_DEBUG "Reboot to check\n");
3006 }
3007
3008 written += thislen;
3009 if (written == len)
3010 break;
3011
3012 to += mtd->writesize;
3013 buf += thislen;
3014 column = 0;
3015 }
3016
3017 ops->oobretlen = written;
3018
3019 return ret;
3020}
3021
3022
3023typedef int (*otp_op_t)(struct mtd_info *mtd, loff_t form, size_t len,
3024 size_t *retlen, u_char *buf);
3025
3026
3027
3028
3029
3030
3031
3032
3033
3034
3035
3036static int do_otp_read(struct mtd_info *mtd, loff_t from, size_t len,
3037 size_t *retlen, u_char *buf)
3038{
3039 struct onenand_chip *this = mtd->priv;
3040 struct mtd_oob_ops ops = {
3041 .len = len,
3042 .ooblen = 0,
3043 .datbuf = buf,
3044 .oobbuf = NULL,
3045 };
3046 int ret;
3047
3048
3049 this->command(mtd, ONENAND_CMD_OTP_ACCESS, 0, 0);
3050 this->wait(mtd, FL_OTPING);
3051
3052 ret = ONENAND_IS_4KB_PAGE(this) ?
3053 onenand_mlc_read_ops_nolock(mtd, from, &ops) :
3054 onenand_read_ops_nolock(mtd, from, &ops);
3055
3056
3057 this->command(mtd, ONENAND_CMD_RESET, 0, 0);
3058 this->wait(mtd, FL_RESETING);
3059
3060 return ret;
3061}
3062
3063
3064
3065
3066
3067
3068
3069
3070
3071
3072
3073static int do_otp_write(struct mtd_info *mtd, loff_t to, size_t len,
3074 size_t *retlen, u_char *buf)
3075{
3076 struct onenand_chip *this = mtd->priv;
3077 unsigned char *pbuf = buf;
3078 int ret;
3079 struct mtd_oob_ops ops;
3080
3081
3082 if (len < mtd->writesize) {
3083 memcpy(this->page_buf, buf, len);
3084 memset(this->page_buf + len, 0xff, mtd->writesize - len);
3085 pbuf = this->page_buf;
3086 len = mtd->writesize;
3087 }
3088
3089
3090 this->command(mtd, ONENAND_CMD_OTP_ACCESS, 0, 0);
3091 this->wait(mtd, FL_OTPING);
3092
3093 ops.len = len;
3094 ops.ooblen = 0;
3095 ops.datbuf = pbuf;
3096 ops.oobbuf = NULL;
3097 ret = onenand_write_ops_nolock(mtd, to, &ops);
3098 *retlen = ops.retlen;
3099
3100
3101 this->command(mtd, ONENAND_CMD_RESET, 0, 0);
3102 this->wait(mtd, FL_RESETING);
3103
3104 return ret;
3105}
3106
3107
3108
3109
3110
3111
3112
3113
3114
3115
3116
3117static int do_otp_lock(struct mtd_info *mtd, loff_t from, size_t len,
3118 size_t *retlen, u_char *buf)
3119{
3120 struct onenand_chip *this = mtd->priv;
3121 struct mtd_oob_ops ops;
3122 int ret;
3123
3124 if (FLEXONENAND(this)) {
3125
3126
3127 this->command(mtd, ONENAND_CMD_OTP_ACCESS, 0, 0);
3128 this->wait(mtd, FL_OTPING);
3129
3130
3131
3132
3133 ops.len = mtd->writesize;
3134 ops.ooblen = 0;
3135 ops.datbuf = buf;
3136 ops.oobbuf = NULL;
3137 ret = onenand_write_ops_nolock(mtd, mtd->writesize * 49, &ops);
3138 *retlen = ops.retlen;
3139
3140
3141 this->command(mtd, ONENAND_CMD_RESET, 0, 0);
3142 this->wait(mtd, FL_RESETING);
3143 } else {
3144 ops.mode = MTD_OOB_PLACE;
3145 ops.ooblen = len;
3146 ops.oobbuf = buf;
3147 ops.ooboffs = 0;
3148 ret = onenand_otp_write_oob_nolock(mtd, from, &ops);
3149 *retlen = ops.oobretlen;
3150 }
3151
3152 return ret;
3153}
3154
3155
3156
3157
3158
3159
3160
3161
3162
3163
3164
3165
3166
3167static int onenand_otp_walk(struct mtd_info *mtd, loff_t from, size_t len,
3168 size_t *retlen, u_char *buf,
3169 otp_op_t action, int mode)
3170{
3171 struct onenand_chip *this = mtd->priv;
3172 int otp_pages;
3173 int density;
3174 int ret = 0;
3175
3176 *retlen = 0;
3177
3178 density = onenand_get_density(this->device_id);
3179 if (density < ONENAND_DEVICE_DENSITY_512Mb)
3180 otp_pages = 20;
3181 else
3182 otp_pages = 50;
3183
3184 if (mode == MTD_OTP_FACTORY) {
3185 from += mtd->writesize * otp_pages;
3186 otp_pages = ONENAND_PAGES_PER_BLOCK - otp_pages;
3187 }
3188
3189
3190 if (mode == MTD_OTP_USER) {
3191 if (mtd->writesize * otp_pages < from + len)
3192 return 0;
3193 } else {
3194 if (mtd->writesize * otp_pages < len)
3195 return 0;
3196 }
3197
3198 onenand_get_device(mtd, FL_OTPING);
3199 while (len > 0 && otp_pages > 0) {
3200 if (!action) {
3201 struct otp_info *otpinfo;
3202
3203 len -= sizeof(struct otp_info);
3204 if (len <= 0) {
3205 ret = -ENOSPC;
3206 break;
3207 }
3208
3209 otpinfo = (struct otp_info *) buf;
3210 otpinfo->start = from;
3211 otpinfo->length = mtd->writesize;
3212 otpinfo->locked = 0;
3213
3214 from += mtd->writesize;
3215 buf += sizeof(struct otp_info);
3216 *retlen += sizeof(struct otp_info);
3217 } else {
3218 size_t tmp_retlen;
3219
3220 ret = action(mtd, from, len, &tmp_retlen, buf);
3221
3222 buf += tmp_retlen;
3223 len -= tmp_retlen;
3224 *retlen += tmp_retlen;
3225
3226 if (ret)
3227 break;
3228 }
3229 otp_pages--;
3230 }
3231 onenand_release_device(mtd);
3232
3233 return ret;
3234}
3235
3236
3237
3238
3239
3240
3241
3242
3243
3244static int onenand_get_fact_prot_info(struct mtd_info *mtd,
3245 struct otp_info *buf, size_t len)
3246{
3247 size_t retlen;
3248 int ret;
3249
3250 ret = onenand_otp_walk(mtd, 0, len, &retlen, (u_char *) buf, NULL, MTD_OTP_FACTORY);
3251
3252 return ret ? : retlen;
3253}
3254
3255
3256
3257
3258
3259
3260
3261
3262
3263
3264
3265static int onenand_read_fact_prot_reg(struct mtd_info *mtd, loff_t from,
3266 size_t len, size_t *retlen, u_char *buf)
3267{
3268 return onenand_otp_walk(mtd, from, len, retlen, buf, do_otp_read, MTD_OTP_FACTORY);
3269}
3270
3271
3272
3273
3274
3275
3276
3277
3278
3279static int onenand_get_user_prot_info(struct mtd_info *mtd,
3280 struct otp_info *buf, size_t len)
3281{
3282 size_t retlen;
3283 int ret;
3284
3285 ret = onenand_otp_walk(mtd, 0, len, &retlen, (u_char *) buf, NULL, MTD_OTP_USER);
3286
3287 return ret ? : retlen;
3288}
3289
3290
3291
3292
3293
3294
3295
3296
3297
3298
3299
3300static int onenand_read_user_prot_reg(struct mtd_info *mtd, loff_t from,
3301 size_t len, size_t *retlen, u_char *buf)
3302{
3303 return onenand_otp_walk(mtd, from, len, retlen, buf, do_otp_read, MTD_OTP_USER);
3304}
3305
3306
3307
3308
3309
3310
3311
3312
3313
3314
3315
3316static int onenand_write_user_prot_reg(struct mtd_info *mtd, loff_t from,
3317 size_t len, size_t *retlen, u_char *buf)
3318{
3319 return onenand_otp_walk(mtd, from, len, retlen, buf, do_otp_write, MTD_OTP_USER);
3320}
3321
3322
3323
3324
3325
3326
3327
3328
3329
3330static int onenand_lock_user_prot_reg(struct mtd_info *mtd, loff_t from,
3331 size_t len)
3332{
3333 struct onenand_chip *this = mtd->priv;
3334 u_char *buf = FLEXONENAND(this) ? this->page_buf : this->oob_buf;
3335 size_t retlen;
3336 int ret;
3337 unsigned int otp_lock_offset = ONENAND_OTP_LOCK_OFFSET;
3338
3339 memset(buf, 0xff, FLEXONENAND(this) ? this->writesize
3340 : mtd->oobsize);
3341
3342
3343
3344
3345
3346
3347
3348 from = 0;
3349 len = FLEXONENAND(this) ? mtd->writesize : 16;
3350
3351
3352
3353
3354
3355
3356
3357 if (FLEXONENAND(this))
3358 otp_lock_offset = FLEXONENAND_OTP_LOCK_OFFSET;
3359
3360
3361 if (otp == 1)
3362 buf[otp_lock_offset] = 0xFC;
3363 else if (otp == 2)
3364 buf[otp_lock_offset] = 0xF3;
3365 else if (otp == 3)
3366 buf[otp_lock_offset] = 0xF0;
3367 else if (otp != 0)
3368 printk(KERN_DEBUG "[OneNAND] Invalid option selected for OTP\n");
3369
3370 ret = onenand_otp_walk(mtd, from, len, &retlen, buf, do_otp_lock, MTD_OTP_USER);
3371
3372 return ret ? : retlen;
3373}
3374
3375#endif
3376
3377
3378
3379
3380
3381
3382
3383
3384
3385static void onenand_check_features(struct mtd_info *mtd)
3386{
3387 struct onenand_chip *this = mtd->priv;
3388 unsigned int density, process, numbufs;
3389
3390
3391 density = onenand_get_density(this->device_id);
3392 process = this->version_id >> ONENAND_VERSION_PROCESS_SHIFT;
3393 numbufs = this->read_word(this->base + ONENAND_REG_NUM_BUFFERS) >> 8;
3394
3395
3396 switch (density) {
3397 case ONENAND_DEVICE_DENSITY_4Gb:
3398 if (ONENAND_IS_DDP(this))
3399 this->options |= ONENAND_HAS_2PLANE;
3400 else if (numbufs == 1) {
3401 this->options |= ONENAND_HAS_4KB_PAGE;
3402 this->options |= ONENAND_HAS_CACHE_PROGRAM;
3403 }
3404
3405 case ONENAND_DEVICE_DENSITY_2Gb:
3406
3407 if (!ONENAND_IS_DDP(this))
3408 this->options |= ONENAND_HAS_2PLANE;
3409 this->options |= ONENAND_HAS_UNLOCK_ALL;
3410
3411 case ONENAND_DEVICE_DENSITY_1Gb:
3412
3413 if (process)
3414 this->options |= ONENAND_HAS_UNLOCK_ALL;
3415 break;
3416
3417 default:
3418
3419 if (!process)
3420 this->options |= ONENAND_HAS_CONT_LOCK;
3421 break;
3422 }
3423
3424
3425 if (ONENAND_IS_MLC(this))
3426 this->options |= ONENAND_HAS_4KB_PAGE;
3427
3428 if (ONENAND_IS_4KB_PAGE(this))
3429 this->options &= ~ONENAND_HAS_2PLANE;
3430
3431 if (FLEXONENAND(this)) {
3432 this->options &= ~ONENAND_HAS_CONT_LOCK;
3433 this->options |= ONENAND_HAS_UNLOCK_ALL;
3434 }
3435
3436 if (this->options & ONENAND_HAS_CONT_LOCK)
3437 printk(KERN_DEBUG "Lock scheme is Continuous Lock\n");
3438 if (this->options & ONENAND_HAS_UNLOCK_ALL)
3439 printk(KERN_DEBUG "Chip support all block unlock\n");
3440 if (this->options & ONENAND_HAS_2PLANE)
3441 printk(KERN_DEBUG "Chip has 2 plane\n");
3442 if (this->options & ONENAND_HAS_4KB_PAGE)
3443 printk(KERN_DEBUG "Chip has 4KiB pagesize\n");
3444 if (this->options & ONENAND_HAS_CACHE_PROGRAM)
3445 printk(KERN_DEBUG "Chip has cache program feature\n");
3446}
3447
3448
3449
3450
3451
3452
3453
3454
3455static void onenand_print_device_info(int device, int version)
3456{
3457 int vcc, demuxed, ddp, density, flexonenand;
3458
3459 vcc = device & ONENAND_DEVICE_VCC_MASK;
3460 demuxed = device & ONENAND_DEVICE_IS_DEMUX;
3461 ddp = device & ONENAND_DEVICE_IS_DDP;
3462 density = onenand_get_density(device);
3463 flexonenand = device & DEVICE_IS_FLEXONENAND;
3464 printk(KERN_INFO "%s%sOneNAND%s %dMB %sV 16-bit (0x%02x)\n",
3465 demuxed ? "" : "Muxed ",
3466 flexonenand ? "Flex-" : "",
3467 ddp ? "(DDP)" : "",
3468 (16 << density),
3469 vcc ? "2.65/3.3" : "1.8",
3470 device);
3471 printk(KERN_INFO "OneNAND version = 0x%04x\n", version);
3472}
3473
3474static const struct onenand_manufacturers onenand_manuf_ids[] = {
3475 {ONENAND_MFR_SAMSUNG, "Samsung"},
3476 {ONENAND_MFR_NUMONYX, "Numonyx"},
3477};
3478
3479
3480
3481
3482
3483
3484
3485static int onenand_check_maf(int manuf)
3486{
3487 int size = ARRAY_SIZE(onenand_manuf_ids);
3488 char *name;
3489 int i;
3490
3491 for (i = 0; i < size; i++)
3492 if (manuf == onenand_manuf_ids[i].id)
3493 break;
3494
3495 if (i < size)
3496 name = onenand_manuf_ids[i].name;
3497 else
3498 name = "Unknown";
3499
3500 printk(KERN_DEBUG "OneNAND Manufacturer: %s (0x%0x)\n", name, manuf);
3501
3502 return (i == size);
3503}
3504
3505
3506
3507
3508
3509static int flexonenand_get_boundary(struct mtd_info *mtd)
3510{
3511 struct onenand_chip *this = mtd->priv;
3512 unsigned die, bdry;
3513 int ret, syscfg, locked;
3514
3515
3516 syscfg = this->read_word(this->base + ONENAND_REG_SYS_CFG1);
3517 this->write_word((syscfg | 0x0100), this->base + ONENAND_REG_SYS_CFG1);
3518
3519 for (die = 0; die < this->dies; die++) {
3520 this->command(mtd, FLEXONENAND_CMD_PI_ACCESS, die, 0);
3521 this->wait(mtd, FL_SYNCING);
3522
3523 this->command(mtd, FLEXONENAND_CMD_READ_PI, die, 0);
3524 ret = this->wait(mtd, FL_READING);
3525
3526 bdry = this->read_word(this->base + ONENAND_DATARAM);
3527 if ((bdry >> FLEXONENAND_PI_UNLOCK_SHIFT) == 3)
3528 locked = 0;
3529 else
3530 locked = 1;
3531 this->boundary[die] = bdry & FLEXONENAND_PI_MASK;
3532
3533 this->command(mtd, ONENAND_CMD_RESET, 0, 0);
3534 ret = this->wait(mtd, FL_RESETING);
3535
3536 printk(KERN_INFO "Die %d boundary: %d%s\n", die,
3537 this->boundary[die], locked ? "(Locked)" : "(Unlocked)");
3538 }
3539
3540
3541 this->write_word(syscfg, this->base + ONENAND_REG_SYS_CFG1);
3542 return 0;
3543}
3544
3545
3546
3547
3548
3549
3550static void flexonenand_get_size(struct mtd_info *mtd)
3551{
3552 struct onenand_chip *this = mtd->priv;
3553 int die, i, eraseshift, density;
3554 int blksperdie, maxbdry;
3555 loff_t ofs;
3556
3557 density = onenand_get_density(this->device_id);
3558 blksperdie = ((loff_t)(16 << density) << 20) >> (this->erase_shift);
3559 blksperdie >>= ONENAND_IS_DDP(this) ? 1 : 0;
3560 maxbdry = blksperdie - 1;
3561 eraseshift = this->erase_shift - 1;
3562
3563 mtd->numeraseregions = this->dies << 1;
3564
3565
3566 flexonenand_get_boundary(mtd);
3567 die = ofs = 0;
3568 i = -1;
3569 for (; die < this->dies; die++) {
3570 if (!die || this->boundary[die-1] != maxbdry) {
3571 i++;
3572 mtd->eraseregions[i].offset = ofs;
3573 mtd->eraseregions[i].erasesize = 1 << eraseshift;
3574 mtd->eraseregions[i].numblocks =
3575 this->boundary[die] + 1;
3576 ofs += mtd->eraseregions[i].numblocks << eraseshift;
3577 eraseshift++;
3578 } else {
3579 mtd->numeraseregions -= 1;
3580 mtd->eraseregions[i].numblocks +=
3581 this->boundary[die] + 1;
3582 ofs += (this->boundary[die] + 1) << (eraseshift - 1);
3583 }
3584 if (this->boundary[die] != maxbdry) {
3585 i++;
3586 mtd->eraseregions[i].offset = ofs;
3587 mtd->eraseregions[i].erasesize = 1 << eraseshift;
3588 mtd->eraseregions[i].numblocks = maxbdry ^
3589 this->boundary[die];
3590 ofs += mtd->eraseregions[i].numblocks << eraseshift;
3591 eraseshift--;
3592 } else
3593 mtd->numeraseregions -= 1;
3594 }
3595
3596
3597 mtd->erasesize = 1 << this->erase_shift;
3598 if (mtd->numeraseregions == 1)
3599 mtd->erasesize >>= 1;
3600
3601 printk(KERN_INFO "Device has %d eraseregions\n", mtd->numeraseregions);
3602 for (i = 0; i < mtd->numeraseregions; i++)
3603 printk(KERN_INFO "[offset: 0x%08x, erasesize: 0x%05x,"
3604 " numblocks: %04u]\n",
3605 (unsigned int) mtd->eraseregions[i].offset,
3606 mtd->eraseregions[i].erasesize,
3607 mtd->eraseregions[i].numblocks);
3608
3609 for (die = 0, mtd->size = 0; die < this->dies; die++) {
3610 this->diesize[die] = (loff_t)blksperdie << this->erase_shift;
3611 this->diesize[die] -= (loff_t)(this->boundary[die] + 1)
3612 << (this->erase_shift - 1);
3613 mtd->size += this->diesize[die];
3614 }
3615}
3616
3617
3618
3619
3620
3621
3622
3623
3624
3625
3626
3627
3628
3629
3630
3631static int flexonenand_check_blocks_erased(struct mtd_info *mtd, int start, int end)
3632{
3633 struct onenand_chip *this = mtd->priv;
3634 int i, ret;
3635 int block;
3636 struct mtd_oob_ops ops = {
3637 .mode = MTD_OOB_PLACE,
3638 .ooboffs = 0,
3639 .ooblen = mtd->oobsize,
3640 .datbuf = NULL,
3641 .oobbuf = this->oob_buf,
3642 };
3643 loff_t addr;
3644
3645 printk(KERN_DEBUG "Check blocks from %d to %d\n", start, end);
3646
3647 for (block = start; block <= end; block++) {
3648 addr = flexonenand_addr(this, block);
3649 if (onenand_block_isbad_nolock(mtd, addr, 0))
3650 continue;
3651
3652
3653
3654
3655
3656 ret = onenand_read_oob_nolock(mtd, addr, &ops);
3657 if (ret)
3658 return ret;
3659
3660 for (i = 0; i < mtd->oobsize; i++)
3661 if (this->oob_buf[i] != 0xff)
3662 break;
3663
3664 if (i != mtd->oobsize) {
3665 printk(KERN_WARNING "%s: Block %d not erased.\n",
3666 __func__, block);
3667 return 1;
3668 }
3669 }
3670
3671 return 0;
3672}
3673
3674
3675
3676
3677
3678int flexonenand_set_boundary(struct mtd_info *mtd, int die,
3679 int boundary, int lock)
3680{
3681 struct onenand_chip *this = mtd->priv;
3682 int ret, density, blksperdie, old, new, thisboundary;
3683 loff_t addr;
3684
3685
3686 if (die && (!ONENAND_IS_DDP(this)))
3687 return 0;
3688
3689
3690 if (boundary < 0 || boundary == this->boundary[die])
3691 return 0;
3692
3693 density = onenand_get_density(this->device_id);
3694 blksperdie = ((16 << density) << 20) >> this->erase_shift;
3695 blksperdie >>= ONENAND_IS_DDP(this) ? 1 : 0;
3696
3697 if (boundary >= blksperdie) {
3698 printk(KERN_ERR "%s: Invalid boundary value. "
3699 "Boundary not changed.\n", __func__);
3700 return -EINVAL;
3701 }
3702
3703
3704 old = this->boundary[die] + (die * this->density_mask);
3705 new = boundary + (die * this->density_mask);
3706 ret = flexonenand_check_blocks_erased(mtd, min(old, new) + 1, max(old, new));
3707 if (ret) {
3708 printk(KERN_ERR "%s: Please erase blocks "
3709 "before boundary change\n", __func__);
3710 return ret;
3711 }
3712
3713 this->command(mtd, FLEXONENAND_CMD_PI_ACCESS, die, 0);
3714 this->wait(mtd, FL_SYNCING);
3715
3716
3717 this->command(mtd, FLEXONENAND_CMD_READ_PI, die, 0);
3718 ret = this->wait(mtd, FL_READING);
3719
3720 thisboundary = this->read_word(this->base + ONENAND_DATARAM);
3721 if ((thisboundary >> FLEXONENAND_PI_UNLOCK_SHIFT) != 3) {
3722 printk(KERN_ERR "%s: boundary locked\n", __func__);
3723 ret = 1;
3724 goto out;
3725 }
3726
3727 printk(KERN_INFO "Changing die %d boundary: %d%s\n",
3728 die, boundary, lock ? "(Locked)" : "(Unlocked)");
3729
3730 addr = die ? this->diesize[0] : 0;
3731
3732 boundary &= FLEXONENAND_PI_MASK;
3733 boundary |= lock ? 0 : (3 << FLEXONENAND_PI_UNLOCK_SHIFT);
3734
3735 this->command(mtd, ONENAND_CMD_ERASE, addr, 0);
3736 ret = this->wait(mtd, FL_ERASING);
3737 if (ret) {
3738 printk(KERN_ERR "%s: Failed PI erase for Die %d\n",
3739 __func__, die);
3740 goto out;
3741 }
3742
3743 this->write_word(boundary, this->base + ONENAND_DATARAM);
3744 this->command(mtd, ONENAND_CMD_PROG, addr, 0);
3745 ret = this->wait(mtd, FL_WRITING);
3746 if (ret) {
3747 printk(KERN_ERR "%s: Failed PI write for Die %d\n",
3748 __func__, die);
3749 goto out;
3750 }
3751
3752 this->command(mtd, FLEXONENAND_CMD_PI_UPDATE, die, 0);
3753 ret = this->wait(mtd, FL_WRITING);
3754out:
3755 this->write_word(ONENAND_CMD_RESET, this->base + ONENAND_REG_COMMAND);
3756 this->wait(mtd, FL_RESETING);
3757 if (!ret)
3758
3759 flexonenand_get_size(mtd);
3760
3761 return ret;
3762}
3763
3764
3765
3766
3767
3768
3769
3770
3771static int onenand_chip_probe(struct mtd_info *mtd)
3772{
3773 struct onenand_chip *this = mtd->priv;
3774 int bram_maf_id, bram_dev_id, maf_id, dev_id;
3775 int syscfg;
3776
3777
3778 syscfg = this->read_word(this->base + ONENAND_REG_SYS_CFG1);
3779
3780 this->write_word((syscfg & ~ONENAND_SYS_CFG1_SYNC_READ & ~ONENAND_SYS_CFG1_SYNC_WRITE), this->base + ONENAND_REG_SYS_CFG1);
3781
3782
3783 this->write_word(ONENAND_CMD_READID, this->base + ONENAND_BOOTRAM);
3784
3785
3786 bram_maf_id = this->read_word(this->base + ONENAND_BOOTRAM + 0x0);
3787 bram_dev_id = this->read_word(this->base + ONENAND_BOOTRAM + 0x2);
3788
3789
3790 this->write_word(ONENAND_CMD_RESET, this->base + ONENAND_BOOTRAM);
3791
3792 this->wait(mtd, FL_RESETING);
3793
3794
3795 this->write_word(syscfg, this->base + ONENAND_REG_SYS_CFG1);
3796
3797
3798 if (onenand_check_maf(bram_maf_id))
3799 return -ENXIO;
3800
3801
3802 maf_id = this->read_word(this->base + ONENAND_REG_MANUFACTURER_ID);
3803 dev_id = this->read_word(this->base + ONENAND_REG_DEVICE_ID);
3804
3805
3806 if (maf_id != bram_maf_id || dev_id != bram_dev_id)
3807 return -ENXIO;
3808
3809 return 0;
3810}
3811
3812
3813
3814
3815
3816static int onenand_probe(struct mtd_info *mtd)
3817{
3818 struct onenand_chip *this = mtd->priv;
3819 int maf_id, dev_id, ver_id;
3820 int density;
3821 int ret;
3822
3823 ret = this->chip_probe(mtd);
3824 if (ret)
3825 return ret;
3826
3827
3828 maf_id = this->read_word(this->base + ONENAND_REG_MANUFACTURER_ID);
3829 dev_id = this->read_word(this->base + ONENAND_REG_DEVICE_ID);
3830 ver_id = this->read_word(this->base + ONENAND_REG_VERSION_ID);
3831 this->technology = this->read_word(this->base + ONENAND_REG_TECHNOLOGY);
3832
3833
3834 onenand_print_device_info(dev_id, ver_id);
3835 this->device_id = dev_id;
3836 this->version_id = ver_id;
3837
3838
3839 onenand_check_features(mtd);
3840
3841 density = onenand_get_density(dev_id);
3842 if (FLEXONENAND(this)) {
3843 this->dies = ONENAND_IS_DDP(this) ? 2 : 1;
3844
3845 mtd->numeraseregions = this->dies << 1;
3846 mtd->eraseregions = kzalloc(sizeof(struct mtd_erase_region_info)
3847 * (this->dies << 1), GFP_KERNEL);
3848 if (!mtd->eraseregions)
3849 return -ENOMEM;
3850 }
3851
3852
3853
3854
3855
3856 this->chipsize = (16 << density) << 20;
3857
3858
3859
3860 mtd->writesize = this->read_word(this->base + ONENAND_REG_DATA_BUFFER_SIZE);
3861
3862 if (ONENAND_IS_4KB_PAGE(this))
3863 mtd->writesize <<= 1;
3864
3865 mtd->oobsize = mtd->writesize >> 5;
3866
3867 mtd->erasesize = mtd->writesize << 6;
3868
3869
3870
3871
3872
3873 if (FLEXONENAND(this))
3874 mtd->erasesize <<= 1;
3875
3876 this->erase_shift = ffs(mtd->erasesize) - 1;
3877 this->page_shift = ffs(mtd->writesize) - 1;
3878 this->page_mask = (1 << (this->erase_shift - this->page_shift)) - 1;
3879
3880 if (ONENAND_IS_DDP(this))
3881 this->density_mask = this->chipsize >> (this->erase_shift + 1);
3882
3883 this->writesize = mtd->writesize;
3884
3885
3886
3887 if (FLEXONENAND(this))
3888 flexonenand_get_size(mtd);
3889 else
3890 mtd->size = this->chipsize;
3891
3892
3893
3894
3895
3896
3897
3898 if (ONENAND_IS_2PLANE(this)) {
3899 mtd->writesize <<= 1;
3900 mtd->erasesize <<= 1;
3901 }
3902
3903 return 0;
3904}
3905
3906
3907
3908
3909
3910static int onenand_suspend(struct mtd_info *mtd)
3911{
3912 return onenand_get_device(mtd, FL_PM_SUSPENDED);
3913}
3914
3915
3916
3917
3918
3919static void onenand_resume(struct mtd_info *mtd)
3920{
3921 struct onenand_chip *this = mtd->priv;
3922
3923 if (this->state == FL_PM_SUSPENDED)
3924 onenand_release_device(mtd);
3925 else
3926 printk(KERN_ERR "%s: resume() called for the chip which is not "
3927 "in suspended state\n", __func__);
3928}
3929
3930
3931
3932
3933
3934
3935
3936
3937
3938
3939
3940int onenand_scan(struct mtd_info *mtd, int maxchips)
3941{
3942 int i, ret;
3943 struct onenand_chip *this = mtd->priv;
3944
3945 if (!this->read_word)
3946 this->read_word = onenand_readw;
3947 if (!this->write_word)
3948 this->write_word = onenand_writew;
3949
3950 if (!this->command)
3951 this->command = onenand_command;
3952 if (!this->wait)
3953 onenand_setup_wait(mtd);
3954 if (!this->bbt_wait)
3955 this->bbt_wait = onenand_bbt_wait;
3956 if (!this->unlock_all)
3957 this->unlock_all = onenand_unlock_all;
3958
3959 if (!this->chip_probe)
3960 this->chip_probe = onenand_chip_probe;
3961
3962 if (!this->read_bufferram)
3963 this->read_bufferram = onenand_read_bufferram;
3964 if (!this->write_bufferram)
3965 this->write_bufferram = onenand_write_bufferram;
3966
3967 if (!this->block_markbad)
3968 this->block_markbad = onenand_default_block_markbad;
3969 if (!this->scan_bbt)
3970 this->scan_bbt = onenand_default_bbt;
3971
3972 if (onenand_probe(mtd))
3973 return -ENXIO;
3974
3975
3976 if (this->mmcontrol) {
3977 printk(KERN_INFO "OneNAND Sync. Burst Read support\n");
3978 this->read_bufferram = onenand_sync_read_bufferram;
3979 }
3980
3981
3982 if (!this->page_buf) {
3983 this->page_buf = kzalloc(mtd->writesize, GFP_KERNEL);
3984 if (!this->page_buf) {
3985 printk(KERN_ERR "%s: Can't allocate page_buf\n",
3986 __func__);
3987 return -ENOMEM;
3988 }
3989#ifdef CONFIG_MTD_ONENAND_VERIFY_WRITE
3990 this->verify_buf = kzalloc(mtd->writesize, GFP_KERNEL);
3991 if (!this->verify_buf) {
3992 kfree(this->page_buf);
3993 return -ENOMEM;
3994 }
3995#endif
3996 this->options |= ONENAND_PAGEBUF_ALLOC;
3997 }
3998 if (!this->oob_buf) {
3999 this->oob_buf = kzalloc(mtd->oobsize, GFP_KERNEL);
4000 if (!this->oob_buf) {
4001 printk(KERN_ERR "%s: Can't allocate oob_buf\n",
4002 __func__);
4003 if (this->options & ONENAND_PAGEBUF_ALLOC) {
4004 this->options &= ~ONENAND_PAGEBUF_ALLOC;
4005 kfree(this->page_buf);
4006 }
4007 return -ENOMEM;
4008 }
4009 this->options |= ONENAND_OOBBUF_ALLOC;
4010 }
4011
4012 this->state = FL_READY;
4013 init_waitqueue_head(&this->wq);
4014 spin_lock_init(&this->chip_lock);
4015
4016
4017
4018
4019 switch (mtd->oobsize) {
4020 case 128:
4021 this->ecclayout = &onenand_oob_128;
4022 mtd->subpage_sft = 0;
4023 break;
4024 case 64:
4025 this->ecclayout = &onenand_oob_64;
4026 mtd->subpage_sft = 2;
4027 break;
4028
4029 case 32:
4030 this->ecclayout = &onenand_oob_32;
4031 mtd->subpage_sft = 1;
4032 break;
4033
4034 default:
4035 printk(KERN_WARNING "%s: No OOB scheme defined for oobsize %d\n",
4036 __func__, mtd->oobsize);
4037 mtd->subpage_sft = 0;
4038
4039 this->ecclayout = &onenand_oob_32;
4040 break;
4041 }
4042
4043 this->subpagesize = mtd->writesize >> mtd->subpage_sft;
4044
4045
4046
4047
4048
4049 this->ecclayout->oobavail = 0;
4050 for (i = 0; i < MTD_MAX_OOBFREE_ENTRIES &&
4051 this->ecclayout->oobfree[i].length; i++)
4052 this->ecclayout->oobavail +=
4053 this->ecclayout->oobfree[i].length;
4054 mtd->oobavail = this->ecclayout->oobavail;
4055
4056 mtd->ecclayout = this->ecclayout;
4057
4058
4059 mtd->type = ONENAND_IS_MLC(this) ? MTD_MLCNANDFLASH : MTD_NANDFLASH;
4060 mtd->flags = MTD_CAP_NANDFLASH;
4061 mtd->erase = onenand_erase;
4062 mtd->point = NULL;
4063 mtd->unpoint = NULL;
4064 mtd->read = onenand_read;
4065 mtd->write = onenand_write;
4066 mtd->read_oob = onenand_read_oob;
4067 mtd->write_oob = onenand_write_oob;
4068 mtd->panic_write = onenand_panic_write;
4069#ifdef CONFIG_MTD_ONENAND_OTP
4070 mtd->get_fact_prot_info = onenand_get_fact_prot_info;
4071 mtd->read_fact_prot_reg = onenand_read_fact_prot_reg;
4072 mtd->get_user_prot_info = onenand_get_user_prot_info;
4073 mtd->read_user_prot_reg = onenand_read_user_prot_reg;
4074 mtd->write_user_prot_reg = onenand_write_user_prot_reg;
4075 mtd->lock_user_prot_reg = onenand_lock_user_prot_reg;
4076#endif
4077 mtd->sync = onenand_sync;
4078 mtd->lock = onenand_lock;
4079 mtd->unlock = onenand_unlock;
4080 mtd->suspend = onenand_suspend;
4081 mtd->resume = onenand_resume;
4082 mtd->block_isbad = onenand_block_isbad;
4083 mtd->block_markbad = onenand_block_markbad;
4084 mtd->owner = THIS_MODULE;
4085 mtd->writebufsize = mtd->writesize;
4086
4087
4088 if (!(this->options & ONENAND_SKIP_INITIAL_UNLOCKING))
4089 this->unlock_all(mtd);
4090
4091 ret = this->scan_bbt(mtd);
4092 if ((!FLEXONENAND(this)) || ret)
4093 return ret;
4094
4095
4096 for (i = 0; i < MAX_DIES; i++)
4097 flexonenand_set_boundary(mtd, i, flex_bdry[2 * i],
4098 flex_bdry[(2 * i) + 1]);
4099
4100 return 0;
4101}
4102
4103
4104
4105
4106
4107void onenand_release(struct mtd_info *mtd)
4108{
4109 struct onenand_chip *this = mtd->priv;
4110
4111#ifdef CONFIG_MTD_PARTITIONS
4112
4113 del_mtd_partitions (mtd);
4114#endif
4115
4116 del_mtd_device (mtd);
4117
4118
4119 if (this->bbm) {
4120 struct bbm_info *bbm = this->bbm;
4121 kfree(bbm->bbt);
4122 kfree(this->bbm);
4123 }
4124
4125 if (this->options & ONENAND_PAGEBUF_ALLOC) {
4126 kfree(this->page_buf);
4127#ifdef CONFIG_MTD_ONENAND_VERIFY_WRITE
4128 kfree(this->verify_buf);
4129#endif
4130 }
4131 if (this->options & ONENAND_OOBBUF_ALLOC)
4132 kfree(this->oob_buf);
4133 kfree(mtd->eraseregions);
4134}
4135
4136EXPORT_SYMBOL_GPL(onenand_scan);
4137EXPORT_SYMBOL_GPL(onenand_release);
4138
4139MODULE_LICENSE("GPL");
4140MODULE_AUTHOR("Kyungmin Park <kyungmin.park@samsung.com>");
4141MODULE_DESCRIPTION("Generic OneNAND flash driver code");
4142