Anyone with experience with Spi +dma+fifo on a c2000 or a f28377D?? an not get the example running
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
Anyone with experience with Spi +dma+fifo on a c2000 or a f28377D?? an not get the example running
Thanks for your reaction, Gautam.
That sample works as is, but is unuseble, as in practice loopback will be off.
Try to change the clock polarity to 1, although no peripheral I/O is programmed and the loopback don't need a clock signal, the sample does not work any more.
As soon as fifo is enabled, the spi communicarion with the ethernet device on my board becomes unreliable, with complete bursts missing. And, I need to use clockpolarity 1. This took me a month now and is killing the project. Without fifo everything works perfect and with very high speed (30 MHz), But the dma is essential for timing reasons. Is there still a bug in my TMX device? TMS only was available this year.
Any help is welcome!!!
Bye, Henk Schutte, Amsterdam
Hi Henk,
I'm looking into this. Can you give me some more details about the specific failures you're seeing? You say it's DMA bursts going missing? Anything else?
Thanks,
Whitney
Hello Whitney,
Basis of what I did was the example app spi+dma+fifo.
This sample worked, of course.
Then I checked the hi-speed options, as I need up to 40MHz, still succesful.
Then I programmed the Gpio58...61 for HiSpeed connection with my ethernet device (Beckhoff ET1100). I changed the clock polarity (not phase) to 1, released the loopback, released the fifo (.SPIFFTX.bit.SPIFFENA = 0) and then all the communication was working perfect up to 33MHz.
Then I switched on the fifo again and started dma:
SpiState = 0;
ReadReg(0x1300, &rdata, 256); // this is the routine that works perfectly, view memory at 0x1300 shows the content of the ET1100
-> SpiaRegs.SPIFFTX.bit.SPIFFENA = 1; // enable fifo FFLvl = 8,
GPIO_WritePin(61, 0); // active low
StartDMACH6(); // Start SPI RX DMA channel
StartDMACH5(); // Start SPI TX DMA channel
while (SpiState == 0); // wait until the DMA transfer is complete
At this point I can not see the same data arriving at rdata, although the dma finished completely. (8-1 burst, 32-1 transfers) and the memory view showed 256 words mostly in red.
Slowing the speed to 10 Mhz, introducing ...TXDLY = 8, ....nada.
I tested also the ReadReg() function with fifo enabled as the only change, Same problem. Maybe the problem is in the fifo functionality. I tested this further::
As soon as fifo is enabled, things go wrong. Inserting delay after a fifoenable does not work. Apparently, it is not possible to change fifoenable in a running program.
Thanks a lot for your assistence.
Henk
Hi Henk,
I'm glad you managed to track down a way around the issue. I'm sending a note to a colleague who knows our SPI behavior better than I do to ask if he knows of any issues with enabling the FIFO on the fly and what notes we may need to add to the documentation.
Edit: I know we do support changing the FIFO reset bits, but I think that's mostly with the intent of resetting the FIFO pointer.
Thanks,
Whitney
Well, I finished changing all the spi routines, so they work with fifoenabled. Things run completely predictable now, but I still miss 1 burst data at the beginning of the block (8 zero's). On the scope, things look normal, second word shows to be 0x0030, but in the data 0x0030 is on location 9. All fifo statusses are 0 at start. Hope this info helps.
Henk
Sure, Whitney,
#define FIFO_LVL 8 //RX FIFO Interrupt Level
#define BURST 8 // -1
#define TRANSFER 27 // -1 MEM_BUFFER_SIZE/BURST dus 208 words/8 = 26 bursts (+1 added burst to compensate for the empty first burst)
// DMA setup for both TX and RX channels.
void dma_init()
{//Initialize DMA
DMAInitialize();
DMASource = (volatile Uint16*)&sdata;
DMADest = (volatile Uint16*)&rDatag - 9;//skip first burst + cmnd
// configura DMACH5 for TX
DMACH5AddrConfig(&SpiaRegs.SPITXBUF,DMASource);
DMACH5BurstConfig(BURST-1,1,0); // Burst size, src step, dest step
DMACH5TransferConfig(TRANSFER-1,1,0); // transfer size, src step, dest step
DMACH5ModeConfig(DMA_SPIATX,PERINT_ENABLE,ONESHOT_DISABLE,CONT_DISABLE
,SYNC_DISABLE,SYNC_SRC,OVRFLOW_DISABLE,SIXTEEN_BIT,CHINT_END,CHINT_ENABLE);
// configure DMA CH6 for RX
DMACH6AddrConfig(DMADest,&SpiaRegs.SPIRXBUF);
DMACH6BurstConfig(BURST-1,0,1);
DMACH6TransferConfig(TRANSFER-1,0,1);
DMACH6ModeConfig(DMA_SPIARX,PERINT_ENABLE,ONESHOT_DISABLE,CONT_DISABLE,
SYNC_DISABLE,SYNC_SRC,OVRFLOW_DISABLE,SIXTEEN_BIT,CHINT_END,CHINT_ENABLE);
}
Hello Whitney,
Yes, both fifolevels are 8.
The subtracting (-9) is a little dirty solution to skip the first burst (and a not-significant word). I know that this memory is not in use. Anyway, before this dirty workaround, the first 8 words in rDatag were 0, loosing the last 8, now these meaningless words are located before rDatag.
I ruled out the possibility that a former spi command was not finished properly, as the first dma code after reset already showed the problem.
I stopped momentarily with the dma+fifo solution as a more serious problem did show up, so there is more at hand. I found that the memory of the ethernet chip was polluted with data at an address outside the dma/fifo addresses.
For the moment I use a simple spi read routine that works reliably and which basically should do the same as the dma. But it holds the Delfino for an unacceptable 250 usec, only interrupt routines produce some functionality.
As you may have noticed, the dma code is just copied from the TI-example.
The dma was programmed to send part (first 208, 26 bursts, now 216, 27 bursts) of the data from sdata[256], which contains only zero's, except sdata[0] which contains the address+read-command. This must be the code that does not perform what I intended it to do.However, I confirmed that all the registers for DmaCh5 and 6 indeed contains the proper addresses.
It seems unlikely that some hardware problem is at hand, as the TI-loopback example worked perfectly.
I really hope you may come up with some useful suggestions.
Hi Henk,
I apologize for the slow response. You say you're using the ET1100, right? Their data sheet seems to say that the SPI clock speed should be <= 20MHz. I'm concerned that that could be the issue. Do you get better behavior at 20MHz? For example, can you keep the phase set to 0? Do the extra words in the FIFO go away?
Our SPI module hasn't changed much across devices over the years, so F2837x's newness isn't likely to be an issue where SPI is concerned.
Edit: Out of curiosity, have you looked at our ET1100 reference module? Or any of the software for it? http://www.ti.com/tool/TIDM-DELFINO-ETHERCAT
Whitney
Hello Santosh,
Thanks for your concern.
Phase is the Spi clock_phase, together with polarity it provides four modes. The ET1100 is on Spi mode 3, corresponding to clock polarity = 1 and clock phase = 0. Al the communication between the F28377D and the ET runs reliably up to 40 MHz, although Beckhoff limits the ET to 20 MHz. On the scope, the DO signal from ET looks completely healthy at 40.
The initial need for dma was saving time. I use almost the complete bandwidth of the f28377d to close a servo loop, which runs at high speed and high precision.
Initially, things went completely out of control as soon I used the dma+fifo example from the TI F28377d.example codes in ControlSUITE. I did not know whether there was something wrong with dma or with fifo. Anyway, the example code uses loopback and runs perfectly this way, but then with clock polarity = 1 and then with the Gpio pins 58..60 programmed for spi, problems started.
I decided first to rewrite all of the spi routines to work perfectly with fifo enabled. I use 16 bit as this seems to me the more efficient way to do in a F28 and the ET supports this too. I do not use addressing with wait states, like in the code ( that maybe you made), publshed (ethercat_slave_c28x_hal.c). I control the SPISTE signal manually, this way you can insert the 200 ns delay required by Beckhoff.
I analysed further the differences with the TI example and my code. Maybe essential was to insert a while loop for BUFFULL.between writes to SPITXBUF.
At this moment I use the 16 level fifo as follows. First i send the address + command (Read) word to the ET (gpio61 first made low) and read one dummy word. Then I fill quickly the TX fifo 16x with zero words. In the next timer interrupt (48KHz timer) I read 16x RXBUF) and send another 16 zero's to TX. This is repeated until all data are in (208 words every millisec).
I use the same trick for writing two 16 word blocks; that works reliably but only with the following.
I found that the RXFFSTS is not always zero after RXFIFORESET 0...1. , also after some delay. also if repeated. For security I reset the complete spi (SPIRST) after writing all data, which I consider as a dirty solution. I don't know if this happens randomly with reading as well, I am afraid this is the case as my motor runs not smoothly.
I suspect that some unpredictable behaviour originates from the transfer of TXfifo to TXBUF to DATA with high data rates.
It would be very nice to have your attention on my Spi problems, and maybe for the whole F28 community as well.
By the way, I don't use TwinCat, but I use my own EtherCAT stack, a C++ translation of Simple Open EtherCat Master (SOEM) written by Arthur Ketels. This is a fast but not a real time solution in Windows, but my servo code runs inside the F28. SOEMaster runs on Windows 10, as my CNC code does. Everything will ultimately run in Win8 Embedded..
Henk Schutte
Amsterdam NL
Santosh Athuru said:Henk,
thanks for the details. I will try to get my examples running with FIFO enabled and let you know how it goes.
Best Regards
Santosh
Hello Santosh,
Anything to report already?
You might also call me in Amsterdam, +31 651317847
Thanks,
Henk Schutte
Henk,
I'm still looking into it among other things. Have the SPI RX FIFO working, need to add DMA and SPI TX FIFO.
Will keep you updated.
Best Regards
Santosh
Henk,
I'm still looking on this, just letting you know. Have been pulled into other priorities, hope to get back to this example mid week, next week.
will keep you posted.
Best Regards
Santosh Athuru
Hello Friedeman,
Actually, I started with some SOEM version, then rewrote all the sources to C++ classes, also removing all the redundancy; both ways reduced 3/4 of the code. With max. 8 nodes, the necessity of redundancy is zero: don't touch the RJ45 plugs while a machine is running and do not close the EtherCAT loop with a second port on the PC. If you want to automate a big plant, stay with Beckhoff. They wil come soon with a Win10 version of TwinCAT, I was told. Otherwise, run SOEM on Linux.
What is left is quite simple code and runs perfectly. Biggest problem remains to be the non-real-time nature of Win10. You have to design clever tricks to have all the handshaking in 1 Ethernet frame, as sending 1 frame takes at least 400 usecs using WinPCap (latest version, there is also a Japanese Win10 version). My problem from the onset was extremely high data rates. Actually now, I am still finishing the handshake protocol.
It took me some time to find out that an ultra-stripped minimum EtherCAT master is also possible, almost 10 times smaller then any other master. For example, an empty system with no mailbox and no sync manager etc. is still able to write directly to the ET1100 memory. And don't worry about the official protocol, as long as you use a Beckhoff slave chip, your system will automatically conform to EtherCAT. If you use commercially available slave (I/O) modules, the mailbox protocol will still be needed.
According to Arthur Ketels, the original developer of SOEM, real time machine control with Windows and EtherCAT (and TwinCAT) is impossible. Well, it is quite difficult, but with some restrictions (big data buffers) I came a long way. Arthur is the most capable EtherCAT expert in The Netherlands and helped me a lot. Also, the TI example code for C2000 and the ET1100 helps a lot for the slave side, although I did not use them, I was already finished when this was published.
Let me know how things are going.