forked from ~ljy/RK356X_SDK_RELEASE

hc
2023-12-09 95099d4622f8cb224d94e314c7a8e0df60b13f87
kernel/drivers/mtd/nand/raw/s3c2410.c
....@@ -1,23 +1,10 @@
1
+// SPDX-License-Identifier: GPL-2.0-or-later
12 /*
23 * Copyright © 2004-2008 Simtec Electronics
34 * http://armlinux.simtec.co.uk/
45 * Ben Dooks <ben@simtec.co.uk>
56 *
67 * Samsung S3C2410/S3C2440/S3C2412 NAND driver
7
- *
8
- * This program is free software; you can redistribute it and/or modify
9
- * it under the terms of the GNU General Public License as published by
10
- * the Free Software Foundation; either version 2 of the License, or
11
- * (at your option) any later version.
12
- *
13
- * This program is distributed in the hope that it will be useful,
14
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
- * GNU General Public License for more details.
17
- *
18
- * You should have received a copy of the GNU General Public License
19
- * along with this program; if not, write to the Free Software
20
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
218 */
229
2310 #define pr_fmt(fmt) "nand-s3c2410: " fmt
....@@ -304,7 +291,7 @@
304291 int tacls_max = (info->cpu_type == TYPE_S3C2412) ? 8 : 4;
305292 int tacls, twrph0, twrph1;
306293 unsigned long clkrate = clk_get_rate(info->clk);
307
- unsigned long uninitialized_var(set), cfg, uninitialized_var(mask);
294
+ unsigned long set, cfg, mask;
308295 unsigned long flags;
309296
310297 /* calculate the timing information for the controller */
....@@ -404,7 +391,7 @@
404391
405392 /**
406393 * s3c2410_nand_select_chip - select the given nand chip
407
- * @mtd: The MTD instance for this chip.
394
+ * @this: NAND chip object.
408395 * @chip: The chip number.
409396 *
410397 * This is called by the MTD layer to either select a given chip for the
....@@ -415,11 +402,10 @@
415402 * platform specific selection code is called to route nFCE to the specific
416403 * chip.
417404 */
418
-static void s3c2410_nand_select_chip(struct mtd_info *mtd, int chip)
405
+static void s3c2410_nand_select_chip(struct nand_chip *this, int chip)
419406 {
420407 struct s3c2410_nand_info *info;
421408 struct s3c2410_nand_mtd *nmtd;
422
- struct nand_chip *this = mtd_to_nand(mtd);
423409 unsigned long cur;
424410
425411 nmtd = nand_get_controller_data(this);
....@@ -457,9 +443,10 @@
457443 * Issue command and address cycles to the chip
458444 */
459445
460
-static void s3c2410_nand_hwcontrol(struct mtd_info *mtd, int cmd,
446
+static void s3c2410_nand_hwcontrol(struct nand_chip *chip, int cmd,
461447 unsigned int ctrl)
462448 {
449
+ struct mtd_info *mtd = nand_to_mtd(chip);
463450 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
464451
465452 if (cmd == NAND_CMD_NONE)
....@@ -473,9 +460,10 @@
473460
474461 /* command and control functions */
475462
476
-static void s3c2440_nand_hwcontrol(struct mtd_info *mtd, int cmd,
463
+static void s3c2440_nand_hwcontrol(struct nand_chip *chip, int cmd,
477464 unsigned int ctrl)
478465 {
466
+ struct mtd_info *mtd = nand_to_mtd(chip);
479467 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
480468
481469 if (cmd == NAND_CMD_NONE)
....@@ -492,29 +480,33 @@
492480 * returns 0 if the nand is busy, 1 if it is ready
493481 */
494482
495
-static int s3c2410_nand_devready(struct mtd_info *mtd)
483
+static int s3c2410_nand_devready(struct nand_chip *chip)
496484 {
485
+ struct mtd_info *mtd = nand_to_mtd(chip);
497486 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
498487 return readb(info->regs + S3C2410_NFSTAT) & S3C2410_NFSTAT_BUSY;
499488 }
500489
501
-static int s3c2440_nand_devready(struct mtd_info *mtd)
490
+static int s3c2440_nand_devready(struct nand_chip *chip)
502491 {
492
+ struct mtd_info *mtd = nand_to_mtd(chip);
503493 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
504494 return readb(info->regs + S3C2440_NFSTAT) & S3C2440_NFSTAT_READY;
505495 }
506496
507
-static int s3c2412_nand_devready(struct mtd_info *mtd)
497
+static int s3c2412_nand_devready(struct nand_chip *chip)
508498 {
499
+ struct mtd_info *mtd = nand_to_mtd(chip);
509500 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
510501 return readb(info->regs + S3C2412_NFSTAT) & S3C2412_NFSTAT_READY;
511502 }
512503
513504 /* ECC handling functions */
514505
515
-static int s3c2410_nand_correct_data(struct mtd_info *mtd, u_char *dat,
506
+static int s3c2410_nand_correct_data(struct nand_chip *chip, u_char *dat,
516507 u_char *read_ecc, u_char *calc_ecc)
517508 {
509
+ struct mtd_info *mtd = nand_to_mtd(chip);
518510 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
519511 unsigned int diff0, diff1, diff2;
520512 unsigned int bit, byte;
....@@ -591,38 +583,42 @@
591583 * generator block to ECC the data as it passes through]
592584 */
593585
594
-static void s3c2410_nand_enable_hwecc(struct mtd_info *mtd, int mode)
586
+static void s3c2410_nand_enable_hwecc(struct nand_chip *chip, int mode)
595587 {
596
- struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
588
+ struct s3c2410_nand_info *info;
597589 unsigned long ctrl;
598590
591
+ info = s3c2410_nand_mtd_toinfo(nand_to_mtd(chip));
599592 ctrl = readl(info->regs + S3C2410_NFCONF);
600593 ctrl |= S3C2410_NFCONF_INITECC;
601594 writel(ctrl, info->regs + S3C2410_NFCONF);
602595 }
603596
604
-static void s3c2412_nand_enable_hwecc(struct mtd_info *mtd, int mode)
597
+static void s3c2412_nand_enable_hwecc(struct nand_chip *chip, int mode)
605598 {
606
- struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
599
+ struct s3c2410_nand_info *info;
607600 unsigned long ctrl;
608601
602
+ info = s3c2410_nand_mtd_toinfo(nand_to_mtd(chip));
609603 ctrl = readl(info->regs + S3C2440_NFCONT);
610604 writel(ctrl | S3C2412_NFCONT_INIT_MAIN_ECC,
611605 info->regs + S3C2440_NFCONT);
612606 }
613607
614
-static void s3c2440_nand_enable_hwecc(struct mtd_info *mtd, int mode)
608
+static void s3c2440_nand_enable_hwecc(struct nand_chip *chip, int mode)
615609 {
616
- struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
610
+ struct s3c2410_nand_info *info;
617611 unsigned long ctrl;
618612
613
+ info = s3c2410_nand_mtd_toinfo(nand_to_mtd(chip));
619614 ctrl = readl(info->regs + S3C2440_NFCONT);
620615 writel(ctrl | S3C2440_NFCONT_INITECC, info->regs + S3C2440_NFCONT);
621616 }
622617
623
-static int s3c2410_nand_calculate_ecc(struct mtd_info *mtd, const u_char *dat,
624
- u_char *ecc_code)
618
+static int s3c2410_nand_calculate_ecc(struct nand_chip *chip,
619
+ const u_char *dat, u_char *ecc_code)
625620 {
621
+ struct mtd_info *mtd = nand_to_mtd(chip);
626622 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
627623
628624 ecc_code[0] = readb(info->regs + S3C2410_NFECC + 0);
....@@ -634,9 +630,10 @@
634630 return 0;
635631 }
636632
637
-static int s3c2412_nand_calculate_ecc(struct mtd_info *mtd, const u_char *dat,
638
- u_char *ecc_code)
633
+static int s3c2412_nand_calculate_ecc(struct nand_chip *chip,
634
+ const u_char *dat, u_char *ecc_code)
639635 {
636
+ struct mtd_info *mtd = nand_to_mtd(chip);
640637 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
641638 unsigned long ecc = readl(info->regs + S3C2412_NFMECC0);
642639
....@@ -649,9 +646,10 @@
649646 return 0;
650647 }
651648
652
-static int s3c2440_nand_calculate_ecc(struct mtd_info *mtd, const u_char *dat,
653
- u_char *ecc_code)
649
+static int s3c2440_nand_calculate_ecc(struct nand_chip *chip,
650
+ const u_char *dat, u_char *ecc_code)
654651 {
652
+ struct mtd_info *mtd = nand_to_mtd(chip);
655653 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
656654 unsigned long ecc = readl(info->regs + S3C2440_NFMECC0);
657655
....@@ -668,14 +666,14 @@
668666 * use read/write block to move the data buffers to/from the controller
669667 */
670668
671
-static void s3c2410_nand_read_buf(struct mtd_info *mtd, u_char *buf, int len)
669
+static void s3c2410_nand_read_buf(struct nand_chip *this, u_char *buf, int len)
672670 {
673
- struct nand_chip *this = mtd_to_nand(mtd);
674
- readsb(this->IO_ADDR_R, buf, len);
671
+ readsb(this->legacy.IO_ADDR_R, buf, len);
675672 }
676673
677
-static void s3c2440_nand_read_buf(struct mtd_info *mtd, u_char *buf, int len)
674
+static void s3c2440_nand_read_buf(struct nand_chip *this, u_char *buf, int len)
678675 {
676
+ struct mtd_info *mtd = nand_to_mtd(this);
679677 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
680678
681679 readsl(info->regs + S3C2440_NFDATA, buf, len >> 2);
....@@ -689,16 +687,16 @@
689687 }
690688 }
691689
692
-static void s3c2410_nand_write_buf(struct mtd_info *mtd, const u_char *buf,
690
+static void s3c2410_nand_write_buf(struct nand_chip *this, const u_char *buf,
693691 int len)
694692 {
695
- struct nand_chip *this = mtd_to_nand(mtd);
696
- writesb(this->IO_ADDR_W, buf, len);
693
+ writesb(this->legacy.IO_ADDR_W, buf, len);
697694 }
698695
699
-static void s3c2440_nand_write_buf(struct mtd_info *mtd, const u_char *buf,
696
+static void s3c2440_nand_write_buf(struct nand_chip *this, const u_char *buf,
700697 int len)
701698 {
699
+ struct mtd_info *mtd = nand_to_mtd(this);
702700 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
703701
704702 writesl(info->regs + S3C2440_NFDATA, buf, len >> 2);
....@@ -781,7 +779,8 @@
781779
782780 for (mtdno = 0; mtdno < info->mtd_count; mtdno++, ptr++) {
783781 pr_debug("releasing mtd %d (%p)\n", mtdno, ptr);
784
- nand_release(&ptr->chip);
782
+ WARN_ON(mtd_device_unregister(nand_to_mtd(&ptr->chip)));
783
+ nand_cleanup(&ptr->chip);
785784 }
786785 }
787786
....@@ -809,9 +808,10 @@
809808 return -ENODEV;
810809 }
811810
812
-static int s3c2410_nand_setup_data_interface(struct mtd_info *mtd, int csline,
813
- const struct nand_data_interface *conf)
811
+static int s3c2410_nand_setup_interface(struct nand_chip *chip, int csline,
812
+ const struct nand_interface_config *conf)
814813 {
814
+ struct mtd_info *mtd = nand_to_mtd(chip);
815815 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
816816 struct s3c2410_platform_nand *pdata = info->platform;
817817 const struct nand_sdr_timings *timings;
....@@ -852,10 +852,10 @@
852852
853853 nand_set_flash_node(chip, set->of_node);
854854
855
- chip->write_buf = s3c2410_nand_write_buf;
856
- chip->read_buf = s3c2410_nand_read_buf;
857
- chip->select_chip = s3c2410_nand_select_chip;
858
- chip->chip_delay = 50;
855
+ chip->legacy.write_buf = s3c2410_nand_write_buf;
856
+ chip->legacy.read_buf = s3c2410_nand_read_buf;
857
+ chip->legacy.select_chip = s3c2410_nand_select_chip;
858
+ chip->legacy.chip_delay = 50;
859859 nand_set_controller_data(chip, nmtd);
860860 chip->options = set->options;
861861 chip->controller = &info->controller;
....@@ -864,34 +864,34 @@
864864 * let's keep behavior unchanged for legacy boards booting via pdata and
865865 * auto-detect timings only when booting with a device tree.
866866 */
867
- if (np)
868
- chip->setup_data_interface = s3c2410_nand_setup_data_interface;
867
+ if (!np)
868
+ chip->options |= NAND_KEEP_TIMINGS;
869869
870870 switch (info->cpu_type) {
871871 case TYPE_S3C2410:
872
- chip->IO_ADDR_W = regs + S3C2410_NFDATA;
872
+ chip->legacy.IO_ADDR_W = regs + S3C2410_NFDATA;
873873 info->sel_reg = regs + S3C2410_NFCONF;
874874 info->sel_bit = S3C2410_NFCONF_nFCE;
875
- chip->cmd_ctrl = s3c2410_nand_hwcontrol;
876
- chip->dev_ready = s3c2410_nand_devready;
875
+ chip->legacy.cmd_ctrl = s3c2410_nand_hwcontrol;
876
+ chip->legacy.dev_ready = s3c2410_nand_devready;
877877 break;
878878
879879 case TYPE_S3C2440:
880
- chip->IO_ADDR_W = regs + S3C2440_NFDATA;
880
+ chip->legacy.IO_ADDR_W = regs + S3C2440_NFDATA;
881881 info->sel_reg = regs + S3C2440_NFCONT;
882882 info->sel_bit = S3C2440_NFCONT_nFCE;
883
- chip->cmd_ctrl = s3c2440_nand_hwcontrol;
884
- chip->dev_ready = s3c2440_nand_devready;
885
- chip->read_buf = s3c2440_nand_read_buf;
886
- chip->write_buf = s3c2440_nand_write_buf;
883
+ chip->legacy.cmd_ctrl = s3c2440_nand_hwcontrol;
884
+ chip->legacy.dev_ready = s3c2440_nand_devready;
885
+ chip->legacy.read_buf = s3c2440_nand_read_buf;
886
+ chip->legacy.write_buf = s3c2440_nand_write_buf;
887887 break;
888888
889889 case TYPE_S3C2412:
890
- chip->IO_ADDR_W = regs + S3C2440_NFDATA;
890
+ chip->legacy.IO_ADDR_W = regs + S3C2440_NFDATA;
891891 info->sel_reg = regs + S3C2440_NFCONT;
892892 info->sel_bit = S3C2412_NFCONT_nFCE0;
893
- chip->cmd_ctrl = s3c2440_nand_hwcontrol;
894
- chip->dev_ready = s3c2412_nand_devready;
893
+ chip->legacy.cmd_ctrl = s3c2440_nand_hwcontrol;
894
+ chip->legacy.dev_ready = s3c2412_nand_devready;
895895
896896 if (readl(regs + S3C2410_NFCONF) & S3C2412_NFCONF_NANDBOOT)
897897 dev_info(info->device, "System booted from NAND\n");
....@@ -899,12 +899,12 @@
899899 break;
900900 }
901901
902
- chip->IO_ADDR_R = chip->IO_ADDR_W;
902
+ chip->legacy.IO_ADDR_R = chip->legacy.IO_ADDR_W;
903903
904904 nmtd->info = info;
905905 nmtd->set = set;
906906
907
- chip->ecc.mode = info->platform->ecc_mode;
907
+ chip->ecc.engine_type = info->platform->engine_type;
908908
909909 /*
910910 * If you use u-boot BBT creation code, specifying this flag will
....@@ -929,24 +929,24 @@
929929 struct mtd_info *mtd = nand_to_mtd(chip);
930930 struct s3c2410_nand_info *info = s3c2410_nand_mtd_toinfo(mtd);
931931
932
- switch (chip->ecc.mode) {
932
+ switch (chip->ecc.engine_type) {
933933
934
- case NAND_ECC_NONE:
934
+ case NAND_ECC_ENGINE_TYPE_NONE:
935935 dev_info(info->device, "ECC disabled\n");
936936 break;
937937
938
- case NAND_ECC_SOFT:
938
+ case NAND_ECC_ENGINE_TYPE_SOFT:
939939 /*
940
- * This driver expects Hamming based ECC when ecc_mode is set
941
- * to NAND_ECC_SOFT. Force ecc.algo to NAND_ECC_HAMMING to
942
- * avoid adding an extra ecc_algo field to
943
- * s3c2410_platform_nand.
940
+ * This driver expects Hamming based ECC when engine_type is set
941
+ * to NAND_ECC_ENGINE_TYPE_SOFT. Force ecc.algo to
942
+ * NAND_ECC_ALGO_HAMMING to avoid adding an extra ecc_algo field
943
+ * to s3c2410_platform_nand.
944944 */
945
- chip->ecc.algo = NAND_ECC_HAMMING;
945
+ chip->ecc.algo = NAND_ECC_ALGO_HAMMING;
946946 dev_info(info->device, "soft ECC\n");
947947 break;
948948
949
- case NAND_ECC_HW:
949
+ case NAND_ECC_ENGINE_TYPE_ON_HOST:
950950 chip->ecc.calculate = s3c2410_nand_calculate_ecc;
951951 chip->ecc.correct = s3c2410_nand_correct_data;
952952 chip->ecc.strength = 1;
....@@ -999,6 +999,7 @@
999999
10001000 static const struct nand_controller_ops s3c24xx_nand_controller_ops = {
10011001 .attach_chip = s3c2410_nand_attach_chip,
1002
+ .setup_interface = s3c2410_nand_setup_interface,
10021003 };
10031004
10041005 static const struct of_device_id s3c24xx_nand_dt_ids[] = {