Răsfoiți Sursa

Merge branch 'packcfg_over_stdin'

* packcfg_over_stdin:
  Fix compile error
  * Don't generate SALTS if missing during initialization
  * Add -Q to read PackConfig securely over stdin

Conflicts:
	doc/UPDATES
Bryan Drewery 17 ani în urmă
părinte
comite
b981b4e621
4 a modificat fișierele cu 80 adăugiri și 46 ștergeri
  1. 2 0
      doc/UPDATES
  2. 69 44
      src/binary.c
  3. 1 1
      src/binary.h
  4. 8 1
      src/main.c

+ 2 - 0
doc/UPDATES

@@ -2,6 +2,8 @@
 * Fix uname checking on NetBSD and OpenBSD
 * Fix uname checking on NetBSD and OpenBSD
 * EFnet server list updates
 * EFnet server list updates
 * Make errors non-obscure. (Compile with OBSCURE_ERRORS to re-enable)
 * Make errors non-obscure. (Compile with OBSCURE_ERRORS to re-enable)
+* PackConfig can now be securely read over STDIN. Use ./wraith -Q, then paste it in.
+* Binary will no longer generate SALTS if missing from the PackConfig. This was causing too much confusion.
 
 
 1.2.16 - http://wraith.botpack.net/milestone/1.2.16
 1.2.16 - http://wraith.botpack.net/milestone/1.2.16
 * Add 'set altchars' so that alternative characters used for nicks can be changed. (fixes #418)
 * Add 'set altchars' so that alternative characters used for nicks can be changed. (fixes #418)

+ 69 - 44
src/binary.c

@@ -25,7 +25,7 @@
 #include <signal.h>
 #include <signal.h>
 #include <sys/stat.h>
 #include <sys/stat.h>
 #include <fcntl.h>
 #include <fcntl.h>
-
+#include <termios.h>
 
 
 settings_t settings = {
 settings_t settings = {
   "\200\200\200\200\200\200\200\200\200\200\200\200\200\200\200",
   "\200\200\200\200\200\200\200\200\200\200\200\200\200\200\200",
@@ -276,21 +276,60 @@ features_find(const char *buffer)
   return 0;
   return 0;
 }
 }
 
 
+/* It is desirable to use this bit on systems that have it.
+   The only bit of terminal state we want to twiddle is echoing, which is
+   done in software; there is no need to change the state of the terminal
+   hardware.  */
+
+#ifndef TCSASOFT
+# define TCSASOFT 0
+#endif
+
+typedef struct line_list {
+  struct line_list* next;
+  int line;
+} line_list_t;
+
 static int
 static int
-readcfg(const char *cfgfile)
+readcfg(const char *cfgfile, bool read_stdin)
 {
 {
   FILE *f = NULL;
   FILE *f = NULL;
-
-  if ((f = fopen(cfgfile, "r")) == NULL) {
-    printf(STR("Error: Can't open '%s' for reading\n"), cfgfile);
-    exit(1);
+  struct termios s, t;
+  bool tty_changed = false;
+  line_list_t *error_list = NULL, *error_line = NULL;
+
+  if (read_stdin) {
+    f = stdin;
+    setbuf(stdin, NULL);
+    setbuf(stdout, NULL);
+    /* Taken from libc: getpass.c */
+    /* Turn echoing off if it is on now.  */
+    if (tcgetattr (fileno (stdin), &t) == 0) {
+      s = t;
+      t.c_lflag &= ~(ECHO | ISIG);
+      tty_changed = (tcsetattr (fileno (stdin), TCSAFLUSH | TCSASOFT, &t) == 0);
+    }
+    printf(STR("// Paste in your PACKCONFIG. Reference http://wraith.botpack.net/wiki/PackConfig\n"));
+    printf(STR("// Press <enter> if it gets hung up. If that doesn't work hit ^D (CTRL+d)\n"));
+    fflush(stdout);
+  } else {
+    if ((f = fopen(cfgfile, "r")) == NULL) {
+      fprintf(stderr, STR("Error: Can't open '%s' for reading\n"), cfgfile);
+      exit(1);
+    }
   }
   }
 
 
   char *buffer = NULL, *p = NULL;
   char *buffer = NULL, *p = NULL;
   int skip = 0, line = 0, feature = 0;
   int skip = 0, line = 0, feature = 0;
+  bool error = 0;
 
 
-  printf(STR("Reading '%s' "), cfgfile);
+  if (!read_stdin)
+    printf(STR("Reading '%s' "), cfgfile);
   while ((!feof(f)) && ((buffer = step_thru_file(f)) != NULL)) {
   while ((!feof(f)) && ((buffer = step_thru_file(f)) != NULL)) {
+    if (tty_changed) {
+      printf(".");
+      fflush(stdout);
+    }
     ++line;
     ++line;
     if ((*buffer)) {
     if ((*buffer)) {
       if (strchr(buffer, '\n'))
       if (strchr(buffer, '\n'))
@@ -298,9 +337,11 @@ readcfg(const char *cfgfile)
       if ((skipline(buffer, &skip)))
       if ((skipline(buffer, &skip)))
         continue;
         continue;
       if ((strchr(buffer, '<') || strchr(buffer, '>')) && !strstr(buffer, "SALT")) {
       if ((strchr(buffer, '<') || strchr(buffer, '>')) && !strstr(buffer, "SALT")) {
-        printf(STR(" Failed\n"));
-        printf(STR("%s:%d: error: Look at your configuration file again...\n"), cfgfile, line);
-//        exit(1);
+        error_line = (line_list_t *) my_calloc(1, sizeof(line_list_t));
+        error_line->line = line;
+        error_line->next = NULL;
+        list_append((struct list_type **) &(error_list), (struct list_type *) error_line);
+        error = 1;
       }
       }
       p = strchr(buffer, ' ');
       p = strchr(buffer, ' ');
       while (p && (strchr(LISTSEPERATORS, p[0])))
       while (p && (strchr(LISTSEPERATORS, p[0])))
@@ -308,68 +349,52 @@ readcfg(const char *cfgfile)
       if (p) {
       if (p) {
         if (!egg_strcasecmp(buffer, STR("packname"))) {
         if (!egg_strcasecmp(buffer, STR("packname"))) {
           strlcpy(settings.packname, trim(p), sizeof settings.packname);
           strlcpy(settings.packname, trim(p), sizeof settings.packname);
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("shellhash"))) {
         } else if (!egg_strcasecmp(buffer, STR("shellhash"))) {
           strlcpy(settings.shellhash, trim(p), sizeof settings.shellhash);
           strlcpy(settings.shellhash, trim(p), sizeof settings.shellhash);
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("dccprefix"))) {
         } else if (!egg_strcasecmp(buffer, STR("dccprefix"))) {
           strlcpy(settings.dcc_prefix, trim(p), sizeof settings.dcc_prefix);
           strlcpy(settings.dcc_prefix, trim(p), sizeof settings.dcc_prefix);
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("owner"))) {
         } else if (!egg_strcasecmp(buffer, STR("owner"))) {
           strlcat(settings.owners, trim(p), sizeof(settings.owners));
           strlcat(settings.owners, trim(p), sizeof(settings.owners));
           strlcat(settings.owners, ",", sizeof(settings.owners));
           strlcat(settings.owners, ",", sizeof(settings.owners));
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("owneremail"))) {
         } else if (!egg_strcasecmp(buffer, STR("owneremail"))) {
           strlcat(settings.owneremail, trim(p), sizeof(settings.owneremail));
           strlcat(settings.owneremail, trim(p), sizeof(settings.owneremail));
           strlcat(settings.owneremail, ",", sizeof(settings.owneremail));
           strlcat(settings.owneremail, ",", sizeof(settings.owneremail));
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("hub"))) {
         } else if (!egg_strcasecmp(buffer, STR("hub"))) {
           strlcat(settings.hubs, trim(p), sizeof(settings.hubs));
           strlcat(settings.hubs, trim(p), sizeof(settings.hubs));
           strlcat(settings.hubs, ",", sizeof(settings.hubs));
           strlcat(settings.hubs, ",", sizeof(settings.hubs));
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("salt1"))) {
         } else if (!egg_strcasecmp(buffer, STR("salt1"))) {
           strlcat(settings.salt1, trim(p), sizeof(settings.salt1));
           strlcat(settings.salt1, trim(p), sizeof(settings.salt1));
-          printf(".");
         } else if (!egg_strcasecmp(buffer, STR("salt2"))) {
         } else if (!egg_strcasecmp(buffer, STR("salt2"))) {
           strlcat(settings.salt2, trim(p), sizeof(settings.salt2));
           strlcat(settings.salt2, trim(p), sizeof(settings.salt2));
-          printf(".");
-        } else {
-          printf("%s %s\n", buffer, p);
-          printf(",");
+          if (read_stdin) break;
         }
         }
       } else { /* SINGLE DIRECTIVES */
       } else { /* SINGLE DIRECTIVES */
         if ((feature = features_find(buffer))) {
         if ((feature = features_find(buffer))) {
           int features = atol(settings.features);
           int features = atol(settings.features);
           features |= feature;
           features |= feature;
           simple_snprintf(settings.features, sizeof(settings.features), "%d", features);
           simple_snprintf(settings.features, sizeof(settings.features), "%d", features);
-          printf(".");
         }
         }
       }
       }
     }
     }
     buffer = NULL;
     buffer = NULL;
   }
   }
