Help with Perl to change dhcpd.conf file

Hi all,
I am too new for this stuff and i am lost in perl tutorials. I need help to change dhcp entries in .conf file with a perl script.

The file entries are like below :

host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp;
}
host mona-clp-1 {
    hardware ethernet       00:0A:A0:00:20:CC;
    fixed-address           10.10.10.73;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp";
}

I want to change bertha entry - filename portion to kucar.clp with command of " editdhcp.pl bertha kucar"

Hope you can help me
Thanks

Hi,

Test next Perl script:

$ cat infile
host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp;
}
host mona-clp-1 {
    hardware ethernet       00:0A:A0:00:20:CC;
    fixed-address           10.10.10.73;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp";
}
$ cat script.pl
use warnings;
use strict;

@ARGV == 3 or die qq[Usage: perl $0 file entry name\n];

my ( $name, $entry ) = ( pop @ARGV, pop @ARGV );

{ 
        local $/ = "}";
        while ( <> ) {
                if ( /(?i:host)\s+${entry}-(?i:clp)-/ ) {
                        s|(filename\s+"/).+(\.clp)|$1${name}$2|is;
                }

                print;
        }
}
$ perl script.pl
Usage: perl script.pl file entry name
$ perl script.pl infile bertha kucar
host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/kucar.clp;
}
host mona-clp-1 {
    hardware ethernet       00:0A:A0:00:20:CC;
    fixed-address           10.10.10.73;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp";
}

Regards,
Birei

thanks Birei,
the thing is that i cropped other entries in the file to make it short here, so there are entries not only for clp in bertha class.

I tried to modify your script but it`s too complex to understand regexp in script. So for all bertha i want to change agul to kucar in filename portion.

thanks again

Ah, ok. You mean that there are more entries like

host bertha-clp-0 {

but with different strings of 'clp'.

In that case, the script should change to:

$ cat script.pl
use warnings;
use strict;

@ARGV == 3 or die qq[Usage: perl $0 file entry name\n];

my ( $name, $entry ) = ( pop @ARGV, pop @ARGV );

{ 
        local $/ = "}";
        while ( <> ) {
                if ( /(?i:host)\s+${entry}/ ) {
                        s|(filename\s+"/).+(\.clp)|$1${name}$2|is;
                }

                print;
        }
}

Removing the part that tries to match '-clp-'. I hope it helps.

Regards,
Birei

yes it worked , thanks a lot but it seems it does not write the changes to the file. how can i do that ? assigning the output to a variable and putting that var into a file ?

The -i switch edits each file in-place. Use it with care. Next example saves the file appending .orig to it and later changes the original:

$ perl -i.orig script.pl infile bertha kucar

Next command changes original file without backup.

$ perl -i script.pl infile bertha kucar 

Regards,
Birei

1 Like

And yet another Perl program -

$
$
$ # Display the content of the file "dhcp.conf"
$
$ cat dhcp.conf
host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp"
}
host mona-clp-1 {
    hardware ethernet       00:0A:A0:00:20:CC;
    fixed-address           10.10.10.73;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp";
}
host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/blah.txt"
}
$
$ # Display the content of the Perl program
$
$ cat -n editdhcp.pl
     1  #perl -w
     2  # Usage: perl editdhcp.pl <host> <file>
     3  use strict;
     4
     5  my $infile  = "dhcp.conf";
     6  my $outfile = "dhcp.conf.upd";
     7  my $start   = 0;
     8  my $host    = $ARGV[0];
     9  my $file    = $ARGV[1];
    10
    11  open (IN, "<", $infile) or die "Can't open $infile for reading: $!";
    12  open (OUT, ">", $outfile) or die "Can't open $outfile for writing: $!";
    13  while (<IN>) {
    14    if (/^host\s*$host-.*$/) {
    15      $start = 1;
    16    } elsif ($start and /^(\s+)filename(\s+)\S+$/) {
    17      $_ = "$1filename$2\"/$file.clp\"\n";
    18      $start = 0;
    19    }
    20    print OUT $_;
    21  }
    22  close (OUT) or die "Can't close $outfile: $!";
    23  close (IN) or die "Can't close $infile: $!";
    24  rename $outfile, $infile
    25
$
$
$ # Run the Perl program
$
$ perl editdhcp.pl bertha kucar
$
$ # Check the "dhcp.conf" file again
$
$ cat dhcp.conf
host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/kucar.clp"
}
host mona-clp-1 {
    hardware ethernet       00:0A:A0:00:20:CC;
    fixed-address           10.10.10.73;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/agul.clp";
}
host bertha-clp-0 {
    hardware ethernet       AA:0A:A0:00:6c:40;
    fixed-address           10.10.10.72;
    option subnet-mask      255.255.255.0;
    next-server             10.10.10.2;
    option routers          10.10.10.1;
    option extensions-path  "bertha.cfg";
    filename                "/kucar.clp"
}
$
$
$

tyler_durden