Forum: Mikrocontroller und Digitale Elektronik DMA repeat timer - springt aber nur einmal rein (M32C)


von Timo (Gast)


Lesenswert?

Hallo zusammen,

ich möchte mit dem Renesas M32C StarterKit folgendes realisieren.

Vom UART werden X Zeichen eingelesen, welche über den DMA direkt aufm 
Speicher abgespeichert werden.

In der DMA ISR setze ich die Zyklen Anzahl und den Zielort wieder fest.
Wenn ich mir vor und nach durchlaufen der ISR die DMA Register anschaue, 
dann haben diese wieder die Werte von zuvor....
Doch leider springt er mir nur ein einziges mal in die ISR hinein und 
kein 2. mal.
Im User Guide, habe ich auch gesehen, dass es eine repeat funktion gibt 
- aber mit der habe ich es auch nicht hinbekommen

Anbei nun mein Code. ich hoffe jmd findet den fehler, ist bestimmt nur 
eine Kleinigkeit....
1
/**** Global Variables *************************************************/
2
unsigned char buffer[5];
3
4
unsigned short dct0;
5
unsigned short drc0;
6
unsigned short dmd0;
7
void  *dsa0;
8
void  *dma0;
9
void  *dra0;
10
11
#pragma DMAC dct0 DCT0 
12
#pragma DMAC dmd0 DMD0
13
#pragma DMAC dsa0 DSA0
14
#pragma DMAC dma0 DMA0
15
#pragma DMAC drc0 DRC0
16
#pragma DMAC dra0 DRA0
17
18
19
void init_DMA0(void)
20
{   
21
  dmd0 = 0x01;  // 8-bit units, single transfer 
22
//  dmd0 = 0x03;  // 8-bit units, repeat transfer 
23
  
24
  dm0sl =  0x0f;    // DMA request source: UART0 Receive
25
  
26
  dma0 = buffer;  //  set memory to RAM buffer
27
28
  dsa0 = &u0rb;   // set peripheral address of UART0 receive register  
29
//  dra0 = buffer;
30
  
31
  dct0 = 5;    //  set transfer counter for 5
32
//  drc0 = 5;
33
  
34
  
35
  dm0ic = 0x04;
36
}
37
38
void dma0_isr(void)
39
{    
40
  BER(); 
41
42
   dma0 = buffer;  //  set memory to RAM buffer
43
  dct0 = 5;
44
  ir_dm0ic &= 0;
45
}

Vielen Dank, Gruß
Timo

von Judge (Gast)


Lesenswert?

Hallo Timo,

funktioniert einwandfrei, auch als repeated transfer. Allerdings sollte 
das Register dm0sl gesetzt werden während die DMA abgeschaltet ist (dmd0 
= 0x00), also die ersten beiden Initialisierungsschritte vertauschen.

Das nur ein DMA-Interrupt kommt könnte daran liegen das in der UART 
während der ISR ein Overrun-Error auftritt, also neue Daten empfangen 
wurden und die alten noch nicht abgeholt wurden. In diesem Fall wird 
kein Interrupt mehr generiert, und die DMA läuft nicht weiter. Prüfe mal 
das high-byte im Empfangsregister auf irgendwelche Übertragungsfehler.
Um diese Fehler wieder zurückzusetzen muss das high-byte ausgelesen 
werden (ggf. 16 bit Transfer benutzen).

Gruss
Judge

von Timo (Gast)


Lesenswert?

Morgen,
danke für die Nachricht - habe den Fehler gestern noch gefunden ....
1
#pragma INTERRUPT dma0_isr
2
void dma0_isr(void)

Hatte die erste Zeile vergessen gehabt und somit macht die Renesas HEW 
Software kein Return from Interrupt sondern ein Return from Subroutine 
ans Ende....

Somit wäre das nun auch geklärt ;)

Nun klappts nämlich wunderbar.

Gruß
Timo

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.