View Single Post
  #5   Spotlight this post!  
Unread 26-03-2011, 09:18
Greg McKaskle Greg McKaskle is offline
Registered User
FRC #2468 (Team NI & Appreciate)
 
Join Date: Apr 2008
Rookie Year: 2008
Location: Austin, TX
Posts: 4,751
Greg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond reputeGreg McKaskle has a reputation beyond repute
Re: More local variables.

Quote:
Originally Posted by linkhyrule5 View Post
Actually, I would warn against using Globals in LabVIEW. LabVIEW will actually avoid race conditions by automatically pausing the program to allow everything that needs to write to it to do so before anything can read. This can cause massive slowdowns, as well as otherwise inexplicable pauses in the code.

If you really need to communicate across VIs, make a VI whose only purpose is to serve and receive a value, as follows:

Code:
Indicator - Control
Perhaps I can clarify a bit. Data updates in LV are always atomic. They are protected so that competing writes will not corrupt the result, but they do not avoid race conditions -- using the definition that NI teaches in its classes.

As an example, lets say that some loops are playing a game. Each loop is assigned a color from the rainbow, and they update a global with the color whenever they like. They don't coordinate their updates, but since the writes are atomic, the color in the global will always be a legal color -- "red", "orange", "yellow", ..., "violet". You will never see odd combinations such as "blulet" or "violow". To do this, LV must make the writes atomic using a lock or mutex. It adds some overhead to the value update, but it is certainly not a massive slowdown.

To show that, write the program to play the game on your laptop. Seven loops running full speed in parallel, each updating a variable with their color and the loop iteration they are on. I wrote mine to each update 1000 times. No race conditions or corruptions ... yet.

Change the game so that the loops append their values, and you will start to see race conditions as shown in the second png. If you look carefully at the resulting data stream, you'll notice that yellow skips number 309. Or rather, that the orange loop and yellow loop had a race. They both read the buffer, both updated, their local copy of the buffer, and then both wrote their string to the variable. In doing so, the yellow buffer that contained 309 was overwritten with the one from orange that was old. There is evidence of several other races in that portion of the buffer. You also get to see how the OS scheduler chooses to swap out threads. This laptop is a Core 2 Duo and you will see lots of interleaving, allowing more races.

To get rid of the race, you get rid of the read-modify-write access patterns that can interleave. In this case, the easiest way to do this is to build a subVI that accumulates the buffer. Each loop will pass in only the value to add "color #", and since subVI are also atomic, no values are lost -- ever. Again, this is a bit more overhead, but not massive. Making the subVI is a bit more complex than just a control wired to an indicator, but if you look in tutorials or examples, we refer to them as either "functional globals", or sometimes as LV 2 style. The name refers to when this was this was the only way to get global data. LV used to be ever more functional and didn't have global or local variables.

Back to the topic, it is really the access pattern that causes race conditions, and they aren't necessarily bad. Just be aware when you are allowing them to happen. If you have only one writer to a global or other storage within your program there are no races.

Greg McKaskle
Attached Thumbnails
Click image for larger version

Name:	Screen shot 2011-03-26 at 7.33.25 AM.png
Views:	19
Size:	25.2 KB
ID:	10485  Click image for larger version

Name:	Screen shot 2011-03-26 at 7.40.38 AM.png
Views:	16
Size:	53.2 KB
ID:	10486  
Reply With Quote