Recent

Author Topic: stm32f103 dma problem [SOLVED]  (Read 2013 times)

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
stm32f103 dma problem [SOLVED]
« on: July 07, 2020, 07:10:37 pm »
hi

im trying bluepill board

using  unit stm32f103fw
{ Converted from STM FWlib

 Contributors:
  Jeppe Johansen
  Bernd Mueller
  Valerio Turrini with really small adjustments.....
}

when i use dma channels system hangs

Code: Pascal  [Select][+][-]
  1.   DMA_InitTypeDef.DMA_BufferSize:= 64;
  2.   DMA_InitTypeDef.DMA_DIR:= DMA_DIR_PeripheralSRC;
  3.   DMA_InitTypeDef.DMA_M2M:= DMA_M2M_Disable;
  4.   DMA_InitTypeDef.DMA_MemoryBaseAddr:=  @RXbuffer1;
  5.   DMA_InitTypeDef.DMA_MemoryDataSize:= DMA_MemoryDataSize_Byte;
  6.   DMA_InitTypeDef.DMA_MemoryInc:= DMA_MemoryInc_Enable;
  7.   DMA_InitTypeDef.DMA_Mode:= DMA_Mode_Circular;
  8.   DMA_InitTypeDef.DMA_PeripheralBaseAddr:= @Usart1.DR;
  9.   DMA_InitTypeDef.DMA_PeripheralDataSize:= DMA_PeripheralDataSize_Byte;
  10.   DMA_InitTypeDef.DMA_PeripheralInc:= DMA_PeripheralInc_Disable;
  11.   DMA_InitTypeDef.DMA_Priority:= DMA_Priority_Medium;
  12.   DMA_Init(DMA1.Channel[5], DMA_InitTypeDef); //USART1_RX
  13.   DMA_CMD(DMA1.Channel[5], Enabled);
  14.  

or even hangs if i use only the dma_deinit function

if i comment out the last 2 lines, dont hang, but ovbiously, dont work the dma controller, but all the rest code work fine


in the stm32f10x_md file i found this ¿bug?
Code: Pascal  [Select][+][-]
  1.  TDMARegisters = record
  2.   ISR,
  3.   IFCR: longword;
  4.   //Channel: array[0..7] of TDMAChannel; //wrong!! 8 channels space but have only 7
  5.   Channel: array[0..6] of TDMAChannel;  //diego bertotti 7/7/2020
  6.  end;
  7.  


 thanks in advance for any help/suggestions

 
« Last Edit: July 21, 2020, 01:58:18 pm by diego bertotti »

MiR

  • Full Member
  • ***
  • Posts: 116
Re: stm32f103 dma problem
« Reply #1 on: July 07, 2020, 09:35:51 pm »
Looking at the datasheet 0..6 is correct, but better values would have been 1..7 as the DMA channels are numbered 1-7 in the reference manual.

Not sure if you took the offset of one into account in your code, DMA1.Channel[5] actually means use Channel6

Michael
« Last Edit: July 07, 2020, 09:41:29 pm by MiR »

MiR

  • Full Member
  • ***
  • Posts: 116
Re: stm32f103 dma problem
« Reply #2 on: July 07, 2020, 09:40:10 pm »
Again, from the reference manual:

USART1.RX is attached to Channel5 which means you will have to take index '4'

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #3 on: July 07, 2020, 10:17:19 pm »
thanks for replys

i try with index 4 (you are right). same problem.

remember, i have the same problem, using the DMA_deinit function. in this case is not important the index value, is just an initilization, and hangs too.

i fix index form 0 to 6 because this code

