1#pragma ident	"%Z%%M%	%I%	%E% SMI"
2
3/*
4 * Replacement for getpwnam - we need it to handle files other than
5 * /etc/passwd so we can permit different passwd files for each different
6 * host
7 * (c) 1998-2000 by Bernhard Rosenkr�nzer <bero@redhat.com>
8 * 19980930	Initial version
9 * 20000211	Various fixes
10 */
11
12#include "config.h"
13#include <pwd.h>
14#include <sys/types.h>
15#include <stdio.h>
16#ifdef SHADOW_PASSWORD
17# ifdef HAVE_SHADOW_H
18#  include <shadow.h>
19# endif
20#endif
21
22#ifndef HAVE_FGETPWENT /* Some systems (*BSD) don't have fgetpwent... */
23#ifdef HAVE_STRINGS_H
24#include <strings.h>
25#else
26#include <string.h>
27#endif
28struct passwd *fgetpwent(FILE *stream)
29{
30	char *entry=(char *) malloc(1024);
31	struct passwd *p=(struct passwd *) malloc(sizeof(struct passwd));
32	char *tmp,*tmp2;
33
34	if(!fgets(entry,1024,stream)) {
35		free(entry);
36		free(p);
37		return NULL;
38	}
39	tmp=strdup(entry);
40	if(strchr(tmp,':')) {
41		*strchr(tmp,':')=0;
42		p->pw_name=tmp;
43	} else {
44		free(tmp); free(entry);	free(p); return NULL;
45	}
46	tmp2=strchr(entry,':')+1;
47	tmp=strdup(tmp2);
48	if(strchr(tmp,':')) {
49		*strchr(tmp,':')=0;
50		p->pw_passwd=tmp;
51	} else {
52		free(tmp); free(entry); free(p->pw_name); free(p); return NULL;
53	}
54	tmp2=strchr(tmp2,':')+1;
55	tmp=strdup(tmp2);
56	if(strchr(tmp,':')) {
57		*strchr(tmp,':')=0;
58		p->pw_uid=(uid_t) atoi(tmp);
59	} else {
60		free(tmp); free(entry); free(p->pw_passwd); free(p->pw_name); free(p); return NULL;
61	}
62	free(tmp);
63	tmp2=strchr(tmp2,':')+1;
64	tmp=strdup(tmp2);
65	if(strchr(tmp,':')) {
66		*strchr(tmp,':')=0;
67		p->pw_gid=(gid_t) atoi(tmp);
68	} else {
69		free(tmp); free(entry); free(p->pw_passwd); free(p->pw_name); free(p); return NULL;
70	}
71	free(tmp);
72	tmp2=strchr(tmp2,':')+1;
73	tmp=strdup(tmp2);
74	if(strchr(tmp,':')) {
75		*strchr(tmp,':')=0;
76		p->pw_gecos=tmp;
77	} else {
78		free(tmp); free(entry); free(p->pw_passwd); free(p->pw_name); free(p); return NULL;
79	}
80	tmp2=strchr(tmp2,':')+1;
81	tmp=strdup(tmp2);
82	if(strchr(tmp,':')) {
83		*strchr(tmp,':')=0;
84		p->pw_dir=tmp;
85	} else {
86		free(tmp); free(entry); free(p->pw_gecos); free(p->pw_passwd); free(p->pw_name); free(p); return NULL;
87	}
88	tmp2=strchr(tmp2,':')+1;
89	if(strchr(tmp2,':')) {
90		free(entry); free(p->pw_dir); free(p->pw_gecos); free(p->pw_passwd); free(p->pw_name); free(p); return NULL;
91	}
92	while(strlen(tmp2) && isspace(tmp2[strlen(tmp2)-1]))
93		tmp2[strlen(tmp2)-1]=0;
94	p->pw_shell=strdup(tmp2);
95	free(entry);
96	return p;
97}
98#endif
99
100
101struct passwd *bero_getpwnam(const char * name, const char * file)
102{
103	FILE *f;
104	struct passwd *p;
105	struct passwd *r;
106
107	if (!strcmp(file,"/etc/passwd"))
108	  return (getpwnam(name));
109	f=fopen(file,"r");
110	if(f==NULL)
111		return NULL;
112	p=NULL;
113	r=NULL;
114	while((r==NULL) && (p=fgetpwent(f)))
115		if(!strcasecmp(p->pw_name,name))
116			r=p;
117	fclose(f);
118	return r;
119}
120
121struct passwd *bero_getpwuid(uid_t uid, const char * file)
122{
123	FILE *f;
124	struct passwd *p;
125	struct passwd *r;
126
127	if (!strcmp(file,"/etc/passwd"))
128	  return getpwuid(uid);
129	f=fopen(file,"r");
130	if(f==NULL)
131		return NULL;
132	p=NULL;
133	r=NULL;
134	while((r==NULL) && (p=fgetpwent(f)))
135		if(p->pw_uid==uid)
136			r=p;
137	fclose(f);
138	return r;
139}
140
141#ifdef SHADOW_PASSWORD
142struct spwd *bero_getspnam(const char * name, const char * file)
143{
144	FILE *f;
145	struct spwd *s;
146	struct spwd *r;
147	f=fopen(file,"r");
148	if(f==NULL)
149		return NULL;
150	s=NULL;
151	r=NULL;
152	while((r==NULL) && (s=fgetspent(f)))
153		if(!strcasecmp(s->sp_namp,name))
154			r=s;
155	fclose(f);
156	return r;
157}
158#endif
159