]> git.sur5r.net Git - bacula/bacula/blob - bacula/src/lib/bsys.c
Implement RestoreObject for sqlite + cleanups
[bacula/bacula] / bacula / src / lib / bsys.c
1 /*
2    Bacula® - The Network Backup Solution
3
4    Copyright (C) 2000-2011 Free Software Foundation Europe e.V.
5
6    The main author of Bacula is Kern Sibbald, with contributions from
7    many others, a complete list can be found in the file AUTHORS.
8    This program is Free Software; you can redistribute it and/or
9    modify it under the terms of version three of the GNU Affero General Public
10    License as published by the Free Software Foundation and included
11    in the file LICENSE.
12
13    This program is distributed in the hope that it will be useful, but
14    WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16    General Public License for more details.
17
18    You should have received a copy of the GNU Affero General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21    02110-1301, USA.
22
23    Bacula® is a registered trademark of Kern Sibbald.
24    The licensor of Bacula is the Free Software Foundation Europe
25    (FSFE), Fiduciary Program, Sumatrastrasse 25, 8006 Zürich,
26    Switzerland, email:ftf@fsfeurope.org.
27 */
28 /*
29  * Miscellaneous Bacula memory and thread safe routines
30  *   Generally, these are interfaces to system or standard
31  *   library routines.
32  *
33  *  Bacula utility functions are in util.c
34  *
35  */
36
37 #include "bacula.h"
38 #ifdef HAVE_LIBZ
39 #include <zlib.h>
40 #endif
41
42
43 static pthread_mutex_t timer_mutex = PTHREAD_MUTEX_INITIALIZER;
44 static pthread_cond_t timer = PTHREAD_COND_INITIALIZER;
45
46 /*
47  * This routine will sleep (sec, microsec).  Note, however, that if a
48  *   signal occurs, it will return early.  It is up to the caller
49  *   to recall this routine if he/she REALLY wants to sleep the
50  *   requested time.
51  */
52 int bmicrosleep(int32_t sec, int32_t usec)
53 {
54    struct timespec timeout;
55    struct timeval tv;
56    struct timezone tz;
57    int stat;
58
59    timeout.tv_sec = sec;
60    timeout.tv_nsec = usec * 1000;
61
62 #ifdef HAVE_NANOSLEEP
63    stat = nanosleep(&timeout, NULL);
64    if (!(stat < 0 && errno == ENOSYS)) {
65       return stat;
66    }
67    /* If we reach here it is because nanosleep is not supported by the OS */
68 #endif
69
70    /* Do it the old way */
71    gettimeofday(&tv, &tz);
72    timeout.tv_nsec += tv.tv_usec * 1000;
73    timeout.tv_sec += tv.tv_sec;
74    while (timeout.tv_nsec >= 1000000000) {
75       timeout.tv_nsec -= 1000000000;
76       timeout.tv_sec++;
77    }
78
79    Dmsg2(200, "pthread_cond_timedwait sec=%lld usec=%d\n", sec, usec);
80    /* Note, this unlocks mutex during the sleep */
81    P(timer_mutex);
82    stat = pthread_cond_timedwait(&timer, &timer_mutex, &timeout);
83    if (stat != 0) {
84       berrno be;
85       Dmsg2(200, "pthread_cond_timedwait stat=%d ERR=%s\n", stat,
86          be.bstrerror(stat));
87    }
88    V(timer_mutex);
89    return stat;
90 }
91
92 /*
93  * Guarantee that the string is properly terminated */
94 char *bstrncpy(char *dest, const char *src, int maxlen)
95 {
96    strncpy(dest, src, maxlen-1);
97    dest[maxlen-1] = 0;
98    return dest;
99 }
100
101 /*
102  * Guarantee that the string is properly terminated */
103 char *bstrncpy(char *dest, POOL_MEM &src, int maxlen)
104 {
105    strncpy(dest, src.c_str(), maxlen-1);
106    dest[maxlen-1] = 0;
107    return dest;
108 }
109
110 /*
111  * Note: Here the maxlen is the maximum length permitted
112  *  stored in dest, while on Unix systems, it is the maximum characters
113  *  that may be copied from src.
114  */
115 char *bstrncat(char *dest, const char *src, int maxlen)
116 {
117    int len = strlen(dest);
118    if (len < maxlen-1) {
119       strncpy(dest+len, src, maxlen-len-1);
120    }
121    dest[maxlen-1] = 0;
122    return dest;
123 }
124
125 /*
126  * Note: Here the maxlen is the maximum length permitted
127  *  stored in dest, while on Unix systems, it is the maximum characters
128  *  that may be copied from src.
129  */
130 char *bstrncat(char *dest, POOL_MEM &src, int maxlen)
131 {
132    int len = strlen(dest);
133    if (len < maxlen-1) {
134       strncpy(dest+len, src.c_str(), maxlen-len-1);
135    }
136    dest[maxlen-1] = 0;
137    return dest;
138 }
139
140 /*
141  * Allows one or both pointers to be NULL
142  */
143 bool bstrcmp(const char *s1, const char *s2)
144 {
145    if (s1 == s2) return true;
146    if (s1 == NULL || s2 == NULL) return false;
147    return strcmp(s1, s2) == 0;
148 }
149
150 /*
151  * Get character length of UTF-8 string
152  *
153  * Valid UTF-8 codes
154  * U-00000000 - U-0000007F: 0xxxxxxx 
155  * U-00000080 - U-000007FF: 110xxxxx 10xxxxxx 
156  * U-00000800 - U-0000FFFF: 1110xxxx 10xxxxxx 10xxxxxx 
157  * U-00010000 - U-001FFFFF: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx 
158  * U-00200000 - U-03FFFFFF: 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 
159  * U-04000000 - U-7FFFFFFF: 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
160  */
161 int cstrlen(const char *str)
162 {
163    uint8_t *p = (uint8_t *)str;
164    int len = 0;
165    if (str == NULL) {
166       return 0;
167    }
168    while (*p) {
169       if ((*p & 0xC0) != 0xC0) {
170          p++;
171          len++;
172          continue;
173       }
174       if ((*p & 0xD0) == 0xC0) {
175          p += 2;
176          len++;
177          continue;
178       }
179       if ((*p & 0xF0) == 0xD0) {
180          p += 3;
181          len++;
182          continue;
183       }
184       if ((*p & 0xF8) == 0xF0) {
185          p += 4;
186          len++;
187          continue;
188       }
189       if ((*p & 0xFC) == 0xF8) {
190          p += 5;
191          len++;
192          continue;
193       }
194       if ((*p & 0xFE) == 0xFC) {
195          p += 6;
196          len++;
197          continue;
198       }
199       p++;                      /* Shouln't get here but must advance */
200    }
201    return len;
202 }
203
204
205
206 #ifndef bmalloc
207 void *bmalloc(size_t size)
208 {
209   void *buf;
210
211 #ifdef SMARTALLOC
212   buf = sm_malloc(file, line, size);
213 #else
214   buf = malloc(size);
215 #endif
216   if (buf == NULL) {
217      berrno be;
218      Emsg1(M_ABORT, 0, _("Out of memory: ERR=%s\n"), be.bstrerror());
219   }
220   return buf;
221 }
222 #endif
223
224 void *b_malloc(const char *file, int line, size_t size)
225 {
226   void *buf;
227
228 #ifdef SMARTALLOC
229   buf = sm_malloc(file, line, size);
230 #else
231   buf = malloc(size);
232 #endif
233   if (buf == NULL) {
234      berrno be;
235      e_msg(file, line, M_ABORT, 0, _("Out of memory: ERR=%s\n"), be.bstrerror());
236   }
237   return buf;
238 }
239
240
241 void bfree(void *buf)
242 {
243 #ifdef SMARTALLOC
244   sm_free(__FILE__, __LINE__, buf);
245 #else
246   free(buf);
247 #endif
248 }
249
250 void *brealloc (void *buf, size_t size)
251 {
252 #ifdef SMARTALOC
253    buf = sm_realloc(__FILE__, __LINE__, buf, size);
254 #else
255    buf = realloc(buf, size);
256 #endif
257    if (buf == NULL) {
258       berrno be;
259       Emsg1(M_ABORT, 0, _("Out of memory: ERR=%s\n"), be.bstrerror());
260    }
261    return buf;
262 }
263
264
265 void *bcalloc(size_t size1, size_t size2)
266 {
267   void *buf;
268
269    buf = calloc(size1, size2);
270    if (buf == NULL) {
271       berrno be;
272       Emsg1(M_ABORT, 0, _("Out of memory: ERR=%s\n"), be.bstrerror());
273    }
274    return buf;
275 }
276
277 /* Code now in src/lib/bsnprintf.c */
278 #ifndef USE_BSNPRINTF
279
280 #define BIG_BUF 5000
281 /*
282  * Implement snprintf
283  */
284 int bsnprintf(char *str, int32_t size, const char *fmt,  ...)
285 {
286    va_list   arg_ptr;
287    int len;
288
289    va_start(arg_ptr, fmt);
290    len = bvsnprintf(str, size, fmt, arg_ptr);
291    va_end(arg_ptr);
292    return len;
293 }
294
295 /*
296  * Implement vsnprintf()
297  */
298 int bvsnprintf(char *str, int32_t size, const char  *format, va_list ap)
299 {
300 #ifdef HAVE_VSNPRINTF
301    int len;
302    len = vsnprintf(str, size, format, ap);
303    str[size-1] = 0;
304    return len;
305
306 #else
307
308    int len, buflen;
309    char *buf;
310    buflen = size > BIG_BUF ? size : BIG_BUF;
311    buf = get_memory(buflen);
312    len = vsprintf(buf, format, ap);
313    if (len >= buflen) {
314       Emsg0(M_ABORT, 0, _("Buffer overflow.\n"));
315    }
316    memcpy(str, buf, len);
317    str[len] = 0;                /* len excludes the null */
318    free_memory(buf);
319    return len;
320 #endif
321 }
322 #endif /* USE_BSNPRINTF */
323
324 #ifndef HAVE_LOCALTIME_R
325
326 struct tm *localtime_r(const time_t *timep, struct tm *tm)
327 {
328     static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
329     struct tm *ltm,
330
331     P(mutex);
332     ltm = localtime(timep);
333     if (ltm) {
334        memcpy(tm, ltm, sizeof(struct tm));
335     }
336     V(mutex);
337     return ltm ? tm : NULL;
338 }
339 #endif /* HAVE_LOCALTIME_R */
340
341 #ifndef HAVE_READDIR_R
342 #ifndef HAVE_WIN32
343 #include <dirent.h>
344
345 int readdir_r(DIR *dirp, struct dirent *entry, struct dirent **result)
346 {
347     static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
348     struct dirent *ndir;
349     int stat;
350
351     P(mutex);
352     errno = 0;
353     ndir = readdir(dirp);
354     stat = errno;
355     if (ndir) {
356        memcpy(entry, ndir, sizeof(struct dirent));
357        strcpy(entry->d_name, ndir->d_name);
358        *result = entry;
359     } else {
360        *result = NULL;
361     }
362     V(mutex);
363     return stat;
364
365 }
366 #endif
367 #endif /* HAVE_READDIR_R */
368
369
370 int b_strerror(int errnum, char *buf, size_t bufsiz)
371 {
372     static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
373     int stat = 0;
374     const char *msg;
375
376     P(mutex);
377
378     msg = strerror(errnum);
379     if (!msg) {
380        msg = _("Bad errno");
381        stat = -1;
382     }
383     bstrncpy(buf, msg, bufsiz);
384     V(mutex);
385     return stat;
386 }
387
388 #ifdef DEBUG_MEMSET
389 /* These routines are not normally turned on */
390 #undef memset
391 void b_memset(const char *file, int line, void *mem, int val, size_t num)
392 {
393    /* Testing for 2000 byte zero at beginning of Volume block */
394    if (num > 1900 && num < 3000) {
395       Pmsg3(000, _("Memset for %d bytes at %s:%d\n"), (int)num, file, line);
396    }
397    memset(mem, val, num);
398 }
399 #endif
400
401 #if !defined(HAVE_WIN32)
402 static int del_pid_file_ok = FALSE;
403 #endif
404
405 /*
406  * Create a standard "Unix" pid file.
407  */
408 void create_pid_file(char *dir, const char *progname, int port)
409 {
410 #if !defined(HAVE_WIN32)
411    int pidfd, len;
412    int oldpid;
413    char  pidbuf[20];
414    POOLMEM *fname = get_pool_memory(PM_FNAME);
415    struct stat statp;
416
417    Mmsg(&fname, "%s/%s.%d.pid", dir, progname, port);
418    if (stat(fname, &statp) == 0) {
419       /* File exists, see what we have */
420       *pidbuf = 0;
421       if ((pidfd = open(fname, O_RDONLY|O_BINARY, 0)) < 0 ||
422            read(pidfd, &pidbuf, sizeof(pidbuf)) < 0 ||
423            sscanf(pidbuf, "%d", &oldpid) != 1) {
424          berrno be;
425          Emsg2(M_ERROR_TERM, 0, _("Cannot open pid file. %s ERR=%s\n"), fname, 
426                be.bstrerror());
427       }
428       /* Some OSes (IRIX) don't bother to clean out the old pid files after a crash, and
429        * since they use a deterministic algorithm for assigning PIDs, we can have
430        * pid conflicts with the old PID file after a reboot.
431        * The intent the following code is to check if the oldpid read from the pid
432        * file is the same as the currently executing process's pid,
433        * and if oldpid == getpid(), skip the attempt to
434        * kill(oldpid,0), since the attempt is guaranteed to succeed,
435        * but the success won't actually mean that there is an
436        * another Bacula process already running.
437        * For more details see bug #797.
438        */
439        if ((oldpid != (int)getpid()) && (kill(oldpid, 0) != -1 || errno != ESRCH)) {
440          Emsg3(M_ERROR_TERM, 0, _("%s is already running. pid=%d\nCheck file %s\n"),
441                progname, oldpid, fname);
442       }
443       /* He is not alive, so take over file ownership */
444       unlink(fname);                  /* remove stale pid file */
445    }
446    /* Create new pid file */
447    if ((pidfd = open(fname, O_CREAT|O_TRUNC|O_WRONLY|O_BINARY, 0640)) >= 0) {
448       len = sprintf(pidbuf, "%d\n", (int)getpid());
449       write(pidfd, pidbuf, len);
450       close(pidfd);
451       del_pid_file_ok = TRUE;         /* we created it so we can delete it */
452    } else {
453       berrno be;
454       Emsg2(M_ERROR_TERM, 0, _("Could not open pid file. %s ERR=%s\n"), fname, 
455             be.bstrerror());
456    }
457    free_pool_memory(fname);
458 #endif
459 }
460
461
462 /*
463  * Delete the pid file if we created it
464  */
465 int delete_pid_file(char *dir, const char *progname, int port)
466 {
467 #if !defined(HAVE_WIN32)
468    POOLMEM *fname = get_pool_memory(PM_FNAME);
469
470    if (!del_pid_file_ok) {
471       free_pool_memory(fname);
472       return 0;
473    }
474    del_pid_file_ok = FALSE;
475    Mmsg(&fname, "%s/%s.%d.pid", dir, progname, port);
476    unlink(fname);
477    free_pool_memory(fname);
478 #endif
479    return 1;
480 }
481
482 struct s_state_hdr {
483    char id[14];
484    int32_t version;
485    uint64_t last_jobs_addr;
486    uint64_t reserved[20];
487 };
488
489 static struct s_state_hdr state_hdr = {
490    "Bacula State\n",
491    4,
492    0
493 };
494
495 /*
496  * Open and read the state file for the daemon
497  */
498 void read_state_file(char *dir, const char *progname, int port)
499 {
500    int sfd;
501    ssize_t stat;
502    bool ok = false;
503    POOLMEM *fname = get_pool_memory(PM_FNAME);
504    struct s_state_hdr hdr;
505    int hdr_size = sizeof(hdr);
506
507    Mmsg(&fname, "%s/%s.%d.state", dir, progname, port);
508    /* If file exists, see what we have */
509 // Dmsg1(10, "O_BINARY=%d\n", O_BINARY);
510    if ((sfd = open(fname, O_RDONLY|O_BINARY)) < 0) {
511       berrno be;
512       Dmsg3(010, "Could not open state file. sfd=%d size=%d: ERR=%s\n",
513                     sfd, sizeof(hdr), be.bstrerror());
514       goto bail_out;
515    }
516    if ((stat=read(sfd, &hdr, hdr_size)) != hdr_size) {
517       berrno be;
518       Dmsg4(010, "Could not read state file. sfd=%d stat=%d size=%d: ERR=%s\n",
519                     sfd, (int)stat, hdr_size, be.bstrerror());
520       goto bail_out;
521    }
522    if (hdr.version != state_hdr.version) {
523       Dmsg2(010, "Bad hdr version. Wanted %d got %d\n",
524          state_hdr.version, hdr.version);
525       goto bail_out;
526    }
527    hdr.id[13] = 0;
528    if (strcmp(hdr.id, state_hdr.id) != 0) {
529       Dmsg0(000, "State file header id invalid.\n");
530       goto bail_out;
531    }
532 // Dmsg1(010, "Read header of %d bytes.\n", sizeof(hdr));
533    if (!read_last_jobs_list(sfd, hdr.last_jobs_addr)) {
534       goto bail_out;
535    }
536    ok = true;
537 bail_out:
538    if (sfd >= 0) {
539       close(sfd);
540    }
541    if (!ok) {
542       unlink(fname);
543     }
544    free_pool_memory(fname);
545 }
546
547 /*
548  * Write the state file
549  */
550 void write_state_file(char *dir, const char *progname, int port)
551 {
552    int sfd;
553    bool ok = false;
554    POOLMEM *fname = get_pool_memory(PM_FNAME);
555
556    Mmsg(&fname, "%s/%s.%d.state", dir, progname, port);
557    /* Create new state file */
558    unlink(fname);
559    if ((sfd = open(fname, O_CREAT|O_WRONLY|O_BINARY, 0640)) < 0) {
560       berrno be;
561       Dmsg2(000, "Could not create state file. %s ERR=%s\n", fname, be.bstrerror());
562       Emsg2(M_ERROR, 0, _("Could not create state file. %s ERR=%s\n"), fname, be.bstrerror());
563       goto bail_out;
564    }
565    if (write(sfd, &state_hdr, sizeof(state_hdr)) != sizeof(state_hdr)) {
566       berrno be;
567       Dmsg1(000, "Write hdr error: ERR=%s\n", be.bstrerror());
568       goto bail_out;
569    }
570 // Dmsg1(010, "Wrote header of %d bytes\n", sizeof(state_hdr));
571    state_hdr.last_jobs_addr = sizeof(state_hdr);
572    state_hdr.reserved[0] = write_last_jobs_list(sfd, state_hdr.last_jobs_addr);
573 // Dmsg1(010, "write last job end = %d\n", (int)state_hdr.reserved[0]);
574    if (lseek(sfd, 0, SEEK_SET) < 0) {
575       berrno be;
576       Dmsg1(000, "lseek error: ERR=%s\n", be.bstrerror());
577       goto bail_out;
578    }
579    if (write(sfd, &state_hdr, sizeof(state_hdr)) != sizeof(state_hdr)) {
580       berrno be;
581       Pmsg1(000, _("Write final hdr error: ERR=%s\n"), be.bstrerror());
582       goto bail_out;
583    }
584    ok = true;
585 // Dmsg1(010, "rewrote header = %d\n", sizeof(state_hdr));
586 bail_out:
587    if (sfd >= 0) {
588       close(sfd);
589    }
590    if (!ok) {
591       unlink(fname);
592    }
593    free_pool_memory(fname);
594 }
595
596
597 /* BSDI does not have this.  This is a *poor* simulation */
598 #ifndef HAVE_STRTOLL
599 long long int
600 strtoll(const char *ptr, char **endptr, int base)
601 {
602    return (long long int)strtod(ptr, endptr);
603 }
604 #endif
605
606 /*
607  * Bacula's implementation of fgets(). The difference is that it handles
608  *   being interrupted by a signal (e.g. a SIGCHLD).
609  */
610 #undef fgetc
611 char *bfgets(char *s, int size, FILE *fd)
612 {
613    char *p = s;
614    int ch;
615    *p = 0;
616    for (int i=0; i < size-1; i++) {
617       do {
618          errno = 0;
619          ch = fgetc(fd);
620       } while (ch == EOF && ferror(fd) && (errno == EINTR || errno == EAGAIN));
621       if (ch == EOF) {
622          if (i == 0) {
623             return NULL;
624          } else {
625             return s;
626          }
627       }
628       *p++ = ch;
629       *p = 0;
630       if (ch == '\r') { /* Support for Mac/Windows file format */
631          ch = fgetc(fd);
632          if (ch != '\n') { /* Mac (\r only) */
633             (void)ungetc(ch, fd); /* Push next character back to fd */
634          }
635          p[-1] = '\n';
636          break;
637       }
638       if (ch == '\n') {
639          break;
640       }
641    }
642    return s;
643 }
644
645 /*
646  * Make a "unique" filename.  It is important that if
647  *   called again with the same "what" that the result
648  *   will be identical. This allows us to use the file
649  *   without saving its name, and re-generate the name
650  *   so that it can be deleted.
651  */
652 void make_unique_filename(POOLMEM **name, int Id, char *what)
653 {
654    Mmsg(name, "%s/%s.%s.%d.tmp", working_directory, my_name, what, Id);
655 }
656
657 char *escape_filename(const char *file_path)
658 {
659    if (file_path == NULL || strpbrk(file_path, "\"\\") == NULL) {
660       return NULL;
661    }
662
663    char *escaped_path = (char *)bmalloc(2 * (strlen(file_path) + 1));
664    char *cur_char = escaped_path;
665
666    while (*file_path) {
667       if (*file_path == '\\' || *file_path == '"') {
668          *cur_char++ = '\\';
669       }
670
671       *cur_char++ = *file_path++;
672    }
673
674    *cur_char = '\0';
675
676    return escaped_path;
677 }
678
679 /*
680  * Deflate or compress and input buffer.  You must supply an
681  *  output buffer sufficiently long and the length of the
682  *  output buffer. Generally, if the output buffer is the
683  *  same size as the input buffer, it should work (at least
684  *  for text).
685  */
686 int Zdeflate(char *in, int in_len, char *out, int &out_len)
687 {
688 #ifdef HAVE_LIBZ
689    z_stream strm;
690    int ret;
691
692    /* allocate deflate state */
693    strm.zalloc = Z_NULL;
694    strm.zfree = Z_NULL;
695    strm.opaque = Z_NULL;
696    ret = deflateInit(&strm, 9);
697    if (ret != Z_OK) {
698       Dmsg0(200, "deflateInit error\n");
699       (void)deflateEnd(&strm);
700       return ret;
701    }
702
703    strm.next_in = (Bytef *)in;
704    strm.avail_in = in_len;
705    Dmsg1(200, "In: %d bytes\n", strm.avail_in);
706    strm.avail_out = out_len;
707    strm.next_out = (Bytef *)out;
708    ret = deflate(&strm, Z_FINISH);
709    out_len = out_len - strm.avail_out;
710    Dmsg1(200, "compressed=%d\n", out_len);
711    (void)deflateEnd(&strm);
712    return ret;
713 #else
714    return 1;
715 #endif
716 }
717
718 /* 
719  * Inflate or uncompress an input buffer.  You must supply
720  *  and output buffer and an output length sufficiently long
721  *  or there will be an error.  This uncompresses in one call.
722  */
723 int Zinflate(char *in, int in_len, char *out, int &out_len)
724 {
725 #ifdef HAVE_LIBZ
726    z_stream strm;
727    int ret;
728
729    /* allocate deflate state */
730    strm.zalloc = Z_NULL;
731    strm.zfree = Z_NULL;
732    strm.opaque = Z_NULL;
733    strm.next_in = (Bytef *)in;
734    strm.avail_in = in_len;
735    ret = inflateInit(&strm);
736    if (ret != Z_OK) {
737       Dmsg0(200, "inflateInit error\n");
738       (void)inflateEnd(&strm);
739       return ret;
740    }
741
742    Dmsg1(200, "In len: %d bytes\n", strm.avail_in);
743    strm.avail_out = out_len;
744    strm.next_out = (Bytef *)out;
745    ret = inflate(&strm, Z_FINISH);
746    out_len -= strm.avail_out;
747    Dmsg1(200, "Uncompressed=%d\n", out_len);
748    (void)inflateEnd(&strm);
749    return ret;
750 #else
751    return 1;
752 #endif
753 }
754
755 #if HAVE_BACKTRACE && HAVE_GCC
756 #include <cxxabi.h>
757 #include <execinfo.h>
758 void stack_trace()
759 {
760    const size_t max_depth = 100;
761    size_t stack_depth;
762    void *stack_addrs[max_depth];
763    char **stack_strings;
764    
765    stack_depth = backtrace(stack_addrs, max_depth);
766    stack_strings = backtrace_symbols(stack_addrs, stack_depth);
767    
768    for (size_t i = 3; i < stack_depth; i++) {
769       size_t sz = 200; /* just a guess, template names will go much wider */
770       char *function = (char *)actuallymalloc(sz);
771       char *begin = 0, *end = 0;
772       /* find the parentheses and address offset surrounding the mangled name */
773       for (char *j = stack_strings[i]; *j; ++j) {
774          if (*j == '(') {
775             begin = j;
776          } else if (*j == '+') {
777             end = j;
778          }
779       }
780       if (begin && end) {
781          *begin++ = '\0';
782          *end = '\0';
783          /* found our mangled name, now in [begin, end] */
784          
785          int status;
786          char *ret = abi::__cxa_demangle(begin, function, &sz, &status);
787          if (ret) {
788             /* return value may be a realloc() of the input */
789             function = ret;
790          } else {
791             /* demangling failed, just pretend it's a C function with no args */
792             strncpy(function, begin, sz);
793             strncat(function, "()", sz);
794             function[sz-1] = '\0';
795          }
796          Pmsg2(000, "    %s:%s\n", stack_strings[i], function);
797
798       } else {
799          /* didn't find the mangled name, just print the whole line */
800          Pmsg1(000, "    %s\n", stack_strings[i]);
801       }
802       actuallyfree(function);
803    }
804    actuallyfree(stack_strings); /* malloc()ed by backtrace_symbols */
805 }
806 #else /* HAVE_BACKTRACE && HAVE_GCC */
807 void stack_trace() {}
808 #endif /* HAVE_BACKTRACE && HAVE_GCC */