LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Interleaving arrays on FPGA

Solved!
Go to solution

My point being, to read five channels of analogue input data, you don't tend to read in multiple data points for each, interleave into an array and then write them into the FIFO. You acquire one point from each five channels immediately, then build the array, and then write into the FIFO. Your FIFO then ends up being the interleaved array, and because you've pre-allocated resources then you can read and write with minimal performance hit.

 

If you have a particular reason to have to interleave arrays on the FPGA, then you may have to resort to using arrays in the manner that Alex is describing, but I can't think of many instances where that's really necessary, because that's what FIFOs are for.


If you post your FPGA, it would help to understand exactly what you're trying to do.

 

As an example, the following loop is code in one of my FPGA targets:

fpga-fifo.png

 

Every 800 clock ticks (at 40 MHz, that's 50 kHz) I read the count value from three counters (Laser Position, UUT Position, Z Position, generated in another loop at 40 MHz). If the FIFO transmit boolean is true, I write these three elements into the FIFO. In the next iteration, those three elements are added to the end of the FIFO, and so on and so on.

 

On the host, I read from the FIFO and decimate the data as appropriate.

 

This is the recommended method for transmitting multi-channel data from FPGA target to host.

---
CLA
Message 11 of 19
(2,155 Views)

Hi,

 

I have tried placing the data into the FIFO the same as in your example but exactly the same thing happens, for 2 inputs it works fine but for 3 it doesn't.

 

I have this on my FPGA:

 

AI FIFO.png

 

And this is the result:

 

Result.png

 

The 'top' of the peak is at 10k (the amplitude of sine 1) and the 'bottom' of the peak is at 5k (the amplitude of sine 2) while sine 3 is nowhere to be seen (set at 3k)

 

There is a possibility that I am missing something obvious, seeing as both fail at 3 inputs so feel free to mention anything that could be affecting it, no matter how simple.

 

EDIT: Just tried doing the interleaving and the decimate on the FPGA and it works fine so the problem is definitely with the way the FIFO handles the data.

0 Kudos
Message 12 of 19
(2,145 Views)

Just to clarify, say you're trying to add elements A, B and C to the FIFO, are you seeing:

 

- an array with elements A, B and C in the correct order, but sometimes swapping position (e.g. instead of A B C A B C A B C your array might be B C A B C A B C A, starting from a different place)

 

or

 

- an array with elements A, B and C in a completely random order

 

or something else?

 

Also, when you create that graph on the bottom, are you decimating / reshaping the incoming array by the correct number of channels? I'd be curious to see the code that you use to read from the FIFO.

---
CLA
0 Kudos
Message 13 of 19
(2,124 Views)

I see an array with the values in the wrong order, but it is not completly random as the resulting waveform is very uniform. Zoomed in the waveform is sine shaped but instead of a smooth curve I see more like a sawtooth waveform as the points switch from one sinewave amplitude to the other, that is why the waveform on the image appears to be coloured in.

 

To recover the data I use the decimate 1D array if I have used the Interleave 1D array to send the data, or when using the way you suggested I used the index array function. I have tried variations on these themes but that doesn't work either.

 

Maybe I can have a closer look at the data to see if it is consistantly wrong on every run of the program, if so then I can just correct it in the code.

 

Cheers.

0 Kudos
Message 14 of 19
(2,119 Views)

Ah, I see. You also need to use decimate 1D array using this technique.

 

On the target, using my method, you write data into the FIFO of:

 

A B C A B C A B C A B C etc

 

On the host, you read a number of elements from the FIFO. The result is an array of datapoints. You want to separate out the datapoints so that you have an array of As, an array of Bs, an array of Cs. This is where you use decimate. The relevant code from my host:

 

Read all elements in the FIFO:

fifo-read.png

 

Decimate the array from the FIFO to return my original three arrays:

 

fifo-decimate.png

 

 

An alternative to using decimate to reconstruct the original three datasets would be to use a reshape array primitive and wire accordingly. This would allow you to change the number of channels you decode into programmatically.

 

(I'd upload code / snippets, but there's a load of other stuff going on in these VIs alongside that I am unable to share, and don't have time to create examples for you!)

---
CLA
0 Kudos
Message 15 of 19
(2,112 Views)
Solution
Accepted by REAL!

I have finally managed to get it to work and the problem was nothing to do with the interleave array or the decimate array but in fact was caused by the way I was checking to see if there were elements available.

 

This was done as follows:

 

No. to read.png

 

Previously the '9' was a '10' which meant that there was always an extra element read (as 10 is not a multiple of 3) that was just attached to the end of the decimated arrays. It worked for 2 1D arrays as obviously 10 is a multiple of 2, it also explains why it didn't work for 4 arrays.

 

Amazing what you can "see" after a good nights sleep and a big cup of tea!

 

Thanks for the help, even though the problem turned out to be of my own making I still learned something from you guys.

 

Cheers,

 

Darren.

Message 16 of 19
(2,091 Views)

Great that you now get the correct data!

 

I was wondering why I still couldn't get correct data, as I didn't make the same mistake as you. I finally realized, that I opened a ref to the wrong FPGA VI 😄 Haha! So I didn't receive the data I expected.

 

Well well. Nothing a good night of sleep can't fix!

 

Best Regards

Alex E. Munkhaus
Certified LabVIEW Developer (CLD)
System Engineer
0 Kudos
Message 17 of 19
(2,085 Views)

@REAL! wrote:
Previously the '9' was a '10' which meant that there was always an extra element read (as 10 is not a multiple of 3) that was just attached to the end of the decimated arrays. It worked for 2 1D arrays as obviously 10 is a multiple of 2, it also explains why it didn't work for 4 arrays.

Glad you figured it out! As a suggestion for future posts, if you had attached that screenshot to your first message, we might have gotten to the solution a lot faster.

0 Kudos
Message 18 of 19
(2,073 Views)

can you share the completed code file

0 Kudos
Message 19 of 19
(1,008 Views)