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

Im getting a 'Use of uninitialized value in concatenation (.) or string at ./working.pl line 95, <CONFIGFILE> line 5.' from the following code. I thought at first it might be the \n at the end of the print statement at the end, I removed it and still get the warning. Can anyone point me in the right direction? Ill post the config file Im using for testing at the end also.
thanks
#!/usr/bin/perl # mothership.pl # Ted Fiedler (tfiedler@gmail.com) # See NOTES for more info use strict; use warnings; use IO::Socket::INET; # does network socket connections # use POSIX qw(strftime); # time # use File::Copy; # file copy operations # use Data::Dumper; # for testing # ################################################### # User configurable variables # ################################################### my $path_to_ship = "/home/tfiedler/network"; my $configfile = "mothership.cfg"; ################################################### # configuration file is here # ################################################### open( CONFIGFILE, "$path_to_ship/$configfile" ) || die "$!\n"; my @information = <CONFIGFILE>; # pull config into array ################################################### # This file will hold _new_ status # ################################################### open( NEWSTATS, "> status.new" ) || die "$!\n"; ################################################### # Copy _previous_ stats to _old_ stats file # # for comparison # ################################################### my $copystats = ( -e "status.msp" ) ? copy( "status.msp", "status.old" ) : warn "Unable to copy status.msp to status.old $!\n"; ################################################### # iterate through each line in config and do # # processing here. # ################################################### foreach $_ (@information) { chomp($_); # break each line into individual vars # my ( $hostname, $ipadd, $port, $proto, $description ) = split( /,/ +, $_ ); # create a hash services with key hostname and values # # $ipadd => ipaddress, $port => port number, $proto => protocol # my %services = ( $hostname => [ $ipadd, $port, $proto ] ); my %status; # initially everything is up # $status{$_} = 'Up' for keys %services; while ( my ( $name, $svc ) = each %services ) { my $sock = IO::Socket::INET->new( Timeout => 2, PeerAddr => $svc->[0], PeerPort => $svc->[1], Proto => $svc->[2] ) # or else it is down # or $status{$name} = 'Down'; } # end of while statement # # This will be changed to reflect a correct last up and down times + # # eventually for comparison and evaluation of total uptime + # # my $nowstring = strftime '%F %R', localtime; # my $oldtime; # for future use # my $nowstring = time; # in seconds # # this next line is EACH name (aka host) and its corresponding sta +tus # while ( my ( $name, $sts ) = each %status ) { # find out what nervice this is # # man getservbyport for more info # my $svcwatch = ( $name !~ /^#/ ) ? getservbyport( $port, $proto ) : next; ################################################### # pick through the data and skip anything that # # doesnt qualify # ################################################### next unless ($hostname); next unless ( $ipadd =~ /^(\d+)\.(\d+)\.(\d+)\.(\d+)$/ ); next unless ( $port =~ /^(\d+)/ ); next unless ( $proto eq "udp" || $proto eq "tcp" || $proto eq +"icmp" ); unless ( $description =~ m/\w/ ) { $description = "No Description entered"; } # end of unless # # print out the data to status.new # # this will eventually get changed to status.msp for now # # I use status.new for testing # print NEWSTATS "$name,$sts,$svcwatch,$description,$nowstring\n +"; print Dumper "$name,$sts,$svcwatch,$description,$nowstring\n"; } # End of while ( my ($name, $sts ... ) } # end of toplevel ( 1st foreach ) close(NEWSTATS); # copy status.new to status.msp # copy( "status.new", "status.msp" ) || die "Unable to copy status.new to status.msp\n"; # EOF #
and the config file
#Server name, IP Address, port number, protocol (tcp/udp), description + (optional) linux,127.0.0.1,22,tcp, linux,127.0.0.1,8080,tcp,Local web server linux,127.0.0.1,22,udp,Local SSH using udp linux,127.0.0.1,504,tcp,Citadel server on local

Readmore tags added by davido per consideration.

Replies are listed 'Best First'.
Re: Use of uninitialized value warning on print
by PodMaster (Abbot) on Jan 23, 2005 at 04:37 UTC
    I thought at first it might be the \n at the end of the print statement at the end, I removed it and still get the warning. Can anyone point me in the right direction? Ill post the config file ...
    No need to post the config file just yet. Do you understand the error? Can you write a one-liner that will reproduce the error? Here's an example
    perl -we"print $_" Use of uninitialized value in print at -e line 1.
    Is that close to what you wrote? Now try this
    perl -Mdiagnostics -we"print $_"
    Use of uninitialized value in print at -e line 1 (#1)
    
        (W uninitialized) An undefined value was used as if it were already
        defined.  It was interpreted as a "" or a 0, but maybe it was a mistake.
        To suppress this warning assign a defined value to your variables.
    
        To help you figure out what was undefined, perl tells you what operation
        you used the undefined value in.  Note, however, that perl optimizes your
        program and the operation displayed in the warning may not necessarily
        appear literally in your program.  For example, "that $foo" is
        usually optimized into "that " . $foo, and the warning will refer to
        the concatenation (.) operator, even though there is no . in your
        program.
    
    So what is line 95 of your program? It's
    print NEWSTATS "$name,$sts,$svcwatch,$description,$nowstring\n";
    So what does the error message mean then? It means that either $name, $sts, $svcwatch, $description or $nowstring is undefined.

    Do you now know how to fix it?

    MJD says "you can't just make shit up and expect the computer to know what you mean, retardo!"
    I run a Win32 PPM repository for perl 5.6.x and 5.8.x -- I take requests (README).
    ** The third rule of perl club is a statement of fact: pod is sexy.

    Considered by holli: "make this a categorized answer." Vote (keep/edit/delete)=6/9/1
    Unconsidered by davido: Consideration doesn't make sense. Without the thread, moving this reply would take it out of context.

Re: Use of uninitialized value warning on print
by vek (Prior) on Jan 23, 2005 at 05:18 UTC

    Looking at your code I would guess that getservbyport() is returning undef which means that $svcwatch will also be undefined. Try adding the following to be sure:

    my $svcwatch = ( $name !~ /^#/ ) ? getservbyport ( $port, $proto ) : next; if (! defined $svcwatch) { warn("getservbyport return undef"); }
    -- vek --
Re: Use of uninitialized value warning on print
by Mr. Muskrat (Canon) on Jan 23, 2005 at 05:00 UTC

    Chances are that the ports you want getservbyport to look up are not listed in your services file. (Sounds to me like you are testing this on Windows as most versions of Windows have a stripped down services file.)

Re: Use of uninitialized value warning on print
by talexb (Chancellor) on Jan 23, 2005 at 04:23 UTC

    I downloaded your code, and in my editor line 95 is the comment # I use status.new for testing. I suggest that you try to track down your problem with the Perl debugger. If you have more time, I highly recommend Log::Log4Perl.

    Alex / talexb / Toronto

    "Groklaw is the open-source mentality applied to legal research" ~ Linus Torvalds