17c478bd9Sstevel@tonic-gate /*
27c478bd9Sstevel@tonic-gate * CDDL HEADER START
37c478bd9Sstevel@tonic-gate *
47c478bd9Sstevel@tonic-gate * The contents of this file are subject to the terms of the
5cb5caa98Sdjl * Common Development and Distribution License (the "License").
6cb5caa98Sdjl * You may not use this file except in compliance with the License.
77c478bd9Sstevel@tonic-gate *
87c478bd9Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
97c478bd9Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing.
107c478bd9Sstevel@tonic-gate * See the License for the specific language governing permissions
117c478bd9Sstevel@tonic-gate * and limitations under the License.
127c478bd9Sstevel@tonic-gate *
137c478bd9Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each
147c478bd9Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
157c478bd9Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the
167c478bd9Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying
177c478bd9Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner]
187c478bd9Sstevel@tonic-gate *
197c478bd9Sstevel@tonic-gate * CDDL HEADER END
207c478bd9Sstevel@tonic-gate */
217c478bd9Sstevel@tonic-gate /*
22*2b4a7802SBaban Kenkre * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
23cb5caa98Sdjl * Use is subject to license terms.
247c478bd9Sstevel@tonic-gate *
257c478bd9Sstevel@tonic-gate * nis/getpwnam.c -- "nis" backend for nsswitch "passwd" database
267c478bd9Sstevel@tonic-gate */
277c478bd9Sstevel@tonic-gate
287c478bd9Sstevel@tonic-gate #include <pwd.h>
297c478bd9Sstevel@tonic-gate #include "nis_common.h"
307c478bd9Sstevel@tonic-gate
317c478bd9Sstevel@tonic-gate static nss_status_t
getbyname(be,a)327c478bd9Sstevel@tonic-gate getbyname(be, a)
337c478bd9Sstevel@tonic-gate nis_backend_ptr_t be;
347c478bd9Sstevel@tonic-gate void *a;
357c478bd9Sstevel@tonic-gate {
36cb5caa98Sdjl nss_XbyY_args_t *argp = (nss_XbyY_args_t *)a;
377c478bd9Sstevel@tonic-gate
387c478bd9Sstevel@tonic-gate return (_nss_nis_lookup(be, argp, 0,
397c478bd9Sstevel@tonic-gate "passwd.byname", argp->key.name, 0));
407c478bd9Sstevel@tonic-gate }
417c478bd9Sstevel@tonic-gate
427c478bd9Sstevel@tonic-gate static nss_status_t
getbyuid(be,a)437c478bd9Sstevel@tonic-gate getbyuid(be, a)
447c478bd9Sstevel@tonic-gate nis_backend_ptr_t be;
457c478bd9Sstevel@tonic-gate void *a;
467c478bd9Sstevel@tonic-gate {
47cb5caa98Sdjl nss_XbyY_args_t *argp = (nss_XbyY_args_t *)a;
487c478bd9Sstevel@tonic-gate char uidstr[12]; /* More than enough */
497c478bd9Sstevel@tonic-gate
50*2b4a7802SBaban Kenkre if (argp->key.uid > MAXUID)
51*2b4a7802SBaban Kenkre return (NSS_NOTFOUND);
52*2b4a7802SBaban Kenkre (void) snprintf(uidstr, 12, "%u", argp->key.uid);
537c478bd9Sstevel@tonic-gate return (_nss_nis_lookup(be, argp, 0, "passwd.byuid", uidstr, 0));
547c478bd9Sstevel@tonic-gate }
557c478bd9Sstevel@tonic-gate
56*2b4a7802SBaban Kenkre /*
57*2b4a7802SBaban Kenkre * Validates passwd entry replacing uid/gid > MAXUID by ID_NOBODY.
58*2b4a7802SBaban Kenkre */
59*2b4a7802SBaban Kenkre int
validate_passwd_ids(char ** linepp,int * linelenp,int allocbuf)60*2b4a7802SBaban Kenkre validate_passwd_ids(char **linepp, int *linelenp, int allocbuf)
61*2b4a7802SBaban Kenkre {
62*2b4a7802SBaban Kenkre char *linep, *limit, *uidp, *gidp, *newline;
63*2b4a7802SBaban Kenkre uid_t uid;
64*2b4a7802SBaban Kenkre gid_t gid;
65*2b4a7802SBaban Kenkre ulong_t uidl, gidl;
66*2b4a7802SBaban Kenkre int olduidlen, oldgidlen, idlen;
67*2b4a7802SBaban Kenkre int linelen = *linelenp, newlinelen;
68*2b4a7802SBaban Kenkre
69*2b4a7802SBaban Kenkre linep = *linepp;
70*2b4a7802SBaban Kenkre limit = linep + linelen;
71*2b4a7802SBaban Kenkre
72*2b4a7802SBaban Kenkre /* +/- entries valid for compat source only */
73*2b4a7802SBaban Kenkre if (linelen == 0 || *linep == '+' || *linep == '-')
74*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_SUCCESS);
75*2b4a7802SBaban Kenkre
76*2b4a7802SBaban Kenkre while (linep < limit && *linep++ != ':') /* skip username */
77*2b4a7802SBaban Kenkre continue;
78*2b4a7802SBaban Kenkre while (linep < limit && *linep++ != ':') /* skip password */
79*2b4a7802SBaban Kenkre continue;
80*2b4a7802SBaban Kenkre if (linep == limit)
81*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_PARSE);
82*2b4a7802SBaban Kenkre
83*2b4a7802SBaban Kenkre uidp = linep;
84*2b4a7802SBaban Kenkre uidl = strtoul(uidp, (char **)&linep, 10); /* grab uid */
85*2b4a7802SBaban Kenkre olduidlen = linep - uidp;
86*2b4a7802SBaban Kenkre if (++linep >= limit || olduidlen == 0)
87*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_PARSE);
88*2b4a7802SBaban Kenkre
89*2b4a7802SBaban Kenkre gidp = linep;
90*2b4a7802SBaban Kenkre gidl = strtoul(gidp, (char **)&linep, 10); /* grab gid */
91*2b4a7802SBaban Kenkre oldgidlen = linep - gidp;
92*2b4a7802SBaban Kenkre if (linep >= limit || oldgidlen == 0)
93*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_PARSE);
94*2b4a7802SBaban Kenkre
95*2b4a7802SBaban Kenkre if (uidl <= MAXUID && gidl <= MAXUID)
96*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_SUCCESS);
97*2b4a7802SBaban Kenkre uid = (uidl > MAXUID) ? UID_NOBODY : (uid_t)uidl;
98*2b4a7802SBaban Kenkre gid = (gidl > MAXUID) ? GID_NOBODY : (gid_t)gidl;
99*2b4a7802SBaban Kenkre
100*2b4a7802SBaban Kenkre /* Check if we have enough space in the buffer */
101*2b4a7802SBaban Kenkre idlen = snprintf(NULL, 0, "%u:%u", uid, gid);
102*2b4a7802SBaban Kenkre newlinelen = linelen + idlen - olduidlen - oldgidlen - 1;
103*2b4a7802SBaban Kenkre if (newlinelen > linelen) {
104*2b4a7802SBaban Kenkre /* need a larger buffer */
105*2b4a7802SBaban Kenkre if (!allocbuf || (newline = malloc(newlinelen + 1)) == NULL)
106*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_ERANGE);
107*2b4a7802SBaban Kenkre /* Replace ephemeral ids by ID_NOBODY in the new buffer */
108*2b4a7802SBaban Kenkre *(uidp - 1) = '\0';
109*2b4a7802SBaban Kenkre (void) snprintf(newline, newlinelen + 1, "%s:%u:%u%s",
110*2b4a7802SBaban Kenkre *linepp, uid, gid, linep);
111*2b4a7802SBaban Kenkre free(*linepp);
112*2b4a7802SBaban Kenkre *linepp = newline;
113*2b4a7802SBaban Kenkre *linelenp = newlinelen;
114*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_SUCCESS);
115*2b4a7802SBaban Kenkre }
116*2b4a7802SBaban Kenkre
117*2b4a7802SBaban Kenkre /* Replace ephemeral ids by ID_NOBODY in the same buffer */
118*2b4a7802SBaban Kenkre (void) bcopy(linep, uidp + idlen, limit - linep + 1);
119*2b4a7802SBaban Kenkre (void) snprintf(uidp, idlen + 1, "%u:%u", uid, gid);
120*2b4a7802SBaban Kenkre *(uidp + idlen) = ':'; /* restore : that was overwritten by snprintf */
121*2b4a7802SBaban Kenkre *linelenp = newlinelen;
122*2b4a7802SBaban Kenkre return (NSS_STR_PARSE_SUCCESS);
123*2b4a7802SBaban Kenkre }
124*2b4a7802SBaban Kenkre
1257c478bd9Sstevel@tonic-gate static nis_backend_op_t passwd_ops[] = {
1267c478bd9Sstevel@tonic-gate _nss_nis_destr,
1277c478bd9Sstevel@tonic-gate _nss_nis_endent,
1287c478bd9Sstevel@tonic-gate _nss_nis_setent,
1297c478bd9Sstevel@tonic-gate _nss_nis_getent_rigid,
1307c478bd9Sstevel@tonic-gate getbyname,
1317c478bd9Sstevel@tonic-gate getbyuid
1327c478bd9Sstevel@tonic-gate };
1337c478bd9Sstevel@tonic-gate
1347c478bd9Sstevel@tonic-gate /*ARGSUSED*/
1357c478bd9Sstevel@tonic-gate nss_backend_t *
_nss_nis_passwd_constr(dummy1,dummy2,dummy3)1367c478bd9Sstevel@tonic-gate _nss_nis_passwd_constr(dummy1, dummy2, dummy3)
1377c478bd9Sstevel@tonic-gate const char *dummy1, *dummy2, dummy3;
1387c478bd9Sstevel@tonic-gate {
1397c478bd9Sstevel@tonic-gate return (_nss_nis_constr(passwd_ops,
1407c478bd9Sstevel@tonic-gate sizeof (passwd_ops) / sizeof (passwd_ops[0]),
1417c478bd9Sstevel@tonic-gate "passwd.byname"));
1427c478bd9Sstevel@tonic-gate }
143