LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

LabVIEW array performance: Two loops operating on the same massive array

I would agree that if you don't want to split the array (although with such a large array) then checking out the section you want to work on, working on it externally and then checking it back in would probably be your second best option. This should guarantee that you don't make a copy of the entire array.

 

The next version of LabVIEW should have a feature which would make this somewhat simpler, but only somewhat.


___________________
Try to take over the world!
0 Kudos
Message 11 of 30
(1,025 Views)

I've no idea what is coming in the next versions, but at some point the inevitable is that NI has to trust the LabVIEW user enough to give him the ultimate in-place construct - the pointer to array or cluster (and polymorphic functions that accept the variable or the pointer to variable).  There are glimpses of this already (IMAQ image reference for instance).  

 

Yes this will cause many a novice programmer who dares to use this construct hours of heartache and no doubt the forums will be overrun by problems caused by its careless use.  

 

But if you are serious about performance, determinism and efficiency in an embedded application and you truly want to exploit the power of multicore which requires data sharing between threads (and you don't want to cheat by using DLLs) - you need pointers, even if you have to sign a disclaimer that you understand the risks. 

 

   

Message 12 of 30
(1,013 Views)

AnthonV wrote:

Thanks for these ideas guys.  

 

But am I correct in saying that the functional global or 'action engine' will not work for me if the one loop's period is shorter than the time taken to process in the other loop.  This means that while the one loop is doing an 'action' that takes say 100ms to complete, the other loop which is running at say a 1ms period is going to be denied access to the functional global for 100 iterations?

 

What is key here is that I need concurrent access to the array. 

 

(BTW this is an RT application running on a DELL 4 core desktop PC).

 

 

 


It really depends on what you are doing with both of those competting actions.

 

"back in the day..." when I attended the NI LV RT course, AEs were the one and only best way to interact between deterministic and non-deterministic loops.

 

THe "trick" was to make the AE a sub-routine (Execution >>> Priority). When a sub-VI is maked as a sub-routine you will pick-up an option for the sub-VI call (right-click on the VI icon in the diagram) called "Skip if busy". So if you number crunching action is running when the deterministic loop tries to access it, then LV will not wait for the sub-VI and the call will be skipped.

 

I used that technique on a jet aircraft engine simulator I did back in LV 6. I had a RT loop that had to keep all of the loops closed deterministically but I also need to be able to let the loop know the throotle lever nagel had changed since this was part of the model. So this is how it broke down. The AE was called by a VI that was served (using VI server) to a Widows based app that would allow changes to the throttle postion. THe RT loop would get an initial set of paramter values when the loop first started and would keep a copy in its own SR. THe values in the SR (not in the AE) would be updated from values in the AE IF the AE was not skipped.

 

I would think a similar scheme could work provided the code calling the AE to number crunch was not hammering the AE such that the RT loop could never get at it.

 

In that case maybe using a queue to move the data that needs to be crunched somewhere private may be a better solution.

 

Since I don't know your app and I don't care for playing "fifty questions" I'll have to leave it at that.

 

Have fun!

 

Ben

 

PS And to echo tst, "stay tuned Bat-Fans."

Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
0 Kudos
Message 13 of 30
(997 Views)

You appear to be doing something similar to a project I worked on some time ago.  I needed to capture data at > 1 kHz and write it to a file while evaluating a sample of the data at 10 Hz (running least squares fit).  I used 2 queues and placed data in the 'real time' evaluation queue once every one hundred samples.  I had two copies of data, but not 1 kHz data...

 

 

In your case you might have 1 GB + 10 MB of data instead of 2 GB...

 

If you're using LabVIEW 8.6, the queues have a great option called 'lossy enqueue' that will relieve you of maintaining the positions in your functional global (FG2) array.

 

This thread on the LAVA forums contains some background you might help... 

 

 

 

 

 

Message Edited by Phillip Brooks on 05-20-2009 04:03 PM
Message Edited by Phillip Brooks on 05-20-2009 04:12 PM

Now is the right time to use %^<%Y-%m-%dT%H:%M:%S%3uZ>T
If you don't hate time zones, you're not a real programmer.

"You are what you don't automate"
Inplaceness is synonymous with insidiousness

Message 14 of 30
(995 Views)

I don't think LabVIEW will ever have something equivalent to pointers, as not only does it stand in direct opposition to the direction NI has been taking of doing things automatically (including using pointers behind the scenes to avoid memory allocations) and not giving the user the option to crash, but also because it will probably be techincally complicated. The IMAQ image, as you pointed out, is a reference, not a pointer. A subtle, but important, distinction.

 

NI has been providing more tools to allow you to control memory more explicitly, but I doubt they would give you something which would directly allow you to play with parts of an existing buffer directly. They will probably tell you to simply split the array into smaller parts.


___________________
Try to take over the world!
0 Kudos
Message 15 of 30
(991 Views)

tst wrote:

I don't think LabVIEW will ever have something equivalent to pointers, as not only does it stand in direct opposition to the direction NI has been taking of doing things automatically (including using pointers behind the scenes to avoid memory allocations) and not giving the user the option to crash, but also because it will probably be techincally complicated. The IMAQ image, as you pointed out, is a reference, not a pointer. A subtle, but important, distinction.

 

NI has been providing more tools to allow you to control memory more explicitly, but I doubt they would give you something which would directly allow you to play with parts of an existing buffer directly. They will probably tell you to simply split the array into smaller parts.


 

tst,

 

...

Smiley Mad

 

Smiley Wink

 

Ben

Message Edited by Ben on 05-20-2009 03:25 PM
Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
0 Kudos
Message 16 of 30
(992 Views)

Thanks for all the advice, I'll need a bit of time to digest it all and find what works best for my situation.

 

I agree pointers in the true sense of the word is probably too much to ask for.  How about an in-place constuct as shown in the image attached (lets hope I don't forget to attach it).  This could tell the compiler never to make a copy of the data, no matter how many times the wire is split, acted on, processed or whatever.  If you use this construct, you are saying you take responsibility for your actions and you cannot blame LabVIEW for doing what you told it to do.

 

I am simply trying to protect our investment in LabVIEW - the whole point for us migrating to it was to make things simpler and to make our developers more productive and less frustrated.  Workarounds tend to cause these guys to roll their eyes back and I can always here a couple of 'told-you-so's' muttered from the back.  Given, LabVIEW HAS made our developers more productive and less frustrated - in a huge way and we are thankful for that.  And getting a workaround to work DOES give you that great 'I beat this thing' feeling when it works, but you didn't actually add any value you just made it do what it was supposed to do in the first place.

 

I suppose as the percentage embedded users increase and the percentage express-vi users decrease you'll see a couple more performance related features creap into the Functions Palette.

 

So any thoughts on my suggested inplace construct (in the attached image)?

0 Kudos
Message 17 of 30
(964 Views)

your image ...

 

 

 

...

It still sounds like you should be splitting your data.

 

Ben

 

 

Message Edited by Ben on 05-21-2009 05:49 AM
Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
0 Kudos
Message 18 of 30
(940 Views)

AnthonV wrote:

 

This could tell the compiler never to make a copy of the data, no matter how many times the wire is split, acted on, processed or whatever.


That's an interesting idea, although I don't see it happening, as it opens too many possibilities for users to screw up and because you can implement things differently.


___________________
Try to take over the world!
0 Kudos
Message 19 of 30
(926 Views)

OK so after reading many threads on the topic (thanks for the references to all who contributed) I'm slowly warming up to the idea of splitting my large array into several smaller parts to overcome the concurrent access issues that you get when using single element Qs or AEs.  As suggested above, as long as different concurrent accessors request different parts of the array (this I can enforce) there should be no blocking calls.

 

Now I need to know from those who know - is single element Q's or AEs preferred?  I will be doing a lot of processing on the data so for that reason it might be easier to control memory copies in an AE, but in some threads Q's are said to be many times faster than AE's. An array of Q references also seem simpler mainly as I have no experience with dynamically spawning multiple instances of an AE.

 

Any thoughts? 

 

 

 

 

0 Kudos
Message 20 of 30
(900 Views)