Newsgroups: comp.lang.perl
Path: utzoo!telly!eci386!jmm
From: jmm@eci386.uucp (John Macdonald)
Subject: Re: implicit limit on number of members in netgroup
Message-ID: <1990Dec10.132932.6536@eci386.uucp>
Reply-To: jmm@eci386.UUCP (John Macdonald)
Organization: Elegant Communications Inc.
References: <1990Dec4.225525.15948@uvaarpa.Virginia.EDU>
Date: Mon, 10 Dec 90 13:29:32 GMT

In article <1990Dec4.225525.15948@uvaarpa.Virginia.EDU> aks@hub.ucsb.edu writes:
|| is there some arbitrary ceiling on the number of machines one can
|| define for membership in a netgroup id in the /etc/netgroup file ??  I
|| have evidence that there is some limit.  Would like to know if others
|| have similar suspicions.
|
|Yes.  If you are using the older YP routines, they use "dbm" maps, which
|have an internal limit of 1024 characters per record.  Even the newer
|versions, using "ndbm", still have the internal limit, it's just a
|little bigger, at 4096 bytes per record.

As an alternative to dbm or ndbm, you can link in Ozan Yigit's sdbm
routines.  They provide a superset of ndbm for calling interface,
run faster, and don't limit the size of either individual elements
or groups of elements that have the same hash code.  It uses a different
hash function (and provides a straightforward hook for you to provide
your own [via recompiling] if you have odd data that pashes poorly).
Oh, and it has no restrictions on usage.  Go to his presentation in
Houston.

For ease of converting, I wrote a simple perl program that can turn
a dbm file into a binary dump and vice versa, you just run it using
a version of perl linked with the appropriate dbm routines in each
case - e.g. "operl dbdump olddata | nperl dbgen newdata".

Here it is...

----- cut here for dbtool - dbdump/dbgen/dbdiff/dbincl -----
sub usage {
    print "usage: perl dbtool -dump|-diff|-gen|-incl dbm-file\n";
    print "   or: perl dbdump dbm-file\n";
    print "   or: perl dbdiff dbm-file\n";
    print "   or: perl dbgen  dbm-file\n";
    print "   or: perl dbincl dbm-file\n";
    exit(1);
}

if( $0 =~ m/dbtool$/ ) {
    $0 = shift;
    $0 =~ s/^-/db/;
}

if( $0 =~ m/db(dump|diff|gen|incl)$/ ) {
    $proc = "do$1";
} else {
    &usage();
}

if( $#ARGV != 0) {
    &usage();
}

dbmopen( DB, $ARGV[0], 0644 );

do $proc();

dbmclose( DB );

sub dodump {
    while( ($key,$val) = each %DB ) {
	printf( "K%8d", length($key) );
	print $key;
	printf( "V%8d", length($val) );
	print $val;
    }
}

sub dodiff {
    while( ($key,$val) = each %DB ) {
	$recnum++;

	$stdkey = &getstr( 'K' );
	$stdval = &getstr( 'V' );

	if( $stdkey != $key ) {
	    die "key mismatch in record $recnum\ndb file key:<$key>\nstdin    key:<$stdkey>\n";
	}
	if( $stdval != $val ) {
	    die "val mismatch in record $recnum\ndb file val:<$val>\nstdin    val:<$stdval>\n";
	}
    }
}

sub doincl {
    for(;;) {
	$stdkey = &checkifstr( 'K' );
	exit if chop($stdkey) eq 'E';
	$stdval = &getstr( 'V' );

	if( !defined($DB{$stdkey}) ) {
	    die "key not found:<$stdkey>\n";
	}
	if( $DB{$stdkey} ne $stdval ) {
	    die "value mismatch\n  key read: <$stdkey>\n  val read: <$stdval>\n  val found: <$DB{$stdkey}>\n";
	}
    }
}

sub dogen {
    for(;;) {
	$stdkey = &checkifstr( 'K' );
	exit if chop($stdkey) eq 'E';
	$stdval = &getstr( 'V' );

	$DB{$stdkey} = $stdval;
    }
}

sub getstr {
    local($reqcode) = @_;
    local($code);

    if( read(STDIN,$code,1) != 1 ) {
	die "unexpected EOF at record $recnum";
    }
    if( $code != $reqcode ) {
	die "out of sync at record $recnum, expected $reqcode, got $code";
    }
    &getrest();
}

sub checkifstr {
    local($code);

    if( read(STDIN,$code,1) == 1 ) {
	if( $code != 'K' ) {
	    die "out of sync at record $recnum, expected K, got $code";
	}
	&getrest() . 'K';
    } else {
	'E';
    }
}

sub getrest {
    local($strlen,$result);

    if( read(STDIN,$strlen,8) != 8 ) {
	die "unexpected EOF at record $recnum";
    }
    if( read(STDIN,$result,$strlen+0) != $strlen+0 ) {
	die "unexpected EOF at record $recnum";
    }
    $result;
}
-- 
Cure the common code...                      | John Macdonald
...Ban Basic      - Christine Linge          |   jmm@eci386
