Imported Upstream version 3.1.0
[debian/amanda] / common-src / amanda.h
1 /*
2  * Amanda, The Advanced Maryland Automatic Network Disk Archiver
3  * Copyright (c) 1991-1999 University of Maryland at College Park
4  * All Rights Reserved.
5  *
6  * Permission to use, copy, modify, distribute, and sell this software and its
7  * documentation for any purpose is hereby granted without fee, provided that
8  * the above copyright notice appear in all copies and that both that
9  * copyright notice and this permission notice appear in supporting
10  * documentation, and that the name of U.M. not be used in advertising or
11  * publicity pertaining to distribution of the software without specific,
12  * written prior permission.  U.M. makes no representations about the
13  * suitability of this software for any purpose.  It is provided "as is"
14  * without express or implied warranty.
15  *
16  * U.M. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL U.M.
18  * BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
19  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
20  * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
21  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
22  *
23  * Authors: the Amanda Development Team.  Its members are listed in a
24  * file named AUTHORS, in the root directory of this distribution.
25  */
26 /*
27  * $Id: amanda.h,v 1.131 2006/07/25 18:27:56 martinea Exp $
28  *
29  * the central header file included by all amanda sources
30  */
31 #ifndef AMANDA_H
32 #define AMANDA_H
33
34 #ifdef HAVE_CONFIG_H
35 /* use a relative path here to avoid conflicting with Perl's config.h. */
36 #include "../config/config.h"
37 #endif
38
39 #include <glib.h>
40 #include <glib/gprintf.h>
41
42 #include "amflock.h"
43
44 /*
45  * Force large file source even if configure guesses wrong.
46  */
47 #ifndef _LARGEFILE64_SOURCE
48 #define _LARGEFILE64_SOURCE 1
49 #endif
50
51 #ifndef  _FILE_OFFSET_BITS
52 #define _FILE_OFFSET_BITS 64
53 #endif
54
55 #ifdef HAVE_SYS_TYPES_H
56 #  include <sys/types.h>
57 #endif
58
59 /* gnulib creates this header locally if the system doesn't provide it,
60  * so it uses a local ("") include */
61 #include "stdint.h"
62
63 /*
64  * I would prefer that each Amanda module include only those system headers
65  * that are locally needed, but on most Unixes the system header files are not
66  * protected against multiple inclusion, so this can lead to problems.
67  *
68  * Also, some systems put key files in different places, so by including 
69  * everything here the rest of the system is isolated from such things.
70  */
71
72 /* from the autoconf documentation */
73 #ifdef HAVE_DIRENT_H
74 #  include <dirent.h>
75 #  define NAMLEN(dirent) strlen((dirent)->d_name)
76 #else
77 #  define dirent direct
78 #  define NAMLEN(dirent) (dirent)->d_namlen
79 #  if HAVE_SYS_NDIR_H
80 #    include <sys/ndir.h>
81 #  endif
82 #  if HAVE_SYS_DIR_H
83 #    include <sys/dir.h>
84 #  endif
85 #  if HAVE_NDIR_H
86 #    include <ndir.h>
87 #  endif
88 #endif
89
90 #ifdef ENABLE_NLS
91 #  include <libintl.h>
92 #  include <locale.h>
93 #  define  plural(String1, String2, Count)                              \
94                 (((Count) == 1) ? (String1) : (String2))
95 #else
96 #  define plural(String1, String2, Count)                               \
97                 (((Count) == 1) ? (String1) : (String2))
98 #  define setlocale(Which, Locale)
99 #  define textdomain(Domain)
100 #  define bindtextdomain(Package, Directory)
101 #  define gettext(String)                       String
102 #  define dgettext(Domain, String)              String
103 #  define dcgettext(Domain, String, Catagory)   String
104 #  define ngettext(String1, String2, Count)                             \
105                 plural((String1), (String2), (Count))
106 #  define dngettext(Domain, String1, String2, Count)                    \
107                 plural((String1), (String2), (Count))
108 #  define dcngettext(Domain, String1, String2, Count, Catagory)         \
109                 plural((String1), (String2), (Count))
110 #endif
111 #define T_(String)                      String
112 #ifndef SWIG /* TODO: make this go away */
113 #define _(String)                       dgettext("amanda", (String))
114 #endif
115
116 #ifdef HAVE_FCNTL_H
117 #  include <fcntl.h>
118 #endif
119
120 #ifdef HAVE_GRP_H
121 #  include <grp.h>
122 #endif
123
124 #if defined(USE_DB_H)
125 #  include <db.h>
126 #else
127 #if defined(USE_DBM_H)
128 #  include <dbm.h>
129 #else
130 #if defined(USE_GDBM_H)
131 #  include <gdbm.h>
132 #else
133 #if defined(USE_NDBM_H)
134 #  include <ndbm.h>
135 #endif
136 #endif
137 #endif
138 #endif
139
140 #ifdef TIME_WITH_SYS_TIME
141 #  include <sys/time.h>
142 #  include <time.h>
143 #else
144 #  ifdef HAVE_SYS_TIME_H
145 #    include <sys/time.h>
146 #  else
147 #    include <time.h>
148 #  endif
149 #endif
150
151 #ifdef HAVE_LIBC_H
152 #  include <libc.h>
153 #endif
154
155 #ifdef HAVE_STDLIB_H
156 #  include <stdlib.h>
157 #endif
158
159 #ifdef HAVE_LIBGEN_H
160 #  include <libgen.h>
161 #endif
162
163 #ifdef HAVE_STRING_H
164 #  include <string.h>
165 #endif
166
167 #ifdef HAVE_STRINGS_H
168 #  include <strings.h>
169 #endif
170
171 #ifdef HAVE_SYSLOG_H
172 #  include <syslog.h>
173 #endif
174
175 #ifdef HAVE_MATH_H
176 #  include <math.h>
177 #endif
178
179 #ifdef HAVE_SYS_FILE_H
180 #  include <sys/file.h>
181 #endif
182
183 #ifdef HAVE_SYS_IOCTL_H
184 #  include <sys/ioctl.h>
185 #endif
186
187 #ifdef HAVE_LIMITS_H
188 #include <limits.h>
189 #endif
190
191 #ifdef HAVE_SYS_PARAM_H
192 #  include <sys/param.h>
193 #endif
194
195 #if defined(HAVE_SYS_IPC_H) && defined(HAVE_SYS_SHM_H)
196 #  include <sys/ipc.h>
197 #  include <sys/shm.h>
198 #else
199 #  ifdef HAVE_SYS_MMAN_H
200 #    include <sys/mman.h>
201 #  endif
202 #endif
203
204 #ifdef HAVE_SYS_SELECT_H
205 #  include <sys/select.h>
206 #endif
207
208 #ifdef HAVE_SYS_STAT_H
209 #  include <sys/stat.h>
210 #endif
211
212 #ifdef HAVE_SYS_UIO_H
213 #  include <sys/uio.h>
214 #else
215 struct iovec {
216     void *iov_base;
217     int iov_len;
218 };
219 #endif
220
221 #ifdef HAVE_WAIT_H
222 #  include <wait.h>
223 #endif
224
225 #ifdef HAVE_SYS_WAIT_H
226 #  include <sys/wait.h>
227 #endif
228
229 #ifdef HAVE_STDARG_H
230 #include <stdarg.h>
231 #endif
232
233 #ifdef WAIT_USES_INT
234   typedef int amwait_t;
235 # ifndef WEXITSTATUS
236 #  define WEXITSTATUS(stat_val) (*(unsigned*)&(stat_val) >> 8)
237 # endif
238 # ifndef WTERMSIG
239 #  define WTERMSIG(stat_val) (*(unsigned*)&(stat_val) & 0x7F)
240 # endif
241 # ifndef WIFEXITED
242 #  define WIFEXITED(stat_val) ((*(unsigned*)&(stat_val) & 255) == 0)
243 # endif
244 #else
245 # ifdef WAIT_USES_UNION
246    typedef union wait amwait_t;
247 #  ifndef WEXITSTATUS
248 #  define WEXITSTATUS(stat_val) (((amwait_t*)&(stat_val))->w_retcode)
249 #  endif
250 #  ifndef WTERMSIG
251 #   define WTERMSIG(stat_val) (((amwait_t*)&(stat_val))->w_termsig)
252 #  endif
253 #  ifndef WIFEXITED
254 #   define WIFEXITED(stat_val) (WTERMSIG(stat_val) == 0)
255 #  endif
256 # else
257    typedef int amwait_t;
258 #  ifndef WEXITSTATUS
259 #   define WEXITSTATUS(stat_val) (*(unsigned*)&(stat_val) >> 8)
260 #  endif
261 #  ifndef WTERMSIG
262 #   define WTERMSIG(stat_val) (*(unsigned*)&(stat_val) & 0x7F)
263 #  endif
264 #  ifndef WIFEXITED
265 #   define WIFEXITED(stat_val) ((*(unsigned*)&(stat_val) & 255) == 0)
266 #  endif
267 # endif
268 #endif
269
270 #ifndef WIFSIGNALED
271 # define WIFSIGNALED(stat_val)  (WTERMSIG(stat_val) != 0)
272 #endif
273
274 #ifdef HAVE_UNISTD_H
275 #  include <unistd.h>
276 #endif
277
278 #ifdef HAVE_NETINET_IN_H
279 #  include <netinet/in.h>
280 #endif
281
282 #include <ctype.h>
283 #include <errno.h>
284 #include <pwd.h>
285 #include <signal.h>
286 #include <setjmp.h>
287 #include <stdio.h>
288 #include <sys/resource.h>
289 #include <sys/socket.h>
290
291 #ifdef WORKING_IPV6
292 #define INET6
293 #endif
294
295 #ifndef INET_ADDRSTRLEN
296 #define INET_ADDRSTRLEN 16
297 #endif
298
299 #if !defined(HAVE_SIGACTION) && defined(HAVE_SIGVEC)
300 /* quick'n'dirty hack for NextStep31 */
301 #  define sa_flags sv_flags
302 #  define sa_handler sv_handler
303 #  define sa_mask sv_mask
304 #  define sigaction sigvec
305 #  define sigemptyset(mask) /* no way to clear pending signals */
306 #endif
307
308 /*
309  * Most Unixen declare errno in <errno.h>, some don't.  Some multithreaded
310  * systems have errno as a per-thread macro.  So, we have to be careful.
311  */
312 #ifndef errno
313 extern int errno;
314 #endif
315
316 /*
317  * Some compilers have int for type of sizeof() some use size_t.
318  * size_t is the one we want...
319  */
320 #define SIZEOF(x)       (size_t)sizeof(x)
321
322
323 /*
324  * Some older BSD systems don't have these FD_ macros, so if not, provide them.
325  */
326 #if !defined(FD_SET) || defined(LINT) || defined(__lint)
327 #  undef FD_SETSIZE
328 #  define FD_SETSIZE      (int)(SIZEOF(fd_set) * CHAR_BIT)
329
330 #  undef FD_SET
331 #  define FD_SET(n, p)    (((fd_set *)(p))->fds_bits[(n)/WORD_BIT] |= (int)((1 << ((n) % WORD_BIT))))
332
333 #  undef FD_CLR
334 #  define FD_CLR(n, p)    (((fd_set *)(p))->fds_bits[(n)/WORD_BIT] &= (int)(~(1 << ((n) % WORD_BIT))))
335
336 #  undef FD_ISSET
337 #  define FD_ISSET(n, p)  (((fd_set *)(p))->fds_bits[(n)/WORD_BIT] & (1 << ((n) % WORD_BIT)))
338
339 #  undef FD_ZERO
340 #  define FD_ZERO(p)      memset((p), 0, SIZEOF(*(p)))
341 #endif
342
343 #ifndef FD_COPY
344 #  define FD_COPY(p, q)   memcpy((q), (p), SIZEOF(*(p)))
345 #endif
346
347
348 /*
349  * Define MAX_HOSTNAME_LENGTH as the size of arrays to hold hostname's.
350  */
351 #undef  MAX_HOSTNAME_LENGTH
352 #define MAX_HOSTNAME_LENGTH 1025
353
354 /*
355  * If void is broken, substitute char.
356  */
357 #ifdef BROKEN_VOID
358 #  define void char
359 #endif
360
361 #define stringize(x) #x
362 #define stringconcat(x, y) x ## y
363
364 /* amanda #days calculation, with roundoff */
365
366 #define SECS_PER_DAY    (24*60*60)
367 #define days_diff(a, b) (int)(((b) - (a) + SECS_PER_DAY/2) / SECS_PER_DAY)
368
369 /* Global constants.  */
370 #ifndef AMANDA_SERVICE_NAME
371 #define AMANDA_SERVICE_NAME "amanda"
372 #endif
373 #ifndef KAMANDA_SERVICE_NAME
374 #define KAMANDA_SERVICE_NAME "kamanda"
375 #endif
376 #ifndef SERVICE_SUFFIX
377 #define SERVICE_SUFFIX ""
378 #endif
379 #ifndef AMANDA_SERVICE_DEFAULT
380 #define AMANDA_SERVICE_DEFAULT  ((in_port_t)10080)
381 #endif
382 #ifndef KAMANDA_SERVICE_DEFAULT
383 #define KAMANDA_SERVICE_DEFAULT ((in_port_t)10081)
384 #endif
385
386 #define am_round(v,u)   ((((v) + (u) - 1) / (u)) * (u))
387 #define am_floor(v,u)   (((v) / (u)) * (u))
388
389 /* Holding disk block size.  Do not even think about changint this!  :-) */
390 #define DISK_BLOCK_KB           32
391 #define DISK_BLOCK_BYTES        (DISK_BLOCK_KB * 1024)
392
393 /* Maximum length of tape label, plus one for null-terminator. */
394 #define MAX_TAPE_LABEL_LEN (10240)
395 #define MAX_TAPE_LABEL_BUF (MAX_TAPE_LABEL_LEN+1)
396 #define MAX_TAPE_LABEL_FMT "%10240s"
397
398 /* Unfortunately, the system-level sockaddr_storage definition can lead to
399  * C aliasing errors (where the optimizer doesn't notice that two operations
400  * affect the same datum).  We define our own similar type as a union.
401  */
402 typedef union sockaddr_union {
403     struct sockaddr         sa;
404     struct sockaddr_in      sin;
405 #ifdef WORKING_IPV6
406     struct sockaddr_in6     sin6;
407 #endif
408 #ifdef HAVE_SOCKADDR_STORAGE
409     struct sockaddr_storage ss; /* not used; just here to make the union full-size */
410 #endif
411 } sockaddr_union;
412
413 #include "debug.h"
414 #include "file.h"
415
416 void *debug_alloc(const char *file, int line, size_t size);
417 void *debug_newalloc(const char *file, int line, void *old, size_t size);
418 char *debug_stralloc(const char *file, int line, const char *str);
419 char *debug_newstralloc(const char *file, int line,
420                 char *oldstr, const char *newstr);
421 char *debug_vstralloc(const char *file, int line, const char *str, ...);
422 char *debug_newvstralloc(const char *file, int line,
423                 char *oldstr, const char *str, ...);
424 char *debug_vstrallocf(const char *file, int line, const char *fmt,
425                 ...) G_GNUC_PRINTF(3, 4);
426 char *debug_newvstrallocf(const char *file, int line, char *oldstr,
427                 const char *fmt, ...) G_GNUC_PRINTF(4, 5);
428
429 /* Usage: vstrextend(foo, "bar, "baz", NULL). Extends the existing 
430  * string, or allocates a brand new one. */
431 char *debug_vstrextend(const char *file, int line, char **oldstr, ...);
432
433 #define alloc(s)                debug_alloc(__FILE__, __LINE__, (s))
434 #define newalloc(p,s)           debug_newalloc(__FILE__, __LINE__, (p), (s))
435 #define stralloc(s)             debug_stralloc(__FILE__, __LINE__, (s))
436 #define newstralloc(p,s)        debug_newstralloc(__FILE__, __LINE__, (p), (s))
437 #define vstralloc(...)          debug_vstralloc(__FILE__,__LINE__,__VA_ARGS__)
438 #define newvstralloc(...)       debug_newvstralloc(__FILE__,__LINE__,__VA_ARGS__)
439 #define vstrallocf(...)         debug_vstrallocf(__FILE__,__LINE__,__VA_ARGS__)
440 #define newvstrallocf(...)      debug_newvstrallocf(__FILE__,__LINE__,__VA_ARGS__)
441 #define vstrextend(...)         debug_vstrextend(__FILE__,__LINE__,__VA_ARGS__)
442
443 #define stralloc2(s1,s2)        vstralloc((s1),(s2),NULL)
444 #define newstralloc2(p,s1,s2)   newvstralloc((p),(s1),(s2),NULL)
445
446 #define vstrallocf(...)         debug_vstrallocf(__FILE__,__LINE__,__VA_ARGS__)
447
448 /*@only@*/ /*@null@*/ char *debug_agets(const char *file, int line, FILE *f);
449 /*@only@*/ /*@null@*/ char *debug_areads(const char *file, int line, int fd);
450 #define agets(f)              debug_agets(__FILE__,__LINE__,(f))
451 #define areads(f)             debug_areads(__FILE__,__LINE__,(f))
452
453 extern int debug_amtable_alloc(const char *file,
454                                   int line,
455                                   void **table,
456                                   size_t *current,
457                                   size_t elsize,
458                                   size_t count,
459                                   int bump,
460                                   void (*init_func)(void *));
461
462 #define amtable_alloc(t,c,s,n,b,f) debug_amtable_alloc(__FILE__,      \
463                                                      __LINE__,        \
464                                                      (t),             \
465                                                      (c),             \
466                                                      (s),             \
467                                                      (n),             \
468                                                      (b),             \
469                                                      (f))
470
471 extern void amtable_free(void **, size_t *);
472
473 char ** safe_env(void);
474
475 time_t  unctime(char *timestr);
476
477 /*
478  * amfree(ptr) -- if allocated, release space and set ptr to NULL.
479  *
480  * In general, this should be called instead of just free(), unless
481  * the very next source line sets the pointer to a new value.
482  */
483
484 #define amfree(ptr) do {                                                \
485     if((ptr) != NULL) {                                                 \
486         int e__errno = errno;                                           \
487         free(ptr);                                                      \
488         (ptr) = NULL;                                                   \
489         errno = e__errno;                                               \
490         (void)(ptr);  /* Fix value never used warning at end of routines */ \
491     }                                                                   \
492 } while (0)
493
494 #define strappend(s1,s2) do {                                           \
495     char *t_t_t = (s1) ? stralloc2((s1),(s2)) : stralloc((s2));         \
496     amfree((s1));                                                       \
497     (s1) = t_t_t;                                                       \
498 } while(0)
499
500 /*
501  * Return the number of elements in an array.
502  */
503 #define am_countof(a)   (int)(SIZEOF(a) / SIZEOF((a)[0]))
504
505 /*
506  * min/max.  Don't do something like
507  *
508  *    x = min(y++, z);
509  *
510  * because the increment will be duplicated.
511  */
512 #undef min
513 #undef max
514 #define min(a, b)       ((a) < (b) ? (a) : (b))
515 #define max(a, b)       ((a) > (b) ? (a) : (b))
516
517 /*
518  * Utility bitmask manipulation macros.
519  */
520 #define SET(t, f)       ((t) |= (f))
521 #define CLR(t, f)       ((t) &= ~((unsigned)(f)))
522 #define ISSET(t, f)     ((t) & (f))
523
524 /*
525  * Utility string macros.  All assume a variable holds the current
526  * character and the string pointer points to the next character to
527  * be processed.  Typical setup is:
528  *
529  *  s = buffer;
530  *  ch = *s++;
531  *  skip_whitespace(s, ch);
532  *  ...
533  *
534  * If you advance the pointer "by hand" to skip over something, do
535  * it like this:
536  *
537  *  s += some_amount;
538  *  ch = s[-1];
539  *
540  * Note that ch has the character at the end of the just skipped field.
541  * It is often useful to terminate a string, make a copy, then restore
542  * the input like this:
543  *
544  *  skip_whitespace(s, ch);
545  *  fp = s-1;                   ## save the start
546  *  skip_nonwhitespace(s, ch);  ## find the end
547  *  p[-1] = '\0';               ## temporary terminate
548  *  field = stralloc(fp);       ## make a copy
549  *  p[-1] = ch;                 ## restore the input
550  *
551  * The scanning macros are:
552  *
553  *  skip_whitespace (ptr, var)
554  *    -- skip whitespace, but stops at a newline
555  *  skip_non_whitespace (ptr, var)
556  *    -- skip non whitespace
557  *  skip_non_whitespace_cs (ptr, var)
558  *    -- skip non whitespace, stop at comment
559  *  skip_integer (ptr, var)
560  *    -- skip an integer field
561  *  skip_line (ptr, var)
562  *    -- skip just past the next newline
563  *  strncmp_const (str, const_str)
564  *    -- compare str to const_str, a string constant
565  *  strncmp_const_skip (str, const_var, ptr, var)
566  *    -- like strncmp_const, but skip the string if a match is
567  *       found; this macro only tests for equality, discarding
568  *       ordering information.
569  *
570  * where:
571  *
572  *  ptr -- string pointer
573  *  var -- current character
574  *
575  * These macros copy a non-whitespace field to a new buffer, and should
576  * only be used if dynamic allocation is impossible (fixed size buffers
577  * are asking for trouble):
578  *
579  *  copy_string (ptr, var, field, len, fldptr)
580  *    -- copy a non-whitespace field
581  *  copy_string_cs (ptr, var, field, len, fldptr)
582  *    -- copy a non-whitespace field, stop at comment
583  *
584  * where:
585  *
586  *  ptr -- string pointer
587  *  var -- current character
588  *  field -- area to copy to
589  *  len -- length of area (needs room for null byte)
590  *  fldptr -- work pointer used in move
591  *            if NULL on exit, the field was too small for the input
592  */
593
594 #define STR_SIZE        4096            /* a generic string buffer size */
595 #define NUM_STR_SIZE    128             /* a generic number buffer size */
596
597 #define skip_whitespace(ptr,c) do {                                     \
598     while((c) != '\n' && g_ascii_isspace((int)c)) (c) = *(ptr)++;               \
599 } while(0)
600
601 #define skip_non_whitespace(ptr,c) do {                                 \
602     while((c) != '\0' && !g_ascii_isspace((int)c)) (c) = *(ptr)++;              \
603 } while(0)
604
605 #define skip_non_whitespace_cs(ptr,c) do {                              \
606     while((c) != '\0' && (c) != '#' && !g_ascii_isspace((int)c)) (c) = *(ptr)++;\
607 } while(0)
608
609 #define skip_non_integer(ptr,c) do {                                    \
610     while((c) != '\0' && !isdigit(c)) (c) = *(ptr)++;                   \
611 } while(0)
612
613 #define skip_integer(ptr,c) do {                                        \
614     if((c) == '+' || (c) == '-') (c) = *(ptr)++;                        \
615     while(isdigit(c)) (c) = *(ptr)++;                                   \
616 } while(0)
617
618 #define skip_quoted_string(ptr, c) do {                                 \
619     int iq = 0;                                                         \
620     while (((c) != '\0') && !((iq == 0) && g_ascii_isspace((int)c))) {          \
621         if ((c) == '"') {                                               \
622             iq = !iq;                                                   \
623         } else if ((c) == '\\') {                                       \
624             if (*ptr)   /* not last character */                        \
625                 (ptr)++;                                                \
626         }                                                               \
627         (c) = *(ptr)++;                                                 \
628     }                                                                   \
629 } while (0)
630
631 #define skip_quoted_line(ptr, c) do {                                   \
632     int iq = 0;                                                         \
633     while((c) && !((iq == 0) && ((c) == '\n'))) {                       \
634         if ((c) == '"')                                                 \
635             iq = !iq;                                                   \
636         (c) = *(ptr)++;                                                 \
637     }                                                                   \
638     if(c)                                                               \
639         (c) = *(ptr)++;                                                 \
640 } while(0)
641
642 #define skip_line(ptr,c) do {                                           \
643     while((c) && (c) != '\n')                                           \
644         (c) = *(ptr)++;                                                 \
645     if(c)                                                               \
646         (c) = *(ptr)++;                                                 \
647 } while(0)
648
649 #define copy_string(ptr,c,f,l,fp) do {                                  \
650     (fp) = (f);                                                         \
651     while((c) != '\0' && !g_ascii_isspace((int)c)) {                            \
652         if((fp) >= (f) + (l) - 1) {                                     \
653             *(fp) = '\0';                                               \
654             (fp) = NULL;                                                \
655             (void)(fp);  /* Fix value never used warning at end of routines */ \
656             break;                                                      \
657         }                                                               \
658         *(fp)++ = (c);                                                  \
659         (c) = *(ptr)++;                                                 \
660     }                                                                   \
661     if(fp)                                                              \
662         *fp = '\0';                                                     \
663 } while(0)
664
665 #define copy_string_cs(ptr,c,f,l,fp) do {                               \
666     (fp) = (f);                                                         \
667     while((c) != '\0' && (c) != '#' && !g_ascii_isspace((int)c)) {              \
668         if((fp) >= (f) + (l) - 1) {                                     \
669             *(fp) = '\0';                                               \
670             (fp) = NULL;                                                \
671             break;                                                      \
672         }                                                               \
673         *(fp)++ = (c);                                                  \
674         (c) = *(ptr)++;                                                 \
675     }                                                                   \
676     if(fp) *fp = '\0';                                                  \
677 } while(0)
678
679 #define is_dot_or_dotdot(s)                                             \
680     ((s)[0] == '.'                                                      \
681      && ((s)[1] == '\0'                                                 \
682          || ((s)[1] == '.' && (s)[2] == '\0')))
683
684 #define strncmp_const(str, cnst)                                        \
685         strncmp((str), (cnst), sizeof((cnst))-1)
686
687 /* (have to roll this up in an expression, so it can be used in if()) */
688 #define strncmp_const_skip(str, cnst, ptr, var)                         \
689         ((strncmp((str), (cnst), sizeof((cnst))-1) == 0)?               \
690                  ((ptr)+=sizeof((cnst))-1, (var)=(ptr)[-1], 0)          \
691                 :1)
692
693 /* from old bsd-security.c */
694 extern int debug;
695 extern int check_security(sockaddr_union *, char *, unsigned long, char **);
696
697 /*
698  * Handle functions which are not always declared on all systems.  This
699  * stops gcc -Wall and lint from complaining.
700  */
701
702 /* AIX #defines accept, and provides a prototype for the alternate name */
703 #if !defined(HAVE_ACCEPT_DECL) && !defined(accept)
704 extern int accept(int s, struct sockaddr *addr, socklen_t_equiv *addrlen);
705 #endif
706
707 #ifndef HAVE_ATOF_DECL
708 extern double atof(const char *ptr);
709 #endif
710
711 #ifndef HAVE_BCOPY
712 # define bcopy(from,to,n) ((void)memmove((to), (from), (n)))
713 #else
714 # ifndef HAVE_BCOPY_DECL
715 extern void bcopy(const void *s1, void *s2, size_t n);
716 # endif
717 #endif
718
719 #ifndef HAVE_BIND_DECL
720 extern int bind(int s, const struct sockaddr *name, socklen_t_equiv namelen);
721 #endif
722
723 #ifndef HAVE_BZERO
724 #define bzero(s,n) ((void)memset((s),0,(n)))
725 #else
726 # ifndef HAVE_BZERO_DECL
727 extern void bzero(void *s, size_t n);
728 # endif
729 #endif
730
731 #ifndef HAVE_CLOSELOG_DECL
732 extern void closelog(void);
733 #endif
734
735 #ifndef HAVE_CONNECT_DECL
736 extern int connect(int s, struct sockaddr *name, socklen_t_equiv namelen);
737 #endif
738
739 #ifndef HAVE_FCLOSE_DECL
740 extern int fclose(FILE *stream);
741 #endif
742
743 #ifndef HAVE_FFLUSH_DECL
744 extern int fflush(FILE *stream);
745 #endif
746
747 #ifndef HAVE_FPRINTF_DECL
748 extern int fprintf(FILE *stream, const char *format, ...);
749 #endif
750
751 #ifndef HAVE_FPUTC_DECL
752 extern int fputc(int c, FILE *stream);
753 #endif
754
755 #ifndef HAVE_FPUTS_DECL
756 extern int fputs(const char *s, FILE *stream);
757 #endif
758
759 #ifndef HAVE_FREAD_DECL
760 extern size_t fread(void *ptr, size_t size, size_t nitems, FILE *stream);
761 #endif
762
763 #ifndef HAVE_FSEEK_DECL
764 extern int fseek(FILE *stream, long offset, int ptrname);
765 #endif
766
767 #ifndef HAVE_FWRITE_DECL
768 extern size_t fwrite(const void *ptr, size_t size, size_t nitems,
769                         FILE *stream);
770 #endif
771
772 #ifndef HAVE_GETHOSTNAME_DECL
773 extern int gethostname(char *name, int namelen);
774 #endif
775
776 #ifndef HAVE_GETOPT_DECL
777 extern char *optarg;
778 extern int getopt(int argc, char * const *argv, const char *optstring);
779 #endif
780
781 /* AIX #defines getpeername, and provides a prototype for the alternate name */
782 #if !defined(HAVE_GETPEERNAME_DECL) && !defined(getpeername)
783 extern int getpeername(int s, struct sockaddr *name, socklen_t_equiv *namelen);
784 #endif
785
786 /* AIX #defines getsockname, and provides a prototype for the alternate name */
787 #if !defined(HAVE_GETSOCKNAME_DECL) && !defined(getsockname)
788 extern int getsockname(int s, struct sockaddr *name, socklen_t_equiv *namelen);
789 #endif
790
791 #ifndef HAVE_GETSOCKOPT_DECL
792 extern int getsockopt(int s, int level, int optname, char *optval,
793                          socklen_t_equiv *optlen);
794 #endif
795
796 #ifndef HAVE_INITGROUPS
797 # define initgroups(name,basegid) 0
798 #else
799 # ifndef HAVE_INITGROUPS_DECL
800 extern int initgroups(const char *name, gid_t basegid);
801 # endif
802 #endif
803
804 #ifndef HAVE_IOCTL_DECL
805 extern int ioctl(int fildes, int request, ...);
806 #endif
807
808 #ifndef isnormal
809 #ifndef HAVE_ISNORMAL
810 #define isnormal(f) (((f) < 0.0) || ((f) > 0.0))
811 #endif
812 #endif
813
814 #ifndef HAVE_LISTEN_DECL
815 extern int listen(int s, int backlog);
816 #endif
817
818 #ifndef HAVE_LSTAT_DECL
819 extern int lstat(const char *path, struct stat *buf);
820 #endif
821
822 #ifndef HAVE_MALLOC_DECL
823 extern void *malloc (size_t size);
824 #endif
825
826 #ifndef HAVE_MEMMOVE_DECL
827 #ifdef HAVE_MEMMOVE
828 extern void *memmove(void *to, const void *from, size_t n);
829 #else
830 extern char *memmove(char *to, /*const*/ char *from, size_t n);
831 #endif
832 #endif
833
834 #ifndef HAVE_MEMSET_DECL
835 extern void *memset(void *s, int c, size_t n);
836 #endif
837
838 #ifndef HAVE_MKTEMP_DECL
839 extern char *mktemp(char *template);
840 #endif
841
842 #ifndef HAVE_MKSTEMP_DECL
843 extern int mkstemp(char *template);
844 #endif
845
846 #ifndef HAVE_MKTIME_DECL
847 extern time_t mktime(struct tm *timeptr);
848 #endif
849
850 #ifndef HAVE_OPENLOG_DECL
851 #ifdef LOG_AUTH
852 extern void openlog(const char *ident, int logopt, int facility);
853 #else
854 extern void openlog(const char *ident, int logopt);
855 #endif
856 #endif
857
858 #ifndef HAVE_PCLOSE_DECL
859 extern int pclose(FILE *stream);
860 #endif
861
862 #ifndef HAVE_PERROR_DECL
863 extern void perror(const char *s);
864 #endif
865
866 #ifndef HAVE_PRINTF_DECL
867 extern int printf(const char *format, ...);
868 #endif
869
870 #ifndef HAVE_PUTS_DECL
871 extern int puts(const char *s);
872 #endif
873
874 #ifndef HAVE_REALLOC_DECL
875 extern void *realloc(void *ptr, size_t size);
876 #endif
877
878 /* AIX #defines recvfrom, and provides a prototype for the alternate name */
879 #if !defined(HAVE_RECVFROM_DECL) && !defined(recvfrom)
880 extern int recvfrom(int s, char *buf, int len, int flags,
881                        struct sockaddr *from, socklen_t_equiv *fromlen);
882 #endif
883
884 #ifndef HAVE_REMOVE_DECL
885 extern int remove(const char *path);
886 #endif
887
888 #ifndef HAVE_RENAME_DECL
889 extern int rename(const char *old, const char *new);
890 #endif
891
892 #ifndef HAVE_REWIND_DECL
893 extern void rewind(FILE *stream);
894 #endif
895
896 #ifndef HAVE_RUSEROK_DECL
897 extern int ruserok(const char *rhost, int suser,
898                       const char *ruser, const char *luser);
899 #endif
900
901 #ifndef HAVE_SELECT_DECL
902 extern int select(int nfds,
903                      SELECT_ARG_TYPE *readfds,
904                      SELECT_ARG_TYPE *writefds,
905                      SELECT_ARG_TYPE *exceptfds,
906                      struct timeval *timeout);
907 #endif
908
909 #ifndef HAVE_SENDTO_DECL
910 extern int sendto(int s, const char *msg, int len, int flags,
911                      const struct sockaddr *to, int tolen);
912 #endif
913
914 #ifdef HAVE_SETRESGID
915 #define setegid(x)      setresgid((gid_t)-1,(x),(gid_t)-1)
916 #ifndef HAVE_SETRESGID_DECL
917 extern int setresgid(gid_t rgid, gid_t egid, gid_t sgid);
918 #endif
919 #else
920 #ifndef HAVE_SETEGID_DECL
921 extern int setegid(gid_t egid);
922 #endif
923 #endif
924
925 #ifdef HAVE_SETRESUID
926 #define seteuid(x)      setresuid((uid_t)-1,(x),(uid_t)-1)
927 #ifndef HAVE_SETRESUID_DECL
928 extern int setresuid(uid_t ruid, uid_t euid, uid_t suid);
929 #endif
930 #else
931 #ifndef HAVE_SETEUID_DECL
932 extern int seteuid(uid_t euid);
933 #endif
934 #endif
935
936 #ifndef HAVE_SETPGID_DECL
937 #ifdef HAVE_SETPGID
938 extern int setpgid(pid_t pid, pid_t pgid);
939 #endif
940 #endif
941
942 #ifndef HAVE_SETPGRP_DECL
943 #ifdef SETPGRP_VOID
944 extern pid_t setpgrp(void);
945 #else
946 extern pid_t setpgrp(pid_t pgrp, pid_t pid);
947 #endif
948 #endif
949
950 #ifndef HAVE_SETSOCKOPT_DECL
951 extern int setsockopt(int s, int level, int optname,
952                          const char *optval, int optlen);
953 #endif
954
955 #ifdef HAVE_SHMGET
956 #ifndef HAVE_SHMAT_DECL
957 extern void *shmat(int shmid, const SHM_ARG_TYPE *shmaddr, int shmflg);
958 #endif
959
960 #ifndef HAVE_SHMCTL_DECL
961 extern int shmctl(int shmid, int cmd, struct shmid_ds *buf);
962 #endif
963
964 #ifndef HAVE_SHMDT_DECL
965 extern int shmdt(SHM_ARG_TYPE *shaddr);
966 #endif
967
968 #ifndef HAVE_SHMGET_DECL
969 extern int shmget(key_t key, size_t size, int shmflg);
970 #endif
971 #endif
972
973 #ifndef HAVE_SNPRINTF_DECL
974 #include "arglist.h"
975 int snprintf(char *buf, size_t len, const char *format,...)
976      G_GNUC_PRINTF(3,4);
977 #endif
978 #ifndef HAVE_VSNPRINTF_DECL
979 #include "arglist.h"
980 int vsnprintf(char *buf, size_t len, const char *format, va_list ap);
981 #endif
982
983 #ifndef HAVE_SOCKET_DECL
984 extern int socket(int domain, int type, int protocol);
985 #endif
986
987 #ifndef HAVE_SOCKETPAIR_DECL
988 extern int socketpair(int domain, int type, int protocol, int sv[2]);
989 #endif
990
991 #ifndef HAVE_SSCANF_DECL
992 extern int sscanf(const char *s, const char *format, ...);
993 #endif
994
995 #ifndef HAVE_STRCASECMP_DECL
996 extern int strcasecmp(const char *s1, const char *s2);
997 #endif
998
999 #ifndef HAVE_STRERROR_DECL
1000 extern char *strerror(int errnum);
1001 #endif
1002
1003 #ifndef HAVE_STRFTIME_DECL
1004 extern size_t strftime(char *s, size_t maxsize, const char *format,
1005                           const struct tm *timeptr);
1006 #endif
1007
1008 #ifndef HAVE_STRNCASECMP_DECL
1009 extern int strncasecmp(const char *s1, const char *s2, int n);
1010 #endif
1011
1012 #ifndef HAVE_SYSLOG_DECL
1013 extern void syslog(int priority, const char *logstring, ...)
1014      G_GNUC_PRINTF(2,3);
1015 #endif
1016
1017 #ifndef HAVE_SYSTEM_DECL
1018 extern int system(const char *string);
1019 #endif
1020
1021 #ifndef HAVE_TIME_DECL
1022 extern time_t time(time_t *tloc);
1023 #endif
1024
1025 #ifndef HAVE_TOLOWER_DECL
1026 extern int tolower(int c);
1027 #endif
1028
1029 #ifndef HAVE_TOUPPER_DECL
1030 extern int toupper(int c);
1031 #endif
1032
1033 #ifndef HAVE_UNGETC_DECL
1034 extern int ungetc(int c, FILE *stream);
1035 #endif
1036
1037 #ifndef HAVE_VFPRINTF_DECL
1038 #include "arglist.h"
1039 extern int vfprintf(FILE *stream, const char *format, va_list ap);
1040 #endif
1041
1042 #ifndef HAVE_VPRINTF_DECL
1043 #include "arglist.h"
1044 extern int vprintf(const char *format, va_list ap);
1045 #endif
1046
1047 /* these system headers are added by gnulib if they
1048  * do not exist */
1049 #include "netdb.h"
1050 #include "arpa/inet.h"
1051
1052 /* gnulib-only includes */
1053 #include "safe-read.h"
1054 #include "full-read.h"
1055 #include "full-write.h"
1056
1057 #if !defined(S_ISCHR) && defined(_S_IFCHR) && defined(_S_IFMT)
1058 #define S_ISCHR(mode) (((mode) & _S_IFMT) == _S_IFCHR)
1059 #endif
1060
1061 #if !defined(S_ISREG) && defined(_S_IFREG) && defined(_S_IFMT)
1062 #define S_ISREG(mode) (((mode) & _S_IFMT) == _S_IFREG)
1063 #endif
1064
1065 #ifndef HAVE_WAITPID
1066 #ifdef HAVE_WAIT4
1067 #define waitpid(pid,status,options) wait4(pid,status,options,0)
1068 #else
1069 extern pid_t waitpid(pid_t pid, amwait_t *stat_loc, int options);
1070 #endif
1071 #endif
1072
1073 #ifndef HAVE_WRITEV_DECL
1074 extern ssize_t writev(int fd, const struct iovec *iov, int iovcnt);
1075 #endif
1076
1077 #ifndef STDIN_FILENO
1078 #define STDIN_FILENO 0
1079 #endif
1080
1081 #ifndef STDOUT_FILENO
1082 #define STDOUT_FILENO 1
1083 #endif
1084
1085 #ifndef STDERR_FILENO
1086 #define STDERR_FILENO 2
1087 #endif
1088
1089 /* S_ISDIR is not defined on Nextstep */
1090 #ifndef S_ISDIR
1091 #if defined(_S_IFMT) && defined(_S_IFDIR)
1092 #define S_ISDIR(mode)   (((mode) & (_S_IFMT)) == (_S_IFDIR))
1093 #else
1094 #error Don t know how to define S_ISDIR
1095 #endif
1096 #endif
1097
1098 #if SIZEOF_SIZE_T == SIZEOF_INT
1099 #  define        SIZE_T_ATOI    (size_t)atoi
1100 #  ifndef SIZE_MAX
1101 #    define      SIZE_MAX       G_MAXUINT
1102 #  endif
1103 #else
1104 #  define        SIZE_T_ATOI    (size_t)atol
1105 #  ifndef SIZE_MAX
1106 #    define      SIZE_MAX       ULONG_MAX
1107 #  endif
1108 #endif
1109
1110 #if SIZEOF_SSIZE_T == SIZEOF_INT
1111 #  define        SSIZE_T_ATOI   (ssize_t)atoi
1112 #  ifndef SSIZE_MAX
1113 #    define      SSIZE_MAX      INT_MAX
1114 #  endif
1115 #  ifndef SSIZE_MIN
1116 #    define      SSIZE_MIN      INT_MIN
1117 #  endif
1118 #else
1119 #  define        SSIZE_T_ATOI   (ssize_t)atol
1120 #  ifndef SSIZE_MAX
1121 #    define      SSIZE_MAX      LONG_MAX
1122 #  endif
1123 #  ifndef SSIZE_MIN
1124 #    define      SSIZE_MIN      LONG_MIN
1125 #  endif
1126 #endif
1127
1128 #if SIZEOF_TIME_T == SIZEOF_INT
1129 #  define        TIME_T_ATOI    (time_t)atoi
1130 #  ifndef TIME_MAX
1131 #    define      TIME_MAX       G_MAXUINT
1132 #  endif
1133 #else
1134 #  define        TIME_T_ATOI    (time_t)atol
1135 #  ifndef TIME_MAX
1136 #    define      TIME_MAX       ULONG_MAX
1137 #  endif
1138 #endif
1139
1140 #if SIZEOF_OFF_T > SIZEOF_LONG
1141 #  ifdef HAVE_ATOLL
1142 #    define        OFF_T_ATOI    (off_t)atoll
1143 #  else
1144 #    define        OFF_T_ATOI    (off_t)atol
1145 #  endif
1146 #  ifdef HAVE_STRTOLL
1147 #    define        OFF_T_STRTOL  (off_t)strtoll
1148 #  else
1149 #    define        OFF_T_STRTOL  (off_t)strtol
1150 #  endif
1151 #else
1152 #  if SIZEOF_OFF_T == SIZEOF_LONG
1153 #    define        OFF_T_ATOI    (off_t)atol
1154 #    define        OFF_T_STRTOL  (off_t)strtol
1155 #  else
1156 #    define        OFF_T_ATOI    (off_t)atoi
1157 #    define        OFF_T_STRTOL  (off_t)strtol
1158 #  endif
1159 #endif
1160
1161
1162 #define BIND_CYCLE_RETRIES      120             /* Total of 30 minutes */
1163
1164 #define MAX_DUMPERS 63
1165
1166 #ifndef NI_MAXHOST
1167 #define NI_MAXHOST 1025
1168 #endif
1169
1170 typedef enum {
1171     KENCRYPT_NONE,      /* krb5 encryption not enabled */
1172     KENCRYPT_WILL_DO,   /* krb5 encryption will be enabled once amanda
1173                            protocol stream is closed */
1174     KENCRYPT_YES        /* krb5 encryption enabled on all stream */
1175 } kencrypt_type;
1176
1177 #define DUMP_LEVELS    400
1178
1179 /* Constants to define the number of pre-opened pipes between amandad and
1180  * its services */
1181
1182 /* If you change these (don't!), change them in perl/Amanda/Constants.pm, too */
1183 #define DATA_FD_COUNT   3               /* number of general-use pipes */
1184 #define DATA_FD_OFFSET  50
1185
1186 #endif  /* !AMANDA_H */