Real-Time Measurement and Control

cancel
Showing results for 
Search instead for 
Did you mean: 

[FPGA] Best Method to Empty Local/DMA FIFOs in State Machine?

I am writing code on our PXI-7833R RIO card to impliment a propriatary digital protocol.  The architecture I choose to go with is a state machine that will allow the user to download pre-defined data to the FGPA's FIFO's and have the data be output appropriatley.  Once all the data has been output, the state machine should return to the "Initialize" state to reset everything back to normal so that the test can be run again.  Additionally, the user is able to STOP the test no matter what state the FPGA is in, forcing it to go back to the Initialize state.

A problem quickly surfaced when I would test out the STOP functionality and noticed that the old elements from the previous test were still in the local FIFOs.  I remedied this problem by creating a while loop in the Initialize state, placing FIFO READ vi's for each local FIFO then AND'ing the outputs of their "empty" indicator to the stop button on the while-loop.  In this way, any additional items in the FIFO will be read until they are all empty and then the loop will exit and the state machine can procede to the next state.

Recently I just installed Labview 8.0 and am now testing out DMA functionality to send data from the Target to the Host.  In this case the same problem arrises when I allow the user to STOP the test prematurely allowing elements to remain in the DMA FIFO.  However, in this scenario I run into a problem on how to empty these DMA FIFO's in the Initialize state since I cannot do a DMA FIFO Read on the FPGA for a "Target to Host" DMA FIFO.  Is my only solution to have a similar while-loop with the DMA FIFO Fead method on the *Real-Time* target, but now hooking up "Number of Elements" to 1, Timeout to 0, and testing to see if "Elements Remaining" is equal to zero in order to stop this loop?   If at all possible I would prefer a way to do this on the FPGA itself much like I do for Local FIFO's.  Thanks

0 Kudos
Message 1 of 10
(10,884 Views)
Hi SiegeX,

I hope you're doing well.  Typically to clear the DMA FIFOs, you could use an Invoke Method to reset the FPGA VI, but I am not sure if this would fit in nicely with your state-machine architecture or not.  Otherwise, there is no way to clear the FIFO directly on the FPGA.  The DMA FIFO is split up across both the FPGA target and the host machine, so the FPGA end cannot clear all the FIFO elements on its own.  Let us know if this helps!

Thaison V
Applications Engineer
National Instruments
Message 2 of 10
(10,866 Views)
As Thaison mentioned, one option is to reset the FPGA from the host interface. This will stop/abort any VI running on the FPGA and will empty/reset all FIFOs on the FPGA. In addition you need to stop and start the DMA process in the host interface. Doing a stop and start will empty/reset the memory allocated to DMA in the host. The drawback of this solution is that it forces you to stop the VI on the FPGA which may not be possible in some applications.
 
The second method is to read data from the DMA FIFO and buffer in the host interface until the FIFO and DMA buffer are empty. To accomplish this you need to stop the process on the FPGA that is sending data to the the DMA FIFO, but continue calling the DMA Read method in the host interface until Elemens Remaining is 0. See the following pseudo code for the proper sequence of calls in the host interface.
 
Pseudo Code:
 
FPGA Open VI Reference (open only, not run)
Reset
Start
 
DMA Config
DMA Start
 
Start acquisition or other process on the FPGA that sends data to the DMA FIFO
 
While  (not Stop)
   DMA Read
   Process data read from the FPGA
End While
Stop acquisition or other process on the FPGA that sends data to the DMA FIFO
 
While (Elements Remaining != 0)
   DMA Read
End While
 
DMA Stop
 
Close FPGA VI Reference or loop back to DMA Config
 
 
authored by
Christian L, CLA
Systems Engineering Manager - Automotive and Transportation
NI - Austin, TX


  
Message 3 of 10
(10,850 Views)

Thanks for the replies.  First off resetting the entire FPGA is not an option for me as the FPGA is simultaneously doing digital data generation as well as digital data recording and they work independantly of eachother as two seperate state machines.   As for Christian's suggestion I think this is (near) exactly what I am doing.  Let me post a state diagram

[b]Initialize[/b]

While (number of elements != 0)
 

 

 

 


0 Kudos
Message 4 of 10
(10,838 Views)

Thanks for the replies.  First off resetting the entire FPGA is not an option for me as the FPGA is simultaneously doing digital data generation as well as digital data recording and they work independantly of eachother as two seperate state machines.   As for Christian's suggestion I think this is (near) exactly what I am doing.  Let me post a state diagram

[b]Initialize[/b]

While (number of elements != 0)
 

 

 

 


0 Kudos
Message 5 of 10
(10,838 Views)

Thanks for the replies.  First off resetting the entire FPGA is not an option for me as the FPGA is simultaneously doing digital data generation as well as digital data recording and they work independantly of eachother as two seperate state machines.   As for Christian's suggestion I think this is (near) exactly what I am doing.  Let me post a state diagram

[b]Initialize[/b]

While (number of elements != 0)
  

 

 

 


0 Kudos
Message 6 of 10
(10,843 Views)
Attached is a LV 8 project and VIs that implement the pseudo code I posted earlier plus error checking to detect a buffer overflow.
 
This code may require NI-RIO 2.01 to load which you can download from the NI web site (2.01 is included on the NI-RIO 2.0 download page.)
authored by
Christian L, CLA
Systems Engineering Manager - Automotive and Transportation
NI - Austin, TX


  
Message 7 of 10
(10,832 Views)

Sorry about all those multiple posts, I was trying to edit my post and pressed back a few times not knowing that would happen. The forum doesnt seem to want to let me edit/delete them either.   In any case here is what  the pertient parts of the state machine are doing.  Note that I have never used DMA  Configure/Stop/Start, simply DMA Read which seems to do all the configuring for me.  If this isnt optimal, please let me know.   One thing I noticed by adding this DMA Read functionality in the Initialize state is that it added a noticible pause between the initialize state and the idle state at which time Resource manager shows 100% cpu activity. The pause is about 3-4 seconds.

State: Initialize
While( Number_of_Elements != 0 )
{
      DMA READ (timeout = 0,number of elements = 1)
}

Next_State = idle

State: Idle
While ( Start != 1 )
{
}

Next_State = Recording

State: Recording
Timed_While ( (DMA_STOP || ABORT) != 1 )
{
     DMA READ (timeout = 0, number of elements = 14000, timed loop period = 130ms )
}

Next_State = Initialize


0 Kudos
Message 8 of 10
(10,830 Views)

If you don't call DMA Configure and DMA Start, they will be executed automatically the first time you call DMA Read. I think this may explain why your Initialize state is taking so long. I would suggest you call these methods explicitly. It also allows you to manually configure the size of the DMA buffer on the host.

I don't know if you have other code in your Initialize state, but if you don't, you should not need this state any more. Once you have called DMA Configure and DMA Start you are ready to go into the Recording state.

authored by
Christian L, CLA
Systems Engineering Manager - Automotive and Transportation
NI - Austin, TX


  
Message 9 of 10
(10,822 Views)
Christian,
 
Thanks for your example code, I really appreciate you taking the time to do that for me.  Im glad to see what you had is nearly exactly what I had already done, except I had hardcoded "Number of Elements" to 1 whereas you had used a shift-register to read back exactly the # of elements left which is obviously the better way to go.  Reading 1 at a time in conjuction with not explicitly setting DMA Config/Start seemed to be causing the long delay in the initialize state.  And for your other question, yes I do other things in the initialize state, mainly resetting boolean controlls back to false and other such things. 

Message Edited by SiegeX on 04-10-2006 06:28 PM


0 Kudos
Message 10 of 10
(10,816 Views)