LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

plugin architecture

I have an issue I would like to ponder about:
I have created a program that heavily relies on stricltly called plugins. The plugins perform very varying functions and are developed completely seperate from the main program.
The structure decided to use is to build every plugin into an llb source distribution. I give these builds a special plugin extension. The main vi of the plugin is set to top-vi. the top-vi's are indexed by the main program and enumerated in a menu.
So far so good...
Now, the following problem arises: it is often very hard to make the plugin distribution such, that it will run from within executable. The main issue seems to be that the llb does not contain all dependencies. Furthermore, I have some major issues with building source distribibutions that contain all vi.lib VI's, because the chance of cross linking is considerable.  In short; many plugins work, but this method seems to fragile for a robust application distribution.

I am now evaluating the best possible alternatives: I think I prefer to have the plugins built as executables, but I would still prefer to call the plugin top vi directly within the executable. This doesn't work like it used to anymore, either..
What to do? who has a good, robust solution for elaborate plugins? Maybe I just need to change the way I build the plugin llb's?


0 Kudos
Message 1 of 22
(4,647 Views)

i stopped using llb when i discovered that not all vis where saved in it. it happens often when i call the reference to the subvi, and not the sub itself.

since then i am working under "labview project" environment. in this case all vis are saved in the HD in designated folders that are not affected by the project. the files can be moved in the project from library to library or project folder, without changing any property on the HD. that allows to use subvis in different projects, and to easily keep track of changes.

now i have never made executables in such configuration, but it seems it worth a try.

 

-----------------------------------------------------------------------------------------------------
... And here's where I keep assorted lengths of wires...
Message 2 of 22
(4,633 Views)

Well, I am doing that too, but it is not the issue I am trying to solve here. When I build a program that is to function as a plugin, I want it to be one file (maybe with a support directory). This means it will have to be an llb or executable.

I am now looking into using TCP/IP for communication and build all plugins into executables, but it makes the plugins somewhat slow to pop up.

I am using LV8.2.1 Hopefully moving on to 8.5 this week.

0 Kudos
Message 3 of 22
(4,603 Views)

Note - I don't have any experience with this type of architecture, so this is just a thought.

How about namespacing each LLB (including the vi.lib VIs in it) so that you can load them at the same time? That would make them individual entities which means you can move them around as much as you like. I believe the OpenG builder can build LLBs like this, but I don't know how nicely it plays with 8.x.

Some disadvantages:

You get large LLBs with multiple copies of the same VIs in memory.

If you have dynamic calls by name, you will have a problem.


___________________
Try to take over the world!
Message 4 of 22
(4,593 Views)
NI uses this type of architecture internally quite a bit.  Here are some tips to make it work.
  1. As tst mentioned, when you create a plug-in LLB, namespace it and include all dependencies.  Namespacing will depend on which version of LabVIEW you are using.  If you have version 8.0 or higher, putting the VIs in a uniquely named library will do it.  Any other version can be namespaced by adding a unique prefix or suffix to your VI names during your LLB building process.  As tst said, this has the disadvantage of having a lot of VIs which are the same, but with different names, in memory at the same time.  This is not all bad, since a given VI can only be in use at one location, unless it is reentrant, so this can give you some extra performance.
  2. Use a well-defined set of core VIs in a well defined relationship to your core VIs.  Typically, during development, you would use a set of directories named xx.llb.  During deployment, you would create LLBs with the same names.  To the LabVIEW code, the path is the same.  The key is to maintain the exact same directory path relationship between the various code pieces.  This has the down side that if the core code changes without the plug-ins changing, it will break the plug-ins.  This is the LabVIEW equivalent of the Windows DLL hell issues that were common in early Windows builds.  Proper installer and versioning support should take care of this issue.
  3. Assume the root position of your plug-ins will change.  To find the plug-ins during use,  place a statically called VI in their directory that you can use to find the directory path (use the current VI path property to do this). Note that condition 2 must still be met - the VIs must have a well defined relation between their directory positions.
