LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Refnum is No Longer Valid

Hi Guys:

 

     i met a "Refnum is No Longer Valid" issue in following case:

 

1 In B.vi , "Open vi reference" of A.vi(option x100) , Start Asynchronous Call , and store the reference into a global variable

2 In C.vi,  use "Wait On Asynchronous Call" to queue the status of the A.vi instance calling from B

 

     Problem here is , when i use the global variable in C.vi , it shows the correct memory address but "Refnum is No Longer Valid" , i know there's already some discussion about this , saying that all the reference will be clean after vi finish , solution is like "The simple (and correct) solution is not to call the functional global by itself, but only to call it as a subVI." , i don't quite understand what does this mean , any suggestion ?

 

 

0 Kudos
Message 1 of 9
(3,745 Views)

Basically suppose you have your two top level VIs A and B. If you open a refnum in the hierarchy (any subVI) of the top level VI A and A terminates, that refnum will be automatically closed. The only kind of refnum where you can disable that are VISA refnums, by going into the LabVIEW Options and selecting the according checkmark.

 

It doesn't matter if you store the refnum in a global variable or a subVI (Intelligent Variable). As soon as the top level VI, in whose hierarchy a refnum was created goes idle (stops executing) LabVIEW automatically garbage collects that refnum and it is not anymore valid to be used in another top level hierarchy. By using either the Run VI or Call VI Asynchronous option, that VI is running as an independant top level VI and therefore independent of the refnum that was created in the original hierarchy that started your B VI.

 

Solution is either to make sure the refnum is only opened in the hierarchy of B VI, or make sure A VI stays active and running, until the refnum is not anymore needed.

Rolf Kalbermatter
My Blog
Message 2 of 9
(3,715 Views)

Seems like there's no good solution for this , 

 

The reason why i need to do like this is :   i want to build those Vis into dll , export B.vi and C.vi as functions, so that i can load A.vi using B.vi asynchronously instead of starting another thread in c code , and i can use C to queue the status of A,vi, even abort A.vi using abort vi ....

 

What do you think i can do the mulithread inside labview, i just don't want to build a labview dll which require creating mulit thread in c ode.

0 Kudos
Message 3 of 9
(3,692 Views)

adobefree@gmail.com wrote:

Seems like there's no good solution for this ...


Try "Call and Forget" (option0x80), as that starts a VI as independant of its caller.  "Call and Collect" (0x100) creates a VI that is "owned" by its caller and will abort if its caller goes idle.  

0 Kudos
Message 4 of 9
(3,680 Views)

Thank you, i wil try "Call and Forget" (option0x80) , but does that mean i can't get the results any more ?

0 Kudos
Message 5 of 9
(3,655 Views)

adobefree@gmail.com wrote:

Thank you, i wil try "Call and Forget" (option0x80) , but does that mean i can't get the results any more ?


You'd need to use a different method to get the results.  

 

Quick aside: I've never worked with a LabVIEW dll, but are you sure that your A, B and C VIs won't be all running under the same hierarchy?  "Going Idle" doesn't mean the VI stops running; it means it isn't reserved for execution (i.e.. nothing that calls it is running).  I would have expected all functions in a dll to be reserved together.

 

Working with independant VI hierarchies and the issue of reference lifetime is tricky, but also doable.  So if you do need A to continue after B's VI hierarchy has stopped then I can describe it.  But first double check that you need the complexity.

 

 

 

 

0 Kudos
Message 6 of 9
(3,641 Views)

 

"So if you do need A to continue after B's VI hierarchy has stopped then I can describe it.  But first double check that you need the complexity."

 

Yes, i do need this, could you help on this ?

0 Kudos
Message 7 of 9
(3,626 Views)

Any update ?

0 Kudos
Message 8 of 9
(3,574 Views)

adobefree@gmail.com wrote:

Any update ?


Sorry, I'm away at a conference at teh moment.  Basically, when you have VI hierarchies that "live" for different times, then you have to make sure that every reference is created (and thus "owned")  by something that is going to stay active.  So if B launches  A and then goes idle, the communication method to A (which will be used by C) must be created by A.  The easy method for that is:

-- have B create a temporary Queue

-- pass it to A when launched (launch with 0x80 "Call and Forget")

-- have A create its communication queue (or User Event or whatever)

-- pass the comm queue refnum back to B using the temporary queue

-- B destroys the temporary queue, stores the comm queue somehow for C, and finishes.

-- C waits on the Com Queue for the result of A.  

-- you also need a way for A to know that C has gotten the result so it can then finish

0 Kudos
Message 9 of 9
(3,554 Views)