diff options
-rw-r--r-- | ChangeLog | 16 | ||||
-rw-r--r-- | nis/nis_call.c | 46 | ||||
-rw-r--r-- | nis/nis_lookup.c | 7 | ||||
-rw-r--r-- | nis/nis_table.c | 3 | ||||
-rw-r--r-- | nis/rpcsvc/nislib.h | 5 |
5 files changed, 56 insertions, 21 deletions
@@ -1,3 +1,19 @@ +2006-08-07 Ulrich Drepper <drepper@redhat.com> + + * nis/nis_call.c: Minor cleanups throughout. + (rec_dirsearch) [HIGHER_NAME]: Correctly size ndomain array. + (first_shoot): Add search_parent_first parameter. Only if it is set + search parent server first. + If directory for table found through cold start cache is not the same + as referenced in the cache, don't use it. + (__nisfind_server): Take additional parameter. Pass it on to + first_shoot. + (__prepare_niscall): Adjust __nisfind_server call. + * nis/rpcsvc/nislib.h: Adjust __nisfind_server prototype. + * nis/nis_table.c: Adjust __nisfind_server call. + * nis/nis_lookup.c: Likewise. + (nis_lookup): Don't loop endlessly if name is reduced to ".". + 2006-08-03 Ulrich Drepper <drepper@redhat.com> [BZ #2182] diff --git a/nis/nis_call.c b/nis/nis_call.c index f8f00d8c82..bad1f776a1 100644 --- a/nis/nis_call.c +++ b/nis/nis_call.c @@ -38,12 +38,12 @@ static const struct timeval UDPTIMEOUT = {5, 0}; extern u_short __pmap_getnisport (struct sockaddr_in *address, u_long program, u_long version, u_int protocol); -unsigned long +unsigned long int inetstr2int (const char *str) { size_t j = 0; for (size_t i = 0; str[i] != '\0'; ++i) - if (str[i] == '.' && ++j == 4) + if (str[i] == '.' && __builtin_expect (++j == 4, 0)) { char buffer[i + 1]; buffer[i] = '\0'; @@ -68,8 +68,6 @@ libnsl_hidden_def (__nisbind_destroy) nis_error __nisbind_next (dir_binding *bind) { - u_int j; - if (bind->clnt != NULL) { if (bind->use_auth) @@ -81,7 +79,7 @@ __nisbind_next (dir_binding *bind) if (bind->trys >= bind->server_len) return NIS_FAIL; - for (j = bind->current_ep + 1; + for (u_int j = bind->current_ep + 1; j < bind->server_val[bind->server_used].ep.ep_len; ++j) if (strcmp (bind->server_val[bind->server_used].ep.ep_val[j].family, "inet") == 0) @@ -96,7 +94,7 @@ __nisbind_next (dir_binding *bind) if (bind->server_used >= bind->server_len) bind->server_used = 0; - for (j = 0; j < bind->server_val[bind->server_used].ep.ep_len; ++j) + for (u_int j = 0; j < bind->server_val[bind->server_used].ep.ep_len; ++j) if (strcmp (bind->server_val[bind->server_used].ep.ep_val[j].family, "inet") == 0) if (bind->server_val[bind->server_used].ep.ep_val[j].proto[0] == '-') @@ -125,7 +123,7 @@ __nisbind_connect (dir_binding *dbp) dbp->addr.sin_addr.s_addr = inetstr2int (serv->ep.ep_val[dbp->current_ep].uaddr); - if (dbp->addr.sin_addr.s_addr == 0) + if (dbp->addr.sin_addr.s_addr == INADDR_NONE) return NIS_FAIL; /* Check, if the host is online and rpc.nisd is running. Much faster @@ -340,7 +338,7 @@ rec_dirsearch (const_nis_name name, directory_obj *dir, nis_error *status) case HIGHER_NAME: { /* We need data from a parent domain */ directory_obj *obj; - char ndomain [strlen (name) + 3]; + char ndomain[strlen (dir->do_name) + 3]; nis_domain_of_r (dir->do_name, ndomain, sizeof (ndomain)); @@ -461,31 +459,44 @@ rec_dirsearch (const_nis_name name, directory_obj *dir, nis_error *status) /* We try to query the current server for the searched object, maybe he know about it ? */ static directory_obj * -first_shoot (const_nis_name name, directory_obj *dir) +first_shoot (const_nis_name name, int search_parent_first, directory_obj *dir) { directory_obj *obj = NULL; fd_result *fd_res; XDR xdrs; char domain[strlen (name) + 3]; +#if 0 if (nis_dir_cmp (name, dir->do_name) == SAME_NAME) return dir; +#endif - nis_domain_of_r (name, domain, sizeof (domain)); + const char *search_name = name; + if (search_parent_first) + { + nis_domain_of_r (name, domain, sizeof (domain)); + search_name = domain; + } - if (nis_dir_cmp (domain, dir->do_name) == SAME_NAME) + if (nis_dir_cmp (search_name, dir->do_name) == SAME_NAME) return dir; - fd_res = __nis_finddirectory (dir, domain); + fd_res = __nis_finddirectory (dir, search_name); if (fd_res == NULL) return NULL; if (fd_res->status == NIS_SUCCESS && (obj = calloc (1, sizeof (directory_obj))) != NULL) { - xdrmem_create(&xdrs, fd_res->dir_data.dir_data_val, - fd_res->dir_data.dir_data_len, XDR_DECODE); + xdrmem_create (&xdrs, fd_res->dir_data.dir_data_val, + fd_res->dir_data.dir_data_len, XDR_DECODE); _xdr_directory_obj (&xdrs, obj); xdr_destroy (&xdrs); + + if (strcmp (dir->do_name, obj->do_name) != 0) + { + nis_free_directory (obj); + obj = NULL; + } } __free_fdresult (fd_res); @@ -497,7 +508,8 @@ first_shoot (const_nis_name name, directory_obj *dir) } nis_error -__nisfind_server (const_nis_name name, directory_obj **dir) +__nisfind_server (const_nis_name name, int search_parent_first, + directory_obj **dir) { if (name == NULL) return NIS_BADNAME; @@ -520,7 +532,7 @@ __nisfind_server (const_nis_name name, directory_obj **dir) return NIS_UNAVAIL; /* Try at first, if servers in "dir" know our object */ - obj = first_shoot (name, *dir); + obj = first_shoot (name, search_parent_first, *dir); if (obj == NULL) { obj = rec_dirsearch (name, *dir, &status); @@ -539,7 +551,7 @@ nis_error __prepare_niscall (const_nis_name name, directory_obj **dirp, dir_binding *bptrp, unsigned int flags) { - nis_error retcode = __nisfind_server (name, dirp); + nis_error retcode = __nisfind_server (name, 1, dirp); if (__builtin_expect (retcode != NIS_SUCCESS, 0)) return retcode; diff --git a/nis/nis_lookup.c b/nis/nis_lookup.c index c198376464..839ee4ee42 100644 --- a/nis/nis_lookup.c +++ b/nis/nis_lookup.c @@ -127,7 +127,7 @@ nis_lookup (const_nis_name name, const unsigned int flags) /* Otherwise __nisfind_server will not do anything. */ dir = NULL; - if (__nisfind_server (req.ns_name, &dir) + if (__nisfind_server (req.ns_name, 1, &dir) != NIS_SUCCESS) goto out; @@ -147,6 +147,11 @@ nis_lookup (const_nis_name name, const unsigned int flags) nis_domain_of_r (req.ns_name, ndomain, sizeof (ndomain)); req.ns_name = strdupa (ndomain); + if (strcmp (ndomain, ".") == 0) + { + NIS_RES_STATUS (res) = NIS_NAMEUNREACHABLE; + goto out; + } __nisbind_destroy (&bptr); nis_free_directory (dir); diff --git a/nis/nis_table.c b/nis/nis_table.c index 3213035067..a92a4b64ce 100644 --- a/nis/nis_table.c +++ b/nis/nis_table.c @@ -271,7 +271,8 @@ nis_list (const_nis_name name, unsigned int flags, memset (res, '\0', sizeof (nis_result)); - status = __nisfind_server (ibreq->ibr_name, &dir); + status = __nisfind_server (ibreq->ibr_name, + ibreq->ibr_srch.ibr_srch_val != NULL, &dir); if (status != NIS_SUCCESS) { NIS_RES_STATUS (res) = status; diff --git a/nis/rpcsvc/nislib.h b/nis/rpcsvc/nislib.h index a55de61830..c993bac5e8 100644 --- a/nis/rpcsvc/nislib.h +++ b/nis/rpcsvc/nislib.h @@ -1,4 +1,4 @@ -/* Copyright (C) 1997, 1998, 1999 Free Software Foundation, Inc. +/* Copyright (C) 1997, 1998, 1999, 2006 Free Software Foundation, Inc. This file is part of the GNU C Library. Contributed by Thorsten Kukuk <kukuk@suse.de>, 1997. @@ -276,7 +276,8 @@ extern nis_error __nisbind_create (dir_binding *, const nis_server *, extern nis_error __nisbind_connect (dir_binding *) __THROW; extern nis_error __nisbind_next (dir_binding *) __THROW; extern void __nisbind_destroy (dir_binding *) __THROW; -extern nis_error __nisfind_server (const_nis_name, directory_obj **) __THROW; +extern nis_error __nisfind_server (const_nis_name, int, directory_obj **) + __THROW; #endif |