Print this page
*** NO COMMENTS ***

Split Close
Expand all
Collapse all
          --- old/usr/src/cmd/ypcmd/revnetgroup/revnetgroup.c
          +++ new/usr/src/cmd/ypcmd/revnetgroup/revnetgroup.c
↓ open down ↓ 13 lines elided ↑ open up ↑
  14   14   * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15   15   * If applicable, add the following below this CDDL HEADER, with the
  16   16   * fields enclosed by brackets "[]" replaced with your own identifying
  17   17   * information: Portions Copyright [yyyy] [name of copyright owner]
  18   18   *
  19   19   * CDDL HEADER END
  20   20   */
  21   21  
  22   22  /*
  23   23   * Copyright (c) 1990, 2010, Oracle and/or its affiliates. All rights reserved.
       24 + * Copyright 2012 Nexenta Systems, Inc.  All rights reserved.
  24   25   */
  25   26  
  26   27  /*
  27   28   * For SUNWnskit - version 1.1
  28   29   */
  29   30  
  30   31  #include <stdlib.h>
  31   32  #include <unistd.h>
  32   33  #include <string.h>
  33   34  #include <stdio.h>
  34   35  #include <ctype.h>
  35   36  #include <pwd.h>
  36   37  #include <rpcsvc/ypclnt.h>
  37   38  #include "util.h"
  38   39  #include "table.h"
  39   40  #include "getgroup.h"
       41 +#include "revnetgroup.h"
  40   42  
  41   43  #define MAXDOMAINLEN 256
  42      -#define MAXGROUPLEN 1024
       44 +#define MAXGROUPLEN  131072
       45 +#define MAXKEYLEN    512
  43   46  
  44   47  /*
  45   48   * Reverse the netgroup file. A flag of "-u" means reverse by username,
  46   49   * one of "-h" means reverse by hostname. Each line in the output file
  47   50   * will begin with a key formed by concatenating the host or user name
  48   51   * with the domain name. The key will be followed by a tab, then the
  49   52   * comma-separated, newline-terminated list of groups to which the
  50   53   * user or host belongs.
  51   54   *
  52   55   * Exception: Groups to which everyone belongs (universal groups) will
  53   56   * not be included in the list.  The universal groups will be listed under
  54   57   * the special name "*".
  55   58   *
  56   59   * Thus to find out all the groups that user "foo" of domain "bar" is in,
  57   60   * lookup the groups under  foo.bar, foo.*, *.bar and *.*.
  58   61   *
  59   62   */
  60   63  
  61      -
  62      -
  63      -/* Stores a list of strings */
  64      -typedef struct stringnode *stringlist;
  65      -struct stringnode {
  66      -    char *str;
  67      -    stringlist next;
  68      -};
  69      -typedef struct stringnode stringnode;
  70      -
  71      -
  72      -
  73      -/* Stores a list of (name,list-of-groups) */
  74      -typedef struct groupentrynode *groupentrylist;
  75      -struct groupentrynode {
  76      -    char *name;
  77      -    stringlist groups;
  78      -    groupentrylist next;
  79      -};
  80      -typedef struct groupentrynode groupentrynode;
  81      -
  82      -stringtable ngtable;
  83      -
  84      -static groupentrylist grouptable[TABLESIZE];
  85      -
  86      -static char *nextgroup(void);
  87      -static void storegroup(char *group, struct grouplist *glist, int byuser);
  88      -static void enter(char *name, char *group);
       64 +static char *nextgroup(revhandle_t *, tablelist *);
       65 +static void storegroup(char *group, revhandle_t *hdl);
       66 +static void enter(char *name, char *group, revhandle_t *hdl);
  89   67  static void appendgroup(groupentrylist grlist, char *group);
  90   68  static groupentrylist newentry(char *name, char *group);
  91      -static void loadtable(FILE *nf);
  92      -static void dumptable(void);
       69 +static void loadtable(FILE *nf, revhandle_t *hdl);
       70 +static void dumptable(FILE *out, revhandle_t *hdl);
       71 +static void free_table(revhandle_t *hdl);
  93   72  
  94   73  int
  95      -main(argc, argv)
  96      -    int argc;
  97      -    char *argv[];
       74 +revnetgroup_handle(FILE *fin, FILE *fout, boolean_t byuser)
  98   75  {
  99   76          char *group;
 100      -        struct grouplist *glist;
 101      -        int byuser;
       77 +        revhandle_t hdl = {0};
       78 +        tablelist walker = NULL;
 102   79  
 103      -        loadtable(stdin);
 104      -        if (argc == 2 && argv[1][0] == '-' &&
 105      -                        (argv[1][1] == 'u' || argv[1][1] == 'h')) {
 106      -                byuser = (argv[1][1] == 'u');
 107      -        } else {
 108      -                (void) fprintf(stderr,
 109      -                                "usage: %s -h (by host), %s -u (by user)\n",
 110      -                                argv[0], argv[0]);
 111      -                exit(1);
 112      -        }
       80 +        hdl.rh_byuser = byuser;
       81 +        loadtable(fin, &hdl);
 113   82  
 114      -        while (group = nextgroup()) {
 115      -                glist = my_getgroup(group);
 116      -                storegroup(group, glist, byuser);
 117      -        }
 118      -        dumptable();
       83 +        while (group = nextgroup(&hdl, &walker))
       84 +                storegroup(group, &hdl);
 119   85  
       86 +        dumptable(fout, &hdl);
       87 +        free_table(&hdl);
 120   88          return (0);
 121   89  }
 122   90  
 123   91  /*
 124   92   *      Get the next netgroup from /etc/netgroup
 125   93   */
 126   94  static char *
 127      -nextgroup(void)
       95 +nextgroup(revhandle_t *hdl, tablelist *next)
 128   96  {
 129      -        static int index = -1;
 130      -        static tablelist cur = NULL;
 131      -        char *group;
       97 +        tablelist entry = *next;
       98 +        uint_t i;
 132   99  
 133      -        while (cur == NULL) {
 134      -                if (++index == TABLESIZE) {
 135      -                        return (NULL);
      100 +        if (entry == NULL) {
      101 +                for (i = hdl->rh_index; i < TABLESIZE; i++) {
      102 +                        entry = hdl->ngtable[i];
      103 +                        if (entry != NULL) {
      104 +                                hdl->rh_index = i + 1;
      105 +                                break;
      106 +                        }
 136  107                  }
 137      -                cur = ngtable[index];
 138  108          }
 139      -        group = cur->key;
 140      -        cur = cur->next;
 141      -        return (group);
      109 +
      110 +        if (entry == NULL) {
      111 +                /* out of table */
      112 +                hdl->rh_index = 0;
      113 +                return (NULL);
      114 +        }
      115 +
      116 +        *next = entry->next;
      117 +        return (entry->key);
 142  118  }
 143  119  
 144  120  
      121 +static void
      122 +free_tablelist(tablelist e)
      123 +{
      124 +        tablelist next;
 145  125  
      126 +        do {
      127 +                next = e->next;
      128 +
      129 +                free(e->key);
      130 +                free(e->datum);
      131 +                free(e);
      132 +        } while ((e = next) != NULL);
      133 +}
      134 +
      135 +static void
      136 +free_stringnode(stringnode *s)
      137 +{
      138 +        stringnode *next;
      139 +
      140 +        do {
      141 +                next = s->s_next;
      142 +
      143 +                free(s);
      144 +        } while ((s = next) != NULL);
      145 +}
      146 +
      147 +static void
      148 +free_groupentrylist(groupentrylist e)
      149 +{
      150 +        groupentrylist next;
      151 +
      152 +        do {
      153 +                next = e->next;
      154 +
      155 +                free_stringnode(e->groups);
      156 +                free(e->name);
      157 +                free(e);
      158 +        } while ((e = next) != NULL);
      159 +}
      160 +
      161 +static void
      162 +free_table(revhandle_t *hdl)
      163 +{
      164 +        int i;
      165 +
      166 +        /* ngtable */
      167 +        for (i = 0; i < TABLESIZE; i++) {
      168 +                tablelist e;
      169 +
      170 +                if ((e = hdl->ngtable[i]) == NULL)
      171 +                        continue;
      172 +
      173 +                free_tablelist(e);
      174 +                hdl->ngtable[i] = NULL;
      175 +        }
      176 +
      177 +        /* grouptable */
      178 +        for (i = 0; i < TABLESIZE; i++) {
      179 +                groupentrylist e;
      180 +
      181 +                if ((e = hdl->grouptable[i]) == NULL)
      182 +                        continue;
      183 +
      184 +                free_groupentrylist(e);
      185 +                hdl->grouptable[i] = NULL;
      186 +        }
      187 +}
      188 +
 146  189  /*
 147  190   * Dump out all of the stored info into a file
 148  191   */
 149  192  static void
 150      -dumptable(void)
      193 +dumptable(FILE *out, revhandle_t *hdl)
 151  194  {
 152  195          int i;
 153  196          groupentrylist entry;
 154      -        stringlist groups;
      197 +        stringnode *groups;
 155  198  
 156  199          for (i = 0; i < TABLESIZE; i++) {
 157      -                if (entry = grouptable[i]) {
      200 +                if (entry = hdl->grouptable[i]) {
 158  201                          while (entry) {
 159      -                                fputs(entry->name, stdout);
 160      -                                putc('\t', stdout);
      202 +                                fputs(entry->name, out);
      203 +                                putc('\t', out);
 161  204                                  for (groups = entry->groups; groups;
 162      -                                                groups = groups->next) {
 163      -                                        fputs(groups->str, stdout);
 164      -                                        if (groups->next) {
 165      -                                                putc(',', stdout);
      205 +                                    groups = groups->s_next) {
      206 +                                        fputs(groups->str, out);
      207 +                                        if (groups->s_next) {
      208 +                                                putc(',', out);
 166  209                                          }
 167  210                                  }
 168      -                                putc('\n', stdout);
      211 +                                putc('\n', out);
 169  212                                  entry = entry->next;
 170  213                          }
 171  214                  }
 172  215          }
 173  216  }
 174  217  
 175  218  
 176  219  
 177      -
 178  220  /*
 179  221   *      Add a netgroup to a user's list of netgroups
 180  222   */
 181  223  static void
 182      -storegroup(char *group, struct grouplist *glist, int byuser)
      224 +storegroup(char *group, revhandle_t *hdl)
 183  225  {
 184      -        char *name;     /* username or hostname */
 185      -        char *domain;
 186      -        char *key;
 187      -        static char *universal = "*";
      226 +        char key[MAXKEYLEN];
      227 +        struct grouplist *glist;
 188  228  
 189      -        for (; glist; glist = glist->gl_nxt) {
 190      -                name = byuser ? glist->gl_name : glist->gl_machine;
      229 +        doit(group, (struct list *)NULL, hdl);
      230 +
      231 +        for (glist = hdl->grouplist; glist; glist = glist->gl_nxt) {
      232 +                const char *name;       /* username or hostname */
      233 +                const char *domain;
      234 +
      235 +                name = hdl->rh_byuser ? glist->gl_name : glist->gl_machine;
 191  236                  if (!name) {
 192      -                    name = universal;
      237 +                        name = "*";
 193  238                  } else if (!isalnum(*name) && *name != '_') {
 194      -                    continue;
      239 +                        continue;
 195  240                  }
 196  241                  domain = glist->gl_domain;
 197  242                  if (!domain) {
 198      -                    domain = universal;
      243 +                        domain = "*";
 199  244                  }
 200      -                key = malloc((unsigned) (strlen(name)+strlen(domain)+2));
 201      -                (void) sprintf(key, "%s.%s", name, domain);
 202      -                enter(key, group);
      245 +                (void) snprintf(key, sizeof (key), "%s.%s", name, domain);
      246 +                enter(key, group, hdl);
 203  247          }
      248 +        freegrouplist(hdl);
 204  249  }
 205  250  
 206  251  
 207  252  
 208  253  static groupentrylist
 209  254  newentry(char *name, char *group)
 210  255  {
 211  256          groupentrylist new;
 212  257  
 213  258          new = MALLOC(groupentrynode);
 214  259  
 215  260          STRCPY(new->name, name);
 216  261  
 217  262          new->groups = MALLOC(stringnode);
 218  263          new->groups->str = group;
 219      -        new->groups->next = NULL;
      264 +        new->groups->s_next = NULL;
 220  265  
 221  266          new->next = NULL;
 222  267          return (new);
 223  268  }
 224  269  
 225  270  static void
 226  271  appendgroup(groupentrylist grlist, char *group)
 227  272  {
 228      -        stringlist cur, prev;
      273 +        stringnode *cur, *prev;
 229  274  
 230      -        for (cur = grlist->groups; cur; prev = cur, cur = cur->next) {
      275 +        for (cur = grlist->groups; cur; prev = cur, cur = cur->s_next) {
 231  276                  if (strcmp(group, cur->str) == 0) {
 232      -                    return;
      277 +                        return;
 233  278                  }
 234  279          }
 235      -        prev->next = MALLOC(stringnode);
 236      -        cur = prev->next;
      280 +        prev->s_next = MALLOC(stringnode);
      281 +        cur = prev->s_next;
 237  282          cur->str = group;
 238      -        cur->next = NULL;
      283 +        cur->s_next = NULL;
 239  284  }
 240  285  
 241  286  static void
 242      -enter(char *name, char *group)
      287 +enter(char *name, char *group, revhandle_t *hdl)
 243  288  {
 244  289          int key;
 245  290          groupentrylist gel;
 246  291          groupentrylist gelprev;
 247  292  
 248  293          key = tablekey(name);
 249      -        if (grouptable[key] == NULL) {
 250      -                grouptable[key] = newentry(name, group);
      294 +        if (hdl->grouptable[key] == NULL) {
      295 +                hdl->grouptable[key] = newentry(name, group);
 251  296          } else {
 252      -                gel = grouptable[key];
      297 +                gel = hdl->grouptable[key];
 253  298                  while (gel && strcmp(gel->name, name)) {
 254      -                    gelprev = gel;
 255      -                    gel = gel->next;
      299 +                        gelprev = gel;
      300 +                        gel = gel->next;
 256  301                  }
 257  302                  if (gel) {
 258      -                    appendgroup(gel, group);
      303 +                        appendgroup(gel, group);
 259  304                  } else {
 260      -                    gelprev->next = newentry(name, group);
      305 +                        gelprev->next = newentry(name, group);
 261  306                  }
 262  307          }
 263  308  }
 264  309  
 265  310  /*
 266  311   * Load up a hash table with the info in /etc/netgroup
 267  312   */
 268  313  static void
 269      -loadtable(FILE *nf)
      314 +loadtable(FILE *nf, revhandle_t *hdl)
 270  315  {
 271      -        char buf[MAXGROUPLEN];
      316 +        char *buf;
 272  317          char *p;
 273  318          char *group;
 274  319          char *line;
 275  320  
      321 +        buf = malloc(MAXGROUPLEN);
      322 +        if (buf == NULL)
      323 +                return;
      324 +
 276  325          while (getaline(buf, MAXGROUPLEN, nf)) {
      326 +                /* skip leading blanks */
 277  327                  for (p = buf; *p && isspace((int)*p); p++)
 278      -                        ;       /* skip leading blanks */
      328 +                        ;
 279  329                  for (; *p && *p != '#' && *p != ' ' && *p != '\t'; p++)
 280  330                          ;
 281  331                  if (*p == EOS || *p == '#')
 282  332                          continue;
 283  333                  *p++ = EOS;
 284  334  
 285  335                  while (*p == ' ' || *p == '\t') {
 286  336                          p++;
 287  337                  }
 288  338                  if (*p == EOS || *p == '#')
 289  339                          continue;
 290  340  
 291  341                  STRCPY(group, buf);
 292  342                  STRCPY(line, p);
 293      -                store(ngtable, group, line);
      343 +                store(hdl->ngtable, group, line);
 294  344          }
      345 +
      346 +        free(buf);
 295  347  }
    
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX