Commit bd0b6434 authored by Miquel Raynal's avatar Miquel Raynal Committed by Boris Brezillon

mtd: rawnand: get rid of the ONFI parameter page in nand_chip

The NAND chip parameter page is statically allocated within the
nand_chip structure, which reserves a lot of space. Even not ONFI nor
JEDEC chips have it embedded. Also, only a few parameters are actually
read from the parameter page after the detection.

Now that there is a small nand_parameters structure that hold all needed
ONFI parameters, remove the ONFI page from the nand_chip structure by
just allocating it during the identification phase and removing it right
after.
Signed-off-by: default avatarMiquel Raynal <miquel.raynal@bootlin.com>
Signed-off-by: default avatarBoris Brezillon <boris.brezillon@bootlin.com>
parent 480139d9
...@@ -5101,7 +5101,7 @@ static int nand_flash_detect_ext_param_page(struct nand_chip *chip, ...@@ -5101,7 +5101,7 @@ static int nand_flash_detect_ext_param_page(struct nand_chip *chip,
static int nand_flash_detect_onfi(struct nand_chip *chip) static int nand_flash_detect_onfi(struct nand_chip *chip)
{ {
struct mtd_info *mtd = nand_to_mtd(chip); struct mtd_info *mtd = nand_to_mtd(chip);
struct nand_onfi_params *p = &chip->onfi_params; struct nand_onfi_params *p;
char id[4]; char id[4];
int i, ret, val; int i, ret, val;
...@@ -5110,14 +5110,23 @@ static int nand_flash_detect_onfi(struct nand_chip *chip) ...@@ -5110,14 +5110,23 @@ static int nand_flash_detect_onfi(struct nand_chip *chip)
if (ret || strncmp(id, "ONFI", 4)) if (ret || strncmp(id, "ONFI", 4))
return 0; return 0;
/* ONFI chip: allocate a buffer to hold its parameter page */
p = kzalloc(sizeof(*p), GFP_KERNEL);
if (!p)
return -ENOMEM;
ret = nand_read_param_page_op(chip, 0, NULL, 0); ret = nand_read_param_page_op(chip, 0, NULL, 0);
if (ret) if (ret) {
return 0; ret = 0;
goto free_onfi_param_page;
}
for (i = 0; i < 3; i++) { for (i = 0; i < 3; i++) {
ret = nand_read_data_op(chip, p, sizeof(*p), true); ret = nand_read_data_op(chip, p, sizeof(*p), true);
if (ret) if (ret) {
return 0; ret = 0;
goto free_onfi_param_page;
}
if (onfi_crc16(ONFI_CRC_BASE, (uint8_t *)p, 254) == if (onfi_crc16(ONFI_CRC_BASE, (uint8_t *)p, 254) ==
le16_to_cpu(p->crc)) { le16_to_cpu(p->crc)) {
...@@ -5127,7 +5136,7 @@ static int nand_flash_detect_onfi(struct nand_chip *chip) ...@@ -5127,7 +5136,7 @@ static int nand_flash_detect_onfi(struct nand_chip *chip)
if (i == 3) { if (i == 3) {
pr_err("Could not find valid ONFI parameter page; aborting\n"); pr_err("Could not find valid ONFI parameter page; aborting\n");
return 0; goto free_onfi_param_page;
} }
/* Check version */ /* Check version */
...@@ -5145,7 +5154,9 @@ static int nand_flash_detect_onfi(struct nand_chip *chip) ...@@ -5145,7 +5154,9 @@ static int nand_flash_detect_onfi(struct nand_chip *chip)
if (!chip->parameters.onfi.version) { if (!chip->parameters.onfi.version) {
pr_info("unsupported ONFI version: %d\n", val); pr_info("unsupported ONFI version: %d\n", val);
return 0; goto free_onfi_param_page;
} else {
ret = 1;
} }
sanitize_string(p->manufacturer, sizeof(p->manufacturer)); sanitize_string(p->manufacturer, sizeof(p->manufacturer));
...@@ -5217,7 +5228,9 @@ static int nand_flash_detect_onfi(struct nand_chip *chip) ...@@ -5217,7 +5228,9 @@ static int nand_flash_detect_onfi(struct nand_chip *chip)
memcpy(chip->parameters.onfi.vendor, p->vendor, memcpy(chip->parameters.onfi.vendor, p->vendor,
sizeof(p->vendor)); sizeof(p->vendor));
return 1; free_onfi_param_page:
kfree(p);
return ret;
} }
/* /*
...@@ -5612,7 +5625,10 @@ static int nand_detect(struct nand_chip *chip, struct nand_flash_dev *type) ...@@ -5612,7 +5625,10 @@ static int nand_detect(struct nand_chip *chip, struct nand_flash_dev *type)
chip->parameters.onfi.version = 0; chip->parameters.onfi.version = 0;
if (!type->name || !type->pagesize) { if (!type->name || !type->pagesize) {
/* Check if the chip is ONFI compliant */ /* Check if the chip is ONFI compliant */
if (nand_flash_detect_onfi(chip)) ret = nand_flash_detect_onfi(chip);
if (ret < 0)
return ret;
else if (ret)
goto ident_done; goto ident_done;
/* Check if the chip is JEDEC compliant */ /* Check if the chip is JEDEC compliant */
......
...@@ -1200,8 +1200,6 @@ int nand_op_parser_exec_op(struct nand_chip *chip, ...@@ -1200,8 +1200,6 @@ int nand_op_parser_exec_op(struct nand_chip *chip,
* currently in data_buf. * currently in data_buf.
* @subpagesize: [INTERN] holds the subpagesize * @subpagesize: [INTERN] holds the subpagesize
* @id: [INTERN] holds NAND ID * @id: [INTERN] holds NAND ID
* @onfi_params: [INTERN] holds the ONFI page parameter when ONFI is
* supported, 0 otherwise.
* @parameters: [INTERN] holds generic parameters under an easily * @parameters: [INTERN] holds generic parameters under an easily
* readable form. * readable form.
* @max_bb_per_die: [INTERN] the max number of bad blocks each die of a * @max_bb_per_die: [INTERN] the max number of bad blocks each die of a
...@@ -1282,7 +1280,6 @@ struct nand_chip { ...@@ -1282,7 +1280,6 @@ struct nand_chip {
int badblockbits; int badblockbits;
struct nand_id id; struct nand_id id;
struct nand_onfi_params onfi_params;
struct nand_parameters parameters; struct nand_parameters parameters;
u16 max_bb_per_die; u16 max_bb_per_die;
u32 blocks_per_die; u32 blocks_per_die;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment