Commit 5bd34c091a044d130601370c370f84b1c59f1627

Authored by Thomas Gleixner
1 parent ff268fb879

[MTD] NAND Replace oobinfo by ecclayout

The nand_oobinfo structure is not fitting the newer error correction
demands anymore. Replace it by struct nand_ecclayout and fixup the users
all over the place. Keep the nand_oobinfo based ioctl for user space
compability reasons.

Signed-off-by: Thomas Gleixner <tglx@linutronix.de>

Showing 20 changed files with 134 additions and 99 deletions Side-by-side Diff

drivers/mtd/mtdchar.c
... ... @@ -512,13 +512,35 @@
512 512 break;
513 513 }
514 514  
  515 + /* Legacy interface */
515 516 case MEMGETOOBSEL:
516 517 {
517   - if (copy_to_user(argp, mtd->oobinfo,
518   - sizeof(struct nand_oobinfo)))
  518 + struct nand_oobinfo oi;
  519 +
  520 + if (!mtd->ecclayout)
  521 + return -EOPNOTSUPP;
  522 + if (mtd->ecclayout->eccbytes > ARRAY_SIZE(oi.eccpos))
  523 + return -EINVAL;
  524 +
  525 + oi.useecc = MTD_NANDECC_AUTOPLACE;
  526 + memcpy(&oi.eccpos, mtd->ecclayout->eccpos, sizeof(oi.eccpos));
  527 + memcpy(&oi.oobfree, mtd->ecclayout->oobfree,
  528 + sizeof(oi.oobfree));
  529 +
  530 + if (copy_to_user(argp, &oi, sizeof(struct nand_oobinfo)))
519 531 return -EFAULT;
520 532 break;
521 533 }
  534 +
  535 + case ECCGETLAYOUT:
  536 +
  537 + if (!mtd->ecclayout)
  538 + return -EOPNOTSUPP;
  539 +
  540 + if (copy_to_user(argp, &mtd->ecclayout,
  541 + sizeof(struct nand_ecclayout)))
  542 + return -EFAULT;
  543 + break;
522 544  
523 545 case MEMGETBADBLOCK:
524 546 {
drivers/mtd/mtdconcat.c
... ... @@ -766,7 +766,7 @@
766 766  
767 767 }
768 768  
769   - concat->mtd.oobinfo = subdev[0]->oobinfo;
  769 + concat->mtd.ecclayout = subdev[0]->ecclayout;
770 770  
771 771 concat->num_subdev = num_devs;
772 772 concat->mtd.name = name;
drivers/mtd/mtdpart.c
... ... @@ -434,7 +434,7 @@
434 434 parts[i].name);
435 435 }
436 436  
437   - slave->mtd.oobinfo = master->oobinfo;
  437 + slave->mtd.ecclayout = master->ecclayout;
