Cogs and locks
rtarbell
Posts: 7
Hello all,
I wanted to make sure that I understand this concept of locks before I move on. My apologies if my question doesn't exactly make sense:
Are locks used to lock up variables, or methods, or objects, or all three? As in, if I have a cog, and I want that cog to operate on a long variable, can I have the cog check out a lock on that variable so that no other cog can operate on it?
Same question with a method?
Same question with an object?
The manual says that locks can lock up resources, but what exactly is a resource?
I wanted to make sure that I understand this concept of locks before I move on. My apologies if my question doesn't exactly make sense:
Are locks used to lock up variables, or methods, or objects, or all three? As in, if I have a cog, and I want that cog to operate on a long variable, can I have the cog check out a lock on that variable so that no other cog can operate on it?
Same question with a method?
Same question with an object?
The manual says that locks can lock up resources, but what exactly is a resource?
Comments
But I have an example in that chapter and some SPIN code as well.....
Post Edited (deSilva) : 10/5/2007 7:39:57 PM GMT
- reading it
- adding one
- storing it away
When you have two parallel processes, A and B, incrementing the same variable, their accesses might conflict:
- A reading it
- A adding one
- B reading it
- B adding one
- A storing it away
- B storing it away
Now it will be incremented only once rather than twice...
To synchronize such situations, "semaphores" have been invented. A semaphore (which is a technical term in computer science) is called "lock" with the propeller.
There are eight locks only so you have to be very picky as to which accesses to synchronize.
What you have to do is:
(a) One of the involved processes must reserve a lock (locknmb := LOCKNEW)
(b) When any process wants to modifiy the bespoken variable, it has to wait until a nothr process has completed an concurrent access and stop any one cooperating in that scheme to make a modifying access:
(c) When the modification is completed, the program has to call
Note that the "locking" applies only to "co-operating" processes; there is no enforecement of anything , as the connection between the locknmb and the variable to be "locked" or whatever action, is arbitrary and volatile...
Post Edited (deSilva) : 10/5/2007 8:01:45 PM GMT
...and you could ignore them just the same. If all processes accessing the variable don't check the lock before accessing the variable, nothing is stopping the process from ignoring the "lock" and munging the data. It's really just special use bit flag, I think (?).
You are basically right, but it's not "just", it's quite complex
The "read and modify" must be an inseparable action, needing special HUB logic - as you nowadays can even see in the photograph of th chip
How differently does this behave from settings a variable (bit flag or whatever) in Hub ram that the other cogs would check to make sure it's okay or not to update a specific Hub ram variable? It sounds like the LOCKSET just allows a Cog to Check and Set a "lock flag" in one step, as opposed to a Cog reading a Hub ram variable(flag) to determine a lock, then Setting it if not locked, but in-between the read and write some other Cog could have been doing the same thing.
eh?
Don't let you be fooled by the simple syntax. "myVar++" will take around 10 mys which means that around 200 machine instructions will be spent for it
But even in machine code you would need two turns of the HUB wheel: one for reading the variable, and one to store it. Ample opportunities for ALL other COGs to cross your best designs :-
Post Edited (deSilva) : 10/5/2007 10:02:59 PM GMT
It contains the most important information about semaphores on 200+ pages
But you need some caution IF IT IS NOT JUST WORD (=LONG) you are reading and writing!
The critical scenario would be as follows:
The writer updates word A and B, for some reason having a wait after having written A.
The reader reads A and THE OLD VERSION of B.
This however is not a typical semaphore problem; you could use a "system lock", but you can easily work with a "private lock" C: Whenever the writer updates A and B it previously sets C and resets C after A AND B have been updated.
The reader waits, it it finds the "private lock" C set.
This is a very common use by many COG drivers - see FLOAT32 as a simple example.
Why does it work? Simply because the writer is THE ONLY ONE setting and resetting C - no conflict possible.
Post Edited (deSilva) : 10/5/2007 10:27:16 PM GMT
Let me ask this (assuming I am programming in SPIN language):
Let's say I have a variable I call AAA, and a stack space for another cog called newstack[noparse][[/noparse]20]
And a PUB method called arithmetic_add (takes in one variable, adds 3 to it, and returns a result)
PUB arithmetic_add(input)
output := input + 3
Then, in my main method, I call a function on a new cog:
cognew(arithmetic_add(AAA), @newstack)
1) If I have lots of other cog process running (let's assume I plan on using all cogs), what code for a lock would I write to protect my variable AAA such that no other function or method can use AAA until arithmetic_add is done with it?
2) If I have another method called arithmetic_subtract, what code would I write to test whether variable AAA is locked or not?
3) What does the @ symbol mean when referencing variables?
(1) As long as you use routine (method) parameters a copy of them is made when calling the routine. It might become more complex when this parameter is a pointer and you are using the memory vector pointed to. Then you can use one of the methods discussed above, depending on whether only one writes to it, or many do.
(2) See above, AAA is "read only"
(3) @ means just what you say: It gives you the address of that variable, so you can access it vie
BYTE[noparse][[/noparse]pointer]
or
WORD[noparse][[/noparse]pointer]
or
LONG[noparse][[/noparse]pointer]
or many more variations...
Just edited some most extraordinary typos .
Post Edited (deSilva) : 10/6/2007 3:19:24 PM GMT