]> andersk Git - moira.git/blobdiff - gen/mailhub.pc
Command line printer manipulation client, and build goo.
[moira.git] / gen / mailhub.pc
index 4247f8dbe32c6c87b24705ef53b2e2cadac310e0..2d075aaa6097601c349acd250bc985166fd132cd 100644 (file)
@@ -1,64 +1,81 @@
-
-/* $Header$
+/* $Id$
  *
  * This generates the /usr/lib/aliases file for the mailhub.
  *
- *  (c) Copyright 1988, 1990 by the Massachusetts Institute of Technology.
- *  For copying and distribution information, please see the file
- *  <mit-copyright.h>.
+ * (c) Copyright 1988-1998 by the Massachusetts Institute of Technology.
+ * For copying and distribution information, please see the file
+ * <mit-copyright.h>.
  */
 
 #include <mit-copyright.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <ctype.h>
-#include <errno.h>
 #include <moira.h>
 #include <moira_site.h>
-#include <sys/types.h>
+
 #include <sys/stat.h>
-#include <sys/time.h>
+
+#include <ctype.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "util.h"
+
 EXEC SQL INCLUDE sqlca;
 
+RCSID("$Header$");
+
 char *whoami = "mailhub.gen";
 char *db = "moira/moira";
-char *perm_malloc();
-char *pstrsave();
 char *divide = "##############################################################";
 
-#define ML_WID 72
-#define AL_MAX_WID 592
+#define MAX_LINE_WIDTH 72
+#define MAX_ALIAS_WIDTH 592
 
 #define FALSE 0
 #define TRUE (!FALSE)
 
 FILE *out = stdout;
 
