hc
2024-05-10 23fa18eaa71266feff7ba8d83022d9e1cc83c65a
kernel/include/linux/mtd/spinand.h
....@@ -32,9 +32,9 @@
3232 SPI_MEM_OP_NO_DUMMY, \
3333 SPI_MEM_OP_NO_DATA)
3434
35
-#define SPINAND_READID_OP(ndummy, buf, len) \
35
+#define SPINAND_READID_OP(naddr, ndummy, buf, len) \
3636 SPI_MEM_OP(SPI_MEM_OP_CMD(0x9f, 1), \
37
- SPI_MEM_OP_NO_ADDR, \
37
+ SPI_MEM_OP_ADDR(naddr, 0, 1), \
3838 SPI_MEM_OP_DUMMY(ndummy, 1), \
3939 SPI_MEM_OP_DATA_IN(len, buf, 1))
4040
....@@ -68,9 +68,21 @@
6868 SPI_MEM_OP_DUMMY(ndummy, 1), \
6969 SPI_MEM_OP_DATA_IN(len, buf, 1))
7070
71
+#define SPINAND_PAGE_READ_FROM_CACHE_OP_3A(fast, addr, ndummy, buf, len) \
72
+ SPI_MEM_OP(SPI_MEM_OP_CMD(fast ? 0x0b : 0x03, 1), \
73
+ SPI_MEM_OP_ADDR(3, addr, 1), \
74
+ SPI_MEM_OP_DUMMY(ndummy, 1), \
75
+ SPI_MEM_OP_DATA_IN(len, buf, 1))
76
+
7177 #define SPINAND_PAGE_READ_FROM_CACHE_X2_OP(addr, ndummy, buf, len) \
7278 SPI_MEM_OP(SPI_MEM_OP_CMD(0x3b, 1), \
7379 SPI_MEM_OP_ADDR(2, addr, 1), \
80
+ SPI_MEM_OP_DUMMY(ndummy, 1), \
81
+ SPI_MEM_OP_DATA_IN(len, buf, 2))
82
+
83
+#define SPINAND_PAGE_READ_FROM_CACHE_X2_OP_3A(addr, ndummy, buf, len) \
84
+ SPI_MEM_OP(SPI_MEM_OP_CMD(0x3b, 1), \
85
+ SPI_MEM_OP_ADDR(3, addr, 1), \
7486 SPI_MEM_OP_DUMMY(ndummy, 1), \
7587 SPI_MEM_OP_DATA_IN(len, buf, 2))
7688
....@@ -80,15 +92,33 @@
8092 SPI_MEM_OP_DUMMY(ndummy, 1), \
8193 SPI_MEM_OP_DATA_IN(len, buf, 4))
8294
95
+#define SPINAND_PAGE_READ_FROM_CACHE_X4_OP_3A(addr, ndummy, buf, len) \
96
+ SPI_MEM_OP(SPI_MEM_OP_CMD(0x6b, 1), \
97
+ SPI_MEM_OP_ADDR(3, addr, 1), \
98
+ SPI_MEM_OP_DUMMY(ndummy, 1), \
99
+ SPI_MEM_OP_DATA_IN(len, buf, 4))
100
+
83101 #define SPINAND_PAGE_READ_FROM_CACHE_DUALIO_OP(addr, ndummy, buf, len) \
84102 SPI_MEM_OP(SPI_MEM_OP_CMD(0xbb, 1), \
85103 SPI_MEM_OP_ADDR(2, addr, 2), \
86104 SPI_MEM_OP_DUMMY(ndummy, 2), \
87105 SPI_MEM_OP_DATA_IN(len, buf, 2))
88106
107
+#define SPINAND_PAGE_READ_FROM_CACHE_DUALIO_OP_3A(addr, ndummy, buf, len) \
108
+ SPI_MEM_OP(SPI_MEM_OP_CMD(0xbb, 1), \
109
+ SPI_MEM_OP_ADDR(3, addr, 2), \
110
+ SPI_MEM_OP_DUMMY(ndummy, 2), \
111
+ SPI_MEM_OP_DATA_IN(len, buf, 2))
112
+
89113 #define SPINAND_PAGE_READ_FROM_CACHE_QUADIO_OP(addr, ndummy, buf, len) \
90114 SPI_MEM_OP(SPI_MEM_OP_CMD(0xeb, 1), \
91115 SPI_MEM_OP_ADDR(2, addr, 4), \
116
+ SPI_MEM_OP_DUMMY(ndummy, 4), \
117
+ SPI_MEM_OP_DATA_IN(len, buf, 4))
118
+
119
+#define SPINAND_PAGE_READ_FROM_CACHE_QUADIO_OP_3A(addr, ndummy, buf, len) \
120
+ SPI_MEM_OP(SPI_MEM_OP_CMD(0xeb, 1), \
121
+ SPI_MEM_OP_ADDR(3, addr, 4), \
92122 SPI_MEM_OP_DUMMY(ndummy, 4), \
93123 SPI_MEM_OP_DATA_IN(len, buf, 4))
94124
....@@ -119,6 +149,7 @@
119149 /* feature register */
120150 #define REG_BLOCK_LOCK 0xa0
121151 #define BL_ALL_UNLOCKED 0x00
152
+#define HWP_EN 0x02 /* Skyhigh feature, Hardware write protection */
122153
123154 /* configuration register */
124155 #define REG_CFG 0xb0
....@@ -146,37 +177,46 @@
146177 * @data: buffer containing the id bytes. Currently 4 bytes large, but can
147178 * be extended if required
148179 * @len: ID length
149
- *
150
- * struct_spinand_id->data contains all bytes returned after a READ_ID command,
151
- * including dummy bytes if the chip does not emit ID bytes right after the
152
- * READ_ID command. The responsibility to extract real ID bytes is left to
153
- * struct_manufacurer_ops->detect().
154180 */
155181 struct spinand_id {
156182 u8 data[SPINAND_MAX_ID_LEN];
157183 int len;
158184 };
159185
186
+enum spinand_readid_method {
187
+ SPINAND_READID_METHOD_OPCODE,
188
+ SPINAND_READID_METHOD_OPCODE_ADDR,
189
+ SPINAND_READID_METHOD_OPCODE_DUMMY,
190
+};
191
+
192
+/**
193
+ * struct spinand_devid - SPI NAND device id structure
194
+ * @id: device id of current chip
195
+ * @len: number of bytes in device id
196
+ * @method: method to read chip id
197
+ * There are 3 possible variants:
198
+ * SPINAND_READID_METHOD_OPCODE: chip id is returned immediately
199
+ * after read_id opcode.
200
+ * SPINAND_READID_METHOD_OPCODE_ADDR: chip id is returned after
201
+ * read_id opcode + 1-byte address.
202
+ * SPINAND_READID_METHOD_OPCODE_DUMMY: chip id is returned after
203
+ * read_id opcode + 1 dummy byte.
204
+ */
205
+struct spinand_devid {
206
+ const u8 *id;
207
+ const u8 len;
208
+ const enum spinand_readid_method method;
209
+};
210
+
160211 /**
161212 * struct manufacurer_ops - SPI NAND manufacturer specific operations
162
- * @detect: detect a SPI NAND device. Every time a SPI NAND device is probed
163
- * the core calls the struct_manufacurer_ops->detect() hook of each
164
- * registered manufacturer until one of them return 1. Note that
165
- * the first thing to check in this hook is that the manufacturer ID
166
- * in struct_spinand_device->id matches the manufacturer whose
167
- * ->detect() hook has been called. Should return 1 if there's a
168
- * match, 0 if the manufacturer ID does not match and a negative
169
- * error code otherwise. When true is returned, the core assumes
170
- * that properties of the NAND chip (spinand->base.memorg and
171
- * spinand->base.eccreq) have been filled
172213 * @init: initialize a SPI NAND device
173214 * @cleanup: cleanup a SPI NAND device
174215 *
175216 * Each SPI NAND manufacturer driver should implement this interface so that
176
- * NAND chips coming from this vendor can be detected and initialized properly.
217
+ * NAND chips coming from this vendor can be initialized properly.
177218 */
178219 struct spinand_manufacturer_ops {
179
- int (*detect)(struct spinand_device *spinand);
180220 int (*init)(struct spinand_device *spinand);
181221 void (*cleanup)(struct spinand_device *spinand);
182222 };
....@@ -185,18 +225,41 @@
185225 * struct spinand_manufacturer - SPI NAND manufacturer instance
186226 * @id: manufacturer ID
187227 * @name: manufacturer name
228
+ * @devid_len: number of bytes in device ID
229
+ * @chips: supported SPI NANDs under current manufacturer
230
+ * @nchips: number of SPI NANDs available in chips array
188231 * @ops: manufacturer operations
189232 */
190233 struct spinand_manufacturer {
191234 u8 id;
192235 char *name;
236
+ const struct spinand_info *chips;
237
+ const size_t nchips;
193238 const struct spinand_manufacturer_ops *ops;
194239 };
195240
196241 /* SPI NAND manufacturers */
242
+extern const struct spinand_manufacturer biwin_spinand_manufacturer;
243
+extern const struct spinand_manufacturer dosilicon_spinand_manufacturer;
244
+extern const struct spinand_manufacturer esmt_spinand_manufacturer;
245
+extern const struct spinand_manufacturer etron_spinand_manufacturer;
246
+extern const struct spinand_manufacturer fmsh_spinand_manufacturer;
247
+extern const struct spinand_manufacturer foresee_spinand_manufacturer;
248
+extern const struct spinand_manufacturer gigadevice_spinand_manufacturer;
249
+extern const struct spinand_manufacturer gsto_spinand_manufacturer;
250
+extern const struct spinand_manufacturer hyf_spinand_manufacturer;
251
+extern const struct spinand_manufacturer jsc_spinand_manufacturer;
197252 extern const struct spinand_manufacturer macronix_spinand_manufacturer;
198253 extern const struct spinand_manufacturer micron_spinand_manufacturer;
254
+extern const struct spinand_manufacturer paragon_spinand_manufacturer;
255
+extern const struct spinand_manufacturer toshiba_spinand_manufacturer;
256
+extern const struct spinand_manufacturer silicongo_spinand_manufacturer;
257
+extern const struct spinand_manufacturer skyhigh_spinand_manufacturer;
258
+extern const struct spinand_manufacturer unim_spinand_manufacturer;
259
+extern const struct spinand_manufacturer unim_zl_spinand_manufacturer;
199260 extern const struct spinand_manufacturer winbond_spinand_manufacturer;
261
+extern const struct spinand_manufacturer xincun_spinand_manufacturer;
262
+extern const struct spinand_manufacturer xtx_spinand_manufacturer;
200263
201264 /**
202265 * struct spinand_op_variants - SPI NAND operation variants
....@@ -237,6 +300,16 @@
237300 };
238301
239302 #define SPINAND_HAS_QE_BIT BIT(0)
303
+#define SPINAND_HAS_CR_FEAT_BIT BIT(1)
304
+
305
+/**
306
+ * struct spinand_ondie_ecc_conf - private SPI-NAND on-die ECC engine structure
307
+ * @status: status of the last wait operation that will be used in case
308
+ * ->get_status() is not populated by the spinand device.
309
+ */
310
+struct spinand_ondie_ecc_conf {
311
+ u8 status;
312
+};
240313
241314 /**
242315 * struct spinand_info - Structure used to describe SPI NAND chips
....@@ -258,10 +331,10 @@
258331 */
259332 struct spinand_info {
260333 const char *model;
261
- u8 devid;
334
+ struct spinand_devid devid;
262335 u32 flags;
263336 struct nand_memory_organization memorg;
264
- struct nand_ecc_req eccreq;
337
+ struct nand_ecc_props eccreq;
265338 struct spinand_ecc_info eccinfo;
266339 struct {
267340 const struct spinand_op_variants *read_cache;
....@@ -271,6 +344,13 @@
271344 int (*select_target)(struct spinand_device *spinand,
272345 unsigned int target);
273346 };
347
+
348
+#define SPINAND_ID(__method, ...) \
349
+ { \
350
+ .id = (const u8[]){ __VA_ARGS__ }, \
351
+ .len = sizeof((u8[]){ __VA_ARGS__ }), \
352
+ .method = __method, \
353
+ }
274354
275355 #define SPINAND_INFO_OP_VARIANTS(__read, __write, __update) \
276356 { \
....@@ -299,6 +379,11 @@
299379 .flags = __flags, \
300380 __VA_ARGS__ \
301381 }
382
+
383
+struct spinand_dirmap {
384
+ struct spi_mem_dirmap_desc *wdesc;
385
+ struct spi_mem_dirmap_desc *rdesc;
386
+};
302387
303388 /**
304389 * struct spinand_device - SPI NAND device instance
....@@ -338,6 +423,8 @@
338423 const struct spi_mem_op *write_cache;
339424 const struct spi_mem_op *update_cache;
340425 } op_templates;
426
+
427
+ struct spinand_dirmap *dirmaps;
341428
342429 int (*select_target)(struct spinand_device *spinand,
343430 unsigned int target);
....@@ -411,9 +498,10 @@
411498 nanddev_set_of_node(&spinand->base, np);
412499 }
413500
414
-int spinand_match_and_init(struct spinand_device *dev,
501
+int spinand_match_and_init(struct spinand_device *spinand,
415502 const struct spinand_info *table,
416
- unsigned int table_size, u8 devid);
503
+ unsigned int table_size,
504
+ enum spinand_readid_method rdid_method);
417505
418506 int spinand_upd_cfg(struct spinand_device *spinand, u8 mask, u8 val);
419507 int spinand_select_target(struct spinand_device *spinand, unsigned int target);