Code: Pascal  [Select][+][-]
  1. procedure DMA_DeInit(var DMAy_Channelx: TDMAChannel);
  2.  
  3. begin
  4.    DMAy_Channelx.CCR:= DMAy_Channelx.CCR and (not(CCR_ENABLE_SET));
  5.    DMAy_Channelx.CCR:=0;
  6.    DMAy_Channelx.CNDTR:=0;
  7.    DMAy_Channelx.CPAR:=0;
  8.    DMAy_Channelx.CMAR:=0;
  9.    if @DMAy_Channelx = @DMA1.Channel[0] then
  10.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel1_IT_Mask
  11.    else if @DMAy_Channelx = @DMA1.Channel[1] then
  12.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel2_IT_Mask
  13.    else if @DMAy_Channelx = @DMA1.Channel[2] then
  14.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel3_IT_Mask
  15.    else if @DMAy_Channelx = @DMA1.Channel[3] then
  16.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel4_IT_Mask
  17.    else if @DMAy_Channelx = @DMA1.Channel[4] then
  18.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel5_IT_Mask
  19.    else if @DMAy_Channelx = @DMA1.Channel[5] then
  20.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel6_IT_Mask
  21.    else if @DMAy_Channelx = @DMA1.Channel[6] then
  22.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel7_IT_Mask
  23.    else if @DMAy_Channelx = @DMA2.Channel[0] then
  24.       DMA2.IFCR := DMA2.IFCR or DMA2_Channel1_IT_Mask
  25.    else if @DMAy_Channelx = @DMA2.Channel[1] then
  26.       DMA2.IFCR := DMA2.IFCR or DMA2_Channel2_IT_Mask
  27.    else if @DMAy_Channelx = @DMA2.Channel[2] then
  28.       DMA2.IFCR := DMA2.IFCR or DMA2_Channel3_IT_Mask
  29.    else if @DMAy_Channelx = @DMA2.Channel[3] then
  30.       DMA2.IFCR := DMA2.IFCR or DMA2_Channel4_IT_Mask
  31.    else if @DMAy_Channelx = @DMA2.Channel[4] then
  32.       DMA2.IFCR := DMA2.IFCR or DMA2_Channel5_IT_Mask
  33. end;    
  34.  

look for example channel 1 use index 0!

MiR

  • Full Member
  • ***
  • Posts: 116
Re: stm32f103 dma problem
« Reply #4 on: July 07, 2020, 10:32:49 pm »
Have you tried running your deinit code in a debugger?

When I compare your De-Init Code to the original code in the C-Library it looks like a 1:1 translation so there does not seem to be an issue with the code itself.

In the debugger you will see easily if some interrupt triggers or you get some other exception

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #5 on: July 07, 2020, 10:39:33 pm »
sorry, dont have debugger
wich one?

MiR

  • Full Member
  • ***
  • Posts: 116
Re: stm32f103 dma problem
« Reply #6 on: July 07, 2020, 10:53:46 pm »
There's a moster long thread here in the forum on debugging.
You can use a 2nd bluepill flashed with either original stlink firmware (google is your friend) or use the very good Black Magic Probe which also fits on a bluepill.

Also found reset code in libopencm3 (which I use sometimes) looks pretty much the same...

Is the peripheral clock for DMA enabled?

void dma_channel_reset(uint32_t dma, uint8_t channel)
{
   /* Disable channel and reset config bits. */
   DMA_CCR(dma, channel) = 0;
   /* Reset data transfer number. */
   DMA_CNDTR(dma, channel) = 0;
   /* Reset peripheral address. */
   DMA_CPAR(dma, channel) = 0;
   /* Reset memory address. */
   DMA_CMAR(dma, channel) = 0;
   /* Reset interrupt flags. */
   DMA_IFCR(dma) |= DMA_IFCR_CIF(channel);
}

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #7 on: July 07, 2020, 11:24:18 pm »
look this!!!!

Code: Pascal  [Select][+][-]
  1.  
  2.  
  3.   PDMARegisters : ^LongWord;
  4.  
  5.  
  6.   PDMARegisters := @DMA1 + $58;   //CCR5
  7.   PDMARegisters^:= %000000010100001;
  8.   PDMARegisters := @DMA1 + $5C;   //CNDTR5
  9.   PDMARegisters^:= 64;  
  10.   PDMARegisters := @DMA1 + $60;   //CPAR5
  11.   PDMARegisters^:= LongWord(@Usart1.DR);
  12.   PDMARegisters := @DMA1 + $64;   //CMAR5
  13.   PDMARegisters^:= LongWord(@RXBuffer1);
  14.  
  15.  

i still dont know if dma working, but now dont hangs

and dma clock is enabled


Code: Pascal  [Select][+][-]
  1.  RCC_AHBPeriphClockCmd( RCC_AHBPeriph_DMA1 or RCC_AHBPeriph_DMA2 or RCC_AHBPeriph_SRAM or RCC_AHBPeriph_FLITF, Enabled);
  2.  RCC_APB2PeriphClockCmd(RCC_APB2Periph_ALL, Enabled);
  3.  RCC_APB1PeriphClockCmd(RCC_APB1Periph_ALL, Enabled);
  4.  
  5.  
« Last Edit: July 07, 2020, 11:26:00 pm by diego bertotti »

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #8 on: July 13, 2020, 02:47:24 pm »
There's a moster long thread here in the forum on debugging.
You can use a 2nd bluepill flashed with either original stlink firmware (google is your friend) or use the very good Black Magic Probe which also fits on a bluepill.

ok. but what about debugging software. wich one?

