From 9921d74243cad8b8f18cb1dc0265a502f8e3265c Mon Sep 17 00:00:00 2001 From: mobyfab Date: Mon, 17 Sep 2012 18:49:34 +0200 Subject: [PATCH 1/7] Testing DMA --- drivers/gdisp/SSD1963/gdisp_lld.c | 42 ++++++++++++++++++++++++++++++- 1 file changed, 41 insertions(+), 1 deletion(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index 5a80f691..2b4fcaf5 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -184,6 +184,10 @@ bool_t GDISP_LLD(init)(void) { /* Initialise the display */ #if defined(LCD_USE_FSMC) + +#if defined(LCD_USE_DMA) + dmaStreamAllocate(LCD_DMA_STREAM, 0, NULL, NULL); +#endif //#ifdef LCD_USE_DMA #if defined(STM32F1XX) || defined(STM32F3XX) /* FSMC setup for F1/F3 */ @@ -380,9 +384,24 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { GDISP_LLD(setwindow)(x, y, x+cx-1, y+cy-1); GDISP_LLD(writestreamstart)(); +#if defined(LCD_USE_DMA) + if (area > 1000) { // Do not use DMA for small areas + dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); + dmaStreamSetMemory0(LCD_DMA_STREAM, LCD_RAM); + dmaStreamSetTransactionSize(LCD_DMA_STREAM, area); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); + + while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(1); + } + else { + for(index = 0; index < area; index++) + GDISP_LLD(writedata)(color); + } +#else for(index = 0; index < area; index++) GDISP_LLD(writedata)(color); - } +#endif //#ifdef LCD_USE_DMA +} #endif #if GDISP_HARDWARE_BITFILLS || defined(__DOXYGEN__) @@ -418,9 +437,30 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { endy = y + cy; lg = srccx - cx; buffer += srcx + srcy * srccx; + + +#if defined(LCD_USE_DMA) + uint32_t area = cx*cy; + if (area > 1000) { // Do not use DMA for small areas + dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); + dmaStreamSetMemory0(LCD_DMA_STREAM, LCD_RAM); + dmaStreamSetTransactionSize(LCD_DMA_STREAM, area); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_PINC | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); + + while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(1); + } + else { for(; y < endy; y++, buffer += lg) for(x=srcx; x < endx; x++) GDISP_LLD(writedata)(*buffer++); + } +#else + for(; y < endy; y++, buffer += lg) + for(x=srcx; x < endx; x++) + GDISP_LLD(writedata)(*buffer++); +#endif //#ifdef LCD_USE_DMA + + } #endif From ac228656ae741e7f9253e4c9238b702cad896cd8 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Mon, 17 Sep 2012 19:35:10 +0200 Subject: [PATCH 2/7] DMA fixes, splitting the requests since 65535 is the max count --- drivers/gdisp/SSD1963/gdisp_lld.c | 26 ++++++++++++++++++-------- 1 file changed, 18 insertions(+), 8 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index 2b4fcaf5..50f163bb 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -388,10 +388,15 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { if (area > 1000) { // Do not use DMA for small areas dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); dmaStreamSetMemory0(LCD_DMA_STREAM, LCD_RAM); - dmaStreamSetTransactionSize(LCD_DMA_STREAM, area); - dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); - - while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(1); + uint32_t i; + uint16_t splitarea; + for (i = (area/65535)+1; i > 0; i--) { + if (i <= 1) splitarea = area%65535; + else splitarea = 65535; + dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); + while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(5); + } } else { for(index = 0; index < area; index++) @@ -444,10 +449,15 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { if (area > 1000) { // Do not use DMA for small areas dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); dmaStreamSetMemory0(LCD_DMA_STREAM, LCD_RAM); - dmaStreamSetTransactionSize(LCD_DMA_STREAM, area); - dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_PINC | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); - - while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(1); + uint32_t i; + uint16_t splitarea; + for (i = (area/65535)+1; i > 0; i--) { + if (i <= 1) splitarea = area%65535; + else splitarea = 65535; + dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_PINC | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); + while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(5); + } } else { for(; y < endy; y++, buffer += lg) From 4991834cbbc9714e63361cd446ddd39bec35232b Mon Sep 17 00:00:00 2001 From: mobyfab Date: Mon, 17 Sep 2012 22:51:02 +0200 Subject: [PATCH 3/7] DMA fixed and tested for SSD1963 --- drivers/gdisp/SSD1963/gdisp_lld.c | 67 +++++++++++-------------------- 1 file changed, 24 insertions(+), 43 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index 50f163bb..c385d13b 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -184,11 +184,13 @@ bool_t GDISP_LLD(init)(void) { /* Initialise the display */ #if defined(LCD_USE_FSMC) - -#if defined(LCD_USE_DMA) - dmaStreamAllocate(LCD_DMA_STREAM, 0, NULL, NULL); -#endif //#ifdef LCD_USE_DMA - + + #if defined(LCD_USE_DMA) + if (dmaStreamAllocate(LCD_DMA_STREAM, 0, NULL, NULL)) chSysHalt(); + dmaStreamSetMemory0(LCD_DMA_STREAM, &LCD_RAM); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PL(0) | STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M); + #endif + #if defined(STM32F1XX) || defined(STM32F3XX) /* FSMC setup for F1/F3 */ rccEnableAHB(RCC_AHBENR_FSMCEN, 0); @@ -384,27 +386,18 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { GDISP_LLD(setwindow)(x, y, x+cx-1, y+cy-1); GDISP_LLD(writestreamstart)(); -#if defined(LCD_USE_DMA) - if (area > 1000) { // Do not use DMA for small areas +#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) + uint16_t i, splitarea; dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); - dmaStreamSetMemory0(LCD_DMA_STREAM, LCD_RAM); - uint32_t i; - uint16_t splitarea; for (i = (area/65535)+1; i > 0; i--) { - if (i <= 1) splitarea = area%65535; - else splitarea = 65535; + if (i <= 1) splitarea = area%65535; else splitarea = 65535; dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); - dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); - while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(5); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); } - } - else { - for(index = 0; index < area; index++) - GDISP_LLD(writedata)(color); - } #else - for(index = 0; index < area; index++) - GDISP_LLD(writedata)(color); + for(index = 0; index < area; index++) + GDISP_LLD(writedata)(color); #endif //#ifdef LCD_USE_DMA } #endif @@ -444,33 +437,21 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { buffer += srcx + srcy * srccx; -#if defined(LCD_USE_DMA) - uint32_t area = cx*cy; - if (area > 1000) { // Do not use DMA for small areas +#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) + uint32_t area = cx*cy; + uint16_t i, splitarea; dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); - dmaStreamSetMemory0(LCD_DMA_STREAM, LCD_RAM); - uint32_t i; - uint16_t splitarea; for (i = (area/65535)+1; i > 0; i--) { - if (i <= 1) splitarea = area%65535; - else splitarea = 65535; + if (i <= 1) splitarea = area%65535; else splitarea = 65535; dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); - dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_PINC | STM32_DMA_CR_DIR_M2M | STM32_DMA_CR_EN); - while ((LCD_DMA_STREAM)->stream->NDTR > 0) chThdSleepMilliseconds(5); - } - } - else { - for(; y < endy; y++, buffer += lg) - for(x=srcx; x < endx; x++) - GDISP_LLD(writedata)(*buffer++); - } + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); + } #else - for(; y < endy; y++, buffer += lg) - for(x=srcx; x < endx; x++) - GDISP_LLD(writedata)(*buffer++); + for(; y < endy; y++, buffer += lg) + for(x=srcx; x < endx; x++) + GDISP_LLD(writedata)(*buffer++); #endif //#ifdef LCD_USE_DMA - - } #endif From b9618a99d7904565449fde300f73eec5995985bf Mon Sep 17 00:00:00 2001 From: mobyfab Date: Tue, 18 Sep 2012 11:59:50 +0200 Subject: [PATCH 4/7] Cleaning GCC warnings for unused variables --- drivers/gdisp/SSD1963/gdisp_lld.c | 29 +++++++++++++++-------------- 1 file changed, 15 insertions(+), 14 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index c385d13b..a25efe7d 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -185,7 +185,7 @@ bool_t GDISP_LLD(init)(void) { #if defined(LCD_USE_FSMC) - #if defined(LCD_USE_DMA) + #if defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) if (dmaStreamAllocate(LCD_DMA_STREAM, 0, NULL, NULL)) chSysHalt(); dmaStreamSetMemory0(LCD_DMA_STREAM, &LCD_RAM); dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PL(0) | STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M); @@ -372,6 +372,7 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { * @notapi */ void GDISP_LLD(fillarea)(coord_t x, coord_t y, coord_t cx, coord_t cy, color_t color) { + #if GDISP_NEED_VALIDATION || GDISP_NEED_CLIP if (x < GDISP.clipx0) { cx -= GDISP.clipx0 - x; x = GDISP.clipx0; } if (y < GDISP.clipy0) { cy -= GDISP.clipy0 - y; y = GDISP.clipy0; } @@ -380,22 +381,23 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { if (y+cy > GDISP.clipy1) cy = GDISP.clipy1 - y; #endif - uint32_t index = 0, area; + uint32_t area; area = cx*cy; GDISP_LLD(setwindow)(x, y, x+cx-1, y+cy-1); GDISP_LLD(writestreamstart)(); -#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) +#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) uint16_t i, splitarea; dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); for (i = (area/65535)+1; i > 0; i--) { if (i <= 1) splitarea = area%65535; else splitarea = 65535; dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); - dmaStreamEnable(LCD_DMA_STREAM); - dmaWaitCompletion(LCD_DMA_STREAM); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); } #else + uint32_t index, for(index = 0; index < area; index++) GDISP_LLD(writedata)(color); #endif //#ifdef LCD_USE_DMA @@ -416,8 +418,6 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { * @notapi */ void GDISP_LLD(blitareaex)(coord_t x, coord_t y, coord_t cx, coord_t cy, coord_t srcx, coord_t srcy, coord_t srccx, const pixel_t *buffer) { - coord_t endx, endy; - unsigned lg; #if GDISP_NEED_VALIDATION || GDISP_NEED_CLIP if (x < GDISP.clipx0) { cx -= GDISP.clipx0 - x; srcx += GDISP.clipx0 - x; x = GDISP.clipx0; } @@ -431,23 +431,24 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { GDISP_LLD(setwindow)(x, y, x+cx-1, y+cy-1); GDISP_LLD(writestreamstart)(); - endx = srcx + cx; - endy = y + cy; - lg = srccx - cx; buffer += srcx + srcy * srccx; - -#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) +#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) uint32_t area = cx*cy; uint16_t i, splitarea; dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); for (i = (area/65535)+1; i > 0; i--) { if (i <= 1) splitarea = area%65535; else splitarea = 65535; dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); - dmaStreamEnable(LCD_DMA_STREAM); - dmaWaitCompletion(LCD_DMA_STREAM); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); } #else + coord_t endx, endy; + unsigned lg; + endx = srcx + cx; + endy = y + cy; + lg = srccx - cx; for(; y < endy; y++, buffer += lg) for(x=srcx; x < endx; x++) GDISP_LLD(writedata)(*buffer++); From 9718d39d30ae3519a1875eaf9d567753818fe497 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Tue, 18 Sep 2012 12:06:45 +0200 Subject: [PATCH 5/7] Fixed indentation --- drivers/gdisp/SSD1963/gdisp_lld.c | 140 +++++++++++++++--------------- 1 file changed, 70 insertions(+), 70 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index a25efe7d..d8fce7aa 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -254,7 +254,7 @@ bool_t GDISP_LLD(init)(void) { /* Screen size */ GDISP_LLD(writeindex)(SSD1963_SET_LCD_MODE); // GDISP_LLD(writedata)(0x0000); - GDISP_LLD(writedata)(0b00011000); + GDISP_LLD(writedata)(0b00011000); //Enabled dithering GDISP_LLD(writedata)(0x0000); GDISP_LLD(writedata)(mHIGH((SCREEN_WIDTH+1))); GDISP_LLD(writedata)((SCREEN_WIDTH+1)); @@ -327,16 +327,16 @@ void GDISP_LLD(setwindow)(coord_t x0, coord_t y0, coord_t x1, coord_t y1) { * else if (x1 >= GDISP.Width || y1 >= GDISP.Height || y1 < 0 || y2 < 0) return; * #endif */ - GDISP_LLD(writeindex)(SSD1963_SET_PAGE_ADDRESS); - GDISP_LLD(writedata)((y0 >> 8) & 0xFF); - GDISP_LLD(writedata)((y0 >> 0) & 0xFF); - GDISP_LLD(writedata)((y1 >> 8) & 0xFF); - GDISP_LLD(writedata)((y1 >> 0) & 0xFF); - GDISP_LLD(writeindex)(SSD1963_SET_COLUMN_ADDRESS); - GDISP_LLD(writedata)((x0 >> 8) & 0xFF); - GDISP_LLD(writedata)((x0 >> 0) & 0xFF); - GDISP_LLD(writedata)((x1 >> 8) & 0xFF); - GDISP_LLD(writedata)((x1 >> 0) & 0xFF); + GDISP_LLD(writeindex)(SSD1963_SET_PAGE_ADDRESS); + GDISP_LLD(writedata)((y0 >> 8) & 0xFF); + GDISP_LLD(writedata)((y0 >> 0) & 0xFF); + GDISP_LLD(writedata)((y1 >> 8) & 0xFF); + GDISP_LLD(writedata)((y1 >> 0) & 0xFF); + GDISP_LLD(writeindex)(SSD1963_SET_COLUMN_ADDRESS); + GDISP_LLD(writedata)((x0 >> 8) & 0xFF); + GDISP_LLD(writedata)((x0 >> 0) & 0xFF); + GDISP_LLD(writedata)((x1 >> 8) & 0xFF); + GDISP_LLD(writedata)((x1 >> 0) & 0xFF); } /** @@ -350,12 +350,12 @@ void GDISP_LLD(setwindow)(coord_t x0, coord_t y0, coord_t x1, coord_t y1) { */ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { #if GDISP_NEED_VALIDATION || GDISP_NEED_CLIP - if (x < GDISP.clipx0 || y < GDISP.clipy0 || x >= GDISP.clipx1 || y >= GDISP.clipy1) return; + if (x < GDISP.clipx0 || y < GDISP.clipy0 || x >= GDISP.clipx1 || y >= GDISP.clipy1) return; #endif - GDISP_LLD(setwindow)(x, y, x, y); - GDISP_LLD(writestreamstart)(); - GDISP_LLD(writedata)(color); + GDISP_LLD(setwindow)(x, y, x, y); + GDISP_LLD(writestreamstart)(); + GDISP_LLD(writedata)(color); } /* ---- Optional Routines ---- */ @@ -388,18 +388,18 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { GDISP_LLD(writestreamstart)(); #if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) - uint16_t i, splitarea; - dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); - for (i = (area/65535)+1; i > 0; i--) { - if (i <= 1) splitarea = area%65535; else splitarea = 65535; - dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); - dmaStreamEnable(LCD_DMA_STREAM); - dmaWaitCompletion(LCD_DMA_STREAM); - } + uint16_t i, splitarea; + dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); + for (i = (area/65535)+1; i > 0; i--) { + if (i <= 1) splitarea = area%65535; else splitarea = 65535; + dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); + } #else - uint32_t index, - for(index = 0; index < area; index++) - GDISP_LLD(writedata)(color); + uint32_t index, + for(index = 0; index < area; index++) + GDISP_LLD(writedata)(color); #endif //#ifdef LCD_USE_DMA } #endif @@ -434,24 +434,24 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { buffer += srcx + srcy * srccx; #if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) - uint32_t area = cx*cy; - uint16_t i, splitarea; - dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); - for (i = (area/65535)+1; i > 0; i--) { - if (i <= 1) splitarea = area%65535; else splitarea = 65535; - dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); - dmaStreamEnable(LCD_DMA_STREAM); - dmaWaitCompletion(LCD_DMA_STREAM); - } + uint32_t area = cx*cy; + uint16_t i, splitarea; + dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); + for (i = (area/65535)+1; i > 0; i--) { + if (i <= 1) splitarea = area%65535; else splitarea = 65535; + dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); + } #else - coord_t endx, endy; - unsigned lg; - endx = srcx + cx; - endy = y + cy; - lg = srccx - cx; - for(; y < endy; y++, buffer += lg) - for(x=srcx; x < endx; x++) - GDISP_LLD(writedata)(*buffer++); + coord_t endx, endy; + unsigned lg; + endx = srcx + cx; + endy = y + cy; + lg = srccx - cx; + for(; y < endy; y++, buffer += lg) + for(x=srcx; x < endx; x++) + GDISP_LLD(writedata)(*buffer++); #endif //#ifdef LCD_USE_DMA } #endif @@ -481,20 +481,20 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { /* NOT IMPLEMENTED YET */ /* - uint16_t size = x1 - x0 ; + uint16_t size = x1 - x0 ; - lld_lcdWriteIndex(SSD1963_SET_SCROLL_AREA); - lld_lcdWriteData((x0 >> 8) & 0xFF); - lld_lcdWriteData((x0 >> 0) & 0xFF); - lld_lcdWriteData((size >> 8) & 0xFF); - lld_lcdWriteData((size >> 0) & 0xFF); - lld_lcdWriteData(((lcd_height-x1) >> 8) & 0xFF); - lld_lcdWriteData(((lcd_height-x1) >> 0) & 0xFF); + lld_lcdWriteIndex(SSD1963_SET_SCROLL_AREA); + lld_lcdWriteData((x0 >> 8) & 0xFF); + lld_lcdWriteData((x0 >> 0) & 0xFF); + lld_lcdWriteData((size >> 8) & 0xFF); + lld_lcdWriteData((size >> 0) & 0xFF); + lld_lcdWriteData(((lcd_height-x1) >> 8) & 0xFF); + lld_lcdWriteData(((lcd_height-x1) >> 0) & 0xFF); - lld_lcdWriteIndex(SSD1963_SET_SCROLL_START); - lld_lcdWriteData((lines >> 8) & 0xFF); - lld_lcdWriteData((lines >> 0) & 0xFF); - */ + lld_lcdWriteIndex(SSD1963_SET_SCROLL_START); + lld_lcdWriteData((lines >> 8) & 0xFF); + lld_lcdWriteData((lines >> 0) & 0xFF); + */ } #endif @@ -522,37 +522,37 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { void GDISP_LLD(control)(unsigned what, void *value) { /* NOT IMPLEMENTED YET */ switch(what) { - case GDISP_CONTROL_POWER: + case GDISP_CONTROL_POWER: if (GDISP.Powermode == (gdisp_powermode_t)value) return; switch((gdisp_powermode_t)value) { case powerOff: - GDISP_LLD(writeindex)(SSD1963_EXIT_SLEEP_MODE); // leave sleep mode - chThdSleepMicroseconds(5000); - GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_OFF); - GDISP_LLD(writeindex)(SSD1963_SET_DEEP_SLEEP); // enter deep sleep mode + GDISP_LLD(writeindex)(SSD1963_EXIT_SLEEP_MODE); // leave sleep mode + chThdSleepMicroseconds(5000); + GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_OFF); + GDISP_LLD(writeindex)(SSD1963_SET_DEEP_SLEEP); // enter deep sleep mode break; case powerOn: - GDISP_LLD(readreg)(0x0000); chThdSleepMicroseconds(5000); // 2x Dummy reads to wake up from deep sleep - GDISP_LLD(readreg)(0x0000); chThdSleepMicroseconds(5000); - if (GDISP.Powermode != powerSleep) - GDISP_LLD(init)(); + GDISP_LLD(readreg)(0x0000); chThdSleepMicroseconds(5000); // 2x Dummy reads to wake up from deep sleep + GDISP_LLD(readreg)(0x0000); chThdSleepMicroseconds(5000); + if (GDISP.Powermode != powerSleep) + GDISP_LLD(init)(); GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_ON); break; case powerSleep: - GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_OFF); - GDISP_LLD(writeindex)(SSD1963_ENTER_SLEEP_MODE); // enter sleep mode - chThdSleepMicroseconds(5000); + GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_OFF); + GDISP_LLD(writeindex)(SSD1963_ENTER_SLEEP_MODE); // enter sleep mode + chThdSleepMicroseconds(5000); break; default: return; } GDISP.Powermode = (gdisp_powermode_t)value; return; - case GDISP_CONTROL_ORIENTATION: - if (GDISP.Orientation == (gdisp_orientation_t)value) - return; + case GDISP_CONTROL_ORIENTATION: + if (GDISP.Orientation == (gdisp_orientation_t)value) + return; switch((gdisp_orientation_t)value) { case portrait: /* Code here */ From 8e89654081ff1f62690f09a2fbcc23f0aed1f0a0 Mon Sep 17 00:00:00 2001 From: mobyfab Date: Tue, 18 Sep 2012 12:45:32 +0200 Subject: [PATCH 6/7] More info in the readme file. --- drivers/gdisp/SSD1963/readme.txt | 36 +++++++++++++++++++++++++++----- 1 file changed, 31 insertions(+), 5 deletions(-) diff --git a/drivers/gdisp/SSD1963/readme.txt b/drivers/gdisp/SSD1963/readme.txt index 7803cda0..f19ce24c 100644 --- a/drivers/gdisp/SSD1963/readme.txt +++ b/drivers/gdisp/SSD1963/readme.txt @@ -2,11 +2,37 @@ To use this driver: 1. Add in your halconf.h: a) #define HAL_USE_GDISP TRUE - b) Any optional high level driver defines (see gdisp.h) eg: GDISP_NEED_MULTITHREAD + b) Any optional high level driver defines (see gdisp.h) eg: #define GDISP_NEED_MULTITHREAD TRUE c) One (only) of: - #define LCD_USE_GPIO (Work in progress) + #define LCD_USE_GPIO #define LCD_USE_FSMC - d) Edit gdisp_lld_panel.h with your panel properties + d) If you want to use DMA (only works with FSMC): + #define LCD_USE_DMA + #define LCD_DMA_STREAM STM32_DMA2_STREAM6 //You can change the DMA channel according to your needs + +2. Edit gdisp_lld_panel.h with your panel properties -2. To your makefile add the following lines: - include $(LCDLIB)/drivers/gdisp/SSD1963/gdisp_lld.mk \ No newline at end of file +3. To your makefile add the following lines: + include $(LCDLIB)/drivers/gdisp/SSD1963/gdisp_lld.mk + + +Example FSMC config with DMA: + +#define SCREEN_WIDTH 480 +#define SCREEN_HEIGHT 272 + +#define LCD_USE_FSMC + +#define LCD_USE_DMA +#define LCD_DMA_STREAM STM32_DMA2_STREAM6 + +#if defined(LCD_USE_GPIO) + + #define LCD_CMD_PORT GPIOC + #define LCD_DATA_PORT GPIOD + + #define LCD_CS 0 + #define LCD_RS 1 + #define LCD_WR 2 + #define LCD_RD 3 +#endif \ No newline at end of file From da83b0955f86f22799186df294d0ab32488798fb Mon Sep 17 00:00:00 2001 From: mobyfab Date: Tue, 18 Sep 2012 22:55:02 +0200 Subject: [PATCH 7/7] Some cleaning. Fixed and tested DMA blitarea for SSD1963. --- drivers/gdisp/SSD1963/gdisp_lld.c | 119 ++++++++++++----------- drivers/gdisp/SSD1963/gdisp_lld_config.h | 4 +- src/touchpad.c | 8 +- 3 files changed, 71 insertions(+), 60 deletions(-) diff --git a/drivers/gdisp/SSD1963/gdisp_lld.c b/drivers/gdisp/SSD1963/gdisp_lld.c index d8fce7aa..ad261735 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld.c +++ b/drivers/gdisp/SSD1963/gdisp_lld.c @@ -185,22 +185,25 @@ bool_t GDISP_LLD(init)(void) { #if defined(LCD_USE_FSMC) - #if defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) - if (dmaStreamAllocate(LCD_DMA_STREAM, 0, NULL, NULL)) chSysHalt(); - dmaStreamSetMemory0(LCD_DMA_STREAM, &LCD_RAM); - dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PL(0) | STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M); - #endif + #if defined(STM32F1XX) || defined(STM32F3XX) + /* FSMC setup for F1/F3 */ + rccEnableAHB(RCC_AHBENR_FSMCEN, 0); - #if defined(STM32F1XX) || defined(STM32F3XX) - /* FSMC setup for F1/F3 */ - rccEnableAHB(RCC_AHBENR_FSMCEN, 0); - - #elif defined(STM32F4XX) || defined(STM32F2XX) - /* STM32F2-F4 FSMC init */ - rccEnableAHB3(RCC_AHB3ENR_FSMCEN, 0); - #else - #error "FSMC not implemented for this device" - #endif + #if defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) + #error "DMA not implemented for F1/F3 Devices" + #endif + #elif defined(STM32F4XX) || defined(STM32F2XX) + /* STM32F2-F4 FSMC init */ + rccEnableAHB3(RCC_AHB3ENR_FSMCEN, 0); + + #if defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) + if (dmaStreamAllocate(LCD_DMA_STREAM, 0, NULL, NULL)) chSysHalt(); + dmaStreamSetMemory0(LCD_DMA_STREAM, &LCD_RAM); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PL(0) | STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M); + #endif + #else + #error "FSMC not implemented for this device" + #endif /* set pins to FSMC mode */ IOBus busD = {GPIOD, (1 << 0) | (1 << 1) | (1 << 4) | (1 << 5) | (1 << 7) | (1 << 8) | @@ -222,14 +225,14 @@ bool_t GDISP_LLD(init)(void) { * This is actually not needed as already set by default after reset */ FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; - #elif defined(LCD_USE_GPIO) +#elif defined(LCD_USE_GPIO) IOBus busCMD = {LCD_CMD_PORT, (1 << LCD_CS) | (1 << LCD_RS) | (1 << LCD_WR) | (1 << LCD_RD), 0}; IOBus busDATA = {LCD_CMD_PORT, 0xFFFFF, 0}; palSetBusMode(&busCMD, PAL_MODE_OUTPUT_PUSHPULL); palSetBusMode(&busDATA, PAL_MODE_OUTPUT_PUSHPULL); - #else - #error "Please define LCD_USE_FSMC or LCD_USE_GPIO" +#else + #error "Please define LCD_USE_FSMC or LCD_USE_GPIO" #endif GDISP_LLD(writeindex)(SSD1963_SOFT_RESET); chThdSleepMicroseconds(100); @@ -296,11 +299,11 @@ bool_t GDISP_LLD(init)(void) { /* Turn on */ GDISP_LLD(writeindex)(SSD1963_SET_DISPLAY_ON); -#if defined(LCD_USE_FSMC) - /* FSMC delay reduced as the controller now runs at full speed */ - FSMC_Bank1->BTCR[FSMC_Bank+1] = FSMC_BTR1_ADDSET_0 | FSMC_BTR1_DATAST_2 | FSMC_BTR1_BUSTURN_0 ; - FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; -#endif + #if defined(LCD_USE_FSMC) + /* FSMC delay reduced as the controller now runs at full speed */ + FSMC_Bank1->BTCR[FSMC_Bank+1] = FSMC_BTR1_ADDSET_0 | FSMC_BTR1_DATAST_2 | FSMC_BTR1_BUSTURN_0 ; + FSMC_Bank1->BTCR[FSMC_Bank] = FSMC_BCR1_MWID_0 | FSMC_BCR1_WREN | FSMC_BCR1_MBKEN; + #endif /* Initialise the GDISP structure to match */ GDISP.Width = SCREEN_WIDTH; @@ -387,20 +390,23 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { GDISP_LLD(setwindow)(x, y, x+cx-1, y+cy-1); GDISP_LLD(writestreamstart)(); -#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) - uint16_t i, splitarea; - dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); - for (i = (area/65535)+1; i > 0; i--) { - if (i <= 1) splitarea = area%65535; else splitarea = 65535; - dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); + #if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) + uint8_t i; + dmaStreamSetPeripheral(LCD_DMA_STREAM, &color); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PL(0) | STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M); + for (i = area/65535; i; i--) { + dmaStreamSetTransactionSize(LCD_DMA_STREAM, 65535); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); + } + dmaStreamSetTransactionSize(LCD_DMA_STREAM, area%65535); dmaStreamEnable(LCD_DMA_STREAM); - dmaWaitCompletion(LCD_DMA_STREAM); - } -#else - uint32_t index, - for(index = 0; index < area; index++) - GDISP_LLD(writedata)(color); -#endif //#ifdef LCD_USE_DMA + dmaWaitCompletion(LCD_DMA_STREAM); + #else + uint32_t index; + for(index = 0; index < area; index++) + GDISP_LLD(writedata)(color); + #endif //#ifdef LCD_USE_DMA } #endif @@ -433,26 +439,29 @@ void GDISP_LLD(drawpixel)(coord_t x, coord_t y, color_t color) { buffer += srcx + srcy * srccx; -#if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) - uint32_t area = cx*cy; - uint16_t i, splitarea; - dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); - for (i = (area/65535)+1; i > 0; i--) { - if (i <= 1) splitarea = area%65535; else splitarea = 65535; - dmaStreamSetTransactionSize(LCD_DMA_STREAM, splitarea); + #if defined(LCD_USE_FSMC) && defined(LCD_USE_DMA) && defined(LCD_DMA_STREAM) + uint32_t area = cx*cy; + uint8_t i; + dmaStreamSetPeripheral(LCD_DMA_STREAM, buffer); + dmaStreamSetMode(LCD_DMA_STREAM, STM32_DMA_CR_PL(0) | STM32_DMA_CR_PINC | STM32_DMA_CR_PSIZE_HWORD | STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_DIR_M2M); + for (i = area/65535; i; i--) { + dmaStreamSetTransactionSize(LCD_DMA_STREAM, 65535); + dmaStreamEnable(LCD_DMA_STREAM); + dmaWaitCompletion(LCD_DMA_STREAM); + } + dmaStreamSetTransactionSize(LCD_DMA_STREAM, area%65535); dmaStreamEnable(LCD_DMA_STREAM); - dmaWaitCompletion(LCD_DMA_STREAM); - } -#else - coord_t endx, endy; - unsigned lg; - endx = srcx + cx; - endy = y + cy; - lg = srccx - cx; - for(; y < endy; y++, buffer += lg) - for(x=srcx; x < endx; x++) - GDISP_LLD(writedata)(*buffer++); -#endif //#ifdef LCD_USE_DMA + dmaWaitCompletion(LCD_DMA_STREAM); + #else + coord_t endx, endy; + unsigned lg; + endx = srcx + cx; + endy = y + cy; + lg = srccx - cx; + for(; y < endy; y++, buffer += lg) + for(x=srcx; x < endx; x++) + GDISP_LLD(writedata)(*buffer++); + #endif //#ifdef LCD_USE_DMA } #endif diff --git a/drivers/gdisp/SSD1963/gdisp_lld_config.h b/drivers/gdisp/SSD1963/gdisp_lld_config.h index fc8d8489..662adcc2 100644 --- a/drivers/gdisp/SSD1963/gdisp_lld_config.h +++ b/drivers/gdisp/SSD1963/gdisp_lld_config.h @@ -39,10 +39,10 @@ #define GDISP_LLD(x) gdisp_lld_##x##_SSD1963 #define GDISP_HARDWARE_FILLS TRUE -#define GDISP_HARDWARE_BITFILLS TRUE +#define GDISP_HARDWARE_BITFILLS TRUE /* Maybe someday soon */ #define GDISP_HARDWARE_SCROLL FALSE -#define GDISP_HARDWARE_CONTROL FALSE +#define GDISP_HARDWARE_CONTROL FALSE #define GDISP_PIXELFORMAT GDISP_PIXELFORMAT_RGB565 diff --git a/src/touchpad.c b/src/touchpad.c index 5e81738b..e531af80 100644 --- a/src/touchpad.c +++ b/src/touchpad.c @@ -52,7 +52,7 @@ /*===========================================================================*/ /* Driver local variables. */ /*===========================================================================*/ -volatile static struct cal cal = { +static volatile struct cal cal = { 1, 1, 0, 0 }; @@ -167,7 +167,8 @@ uint16_t tpReadX(void) { return SCREEN_WIDTH - x; case landscapeInv: return y; - } + } + return 0; } /** @@ -193,6 +194,7 @@ uint16_t tpReadY(void) { case landscapeInv: return SCREEN_WIDTH - x; } + return 0; } void tpCalibrate(void) { @@ -202,7 +204,7 @@ void tpCalibrate(void) { uint16_t points[2][2]; uint8_t i; - gdispClear(Red); + gdispClear(Red); gdispFillStringBox(0, 10, gdispGetWidth(), 30, "Calibration", &fontUI2Double, White, Red, justifyCenter); for(i = 0; i < 2; i++) {