1 // SPDX-License-Identifier: GPL-2.0+
3 * Arasan NAND Flash Controller Driver
5 * Copyright (C) 2014 - 2015 Xilinx, Inc.
11 #include <linux/errno.h>
12 #include <linux/mtd/mtd.h>
13 #include <linux/mtd/rawnand.h>
14 #include <linux/mtd/partitions.h>
15 #include <linux/mtd/nand_ecc.h>
16 #include <asm/arch/hardware.h>
17 #include <asm/arch/sys_proto.h>
23 bool on_die_ecc_enabled;
27 struct nand_regs *reg;
28 struct nand_config config;
31 struct arasan_nand_info {
33 struct nand_drv nand_ctrl;
34 struct nand_chip nand_chip;
68 struct arasan_nand_command_format {
75 #define ONDIE_ECC_FEATURE_ADDR 0x90
76 #define ENABLE_ONDIE_ECC 0x08
78 #define ARASAN_PROG_RD_MASK 0x00000001
79 #define ARASAN_PROG_BLK_ERS_MASK 0x00000004
80 #define ARASAN_PROG_RD_ID_MASK 0x00000040
81 #define ARASAN_PROG_RD_STS_MASK 0x00000008
82 #define ARASAN_PROG_PG_PROG_MASK 0x00000010
83 #define ARASAN_PROG_RD_PARAM_PG_MASK 0x00000080
84 #define ARASAN_PROG_RST_MASK 0x00000100
85 #define ARASAN_PROG_GET_FTRS_MASK 0x00000200
86 #define ARASAN_PROG_SET_FTRS_MASK 0x00000400
87 #define ARASAN_PROG_CHNG_ROWADR_END_MASK 0x00400000
89 #define ARASAN_NAND_CMD_ECC_ON_MASK 0x80000000
90 #define ARASAN_NAND_CMD_CMD12_MASK 0xFFFF
91 #define ARASAN_NAND_CMD_PG_SIZE_MASK 0x3800000
92 #define ARASAN_NAND_CMD_PG_SIZE_SHIFT 23
93 #define ARASAN_NAND_CMD_CMD2_SHIFT 8
94 #define ARASAN_NAND_CMD_ADDR_CYCL_MASK 0x70000000
95 #define ARASAN_NAND_CMD_ADDR_CYCL_SHIFT 28
97 #define ARASAN_NAND_MEM_ADDR1_PAGE_MASK 0xFFFF0000
98 #define ARASAN_NAND_MEM_ADDR1_COL_MASK 0xFFFF
99 #define ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT 16
100 #define ARASAN_NAND_MEM_ADDR2_PAGE_MASK 0xFF
101 #define ARASAN_NAND_MEM_ADDR2_CS_MASK 0xC0000000
102 #define ARASAN_NAND_MEM_ADDR2_CS0_MASK (0x3 << 30)
103 #define ARASAN_NAND_MEM_ADDR2_CS1_MASK (0x1 << 30)
104 #define ARASAN_NAND_MEM_ADDR2_BCH_MASK 0xE000000
105 #define ARASAN_NAND_MEM_ADDR2_BCH_SHIFT 25
107 #define ARASAN_NAND_INT_STS_ERR_EN_MASK 0x10
108 #define ARASAN_NAND_INT_STS_MUL_BIT_ERR_MASK 0x08
109 #define ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK 0x02
110 #define ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK 0x01
111 #define ARASAN_NAND_INT_STS_XFR_CMPLT_MASK 0x04
113 #define ARASAN_NAND_PKT_REG_PKT_CNT_MASK 0xFFF000
114 #define ARASAN_NAND_PKT_REG_PKT_SIZE_MASK 0x7FF
115 #define ARASAN_NAND_PKT_REG_PKT_CNT_SHFT 12
117 #define ARASAN_NAND_ROW_ADDR_CYCL_MASK 0x0F
118 #define ARASAN_NAND_COL_ADDR_CYCL_MASK 0xF0
119 #define ARASAN_NAND_COL_ADDR_CYCL_SHIFT 4
121 #define ARASAN_NAND_ECC_SIZE_SHIFT 16
122 #define ARASAN_NAND_ECC_BCH_SHIFT 27
124 #define ARASAN_NAND_PKTSIZE_1K 1024
125 #define ARASAN_NAND_PKTSIZE_512 512
127 #define ARASAN_NAND_POLL_TIMEOUT 1000000
128 #define ARASAN_NAND_INVALID_ADDR_CYCL 0xFF
130 #define ERR_ADDR_CYCLE -1
131 #define READ_BUFF_SIZE 0x4000
133 static struct arasan_nand_command_format *curr_cmd;
143 static struct arasan_nand_command_format arasan_nand_commands[] = {
144 {NAND_CMD_READ0, NAND_CMD_READSTART, NAND_ADDR_CYCL_BOTH,
145 ARASAN_PROG_RD_MASK},
146 {NAND_CMD_RNDOUT, NAND_CMD_RNDOUTSTART, NAND_ADDR_CYCL_COL,
147 ARASAN_PROG_RD_MASK},
148 {NAND_CMD_READID, NAND_CMD_NONE, NAND_ADDR_CYCL_ONE,
149 ARASAN_PROG_RD_ID_MASK},
150 {NAND_CMD_STATUS, NAND_CMD_NONE, NAND_ADDR_CYCL_NONE,
151 ARASAN_PROG_RD_STS_MASK},
152 {NAND_CMD_SEQIN, NAND_CMD_PAGEPROG, NAND_ADDR_CYCL_BOTH,
153 ARASAN_PROG_PG_PROG_MASK},
154 {NAND_CMD_RNDIN, NAND_CMD_NONE, NAND_ADDR_CYCL_COL,
155 ARASAN_PROG_CHNG_ROWADR_END_MASK},
156 {NAND_CMD_ERASE1, NAND_CMD_ERASE2, NAND_ADDR_CYCL_ROW,
157 ARASAN_PROG_BLK_ERS_MASK},
158 {NAND_CMD_RESET, NAND_CMD_NONE, NAND_ADDR_CYCL_NONE,
159 ARASAN_PROG_RST_MASK},
160 {NAND_CMD_PARAM, NAND_CMD_NONE, NAND_ADDR_CYCL_ONE,
161 ARASAN_PROG_RD_PARAM_PG_MASK},
162 {NAND_CMD_GET_FEATURES, NAND_CMD_NONE, NAND_ADDR_CYCL_ONE,
163 ARASAN_PROG_GET_FTRS_MASK},
164 {NAND_CMD_SET_FEATURES, NAND_CMD_NONE, NAND_ADDR_CYCL_ONE,
165 ARASAN_PROG_SET_FTRS_MASK},
166 {NAND_CMD_NONE, NAND_CMD_NONE, NAND_ADDR_CYCL_NONE, 0},
169 struct arasan_ecc_matrix {
171 u32 ecc_codeword_size;
179 static const struct arasan_ecc_matrix ecc_matrix[] = {
180 {512, 512, 1, 0, 0, 0x20D, 0x3},
181 {512, 512, 4, 1, 3, 0x209, 0x7},
182 {512, 512, 8, 1, 2, 0x203, 0xD},
186 {2048, 512, 1, 0, 0, 0x834, 0xC},
187 {2048, 512, 4, 1, 3, 0x826, 0x1A},
188 {2048, 512, 8, 1, 2, 0x80c, 0x34},
189 {2048, 512, 12, 1, 1, 0x822, 0x4E},
190 {2048, 512, 16, 1, 0, 0x808, 0x68},
191 {2048, 1024, 24, 1, 4, 0x81c, 0x54},
195 {4096, 512, 1, 0, 0, 0x1068, 0x18},
196 {4096, 512, 4, 1, 3, 0x104c, 0x34},
197 {4096, 512, 8, 1, 2, 0x1018, 0x68},
198 {4096, 512, 12, 1, 1, 0x1044, 0x9C},
199 {4096, 512, 16, 1, 0, 0x1010, 0xD0},
200 {4096, 1024, 24, 1, 4, 0x1038, 0xA8},
204 {8192, 512, 1, 0, 0, 0x20d0, 0x30},
205 {8192, 512, 4, 1, 3, 0x2098, 0x68},
206 {8192, 512, 8, 1, 2, 0x2030, 0xD0},
207 {8192, 512, 12, 1, 1, 0x2088, 0x138},
208 {8192, 512, 16, 1, 0, 0x2020, 0x1A0},
209 {8192, 1024, 24, 1, 4, 0x2070, 0x150},
213 {16384, 512, 1, 0, 0, 0x4460, 0x60},
214 {16384, 512, 4, 1, 3, 0x43f0, 0xD0},
215 {16384, 512, 8, 1, 2, 0x4320, 0x1A0},
216 {16384, 512, 12, 1, 1, 0x4250, 0x270},
217 {16384, 512, 16, 1, 0, 0x4180, 0x340},
218 {16384, 1024, 24, 1, 4, 0x4220, 0x2A0}
221 static struct nand_ecclayout ondie_nand_oob_64 = {
225 8, 9, 10, 11, 12, 13, 14, 15,
226 24, 25, 26, 27, 28, 29, 30, 31,
227 40, 41, 42, 43, 44, 45, 46, 47,
228 56, 57, 58, 59, 60, 61, 62, 63
232 { .offset = 4, .length = 4 },
233 { .offset = 20, .length = 4 },
234 { .offset = 36, .length = 4 },
235 { .offset = 52, .length = 4 }
240 * bbt decriptors for chips with on-die ECC and
241 * chips with 64-byte OOB
243 static u8 bbt_pattern[] = {'B', 'b', 't', '0' };
244 static u8 mirror_pattern[] = {'1', 't', 'b', 'B' };
246 static struct nand_bbt_descr bbt_main_descr = {
247 .options = NAND_BBT_LASTBLOCK | NAND_BBT_CREATE | NAND_BBT_WRITE |
248 NAND_BBT_2BIT | NAND_BBT_VERSION | NAND_BBT_PERCHIP,
253 .pattern = bbt_pattern
256 static struct nand_bbt_descr bbt_mirror_descr = {
257 .options = NAND_BBT_LASTBLOCK | NAND_BBT_CREATE | NAND_BBT_WRITE |
258 NAND_BBT_2BIT | NAND_BBT_VERSION | NAND_BBT_PERCHIP,
263 .pattern = mirror_pattern
266 static u8 buf_data[READ_BUFF_SIZE];
267 static u32 buf_index;
269 static struct nand_ecclayout nand_oob;
271 static void arasan_nand_select_chip(struct mtd_info *mtd, int chip)
273 struct nand_chip *nand_chip = mtd_to_nand(mtd);
274 struct nand_drv *info = nand_get_controller_data(nand_chip);
277 reg_val = readl(&info->reg->memadr_reg2);
279 reg_val &= ~ARASAN_NAND_MEM_ADDR2_CS0_MASK;
280 writel(reg_val, &info->reg->memadr_reg2);
281 } else if (chip == 1) {
282 reg_val |= ARASAN_NAND_MEM_ADDR2_CS1_MASK;
283 writel(reg_val, &info->reg->memadr_reg2);
287 static void arasan_nand_enable_ecc(struct mtd_info *mtd)
289 struct nand_chip *chip = mtd_to_nand(mtd);
290 struct nand_drv *info = nand_get_controller_data(chip);
293 reg_val = readl(&info->reg->cmd_reg);
294 reg_val |= ARASAN_NAND_CMD_ECC_ON_MASK;
296 writel(reg_val, &info->reg->cmd_reg);
299 static u8 arasan_nand_get_addrcycle(struct mtd_info *mtd)
302 struct nand_chip *chip = mtd_to_nand(mtd);
304 switch (curr_cmd->addr_cycles) {
305 case NAND_ADDR_CYCL_NONE:
308 case NAND_ADDR_CYCL_ONE:
311 case NAND_ADDR_CYCL_ROW:
312 addrcycles = chip->onfi_params.addr_cycles &
313 ARASAN_NAND_ROW_ADDR_CYCL_MASK;
315 case NAND_ADDR_CYCL_COL:
316 addrcycles = (chip->onfi_params.addr_cycles &
317 ARASAN_NAND_COL_ADDR_CYCL_MASK) >>
318 ARASAN_NAND_COL_ADDR_CYCL_SHIFT;
320 case NAND_ADDR_CYCL_BOTH:
321 addrcycles = chip->onfi_params.addr_cycles &
322 ARASAN_NAND_ROW_ADDR_CYCL_MASK;
323 addrcycles += (chip->onfi_params.addr_cycles &
324 ARASAN_NAND_COL_ADDR_CYCL_MASK) >>
325 ARASAN_NAND_COL_ADDR_CYCL_SHIFT;
328 addrcycles = ARASAN_NAND_INVALID_ADDR_CYCL;
334 static int arasan_nand_read_page(struct mtd_info *mtd, u8 *buf, u32 size)
336 struct nand_chip *chip = mtd_to_nand(mtd);
337 struct nand_drv *info = nand_get_controller_data(chip);
338 struct nand_config *nand = &info->config;
339 u32 reg_val, i, pktsize, pktnum;
340 u32 *bufptr = (u32 *)buf;
345 if (chip->ecc_step_ds >= ARASAN_NAND_PKTSIZE_1K)
346 pktsize = ARASAN_NAND_PKTSIZE_1K;
348 pktsize = ARASAN_NAND_PKTSIZE_512;
351 pktnum = size/pktsize + 1;
353 pktnum = size/pktsize;
355 reg_val = readl(&info->reg->intsts_enr);
356 reg_val |= ARASAN_NAND_INT_STS_ERR_EN_MASK |
357 ARASAN_NAND_INT_STS_MUL_BIT_ERR_MASK;
358 writel(reg_val, &info->reg->intsts_enr);
360 reg_val = readl(&info->reg->pkt_reg);
361 reg_val &= ~(ARASAN_NAND_PKT_REG_PKT_CNT_MASK |
362 ARASAN_NAND_PKT_REG_PKT_SIZE_MASK);
363 reg_val |= (pktnum << ARASAN_NAND_PKT_REG_PKT_CNT_SHFT) |
365 writel(reg_val, &info->reg->pkt_reg);
367 if (!nand->on_die_ecc_enabled) {
368 arasan_nand_enable_ecc(mtd);
369 addr_cycles = arasan_nand_get_addrcycle(mtd);
370 if (addr_cycles == ARASAN_NAND_INVALID_ADDR_CYCL)
371 return ERR_ADDR_CYCLE;
373 writel((NAND_CMD_RNDOUTSTART << ARASAN_NAND_CMD_CMD2_SHIFT) |
374 NAND_CMD_RNDOUT | (addr_cycles <<
375 ARASAN_NAND_CMD_ADDR_CYCL_SHIFT),
376 &info->reg->ecc_sprcmd_reg);
378 writel(curr_cmd->pgm, &info->reg->pgm_reg);
380 while (rdcount < pktnum) {
381 timeout = ARASAN_NAND_POLL_TIMEOUT;
382 while (!(readl(&info->reg->intsts_reg) &
383 ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK) && timeout) {
388 puts("arasan_read_page: timedout:Buff RDY\n");
394 if (pktnum == rdcount) {
395 reg_val = readl(&info->reg->intsts_enr);
396 reg_val |= ARASAN_NAND_INT_STS_XFR_CMPLT_MASK;
397 writel(reg_val, &info->reg->intsts_enr);
399 reg_val = readl(&info->reg->intsts_enr);
400 writel(reg_val | ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK,
401 &info->reg->intsts_enr);
403 reg_val = readl(&info->reg->intsts_reg);
404 writel(reg_val | ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK,
405 &info->reg->intsts_reg);
407 for (i = 0; i < pktsize/4; i++)
408 bufptr[i] = readl(&info->reg->buf_dataport);
413 if (rdcount >= pktnum)
416 writel(ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK,
417 &info->reg->intsts_enr);
420 timeout = ARASAN_NAND_POLL_TIMEOUT;
422 while (!(readl(&info->reg->intsts_reg) &
423 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
428 puts("arasan rd_page timedout:Xfer CMPLT\n");
432 reg_val = readl(&info->reg->intsts_enr);
433 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
434 &info->reg->intsts_enr);
435 reg_val = readl(&info->reg->intsts_reg);
436 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
437 &info->reg->intsts_reg);
439 if (!nand->on_die_ecc_enabled) {
440 if (readl(&info->reg->intsts_reg) &
441 ARASAN_NAND_INT_STS_MUL_BIT_ERR_MASK) {
442 printf("arasan rd_page:sbiterror\n");
446 if (readl(&info->reg->intsts_reg) &
447 ARASAN_NAND_INT_STS_ERR_EN_MASK) {
448 mtd->ecc_stats.failed++;
449 printf("arasan rd_page:multibiterror\n");
457 static int arasan_nand_read_page_hwecc(struct mtd_info *mtd,
458 struct nand_chip *chip, u8 *buf, int oob_required, int page)
462 status = arasan_nand_read_page(mtd, buf, (mtd->writesize));
465 chip->ecc.read_oob(mtd, chip, page);
470 static void arasan_nand_fill_tx(struct mtd_info *mtd, const u8 *buf, int len)
472 struct nand_chip *chip = mtd_to_nand(mtd);
473 struct nand_drv *info = nand_get_controller_data(chip);
474 u32 __iomem *nand = &info->reg->buf_dataport;
476 if (((unsigned long)buf & 0x3) != 0) {
477 if (((unsigned long)buf & 0x1) != 0) {
485 if (((unsigned long)buf & 0x3) != 0) {
487 writew(*(u16 *)buf, nand);
495 writel(*(u32 *)buf, nand);
502 writew(*(u16 *)buf, nand);
512 static int arasan_nand_write_page_hwecc(struct mtd_info *mtd,
513 struct nand_chip *chip, const u8 *buf, int oob_required,
516 struct nand_drv *info = nand_get_controller_data(chip);
517 struct nand_config *nand = &info->config;
518 u32 reg_val, i, pktsize, pktnum;
519 const u32 *bufptr = (const u32 *)buf;
520 u32 timeout = ARASAN_NAND_POLL_TIMEOUT;
521 u32 size = mtd->writesize;
523 u8 column_addr_cycles;
525 if (chip->ecc_step_ds >= ARASAN_NAND_PKTSIZE_1K)
526 pktsize = ARASAN_NAND_PKTSIZE_1K;
528 pktsize = ARASAN_NAND_PKTSIZE_512;
531 pktnum = size/pktsize + 1;
533 pktnum = size/pktsize;
535 reg_val = readl(&info->reg->pkt_reg);
536 reg_val &= ~(ARASAN_NAND_PKT_REG_PKT_CNT_MASK |
537 ARASAN_NAND_PKT_REG_PKT_SIZE_MASK);
538 reg_val |= (pktnum << ARASAN_NAND_PKT_REG_PKT_CNT_SHFT) | pktsize;
539 writel(reg_val, &info->reg->pkt_reg);
541 if (!nand->on_die_ecc_enabled) {
542 arasan_nand_enable_ecc(mtd);
543 column_addr_cycles = (chip->onfi_params.addr_cycles &
544 ARASAN_NAND_COL_ADDR_CYCL_MASK) >>
545 ARASAN_NAND_COL_ADDR_CYCL_SHIFT;
546 writel((NAND_CMD_RNDIN | (column_addr_cycles << 28)),
547 &info->reg->ecc_sprcmd_reg);
549 writel(curr_cmd->pgm, &info->reg->pgm_reg);
551 while (rdcount < pktnum) {
552 timeout = ARASAN_NAND_POLL_TIMEOUT;
553 while (!(readl(&info->reg->intsts_reg) &
554 ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK) && timeout) {
560 puts("arasan_write_page: timedout:Buff RDY\n");
566 if (pktnum == rdcount) {
567 reg_val = readl(&info->reg->intsts_enr);
568 reg_val |= ARASAN_NAND_INT_STS_XFR_CMPLT_MASK;
569 writel(reg_val, &info->reg->intsts_enr);
571 reg_val = readl(&info->reg->intsts_enr);
572 writel(reg_val | ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK,
573 &info->reg->intsts_enr);
576 reg_val = readl(&info->reg->intsts_reg);
577 writel(reg_val | ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK,
578 &info->reg->intsts_reg);
580 for (i = 0; i < pktsize/4; i++)
581 writel(bufptr[i], &info->reg->buf_dataport);
585 if (rdcount >= pktnum)
588 writel(ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK,
589 &info->reg->intsts_enr);
592 timeout = ARASAN_NAND_POLL_TIMEOUT;
594 while (!(readl(&info->reg->intsts_reg) &
595 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
600 puts("arasan write_page timedout:Xfer CMPLT\n");
604 reg_val = readl(&info->reg->intsts_enr);
605 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
606 &info->reg->intsts_enr);
607 reg_val = readl(&info->reg->intsts_reg);
608 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
609 &info->reg->intsts_reg);
612 chip->ecc.write_oob(mtd, chip, nand->page);
617 static int arasan_nand_read_oob(struct mtd_info *mtd, struct nand_chip *chip,
620 chip->cmdfunc(mtd, NAND_CMD_READOOB, 0, page);
621 chip->read_buf(mtd, chip->oob_poi, (mtd->oobsize));
626 static int arasan_nand_write_oob(struct mtd_info *mtd, struct nand_chip *chip,
630 const u8 *buf = chip->oob_poi;
632 chip->cmdfunc(mtd, NAND_CMD_SEQIN, mtd->writesize, page);
633 chip->write_buf(mtd, buf, mtd->oobsize);
638 static int arasan_nand_reset(struct mtd_info *mtd,
639 struct arasan_nand_command_format *curr_cmd)
641 struct nand_chip *chip = mtd_to_nand(mtd);
642 struct nand_drv *info = nand_get_controller_data(chip);
643 u32 timeout = ARASAN_NAND_POLL_TIMEOUT;
646 writel(ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
647 &info->reg->intsts_enr);
648 cmd_reg = readl(&info->reg->cmd_reg);
649 cmd_reg &= ~ARASAN_NAND_CMD_CMD12_MASK;
651 cmd_reg |= curr_cmd->cmd1 |
652 (curr_cmd->cmd2 << ARASAN_NAND_CMD_CMD2_SHIFT);
653 writel(cmd_reg, &info->reg->cmd_reg);
654 writel(curr_cmd->pgm, &info->reg->pgm_reg);
656 while (!(readl(&info->reg->intsts_reg) &
657 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
662 printf("ERROR:%s timedout\n", __func__);
666 writel(ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
667 &info->reg->intsts_enr);
669 writel(ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
670 &info->reg->intsts_reg);
675 static u8 arasan_nand_page(struct mtd_info *mtd)
679 switch (mtd->writesize) {
699 printf("%s:Pagesize>16K\n", __func__);
706 static int arasan_nand_send_wrcmd(struct arasan_nand_command_format *curr_cmd,
707 int column, int page_addr, struct mtd_info *mtd)
709 struct nand_chip *chip = mtd_to_nand(mtd);
710 struct nand_drv *info = nand_get_controller_data(chip);
712 u8 page_val, addr_cycles;
714 writel(ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK,
715 &info->reg->intsts_enr);
716 reg_val = readl(&info->reg->cmd_reg);
717 reg_val &= ~ARASAN_NAND_CMD_CMD12_MASK;
718 reg_val |= curr_cmd->cmd1 |
719 (curr_cmd->cmd2 << ARASAN_NAND_CMD_CMD2_SHIFT);
720 if (curr_cmd->cmd1 == NAND_CMD_SEQIN) {
721 reg_val &= ~ARASAN_NAND_CMD_PG_SIZE_MASK;
722 page_val = arasan_nand_page(mtd);
723 reg_val |= (page_val << ARASAN_NAND_CMD_PG_SIZE_SHIFT);
726 reg_val &= ~ARASAN_NAND_CMD_ADDR_CYCL_MASK;
727 addr_cycles = arasan_nand_get_addrcycle(mtd);
729 if (addr_cycles == ARASAN_NAND_INVALID_ADDR_CYCL)
730 return ERR_ADDR_CYCLE;
732 reg_val |= (addr_cycles <<
733 ARASAN_NAND_CMD_ADDR_CYCL_SHIFT);
734 writel(reg_val, &info->reg->cmd_reg);
739 page = (page_addr << ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT) &
740 ARASAN_NAND_MEM_ADDR1_PAGE_MASK;
741 column &= ARASAN_NAND_MEM_ADDR1_COL_MASK;
742 writel(page | column, &info->reg->memadr_reg1);
744 reg_val = readl(&info->reg->memadr_reg2);
745 reg_val &= ~ARASAN_NAND_MEM_ADDR2_PAGE_MASK;
746 reg_val |= (page_addr >> ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT);
747 writel(reg_val, &info->reg->memadr_reg2);
752 static void arasan_nand_write_buf(struct mtd_info *mtd, const u8 *buf, int len)
754 struct nand_chip *chip = mtd_to_nand(mtd);
755 struct nand_drv *info = nand_get_controller_data(chip);
757 u32 timeout = ARASAN_NAND_POLL_TIMEOUT;
759 reg_val = readl(&info->reg->pkt_reg);
760 reg_val &= ~(ARASAN_NAND_PKT_REG_PKT_CNT_MASK |
761 ARASAN_NAND_PKT_REG_PKT_SIZE_MASK);
763 reg_val |= (1 << ARASAN_NAND_PKT_REG_PKT_CNT_SHFT) | len;
764 writel(reg_val, &info->reg->pkt_reg);
765 writel(curr_cmd->pgm, &info->reg->pgm_reg);
767 while (!(readl(&info->reg->intsts_reg) &
768 ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK) && timeout) {
774 puts("ERROR:arasan_nand_write_buf timedout:Buff RDY\n");
776 reg_val = readl(&info->reg->intsts_enr);
777 reg_val |= ARASAN_NAND_INT_STS_XFR_CMPLT_MASK;
778 writel(reg_val, &info->reg->intsts_enr);
779 writel(reg_val | ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK,
780 &info->reg->intsts_enr);
781 reg_val = readl(&info->reg->intsts_reg);
782 writel(reg_val | ARASAN_NAND_INT_STS_BUF_WR_RDY_MASK,
783 &info->reg->intsts_reg);
785 arasan_nand_fill_tx(mtd, buf, len);
787 timeout = ARASAN_NAND_POLL_TIMEOUT;
788 while (!(readl(&info->reg->intsts_reg) &
789 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
794 puts("ERROR:arasan_nand_write_buf timedout:Xfer CMPLT\n");
796 writel(readl(&info->reg->intsts_enr) |
797 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
798 &info->reg->intsts_enr);
799 writel(readl(&info->reg->intsts_reg) |
800 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
801 &info->reg->intsts_reg);
804 static int arasan_nand_erase(struct arasan_nand_command_format *curr_cmd,
805 int column, int page_addr, struct mtd_info *mtd)
807 struct nand_chip *chip = mtd_to_nand(mtd);
808 struct nand_drv *info = nand_get_controller_data(chip);
810 u32 timeout = ARASAN_NAND_POLL_TIMEOUT;
813 writel(ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
814 &info->reg->intsts_enr);
815 reg_val = readl(&info->reg->cmd_reg);
816 reg_val &= ~ARASAN_NAND_CMD_CMD12_MASK;
817 reg_val |= curr_cmd->cmd1 |
818 (curr_cmd->cmd2 << ARASAN_NAND_CMD_CMD2_SHIFT);
819 row_addr_cycles = arasan_nand_get_addrcycle(mtd);
821 if (row_addr_cycles == ARASAN_NAND_INVALID_ADDR_CYCL)
822 return ERR_ADDR_CYCLE;
824 reg_val &= ~ARASAN_NAND_CMD_ADDR_CYCL_MASK;
825 reg_val |= (row_addr_cycles <<
826 ARASAN_NAND_CMD_ADDR_CYCL_SHIFT);
828 writel(reg_val, &info->reg->cmd_reg);
830 page = (page_addr >> ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT) &
831 ARASAN_NAND_MEM_ADDR1_COL_MASK;
832 column = page_addr & ARASAN_NAND_MEM_ADDR1_COL_MASK;
833 writel(column | (page << ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT),
834 &info->reg->memadr_reg1);
836 reg_val = readl(&info->reg->memadr_reg2);
837 reg_val &= ~ARASAN_NAND_MEM_ADDR2_PAGE_MASK;
838 reg_val |= (page_addr >> ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT);
839 writel(reg_val, &info->reg->memadr_reg2);
840 writel(curr_cmd->pgm, &info->reg->pgm_reg);
842 while (!(readl(&info->reg->intsts_reg) &
843 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
848 printf("ERROR:%s timedout:Xfer CMPLT\n", __func__);
852 reg_val = readl(&info->reg->intsts_enr);
853 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
854 &info->reg->intsts_enr);
855 reg_val = readl(&info->reg->intsts_reg);
856 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
857 &info->reg->intsts_reg);
862 static int arasan_nand_read_status(struct arasan_nand_command_format *curr_cmd,
863 int column, int page_addr, struct mtd_info *mtd)
865 struct nand_chip *chip = mtd_to_nand(mtd);
866 struct nand_drv *info = nand_get_controller_data(chip);
868 u32 timeout = ARASAN_NAND_POLL_TIMEOUT;
871 writel(ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
872 &info->reg->intsts_enr);
873 reg_val = readl(&info->reg->cmd_reg);
874 reg_val &= ~ARASAN_NAND_CMD_CMD12_MASK;
875 reg_val |= curr_cmd->cmd1 |
876 (curr_cmd->cmd2 << ARASAN_NAND_CMD_CMD2_SHIFT);
877 addr_cycles = arasan_nand_get_addrcycle(mtd);
879 if (addr_cycles == ARASAN_NAND_INVALID_ADDR_CYCL)
880 return ERR_ADDR_CYCLE;
882 reg_val &= ~ARASAN_NAND_CMD_ADDR_CYCL_MASK;
883 reg_val |= (addr_cycles <<
884 ARASAN_NAND_CMD_ADDR_CYCL_SHIFT);
886 writel(reg_val, &info->reg->cmd_reg);
888 reg_val = readl(&info->reg->pkt_reg);
889 reg_val &= ~(ARASAN_NAND_PKT_REG_PKT_CNT_MASK |
890 ARASAN_NAND_PKT_REG_PKT_SIZE_MASK);
891 reg_val |= (1 << ARASAN_NAND_PKT_REG_PKT_CNT_SHFT) | 1;
892 writel(reg_val, &info->reg->pkt_reg);
894 writel(curr_cmd->pgm, &info->reg->pgm_reg);
895 while (!(readl(&info->reg->intsts_reg) &
896 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
902 printf("ERROR:%s: timedout:Xfer CMPLT\n", __func__);
906 reg_val = readl(&info->reg->intsts_enr);
907 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
908 &info->reg->intsts_enr);
909 reg_val = readl(&info->reg->intsts_reg);
910 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
911 &info->reg->intsts_reg);
916 static int arasan_nand_send_rdcmd(struct arasan_nand_command_format *curr_cmd,
917 int column, int page_addr, struct mtd_info *mtd)
919 struct nand_chip *chip = mtd_to_nand(mtd);
920 struct nand_drv *info = nand_get_controller_data(chip);
921 u32 reg_val, addr_cycles, page;
924 reg_val = readl(&info->reg->intsts_enr);
925 writel(reg_val | ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK,
926 &info->reg->intsts_enr);
928 reg_val = readl(&info->reg->cmd_reg);
929 reg_val &= ~ARASAN_NAND_CMD_CMD12_MASK;
930 reg_val |= curr_cmd->cmd1 |
931 (curr_cmd->cmd2 << ARASAN_NAND_CMD_CMD2_SHIFT);
933 if (curr_cmd->cmd1 == NAND_CMD_RNDOUT ||
934 curr_cmd->cmd1 == NAND_CMD_READ0) {
935 reg_val &= ~ARASAN_NAND_CMD_PG_SIZE_MASK;
936 page_val = arasan_nand_page(mtd);
937 reg_val |= (page_val << ARASAN_NAND_CMD_PG_SIZE_SHIFT);
940 reg_val &= ~ARASAN_NAND_CMD_ECC_ON_MASK;
942 reg_val &= ~ARASAN_NAND_CMD_ADDR_CYCL_MASK;
944 addr_cycles = arasan_nand_get_addrcycle(mtd);
946 if (addr_cycles == ARASAN_NAND_INVALID_ADDR_CYCL)
947 return ERR_ADDR_CYCLE;
949 reg_val |= (addr_cycles << 28);
950 writel(reg_val, &info->reg->cmd_reg);
955 page = (page_addr << ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT) &
956 ARASAN_NAND_MEM_ADDR1_PAGE_MASK;
957 column &= ARASAN_NAND_MEM_ADDR1_COL_MASK;
958 writel(page | column, &info->reg->memadr_reg1);
960 reg_val = readl(&info->reg->memadr_reg2);
961 reg_val &= ~ARASAN_NAND_MEM_ADDR2_PAGE_MASK;
962 reg_val |= (page_addr >> ARASAN_NAND_MEM_ADDR1_PAGE_SHIFT);
963 writel(reg_val, &info->reg->memadr_reg2);
970 static void arasan_nand_read_buf(struct mtd_info *mtd, u8 *buf, int size)
972 struct nand_chip *chip = mtd_to_nand(mtd);
973 struct nand_drv *info = nand_get_controller_data(chip);
975 u32 *bufptr = (u32 *)buf;
976 u32 timeout = ARASAN_NAND_POLL_TIMEOUT;
978 reg_val = readl(&info->reg->pkt_reg);
979 reg_val &= ~(ARASAN_NAND_PKT_REG_PKT_CNT_MASK |
980 ARASAN_NAND_PKT_REG_PKT_SIZE_MASK);
981 reg_val |= (1 << ARASAN_NAND_PKT_REG_PKT_CNT_SHFT) | size;
982 writel(reg_val, &info->reg->pkt_reg);
984 writel(curr_cmd->pgm, &info->reg->pgm_reg);
986 while (!(readl(&info->reg->intsts_reg) &
987 ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK) && timeout) {
993 puts("ERROR:arasan_nand_read_buf timedout:Buff RDY\n");
995 reg_val = readl(&info->reg->intsts_enr);
996 reg_val |= ARASAN_NAND_INT_STS_XFR_CMPLT_MASK;
997 writel(reg_val, &info->reg->intsts_enr);
999 writel(reg_val | ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK,
1000 &info->reg->intsts_enr);
1001 reg_val = readl(&info->reg->intsts_reg);
1002 writel(reg_val | ARASAN_NAND_INT_STS_BUF_RD_RDY_MASK,
1003 &info->reg->intsts_reg);
1006 for (i = 0; i < size / 4; i++)
1007 bufptr[i] = readl(&info->reg->buf_dataport);
1010 bufptr[i] = readl(&info->reg->buf_dataport);
1012 timeout = ARASAN_NAND_POLL_TIMEOUT;
1014 while (!(readl(&info->reg->intsts_reg) &
1015 ARASAN_NAND_INT_STS_XFR_CMPLT_MASK) && timeout) {
1021 puts("ERROR:arasan_nand_read_buf timedout:Xfer CMPLT\n");
1023 reg_val = readl(&info->reg->intsts_enr);
1024 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
1025 &info->reg->intsts_enr);
1026 reg_val = readl(&info->reg->intsts_reg);
1027 writel(reg_val | ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
1028 &info->reg->intsts_reg);
1031 static u8 arasan_nand_read_byte(struct mtd_info *mtd)
1033 struct nand_chip *chip = mtd_to_nand(mtd);
1034 struct nand_drv *info = nand_get_controller_data(chip);
1037 struct nand_onfi_params *p;
1039 if (buf_index == 0) {
1040 p = &chip->onfi_params;
1041 if (curr_cmd->cmd1 == NAND_CMD_READID)
1043 else if (curr_cmd->cmd1 == NAND_CMD_PARAM)
1044 size = sizeof(struct nand_onfi_params);
1045 else if (curr_cmd->cmd1 == NAND_CMD_RNDOUT)
1046 size = le16_to_cpu(p->ext_param_page_length) * 16;
1047 else if (curr_cmd->cmd1 == NAND_CMD_GET_FEATURES)
1049 else if (curr_cmd->cmd1 == NAND_CMD_STATUS)
1050 return readb(&info->reg->flash_sts_reg);
1053 chip->read_buf(mtd, &buf_data[0], size);
1056 val = *(&buf_data[0] + buf_index);
1062 static void arasan_nand_cmd_function(struct mtd_info *mtd, unsigned int command,
1063 int column, int page_addr)
1065 struct nand_chip *chip = mtd_to_nand(mtd);
1066 struct nand_drv *info = nand_get_controller_data(chip);
1067 struct nand_config *nand = &info->config;
1071 writel(ARASAN_NAND_INT_STS_XFR_CMPLT_MASK,
1072 &info->reg->intsts_enr);
1074 if ((command == NAND_CMD_READOOB) &&
1075 (mtd->writesize > 512)) {
1076 column += mtd->writesize;
1077 command = NAND_CMD_READ0;
1080 /* Get the command format */
1081 for (i = 0; (arasan_nand_commands[i].cmd1 != NAND_CMD_NONE ||
1082 arasan_nand_commands[i].cmd2 != NAND_CMD_NONE); i++) {
1083 if (command == arasan_nand_commands[i].cmd1) {
1084 curr_cmd = &arasan_nand_commands[i];
1089 if (curr_cmd == NULL) {
1090 printf("Unsupported Command; 0x%x\n", command);
1094 if (curr_cmd->cmd1 == NAND_CMD_RESET)
1095 ret = arasan_nand_reset(mtd, curr_cmd);
1097 if ((curr_cmd->cmd1 == NAND_CMD_READID) ||
1098 (curr_cmd->cmd1 == NAND_CMD_PARAM) ||
1099 (curr_cmd->cmd1 == NAND_CMD_RNDOUT) ||
1100 (curr_cmd->cmd1 == NAND_CMD_GET_FEATURES) ||
1101 (curr_cmd->cmd1 == NAND_CMD_READ0))
1102 ret = arasan_nand_send_rdcmd(curr_cmd, column, page_addr, mtd);
1104 if ((curr_cmd->cmd1 == NAND_CMD_SET_FEATURES) ||
1105 (curr_cmd->cmd1 == NAND_CMD_SEQIN)) {
1106 nand->page = page_addr;
1107 ret = arasan_nand_send_wrcmd(curr_cmd, column, page_addr, mtd);
1110 if (curr_cmd->cmd1 == NAND_CMD_ERASE1)
1111 ret = arasan_nand_erase(curr_cmd, column, page_addr, mtd);
1113 if (curr_cmd->cmd1 == NAND_CMD_STATUS)
1114 ret = arasan_nand_read_status(curr_cmd, column, page_addr, mtd);
1117 printf("ERROR:%s:command:0x%x\n", __func__, curr_cmd->cmd1);
1120 static void arasan_check_ondie(struct mtd_info *mtd)
1122 struct nand_chip *nand_chip = mtd_to_nand(mtd);
1123 struct nand_drv *info = nand_get_controller_data(nand_chip);
1124 struct nand_config *nand = &info->config;
1127 u8 set_feature[4] = {ENABLE_ONDIE_ECC, 0x00, 0x00, 0x00};
1130 nand_chip->select_chip(mtd, 0);
1132 /* Send the command for reading device ID */
1133 nand_chip->cmdfunc(mtd, NAND_CMD_RESET, -1, -1);
1134 nand_chip->cmdfunc(mtd, NAND_CMD_READID, 0, -1);
1136 /* Read manufacturer and device IDs */
1137 maf_id = nand_chip->read_byte(mtd);
1138 dev_id = nand_chip->read_byte(mtd);
1140 if ((maf_id == NAND_MFR_MICRON) &&
1141 ((dev_id == 0xf1) || (dev_id == 0xa1) || (dev_id == 0xb1) ||
1142 (dev_id == 0xaa) || (dev_id == 0xba) || (dev_id == 0xda) ||
1143 (dev_id == 0xca) || (dev_id == 0xac) || (dev_id == 0xbc) ||
1144 (dev_id == 0xdc) || (dev_id == 0xcc) || (dev_id == 0xa3) ||
1145 (dev_id == 0xb3) || (dev_id == 0xd3) || (dev_id == 0xc3))) {
1146 nand_chip->cmdfunc(mtd, NAND_CMD_SET_FEATURES,
1147 ONDIE_ECC_FEATURE_ADDR, -1);
1149 nand_chip->write_buf(mtd, &set_feature[0], 4);
1150 nand_chip->cmdfunc(mtd, NAND_CMD_GET_FEATURES,
1151 ONDIE_ECC_FEATURE_ADDR, -1);
1153 for (i = 0; i < 4; i++)
1154 get_feature[i] = nand_chip->read_byte(mtd);
1156 if (get_feature[0] & ENABLE_ONDIE_ECC) {
1157 nand->on_die_ecc_enabled = true;
1158 printf("On-DIE ECC Enabled\n");
1160 printf("%s: Unable to enable OnDie ECC\n", __func__);
1163 /* Use the BBT pattern descriptors */
1164 nand_chip->bbt_td = &bbt_main_descr;
1165 nand_chip->bbt_md = &bbt_mirror_descr;
1169 static int arasan_nand_ecc_init(struct mtd_info *mtd)
1171 struct nand_chip *nand_chip = mtd_to_nand(mtd);
1172 struct nand_drv *info = nand_get_controller_data(nand_chip);
1174 u32 regval, eccpos_start, i, eccaddr;
1176 for (i = 0; i < ARRAY_SIZE(ecc_matrix); i++) {
1177 if ((ecc_matrix[i].pagesize == mtd->writesize) &&
1178 (ecc_matrix[i].ecc_codeword_size >=
1179 nand_chip->ecc_step_ds)) {
1180 if (ecc_matrix[i].eccbits >=
1181 nand_chip->ecc_strength_ds) {
1192 eccaddr = mtd->writesize + mtd->oobsize -
1193 ecc_matrix[found].eccsize;
1196 (ecc_matrix[found].eccsize << ARASAN_NAND_ECC_SIZE_SHIFT) |
1197 (ecc_matrix[found].bch << ARASAN_NAND_ECC_BCH_SHIFT);
1198 writel(regval, &info->reg->ecc_reg);
1200 if (ecc_matrix[found].bch) {
1201 regval = readl(&info->reg->memadr_reg2);
1202 regval &= ~ARASAN_NAND_MEM_ADDR2_BCH_MASK;
1203 regval |= (ecc_matrix[found].bchval <<
1204 ARASAN_NAND_MEM_ADDR2_BCH_SHIFT);
1205 writel(regval, &info->reg->memadr_reg2);
1208 nand_oob.eccbytes = ecc_matrix[found].eccsize;
1209 eccpos_start = mtd->oobsize - nand_oob.eccbytes;
1211 for (i = 0; i < nand_oob.eccbytes; i++)
1212 nand_oob.eccpos[i] = eccpos_start + i;
1214 nand_oob.oobfree[0].offset = 2;
1215 nand_oob.oobfree[0].length = eccpos_start - 2;
1217 nand_chip->ecc.size = ecc_matrix[found].ecc_codeword_size;
1218 nand_chip->ecc.strength = ecc_matrix[found].eccbits;
1219 nand_chip->ecc.bytes = ecc_matrix[found].eccsize;
1220 nand_chip->ecc.layout = &nand_oob;
1225 static int arasan_probe(struct udevice *dev)
1227 struct arasan_nand_info *arasan = dev_get_priv(dev);
1228 struct nand_chip *nand_chip = &arasan->nand_chip;
1229 struct nand_drv *info = &arasan->nand_ctrl;
1230 struct nand_config *nand = &info->config;
1231 struct mtd_info *mtd;
1234 info->reg = (struct nand_regs *)dev_read_addr(dev);
1235 mtd = nand_to_mtd(nand_chip);
1236 nand_set_controller_data(nand_chip, &arasan->nand_ctrl);
1238 #ifdef CONFIG_SYS_NAND_NO_SUBPAGE_WRITE
1239 nand_chip->options |= NAND_NO_SUBPAGE_WRITE;
1242 /* Set the driver entry points for MTD */
1243 nand_chip->cmdfunc = arasan_nand_cmd_function;
1244 nand_chip->select_chip = arasan_nand_select_chip;
1245 nand_chip->read_byte = arasan_nand_read_byte;
1247 /* Buffer read/write routines */
1248 nand_chip->read_buf = arasan_nand_read_buf;
1249 nand_chip->write_buf = arasan_nand_write_buf;
1250 nand_chip->bbt_options = NAND_BBT_USE_FLASH;
1252 writel(0x0, &info->reg->cmd_reg);
1253 writel(0x0, &info->reg->pgm_reg);
1255 /* first scan to find the device and get the page size */
1256 if (nand_scan_ident(mtd, CONFIG_SYS_NAND_MAX_CHIPS, NULL)) {
1257 printf("%s: nand_scan_ident failed\n", __func__);
1261 nand_chip->ecc.mode = NAND_ECC_HW;
1262 nand_chip->ecc.hwctl = NULL;
1263 nand_chip->ecc.read_page = arasan_nand_read_page_hwecc;
1264 nand_chip->ecc.write_page = arasan_nand_write_page_hwecc;
1265 nand_chip->ecc.read_oob = arasan_nand_read_oob;
1266 nand_chip->ecc.write_oob = arasan_nand_write_oob;
1268 arasan_check_ondie(mtd);
1271 * If on die supported, then give priority to on-die ecc and use
1272 * it instead of controller ecc.
1274 if (nand->on_die_ecc_enabled) {
1275 nand_chip->ecc.strength = 1;
1276 nand_chip->ecc.size = mtd->writesize;
1277 nand_chip->ecc.bytes = 0;
1278 nand_chip->ecc.layout = &ondie_nand_oob_64;
1280 if (arasan_nand_ecc_init(mtd)) {
1281 printf("%s: nand_ecc_init failed\n", __func__);
1286 if (nand_scan_tail(mtd)) {
1287 printf("%s: nand_scan_tail failed\n", __func__);
1291 if (nand_register(0, mtd)) {
1292 printf("Nand Register Fail\n");
1302 static const struct udevice_id arasan_nand_dt_ids[] = {
1303 {.compatible = "arasan,nfc-v3p10",},
1307 U_BOOT_DRIVER(arasan_nand) = {
1308 .name = "arasan-nand",
1310 .of_match = arasan_nand_dt_ids,
1311 .probe = arasan_probe,
1312 .priv_auto_alloc_size = sizeof(struct arasan_nand_info),
1315 void board_nand_init(void)
1317 struct udevice *dev;
1320 ret = uclass_get_device_by_driver(UCLASS_MTD,
1321 DM_GET_DRIVER(arasan_nand), &dev);
1322 if (ret && ret != -ENODEV)
1323 pr_err("Failed to initialize %s. (error %d)\n", dev->name, ret);