diff --git a/drivers/dma/dma_mcux_smartdma.c b/drivers/dma/dma_mcux_smartdma.c index 9899797ae53..86663dd02e8 100644 --- a/drivers/dma/dma_mcux_smartdma.c +++ b/drivers/dma/dma_mcux_smartdma.c @@ -19,30 +19,14 @@ LOG_MODULE_REGISTER(dma_mcux_smartdma, CONFIG_DMA_LOG_LEVEL); -/* SMARTDMA peripheral registers, taken from MCUX driver implementation*/ -struct smartdma_periph { - volatile uint32_t BOOT; - volatile uint32_t CTRL; - volatile uint32_t PC; - volatile uint32_t SP; - volatile uint32_t BREAK_ADDR; - volatile uint32_t BREAK_VECT; - volatile uint32_t EMER_VECT; - volatile uint32_t EMER_SEL; - volatile uint32_t ARM2SMARTDMA; - volatile uint32_t SMARTDMA2ARM; - volatile uint32_t PENDTRAP; -}; - struct dma_mcux_smartdma_config { - struct smartdma_periph *base; + SMARTDMA_Type *base; void (*irq_config_func)(const struct device *dev); void (**smartdma_progs)(void); }; struct dma_mcux_smartdma_data { - uint32_t smartdma_stack[32]; /* Stack for SMARTDMA */ /* Installed DMA callback and user data */ dma_callback_t callback; void *user_data; @@ -53,22 +37,13 @@ struct dma_mcux_smartdma_data { /* These bits are set when the SMARTDMA boots, cleared to reset it */ #define SMARTDMA_BOOT 0x11 -static inline bool dma_mcux_smartdma_prog_is_mipi(uint32_t prog) -{ - return ((prog == kSMARTDMA_MIPI_RGB565_DMA) || - (prog == kSMARTDMA_MIPI_RGB888_DMA) || - (prog == kSMARTDMA_MIPI_RGB565_R180_DMA) || - (prog == kSMARTDMA_MIPI_RGB888_R180_DMA)); -} - /* Configure a channel */ static int dma_mcux_smartdma_configure(const struct device *dev, uint32_t channel, struct dma_config *config) { const struct dma_mcux_smartdma_config *dev_config = dev->config; struct dma_mcux_smartdma_data *data = dev->data; - uint32_t prog_idx; - bool swap_pixels = false; + uint32_t prog_idx = config->dma_slot; /* SMARTDMA does not have channels */ ARG_UNUSED(channel); @@ -79,68 +54,11 @@ static int dma_mcux_smartdma_configure(const struct device *dev, /* Reset smartDMA */ SMARTDMA_Reset(); - /* - * The dma_slot parameter is used to determine which SMARTDMA program - * to run. First, convert the Zephyr define to a HAL enum. - */ - switch (config->dma_slot) { - case DMA_SMARTDMA_MIPI_RGB565_DMA: - prog_idx = kSMARTDMA_MIPI_RGB565_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB888_DMA: - prog_idx = kSMARTDMA_MIPI_RGB888_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB565_180: - prog_idx = kSMARTDMA_MIPI_RGB565_R180_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB888_180: - prog_idx = kSMARTDMA_MIPI_RGB888_R180_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB565_DMA_SWAP: - swap_pixels = true; - prog_idx = kSMARTDMA_MIPI_RGB565_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB888_DMA_SWAP: - swap_pixels = true; - prog_idx = kSMARTDMA_MIPI_RGB888_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB565_180_SWAP: - swap_pixels = true; - prog_idx = kSMARTDMA_MIPI_RGB565_R180_DMA; - break; - case DMA_SMARTDMA_MIPI_RGB888_180_SWAP: - swap_pixels = true; - prog_idx = kSMARTDMA_MIPI_RGB888_R180_DMA; - break; - default: - prog_idx = config->dma_slot; - break; - } - - if (dma_mcux_smartdma_prog_is_mipi(prog_idx)) { - smartdma_dsi_param_t param = {.disablePixelByteSwap = (swap_pixels == false)}; - - if (config->block_count != 1) { - return -ENOTSUP; - } - /* Setup SMARTDMA */ - param.p_buffer = (uint8_t *)config->head_block->source_address; - param.buffersize = config->head_block->block_size; - param.smartdma_stack = data->smartdma_stack; - /* Save configuration to SMARTDMA */ - dev_config->base->ARM2SMARTDMA = (uint32_t)(¶m); - } else { - /* For other cases, we simply pass the entire DMA config - * struct to the SMARTDMA. The user's application could either - * populate this structure with data, or choose to write - * different configuration data to the SMARTDMA in their - * application - */ - dev_config->base->ARM2SMARTDMA = ((uint32_t)config); - } + /* Write the head block pointer directly to SMARTDMA */ + dev_config->base->ARM2EZH = (uint32_t)config->head_block; /* Save program */ - dev_config->base->BOOT = (uint32_t)dev_config->smartdma_progs[prog_idx]; - LOG_DBG("Boot address set to 0x%X", dev_config->base->BOOT); + dev_config->base->BOOTADR = (uint32_t)dev_config->smartdma_progs[prog_idx]; + LOG_DBG("Boot address set to 0x%X", dev_config->base->BOOTADR); return 0; } @@ -175,15 +93,7 @@ static int dma_mcux_smartdma_stop(const struct device *dev, uint32_t channel) static int dma_mcux_smartdma_init(const struct device *dev) { const struct dma_mcux_smartdma_config *config = dev->config; - /* - * Initialize the SMARTDMA with firmware. The default firmware - * from MCUX SDK is a display firmware, which has functions - * implemented above in the dma configuration function. The - * user can install another firmware using `dma_smartdma_install_fw` - */ - SMARTDMA_Init((uint32_t)config->smartdma_progs, - s_smartdmaDisplayFirmware, - SMARTDMA_DISPLAY_FIRMWARE_SIZE); + SMARTDMA_InitWithoutFirmware(); config->irq_config_func(dev); return 0; @@ -236,7 +146,7 @@ static const struct dma_driver_api dma_mcux_smartdma_api = { } \ \ static const struct dma_mcux_smartdma_config smartdma_##n##_config = { \ - .base = (struct smartdma_periph *)DT_INST_REG_ADDR(n), \ + .base = (SMARTDMA_Type *)DT_INST_REG_ADDR(n), \ .smartdma_progs = (void (**)(void))DT_INST_PROP(n, program_mem),\ .irq_config_func = dma_mcux_smartdma_config_func_##n, \ }; \ diff --git a/drivers/mipi_dsi/dsi_mcux_2l.c b/drivers/mipi_dsi/dsi_mcux_2l.c index 53201cd123f..9ca8a60ca99 100644 --- a/drivers/mipi_dsi/dsi_mcux_2l.c +++ b/drivers/mipi_dsi/dsi_mcux_2l.c @@ -19,6 +19,9 @@ #include #include #include +#ifdef CONFIG_MIPI_DSI_MCUX_2L_SMARTDMA +#include +#endif #include @@ -47,6 +50,8 @@ struct mcux_mipi_dsi_data { dsi_handle_t mipi_handle; struct k_sem transfer_sem; #ifdef CONFIG_MIPI_DSI_MCUX_2L_SMARTDMA + smartdma_dsi_param_t smartdma_params __aligned(4); + uint32_t smartdma_stack[32]; uint8_t dma_slot; #endif }; @@ -94,7 +99,6 @@ static int dsi_mcux_tx_color(const struct device *dev, uint8_t channel, const struct mcux_mipi_dsi_config *config = dev->config; struct mcux_mipi_dsi_data *data = dev->data; struct dma_config dma_cfg = {0}; - struct dma_block_config block = {0}; int ret; if (channel != 0) { @@ -102,12 +106,12 @@ static int dsi_mcux_tx_color(const struct device *dev, uint8_t channel, } /* Configure smartDMA device, and run transfer */ - block.source_address = (uint32_t)msg->tx_buf; - block.block_size = msg->tx_len; + data->smartdma_params.p_buffer = msg->tx_buf; + data->smartdma_params.buffersize = msg->tx_len; dma_cfg.dma_callback = dsi_mcux_dma_cb; dma_cfg.user_data = (struct device *)dev; - dma_cfg.head_block = █ + dma_cfg.head_block = (struct dma_block_config *)&data->smartdma_params; dma_cfg.block_count = 1; dma_cfg.dma_slot = data->dma_slot; dma_cfg.channel_direction = MEMORY_TO_PERIPHERAL; @@ -250,13 +254,15 @@ static int dsi_mcux_attach(const struct device *dev, switch (mdev->pixfmt) { case MIPI_DSI_PIXFMT_RGB888: - data->dma_slot = DMA_SMARTDMA_MIPI_RGB888_DMA; + data->dma_slot = kSMARTDMA_MIPI_RGB888_DMA; + data->smartdma_params.disablePixelByteSwap = true; break; case MIPI_DSI_PIXFMT_RGB565: + data->dma_slot = kSMARTDMA_MIPI_RGB565_DMA; if (IS_ENABLED(CONFIG_MIPI_DSI_MCUX_2L_SWAP16)) { - data->dma_slot = DMA_SMARTDMA_MIPI_RGB565_DMA_SWAP; + data->smartdma_params.disablePixelByteSwap = false; } else { - data->dma_slot = DMA_SMARTDMA_MIPI_RGB565_DMA; + data->smartdma_params.disablePixelByteSwap = true; } break; default: @@ -264,6 +270,12 @@ static int dsi_mcux_attach(const struct device *dev, mdev->pixfmt); return -ENODEV; } + + data->smartdma_params.smartdma_stack = data->smartdma_stack; + + dma_smartdma_install_fw(config->smart_dma, + (uint8_t *)s_smartdmaDisplayFirmware, + s_smartdmaDisplayFirmwareSize); #else struct mcux_mipi_dsi_data *data = dev->data; diff --git a/dts/arm/nxp/nxp_rt5xx_common.dtsi b/dts/arm/nxp/nxp_rt5xx_common.dtsi index 79f1aec091c..8467b231cc9 100644 --- a/dts/arm/nxp/nxp_rt5xx_common.dtsi +++ b/dts/arm/nxp/nxp_rt5xx_common.dtsi @@ -587,7 +587,7 @@ smartdma: dma@27020 { compatible = "nxp,smartdma"; - reg = <0x27020 0x1000>; + reg = <0x27000 0x1000>; program-mem = <0x24100000>; interrupts = <73 0>; status = "disabled"; diff --git a/include/zephyr/drivers/dma/dma_mcux_smartdma.h b/include/zephyr/drivers/dma/dma_mcux_smartdma.h index 0e09d348d8f..5171a5491ce 100644 --- a/include/zephyr/drivers/dma/dma_mcux_smartdma.h +++ b/include/zephyr/drivers/dma/dma_mcux_smartdma.h @@ -7,34 +7,6 @@ #ifndef ZEPHYR_INCLUDE_DRIVERS_DMA_MCUX_SMARTDMA_H_ #define ZEPHYR_INCLUDE_DRIVERS_DMA_MCUX_SMARTDMA_H_ -/* Write RGB565 data to MIPI DSI via DMA. */ -#define DMA_SMARTDMA_MIPI_RGB565_DMA 0 -/* Write RGB888 data to MIPI DSI via DMA */ -#define DMA_SMARTDMA_MIPI_RGB888_DMA 1 -/* Write RGB565 data to MIPI DSI via DMA. Rotate output data by 180 degrees */ -#define DMA_SMARTDMA_MIPI_RGB565_180 2 -/* Write RGB888 data to MIPI DSI via DMA. Rotate output data by 180 degrees */ -#define DMA_SMARTDMA_MIPI_RGB888_180 3 - -/* Write RGB565 data to MIPI DSI via DMA. Swap data endianness, so that - * little endian RGB565 data will be written big endian style. - */ -#define DMA_SMARTDMA_MIPI_RGB565_DMA_SWAP 4 -/* Write RGB888 data to MIPI DSI via DMA. Swap data endianness, so that - * little endian RGB888 data will be written big endian style. - */ -#define DMA_SMARTDMA_MIPI_RGB888_DMA_SWAP 5 -/* Write RGB565 data to MIPI DSI via DMA. Rotate output data by 180 degrees, - * and swap data endianness - */ -#define DMA_SMARTDMA_MIPI_RGB565_180_SWAP 6 -/* Write RGB888 data to MIPI DSI via DMA. Rotate output data by 180 degrees, - * and swap data endianness - */ -#define DMA_SMARTDMA_MIPI_RGB888_180_SWAP 7 - - - /** * @brief install SMARTDMA firmware * @@ -48,6 +20,4 @@ void dma_smartdma_install_fw(const struct device *dev, uint8_t *firmware, uint32_t len); -#define GD32_DMA_FEATURES_FIFO_THRESHOLD(threshold) (threshold & 0x3) - #endif /* ZEPHYR_INCLUDE_DRIVERS_DMA_MCUX_SMARTDMA_H_ */