]> git.sur5r.net Git - bacula/bacula/commitdiff
Print jmsg if file descriptor leaks occur
authorKern Sibbald <kern@sibbald.com>
Thu, 2 Oct 2003 19:17:29 +0000 (19:17 +0000)
committerKern Sibbald <kern@sibbald.com>
Thu, 2 Oct 2003 19:17:29 +0000 (19:17 +0000)
git-svn-id: https://bacula.svn.sourceforge.net/svnroot/bacula/trunk@722 91ce42f0-d328-0410-95d8-f526ca767f89

bacula/CheckList
bacula/ReleaseNotes
bacula/kernstodo
bacula/src/dird/run_conf.c
bacula/src/findlib/bfile.c
bacula/src/findlib/create_file.c
bacula/src/lib/parse_conf.c
bacula/src/stored/mount.c
bacula/src/tools/testls.c

index ff26ed374ba20c6aadb3de2120a4ffdce661ef98..ccc71d7e7994056ee376ff530cd007242ff67cf3 100644 (file)
@@ -8,7 +8,7 @@
 - Update ChangeLog (add release date)
 - Do a cvs commit
 - Do a cvs -q export -D now -d bacula-1.nn bacula
-- Build new bacula-1.nn to ensure everything is committed
+- Run the regression tests on the new bacula
 - Write ReleaseNotes
 - If everything is good
 - cd bacula/k
index d2a70b5ba8979ab536bc7b4a209846202459e369..b9b34df1d9ab01a79090b5d50c2b0e468a5b7d0a 100644 (file)
@@ -1,76 +1,13 @@
 
-          Release Notes for Bacula 1.32
+          Release Notes for Bacula 1.33
 
   Bacula code: Total files = 259 Total lines = 77,740 (*.h *.c *.in)
 
 Major Changes this Release:
