packages: sort network related packages into package/network/
[openwrt.git] / package / network / services / ead / src / tinysrp / t_pw.c
1 /*
2  * Copyright (c) 1997-2000  The Stanford SRP Authentication Project
3  * All Rights Reserved.
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining
6  * a copy of this software and associated documentation files (the
7  * "Software"), to deal in the Software without restriction, including
8  * without limitation the rights to use, copy, modify, merge, publish,
9  * distribute, sublicense, and/or sell copies of the Software, and to
10  * permit persons to whom the Software is furnished to do so, subject to
11  * the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be
14  * included in all copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
17  * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY
18  * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
19  *
20  * IN NO EVENT SHALL STANFORD BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
21  * INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
22  * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER OR NOT ADVISED OF
23  * THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING OUT
24  * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
25  *
26  * In addition, the following conditions apply:
27  *
28  * 1. Any software that incorporates the SRP authentication technology
29  *    must display the following acknowlegment:
30  *    "This product uses the 'Secure Remote Password' cryptographic
31  *     authentication system developed by Tom Wu (tjw@CS.Stanford.EDU)."
32  *
33  * 2. Any software that incorporates all or part of the SRP distribution
34  *    itself must also display the following acknowledgment:
35  *    "This product includes software developed by Tom Wu and Eugene
36  *     Jhong for the SRP Distribution (http://srp.stanford.edu/srp/)."
37  *
38  * 3. Redistributions in source or binary form must retain an intact copy
39  *    of this copyright notice and list of conditions.
40  */
41
42 #include "t_defines.h"
43
44 #ifdef HAVE_UNISTD_H
45 #include <unistd.h>
46 #endif /* HAVE_UNISTD_H */
47
48 #include <stdio.h>
49 #include <sys/types.h>
50 #include <sys/stat.h>
51 #ifdef USE_HOMEDIR
52 #include <pwd.h>
53 #endif
54 #ifdef WIN32
55 #include <io.h>
56 #endif
57
58 #include "t_pwd.h"
59 #include "t_read.h"
60 #include "t_sha.h"
61 #include "t_server.h"
62
63 static struct t_pw * syspw = NULL;
64 static struct t_passwd tpass;
65
66 _TYPE( struct t_server * )
67 t_serveropen(username)
68      const char * username;
69 {
70   struct t_passwd * p;
71   p = gettpnam(username);
72   if(p == NULL) {
73     return NULL;
74   } else {
75     return t_serveropenraw(&p->tp, &p->tc);
76   }
77 }
78
79
80 /* t_openpw(NULL) is deprecated - use settpent()/gettpnam() instead */
81
82 _TYPE( struct t_pw * )
83 t_openpw(fp)
84      FILE * fp;
85 {
86   struct t_pw * tpw;
87   char close_flag = 0;
88
89   if(fp == NULL) { /* Deprecated */
90     if((fp = fopen(DEFAULT_PASSWD, "r")) == NULL)
91       return NULL;
92     close_flag = 1;
93   }
94   else
95     close_flag = 0;
96
97   if((tpw = malloc(sizeof(struct t_pw))) == NULL)
98     return NULL;
99   tpw->instream = fp;
100   tpw->close_on_exit = close_flag;
101   tpw->state = FILE_ONLY;
102
103   return tpw;
104 }
105
106 _TYPE( struct t_pw * )
107 t_openpwbyname(pwname)
108      const char * pwname;
109 {
110   FILE * fp;
111   struct t_pw * t;
112
113   if(pwname == NULL)            /* Deprecated */
114     return t_openpw(NULL);
115
116   if((fp = fopen(pwname, "r")) == NULL)
117     return NULL;
118
119   t = t_openpw(fp);
120   t->close_on_exit = 1;
121   return t;
122 }
123
124 _TYPE( void )
125 t_closepw(tpw)
126      struct t_pw * tpw;
127 {
128   if(tpw->close_on_exit)
129     fclose(tpw->instream);
130   free(tpw);
131 }
132
133 _TYPE( void )
134 t_rewindpw(tpw)
135      struct t_pw * tpw;
136 {
137 #ifdef ENABLE_YP
138   if(tpw->state == IN_NIS)
139     tpw->state = FILE_NIS;
140 #endif
141   rewind(tpw->instream);
142 }
143
144 #ifdef ENABLE_YP
145 static void
146 savepwent(tpw, pwent)
147      struct t_pw * tpw;
148      struct t_pwent *pwent;
149 {
150   tpw->pebuf.name = tpw->userbuf;
151   tpw->pebuf.password.data = tpw->pwbuf;
152   tpw->pebuf.salt.data = tpw->saltbuf;
153   strcpy(tpw->pebuf.name, pwent->name);
154   tpw->pebuf.password.len = pwent->password.len;
155   memcpy(tpw->pebuf.password.data, pwent->password.data, pwent->password.len);
156   tpw->pebuf.salt.len = pwent->salt.len;
157   memcpy(tpw->pebuf.salt.data, pwent->salt.data, pwent->salt.len);
158   tpw->pebuf.index = pwent->index;
159 }
160 #endif /* ENABLE_YP */
161
162 _TYPE( struct t_pwent * )
163 t_getpwbyname(tpw, user)
164      struct t_pw * tpw;
165      const char * user;
166 {
167   char indexbuf[16];
168   char passbuf[MAXB64PARAMLEN];
169   char saltstr[MAXB64SALTLEN];
170   char username[MAXUSERLEN];
171 #ifdef ENABLE_YP
172   struct t_passwd * nisent;
173 #endif
174
175   t_rewindpw(tpw);
176
177   while(t_nextfield(tpw->instream, username, MAXUSERLEN) > 0) {
178 #ifdef ENABLE_YP
179     if(tpw->state == FILE_NIS && *username == '+') {
180       if(strlen(username) == 1 || strcmp(user, username+1) == 0) {
181         nisent = _yp_gettpnam(user);    /* Entry is +username or + */
182         if(nisent != NULL) {
183           savepwent(tpw, &nisent->tp);
184           return &tpw->pebuf;
185         }
186       }
187     }
188 #endif
189     if(strcmp(user, username) == 0)
190       if(t_nextfield(tpw->instream, passbuf, MAXB64PARAMLEN) > 0 &&
191          (tpw->pebuf.password.len = t_fromb64(tpw->pwbuf, passbuf)) > 0 &&
192          t_nextfield(tpw->instream, saltstr, MAXB64SALTLEN) > 0 &&
193          (tpw->pebuf.salt.len = t_fromb64(tpw->saltbuf, saltstr)) > 0 &&
194          t_nextfield(tpw->instream, indexbuf, 16) > 0 &&
195          (tpw->pebuf.index = atoi(indexbuf)) > 0) {
196         strcpy(tpw->userbuf, username);
197         tpw->pebuf.name = tpw->userbuf;
198         tpw->pebuf.password.data = tpw->pwbuf;
199         tpw->pebuf.salt.data = tpw->saltbuf;
200         t_nextline(tpw->instream);
201         return &tpw->pebuf;
202       }
203     if(t_nextline(tpw->instream) < 0)
204       return NULL;
205   }
206   return NULL;
207 }
208
209 /* System password file accessors */
210
211 static int
212 pwinit()
213 {
214   if(syspw == NULL) {
215     if((syspw = t_openpwbyname(DEFAULT_PASSWD)) == NULL)
216       return -1;
217     syspw->state = FILE_NIS;
218   }
219   return 0;
220 }
221
222 static void
223 pwsetup(out, tpwd, tcnf)
224      struct t_passwd * out;
225      struct t_pwent * tpwd;
226      struct t_confent * tcnf;
227 {
228   out->tp.name = tpwd->name;
229   out->tp.password.len = tpwd->password.len;
230   out->tp.password.data = tpwd->password.data;
231   out->tp.salt.len = tpwd->salt.len;
232   out->tp.salt.data = tpwd->salt.data;
233   out->tp.index = tpwd->index;
234
235   out->tc.index = tcnf->index;
236   out->tc.modulus.len = tcnf->modulus.len;
237   out->tc.modulus.data = tcnf->modulus.data;
238   out->tc.generator.len = tcnf->generator.len;
239   out->tc.generator.data = tcnf->generator.data;
240 }
241
242 _TYPE( struct t_passwd * )
243 gettpnam
244 (user)
245      const char * user;
246 {
247   struct t_pwent * tpptr;
248   struct t_confent * tcptr;
249
250   if(pwinit() < 0)
251     return NULL;
252   tpptr = t_getpwbyname(syspw, user);
253   if(tpptr == NULL)
254     return NULL;
255   tcptr =
256     gettcid
257     (tpptr->index);
258   if(tcptr == NULL)
259     return NULL;
260   pwsetup(&tpass, tpptr, tcptr);
261   return &tpass;
262 }