Let us know if you have any more specific issues.
0 Kudos
Message 5 of 22
(4,572 Views)


@DFGray wrote:

If you have version 8.0 or higher, putting the VIs in a uniquely named library will do it. 


I was thinking of mentioning libraries, but I was under the impression that once you put a VI into a library, you can't use it in any other library. Is this impression wrong?

Also, do libraries work the same in the RTE?


___________________
Try to take over the world!
0 Kudos
Message 6 of 22
(4,554 Views)
Great, this is the pondering I was hoping for.

Your responses reminded me of some more details I have implemented:
-Of course I have a predefined pane for the stricly called plugin VI. Actually, I have several, for several types of plugins (defined by extension)
-each plugin exists of one llb only
-each plugin is using unique lvlib namespacing, although I need to take caution here, since I am using a "plugin template" lvlib.
-all VI's used in a plugin are developed from within a single directory: this prevents llb building issues
-I try to nest other lvlib's inside the plugin lvlib. Unfortunately 8.2.1 is buggy with nesting lvlibs, and I oftentimes don't nest. I DO put these other lvlib's in the same directory.
-When building, I define most items as "include if referenced"

When I build while removing vi.lib etc, it will oftentime still run on a machine that has labview installed. On machines with just the RTE, there is no way. I have oftentimes had to build plugins over and over, before I get them to work. Recently I failed to get one to work at all. I am just now realizing I should open this plugins on that particular machine development system. Then, at least, I should be able to see what is breaking the code.

DFGray:
I am trying to understand your recommendations. I am not sure how much I meet them with the methods described above. The plugins are not root sensitive. The main program will only detect the plugins located in the executable directory path.
I just installed 8.5 and I hope it will do a better job at building llb's: oftentimes in 8.2.1, the plugin project lists crazy dependencies that in no way can be necesary for that particular project.

When including the vi.lib dependencies, I cannot really test the built llb. I experienced that vi.lib cross linking is easily invoked.

So, you guys actually recommend this method? No one thinks I should try dll or executables?
Is there still no way to directly run an VI from within an exe?

Message Edited by aartjan on 09-11-2007 12:41 AM

Message 7 of 22
(4,534 Views)
tst: yes, lvlib's will reside inside lvlib's and llb's. A major issue is that the nested lvlib will break when being nested, as described in this thread
As the thread concludes, this nesting issue should be resolved in 8.5.



Message 8 of 22
(4,528 Views)
Hi aartjan,
      I know nothing about namespaces, but have been distributing "plug-in" LLBs for a while and have learned how to gather dependencies.  The method changed between 7.1 and 8.2  and I had to get help myself - the 8.2 (8.x?) method is described here.
 
Cheers.
"Inside every large program is a small program struggling to get out." (attributed to Tony Hoare)
Message 9 of 22
(4,514 Views)
tst, you are correct that once you put a VI in a library, you cannot put it in another one (well, you can, but it removes it from the first one).  Putting a VI in a library is, to LabVIEW, equivalent to renaming it.  But it does not rename it on disk.  I have used this to my advantage in plug-in architectures to have the entire plug-in always have the same names on the VIs, contained in different libraries in different LLBs or directories.  The VIs are opened by name and path, so the core code never changes since the VI names on disk are all the same.  All that changes is the location.  The scheme works as follows.  In a preset directory, I have a set of VIs with a set prefix, one for each plug-in (e.g. VIs are named plugInInfo_*.vi).  These VIs' sole purpose is to return information about the plug-ins, one piece of which is the disk location of the plug-in.  The plug-ins can then be located anywhere on disk.  With the location and constant disk naming convention, the plug-in VIs can be easily located and run.  Without libraries, you can do something similar, but would need to include prefix/postfix information in the plug-in information VIs (I did this until I found out how easy it is using libraries).

Libraries are supposed to work in the RTE.  I have never done this, however.
Message 10 of 22
(4,494 Views)