Skip Menu |

This queue is for tickets about the Net-Ping CPAN distribution.

Report information
The Basics
Id: 31697
Status: open
Priority: 0/
Queue: Net-Ping

People
Owner: Nobody in particular
Requestors: kinpoo [...] gmail.com
Cc:
AdminCc:

Bug Information
Severity: (no value)
Broken in: (no value)
Fixed in: (no value)



Subject: When using multi-threads, it will return with fault.
Date: Wed, 19 Dec 2007 19:45:48 +0800
To: bug-Net-Ping [...] rt.cpan.org
From: Kinpoo <kinpoo [...] gmail.com>
When using multi-threads, it will return with fault. #./ ping.pl 255 ... -- 66.94.234.14 -- -- -- -- -- -- -- ping $host -c 1 -w 2 -- # using system's ping 0 2000 ms 0 2000 ms 0 2000 ms -- Net::Ping->ping($host) -- # using Net::Ping 1 237.16 ms 1 197.78 ms 1 206.21 ms -- 66.94.234.5 -- -- -- -- -- -- -- ping $host -c 1 -w 2 -- 0 2000 ms 0 2000 ms 0 2000 ms -- Net::Ping->ping($host) -- 0 1259.97 ms 0 190.26 ms 1 775.19 ms ... #cat ping.pl #! /usr/bin/perl use strict; use warnings; use threads(stack_size => 17*1024); use Net::Ping; use Time::HiRes qw(gettimeofday); my $end = defined($ARGV[0]) ? $ARGV[0] : 1; my $t_b = getMilliseconds(); threads->create(\&processPingScan, '66.94.234.' . $_) foreach ((1..$end)); while (threads->list(threads::running)) { sleep(1); # waiting for threads } my $t_e = getMilliseconds(); my $t_u = nearest(0.01, $t_e - $t_b); print "\nDone!$t_u ms used!\n"; sub processPingScan { my $host = shift; my $temp = ''; my $num = 3; $temp .= "-- ping \$host -c 1 -w 2 --\n"; foreach ((1..$num)) { my ($ret, $t_u); if (`ping $host -c 1 -w 2` =~ /time=([\d\.]+)/) { $ret = 1; $t_u = $1; } else { $ret = 0; $t_u = 2000; } $temp .= "\t$ret\t$t_u ms\n"; } $temp .= "\n-- Net::Ping->ping(\$host) --\n"; my $oPing = Net::Ping->new('icmp', 2); foreach ((1..$num)) { my $t_b = getMilliseconds(); my $ret = $oPing->ping($host); my $t_e = getMilliseconds(); my $t_u = nearest(0.01, $t_e - $t_b); $temp .= "\t$ret\t$t_u ms\n"; } print "-- $host -- -- -- -- -- --\n$temp\n"; threads->detach(); threads->exit(); } sub getMilliseconds { my ($sec, $usec) = gettimeofday(); return $sec*1000 + $usec/1000; } sub nearest { # nearest(0.01, 1.123) = 1.12 my ($target, $num) = @_; my $x; $target = abs($target); if ($num >= 0) { $num = $target * int(($num + 0.5 * $target) / $target); } else { $num = $target * int(($num - 0.5 * $target) / $target); } return $num; }
Subject: Re: [rt.cpan.org #31697] When using multi-threads, it will return with fault.
Date: Wed, 19 Dec 2007 08:41:48 -0600
To: bug-Net-Ping [...] rt.cpan.org
From: "Steve Peters" <steve [...] fisharerojo.org>
What version of Net::Ping are you using? Steve On Dec 19, 2007 5:47 AM, Kinpoo via RT <bug-Net-Ping@rt.cpan.org> wrote: Show quoted text
> > Wed Dec 19 06:47:08 2007: Request 31697 was acted upon. > Transaction: Ticket created by kinpoo@gmail.com > Queue: Net-Ping > Subject: When using multi-threads, it will return with fault. > Broken in: (no value) > Severity: (no value) > Owner: Nobody > Requestors: kinpoo@gmail.com > Status: new > Ticket <URL: http://rt.cpan.org/Ticket/Display.html?id=31697 > > > > When using multi-threads, it will return with fault. > > #./ ping.pl 255 > ... > -- 66.94.234.14 -- -- -- -- -- -- > -- ping $host -c 1 -w 2 -- # using system's ping > 0 2000 ms > 0 2000 ms > 0 2000 ms > > -- Net::Ping->ping($host) -- # using Net::Ping > 1 237.16 ms > 1 197.78 ms > 1 206.21 ms > > -- 66.94.234.5 -- -- -- -- -- -- > -- ping $host -c 1 -w 2 -- > 0 2000 ms > 0 2000 ms > 0 2000 ms > > -- Net::Ping->ping($host) -- > 0 1259.97 ms > 0 190.26 ms > 1 775.19 ms > ... > > > #cat ping.pl > > #! /usr/bin/perl > > use strict; > use warnings; > use threads(stack_size => 17*1024); > > use Net::Ping; > use Time::HiRes qw(gettimeofday); > > my $end = defined($ARGV[0]) ? $ARGV[0] : 1; > > > my $t_b = getMilliseconds(); > > threads->create(\&processPingScan, '66.94.234.' . $_) foreach ((1..$end)); > > while (threads->list(threads::running)) { > sleep(1); # waiting for threads > } > > my $t_e = getMilliseconds(); > > my $t_u = nearest(0.01, $t_e - $t_b); > > print "\nDone!$t_u ms used!\n"; > > sub processPingScan { > my $host = shift; > my $temp = ''; > my $num = 3; > > > $temp .= "-- ping \$host -c 1 -w 2 --\n"; > foreach ((1..$num)) { > my ($ret, $t_u); > if (`ping $host -c 1 -w 2` =~ /time=([\d\.]+)/) { > $ret = 1; > $t_u = $1; > } > else { > $ret = 0; > $t_u = 2000; > } > $temp .= "\t$ret\t$t_u ms\n"; > } > > $temp .= "\n-- Net::Ping->ping(\$host) --\n"; > my $oPing = Net::Ping->new('icmp', 2); > foreach ((1..$num)) { > my $t_b = getMilliseconds(); > my $ret = $oPing->ping($host); > my $t_e = getMilliseconds(); > my $t_u = nearest(0.01, $t_e - $t_b); > $temp .= "\t$ret\t$t_u ms\n"; > } > > print "-- $host -- -- -- -- -- --\n$temp\n"; > threads->detach(); > threads->exit(); > } > > sub getMilliseconds { > my ($sec, $usec) = gettimeofday(); > return $sec*1000 + $usec/1000; > } > > sub nearest { # nearest(0.01, 1.123) = 1.12 > my ($target, $num) = @_; > my $x; > > $target = abs($target); > > if ($num >= 0) { > $num = $target * int(($num + 0.5 * $target) / $target); > } > else { > $num = $target * int(($num - 0.5 * $target) / $target); > } > return $num; > } > > > When using multi-threads, it will return with fault. > > #./ ping.pl 255 > ... > -- 66.94.234.14 -- -- -- -- -- -- > -- ping $host -c 1 -w 2 -- # using system's ping > 0 2000 ms > 0 2000 ms > 0 2000 ms > > -- Net::Ping->ping($host) -- # using Net::Ping > 1 237.16 ms > 1 197.78 ms > 1 206.21 ms > > -- 66.94.234.5 -- -- -- -- -- -- > -- ping $host -c 1 -w 2 -- > 0 2000 ms > 0 2000 ms > 0 2000 ms > > -- Net::Ping->ping($host) -- > 0 1259.97 ms > 0 190.26 ms > 1 775.19 ms > ... > > > #cat ping.pl > > #! /usr/bin/perl > > use strict; > use warnings; > use threads(stack_size => 17*1024); > > use Net::Ping; > use Time::HiRes qw(gettimeofday); > > my $end = defined($ARGV[0]) ? $ARGV[0] : 1; > > > my $t_b = getMilliseconds(); > > threads->create(\&processPingScan, '66.94.234.' . $_) foreach ((1..$end)); > > while (threads->list(threads::running)) { > sleep(1); # waiting for threads > } > > my $t_e = getMilliseconds(); > > my $t_u = nearest(0.01, $t_e - $t_b); > > print "\nDone!$t_u ms used!\n"; > > sub processPingScan { > my $host = shift; > my $temp = ''; > my $num = 3; > > > $temp .= "-- ping \$host -c 1 -w 2 --\n"; > foreach ((1..$num)) { > my ($ret, $t_u); > if (`ping $host -c 1 -w 2` =~ /time=([\d\.]+)/) { > $ret = 1; > $t_u = $1; > } > else { > $ret = 0; > $t_u = 2000; > } > $temp .= "\t$ret\t$t_u ms\n"; > } > > $temp .= "\n-- Net::Ping->ping(\$host) --\n"; > my $oPing = Net::Ping->new('icmp', 2); > foreach ((1..$num)) { > my $t_b = getMilliseconds(); > my $ret = $oPing->ping($host); > my $t_e = getMilliseconds(); > my $t_u = nearest(0.01, $t_e - $t_b); > $temp .= "\t$ret\t$t_u ms\n"; > } > > print "-- $host -- -- -- -- -- --\n$temp\n"; > threads->detach(); > threads->exit(); > } > > sub getMilliseconds { > my ($sec, $usec) = gettimeofday(); > return $sec*1000 + $usec/1000; > } > > sub nearest { # nearest(0.01, 1.123) = 1.12 > my ($target, $num) = @_; > my $x; > > $target = abs($target); > > if ($num >= 0) { > $num = $target * int(($num + 0.5 * $target) / $target); > } > else { > $num = $target * int(($num - 0.5 * $target) / $target); > } > return $num; > } >
Subject: Re: [rt.cpan.org #31697] When using multi-threads, it will return with fault.
Date: Thu, 20 Dec 2007 10:13:10 +0800
To: bug-Net-Ping [...] rt.cpan.org
From: Kinpoo <kinpoo [...] gmail.com>
Dear Steve, I'm using perl 5.8.5, Net::Ping 2.31 and 2.33, threads 1.67. On 12/19/07, steve@fisharerojo.org via RT <bug-Net-Ping@rt.cpan.org> wrote: Show quoted text
> > > <URL: http://rt.cpan.org/Ticket/Display.html?id=31697 > > > What version of Net::Ping are you using? > > Steve >
From: crsthn [...] ibest.com.br
Hi, I'm have problem with threads too. My Net::Ping is 2.31. In Dump of packets, I see field SEQ never change. And this is the problem with threads. My solution is: --- Ping.pm.orig 2008-07-22 16:25:39.465715986 -0300 +++ Ping.pm 2008-07-22 16:51:16.317763237 -0300 @@ -430,7 +430,8 @@ $from_msg # ICMP message ); - $self->{"seq"} = ($self->{"seq"} + 1) % 65536; # Increment sequence + #$self->{"seq"} = ($self->{"seq"} + 1) % 65536; # Increment sequence + $self->{"seq"} = ($self->{"seq"} + int(rand(1024))) % 65536; # Increment sequence $checksum = 0; # No checksum for starters $msg = pack(ICMP_STRUCT . $self->{"data_size"}, ICMP_ECHO, SUBCODE, $checksum, $self->{"pid"}, $self->{"seq"}, $self->{"data"}); Thanks! Cristhiano Em Qua. Dez. 19 21:13:29 2007, kinpoo@gmail.com escreveu: Show quoted text
> Dear Steve, > > I'm using perl 5.8.5, Net::Ping 2.31 and 2.33, threads 1.67. > > On 12/19/07, steve@fisharerojo.org via RT <bug-Net-Ping@rt.cpan.org>
wrote: Show quoted text
> > > > > > <URL: http://rt.cpan.org/Ticket/Display.html?id=31697 > > > > > What version of Net::Ping are you using? > > > > Steve > >
From: < viliam dot pucik at gmail dot com >
Hello, problem with Cristhiano solution is that two or more threads can still have the same sequence when they are generated by a random number generator. IMHO better solution is to specify uniq offset and max numbers for every thread (via set_thread) where Net::Ping is used: $THREADS_MAX = 10; ... my $ping = new Net::Ping( "icmp" ); # the uniq sequence number for each thread is now calculated as: # [ threads->tid() + $THREADS_MAX * number_of_send_PINGs_in_the_thread ] $ping->set_thread( threads->tid(), $THREADS_MAX ); ... To use "set_thread" you need to apply the "set_thread.patch" patch. Hope this helps. Viliam On Tue Jul 22 16:30:02 2008, cristhiano wrote: Show quoted text
> Hi, > > I'm have problem with threads too. My Net::Ping is 2.31. In Dump of > packets, I see field SEQ never change. And this is the problem with
threads. Show quoted text
> > My solution is: > > --- Ping.pm.orig 2008-07-22 16:25:39.465715986 -0300 > +++ Ping.pm 2008-07-22 16:51:16.317763237 -0300 > @@ -430,7 +430,8 @@ > $from_msg # ICMP message > ); > > - $self->{"seq"} = ($self->{"seq"} + 1) % 65536; # Increment sequence > + #$self->{"seq"} = ($self->{"seq"} + 1) % 65536; # Increment
sequence Show quoted text
> + $self->{"seq"} = ($self->{"seq"} + int(rand(1024))) % 65536; # > Increment sequence > $checksum = 0; # No checksum for starters > $msg = pack(ICMP_STRUCT . $self->{"data_size"}, ICMP_ECHO, SUBCODE, > $checksum, $self->{"pid"}, $self->{"seq"}, $self->
{"data"}); Show quoted text
> > Thanks! > Cristhiano
Subject: set_thread.patch
--- Ping.pm.org 2010-03-26 23:06:51.346739372 +0100 +++ Ping.pm 2010-03-27 21:12:35.075014549 +0100 @@ -128,6 +128,9 @@ sub new $self->{"econnrefused"} = undef; # Default Connection refused behavior $self->{"seq"} = 0; # For counting packets + $self->{"thread"} = 0; # Used for fixing "seq" when executing in threads + $self->{"thread_max"} = 1; # Used for fixing "seq" when executing in threads + $self->{"count"} = 0; # Used for fixing "seq" when executing in threads if ($self->{"proto"} eq "udp") # Open a socket { $self->{"proto_num"} = (getprotobyname('udp'))[2] || @@ -201,6 +204,16 @@ sub new return($self); } +# Every thread will have its own uniq sequences calculated as +# [ seq = thread + thread_max * count ] +# where count is the number of send pings +sub set_thread { + my ( $self, $thread, $thread_max ) = @_; + + $self->{"thread"} = $thread; + $self->{"thread_max"} = $thread_max; +} + # Description: Set the local IP address from which pings will be sent. # For ICMP and UDP pings, this calls bind() on the already-opened socket; # for TCP pings, just saves the address to be used when the socket is @@ -443,7 +456,10 @@ sub ping_icmp $from_msg # ICMP message ); - $self->{"seq"} = ($self->{"seq"} + 1) % 65536; # Increment sequence + #$self->{"seq"} = ($self->{"seq"} + 1) % 65536; # Increment sequence + $self->{"seq"} = ( $self->{"thread"} + $self->{"thread_max"} * $self->{"count"} ) % 65536; # Increment sequence + $self->{"count"}++; # Increment number of send PINGs + $checksum = 0; # No checksum for starters $msg = pack(ICMP_STRUCT . $self->{"data_size"}, ICMP_ECHO, SUBCODE, $checksum, $self->{"pid"}, $self->{"seq"}, $self->{"data"});