aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/mtd/spi-nor/sfdp.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2021-07-05 11:21:51 -0700
committerLinus Torvalds <torvalds@linux-foundation.org>2021-07-05 11:21:51 -0700
commitda85e7ed6993144a9ca43a1106c7f898626390a3 (patch)
treea5fdbea1cfe8deb13bcbef1b6e102ad1ca965e34 /drivers/mtd/spi-nor/sfdp.c
parentMerge tag 'm68knommu-for-v5.14' of git://git.kernel.org/pub/scm/linux/kernel/git/gerg/m68knommu (diff)
parentMerge tag 'spi-nor/for-5.14' into mtd/next (diff)
downloadlinux-dev-da85e7ed6993144a9ca43a1106c7f898626390a3.tar.xz
linux-dev-da85e7ed6993144a9ca43a1106c7f898626390a3.zip
Merge tag 'mtd/for-5.14' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux
Pull MTD updates from Richard Weinberger: "MTD core changes: - Convert list_for_each to entry variant - Use MTD_DEVICE_ATTR_RO/RW() helper macros - Remove unnecessary OOM messages - Potential NULL dereference in mtd_otp_size() - Fix freeing of otp_info buffer - Create partname and partid debug files for child MTDs - tests: - Remove redundant assignment to err - Fix error return code in mtd_oobtest_init() - Add OTP NVMEM provider support - Allow specifying of_node - Convert sysfs sprintf/snprintf family to sysfs_emit Bindings changes: - Convert ti,am654-hbmc.txt to YAML schema - spi-nor: add otp property - Add OTP bindings - add YAML schema for the generic MTD bindings - Add brcm,trx-magic MTD device drivers changes: - Add support for microchip 48l640 EERAM - Remove superfluous "break" - sm_ftl: - Fix alignment of block comment - nftl: - Return -ENOMEM when kmalloc failed - nftlcore: - Remove set but rewrite variables - phram: - Fix error return code in phram_setup() - plat-ram: - Remove redundant dev_err call in platram_probe() MTD parsers changes: - Qcom: - Fix leaking of partition name - Redboot: - Fix style issues - Seek fis-index-block in the right node - trx: - Allow to use TRX parser on Mediatek SoCs - Allow to specify brcm, trx-magic in DT Raw NAND core: - Allow SDR timings to be nacked - Bring support for NV-DDR timings which involved a number of small preparation changes to bring new helpers, properly introduce NV-DDR structures, fill them, differenciate them and pick the best timing set. - Add the necessary infrastructure to parse the new gpio-cs property which aims at enlarging the number of available CS when a hardware controller is too constrained. - Update dead URL - Silence static checker warning in nand_setup_interface() - BBT: - Fix corner case in bad block table handling - onfi: - Use more recent ONFI specification wording - Use the BIT() macro when possible Raw NAND controller drivers: - Atmel: - Ensure the data interface is supported. - Arasan: - Finer grain NV-DDR configuration - Rename the data interface register - Use the right DMA mask - Leverage additional GPIO CS - Ensure proper configuration for the asserted target - Add support for the NV-DDR interface - Fix a macro parameter - brcmnand: - Convert bindings to json-schema - OMAP: - Various fixes and style improvements - Add larger page NAND chips support - PL35X: - New driver - QCOM: - Avoid writing to obsolete register - Delete an unneeded bool conversion - Allow override of partition parser - Marvell: - Minor documentation correction - Add missing clk_disable_unprepare() on error in marvell_nfc_resume() - R852: - Use DEVICE_ATTR_RO() helper macro - MTK: - Remove redundant dev_err call in mtk_ecc_probe() - HISI504: - Remove redundant dev_err call in probe SPI-NAND core: - Light reorganisation for the introduction of a core resume handler - Fix double counting of ECC stats SPI-NAND manufacturer drivers: - Macronix: - Add support for serial NAND flash SPI NOR core changes: - Ability to dump SFDP tables via sysfs - Support for erasing OTP regions on Winbond and similar flashes - Few API doc updates and fixes - Locking support for MX25L12805D SPI NOR controller drivers changes: - Use SPI_MODE_X_MASK in nxp-spifi - Intel Alder Lake-M SPI serial flash support" * tag 'mtd/for-5.14' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux: (125 commits) mtd: spi-nor: remove redundant continue statement mtd: rawnand: omap: Add larger page NAND chips support mtd: rawnand: omap: Various style fixes mtd: rawnand: omap: Check return values mtd: rawnand: omap: Rename a macro mtd: rawnand: omap: Aggregate the HW configuration of the ELM mtd: rawnand: pl353: Add support for the ARM PL353 SMC NAND controller dt-bindings: mtd: pl353-nand: Describe this hardware controller MAINTAINERS: Add PL353 NAND controller entry mtd: rawnand: qcom: avoid writing to obsolete register mtd: rawnand: marvell: Minor documentation correction mtd: rawnand: r852: use DEVICE_ATTR_RO() helper macro mtd: spinand: add SPI-NAND MTD resume handler mtd: spinand: Add spinand_init_flash() helper mtd: spinand: add spinand_read_cfg() helper mtd: rawnand: marvell: add missing clk_disable_unprepare() on error in marvell_nfc_resume() mtd: rawnand: arasan: Finer grain NV-DDR configuration mtd: rawnand: arasan: Rename the data interface register mtd: rawnand: onfi: Fix endianness when reading NV-DDR values mtd: rawnand: arasan: Use the right DMA mask ...
Diffstat (limited to 'drivers/mtd/spi-nor/sfdp.c')
-rw-r--r--drivers/mtd/spi-nor/sfdp.c58
1 files changed, 58 insertions, 0 deletions
diff --git a/drivers/mtd/spi-nor/sfdp.c b/drivers/mtd/spi-nor/sfdp.c
index 23c28e91f698..c500c2118a5d 100644
--- a/drivers/mtd/spi-nor/sfdp.c
+++ b/drivers/mtd/spi-nor/sfdp.c
@@ -16,6 +16,7 @@
(((p)->parameter_table_pointer[2] << 16) | \
((p)->parameter_table_pointer[1] << 8) | \
((p)->parameter_table_pointer[0] << 0))
+#define SFDP_PARAM_HEADER_PARAM_LEN(p) ((p)->length * 4)
#define SFDP_BFPT_ID 0xff00 /* Basic Flash Parameter Table */
#define SFDP_SECTOR_MAP_ID 0xff81 /* Sector Map Table */
@@ -1245,6 +1246,8 @@ int spi_nor_parse_sfdp(struct spi_nor *nor)
struct sfdp_parameter_header *param_headers = NULL;
struct sfdp_header header;
struct device *dev = nor->dev;
+ struct sfdp *sfdp;
+ size_t sfdp_size;
size_t psize;
int i, err;
@@ -1267,6 +1270,9 @@ int spi_nor_parse_sfdp(struct spi_nor *nor)
bfpt_header->major != SFDP_JESD216_MAJOR)
return -EINVAL;
+ sfdp_size = SFDP_PARAM_HEADER_PTP(bfpt_header) +
+ SFDP_PARAM_HEADER_PARAM_LEN(bfpt_header);
+
/*
* Allocate memory then read all parameter headers with a single
* Read SFDP command. These parameter headers will actually be parsed
@@ -1294,6 +1300,58 @@ int spi_nor_parse_sfdp(struct spi_nor *nor)
}
/*
+ * Cache the complete SFDP data. It is not (easily) possible to fetch
+ * SFDP after probe time and we need it for the sysfs access.
+ */
+ for (i = 0; i < header.nph; i++) {
+ param_header = &param_headers[i];
+ sfdp_size = max_t(size_t, sfdp_size,
+ SFDP_PARAM_HEADER_PTP(param_header) +
+ SFDP_PARAM_HEADER_PARAM_LEN(param_header));
+ }
+
+ /*
+ * Limit the total size to a reasonable value to avoid allocating too
+ * much memory just of because the flash returned some insane values.
+ */
+ if (sfdp_size > PAGE_SIZE) {
+ dev_dbg(dev, "SFDP data (%zu) too big, truncating\n",
+ sfdp_size);
+ sfdp_size = PAGE_SIZE;
+ }
+
+ sfdp = devm_kzalloc(dev, sizeof(*sfdp), GFP_KERNEL);
+ if (!sfdp) {
+ err = -ENOMEM;
+ goto exit;
+ }
+
+ /*
+ * The SFDP is organized in chunks of DWORDs. Thus, in theory, the
+ * sfdp_size should be a multiple of DWORDs. But in case a flash
+ * is not spec compliant, make sure that we have enough space to store
+ * the complete SFDP data.
+ */
+ sfdp->num_dwords = DIV_ROUND_UP(sfdp_size, sizeof(*sfdp->dwords));
+ sfdp->dwords = devm_kcalloc(dev, sfdp->num_dwords,
+ sizeof(*sfdp->dwords), GFP_KERNEL);
+ if (!sfdp->dwords) {
+ err = -ENOMEM;
+ devm_kfree(dev, sfdp);
+ goto exit;
+ }
+
+ err = spi_nor_read_sfdp(nor, 0, sfdp_size, sfdp->dwords);
+ if (err < 0) {
+ dev_dbg(dev, "failed to read SFDP data\n");
+ devm_kfree(dev, sfdp->dwords);
+ devm_kfree(dev, sfdp);
+ goto exit;
+ }
+
+ nor->sfdp = sfdp;
+
+ /*
* Check other parameter headers to get the latest revision of
* the basic flash parameter table.
*/