Imported Upstream version 3.2.0
[debian/amanda] / server-src / holding.c
index e6a5f6626f840c98fa58729c8be134eeb2fba503..15286bd3a432760d2577a2811aece707efce90b0 100644 (file)
@@ -32,6 +32,7 @@
 #include "amanda.h"
 #include "util.h"
 #include "holding.h"
+#include "diskfile.h"
 #include "fileheader.h"
 #include "logfile.h"
 
@@ -208,6 +209,7 @@ static void holding_walk_file(
         /* and go on to the next chunk if this wasn't cruft */
        if (!is_cruft)
            filename = stralloc(file.cont_filename);
+       dumpfile_free_data(&file);
     }
 
     amfree(filename);
@@ -287,6 +289,7 @@ static void holding_walk_dir(
            holding_walk_file(hfile,
                    datap,
                    per_chunk_fn);
+       dumpfile_free_data(&dumpf);
     }
 
     closedir(dir);
@@ -390,14 +393,16 @@ holding_walk(
     holding_walk_fn per_file_fn,
     holding_walk_fn per_chunk_fn)
 {
+    identlist_t    il;
     holdingdisk_t *hdisk_conf;
     char *hdisk;
     int proceed = 1;
 
-    for (hdisk_conf = getconf_holdingdisks(); 
-               hdisk_conf != NULL;
-               hdisk_conf = holdingdisk_next(hdisk_conf)) {
+    for (il = getconf_identlist(CNF_HOLDINGDISK);
+               il != NULL;
+               il = il->next) {
        int is_cruft = 0;
+       hdisk_conf = lookup_holdingdisk(il->data);
 
        hdisk = holdingdisk_get_diskdir(hdisk_conf);
        if (!is_dir(hdisk))
@@ -497,6 +502,7 @@ holding_get_file_chunks(char *hfile)
 {
     holding_get_datap_t data;
     data.result = NULL;
+    data.fullpaths = 1;
 
     holding_walk_file(hfile, (gpointer)&data,
        holding_get_walk_fn);
@@ -511,7 +517,6 @@ holding_get_files_for_flush(
     GSList *file_list, *file_elt;
     GSList *date;
     int date_matches;
-    disk_t *dp;
     dumpfile_t file;
     GSList *result_list = NULL;
 
@@ -523,8 +528,10 @@ holding_get_files_for_flush(
        if (!holding_file_get_dumpfile((char *)file_elt->data, &file))
            continue;
 
-        if (file.type != F_DUMPFILE)
+        if (file.type != F_DUMPFILE) {
+           dumpfile_free_data(&file);
             continue;
+       }
 
        if (dateargs) {
            date_matches = 0;
@@ -539,21 +546,16 @@ holding_get_files_for_flush(
            /* if no date list was provided, then all dates match */
            date_matches = 1;
        }
-        if (!date_matches)
+        if (!date_matches) {
+           dumpfile_free_data(&file);
             continue;
-
-        /* check that the hostname and disk are in the disklist */
-        dp = lookup_disk(file.name, file.disk);
-        if (dp == NULL) {
-           dbprintf(_("%s: disk %s:%s not in database, skipping it."),
-                        (char *)file_elt->data, file.name, file.disk);
-            continue;
-        }
+       }
 
         /* passed all tests -- we'll flush this file */
         result_list = g_slist_insert_sorted(result_list, 
            stralloc(file_elt->data), 
            g_compare_strings);
+       dumpfile_free_data(&file);
     }
 
     if (file_list) g_slist_free_full(file_list);
@@ -579,6 +581,7 @@ holding_get_all_datestamps(void)
                                               stralloc(dfile.datestamp), 
                                               g_compare_strings);
        }
+       dumpfile_free_data(&dfile);
     }
 
     g_slist_free_full(all_files);
@@ -605,7 +608,8 @@ holding_file_size(
         /* stat the file for its size */
         if (stat(filename, &finfo) == -1) {
            dbprintf(_("stat %s: %s\n"), filename, strerror(errno));
-            return (off_t)-1;
+            size = -1;
+           break;
         }
         size += (finfo.st_size+(off_t)1023)/(off_t)1024;
         if (strip_headers)
@@ -614,12 +618,13 @@ holding_file_size(
         /* get the header to look for cont_filename */
         if (!holding_file_get_dumpfile(filename, &file)) {
            dbprintf(_("holding_file_size: open of %s failed.\n"), filename);
-            amfree(filename);
-            return (off_t)-1;
+            size = -1;
+           break;
         }
 
         /* on to the next chunk */
         filename = newstralloc(filename, file.cont_filename);
+       dumpfile_free_data(&file);
     }
     amfree(filename);
     return size;
@@ -662,7 +667,7 @@ holding_file_get_dumpfile(
     if((fd = robust_open(fname, O_RDONLY, 0)) == -1)
         return 0;
 
-    if(fullread(fd, buffer, SIZEOF(buffer)) != (ssize_t)sizeof(buffer)) {
+    if(full_read(fd, buffer, SIZEOF(buffer)) != sizeof(buffer)) {
         aclose(fd);
         return 0;
     }
@@ -764,6 +769,7 @@ holding_cleanup_file(
        if (data->verbose_output)
            g_fprintf(data->verbose_output, 
                _("Could not read read header from '%s'\n"), element);
+       dumpfile_free_data(&file);
        return 0;
     }
 
@@ -771,6 +777,7 @@ holding_cleanup_file(
        if (data->verbose_output)
            g_fprintf(data->verbose_output, 
                _("File '%s' is not a dump file\n"), element);
+       dumpfile_free_data(&file);
        return 0;
     }
 
@@ -778,6 +785,7 @@ holding_cleanup_file(
        if (data->verbose_output)
            g_fprintf(data->verbose_output, 
                _("File '%s' has invalid level %d\n"), element, file.dumplevel);
+       dumpfile_free_data(&file);
        return 0;
     }
 
@@ -788,6 +796,7 @@ holding_cleanup_file(
            g_fprintf(data->verbose_output, 
                _("File '%s' is for '%s:%s', which is not in the disklist\n"), 
                    element, file.name, file.disk);
+       dumpfile_free_data(&file);
        return 0;
     }
 
@@ -817,6 +826,7 @@ holding_cleanup_file(
        amfree(destname);
     }
 
+    dumpfile_free_data(&file);
     return 1;
 }
 
@@ -841,13 +851,45 @@ holding_cleanup(
  * Application support
  */
 
+void
+holding_set_origsize(
+    char  *holding_file,
+    off_t  orig_size)
+{
+    int         fd;
+    size_t      buflen;
+    char        buffer[DISK_BLOCK_BYTES];
+    char       *read_buffer;
+    dumpfile_t  file;
+
+    if((fd = robust_open(holding_file, O_RDWR, 0)) == -1) {
+       dbprintf(_("holding_set_origsize: open of %s failed: %s\n"),
+                holding_file, strerror(errno));
+       return;
+    }
+
+    buflen = full_read(fd, buffer, SIZEOF(buffer));
+    if (buflen <= 0) {
+       dbprintf(_("holding_set_origsize: %s: empty file?\n"), holding_file);
+       return;
+    }
+    parse_file_header(buffer, &file, (size_t)buflen);
+    lseek(fd, (off_t)0, SEEK_SET);
+    file.orig_size = orig_size;
+    read_buffer = build_header(&file, NULL, DISK_BLOCK_BYTES);
+    full_write(fd, read_buffer, DISK_BLOCK_BYTES);
+    dumpfile_free_data(&file);
+    amfree(read_buffer);
+    close(fd);
+}
+
 int
 rename_tmp_holding(
     char *     holding_file,
     int                complete)
 {
     int fd;
-    ssize_t buflen;
+    size_t buflen;
     char buffer[DISK_BLOCK_BYTES];
     dumpfile_t file;
     char *filename;
@@ -863,7 +905,7 @@ rename_tmp_holding(
            amfree(filename_tmp);
            return 0;
        }
-       buflen = fullread(fd, buffer, SIZEOF(buffer));
+       buflen = full_read(fd, buffer, SIZEOF(buffer));
        close(fd);
 
        if(rename(filename_tmp, filename) != 0) {
@@ -883,17 +925,33 @@ rename_tmp_holding(
            if((fd = robust_open(filename, O_RDWR, 0)) == -1) {
                dbprintf(_("rename_tmp_holdingX: open of %s failed: %s\n"),
                        filename, strerror(errno));
+               dumpfile_free_data(&file);
                amfree(filename);
                amfree(filename_tmp);
                return 0;
 
            }
            file.is_partial = 1;
-            header = build_header(&file, DISK_BLOCK_BYTES);
-           fullwrite(fd, header, DISK_BLOCK_BYTES);
+           if (debug_holding > 1)
+               dump_dumpfile_t(&file);
+            header = build_header(&file, NULL, DISK_BLOCK_BYTES);
+           if (!header) /* this shouldn't happen */
+               error(_("header does not fit in %zd bytes"), (size_t)DISK_BLOCK_BYTES);
+           if (full_write(fd, header, DISK_BLOCK_BYTES) != DISK_BLOCK_BYTES) {
+               dbprintf(_("rename_tmp_holding: writing new header failed: %s"),
+                       strerror(errno));
+               dumpfile_free_data(&file);
+               amfree(filename);
+               amfree(filename_tmp);
+               free(header);
+               close(fd);
+               return 0;
+           }
+           free(header);
            close(fd);
        }
        filename = newstralloc(filename, file.cont_filename);
+       dumpfile_free_data(&file);
     }
     amfree(filename);
     amfree(filename_tmp);