File: //lib/courier-imap/share/makeuserdb
#! /usr/local/bin/perl
#
# Create userdb database
#
# Usage: makeuserdb
#
# $Id: makeuserdb.in,v 1.10 2003/09/29 03:52:05 mrsam Exp $
#
# Copyright 1998 - 2001 Double Precision, Inc. See COPYING for
# distribution information.
use Fcntl ':flock';
$prefix="/usr/lib/courier-imap";
$exec_prefix="${prefix}";
$bindir="${exec_prefix}/bin";
$ENV{'PATH'}="${exec_prefix}/bin:/usr/bin:/usr/local/bin:/bin";
$dbfile="/etc/userdb";
$datfile="/etc/userdb.dat";
$lockfile="/etc/userdb.lock";
$shadowfile="/etc/userdbshadow.dat";
$tmpdir="/etc";
$tmpdatfile="$tmpdir/userdb.tmp";
$tmpshadowfile="$tmpdir/userdbshadow.tmp";
$makedat="/usr/lib/courier-imap/libexec/makedatprog";
$mode=(stat($dbfile))[2];
die "$dbfile: not found.\n" unless defined $mode;
die "$dbfile: MAY NOT HAVE GROUP OR WORLD PERMISSIONS!!\n"
if ( $mode & 077);
eval {
die "SYMLINK\n" if -l $dbfile;
};
die "ERROR: Wrong makeuserdb command.\n ($dbfile is a symbolic link)\n"
if $@ eq "SYMLINK\n";
eval {
die "SYMLINK\n" if -l $datfile;
};
die "ERROR: Wrong makeuserdb command.\n ($datfile is a symbolic link)\n"
if $@ eq "SYMLINK\n";
eval {
die "SYMLINK\n" if -l $shadowfile;
};
die "ERROR: Wrong makeuserdb command.\n ($shadowfile is a symbolic link)\n"
if $@ eq "SYMLINK\n";
umask (022);
open(LOCK, ">$lockfile") or die "Can't open $lockfile: $!";
flock(LOCK,LOCK_EX) || die "Can't lock $lockfile: $!";
open (DBPIPE, "| ${makedat} - $tmpdatfile $datfile") || die "$!\n";
umask (066);
open (SHADOWPIPE, "| ${makedat} - $tmpshadowfile $shadowfile")
|| die "$!\n";
eval {
if ( -d $dbfile )
{
my (@dirs);
my (@files);
push @dirs, $dbfile;
while ( $#dirs >= 0 )
{
$dir=shift @dirs;
opendir(DIR, $dir) || die "$!\n";
while ( defined($filename=readdir(DIR)))
{
next if $filename =~ /^\./;
if ( -d "$dir/$filename" )
{
push @dirs, "$dir/$filename";
}
else
{
push @files, "$dir/$filename";
}
}
closedir(DIR);
}
while (defined ($filename=shift @files))
{
&do_file( $filename );
}
}
else
{
&do_file( $dbfile );
}
print DBPIPE ".\n" || die "$!\n";
print SHADOWPIPE ".\n" || die "$!\n";
} ;
$err=$@;
close(DBPIPE) || die "$!\n";
exit (1) if $?;
close(SHADOWPIPE) || die "$!\n";
exit (1) if $?;
if ($err)
{
print $err;
exit (1);
}
exit (0);
sub do_file {
my ($filename)=@_;
my ($addr, $fields);
my (@nonshadow, @shadow);
my $location=substr($filename, length("/etc/userdb"));
$location =~ s/^\///;
$location =~ s/\/$//;
$location .= "/" if $location ne "";
open (F, $filename) || die "$!\n";
while (<F>)
{
if ( /^[\n#]/ || ! /^([^\t]*)\t(.*)/ )
{
print DBPIPE;
print SHADOWPIPE;
next;
}
($addr,$fields)=($1,$2);
undef @nonshadow;
undef @shadow;
foreach ( split (/\|/, $fields ) )
{
if ( /^[^=]*pw=/ )
{
push @shadow, $_;
}
else
{
push @nonshadow, $_;
}
}
push @nonshadow, "_=$location";
( print DBPIPE "$addr\t" . join("|", @nonshadow) . "\n"
|| die "$!\n" ) if $#nonshadow >= 0;
( print SHADOWPIPE "$addr\t" . join("|", @shadow) . "\n"
|| die "$!\n" ) if $#shadow >= 0;
}
print DBPIPE "\n";
print SHADOWPIPE "\n";
}