MiR

  • Full Member
  • ***
  • Posts: 116
Re: stm32f103 dma problem
« Reply #9 on: July 13, 2020, 03:52:25 pm »
You can debug from Lazarus, works quite OK when things are not too complex. Instructions are in the Monster Thread on Debugging...

Good alternatives are:
https://www.gdbgui.com/

and if you have JLink use Ozone:
https://www.segger.com/products/development-tools/ozone-j-link-debugger/
To get a JLink buy a nucleo board for $10 and after a quick conversion you are ready to debug whole STM32 family:
https://www.segger.com/products/debug-probes/j-link/models/other-j-links/st-link-on-board/
Advantage of Ozone is that it works well with FreeRTOS

I also saw this, but did not try for myself:

https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-guides/jtag-debugging/using-debugger.html

seems you can use Eclipse as a standalone debugger, looks interesting, may be worth a try!

avra

  • Hero Member
  • *****
  • Posts: 1998
    • Additional info
Re: stm32f103 dma problem
« Reply #10 on: July 13, 2020, 06:22:54 pm »
when i use dma channels system hangs
You should try some Arduino or STM32CubeIDE DMA code for stm32f103 to check if DMA works on your blue pill at all. If you have a cheap clone, there is some chance that you are facing a problem because of not 100% compatible cpu. Take a look at https://www.cnx-software.com/2020/03/22/how-to-detect-stm32-fakes/
ct2laz - Conversion between Lazarus and CodeTyphon
bithelpers - Bit manipulation for standard types
pasettimino - Siemens S7 PLC lib

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #11 on: July 15, 2020, 12:55:14 am »
hi

now i have a working code, but in bare metal way

Code: Pascal  [Select][+][-]
  1.  
  2.   TXBuffer1[0]:= byte('h');  
  3.   TXBuffer1[1]:= byte('e');
  4.   TXBuffer1[2]:= byte('l');
  5.   TXBuffer1[3]:= byte('l');
  6.   TXBuffer1[4]:= byte('o');
  7.  
  8.  Usart1.CR1:= 0; //disable usart1
  9.  Usart1.CR1:= Usart1.CR1 or %00000000001100;
  10.  Usart1.CR2:= 0;
  11.  Usart1.CR2:= Usart1.CR2 or %000000000000000;
  12.  Usart1.CR3:= 0;
  13.  Usart1.CR3:= Usart1.CR3 or %00010000000;
  14.  Usart1.GTPR:= 0;
  15.  Usart1.BRR:= 5000 SHL 4;// 9600 @48mhz
  16.  Usart1.CR1:= Usart1.CR1 or $2000; //enable usart1
  17.  PDMARegisters := @DMA1 + $44;   //CCR4
  18.  PDMARegisters^:= %000000010110110;
  19.  PDMARegisters := @DMA1 + $48;   //CNDTR4
  20.  PDMARegisters^:= 5;
  21.  PDMARegisters := @DMA1 + $4C;   //CPAR4
  22.  PDMARegisters^:= LongWord(@Usart1.DR);
  23.  PDMARegisters := @DMA1 + $50;   //CMAR4
  24.  PDMARegisters^:= LongWord(@TXBuffer1);
  25.  Usart1.SR:= Usart1.SR and not %1000000;
  26.  PDMARegisters := @DMA1 + $44;   //CCR4
  27.  PDMARegisters^:= PDMARegisters^ or %1;   //enable
  28.  


diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #12 on: July 15, 2020, 03:24:49 pm »
hi

problem seems are inside dma lib only

using this code works too