+struct hash *users, *machines, *strings, *lists;
+struct user {
+  char *login;
+  char *pobox;
+};
+struct member {
+  struct member *next;
+  char *name;
+  int list_id;
+};
+struct list {
+  char *name;
+  char maillist;
+  char *description;
+  char acl_t;
+  int acl_id;
+  char mailman;
+  char *mailman_server;
+  struct member *m;
+};
+
+void get_info(void);
+void save_mlist(int id, void *list, void *force);
+int check_string(char *s);
+void output_login(int dummy, void *names, void *out);
+void output_mlist(int id, struct list *l);
+void put_fill(FILE *aliases, char *string);
+void do_people(void);
+
+int incount = 0;
+
 int main(int argc, char **argv)
 {
-  long tm = time(NULL);
-  char filename[64], *targetfile;
-  struct stat sb;
-  EXEC SQL BEGIN DECLARE SECTION;
-  int flag;
-  EXEC SQL END DECLARE SECTION;
+  time_t tm = time(NULL);
+  char filename[MAXPATHLEN], *targetfile;
 
   EXEC SQL CONNECT :db;
 
   if (argc == 2)
     {
-      if (stat(argv[1], &sb) == 0)
-       {
-         if (ModDiff (&flag, "users", sb.st_mtime))
-           exit(MR_DATE);
-         if (flag < 0)
-           {
-             fprintf(stderr, "File %s does not need to be rebuilt.\n",
-                     argv[1]);
-             exit(MR_NO_CHANGE);
-           }
-       }
       targetfile = argv[1];
       sprintf(filename, "%s~", targetfile);
       if (!(out = fopen(filename, "w")))
@@ -81,11 +98,15 @@ int main(int argc, char **argv)
 
   EXEC SQL COMMIT;
 
-  fprintf(stderr, "Sorting Info\n");
-  sort_info();
+  incount = 0;
+  fprintf(out, "\n%s\n# Mailing lists\n%s\n\n", divide, divide);
+  hash_step(lists, save_mlist, FALSE);
+  fprintf(stderr, "Output %d lists\n", incount);
 
-  fprintf(stderr, "Dumping information\n");
-  do_people();
+  incount = 0;
+  fprintf(out, "\n%s\n# People\n%s\n\n", divide, divide);
+  hash_step(users, output_login, out);
+  fprintf(stderr, "Output %d users\n", incount);
 
   fprintf(out, "\n%s\n# End of aliases file\n", divide);
 
@@ -100,42 +121,14 @@ int main(int argc, char **argv)
   exit(MR_SUCCESS);
 }
 
-
-
-struct hash *users, *machines, *strings, *lists, *names;
-struct user {
-  char *login;
-  char *first;
-  char *last;
-  char mi;
-  char *pobox;
-};
-struct member {
-  struct member *next;
-  char *name;
-  int list_id;
-};
-struct list {
-  char *name;
-  char maillist;
-  char *description;
-  char acl_t;
-  int acl_id;
-  struct member *m;
-};
-struct names {
-  char *name;
-  struct names *next;
-  int keep;
-  int id;
-};
-
-
-get_info(void)
+void get_info(void)
 {
   EXEC SQL BEGIN DECLARE SECTION;
-  int id, pid, bid, cnt, maillistp, acl, mid;
-  char name[129], type[9], fname[17], mname[17], lname[17], buf[257];
+  int id, pid, iid, bid, eid, cnt, maillistp, acl, mid, mailman;
+  char mname[MACHINE_NAME_SIZE], str[STRINGS_STRING_SIZE];
+  char login[USERS_LOGIN_SIZE], potype[USERS_POTYPE_SIZE];
+  char lname[LIST_NAME_SIZE], desc[LIST_DESCRIPTION_SIZE];
+  char type[LIST_ACL_TYPE_SIZE], mailman_server[MACHINE_NAME_SIZE];
   EXEC SQL END DECLARE SECTION;
   char *s;
   struct user *u;
@@ -149,27 +142,30 @@ get_info(void)
   EXEC SQL WHENEVER SQLERROR GOTO sqlerr;
 
   cnt = 0;
-  machines = create_hash(1000);
+  machines = create_hash(100);
 
   EXEC SQL DECLARE m_cursor CURSOR FOR
     SELECT mach_id, name
     FROM machine
     WHERE status = 1
+    AND ( mach_id IN ( SELECT UNIQUE pop_id FROM users ) OR
+         mach_id IN ( SELECT UNIQUE mach_id FROM filesys
+                      WHERE type = 'IMAP' ) )    
     ORDER BY mach_id;
   EXEC SQL OPEN m_cursor;
   while (1)
     {
-      EXEC SQL FETCH m_cursor INTO :id, :name;
+      EXEC SQL FETCH m_cursor INTO :id, :mname;
       if (sqlca.sqlcode)
        break;
-      if (s = strchr(name, '.'))
+      if ((s = strchr(mname, '.')))
        *s = '\0';
       else
-       strtrim(name);
+       strtrim(mname);
 #ifdef ATHENA
-      strcat(name, ".LOCAL");
+      strcat(mname, ".LOCAL");
 #endif
-      if (hash_store(machines, id, pstrsave(name)) < 0)
+      if (hash_store(machines, id, strdup(mname)) < 0)
        {
          fprintf(stderr, "Out of memory!\n");
          exit(MR_NO_MEM);
@@ -178,6 +174,28 @@ get_info(void)
     }
   EXEC SQL CLOSE m_cursor;
 
+  EXEC SQL DECLARE e_cursor CURSOR FOR
+    SELECT mach_id, name
+    FROM machine
+    WHERE status = 1
+    AND mach_id in (SELECT UNIQUE exchange_id FROM users)
+    ORDER BY mach_id;
+  EXEC SQL OPEN e_cursor;
+  while (1)
+    {
+      EXEC SQL FETCH e_cursor INTO :id, :mname;
+      if (sqlca.sqlcode)
+       break;
+      strtrim(mname);
+      if (hash_store(machines, id, strdup(mname)) < 0)
+       {
+         fprintf(stderr, "Out of memory!\n");
+         exit(MR_NO_MEM);
+       }
+      cnt++;
+    }
+  EXEC SQL CLOSE e_cursor;
+       
   fprintf(stderr, "Loaded %d machines\n", cnt);
 
   cnt = 0;
@@ -190,10 +208,10 @@ get_info(void)
   EXEC SQL OPEN s_cursor;
   while (1)
     {
-      EXEC SQL FETCH s_cursor INTO :id, :name;
+      EXEC SQL FETCH s_cursor INTO :id, :str;
       if (sqlca.sqlcode)
        break;
-      if (hash_store(strings, id, pstrsave(strtrim(name))) < 0)
+      if (hash_store(strings, id, strdup(strtrim(str))) < 0)
        {
          fprintf(stderr, "Out of memory!\n");
          exit(MR_NO_MEM);
@@ -208,35 +226,66 @@ get_info(void)
   users = create_hash(13001);
 
   EXEC SQL DECLARE u_cursor CURSOR FOR
-    SELECT users_id, login, first, middle, last, potype, pop_id, box_id
+    SELECT users_id, login, potype, pop_id, imap_id, box_id, exchange_id
     FROM users
     WHERE status != 3
     ORDER BY users_id;
   EXEC SQL OPEN u_cursor;
   while (1)
     {
-      EXEC SQL FETCH u_cursor INTO :id, :name, :fname, :mname, :lname,
-       :type, :pid, :bid;
+      char *saddr = NULL, *paddr = NULL;
+
+      EXEC SQL FETCH u_cursor INTO :id, :login, :potype, :pid, :iid, :bid,
+       :eid;
       if (sqlca.sqlcode)
        break;
-      u = (struct user *) perm_malloc(sizeof(struct user));
-      u->login = pstrsave(strtrim(name));
-      u->first = pstrsave(strtrim(fname));
-      u->last  = pstrsave(strtrim(lname));
-      if (mname[0] != ' ')
-       u->mi = mname[0];
-      else
-       u->mi = 0;
+      u = malloc(sizeof(struct user));
+      u->login = strdup(strtrim(login));
 
-      if (type[0] == 'P' && (s = hash_lookup(machines, pid)))
+      if (!strcmp(strtrim(potype), "NONE"))
+       u->pobox = NULL;
+      else
        {
-         sprintf(buf, "%s@%s", u->login, s);
-         u->pobox = pstrsave(buf);
+         /* If SMTP or SPLIT, get SMTP address. */
+         if (potype[0] == 'S')
+           {
+             saddr = hash_lookup(strings, bid);
+
+             /* If SMTP, clear pid and iid. */
+             if (potype[1] == 'M')
+               pid = iid = eid = 0;
+           }
+
+         /* If IMAP, or SPLIT with IMAP, set pid to mach_id. */
+         if (potype[0] == 'I' || (potype[0] == 'S' && iid))
+           {
+             EXEC SQL SELECT mach_id INTO :pid FROM filesys
+               WHERE filsys_id = :iid;
+           }
+
+         /* If EXCHANGE or SPLIT with EXCHANGE, set pid to eid. */
+         if (potype[0] == 'E' || (potype[0] == 'S' && eid))
+           pid = eid;
+
+         if (pid && (s = hash_lookup(machines, pid)))
+           {
+             paddr = malloc(strlen(u->login) + strlen(s) + 2);
+             sprintf(paddr, "%s@%s", u->login, s);
+           }
+
+         if (paddr && saddr)
+           {
+             u->pobox = malloc(strlen(paddr) + strlen(saddr) + 3);
+             sprintf(u->pobox, "%s, %s", paddr, saddr);
+             free(paddr);
+           }
+         else if (paddr)
+           u->pobox = paddr;
+         else
+           u->pobox = saddr;
        }
-      else if (type[0] ==  'S')
-       u->pobox = hash_lookup(strings, bid);
-      else
-       u->pobox = NULL;
+
+      check_string(u->login);
       if (hash_store(users, id, u) < 0)
        {
          fprintf(stderr, "Out of memory!\n");
@@ -251,22 +300,26 @@ get_info(void)
   lists = create_hash(15000);
 
   EXEC SQL DECLARE l_cursor CURSOR FOR
-    SELECT list_id, name, maillist, description, acl_type, acl_id
-    FROM list
-    WHERE active != 0
+    SELECT l.list_id, l.name, l.maillist, l.description, l.acl_type, l.acl_id,
+    l.mailman, m.name
+    FROM list l, machine m
+    WHERE active != 0 AND l.mailman_id = m.mach_id
     ORDER BY list_id;
   EXEC SQL OPEN l_cursor;
   while (1)
     {
-      EXEC SQL FETCH l_cursor INTO :id, :name, :maillistp, :buf, :type, :acl;
+      EXEC SQL FETCH l_cursor INTO :id, :lname, :maillistp, :desc, :type, :acl,
+       :mailman, :mailman_server;
       if (sqlca.sqlcode)
        break;
-      l = (struct list *) perm_malloc(sizeof(struct list));
-      l->name = pstrsave(strtrim(name));
+      l = malloc(sizeof(struct list));
+      l->name = strdup(strtrim(lname));
       l->maillist = maillistp;
-      l->description = pstrsave(strtrim(buf));
+      l->description = strdup(strtrim(desc));
       l->acl_t = type[0];
       l->acl_id = acl;
+      l->mailman = mailman;
+      l->mailman_server = strdup(strtrim(mailman_server));
       l->m = NULL;
       if (hash_store(lists, id, l) < 0)
        {
@@ -292,18 +345,17 @@ get_info(void)
       if (sqlca.sqlcode)
        break;
       cnt++;
-      if ((l = (struct list *) hash_lookup(lists, id)))
+      if ((l = hash_lookup(lists, id)))
        {
-         m = (struct member *) perm_malloc(sizeof(struct member));
-         if (type[0] == 'U' && (u = (struct user *) hash_lookup(users, mid)))
+         m = malloc(sizeof(struct member));
+         if (type[0] == 'U' && (u = hash_lookup(users, mid)))
            {
              m->list_id = 0;
              m->name = u->login;
              m->next = l->m;
              l->m = m;
            }
-         else if (type[0] == 'L' &&
-                  (memberlist = (struct list *) hash_lookup(lists, mid)))
+         else if (type[0] == 'L' && (memberlist = hash_lookup(lists, mid)))
            {
              m->list_id = mid;
              m->name = memberlist->name;
@@ -330,290 +382,132 @@ sqlerr:
 }
 
 
-save_mlist(int id, struct list *l, int force)
+void save_mlist(int id, void *list, void *force)
 {
   struct member *m;
-  struct list *l1;
+  struct list *l = list, *l1;
 
-  if (l->maillist > 1 || (l->maillist == 0 && !force))
+  if (l->maillist > 1 || (l->maillist == 0 && !force) ||
+      !check_string(l->name))
     return;
 
+  /* If user group appears on list, replace with user. */
   if (l->m && l->m->next == NULL && !strcasecmp(l->name, l->m->name))
     {
       l->maillist = 3;
       return;
     }
   l->maillist = 2;
-  insert_name(l->name, -1, TRUE, FALSE);
   output_mlist(id, l);
 
-  if (l->acl_t == 'L' && (l1 = (struct list *)hash_lookup(lists, l->acl_id)))
-    save_mlist(0, l1, TRUE);
+  if (l->acl_t == 'L' && (l1 = hash_lookup(lists, l->acl_id)))
+    save_mlist(0, l1, (void *)TRUE);
 
   for (m = l->m; m; m = m->next)
     {
-      if (m->list_id && (l1 = (struct list *)hash_lookup(lists, m->list_id)))
-       save_mlist(0, l1, TRUE);
+      if (m->list_id && (l1 = hash_lookup(lists, m->list_id)))
+       save_mlist(0, l1, (void *)TRUE);
     }
 }
 
-
-insert_login(int id, struct user *u, int dummy)
+void output_login(int dummy, void *user, void *out)
 {
-  if (u->pobox && u->login[0] != '#')
-    insert_name(u->login, id, TRUE, FALSE);
-}
+  struct user *u = user;
 
-void insert_names(int id, struct user *u, int dummy)
-{
-  char buffer[256];
-
-  insert_name(u->last, id, FALSE, FALSE);
-  sprintf(buffer, "%s_%s", u->first, u->last);
-  insert_name(buffer, id, FALSE, TRUE);
-#if 0
-  sprintf(buffer, "%c_%s", u->first[0], u->last);
-  insert_name(buffer, id, FALSE, TRUE);
-#endif
-  if (u->mi)
-    {
-      sprintf(buffer, "%s_%c_%s", u->first, u->mi, u->last);
-      insert_name(buffer, id, FALSE, TRUE);
-    }
+  incount++;
+  if (u->pobox && check_string(u->login) && u->login[0] != '#')
+    fprintf(out, "%s: %s\n", u->login, u->pobox);
 }
 
-int incount = 0;
+static const char *mailman_suffixes[] = { "-admin", "-owner", "-request",
+                                         "-bounces", "-confirm", "-join",
+                                         "-leave", "-subscribe",
+                                         "-unsubscribe", NULL };
 
-insert_name(char *s, int id, int nodups, int copy)
+void output_mlist(int id, struct list *l)
 {
-  int code;
-  struct names *ns;
+  struct list *l1;
+  struct member *m;
+  struct user *u;
+  int line_width, alias_width, word_width, beginning;
+  static int cont = 1;
+  char str[8];
+  int i;
 
-  incount++;
-  code = hashstr(s);
-  ns = (struct names *) hash_lookup(names, code);
-  if (!ns)
+  put_fill(out, l->description);
+
+  if (l->mailman && strcmp(l->mailman_server, "[NONE]"))
     {
-      if (!(ns = (struct names *) perm_malloc(sizeof(struct names))))
-       {
-         fprintf(stderr, "ran out of memory inserting name (sorting)\n");
-         exit(MR_NO_MEM);
-       }
-      if (copy)
-       ns->name = pstrsave(s);
-      else
-       ns->name = s;
-      ns->keep = nodups;
-      ns->id = id;
-      ns->next = NULL;
-      if (hash_store(names, code, ns) < 0)
-       {
-         fprintf(stderr, "Out of memory!\n");
-         exit(MR_NO_MEM);
-       }
-      return;
+      for (i = 0; mailman_suffixes[i]; i++)
+       fprintf(out, "%s%s: %s%s@%s\n", l->name, mailman_suffixes[i], l->name,
+               mailman_suffixes[i], l->mailman_server);
+      fprintf(out, "owner-%s: %s-owner@%s\n%s: ", l->name, l->name,
+             l->mailman_server, l->name);
     }
-  if (strcasecmp(ns->name, s))
+  else if (l->acl_t ==  'L' && (l1 = hash_lookup(lists, l->acl_id)))
+    fprintf(out, "owner-%s: %s\n%s: ", l->name, l1->name, l->name);
+  else if (l->acl_t ==  'U' && (u = hash_lookup(users, l->acl_id)))
+    fprintf(out, "owner-%s: %s\n%s: ", l->name, u->login, l->name);
+  else
+    fprintf(out, "%s: ", l->name);
+
+  alias_width = line_width = strlen(l->name) + 2;
+  beginning = 1;
+  for (m = l->m; m; m = m->next)
     {
-      while (ns->next)
+      word_width = strlen(m->name);
+
+      if (!beginning && alias_width + word_width + 2 > MAX_ALIAS_WIDTH)
        {
-         ns = ns->next;
-         if (!strcasecmp(ns->name, s))
-           goto foundns;
+         /* Make a continuation. */
+         sprintf(str, "%c%c%c%c%c%c", rand() % 26 + 97, rand() % 26 + 97,
+                 rand() % 26 + 97, rand() % 26 + 97,
+                 rand() % 26 + 97, rand() % 26 + 97);
+         fprintf(out, ",\n\tcont%d-%s\ncont%d-%s: ", cont, str, cont, str);
+         cont++;
+         alias_width = line_width = 17 + word_width;
+         fputs(m->name, out);
        }
-      if (!(ns->next = (struct names *) perm_malloc(sizeof(struct names))))
+      else if (beginning)
        {
-         fprintf(stderr, "ran out of memory insterting name (sorting)\n");
-         exit(MR_NO_MEM);
+         /* Beginning of alias, so don't wrap. */
+         line_width += word_width;
+         alias_width = line_width;
+         fputs(m->name, out);
+         beginning = 0;
        }
-      ns = ns->next;
-      if (copy)
-       ns->name = pstrsave(s);
-      else
-       ns->name = s;
-      ns->keep = nodups;
-      ns->id = id;
-      ns->next = NULL;
-      return;
-    }
-foundns:
-  if (nodups || ns->keep)
-    {
-      if (nodups && ns->keep)
-       fprintf(stderr, "duplicated name: %s\n", s);
-      return;
-    }
-  ns->id = 0;
-}
-
-
-/* Illegal chars: ! " % ( ) , / : ; < = > @ [ \ ] ^ { | } */
-
-static int illegalchars[] = {
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^@ - ^O */
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^P - ^_ */
-  0, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, /* SPACE - / */
-  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, /* 0 - ? */
-  1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* @ - O */
-  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, /* P - _ */
-  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* ` - o */
-  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, /* p - ^? */
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
-};
-
-
-/* While hashing the string, punt any illegal characters */
-
-int hashstr(char *s)
-{
-  int result;
-  int c;
-
-  for (result = 0; c = *s; s++)
-    {
-      if (illegalchars[c])
-       {
-         char *p;
-         for (p = s; *p; p++)
-           *p = p[1];
-         continue;
-       }
-      if (isupper(c))
-       c = *s = tolower(c);
-      result = (result << 5) - result + c - '`';
-    }
-  return result < 0 ? -result : result;
-}
-
-
-sort_info(void)
-{
-  names = create_hash(20001);
-  hash_step(users, insert_login, NULL);
-  incount = 0;
-  fprintf(out, "\n%s\n# Mailing lists\n%s\n", divide, divide);
-  hash_step(lists, save_mlist, FALSE);
-  fprintf(stderr, "Output %d lists\n", incount);
-  hash_step(users, insert_names, NULL);
-  fprintf(stderr, "Inserted %d names\n", incount);
-}
-
-
-output_data(int dummy, struct names *nms, FILE *out)
-{
-  struct names *ns;
-  struct user *u;
-
-  incount++;
-  for (ns = nms; ns; ns = ns->next)
-    {
-      if (!ns->name[0] || !ns->name[1])
+      else if (line_width + word_width + 2 > MAX_LINE_WIDTH)
        {
-         fprintf(stderr, "punting %s due to short name\n", ns->name);
-         continue;
+         /* Wrap. */
+         fprintf(out, ",\n\t%s", m->name);
+         alias_width += line_width + word_width + 2;
+         line_width = word_width + 8;
        }
-      if (ns->id > 0)
+      else
        {
-         u = (struct user *) hash_lookup(users, ns->id);
-         if (u->pobox)
-           fprintf(out, "%s: %s\n", ns->name, u->pobox);
-         else
-           fprintf(out, "%s: =%s=@nobox\n", ns->name, ns->name);
+         /* Continue line. */
+         line_width += word_width + 2;
+         fprintf(out, ", %s", m->name);
        }
-      else if (ns->id == 0)
-       fprintf(out, "%s: =%s=@ambig\n", ns->name, ns->name);
     }
-}
-
-
-int lwid, bol, awid;
-
-output_mlist(int id, struct list *l)
-{
-  struct list *l1;
-  struct member *m;
-  struct user *u;
-
-  put_fill(out, l->description);
-  if (l->acl_t ==  'L' && (l1 = (struct list *) hash_lookup(lists, l->acl_id)))
-    fprintf(out, "owner-%s: %s\n%s: ", l->name, l1->name, l->name);
-  else if (l->acl_t ==  'U' &&
-            (u = (struct user *) hash_lookup(users, l->acl_id)))
-    fprintf(out, "owner-%s: %s\n%s: ", l->name, u->login, l->name);
-  else
-    fprintf(out, "%s: ", l->name);
-
-  lwid = strlen(l->name) + 2;
-  bol = 1;
-  for (m = l->m; m; m = m->next)
-    do_member(out, m->name);
   if (!l->m)
     fprintf(out, "/dev/null");
   fprintf(out, "\n\n");
   incount++;
 }
 
-
-/* print out strings separated by commas, doing line breaks as appropriate */
-
-do_member(FILE *out, char *s)
-{
-  wwid;
-  static int cont = 1;
-  char str[8];
-
-  wwid = strlen(s);
-
-  if (!bol && awid + wwid + 2 > AL_MAX_WID)
-    {
-      sprintf(str, "%c%c%c%c%c%c", rand() % 26 + 97, rand() % 26 + 97,
-             rand() % 26 + 97, rand() % 26 + 97,
-             rand() % 26 + 97, rand() % 26 + 97);
-      str[6] = '\0';
-      fprintf(out, ",\n\tcont%d-%s\ncont%d-%s: ", cont, str, cont, str);
-      cont++;
-      awid = lwid = 17 + wwid;
-      fputs(s, out);
-      return;
-    }
-
-  if (bol)
-    {
-      lwid += wwid;
-      awid = lwid;
-      fputs(s, out);
-      bol = 0;
-      return;
-    }
-  if (lwid + wwid + 2 > ML_WID)
-    {
-      fprintf(out, ",\n\t%s", s);
-      awid += lwid + wwid + 2;
-      lwid = wwid + 8;
-      return;
-    }
-  lwid += wwid + 2;
-  fprintf(out, ", %s", s);
-}
-
-
-put_fill(FILE *aliases, char *string)
+/* Write a word-wrapped list description to the aliases file as a
+ * comment. */
+void put_fill(FILE *aliases, char *string)
 {
   char *c;
-  int lwid;
-  int wwid;
+  int line_width;
+  int word_width;
 
   if (!string || !*string)
     return;
   fputs("#  ", aliases);
-  lwid = 3;
+  line_width = 3;
 
   while (1)
     {
@@ -621,17 +515,17 @@ put_fill(FILE *aliases, char *string)
        string++;
       c = strchr(string, ' ');
       if (!c)
-       wwid = strlen(string);
+       word_width = strlen(string);
       else
        {
-         wwid = c - string;
+         word_width = c - string;
          *c = '\0';
        }
 
-      if ((lwid + wwid) > ML_WID)
+      if (line_width + word_width > MAX_LINE_WIDTH)
        {
          fputs("\n#  ", aliases);
-         lwid = 3;
+         line_width = 3;
          fputs(string, aliases);
        }
       else
@@ -641,14 +535,14 @@ put_fill(FILE *aliases, char *string)
        break;
       /* add a space after the word */
       fputc(' ', aliases);
-      wwid++;
-      lwid += wwid;
-      string += wwid;
+      word_width++;
+      line_width += word_width;
+      string += word_width;
       /* add another if after a period */
       if (*--c == '.')
        {
          fputc(' ', aliases);
-         lwid++;
+         line_width++;
        }
     }
 
@@ -656,182 +550,39 @@ put_fill(FILE *aliases, char *string)
 }
 
 
-do_people(void)
-{
-  incount = 0;
-  fprintf(out, "\n%s\n# People\n%s\n", divide, divide);
-  hash_step(names, output_data, out);
-  fprintf(stderr, "Output %d entries\n", incount);
-}
-
-
-#define chunk_size     102400
-
-char *perm_malloc(unsigned size)
-{
-  static char *pool = NULL;
-  static unsigned pool_size = 0;
-  char *ret;
-
-  if (size > pool_size)
-    {
-      pool = malloc(chunk_size);
-      pool_size = chunk_size;
-    }
-  ret = pool;
-  pool += size;
-  pool = (char *)(((unsigned) (pool + 3)) & ~3);
-  pool_size -= (pool - ret);
-  return ret;
-}
-
-
-/*
- * Make a (permenant) copy of a string.
- */
-char *pstrsave(char *s)
-{
-  int len;
-  char *p;
-  /* Kludge for sloppy string semantics */
-  if (!s)
-    {
-      printf("NULL != \"\" !!!!\r\n");
-      p = perm_malloc(1);
-      *p = '\0';
-      return p;
-    }
-  len = strlen(s) + 1;
-  p = perm_malloc((u_int)len);
-  if (p)
-    memcpy(p, s, len);
-  return p;
-}
-
-#define hash_func(h, key) (key >= 0 ? (key % h->size) : (-key % h->size))
-
-/* Create a hash table.  The size is just a hint, not a maximum. */
-
-struct hash *create_hash(int size)
-{
-  struct hash *h;
-
-  h = (struct hash *) perm_malloc(sizeof(struct hash));
-  if (!h)
-    return NULL;
-  h->size = size;
-  h->data = (struct bucket **) perm_malloc(size * sizeof(char *));
-  if (!h->data)
-    return NULL;
-  memset(h->data, 0, size * sizeof(char *));
-  return h;
-}
-
-/* Lookup an object in the hash table.  Returns the value associated with
- * the key, or NULL (thus NULL is not a very good value to store...)
- */
-
-char *hash_lookup(struct hash *h, int key)
-{
-  struct bucket *b;
-
-  b = h->data[hash_func(h, key)];
-  while (b && b->key != key)
-    b = b->next;
-  if (b && b->key == key)
-    return b->data;
-  else
-    return NULL;
-}
-
-
-/* Update an existing object in the hash table.  Returns 1 if the object
- * existed, or 0 if not.
+/* Illegal chars: this no longer corresponds to the array
+ * in setup_alis.  '+' is a valid character in a string on 
+ * a list, but is not a valid character in a listname.
  */
 
-int hash_update(struct hash *h, int key, char *value)
-{
-  struct bucket *b;
-
-  b = h->data[hash_func(h, key)];
-  while (b && b->key != key)
-    b = b->next;
-  if (b && b->key == key)
-    {
-      b->data = value;
-      return 1;
-    }
-  else
-    return 0;
-}
-
-
-/* Store an item in the hash table.  Returns 0 if the key was not previously
- * there, 1 if it was, or -1 if we ran out of memory.
- */
-
-int hash_store(struct hash *h, int key, char *value)
-{
-  struct bucket *b, **p;
-
-  p = &(h->data[hash_func(h, key)]);
-  if (!*p)
-    {
-      b = *p = (struct bucket *) perm_malloc(sizeof(struct bucket));
-      if (!b)
-       return -1;
-      b->next = NULL;
-      b->key = key;
-      b->data = value;
-      return 0;
-    }
-
-  for (b = *p; b && b->key != key; b = *p)
-    p = (struct bucket **) *p;
-  if (b && b->key == key)
-    {
-      b->data = value;
-      return 1;
-    }
-  b = *p = (struct bucket *) perm_malloc(sizeof(struct bucket));
-  if (!b)
-    return -1;
-  b->next = NULL;
-  b->key = key;
-  b->data = value;
-  return 0;
-}
-
-
-/* Search through the hash table for a given value.  For each piece of
- * data with that value, call the callback proc with the corresponding key.
- */
+static int illegalchars[] = {
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^@ - ^O */
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^P - ^_ */
+  1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, /* SPACE - / */
+  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, /* 0 - ? */
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* @ - O */
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, /* P - _ */
+  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* ` - o */
+  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, /* p - ^? */
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+  1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+};
 
-hash_search(struct hash *h, char *value, void (*callback)())
+int check_string(char *s)
 {
-  struct bucket *b, **p;
-
-  for (p = &(h->data[h->size - 1]); p >= h->data; p--)
+  for (; *s; s++)
     {
-      for (b = *p; b; b = b->next)
-       {
-         if (b->data == value)
-           (*callback)(b->key);
-       }
-    }
-}
+      if (isupper(*s))
+       *s = tolower(*s);
 
-
-/* Step through the hash table, calling the callback proc with each key.
- */
-
-hash_step(struct hash *h, void (*callback)(), char *hint)
-{
-  struct bucket *b, **p;
-
-  for (p = &(h->data[h->size - 1]); p >= h->data; p--)
-    {
-      for (b = *p; b; b = b->next)
-       (*callback)(b->key, b->data, hint);
+      if (illegalchars[(unsigned) *s])
+       return 0;
     }
+  return 1;
 }
This page took 1.35866 seconds and 4 git commands to generate.