User and group info

endpwent#

Close the passwd-database iterator opened by getpwent or setpwent.

endpwent is the companion teardown call for a passwd-file walk. After iterating the password database with repeated getpwent calls, endpwent releases whatever per-process state the C library allocated to hold the iteration cursor (an open file descriptor on /etc/passwd, a cached buffer for NSS, a connection to nscd / sssd, an LDAP session, depending on the host’s name-service configuration). It takes no arguments and wraps the system endpwent(3) call directly.

Synopsis#

endpwent

What you get back#

A single boolean value. The return is rarely checked — on every platform PetaPerl supports, endpwent cannot meaningfully fail, and real code treats it as a void call.

Global state it touches#

endpwent mutates no Perl-visible variable. The state it clears is entirely inside the C library: the per-process passwd iterator, shared with getpwent and setpwent (and, on some systems, with getpwnam / getpwuid when those happen to reuse the same underlying stream). Calling endpwent in one thread affects every other thread in the same process — the iterator is per-process, not per-thread.

Examples#

Standard iterate-then-close idiom:

setpwent;
while (my @ent = getpwent) {
    my ($name, undef, $uid) = @ent;
    print "$uid\t$name\n";
}
endpwent;

Ensure the iterator is closed even if the loop exits early:

setpwent;
eval {
    while (my @ent = getpwent) {
        my ($name, undef, $uid, $gid) = @ent;
        die "found it\n" if $uid == $target;
    }
};
endpwent;       # always run, regardless of how the loop ended

Pair with a local guard so nested code cannot leave the iterator half-walked:

sub each_user {
    my $cb = shift;
    setpwent;
    my $guard = Guard::guard { endpwent };   # or a manual eval-and-rethrow
    while (my @ent = getpwent) { $cb->(@ent) }
}

endpwent with no prior iteration is harmless:

endpwent;                                    # no-op on a fresh process

Edge cases#

  • No arguments, no parentheses needed. endpwent is a named unary operator with zero arguments; write it bare. endpwent() is accepted but adds nothing.

  • Idempotent. Calling endpwent twice in a row, or calling it before any getpwent / setpwent, is defined as a successful no-op on every supported platform.

  • Does not invalidate records you already fetched. Arrays and hashes returned by earlier getpwent / getpwnam / getpwuid calls are plain Perl data and remain valid after endpwent — only the iterator cursor is closed.

  • Thread safety. The iterator is process-wide. If two threads are walking the passwd database simultaneously, endpwent closes the shared cursor for both — neither thread will get the full record set. Use a lock around the whole setpwent / loop / endpwent block when iterating from threads.

  • Name-service backends. On hosts using LDAP, NIS, sssd, or any other non-flat-file backend, endpwent may release a network handle. A long-running daemon that iterates the passwd database periodically should call endpwent at the end of each pass rather than leaking one handle per pass.

  • Not a forced cache flush. endpwent closes the iterator; it does not flush the C library’s getpwnam / getpwuid caches. A subsequent getpwnam may still return a cached record.

Differences from upstream#

Fully compatible with upstream Perl 5.42.

See also#

  • setpwent — rewind or open the passwd-database iterator before a walk; pairs with endpwent as the open/close bracket

  • getpwent — fetch the next record from the iterator that endpwent closes

  • getpwnam — direct lookup by login name, independent of the iterator in most implementations

  • getpwuid — direct lookup by numeric UID, same independence note as getpwnam

  • endgrent — analogous teardown for the group-database iterator; the two are almost always called together