Subject: lib/29849: need reentrant API for getgrent_r()
To: None <lib-bug-people@netbsd.org, gnats-admin@netbsd.org,>
From: None <lukem@NetBSD.org>
List: netbsd-bugs
Date: 03/31/2005 23:55:00
>Number:         29849
>Category:       lib
>Synopsis:       need reentrant API for getgrent_r()
>Confidential:   no
>Severity:       serious
>Priority:       high
>Responsible:    lib-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Thu Mar 31 23:55:00 +0000 2005
>Originator:     Luke Mewburn
>Release:        NetBSD 3.99.1
>Organization:
TNF
>Environment:
>Description:
	We currently don't have the reentrant getgrent_r().

	This is a Problem, because the 'compat' backend for "group"
	uses the non-reentrant getgrent() when looking up groups
	when a `+' directive is being parsed.
	This would have adverse side effects on callers of getgrnam_r()
	and getgrgid_r() that don't expect that the result of the most
	recent getgr{ent,nam,gid} will be changed by calling the
	former.

	Unfortunately, getgrent_r() is not a standardized API
	by POSIX (unlike getgrgid_r() and getgrnam_r()),
	and other vendors have different incompatible APIs.

	Linux (glibc)
		int
		getgrent_r(struct group *grp, char *buffer, size_t buflen,
				struct group **result)

		This is similar to the rest of the POSIX getgrxxx_r() API.

	Solaris/IRIX
		struct group *
		getgrent_r(struct group *grp, char *buffer, int bufsize);

		This is similar to the rest of their non-POSIX
		compatible getgrxxx_r() API.

	Tru64 [I haven't confirmed this]
		int
		getgrent_r(struct group *grent, char *buffer, int bufsize,
				FILE **gr_fp);


	We need to select an API for getgrent_r() and implement it.
	I recommend the Linux one, only because it's in line with
	the POSIX API for the rest of the getgrxxx_r() and getpwxxx_r()
	functions, but I'm open to discussion.


>How-To-Repeat:
	Code inspection of getgrent.c.

>Fix:
	Select an appropriate API for getgrent_r().
	Implement getgrent_r().
	Change getgrent.c::__grscan_compat() to use this.