LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Implementing high-throughput, multi-input FXP maths on an FPGA

I'm a bit of a novice with LabVIEW FPGA programming, especially when it comes to the effective use of SCTLs. I was hoping for some pointers when implementing handshaking with the multi-input high-throughput FXP functions (such as add, multiply etc.).

 

The online help I've seen (http://zone.ni.com/reference/en-XX/help/371599K-01/lvfpgaconcepts/fpga_handshaking/ ) doesn't show any multi-input maths and the example to which they link doesn't have any hand-shaking code. So I had to forge ahead blindly.

 

My first naïve attempt was to do something like the following:

FpgaMultiply.png

(ignore the dodgy FIFO, that's just for example I/O).

 

The problem is: this code will fall down if one of the inputs is valid while the other isn't. We'll lose the valid data, and only be able to perform a calculation if both inputs happen to be valid simultaneously. (I think this is difficult to guarantee if the input data come from different sources, e.g. maybe the host and over p2p).

 

 

The new linear algebra palette solves this problem by having separate handshaking for each input.

FpgaMatrix.png

 

I guess we need to implement something analogous for the simple multiply? As below.

FpgaMiFxp.png

 

This middleman needs to hang-on to valid data in either input, outputting only when both inputs have been valid. It should only ask for input if it is not already storing valid data from that output. Here is my attempt at coding this (also see attached).

 

MultiInputFXP.png

 

Obviously, there are plenty of problems with my implementation – primarily, the introduction of latency and complexity to the FPGA.

 

I suspect others must have run into this issue, and so I’m sure there are better solutions. Does anyone know of any, or have advice on how to improve on my attempt?

0 Kudos
Message 1 of 9
(3,491 Views)

Why not just buffer them yourself with a feedback node and store the values when they are ready from your input FIFOs and empty them when they are read out?

 

I don't see the benefit of pushing this work into a primitive.

 

Shane

0 Kudos
Message 2 of 9
(3,475 Views)

Thanks for the response.

 

Firstly, I don't think I've explained myself very well - I'm not suggesting that NI add a primitive to solve this problem, merely that it's a problem I would like a solution to.

 

And I'm not quite sure I understand your response (sorry!). Do you mean buffer the input data only when they're valid? As below.

 

FpgaMiFxp2.png

 

If so, you still have the problem that you might be losing data. I.e. you can’t guarantee element n of FIFO 1 is multiplied by element n of FIFO 2, if they are not ready on the same iteration.

0 Kudos
Message 3 of 9
(3,466 Views)

I forget (and I don't have LV here), but can't you query the no of available elements in the FIFO? If so, the easy way is just to ensure they both have an element, then only read and pass them when that is the case. 

 

Using latches to store valid values is also a way to go, but there are problems with your implementation.

 

For starters, the state of the latches, not the multiply, should determine whether a 'ready for output' is passed to the FIFOs.

'Input valid' on the multiply should be set true when the latches are both 'full' with new data, not when both FIFO outputs are valid. I would maybe use a couple more latches which store a boolean indicating whether the buffering latches have valid data. (latch==FF node)

Message 4 of 9
(3,459 Views)

And don't forget, the FF node output only becomes available one cycle after it is fed in.

0 Kudos
Message 5 of 9
(3,458 Views)

I was thnking of something like THIS.

 

FPGA Multiinput Multiply buffering.png

 

Haven't tested it but something similar should work.

 

If you get multiple values on one FIFO before the other, you will lose data... YOumight need more work to take care of that if it''s possible this might occur.

 

Shane.

 

PS I don't know what type of FIFO you have selected but I don't have a FIFO Read with those terminaly available on my machine.  I improvised and simply placed controls and Indicators instead.  Hope you don't mind... Smiley LOL

 

Message 6 of 9
(3,455 Views)

Thanks both for the suggestions.

 

Shane, that makes sense to me, and looks like a good implementation. And, FYI, the handshaking interface for the FIFO was introduced (I think) in LabVIEW 2014.

 

ToeCutter, I like the idea of using the FIFO state to check whether any elements can be read - I didn't think of that.

 

What do you reckon the comparative resource usage of the above two routes would be?

 

 

Also, I hesitated marking either option as a solution, as I think both could work. Can one accept multiple solutions to a question?

0 Kudos
Message 7 of 9
(3,447 Views)

AFAIK, utilising the status information of the FIFO is not free.  A FIFO which does not access the status is implemented differently than one with status.  How expensive it is, I don't know but I would go my route (what a surprise). Smiley Very Happy

0 Kudos
Message 8 of 9
(3,420 Views)

Intaris gave a more complete solution, so happy for you to mark that as the official one.

 

I doubt (but don't know for sure, so the only way is to try it) there's much resource difference between the solutions in the grand scheme of things. Perhaps a more interesting question is if one or the other has a significantly lower propagation delay/higher SCTL rate.

0 Kudos
Message 9 of 9
(3,365 Views)