? sys/atomic.h Index: kern/kern_prot.c =================================================================== RCS file: /home/ncvs/src/sys/kern/kern_prot.c,v retrieving revision 1.67 diff -c -r1.67 kern_prot.c *** kern/kern_prot.c 2000/11/10 23:57:48 1.67 --- kern/kern_prot.c 2000/11/26 21:29:46 *************** *** 1131,1139 **** { register struct ucred *cr; ! MALLOC(cr, struct ucred *, sizeof(*cr), M_CRED, M_WAITOK); ! bzero((caddr_t)cr, sizeof(*cr)); cr->cr_ref = 1; return (cr); } --- 1131,1139 ---- { register struct ucred *cr; ! MALLOC(cr, struct ucred *, sizeof(*cr), M_CRED, M_WAITOK|M_ZERO); cr->cr_ref = 1; + mtx_init(&cr->cr_mtx, "ucred", MTX_DEF); return (cr); } *************** *** 1145,1151 **** --- 1145,1154 ---- crfree(cr) struct ucred *cr; { + + mtx_enter(&cr->cr_mtx, MTX_DEF); if (--cr->cr_ref == 0) { + mtx_destroy(&cr->cr_mtx); /* * Some callers of crget(), such as nfs_statfs(), * allocate a temporary credential, but don't *************** *** 1154,1159 **** --- 1157,1164 ---- if (cr->cr_uidinfo != NULL) uifree(cr->cr_uidinfo); FREE((caddr_t)cr, M_CRED); + } else { + mtx_exit(&cr->cr_mtx, MTX_DEF); } } *************** *** 1166,1178 **** { struct ucred *newcr; ! if (cr->cr_ref == 1) return (cr); ! newcr = crget(); ! *newcr = *cr; ! uihold(newcr->cr_uidinfo); crfree(cr); - newcr->cr_ref = 1; return (newcr); } --- 1171,1184 ---- { struct ucred *newcr; ! mtx_enter(&cr->cr_mtx, MTX_DEF); ! if (cr->cr_ref == 1) { ! mtx_exit(&cr->cr_mtx, MTX_DEF); return (cr); ! } ! mtx_exit(&cr->cr_mtx, MTX_DEF); ! newcr = crdup(cr); crfree(cr); return (newcr); } *************** *** 1185,1192 **** { struct ucred *newcr; ! newcr = crget(); *newcr = *cr; uihold(newcr->cr_uidinfo); newcr->cr_ref = 1; return (newcr); --- 1191,1199 ---- { struct ucred *newcr; ! MALLOC(newcr, struct ucred *, sizeof(*cr), M_CRED, M_WAITOK); *newcr = *cr; + mtx_init(&newcr->cr_mtx, "ucred", MTX_DEF); uihold(newcr->cr_uidinfo); newcr->cr_ref = 1; return (newcr); Index: sys/ucred.h =================================================================== RCS file: /home/ncvs/src/sys/sys/ucred.h,v retrieving revision 1.17 diff -c -r1.17 ucred.h *** sys/ucred.h 2000/10/26 15:49:35 1.17 --- sys/ucred.h 2000/11/26 21:29:48 *************** *** 37,42 **** --- 37,44 ---- #ifndef _SYS_UCRED_H_ #define _SYS_UCRED_H_ + #include + /* * Credentials. * *************** *** 44,50 **** * Only the suser()/suser_xxx() function should be used for this. */ struct ucred { ! u_short cr_ref; /* reference count */ uid_t cr_uid; /* effective user id */ short cr_ngroups; /* number of groups */ gid_t cr_groups[NGROUPS]; /* groups */ --- 46,53 ---- * Only the suser()/suser_xxx() function should be used for this. */ struct ucred { ! struct mtx cr_mtx; /* protect refcount */ ! u_int cr_ref; /* reference count */ uid_t cr_uid; /* effective user id */ short cr_ngroups; /* number of groups */ gid_t cr_groups[NGROUPS]; /* groups */ *************** *** 55,61 **** #define FSCRED ((struct ucred *)-1) /* filesystem credential */ #ifdef _KERNEL ! #define crhold(cr) (cr)->cr_ref++ struct proc; --- 58,69 ---- #define FSCRED ((struct ucred *)-1) /* filesystem credential */ #ifdef _KERNEL ! #define crhold(cr) \ ! do { \ ! mtx_enter(&(cr)->cr_mtx, MTX_DEF); \ ! (cr)->cr_ref++; \ ! mtx_exit(&(cr)->cr_mtx, MTX_DEF); \ ! } while (0) struct proc;