drivers: flash: add API to access SFDP region of serial flash devices

Some flash drivers are capable of issuing a JESD216 READ_SFDP command
to read serial flash discoverable parameters.  Allow applications and
utilities access to that capability where it's supported.

Signed-off-by: Peter A. Bigot <pab@pabigot.com>
This commit is contained in:
Peter A. Bigot 2020-06-03 19:55:54 -05:00 committed by Anas Nashif
commit 4eb8d9dd9e
4 changed files with 67 additions and 1 deletions

View file

@ -1969,6 +1969,7 @@ PREDEFINED = "CONFIG_ARCH_HAS_CUSTOM_BUSY_WAIT" \
"CONFIG_DEVICE_IDLE_PM" \ "CONFIG_DEVICE_IDLE_PM" \
"CONFIG_ERRNO" \ "CONFIG_ERRNO" \
"CONFIG_EXECUTION_BENCHMARKING" \ "CONFIG_EXECUTION_BENCHMARKING" \
"CONFIG_FLASH_JESD216_API" \
"CONFIG_FLASH_PAGE_LAYOUT" \ "CONFIG_FLASH_PAGE_LAYOUT" \
"CONFIG_FPU" \ "CONFIG_FPU" \
"CONFIG_FPU_SHARING" \ "CONFIG_FPU_SHARING" \

View file

@ -23,6 +23,14 @@ config FLASH_JESD216
Selected by drivers that support JESD216-compatible flash Selected by drivers that support JESD216-compatible flash
devices to enable building a common support module. devices to enable building a common support module.
config FLASH_JESD216_API
bool "Provide API to read JESD216 flash parameters"
help
This option extends the Zephyr flash API with the ability
to access the Serial Flash Discoverable Parameter section
allowing runtime determination of serial flash parameters
for flash drivers that expose this capability.
menuconfig FLASH menuconfig FLASH
bool "Flash hardware support" bool "Flash hardware support"
help help

View file

@ -72,4 +72,17 @@ static inline size_t z_vrfy_flash_get_page_count(struct device *dev)
} }
#include <syscalls/flash_get_page_count_mrsh.c> #include <syscalls/flash_get_page_count_mrsh.c>
#endif #endif /* CONFIG_FLASH_PAGE_LAYOUT */
#ifdef CONFIG_FLASH_JESD216_API
static inline int z_vrfy_flash_sfdp_read(struct device *dev, off_t offset,
void *data, size_t len)
{
Z_OOPS(Z_SYSCALL_DRIVER_FLASH(dev, sfdp_read));
Z_OOPS(Z_SYSCALL_MEMORY_WRITE(data, len));
return z_impl_flash_sfdp_read(dev, offset, data, len);
}
#include <syscalls/flash_sfdp_read.c>
#endif /* CONFIG_FLASH_JESD216_API */

View file

@ -81,6 +81,9 @@ typedef void (*flash_api_pages_layout)(struct device *dev,
size_t *layout_size); size_t *layout_size);
#endif /* CONFIG_FLASH_PAGE_LAYOUT */ #endif /* CONFIG_FLASH_PAGE_LAYOUT */
typedef int (*flash_api_sfdp_read)(struct device *dev, off_t offset,
void *data, size_t len);
__subsystem struct flash_driver_api { __subsystem struct flash_driver_api {
flash_api_read read; flash_api_read read;
flash_api_write write; flash_api_write write;
@ -90,6 +93,9 @@ __subsystem struct flash_driver_api {
#if defined(CONFIG_FLASH_PAGE_LAYOUT) #if defined(CONFIG_FLASH_PAGE_LAYOUT)
flash_api_pages_layout page_layout; flash_api_pages_layout page_layout;
#endif /* CONFIG_FLASH_PAGE_LAYOUT */ #endif /* CONFIG_FLASH_PAGE_LAYOUT */
#if defined(CONFIG_FLASH_JESD216_API)
flash_api_sfdp_read sfdp_read;
#endif /* CONFIG_FLASH_JESD216_API */
}; };
/** /**
@ -289,6 +295,44 @@ typedef bool (*flash_page_cb)(const struct flash_pages_info *info, void *data);
void flash_page_foreach(struct device *dev, flash_page_cb cb, void *data); void flash_page_foreach(struct device *dev, flash_page_cb cb, void *data);
#endif /* CONFIG_FLASH_PAGE_LAYOUT */ #endif /* CONFIG_FLASH_PAGE_LAYOUT */
#if defined(CONFIG_FLASH_JESD216_API)
/**
* @brief Read data from Serial Flash Discoverable Parameters
*
* This routine reads data from a serial flash device compatible with
* the JEDEC JESD216 standard for encoding flash memory
* characteristics.
*
* Availability of this API is conditional on selecting
* @c CONFIG_FLASH_JESD216_API and support of that functionality in
* the driver underlying @p dev.
*
* @param dev device from which parameters will be read
* @param offset address within the SFDP region containing data of interest
* @param data where the data to be read will be placed
* @param len the number of bytes of data to be read
*
* @retval 0 on success
* @retval -ENOTSUP if the flash driver does not support SFDP access
* @retval negative values for other errors.
*/
__syscall int flash_sfdp_read(struct device *dev, off_t offset,
void *data, size_t len);
static inline int z_impl_flash_sfdp_read(struct device *dev, off_t offset,
void *data, size_t len)
{
int rv = -ENOTSUP;
const struct flash_driver_api *api =
(const struct flash_driver_api *)dev->api;
if (api->sfdp_read != NULL) {
rv = api->sfdp_read(dev, offset, data, len);
}
return rv;
}
#endif /* CONFIG_FLASH_JESD216_API */
/** /**
* @brief Get the minimum write block size supported by the driver * @brief Get the minimum write block size supported by the driver
* *