Counting Free Cogs
RossH
Posts: 5,519
All,
I recently had a need for a function to return the current number of free cogs. Here is something I whipped up in SPIN that did what I needed:
Anybody?
I recently had a need for a function to return the current number of free cogs. Here is something I whipped up in SPIN that did what I needed:
CON STACKSIZE = 4 ' what is the smallest size this could be? VAR LONG Status[ 8 ] LONG Stack[ 8*STACKSIZE ] ' ' Set Status - set our value in the Status array to 1 ' PRI Set_Status Status[ cogid ] := 1 ' now just wait forever repeat ' ' Start Set_Status in free cogs until we can't run any more, then count them ' PUB Free_Cog_Count : count | i repeat i from 0 to 7 Status[ i ] := 0 repeat i from 0 to 7 if cognew(Set_Status, @Stack[ STACKSIZE*i ]) < 0 ' no more cogs, so ... quit repeat i from 0 to 7 if Status[ i ] > 0 cogstop(i) count++ return countI didn't need it to be very efficient, but it strikes me that this would be a useful function to keep in my box of 'Propeller tricks' - but those who are better at SPIN than I am should be able to do it in much less space (this version takes 96 code bytes, plus 40 longs!).
Anybody?
Comments
-Phil
Neat idea - but all your instances of "dummy" are using the same stack. Won't this cause problems?
Also (and I know I didn't say this, but I should have) the counting function should not return till all the cogs are free again. The main reason you would want to check how many cogs are free is that you want to use one, but with this solution you would get told there are "n" cogs free, but when you actually try and use one there won't be any!
Ross.
Good point about returning.
Andy
Thanks - this is more like the size I had in mind. But it suffers the same problem as Bill's solution - i.e. that you have to wait a certain amount of time after you have calculated the number of free cogs before any use can be made of this knowledge - because the cogs that are supposed to be free will not actually be available for use (in this case, for the next 100_000 cycles).
Perhaps we could instead take a slightly different approach - if the code returned the identity of the free cogs (in a bitset) rather than just the number of them, then programs could then use a coginit instead of a cognew.
Ross.
but needs 2 longs more
Andy
Nice!
-Phil
You are not trying hard enough. You could make that faster by terminating the loop when cognew fails:-)
Does anyone know why I might think so?
[8^) FreeCogs is 20 bytes, plus the 4 longs for the PASM code.
Jonathan
I can not see any other way to get an accurate count given all situations. If more than one cog executes code to start and or stop a cog you can not have an accurate count.
EDIT: Oh, I now see that Phil's "solution" was intended as a joke.
That's some very elegant Spin!
-Phil
Well, I can't fault Phil's method for accuracy - but I think Dave's method wins on size and utility!
Ross
NOTE: THIS CODE IS UNTESTED. THIS IS THE FIRST TIME I HAVE USED THE LOCK OPS.
Please point out any optimizations and/or errors that I may have made.
This is fine if you are writing code completely from scratch - but most people make use of other code that already exists - and that code won't be quite so co-operative!
It would have been good if the Prop had included a built in register that showed the current run state of all cogs. But even that would be fooled on occasion (e.g. if a new cog is started between the time you checked the register and the time you tried to use what you thought was a free cog!).
I wonder if it's too late for the Prop II?
-Phil
Ah I could see this as a problem. I have always preferred to write my own code from the ground up only including existing routines as I must, and then I only use routines written by others if I truly do not understand the core concepts. This is why I have never liked the standard libraries of most programming languages.
Hi Phil,
I hate to tell you this, but I use coginit quite a lot - e.g. in the Catalyst loader.
For instance, some programs fail to run if they are run by a SPIN interpreter that is not running in cog 0.
Other times programs have to restart the cog they are currently running in.
Is there a reason not to use coginit?
Ross.
Different issue really. You already own the cog so no harm done.