From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.

We appreciate your patience as we improve our online experience.

LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Storing Information within VIs

Solved!
Go to solution

I have an interesting problem...

 

I have a VI that controls a sub-system. It has ~80 inputs, when it's used it programs the sub-system with those inputs. The inputs aren't homogenous, they're configuration information and each means something different. This VI is used both interactively and as part of a larger system. Since it has many inputs I've used clusters to group together related inputs.

 

As far as I can tell LabVIEW enforces the following scope rules when SubVIs are involved:

* Controls that are wired to the connector panel

When a higher-level VI calls a SubVI if the higher-level VI wires an input then the SubVI recieves that value. If the higher-level VI doesn't wire an input then the default value is used.

* Controls that are not wired to the connector panel

When a VI is loaded into memory the front panel is loaded with the default values, even if the VI isn't visible. LabVIEW retains the values set by the last use of the VI. The same applies to unwired shift-register inputs.

 

The behaviour of unwired controls is useful as it allows information to be stored, it allos "information hiding". In my application I can open the sub-system VI described above interactively and set up some values. Then higher-level VIs call that VI as usual. Those higher-level VIs need not know anything about the settings I've changed. Where I work this idea is used in the code for many years. It's similar to the "functional global variables" made using unwired shift-register terminals.

 

Once a control must be wired to the connector pane though everything changes, a value can't persist from one use of the VI to the next.  That's true even if the connector pane input is left unconnected since in that case LabVIEW uses the *default value* not the existing value. So, all of the controls that deal with low-level things specific to my subsystem can be left unwired. Then, all the controls that deal with higher-level things that the higher-level VIs can control must be wired and the higher-level VI must take on the responsibility for that information. Previous versions of the system I'm discussing did this.

 

The problem with this scheme though is clusters.  A cluster is either on a connector pane or not, I can find no way of putting some inputs of a cluster onto the connector pane but not others. Since I have so many inputs I need clusters. But, once I assign a cluster to the connector pane the higher-level VIs have to take responsibility for all of it's values. That means I lose all the information hiding I had before and my code becomes much more complicated.

 

Has anyone found a solution to this sort of problem?

 

I can draw it out as example VIs if people are interested.

0 Kudos
Message 1 of 18
(2,747 Views)

Data can persist between calls to a subVI by using uninitialized shift registers.

 

See Ben's Action Engine Nugget.

Message 2 of 18
(2,743 Views)
Once a control must be wired to the connector pane though everything changes, a value can't persist from one use of the VI to the next.

When you say from "one use of the VI to the next", are you talking about between runs or between calls to the VI in one run of the application?

 

=====================
LabVIEW 2012


0 Kudos
Message 3 of 18
(2,730 Views)

Steve Chandler,

 

I mean between calls in one run of an application.

 

Am I right?

0 Kudos
Message 4 of 18
(2,705 Views)

Extracting part of the information is easy. Unbundle the parts you want, single numbers or sub clusters and create indicators for those parts.

 

Same with updating the Action Engine (which is what you're after), get the full cluster, bundle by name to replace parts and write it all back.

 

/Y 

G# - Award winning reference based OOP for LV, for free! - Qestit VIPM GitHub

Qestit Systems
Certified-LabVIEW-Developer
0 Kudos
Message 5 of 18
(2,695 Views)

Yameda,

 

Maybe my description of the problem wasn't clear.

 

Within each VI I can use bundle and unbundle operations. Between VIs though I can only pass clusters or single values. Passing single values is out because the maximum connector pane size only allows 28 values.

 

Passing clusters is problematic though because a cluster write always writes to every field of the cluster.

 

Let's say on the front panel of my SubVI I have three controls A, B & C. A and C are subsystem variables the higher-level code need not know anything about them. My code shows me the SubVI and I update A & C interactively. The B variable is used by the higher-level VIs though, they set it and use the SubVI non-interactively. Now, suppose I have A, B & C in a cluster. The higher-level code must still update B and only needs to know about B. But, because a cluster is written as a whole unit, all of A, B & C have to be written. But how can the higher-level code do that? It doesn't know about A & C. If I make it know about all the 70 odd variables like A & C it would become much more complicated.

 

I think that action engine approach might help.

0 Kudos
Message 6 of 18
(2,689 Views)

A cluster can include clusters. 🙂 Create A, B and C as clusters within the Master cluster.

 

Then you can easily extract cluster A through unbundle.

 

/Y 

G# - Award winning reference based OOP for LV, for free! - Qestit VIPM GitHub

Qestit Systems
Certified-LabVIEW-Developer
0 Kudos
Message 7 of 18
(2,685 Views)

I feel appointed to correct one aspect of the initial post:


@rthorpe wrote:
[...]

* Controls that are not wired to the connector panel

When a VI is loaded into memory the front panel is loaded with the default values, even if the VI isn't visible. LabVIEW retains the values set by the last use of the VI. The same applies to unwired shift-register inputs.

[...]



This is not true. When loading a VI, loading of the front panel depends on some factors. So it is possible, that the front panel is not loaded into memory; still, the default values will be available for control terminal (to be more precise: the default value is already in the "Execution Buffer").

If the data space is not unloaded, the memory space for the 'Execution Buffer' will also remain in memory, hence the "VI remembers it's last settings".

So it does behave similar to an uninitialized shift register, but you still cannot compare it: You could use VI server to modify the data content of the Execution Buffer, but you cannot modify the content of the shift register.

So a shift register is always the better choice for storing information locally.

 

hope this helps,

Norbert

 

EDIT: Those mechanism store information volatile. So nothing "for eternity"....

Norbert
----------------------------------------------------------------------------------------------------
CEO: What exactly is stopping us from doing this?
Expert: Geometry
Marketing Manager: Just ignore it.
Message 8 of 18
(2,679 Views)

Norbert,

 

Is the execution buffer you mention ever emptied?

 

Perhaps I should ask it like this.  In C I can write:

 

void foo (int x)

int y;

static int z;

{

... code ...

}

 

Does an unwired terminal act like z?

 

0 Kudos
Message 9 of 18
(2,666 Views)

Yamaeda,

 

I know clusters can be put inside clusters but I don't see how that helps.  Even if I put A, B & C within a larger cluster I still have to write to all of them whenever a SubVI is called. The larger cluster follows that same rules as the smaller one, it must be written as a block when it's wired into a connector pane.

 

0 Kudos
Message 10 of 18
(2,660 Views)