-  if (f)
-    fclose(f);
-  if (!settings.salt1[0] || !settings.salt2[0]) {
-    /* Write salts back to the cfgfile */
-    char salt1[SALT1LEN + 1] = "", salt2[SALT2LEN + 1] = "";
 
 
-    printf(STR("Creating Salts"));
-    if ((f = fopen(cfgfile, "a")) == NULL) {
-      printf(STR("Cannot open cfgfile for appending.. aborting\n"));
-      exit(1);
-    }
-    make_rand_str(salt1, SALT1LEN);
-    make_rand_str(salt2, SALT2LEN);
-    salt1[sizeof salt1 - 1] = salt2[sizeof salt2 - 1] = 0;
-    strlcpy(settings.salt1, salt1, sizeof(settings.salt1));
-    strlcpy(settings.salt2, salt2, sizeof(settings.salt2));
-    fprintf(f, STR("SALT1 %s\n"), salt1);
-    fprintf(f, STR("SALT2 %s\n"), salt2);
-    fflush(f);
+  if (f && !read_stdin) {
     fclose(f);
     fclose(f);
+  } else if (read_stdin && tty_changed) {
+    /* Restore the original setting.  */
+    tcsetattr (fileno (stdin), TCSAFLUSH | TCSASOFT, &s);
   }
   }