-- Implemented forward space file/block whenever possible 
-  during restore. Restoring a small number of files is now  
-  much faster.
-- There is a new option to restore that allows you   
-  to restore files based on their Filename. You can
-  also specify a file to read which contains the list.
-- Added ClientRunBeforeJob and ClientRunAfterJob.
-- Implemented Include | and < in File daemon.
-- Automatic labeling of tape Volumes should work now.
-- Recycling has been completely restructured and should work.
-- Implemented full length time interval qualifiers (e.g
-  "5n is now "5 min" or "5 minutes". A modifier is now required!
-- Fixed gnome-console to compile with RH9 (Gnome 2.0)
-- Implemented "list nextvol job=xxx", which displays the
-  next volume to be used by job xxx. The Volume name to
-  be used is also added to the "status dir" output.
-- Lots of fixes with variable expansion and counter variables
-- Implemented a new Include/Exclude syntax.
-- While writing a tape, an end of file mark will be written
-  every 1Gb. This makes restores faster. If you want to
-  change this use "Maximum File Size" in the SD Device
-  resource.
 
 
 Other Changes this Release:
-- A warning message is sent when a job starts that will be
-  blocked because the user did an "unmount".
-- Block checksum errors if any are printed in the job report.
-- Implemented a single routine to read_records. It also returns
-  a different record packet for each session.  This means
-  that multiple simultaneous jobs should work.
-- Added SDConnectTimeout to FD.    
-- Lots of doc enhancements
-- Fixed a PurgeOldestVolume bug (VolStatus not returned)
-- Don't crash if DB address record not specified.
-- Return VolStatus on find_next_volume.
-- Use alist for incexe name_list.
-- Use bget_dirmsg() everywhere possible when talking to FD.
-- Delete old semaphore job and workq job scheduling code.
-- edit_run_codes in one place (/lib)  Add Job name
-- Update query.sql to find current backups correctly.
-- Correct ambiguous SQL statement for pruning.
-- Set heartbeat interval to zero by default.
-- Fix a possible race condition in stopping the 
-  heartbeat thread.
-- Eliminate gnome2-console directory. Everything is in gnome-console
-- Enhanced "packet too big" message to indicate who sent it.
-- Corrected console prompt problem in non-readline versions.
-- Correct a number of variable expansion problems.
-- Added a number of new regression tests.
-- In an attempt to make configuration a bit less confusing, I've changed
-  the name of a number of variables. The old ones still work, but will
-  be phased out over time. FDAddress, FDPassword, SDAddress SDPassword,
-  SDDeviceName, and DBPassword.
-- A possible fix to the very intermittent SD crashes that Alex gets.
               
 
 
 Items to note:  !!!!!
-- Modifiers (sec, min, hour, day, ...) are now required on conf file
-  time interval specifications.
-- Duplicate names within the same conf resource are prohibited.
-- If you have used a prior BETA version of 1.32, please do
-  the following to cleanup any zero length spool files:
-
-   cd <working-directory-as-in-Bacula-conf>
-   rm -f *.spool.*
-
-  Please be sure there are no spaces between the asterisks
-  and the periods.
index ad3ed564e05c40a637705926f66d1acdbc7b6e83..61c51d4fc03dbd314053a229d4c05fe245f62186 100644 (file)
@@ -24,6 +24,7 @@ Testing to do: (painful)
 - Test connect timeouts.
 
 For 1.33 Testing/Documentation:
+- suppress "Do not forget to mount the drive!!!" if error
 - Document new records in Director. SDAddress SDDeviceName, SDPassword.
   FDPassword, FDAddress, DBAddress, DBPort, DBPassword.
 - Document new Include/Exclude ...
@@ -31,6 +32,13 @@ For 1.33 Testing/Documentation:
 - Add counter variable test.
                 
 For 1.33
+- Make sure a rescheduled job is properly reported by status.
+- Walk through the Pool records rather than the Job records
+  in dird.c to create/update pools.
+- Figure out a way to move Volumes from one pool to another.
+- What to do about "list files job=xxx".
+- Implement delete Job.
+- Document need to put LabelFormat in quotes.
 - Implement scan: for every slot it finds, zero the slot of
   Volume other volume having that slot.
 - When job rescheduled, status gives is waiting for Client Rufus 
index d08d9e315b17833c150b0aa9e14ab8d11399e85c..920f92638474342ad553e64813f2a09d10922847 100644 (file)
@@ -298,243 +298,243 @@ void store_run(LEX *lc, struct res_items *item, int index, int pass)
    for ( ; token != T_EOL; (token = lex_get_token(lc, T_ALL))) {
       int len, pm = 0;
       switch (token) {
-        case T_NUMBER:
-           state = s_mday;
-           code = atoi(lc->str) - 1;
-           if (code < 0 || code > 30) {
-               scan_err0(lc, _("Day number out of range (1-31)"));
-           }
+      case T_NUMBER:
+        state = s_mday;
+        code = atoi(lc->str) - 1;
+        if (code < 0 || code > 30) {
+            scan_err0(lc, _("Day number out of range (1-31)"));
+        }
+        break;
+      case T_NAME:                /* this handles drop through from keyword */
+      case T_UNQUOTED_STRING:
+         if (strchr(lc->str, (int)'-')) {
+           state = s_range;
            break;
-        case T_NAME:                 /* this handles drop through from keyword */
-        case T_UNQUOTED_STRING:
-            if (strchr(lc->str, (int)'-')) {
-              state = s_range;
-              break;
-           }
-            if (strchr(lc->str, (int)':')) {
-              state = s_time;
+        }
+         if (strchr(lc->str, (int)':')) {
+           state = s_time;
+           break;
+        }
+        /* everything else must be a keyword */
+        for (i=0; keyw[i].name; i++) {
+           if (strcasecmp(lc->str, keyw[i].name) == 0) {
+              state = keyw[i].state;
+              code   = keyw[i].code;
+              i = 0;
               break;
            }
-           /* everything else must be a keyword */
-           for (i=0; keyw[i].name; i++) {
-              if (strcasecmp(lc->str, keyw[i].name) == 0) {
-                 state = keyw[i].state;
-                 code   = keyw[i].code;
-                 i = 0;
-                 break;
-              }
-           }
-           if (i != 0) {
-               scan_err1(lc, _("Job type field: %s in run record not found"), lc->str);
-              /* NOT REACHED */
-           }
-           break;
-        case T_COMMA:
-           continue;
-        default:
-            scan_err2(lc, _("Unexpected token: %d:%s"), token, lc->str);
+        }
+        if (i != 0) {
+            scan_err1(lc, _("Job type field: %s in run record not found"), lc->str);
            /* NOT REACHED */
-           break;
+        }
+        break;
+      case T_COMMA:
+        continue;
+      default:
+         scan_err2(lc, _("Unexpected token: %d:%s"), token, lc->str);
+        /* NOT REACHED */
+        break;
       }
       switch (state) {
-        case s_none:
-           continue;
-        case s_mday:                 /* day of month */
+      case s_none:
+        continue;
+      case s_mday:                /* day of month */
+        if (!have_mday) {
+           clear_bits(0, 30, lrun.mday);
+           clear_bits(0, 6, lrun.wday);
+           have_mday = TRUE;
+        }
+        set_bit(code, lrun.mday);
+        break;
+      case s_month:               /* month of year */
+        if (!have_month) {
+           clear_bits(0, 11, lrun.month);
+           have_month = TRUE;
+        }
+        set_bit(code, lrun.month);
+        break;
+      case s_wday:                /* week day */
+        if (!have_wday) {
+           clear_bits(0, 6, lrun.wday);
+           clear_bits(0, 30, lrun.mday);
+           have_wday = TRUE;
+        }
+        set_bit(code, lrun.wday);
+        break;
+      case s_wpos:                /* Week position 1st, ... */
+        if (!have_wpos) {
+           clear_bits(0, 4, lrun.wpos);
+           have_wpos = TRUE;
+        }
+        set_bit(code, lrun.wpos);
+        break;
+      case s_time:                /* time */
+        if (!have_at) {
+            scan_err0(lc, _("Time must be preceded by keyword AT."));
+           /* NOT REACHED */
+        }
+        if (!have_hour) {
+           clear_bit(0, lrun.hour);
+        }
+         p = strchr(lc->str, ':');
+        if (!p)  {
+            scan_err0(lc, _("Time logic error.\n"));
+           /* NOT REACHED */
+        }
+        *p++ = 0;                 /* separate two halves */
+        code = atoi(lc->str);
+        len = strlen(p);
+         if (len > 2 && p[len-1] == 'm') {
+            if (p[len-2] == 'a') {
+              pm = 0;
+            } else if (p[len-2] == 'p') {
+              pm = 1;
+           } else {
+               scan_err0(lc, _("Bad time specification."));
+              /* NOT REACHED */
+           }
+        } else {
+           pm = 0;
+        }
+        code2 = atoi(p);
+        if (pm) {
+           code += 12;
+        }
+        if (code < 0 || code > 23 || code2 < 0 || code2 > 59) {
+            scan_err0(lc, _("Bad time specification."));
+           /* NOT REACHED */
+        }
+        set_bit(code, lrun.hour);
+        lrun.minute = code2;
+        have_hour = TRUE;
+        break;
+      case s_at:
+        have_at = TRUE;
+        break;
+      case s_range:
+         p = strchr(lc->str, '-');
+        if (!p) {
+            scan_err0(lc, _("Range logic error.\n"));
+        }
+        *p++ = 0;                 /* separate two halves */
+
+        /* Check for day range */
+        if (is_num(lc->str) && is_num(p)) {
+           code = atoi(lc->str) - 1;
+           code2 = atoi(p) - 1;
+           if (code < 0 || code > 30 || code2 < 0 || code2 > 30) {
+               scan_err0(lc, _("Bad day range specification."));
+           }
            if (!have_mday) {
               clear_bits(0, 30, lrun.mday);
               clear_bits(0, 6, lrun.wday);
               have_mday = TRUE;
            }
-           set_bit(code, lrun.mday);
-           break;
-        case s_month:                /* month of year */
-           if (!have_month) {
-              clear_bits(0, 11, lrun.month);
-              have_month = TRUE;
+           if (code < code2) {
+              set_bits(code, code2, lrun.mday);
+           } else {
+              set_bits(code, 30, lrun.mday);
+              set_bits(0, code2, lrun.mday);
            }
-           set_bit(code, lrun.month);
            break;
-        case s_wday:                 /* week day */
+        }
+
+        /* lookup first half of keyword range (week days or months) */
+        lcase(lc->str);
+        for (i=0; keyw[i].name; i++) {
+           if (strcmp(lc->str, keyw[i].name) == 0) {
+              state = keyw[i].state;
+              code   = keyw[i].code;
+              i = 0;
+              break;
+           }
+        }
+        if (i != 0 || (state != s_month && state != s_wday && state != s_wpos)) {
+            scan_err0(lc, _("Invalid month, week or position day range"));
+           /* NOT REACHED */
+        }
+
+        /* Lookup end of range */
+        lcase(p);
+        for (i=0; keyw[i].name; i++) {
+           if (strcmp(p, keyw[i].name) == 0) {
+              state2  = keyw[i].state;
+              code2   = keyw[i].code;
+              i = 0;
+              break;
+           }
+        }
+        if (i != 0 || state != state2 || code == code2) {
+            scan_err0(lc, _("Invalid month, weekday or position range"));
+           /* NOT REACHED */
+        }
+        if (state == s_wday) {
            if (!have_wday) {
               clear_bits(0, 6, lrun.wday);
               clear_bits(0, 30, lrun.mday);
               have_wday = TRUE;
            }
-           set_bit(code, lrun.wday);
-           break;
-        case s_wpos:                 /* Week position 1st, ... */
-           if (!have_wpos) {
-              clear_bits(0, 4, lrun.wpos);
-              have_wpos = TRUE;
-           }
-           set_bit(code, lrun.wpos);
-           break;
-        case s_time:                 /* time */
-           if (!have_at) {
-               scan_err0(lc, _("Time must be preceded by keyword AT."));
-              /* NOT REACHED */
-           }
-           if (!have_hour) {
-              clear_bit(0, lrun.hour);
-           }
-            p = strchr(lc->str, ':');
-           if (!p)  {
-               scan_err0(lc, _("Time logic error.\n"));
-              /* NOT REACHED */
-           }
-           *p++ = 0;                 /* separate two halves */
-           code = atoi(lc->str);
-           len = strlen(p);
-            if (len > 2 && p[len-1] == 'm') {
-               if (p[len-2] == 'a') {
-                 pm = 0;
-               } else if (p[len-2] == 'p') {
-                 pm = 1;
-              } else {
-                  scan_err0(lc, _("Bad time specification."));
-                 /* NOT REACHED */
-              }
+           if (code < code2) {
+              set_bits(code, code2, lrun.wday);
            } else {
-              pm = 0;
-           }
-           code2 = atoi(p);
-           if (pm) {
-              code += 12;
-           }
-           if (code < 0 || code > 23 || code2 < 0 || code2 > 59) {
-               scan_err0(lc, _("Bad time specification."));
-              /* NOT REACHED */
-           }
-           set_bit(code, lrun.hour);
-           lrun.minute = code2;
-           have_hour = TRUE;
-           break;
-        case s_at:
-           have_at = TRUE;
-           break;
-        case s_range:
-            p = strchr(lc->str, '-');
-           if (!p) {
-               scan_err0(lc, _("Range logic error.\n"));
-           }
-           *p++ = 0;                 /* separate two halves */
-
-           /* Check for day range */
-           if (is_num(lc->str) && is_num(p)) {
-              code = atoi(lc->str) - 1;
-              code2 = atoi(p) - 1;
-              if (code < 0 || code > 30 || code2 < 0 || code2 > 30) {
-                  scan_err0(lc, _("Bad day range specification."));
-              }
-              if (!have_mday) {
-                 clear_bits(0, 30, lrun.mday);
-                 clear_bits(0, 6, lrun.wday);
-                 have_mday = TRUE;
-              }
-              if (code < code2) {
-                 set_bits(code, code2, lrun.mday);
-              } else {
-                 set_bits(code, 30, lrun.mday);
-                 set_bits(0, code2, lrun.mday);
-              }
-              break;
+              set_bits(code, 6, lrun.wday);
+              set_bits(0, code2, lrun.wday);
            }
-
-           /* lookup first half of keyword range (week days or months) */
-           lcase(lc->str);
-           for (i=0; keyw[i].name; i++) {
-              if (strcmp(lc->str, keyw[i].name) == 0) {
-                 state = keyw[i].state;
-                 code   = keyw[i].code;
-                 i = 0;
-                 break;
-              }
-           }
-           if (i != 0 || (state != s_month && state != s_wday && state != s_wpos)) {
-               scan_err0(lc, _("Invalid month, week or position day range"));
-              /* NOT REACHED */
+        } else if (state == s_month) {
+           if (!have_month) {
+              clear_bits(0, 30, lrun.month);
+              have_month = TRUE;
            }
-
-           /* Lookup end of range */
-           lcase(p);
-           for (i=0; keyw[i].name; i++) {
-              if (strcmp(p, keyw[i].name) == 0) {
-                 state2  = keyw[i].state;
-                 code2   = keyw[i].code;
-                 i = 0;
-                 break;
-              }
+           if (code < code2) {
+              set_bits(code, code2, lrun.month);
+           } else {
+              /* this is a bit odd, but we accept it anyway */
+              set_bits(code, 30, lrun.month);
+              set_bits(0, code2, lrun.month);
            }
-           if (i != 0 || state != state2 || code == code2) {
-               scan_err0(lc, _("Invalid month, weekday or position range"));
-              /* NOT REACHED */
+        } else {
+           /* Must be position */
+           if (!have_wpos) {
+              clear_bits(0, 4, lrun.wpos);
+              have_wpos = TRUE;
            }
-           if (state == s_wday) {
-              if (!have_wday) {
-                 clear_bits(0, 6, lrun.wday);
-                 clear_bits(0, 30, lrun.mday);
-                 have_wday = TRUE;
-              }
-              if (code < code2) {
-                 set_bits(code, code2, lrun.wday);
-              } else {
-                 set_bits(code, 6, lrun.wday);
-                 set_bits(0, code2, lrun.wday);
-              }
-           } else if (state == s_month) {
-              if (!have_month) {
-                 clear_bits(0, 30, lrun.month);
-                 have_month = TRUE;
-              }
-              if (code < code2) {
-                 set_bits(code, code2, lrun.month);
-              } else {
-                 /* this is a bit odd, but we accept it anyway */
-                 set_bits(code, 30, lrun.month);
-                 set_bits(0, code2, lrun.month);
-              }
+           if (code < code2) {
+              set_bits(code, code2, lrun.wpos);
            } else {
-              /* Must be position */
-              if (!have_wpos) {
-                 clear_bits(0, 4, lrun.wpos);
-                 have_wpos = TRUE;
-              }
-              if (code < code2) {
-                 set_bits(code, code2, lrun.wpos);
-              } else {
-                 set_bits(code, 4, lrun.wpos);
-                 set_bits(0, code2, lrun.wpos);
-              }
-           }                      
-           break;
-        case s_hourly:
-           clear_defaults();
-           set_bits(0, 23, lrun.hour);
-           set_bits(0, 30, lrun.mday);
-           set_bits(0, 11, lrun.month);
-           set_bits(0, 4, lrun.wpos);
-           break;
-        case s_weekly:
-           clear_defaults();
-           set_bit(0, lrun.wday);
-           set_bits(0, 11, lrun.month);
-           set_bits(0, 4, lrun.wpos);
-           break;
-        case s_daily:
-           clear_defaults();
-           set_bits(0, 30, lrun.mday);
-           set_bits(0, 11, lrun.month);
-           set_bits(0, 4,  lrun.wpos);
-           break;
-        case s_monthly:
-           clear_defaults();
-           set_bits(0, 11, lrun.month);
-           set_bits(0, 4,  lrun.wpos);
-           break;
-        default:
-            scan_err0(lc, _("Unexpected run state\n"));
-           /* NOT REACHED */
-           break;
+              set_bits(code, 4, lrun.wpos);
+              set_bits(0, code2, lrun.wpos);
+           }
+        }                      
+        break;
+      case s_hourly:
+        clear_defaults();
+        set_bits(0, 23, lrun.hour);
+        set_bits(0, 30, lrun.mday);
+        set_bits(0, 11, lrun.month);
+        set_bits(0, 4, lrun.wpos);
+        break;
+      case s_weekly:
+        clear_defaults();
+        set_bit(0, lrun.wday);
+        set_bits(0, 11, lrun.month);
+        set_bits(0, 4, lrun.wpos);
+        break;
+      case s_daily:
+        clear_defaults();
+        set_bits(0, 30, lrun.mday);
+        set_bits(0, 11, lrun.month);
+        set_bits(0, 4,  lrun.wpos);
+        break;
+      case s_monthly:
+        clear_defaults();
+        set_bits(0, 11, lrun.month);
+        set_bits(0, 4,  lrun.wpos);
+        break;
+      default:
+         scan_err0(lc, _("Unexpected run state\n"));
+        /* NOT REACHED */
+        break;
       }
    }
 
index b09bde218019dddef2bbeb6bdfd1c35b84af131b..ba90a83938c96e867309af9dbb17993b8d0fd2e7 100644 (file)
@@ -477,12 +477,14 @@ int bopen(BFILE *bfd, const char *fname, int flags, mode_t mode)
 {
    bfd->fid = open(fname, flags, mode);
    bfd->berrno = errno;
+   Dmsg1(50, "Open file %d\n", bfd->fid);
    return bfd->fid;
 }
 
 int bclose(BFILE *bfd)
 { 
    int stat;  
+   Dmsg1(50, "Close file %d\n", bfd->fid);
    stat = close(bfd->fid);
    bfd->berrno = errno;
    bfd->fid = -1;
index 2900f998d9c0eee9a01cac18062cb9d7438a4344..766120df91609dea4be2a6347c58609c9b6a9501 100644 (file)
@@ -170,6 +170,9 @@ int create_file(JCR *jcr, ATTR *attr, BFILE *bfd, int replace)
            mode |= O_CTG;               /* set contiguous bit if needed */
         }
          Dmsg1(50, "Create file: %s\n", attr->ofname);
+        if (is_bopen(bfd)) {
+            Jmsg1(jcr, M_ERROR, 0, "bpkt already open fid=%d\n", bfd->fid);
+        }
         if ((bopen(bfd, attr->ofname, mode, S_IRUSR | S_IWUSR)) < 0) {
             Jmsg2(jcr, M_ERROR, 0, _("Could not create %s: ERR=%s\n"), 
                  attr->ofname, berror(bfd));
@@ -205,6 +208,9 @@ int create_file(JCR *jcr, ATTR *attr, BFILE *bfd, int replace)
            } else {
               tid = NULL;
            }
+           if (is_bopen(bfd)) {
+               Jmsg1(jcr, M_ERROR, 0, "bpkt already open fid=%d\n", bfd->fid);
+           }
            if ((bopen(bfd, attr->ofname, mode, 0)) < 0) {
                Jmsg2(jcr, M_ERROR, 0, _("Could not open %s: ERR=%s\n"), 
                     attr->ofname, berror(bfd));
@@ -248,6 +254,9 @@ int create_file(JCR *jcr, ATTR *attr, BFILE *bfd, int replace)
        *   and saved.
        */
       if (!is_portable_backup(bfd)) {
+        if (is_bopen(bfd)) {
+            Jmsg1(jcr, M_ERROR, 0, "bpkt already open fid=%d\n", bfd->fid);
+        }
         if ((bopen(bfd, attr->ofname, O_WRONLY|O_BINARY, 0)) < 0) {
             Jmsg2(jcr, M_ERROR, 0, _("Could not open %s: ERR=%s\n"), 
                  attr->ofname, berror(bfd));
index 6b612deb0a711cead969af7704a73fac5ec104af..2c68d7a2e1e0ee3eb967a342022557e225216c4c 100755 (executable)
@@ -191,69 +191,69 @@ void store_msgs(LEX *lc, struct res_items *item, int index, int pass)
    Dmsg2(200, "store_msgs pass=%d code=%d\n", pass, item->code);
    if (pass == 1) {
       switch (item->code) {
-        case MD_STDOUT:
-        case MD_STDERR:
-        case MD_SYSLOG:              /* syslog */
-        case MD_CONSOLE:
-           scan_types(lc, (MSGS *)(item->value), item->code, NULL, NULL);
-           break;
-        case MD_OPERATOR:            /* send to operator */
-        case MD_DIRECTOR:            /* send to Director */
-        case MD_MAIL:                /* mail */
-        case MD_MAIL_ON_ERROR:       /* mail if Job errors */
-           if (item->code == MD_OPERATOR) {
-              cmd = res_all.res_msgs.operator_cmd;
-           } else {
-              cmd = res_all.res_msgs.mail_cmd;
-           }
-           dest = get_pool_memory(PM_MESSAGE);
-           dest[0] = 0;
-           dest_len = 0;
-           /* Pick up comma separated list of destinations */
-           for ( ;; ) {
-              token = lex_get_token(lc, T_NAME);   /* scan destination */
-              dest = check_pool_memory_size(dest, dest_len + lc->str_len + 2);
-              if (dest[0] != 0) {
-                  strcat(dest, " ");  /* separate multiple destinations with space */
-                 dest_len++;
-              }
-              strcat(dest, lc->str);
-              dest_len += lc->str_len;
-               Dmsg2(100, "store_msgs newdest=%s: dest=%s:\n", lc->str, NPRT(dest));
-              token = lex_get_token(lc, T_ALL);
-              if (token == T_COMMA) { 
-                 continue;           /* get another destination */
-              }
-              if (token != T_EQUALS) {
-                  scan_err1(lc, "expected an =, got: %s", lc->str); 
-              }
-              break;
-           }
-            Dmsg1(200, "mail_cmd=%s\n", NPRT(cmd));
-           scan_types(lc, (MSGS *)(item->value), item->code, dest, cmd);
-           free_pool_memory(dest);
-            Dmsg0(200, "done with dest codes\n");
-           break;
-        case MD_FILE:                /* file */
-        case MD_APPEND:              /* append */
-           dest = get_pool_memory(PM_MESSAGE);
-           /* Pick up a single destination */
+      case MD_STDOUT:
+      case MD_STDERR:
+      case MD_SYSLOG:             /* syslog */
+      case MD_CONSOLE:
+        scan_types(lc, (MSGS *)(item->value), item->code, NULL, NULL);
+        break;
+      case MD_OPERATOR:           /* send to operator */
+      case MD_DIRECTOR:           /* send to Director */
+      case MD_MAIL:               /* mail */
+      case MD_MAIL_ON_ERROR:      /* mail if Job errors */
+        if (item->code == MD_OPERATOR) {
+           cmd = res_all.res_msgs.operator_cmd;
+        } else {
+           cmd = res_all.res_msgs.mail_cmd;
+        }
+        dest = get_pool_memory(PM_MESSAGE);
+        dest[0] = 0;
+        dest_len = 0;
+        /* Pick up comma separated list of destinations */
+        for ( ;; ) {
            token = lex_get_token(lc, T_NAME);   /* scan destination */
-           pm_strcpy(&dest, lc->str);
-           dest_len = lc->str_len;
+           dest = check_pool_memory_size(dest, dest_len + lc->str_len + 2);
+           if (dest[0] != 0) {
+               strcat(dest, " ");  /* separate multiple destinations with space */
+              dest_len++;
+           }
+           strcat(dest, lc->str);
+           dest_len += lc->str_len;
+            Dmsg2(100, "store_msgs newdest=%s: dest=%s:\n", lc->str, NPRT(dest));
            token = lex_get_token(lc, T_ALL);
-            Dmsg1(200, "store_msgs dest=%s:\n", NPRT(dest));
+           if (token == T_COMMA) { 
+              continue;           /* get another destination */
+           }
            if (token != T_EQUALS) {
                scan_err1(lc, "expected an =, got: %s", lc->str); 
            }
-           scan_types(lc, (MSGS *)(item->value), item->code, dest, NULL);
-           free_pool_memory(dest);
-            Dmsg0(200, "done with dest codes\n");
            break;
+        }
+         Dmsg1(200, "mail_cmd=%s\n", NPRT(cmd));
+        scan_types(lc, (MSGS *)(item->value), item->code, dest, cmd);
+        free_pool_memory(dest);
+         Dmsg0(200, "done with dest codes\n");
+        break;
+      case MD_FILE:               /* file */
+      case MD_APPEND:             /* append */
+        dest = get_pool_memory(PM_MESSAGE);
+        /* Pick up a single destination */
+        token = lex_get_token(lc, T_NAME);   /* scan destination */
+        pm_strcpy(&dest, lc->str);
+        dest_len = lc->str_len;
+        token = lex_get_token(lc, T_ALL);
+         Dmsg1(200, "store_msgs dest=%s:\n", NPRT(dest));
+        if (token != T_EQUALS) {
+            scan_err1(lc, "expected an =, got: %s", lc->str); 
+        }
+        scan_types(lc, (MSGS *)(item->value), item->code, dest, NULL);
+        free_pool_memory(dest);
+         Dmsg0(200, "done with dest codes\n");
+        break;
 
-        default:
-            scan_err1(lc, "Unknown item code: %d\n", item->code);
-           break;
+      default:
+         scan_err1(lc, "Unknown item code: %d\n", item->code);
+        break;
       }
    }
    scan_to_eol(lc);
@@ -284,7 +284,7 @@ static void scan_types(LEX *lc, MSGS *msg, int dest_code, char *where, char *cmd
         str = &lc->str[0];
       }
       for (i=0; msg_types[i].name; i++) {
-        if (strcmp(str, msg_types[i].name) == 0) {
+        if (strcasecmp(str, msg_types[i].name) == 0) {
            msg_type = msg_types[i].token;
            found = TRUE;
            break;
index b67c1cb526954f48e6e3d13e0cee394cf2f9d505..c3ac6728af3cfbae5520564a33221395aef69021 100644 (file)
@@ -115,7 +115,7 @@ mount_next_vol:
 
       release = 1;                    /* release next time if we "recurse" */
 
-ask_again:
+// ask_again:
       if (ask && !dir_ask_sysop_to_mount_next_volume(jcr, dev)) {
          Dmsg0(100, "Error return ask_sysop ...\n");
         return 0;              /* error return */
@@ -226,7 +226,8 @@ mount_error:
          Jmsg1(jcr, M_WARNING, 0, "%s", jcr->errmsg);                         
          Dmsg0(100, "Default\n");
         ask = true;
-        goto ask_again;
+        /* was - goto ask_again; */         
+        goto mount_next_vol;
       }
       break;
    }
index 51d178023c820ae5fc76984e36d7258bb8876023..236d3b7d8f27ff302fc029e22ea958e1b2dfaeb4 100755 (executable)
@@ -71,28 +71,28 @@ main (int argc, char *const *argv)
 
    while ((ch = getopt(argc, argv, "ad:e:i:?")) != -1) {
       switch (ch) {
-         case 'a':                    /* print extended attributes *debug* */
-           attrs = 1;
-           break;
-
-         case 'd':                    /* set debug level */
-           debug_level = atoi(optarg);
-           if (debug_level <= 0) {
-              debug_level = 1; 
-           }
-           break;
+      case 'a':                       /* print extended attributes *debug* */
+        attrs = 1;
+        break;
+
+      case 'd':                       /* set debug level */
+        debug_level = atoi(optarg);
+        if (debug_level <= 0) {
+           debug_level = 1; 
+        }
+        break;
 
-         case 'e':                    /* exclude patterns */
-           exc = optarg;
-           break;
+      case 'e':                       /* exclude patterns */
+        exc = optarg;
+        break;
 
-         case 'i':                    /* include patterns */
-           inc = optarg;
-           break;
+      case 'i':                       /* include patterns */
+        inc = optarg;
+        break;
 
-         case '?':
-        default:
-           usage();
+      case '?':
+      default:
+        usage();
 
       }  
    }
@@ -200,6 +200,10 @@ static void print_ls_output(char *fname, char *link, int type, struct stat *stat
    char *p, *f;
    int n;
 
+   if (type == FT_LNK) {
+      statp->st_mtime = 0;
+      statp->st_mode |= 0777;
+   }
    p = encode_mode(statp->st_mode, buf);
    n = sprintf(p, " %2d ", (uint32_t)statp->st_nlink);
    p += n;
@@ -213,11 +217,7 @@ static void print_ls_output(char *fname, char *link, int type, struct stat *stat
       n = sprintf(p, "     ");
    }
    p += n;
-   if (type != FT_LNK) {
-      p = encode_time(statp->st_mtime, p);
-   } else {
-      p = encode_time(0, p);
-   }
+   p = encode_time(statp->st_mtime, p);
    *p++ = ' ';
    /* Copy file name */
    for (f=fname; *f && (p-buf) < (int)sizeof(buf); )