tech-kern archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Changing NGROUPS_MAX to 1024?



Hello,

At ${WORK} our organizational identity provider assigns quite a number of groups to each person---many more than 16---which causes users not being able to authenticate to SaMBa running on a NetBSD host.  To address this, I've been running for quite a while with a patch to set NGROUPS_MAX to 1024, with a compatibility setting to 16 for use in NFS.

Is this something that we'd like to have in base?  I haven't tested the NFS functionality widely (all our systems are patched), but last time I tried it between a patched and an unpatched system, it seemed to work.  Is there anything else I should be looking at aside from NFS?  Any other thoughts?

The patch is attached.

Thanks,

--
Konrad Schroder
perseant%hhhh.org@localhost
Index: sys/compat/netbsd32/netbsd32.h
===================================================================
RCS file: /cvsroot/src/sys/compat/netbsd32/netbsd32.h,v
retrieving revision 1.140
diff -u -r1.140 netbsd32.h
--- sys/compat/netbsd32/netbsd32.h	23 Apr 2022 17:46:23 -0000	1.140
+++ sys/compat/netbsd32/netbsd32.h	10 Apr 2026 20:35:18 -0000
@@ -309,7 +309,7 @@
 struct netbsd32_export_args30 {
 	int	ex_flags;		/* export related flags */
 	uid_t	ex_root;		/* mapping for root uid */
-	struct	uucred ex_anon;		/* mapping for anonymous user */
+	struct	uucred100 ex_anon;		/* mapping for anonymous user */
 	netbsd32_pointer_t ex_addr;	/* net address to which exported */
 	int	ex_addrlen;		/* and the net address length */
 	netbsd32_pointer_t ex_mask;	/* mask of valid bits in saddr */
@@ -1075,7 +1075,7 @@
 	netbsd32_nfsdp	nsd_nfsd;
 	uid_t		nsd_uid;
 	uint32_t	nsd_haddr;
-	struct uucred	nsd_cr;
+	struct uucred100	nsd_cr;
 	int		nsd_authlen;
 	netbsd32_u_charp nsd_authstr;
 	int		nsd_verflen;
@@ -1089,7 +1089,7 @@
 struct netbsd32_export_args {
 	int		ex_flags;
 	uid_t		ex_root;
-	struct uucred	ex_anon;
+	struct uucred100	ex_anon;
 	netbsd32_sockaddrp_t ex_addr;
 	int		ex_addrlen;
 	netbsd32_sockaddrp_t ex_mask;
Index: sys/conf/Makefile.kern.inc
===================================================================
RCS file: /cvsroot/src/sys/conf/Makefile.kern.inc,v
retrieving revision 1.295.4.1
diff -u -r1.295.4.1 Makefile.kern.inc
--- sys/conf/Makefile.kern.inc	11 Sep 2023 13:35:37 -0000	1.295.4.1
+++ sys/conf/Makefile.kern.inc	10 Apr 2026 20:35:18 -0000
@@ -113,7 +113,7 @@
 #    find . -name \*.su | xargs awk '{ printf "%6d %s\n", $2, $1 }' | sort -n
 .if ${MACHINE} != "vax"
 # GCC/vax 8.4 does not support -fstack-usage.
-CFLAGS+=	${${ACTIVE_CC} == "gcc":? -fstack-usage -Wstack-usage=3584 :}
+CFLAGS+=	${${ACTIVE_CC} == "gcc":? -fstack-usage -Wstack-usage=9999 :}
 .endif
 CWARNFLAGS+=	-Walloca
 
Index: sys/kern/kern_auth.c
===================================================================
RCS file: /cvsroot/src/sys/kern/kern_auth.c,v
retrieving revision 1.81
diff -u -r1.81 kern_auth.c
--- sys/kern/kern_auth.c	9 Apr 2022 23:38:33 -0000	1.81
+++ sys/kern/kern_auth.c	10 Apr 2026 20:35:23 -0000
@@ -640,6 +640,29 @@
 }
 
 /*
+ * Same as above but using uucred100.
+ */
+void    
+kauth_uucred100_to_cred(kauth_cred_t cred, const struct uucred100 *uuc)
+{       
+	KASSERT(cred != NULL);
+	KASSERT(cred != NOCRED);
+	KASSERT(cred != FSCRED);
+	KASSERT(uuc != NULL);
+ 
+	cred->cr_refcnt = 1;
+	cred->cr_uid = uuc->cr_uid;
+	cred->cr_euid = uuc->cr_uid;
+	cred->cr_svuid = uuc->cr_uid;
+	cred->cr_gid = uuc->cr_gid;
+	cred->cr_egid = uuc->cr_gid;
+	cred->cr_svgid = uuc->cr_gid;
+	cred->cr_ngroups = uimin(uuc->cr_ngroups, NGROUPS_MAX_100);
+	kauth_cred_setgroups(cred, __UNCONST(uuc->cr_groups),
+	    cred->cr_ngroups, -1, UIO_SYSSPACE);
+}
+
+/*
  * Convert kauth_cred_t to userland credentials (struct uucred).
  * XXX: For NFS & puffs
  */
@@ -660,6 +683,25 @@
 }
 
 /*
+ * Same as above but for uucred100.
+ */
+void    
+kauth_cred_to_uucred100(struct uucred100 *uuc, const kauth_cred_t cred)
+{       
+	KASSERT(cred != NULL);
+	KASSERT(cred != NOCRED);
+	KASSERT(cred != FSCRED);
+	KASSERT(uuc != NULL);
+	int ng;
+
+	ng = uimin(cred->cr_ngroups, NGROUPS_MAX_100);
+	uuc->cr_uid = cred->cr_euid;  
+	uuc->cr_gid = cred->cr_egid;  
+	uuc->cr_ngroups = ng;
+	kauth_cred_getgroups(cred, uuc->cr_groups, ng, UIO_SYSSPACE);
+}
+
+/*
  * Compare kauth_cred_t and uucred credentials.
  * XXX: Modelled after crcmp() for NFS.
  */
