From ea3cd9f1faa320053e7bc8926be47fc89467d54f Mon Sep 17 00:00:00 2001 From: Tom Burdick Date: Tue, 4 Jan 2022 12:16:39 -0600 Subject: [PATCH] dma: Add suspend and resume API This adds the necessary API calls to support the hardware feature of suspending and resuming active DMA channels. The hardware feature is supported by at least Synopsys's DesignWare DMA and NXP's eDMA. Signed-off-by: Tom Burdick --- include/drivers/dma.h | 59 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 59 insertions(+) diff --git a/include/drivers/dma.h b/include/drivers/dma.h index 8a93544514b..f4c49fe08ce 100644 --- a/include/drivers/dma.h +++ b/include/drivers/dma.h @@ -239,6 +239,10 @@ typedef int (*dma_api_start)(const struct device *dev, uint32_t channel); typedef int (*dma_api_stop)(const struct device *dev, uint32_t channel); +typedef int (*dma_api_suspend)(const struct device *dev, uint32_t channel); + +typedef int (*dma_api_resume)(const struct device *dev, uint32_t channel); + typedef int (*dma_api_get_status)(const struct device *dev, uint32_t channel, struct dma_status *status); @@ -263,6 +267,8 @@ __subsystem struct dma_driver_api { dma_api_reload reload; dma_api_start start; dma_api_stop stop; + dma_api_suspend suspend; + dma_api_resume resume; dma_api_get_status get_status; dma_api_chan_filter chan_filter; }; @@ -368,6 +374,59 @@ static inline int z_impl_dma_stop(const struct device *dev, uint32_t channel) return api->stop(dev, channel); } + +/** + * @brief Suspend a DMA channel transfer + * + * Implementations must check the validity of the channel state and ID passed + * in and return -EINVAL if either are invalid. + * + * @param dev Pointer to the device structure for the driver instance. + * @param channel Numeric identification of the channel to suspend + * + * @retval 0 If successful. + * @retval -ENOSYS If not implemented. + * @retval -EINVAL If invalid channel id or state. + * @retval -errno Other negative errno code failure. + */ +__syscall int dma_suspend(const struct device *dev, uint32_t channel); + +static inline int z_impl_dma_suspend(const struct device *dev, uint32_t channel) +{ + const struct dma_driver_api *api = (const struct dma_driver_api *)dev->api; + + if (api->suspend == NULL) { + return -ENOSYS; + } + return api->suspend(dev, channel); +} + +/** + * @brief Resume a DMA channel transfer + * + * Implementations must check the validity of the channel state and ID passed + * in and return -EINVAL if either are invalid. + * + * @param dev Pointer to the device structure for the driver instance. + * @param channel Numeric identification of the channel to resume + * + * @retval 0 If successful. + * @retval -ENOSYS If not implemented + * @retval -EINVAL If invalid channel id or state. + * @retval -errno Other negative errno code failure. + */ +__syscall int dma_resume(const struct device *dev, uint32_t channel); + +static inline int z_impl_dma_resume(const struct device *dev, uint32_t channel) +{ + const struct dma_driver_api *api = (const struct dma_driver_api *)dev->api; + + if (api->resume == NULL) { + return -ENOSYS; + } + return api->resume(dev, channel); +} + /** * @brief request DMA channel. *