xref: /rk3399_rockchip-uboot/drivers/rkflash/sfc_nor.c (revision 2a3fb7bb049d69d96f3bc7dae8caa756fdc8a613)
1 /*
2  * Copyright (c) 2018 Fuzhou Rockchip Electronics Co., Ltd
3  *
4  * SPDX-License-Identifier:	GPL-2.0
5  */
6 #include <linux/compat.h>
7 #include <linux/delay.h>
8 #include <linux/kernel.h>
9 #include <linux/string.h>
10 
11 #include "rkflash_debug.h"
12 #include "sfc_nor.h"
13 
14 static struct flash_info spi_flash_tbl[] = {
15 	/* GD25Q32B */
16 	{ 0xc84016, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 13, 9, 0 },
17 	/* GD25Q64B */
18 	{ 0xc84017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 14, 9, 0 },
19 	/* GD25Q127C and GD25Q128C*/
20 	{ 0xc84018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 15, 9, 0 },
21 	/* GD25Q256B/C/D */
22 	{ 0xc84019, 128, 8, 0x13, 0x12, 0x6C, 0x3E, 0x21, 0xDC, 0x1C, 16, 6, 0 },
23 	/* GD25Q512MC */
24 	{ 0xc84020, 128, 8, 0x13, 0x12, 0x6C, 0x3E, 0x21, 0xDC, 0x3C, 17, 6, 0 },
25 	/* 25Q64JVSSIQ */
26 	{ 0xef4017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 9, 0 },
27 	/* 25Q128FV and 25Q128JV*/
28 	{ 0xef4018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 15, 9, 0 },
29 	/* 25Q256F/J */
30 	{ 0xef4019, 128, 8, 0x13, 0x02, 0x6C, 0x32, 0x20, 0xD8, 0x3C, 16, 9, 0 },
31 	/* 25Q256JWEQ*/
32 	{ 0xef6019, 128, 8, 0x13, 0x02, 0x6C, 0x32, 0x20, 0xD8, 0x3C, 16, 9, 0 },
33 	/* 25Q64FWSSIG */
34 	{ 0xef6017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 9, 0 },
35 	/* MX25L3233FM2I-08G */
36 	{ 0xc22016, 128, 8, 0x03, 0x02, 0x6B, 0x38, 0x20, 0xD8, 0x0E, 13, 6, 0 },
37 	/* MX25L6433F */
38 	{ 0xc22017, 128, 8, 0x03, 0x02, 0x6B, 0x38, 0x20, 0xD8, 0x0E, 14, 6, 0 },
39 	/* MX25L12835E/F MX25L12833FMI-10G */
40 	{ 0xc22018, 128, 8, 0x03, 0x02, 0x6B, 0x38, 0x20, 0xD8, 0x0E, 15, 6, 0 },
41 	/* MX25L25635E/F MX25L25645G MX25L25645GMI-08G*/
42 	{ 0xc22019, 128, 8, 0x13, 0x12, 0x6C, 0x38, 0x21, 0xDC, 0x3E, 16, 6, 0 },
43 	/* MX25L51245GMI */
44 	{ 0xc2201a, 128, 8, 0x13, 0x12, 0x6C, 0x38, 0x21, 0xDC, 0x3E, 17, 6, 0 },
45 	/* XM25QH32C */
46 	{ 0x204016, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 13, 9, 0 },
47 	/* XM25QH64B */
48 	{ 0x206017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 14, 6, 0 },
49 	/* XM25QH128B */
50 	{ 0x206018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 15, 6, 0 },
51 	/* XM25QH(QU)256B */
52 	{ 0x206019, 128, 8, 0x13, 0x12, 0x6C, 0x3E, 0x21, 0xDC, 0x1D, 16, 6, 0 },
53 	/* XM25QH64A */
54 	{ 0x207017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 0, 0 },
55 	/* XT25F128A XM25QH128A */
56 	{ 0x207018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 15, 0, 0 },
57 	/* XT25F64BSSIGU-5 */
58 	{ 0x0b4017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 14, 9, 0 },
59 	/* XT25F128BSSIGU */
60 	{ 0x0b4018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 15, 9, 0 },
61 	/* EN25QH64A */
62 	{ 0x1c7017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 0, 0 },
63 	/* EN25QH128A */
64 	{ 0x1c7018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 15, 0, 0 },
65 	/* EN25QH32B */
66 	{ 0x1c7016, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 13, 0, 0 },
67 	/* EN25S32A */
68 	{ 0x1c3816, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 13, 0, 0 },
69 	/* EN25S64A */
70 	{ 0x1c3817, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 0, 0 },
71 	/* P25Q64H */
72 	{ 0x856017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 9, 0 },
73 	/* EN25QH256A */
74 	{ 0x1c7019, 128, 8, 0x13, 0x12, 0x6C, 0x34, 0x21, 0xDC, 0x3C, 16, 0, 0 },
75 	/* FM25Q64A */
76 	{ 0xf83217, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0D, 14, 9, 0 },
77 	/* ZB25VQ64 */
78 	{ 0x5e4017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 14, 9, 0 },
79 	/* ZB25VQ128 */
80 	{ 0x5e4018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 15, 9, 0 },
81 	/* 25Q256JVEM */
82 	{ 0xef7019, 128, 8, 0x13, 0x12, 0x6C, 0x34, 0x21, 0xDC, 0x3C, 16, 9, 0 },
83 	/* BH25Q128AS */
84 	{ 0x684018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x04, 15, 9, 0 },
85 	/* BH25Q64BS */
86 	{ 0x684017, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x04, 14, 9, 0 },
87 	/* FM25Q128A */
88 	{ 0xA14018, 128, 8, 0x03, 0x02, 0x6B, 0x32, 0x20, 0xD8, 0x0C, 15, 9, 0 },
89 };
90 
91 static int snor_write_en(void)
92 {
93 	int ret;
94 	struct rk_sfc_op op;
95 
96 	op.sfcmd.d32 = 0;
97 	op.sfcmd.b.cmd = CMD_WRITE_EN;
98 
99 	op.sfctrl.d32 = 0;
100 
101 	ret = sfc_request(&op, 0, NULL, 0);
102 
103 	return ret;
104 }
105 
106 int snor_reset_device(void)
107 {
108 	struct rk_sfc_op op;
109 
110 	op.sfcmd.d32 = 0;
111 	op.sfcmd.b.cmd = CMD_ENABLE_RESER;
112 
113 	op.sfctrl.d32 = 0;
114 	sfc_request(&op, 0, NULL, 0);
115 
116 	op.sfcmd.d32 = 0;
117 	op.sfcmd.b.cmd = CMD_RESET_DEVICE;
118 
119 	op.sfctrl.d32 = 0;
120 	sfc_request(&op, 0, NULL, 0);
121 	/* tRST=30us , delay 1ms here */
122 	sfc_delay(1000);
123 
124 	return SFC_OK;
125 }
126 
127 static int snor_enter_4byte_mode(void)
128 {
129 	int ret;
130 	struct rk_sfc_op op;
131 
132 	op.sfcmd.d32 = 0;
133 	op.sfcmd.b.cmd = CMD_ENTER_4BYTE_MODE;
134 
135 	op.sfctrl.d32 = 0;
136 
137 	ret = sfc_request(&op, 0, NULL, 0);
138 	return ret;
139 }
140 
141 static int snor_read_status(u32 reg_index, u8 *status)
142 {
143 	int ret;
144 	struct rk_sfc_op op;
145 	u8 read_stat_cmd[] = {CMD_READ_STATUS,
146 				CMD_READ_STATUS2, CMD_READ_STATUS3};
147 	op.sfcmd.d32 = 0;
148 	op.sfcmd.b.cmd = read_stat_cmd[reg_index];
149 
150 	op.sfctrl.d32 = 0;
151 	ret = sfc_request(&op, 0, status, 1);
152 
153 	return ret;
154 }
155 
156 static int snor_wait_busy(int timeout)
157 {
158 	int ret;
159 	struct rk_sfc_op op;
160 	int i;
161 	u32 status;
162 
163 	op.sfcmd.d32 = 0;
164 	op.sfcmd.b.cmd = CMD_READ_STATUS;
165 
166 	op.sfctrl.d32 = 0;
167 
168 	for (i = 0; i < timeout; i++) {
169 		ret = sfc_request(&op, 0, &status, 1);
170 		if (ret != SFC_OK)
171 			return ret;
172 
173 		if ((status & 0x01) == 0)
174 			return SFC_OK;
175 
176 		sfc_delay(1);
177 	}
178 	rkflash_print_error("%s  error %x\n", __func__, timeout);
179 
180 	return SFC_BUSY_TIMEOUT;
181 }
182 
183 static int snor_write_status2(u32 reg_index, u8 status)
184 {
185 	int ret;
186 	struct rk_sfc_op op;
187 	u8 status2[2];
188 
189 	status2[reg_index] = status;
190 	if (reg_index == 0)
191 		ret = snor_read_status(2, &status2[1]);
192 	else
193 		ret = snor_read_status(0, &status2[0]);
194 	if (ret != SFC_OK)
195 		return ret;
196 
197 	snor_write_en();
198 
199 	op.sfcmd.d32 = 0;
200 	op.sfcmd.b.cmd = CMD_WRITE_STATUS;
201 	op.sfcmd.b.rw = SFC_WRITE;
202 
203 	op.sfctrl.d32 = 0;
204 
205 	ret = sfc_request(&op, 0, &status2[0], 2);
206 	if (ret != SFC_OK)
207 		return ret;
208 
209 	ret = snor_wait_busy(10000);    /* 10ms */
210 
211 	return ret;
212 }
213 
214 static int snor_write_status1(u32 reg_index, u8 status)
215 {
216 	int ret;
217 	struct rk_sfc_op op;
218 	u8 status2[2];
219 	u8 read_index;
220 
221 	status2[reg_index] = status;
222 	read_index = (reg_index == 0) ? 1 : 0;
223 	ret = snor_read_status(read_index, &status2[read_index]);
224 	if (ret != SFC_OK)
225 		return ret;
226 
227 	snor_write_en();
228 
229 	op.sfcmd.d32 = 0;
230 	op.sfcmd.b.cmd = CMD_WRITE_STATUS;
231 	op.sfcmd.b.rw = SFC_WRITE;
232 
233 	op.sfctrl.d32 = 0;
234 
235 	ret = sfc_request(&op, 0, &status2[0], 2);
236 	if (ret != SFC_OK)
237 		return ret;
238 
239 	ret = snor_wait_busy(10000);    /* 10ms */
240 
241 	return ret;
242 }
243 
244 static int snor_write_status(u32 reg_index, u8 status)
245 {
246 	int ret;
247 	struct rk_sfc_op op;
248 	u8 write_stat_cmd[] = {CMD_WRITE_STATUS,
249 			       CMD_WRITE_STATUS2, CMD_WRITE_STATUS3};
250 	snor_write_en();
251 	op.sfcmd.d32 = 0;
252 	op.sfcmd.b.cmd = write_stat_cmd[reg_index];
253 	op.sfcmd.b.rw = SFC_WRITE;
254 
255 	op.sfctrl.d32 = 0;
256 
257 	ret = sfc_request(&op, 0, &status, 1);
258 	if (ret != SFC_OK)
259 		return ret;
260 
261 	ret = snor_wait_busy(10000);    /* 10ms */
262 
263 	return ret;
264 }
265 
266 int snor_erase(struct SFNOR_DEV *p_dev,
267 	       u32 addr,
268 	       enum NOR_ERASE_TYPE erase_type)
269 {
270 	int ret;
271 	struct rk_sfc_op op;
272 	int timeout[] = {400, 2000, 40000};   /* ms */
273 
274 	rkflash_print_dio("%s %x %x\n", __func__, addr, erase_type);
275 
276 	if (erase_type > ERASE_CHIP)
277 		return SFC_PARAM_ERR;
278 
279 	op.sfcmd.d32 = 0;
280 	if (erase_type == ERASE_BLOCK64K)
281 		op.sfcmd.b.cmd = p_dev->blk_erase_cmd;
282 	else if (erase_type == ERASE_SECTOR)
283 		op.sfcmd.b.cmd = p_dev->sec_erase_cmd;
284 	else
285 		op.sfcmd.b.cmd = CMD_CHIP_ERASE;
286 
287 	op.sfcmd.b.addrbits = (erase_type != ERASE_CHIP) ?
288 				SFC_ADDR_24BITS : SFC_ADDR_0BITS;
289 	if (p_dev->addr_mode == ADDR_MODE_4BYTE && erase_type != ERASE_CHIP)
290 		op.sfcmd.b.addrbits = SFC_ADDR_32BITS;
291 
292 	op.sfctrl.d32 = 0;
293 
294 	snor_write_en();
295 
296 	ret = sfc_request(&op, addr, NULL, 0);
297 	if (ret != SFC_OK)
298 		return ret;
299 
300 	ret = snor_wait_busy(timeout[erase_type] * 1000);
301 	return ret;
302 }
303 
304 int snor_prog_page(struct SFNOR_DEV *p_dev,
305 		   u32 addr,
306 		   void *p_data,
307 		   u32 size)
308 {
309 	int ret;
310 	struct rk_sfc_op op;
311 
312 	rkflash_print_dio("%s %x %x\n", __func__, addr, *(u32 *)(p_data));
313 
314 	op.sfcmd.d32 = 0;
315 	op.sfcmd.b.cmd = p_dev->prog_cmd;
316 	op.sfcmd.b.addrbits = SFC_ADDR_24BITS;
317 	op.sfcmd.b.rw = SFC_WRITE;
318 
319 	op.sfctrl.d32 = 0;
320 	op.sfctrl.b.datalines = p_dev->prog_lines;
321 	op.sfctrl.b.enbledma = 1;
322 	if (p_dev->prog_cmd == CMD_PAGE_PROG_A4)
323 		op.sfctrl.b.addrlines = SFC_4BITS_LINE;
324 
325 	if (p_dev->addr_mode == ADDR_MODE_4BYTE)
326 		op.sfcmd.b.addrbits = SFC_ADDR_32BITS;
327 
328 	snor_write_en();
329 
330 	ret = sfc_request(&op, addr, p_data, size);
331 	if (ret != SFC_OK)
332 		return ret;
333 
334 	ret = snor_wait_busy(10000);
335 
336 	return ret;
337 }
338 
339 static int snor_prog(struct SFNOR_DEV *p_dev, u32 addr, void *p_data, u32 size)
340 {
341 	int ret = SFC_OK;
342 	u32 page_size, len;
343 	u8 *p_buf =  (u8 *)p_data;
344 
345 	page_size = NOR_PAGE_SIZE;
346 	while (size) {
347 		len = page_size < size ? page_size : size;
348 		ret = snor_prog_page(p_dev, addr, p_buf, len);
349 		if (ret != SFC_OK)
350 			return ret;
351 
352 		size -= len;
353 		addr += len;
354 		p_buf += len;
355 	}
356 
357 	return ret;
358 }
359 
360 static int snor_enable_QE(struct SFNOR_DEV *p_dev)
361 {
362 	int ret = SFC_OK;
363 	int reg_index;
364 	int bit_offset;
365 	u8 status;
366 
367 	reg_index = p_dev->QE_bits >> 3;
368 	bit_offset = p_dev->QE_bits & 0x7;
369 	ret = snor_read_status(reg_index, &status);
370 	if (ret != SFC_OK)
371 		return ret;
372 
373 	if (status & (1 << bit_offset))   /* is QE bit set */
374 		return SFC_OK;
375 
376 	status |= (1 << bit_offset);
377 
378 	return p_dev->write_status(reg_index, status);
379 }
380 
381 int snor_disable_QE(struct SFNOR_DEV *p_dev)
382 {
383 	int ret = SFC_OK;
384 	int reg_index;
385 	int bit_offset;
386 	u8 status;
387 
388 	reg_index = p_dev->QE_bits >> 3;
389 	bit_offset = p_dev->QE_bits & 0x7;
390 	ret = snor_read_status(reg_index, &status);
391 	if (ret != SFC_OK)
392 		return ret;
393 
394 	if (!(status & (1 << bit_offset)))
395 		return SFC_OK;
396 
397 	status &= ~(1 << bit_offset);
398 
399 	return p_dev->write_status(reg_index, status);
400 }
401 
402 int snor_read_data(struct SFNOR_DEV *p_dev,
403 		   u32 addr,
404 		   void *p_data,
405 		   u32 size)
406 {
407 	int ret;
408 	struct rk_sfc_op op;
409 
410 	op.sfcmd.d32 = 0;
411 	op.sfcmd.b.cmd = p_dev->read_cmd;
412 	op.sfcmd.b.addrbits = SFC_ADDR_24BITS;
413 
414 	op.sfctrl.d32 = 0;
415 	op.sfctrl.b.datalines = p_dev->read_lines;
416 	if (!(size & 0x3) && size >= 4)
417 		op.sfctrl.b.enbledma = 1;
418 
419 	if (p_dev->read_cmd == CMD_FAST_READ_X1 ||
420 	    p_dev->read_cmd == CMD_FAST_READ_X4 ||
421 	    p_dev->read_cmd == CMD_FAST_READ_X2 ||
422 	    p_dev->read_cmd == CMD_FAST_4READ_X4) {
423 		op.sfcmd.b.dummybits = 8;
424 	} else if (p_dev->read_cmd == CMD_FAST_READ_A4) {
425 		op.sfcmd.b.addrbits = SFC_ADDR_32BITS;
426 		addr = (addr << 8) | 0xFF;	/* Set M[7:0] = 0xFF */
427 		op.sfcmd.b.dummybits = 4;
428 		op.sfctrl.b.addrlines = SFC_4BITS_LINE;
429 	}
430 
431 	if (p_dev->addr_mode == ADDR_MODE_4BYTE)
432 		op.sfcmd.b.addrbits = SFC_ADDR_32BITS;
433 
434 	ret = sfc_request(&op, addr, p_data, size);
435 	rkflash_print_dio("%s %x %x\n", __func__, addr, *(u32 *)(p_data));
436 
437 	return ret;
438 }
439 
440 int snor_read(struct SFNOR_DEV *p_dev, u32 sec, u32 n_sec, void *p_data)
441 {
442 	int ret = SFC_OK;
443 	u32 addr, size, len;
444 	u8 *p_buf =  (u8 *)p_data;
445 
446 	rkflash_print_dio("%s %x %x\n", __func__, sec, n_sec);
447 
448 	if ((sec + n_sec) > p_dev->capacity)
449 		return SFC_PARAM_ERR;
450 
451 	addr = sec << 9;
452 	size = n_sec << 9;
453 	while (size) {
454 		len = size < p_dev->max_iosize ? size : p_dev->max_iosize;
455 		ret = snor_read_data(p_dev, addr, p_buf, len);
456 		if (ret != SFC_OK) {
457 			rkflash_print_error("snor_read_data %x ret= %x\n",
458 					    addr >> 9, ret);
459 			goto out;
460 		}
461 
462 		size -= len;
463 		addr += len;
464 		p_buf += len;
465 	}
466 out:
467 	if (!ret)
468 		ret = n_sec;
469 
470 	return ret;
471 }
472 
473 int snor_write(struct SFNOR_DEV *p_dev, u32 sec, u32 n_sec, void *p_data)
474 {
475 	int ret = SFC_OK;
476 	u32 len, blk_size, offset;
477 	u8 *p_buf =  (u8 *)p_data;
478 	u32 total_sec = n_sec;
479 
480 	rkflash_print_dio("%s %x %x\n", __func__, sec, n_sec);
481 
482 	if ((sec + n_sec) > p_dev->capacity)
483 		return SFC_PARAM_ERR;
484 
485 	while (n_sec) {
486 		if (sec < 512 || sec >= p_dev->capacity  - 512)
487 			blk_size = 8;
488 		else
489 			blk_size = p_dev->blk_size;
490 
491 		offset = (sec & (blk_size - 1));
492 		if (!offset) {
493 			ret = snor_erase(p_dev, sec << 9, (blk_size == 8) ?
494 				ERASE_SECTOR : ERASE_BLOCK64K);
495 			if (ret != SFC_OK) {
496 				rkflash_print_error("snor_erase %x ret= %x\n",
497 						    sec, ret);
498 				goto out;
499 			}
500 		}
501 		len = (blk_size - offset) < n_sec ?
502 		      (blk_size - offset) : n_sec;
503 		ret = snor_prog(p_dev, sec << 9, p_buf, len << 9);
504 		if (ret != SFC_OK) {
505 			rkflash_print_error("snor_prog %x ret= %x\n", sec, ret);
506 			goto out;
507 		}
508 		n_sec -= len;
509 		sec += len;
510 		p_buf += len << 9;
511 	}
512 out:
513 	if (!ret)
514 		ret = total_sec;
515 
516 	return ret;
517 }
518 
519 int snor_read_id(u8 *data)
520 {
521 	int ret;
522 	struct rk_sfc_op op;
523 
524 	op.sfcmd.d32 = 0;
525 	op.sfcmd.b.cmd = CMD_READ_JEDECID;
526 
527 	op.sfctrl.d32 = 0;
528 
529 	ret = sfc_request(&op, 0, data, 3);
530 
531 	return ret;
532 }
533 
534 static int snor_read_parameter(u32 addr, u8 *data)
535 {
536 	int ret;
537 	struct rk_sfc_op op;
538 
539 	op.sfcmd.d32 = 0;
540 	op.sfcmd.b.cmd = CMD_READ_PARAMETER;
541 	op.sfcmd.b.addrbits = SFC_ADDR_24BITS;
542 	op.sfcmd.b.dummybits = 8;
543 
544 	op.sfctrl.d32 = 0;
545 
546 	ret = sfc_request(&op, addr, data, 1);
547 
548 	return ret;
549 }
550 
551 u32 snor_get_capacity(struct SFNOR_DEV *p_dev)
552 {
553 	return p_dev->capacity;
554 }
555 
556 static struct flash_info *snor_get_flash_info(u8 *flash_id)
557 {
558 	u32 i;
559 	u32 id = (flash_id[0] << 16) | (flash_id[1] << 8) | (flash_id[2] << 0);
560 
561 	for (i = 0; i < ARRAY_SIZE(spi_flash_tbl); i++) {
562 		if (spi_flash_tbl[i].id == id)
563 			return &spi_flash_tbl[i];
564 	}
565 	return NULL;
566 }
567 
568 /* Adjust flash info in ram base on parameter */
569 static void *snor_flash_info_adjust(struct flash_info *spi_flash_info)
570 {
571 	u32 addr;
572 	u8 para_version;
573 
574 	if (spi_flash_info->id == 0xc84019) {
575 		addr = 0x09;
576 		snor_read_parameter(addr, &para_version);
577 		if (para_version == 0x06) {
578 			spi_flash_info->QE_bits = 9;
579 			spi_flash_info->prog_cmd_4 = 0x34;
580 		}
581 	}
582 	return 0;
583 }
584 
585 static int snor_parse_flash_table(struct SFNOR_DEV *p_dev,
586 				  struct flash_info *g_spi_flash_info)
587 {
588 	int i, ret;
589 
590 	if (g_spi_flash_info) {
591 		snor_flash_info_adjust(g_spi_flash_info);
592 		p_dev->manufacturer = (g_spi_flash_info->id >> 16) & 0xFF;
593 		p_dev->mem_type = (g_spi_flash_info->id >> 8) & 0xFF;
594 		p_dev->capacity = 1 << ((g_spi_flash_info->id & 0xFF) - 9);
595 		p_dev->blk_size = g_spi_flash_info->block_size;
596 		p_dev->page_size = NOR_SECS_PAGE;
597 		p_dev->read_cmd = g_spi_flash_info->read_cmd;
598 		p_dev->prog_cmd = g_spi_flash_info->prog_cmd;
599 		p_dev->sec_erase_cmd = g_spi_flash_info->sector_erase_cmd;
600 		p_dev->blk_erase_cmd = g_spi_flash_info->block_erase_cmd;
601 		p_dev->prog_lines = DATA_LINES_X1;
602 		p_dev->read_lines = DATA_LINES_X1;
603 		p_dev->QE_bits = g_spi_flash_info->QE_bits;
604 		p_dev->addr_mode = ADDR_MODE_3BYTE;
605 
606 		i = g_spi_flash_info->feature & FEA_READ_STATUE_MASK;
607 		if (i == 0)
608 			p_dev->write_status = snor_write_status;
609 		else if (i == 1)
610 			p_dev->write_status = snor_write_status1;
611 		else if (i == 2)
612 			p_dev->write_status = snor_write_status2;
613 
614 		if (g_spi_flash_info->feature & FEA_4BIT_READ) {
615 			ret = SFC_OK;
616 			if (g_spi_flash_info->QE_bits)
617 				ret = snor_enable_QE(p_dev);
618 			if (ret == SFC_OK) {
619 				p_dev->read_lines = DATA_LINES_X4;
620 				p_dev->read_cmd = g_spi_flash_info->read_cmd_4;
621 			}
622 		}
623 		if (g_spi_flash_info->feature & FEA_4BIT_PROG &&
624 		    p_dev->read_lines == DATA_LINES_X4) {
625 			p_dev->prog_lines = DATA_LINES_X4;
626 			p_dev->prog_cmd = g_spi_flash_info->prog_cmd_4;
627 		}
628 
629 		if (g_spi_flash_info->feature & FEA_4BYTE_ADDR)
630 			p_dev->addr_mode = ADDR_MODE_4BYTE;
631 
632 		if ((g_spi_flash_info->feature & FEA_4BYTE_ADDR_MODE))
633 			snor_enter_4byte_mode();
634 	}
635 
636 	return SFC_OK;
637 }
638 
639 int snor_init(struct SFNOR_DEV *p_dev)
640 {
641 	struct flash_info *g_spi_flash_info;
642 	u8 id_byte[5];
643 
644 	if (!p_dev)
645 		return SFC_PARAM_ERR;
646 
647 	memset((void *)p_dev, 0, sizeof(struct SFNOR_DEV));
648 	p_dev->max_iosize = sfc_get_max_iosize();
649 
650 	snor_read_id(id_byte);
651 	rkflash_print_error("sfc nor id: %x %x %x\n",
652 			    id_byte[0], id_byte[1], id_byte[2]);
653 	if (0xFF == id_byte[0] || 0x00 == id_byte[0])
654 		return SFC_ERROR;
655 
656 	g_spi_flash_info = snor_get_flash_info(id_byte);
657 	if (g_spi_flash_info) {
658 		snor_parse_flash_table(p_dev, g_spi_flash_info);
659 	} else {
660 		p_dev->manufacturer = id_byte[0];
661 		p_dev->mem_type = id_byte[1];
662 		p_dev->capacity = 1 << (id_byte[2] - 9);
663 		p_dev->QE_bits = 0;
664 		p_dev->blk_size = NOR_SECS_BLK;
665 		p_dev->page_size = NOR_SECS_PAGE;
666 		p_dev->read_cmd = CMD_READ_DATA;
667 		p_dev->prog_cmd = CMD_PAGE_PROG;
668 		p_dev->sec_erase_cmd = CMD_SECTOR_ERASE;
669 		p_dev->blk_erase_cmd = CMD_BLOCK_ERASE;
670 		p_dev->prog_lines = DATA_LINES_X1;
671 		p_dev->read_lines = DATA_LINES_X1;
672 		p_dev->write_status = snor_write_status;
673 		snor_reset_device();
674 	}
675 
676 	rkflash_print_info("addr_mode: %x\n", p_dev->addr_mode);
677 	rkflash_print_info("read_lines: %x\n", p_dev->read_lines);
678 	rkflash_print_info("prog_lines: %x\n", p_dev->prog_lines);
679 	rkflash_print_info("read_cmd: %x\n", p_dev->read_cmd);
680 	rkflash_print_info("prog_cmd: %x\n", p_dev->prog_cmd);
681 	rkflash_print_info("blk_erase_cmd: %x\n", p_dev->blk_erase_cmd);
682 	rkflash_print_info("sec_erase_cmd: %x\n", p_dev->sec_erase_cmd);
683 	rkflash_print_info("capacity: %x\n", p_dev->capacity);
684 
685 	return SFC_OK;
686 }
687 
688 int snor_reinit_from_table_packet(struct SFNOR_DEV *p_dev,
689 				  struct snor_info_packet *packet)
690 {
691 	struct flash_info g_spi_flash_info;
692 	u8 id_byte[5];
693 	int ret;
694 
695 	if (!p_dev || packet->id != SNOR_INFO_PACKET_ID)
696 		return SFC_PARAM_ERR;
697 
698 	snor_read_id(id_byte);
699 	if (0xFF == id_byte[0] || 0x00 == id_byte[0])
700 		return SFC_ERROR;
701 
702 	g_spi_flash_info.id = id_byte[0] << 16 | id_byte[1] << 8 | id_byte[2];
703 	g_spi_flash_info.block_size = NOR_SECS_BLK;
704 	g_spi_flash_info.sector_size = NOR_SECS_PAGE;
705 	g_spi_flash_info.read_cmd = packet->read_cmd;
706 	g_spi_flash_info.prog_cmd = packet->prog_cmd;
707 	g_spi_flash_info.read_cmd_4 = packet->read_cmd_4;
708 	g_spi_flash_info.prog_cmd_4 = packet->prog_cmd_4;
709 	if (id_byte[2] >=  0x19)
710 		g_spi_flash_info.read_cmd_4 = CMD_FAST_4READ_X4;
711 	g_spi_flash_info.sector_erase_cmd = packet->sector_erase_cmd;
712 	g_spi_flash_info.block_erase_cmd = packet->block_erase_cmd;
713 	g_spi_flash_info.feature = packet->feature;
714 	g_spi_flash_info.density = id_byte[2] - 9;
715 	g_spi_flash_info.QE_bits = packet->QE_bits;
716 
717 	ret = snor_parse_flash_table(p_dev, &g_spi_flash_info);
718 
719 	return ret;
720 }
721 
722