Code: Pascal  [Select][+][-]
  1.  Usart_ini.USART_BaudRate:= 9600;
  2.  Usart_ini.USART_WordLength:= USART_WordLength_8b;
  3.  Usart_ini.USART_StopBits:= USART_StopBits_1;
  4.  Usart_ini.USART_Parity:= USART_Parity_No ;
  5.  Usart_ini.USART_Mode:= USART_Mode_Rx or USART_Mode_Tx;
  6.  Usart_ini.USART_HardwareFlowControl:= USART_HardwareFlowControl_None;
  7.  Usart_ini.USART_Clock:= USART_Clock_Disable;
  8.  Usart_ini.USART_CPOL:= USART_CPOL_Low;
  9.  Usart_ini.USART_CPHA:= USART_CPHA_1Edge;
  10.  Usart_ini.USART_LastBit:= USART_LastBit_Disable;
  11.  USART_Init(USart1, Usart_ini);
  12.  USART_Init(USart3, Usart_ini);
  13.  Usart_ini.USART_HardwareFlowControl:= USART_HardwareFlowControl_RTS;
  14.  USART_Init(USart2, Usart_ini);
  15.  
  16.  USART_DMACmd(Usart1,USART_DMAReq_Tx  or USART_DMAReq_Rx ,Enabled);
  17.  USART_ITConfig(Usart1, USART_IT_TC , enabled);
  18.  Usart_Cmd(Usart1, ENABLED);
  19.  PDMARegisters := @DMA1 + $44;   //CCR4
  20.  PDMARegisters^:= %000000010110110;
  21.  PDMARegisters := @DMA1 + $48;   //CNDTR4
  22.  PDMARegisters^:= 5;
  23.  PDMARegisters := @DMA1 + $4C;   //CPAR4
  24.  PDMARegisters^:= LongWord(@Usart1.DR);
  25.  PDMARegisters := @DMA1 + $50;   //CMAR4
  26.  PDMARegisters^:= LongWord(@TXBuffer1);
  27.  Usart1.SR:= Usart1.SR and not %1000000;
  28.  PDMARegisters := @DMA1 + $44;   //CCR4
  29.  PDMARegisters^:= PDMARegisters^ or %1;   //enable    
  30.  

MiR

  • Full Member
  • ***
  • Posts: 116
Re: stm32f103 dma problem
« Reply #13 on: July 15, 2020, 05:14:27 pm »
I compared the definition in the unit file with my own autogenerated units for stm32f103rb.

There are two differences, one is that in the official lib we have word access to some of the fields, this does matter on Cortex-M0 but on Cortex M3 it should not matter as the chip can handle word access to 32bit registers. But it is perhaps worth a try to redefine the fields to be longWord and by this to force proper 32bit access.

The other difference is that STM defines hard offsets for the DMA_Channels, you do the same in your code.

Can you check if address of DMA1.Channel[4].CCR is the same as @DMA1 + $58;

or

DMA1.Channel[3].CCR is the same as @DMA1 + $44; (From your last example, there you use DMA Channel 4)


If addresses are the same then the word/longword access sounds like a good cause for the problem.

diego bertotti

  • Jr. Member
  • **
  • Posts: 73
Re: stm32f103 dma problem
« Reply #14 on: July 15, 2020, 11:15:41 pm »
@DMA1.Channel[2] = $4002 0030




using this code and a logic analizer in the out pin

Code: Pascal  [Select][+][-]
  1.  
  2.    tmpreg:= longWord(@DMA1.Channel[2]);
  3.    AUX_B:= Byte((tmpreg AND $000000FF));
  4.    TXBuffer1[5]:= AUX_B;
  5.    AUX_B:= Byte((tmpreg  AND $0000FF00) shr 8);
  6.    TXBuffer1[6]:= AUX_B;
  7.    AUX_B:= Byte((tmpreg  AND $00FF0000) shr 16);
  8.    TXBuffer1[7]:= AUX_B;
  9.    AUX_B:= Byte((tmpreg  AND $FF000000) shr 24);
  10.    TXBuffer1[8]:= AUX_B;
  11.  
  12.  

seems ok but shifted one.

i try deinit function with any index btw 0..6 and always hangs!!

i try modify record form word to lonword...and hangs!!!

now, if i comment out lines in library writing the ccr and cntdr, dont hang

Code: Pascal  [Select][+][-]
  1.  
  2. procedure DMA_DeInit(var DMAy_Channelx: TDMAChannel);
  3.  
  4. begin
  5.   // DMAy_Channelx.CCR:= DMAy_Channelx.CCR and (not(CCR_ENABLE_SET));
  6.   // DMAy_Channelx.CCR:=0;
  7.   // DMAy_Channelx.CNDTR:= 0;
  8.    DMAy_Channelx.CPAR:=0;
  9.    DMAy_Channelx.CMAR:=0;
  10.    if @DMAy_Channelx = @DMA1.Channel[0] then
  11.       DMA1.IFCR := DMA1.IFCR or DMA1_Channel1_IT_Mask  
  12.  
  13.  

but i try to modify declaration from word to longword, (and eliminating the res1 and res2 words) and still hangs

Code: Pascal  [Select][+][-]
  1.  
  2.  TDMAChannel = record
  3.   {CCR, res1,
  4.   CNDTR, res2: word;}
  5.   CCR,
  6.   CNDTR,
  7.   CPAR,
  8.   CMAR,
  9.   res: longword;
  10.  end;
  11.  
  12.  
« Last Edit: July 16, 2020, 12:15:23 am by diego bertotti »

 

TinyPortal © 2005-2018