LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Setting up use of a DLL for Multithreading operations.

Hi all,

I have been working the past few weeks converting a slow part of our labview code into C++ and hoping that from there I can use CUDA to further optimize and speed up the process.

 

I just finished writing everything in C++, and the program works well, but it is already much slower than the old code. This is due to the fact that the old code could multithreading and use up the entire processing power of my processor, while my current code does not seem to want to do this.

 

I know that there are many settings from labview to visual studios to even my code itself to allow for mutlithreaded operations, and allow them to happen safely.

 

I was wondering if anyone could help me identify these settings so I can move forward with my optimization.

I will tell you what I have looked at and done so far:

 

First I made sure that my program takes all the Array Handles and Numeric values, and assigns them to local variables in my program. I believe this makes my program reentrant safe.

 

Then in VC++ 2008, I added some settings to my project settings: Under C++ Optimization, I have Maximize Speed(/O2), enabled intrinsic functions, and favored fast code.

In code generation, I have my runtime library as Multithreaded debug dll.

 

Then in labview, the DLL is nested 2 SubVIs deep. The main VI has no special settings that I am aware of, but the first SubVI is set to time critical priority, and reentrant execution, while the final subVI which holds my DLL is set to subroutine, and reentrant execution.

 

FInally my DLL has run in any thread selected, and debugging turned off.

 

Am I doing this correctly? Are there parts missing in my program that I need to write to allow for this sort of functionality?

 

Thanks!

0 Kudos
Message 1 of 5
(2,908 Views)

Well most of the things seem to be right, however not sure why you think that assigning parameters to local variables makes them any more thread safe than using the parameter directly. For the duration of the Call Library Node call all native LabVIEW data parameters are guaranteed to stay valid and after that they are never guaranteed to stay valid, no matter if you assigned them to local values or not.

 

The other thing you found is that doing multithreading effectively is more complicated than throwing some code together. In LabVIEW most of this is taken care of automatically, in C(++), you have have to jump through a lot of hoops and rings to make that happen. While LabVIEW itself will happily call the DLL function from multiple threads, whenever your C code hits some shared resource, there will be some arbitration and most likely some blocking of one thread by another. And many CUDA resources are such shared resources. So just by separating your code across C functions you may have made your code less parallel than executing it entirely in LabVIEW.

 

Generally performance in itself is nowadays seldom a valid reason to change LabVIEW code to C(++) (and in fact has been for a long time already if you took certain precautions in LabVIEW coding into account). But the LabVIEW compiler has become so effective that many of those prcautions are not as important anymore either.

 

One point which sure is most likely contradictive is to use multi threading debug DLL C runtime and O2 or higher optimation. I'm not sure if one nulls out the other and which one would which but it is generally not the recommended combination for sure.

Rolf Kalbermatter
My Blog
0 Kudos
Message 2 of 5
(2,901 Views)

Thank you for your reply.

I assign parameters to local variables for exactly the problem you described, shared resources. For example, this program in particular works on a video file, and completes a process on a frame by frame image. I assume that if I do not copy the values to a local variable, the array handle for the image will change between different instances of the program, and this might be bad if we are at first analyzing frame 3, and then suddenly, it changes to frame 5.

 

Is this not something I should be concerned with, does labview take care of this already? It seems there is a lot of magic happening behind the walls and options of labview

 

And I agree, Labview is quite good, and I did not expect a big boost from converting my code to C++. However I see no reason it should be any slower than the existing labview code, if most of the functionality is just rewritten in C++. The real reason for the code conversion, was to eventually write certain parts in CUDA, which I felt would be easiest once the code is in C++.

 

I guess my real question is what are the "hoops and rings" i need to jump through to match the labview efficiency?

 

thank again!

0 Kudos
Message 3 of 5
(2,896 Views)

@Deturbanator wrote:

Thank you for your reply.

I assign parameters to local variables for exactly the problem you described, shared resources. For example, this program in particular works on a video file, and completes a process on a frame by frame image. I assume that if I do not copy the values to a local variable, the array handle for the image will change between different instances of the program, and this might be bad if we are at first analyzing frame 3, and then suddenly, it changes to frame 5.

 

Is this not something I should be concerned with, does labview take care of this already? It seems there is a lot of magic happening behind the walls and options of labview

 

And I agree, Labview is quite good, and I did not expect a big boost from converting my code to C++. However I see no reason it should be any slower than the existing labview code, if most of the functionality is just rewritten in C++. The real reason for the code conversion, was to eventually write certain parts in CUDA, which I felt would be easiest once the code is in C++.

 

I guess my real question is what are the "hoops and rings" i need to jump through to match the labview efficiency?

 

thank again!


It's still not clear to me what you expect by the use of local varaibles in terms of parallel execution. Or maybe you are not talking about function local variables but module local variables outside the function???? If that is the case, then you have probably totally misunderstood the fundamentals of multithreading safe code.

 

When LabVIEW calls a function through the Call Library Node, it will make sure that all the parameters passed to that function stay valid for the duration of the call. Once the function returns to the LabVIEW diagram LabVIEW considers it safe to do with the buffers as it likes, including moving them in memory, resizing them, reusing them for other stuff, or simply deallocating them. So saving such a parameter to a function local variable makes no difference, since the function local variable will exist just as long as the parameter is guranteed to be valid. And saving it to a module local variable is either creating a pretty sure race condition or even crash, if you just save the reference, since the buffer the reference is pointing to will not be guranteed to stay valid after the function returns. And if you save it to a local variable by copying its contents it will be safe, but a performance problem, as you create a copy of the data.

 

So what are you really doing here? Some example code could certainly help to understand what you are doing, as I have a hunch that what you call a local variable is in fact more a global variable although you may declare it as static and make it in that way local to your code module (but still global to all functions in that module).

 

Generally if you want your C code to process data asynchronously however (meaning working on it after the function returns control to LabVIEW, then you can't avoid to copy the buffers.

 

As to the hoops and rings to jump through there is no simple explanation. In fact there have been entire books written about multithreading, and more importantly correct multiprocessor programming.

Rolf Kalbermatter
My Blog
0 Kudos
Message 4 of 5
(2,888 Views)

Have you considered posting your LabVIEW code here and asking for help with optimization?  I am constantly amazed at the ability of many forum contributors to optimize LabVIEW code in ways that would never occur to me.  You might find you can get acceptable speed purely in LabVIEW.

0 Kudos
Message 5 of 5
(2,880 Views)