Hi,
I'm working on sending data by UART0 over EDMA. I'm doing this by following code (StarterWare base) :
#define UART_RBR_THR_REG (SOC_UART_0_REGS + 0) volatile uint32_t flag_tx_busy=0; static void UartTransmitData(unsigned int tccNum, unsigned int chNum, volatile uint8_t *buffer, unsigned int len) { EDMA3CCPaRAMEntry paramSet; /* Fill the PaRAM Set with transfer specific information */ paramSet.srcAddr = (unsigned int) buffer; paramSet.destAddr = UART_RBR_THR_REG + C674x_MMU_OFFSET; paramSet.aCnt = 1; paramSet.bCnt = (unsigned short) len; paramSet.cCnt = 1; /* The src index should increment for every byte being transferred. */ paramSet.srcBIdx = (short) 1u; /* The dst index should not be increment since it is a h/w register*/ paramSet.destBIdx = (short) 0u; /* A sync Transfer Mode */ paramSet.srcCIdx = (short) 0u; paramSet.destCIdx = (short) 0u; paramSet.linkAddr = (unsigned short)0xFFFFu; //NULL PaRAM paramSet.bCntReload = (unsigned short)0u; paramSet.opt = 0x00000000u; paramSet.opt |= (EDMA3CC_OPT_DAM ); paramSet.opt |= ((tccNum << EDMA3CC_OPT_TCC_SHIFT) & EDMA3CC_OPT_TCC); paramSet.opt |= (1 << EDMA3CC_OPT_TCINTEN_SHIFT); /* Now write the PaRAM Set */ EDMA3SetPaRAM(SOC_EDMATPCC_REGS, chNum, ¶mSet); /* Enable EDMA Transfer */ EDMA3EnableTransfer(SOC_EDMATPCC_REGS, chNum, EDMA3_TRIG_MODE_EVENT); } static void UartInit(){ unsigned int fifoConfig = 0; unsigned int divisorValue = 0; UARTModuleReset(SOC_UART_0_REGS); /* Setting the TX and RX FIFO Trigger levels as 1. No DMA enabled. */ fifoConfig = UART_FIFO_CONFIG(UART_TRIG_LVL_GRANULARITY_1, UART_TRIG_LVL_GRANULARITY_1, 1, 1, 1, 1, UART_DMA_EN_PATH_SCR, UART_DMA_MODE_0_ENABLE); /* Configuring the FIFO settings. */ UARTFIFOConfig(SOC_UART_0_REGS, fifoConfig); /* Computing the Divisor Value. */ divisorValue = UARTDivisorValCompute(48000000, 9600, UART16x_OPER_MODE, UART_MIR_OVERSAMPLING_RATE_42); /* Programming the Divisor Latches. */ UARTDivisorLatchWrite(SOC_UART_0_REGS, divisorValue); /* Switching to Configuration Mode B. */ UARTRegConfigModeEnable(SOC_UART_0_REGS, UART_REG_CONFIG_MODE_B); /* Programming the Line Characteristics. */ UARTLineCharacConfig(SOC_UART_0_REGS, (UART_FRAME_WORD_LENGTH_8 | UART_FRAME_NUM_STB_1), UART_PARITY_NONE); /* Disabling write access to Divisor Latches. */ UARTDivisorLatchDisable(SOC_UART_0_REGS); /* Disabling Break Control. */ UARTBreakCtl(SOC_UART_0_REGS, UART_BREAK_COND_DISABLE); /* Switching to UART16x operating mode. */ UARTOperatingModeSelect(SOC_UART_0_REGS, UART16x_OPER_MODE); } void ConsoleInit(void){ EDMAModuleClkConfig(); EDMA3Init(SOC_EDMATPCC_REGS, 0); EDMA3RequestChannel(SOC_EDMATPCC_REGS, EDMA3_CHANNEL_TYPE_DMA, EDMA3_CHA_UART0_TX, EDMA3_CHA_UART0_TX, 0); UartInit(); } void UartSend(uint8_t * data,uint32_t size){ //uint32_t max_try = 100000; flag_tx_busy = 1; UartTransmitData(EDMA3_CHA_UART0_TX, EDMA3_CHA_UART0_TX, data,size); UARTDMAEnable(SOC_UART_0_REGS, UART_DMA_MODE_3_ENABLE); while(flag_tx_busy/* && max_try--*/); // Block program until EDMA interrupts received. } void Edma3ErrIsr(void) { uint32_t missedIrqs = HWREG(SOC_EDMATPCC_REGS + EDMA3CC_EMR); if(missedIrqs && (1<<EDMA3_CHA_UART0_TX)) EDMA3ClearErrorBits(SOC_EDMATPCC_REGS,EDMA3_CHA_UART0_TX,0); // Clear SER and EMR corresponding bits } // EDMA operation completion interrupt void edma3CompIsr(void) { if(EDMA3GetIntrStatus(SOC_EDMATPCC_REGS) & (1 << EDMA3_CHA_UART0_TX)){ EDMA3ClrIntr(SOC_EDMATPCC_REGS, EDMA3_CHA_UART0_TX); flag_tx_busy=0; } }
My problem is EDMA ( Or UART configuration). Data transmission by EDMA, works just one time! After calling ConsoleInit function, I will call UartSend twice. First time data will be sent perfectly, but second time does not works and does not sends any data.
I know that when PaRAM link field is 0xFFFF (NULL), corresponding bits in EMR and SER will be set high after transmission completed. As mentioned in reference manual section 8.3.3.3, EDMA3CC will ignores future events on this channel (UART0_TX). But SER and EMR corresponding bits will be cleared by calling EDMA3EnableTransfer in each transfer.
I changed UART FIFO parameters, but result not changed.
When I set EDMA UART0 TX event manually by setting corresponding bit in ESR register at each transmission, EDMA works well.
Also, When I put a dummy character in FIFO manually ( By filling THR register ) at every transmission, EDMA works well for each UartSend calling.
Where is my problem?
Thanks in advance.