-  printf(STR(" Success\n"));
+
+  if (error) {
+    printf("\n");
+    fprintf(stderr, STR("Error: Look at your configuration again and remove any <>\n"));
+    for (error_line = error_list; error_line; error_line = error_line->next)
+        fprintf(stderr, STR("Line %d\n"), error_line->line);
+    exit(1);
+  }
+
+  if (!read_stdin) printf(STR(" Success\n"));
   return 1;
   return 1;
 }
 }
 
 
@@ -490,14 +515,14 @@ tellconfig(settings_t *incfg)
 #endif
 #endif
 
 
 void
 void
-check_sum(const char *fname, const char *cfgfile)
+check_sum(const char *fname, const char *cfgfile, bool read_stdin)
 {
 {
    if (!settings.hash[0]) {
    if (!settings.hash[0]) {
 
 
-    if (!cfgfile)
+    if (!cfgfile && !read_stdin)
       fatal(STR("Binary not initialized."), 0);
       fatal(STR("Binary not initialized."), 0);
 
 
-    readcfg(cfgfile);
+    readcfg(cfgfile, read_stdin);
 
 
 // tellconfig(&settings); 
 // tellconfig(&settings); 
     if (bin_checksum(fname, WRITE_CHECKSUM|WRITE_CONF|WRITE_PACK))
     if (bin_checksum(fname, WRITE_CHECKSUM|WRITE_CONF|WRITE_PACK))

+ 1 - 1
src/binary.h

@@ -11,7 +11,7 @@ extern int checked_bin_buf;
 #  define WRITE_CONF            BIT3
 #  define WRITE_CONF            BIT3
 #  define GET_CONF              BIT4
 #  define GET_CONF              BIT4
 
 
-void check_sum(const char *, const char *);
+void check_sum(const char *, const char *, bool);
 void write_settings(const char *, int, bool);
 void write_settings(const char *, int, bool);
 void conf_to_bin(conf_t *, bool, int);
 void conf_to_bin(conf_t *, bool, int);
 void reload_bin_data();
 void reload_bin_data();

+ 8 - 1
src/main.c

@@ -312,6 +312,8 @@ static void show_help()
   printf(format, STR("-h"), STR("Display this help listing"));
   printf(format, STR("-h"), STR("Display this help listing"));
   printf(format, STR("-k <botname>"), STR("Terminates (botname) with kill -9 (see also: -r)"));
   printf(format, STR("-k <botname>"), STR("Terminates (botname) with kill -9 (see also: -r)"));
   printf(format, STR("-n"), STR("Disables backgrounding bot (requires [-B] <botnick>)"));
   printf(format, STR("-n"), STR("Disables backgrounding bot (requires [-B] <botnick>)"));
+  printf(format, STR("-q <pack.cfg>"), STR("Initialize the binary with the given pack.cfg (Can only be done once per binary)"));
+  printf(format, STR("-Q"), STR("Securely initialize the binary by reading the PackConfig from stdin (paste). (Can only be done once per binary)"));
   printf(format, STR("-r <botname>"), STR("Restarts the specified bot (see also: -k)"));
   printf(format, STR("-r <botname>"), STR("Restarts the specified bot (see also: -k)"));
 //  printf(format, STR("-s"), STR("Disables checking for ptrace/strace during startup (no pass needed)"));
 //  printf(format, STR("-s"), STR("Disables checking for ptrace/strace during startup (no pass needed)"));
   printf(format, STR("-t"), STR("Enables \"Partyline\" emulation (requires -nB)"));
   printf(format, STR("-t"), STR("Enables \"Partyline\" emulation (requires -nB)"));
@@ -765,7 +767,12 @@ printf("out: %s\n", out);
     exit(5);				/* not initialized */
     exit(5);				/* not initialized */
   }
   }
 
 
-  check_sum(binname, argc >= 3 && !strcmp(argv[1], STR("-q")) ? argv[2] : NULL);
+  {
+    bool read_stdin = 0;
+    if (argc == 2 && !strcmp(argv[1], STR("-Q")))
+      read_stdin =1;
+    check_sum(binname, argc >= 3 && !strcmp(argv[1], STR("-q")) ? argv[2] : NULL, read_stdin);
+  }
   // Now settings struct is decrypted
   // Now settings struct is decrypted
   if (!checked_bin_buf)
   if (!checked_bin_buf)
     exit(1);
     exit(1);