@@ -693,6 +735,38 @@
 }
 
 /*
+ * Same as above, but using the smaller struct uucred100.
+ */
+int
+kauth_cred_uucmp100(kauth_cred_t cred, const struct uucred100 *uuc)
+{
+	KASSERT(cred != NULL);
+	KASSERT(cred != NOCRED);
+	KASSERT(cred != FSCRED);
+	KASSERT(uuc != NULL);
+
+	if (cred->cr_euid == uuc->cr_uid &&
+	    cred->cr_egid == uuc->cr_gid &&
+	    cred->cr_ngroups == (uint32_t)uuc->cr_ngroups) {
+		int i;
+
+		/* Check if all groups from uuc appear in cred. */
+		for (i = 0; i < uuc->cr_ngroups; i++) {
+			int ismember;
+
+			ismember = 0;
+			if (kauth_cred_ismember_gid(cred, uuc->cr_groups[i],
+			    &ismember) != 0 || !ismember)
+				return (1);
+		}
+
+		return (0);
+	}
+
+	return (1);
+}
+
+/*
  * Make a struct ucred out of a kauth_cred_t.  For compatibility.
  */
 void
Index: sys/nfs/nfs.h
===================================================================
RCS file: /cvsroot/src/sys/nfs/nfs.h,v
retrieving revision 1.80
diff -u -r1.80 nfs.h
--- sys/nfs/nfs.h	5 Dec 2021 07:44:53 -0000	1.80
+++ sys/nfs/nfs.h	10 Apr 2026 20:35:23 -0000
@@ -179,7 +179,7 @@
 struct export_args {
 	int	ex_flags;		/* export related flags */
 	uid_t	ex_root;		/* mapping for root uid */
-	struct	uucred ex_anon;		/* mapping for anonymous user */
+	struct	uucred100 ex_anon;	/* mapping for anonymous user */
 	struct	sockaddr *ex_addr;	/* net address to which exported */
 	int	ex_addrlen;		/* and the net address length */
 	struct	sockaddr *ex_mask;	/* mask of valid bits in saddr */
@@ -201,7 +201,7 @@
 	struct nfsd	*nsd_nfsd;	/* Pointer to in kernel nfsd struct */
 	uid_t		nsd_uid;	/* Effective uid mapped to cred */
 	u_int32_t	nsd_haddr;	/* Ip address of client */
-	struct uucred	nsd_cr;		/* Cred. uid maps to */
+	struct uucred100 nsd_cr;		/* Cred. uid maps to */
 	int		nsd_authlen;	/* Length of auth string (ret) */
 	u_char		*nsd_authstr;	/* Auth string (ret) */
 	int		nsd_verflen;	/* and the verfier */
Index: sys/nfs/nfs_export.c
===================================================================
RCS file: /cvsroot/src/sys/nfs/nfs_export.c,v
retrieving revision 1.63
diff -u -r1.63 nfs_export.c
--- sys/nfs/nfs_export.c	4 Jun 2021 10:44:58 -0000	1.63
+++ sys/nfs/nfs_export.c	10 Apr 2026 20:35:23 -0000
@@ -514,7 +514,7 @@
 		KASSERT(np->netc_anon == NULL);
 		np->netc_anon = kauth_cred_alloc();
 		np->netc_exflags = argp->ex_flags;
-		kauth_uucred_to_cred(np->netc_anon, &argp->ex_anon);
+		kauth_uucred100_to_cred(np->netc_anon, &argp->ex_anon);
 		mp->mnt_flag |= MNT_DEFEXPORTED;
 		return 0;
 	}
