This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

Author Peter.Saveliev
Recipients Peter.Saveliev
Date 2011-04-18.11:29:01
SpamBayes Score 3.2429226e-10
Marked as misclassified No
Message-id <>
The _newname() function has no locking.

It is called from the new thread constructor. Such constructor is executed within parent thread. So, when several threads create new threads simultaneously, there can be race condition, leading to the same name for two (or even more) threads.


>>> import threading
>>> import dis
>>> dis.dis(threading._newname)
403           0 LOAD_GLOBAL              0 (_counter)
              3 LOAD_CONST               1 (1)
              6 BINARY_ADD         
              7 STORE_GLOBAL             0 (_counter)

404          10 LOAD_FAST                0 (template)
             13 LOAD_GLOBAL              0 (_counter)
             16 BINARY_MODULO      
             17 RETURN_VALUE       

The race condition can be achieved between BINARY_ADD and STORE_GLOBAL. Several threads can do BINARY_ADD before the first one will do STORE_GLOBAL. All racing threads will get the same name.

$ for i in `seq 0 100`; do python |\
 awk -F Thread- '{print $2}' |\
 grep -vE '^$' |\
 sort |\
 uniq -c -d; done
      2 35
      2 12

As you see, there are cases when several threads can get same name.

Proposals: use thread-safe increment counter (with atomic get-increment) like itertools.counter() (that does not release GIL)
Date User Action Args
2011-04-18 11:29:03Peter.Savelievsetrecipients: + Peter.Saveliev
2011-04-18 11:29:02Peter.Savelievsetmessageid: <>
2011-04-18 11:29:02Peter.Savelievlinkissue11866 messages
2011-04-18 11:29:02Peter.Savelievcreate