Hello,
I am using LLD driver of edma3 on c6767/omapl137 starter kit. I am building an application that copy a data from external SDRAM to internal RAM, and generates interrupt on completion.
It almost working, copies the data successifully, and sometimes even generates an interrupt[:|], but it has some issues:
1. It works only when I define .text section in BIOS in SDRAM. Why?
2. I am a lillte confused on how the interrupt is working with this driver - is it uses ECM dispatcher or not? If I configure the program to ECM dispatcher, where do I define the pointer to interrupt handler? Is there any help on ECM Module? I've found only help for LLD Driver, but ECM_Dispatch and all other functions descriptions are missing.
3. When I use direct (without the dispatcher) interrupt (interrupt event 8 - transfer completion) and, say, link it to CPU interrupt #5, it SOMTIMES generate an interrupt, ususally if I perform step by step run, not when I let it run.
But mostly my software crushes! It simply generates an NMI interrupt and then jumps to some random location.
I dont think that this is a stack overflow, since I increased the stack big time, and it didnt helped.
I did build my program in such way that it starts the EDMA transfer, exits the function, and pendsby semaphore, until completion interrupt is generated - the interrupt releases the semaphore.
I use the function given by LLD driver edma3_lld_01_10_00_01.
Thank You
Arye
This is part of the code that relates to edma, it is a simplified version of what is provided in example:
unsigned int ch1Id = 0;EDMA3_DRV_Result result = EDMA3_DRV_SOK;extern EDMA3_DRV_Handle hEdma;
// Interrupt Handler#pragma CODE_SECTION(EDMA3_Interrupt_Handler,".CodeBuffer");void EDMA3_Interrupt_Handler(){ result = EDMA3_DRV_SOK;
SEM_postBinary(&EDMA3_SEM);
result = EDMA3_DRV_freeChannel (hEdma, ch1Id);}
#pragma CODE_SECTION(Edma3_Transfer,".CodeBuffer")void Edma3_Transfer(signed char * dstBuff1, signed char * srcBuff1, unsigned int length){/* EDMA3_DRV_ChainOptions chain = {EDMA3_DRV_TCCHEN_DIS, EDMA3_DRV_ITCCHEN_DIS, EDMA3_DRV_TCINTEN_DIS, EDMA3_DRV_ITCINTEN_DIS};*/
// EDMA3_DRV_Result result = EDMA3_DRV_SOK; // dwefined externally static unsigned int BRCnt = 0; static int srcbidx = 0, desbidx = 0; static int srccidx = 0, descidx = 0; static unsigned int tcc1 = 0;
unsigned int restore_value;
// ----------- arguments of example function ------------------ static unsigned int acnt = 4; static unsigned int bcnt; static unsigned int ccnt = 1;// EDMA3_DRV_SyncType syncType = EDMA3_DRV_SYNC_AB;// ------------------------------------------------------------ bcnt = length; result = EDMA3_DRV_SOK;
// Save interrupt state// restore_value = HWI_disable();
#ifdef EDMA3_ENABLE_DCACHE /* * Note: These functions are required if the buffer is in DDR. * For other cases, where buffer is NOT in DDR, user * may or may not require the below functions. */ /* Flush the Source Buffers */ if (result == EDMA3_DRV_SOK) result = Edma3_CacheFlush((unsigned int)srcBuff1, (acnt*bcnt*ccnt));
/* Invalidate the Destination Buffers */ if (result == EDMA3_DRV_SOK) result = Edma3_CacheInvalidate((unsigned int)dstBuff1, (acnt*bcnt*ccnt));#endif /* EDMA3_ENABLE_DCACHE */
/* Set B count reload as B count. */ BRCnt = bcnt;
/* Setting up the SRC/DES Index */ srcbidx = (int)acnt; desbidx = (int)acnt;
/* AB Sync Transfer Mode */ srccidx = ((int)acnt * (int)bcnt); descidx = ((int)acnt * (int)bcnt);
/* // Transfer complete chaining enable chain.tcchEn = EDMA3_DRV_TCCHEN_EN; // Intermediate transfer complete chaining disabled chain.itcchEn = EDMA3_DRV_ITCCHEN_DIS; // Transfer complete interrupt is enabled chain.tcintEn = EDMA3_DRV_TCINTEN_EN; // Intermediate transfer complete interrupt is disabled chain.itcintEn = EDMA3_DRV_ITCINTEN_DIS;*/ /* Setup for Channel 1*/ tcc1 = EDMA3_DRV_TCC_ANY; ch1Id = EDMA3_DRV_DMA_CHANNEL_ANY;
if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_requestChannel (hEdma, &ch1Id, &tcc1,(EDMA3_RM_EventQueue)0,&callback1, NULL); if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_setSrcParams (hEdma, ch1Id,(unsigned int)(srcBuff1),EDMA3_DRV_ADDR_MODE_INCR,EDMA3_DRV_W8BIT); if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_setDestParams (hEdma, ch1Id,(unsigned int)(dstBuff1),EDMA3_DRV_ADDR_MODE_INCR,EDMA3_DRV_W8BIT); if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_setSrcIndex (hEdma, ch1Id, srcbidx, srccidx); if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_setDestIndex (hEdma, ch1Id, desbidx, descidx); if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_setOptField (hEdma,ch1Id,EDMA3_DRV_OPT_FIELD_TCINTEN,1u);
/* AB Sync Transfer Mode */ if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_setTransferParams (hEdma, ch1Id, acnt, bcnt,ccnt, BRCnt,EDMA3_DRV_SYNC_AB);
if (result == EDMA3_DRV_SOK) result = EDMA3_DRV_enableTransfer (hEdma, ch1Id,EDMA3_DRV_TRIG_MODE_MANUAL); // HWI_restore(restore_value);}