LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

What's wrong with a "regular" global in this case? AND WIl ActiveX objects stored in functional globals remain valid (when used in an executable)?

I've written a plugin layer for a LV executable.  When this layer makes a call to the plugins' initialization functions, I want each plugin library to be able to initialize and maintain its own global memory (where things like VISA resource names or ActiveX objects are stored).  However, I've found that I can't manage to keep my global VIs "alive."  I'm inclined to switch to functional globals, but I suspect that this will be a problem for things like ActiveX objects (that in this particular case reference a CAN interface).  I believe that the functional global will indeed store the object from run to run, it's just that I'm somehow disinclined to think that the object will remain valid.  I think you'll have to re-initialize it.  Can anyone speak for or against this hunch?  (If you can't tell, I'm trying to avoid building a whole little test executable just to debug this problem.)

I suppose the more profound question is "Why don't the globals stay in memory?"  I'm attaching an image of what the application layer that calls the plugins' intializations looks like.  Next I'm attaching an example of an actual initialization routine.  You'll notice that I've even gone so far as to explicitly open the ref to the global VI that I want to keep in memory.  Then I just leave it there dangling - but it still gets dropped!  In my mind I shouldn't even have to do this, since the dynamically-called subVI "MC_CMO Init.vi" actually initializes the globals and runs with AutoDisposeRef = False. 

Lastly, this is my first-ever attempt at writting plugin software.  So if you look at my code and have any criticisms/pointers, I'll greatly appreciate them.

Thanks in advance,
Nick




"You keep using that word. I do not think it means what you think it means." - Inigo Montoya
Download All
0 Kudos
Message 1 of 5
(2,937 Views)

Hi Nick,

I wrote about this years ago and I suspect your suspicions are correct.

The value stored in the global or LV2 is still there but the validity of the "value" is what changes if the top level VI containing those goes idle.

This is good thing. (back in the old days if you forget to close a ref to a comm port, or a file, you had to re-boot the computer to free-up the resource).

What I believe is happening is LV is doing us a favor and it cleans up the mess we leave whe we are done playing.

So if you want to keep those refences alive then the widget that holds them has to keep running.

Ben

Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
Message 2 of 5
(2,929 Views)
Thanks, Ben.

So it sounds like the work-around is to create some piece of code (widget) that I call dynamically (with WaitUntilDone = False) and all it does is load the globals and then essentially "hang" by waiting on some kind of "close" or "unload" event.  This should keep the globals alive, right?

Nick
"You keep using that word. I do not think it means what you think it means." - Inigo Montoya
0 Kudos
Message 3 of 5
(2,924 Views)

I am not sure if I follow you completely on your work-around.

Everything I have to say on this topic is based on obesrvations and threads I have read on Info-LabVIEW. Therefore it is subject to corecttion by those who know better. Smiley Wink

LV is smart enough to know when "something" that had been opened, can be closed. It is not perfect.

If for instance you open a VISA refnum and pass the refnum  to a LV2 AS A REFNUM the refnum in the LV2 stay alive as long as the VI's are running.

If you start another VI that uses the LV2 to fetch the refnum, it should get a valid ref as long as it starts before the first goes idle.

You then be able to work with refnum usign the VI launched second as long as stays active.

I often create action engine that can be invoked where required throughout an application. If the action engines get a ref in one state (like init) and use it another, I will generally write a "tester" that calls the action engine action to test the engine. In this case, my "tester" stays live and it keeps the ref's fresh.

I suspect if you tried to trick LV you could. If you type cast the ref nums to I32 and stored those in a LV2, I could see how LV could loose track of the resource sharing, but that is something I would avoid.

So I encourage you to do some experimenting with keeping track of who's running when to see if your work-around will work.

If you think you understand it better than I explained it, please post.

Trying to help,

Ben

Retired Senior Automation Systems Architect with Data Science Automation LabVIEW Champion Knight of NI and Prepper LinkedIn Profile YouTube Channel
Message 4 of 5
(2,915 Views)
All I meant by my work-around was something like the attachement below.

I get what you're saying with the "action engine" and tester.  I'll have to see if that sort of scheme would be easily compatible with my code.

Thanks for all the help.  I think I've got some directions I can go with this.  I just wonder when I'll ever stop being confused by LV's memory management!  Just when I think I've got it figured out, something new comes along to stump me!

Thanks again,
Nick
"You keep using that word. I do not think it means what you think it means." - Inigo Montoya
0 Kudos
Message 5 of 5
(2,908 Views)