Perl- check the port used

hi everybody;
my code is cheking if a port is an actif or not with the cmd netstat -ln,I want first to enter the number of the port which I want to check it but I think that the value of $con in the second "if" is always "0" so the code give me always that the port is not used!!!

#!/usr/bin/perl
print "enter the port :\n";
$port=<STDIN>;
$con=0;
open (FILE,"-|") exec "netstat -ln |grep" .$port;
open (FIL,">res.txt");
whiel (<FILE>){
if ($_ =~/:$port/){$con++;}}
if ($con){
print FIL "The active port is : $port\n"}
else{
print FIL "the port is not active\n";}
close FIL;
close FILE;
  1. use strict; and use warnings; will catch & tell you about a lot of potential errors if you let them
  2. Without chomp $port will still have a newline at the end of the string, which will be included in any match attempt.
  3. Why do you grep and then do additional filtering in Perl, when you can do it all in Perl?
1 Like

can you please clarify the second and the third point I'm just a beginner

Reading from a filehandle, such as STDIN, will always read all characters up to and including the new line character(s), and save them to the variable given on the left side. That means when your user inputs (for example) "22" and then hit return, $port will actually contain "22\n" (on Unix) or "22\r\n" on Windows or "22\r" on MacOS. chomp will remove any non-printable characters at the end of the line for you. Try this small script:

#!/usr/bin/perl

use strict;
use warnings;

print "Enter something: ";
my $input1 = <STDIN>;
print "You wrote >>$input1<<\n";

print "Enter something again: ";
my $input2 = <STDIN>;
chomp $input2;
print "You wrote >>$input2<<\n";

See the difference?

Now when you try to match the contents of $port on line 7, Perl is trying to match (with the example 22 again) ":22<newline>" exactly. Since the port number isn't at the end of netstats output, it will never match.

As for point 3, take a look at the (aptly named) grep function.

1 Like

thank you a lot Pludi for your quick help

I'd tend to use grep on an array rather than a string, for a string I'd go for something like the following with a straight regex. (Note: regex used works for my flavour of netstat and may need amending to work for you, (netstat 1.42 (2001-04-15) from net-tools 1.6)

#!/usr/bin/perl

#ALWAYS use these 2 lines if it's worth saving the file
use strict ;
use warnings;

my $port=$ARGV[0]; #TODO validate and print usage if wrong
my $netstat=`netstat -ln`; #get output of netstat command

#Check for service listening on the port
my ($service)=$netstat=~/\w+\s+\d+\s+\d+\s+[\d.:]+:$port\s+[\d:.]+:\*\s+LISTEN/;

if ($service){
    print "There is a service listening on $port\n"
}else{
   print"No service on $port\n";
}
1 Like