aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorJoel Bodenmann <joel@seriouslyembedded.com>2015-07-12 01:43:23 +0200
committerJoel Bodenmann <joel@seriouslyembedded.com>2015-07-12 01:43:23 +0200
commit83bd8c21a35a14eef0c059dd8b730aa13e8eb99d (patch)
treeeeeb2a43cb5b417e67cceb76fadb2ae2af2830aa /drivers
parent64752ab52c61f053c0690cf36c712f4662bccfb1 (diff)
downloaduGFX-83bd8c21a35a14eef0c059dd8b730aa13e8eb99d.tar.gz
uGFX-83bd8c21a35a14eef0c059dd8b730aa13e8eb99d.tar.bz2
uGFX-83bd8c21a35a14eef0c059dd8b730aa13e8eb99d.zip
Adding DMA2D support to STM32LTDC driver
Diffstat (limited to 'drivers')
-rw-r--r--drivers/gdisp/STM32LTDC/gdisp_lld_STM32LTDC.c96
-rw-r--r--drivers/gdisp/STM32LTDC/gdisp_lld_config.h14
-rw-r--r--drivers/gdisp/STM32LTDC/stm32_dma2d.h18
3 files changed, 126 insertions, 2 deletions
diff --git a/drivers/gdisp/STM32LTDC/gdisp_lld_STM32LTDC.c b/drivers/gdisp/STM32LTDC/gdisp_lld_STM32LTDC.c
index a6a185ee..ebde3345 100644
--- a/drivers/gdisp/STM32LTDC/gdisp_lld_STM32LTDC.c
+++ b/drivers/gdisp/STM32LTDC/gdisp_lld_STM32LTDC.c
@@ -18,12 +18,20 @@
#undef GDISP_SCREEN_WIDTH
#endif
+#ifndef LTDC_USE_DMA2D
+ #define LTDC_USE_DMA2D FALSE
+#endif
+
#define GDISP_DRIVER_VMT GDISPVMT_STM32LTDC
#include "drivers/gdisp/STM32LTDC/gdisp_lld_config.h"
#include "src/gdisp/gdisp_driver.h"
#include "stm32_ltdc.h"
+#if LTDC_USE_DMA2D
+ #include "stm32_dma2d.h"
+#endif
+
typedef struct ltdcLayerConfig {
// frame
LLDCOLOR_TYPE *frame; // Frame buffer address
@@ -223,8 +231,9 @@ LLDSPEC bool_t gdisp_lld_init(GDisplay* g)
LTDC_Init();
// Initialise DMA2D
- //dma2dStart(&DMA2DD1, &dma2d_cfg);
- //dma2d_test();
+ #if LTDC_USE_DMA2D
+ dma2d_init();
+ #endif
// Finish Init the board
post_init_board(g);
@@ -362,4 +371,87 @@ LLDSPEC color_t gdisp_lld_get_pixel_color(GDisplay* g)
}
#endif
+#if LTDC_USE_DMA2D
+ static void dma2d_init(void)
+ {
+ // Enable DMA2D clock (DMA2DEN = 1)
+ RCC->AHB1ENR |= RCC_AHB1ENR_DMA2DEN;
+
+ // Output color format
+ #if GDISP_LLD_PIXELFORMAT == GDISP_PIXELFORMAT_RGB565
+ DMA2D->OPFCCR = OPFCCR_RGB565;
+ #elif GDISP_LLD_PIXELFORMAT == GDISP_PIXELFORMAT_RGB888
+ DMA2D->OPFCCR = OPFCCR_OPFCCR_RGB888;
+ #endif
+
+ // Foreground color format
+ #if GDISP_LLD_PIXELFORMAT == GDISP_PIXELFORMAT_RGB565
+ DMA2D->FGPFCCR = FGPFCCR_CM_RGB565;
+ #elif GDISP_LLD_PIXELFORMAT == GDISP_PIXELFORMAT_RGB888
+ DMA2D->FGPFCCR = FGPFCCR_CM_RGB888;
+ #endif
+ }
+
+ // Uses p.x,p.y p.cx,p.cy p.color
+ LLDSPEC void gdisp_lld_fill_area(GDisplay* g)
+ {
+ LLDCOLOR_TYPE c;
+
+ // Wait until DMA2D is ready
+ while (1) {
+ if (!(DMA2D->CR & DMA2D_CR_START)) {
+ break;
+ }
+ }
+
+ c = gdispColor2Native(g->p.color);
+
+ // Output color register
+ DMA2D->OCOLR = (uint32_t)c;
+
+ // Output memory address register
+ DMA2D->OMAR = g->p.y * g->g.Width * LTDC_PIXELBYTES + g->p.x * LTDC_PIXELBYTES + (uint32_t)driverCfg.bglayer.frame;
+
+ // Output offset register (in pixels)
+ DMA2D->OOR = g->g.Width - g->p.cx;
+
+ // PL (pixel per lines to be transferred); NL (number of lines)
+ DMA2D->NLR = (g->p.cx << 16) | (g->p.cy);
+
+ // Set MODE to R2M and Start the process
+ DMA2D->CR = DMA2D_CR_MODE_R2M | DMA2D_CR_START;
+ }
+
+ // Uses p.x,p.y p.cx,p.cy p.x1,p.y1 (=srcx,srcy) p.x2 (=srccx), p.ptr (=buffer)
+ LLDSPEC void gdisp_lld_blit_area(GDisplay* g)
+ {
+ // Wait until DMA2D is ready
+ while (1) {
+ if (!(DMA2D->CR & DMA2D_CR_START)) {
+ break;
+ }
+ }
+
+ // Foreground memory address register
+ DMA2D->FGMAR = g->p.y1 * g->p.x2 * LTDC_PIXELBYTES + g->p.x1 * LTDC_PIXELBYTES + (uint32_t)g->p.ptr;
+
+ // Foreground offset register (expressed in pixels)
+ DMA2D->FGOR = g->p.x2 - g->p.cx;
+
+ // Output memory address register
+ DMA2D->OMAR = g->p.y * g->g.Width * LTDC_PIXELBYTES + g->p.x * LTDC_PIXELBYTES + (uint32_t)driverCfg.bglayer.frame;
+
+ // Output offset register (expressed in pixels)
+ DMA2D->OOR = g->g.Width - g->p.cx;
+
+ // PL (pixel per lines to be transferred); NL (number of lines)
+ DMA2D->NLR = (g->p.cx << 16) | (g->p.cy);
+
+ // Set MODE to M2M and Start the process
+ DMA2D->CR = DMA2D_CR_MODE_M2M | DMA2D_CR_START;
+ }
+
+#endif /* LTDC_USE_DMA2D */
+
+
#endif /* GFX_USE_GDISP */
diff --git a/drivers/gdisp/STM32LTDC/gdisp_lld_config.h b/drivers/gdisp/STM32LTDC/gdisp_lld_config.h
index 29e016ce..c661f67c 100644
--- a/drivers/gdisp/STM32LTDC/gdisp_lld_config.h
+++ b/drivers/gdisp/STM32LTDC/gdisp_lld_config.h
@@ -14,11 +14,25 @@
/* Driver hardware support. */
/*===========================================================================*/
+#define LTDC_USE_DMA2D TRUE
#define GDISP_HARDWARE_DRAWPIXEL TRUE
#define GDISP_HARDWARE_PIXELREAD TRUE
#define GDISP_HARDWARE_CONTROL TRUE
#define GDISP_LLD_PIXELFORMAT GDISP_PIXELFORMAT_RGB565
+
+/*===========================================================================*/
+/* Don't change stuff below this line. Please. */
+/*===========================================================================*/
+
+#if LTDC_USE_DMA2D
+ #define GDISP_HARDWARE_FILLS TRUE
+ #define GDISP_HARDWARE_BITFILLS TRUE
+#else
+ #define GDISP_HARDWARE_FILLS FALSE
+ #define GDISP_HARDWARE_BITFILLS FALSE
+#endif /* GDISP_USE_DMA2D */
+
#endif /* GFX_USE_GDISP */
#endif /* _GDISP_LLD_CONFIG_H */
diff --git a/drivers/gdisp/STM32LTDC/stm32_dma2d.h b/drivers/gdisp/STM32LTDC/stm32_dma2d.h
new file mode 100644
index 00000000..d3374d05
--- /dev/null
+++ b/drivers/gdisp/STM32LTDC/stm32_dma2d.h
@@ -0,0 +1,18 @@
+#ifndef _STM32_DMA2D_H
+#define _STM32_DMA2D_H
+
+#define OPFCCR_ARGB8888 0x00
+#define OPFCCR_RGB888 0x01
+#define OPFCCR_RGB565 0x02
+#define OPFCCR_ARGB1555 0x03
+#define OPFCCR_ARGB4444 0x04
+
+#define FGPFCCR_CM_RGB888 0x01
+#define FGPFCCR_CM_RGB565 0x02
+
+#define DMA2D_CR_MODE_R2M ((uint32_t)0x00030000) /* Register-to-memory mode */
+#define DMA2D_CR_MODE_M2M ((uint32_t)0x00000000) /* Register-to-memory mode */
+
+static void dma2d_init(void);
+
+#endif /* _STM32_DMA2D_H */