LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Compiler optimisations and IPE

I have a general question regarding compiler optimisations in LabVIEW.

 

There are many things the compiler can optimise inclusing the unbundle - modify - bundle action becomine an in-place operation which is cool.  Generally one can forgo using an inplace element structure when doing such operations.

 

HOWEVER: At some stage as code complexity grows, the compiler stops applying some (all) compiler optimisations and suddenly the performance dropy like a stone.  Is there any way of knowing which optimisations will be lost first or is it purely dependent on the complexity of the code itself?  Is there any kind of guide for this or is it simply a case of "pray for a miracle" once the compiler complexity threshold is reached?

 

I ask because I think there may actually be some issues with the display of the code complexity for some VIs.  In a project of mine I utilise a LOT of inlined vis (static LVOOP) and although the overall VI says it has a complexity of 4-5, the unbundle-modify-bundle operation is massively more expensive than the same operation using an IPE.

 

In addition, does it matter whether the code to be optimised is ont he top-level BD, in a sub-vi or 5 levels down in sub-vis (all inlined)?

0 Kudos
Message 1 of 10
(4,198 Views)

The only optimizations that we turn off are those applied by LLVM. At a certain threshold of complexity, we drop to a lower level of LLVM optimization. (We used to drop LLVM entirely, but not any more... I'm not sure what version that changed in.) That threshold is controlled by Tools >> Options >> Environment >> Compiler. Note that there are some specific LLVM optimizations that we always disable for very large VIs regardless of this threshold setting. Breaking your VIs into subVIs avoids this issue... unless you inline the subVIs in which case you're right back to where you started in terms of code complexity.

 

The LabVIEW optimizations always apply when the compiler recognizes that it can apply them, but as code grows, the probability that you do something that makes the analysis fail increases. The compiler is way more complex than any human being can decisively analyze at this point. The number of optimizations that stack on top of each other and the geometric ways that they can interact with each other mean that the rules for what goes first is pretty much "read the source code of the compiler and execute it for yourself for your particular VI." Not particularly helpful.

 

What I can say is that the more information that you provide to the compiler about what you're trying to do, the better things work out. So, for example, use the Swap Values primitive instead of crossing a pair of wires -- it's easy to drop and looks cleaner than the "swastika" that usually forms from swapping. Use the Inplace Element Structure when you're digging a value out of a structure and then putting it back modified. Again, it cleans up the wire that is the cluster/array being modified, so it often helps the readability of your code to do these things anyway.

Message 2 of 10
(4,141 Views)

@AristosQueue (NI) wrote:

So, for example, use the Swap Values primitive instead of crossing a pair of wires -- it's easy to drop and looks cleaner than the "swastika" that usually forms from swapping. 


Thanks, AQ, I'd completely forgotten about this little function!  I have good reasons to avoid backward swastikas, so I'll start using Swap more! 

 

Bob Schor

0 Kudos
Message 3 of 10
(4,133 Views)

I suddenly feel the need to fill in extreme detail ... use it instead of crossing wires when what you're doing is swapping two values. Don't do it just because wires of the same type happen to cross! 🙂

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

Duh ...  my bad.

 

BS

0 Kudos
Message 5 of 10
(4,104 Views)

@AristosQueue (NI) wrote:

I suddenly feel the need to fill in extreme detail ... use it instead of crossing wires when what you're doing is swapping two values. Don't do it just because wires of the same type happen to cross! 🙂


If you didn't make that clarification people might have started cleaning up their Block Diagrams in hopes that their code would run faster without visual wire crossings so it wouldn't have been that bad.

Matt J | National Instruments | CLA
0 Kudos
Message 6 of 10
(4,094 Views)

I apologize for hijacking this thread, but I am desparate for an answer. (I believe it is directly related to the conversation here) Could you look at http://forums.ni.com/t5/LabVIEW/LabVIEW-2015-Buffer-Allocation-Bug/m-p/3303432#M966610 the last entry. I would like to know why the IPE structure makes two buffer allocations. You are probably one of the only people who can answer.

 

cheers,

mcduff

0 Kudos
Message 7 of 10
(4,015 Views)

Looks like a bug to my eyes, but I am definitely not an expert. I've passed your post along to those who are.

0 Kudos
Message 8 of 10
(3,931 Views)

Thanks for looking into this!

 

Cheers,

mcduff

 

0 Kudos
Message 9 of 10
(3,928 Views)

For anyone else reading this thread:  I posted an answer in the other thread that mcduff linked to above.

0 Kudos
Message 10 of 10
(3,853 Views)