@@ -588,11 +588,11 @@
 		enp->netc_refcnt = 1;
 
 	np->netc_exflags = argp->ex_flags;
-	kauth_uucred_to_cred(np->netc_anon, &argp->ex_anon);
+	kauth_uucred100_to_cred(np->netc_anon, &argp->ex_anon);
 	return 0;
 check:
 	if (enp->netc_exflags != argp->ex_flags ||
-	    kauth_cred_uucmp(enp->netc_anon, &argp->ex_anon) != 0)
+	    kauth_cred_uucmp100(enp->netc_anon, &argp->ex_anon) != 0)
 		error = EPERM;
 	else
 		error = 0;
Index: sys/nfs/nfs_syscalls.c
===================================================================
RCS file: /cvsroot/src/sys/nfs/nfs_syscalls.c,v
retrieving revision 1.163
diff -u -r1.163 nfs_syscalls.c
--- sys/nfs/nfs_syscalls.c	4 Jun 2021 10:44:58 -0000	1.163
+++ sys/nfs/nfs_syscalls.c	10 Apr 2026 20:35:23 -0000
@@ -412,7 +412,7 @@
 					m_freem(nuidp->nu_nam);
 			        }
 				nuidp->nu_flag = 0;
-				kauth_uucred_to_cred(nuidp->nu_cr,
+				kauth_uucred100_to_cred(nuidp->nu_cr,
 				    &nsd->nsd_cr);
 				nuidp->nu_timestamp = nsd->nsd_timestamp;
 				nuidp->nu_expire = time_second + nsd->nsd_ttl;
Index: sys/sys/kauth.h
===================================================================
RCS file: /cvsroot/src/sys/sys/kauth.h,v
retrieving revision 1.87.4.2
diff -u -r1.87.4.2 kauth.h
--- sys/sys/kauth.h	13 Jan 2023 19:14:13 -0000	1.87.4.2
+++ sys/sys/kauth.h	10 Apr 2026 20:35:24 -0000
@@ -39,6 +39,7 @@
 #include <sys/stat.h> /* for modes */
 
 struct uucred;
+struct uucred100;
 struct ki_ucred;
 struct ki_pcred;
 struct proc;
@@ -526,8 +527,11 @@
 
 int kauth_cred_uidmatch(kauth_cred_t, kauth_cred_t);
 void kauth_uucred_to_cred(kauth_cred_t, const struct uucred *);
+void kauth_uucred100_to_cred(kauth_cred_t, const struct uucred100 *);
 void kauth_cred_to_uucred(struct uucred *, const kauth_cred_t);
+void kauth_cred_to_uucred100(struct uucred100 *, const kauth_cred_t);
 int kauth_cred_uucmp(kauth_cred_t, const struct uucred *);
+int kauth_cred_uucmp100(kauth_cred_t, const struct uucred100 *);
 void kauth_cred_toucred(kauth_cred_t, struct ki_ucred *);
 void kauth_cred_topcred(kauth_cred_t, struct ki_pcred *);
 
Index: sys/sys/mount.h
===================================================================
RCS file: /cvsroot/src/sys/sys/mount.h,v
retrieving revision 1.240
diff -u -r1.240 mount.h
--- sys/sys/mount.h	4 Nov 2022 11:20:40 -0000	1.240
+++ sys/sys/mount.h	10 Apr 2026 20:35:24 -0000
@@ -359,7 +359,7 @@
 struct export_args30 {
 	int	ex_flags;		/* export related flags */
 	uid_t	ex_root;		/* mapping for root uid */
-	struct	uucred ex_anon;		/* mapping for anonymous user */
+	struct	uucred100 ex_anon;	/* mapping for anonymous user */
 	struct	sockaddr *ex_addr;	/* net address to which exported */
 	int	ex_addrlen;		/* and the net address length */
 	struct	sockaddr *ex_mask;	/* mask of valid bits in saddr */
Index: sys/sys/syslimits.h
===================================================================
RCS file: /cvsroot/src/sys/sys/syslimits.h,v
retrieving revision 1.28
diff -u -r1.28 syslimits.h
--- sys/sys/syslimits.h	21 Aug 2015 07:19:39 -0000	1.28
+++ sys/sys/syslimits.h	10 Apr 2026 20:35:24 -0000
@@ -52,7 +52,8 @@
 #define	MAX_INPUT		  255	/* max bytes in terminal input */
 #define	NAME_MAX		  511	/* max bytes in a file name, must be */
 					/* kept in sync with MAXNAMLEN */
-#define	NGROUPS_MAX		   16	/* max supplemental group id's */
+#define	NGROUPS_MAX_100		   16	/* COMPAT: max supplemental group ids */
+#define	NGROUPS_MAX		 1024	/* max supplemental group ids */
 #define	UID_MAX		   2147483647U	/* max value for a uid_t (2^31-2) */
 #ifndef OPEN_MAX
 #define	OPEN_MAX		  128	/* max open files per process */
Index: sys/sys/ucred.h
===================================================================
RCS file: /cvsroot/src/sys/sys/ucred.h,v
retrieving revision 1.36
diff -u -r1.36 ucred.h
--- sys/sys/ucred.h	12 Oct 2011 23:03:36 -0000	1.36
+++ sys/sys/ucred.h	10 Apr 2026 20:35:24 -0000
@@ -53,4 +53,13 @@
 	gid_t		cr_groups[NGROUPS_MAX];	/* groups */
 };
 
+struct uucred100 {
+	unsigned short	cr_unused;		/* not used, compat */
+	uid_t		cr_uid;			/* effective user id */
+	gid_t		cr_gid;			/* effective group id */
+	short		cr_ngroups;		/* number of groups */
+	gid_t		cr_groups[NGROUPS_MAX_100];	/* groups */
+};
+
+
 #endif /* !_SYS_UCRED_H_ */
Index: usr.sbin/mountd/mountd.c
===================================================================
RCS file: /cvsroot/src/usr.sbin/mountd/mountd.c,v
retrieving revision 1.137
diff -u -r1.137 mountd.c
--- usr.sbin/mountd/mountd.c	5 Jun 2021 08:26:34 -0000	1.137
+++ usr.sbin/mountd/mountd.c	10 Apr 2026 20:35:26 -0000
@@ -185,9 +185,9 @@
 static int del_mlist(char *, char *, struct sockaddr *);
 static struct dirlist *dirp_search(struct dirlist *, char *);
 static int do_nfssvc(const char *, size_t, struct exportlist *,
-    struct grouplist *, int, struct uucred *, char *, int, struct statvfs *);
+    struct grouplist *, int, struct uucred100 *, char *, int, struct statvfs *);
 static int do_opt(const char *, size_t, char **, char **,
-    struct exportlist *, struct grouplist *, int *, int *, struct uucred *);
+    struct exportlist *, struct grouplist *, int *, int *, struct uucred100 *);
 static struct exportlist *ex_search(fsid_t *);
 static int parse_directory(const char *, size_t, struct grouplist *,
     int, char *, struct exportlist **, struct statvfs *);
