[Tutor] Changing instance attributes in different threads

Kent Johnson kent37 at tds.net
Tue Feb 7 12:31:05 CET 2006


Bernard Lebel wrote:
> Hi Kent,
> 
> I have put together a little script to give a rough idea about what
> the program does.
> 
> http://www.bernardlebel.com/scripts/nonxsi/help/bl_threadtest.py

In this code, there is no guarantee that callMeWhenAttributeChanged() 
will see every change to oBernard.firstname. It could change more than 
once while checkFirstName() is sleeping and looping. The change to 
oBernard.firstname in main could stomp on a change from 
changeAttribute() before it is seen in checkFirstName().

I don't know what the consequences of missing a change are. If the names 
are some kind of command token I would use a Queue - in this example you 
have two producers and one consumer, a Queue will ensure that every 
command is seen. If there is no consequence of missing a change you 
could leave it as-is or use a threading.Condition to replace the polling 
loop with wait() / notify().
> 
> 
> The true program does this:
> 
> - the top program file imports a module called fcJob
> 
> - the top program instantiate the only class in the fcJob module. The
> class is named fcJob as well, the instance is named simply "job". This
> instance has few attribute, the one that I'm interested in now is
> "localjobstatus".
> 
> - the top program file enters a while loop where it checks a variety
> of things, and if certain conditions are met, will start a big
> function in a separate thread.
> 
> - the function that runs in the separate thread reads and writes the
> localjobstatus attributes.
> 
> - while the child thread is running, the main thread checks a database
> every 5 seconds to test the value of certain fields.
> 
> - would the value of specific field changed to certain values, the top
> thread will set the localjobstatus value to something like "killed".
> 
> - the child thread, also running a while loop, tests the local job
> attribute at 3 times during a single iteration. If it gets a "Killed"
> value, it will call a function that basically terminates this child
> thread in a clean way. Ultimately, it will set the localjobstatus to
> "Pending".

This sounds unsafe. What happens if the "Pending" value is overwritten 
by another "Killed" value? It might be fine if you use two different 
status variables.

When working with threads you have to imagine what would happen if one 
thread stopped indefinitely at any point, and another thread ran long 
enough to do something unexpected. Or two threads interleave statements 
in the worst possible way. Your code seems to have several opportunities 
for bad things to happen. I can't tell what the consequences of them 
are, which will determine how hard you should work to prevent them.

HTH
Kent



More information about the Tutor mailing list