X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=bacula%2Fsrc%2Fstored%2Fbls.c;h=e9ca15b5a4421decc83cdb8f4f6b29b4eff95467;hb=dc9f8d415d12cc92db533adbf7b01fc39e1e30f2;hp=c26634706c0e79ae7491676d8994d07021a1556e;hpb=80eb45e0ca629dc18f4faede11d2c883de899b77;p=bacula%2Fbacula diff --git a/bacula/src/stored/bls.c b/bacula/src/stored/bls.c index c26634706c..e9ca15b5a4 100644 --- a/bacula/src/stored/bls.c +++ b/bacula/src/stored/bls.c @@ -5,22 +5,17 @@ * Version $Id$ */ /* - Copyright (C) 2000, 2001, 2002 Kern Sibbald and John Walker + Copyright (C) 2000-2005 Kern Sibbald This program is free software; you can redistribute it and/or - modify it under the terms of the GNU General Public License as - published by the Free Software Foundation; either version 2 of - the License, or (at your option) any later version. + modify it under the terms of the GNU General Public License + version 2 as ammended with additional clauses defined in the + file LICENSE in the main source directory. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public - License along with this program; if not, write to the Free - Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, - MA 02111-1307, USA. + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + the file LICENSE for additional details. */ @@ -28,44 +23,64 @@ #include "stored.h" #include "findlib/find.h" +#if defined(HAVE_CYGWIN) || defined(HAVE_WIN32) +int win32_client = 1; +#else +int win32_client = 0; +#endif + +/* Dummy functions */ +int generate_daemon_event(JCR *jcr, const char *event) { return 1; } + static void do_blocks(char *infname); static void do_jobs(char *infname); static void do_ls(char *fname); -static void print_ls_output(char *fname, char *link, int type, struct stat *statp); -static void do_setup(char *infname); -static void do_close(); +static void do_close(JCR *jcr); +static void get_session_record(DEVICE *dev, DEV_RECORD *rec, SESSION_LABEL *sessrec); +static bool record_cb(DCR *dcr, DEV_RECORD *rec); static DEVICE *dev; -static int default_tape = FALSE; -static int dump_label = FALSE; -static int list_blocks = FALSE; -static int list_jobs = FALSE; -static int verbose = 0; -static char Vol[2000]; -static char *VolName; -static char *p; +static DCR *dcr; +static bool dump_label = false; +static bool list_blocks = false; +static bool list_jobs = false; static DEV_RECORD *rec; static DEV_BLOCK *block; -static int NumVolumes, CurVolume; static JCR *jcr; +static SESSION_LABEL sessrec; +static uint32_t num_files = 0; +static ATTR *attr; +#define CONFIG_FILE "bacula-sd.conf" +char *configfile = NULL; +STORES *me = NULL; /* our Global resource */ +bool forge_on = false; +pthread_mutex_t device_release_mutex = PTHREAD_MUTEX_INITIALIZER; +pthread_cond_t wait_device_release = PTHREAD_COND_INITIALIZER; -extern char BaculaId[]; -static FF_PKT ff; +static FF_PKT *ff; + +static BSR *bsr = NULL; static void usage() { fprintf(stderr, -"Usage: bls [-d debug_level] \n" -" -b list blocks\n" +"Copyright (C) 2000-2005 Kern Sibbald.\n" +"\nVersion: " VERSION " (" BDATE ")\n\n" +"Usage: bls [options] \n" +" -b specify a bootstrap file\n" +" -c specify a config file\n" +" -d specify debug level\n" " -e exclude list\n" " -i include list\n" " -j list jobs\n" -" -L list tape label\n" -" (none of above) list saved files\n" -" -t use default tape device\n" +" -k list blocks\n" +" (no j or k option) list saved files\n" +" -L dump label\n" +" -p proceed inspite of errors\n" " -v be verbose\n" +" -V specify Volume names (separated by |)\n" " -? print this message\n\n"); exit(1); } @@ -76,484 +91,350 @@ int main (int argc, char *argv[]) int i, ch; FILE *fd; char line[1000]; + char *VolumeName= NULL; + char *bsrName = NULL; + bool ignore_label_errors = false; + working_directory = "/tmp"; my_name_is(argc, argv, "bls"); - init_msg(NULL, NULL); /* initialize message handler */ + init_msg(NULL, NULL); /* initialize message handler */ - memset(&ff, 0, sizeof(ff)); - init_include_exclude_files(&ff); + ff = init_find_files(); - while ((ch = getopt(argc, argv, "bd:e:i:jLtv?")) != -1) { + while ((ch = getopt(argc, argv, "b:c:d:e:i:jkLpvV:?")) != -1) { switch (ch) { - case 'b': - list_blocks = TRUE; - break; - case 'd': /* debug level */ - debug_level = atoi(optarg); - if (debug_level <= 0) - debug_level = 1; - break; - - case 'e': /* exclude list */ - if ((fd = fopen(optarg, "r")) == NULL) { - Pmsg2(0, "Could not open exclude file: %s, ERR=%s\n", - optarg, strerror(errno)); - exit(1); - } - while (fgets(line, sizeof(line), fd) != NULL) { - strip_trailing_junk(line); - Dmsg1(000, "add_exclude %s\n", line); - add_fname_to_exclude_list(&ff, line); - } - fclose(fd); - break; - - case 'i': /* include list */ - if ((fd = fopen(optarg, "r")) == NULL) { - Pmsg2(0, "Could not open include file: %s, ERR=%s\n", - optarg, strerror(errno)); - exit(1); - } - while (fgets(line, sizeof(line), fd) != NULL) { - strip_trailing_junk(line); - Dmsg1(000, "add_include %s\n", line); - add_fname_to_include_list(&ff, 0, line); - } - fclose(fd); - break; - - case 'j': - list_jobs = TRUE; - break; - - case 'L': - dump_label = TRUE; - break; - - case 't': - default_tape = TRUE; - break; - - case 'v': - verbose++; - break; - - case '?': - default: - usage(); - - } - } + case 'b': + bsrName = optarg; + break; + + case 'c': /* specify config file */ + if (configfile != NULL) { + free(configfile); + } + configfile = bstrdup(optarg); + break; + + case 'd': /* debug level */ + debug_level = atoi(optarg); + if (debug_level <= 0) + debug_level = 1; + break; + + case 'e': /* exclude list */ + if ((fd = fopen(optarg, "r")) == NULL) { + Pmsg2(0, _("Could not open exclude file: %s, ERR=%s\n"), + optarg, strerror(errno)); + exit(1); + } + while (fgets(line, sizeof(line), fd) != NULL) { + strip_trailing_junk(line); + Dmsg1(100, "add_exclude %s\n", line); + add_fname_to_exclude_list(ff, line); + } + fclose(fd); + break; + + case 'i': /* include list */ + if ((fd = fopen(optarg, "r")) == NULL) { + Pmsg2(0, "Could not open include file: %s, ERR=%s\n", + optarg, strerror(errno)); + exit(1); + } + while (fgets(line, sizeof(line), fd) != NULL) { + strip_trailing_junk(line); + Dmsg1(100, "add_include %s\n", line); + add_fname_to_include_list(ff, 0, line); + } + fclose(fd); + break; + + case 'j': + list_jobs = true; + break; + + case 'k': + list_blocks = true; + break; + + case 'L': + dump_label = true; + break; + + case 'p': + ignore_label_errors = true; + forge_on = true; + break; + + case 'v': + verbose++; + break; + + case 'V': /* Volume name */ + VolumeName = optarg; + break; + + case '?': + default: + usage(); + + } /* end switch */ + } /* end while */ argc -= optind; argv += optind; - if (!argc && !default_tape) { - Pmsg0(0, "No archive name specified\n"); + if (!argc) { + Pmsg0(0, _("No archive name specified\n")); usage(); } - if (ff.included_files_list == NULL) { - add_fname_to_include_list(&ff, 0, "/"); + if (configfile == NULL) { + configfile = bstrdup(CONFIG_FILE); } - /* Try default device */ - if (default_tape) { - do_ls(DEFAULT_TAPE_DRIVE); - return 0; + parse_config(configfile); + + if (ff->included_files_list == NULL) { + add_fname_to_include_list(ff, 0, "/"); } for (i=0; i < argc; i++) { - do_setup(argv[i]); + if (bsrName) { + bsr = parse_bsr(NULL, bsrName); + } + jcr = setup_jcr("bls", argv[i], bsr, VolumeName, 1); /* acquire for read */ + if (!jcr) { + exit(1); + } + jcr->ignore_label_errors = ignore_label_errors; + dev = jcr->dcr->dev; + if (!dev) { + exit(1); + } + dcr = jcr->dcr; + rec = new_record(); + block = new_block(dev); + attr = new_attr(); + /* + * Assume that we have already read the volume label. + * If on second or subsequent volume, adjust buffer pointer + */ + if (dev->VolHdr.PrevVolName[0] != 0) { /* second volume */ + Pmsg1(0, "\n" +"Warning, this Volume is a continuation of Volume %s\n", + dev->VolHdr.PrevVolName); + } + if (list_blocks) { - do_blocks(argv[i]); + do_blocks(argv[i]); } else if (list_jobs) { - do_jobs(argv[i]); + do_jobs(argv[i]); } else { - do_ls(argv[i]); + do_ls(argv[i]); } - do_close(); + do_close(jcr); } + if (bsr) { + free_bsr(bsr); + } + term_include_exclude_files(ff); + term_find_files(ff); return 0; } -static void my_free_jcr(JCR *jcr) -{ - return; -} -/* - * Setup device, jcr, and prepare to read - */ -static void do_setup(char *infname) +static void do_close(JCR *jcr) { - jcr = new_jcr(sizeof(JCR), my_free_jcr); - VolName = Vol; - VolName[0] = 0; - if (strncmp(infname, "/dev/", 5) != 0) { - /* Try stripping file part */ - p = infname + strlen(infname); - while (p >= infname && *p != '/') - p--; - if (*p == '/') { - strcpy(VolName, p+1); - *p = 0; - } - } - Dmsg2(10, "Device=%s, Vol=%s.\n", infname, VolName); - dev = init_dev(NULL, infname); - if (!dev) { - Emsg1(M_FATAL, 0, "Cannot open %s\n", infname); - exit(1); - } - /* ***FIXME**** init capabilities */ - if (!open_device(dev)) { - Emsg1(M_FATAL, 0, "Cannot open %s\n", infname); - exit(1); - } - Dmsg0(90, "Device opened for read.\n"); - - rec = new_record(); - block = new_block(dev); - - NumVolumes = 0; - CurVolume = 1; - for (p = VolName; p && *p; ) { - p = strchr(p, '^'); - if (p) { - *p++ = 0; - } - NumVolumes++; - } - - jcr->VolumeName = (char *)check_pool_memory_size(jcr->VolumeName, strlen(VolName)+1); - strcpy(jcr->VolumeName, VolName); - if (!acquire_device_for_read(jcr, dev, block)) { - Emsg0(M_ERROR, 0, dev->errmsg); - exit(1); - } -} - -static void do_close() -{ - term_dev(dev); + release_device(jcr->dcr); + free_attr(attr); free_record(rec); free_block(block); free_jcr(jcr); -} - -static int mount_next_volume(char *infname) -{ - if (rec->remainder) { - Dmsg0(20, "Not end of record. Next volume has more data for current record.\n"); - } - Dmsg2(20, "NumVolumes=%d CurVolume=%d\n", NumVolumes, CurVolume); - if (NumVolumes > 1 && CurVolume < NumVolumes) { - p = VolName; - while (*p++) - { } - CurVolume++; - Dmsg1(20, "There is another volume %s.\n", p); - VolName = p; - jcr->VolumeName = check_pool_memory_size(jcr->VolumeName, - strlen(VolName)+1); - strcpy(jcr->VolumeName, VolName); - - close_dev(dev); - dev->state &= ~ST_READ; - if (!acquire_device_for_read(jcr, dev, block)) { - Emsg2(M_FATAL, 0, "Cannot open Dev=%s, Vol=%s\n", infname, VolName); - exit(1); - } - return 1; /* Next volume mounted */ - } - printf("End of Device reached.\n"); - return 0; /* EOT */ -} - -/* - * Device got an error, attempt to analyse it - */ -static void display_error_status() -{ - uint32_t status; - - Emsg0(M_ERROR, 0, dev->errmsg); - status_dev(dev, &status); - Dmsg1(20, "Device status: %x\n", status); - if (status & MT_EOD) - Emsg0(M_ERROR_TERM, 0, "Unexpected End of Data\n"); - else if (status & MT_EOT) - Emsg0(M_ERROR_TERM, 0, "Unexpected End of Tape\n"); - else if (status & MT_EOF) - Emsg0(M_ERROR_TERM, 0, "Unexpected End of File\n"); - else if (status & MT_DR_OPEN) - Emsg0(M_ERROR_TERM, 0, "Tape Door is Open\n"); - else if (!(status & MT_ONLINE)) - Emsg0(M_ERROR_TERM, 0, "Unexpected Tape is Off-line\n"); - else - Emsg2(M_ERROR_TERM, 0, "Read error on Record Header %s: %s\n", dev_name(dev), strerror(errno)); + term_dev(dev); } /* List just block information */ static void do_blocks(char *infname) { - - dump_volume_label(dev); - - /* Assume that we have already read the volume label. - * If on second or subsequent volume, adjust buffer pointer - */ - if (dev->VolHdr.PrevVolName[0] != 0) { /* second volume */ - Pmsg1(0, "\n\ -Warning, this Volume is a continuation of Volume %s\n", - dev->VolHdr.PrevVolName); - } - for ( ;; ) { - - if (!read_block_from_device(dev, block)) { - Dmsg0(20, "!read_record()\n"); - if (dev->state & ST_EOT) { - if (!mount_next_volume(infname)) { - break; - } - continue; - } - if (dev->state & ST_EOF) { - Emsg1(M_INFO, 0, "Got EOF on device %s\n", dev_name(dev)); + if (!read_block_from_device(dcr, NO_BLOCK_NUMBER_CHECK)) { + Dmsg1(100, "!read_block(): ERR=%s\n", dev->strerror()); + if (dev->at_eot()) { + if (!mount_next_read_volume(dcr)) { + Jmsg(jcr, M_INFO, 0, _("Got EOM at file %u on device %s, Volume \"%s\"\n"), + dev->file, dev->print_name(), dcr->VolumeName); + break; + } + /* Read and discard Volume label */ + DEV_RECORD *record; + record = new_record(); + read_block_from_device(dcr, NO_BLOCK_NUMBER_CHECK); + read_record_from_block(block, record); + get_session_record(dev, record, &sessrec); + free_record(record); + Jmsg(jcr, M_INFO, 0, _("Mounted Volume \"%s\".\n"), dcr->VolumeName); + } else if (dev->at_eof()) { + Jmsg(jcr, M_INFO, 0, _("Got EOF at file %u on device %s, Volume \"%s\"\n"), + dev->file, dev->print_name(), dcr->VolumeName); Dmsg0(20, "read_record got eof. try again\n"); - continue; - } - if (dev->state & ST_SHORT) { - Emsg0(M_INFO, 0, dev->errmsg); - continue; - } - display_error_status(); - break; + continue; + } else if (dev->state & ST_SHORT) { + Jmsg(jcr, M_INFO, 0, "%s", dev->errmsg); + continue; + } else { + /* I/O error */ + display_tape_error_status(jcr, dev); + break; + } + } + if (!match_bsr_block(bsr, block)) { + Dmsg5(100, "reject Blk=%u blen=%u bVer=%d SessId=%u SessTim=%u\n", + block->BlockNumber, block->block_len, block->BlockVer, + block->VolSessionId, block->VolSessionTime); + continue; + } + Dmsg5(100, "Blk=%u blen=%u bVer=%d SessId=%u SessTim=%u\n", + block->BlockNumber, block->block_len, block->BlockVer, + block->VolSessionId, block->VolSessionTime); + if (verbose == 1) { + read_record_from_block(block, rec); + Pmsg9(-1, "File:blk=%u:%u blk_num=%u blen=%u First rec FI=%s SessId=%u SessTim=%u Strm=%s rlen=%d\n", + dev->file, dev->block_num, + block->BlockNumber, block->block_len, + FI_to_ascii(rec->FileIndex), rec->VolSessionId, rec->VolSessionTime, + stream_to_ascii(rec->Stream, rec->FileIndex), rec->data_len); + rec->remainder = 0; + } else if (verbose > 1) { + dump_block(block, ""); + } else { + printf("Block: %d size=%d\n", block->BlockNumber, block->block_len); } - - printf("Block: %d size=%d\n", block->BlockNumber, block->block_len); } return; } -/* Do list job records */ -static void do_jobs(char *infname) +/* + * We are only looking for labels or in particular Job Session records + */ +static bool jobs_cb(DCR *dcr, DEV_RECORD *rec) { - - /* Assume that we have already read the volume label. - * If on second or subsequent volume, adjust buffer pointer - */ - if (dev->VolHdr.PrevVolName[0] != 0) { /* second volume */ - Pmsg1(0, "\n\ -Warning, this Volume is a continuation of Volume %s\n", - dev->VolHdr.PrevVolName); + if (rec->FileIndex < 0) { + dump_label_record(dcr->dev, rec, verbose); } - - for ( ;; ) { - if (!read_record(dev, block, rec)) { - Dmsg0(20, "!read_record()\n"); - if (dev->state & ST_EOT) { - if (!mount_next_volume(infname)) { - break; - } - continue; - } - if (dev->state & ST_EOF) { - Emsg1(M_INFO, 0, "Got EOF on device %s\n", dev_name(dev)); - Dmsg0(20, "read_record got eof. try again\n"); - continue; - } - if (dev->state & ST_SHORT) { - Emsg0(M_INFO, 0, dev->errmsg); - continue; - } - display_error_status(); - break; - } - - if (debug_level >= 30) { - Dmsg4(30, "VolSId=%ld FI=%s Strm=%s Size=%ld\n", rec->VolSessionId, - FI_to_ascii(rec->FileIndex), stream_to_ascii(rec->Stream), - rec->data_len); - } - - - /* - * Check for End of File record (all zeros) - * NOTE: this no longer exists - */ - if (rec->VolSessionId == 0 && rec->VolSessionTime == 0) { - Emsg0(M_ERROR_TERM, 0, "Zero VolSessionId and VolSessionTime. This shouldn't happen\n"); - } + rec->remainder = 0; + return true; +} - /* - * Check for Start or End of Session Record - * - */ - if (rec->FileIndex < 0) { - dump_label_record(dev, rec, verbose); - continue; - } - } - return; +/* Do list job records */ +static void do_jobs(char *infname) +{ + read_records(dcr, jobs_cb, mount_next_read_volume); } /* Do an ls type listing of an archive */ static void do_ls(char *infname) { - char fname[2000]; - struct stat statp; - int type; - long record_file_index; - if (dump_label) { dump_volume_label(dev); return; } + read_records(dcr, record_cb, mount_next_read_volume); + printf("%u files found.\n", num_files); +} - /* Assume that we have already read the volume label. - * If on second or subsequent volume, adjust buffer pointer - */ - if (dev->VolHdr.PrevVolName[0] != 0) { /* second volume */ - Pmsg1(0, "\n\ -Warning, this Volume is a continuation of Volume %s\n", - dev->VolHdr.PrevVolName); +/* + * Called here for each record from read_records() + */ +static bool record_cb(DCR *dcr, DEV_RECORD *rec) +{ + if (rec->FileIndex < 0) { + get_session_record(dev, rec, &sessrec); + return true; } - - for ( ;; ) { - if (!read_record(dev, block, rec)) { - Dmsg0(20, "!read_record()\n"); - if (dev->state & ST_EOT) { - if (!mount_next_volume(infname)) { - break; - } - continue; - } - if (dev->state & ST_EOF) { - Emsg1(M_INFO, 0, "Got EOF on device %s\n", dev_name(dev)); - Dmsg0(20, "read_record got eof. try again\n"); - continue; - } - if (dev->state & ST_SHORT) { - Emsg0(M_INFO, 0, dev->errmsg); - continue; - } - display_error_status(); - break; + /* File Attributes stream */ + if (rec->Stream == STREAM_UNIX_ATTRIBUTES || + rec->Stream == STREAM_UNIX_ATTRIBUTES_EX) { + + if (!unpack_attributes_record(jcr, rec->Stream, rec->data, attr)) { + if (!forge_on) { + Emsg0(M_ERROR_TERM, 0, _("Cannot continue.\n")); + } + num_files++; + return true; } - if (debug_level >= 30) { - Dmsg4(30, "VolSId=%ld FI=%s Strm=%s Size=%ld\n", rec->VolSessionId, - FI_to_ascii(rec->FileIndex), stream_to_ascii(rec->Stream), - rec->data_len); + if (attr->file_index != rec->FileIndex) { + Emsg2(forge_on?M_WARNING:M_ERROR_TERM, 0, _("Record header file index %ld not equal record index %ld\n"), + rec->FileIndex, attr->file_index); } + attr->data_stream = decode_stat(attr->attr, &attr->statp, &attr->LinkFI); + build_attr_output_fnames(jcr, attr); - /* - * Check for End of File record (all zeros) - * NOTE: this no longer exists - */ - if (rec->VolSessionId == 0 && rec->VolSessionTime == 0) { - Emsg0(M_ERROR_TERM, 0, "Zero VolSessionId and VolSessionTime. This shouldn't happen\n"); - } - - /* - * Check for Start or End of Session Record - * - */ - if (rec->FileIndex < 0) { - dump_label_record(dev, rec, 0); - continue; - } - - /* File Attributes stream */ - if (rec->Stream == STREAM_UNIX_ATTRIBUTES) { - char *ap, *fp; - sscanf(rec->data, "%ld %d", &record_file_index, &type); - if (record_file_index != rec->FileIndex) { - Emsg2(M_ERROR_TERM, 0, "Record header file index %ld not equal record index %ld\n", - rec->FileIndex, record_file_index); - } - ap = rec->data; - - while (*ap++ != ' ') /* skip record file index */ - ; - while (*ap++ != ' ') /* skip type */ - ; - /* Save filename and position to attributes */ - fp = fname; - while (*ap != 0) { - *fp++ = *ap++; - } - *fp = *ap++; /* terminate filename & point to attribs */ - - decode_stat(ap, &statp); - /* Skip to link name */ - while (*ap++ != 0) - ; - print_ls_output(fname, ap, type, &statp); + if (file_is_included(ff, attr->fname) && !file_is_excluded(ff, attr->fname)) { + if (verbose) { + Pmsg5(-1, "FileIndex=%d VolSessionId=%d VolSessionTime=%d Stream=%d DataLen=%d\n", + rec->FileIndex, rec->VolSessionId, rec->VolSessionTime, rec->Stream, rec->data_len); + } + print_ls_output(jcr, attr); + num_files++; } } - return; + return true; } -extern char *getuser(uid_t uid); -extern char *getgroup(gid_t gid); -static void print_ls_output(char *fname, char *link, int type, struct stat *statp) +static void get_session_record(DEVICE *dev, DEV_RECORD *rec, SESSION_LABEL *sessrec) { - char buf[1000]; - char ec1[30]; - char *p, *f; - int n; - - if (!file_is_included(&ff, fname) || file_is_excluded(&ff, fname)) { - return; + const char *rtype; + memset(sessrec, 0, sizeof(sessrec)); + switch (rec->FileIndex) { + case PRE_LABEL: + rtype = "Fresh Volume Label"; + break; + case VOL_LABEL: + rtype = "Volume Label"; + unser_volume_label(dev, rec); + break; + case SOS_LABEL: + rtype = "Begin Job Session"; + unser_session_label(sessrec, rec); + break; + case EOS_LABEL: + rtype = "End Job Session"; + break; + case EOM_LABEL: + rtype = "End of Medium"; + break; + default: + rtype = "Unknown"; + break; } - p = encode_mode(statp->st_mode, buf); - n = sprintf(p, " %2d ", (uint32_t)statp->st_nlink); - p += n; - n = sprintf(p, "%-8.8s %-8.8s", getuser(statp->st_uid), getgroup(statp->st_gid)); - p += n; - n = sprintf(p, "%8.8s ", edit_uint64(statp->st_size, ec1)); - p += n; - p = encode_time(statp->st_ctime, p); - *p++ = ' '; - *p++ = ' '; - /* Copy file name */ - for (f=fname; *f && (p-buf) < (int)sizeof(buf); ) - *p++ = *f++; - if (type == FT_LNK) { - *p++ = ' '; - *p++ = '-'; - *p++ = '>'; - *p++ = ' '; - /* Copy link name */ - for (f=link; *f && (p-buf) < (int)sizeof(buf); ) - *p++ = *f++; + Dmsg5(10, "%s Record: VolSessionId=%d VolSessionTime=%d JobId=%d DataLen=%d\n", + rtype, rec->VolSessionId, rec->VolSessionTime, rec->Stream, rec->data_len); + if (verbose) { + Pmsg5(-1, "%s Record: VolSessionId=%d VolSessionTime=%d JobId=%d DataLen=%d\n", + rtype, rec->VolSessionId, rec->VolSessionTime, rec->Stream, rec->data_len); } - *p++ = '\n'; - *p = 0; - fputs(buf, stdout); } -/* Dummies to replace askdir.c */ -int dir_get_volume_info(JCR *jcr) { return 1;} -int dir_find_next_appendable_volume(JCR *jcr) { return 1;} -int dir_update_volume_info(JCR *jcr, VOLUME_CAT_INFO *vol, int relabel) { return 1; } -int dir_create_jobmedia_record(JCR *jcr) { return 1; } -int dir_ask_sysop_to_mount_next_volume(JCR *jcr, DEVICE *dev) { return 1; } -int dir_update_file_attributes(JCR *jcr, DEV_RECORD *rec) { return 1;} -int dir_send_job_status(JCR *jcr) {return 1;} - -int dir_ask_sysop_to_mount_volume(JCR *jcr, DEVICE *dev) +/* Dummies to replace askdir.c */ +bool dir_get_volume_info(DCR *dcr, enum get_vol_info_rw writing) { return 1;} +bool dir_find_next_appendable_volume(DCR *dcr) { return 1;} +bool dir_update_volume_info(DCR *dcr, bool relabel) { return 1; } +bool dir_create_jobmedia_record(DCR *dcr) { return 1; } +bool dir_ask_sysop_to_create_appendable_volume(DCR *dcr) { return 1; } +bool dir_update_file_attributes(DCR *dcr, DEV_RECORD *rec) { return 1;} +bool dir_send_job_status(JCR *jcr) {return 1;} +int generate_job_event(JCR *jcr, const char *event) { return 1; } + +bool dir_ask_sysop_to_mount_volume(DCR *dcr) { - fprintf(stderr, "Mount Volume %s on device %s and press return when ready: ", - jcr->VolumeName, dev_name(dev)); - getchar(); - return 1; + DEVICE *dev = dcr->dev; + fprintf(stderr, "Mount Volume \"%s\" on device %s and press return when ready: ", + dcr->VolumeName, dev->print_name()); + getchar(); + return true; }