#!/usr/bin/perl -w # # update-nsswitch # # Copyright (C) 2004 Fabio Tranchitella # Copyright (C) 2004 Giuseppe Sacco # # update-nsswitch is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published # by the Free Software Foundation; either version 2 of the License, # or (at your option) any later version. # use strict; use Getopt::Long; use File::Basename qw(basename); use File::Temp qw(tempfile); my $CONF_FILE = "./nsswitch.conf"; my $VERSION = '0.01'; sub main { my ($m_add, $m_remove, $m_version, $m_help, $before, $after, $database, $actionitem); $m_add = $m_remove = 0; $after = $before = $actionitem = ""; GetOptions( 'add|a' => \$m_add, 'remove|r' => \$m_remove, 'database=s' => \$database, 'before=s' => \$before, 'after=s' => \$after, 'actionitem=s'=> \$actionitem, 'version|v' => \$m_version, 'help|h' => \$m_help ); version() if ($m_version); usage() if ($m_help or ($m_add + $m_remove) != 1 or not $database or not @ARGV or ($after ne "" and $before ne "")); my $source = shift @ARGV if @ARGV; if ($m_add) { return add($source, $database, $after, $before, $actionitem); } else { return remove($source, $database); } } sub add { my ($source, $database, $after, $before, $actionitem) = @_; my $output = ""; my $done = 1; open(IN, $CONF_FILE) or die "Couldn't open $CONF_FILE $!\n"; while () { if ($_ =~ /^#/ or $_ =~ /^[\s\t]+/) { $output .= $_; } elsif ($_ =~ /(\S+):[\s\t]+([\S ]+)/) { my ($db, $s) = ($1, $2); if ($database =~ /$db/ and $_ !~ /\s$source/) { if ($actionitem ne "") { $source .= " [$actionitem]"; $actionitem = ""; } if ($after eq "" and $before eq "") { $after = "THELAST"; } if ($after ne "") { if ($_ =~ /$after/) { $_ =~ s/$after/$after $source/ig; } elsif ($after eq "THELAST") { chop($_); $_ = $_ . " $source" . "\n"; } else { $done = 0; last; } } if ($before ne "") { if ($_ =~ /$before/) { $_ =~ s/$before/$source $before/ig; } else { $done = 0; last; } } } $output .= $_; } } close IN; if ($done > 0) { my ($tmp, $filetmp) = tempfile('nsswitch.conf.tmpXXXX') or die ("Couldn't open a temporary file: $!\n"); print $tmp $output; close($tmp); rename("$filetmp", $CONF_FILE) or die "Couldn't rename ".$filetmp.": $!\n"; return 0; } else { return 1; } } sub remove { my ($source, $database) = @_; my $output = ""; my $done = 0; open(IN, $CONF_FILE) or die "Couldn't open $CONF_FILE $!\n"; while () { if ($_ =~ /^#/ or $_ =~ /^[\s\t]+/) { $output .= $_; } elsif ($_ =~ /(\S+):[\s\t]+([\S ]+)/) { my ($db, $s) = ($1, $2); if ($database =~ /$db/ and $_ =~ /\s$source/) { $_ =~ s/\s?$source(\s\[[^\]]+\])?//ig; if ($_ !~ /^\S+:[\s\t]+(\S)+/) { $done = 0; last; } $done++; } $output .= $_; } } close IN; if ($done > 0) { my ($tmp, $filetmp) = tempfile('nsswitch.conf.tmpXXXX') or die ("Couldn't open a temporary file: $!\n"); print $tmp $output; close($tmp); rename("$filetmp", $CONF_FILE) or die "Couldn't rename ".$filetmp.": $!\n"; return 0; } return 1; } sub usage { print <