From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mail-wm1-f42.google.com (mail-wm1-f42.google.com [209.85.128.42]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A442A45FFD7 for ; Tue, 18 Aug 2026 11:42:14 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.128.42 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1787053336; cv=none; b=AjidsBDYUsdhDUm4vx7aFqMw93rL2JTv2nNd/Ss98CjNlC+1L664cf0trjlT0Np0LGxpJ1w2K5ow8B3Qv1TmpKmcwejvK1OtaTVqYallJc5ZF9m5POfrs+u/d5bKBuAhEi33s2UIjpHKkf5dFU4Q6j+kvuOy9RHaObES3rc6Xv4= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1787053336; c=relaxed/simple; bh=LgyePt+UKNU9lVqf2Zoo2wx0wmQeWUVRJ7+qDFcGXR0=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=mNrSxkDqcm/mJuCw6bMvR7oLBvRZUpu/jrWwPXlB+ny0YsInTHx6pfLAZKvHZYzZueSsFvOF+2oBCpxe+g/aS0LNHQmFfgXkSTLOlkj5rJ2mLe7SFody7ZMeG90+YsHSXFWGEqOZjo7BEMz2cK36RSEy0Ow/uskL4UwhhPU7zp4= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com; spf=pass smtp.mailfrom=gmail.com; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b=mPICLnsH; arc=none smtp.client-ip=209.85.128.42 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=gmail.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="mPICLnsH" Received: by mail-wm1-f42.google.com with SMTP id 5b1f17b1804b1-4998b5a63e2so38939275e9.1 for ; Tue, 18 Aug 2026 04:42:14 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20251104; t=1787053333; x=1787658133; darn=vger.kernel.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to:content-type; bh=3tMfNTzrnv95v9YWomQJOjZXq4ObY0ENOn5OxxBG6Ow=; b=mPICLnsHbEjDuOmmTCaXxlXeK/pA7w6T5/6V7M29DtNDrxVXbhqHH0jPIHf6CVqpfb sGJBGc20SumFiBL1hiU4hUcIRobVqev08pFuX/wm+P5/5vbgjSRcW3119m4hu3/Si3fi 1sbBQc/aqA3L6JMplDuYI57Ieg+rdeP8ruU6hj3OgeWBEbHzPsqpayLzNL3gai/f8BD8 9wjHmIdaafLyrxM0vAt1Y+h9KUMr/4xEPqA2wnl7QH2N68d1zACZEYYmb+A14QogznwV 7a2KfWzyrJ2Xk326bhg/pVx5RtRvWj6K5IDzu2rMvg7MPVCn32zQGLn5iZVbTRdVQWT1 TnzQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20251104; t=1787053333; x=1787658133; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-gg:x-gm-message-state:from :to:cc:subject:date:message-id:reply-to:content-type; bh=3tMfNTzrnv95v9YWomQJOjZXq4ObY0ENOn5OxxBG6Ow=; b=LdPBvTWKckAD1GiyGJSlItRZ6AsFYqTYFMmRHAr6T1fW8nFUZHGWj8P1/AqRnyzYk4 q60inDlnBcEytQjc6p2BvE72fEtO94xDqAVeovtpL0tgiJ9dWSYxp9V1RwLh+jH0fcJx 8sdJsxF7C2i7iYMs4ha0J+hVwKgSJxjIlLLmTNH/wAAL4JtG9NaZKpcuAaEgK1A+YBvg S5oBCQ5KIqWl85t13pBLlpJEVUtD2bucha8pNFGTLJktm7RI9vnKCZnjeL599bZ+IXOj RpABr3Soe8vZyyFuQkKvjlUcw7VpZX/n9OfB6V8ZKJomTdiqzyqY8EXkY1JRbI/B3gbe gIMw== X-Forwarded-Encrypted: i=1; AHgh+Rp5wLzKGscJ6znaXlUzVXlSvX5ps7b4UeFX2JbeS+Psti41K6bsmFEOkXKUpDFYBf+j18xwb6RW02Gi5+c=@vger.kernel.org X-Gm-Message-State: AOJu0YxxNqSlR2sc21rBwY0pezeG0K3E0qlgu5W4vxDErJSuzNA+N6y5 grJEA2CsWBYvOikbcJgqpdnhbQ7ePMln1Sz4gxzl9QUX1c9wxbE3BqvamagbXJih X-Gm-Gg: AR+sD12VfVFHHGyPzuXZWSq2ocaNi2AxkdssfmGY0+G+JE839Hhun4KHQKfCrP4DGqR bS0rgzcKwL3lFuXUmB/D1tf5+/l9ws/Pb5pQKszBM28jhpihfadYbZoBzhJEDom/SffMqfHtdtI Jv3N86Lgj6zalawd3gCePTDt5B/tHmyMAWH5GE7XoCT9uGSciBKPr+bv3bUTs3ArswX7/07xKJi uk8hNQJtazyx5Wp6qJGv90P2iqLnQSBvd6ilLLmHS8hM3cfXCvZ7Wkkdtpp//9HCvDBJzFgZp/C gkvUVNC88GF2XsicR2yGydWCR04i3mtFMZxgcua5NYnMVbCpu/AFTOm9K9qAYrper8M3Hb7GUtM pqqLXXYbS+wyAdQZLWmI4Uo/yg04OdyjuLli2RSVViE62MY4ygW69+m2uNJ1eyaO3HXLf63GZTa R9x1Ee0fa67u2LNrXMQnwkjy4SpGIhmz+eYKrifTeAhDTk73P2/QsM71X2P4uaAWsI6ONbE0sdq C8o X-Received: by 2002:a05:600d:8489:20b0:499:8b13:3a98 with SMTP id 5b1f17b1804b1-4998b133b3dmr329338725e9.4.1787053332437; Tue, 18 Aug 2026 04:42:12 -0700 (PDT) Received: from deb05.proceq.com ([213.160.61.66]) by smtp.gmail.com with ESMTPSA id 5b1f17b1804b1-4998780397esm28680785e9.3.2026.08.18.04.42.11 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 18 Aug 2026 04:42:11 -0700 (PDT) From: Mehmet Fide To: Stefan Agner , Miquel Raynal , Richard Weinberger , Vignesh Raghavendra Cc: Mehmet Fide , Boris Brezillon , Frieder Schrempf , Edward Karpicz , linux-mtd@lists.infradead.org, linux-kernel@vger.kernel.org Subject: [PATCH 2/2] mtd: rawnand: vf610_nfc: fix false bitflips on reads of erased pages Date: Tue, 18 Aug 2026 13:42:08 +0200 Message-ID: <20260818114208.2780311-3-mehmet.fide@gmail.com> X-Mailer: git-send-email 2.54.0 In-Reply-To: <20260818114208.2780311-1-mehmet.fide@gmail.com> References: <20260818114208.2780311-1-mehmet.fide@gmail.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit From: Mehmet Fide When the ECC engine fails to decode a page, the driver re-reads the OOB area with the engine bypassed, but runs the erased-page check for the data area on the buffer left in the controller SRAM by the failed transfer. That buffer does not hold what is on the flash: the failing engine writes a bogus single-bit "correction" into it. In the 60-byte ECC mode the all-0xff content of an erased page always decodes to the same error location, so every erased page shows one stale zero bit at data offset 0x5FD, which the erased-page check then reports as a corrected bitflip. Edward Karpicz discovered this behaviour and identified the offset on a Colibri VF61; the analysis and the fix build on his finding. Measured with an instrumented driver on a Colibri VF50 (MX30LF1G18AC, 32-bit ECC): reading a 126 MiB partition with nanddump increased the corrected counter by 18035, exactly one per erased page, while raw reads of the same pages return clean 0xff. A v4.4 kernel on the VF61 (MX30LF4G28AC) accumulates the same false counts, so the behaviour follows the controller rather than the chip or the driver generation. Neither the Vybrid reference manual nor the published mask set errata (VFXXX_2N02G) document it. The 45-byte ECC mode is not affected. Restoring the known byte is not enough: on pages that fail to decode with content other than all-0xff the engine writes its correction wherever the syndrome points (measured at a different offset on such a page), so the check has to run on what the flash holds. Re-read the data area with the ECC engine bypassed, exactly as already done for the OOB area. The corrected counter then stays at zero on both boards. Reported-by: Edward Karpicz Link: https://community.toradex.com/t/colibri-vf50-vf61-on-the-current-bsp-mainline-u-boot-v2026-07-and-linux-6-18-lts/30735 Signed-off-by: Mehmet Fide --- drivers/mtd/nand/raw/vf610_nfc.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/drivers/mtd/nand/raw/vf610_nfc.c b/drivers/mtd/nand/raw/vf610_nfc.c index f27ef2b0884d..d41750a4352c 100644 --- a/drivers/mtd/nand/raw/vf610_nfc.c +++ b/drivers/mtd/nand/raw/vf610_nfc.c @@ -514,6 +514,7 @@ static inline int vf610_nfc_correct_data(struct nand_chip *chip, uint8_t *dat, u8 ecc_status; u8 ecc_count; int flips_threshold = nfc->chip.ecc.strength / 2; + int ret; ecc_status = vf610_nfc_read(nfc, ecc_status_off) & 0xff; ecc_count = ecc_status & ECC_STATUS_ERR_COUNT; @@ -521,9 +522,17 @@ static inline int vf610_nfc_correct_data(struct nand_chip *chip, uint8_t *dat, if (!(ecc_status & ECC_STATUS_MASK)) return ecc_count; + /* + * The failed decode leaves a bogus "correction" in the SRAM buffer, + * so re-read the data without ECC too, as already done for the OOB. + */ nfc->data_access = true; - nand_read_oob_op(&nfc->chip, page, 0, oob, mtd->oobsize); + ret = nand_read_page_op(&nfc->chip, page, 0, dat, nfc->chip.ecc.size); + if (!ret) + ret = nand_read_oob_op(&nfc->chip, page, 0, oob, mtd->oobsize); nfc->data_access = false; + if (ret) + return ret; /* * On an erased page, bit count (including OOB) should be zero or -- 2.54.0