Merge "mtd: msm_qpic_nand: Use flash device ECC capability for erase page"

This commit is contained in:
QCTECMDR Service 2025-10-15 12:49:46 -07:00 • committed by Gerrit - the friendly Code Review server
commit 059428d92d
2 changed files with 66 additions and 7 deletions

View file

@ -2,7 +2,7 @@
/*
* Copyright (C) 2007 Google, Inc.
* Copyright (c) 2012-2021 The Linux Foundation. All rights reserved.
* Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) Qualcomm Technologies, Inc. and/or its subsidiaries.
*/
#include "msm_qpic_nand.h"
@ -1944,7 +1944,7 @@ free_dma:
if (last_pos < ecc_bytes_percw_in_bits)
num_zero_bits++;
if (num_zero_bits > 4) {
if (num_zero_bits > info->flash_dev.ecc_capability) {
*erased_page = false;
goto free_mem;
}
@ -1955,8 +1955,8 @@ free_dma:
num_zero_bits = last_pos = next_pos = 0;
ecc_temp += chip->ecc_parity_bytes;
}
if ((n == cwperpage) && (num_zero_bits <= 4))
if ((n == cwperpage) &&
(num_zero_bits <= info->flash_dev.ecc_capability))
*erased_page = true;
free_mem:
kfree(ecc);
@ -2163,6 +2163,33 @@ static int msm_nand_read_pagescope(struct mtd_info *mtd, loff_t from,
goto free_dma;
/* Check for flash status errors */
pageerr = rawerr = 0;
/*
* PAGE_ERASED bit will set only if all
* CODEWORD_ERASED bit of all codewords
* of the page is set.
*
* PAGE_ERASED bit is a 'logical and' of all
* CODEWORD_ERASED bit of all codewords i.e.
* even if one codeword is detected as not
* an erased codeword, PAGE_ERASED bit will unset.
*/
for (n = rw_params.start_sector; n < cwperpage; n++) {
if ((dma_buffer->result[n].erased_cw_status &
(1 << PAGE_ERASED)) &&
(dma_buffer->result[n].buffer_status &
NUM_ERRORS)) {
err = msm_nand_is_erased_page_ps(mtd,
from, ops,
&rw_params,
&erased_page);
if (err)
goto free_dma;
if (erased_page)
rawerr = -EIO;
break;
}
}
for (n = rw_params.start_sector; n < cwperpage; n++) {
if (dma_buffer->result[n].flash_status & (FS_OP_ERR |
FS_MPU_ERR)) {
@ -2554,7 +2581,7 @@ free_dma:
if (last_pos < ecc_bytes_percw_in_bits)
num_zero_bits++;
if (num_zero_bits > 4) {
if (num_zero_bits > info->flash_dev.ecc_capability) {
*erased_page = false;
goto free_mem;
}
@ -2566,7 +2593,8 @@ free_dma:
ecc_temp += chip->ecc_parity_bytes;
}
if ((n == cwperpage) && (num_zero_bits <= 4))
if ((n == cwperpage) &&
(num_zero_bits <= info->flash_dev.ecc_capability))
*erased_page = true;
free_mem:
kfree(ecc);
@ -2760,6 +2788,33 @@ static int msm_nand_read_oob(struct mtd_info *mtd, loff_t from,
goto free_dma;
/* Check for flash status errors */
pageerr = rawerr = 0;
/*
* PAGE_ERASED bit will set only if all
* CODEWORD_ERASED bit of all codewords
* of the page is set.
*
* PAGE_ERASED bit is a 'logical and' of all
* CODEWORD_ERASED bit of all codewords i.e.
* even if one codeword is detected as not
* an erased codeword, PAGE_ERASED bit will unset.
*/
for (n = rw_params.start_sector; n < cwperpage; n++) {
if ((dma_buffer->result[n].erased_cw_status &
(1 << PAGE_ERASED)) &&
(dma_buffer->result[n].buffer_status &
NUM_ERRORS)) {
err = msm_nand_is_erased_page(mtd,
from, ops,
&rw_params,
&erased_page);
if (err)
goto free_dma;
if (erased_page)
rawerr = -EIO;
break;
}
}
for (n = rw_params.start_sector; n < cwperpage; n++) {
if (dma_buffer->result[n].flash_status & (FS_OP_ERR |
FS_MPU_ERR)) {

View file

@ -154,7 +154,10 @@
#define RESET_ERASED_DET (1 << AUTO_DETECT_RES)
#define ACTIVE_ERASED_DET (0 << AUTO_DETECT_RES)
#define CLR_ERASED_PAGE_DET (RESET_ERASED_DET | MASK_ECC)
#define SET_ERASED_PAGE_DET (ACTIVE_ERASED_DET | MASK_ECC)
#define SET_ERASED_PAGE_DET (ACTIVE_ERASED_DET | MASK_ECC | SET_N_MAX_ZEROS)
#define N_MAX_ZEROS 2
#define MAX_ECC_BIT_FLIPS 4
#define SET_N_MAX_ZEROS (MAX_ECC_BIT_FLIPS << N_MAX_ZEROS)
#define MSM_NAND_ERASED_CW_DETECT_STATUS(info) MSM_NAND_REG(info, 0x300EC)
#define PAGE_ALL_ERASED 7
@ -163,6 +166,7 @@
#define CODEWORD_ERASED 4
#define ERASED_PAGE ((1 << PAGE_ALL_ERASED) | (1 << PAGE_ERASED))
#define ERASED_CW ((1 << CODEWORD_ALL_ERASED) | (1 << CODEWORD_ERASED))
#define NUM_ERRORS 0x1f
#define MSM_NAND_CTRL(info) MSM_NAND_REG(info, 0x30F00)
#define BAM_MODE_EN 0