438 438  
439 439 if(parts[i].mtdp)
440 440 { /* store the object pointer (caller may or may not register it */
drivers/mtd/nand/diskonchip.c
... ... @@ -1058,8 +1058,7 @@
1058 1058 * safer. The only problem with it is that any code that parses oobfree must
1059 1059 * be able to handle out-of-order segments.
1060 1060 */
1061   -static struct nand_oobinfo doc200x_oobinfo = {
1062   - .useecc = MTD_NANDECC_AUTOPLACE,
  1061 +static struct nand_ecclayout doc200x_oobinfo = {
1063 1062 .eccbytes = 6,
1064 1063 .eccpos = {0, 1, 2, 3, 4, 5},
1065 1064 .oobfree = {{8, 8}, {6, 2}}
... ... @@ -1662,7 +1661,7 @@
1662 1661 nand->ecc.calculate = doc200x_calculate_ecc;
1663 1662 nand->ecc.correct = doc200x_correct_data;
1664 1663  
1665   - nand->autooob = &doc200x_oobinfo;
  1664 + nand->ecc.layout = &doc200x_oobinfo;
1666 1665 nand->ecc.mode = NAND_ECC_HW_SYNDROME;
1667 1666 nand->ecc.size = 512;
1668 1667 nand->ecc.bytes = 6;
drivers/mtd/nand/nand_base.c
... ... @@ -52,28 +52,33 @@
52 52 #endif
53 53  
54 54 /* Define default oob placement schemes for large and small page devices */
55   -static struct nand_oobinfo nand_oob_8 = {
56   - .useecc = MTD_NANDECC_AUTOPLACE,
  55 +static struct nand_ecclayout nand_oob_8 = {
57 56 .eccbytes = 3,
58 57 .eccpos = {0, 1, 2},
59   - .oobfree = {{3, 2}, {6, 2}}
  58 + .oobfree = {
  59 + {.offset = 3,
  60 + .length = 2},
  61 + {.offset = 6,
  62 + .length = 2}}
60 63 };
61 64  
62   -static struct nand_oobinfo nand_oob_16 = {
63   - .useecc = MTD_NANDECC_AUTOPLACE,
  65 +static struct nand_ecclayout nand_oob_16 = {
64 66 .eccbytes = 6,
65 67 .eccpos = {0, 1, 2, 3, 6, 7},
66   - .oobfree = {{8, 8}}
  68 + .oobfree = {
  69 + {.offset = 8,
  70 + . length = 8}}
67 71 };
68 72  
69   -static struct nand_oobinfo nand_oob_64 = {
70   - .useecc = MTD_NANDECC_AUTOPLACE,
  73 +static struct nand_ecclayout nand_oob_64 = {
71 74 .eccbytes = 24,
72 75 .eccpos = {
73 76 40, 41, 42, 43, 44, 45, 46, 47,
74 77 48, 49, 50, 51, 52, 53, 54, 55,
75 78 56, 57, 58, 59, 60, 61, 62, 63},
76   - .oobfree = {{2, 38}}
  79 + .oobfree = {
  80 + {.offset = 2,
  81 + .length = 38}}
77 82 };
78 83  
79 84 /* This is used for padding purposes in nand_write_oob */
... ... @@ -749,7 +754,7 @@
749 754 uint8_t *p = buf;
750 755 uint8_t *ecc_calc = chip->buffers.ecccalc;
751 756 uint8_t *ecc_code = chip->buffers.ecccode;
752   - int *eccpos = chip->autooob->eccpos;
  757 + int *eccpos = chip->ecc.layout->eccpos;
753 758  
754 759 chip->read_buf(mtd, buf, mtd->writesize);
755 760 chip->read_buf(mtd, chip->oob_poi, mtd->oobsize);
... ... @@ -795,7 +800,7 @@
795 800 uint8_t *p = buf;
796 801 uint8_t *ecc_calc = chip->buffers.ecccalc;
797 802 uint8_t *ecc_code = chip->buffers.ecccode;
798   - int *eccpos = chip->autooob->eccpos;
  803 + int *eccpos = chip->ecc.layout->eccpos;
799 804  
800 805 for (i = 0; eccsteps; eccsteps--, i += eccbytes, p += eccsize) {
801 806 chip->ecc.hwctl(mtd, NAND_ECC_READ);
... ... @@ -1198,7 +1203,7 @@
1198 1203 int eccsteps = chip->ecc.steps;
1199 1204 uint8_t *ecc_calc = chip->buffers.ecccalc;
1200 1205 const uint8_t *p = buf;
1201   - int *eccpos = chip->autooob->eccpos;
  1206 + int *eccpos = chip->ecc.layout->eccpos;
1202 1207  
1203 1208 if (chip->ecc.mode != NAND_ECC_NONE) {
1204 1209 /* Software ecc calculation */
... ... @@ -1227,7 +1232,7 @@
1227 1232 int eccsteps = chip->ecc.steps;
1228 1233 uint8_t *ecc_calc = chip->buffers.ecccalc;
1229 1234 const uint8_t *p = buf;
1230   - int *eccpos = chip->autooob->eccpos;
  1235 + int *eccpos = chip->ecc.layout->eccpos;
1231 1236  
1232 1237 for (i = 0; eccsteps; eccsteps--, i += eccbytes, p += eccsize) {
1233 1238 chip->ecc.hwctl(mtd, NAND_ECC_WRITE);
1234 1239  
1235 1240  
1236 1241  
... ... @@ -2124,16 +2129,16 @@
2124 2129 /*
2125 2130 * If no default placement scheme is given, select an appropriate one
2126 2131 */
2127   - if (!chip->autooob) {
  2132 + if (!chip->ecc.layout) {
2128 2133 switch (mtd->oobsize) {
2129 2134 case 8:
2130   - chip->autooob = &nand_oob_8;
  2135 + chip->ecc.layout = &nand_oob_8;
2131 2136 break;
2132 2137 case 16:
2133   - chip->autooob = &nand_oob_16;
  2138 + chip->ecc.layout = &nand_oob_16;
2134 2139 break;
2135 2140 case 64:
2136   - chip->autooob = &nand_oob_64;
  2141 + chip->ecc.layout = &nand_oob_64;
2137 2142 break;
2138 2143 default:
2139 2144 printk(KERN_WARNING "No oob scheme defined for "
... ... @@ -2198,6 +2203,15 @@
2198 2203 }
2199 2204  
2200 2205 /*
  2206 + * The number of bytes available for a client to place data into
  2207 + * the out of band area
  2208 + */
  2209 + chip->ecc.layout->oobavail = 0;
  2210 + for (i = 0; chip->ecc.layout->oobfree[i].length; i++)
  2211 + chip->ecc.layout->oobavail +=
  2212 + chip->ecc.layout->oobfree[i].length;
  2213 +
  2214 + /*
2201 2215 * Set the number of read / write steps for one page depending on ECC
2202 2216 * mode
2203 2217 */
... ... @@ -2236,8 +2250,8 @@
2236 2250 mtd->block_isbad = nand_block_isbad;
2237 2251 mtd->block_markbad = nand_block_markbad;
2238 2252  
2239   - /* and make the autooob the default one */
2240   - mtd->oobinfo = chip->autooob;
  2253 + /* propagate ecc.layout to mtd_info */
  2254 + mtd->ecclayout = chip->ecc.layout;
2241 2255  
2242 2256 /* Check, if we should skip the bad block table scan */
2243 2257 if (chip->options & NAND_SKIP_BBTSCAN)
drivers/mtd/nand/ndfc.c
... ... @@ -168,7 +168,7 @@
168 168 chip->ecc.mode = NAND_ECC_HW;
169 169 chip->ecc.size = 256;
170 170 chip->ecc.bytes = 3;
171   - chip->autooob = mtd->pl_chip->oobinfo;
  171 + chip->ecclayout = mtd->pl_chip->ecclayout;
172 172 mtd->mtd.priv = chip;
173 173 mtd->mtd.owner = THIS_MODULE;
174 174 }
drivers/mtd/nand/rtc_from4.c
... ... @@ -142,8 +142,7 @@
142 142 /*
143 143 * hardware specific Out Of Band information
144 144 */
145   -static struct nand_oobinfo rtc_from4_nand_oobinfo = {
146   - .useecc = MTD_NANDECC_AUTOPLACE,
  145 +static struct nand_ecclayout rtc_from4_nand_oobinfo = {
147 146 .eccbytes = 32,
148 147 .eccpos = {
149 148 0, 1, 2, 3, 4, 5, 6, 7,
... ... @@ -574,7 +573,7 @@
574 573 /* return the status of extra status and ECC checks */
575 574 this->errstat = rtc_from4_errstat;
576 575 /* set the nand_oobinfo to support FPGA H/W error detection */
577   - this->autooob = &rtc_from4_nand_oobinfo;
  576 + this->ecc.layout = &rtc_from4_nand_oobinfo;
578 577 this->ecc.hwctl = rtc_from4_enable_hwecc;
579 578 this->ecc.calculate = rtc_from4_calculate_ecc;
580 579 this->ecc.correct = rtc_from4_correct_data;
drivers/mtd/nand/s3c2410.c
... ... @@ -76,8 +76,7 @@
76 76 /* new oob placement block for use with hardware ecc generation
77 77 */
78 78  
79   -static struct nand_oobinfo nand_hw_eccoob = {
80   - .useecc = MTD_NANDECC_AUTOPLACE,
  79 +static struct nand_ecclayout nand_hw_eccoob = {
81 80 .eccbytes = 3,
82 81 .eccpos = {0, 1, 2},
83 82 .oobfree = {{8, 8}}
... ... @@ -502,7 +501,7 @@
502 501 chip->ecc.mode = NAND_ECC_HW;
503 502 chip->ecc.size = 512;
504 503 chip->ecc.bytes = 3;
505   - chip->autooob = &nand_hw_eccoob;
  504 + chip->ecc.layout = &nand_hw_eccoob;
506 505  
507 506 if (info->is_s3c2440) {
508 507 chip->ecc.hwctl = s3c2440_nand_enable_hwecc;
drivers/mtd/nand/sharpsl.c
... ... @@ -115,8 +115,7 @@
115 115 .pattern = scan_ff_pattern
116 116 };
117 117  
118   -static struct nand_oobinfo akita_oobinfo = {
119   - .useecc = MTD_NANDECC_AUTOPLACE,
  118 +static struct nand_ecclayout akita_oobinfo = {
120 119 .eccbytes = 24,
121 120 .eccpos = {
122 121 0x5, 0x1, 0x2, 0x3, 0x6, 0x7, 0x15, 0x11,
... ... @@ -202,7 +201,7 @@
202 201 this->badblock_pattern = &sharpsl_bbt;
203 202 if (machine_is_akita() || machine_is_borzoi()) {
204 203 this->badblock_pattern = &sharpsl_akita_bbt;
205   - this->autooob = &akita_oobinfo;
  204 + this->ecc.layout = &akita_oobinfo;
206 205 }
207 206 this->ecc.hwctl = sharpsl_nand_enable_hwecc;
208 207 this->ecc.calculate = sharpsl_nand_calculate_ecc;
drivers/mtd/onenand/onenand_base.c
... ... @@ -23,8 +23,7 @@
23 23 /**
24 24 * onenand_oob_64 - oob info for large (2KB) page
25 25 */
26   -static struct nand_oobinfo onenand_oob_64 = {
27   - .useecc = MTD_NANDECC_AUTOPLACE,
  26 +static struct nand_ecclayout onenand_oob_64 = {
28 27 .eccbytes = 20,
29 28 .eccpos = {
30 29 8, 9, 10, 11, 12,
... ... @@ -41,8 +40,7 @@
41 40 /**
42 41 * onenand_oob_32 - oob info for middle (1KB) page
43 42 */
44   -static struct nand_oobinfo onenand_oob_32 = {
45   - .useecc = MTD_NANDECC_AUTOPLACE,
  43 +static struct nand_ecclayout onenand_oob_32 = {
46 44 .eccbytes = 10,
47 45 .eccpos = {
48 46 8, 9, 10, 11, 12,
49 47  
50 48  
51 49  
... ... @@ -1747,22 +1745,22 @@
1747 1745  
1748 1746 switch (mtd->oobsize) {
1749 1747 case 64:
1750   - this->autooob = &onenand_oob_64;
  1748 + this->ecclayout = &onenand_oob_64;
1751 1749 break;
1752 1750  
1753 1751 case 32:
1754   - this->autooob = &onenand_oob_32;
  1752 + this->ecclayout = &onenand_oob_32;
1755 1753 break;
1756 1754  
1757 1755 default:
1758 1756 printk(KERN_WARNING "No OOB scheme defined for oobsize %d\n",
1759 1757 mtd->oobsize);
1760 1758 /* To prevent kernel oops */
1761   - this->autooob = &onenand_oob_32;
  1759 + this->ecclayout = &onenand_oob_32;
1762 1760 break;
1763 1761 }
1764 1762  
1765   - mtd->oobinfo = this->autooob;
  1763 + mtd->ecclayout = this->ecclayout;
1766 1764  
1767 1765 /* Fill in remaining MTD driver data */
1768 1766 mtd->type = MTD_NANDFLASH;
fs/jffs2/jffs2_fs_sb.h
... ... @@ -107,7 +107,7 @@
107 107 struct rw_semaphore wbuf_sem; /* Protects the write buffer */
108 108  
109 109 /* Information about out-of-band area usage... */
110   - struct nand_oobinfo *oobinfo;
  110 + struct nand_ecclayout *ecclayout;
111 111 uint32_t badblock_pos;
112 112 uint32_t fsdata_pos;
113 113 uint32_t fsdata_len;
... ... @@ -1140,18 +1140,9 @@
1140 1140 return 1;
1141 1141 }
1142 1142  
1143   -#define NAND_JFFS2_OOB16_FSDALEN 8
1144   -
1145   -static struct nand_oobinfo jffs2_oobinfo_docecc = {
1146   - .useecc = MTD_NANDECC_PLACE,
1147   - .eccbytes = 6,
1148   - .eccpos = {0,1,2,3,4,5}
1149   -};
1150   -
1151   -
1152 1143 static int jffs2_nand_set_oobinfo(struct jffs2_sb_info *c)
1153 1144 {
1154   - struct nand_oobinfo *oinfo = c->mtd->oobinfo;
  1145 + struct nand_ecclayout *oinfo = c->mtd->ecclayout;
1155 1146  
1156 1147 /* Do this only, if we have an oob buffer */
1157 1148 if (!c->mtd->oobsize)
1158 1149  
1159 1150  
... ... @@ -1161,33 +1152,23 @@
1161 1152 c->cleanmarker_size = 0;
1162 1153  
1163 1154 /* Should we use autoplacement ? */
1164   - if (oinfo && oinfo->useecc == MTD_NANDECC_AUTOPLACE) {
1165   - D1(printk(KERN_DEBUG "JFFS2 using autoplace on NAND\n"));
1166   - /* Get the position of the free bytes */
1167   - if (!oinfo->oobfree[0][1]) {
1168   - printk (KERN_WARNING "jffs2_nand_set_oobinfo(): Eeep. Autoplacement selected and no empty space in oob\n");
1169   - return -ENOSPC;
1170   - }
1171   - c->fsdata_pos = oinfo->oobfree[0][0];
1172   - c->fsdata_len = oinfo->oobfree[0][1];
1173   - if (c->fsdata_len > 8)
1174   - c->fsdata_len = 8;
1175   - } else {
1176   - /* This is just a legacy fallback and should go away soon */
1177   - switch(c->mtd->ecctype) {
1178   - case MTD_ECC_RS_DiskOnChip:
1179   - printk(KERN_WARNING "JFFS2 using DiskOnChip hardware ECC without autoplacement. Fix it!\n");
1180   - c->oobinfo = &jffs2_oobinfo_docecc;
1181   - c->fsdata_pos = 6;
1182   - c->fsdata_len = NAND_JFFS2_OOB16_FSDALEN;
1183   - c->badblock_pos = 15;
1184   - break;
  1155 + if (!oinfo) {
  1156 + D1(printk(KERN_DEBUG "JFFS2 on NAND. No autoplacment info found\n"));
  1157 + return -EINVAL;
  1158 + }
1185 1159  
1186   - default:
1187   - D1(printk(KERN_DEBUG "JFFS2 on NAND. No autoplacment info found\n"));
1188   - return -EINVAL;
1189   - }
  1160 + D1(printk(KERN_DEBUG "JFFS2 using autoplace on NAND\n"));
  1161 + /* Get the position of the free bytes */
  1162 + if (!oinfo->oobfree[0].length) {
  1163 + printk (KERN_WARNING "jffs2_nand_set_oobinfo(): Eeep."
  1164 + " Autoplacement selected and no empty space in oob\n");
  1165 + return -ENOSPC;
1190 1166 }
  1167 + c->fsdata_pos = oinfo->oobfree[0].offset;
  1168 + c->fsdata_len = oinfo->oobfree[0].length;
  1169 + if (c->fsdata_len > 8)
  1170 + c->fsdata_len = 8;
  1171 +
1191 1172 return 0;
1192 1173 }
1193 1174  
include/linux/mtd/inftl.h
... ... @@ -46,7 +46,7 @@
46 46 unsigned int nb_blocks; /* number of physical blocks */
47 47 unsigned int nb_boot_blocks; /* number of blocks used by the bios */
48 48 struct erase_info instr;
49   - struct nand_oobinfo oobinfo;
  49 + struct nand_ecclayout oobinfo;
50 50 };
51 51  
52 52 int INFTL_mount(struct INFTLrecord *s);
include/linux/mtd/mtd.h
... ... @@ -101,8 +101,8 @@
101 101 char *name;
102 102 int index;
103 103  
104   - /* oobinfo structure pointer - read only ! */
105   - struct nand_oobinfo *oobinfo;
  104 + /* ecc layout structure pointer - read only ! */
  105 + struct nand_ecclayout *ecclayout;
106 106  
107 107 /* Data for variable erase regions. If numeraseregions is zero,
108 108 * it means that the whole device has erasesize as given above.
include/linux/mtd/nand.h
... ... @@ -244,6 +244,7 @@
244 244 int total;
245 245 int prepad;
246 246 int postpad;
  247 + struct nand_ecclayout *layout;
247 248 void (*hwctl)(struct mtd_info *mtd, int mode);
248 249 int (*calculate)(struct mtd_info *mtd,
249 250 const uint8_t *dat,
... ... @@ -318,7 +319,7 @@
318 319 * @chipsize: [INTERN] the size of one chip for multichip arrays
319 320 * @pagemask: [INTERN] page number mask = number of (pages / chip) - 1
320 321 * @pagebuf: [INTERN] holds the pagenumber which is currently in data_buf
321   - * @autooob: [REPLACEABLE] the default (auto)placement scheme
  322 + * @ecclayout: [REPLACEABLE] the default ecc placement scheme
322 323 * @bbt: [INTERN] bad block table pointer
323 324 * @bbt_td: [REPLACEABLE] bad block table descriptor for flash lookup
324 325 * @bbt_md: [REPLACEABLE] bad block table mirror descriptor
... ... @@ -368,7 +369,7 @@
368 369  
369 370 uint8_t *oob_poi;
370 371 struct nand_hw_control *controller;
371   - struct nand_oobinfo *autooob;
  372 + struct nand_ecclayout *ecclayout;
372 373  
373 374 struct nand_ecc_ctrl ecc;
374 375 struct nand_buffers buffers;
... ... @@ -522,7 +523,7 @@
522 523 * @partitions: mtd partition list
523 524 * @chip_delay: R/B delay value in us
524 525 * @options: Option flags, e.g. 16bit buswidth
525   - * @oobinfo: oob info structure (ecc placement)
  526 + * @ecclayout: ecc layout info structure
526 527 * @priv: hardware controller specific settings
527 528 */
528 529 struct platform_nand_chip {
... ... @@ -530,7 +531,7 @@
530 531 int chip_offset;
531 532 int nr_partitions;
532 533 struct mtd_partition *partitions;
533   - struct nand_oobinfo *oobinfo;
  534 + struct nand_ecclayout *ecclayout;
534 535 int chip_delay;
535 536 unsigned int options;
536 537 void *priv;
include/linux/mtd/nftl.h
... ... @@ -37,7 +37,7 @@
37 37 unsigned int nb_blocks; /* number of physical blocks */
38 38 unsigned int nb_boot_blocks; /* number of blocks used by the bios */
39 39 struct erase_info instr;
40   - struct nand_oobinfo oobinfo;
  40 + struct nand_ecclayout oobinfo;
41 41 };
42 42  
43 43 int NFTL_mount(struct NFTLrecord *s);
include/linux/mtd/onenand.h
... ... @@ -77,7 +77,7 @@
77 77 * @param chip_lock [INTERN] spinlock used to protect access to this structure and the chip
78 78 * @param wq [INTERN] wait queue to sleep on if a OneNAND operation is in progress
79 79 * @param state [INTERN] the current state of the OneNAND device
80   - * @param autooob [REPLACEABLE] the default (auto)placement scheme
  80 + * @param ecclayout [REPLACEABLE] the default ecc placement scheme
81 81 * @param bbm [REPLACEABLE] pointer to Bad Block Management
82 82 * @param priv [OPTIONAL] pointer to private chip date
83 83 */
84 84  
... ... @@ -113,9 +113,9 @@
113 113 onenand_state_t state;
114 114 unsigned char *page_buf;
115 115  
116   - struct nand_oobinfo *autooob;
  116 + struct nand_ecclayout *ecclayout;
117 117  
118   - void *bbm;
  118 + void *bbm;
119 119  
120 120 void *priv;
121 121 };
include/linux/mtd/partitions.h
... ... @@ -41,7 +41,7 @@
41 41 u_int32_t size; /* partition size */
42 42 u_int32_t offset; /* offset within the master MTD space */
43 43 u_int32_t mask_flags; /* master MTD flags to mask out for this partition */
44   - struct nand_oobinfo *oobsel; /* out of band layout for this partition (NAND only)*/
  44 + struct nand_ecclayout *ecclayout; /* out of band layout for this partition (NAND only)*/
45 45 struct mtd_info **mtdp; /* pointer to store the MTD object */
46 46 };
47 47  
include/mtd/mtd-abi.h
... ... @@ -82,12 +82,12 @@
82 82 uint32_t locked;
83 83 };
84 84  
85   -#define MEMGETINFO _IOR('M', 1, struct mtd_info_user)
86   -#define MEMERASE _IOW('M', 2, struct erase_info_user)
87   -#define MEMWRITEOOB _IOWR('M', 3, struct mtd_oob_buf)
88   -#define MEMREADOOB _IOWR('M', 4, struct mtd_oob_buf)
89   -#define MEMLOCK _IOW('M', 5, struct erase_info_user)
90   -#define MEMUNLOCK _IOW('M', 6, struct erase_info_user)
  85 +#define MEMGETINFO _IOR('M', 1, struct mtd_info_user)
  86 +#define MEMERASE _IOW('M', 2, struct erase_info_user)
  87 +#define MEMWRITEOOB _IOWR('M', 3, struct mtd_oob_buf)
  88 +#define MEMREADOOB _IOWR('M', 4, struct mtd_oob_buf)
  89 +#define MEMLOCK _IOW('M', 5, struct erase_info_user)
  90 +#define MEMUNLOCK _IOW('M', 6, struct erase_info_user)
91 91 #define MEMGETREGIONCOUNT _IOR('M', 7, int)
92 92 #define MEMGETREGIONINFO _IOWR('M', 8, struct region_info_user)
93 93 #define MEMSETOOBSEL _IOW('M', 9, struct nand_oobinfo)
94 94  
95 95  
... ... @@ -97,13 +97,35 @@
97 97 #define OTPSELECT _IOR('M', 13, int)
98 98 #define OTPGETREGIONCOUNT _IOW('M', 14, int)
99 99 #define OTPGETREGIONINFO _IOW('M', 15, struct otp_info)
100   -#define OTPLOCK _IOR('M', 16, struct otp_info)
  100 +#define OTPLOCK _IOR('M', 16, struct otp_info)
  101 +#define ECCGETLAYOUT _IOR('M', 17, struct nand_ecclayout)
101 102  
  103 +/*
  104 + * Obsolete legacy interface. Keep it in order not to break userspace
  105 + * interfaces
  106 + */
102 107 struct nand_oobinfo {
103 108 uint32_t useecc;
104 109 uint32_t eccbytes;
105 110 uint32_t oobfree[8][2];
106 111 uint32_t eccpos[32];
  112 +};
  113 +
  114 +struct nand_oobfree {
  115 + uint32_t offset;
  116 + uint32_t length;
  117 +};
  118 +
  119 +#define MTD_MAX_OOBFREE_ENTRIES 8
  120 +/*
  121 + * ECC layout control structure. Exported to userspace for
  122 + * diagnosis and to allow creation of raw images
  123 + */
  124 +struct nand_ecclayout {
  125 + uint32_t eccbytes;
  126 + uint32_t eccpos[64];
  127 + uint32_t oobavail;
  128 + struct nand_oobfree oobfree[MTD_MAX_OOBFREE_ENTRIES];
107 129 };
108 130  
109 131 #endif /* __MTD_ABI_H__ */
include/mtd/mtd-user.h
... ... @@ -16,6 +16,7 @@
16 16 typedef struct erase_info_user erase_info_t;
17 17 typedef struct region_info_user region_info_t;
18 18 typedef struct nand_oobinfo nand_oobinfo_t;
  19 +typedef struct nand_ecclayout nand_ecclayout_t;
19 20  
20 21 #endif /* __MTD_USER_H__ */