02-10-2012 10:05 AM
I have a situation where I need to "spawn" one or more clones of a VI. To make what I'm doing more "transparent" and easier to debug (particularly by someone else who doesn't have access to my memories), I like to use a Static VI Reference (which has the icon of the VI I'm trying to spawn) and getting its Path property to pass to Open VI Reference instead of using a Path or String constant.
This worked fine as long as I was in "development mode", and running the code from within LabVIEW itself. However, the moment I made an executable, I got Error 1127, "Cannot instantiate template VI because it is already in memory". Not wanting to admit defeat, I searched for help on this, and found some earlier posts in this Forum that also found this problem, but I wasn't sure that I saw a solution there, other than the suggestion to not use a VIT but instead create a "Reentrant" VI (something of a misnomer -- I think of reentrancy as the ability to call yourself, which is not quite the same thing as the ability to clone yourself ...).
So I worked out a solution, which I'll describe here.
First, when you create a Build in Project and use a Static VI Reference as I've done, you need to include the VIT that you reference in your list of Always Included files (if you don't, Project will complain and not let you build). Next, you need to provide a copy of the VIT inside the Build folder (where your Application file is located). This is a convenient place for the VIT, right next to the file that needs to reference it.
The VI that takes the Static VI Reference in and returns a reference to a VIT Clone needs to detect whether it is running from within a Development System (e.g. LabVIEW.exe) or a Run-Time System (e.g. your application). As noted above, from a Development system, you need only use the Path property of the Static Reference and pass it through Open VI Reference. From the Run Time System, you need to build the appropriate path. You can use the Static Reference's Path property to strip out the filename, and can use the Application Directory property of the application to strip out the path. Now build a path from the App Dir "path part" and VIT Ref "filename part", pass this to Open VI Reference, and you're done.
Best of all, I've tested this within a built executable, and it works!
Here, in two snippets, is the VI, which I call "Create Clone Refnum".
02-11-2012 11:22 AM
@BOB Schor wrote:
...but instead create a "Reentrant" VI (something of a misnomer -- I think of reentrancy as the ability to call yourself, which is not quite the same thing as the ability to clone yourself ...).
That's recursive, not reentrant (although it is true that all recursive VIs in LV have to be reentrant, unless you use VITs). Reentrant doesn't mean that a VI can clone itself, but rather that there can be multiple copies of the VI in memory at the same time.
In any case, making the VI reentrant is actually a lot easier - all you need to do is pass 8 to the OVR primitive, like I said in the other thread, which allows you to keep using the static reference to get the path (which is good) and which doesn't require any tricks when building.
In the past, VITs were required, but these days reentrant VIs can pretty much do everything they do and they're easier to use. This has been the case since around LV 8.0 or 8.2.
02-11-2012 11:37 AM
I stand corrected on the distinction between "reentrant" and "recursive". You'd think as a former PDP-11 programmer who knew all about ISRs, I'd remember what "reentrant" really means ...
Is there any objective reason to prefer constructing clones from VITs or from calls to a reentrant VI? Obviously if one method "worked" and one didn't, the choice would be obvious. Similarly, if one ran 20% faster, used many fewer resources, etc. My current preference for the VIT route is that it is mnemonic -- you know (even if you are not the originator of the code, but are maintaining it a year later) that a clone will be created (though I'll grant that the "8", very mnemonic in itself, in the Obtain VI Reference might serve as a clue).
02-12-2012 02:57 AM - edited 02-12-2012 02:58 AM
@BOB Schor wrote:
Is there any objective reason to prefer constructing clones from VITs or from calls to a reentrant VI?
I'm not sure if there are functional differences anymore. Like I said, in the past VITs did things RVIs could not, but they have since caught up and they're easier to use. There are some differences in resource use (e.g. RVIs can use a shared pool of clones), but I'm not sure what they all are and I'm not sure you can get them when you load them dynamically.
Personally, these days I use only RVIs and they can do everything I needed (expect be called dynamically as a dynamic dispatch VI, but that wouldn't work with VITs either). The only time I remeber using a VIT in the last few years was when I had to make a change to a 7.0 program, where RVIs couldn't have a usable front panel.
As for the 8, it's a bitfield, so that's simply the 4th bit. I don't think it holds any hidden meaning.
02-25-2014 02:47 AM
Hello Bob_Schor,
I tried and worked out this issue as the same way "Next, you need to provide a copy of the VIT inside the Build folder (where your Application file is located). " , before I read your comments.
But there is a risk, anybody can copy the original VITs file and change it, I think it's not the best way to solve this issue. additional method is to set a password to VITs file, but I haven't try it. I have submitted this question to NI technoligy support, I want to get a formal feedback about it.
02-25-2014 03:13 AM
Like I said, you can just have the VIT (or reentrant VI, preferrably) inside the EXE. That way the VI is not easily accessible. The easiest way to do it is to use a static reference to the VI, which causes it to be included in the build and allows you to use the VI Name or VI Path properties on the static reference in order to open a new reference.
02-25-2014 05:59 PM
Wow, a comment from an old Post of mine! I don't use VITs to spawn clones, but am a big fan of Start Asynchronous Call (and Static VI References), which seems to work equally well from Development mode and as a built Executable.
BS
02-26-2014 12:11 PM
@Bob_Schor wrote:
Wow, a comment from an old Post of mine! I don't use VITs to spawn clones, but am a big fan of Start Asynchronous Call (and Static VI References), which seems to work equally well from Development mode and as a built Executable.
BS
Yes this is the more appropriate way to do this same thing without VITs. I posted a while ago an example using this technique which doesn't require knowing the path to any VI files here:
Unofficial Forum Rules and Guidelines
Get going with G! - LabVIEW Wiki.
17 Part Blog on Automotive CAN bus. - Hooovahh - LabVIEW Overlord