У меня уже был пост об этом. Со временем исправил много багов. Теперь нити работают через очередь, не зависают. Данный скрипт пингает хосты из сети, которую мы ему задаем в переменной $network, выдаёт статистику "сколько хостов ответило из общего количества в сети". Сеть задаём в формате N.N.N.N/N, модуль Net::Netmask определяет кол-во хостов в сети. В данном случае стартует 25 нитей, каждая из которых выполняет функцию ping. Когда очередь исчерпана, скрипт переходит к подсчёту статистики из файла.
#!/usr/bin/perl -w #Ping network with threads and queue use threads; use Net::Ping; use Net::Netmask; use Thread::Queue; # Programm variables $debug=1; $data_queue0 = Thread::Queue->new; my $sleeptime = 0; $network='178.76.215.0/25'; sub cidr { my $net = shift @_; my $block = Net::Netmask->new($net); my @pool; $size=$block->size(); for (my $i=0; $i<=$size; $i++) { #print $block->nth($i),"\n"; push (@pool, $block->nth($i)); } return @pool; } sub ping { while ($data_queue0->pending()) { my $host = $data_queue0->dequeue; my $pingprotocol = "icmp"; my $pingtimeout = 1; my $pinglength = 1; my $p = Net::Ping->new($pingprotocol,$pingtimeout,$pinglength); if ( $p->ping($host) ) { print OFILE "$host OK\n"; #print "$host OK\n"; } $p->close(); } } sub que { print "Starting que sub\n"; my @ar=@_; #print @ar,"\n"; my $a; foreach my $ip (@ar) { $data_queue0->enqueue($ip); $a++; } if ($debug==1) { print "$a elements queued\n"; } } sub startthreads { for ($m=0; $m<=24; $m++) { sleep($sleeptime); $thrd[$m] = threads->new(\&ping, $data_queue0); print "Thread $m started.\n"; } print "All threads are started\n"; foreach (@thrd) { $_->join(); } print "All threads are joined!\n"; } #Programm body #1 - Recive data from cidr to array @ipaddr = cidr($network); #2 - Insert array into queue que(@ipaddr); #3 - Open file for inserting stdout from threads open OFILE, ">ping_network_stats.txt"; #4 - Create threads startthreads; #5 - Close file with WRITE ONLY close(OFILE); #6 - Open file with READ ONLY open OFILE1, "; #8 Delete empty strings chomp @count; #9 - Print results of programm print "Network usage\: ",$#count," of ",$size,", ", $use=($#count/$size)*100, " %"; #10 - Close file descriptor with WRITE ONLY close (OFILE1);