Хочу сделать так:
1. таймерА сконфигурирован на частоту 409600
2. по DMA передается 1024 точки в ЦАП по триггеру от Таймера А , результат на ЦАПе - синус 400 Гц
3. в прерывании от порта я останавливаю и запускаю DMA, получаем синхронизацию с опорой.
вот так это реализовано
Код
//---------------------------------------------------------------------------------------
void init_DMA(void)
{
DMACTL0 = DMA0TSEL_1; // запуск DMA от CCR2 таймера А
DMA0SA = (unsigned short)buf_DAC; // Start block address
DMA0DA = DAC12_0DAT_; // Destination block address
DMA0SZ = BUF_LENGTH; // Block size 3,6864e6 = 400 * 9 * 1024
DMA0CTL =
DMADT_4 + // Одиночный перенос с повтором
DMADSTINCR_0 + // Наззначение не инкрементируется
DMASRCINCR_3 + // Источник инкрементируется
0*DMADSTBYTE + // получатель слово
0*DMASRCBYTE + // источник слово
0*DMAIE; // не разрешаем прерывания
DMA0CTL |= DMAEN;
}
//---------------------------------------------------------------------------------------
void init_TimerA(void)
{ // 2 - /4
TACTL = 0; // сбрасываем региср управления
TACTL = ID_0 + TASSEL_2 + TACLR; // input divider: 0 - /1, тактирование SMCLK
// Timer A counter clear - сброс значения в таймере
TACCTL0 = 0*CCIE; // Capture/compare interrupt enable
TACCR0 = 8; // Frequency = 409600 Hz = 1024*400
TACCTL1 = OUTMOD_3; // режим установки/сброса
TACCR1 = 6; // на значении 6 установится , на 9 сбросится
TACCTL2 = OUTMOD_3; // режим установки/сброса
TACCR2 = 4; // на значении 3 установится , на 9 сбросится
TACTL |= MC_1; // Start Timer A in up mode
}
#pragma vector=PORT1_VECTOR
__interrupt void port1_int (void)
{
LedOn();
DMA0CTL &= ~DMAEN; // ReEnable DMA
init_DMA();
P1IFG = 0;
LedOff();
}
void init_DMA(void)
{
DMACTL0 = DMA0TSEL_1; // запуск DMA от CCR2 таймера А
DMA0SA = (unsigned short)buf_DAC; // Start block address
DMA0DA = DAC12_0DAT_; // Destination block address
DMA0SZ = BUF_LENGTH; // Block size 3,6864e6 = 400 * 9 * 1024
DMA0CTL =
DMADT_4 + // Одиночный перенос с повтором
DMADSTINCR_0 + // Наззначение не инкрементируется
DMASRCINCR_3 + // Источник инкрементируется
0*DMADSTBYTE + // получатель слово
0*DMASRCBYTE + // источник слово
0*DMAIE; // не разрешаем прерывания
DMA0CTL |= DMAEN;
}
//---------------------------------------------------------------------------------------
void init_TimerA(void)
{ // 2 - /4
TACTL = 0; // сбрасываем региср управления
TACTL = ID_0 + TASSEL_2 + TACLR; // input divider: 0 - /1, тактирование SMCLK
// Timer A counter clear - сброс значения в таймере
TACCTL0 = 0*CCIE; // Capture/compare interrupt enable
TACCR0 = 8; // Frequency = 409600 Hz = 1024*400
TACCTL1 = OUTMOD_3; // режим установки/сброса
TACCR1 = 6; // на значении 6 установится , на 9 сбросится
TACCTL2 = OUTMOD_3; // режим установки/сброса
TACCR2 = 4; // на значении 3 установится , на 9 сбросится
TACTL |= MC_1; // Start Timer A in up mode
}
#pragma vector=PORT1_VECTOR
__interrupt void port1_int (void)
{
LedOn();
DMA0CTL &= ~DMAEN; // ReEnable DMA
init_DMA();
P1IFG = 0;
LedOff();
}
проблема такая:
после
DMA0CTL &= ~DMAEN;
DMA0CTL |= DMAEN;
DMA не возобновляет работу, зависает.
бит DMAEN остается взведенным а передачи нет.
Что не так?
пробовал сбрасывать/устанавливать DMAEN отладчиком без прерываний
пробовал режим DMADT_0 - Одиночный перенос без повторов, тогда DMA срабатывает только один раз.