7cba7b14fe
The first (sixt) byte in the OOB area contains vendor's bad block information. During identification of the NAND chip this information is collected by scanning the complete chip. The option NAND_USE_FLASH_BBT is used to store this information in a sector so we don't have to scan the complete flash. Unfortunately the code stores a marker in order to recognize the BBT in the OOB area. This will fail if the OOB area is completely used for ECC. This patch introduces the option NAND_USE_FLASH_BBT_NO_OOB which has to be used with NAND_USE_FLASH_BBT. It will then store BBT on flash without touching the OOB area. The BBT format on flash remains same except the first page starts with the recognition pattern followed by the version byte. This change was tested in nandsim and it looks good so far :) Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de> Signed-off-by: David Woodhouse <David.Woodhouse@intel.com>
156 lines
5.5 KiB
C
156 lines
5.5 KiB
C
/*
|
|
* linux/include/linux/mtd/bbm.h
|
|
*
|
|
* NAND family Bad Block Management (BBM) header file
|
|
* - Bad Block Table (BBT) implementation
|
|
*
|
|
* Copyright © 2005 Samsung Electronics
|
|
* Kyungmin Park <kyungmin.park@samsung.com>
|
|
*
|
|
* Copyright © 2000-2005
|
|
* Thomas Gleixner <tglx@linuxtronix.de>
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
*
|
|
*/
|
|
#ifndef __LINUX_MTD_BBM_H
|
|
#define __LINUX_MTD_BBM_H
|
|
|
|
/* The maximum number of NAND chips in an array */
|
|
#define NAND_MAX_CHIPS 8
|
|
|
|
/**
|
|
* struct nand_bbt_descr - bad block table descriptor
|
|
* @options: options for this descriptor
|
|
* @pages: the page(s) where we find the bbt, used with option BBT_ABSPAGE
|
|
* when bbt is searched, then we store the found bbts pages here.
|
|
* Its an array and supports up to 8 chips now
|
|
* @offs: offset of the pattern in the oob area of the page
|
|
* @veroffs: offset of the bbt version counter in the oob are of the page
|
|
* @version: version read from the bbt page during scan
|
|
* @len: length of the pattern, if 0 no pattern check is performed
|
|
* @maxblocks: maximum number of blocks to search for a bbt. This number of
|
|
* blocks is reserved at the end of the device where the tables are
|
|
* written.
|
|
* @reserved_block_code: if non-0, this pattern denotes a reserved (rather than
|
|
* bad) block in the stored bbt
|
|
* @pattern: pattern to identify bad block table or factory marked good /
|
|
* bad blocks, can be NULL, if len = 0
|
|
*
|
|
* Descriptor for the bad block table marker and the descriptor for the
|
|
* pattern which identifies good and bad blocks. The assumption is made
|
|
* that the pattern and the version count are always located in the oob area
|
|
* of the first block.
|
|
*/
|
|
struct nand_bbt_descr {
|
|
int options;
|
|
int pages[NAND_MAX_CHIPS];
|
|
int offs;
|
|
int veroffs;
|
|
uint8_t version[NAND_MAX_CHIPS];
|
|
int len;
|
|
int maxblocks;
|
|
int reserved_block_code;
|
|
uint8_t *pattern;
|
|
};
|
|
|
|
/* Options for the bad block table descriptors */
|
|
|
|
/* The number of bits used per block in the bbt on the device */
|
|
#define NAND_BBT_NRBITS_MSK 0x0000000F
|
|
#define NAND_BBT_1BIT 0x00000001
|
|
#define NAND_BBT_2BIT 0x00000002
|
|
#define NAND_BBT_4BIT 0x00000004
|
|
#define NAND_BBT_8BIT 0x00000008
|
|
/* The bad block table is in the last good block of the device */
|
|
#define NAND_BBT_LASTBLOCK 0x00000010
|
|
/* The bbt is at the given page, else we must scan for the bbt */
|
|
#define NAND_BBT_ABSPAGE 0x00000020
|
|
/* The bbt is at the given page, else we must scan for the bbt */
|
|
#define NAND_BBT_SEARCH 0x00000040
|
|
/* bbt is stored per chip on multichip devices */
|
|
#define NAND_BBT_PERCHIP 0x00000080
|
|
/* bbt has a version counter at offset veroffs */
|
|
#define NAND_BBT_VERSION 0x00000100
|
|
/* Create a bbt if none axists */
|
|
#define NAND_BBT_CREATE 0x00000200
|
|
/* Search good / bad pattern through all pages of a block */
|
|
#define NAND_BBT_SCANALLPAGES 0x00000400
|
|
/* Scan block empty during good / bad block scan */
|
|
#define NAND_BBT_SCANEMPTY 0x00000800
|
|
/* Write bbt if neccecary */
|
|
#define NAND_BBT_WRITE 0x00001000
|
|
/* Read and write back block contents when writing bbt */
|
|
#define NAND_BBT_SAVECONTENT 0x00002000
|
|
/* Search good / bad pattern on the first and the second page */
|
|
#define NAND_BBT_SCAN2NDPAGE 0x00004000
|
|
/* Search good / bad pattern on the last page of the eraseblock */
|
|
#define NAND_BBT_SCANLASTPAGE 0x00008000
|
|
/* Chip stores bad block marker on BOTH 1st and 6th bytes of OOB */
|
|
#define NAND_BBT_SCANBYTE1AND6 0x00100000
|
|
/* The nand_bbt_descr was created dynamicaly and must be freed */
|
|
#define NAND_BBT_DYNAMICSTRUCT 0x00200000
|
|
/* The bad block table does not OOB for marker */
|
|
#define NAND_BBT_NO_OOB 0x00400000
|
|
|
|
/* The maximum number of blocks to scan for a bbt */
|
|
#define NAND_BBT_SCAN_MAXBLOCKS 4
|
|
|
|
/*
|
|
* Constants for oob configuration
|
|
*/
|
|
#define NAND_SMALL_BADBLOCK_POS 5
|
|
#define NAND_LARGE_BADBLOCK_POS 0
|
|
#define ONENAND_BADBLOCK_POS 0
|
|
|
|
/*
|
|
* Bad block scanning errors
|
|
*/
|
|
#define ONENAND_BBT_READ_ERROR 1
|
|
#define ONENAND_BBT_READ_ECC_ERROR 2
|
|
#define ONENAND_BBT_READ_FATAL_ERROR 4
|
|
|
|
/**
|
|
* struct bbm_info - [GENERIC] Bad Block Table data structure
|
|
* @bbt_erase_shift: [INTERN] number of address bits in a bbt entry
|
|
* @badblockpos: [INTERN] position of the bad block marker in the oob area
|
|
* @options: options for this descriptor
|
|
* @bbt: [INTERN] bad block table pointer
|
|
* @isbad_bbt: function to determine if a block is bad
|
|
* @badblock_pattern: [REPLACEABLE] bad block scan pattern used for
|
|
* initial bad block scan
|
|
* @priv: [OPTIONAL] pointer to private bbm date
|
|
*/
|
|
struct bbm_info {
|
|
int bbt_erase_shift;
|
|
int badblockpos;
|
|
int options;
|
|
|
|
uint8_t *bbt;
|
|
|
|
int (*isbad_bbt)(struct mtd_info *mtd, loff_t ofs, int allowbbt);
|
|
|
|
/* TODO Add more NAND specific fileds */
|
|
struct nand_bbt_descr *badblock_pattern;
|
|
|
|
void *priv;
|
|
};
|
|
|
|
/* OneNAND BBT interface */
|
|
extern int onenand_scan_bbt(struct mtd_info *mtd, struct nand_bbt_descr *bd);
|
|
extern int onenand_default_bbt(struct mtd_info *mtd);
|
|
|
|
#endif /* __LINUX_MTD_BBM_H */
|