Witam,
Od dłuższego czasu zastanawiam się jak rozwiązać pewien problem.
Otóż, gdy próbuję ustawić DMA wyzwalane przepełnieniem timera, to nie działa jak powinno. DMA startuje przy pierwszym przepełnieniu TC, a później odczytuje dane z portu w swoim tempie, nie zważając na przerwania timera. Kod wydląda tak:
Natomiast podobny przykład, tylko wyzwalanie przez ADC nie sprawia żadnych problemów:
Od dłuższego czasu zastanawiam się jak rozwiązać pewien problem.
Otóż, gdy próbuję ustawić DMA wyzwalane przepełnieniem timera, to nie działa jak powinno. DMA startuje przy pierwszym przepełnieniu TC, a później odczytuje dane z portu w swoim tempie, nie zważając na przerwania timera. Kod wydląda tak:
TCC0.CTRLA = 0x01; // Prescaler: clk/1
TCC0.PER = 32; //1MHz
//DMA.CTRL =1<<7; //enable DMA upper
DMA.CH3.CTRLA = (0<<5) | (1<<2) | (0<<0); //single, 1-byte
DMA.CH3.CTRLB = 0<<4 | 0<<5 | 0<<2 | 2<<0; //error and complete interrupt flags, high level interrupt
DMA.CH3.ADDRCTRL = (0<<6) | (0<<4) | (3<<2) | (1<<0); //addr reload src after 1-byte, no inc src addr, inc dst addr
DMA.CH3.TRIGSRC = 0x40; //TCC0 - 0x40, TCD1 - 0x66 overflow trig.
DMA.CH3.TRFCNT = 2048; //set 2048Byte block
DMA.CH3.SRCADDR0 =(((uint16_t)(&PORTD.IN))>>0*8) & 0xFF;
DMA.CH3.SRCADDR1 =(((uint16_t)(&PORTD.IN))>>1*8) & 0xFF;
DMA.CH3.SRCADDR2 = 0;
DMA.CH3.DESTADDR0 =(((uint16_t)(buf))>>0*8)&0xFF;
DMA.CH3.DESTADDR1 =(((uint16_t)(buf))>>1*8)&0xFF;
DMA.CH3.DESTADDR2 = 0;Natomiast podobny przykład, tylko wyzwalanie przez ADC nie sprawia żadnych problemów:
DMA.CTRL =1<<7; //enable DMA
DMA.CH1.CTRLA = (0<<5) | (1<<2) | (1<<0); //single, 2-byte
DMA.CH1.CTRLB = 0<<4 | 0<<5 | 0<<2 | 2<<0; //error and complete interrupt flags, high level interrupt
DMA.CH1.ADDRCTRL = (2<<6) | (1<<4) | (1<<2) | (1<<0); //addr reload src after 2-byte, inc src addr, inc dst addr
DMA.CH1.TRIGSRC = 0x10; //ADCA, CH0
DMA.CH1.TRFCNT = 2048; //set 2048Byte block
DMA.CH1.SRCADDR0 =(((uint16_t)(&ADCA.CH0RESL))>>0*8) & 0xFF;
DMA.CH1.SRCADDR1 =(((uint16_t)(&ADCA.CH0RESL))>>1*8) & 0xFF;
DMA.CH1.SRCADDR2 = 0;//(((uint32_t)(&ADCA.CH0))>>2*8) & 0xFF;
DMA.CH1.DESTADDR0 =(((uint16_t)(buf))>>0*8)&0xFF;
DMA.CH1.DESTADDR1 =(((uint16_t)(buf))>>1*8)&0xFF;
DMA.CH1.DESTADDR2 = 0;//(((uint32_t)(buf))>>2*8)&0xFF;