From a2c2690f0d747c973c6a384ab8cd88faa806e5a5 Mon Sep 17 00:00:00 2001 From: Christophe JAILLET Date: Sun, 16 Apr 2023 11:16:36 +0200 Subject: mtd: st_spi_fsm: Use the devm_clk_get_enabled() helper function Use the devm_clk_get_enabled() helper function instead of hand-writing it. It saves some line of codes. Signed-off-by: Christophe JAILLET Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/4025ec3980a956b0e776024e88ec960afc457501.1681636580.git.christophe.jaillet@wanadoo.fr --- drivers/mtd/devices/st_spi_fsm.c | 28 ++++++---------------------- 1 file changed, 6 insertions(+), 22 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/devices/st_spi_fsm.c b/drivers/mtd/devices/st_spi_fsm.c index 54861d889c30..3dbb1aa80bfa 100644 --- a/drivers/mtd/devices/st_spi_fsm.c +++ b/drivers/mtd/devices/st_spi_fsm.c @@ -2046,34 +2046,26 @@ static int stfsm_probe(struct platform_device *pdev) return PTR_ERR(fsm->base); } - fsm->clk = devm_clk_get(&pdev->dev, NULL); + fsm->clk = devm_clk_get_enabled(&pdev->dev, NULL); if (IS_ERR(fsm->clk)) { dev_err(fsm->dev, "Couldn't find EMI clock.\n"); return PTR_ERR(fsm->clk); } - ret = clk_prepare_enable(fsm->clk); - if (ret) { - dev_err(fsm->dev, "Failed to enable EMI clock.\n"); - return ret; - } - mutex_init(&fsm->lock); ret = stfsm_init(fsm); if (ret) { dev_err(&pdev->dev, "Failed to initialise FSM Controller\n"); - goto err_clk_unprepare; + return ret; } stfsm_fetch_platform_configs(pdev); /* Detect SPI FLASH device */ info = stfsm_jedec_probe(fsm); - if (!info) { - ret = -ENODEV; - goto err_clk_unprepare; - } + if (!info) + return -ENODEV; fsm->info = info; /* Use device size to determine address width */ @@ -2089,7 +2081,7 @@ static int stfsm_probe(struct platform_device *pdev) else ret = stfsm_prepare_rwe_seqs_default(fsm); if (ret) - goto err_clk_unprepare; + return ret; fsm->mtd.name = info->name; fsm->mtd.dev.parent = &pdev->dev; @@ -2112,13 +2104,7 @@ static int stfsm_probe(struct platform_device *pdev) (long long)fsm->mtd.size, (long long)(fsm->mtd.size >> 20), fsm->mtd.erasesize, (fsm->mtd.erasesize >> 10)); - ret = mtd_device_register(&fsm->mtd, NULL, 0); - if (ret) { -err_clk_unprepare: - clk_disable_unprepare(fsm->clk); - } - - return ret; + return mtd_device_register(&fsm->mtd, NULL, 0); } static int stfsm_remove(struct platform_device *pdev) @@ -2127,8 +2113,6 @@ static int stfsm_remove(struct platform_device *pdev) WARN_ON(mtd_device_unregister(&fsm->mtd)); - clk_disable_unprepare(fsm->clk); - return 0; } -- cgit v1.2.3 From ef1560b670bd28ca3230c7f5ad29c6a211fb1adb Mon Sep 17 00:00:00 2001 From: Md Sadre Alam Date: Thu, 25 May 2023 16:35:26 +0530 Subject: mtd: spinand: gigadevice: add support for GD5F2GQ5xExxH This is 2Gb SLC NAND flash with 4b/512b on-die ECC capability. Signed-off-by: Md Sadre Alam Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230525110526.21998-1-quic_mdalam@quicinc.com --- drivers/mtd/nand/spi/gigadevice.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/spi/gigadevice.c b/drivers/mtd/nand/spi/gigadevice.c index 6b043e24855f..cfd7c3b26dc4 100644 --- a/drivers/mtd/nand/spi/gigadevice.c +++ b/drivers/mtd/nand/spi/gigadevice.c @@ -501,6 +501,16 @@ static const struct spinand_info gigadevice_spinand_table[] = { SPINAND_HAS_QE_BIT, SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout, gd5fxgq4uexxg_ecc_get_status)), + SPINAND_INFO("GD5F2GQ5xExxH", + SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x22), + NAND_MEMORG(1, 2048, 64, 64, 2048, 40, 1, 1, 1), + NAND_ECCREQ(4, 512), + SPINAND_INFO_OP_VARIANTS(&read_cache_variants_2gq5, + &write_cache_variants, + &update_cache_variants), + SPINAND_HAS_QE_BIT, + SPINAND_ECCINFO(&gd5fxgqx_variant2_ooblayout, + gd5fxgq4uexxg_ecc_get_status)), }; static const struct spinand_manufacturer_ops gigadevice_spinand_manuf_ops = { -- cgit v1.2.3 From 21962132044653f42ff8bbb37127c2557d6c39c2 Mon Sep 17 00:00:00 2001 From: Amit Kumar Mahapatra Date: Wed, 7 Jun 2023 11:09:36 +0530 Subject: Revert "mtd: rawnand: arasan: Prevent an unsupported configuration" This reverts commit fc9e18f9e987ad46722dad53adab1c12148c213c. This patch was a work around to fix timeout issue while operating in NVDDR mode with software ECC engine. This patch prevents the Arasan NAND driver from operating in NVDDR mode with software ECC engine resulting in a significant performance degradation with SW-ECC. 'commit 7499bfeedb47 ("mtd: rawnand: arasan: Update NAND bus clock instead of system clock")' and 'commit e16eceea863b ("mtd: rawnand: arasan: Fix clock rate in NV-DDR")' fixes the timeout issue in NVDDR mode with SW-ECC so, reverting the changes as this work around is no longer required. Signed-off-by: Amit Kumar Mahapatra Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230607053936.14306-1-amit.kumar-mahapatra@amd.com --- drivers/mtd/nand/raw/arasan-nand-controller.c | 15 --------------- 1 file changed, 15 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/arasan-nand-controller.c b/drivers/mtd/nand/raw/arasan-nand-controller.c index d513d2db3549..906eef70cb6d 100644 --- a/drivers/mtd/nand/raw/arasan-nand-controller.c +++ b/drivers/mtd/nand/raw/arasan-nand-controller.c @@ -973,21 +973,6 @@ static int anfc_setup_interface(struct nand_chip *chip, int target, nvddr = nand_get_nvddr_timings(conf); if (IS_ERR(nvddr)) return PTR_ERR(nvddr); - - /* - * The controller only supports data payload requests which are - * a multiple of 4. In practice, most data accesses are 4-byte - * aligned and this is not an issue. However, rounding up will - * simply be refused by the controller if we reached the end of - * the device *and* we are using the NV-DDR interface(!). In - * this situation, unaligned data requests ending at the device - * boundary will confuse the controller and cannot be performed. - * - * This is something that happens in nand_read_subpage() when - * selecting software ECC support and must be avoided. - */ - if (chip->ecc.engine_type == NAND_ECC_ENGINE_TYPE_SOFT) - return -ENOTSUPP; } else { sdr = nand_get_sdr_timings(conf); if (IS_ERR(sdr)) -- cgit v1.2.3 From 30540a0d05d85ef7e6f740e62c3b44c87396e56c Mon Sep 17 00:00:00 2001 From: Arseniy Krasnov Date: Thu, 8 Jun 2023 07:36:44 +0300 Subject: mtd: rawnand: meson: replace integer consts with proper defines Add defines for column address. It makes driver more readable, because bitwise OR with 0 looks useless. Suggested-by: Liang Yang Signed-off-by: Arseniy Krasnov Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230608043644.1271186-1-AVKrasnov@sberdevices.ru --- drivers/mtd/nand/raw/meson_nand.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/meson_nand.c b/drivers/mtd/nand/raw/meson_nand.c index 1feea7d82252..3fe7bcd564f8 100644 --- a/drivers/mtd/nand/raw/meson_nand.c +++ b/drivers/mtd/nand/raw/meson_nand.c @@ -108,6 +108,9 @@ #define PER_INFO_BYTE 8 +#define NFC_COLUMN_ADDR_0 0 +#define NFC_COLUMN_ADDR_1 0 + struct meson_nfc_nand_chip { struct list_head node; struct nand_chip nand; @@ -595,12 +598,12 @@ static int meson_nfc_rw_cmd_prepare_and_execute(struct nand_chip *nand, cmd0 = in ? NAND_CMD_READ0 : NAND_CMD_SEQIN; nfc->cmdfifo.rw.cmd0 = cs | NFC_CMD_CLE | cmd0; - addrs[0] = cs | NFC_CMD_ALE | 0; + addrs[0] = cs | NFC_CMD_ALE | NFC_COLUMN_ADDR_0; if (mtd->writesize <= 512) { cmd_num--; row_start = 1; } else { - addrs[1] = cs | NFC_CMD_ALE | 0; + addrs[1] = cs | NFC_CMD_ALE | NFC_COLUMN_ADDR_1; row_start = 2; } -- cgit v1.2.3 From c17a90a46a712b78578dd7156380fdd515a2af9d Mon Sep 17 00:00:00 2001 From: Arseniy Krasnov Date: Thu, 8 Jun 2023 07:47:28 +0300 Subject: mtd: rawnand: meson: waiting w/o wired ready/busy pin If there is no wired ready/busy pin, classic way to wait for command completion is to use function 'nand_soft_waitrdy()'. Meson NAND has special command which allows to wait for NAND_STATUS_READY bit without reading status in a software loop (as 'nand_soft_waitrdy()' does). To use it send this command along with NAND_CMD_STATUS, then wait for an interrupt, and after interrupt send NAND_CMD_READ0. So this feature allows to use interrupt driven waiting without wired ready/busy pin. Suggested-by: Liang Yang Signed-off-by: Arseniy Krasnov Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230608044728.1328506-3-AVKrasnov@sberdevices.ru --- drivers/mtd/nand/raw/meson_nand.c | 77 +++++++++++++++++++++++++++++++++++++-- 1 file changed, 73 insertions(+), 4 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/meson_nand.c b/drivers/mtd/nand/raw/meson_nand.c index 3fe7bcd564f8..5e2720f4344f 100644 --- a/drivers/mtd/nand/raw/meson_nand.c +++ b/drivers/mtd/nand/raw/meson_nand.c @@ -38,6 +38,7 @@ #define NFC_CMD_SCRAMBLER_DISABLE 0 #define NFC_CMD_SHORTMODE_DISABLE 0 #define NFC_CMD_RB_INT BIT(14) +#define NFC_CMD_RB_INT_NO_PIN ((0xb << 10) | BIT(18) | BIT(16)) #define NFC_CMD_GET_SIZE(x) (((x) >> 22) & GENMASK(4, 0)) @@ -182,6 +183,7 @@ struct meson_nfc { u32 info_bytes; unsigned long assigned_cs; + bool no_rb_pin; }; enum { @@ -395,7 +397,42 @@ static void meson_nfc_set_data_oob(struct nand_chip *nand, } } -static int meson_nfc_queue_rb(struct meson_nfc *nfc, int timeout_ms) +static int meson_nfc_wait_no_rb_pin(struct meson_nfc *nfc, int timeout_ms, + bool need_cmd_read0) +{ + u32 cmd, cfg; + + meson_nfc_cmd_idle(nfc, nfc->timing.twb); + meson_nfc_drain_cmd(nfc); + meson_nfc_wait_cmd_finish(nfc, CMD_FIFO_EMPTY_TIMEOUT); + + cfg = readl(nfc->reg_base + NFC_REG_CFG); + cfg |= NFC_RB_IRQ_EN; + writel(cfg, nfc->reg_base + NFC_REG_CFG); + + reinit_completion(&nfc->completion); + cmd = nfc->param.chip_select | NFC_CMD_CLE | NAND_CMD_STATUS; + writel(cmd, nfc->reg_base + NFC_REG_CMD); + + /* use the max erase time as the maximum clock for waiting R/B */ + cmd = NFC_CMD_RB | NFC_CMD_RB_INT_NO_PIN | nfc->timing.tbers_max; + writel(cmd, nfc->reg_base + NFC_REG_CMD); + + if (!wait_for_completion_timeout(&nfc->completion, + msecs_to_jiffies(timeout_ms))) + return -ETIMEDOUT; + + if (need_cmd_read0) { + cmd = nfc->param.chip_select | NFC_CMD_CLE | NAND_CMD_READ0; + writel(cmd, nfc->reg_base + NFC_REG_CMD); + meson_nfc_drain_cmd(nfc); + meson_nfc_wait_cmd_finish(nfc, CMD_FIFO_EMPTY_TIMEOUT); + } + + return 0; +} + +static int meson_nfc_wait_rb_pin(struct meson_nfc *nfc, int timeout_ms) { u32 cmd, cfg; int ret = 0; @@ -423,6 +460,27 @@ static int meson_nfc_queue_rb(struct meson_nfc *nfc, int timeout_ms) return ret; } +static int meson_nfc_queue_rb(struct meson_nfc *nfc, int timeout_ms, + bool need_cmd_read0) +{ + if (nfc->no_rb_pin) { + /* This mode is used when there is no wired R/B pin. + * It works like 'nand_soft_waitrdy()', but instead of + * polling NAND_CMD_STATUS bit in the software loop, + * it will wait for interrupt - controllers checks IO + * bus and when it detects NAND_CMD_STATUS on it, it + * raises interrupt. After interrupt, NAND_CMD_READ0 is + * sent as terminator of the ready waiting procedure if + * needed (for all cases except page programming - this + * is reason of 'need_cmd_read0' flag). + */ + return meson_nfc_wait_no_rb_pin(nfc, timeout_ms, + need_cmd_read0); + } else { + return meson_nfc_wait_rb_pin(nfc, timeout_ms); + } +} + static void meson_nfc_set_user_byte(struct nand_chip *nand, u8 *oob_buf) { struct meson_nfc_nand_chip *meson_chip = to_meson_nand(nand); @@ -626,7 +684,7 @@ static int meson_nfc_rw_cmd_prepare_and_execute(struct nand_chip *nand, if (in) { nfc->cmdfifo.rw.cmd1 = cs | NFC_CMD_CLE | NAND_CMD_READSTART; writel(nfc->cmdfifo.rw.cmd1, nfc->reg_base + NFC_REG_CMD); - meson_nfc_queue_rb(nfc, PSEC_TO_MSEC(sdr->tR_max)); + meson_nfc_queue_rb(nfc, PSEC_TO_MSEC(sdr->tR_max), true); } else { meson_nfc_cmd_idle(nfc, nfc->timing.tadl); } @@ -672,7 +730,7 @@ static int meson_nfc_write_page_sub(struct nand_chip *nand, cmd = nfc->param.chip_select | NFC_CMD_CLE | NAND_CMD_PAGEPROG; writel(cmd, nfc->reg_base + NFC_REG_CMD); - meson_nfc_queue_rb(nfc, PSEC_TO_MSEC(sdr->tPROG_max)); + meson_nfc_queue_rb(nfc, PSEC_TO_MSEC(sdr->tPROG_max), false); meson_nfc_dma_buffer_release(nand, data_len, info_len, DMA_TO_DEVICE); @@ -955,7 +1013,8 @@ static int meson_nfc_exec_op(struct nand_chip *nand, break; case NAND_OP_WAITRDY_INSTR: - meson_nfc_queue_rb(nfc, instr->ctx.waitrdy.timeout_ms); + meson_nfc_queue_rb(nfc, instr->ctx.waitrdy.timeout_ms, + true); if (instr->delay_ns) meson_nfc_cmd_idle(nfc, delay_idle); break; @@ -1251,6 +1310,7 @@ meson_nfc_nand_chip_init(struct device *dev, struct mtd_info *mtd; int ret, i; u32 tmp, nsels; + u32 nand_rb_val = 0; nsels = of_property_count_elems_of_size(np, "reg", sizeof(u32)); if (!nsels || nsels > MAX_CE_NUM) { @@ -1290,6 +1350,15 @@ meson_nfc_nand_chip_init(struct device *dev, mtd->owner = THIS_MODULE; mtd->dev.parent = dev; + ret = of_property_read_u32(np, "nand-rb", &nand_rb_val); + if (ret == -EINVAL) + nfc->no_rb_pin = true; + else if (ret) + return ret; + + if (nand_rb_val) + return -EINVAL; + ret = nand_scan(nand, nsels); if (ret) return ret; -- cgit v1.2.3 From 1a50947df5b3a574c4c97891f8deb8de6500be6c Mon Sep 17 00:00:00 2001 From: JaimeLiao Date: Thu, 8 Jun 2023 13:21:14 +0800 Subject: mtd: spinand: macronix: Add support for serial NAND flash MX31LF2GE4BC and MX31UF2GE4BC are Macroninx SPI NAND flash with 8-bit on-die ECC. Validated via normal(default) and QUAD mode by read ,read back, on Xilinx Zynq PicoZed FPGA which include Macronix SPI Host(drivers/spi/spi-mxic.c) Signed-off-by: JaimeLiao Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230608052114.20454-1-jaimeliao.tw@gmail.com --- drivers/mtd/nand/spi/macronix.c | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/spi/macronix.c b/drivers/mtd/nand/spi/macronix.c index 722a9738ba37..3dfc7e1e5241 100644 --- a/drivers/mtd/nand/spi/macronix.c +++ b/drivers/mtd/nand/spi/macronix.c @@ -299,6 +299,26 @@ static const struct spinand_info macronix_spinand_table[] = { SPINAND_ECCINFO(&mx35lfxge4ab_ooblayout, mx35lf1ge4ab_ecc_get_status)), + SPINAND_INFO("MX31LF2GE4BC", + SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0x2e), + NAND_MEMORG(1, 2048, 64, 64, 2048, 40, 1, 1, 1), + NAND_ECCREQ(8, 512), + SPINAND_INFO_OP_VARIANTS(&read_cache_variants, + &write_cache_variants, + &update_cache_variants), + SPINAND_HAS_QE_BIT, + SPINAND_ECCINFO(&mx35lfxge4ab_ooblayout, + mx35lf1ge4ab_ecc_get_status)), + SPINAND_INFO("MX3UF2GE4BC", + SPINAND_ID(SPINAND_READID_METHOD_OPCODE_DUMMY, 0xae), + NAND_MEMORG(1, 2048, 64, 64, 2048, 40, 1, 1, 1), + NAND_ECCREQ(8, 512), + SPINAND_INFO_OP_VARIANTS(&read_cache_variants, + &write_cache_variants, + &update_cache_variants), + SPINAND_HAS_QE_BIT, + SPINAND_ECCINFO(&mx35lfxge4ab_ooblayout, + mx35lf1ge4ab_ecc_get_status)), }; static const struct spinand_manufacturer_ops macronix_spinand_manuf_ops = { -- cgit v1.2.3 From 46c37b99b5cbaa69a4d2af498b7d6a6db34d4db0 Mon Sep 17 00:00:00 2001 From: Arseniy Krasnov Date: Fri, 9 Jun 2023 14:28:39 +0300 Subject: mtd: rawnand: meson: check buffer length Meson NAND controller has limited buffer length, so check it before command execution to avoid length trim. Also check MTD write size on chip attach. Signed-off-by: Arseniy Krasnov Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230609112840.2325455-1-AVKrasnov@sberdevices.ru --- drivers/mtd/nand/raw/meson_nand.c | 46 ++++++++++++++++++++++++++++++++++++--- 1 file changed, 43 insertions(+), 3 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/meson_nand.c b/drivers/mtd/nand/raw/meson_nand.c index 5e2720f4344f..9c3300748efb 100644 --- a/drivers/mtd/nand/raw/meson_nand.c +++ b/drivers/mtd/nand/raw/meson_nand.c @@ -109,6 +109,8 @@ #define PER_INFO_BYTE 8 +#define NFC_CMD_RAW_LEN GENMASK(13, 0) + #define NFC_COLUMN_ADDR_0 0 #define NFC_COLUMN_ADDR_1 0 @@ -285,7 +287,7 @@ static void meson_nfc_cmd_access(struct nand_chip *nand, int raw, bool dir, if (raw) { len = mtd->writesize + mtd->oobsize; - cmd = (len & GENMASK(13, 0)) | scrambler | DMA_DIR(dir); + cmd = len | scrambler | DMA_DIR(dir); writel(cmd, nfc->reg_base + NFC_REG_CMD); return; } @@ -605,7 +607,7 @@ static int meson_nfc_read_buf(struct nand_chip *nand, u8 *buf, int len) if (ret) goto out; - cmd = NFC_CMD_N2M | (len & GENMASK(13, 0)); + cmd = NFC_CMD_N2M | len; writel(cmd, nfc->reg_base + NFC_REG_CMD); meson_nfc_drain_cmd(nfc); @@ -629,7 +631,7 @@ static int meson_nfc_write_buf(struct nand_chip *nand, u8 *buf, int len) if (ret) return ret; - cmd = NFC_CMD_M2N | (len & GENMASK(13, 0)); + cmd = NFC_CMD_M2N | len; writel(cmd, nfc->reg_base + NFC_REG_CMD); meson_nfc_drain_cmd(nfc); @@ -960,6 +962,31 @@ meson_nand_op_put_dma_safe_output_buf(const struct nand_op_instr *instr, kfree(buf); } +static int meson_nfc_check_op(struct nand_chip *chip, + const struct nand_operation *op) +{ + int op_id; + + for (op_id = 0; op_id < op->ninstrs; op_id++) { + const struct nand_op_instr *instr; + + instr = &op->instrs[op_id]; + + switch (instr->type) { + case NAND_OP_DATA_IN_INSTR: + case NAND_OP_DATA_OUT_INSTR: + if (instr->ctx.data.len > NFC_CMD_RAW_LEN) + return -ENOTSUPP; + + break; + default: + break; + } + } + + return 0; +} + static int meson_nfc_exec_op(struct nand_chip *nand, const struct nand_operation *op, bool check_only) { @@ -968,8 +995,13 @@ static int meson_nfc_exec_op(struct nand_chip *nand, const struct nand_op_instr *instr = NULL; void *buf; u32 op_id, delay_idle, cmd; + int err; int i; + err = meson_nfc_check_op(nand, op); + if (err) + return err; + if (check_only) return 0; @@ -1243,6 +1275,7 @@ static int meson_nand_attach_chip(struct nand_chip *nand) struct meson_nfc_nand_chip *meson_chip = to_meson_nand(nand); struct mtd_info *mtd = nand_to_mtd(nand); int nsectors = mtd->writesize / 1024; + int raw_writesize; int ret; if (!mtd->name) { @@ -1254,6 +1287,13 @@ static int meson_nand_attach_chip(struct nand_chip *nand) return -ENOMEM; } + raw_writesize = mtd->writesize + mtd->oobsize; + if (raw_writesize > NFC_CMD_RAW_LEN) { + dev_err(nfc->dev, "too big write size in raw mode: %d > %ld\n", + raw_writesize, NFC_CMD_RAW_LEN); + return -EINVAL; + } + if (nand->bbt_options & NAND_BBT_USE_FLASH) nand->bbt_options |= NAND_BBT_NO_OOB; -- cgit v1.2.3 From 87194abaa5ced8c1cee5499d9da058eadfa63f44 Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Sat, 3 Jun 2023 20:52:00 +0200 Subject: mtd: chips: Use SPDX license headers Some of the files in mtd/chips do not have a SPDX license header, presumably because the text string "GPL'd" didn't parse with Thomas rulesets for magic license tagging. Fix this, the code is initially from RedHat which clearly targeted the Linux kernel and intended it to be GPLv2. In any case the original author appears to be David Woodhouse who can then confirm this. Cc: David Woodhouse Cc: Thomas Gleixner Signed-off-by: Linus Walleij Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230603185200.3571174-1-linus.walleij@linaro.org --- drivers/mtd/chips/cfi_cmdset_0001.c | 3 ++- drivers/mtd/chips/cfi_cmdset_0002.c | 3 +-- drivers/mtd/chips/cfi_cmdset_0020.c | 3 ++- drivers/mtd/chips/cfi_probe.c | 3 ++- drivers/mtd/chips/cfi_util.c | 3 +-- drivers/mtd/chips/gen_probe.c | 2 +- drivers/mtd/chips/jedec_probe.c | 3 ++- drivers/mtd/chips/map_ram.c | 3 ++- drivers/mtd/chips/map_rom.c | 3 ++- 9 files changed, 15 insertions(+), 11 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/chips/cfi_cmdset_0001.c b/drivers/mtd/chips/cfi_cmdset_0001.c index 54f92d09d9cf..11b06fefaa0e 100644 --- a/drivers/mtd/chips/cfi_cmdset_0001.c +++ b/drivers/mtd/chips/cfi_cmdset_0001.c @@ -1,8 +1,9 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Common Flash Interface support: * Intel Extended Vendor Command Set (ID 0x0001) * - * (C) 2000 Red Hat. GPL'd + * (C) 2000 Red Hat. * * * 10/10/2000 Nicolas Pitre diff --git a/drivers/mtd/chips/cfi_cmdset_0002.c b/drivers/mtd/chips/cfi_cmdset_0002.c index 67453f59c69c..153fb8d0008e 100644 --- a/drivers/mtd/chips/cfi_cmdset_0002.c +++ b/drivers/mtd/chips/cfi_cmdset_0002.c @@ -1,3 +1,4 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Common Flash Interface support: * AMD & Fujitsu Standard Vendor Command Set (ID 0x0002) @@ -16,8 +17,6 @@ * 25/09/2008 Christopher Moore: TopBottom fixup for many Macronix with CFI V1.0 * * Occasionally maintained by Thayne Harbaugh tharbaugh at lnxi dot com - * - * This code is GPL */ #include diff --git a/drivers/mtd/chips/cfi_cmdset_0020.c b/drivers/mtd/chips/cfi_cmdset_0020.c index d35df526e0a6..60c7f6f751c7 100644 --- a/drivers/mtd/chips/cfi_cmdset_0020.c +++ b/drivers/mtd/chips/cfi_cmdset_0020.c @@ -1,8 +1,9 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Common Flash Interface support: * ST Advanced Architecture Command Set (ID 0x0020) * - * (C) 2000 Red Hat. GPL'd + * (C) 2000 Red Hat. * * 10/10/2000 Nicolas Pitre * - completely revamped method functions so they are aware and diff --git a/drivers/mtd/chips/cfi_probe.c b/drivers/mtd/chips/cfi_probe.c index cf426956454c..a04b6174181c 100644 --- a/drivers/mtd/chips/cfi_probe.c +++ b/drivers/mtd/chips/cfi_probe.c @@ -1,6 +1,7 @@ +// SPDX-License-Identifier: GPL-2.0 /* Common Flash Interface probe code. - (C) 2000 Red Hat. GPL'd. + (C) 2000 Red Hat. */ #include diff --git a/drivers/mtd/chips/cfi_util.c b/drivers/mtd/chips/cfi_util.c index 6a6a2a21d2ed..140c69a67e82 100644 --- a/drivers/mtd/chips/cfi_util.c +++ b/drivers/mtd/chips/cfi_util.c @@ -1,11 +1,10 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Common Flash Interface support: * Generic utility functions not dependent on command set * * Copyright (C) 2002 Red Hat * Copyright (C) 2003 STMicroelectronics Limited - * - * This code is covered by the GPL. */ #include diff --git a/drivers/mtd/chips/gen_probe.c b/drivers/mtd/chips/gen_probe.c index 4d4f97841016..9e53fcd7600d 100644 --- a/drivers/mtd/chips/gen_probe.c +++ b/drivers/mtd/chips/gen_probe.c @@ -1,7 +1,7 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Routines common to all CFI-type probes. * (C) 2001-2003 Red Hat, Inc. - * GPL'd */ #include diff --git a/drivers/mtd/chips/jedec_probe.c b/drivers/mtd/chips/jedec_probe.c index 6f7e7e1b3fe5..23c32fe584b7 100644 --- a/drivers/mtd/chips/jedec_probe.c +++ b/drivers/mtd/chips/jedec_probe.c @@ -1,6 +1,7 @@ +// SPDX-License-Identifier: GPL-2.0 /* Common Flash Interface probe code. - (C) 2000 Red Hat. GPL'd. + (C) 2000 Red Hat. See JEDEC (http://www.jedec.org/) standard JESD21C (section 3.5) for the standard this probe goes back to. diff --git a/drivers/mtd/chips/map_ram.c b/drivers/mtd/chips/map_ram.c index c37fce926864..e8dd6496927e 100644 --- a/drivers/mtd/chips/map_ram.c +++ b/drivers/mtd/chips/map_ram.c @@ -1,6 +1,7 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Common code to handle map devices which are simple RAM - * (C) 2000 Red Hat. GPL'd. + * (C) 2000 Red Hat. */ #include diff --git a/drivers/mtd/chips/map_rom.c b/drivers/mtd/chips/map_rom.c index 20e3604b4d71..0823b15aaadb 100644 --- a/drivers/mtd/chips/map_rom.c +++ b/drivers/mtd/chips/map_rom.c @@ -1,6 +1,7 @@ +// SPDX-License-Identifier: GPL-2.0 /* * Common code to handle map devices which are simple ROM - * (C) 2000 Red Hat. GPL'd. + * (C) 2000 Red Hat. */ #include -- cgit v1.2.3 From 6db02fdfdca0cf39b4d66950451d7f22b72a9031 Mon Sep 17 00:00:00 2001 From: Christophe JAILLET Date: Sun, 4 Jun 2023 06:42:01 +0200 Subject: mtd: mtdpart: Drop useless LIST_HEAD 'tmp_list' is unused, so drop it. Signed-off-by: Christophe JAILLET Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/547248195d87d1240d6126d13eb1364b1a0b634d.1685853690.git.christophe.jaillet@wanadoo.fr --- drivers/mtd/mtdpart.c | 1 - 1 file changed, 1 deletion(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/mtdpart.c b/drivers/mtd/mtdpart.c index 85f5ee6f06fc..a46affbb037d 100644 --- a/drivers/mtd/mtdpart.c +++ b/drivers/mtd/mtdpart.c @@ -326,7 +326,6 @@ static int __mtd_del_partition(struct mtd_info *mtd) static int __del_mtd_partitions(struct mtd_info *mtd) { struct mtd_info *child, *next; - LIST_HEAD(tmp_list); int ret, err = 0; list_for_each_entry_safe(child, next, &mtd->partitions, part.node) { -- cgit v1.2.3 From 3b270fac84439cbd036c98e189d17f2bc3c85494 Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Tue, 6 Jun 2023 16:29:31 +0200 Subject: mtd: otp: Put factory OTP/NVRAM into the entropy pool The factory OTP, if supported, contains factory-programmed information such as typically the serial number or production week for the chip. As this is device-unique information, submit it into the system entropy pool. This does not count as improvement of the entropy as such but in practice it makes it a bit more random to mix in these numbers. Cc: Michael Walle Acked-by: Jason A. Donenfeld Signed-off-by: Linus Walleij Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230606142931.3721374-1-linus.walleij@linaro.org --- drivers/mtd/mtdcore.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) (limited to 'drivers/mtd') diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c index 60670b2f70b9..abf4cb58a8ab 100644 --- a/drivers/mtd/mtdcore.c +++ b/drivers/mtd/mtdcore.c @@ -23,6 +23,7 @@ #include #include #include +#include #include #include #include @@ -966,6 +967,24 @@ static int mtd_otp_nvmem_add(struct mtd_info *mtd) } if (size > 0) { + /* + * The factory OTP contains thing such as a unique serial + * number and is small, so let's read it out and put it + * into the entropy pool. + */ + void *otp; + + otp = kmalloc(size, GFP_KERNEL); + if (!otp) + return -ENOMEM; + err = mtd_nvmem_fact_otp_reg_read(mtd, 0, otp, size); + if (err < 0) { + kfree(otp); + return err; + } + add_device_randomness(otp, err); + kfree(otp); + nvmem = mtd_otp_nvmem_register(mtd, "factory-otp", size, mtd_nvmem_fact_otp_reg_read); if (IS_ERR(nvmem)) { -- cgit v1.2.3 From 12ac188b9355618dbaa892eb795f48845cf7b1af Mon Sep 17 00:00:00 2001 From: Johan Jonker Date: Tue, 13 Jun 2023 23:19:58 +0200 Subject: mtd: rawnand: add basic sandisk manufacturer ops Add basic Sandisk manufacturer ops support to get SDTNQGAMA timing data with the nand_get_sdr_timings() function. Signed-off-by: Johan Jonker Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/aaf4580a-a368-8f70-c9c4-21b5ed4dd599@gmail.com --- drivers/mtd/nand/raw/Makefile | 1 + drivers/mtd/nand/raw/internals.h | 1 + drivers/mtd/nand/raw/nand_ids.c | 2 +- drivers/mtd/nand/raw/nand_sandisk.c | 26 ++++++++++++++++++++++++++ 4 files changed, 29 insertions(+), 1 deletion(-) create mode 100644 drivers/mtd/nand/raw/nand_sandisk.c (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/Makefile b/drivers/mtd/nand/raw/Makefile index 917cdfb815b9..d93e861d8ba7 100644 --- a/drivers/mtd/nand/raw/Makefile +++ b/drivers/mtd/nand/raw/Makefile @@ -67,5 +67,6 @@ nand-objs += nand_esmt.o nand-objs += nand_hynix.o nand-objs += nand_macronix.o nand-objs += nand_micron.o +nand-objs += nand_sandisk.o nand-objs += nand_samsung.o nand-objs += nand_toshiba.o diff --git a/drivers/mtd/nand/raw/internals.h b/drivers/mtd/nand/raw/internals.h index 7016e0f38398..e9932da18bdd 100644 --- a/drivers/mtd/nand/raw/internals.h +++ b/drivers/mtd/nand/raw/internals.h @@ -73,6 +73,7 @@ extern const struct nand_manufacturer_ops hynix_nand_manuf_ops; extern const struct nand_manufacturer_ops macronix_nand_manuf_ops; extern const struct nand_manufacturer_ops micron_nand_manuf_ops; extern const struct nand_manufacturer_ops samsung_nand_manuf_ops; +extern const struct nand_manufacturer_ops sandisk_nand_manuf_ops; extern const struct nand_manufacturer_ops toshiba_nand_manuf_ops; /* MLC pairing schemes */ diff --git a/drivers/mtd/nand/raw/nand_ids.c b/drivers/mtd/nand/raw/nand_ids.c index dacc5529b3df..1a89ed796a33 100644 --- a/drivers/mtd/nand/raw/nand_ids.c +++ b/drivers/mtd/nand/raw/nand_ids.c @@ -188,7 +188,7 @@ static const struct nand_manufacturer_desc nand_manufacturer_descs[] = { {NAND_MFR_NATIONAL, "National"}, {NAND_MFR_RENESAS, "Renesas"}, {NAND_MFR_SAMSUNG, "Samsung", &samsung_nand_manuf_ops}, - {NAND_MFR_SANDISK, "SanDisk"}, + {NAND_MFR_SANDISK, "SanDisk", &sandisk_nand_manuf_ops}, {NAND_MFR_STMICRO, "ST Micro"}, {NAND_MFR_TOSHIBA, "Toshiba", &toshiba_nand_manuf_ops}, {NAND_MFR_WINBOND, "Winbond"}, diff --git a/drivers/mtd/nand/raw/nand_sandisk.c b/drivers/mtd/nand/raw/nand_sandisk.c new file mode 100644 index 000000000000..7c66e4187dc7 --- /dev/null +++ b/drivers/mtd/nand/raw/nand_sandisk.c @@ -0,0 +1,26 @@ +// SPDX-License-Identifier: GPL-2.0-or-later + +#include "internals.h" + +static int +sdtnqgama_choose_interface_config(struct nand_chip *chip, + struct nand_interface_config *iface) +{ + onfi_fill_interface_config(chip, iface, NAND_SDR_IFACE, 0); + + return nand_choose_best_sdr_timings(chip, iface, NULL); +} + +static int sandisk_nand_init(struct nand_chip *chip) +{ + if (!strncmp("SDTNQGAMA", chip->parameters.model, + sizeof("SDTNQGAMA") - 1)) + chip->ops.choose_interface_config = + &sdtnqgama_choose_interface_config; + + return 0; +} + +const struct nand_manufacturer_ops sandisk_nand_manuf_ops = { + .init = sandisk_nand_init, +}; -- cgit v1.2.3 From a6a8a1e16c14b5c93bec202ba2f1c8d7c9173571 Mon Sep 17 00:00:00 2001 From: Johan Jonker Date: Tue, 13 Jun 2023 23:21:06 +0200 Subject: mtd: rawnand: add support for the Sandisk SDTNQGAMA chip MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Sandisk SDTNQGAMA is a 8GB size, 3.3V 8 bit chip with 16KB page size, 1KB write size and 40 bit ecc support Co-developed-by: Paweł Jarosz Signed-off-by: Paweł Jarosz Signed-off-by: Johan Jonker Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/98811c98-4681-6ddc-8287-bd9b77559c51@gmail.com --- drivers/mtd/nand/raw/nand_ids.c | 3 +++ 1 file changed, 3 insertions(+) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/nand_ids.c b/drivers/mtd/nand/raw/nand_ids.c index 1a89ed796a33..650351c62af6 100644 --- a/drivers/mtd/nand/raw/nand_ids.c +++ b/drivers/mtd/nand/raw/nand_ids.c @@ -44,6 +44,9 @@ struct nand_flash_dev nand_flash_ids[] = { {"TC58NVG6D2 64G 3.3V 8-bit", { .id = {0x98, 0xde, 0x94, 0x82, 0x76, 0x56, 0x04, 0x20} }, SZ_8K, SZ_8K, SZ_2M, 0, 8, 640, NAND_ECC_INFO(40, SZ_1K) }, + {"SDTNQGAMA 64G 3.3V 8-bit", + { .id = {0x45, 0xde, 0x94, 0x93, 0x76, 0x57} }, + SZ_16K, SZ_8K, SZ_4M, 0, 6, 1280, NAND_ECC_INFO(40, SZ_1K) }, {"SDTNRGAMA 64G 3.3V 8-bit", { .id = {0x45, 0xde, 0x94, 0x93, 0x76, 0x50} }, SZ_16K, SZ_8K, SZ_4M, 0, 6, 1280, NAND_ECC_INFO(40, SZ_1K) }, -- cgit v1.2.3 From 98480a181a08ceeede417e5b28f6d0429d8ae156 Mon Sep 17 00:00:00 2001 From: Arseniy Krasnov Date: Thu, 15 Jun 2023 11:08:15 +0300 Subject: mtd: rawnand: meson: fix unaligned DMA buffers handling Meson NAND controller requires 8 bytes alignment for DMA addresses, otherwise it "aligns" passed address by itself thus accessing invalid location in the provided buffer. This patch makes unaligned buffers to be reallocated to become valid. Fixes: 8fae856c5350 ("mtd: rawnand: meson: add support for Amlogic NAND flash controller") Cc: Signed-off-by: Arseniy Krasnov Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230615080815.3291006-1-AVKrasnov@sberdevices.ru --- drivers/mtd/nand/raw/meson_nand.c | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/meson_nand.c b/drivers/mtd/nand/raw/meson_nand.c index 9c3300748efb..d3faf8086631 100644 --- a/drivers/mtd/nand/raw/meson_nand.c +++ b/drivers/mtd/nand/raw/meson_nand.c @@ -77,6 +77,7 @@ #define GENCMDIADDRH(aih, addr) ((aih) | (((addr) >> 16) & 0xffff)) #define DMA_DIR(dir) ((dir) ? NFC_CMD_N2M : NFC_CMD_M2N) +#define DMA_ADDR_ALIGN 8 #define ECC_CHECK_RETURN_FF (-1) @@ -905,6 +906,9 @@ static int meson_nfc_read_oob(struct nand_chip *nand, int page) static bool meson_nfc_is_buffer_dma_safe(const void *buffer) { + if ((uintptr_t)buffer % DMA_ADDR_ALIGN) + return false; + if (virt_addr_valid(buffer) && (!object_is_on_stack(buffer))) return true; return false; -- cgit v1.2.3 From e87161321a4081d36c4af95af7f0950137569dfe Mon Sep 17 00:00:00 2001 From: Arseniy Krasnov Date: Thu, 15 Jun 2023 12:40:06 +0300 Subject: mtd: rawnand: macronix: OTP access for MX30LFxG18AC Support for OTP area access on MX30LFxG18AC chip series. Signed-off-by: Arseniy Krasnov Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230615094015.3780078-1-AVKrasnov@sberdevices.ru --- drivers/mtd/nand/raw/nand_macronix.c | 167 +++++++++++++++++++++++++++++++++++ 1 file changed, 167 insertions(+) (limited to 'drivers/mtd') diff --git a/drivers/mtd/nand/raw/nand_macronix.c b/drivers/mtd/nand/raw/nand_macronix.c index 385957eb6762..e229de32ff50 100644 --- a/drivers/mtd/nand/raw/nand_macronix.c +++ b/drivers/mtd/nand/raw/nand_macronix.c @@ -6,6 +6,7 @@ * Author: Boris Brezillon */ +#include #include "linux/delay.h" #include "internals.h" @@ -31,6 +32,16 @@ #define MXIC_CMD_POWER_DOWN 0xB9 +#define ONFI_FEATURE_ADDR_30LFXG18AC_OTP 0x90 +#define MACRONIX_30LFXG18AC_OTP_START_PAGE 2 +#define MACRONIX_30LFXG18AC_OTP_PAGES 30 +#define MACRONIX_30LFXG18AC_OTP_PAGE_SIZE 2112 +#define MACRONIX_30LFXG18AC_OTP_SIZE_BYTES \ + (MACRONIX_30LFXG18AC_OTP_PAGES * \ + MACRONIX_30LFXG18AC_OTP_PAGE_SIZE) + +#define MACRONIX_30LFXG18AC_OTP_EN BIT(0) + struct nand_onfi_vendor_macronix { u8 reserved; u8 reliability_func; @@ -315,6 +326,161 @@ static void macronix_nand_deep_power_down_support(struct nand_chip *chip) chip->ops.resume = mxic_nand_resume; } +static int macronix_30lfxg18ac_get_otp_info(struct mtd_info *mtd, size_t len, + size_t *retlen, + struct otp_info *buf) +{ + if (len < sizeof(*buf)) + return -EINVAL; + + /* Always report that OTP is unlocked. Reason is that this + * type of flash chip doesn't provide way to check that OTP + * is locked or not: subfeature parameter is implemented as + * volatile register. Technically OTP region could be locked + * and become readonly, but as there is no way to check it, + * don't allow to lock it ('_lock_user_prot_reg' callback + * always returns -EOPNOTSUPP) and thus we report that OTP + * is unlocked. + */ + buf->locked = 0; + buf->start = 0; + buf->length = MACRONIX_30LFXG18AC_OTP_SIZE_BYTES; + + *retlen = sizeof(*buf); + + return 0; +} + +static int macronix_30lfxg18ac_otp_enable(struct nand_chip *nand) +{ + u8 feature_buf[ONFI_SUBFEATURE_PARAM_LEN] = { 0 }; + + feature_buf[0] = MACRONIX_30LFXG18AC_OTP_EN; + return nand_set_features(nand, ONFI_FEATURE_ADDR_30LFXG18AC_OTP, + feature_buf); +} + +static int macronix_30lfxg18ac_otp_disable(struct nand_chip *nand) +{ + u8 feature_buf[ONFI_SUBFEATURE_PARAM_LEN] = { 0 }; + + return nand_set_features(nand, ONFI_FEATURE_ADDR_30LFXG18AC_OTP, + feature_buf); +} + +static int __macronix_30lfxg18ac_rw_otp(struct mtd_info *mtd, + loff_t offs_in_flash, + size_t len, size_t *retlen, + u_char *buf, bool write) +{ + struct nand_chip *nand; + size_t bytes_handled; + off_t offs_in_page; + u64 page; + int ret; + + nand = mtd_to_nand(mtd); + nand_select_target(nand, 0); + + ret = macronix_30lfxg18ac_otp_enable(nand); + if (ret) + goto out_otp; + + page = offs_in_flash; + /* 'page' will be result of division. */ + offs_in_page = do_div(page, MACRONIX_30LFXG18AC_OTP_PAGE_SIZE); + bytes_handled = 0; + + while (bytes_handled < len && + page < MACRONIX_30LFXG18AC_OTP_PAGES) { + size_t bytes_to_handle; + u64 phys_page = page + MACRONIX_30LFXG18AC_OTP_START_PAGE; + + bytes_to_handle = min_t(size_t, len - bytes_handled, + MACRONIX_30LFXG18AC_OTP_PAGE_SIZE - + offs_in_page); + + if (write) + ret = nand_prog_page_op(nand, phys_page, offs_in_page, + &buf[bytes_handled], bytes_to_handle); + else + ret = nand_read_page_op(nand, phys_page, offs_in_page, + &buf[bytes_handled], bytes_to_handle); + if (ret) + goto out_otp; + + bytes_handled += bytes_to_handle; + offs_in_page = 0; + page++; + } + + *retlen = bytes_handled; + +out_otp: + if (ret) + dev_err(&mtd->dev, "failed to perform OTP IO: %i\n", ret); + + ret = macronix_30lfxg18ac_otp_disable(nand); + if (ret) + dev_err(&mtd->dev, "failed to leave OTP mode after %s\n", + write ? "write" : "read"); + + nand_deselect_target(nand); + + return ret; +} + +static int macronix_30lfxg18ac_write_otp(struct mtd_info *mtd, loff_t to, + size_t len, size_t *rlen, + const u_char *buf) +{ + return __macronix_30lfxg18ac_rw_otp(mtd, to, len, rlen, (u_char *)buf, + true); +} + +static int macronix_30lfxg18ac_read_otp(struct mtd_info *mtd, loff_t from, + size_t len, size_t *rlen, + u_char *buf) +{ + return __macronix_30lfxg18ac_rw_otp(mtd, from, len, rlen, buf, false); +} + +static int macronix_30lfxg18ac_lock_otp(struct mtd_info *mtd, loff_t from, + size_t len) +{ + /* See comment in 'macronix_30lfxg18ac_get_otp_info()'. */ + return -EOPNOTSUPP; +} + +static void macronix_nand_setup_otp(struct nand_chip *chip) +{ + static const char * const supported_otp_models[] = { + "MX30LF1G18AC", + "MX30LF2G18AC", + "MX30LF4G18AC", + }; + struct mtd_info *mtd; + + if (match_string(supported_otp_models, + ARRAY_SIZE(supported_otp_models), + chip->parameters.model) < 0) + return; + + if (!chip->parameters.supports_set_get_features) + return; + + bitmap_set(chip->parameters.get_feature_list, + ONFI_FEATURE_ADDR_30LFXG18AC_OTP, 1); + bitmap_set(chip->parameters.set_feature_list, + ONFI_FEATURE_ADDR_30LFXG18AC_OTP, 1); + + mtd = nand_to_mtd(chip); + mtd->_get_user_prot_info = macronix_30lfxg18ac_get_otp_info; + mtd->_read_user_prot_reg = macronix_30lfxg18ac_read_otp; + mtd->_write_user_prot_reg = macronix_30lfxg18ac_write_otp; + mtd->_lock_user_prot_reg = macronix_30lfxg18ac_lock_otp; +} + static int macronix_nand_init(struct nand_chip *chip) { if (nand_is_slc(chip)) @@ -324,6 +490,7 @@ static int macronix_nand_init(struct nand_chip *chip) macronix_nand_onfi_init(chip); macronix_nand_block_protection_support(chip); macronix_nand_deep_power_down_support(chip); + macronix_nand_setup_otp(chip); return 0; } -- cgit v1.2.3 From 812a20df6048ba2945b1bda74c45143bbc3e4cda Mon Sep 17 00:00:00 2001 From: Uwe Kleine-König Date: Sun, 11 Jun 2023 22:43:27 +0200 Subject: mtd: maps: pismo: Switch back to use i2c_driver's .probe() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit After commit b8a1a4cd5a98 ("i2c: Provide a temporary .probe_new() call-back type"), all drivers being converted to .probe_new() and then commit 03c835f498b5 ("i2c: Switch .probe() to not take an id parameter") convert back to (the new) .probe() to be able to eventually drop .probe_new() from struct i2c_driver. Signed-off-by: Uwe Kleine-König Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230611204327.828122-1-u.kleine-koenig@pengutronix.de --- drivers/mtd/maps/pismo.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/maps/pismo.c b/drivers/mtd/maps/pismo.c index 3e0fff3f129e..ecf68922da73 100644 --- a/drivers/mtd/maps/pismo.c +++ b/drivers/mtd/maps/pismo.c @@ -259,7 +259,7 @@ static struct i2c_driver pismo_driver = { .driver = { .name = "pismo", }, - .probe_new = pismo_probe, + .probe = pismo_probe, .remove = pismo_remove, .id_table = pismo_id, }; -- cgit v1.2.3 From cefa1aaa31bd7bb73a37c15ec66a9353753b2abc Mon Sep 17 00:00:00 2001 From: Dan Carpenter Date: Thu, 15 Jun 2023 09:09:20 +0300 Subject: mtd: otp: clean up on error in mtd_otp_nvmem_add() Smatch complains that these error paths are missing cleanup: drivers/mtd/mtdcore.c:983 mtd_otp_nvmem_add() warn: missing unwind goto? This needs to call nvmem_unregister(mtd->otp_user_nvmem) before returning. Fixes: 3b270fac8443 ("mtd: otp: Put factory OTP/NVRAM into the entropy pool") Signed-off-by: Dan Carpenter Reviewed-by: Linus Walleij Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/fe7ef901-9571-4c6e-a40e-449046efe2c6@moroto.mountain --- drivers/mtd/mtdcore.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c index abf4cb58a8ab..e00b12aa5ec9 100644 --- a/drivers/mtd/mtdcore.c +++ b/drivers/mtd/mtdcore.c @@ -975,12 +975,14 @@ static int mtd_otp_nvmem_add(struct mtd_info *mtd) void *otp; otp = kmalloc(size, GFP_KERNEL); - if (!otp) - return -ENOMEM; + if (!otp) { + err = -ENOMEM; + goto err; + } err = mtd_nvmem_fact_otp_reg_read(mtd, 0, otp, size); if (err < 0) { kfree(otp); - return err; + goto err; } add_device_randomness(otp, err); kfree(otp); -- cgit v1.2.3 From efd2ed9351efefe40cbcca36a527adf38ffe1b4d Mon Sep 17 00:00:00 2001 From: Bo Liu Date: Tue, 20 Jun 2023 22:03:31 -0400 Subject: mtd: sm_ftl: Fix typos in comments Fix typo in the description of the 'succesfull'. Signed-off-by: Bo Liu Signed-off-by: Miquel Raynal Link: https://lore.kernel.org/linux-mtd/20230621020331.1508-1-wangdeming@inspur.com --- drivers/mtd/sm_ftl.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/mtd') diff --git a/drivers/mtd/sm_ftl.c b/drivers/mtd/sm_ftl.c index 4cfec3b7b446..b5b3c4c44a94 100644 --- a/drivers/mtd/sm_ftl.c +++ b/drivers/mtd/sm_ftl.c @@ -981,7 +981,7 @@ restart: /* Update the FTL table */ zone->lba_to_phys_table[ftl->cache_block] = write_sector; - /* Write succesfull, so erase and free the old block */ + /* Write successful, so erase and free the old block */ if (block_num > 0) sm_erase_block(ftl, zone_num, block_num, 1); -- cgit v1.2.3