znu has asked for the wisdom of the Perl Monks concerning the following question:

Hello again. This is driving me nuts, and i'm beginning to think it's a bug with threads. AFAIK the following code is correct and should continue to spawn 1 thread, wait until it's finished, spawn another, so on and so forth for all eternity. However, on my machine it spawns around 1021 or so threads and around there somewhere it begins to create threads that never return :-/ Could people please confirm that this is a problem, or modify the code so as to make it work (& also work with more than one $worker). Many thanks, Zoltan.
#!/usr/local/bin/perl use threads; use strict; # constants my $workers = 1; #number of simultaneous workers workerPool(); sub list_threads { my @threads = threads->list; print "--threads i know of: -----\n"; for my $t (@threads) { print $t->tid."\n"; } print "--------------------------"; } # sub which maintains a set number of simultaneous threads sub workerPool { print "Starting workerPool...\n"; my $count = 0; my @running_threads = (); while (1) { @running_threads = threads->list; if (scalar(@running_threads) < $workers) { # add a new worker $count++; my $thread = threads->new(\&worker, $count); } list_threads(); } } # this sub represents a thread sub worker { my $thread_num = $_[0]; print "---I am thread $thread_num!\n"; print "+++Thread $thread_num gone!\n"; eval(((threads->self)->join)); }

Replies are listed 'Best First'.
Re: Possible bug with threads
by pg (Canon) on Dec 20, 2002 at 05:29 UTC
    What do you mean by 1021 threads? From the beginning to the end (if there is an end), you only created one child thread.

    Just as what I said in my reply to your first post, the worker thread you created will never ever quit, so your worker pool is full right after you created the first thread, and it stays full, therefore no space left for any new threads, in your worker pool.

    I modified your printing a little bit, to show you that it does not work as you expected or described: ( I didn't make any logic change, just prints)
    use threads; use strict;
    # I added this to make sure we see all printing on time $| ++;
    # constants my $workers = 1; #number of simultaneous workers workerPool(); sub list_threads { my @threads = threads->list; print "--threads i know of: -----\n"; for my $t (@threads) { print $t->tid."\n"; } print "--------------------------"; } # sub which maintains a set number of simultaneous threads sub workerPool { print "Starting workerPool...\n"; my $count = 0; my @running_threads = (); while (1) { @running_threads = threads->list; if (scalar(@running_threads) < $workers) {
    #I added this, and it only shows ONCE print "creating new threads\n";
    # add a new worker $count++; my $thread = threads->new(\&worker, $count); }
    # I commented out this, with this flushing the output all the +time, I cannot see anything useful #list_threads();
    } } # this sub represents a thread sub worker { my $thread_num = $_[0]; print "---I am thread $thread_num!\n";
    #this is simply a lie print "+++Thread $thread_num gone!\n"; #this hangs this worker thread itself eval(((threads->self)->join));
    }
      I don't understand why your saying i only created one child thread from the beginning to end!?!? If what you're saying is correct, and ive got $workers = 1, then when i launch the 1st thread, and it never quits, threads->list should always contain it's tid, therefore no more threads should be created and it should just sit there after showing: Starting workerPool... creating new threads ---I am thread 1! BUT, on my machine it doesnt, it goes on to print "I am thread X.. blah" where X goes from 1 till roughly 1020. Why?? And why does it get to around 1020 and then just hang?? confused :-/ Many thanks! P.S more info on what i'm trying to do is given in my reply to submersible_toaster (the url)
Re: Possible bug with threads
by submersible_toaster (Chaplain) on Dec 20, 2002 at 08:55 UTC

    Follow pg's advice, your eval( ((threads->self)->join)); is completley bogus. The expression is circular. The last statement of &worker is the value it will return, it is trying to return it's return value via ->join ,which blocks until the thread returns - which it can't because it's blocking on the return value of itself.

    I apologise for missing this node when I wrote that , but this code needs an evilevalectomy.

    stat!
      Thanks. I replied to your other post, trying to explain what i'm trying to do. the link is at http://www.perlmonks.org/index.pl?parent=221386&title=Re%3A%20%5E3%3A%20Fun%20with%20threads&lastnode_id=221386&displaytype=display&type=superdoc&node=Comment%20on