cancel
Showing results for 
Search instead for 
Did you mean: 

DMA Configuration...

crusso9
Associate II
Posted on November 22, 2012 at 11:09

Hi, I'm developing on STM3240G-Eval board and I'm trying to use DMA for displaying an image from the SRAM memory on the LCD.

This is the code that I wrote:

void DMA_Write()

{

  uint32_t skippedCycles = 0;

  DMA_InitTypeDef DMA_InitStructure;

  /* 1. Enable DMA Controllers */

  RCC_AHB1PeriphResetCmd(RCC_AHB1Periph_DMA1, ENABLE);

  

  /* 2. Enable and configure Peripheral DMA_Stream (not required by SRAM).*/

  LCD_WriteReg(LCD_REG_3, 0x1008);

  LCD_WriteRAM_Prepare();

 

  /* 3. DMA_Init().*/

  DMA_DeInit(DMA1_Stream0);

  while(DMA_GetCmdStatus(DMA1_Stream0) != DISABLE);

   

  DMA_InitStructure.DMA_Channel = DMA_Channel_0;

  DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t) (0x64000000); // SRAM memory address

  DMA_InitStructure.DMA_Memory0BaseAddr = ((uint32_t)(0x60000000 | 0x60020000)); // LCD memory address

  DMA_InitStructure.DMA_DIR = DMA_DIR_MemoryToMemory;

  DMA_InitStructure.DMA_BufferSize = (uint32_t) (76800);

  DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Enable;

  DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;

  DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord;

  DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;

  DMA_InitStructure.DMA_Mode = DMA_Mode_Normal; //DMA_Mode_Circular;

  DMA_InitStructure.DMA_Priority = DMA_Priority_High;

  DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Enable;

  DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_Full;

  DMA_InitStructure.DMA_MemoryBurst = DMA_PeripheralBurst_Single;

  DMA_Init(DMA1_Stream0, &DMA_InitStructure);

  /* I'm not going to use DMA interrupts so I've commented this line... */

  // DMA_ITConfig(DMA1_Stream0, DMA_IT_TC, ENABLE);

   /* 6. Enable the DMA stream using the DMA_Cmd() function. */

  DMA_Cmd(DMA1_Stream0, ENABLE);

  while(DMA_GetCmdStatus(DMA1_Stream0) == DISABLE) {

    // Wait DMA Start...

    skippedCycles++;

  }

   

  skippedCycles = 0;

  while( DMA_GetFlagStatus(DMA1_Stream0, DMA_FLAG_TCIF0) == RESET) {

 

   // waiting DMA  completes transfer...

    DMA_ClearFlag(DMA1_Stream0, DMA_FLAG_TCIF0);

    skippedCycles++;

  }

 

  return;

}

At the moment the code compiles but seems that DMA1_Stream0 doesn't become ENABLE after the line DMA_Cmd(DAM1_Stream0, ENABLE) is called.

Did I make some mistakes? 

 

#stm3240g #lcd #dma #dma #stm3240g
4 REPLIES 4
Posted on November 22, 2012 at 12:19

>  /* 1. Enable DMA Controllers */

> RCC_AHB1PeriphResetCmd(RCC_AHB1Periph_DMA1, ENABLE);

You need to enable the DMA controller's clock before you reset it.

I know you used the description from the ''library''. Well, it's wrong.

JW
crusso9
Associate II
Posted on November 22, 2012 at 12:44

Thank you so much!

I've added the code line:

RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA1, ENABLE);

after the reset, but still I don't get it work.

Where can I find some samples on the DMA ? Because I cannot figure out how to fix the code if the description inside the library is wrong...

Posted on November 22, 2012 at 13:09

Couple of potential issues.

a) Don't you need to be using DMA2 for memory-to-memory

RM0090 ''Only the DMA2 controller is able to perform memory-to-memory transfers.''

b) The transfer length is 16-bit, so max 65535 memory units (8, 16, or 32-bit, as defined by increment)
Tips, buy me a coffee, or three.. PayPal Venmo Up vote any posts that you find helpful, it shows what's working..
crusso9
Associate II
Posted on November 22, 2012 at 18:03

Hi Clive1,

I switched on DMA 2 stream and checked the size of data to send.

Now code is working fine:

#define DMA_STREAM DMA2_Stream0

#define DMA_CHANNEL DMA2_Channel_0

  /* 1. Enable DMA Controllers and reset them.*/

  RCC_AHB1PeriphClockCmd(DMA_STREAM_CLOCK, ENABLE);

 

  /* 2. Enable and configure Peripheral DMA_Stream (not required by SRAM).*/

 

  /* 3. For a given Stream, program the required configuration

  through following parameters: Source and Destination addresses,

  Transfer Direction, Transfer size, Source and Destination data formats,

  Circular or Normal mode, Stream Priority level, Source and Destination

  Incrementation mode, FIFO mode and its Threshold (if needed),

  Burst mode for Source and/or  Destination (if needed) using the DMA_Init().*/

  DMA_DeInit(DMA_STREAM);

  while(DMA_GetCmdStatus(DMA_STREAM) != DISABLE);

  DMA_InitStructure.DMA_Channel = DMA_CHANNEL;

  DMA_InitStructure.DMA_PeripheralBaseAddr = srcAddress;

  DMA_InitStructure.DMA_Memory0BaseAddr = destAddress;

  DMA_InitStructure.DMA_DIR = DMA_DIR_MemoryToMemory;

  DMA_InitStructure.DMA_BufferSize = (uint32_t) (size);

  DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;

  DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Disable;

  DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord;

  DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;

  DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;

  DMA_InitStructure.DMA_Priority = DMA_Priority_High;

  DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;

  DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_Full;

  DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_INC8;

  DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_INC8;

  DMA_Init(DMA_STREAM, &DMA_InitStructure);

  /* 4. Enable the NVIC and the corresponding interrupt(s)

   using the function DMA_ITConfig() if you need to use DMA interrupts.*/

  DMA_ITConfig(DMA_STREAM, DMA_IT_TC, ENABLE);

  /* 5. Optionally, if the Circular mode is enabled, you can use the

  Double buffer by configuring the second Memory address and the

  first Memory to be used through the function DMA_DoubleBufferModeConfig().

  Then enable the Double buffer mode through the function

  DMA_DoubleBufferModeCmd(). These operations must be done before step 6.*/

  /* 6. Enable the DMA stream using the DMA_Cmd() function. */

  DMA_Cmd(DMA_STREAM, ENABLE); Thank you so much!