From bafa15955d1c0c9e892615afa7fff2476302c7a5 Mon Sep 17 00:00:00 2001 From: Peter Stephenson Date: Mon, 9 May 2011 10:38:02 +0000 Subject: 29195: Separate nameddir hash to avoid clash of "bool" type on Solaris --- Src/.distfiles | 62 +++++++++-- Src/hashnameddir.c | 307 +++++++++++++++++++++++++++++++++++++++++++++++++++++ Src/hashtable.c | 266 ---------------------------------------------- Src/system.h | 2 +- Src/zsh.mdd | 2 +- 5 files changed, 360 insertions(+), 279 deletions(-) create mode 100644 Src/hashnameddir.c (limited to 'Src') diff --git a/Src/.distfiles b/Src/.distfiles index 1b0bc4ec7..9c1859080 100644 --- a/Src/.distfiles +++ b/Src/.distfiles @@ -1,13 +1,53 @@ DISTFILES_SRC=' - .cvsignore .distfiles .exrc .indent.pro - Makefile.in Makemod.in.in - signames1.awk signames2.awk - modentry.c - builtin.c compat.c cond.c exec.c glob.c hashtable.c hashtable.h - hist.c init.c input.c jobs.c lex.c linklist.c loop.c main.c makepro.awk - math.c mem.c mkbltnmlst.sh mkmakemod.sh - module.c options.c params.c parse.c pattern.c prompt.c prototypes.h - signals.c signals.h sort.c string.c subst.c system.h text.c utils.c - watch.c zsh.h zsh.mdd ztype.h - zsh.rc zsh.ico +.cvsignore +.distfiles +.exrc +.indent.pro +Makefile.in +Makemod.in.in +signames1.awk +signames2.awk +modentry.c +builtin.c +compat.c +cond.c +exec.c +glob.c +hashtable.c +hashtable.h +hashnameddir.c +hist.c +init.c +input.c +jobs.c +lex.c +linklist.c +loop.c +main.c +makepro.awk +math.c +mem.c +mkbltnmlst.sh +mkmakemod.sh +module.c +options.c +params.c +parse.c +pattern.c +prompt.c +prototypes.h +signals.c +signals.h +sort.c +string.c +subst.c +system.h +text.c +utils.c +watch.c +zsh.h +zsh.mdd +ztype.h +zsh.rc +zsh.ico ' diff --git a/Src/hashnameddir.c b/Src/hashnameddir.c new file mode 100644 index 000000000..bed43d025 --- /dev/null +++ b/Src/hashnameddir.c @@ -0,0 +1,307 @@ +/* + * hashtable.c - hash tables + * + * This file is part of zsh, the Z shell. + * + * Copyright (c) 1992-1997 Paul Falstad + * All rights reserved. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and to distribute modified versions of this software for any + * purpose, provided that the above copyright notice and the following + * two paragraphs appear in all copies of this software. + * + * In no event shall Paul Falstad or the Zsh Development Group be liable + * to any party for direct, indirect, special, incidental, or consequential + * damages arising out of the use of this software and its documentation, + * even if Paul Falstad and the Zsh Development Group have been advised of + * the possibility of such damage. + * + * Paul Falstad and the Zsh Development Group specifically disclaim any + * warranties, including, but not limited to, the implied warranties of + * merchantability and fitness for a particular purpose. The software + * provided hereunder is on an "as is" basis, and Paul Falstad and the + * Zsh Development Group have no obligation to provide maintenance, + * support, updates, enhancements, or modifications. + * + */ + +#include "../config.h" + +/* + * On Solaris 8 there's a clash between "bool" in curses and RPC. + * We don't need curses here, so ensure it doesn't get included. + */ +#define ZSH_NO_TERM_HANDLING + +#include "zsh.mdh" +#include "hashnameddir.pro" + +/****************************************/ +/* Named Directory Hash Table Functions */ +/****************************************/ + +#ifdef HAVE_NIS_PLUS +# include +#else +# ifdef HAVE_NIS +# include +# include +# include +# include +# endif +#endif + +/* hash table containing named directories */ + +/**/ +mod_export HashTable nameddirtab; + +/* != 0 if all the usernames have already been * + * added to the named directory hash table. */ + +static int allusersadded; + +/* Create new hash table for named directories */ + +/**/ +void +createnameddirtable(void) +{ + nameddirtab = newhashtable(201, "nameddirtab", NULL); + + nameddirtab->hash = hasher; + nameddirtab->emptytable = emptynameddirtable; + nameddirtab->filltable = fillnameddirtable; + nameddirtab->cmpnodes = strcmp; + nameddirtab->addnode = addnameddirnode; + nameddirtab->getnode = gethashnode; + nameddirtab->getnode2 = gethashnode2; + nameddirtab->removenode = removenameddirnode; + nameddirtab->disablenode = NULL; + nameddirtab->enablenode = NULL; + nameddirtab->freenode = freenameddirnode; + nameddirtab->printnode = printnameddirnode; + + allusersadded = 0; + finddir(NULL); /* clear the finddir cache */ +} + +/* Empty the named directories table */ + +/**/ +static void +emptynameddirtable(HashTable ht) +{ + emptyhashtable(ht); + allusersadded = 0; + finddir(NULL); /* clear the finddir cache */ +} + +/* Add all the usernames in the password file/database * + * to the named directories table. */ + +#ifdef HAVE_NIS_PLUS +static int +add_userdir(nis_name table, nis_object *object, void *userdata) +{ + if (object->zo_data.objdata_u.en_data.en_cols.en_cols_len >= 6) { + static char name[40], dir[PATH_MAX + 1]; + register entry_col *ec = + object->zo_data.objdata_u.en_data.en_cols.en_cols_val; + register int nl = minimum(ec[0].ec_value.ec_value_len, 39); + register int dl = minimum(ec[5].ec_value.ec_value_len, PATH_MAX); + + memcpy(name, ec[0].ec_value.ec_value_val, nl); + name[nl] = '\0'; + memcpy(dir, ec[5].ec_value.ec_value_val, dl); + dir[dl] = '\0'; + + adduserdir(name, dir, ND_USERNAME, 1); + } + return 0; +} +#else +# ifdef HAVE_NIS +static int +add_userdir(int status, char *key, int keylen, char *val, int vallen, char *dummy) +{ + char *p, *d, *de; + + if (status != YP_TRUE) + return 1; + + if (vallen > keylen && *(p = val + keylen) == ':') { + *p++ = '\0'; + for (de = val + vallen - 1; *de != ':' && de > val; de--); + if (de > val) { + *de = '\0'; + if ((d = strrchr(p, ':'))) { + if (*++d && val[0]) + adduserdir(val, d, ND_USERNAME, 1); + } + } + } + return 0; +} +# endif /* HAVE_NIS */ +#endif /* HAVE_NIS_PLUS */ + +/**/ +static void +fillnameddirtable(UNUSED(HashTable ht)) +{ + if (!allusersadded) { +#if defined(HAVE_NIS) || defined(HAVE_NIS_PLUS) + FILE *pwf; + char buf[BUFSIZ], *p, *d, *de; + int skipping, oldct = nameddirtab->ct, usepwf = 1; + +# ifndef HAVE_NIS_PLUS + char domain[YPMAXDOMAIN]; + struct ypall_callback cb; + + /* Get potential matches from NIS and cull those without local accounts */ + if (getdomainname(domain, YPMAXDOMAIN) == 0) { + cb.foreach = (int (*)()) add_userdir; + cb.data = NULL; + yp_all(domain, PASSWD_MAP, &cb); + } +# else /* HAVE_NIS_PLUS */ + /* Maybe we should turn this string into a #define'd constant...? */ + + nis_list("passwd.org_dir", EXPAND_NAME|ALL_RESULTS|FOLLOW_LINKS|FOLLOW_PATH, + add_userdir, 0); +# endif + if (nameddirtab->ct == oldct) { + /* Using NIS or NIS+ didn't add any user directories. This seems + * fishy, so we fall back to using getpwent(). If we don't have + * that, we only use the passwd file. */ +#ifdef HAVE_GETPWENT + struct passwd *pw; + + setpwent(); + + /* loop through the password file/database * + * and add all entries returned. */ + while ((pw = getpwent()) && !errflag) + adduserdir(pw->pw_name, pw->pw_dir, ND_USERNAME, 1); + + endpwent(); + usepwf = 0; +#endif /* HAVE_GETPWENT */ + } + if (usepwf) { + /* Don't forget the non-NIS matches from the flat passwd file */ + if ((pwf = fopen(PASSWD_FILE, "r")) != NULL) { + skipping = 0; + while (fgets(buf, BUFSIZ, pwf) != NULL) { + if (strchr(buf, '\n') != NULL) { + if (!skipping) { + if ((p = strchr(buf, ':')) != NULL) { + *p++ = '\0'; + if ((de = strrchr(p, ':'))) { + *de = '\0'; + if ((d = strrchr(p, ':'))) { + if (*++d && buf[0]) + adduserdir(buf, d, ND_USERNAME, 1); + } + } + } + } else + skipping = 0; + } else + skipping = 1; + } + fclose(pwf); + } + } +#else /* no NIS or NIS_PLUS */ +#ifdef USE_GETPWENT + struct passwd *pw; + + setpwent(); + + /* loop through the password file/database * + * and add all entries returned. */ + while ((pw = getpwent()) && !errflag) + adduserdir(pw->pw_name, pw->pw_dir, ND_USERNAME, 1); + + endpwent(); +#endif /* HAVE_GETPWENT */ +#endif + allusersadded = 1; + } +} + +/* Add an entry to the named directory hash * + * table, clearing the finddir() cache and * + * initialising the `diff' member. */ + +/**/ +static void +addnameddirnode(HashTable ht, char *nam, void *nodeptr) +{ + Nameddir nd = (Nameddir) nodeptr; + + nd->diff = strlen(nd->dir) - strlen(nam); + finddir(NULL); /* clear the finddir cache */ + addhashnode(ht, nam, nodeptr); +} + +/* Remove an entry from the named directory * + * hash table, clearing the finddir() cache. */ + +/**/ +static HashNode +removenameddirnode(HashTable ht, const char *nam) +{ + HashNode hn = removehashnode(ht, nam); + + if(hn) + finddir(NULL); /* clear the finddir cache */ + return hn; +} + +/* Free up the memory used by a named directory hash node. */ + +/**/ +static void +freenameddirnode(HashNode hn) +{ + Nameddir nd = (Nameddir) hn; + + zsfree(nd->node.nam); + zsfree(nd->dir); + zfree(nd, sizeof(struct nameddir)); +} + +/* Print a named directory */ + +/**/ +static void +printnameddirnode(HashNode hn, int printflags) +{ + Nameddir nd = (Nameddir) hn; + + if (printflags & PRINT_NAMEONLY) { + zputs(nd->node.nam, stdout); + putchar('\n'); + return; + } + + if (printflags & PRINT_LIST) { + printf("hash -d "); + + if(nd->node.nam[0] == '-') + printf("-- "); + } + + quotedzputs(nd->node.nam, stdout); + putchar('='); + quotedzputs(nd->dir, stdout); + putchar('\n'); +} + +#include "../config.h" diff --git a/Src/hashtable.c b/Src/hashtable.c index 235beda1c..6fca256e3 100644 --- a/Src/hashtable.c +++ b/Src/hashtable.c @@ -1196,272 +1196,6 @@ printaliasnode(HashNode hn, int printflags) putchar('\n'); } -/****************************************/ -/* Named Directory Hash Table Functions */ -/****************************************/ - -#ifdef HAVE_NIS_PLUS -# include -#else -# ifdef HAVE_NIS -# include -# include -# include -# include -# endif -#endif - -/* hash table containing named directories */ - -/**/ -mod_export HashTable nameddirtab; - -/* != 0 if all the usernames have already been * - * added to the named directory hash table. */ - -static int allusersadded; - -/* Create new hash table for named directories */ - -/**/ -void -createnameddirtable(void) -{ - nameddirtab = newhashtable(201, "nameddirtab", NULL); - - nameddirtab->hash = hasher; - nameddirtab->emptytable = emptynameddirtable; - nameddirtab->filltable = fillnameddirtable; - nameddirtab->cmpnodes = strcmp; - nameddirtab->addnode = addnameddirnode; - nameddirtab->getnode = gethashnode; - nameddirtab->getnode2 = gethashnode2; - nameddirtab->removenode = removenameddirnode; - nameddirtab->disablenode = NULL; - nameddirtab->enablenode = NULL; - nameddirtab->freenode = freenameddirnode; - nameddirtab->printnode = printnameddirnode; - - allusersadded = 0; - finddir(NULL); /* clear the finddir cache */ -} - -/* Empty the named directories table */ - -/**/ -static void -emptynameddirtable(HashTable ht) -{ - emptyhashtable(ht); - allusersadded = 0; - finddir(NULL); /* clear the finddir cache */ -} - -/* Add all the usernames in the password file/database * - * to the named directories table. */ - -#ifdef HAVE_NIS_PLUS -static int -add_userdir(nis_name table, nis_object *object, void *userdata) -{ - if (object->zo_data.objdata_u.en_data.en_cols.en_cols_len >= 6) { - static char name[40], dir[PATH_MAX + 1]; - register entry_col *ec = - object->zo_data.objdata_u.en_data.en_cols.en_cols_val; - register int nl = minimum(ec[0].ec_value.ec_value_len, 39); - register int dl = minimum(ec[5].ec_value.ec_value_len, PATH_MAX); - - memcpy(name, ec[0].ec_value.ec_value_val, nl); - name[nl] = '\0'; - memcpy(dir, ec[5].ec_value.ec_value_val, dl); - dir[dl] = '\0'; - - adduserdir(name, dir, ND_USERNAME, 1); - } - return 0; -} -#else -# ifdef HAVE_NIS -static int -add_userdir(int status, char *key, int keylen, char *val, int vallen, char *dummy) -{ - char *p, *d, *de; - - if (status != YP_TRUE) - return 1; - - if (vallen > keylen && *(p = val + keylen) == ':') { - *p++ = '\0'; - for (de = val + vallen - 1; *de != ':' && de > val; de--); - if (de > val) { - *de = '\0'; - if ((d = strrchr(p, ':'))) { - if (*++d && val[0]) - adduserdir(val, d, ND_USERNAME, 1); - } - } - } - return 0; -} -# endif /* HAVE_NIS */ -#endif /* HAVE_NIS_PLUS */ - -/**/ -static void -fillnameddirtable(UNUSED(HashTable ht)) -{ - if (!allusersadded) { -#if defined(HAVE_NIS) || defined(HAVE_NIS_PLUS) - FILE *pwf; - char buf[BUFSIZ], *p, *d, *de; - int skipping, oldct = nameddirtab->ct, usepwf = 1; - -# ifndef HAVE_NIS_PLUS - char domain[YPMAXDOMAIN]; - struct ypall_callback cb; - - /* Get potential matches from NIS and cull those without local accounts */ - if (getdomainname(domain, YPMAXDOMAIN) == 0) { - cb.foreach = (int (*)()) add_userdir; - cb.data = NULL; - yp_all(domain, PASSWD_MAP, &cb); - } -# else /* HAVE_NIS_PLUS */ - /* Maybe we should turn this string into a #define'd constant...? */ - - nis_list("passwd.org_dir", EXPAND_NAME|ALL_RESULTS|FOLLOW_LINKS|FOLLOW_PATH, - add_userdir, 0); -# endif - if (nameddirtab->ct == oldct) { - /* Using NIS or NIS+ didn't add any user directories. This seems - * fishy, so we fall back to using getpwent(). If we don't have - * that, we only use the passwd file. */ -#ifdef HAVE_GETPWENT - struct passwd *pw; - - setpwent(); - - /* loop through the password file/database * - * and add all entries returned. */ - while ((pw = getpwent()) && !errflag) - adduserdir(pw->pw_name, pw->pw_dir, ND_USERNAME, 1); - - endpwent(); - usepwf = 0; -#endif /* HAVE_GETPWENT */ - } - if (usepwf) { - /* Don't forget the non-NIS matches from the flat passwd file */ - if ((pwf = fopen(PASSWD_FILE, "r")) != NULL) { - skipping = 0; - while (fgets(buf, BUFSIZ, pwf) != NULL) { - if (strchr(buf, '\n') != NULL) { - if (!skipping) { - if ((p = strchr(buf, ':')) != NULL) { - *p++ = '\0'; - if ((de = strrchr(p, ':'))) { - *de = '\0'; - if ((d = strrchr(p, ':'))) { - if (*++d && buf[0]) - adduserdir(buf, d, ND_USERNAME, 1); - } - } - } - } else - skipping = 0; - } else - skipping = 1; - } - fclose(pwf); - } - } -#else /* no NIS or NIS_PLUS */ -#ifdef USE_GETPWENT - struct passwd *pw; - - setpwent(); - - /* loop through the password file/database * - * and add all entries returned. */ - while ((pw = getpwent()) && !errflag) - adduserdir(pw->pw_name, pw->pw_dir, ND_USERNAME, 1); - - endpwent(); -#endif /* HAVE_GETPWENT */ -#endif - allusersadded = 1; - } -} - -/* Add an entry to the named directory hash * - * table, clearing the finddir() cache and * - * initialising the `diff' member. */ - -/**/ -static void -addnameddirnode(HashTable ht, char *nam, void *nodeptr) -{ - Nameddir nd = (Nameddir) nodeptr; - - nd->diff = strlen(nd->dir) - strlen(nam); - finddir(NULL); /* clear the finddir cache */ - addhashnode(ht, nam, nodeptr); -} - -/* Remove an entry from the named directory * - * hash table, clearing the finddir() cache. */ - -/**/ -static HashNode -removenameddirnode(HashTable ht, const char *nam) -{ - HashNode hn = removehashnode(ht, nam); - - if(hn) - finddir(NULL); /* clear the finddir cache */ - return hn; -} - -/* Free up the memory used by a named directory hash node. */ - -/**/ -static void -freenameddirnode(HashNode hn) -{ - Nameddir nd = (Nameddir) hn; - - zsfree(nd->node.nam); - zsfree(nd->dir); - zfree(nd, sizeof(struct nameddir)); -} - -/* Print a named directory */ - -/**/ -static void -printnameddirnode(HashNode hn, int printflags) -{ - Nameddir nd = (Nameddir) hn; - - if (printflags & PRINT_NAMEONLY) { - zputs(nd->node.nam, stdout); - putchar('\n'); - return; - } - - if (printflags & PRINT_LIST) { - printf("hash -d "); - - if(nd->node.nam[0] == '-') - printf("-- "); - } - - quotedzputs(nd->node.nam, stdout); - putchar('='); - quotedzputs(nd->dir, stdout); - putchar('\n'); -} - /*************************************/ /* History Line Hash Table Functions */ /*************************************/ diff --git a/Src/system.h b/Src/system.h index 01c6738ca..f38533023 100644 --- a/Src/system.h +++ b/Src/system.h @@ -851,7 +851,7 @@ extern short ospeed; # define GET_ST_CTIME_NSEC(st) (st).st_ctimensec #endif -#ifdef HAVE_TGETENT +#if defined(HAVE_TGETENT) && !defined(ZSH_NO_TERM_HANDLING) # if defined(ZSH_HAVE_CURSES_H) && defined(ZSH_HAVE_TERM_H) # define USES_TERM_H 1 # else diff --git a/Src/zsh.mdd b/Src/zsh.mdd index 9f19b45da..25f4df10f 100644 --- a/Src/zsh.mdd +++ b/Src/zsh.mdd @@ -9,7 +9,7 @@ alwayslink=1 # autobins not specified because of alwayslink -objects="builtin.o compat.o cond.o exec.o glob.o hashtable.o \ +objects="builtin.o compat.o cond.o exec.o glob.o hashtable.o hashnameddir.o \ hist.o init.o input.o jobs.o lex.o linklist.o loop.o math.o \ mem.o module.o options.o params.o parse.o pattern.o prompt.o signals.o \ signames.o sort.o string.o subst.o text.o utils.o watch.o" -- cgit 1.4.1