@@ -209,7 +209,7 @@
     struct exportlist *, int);
 static void mntsrv(struct svc_req *, SVCXPRT *);
 static void nextfield(char **, char **);
-static void parsecred(char *, struct uucred *);
+static void parsecred(char *, struct uucred100 *);
 static int put_exlist(struct dirlist *, XDR *, struct dirlist *, int *);
 static int scan_tree(struct dirlist *, struct sockaddr *);
 __dead static void send_umntall(int);
@@ -228,7 +228,7 @@
 static struct grouplist *grphead;
 static char *const exnames_default[] = { __UNCONST(_PATH_EXPORTS), NULL };
 static char *const *exnames;
-static struct uucred def_anon = {
+static struct uucred100 def_anon = {
 	1,
 	(uid_t) -2,
 	(gid_t) -2,
@@ -1021,7 +1021,7 @@
 	struct dirlist *dirhead;
 	struct statvfs fsb;
 	struct addrinfo *ai;
-	struct uucred anon;
+	struct uucred100 anon;
 	char *cp, *endcp, *dirp, savedc;
 	int has_host, exflags, got_nondir, dirplen;
 	char *line;
@@ -1740,7 +1740,7 @@
 static int
 do_opt(const char *line, size_t lineno, char **cpp, char **endcpp,
     struct exportlist *ep, struct grouplist *grp, int *has_hostp,
-    int *exflagsp, struct uucred *cr)
+    int *exflagsp, struct uucred100 *cr)
 {
 	char *cpoptarg, *cpoptend;
 	char *cp, *cpopt, savedc, savedc2;
@@ -1951,7 +1951,7 @@
 }
 
 static int
-add_export_arg(const char *path, int exflags, struct uucred *anoncrp,
+add_export_arg(const char *path, int exflags, struct uucred100 *anoncrp,
     struct sockaddr *addrp, int addrlen, struct sockaddr *maskp, int masklen,
     char *indexfile)
 {
@@ -1997,7 +1997,7 @@
  */
 static int
 do_nfssvc(const char *line, size_t lineno, struct exportlist *ep,
-    struct grouplist *grp, int exflags, struct uucred *anoncrp,
+    struct grouplist *grp, int exflags, struct uucred100 *anoncrp,
     char *dirp, int dirplen, struct statvfs *fsb)
 {
 	struct sockaddr *addrp;
@@ -2062,7 +2062,7 @@
  * Parse a description of a credential.
  */
 static void
-parsecred(char *namelist, struct uucred *cr)
+parsecred(char *namelist, struct uucred100 *cr)
 {
 	char *username;
 	int cnt;


Home | Main Index | Thread Index | Old Index