From nobody Wed Feb 11 03:26:03 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id BA396C76195 for ; Sat, 18 Mar 2023 01:57:26 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229896AbjCRB5Y (ORCPT ); Fri, 17 Mar 2023 21:57:24 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59896 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229755AbjCRB5S (ORCPT ); Fri, 17 Mar 2023 21:57:18 -0400 Received: from szxga02-in.huawei.com (szxga02-in.huawei.com [45.249.212.188]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 4BB8B49899 for ; Fri, 17 Mar 2023 18:57:15 -0700 (PDT) Received: from dggpemm100009.china.huawei.com (unknown [172.30.72.54]) by szxga02-in.huawei.com (SkyGuard) with ESMTP id 4PdkYt4Qv8zSlqp; Sat, 18 Mar 2023 09:53:54 +0800 (CST) Received: from huawei.com (10.175.127.227) by dggpemm100009.china.huawei.com (7.185.36.113) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.21; Sat, 18 Mar 2023 09:57:13 +0800 From: ZhaoLong Wang To: , , CC: , , , , Subject: [PATCH -next 1/5] ubi: Using the Fault Injection Framework to refactor the debugfs interface Date: Sat, 18 Mar 2023 09:56:17 +0800 Message-ID: <20230318015621.1408243-2-wangzhaolong1@huawei.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20230318015621.1408243-1-wangzhaolong1@huawei.com> References: <20230318015621.1408243-1-wangzhaolong1@huawei.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.175.127.227] X-ClientProxiedBy: dggems705-chm.china.huawei.com (10.3.19.182) To dggpemm100009.china.huawei.com (7.185.36.113) X-CFilter-Loop: Reflected Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" To make debug parameters configurable at run time, use the fault injection framework to reconstruct the debugfs interface. Now, the file emulate_failures and fault_attr files control whether to enable fault emmulation. The file emulate_failures receives a mask that controls type and process of fault injection. Generally, for ease of use, you can directly enter a mask with all 1s. echo 0xffff > /sys/kernel/debug/ubi/ubi0/emulate_failures And you need to configure other fault-injection capabilities for testing purpose: echo 100 > /sys/kernel/debug/ubi/fault_inject/emulate_power_cut/probability echo 15 > /sys/kernel/debug/ubi/fault_inject/emulate_power_cut/space echo 2 > /sys/kernel/debug/ubi/fault_inject/emulate_power_cut/verbose echo -1 > /sys/kernel/debug/ubi/fault_inject/emulate_power_cut/times The CONFIG_MTD_UBI_FAULT_INJECTION to enable the Fault Injection is added to kconfig. Signed-off-by: ZhaoLong Wang --- drivers/mtd/ubi/Kconfig | 8 +++ drivers/mtd/ubi/debug.c | 147 ++++++++++++++++------------------------ drivers/mtd/ubi/debug.h | 91 ++++++++++++++++++++----- drivers/mtd/ubi/io.c | 10 ++- drivers/mtd/ubi/ubi.h | 37 ++-------- 5 files changed, 150 insertions(+), 143 deletions(-) diff --git a/drivers/mtd/ubi/Kconfig b/drivers/mtd/ubi/Kconfig index 2ed77b7b3fcb..0a0180a3a54b 100644 --- a/drivers/mtd/ubi/Kconfig +++ b/drivers/mtd/ubi/Kconfig @@ -103,5 +103,13 @@ config MTD_UBI_BLOCK When selected, this feature will be built in the UBI driver. =20 If in doubt, say "N". +config MTD_UBI_FAULT_INJECTION + bool "Fault injection capability of UBI device" + default n + depends on FAULT_INJECTION_DEBUG_FS + help + this option enable fault-injection support for UBI devices for + testing purposes and is only interesting to developers. =20 + If unsure, say N. endif # MTD_UBI diff --git a/drivers/mtd/ubi/debug.c b/drivers/mtd/ubi/debug.c index 27168f511d6d..2550522e2cd5 100644 --- a/drivers/mtd/ubi/debug.c +++ b/drivers/mtd/ubi/debug.c @@ -10,6 +10,23 @@ #include #include #include +#include + +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION +static DECLARE_FAULT_ATTR(fault_bitflips_attr); +static DECLARE_FAULT_ATTR(fault_io_failures_attr); +static DECLARE_FAULT_ATTR(fault_power_cut_attr); + +#define FAIL_ACTION(name, fault_attr) \ +bool should_fail_##name(void) \ +{ \ + return should_fail(&fault_attr, 1); \ +} + +FAIL_ACTION(bitflips, fault_bitflips_attr) +FAIL_ACTION(io_failures, fault_io_failures_attr) +FAIL_ACTION(power_cut, fault_power_cut_attr) +#endif =20 =20 /** @@ -212,6 +229,31 @@ void ubi_dump_mkvol_req(const struct ubi_mkvol_req *re= q) */ static struct dentry *dfs_rootdir; =20 +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION +static void dfs_create_fault_entry(struct dentry *parent) +{ + struct dentry *dir; + + dir =3D debugfs_create_dir("fault_inject", parent); + if (IS_ERR_OR_NULL(dir)) { + int err =3D dir ? PTR_ERR(dir) : -ENODEV; + + pr_warn("UBI error: cannot create \"fault_inject\" debugfs directory, er= ror %d\n", + err); + return; + } + + fault_create_debugfs_attr("emulate_bitflips", dir, + &fault_bitflips_attr); + + fault_create_debugfs_attr("emulate_io_failures", dir, + &fault_io_failures_attr); + + fault_create_debugfs_attr("emulate_power_cut", dir, + &fault_power_cut_attr); +} +#endif + /** * ubi_debugfs_init - create UBI debugfs directory. * @@ -232,6 +274,10 @@ int ubi_debugfs_init(void) return err; } =20 +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + dfs_create_fault_entry(dfs_rootdir); +#endif + return 0; } =20 @@ -268,27 +314,12 @@ static ssize_t dfs_file_read(struct file *file, char = __user *user_buf, val =3D d->chk_fastmap; else if (dent =3D=3D d->dfs_disable_bgt) val =3D d->disable_bgt; - else if (dent =3D=3D d->dfs_emulate_bitflips) - val =3D d->emulate_bitflips; - else if (dent =3D=3D d->dfs_emulate_io_failures) - val =3D d->emulate_io_failures; - else if (dent =3D=3D d->dfs_emulate_power_cut) { - snprintf(buf, sizeof(buf), "%u\n", d->emulate_power_cut); + else if (dent =3D=3D d->dfs_emulate_failures) { + snprintf(buf, sizeof(buf), "%u\n", d->emulate_failures); count =3D simple_read_from_buffer(user_buf, count, ppos, buf, strlen(buf)); goto out; - } else if (dent =3D=3D d->dfs_power_cut_min) { - snprintf(buf, sizeof(buf), "%u\n", d->power_cut_min); - count =3D simple_read_from_buffer(user_buf, count, ppos, - buf, strlen(buf)); - goto out; - } else if (dent =3D=3D d->dfs_power_cut_max) { - snprintf(buf, sizeof(buf), "%u\n", d->power_cut_max); - count =3D simple_read_from_buffer(user_buf, count, ppos, - buf, strlen(buf)); - goto out; - } - else { + } else { count =3D -EINVAL; goto out; } @@ -330,20 +361,10 @@ static ssize_t dfs_file_write(struct file *file, cons= t char __user *user_buf, goto out; } =20 - if (dent =3D=3D d->dfs_power_cut_min) { - if (kstrtouint(buf, 0, &d->power_cut_min) !=3D 0) - count =3D -EINVAL; - goto out; - } else if (dent =3D=3D d->dfs_power_cut_max) { - if (kstrtouint(buf, 0, &d->power_cut_max) !=3D 0) + if (dent =3D=3D d->dfs_emulate_failures) { + if (kstrtouint(buf, 0, &d->emulate_failures) !=3D 0) count =3D -EINVAL; goto out; - } else if (dent =3D=3D d->dfs_emulate_power_cut) { - if (kstrtoint(buf, 0, &val) !=3D 0) - count =3D -EINVAL; - else - d->emulate_power_cut =3D val; - goto out; } =20 if (buf[0] =3D=3D '1') @@ -363,10 +384,6 @@ static ssize_t dfs_file_write(struct file *file, const= char __user *user_buf, d->chk_fastmap =3D val; else if (dent =3D=3D d->dfs_disable_bgt) d->disable_bgt =3D val; - else if (dent =3D=3D d->dfs_emulate_bitflips) - d->emulate_bitflips =3D val; - else if (dent =3D=3D d->dfs_emulate_io_failures) - d->emulate_io_failures =3D val; else count =3D -EINVAL; =20 @@ -386,6 +403,7 @@ static const struct file_operations dfs_fops =3D { .owner =3D THIS_MODULE, }; =20 + /* As long as the position is less then that total number of erase blocks, * we still have more to print. */ @@ -533,32 +551,14 @@ int ubi_debugfs_init_dev(struct ubi_device *ubi) d->dfs_dir, (void *)ubi_num, &dfs_fops); =20 - d->dfs_emulate_bitflips =3D debugfs_create_file("tst_emulate_bitflips", - mode, d->dfs_dir, - (void *)ubi_num, - &dfs_fops); - - d->dfs_emulate_io_failures =3D debugfs_create_file("tst_emulate_io_failur= es", - mode, d->dfs_dir, - (void *)ubi_num, - &dfs_fops); - - d->dfs_emulate_power_cut =3D debugfs_create_file("tst_emulate_power_cut", - mode, d->dfs_dir, - (void *)ubi_num, - &dfs_fops); - - d->dfs_power_cut_min =3D debugfs_create_file("tst_emulate_power_cut_min", - mode, d->dfs_dir, - (void *)ubi_num, &dfs_fops); - - d->dfs_power_cut_max =3D debugfs_create_file("tst_emulate_power_cut_max", - mode, d->dfs_dir, - (void *)ubi_num, &dfs_fops); - debugfs_create_file("detailed_erase_block_info", S_IRUSR, d->dfs_dir, (void *)ubi_num, &eraseblk_count_fops); =20 +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + d->dfs_emulate_failures =3D debugfs_create_file("emulate_failures", mode, + d->dfs_dir, (void *)ubi_num, + &dfs_fops); +#endif return 0; } =20 @@ -571,36 +571,3 @@ void ubi_debugfs_exit_dev(struct ubi_device *ubi) if (IS_ENABLED(CONFIG_DEBUG_FS)) debugfs_remove_recursive(ubi->dbg.dfs_dir); } - -/** - * ubi_dbg_power_cut - emulate a power cut if it is time to do so - * @ubi: UBI device description object - * @caller: Flags set to indicate from where the function is being called - * - * Returns non-zero if a power cut was emulated, zero if not. - */ -int ubi_dbg_power_cut(struct ubi_device *ubi, int caller) -{ - unsigned int range; - - if ((ubi->dbg.emulate_power_cut & caller) =3D=3D 0) - return 0; - - if (ubi->dbg.power_cut_counter =3D=3D 0) { - ubi->dbg.power_cut_counter =3D ubi->dbg.power_cut_min; - - if (ubi->dbg.power_cut_max > ubi->dbg.power_cut_min) { - range =3D ubi->dbg.power_cut_max - ubi->dbg.power_cut_min; - ubi->dbg.power_cut_counter +=3D get_random_u32_below(range); - } - return 0; - } - - ubi->dbg.power_cut_counter--; - if (ubi->dbg.power_cut_counter) - return 0; - - ubi_msg(ubi, "XXXXXXXXXXXXXXX emulating a power cut XXXXXXXXXXXXXXXX"); - ubi_ro_mode(ubi); - return 1; -} diff --git a/drivers/mtd/ubi/debug.h b/drivers/mtd/ubi/debug.h index 23676f32b681..bf843433a901 100644 --- a/drivers/mtd/ubi/debug.h +++ b/drivers/mtd/ubi/debug.h @@ -8,6 +8,18 @@ #ifndef __UBI_DEBUG_H__ #define __UBI_DEBUG_H__ =20 +/** + * MASK_XXX: Mask for emulate_failures in ubi_debug_info.The mask is used = to + * precisely control the type and process of fault injection. + */ +/* Emulate bit-flips */ +#define MASK_BITFLIPS (1 << 0) +/* Emulates -EIO during write/erase */ +#define MASK_IO_FAILURE (1 << 1) +/* Emulate a power cut when writing EC/VID header */ +#define MASK_POWER_CUT_EC (1 << 2) +#define MASK_POWER_CUT_VID (1 << 3) + void ubi_dump_flash(struct ubi_device *ubi, int pnum, int offset, int len); void ubi_dump_ec_hdr(const struct ubi_ec_hdr *ec_hdr); void ubi_dump_vid_hdr(const struct ubi_vid_hdr *vid_hdr); @@ -64,46 +76,90 @@ static inline int ubi_dbg_is_bgt_disabled(const struct = ubi_device *ubi) return ubi->dbg.disable_bgt; } =20 +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + +extern bool should_fail_bitflips(void); +extern bool should_fail_io_failures(void); +extern bool should_fail_power_cut(void); + /** * ubi_dbg_is_bitflip - if it is time to emulate a bit-flip. * @ubi: UBI device description object * - * Returns non-zero if a bit-flip should be emulated, otherwise returns ze= ro. + * Returns true if a bit-flip should be emulated, otherwise returns false. */ -static inline int ubi_dbg_is_bitflip(const struct ubi_device *ubi) +static inline bool ubi_dbg_is_bitflip(const struct ubi_device *ubi) { - if (ubi->dbg.emulate_bitflips) - return !get_random_u32_below(200); - return 0; + if (ubi->dbg.emulate_failures & MASK_BITFLIPS) + return should_fail_bitflips(); + return false; } =20 /** * ubi_dbg_is_write_failure - if it is time to emulate a write failure. * @ubi: UBI device description object * - * Returns non-zero if a write failure should be emulated, otherwise retur= ns - * zero. + * Returns true if a write failure should be emulated, otherwise returns + * false. */ -static inline int ubi_dbg_is_write_failure(const struct ubi_device *ubi) +static inline bool ubi_dbg_is_write_failure(const struct ubi_device *ubi) { - if (ubi->dbg.emulate_io_failures) - return !get_random_u32_below(500); - return 0; + if (ubi->dbg.emulate_failures & MASK_IO_FAILURE) + return should_fail_io_failures(); + return false; } =20 /** * ubi_dbg_is_erase_failure - if its time to emulate an erase failure. * @ubi: UBI device description object * - * Returns non-zero if an erase failure should be emulated, otherwise retu= rns - * zero. + * Returns true if an erase failure should be emulated, otherwise returns + * false. */ -static inline int ubi_dbg_is_erase_failure(const struct ubi_device *ubi) +static inline bool ubi_dbg_is_erase_failure(const struct ubi_device *ubi) +{ + if (ubi->dbg.emulate_failures & MASK_IO_FAILURE) + return should_fail_io_failures(); + return false; +} + +/** + * ubi_dbg_power_cut - if it is time to emulate power cut. + * @ubi: UBI device description object + * + * Returns true if power cut should be emulated, otherwise returns false. + */ +static inline bool ubi_dbg_power_cut(const struct ubi_device *ubi, + unsigned int caller) +{ + if (ubi->dbg.emulate_failures & caller) + return should_fail_power_cut(); + return false; +} + +#else /* CONFIG_MTD_UBI_FAULT_INJECTION */ + +static inline bool ubi_dbg_is_bitflip(const struct ubi_device *ubi) +{ + return false; +} + +static inline bool ubi_dbg_is_write_failure(const struct ubi_device *ubi) +{ + return false; +} + +static inline bool ubi_dbg_is_erase_failure(const struct ubi_device *ubi) +{ + return false; +} + +static inline bool ubi_dbg_power_cut(const struct ubi_device *ubi, + unsigned int caller) { - if (ubi->dbg.emulate_io_failures) - return !get_random_u32_below(400); - return 0; + return false; } +#endif =20 static inline int ubi_dbg_chk_io(const struct ubi_device *ubi) { @@ -125,5 +181,4 @@ static inline void ubi_enable_dbg_chk_fastmap(struct ub= i_device *ubi) ubi->dbg.chk_fastmap =3D 1; } =20 -int ubi_dbg_power_cut(struct ubi_device *ubi, int caller); #endif /* !__UBI_DEBUG_H__ */ diff --git a/drivers/mtd/ubi/io.c b/drivers/mtd/ubi/io.c index 01b644861253..906ad0811d52 100644 --- a/drivers/mtd/ubi/io.c +++ b/drivers/mtd/ubi/io.c @@ -821,8 +821,11 @@ int ubi_io_write_ec_hdr(struct ubi_device *ubi, int pn= um, if (err) return err; =20 - if (ubi_dbg_power_cut(ubi, POWER_CUT_EC_WRITE)) + if (ubi_dbg_power_cut(ubi, MASK_POWER_CUT_EC)) { + ubi_warn(ubi, "XXXXX emulating a power cut when writing EC header XXXXX"= ); + ubi_ro_mode(ubi); return -EROFS; + } =20 err =3D ubi_io_write(ubi, ec_hdr, pnum, 0, ubi->ec_hdr_alsize); return err; @@ -1071,8 +1074,11 @@ int ubi_io_write_vid_hdr(struct ubi_device *ubi, int= pnum, if (err) return err; =20 - if (ubi_dbg_power_cut(ubi, POWER_CUT_VID_WRITE)) + if (ubi_dbg_power_cut(ubi, MASK_POWER_CUT_VID)) { + ubi_warn(ubi, "XXXXX emulating a power cut when writing VID header XXXXX= "); + ubi_ro_mode(ubi); return -EROFS; + } =20 err =3D ubi_io_write(ubi, p, pnum, ubi->vid_hdr_aloffset, ubi->vid_hdr_alsize); diff --git a/drivers/mtd/ubi/ubi.h b/drivers/mtd/ubi/ubi.h index c8f1bd4fa100..e20e9a6f9c05 100644 --- a/drivers/mtd/ubi/ubi.h +++ b/drivers/mtd/ubi/ubi.h @@ -142,17 +142,6 @@ enum { UBI_BAD_FASTMAP, }; =20 -/* - * Flags for emulate_power_cut in ubi_debug_info - * - * POWER_CUT_EC_WRITE: Emulate a power cut when writing an EC header - * POWER_CUT_VID_WRITE: Emulate a power cut when writing a VID header - */ -enum { - POWER_CUT_EC_WRITE =3D 0x01, - POWER_CUT_VID_WRITE =3D 0x02, -}; - /** * struct ubi_vid_io_buf - VID buffer used to read/write VID info to/from = the * flash. @@ -395,46 +384,28 @@ struct ubi_volume_desc { * @chk_io: if UBI I/O extra checks are enabled * @chk_fastmap: if UBI fastmap extra checks are enabled * @disable_bgt: disable the background task for testing purposes - * @emulate_bitflips: emulate bit-flips for testing purposes - * @emulate_io_failures: emulate write/erase failures for testing purposes - * @emulate_power_cut: emulate power cut for testing purposes - * @power_cut_counter: count down for writes left until emulated power cut - * @power_cut_min: minimum number of writes before emulating a power cut - * @power_cut_max: maximum number of writes until emulating a power cut + * @emulate_failures: emulate failures for testing purposes * @dfs_dir_name: name of debugfs directory containing files of this UBI d= evice * @dfs_dir: direntry object of the UBI device debugfs directory * @dfs_chk_gen: debugfs knob to enable UBI general extra checks * @dfs_chk_io: debugfs knob to enable UBI I/O extra checks * @dfs_chk_fastmap: debugfs knob to enable UBI fastmap extra checks * @dfs_disable_bgt: debugfs knob to disable the background task - * @dfs_emulate_bitflips: debugfs knob to emulate bit-flips - * @dfs_emulate_io_failures: debugfs knob to emulate write/erase failures - * @dfs_emulate_power_cut: debugfs knob to emulate power cuts - * @dfs_power_cut_min: debugfs knob for minimum writes before power cut - * @dfs_power_cut_max: debugfs knob for maximum writes until power cut + * @dfs_emulate_failures: debugfs entry to control the fault injection type */ struct ubi_debug_info { unsigned int chk_gen:1; unsigned int chk_io:1; unsigned int chk_fastmap:1; unsigned int disable_bgt:1; - unsigned int emulate_bitflips:1; - unsigned int emulate_io_failures:1; - unsigned int emulate_power_cut:2; - unsigned int power_cut_counter; - unsigned int power_cut_min; - unsigned int power_cut_max; + unsigned int emulate_failures; char dfs_dir_name[UBI_DFS_DIR_LEN + 1]; struct dentry *dfs_dir; struct dentry *dfs_chk_gen; struct dentry *dfs_chk_io; struct dentry *dfs_chk_fastmap; struct dentry *dfs_disable_bgt; - struct dentry *dfs_emulate_bitflips; - struct dentry *dfs_emulate_io_failures; - struct dentry *dfs_emulate_power_cut; - struct dentry *dfs_power_cut_min; - struct dentry *dfs_power_cut_max; + struct dentry *dfs_emulate_failures; }; =20 /** --=20 2.31.1 From nobody Wed Feb 11 03:26:03 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 98E74C6FD1D for ; Sat, 18 Mar 2023 01:57:24 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229747AbjCRB5X (ORCPT ); Fri, 17 Mar 2023 21:57:23 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59886 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229533AbjCRB5R (ORCPT ); Fri, 17 Mar 2023 21:57:17 -0400 Received: from szxga02-in.huawei.com (szxga02-in.huawei.com [45.249.212.188]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id BC4444A1E7 for ; Fri, 17 Mar 2023 18:57:15 -0700 (PDT) Received: from dggpemm100009.china.huawei.com (unknown [172.30.72.54]) by szxga02-in.huawei.com (SkyGuard) with ESMTP id 4Pdkb83BqNzHwjF; Sat, 18 Mar 2023 09:55:00 +0800 (CST) Received: from huawei.com (10.175.127.227) by dggpemm100009.china.huawei.com (7.185.36.113) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.21; Sat, 18 Mar 2023 09:57:13 +0800 From: ZhaoLong Wang To: , , CC: , , , , Subject: [PATCH -next 2/5] ubi: Split io_failures into write_failure and erase_failure Date: Sat, 18 Mar 2023 09:56:18 +0800 Message-ID: <20230318015621.1408243-3-wangzhaolong1@huawei.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20230318015621.1408243-1-wangzhaolong1@huawei.com> References: <20230318015621.1408243-1-wangzhaolong1@huawei.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.175.127.227] X-ClientProxiedBy: dggems705-chm.china.huawei.com (10.3.19.182) To dggpemm100009.china.huawei.com (7.185.36.113) X-CFilter-Loop: Reflected Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" The emulate_io_failures debugfs entry controls both write failure and erase failure. This patch split io_failures to write_failure and erase_failure. Signed-off-by: ZhaoLong Wang --- drivers/mtd/ubi/debug.c | 14 +++++++++----- drivers/mtd/ubi/debug.h | 18 ++++++++++-------- 2 files changed, 19 insertions(+), 13 deletions(-) diff --git a/drivers/mtd/ubi/debug.c b/drivers/mtd/ubi/debug.c index 2550522e2cd5..9c92bd59b639 100644 --- a/drivers/mtd/ubi/debug.c +++ b/drivers/mtd/ubi/debug.c @@ -14,7 +14,8 @@ =20 #ifdef CONFIG_MTD_UBI_FAULT_INJECTION static DECLARE_FAULT_ATTR(fault_bitflips_attr); -static DECLARE_FAULT_ATTR(fault_io_failures_attr); +static DECLARE_FAULT_ATTR(fault_write_failure_attr); +static DECLARE_FAULT_ATTR(fault_erase_failure_attr); static DECLARE_FAULT_ATTR(fault_power_cut_attr); =20 #define FAIL_ACTION(name, fault_attr) \ @@ -24,7 +25,8 @@ bool should_fail_##name(void) \ } =20 FAIL_ACTION(bitflips, fault_bitflips_attr) -FAIL_ACTION(io_failures, fault_io_failures_attr) +FAIL_ACTION(write_failure, fault_write_failure_attr) +FAIL_ACTION(erase_failure, fault_erase_failure_attr) FAIL_ACTION(power_cut, fault_power_cut_attr) #endif =20 @@ -246,8 +248,11 @@ static void dfs_create_fault_entry(struct dentry *pare= nt) fault_create_debugfs_attr("emulate_bitflips", dir, &fault_bitflips_attr); =20 - fault_create_debugfs_attr("emulate_io_failures", dir, - &fault_io_failures_attr); + fault_create_debugfs_attr("emulate_write_failure", dir, + &fault_write_failure_attr); + + fault_create_debugfs_attr("emulate_erase_failure", dir, + &fault_erase_failure_attr); =20 fault_create_debugfs_attr("emulate_power_cut", dir, &fault_power_cut_attr); @@ -277,7 +282,6 @@ int ubi_debugfs_init(void) #ifdef CONFIG_MTD_UBI_FAULT_INJECTION dfs_create_fault_entry(dfs_rootdir); #endif - return 0; } =20 diff --git a/drivers/mtd/ubi/debug.h b/drivers/mtd/ubi/debug.h index bf843433a901..2486fcab4205 100644 --- a/drivers/mtd/ubi/debug.h +++ b/drivers/mtd/ubi/debug.h @@ -15,10 +15,11 @@ /* Emulate bit-flips */ #define MASK_BITFLIPS (1 << 0) /* Emulates -EIO during write/erase */ -#define MASK_IO_FAILURE (1 << 1) +#define MASK_WRITE_FAILURE (1 << 1) +#define MASK_ERASE_FAILURE (1 << 2) /* Emulate a power cut when writing EC/VID header */ -#define MASK_POWER_CUT_EC (1 << 2) -#define MASK_POWER_CUT_VID (1 << 3) +#define MASK_POWER_CUT_EC (1 << 3) +#define MASK_POWER_CUT_VID (1 << 4) =20 void ubi_dump_flash(struct ubi_device *ubi, int pnum, int offset, int len); void ubi_dump_ec_hdr(const struct ubi_ec_hdr *ec_hdr); @@ -79,7 +80,8 @@ static inline int ubi_dbg_is_bgt_disabled(const struct ub= i_device *ubi) #ifdef CONFIG_MTD_UBI_FAULT_INJECTION =20 extern bool should_fail_bitflips(void); -extern bool should_fail_io_failures(void); +extern bool should_fail_write_failure(void); +extern bool should_fail_erase_failure(void); extern bool should_fail_power_cut(void); =20 /** @@ -104,8 +106,8 @@ static inline bool ubi_dbg_is_bitflip(const struct ubi_= device *ubi) */ static inline bool ubi_dbg_is_write_failure(const struct ubi_device *ubi) { - if (ubi->dbg.emulate_failures & MASK_IO_FAILURE) - return should_fail_io_failures(); + if (ubi->dbg.emulate_failures & MASK_WRITE_FAILURE) + return should_fail_write_failure(); return false; } =20 @@ -118,8 +120,8 @@ static inline bool ubi_dbg_is_write_failure(const struc= t ubi_device *ubi) */ static inline bool ubi_dbg_is_erase_failure(const struct ubi_device *ubi) { - if (ubi->dbg.emulate_failures & MASK_IO_FAILURE) - return should_fail_io_failures(); + if (ubi->dbg.emulate_failures & MASK_ERASE_FAILURE) + return should_fail_erase_failure(); return false; } =20 --=20 2.31.1 From nobody Wed Feb 11 03:26:03 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id E6D69C6FD1D for ; Sat, 18 Mar 2023 01:57:34 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230001AbjCRB5c (ORCPT ); Fri, 17 Mar 2023 21:57:32 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59896 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229816AbjCRB5T (ORCPT ); Fri, 17 Mar 2023 21:57:19 -0400 Received: from szxga01-in.huawei.com (szxga01-in.huawei.com [45.249.212.187]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 751D14A1F4 for ; Fri, 17 Mar 2023 18:57:16 -0700 (PDT) Received: from dggpemm100009.china.huawei.com (unknown [172.30.72.54]) by szxga01-in.huawei.com (SkyGuard) with ESMTP id 4PdkZF03kRznXgF; Sat, 18 Mar 2023 09:54:12 +0800 (CST) Received: from huawei.com (10.175.127.227) by dggpemm100009.china.huawei.com (7.185.36.113) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.21; Sat, 18 Mar 2023 09:57:13 +0800 From: ZhaoLong Wang To: , , CC: , , , , Subject: [PATCH -next 3/5] ubi: Add six fault injection type for testing Date: Sat, 18 Mar 2023 09:56:19 +0800 Message-ID: <20230318015621.1408243-4-wangzhaolong1@huawei.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20230318015621.1408243-1-wangzhaolong1@huawei.com> References: <20230318015621.1408243-1-wangzhaolong1@huawei.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.175.127.227] X-ClientProxiedBy: dggems705-chm.china.huawei.com (10.3.19.182) To dggpemm100009.china.huawei.com (7.185.36.113) X-CFilter-Loop: Reflected Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" This commit adds six fault injection type for testing to cover the abnormal path of the UBI driver. Inject the following faults when the UBI reads the LEB: +----------------------------+-----------------------------------+ | Interface name | emulate behavior | +----------------------------+-----------------------------------+ | emulate_eccerr | ECC error | +----------------------------+-----------------------------------+ | emulate_read_failure | read failure | |----------------------------+-----------------------------------+ | emulate_io_ff | read content as all FF | |----------------------------+-----------------------------------+ | emulate_io_ff_bitflips | content FF with MTD err reported | +----------------------------+-----------------------------------+ | emulate_bad_hdr | bad leb header | |----------------------------+-----------------------------------+ | emulate_bad_hdr_ebadmsg | bad header with ECC err | +----------------------------+-----------------------------------+ Signed-off-by: ZhaoLong Wang --- drivers/mtd/ubi/debug.c | 30 ++++++++++ drivers/mtd/ubi/debug.h | 123 +++++++++++++++++++++++++++++++++++----- drivers/mtd/ubi/io.c | 91 +++++++++++++++++++++++++---- drivers/mtd/ubi/ubi.h | 31 ++++++---- 4 files changed, 240 insertions(+), 35 deletions(-) diff --git a/drivers/mtd/ubi/debug.c b/drivers/mtd/ubi/debug.c index 9c92bd59b639..0c58cbabe9fc 100644 --- a/drivers/mtd/ubi/debug.c +++ b/drivers/mtd/ubi/debug.c @@ -13,10 +13,16 @@ #include =20 #ifdef CONFIG_MTD_UBI_FAULT_INJECTION +static DECLARE_FAULT_ATTR(fault_eccerr_attr); static DECLARE_FAULT_ATTR(fault_bitflips_attr); +static DECLARE_FAULT_ATTR(fault_read_failure_attr); static DECLARE_FAULT_ATTR(fault_write_failure_attr); static DECLARE_FAULT_ATTR(fault_erase_failure_attr); static DECLARE_FAULT_ATTR(fault_power_cut_attr); +static DECLARE_FAULT_ATTR(fault_io_ff_attr); +static DECLARE_FAULT_ATTR(fault_io_ff_bitflips_attr); +static DECLARE_FAULT_ATTR(fault_bad_hdr_attr); +static DECLARE_FAULT_ATTR(fault_bad_hdr_ebadmsg_attr); =20 #define FAIL_ACTION(name, fault_attr) \ bool should_fail_##name(void) \ @@ -24,10 +30,16 @@ bool should_fail_##name(void) \ return should_fail(&fault_attr, 1); \ } =20 +FAIL_ACTION(eccerr, fault_eccerr_attr) FAIL_ACTION(bitflips, fault_bitflips_attr) +FAIL_ACTION(read_failure, fault_read_failure_attr) FAIL_ACTION(write_failure, fault_write_failure_attr) FAIL_ACTION(erase_failure, fault_erase_failure_attr) FAIL_ACTION(power_cut, fault_power_cut_attr) +FAIL_ACTION(io_ff, fault_io_ff_attr) +FAIL_ACTION(io_ff_bitflips, fault_io_ff_bitflips_attr) +FAIL_ACTION(bad_hdr, fault_bad_hdr_attr) +FAIL_ACTION(bad_hdr_ebadmsg, fault_bad_hdr_ebadmsg_attr) #endif =20 =20 @@ -245,9 +257,15 @@ static void dfs_create_fault_entry(struct dentry *pare= nt) return; } =20 + fault_create_debugfs_attr("emulate_eccerr", dir, + &fault_eccerr_attr); + fault_create_debugfs_attr("emulate_bitflips", dir, &fault_bitflips_attr); =20 + fault_create_debugfs_attr("emulate_read_failure", dir, + &fault_read_failure_attr); + fault_create_debugfs_attr("emulate_write_failure", dir, &fault_write_failure_attr); =20 @@ -256,6 +274,18 @@ static void dfs_create_fault_entry(struct dentry *pare= nt) =20 fault_create_debugfs_attr("emulate_power_cut", dir, &fault_power_cut_attr); + + fault_create_debugfs_attr("emulate_io_ff", dir, + &fault_io_ff_attr); + + fault_create_debugfs_attr("emulate_io_ff_bitflips", dir, + &fault_io_ff_bitflips_attr); + + fault_create_debugfs_attr("emulate_bad_hdr", dir, + &fault_bad_hdr_attr); + + fault_create_debugfs_attr("emulate_bad_hdr_ebadmsg", dir, + &fault_bad_hdr_ebadmsg_attr); } #endif =20 diff --git a/drivers/mtd/ubi/debug.h b/drivers/mtd/ubi/debug.h index 2486fcab4205..8272c2b93dd4 100644 --- a/drivers/mtd/ubi/debug.h +++ b/drivers/mtd/ubi/debug.h @@ -13,13 +13,34 @@ * precisely control the type and process of fault injection. */ /* Emulate bit-flips */ -#define MASK_BITFLIPS (1 << 0) -/* Emulates -EIO during write/erase */ -#define MASK_WRITE_FAILURE (1 << 1) -#define MASK_ERASE_FAILURE (1 << 2) +#define MASK_BITFLIPS (1 << 0) +/* Emulate ecc error */ +#define MASK_ECCERR (1 << 1) +/* Emulates -EIO during data read */ +#define MASK_READ_FAILURE (1 << 2) +#define MASK_READ_FAILURE_EC (1 << 3) +#define MASK_READ_FAILURE_VID (1 << 4) +/* Emulates -EIO during data write */ +#define MASK_WRITE_FAILURE (1 << 5) +/* Emulates -EIO during erase a PEB*/ +#define MASK_ERASE_FAILURE (1 << 6) /* Emulate a power cut when writing EC/VID header */ -#define MASK_POWER_CUT_EC (1 << 3) -#define MASK_POWER_CUT_VID (1 << 4) +#define MASK_POWER_CUT_EC (1 << 7) +#define MASK_POWER_CUT_VID (1 << 8) +/* Emulate a power cut when writing data*/ +#define MASK_POWER_CUT_DATA (1 << 9) +/* Return UBI_IO_FF when reading EC/VID header */ +#define MASK_IO_FF_EC (1 << 10) +#define MASK_IO_FF_VID (1 << 11) +/* Return UBI_IO_FF_BITFLIPS when reading EC/VID header */ +#define MASK_IO_FF_BITFLIPS_EC (1 << 12) +#define MASK_IO_FF_BITFLIPS_VID (1 << 13) +/* Return UBI_IO_BAD_HDR when reading EC/VID header */ +#define MASK_BAD_HDR_EC (1 << 14) +#define MASK_BAD_HDR_VID (1 << 15) +/* Return UBI_IO_BAD_HDR_EBADMSG when reading EC/VID header */ +#define MASK_BAD_HDR_EBADMSG_EC (1 << 16) +#define MASK_BAD_HDR_EBADMSG_VID (1 << 17) =20 void ubi_dump_flash(struct ubi_device *ubi, int pnum, int offset, int len); void ubi_dump_ec_hdr(const struct ubi_ec_hdr *ec_hdr); @@ -79,10 +100,16 @@ static inline int ubi_dbg_is_bgt_disabled(const struct= ubi_device *ubi) =20 #ifdef CONFIG_MTD_UBI_FAULT_INJECTION =20 +extern bool should_fail_eccerr(void); extern bool should_fail_bitflips(void); +extern bool should_fail_read_failure(void); extern bool should_fail_write_failure(void); extern bool should_fail_erase_failure(void); extern bool should_fail_power_cut(void); +extern bool should_fail_io_ff(void); +extern bool should_fail_io_ff_bitflips(void); +extern bool should_fail_bad_hdr(void); +extern bool should_fail_bad_hdr_ebadmsg(void); =20 /** * ubi_dbg_is_bitflip - if it is time to emulate a bit-flip. @@ -97,6 +124,34 @@ static inline bool ubi_dbg_is_bitflip(const struct ubi_= device *ubi) return false; } =20 +/** + * ubi_dbg_is_eccerr - if it is time to emulate ECC error. + * @ubi: UBI device description object + * + * Returns true if a ECC error should be emulated, otherwise returns false. + */ +static inline bool ubi_dbg_is_eccerr(const struct ubi_device *ubi) +{ + if (ubi->dbg.emulate_failures & MASK_ECCERR) + return should_fail_eccerr(); + return false; +} + +/** + * ubi_dbg_is_read_failure - if it is time to emulate a read failure. + * @ubi: UBI device description object + * + * Returns true if a read failure should be emulated, otherwise returns + * false. + */ +static inline bool ubi_dbg_is_read_failure(const struct ubi_device *ubi, + unsigned int caller) +{ + if (ubi->dbg.emulate_failures & caller) + return should_fail_read_failure(); + return false; +} + /** * ubi_dbg_is_write_failure - if it is time to emulate a write failure. * @ubi: UBI device description object @@ -139,28 +194,70 @@ static inline bool ubi_dbg_power_cut(const struct ubi= _device *ubi, return false; } =20 -#else /* CONFIG_MTD_UBI_FAULT_INJECTION */ - -static inline bool ubi_dbg_is_bitflip(const struct ubi_device *ubi) +/** + * ubi_dbg_is_ff - if it is time to emulate that read region is only 0xFF. + * @ubi: UBI device description object + * + * Returns true if read region should be emulated 0xFF, otherwise + * returns false. + */ +static inline bool ubi_dbg_is_ff(const struct ubi_device *ubi, + unsigned int caller) { + if (ubi->dbg.emulate_failures & caller) + return should_fail_io_ff(); return false; } =20 -static inline bool ubi_dbg_is_write_failure(const struct ubi_device *ubi) +/** + * ubi_dbg_is_ff_bitflips - if it is time to emulate that read region is o= nly 0xFF + * with error reported by the MTD driver + * + * @ubi: UBI device description object + * + * Returns true if read region should be emulated 0xFF and error + * reported by the MTD driver, otherwise returns false. + */ +static inline bool ubi_dbg_is_ff_bitflips(const struct ubi_device *ubi, + unsigned int caller) { + if (ubi->dbg.emulate_failures & caller) + return should_fail_io_ff_bitflips(); return false; } =20 -static inline bool ubi_dbg_is_erase_failure(const struct ubi_device *ubi) +/** + * ubi_dbg_is_bad_hdr - if it is time to emulate a bad header + * @ubi: UBI device description object + * + * Returns true if a bad header error should be emulated, otherwise + * returns false. + */ +static inline bool ubi_dbg_is_bad_hdr(const struct ubi_device *ubi, + unsigned int caller) { + if (ubi->dbg.emulate_failures & caller) + return should_fail_bad_hdr(); return false; } =20 -static inline bool ubi_dbg_power_cut(const struct ubi_device *ubi, - unsigned int caller) +/** + * ubi_dbg_is_bad_hdr_ebadmsg - if it is time to emulate a bad header with + * ECC error. + * + * @ubi: UBI device description object + * + * Returns true if a bad header with ECC error should be emulated, otherwi= se + * returns false. + */ +static inline bool ubi_dbg_is_bad_hdr_ebadmsg(const struct ubi_device *ubi, + unsigned int caller) { + if (ubi->dbg.emulate_failures & caller) + return should_fail_bad_hdr_ebadmsg(); return false; } + #endif =20 static inline int ubi_dbg_chk_io(const struct ubi_device *ubi) diff --git a/drivers/mtd/ubi/io.c b/drivers/mtd/ubi/io.c index 906ad0811d52..e64914c3cc8d 100644 --- a/drivers/mtd/ubi/io.c +++ b/drivers/mtd/ubi/io.c @@ -192,11 +192,24 @@ int ubi_io_read(const struct ubi_device *ubi, void *b= uf, int pnum, int offset, } } else { ubi_assert(len =3D=3D read); +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + if (ubi_dbg_is_read_failure(ubi, MASK_READ_FAILURE)) { + ubi_warn(ubi, "cannot read %d bytes from PEB %d:%d (emulated)", + len, pnum, offset); + return -EIO; + } + + if (ubi_dbg_is_eccerr(ubi)) { + ubi_warn(ubi, "ECC error (emulated) while reading %d bytes from PEB %d:= %d, read %zd bytes", + len, pnum, offset, read); + return -EBADMSG; + } =20 if (ubi_dbg_is_bitflip(ubi)) { dbg_gen("bit-flip (emulated)"); err =3D UBI_IO_BITFLIPS; } +#endif } =20 return err; @@ -259,14 +272,14 @@ int ubi_io_write(struct ubi_device *ubi, const void *= buf, int pnum, int offset, if (err) return err; } - +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION if (ubi_dbg_is_write_failure(ubi)) { ubi_err(ubi, "cannot write %d bytes to PEB %d:%d (emulated)", len, pnum, offset); dump_stack(); return -EIO; } - +#endif addr =3D (loff_t)pnum * ubi->peb_size + offset; err =3D mtd_write(ubi->mtd, addr, len, &written, buf); if (err) { @@ -339,12 +352,12 @@ static int do_sync_erase(struct ubi_device *ubi, int = pnum) err =3D ubi_self_check_all_ff(ubi, pnum, 0, ubi->peb_size); if (err) return err; - +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION if (ubi_dbg_is_erase_failure(ubi)) { ubi_err(ubi, "cannot erase PEB %d (emulated)", pnum); return -EIO; } - +#endif return 0; } =20 @@ -782,7 +795,36 @@ int ubi_io_read_ec_hdr(struct ubi_device *ubi, int pnu= m, * If there was %-EBADMSG, but the header CRC is still OK, report about * a bit-flip to force scrubbing on this PEB. */ - return read_err ? UBI_IO_BITFLIPS : 0; + if (read_err) + return UBI_IO_BITFLIPS; +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + if (ubi_dbg_is_read_failure(ubi, MASK_READ_FAILURE_EC)) { + ubi_warn(ubi, "cannot read EC header from PEB %d(emulated)", + pnum); + return -EIO; + } + + if (ubi_dbg_is_ff(ubi, MASK_IO_FF_EC)) { + ubi_warn(ubi, "bit-all-ff (emulated)"); + return UBI_IO_FF; + } + + if (ubi_dbg_is_ff_bitflips(ubi, MASK_IO_FF_BITFLIPS_EC)) { + ubi_warn(ubi, "bit-all-ff with error reported by MTD driver (emulated)"); + return UBI_IO_FF_BITFLIPS; + } + + if (ubi_dbg_is_bad_hdr(ubi, MASK_BAD_HDR_EC)) { + ubi_warn(ubi, "bad_hdr (emulated)"); + return UBI_IO_BAD_HDR; + } + + if (ubi_dbg_is_bad_hdr_ebadmsg(ubi, MASK_BAD_HDR_EBADMSG_EC)) { + ubi_warn(ubi, "bad_hdr with ECC error (emulated)"); + return UBI_IO_BAD_HDR_EBADMSG; + } +#endif + return 0; } =20 /** @@ -820,13 +862,13 @@ int ubi_io_write_ec_hdr(struct ubi_device *ubi, int p= num, err =3D self_check_ec_hdr(ubi, pnum, ec_hdr); if (err) return err; - +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION if (ubi_dbg_power_cut(ubi, MASK_POWER_CUT_EC)) { ubi_warn(ubi, "XXXXX emulating a power cut when writing EC header XXXXX"= ); ubi_ro_mode(ubi); return -EROFS; } - +#endif err =3D ubi_io_write(ubi, ec_hdr, pnum, 0, ubi->ec_hdr_alsize); return err; } @@ -1032,7 +1074,36 @@ int ubi_io_read_vid_hdr(struct ubi_device *ubi, int = pnum, return -EINVAL; } =20 - return read_err ? UBI_IO_BITFLIPS : 0; + if (read_err) + return UBI_IO_BITFLIPS; +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + if (ubi_dbg_is_read_failure(ubi, MASK_READ_FAILURE_VID)) { + ubi_warn(ubi, "cannot read VID header from PEB %d(emulated)", + pnum); + return -EIO; + } + + if (ubi_dbg_is_ff(ubi, MASK_IO_FF_VID)) { + ubi_warn(ubi, "bit-all-ff (emulated)\n"); + return UBI_IO_FF; + } + + if (ubi_dbg_is_ff_bitflips(ubi, MASK_IO_FF_BITFLIPS_VID)) { + ubi_warn(ubi, "bit-all-ff with error reported by MTD driver (emulated)\n= "); + return UBI_IO_FF_BITFLIPS; + } + + if (ubi_dbg_is_bad_hdr(ubi, MASK_BAD_HDR_VID)) { + ubi_warn(ubi, "bad_hdr (emulated)\n"); + return UBI_IO_BAD_HDR; + } + + if (ubi_dbg_is_bad_hdr_ebadmsg(ubi, MASK_BAD_HDR_EBADMSG_VID)) { + ubi_warn(ubi, "bad_hdr with ECC error (emulated)\n"); + return UBI_IO_BAD_HDR_EBADMSG; + } +#endif + return 0; } =20 /** @@ -1073,13 +1144,13 @@ int ubi_io_write_vid_hdr(struct ubi_device *ubi, in= t pnum, err =3D self_check_vid_hdr(ubi, pnum, vid_hdr); if (err) return err; - +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION if (ubi_dbg_power_cut(ubi, MASK_POWER_CUT_VID)) { ubi_warn(ubi, "XXXXX emulating a power cut when writing VID header XXXXX= "); ubi_ro_mode(ubi); return -EROFS; } - +#endif err =3D ubi_io_write(ubi, p, pnum, ubi->vid_hdr_aloffset, ubi->vid_hdr_alsize); return err; diff --git a/drivers/mtd/ubi/ubi.h b/drivers/mtd/ubi/ubi.h index e20e9a6f9c05..7ff55a74b313 100644 --- a/drivers/mtd/ubi/ubi.h +++ b/drivers/mtd/ubi/ubi.h @@ -1107,18 +1107,6 @@ static inline int ubi_io_read_data(const struct ubi_= device *ubi, void *buf, return ubi_io_read(ubi, buf, pnum, offset + ubi->leb_start, len); } =20 -/* - * This function is equivalent to 'ubi_io_write()', but @offset is relativ= e to - * the beginning of the logical eraseblock, not to the beginning of the - * physical eraseblock. - */ -static inline int ubi_io_write_data(struct ubi_device *ubi, const void *bu= f, - int pnum, int offset, int len) -{ - ubi_assert(offset >=3D 0); - return ubi_io_write(ubi, buf, pnum, offset + ubi->leb_start, len); -} - /** * ubi_ro_mode - switch to read-only mode. * @ubi: UBI device description object @@ -1132,6 +1120,25 @@ static inline void ubi_ro_mode(struct ubi_device *ub= i) } } =20 +/* + * This function is equivalent to 'ubi_io_write()', but @offset is relativ= e to + * the beginning of the logical eraseblock, not to the beginning of the + * physical eraseblock. + */ +static inline int ubi_io_write_data(struct ubi_device *ubi, const void *bu= f, + int pnum, int offset, int len) +{ + ubi_assert(offset >=3D 0); +#ifdef CONFIG_MTD_UBI_FAULT_INJECTION + if (ubi_dbg_power_cut(ubi, MASK_POWER_CUT_DATA)) { + ubi_warn(ubi, "XXXXX emulating a power cut when writing data XXXXX"); + ubi_ro_mode(ubi); + return -EROFS; + } +#endif + return ubi_io_write(ubi, buf, pnum, offset + ubi->leb_start, len); +} + /** * vol_id2idx - get table index by volume ID. * @ubi: UBI device description object --=20 2.31.1 From nobody Wed Feb 11 03:26:03 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id F232EC74A5B for ; Sat, 18 Mar 2023 01:57:28 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229942AbjCRB50 (ORCPT ); Fri, 17 Mar 2023 21:57:26 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59902 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229794AbjCRB5S (ORCPT ); Fri, 17 Mar 2023 21:57:18 -0400 Received: from szxga01-in.huawei.com (szxga01-in.huawei.com [45.249.212.187]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 797C64AD2C for ; Fri, 17 Mar 2023 18:57:16 -0700 (PDT) Received: from dggpemm100009.china.huawei.com (unknown [172.30.72.56]) by szxga01-in.huawei.com (SkyGuard) with ESMTP id 4PdkZF38LlznXgR; Sat, 18 Mar 2023 09:54:13 +0800 (CST) Received: from huawei.com (10.175.127.227) by dggpemm100009.china.huawei.com (7.185.36.113) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.21; Sat, 18 Mar 2023 09:57:14 +0800 From: ZhaoLong Wang To: , , CC: , , , , Subject: [PATCH -next 4/5] ubi: Reserve sufficient buffer length for the input mask Date: Sat, 18 Mar 2023 09:56:20 +0800 Message-ID: <20230318015621.1408243-5-wangzhaolong1@huawei.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20230318015621.1408243-1-wangzhaolong1@huawei.com> References: <20230318015621.1408243-1-wangzhaolong1@huawei.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.175.127.227] X-ClientProxiedBy: dggems705-chm.china.huawei.com (10.3.19.182) To dggpemm100009.china.huawei.com (7.185.36.113) X-CFilter-Loop: Reflected Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" Because the mask received by the emulate_failures interface is a 32-bit unsigned integer, ensure that there is sufficient buffer length to receive and display this value. Signed-off-by: ZhaoLong Wang --- drivers/mtd/ubi/debug.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/mtd/ubi/debug.c b/drivers/mtd/ubi/debug.c index 0c58cbabe9fc..eafeb10e57bf 100644 --- a/drivers/mtd/ubi/debug.c +++ b/drivers/mtd/ubi/debug.c @@ -332,7 +332,7 @@ static ssize_t dfs_file_read(struct file *file, char __= user *user_buf, struct dentry *dent =3D file->f_path.dentry; struct ubi_device *ubi; struct ubi_debug_info *d; - char buf[8]; + char buf[12]; int val; =20 ubi =3D ubi_get_device(ubi_num); @@ -381,7 +381,7 @@ static ssize_t dfs_file_write(struct file *file, const = char __user *user_buf, struct ubi_device *ubi; struct ubi_debug_info *d; size_t buf_size; - char buf[8] =3D {0}; + char buf[14] =3D {0}; int val; =20 ubi =3D ubi_get_device(ubi_num); --=20 2.31.1 From nobody Wed Feb 11 03:26:03 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id CF0A2C74A5B for ; Sat, 18 Mar 2023 01:57:31 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229962AbjCRB53 (ORCPT ); Fri, 17 Mar 2023 21:57:29 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59904 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229788AbjCRB5S (ORCPT ); Fri, 17 Mar 2023 21:57:18 -0400 Received: from szxga01-in.huawei.com (szxga01-in.huawei.com [45.249.212.187]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 1BB164AD2F for ; Fri, 17 Mar 2023 18:57:17 -0700 (PDT) Received: from dggpemm100009.china.huawei.com (unknown [172.30.72.53]) by szxga01-in.huawei.com (SkyGuard) with ESMTP id 4Pdkcf5SWjzrTNt; Sat, 18 Mar 2023 09:56:18 +0800 (CST) Received: from huawei.com (10.175.127.227) by dggpemm100009.china.huawei.com (7.185.36.113) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.21; Sat, 18 Mar 2023 09:57:14 +0800 From: ZhaoLong Wang To: , , CC: , , , , Subject: [PATCH -next 5/5] mtd: Add several functions to the fail_function list Date: Sat, 18 Mar 2023 09:56:21 +0800 Message-ID: <20230318015621.1408243-6-wangzhaolong1@huawei.com> X-Mailer: git-send-email 2.31.1 In-Reply-To: <20230318015621.1408243-1-wangzhaolong1@huawei.com> References: <20230318015621.1408243-1-wangzhaolong1@huawei.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.175.127.227] X-ClientProxiedBy: dggems705-chm.china.huawei.com (10.3.19.182) To dggpemm100009.china.huawei.com (7.185.36.113) X-CFilter-Loop: Reflected Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" add mtd_read(), mtd_write(), mtd_erase(), mtd_block_markbad() to fail_function list for testing purpose Signed-off-by: ZhaoLong Wang --- drivers/mtd/mtdcore.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c index 0feacb9fbdac..58558088d44e 100644 --- a/drivers/mtd/mtdcore.c +++ b/drivers/mtd/mtdcore.c @@ -29,6 +29,7 @@ #include #include #include +#include =20 #include #include @@ -1371,6 +1372,7 @@ int mtd_erase(struct mtd_info *mtd, struct erase_info= *instr) return ret; } EXPORT_SYMBOL_GPL(mtd_erase); +ALLOW_ERROR_INJECTION(mtd_erase, ERRNO); =20 /* * This stuff for eXecute-In-Place. phys is optional and may be set to NUL= L. @@ -1468,6 +1470,7 @@ int mtd_read(struct mtd_info *mtd, loff_t from, size_= t len, size_t *retlen, return ret; } EXPORT_SYMBOL_GPL(mtd_read); +ALLOW_ERROR_INJECTION(mtd_read, ERRNO); =20 int mtd_write(struct mtd_info *mtd, loff_t to, size_t len, size_t *retlen, const u_char *buf) @@ -1484,6 +1487,7 @@ int mtd_write(struct mtd_info *mtd, loff_t to, size_t= len, size_t *retlen, return ret; } EXPORT_SYMBOL_GPL(mtd_write); +ALLOW_ERROR_INJECTION(mtd_write, ERRNO); =20 /* * In blackbox flight recorder like scenarios we want to make successful w= rites @@ -2304,7 +2308,7 @@ int mtd_block_markbad(struct mtd_info *mtd, loff_t of= s) return 0; } EXPORT_SYMBOL_GPL(mtd_block_markbad); - +ALLOW_ERROR_INJECTION(mtd_block_markbad, ERRNO); /* * default_mtd_writev - the default writev method * @mtd: mtd device description object pointer --=20 2.31.1