* nis/nss_nisplus/nisplus-parser.c: Some cleanups. Remove
[glibc.git] / nis / nss_nisplus / nisplus-parser.c
blob4cd0738aa288fbf22752db8e638b7f7846457f99
1 /* Copyright (C) 1997, 1999, 2004, 2006 Free Software Foundation, Inc.
2 This file is part of the GNU C Library.
3 Contributed by Thorsten Kukuk <kukuk@vt.uni-paderborn.de>, 1997.
5 The GNU C Library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
10 The GNU C Library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public
16 License along with the GNU C Library; if not, write to the Free
17 Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
18 02111-1307 USA. */
20 #include <pwd.h>
21 #include <ctype.h>
22 #include <errno.h>
23 #include <string.h>
24 #include <rpcsvc/nis.h>
26 #include "nisplus-parser.h"
28 #define NISENTRYVAL(idx, col, res) \
29 (NIS_RES_OBJECT (res)[idx].EN_data.en_cols.en_cols_val[col].ec_value.ec_value_val)
31 #define NISENTRYLEN(idx, col, res) \
32 (NIS_RES_OBJECT (res)[idx].EN_data.en_cols.en_cols_val[col].ec_value.ec_value_len)
35 int
36 _nss_nisplus_parse_pwent (nis_result *result, struct passwd *pw,
37 char *buffer, size_t buflen, int *errnop)
39 char *first_unused = buffer;
40 size_t room_left = buflen;
41 size_t len;
43 if (result == NULL)
44 return 0;
46 if ((result->status != NIS_SUCCESS && result->status != NIS_S_SUCCESS)
47 || NIS_RES_NUMOBJ (result) != 1
48 || __type_of (NIS_RES_OBJECT (result)) != NIS_ENTRY_OBJ
49 || strcmp (NIS_RES_OBJECT (result)->EN_data.en_type, "passwd_tbl") != 0
50 || NIS_RES_OBJECT (result)->EN_data.en_cols.en_cols_len < 7)
51 return 0;
53 if (NISENTRYLEN (0, 0, result) >= room_left)
55 /* The line is too long for our buffer. */
56 no_more_room:
57 *errnop = ERANGE;
58 return -1;
61 strncpy (first_unused, NISENTRYVAL (0, 0, result),
62 NISENTRYLEN (0, 0, result));
63 first_unused[NISENTRYLEN (0, 0, result)] = '\0';
64 len = strlen (first_unused);
65 if (len == 0) /* No name ? Should never happen, database is corrupt */
66 return 0;
67 pw->pw_name = first_unused;
68 room_left -= (len + 1);
69 first_unused += (len + 1);
71 if (NISENTRYLEN (0, 1, result) >= room_left)
72 goto no_more_room;
74 strncpy (first_unused, NISENTRYVAL (0, 1, result),
75 NISENTRYLEN (0, 1, result));
76 first_unused[NISENTRYLEN (0, 1, result)] = '\0';
77 pw->pw_passwd = first_unused;
78 len = strlen (first_unused);
79 room_left -= (len + 1);
80 first_unused += (len + 1);
82 if (NISENTRYLEN(0, 2, result) >= room_left)
83 goto no_more_room;
85 strncpy (first_unused, NISENTRYVAL (0, 2, result),
86 NISENTRYLEN (0, 2, result));
87 first_unused[NISENTRYLEN (0, 2, result)] = '\0';
88 len = strlen (first_unused);
89 if (len == 0) /* If we don't have a uid, it's an invalid shadow entry */
90 return 0;
91 pw->pw_uid = strtoul (first_unused, NULL, 10);
93 if (NISENTRYLEN (0, 3, result) >= room_left)
94 goto no_more_room;
96 strncpy (first_unused, NISENTRYVAL (0, 3, result),
97 NISENTRYLEN (0, 3, result));
98 first_unused[NISENTRYLEN (0, 3, result)] = '\0';
99 len = strlen (first_unused);
100 if (len == 0) /* If we don't have a gid, it's an invalid shadow entry */
101 return 0;
102 pw->pw_gid = strtoul (first_unused, NULL, 10);
104 if (NISENTRYLEN(0, 4, result) >= room_left)
105 goto no_more_room;
107 strncpy (first_unused, NISENTRYVAL (0, 4, result),
108 NISENTRYLEN (0, 4, result));
109 first_unused[NISENTRYLEN (0, 4, result)] = '\0';
110 pw->pw_gecos = first_unused;
111 len = strlen (first_unused);
112 room_left -= (len + 1);
113 first_unused += (len + 1);
115 if (NISENTRYLEN (0, 5, result) >= room_left)
116 goto no_more_room;
118 strncpy (first_unused, NISENTRYVAL (0, 5, result),
119 NISENTRYLEN (0, 5, result));
120 first_unused[NISENTRYLEN (0, 5, result)] = '\0';
121 pw->pw_dir = first_unused;
122 len = strlen (first_unused);
123 room_left -= (len + 1);
124 first_unused += (len + 1);
126 if (NISENTRYLEN (0, 6, result) >= room_left)
127 goto no_more_room;
129 strncpy (first_unused, NISENTRYVAL (0, 6, result),
130 NISENTRYLEN (0, 6, result));
131 first_unused[NISENTRYLEN (0, 6, result)] = '\0';
132 pw->pw_shell = first_unused;
133 len = strlen (first_unused);
134 room_left -= (len + 1);
135 first_unused += (len + 1);
137 return 1;
142 _nss_nisplus_parse_grent (nis_result *result, u_long entry, struct group *gr,
143 char *buffer, size_t buflen, int *errnop)
145 char *first_unused = buffer;
146 size_t room_left = buflen;
147 char *line;
148 int count;
149 size_t len;
151 if (result == NULL)
152 return 0;
154 if ((result->status != NIS_SUCCESS && result->status != NIS_S_SUCCESS)
155 || __type_of(NIS_RES_OBJECT (result)) != NIS_ENTRY_OBJ
156 || strcmp (NIS_RES_OBJECT (result)[entry].EN_data.en_type,
157 "group_tbl") != 0
158 || NIS_RES_OBJECT (result)[entry].EN_data.en_cols.en_cols_len < 4)
159 return 0;
161 if (NISENTRYLEN (entry, 0, result) >= room_left)
163 /* The line is too long for our buffer. */
164 no_more_room:
165 *errnop = ERANGE;
166 return -1;
169 strncpy (first_unused, NISENTRYVAL (entry, 0, result),
170 NISENTRYLEN (entry, 0, result));
171 first_unused[NISENTRYLEN (entry, 0, result)] = '\0';
172 len = strlen (first_unused);
173 if (len == 0) /* group table is corrupt */
174 return 0;
175 gr->gr_name = first_unused;
176 room_left -= (len + 1);
177 first_unused += (len + 1);
179 if (NISENTRYLEN (entry, 1, result) >= room_left)
180 goto no_more_room;
182 strncpy (first_unused, NISENTRYVAL (entry, 1, result),
183 NISENTRYLEN (entry, 1, result));
184 first_unused[NISENTRYLEN (entry, 1, result)] = '\0';
185 gr->gr_passwd = first_unused;
186 len = strlen (first_unused);
187 room_left -= (len + 1);
188 first_unused += (len + 1);
190 if (NISENTRYLEN (entry, 2, result) >= room_left)
191 goto no_more_room;
193 strncpy (first_unused, NISENTRYVAL (entry, 2, result),
194 NISENTRYLEN (entry, 2, result));
195 first_unused[NISENTRYLEN (entry, 2, result)] = '\0';
196 len = strlen (first_unused);
197 if (len == 0) /* We should always have a gid */
198 return 0;
199 gr->gr_gid = strtoul (first_unused, NULL, 10);
201 if (NISENTRYLEN (entry, 3, result) >= room_left)
202 goto no_more_room;
204 strncpy (first_unused, NISENTRYVAL (entry, 3, result),
205 NISENTRYLEN (entry, 3, result));
206 first_unused[NISENTRYLEN (entry, 3, result)] = '\0';
207 line = first_unused;
208 len = strlen (line);
209 room_left -= (len + 1);
210 first_unused += (len + 1);
211 /* Adjust the pointer so it is aligned for
212 storing pointers. */
213 size_t adjust = ((__alignof__ (char *)
214 - (first_unused - (char *) 0) % __alignof__ (char *))
215 % __alignof__ (char *));
216 if (room_left < adjust)
217 goto no_more_room;
218 first_unused += adjust;
219 room_left -= adjust;
220 gr->gr_mem = (char **) first_unused;
222 count = 0;
223 while (*line != '\0')
225 /* Skip leading blanks. */
226 while (isspace (*line))
227 ++line;
229 if (*line == '\0')
230 break;
232 if (room_left < sizeof (char *))
233 goto no_more_room;
234 room_left -= sizeof (char *);
235 gr->gr_mem[count++] = line;
237 while (*line != '\0' && *line != ',' && !isspace (*line))
238 ++line;
240 if (*line == ',' || isspace (*line))
242 int is = isspace (*line);
244 *line++ = '\0';
245 if (is)
246 while (*line != '\0' && (*line == ',' || isspace (*line)))
247 ++line;
250 if (room_left < sizeof (char *))
251 goto no_more_room;
252 room_left -= sizeof (char *);
253 gr->gr_mem[count] = NULL;
255 return 1;
260 _nss_nisplus_parse_spent (nis_result *result, struct spwd *sp,
261 char *buffer, size_t buflen, int *errnop)
263 char *first_unused = buffer;
264 size_t room_left = buflen;
265 size_t len;
267 if (result == NULL)
268 return 0;
270 if ((result->status != NIS_SUCCESS && result->status != NIS_S_SUCCESS)
271 || NIS_RES_NUMOBJ (result) != 1
272 || __type_of(NIS_RES_OBJECT (result)) != NIS_ENTRY_OBJ
273 || strcmp (NIS_RES_OBJECT (result)->EN_data.en_type, "passwd_tbl") != 0
274 || NIS_RES_OBJECT (result)->EN_data.en_cols.en_cols_len < 8)
275 return 0;
277 if (NISENTRYLEN (0, 0, result) >= room_left)
279 /* The line is too long for our buffer. */
280 no_more_room:
281 *errnop = ERANGE;
282 return -1;
285 strncpy (first_unused, NISENTRYVAL (0, 0, result),
286 NISENTRYLEN (0, 0, result));
287 first_unused[NISENTRYLEN (0, 0, result)] = '\0';
288 len = strlen (first_unused);
289 if (len == 0)
290 return 0;
291 sp->sp_namp = first_unused;
292 room_left -= (len + 1);
293 first_unused += (len + 1);
295 if (NISENTRYLEN (0, 1, result) >= room_left)
296 goto no_more_room;
298 strncpy (first_unused, NISENTRYVAL (0, 1, result),
299 NISENTRYLEN (0, 1, result));
300 first_unused[NISENTRYLEN (0, 1, result)] = '\0';
301 sp->sp_pwdp = first_unused;
302 len = strlen (first_unused);
303 room_left -= (len + 1);
304 first_unused += (len + 1);
306 sp->sp_lstchg = sp->sp_min = sp->sp_max = sp->sp_warn = sp->sp_inact =
307 sp->sp_expire = -1;
308 sp->sp_flag = ~0ul;
310 if (NISENTRYLEN (0, 7, result) > 0)
312 char *line = NISENTRYVAL (0, 7, result);
313 char *cp = strchr (line, ':');
314 if (cp == NULL)
315 return 1;
316 *cp++ = '\0';
317 if (*line)
318 sp->sp_lstchg = atol (line);
320 line = cp;
321 cp = strchr (line, ':');
322 if (cp == NULL)
323 return 1;
324 *cp++ = '\0';
325 if (*line)
326 sp->sp_min = atol (line);
328 line = cp;
329 cp = strchr (line, ':');
330 if (cp == NULL)
331 return 1;
332 *cp++ = '\0';
333 if (*line)
334 sp->sp_max = atol (line);
336 line = cp;
337 cp = strchr (line, ':');
338 if (cp == NULL)
339 return 1;
340 *cp++ = '\0';
341 if (*line)
342 sp->sp_warn = atol (line);
344 line = cp;
345 cp = strchr (line, ':');
346 if (cp == NULL)
347 return 1;
348 *cp++ = '\0';
349 if (*line)
350 sp->sp_inact = atol (line);
352 line = cp;
353 cp = strchr (line, ':');
354 if (cp == NULL)
355 return 1;
356 *cp++ = '\0';
357 if (*line)
358 sp->sp_expire = atol (line);
360 line = cp;
361 if (line == NULL)
362 return 1;
363 if (*line)
364 sp->sp_flag = atol (line);
367 return 1;