X-Git-Url: https://git.gag.com/?a=blobdiff_plain;f=server-src%2Famflush.c;h=481ff289966e4fe495da10b5d423bea40290b9de;hb=refs%2Fheads%2Fmaster;hp=e2a9d10b3680445cd7ad3d542f65637e87a95bb1;hpb=afaa71b3866b46b082b6c895772e15b36d8865fe;p=debian%2Famanda diff --git a/server-src/amflush.c b/server-src/amflush.c index e2a9d10..481ff28 100644 --- a/server-src/amflush.c +++ b/server-src/amflush.c @@ -1,6 +1,7 @@ /* * Amanda, The Advanced Maryland Automatic Network Disk Archiver * Copyright (c) 1991-1998 University of Maryland at College Park + * Copyright (c) 2007-2012 Zmanda, Inc. All Rights Reserved. * All Rights Reserved. * * Permission to use, copy, modify, distribute, and sell this software and its @@ -30,16 +31,23 @@ */ #include "amanda.h" +#include "match.h" +#include "find.h" #include "conffile.h" #include "diskfile.h" #include "tapefile.h" #include "logfile.h" #include "clock.h" -#include "version.h" #include "holding.h" -#include "driverio.h" #include "server_util.h" #include "timestamp.h" +#include "getopt.h" + +static struct option long_options[] = { + {"version" , 0, NULL, 1}, + {"exact-match" , 0, NULL, 2}, + {NULL, 0, NULL, 0} +}; static char *conf_logdir; FILE *driver_stream; @@ -90,8 +98,11 @@ main( char *tpchanger; char *qdisk, *qhname; GSList *datestamp_list = NULL; - config_overwrites_t *cfg_ovr; + config_overrides_t *cfg_ovr; char **config_options; + find_result_t *holding_files; + disklist_t holding_disklist = { NULL, NULL }; + gboolean exact_match = FALSE; /* * Configure program for internationalization: @@ -112,23 +123,28 @@ main( dbopen(DBG_SUBDIR_SERVER); - erroutput_type = ERR_INTERACTIVE; + add_amanda_log_handler(amanda_log_stderr); foreground = 0; batch = 0; redirect = 1; /* process arguments */ - cfg_ovr = new_config_overwrites(argc/2); - while((opt = getopt(argc, argv, "bfso:D:")) != EOF) { + cfg_ovr = new_config_overrides(argc/2); + while((opt = getopt_long(argc, argv, "bfso:D:", long_options, NULL)) != EOF) { switch(opt) { + case 1 : printf("amflush-%s\n", VERSION); + return(0); + break; + case 2 : exact_match = TRUE; + break; case 'b': batch = 1; break; case 'f': foreground = 1; break; case 's': redirect = 0; break; - case 'o': add_config_overwrite_opt(cfg_ovr, optarg); + case 'o': add_config_override_opt(cfg_ovr, optarg); break; case 'D': if (datearg == NULL) datearg = alloc(21*SIZEOF(char *)); @@ -149,13 +165,13 @@ main( } if(argc < 1) { - error(_("Usage: amflush%s [-b] [-f] [-s] [-D date]* [host [disk]* ]* [-o configoption]*"), versionsuffix()); + error(_("Usage: amflush [-b] [-f] [-s] [-D date]* [--exact-match] [-o configoption]* [host [disk]* ]*")); /*NOTREACHED*/ } + set_config_overrides(cfg_ovr); config_init(CONFIG_INIT_EXPLICIT_NAME, argv[0]); - apply_config_overwrites(cfg_ovr); conf_diskfile = config_dir_relative(getconf_str(CNF_DISKFILE)); read_diskfile(conf_diskfile, &diskq); @@ -172,7 +188,14 @@ main( dbrename(get_config_name(), DBG_SUBDIR_SERVER); - errstr = match_disklist(&diskq, argc-1, argv+1); + /* load DLEs from the holding disk, in case there's anything to flush there */ + search_holding_disk(&holding_files, &holding_disklist); + /* note that the dumps are added to the global disklist, so we need not + * consult holding_files or holding_disklist after this. The holding-only + * dumps will be filtered properly by match_disklist, setting the dp->todo + * flag appropriately. */ + + errstr = match_disklist(&diskq, exact_match, argc-1, argv+1); if (errstr) { g_printf(_("%s"),errstr); amfree(errstr); @@ -205,15 +228,10 @@ main( error(_("%s exists: %s is already running, or you must run amcleanup"), conf_logfile, process_name); /*NOTREACHED*/ } - amfree(conf_logfile); - log_add(L_INFO, "%s pid %ld", get_pname(), (long)getpid()); - driver_program = vstralloc(amlibexecdir, "/", "driver", versionsuffix(), - NULL); - reporter_program = vstralloc(sbindir, "/", "amreport", versionsuffix(), - NULL); - logroll_program = vstralloc(amlibexecdir, "/", "amlogroll", versionsuffix(), - NULL); + driver_program = vstralloc(amlibexecdir, "/", "driver", NULL); + reporter_program = vstralloc(sbindir, "/", "amreport", NULL); + logroll_program = vstralloc(amlibexecdir, "/", "amlogroll", NULL); tapedev = getconf_str(CNF_TAPEDEV); tpchanger = getconf_str(CNF_TPCHANGER); @@ -241,7 +259,7 @@ main( stralloc((char *)datestamp->data), g_compare_strings); } - g_slist_free_full(all_datestamps); + slist_free_full(all_datestamps, g_free); } else { /* otherwise, in batch mode, use all datestamps */ @@ -265,14 +283,30 @@ main( exit(1); } + if (access(conf_logfile, F_OK) == 0) { + char *process_name = get_master_process(conf_logfile); + error(_("%s exists: someone started %s"), conf_logfile, process_name); + /*NOTREACHED*/ + } + log_add(L_INFO, "%s pid %ld", get_pname(), (long)getpid()); + if(!batch) confirm(datestamp_list); for(dp = diskq.head; dp != NULL; dp = dp->next) { if(dp->todo) { - char *qname; - qname = quote_string(dp->name); - log_add(L_DISK, "%s %s", dp->host->hostname, qname); - amfree(qname); + /* is it holding_list */ + for (holding_file=holding_list; holding_file != NULL; + holding_file = holding_file->next) { + dumpfile_t file; + holding_file_get_dumpfile((char *)holding_file->data, &file); + if (g_str_equal(dp->host->hostname, file.name) && + g_str_equal(dp->name, file.disk)) { + char *qname; + qname = quote_string(dp->name); + log_add(L_DISK, "%s %s", dp->host->hostname, qname); + amfree(qname); + } + } } } @@ -285,8 +319,8 @@ main( if(!foreground) detach(); - erroutput_type = (ERR_AMANDALOG|ERR_INTERACTIVE); - set_logerror(logerror); + add_amanda_log_handler(amanda_log_stderr); + add_amanda_log_handler(amanda_log_trace_log); today = time(NULL); tm = localtime(&today); if (tm) { @@ -338,6 +372,7 @@ main( holding_file_get_dumpfile((char *)holding_file->data, &file); if (holding_file_size((char *)holding_file->data, 1) <= 0) { + g_debug("%s is empty - ignoring", (char *)holding_file->data); log_add(L_INFO, "%s: removing file with no data.", (char *)holding_file->data); holding_file_unlink((char *)holding_file->data); @@ -345,11 +380,12 @@ main( continue; } + /* search_holding_disk should have already ensured that every + * holding dumpfile has an entry in the dynamic disklist */ dp = lookup_disk(file.name, file.disk); - if (!dp) { - error("dp == NULL"); - /*NOTREACHED*/ - } + assert(dp != NULL); + + /* but match_disklist may have indicated we should not flush it */ if (dp->todo == 0) continue; qdisk = quote_string(file.disk); @@ -361,6 +397,8 @@ main( file.datestamp, file.dumplevel, qhname); + + g_debug("flushing '%s'", (char *)holding_file->data); g_fprintf(driver_stream, "FLUSH %s %s %s %d %s\n", file.name, @@ -390,9 +428,9 @@ main( } } - g_slist_free_full(datestamp_list); + slist_free_full(datestamp_list, g_free); datestamp_list = NULL; - g_slist_free_full(holding_list); + slist_free_full(holding_list, g_free); holding_list = NULL; if(redirect) { /* rename errfile */ @@ -454,9 +492,10 @@ main( /* * This is the child process. */ - config_options = get_config_options(2); + config_options = get_config_options(3); config_options[0] = "amreport"; config_options[1] = get_config_name(); + config_options[2] = "--from-amdump"; safe_fd(-1, 0); execve(reporter_program, config_options, safe_env()); error(_("cannot exec %s: %s"), reporter_program, strerror(errno)); @@ -583,7 +622,7 @@ pick_datestamp(void) } chupper = (char)toupper(ch); if (chupper < 'A' || chupper > max_char) { - g_slist_free_full(r_datestamp_list); + slist_free_full(r_datestamp_list, g_free); r_datestamp_list = NULL; break; } @@ -591,7 +630,7 @@ pick_datestamp(void) stralloc(datestamps[chupper - 'A'])); } while ((ch = *a++) != '\0'); if (r_datestamp_list && ch == '\0') { - g_slist_free_full(datestamp_list); + slist_free_full(datestamp_list, g_free); datestamp_list = r_datestamp_list; break; } @@ -653,6 +692,7 @@ confirm(GSList *datestamp_list) } g_printf(_("Ok, quitting. Run amflush again when you are ready.\n")); + log_add(L_INFO, "pid-done %ld", (long)getpid()); exit(1); } @@ -664,7 +704,7 @@ redirect_stderr(void) fflush(stdout); fflush(stderr); errfile = vstralloc(conf_logdir, "/amflush", NULL); - if((fderr = open(errfile, O_WRONLY| O_CREAT | O_TRUNC, 0600)) == -1) { + if((fderr = open(errfile, O_WRONLY| O_APPEND | O_CREAT | O_TRUNC, 0600)) == -1) { error(_("could not open %s: %s"), errfile, strerror(errno)); /*NOTREACHED*/ }