General:
Changes to 1.37.28:
+11Jul05
+- Lots of documentation.
+- Do not prune volume marked as append when needing a
+ new Volume.
+- Print a warning message in SD if a non-used Volume
+ is specified and autolabel not turned on.
+- Correct a bug in chksum.c concerning SHA1 signatures
+ (an * should have been & when checking for a bit flag).
+- Print File:Block for all label records in label.c -- concerns
+ primarily bls when doing Job listings (-j).
+- Correct is_volume_in_use() to return false if testing
+ on the same device where the Volume is already mounted.
+- Define a init_done flag in the SD that is set when the
+ devices are initialized and make users connecting wait.
+ This prevents useless connect failure warning messages.
+- Do additional device locking in ask_op_to_mount_volume()
+ to prevent race conditions with a user labeling a Volume
+ or autolabeling.
09Jul05
- Add a test for error return from bnet_wait... in heartbeat.c
in FD to avoid CPU loop.
*
* Version $Id$
*/
-
/*
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 amended 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.
*/
db_lock(mdb);
Mmsg(mdb->cmd, "SELECT MediaId FROM Media WHERE VolumeName='%s'",
mr->VolumeName);
- Dmsg1(300, "selectpool: %s\n", mdb->cmd);
+ Dmsg1(500, "selectpool: %s\n", mdb->cmd);
if (QUERY_DB(jcr, mdb, mdb->cmd)) {
mdb->num_rows = sql_num_rows(mdb);
"VolStatus,Slot,VolBytes,InChanger,VolReadTime,VolWriteTime,VolParts,"
"EndFile,EndBlock,LabelType,StorageId) "
"VALUES ('%s','%s',%u,%s,%s,%d,%s,%s,%u,%u,'%s',%d,%s,%d,%s,%s,%d,0,0,%d,%s)",
- mr->VolumeName,
- mr->MediaType, mr->PoolId,
- edit_uint64(mr->MaxVolBytes,ed1),
- edit_uint64(mr->VolCapacityBytes, ed2),
- mr->Recycle,
- edit_uint64(mr->VolRetention, ed3),
- edit_uint64(mr->VolUseDuration, ed4),
- mr->MaxVolJobs,
- mr->MaxVolFiles,
- mr->VolStatus,
- mr->Slot,
- edit_uint64(mr->VolBytes, ed5),
- mr->InChanger,
- edit_uint64(mr->VolReadTime, ed6),
- edit_uint64(mr->VolWriteTime, ed7),
- mr->VolParts,
- mr->LabelType,
- edit_int64(mr->StorageId, ed8)
- );
+ mr->VolumeName,
+ mr->MediaType, mr->PoolId,
+ edit_uint64(mr->MaxVolBytes,ed1),
+ edit_uint64(mr->VolCapacityBytes, ed2),
+ mr->Recycle,
+ edit_uint64(mr->VolRetention, ed3),
+ edit_uint64(mr->VolUseDuration, ed4),
+ mr->MaxVolJobs,
+ mr->MaxVolFiles,
+ mr->VolStatus,
+ mr->Slot,
+ edit_uint64(mr->VolBytes, ed5),
+ mr->InChanger,
+ edit_uint64(mr->VolReadTime, ed6),
+ edit_uint64(mr->VolWriteTime, ed7),
+ mr->VolParts,
+ mr->LabelType,
+ edit_int64(mr->StorageId, ed8)
+ );
Dmsg1(500, "Create Volume: %s\n", mdb->cmd);
/*
*
* Bacula Director -- Automatic Pruning
- * Applies retention periods
+ * Applies retention periods
*
* Kern Sibbald, May MMII
*
CLIENT *client;
bool pruned;
- if (!jcr->client) { /* temp -- remove me */
+ if (!jcr->client) { /* temp -- remove me */
return 1;
}
* volume and no appendable volumes are available.
*
* Return 0: on error
- * number of Volumes Purged
+ * number of Volumes Purged
*/
int prune_volumes(JCR *jcr)
{
for (i=0; i<num_ids; i++) {
mr.MediaId = ids[i];
if (!db_get_media_record(jcr, jcr->db, &mr)) {
- Jmsg(jcr, M_ERROR, 0, "%s", db_strerror(jcr->db));
- continue;
+ Jmsg(jcr, M_ERROR, 0, "%s", db_strerror(jcr->db));
+ continue;
}
/* Prune only Volumes from current Pool */
if (jcr->PoolId != mr.PoolId) {
- continue;
+ continue;
}
- /* Prune only Volumes with status "Full", "Used", or "Append" */
+ /* Prune only Volumes with status "Full", or "Used" */
if (strcmp(mr.VolStatus, "Full") == 0 ||
- strcmp(mr.VolStatus, "Append") == 0 ||
- strcmp(mr.VolStatus, "Used") == 0) {
- Dmsg1(200, "Prune Volume %s\n", mr.VolumeName);
- stat += prune_volume(ua, &mr);
- Dmsg1(200, "Num pruned = %d\n", stat);
+ strcmp(mr.VolStatus, "Used") == 0) {
+ Dmsg1(200, "Prune Volume %s\n", mr.VolumeName);
+ stat += prune_volume(ua, &mr);
+ Dmsg1(200, "Num pruned = %d\n", stat);
}
}
}
if (cnt.count == 0) {
+ /* Don't mark appendable volume as purged */
+ if (strcmp(mr->VolStatus, "Append") == 0 && verbose) {
+ bsendmsg(ua, "There are no Jobs associated with Volume \"%s\". Prune not needed.\n",
+ mr->VolumeName);
+ stat = 1;
+ goto bail_out;
+ }
+ /* If volume not already purged, do so */
if (strcmp(mr->VolStatus, "Purged") != 0 && verbose) {
bsendmsg(ua, "There are no Jobs associated with Volume \"%s\". Marking it purged.\n",
mr->VolumeName);
*
* Version $Id$
*/
+/*
+ Copyright (C) 2004-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
+ version 2 as amended 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
+ the file LICENSE for additional details.
+
+ */
#ifndef TEST_PROGRAM
#include "acl.h"
#define BACLLEN 65535
-#define pm_strcpy(d,s) (strncpy(d, s, BACLLEN - 1) == NULL ? -1 : (int)strlen(d))
-#define Dmsg0(n,s) fprintf(stderr, s)
-#define Dmsg1(n,s,a1) fprintf(stderr, s, a1)
+#define pm_strcpy(d,s) (strncpy(d, s, BACLLEN - 1) == NULL ? -1 : (int)strlen(d))
+#define Dmsg0(n,s) fprintf(stderr, s)
+#define Dmsg1(n,s,a1) fprintf(stderr, s, a1)
#define Dmsg2(n,s,a1,a2) fprintf(stderr, s, a1, a2)
int aclls(char *fname);
/* On IRIX we can get shortened ACLs */
#if defined(HAVE_IRIX_OS) && defined(BACL_WANT_SHORT_ACLS)
-#define acl_to_text(acl,len) acl_to_short_text((acl), (len))
+#define acl_to_text(acl,len) acl_to_short_text((acl), (len))
#endif
/* In Linux we can get numeric and/or shorted ACLs */
#if defined(HAVE_LINUX_OS)
#if defined(BACL_WANT_SHORT_ACLS) && defined(BACL_WANT_NUMERIC_IDS)
-#define BACL_ALTERNATE_TEXT (TEXT_ABBREVIATE|TEXT_NUMERIC_IDS)
+#define BACL_ALTERNATE_TEXT (TEXT_ABBREVIATE|TEXT_NUMERIC_IDS)
#elif defined(BACL_WANT_SHORT_ACLS)
-#define BACL_ALTERNATE_TEXT TEXT_ABBREVIATE
+#define BACL_ALTERNATE_TEXT TEXT_ABBREVIATE
#elif defined(BACL_WANT_NUMERIC_IDS)
-#define BACL_ALTERNATE_TEXT TEXT_NUMERIC_IDS
+#define BACL_ALTERNATE_TEXT TEXT_NUMERIC_IDS
#endif
#ifdef BACL_ALTERNATE_TEXT
#include <acl/libacl.h>
acl = acl_get_file(jcr->last_fname, ostype);
if (acl) {
if ((acl_text = acl_to_text(acl, NULL)) != NULL) {
- len = pm_strcpy(jcr->acl_text, acl_text);
- acl_free(acl);
- acl_free(acl_text);
- return len;
+ len = pm_strcpy(jcr->acl_text, acl_text);
+ acl_free(acl);
+ acl_free(acl_text);
+ return len;
}
acl_free(acl);
-#ifndef HAVE_OSF1_OS /* BACL_ENOTSUP not defined for OSF1 */
+#ifndef HAVE_OSF1_OS /* BACL_ENOTSUP not defined for OSF1 */
} else if (errno == BACL_ENOTSUP) {
/* Not supported, just pretend there is nothing to see */
return pm_strcpy(jcr->acl_text, "");
/* If we get empty default ACLs, clear ACLs now */
if (ostype == ACL_TYPE_DEFAULT && strlen(jcr->acl_text) == 0) {
if (acl_delete_def_file(jcr->last_fname) == 0) {
- return 0;
+ return 0;
}
return -1;
}
if ((n = getacl(jcr->last_fname, 0, acls)) <= 0) {
if (errno == BACL_ENOTSUP) {
- return pm_strcpy(jcr->acl_text, "");
+ return pm_strcpy(jcr->acl_text, "");
}
return -1;
}
if ((n = getacl(jcr->last_fname, n, acls)) > 0) {
if ((acl_text = acltostr(n, acls, FORM_SHORT)) != NULL) {
- len = pm_strcpy(jcr->acl_text, acl_text);
- free(acl_text);
- return len;
+ len = pm_strcpy(jcr->acl_text, acl_text);
+ free(acl_text);
+ return len;
}
}
return -1;
}
if (acl(jcr->last_fname, GETACL, n, acls) == n) {
if ((acl_text = acltotext(acls, n)) != NULL) {
- len = pm_strcpy(jcr->acl_text, acl_text);
- free(acl_text);
- free(acls);
- return len;
+ len = pm_strcpy(jcr->acl_text, acl_text);
+ free(acl_text);
+ free(acls);
+ return len;
}
}
free(acls);
if (strcmp(prgname, "aclcp") == 0) {
int verbose = 0;
if (strcmp(*argv, "-v") == 0) {
- ++verbose;
- --argc;
- ++argv;
+ ++verbose;
+ --argc;
+ ++argv;
}
if (argc != 2) {
Dmsg2(200, "%s: wrong number of arguments\n"
"usage:\t%s [-v] source destination\n"
"\tCopies ACLs from source to destination.\n"
"\tSpecify -v to show ACLs after copy for verification.\n",
- prgname, prgname);
- return EXIT_FAILURE;
+ prgname, prgname);
+ return EXIT_FAILURE;
}
if (strcmp(argv[0], argv[1]) == 0) {
Dmsg2(200, "%s: identical source and destination.\n"
"usage:\t%s [-v] source destination\n"
"\tCopies ACLs from source to destination.\n"
"\tSpecify -v to show ACLs after copy for verification.\n",
- prgname, prgname);
- return EXIT_FAILURE;
+ prgname, prgname);
+ return EXIT_FAILURE;
}
if (verbose) {
- aclls(argv[0]);
+ aclls(argv[0]);
}
status = aclcp(argv[0], argv[1]);
if (verbose && status == 0) {
- aclls(argv[1]);
+ aclls(argv[1]);
}
return status;
}
Dmsg2(200, "%s: missing arguments\n"
"usage:\t%s file ...\n"
"\tLists ACLs of specified files or directories.\n",
- prgname, prgname);
+ prgname, prgname);
return EXIT_FAILURE;
}
while (argc--) {
if (!aclls(*argv++)) {
- status = EXIT_FAILURE;
+ status = EXIT_FAILURE;
}
}
jcr.last_fname = dst;
if (bacl_set(&jcr, BACL_TYPE_ACCESS) < 0) {
Dmsg1(200, "aclcp: could not set ACLs on %s\n", jcr.last_fname);
- return EXIT_FAILURE;
+ return EXIT_FAILURE;
}
}
jcr.last_fname = src;
if (bacl_get(&jcr, BACL_TYPE_DEFAULT) < 0) {
Dmsg1(200, "aclcp: could not read default ACLs for %s\n", jcr.last_fname);
- return EXIT_FAILURE;
+ return EXIT_FAILURE;
} else {
- jcr.last_fname = dst;
- if (bacl_set(&jcr, BACL_TYPE_DEFAULT) < 0) {
+ jcr.last_fname = dst;
+ if (bacl_set(&jcr, BACL_TYPE_DEFAULT) < 0) {
Dmsg1(200, "aclcp: could not set default ACLs on %s\n", jcr.last_fname);
- return EXIT_FAILURE;
- }
+ return EXIT_FAILURE;
+ }
}
}
len = bacl_get(&jcr, BACL_TYPE_DEFAULT);
if (len < 0) {
Dmsg1(200, "acl: could not read default ACLs for %s\n", jcr.last_fname);
- return EXIT_FAILURE;
+ return EXIT_FAILURE;
} else if (len == 0) {
- printf("#file: %s [default, none - or unsupported]\n\n", jcr.last_fname);
+ printf("#file: %s [default, none - or unsupported]\n\n", jcr.last_fname);
} else {
- printf("#file: %s [default]\n%s\n", jcr.last_fname, jcr.acl_text);
+ printf("#file: %s [default]\n%s\n", jcr.last_fname, jcr.acl_text);
}
}
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 amended 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.
*/
*
* Written by Preben 'Peppe' Guldberg, December MMIV
*/
-
/*
- Copyright (C) 2004 Kern Sibbald
+ Copyright (C) 2004-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 amended 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.
*/
MD5Init(&chksum->context.md5);
chksum->type = CHKSUM_MD5;
bstrncpy(chksum->name, "MD5", sizeof(chksum->name));
- } else if (flags * CHKSUM_SHA1) {
+ } else if (flags & CHKSUM_SHA1) {
chksum->length = 20;
status = SHA1Init(&chksum->context.sha1);
if (status == 0) {
- chksum->type = CHKSUM_SHA1;
- bstrncpy(chksum->name, "SHA1", sizeof(chksum->name));
+ chksum->type = CHKSUM_SHA1;
+ bstrncpy(chksum->name, "SHA1", sizeof(chksum->name));
}
}
return status;
case CHKSUM_SHA1:
status = SHA1Update(&chksum->context.sha1, (uint8_t *)buf, len);
if (status == 0) {
- chksum->updated = true;
+ chksum->updated = true;
}
return status;
default:
/*
* General routines for handling the various checksum supported.
*/
-
/*
- Copyright (C) 2004 Kern Sibbald
+ 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 amended 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.
*/
dcr->dev->num_parts = dcr->VolCatInfo.VolCatParts;
}
- Dmsg2(300, "do_reqest_vol_info got slot=%d Volume=%s\n",
+ Dmsg2(300, "do_reqest_vol_info return true slot=%d Volume=%s\n",
vol.Slot, vol.VolCatName);
return true;
}
bnet_fsend(dir, Get_Vol_Info, jcr->Job, dcr->VolCatInfo.VolCatName,
writing==GET_VOL_INFO_FOR_WRITE?1:0);
Dmsg1(100, ">dird: %s", dir->msg);
- return do_get_volume_info(dcr);
+ bool OK = do_get_volume_info(dcr);
+ return OK;
}
/*
unbash_spaces(dcr->media_type);
unbash_spaces(dcr->pool_name);
Dmsg1(100, ">dird: %s", dir->msg);
- if (do_get_volume_info(dcr)) {
- if (is_volume_in_use(dcr->VolumeName)) {
+ bool OK = do_get_volume_info(dcr);
+ if (OK) {
+ if (is_volume_in_use(dcr)) {
+ Dmsg1(100, "Volume %s is in use.\n", dcr->VolumeName);
continue;
} else {
found = true;
vol->VolCatParts);
Dmsg1(100, ">dird: %s", dir->msg);
+ /* Do not lock device here because it may be locked from label */
if (!do_get_volume_info(dcr)) {
Jmsg(jcr, M_FATAL, 0, "%s", jcr->errmsg);
Pmsg2(000, "Didn't get vol info vol=%s: ERR=%s",
bool first = true;
DEVICE *dev = dcr->dev;
JCR *jcr = dcr->jcr;
+ bool OK = false;
Dmsg0(400, "enter dir_ask_sysop_to_create_appendable_volume\n");
ASSERT(dev->dev_blocked);
return false;
}
/* First pass, we *know* there are no appendable volumes, so no need to call */
- if (!first && dir_find_next_appendable_volume(dcr)) { /* get suggested volume */
+ if (!first) {
+ P(dev->mutex);
+ OK = dir_find_next_appendable_volume(dcr); /* get suggested volume */
+ V(dev->mutex);
+ }
+ if (!first && OK) {
unmounted = is_device_unmounted(dev);
/*
* If we have a valid volume name and we are not
Dmsg1(400, "Someone woke me for device %s\n", dev->print_name());
/* If no VolumeName, and cannot get one, try again */
+ P(dev->mutex);
if (dcr->VolumeName[0] == 0 && !job_canceled(jcr) &&
!dir_find_next_appendable_volume(dcr)) {
+ V(dev->mutex);
Jmsg(jcr, M_MOUNT, 0, _(
"Someone woke me up, but I cannot find any appendable\n"
"volumes for Job=%s.\n"), jcr->Job);
init_device_wait_timers(dcr);
continue;
}
+ V(dev->mutex);
unmounted = is_device_unmounted(dev);
if (unmounted) {
+ Dmsg0(400, "Device is unmounted. Must wait.\n");
continue; /* continue to wait */
}
Jmsg(jcr, M_MOUNT, 0, _("%s Volume \"%s\" on Storage Device %s for Job %s\n"),
msg, dcr->VolumeName, dev->print_name(), jcr->Job);
Dmsg3(400, "Mount \"%s\" on device \"%s\" for Job %s\n",
- dcr->VolumeName, dcr->dev_name, jcr->Job);
+ dcr->VolumeName, dev->print_name(), jcr->Job);
}
jcr->JobStatus = JS_WaitMount;
case 'i': /* include list */
if ((fd = fopen(optarg, "r")) == NULL) {
- Pmsg2(0, "Could not open include file: %s, ERR=%s\n",
+ Pmsg2(0, _("Could not open include file: %s, ERR=%s\n"),
optarg, strerror(errno));
exit(1);
}
return false;
}
}
- Pmsg1(000, "open_ ev %s OK\n", dev->print_name());
+ Pmsg1(000, "open device %s: OK\n", dev->print_name());
dev->set_append(); /* put volume in append mode */
unlock_device(dev);
free_block(block);
dev->no_wait_id = hold->no_wait_id;
Dmsg1(400, "return lock. new=%s\n", dev->print_blocked());
if (dev->num_waiting > 0) {
- Dmsg0(400, "Broadcase\n");
+ Dmsg0(400, "Broadcast\n");
pthread_cond_broadcast(&dev->wait); /* wake them up */
}
}
*
* N.B. in this file, in general we must use P(dev->mutex) rather
* than lock_device(dev) so that we can examine the blocked
- * state rather than blocking ourselves. In some "safe" cases,
+ * state rather than blocking ourselves because a Job
+ * thread has the device blocked. In some "safe" cases,
* we can do things to a blocked device. CAREFUL!!!!
*
* File daemon commands are handled in fdcmd.c
extern char my_name[];
extern time_t daemon_start_time;
extern struct s_last_job last_job;
+extern bool init_done;
/* Static variables */
static char derrmsg[] = "3900 Invalid command\n";
break; /* connection terminated */
}
Dmsg1(199, "<dird: %s\n", bs->msg);
+ /* Ensure that device initialization is complete */
+ while (!init_done) {
+ bmicrosleep(1, 0);
+ }
found = false;
for (i=0; cmds[i].cmd; i++) {
if (strncmp(cmds[i].cmd, bs->msg, strlen(cmds[i].cmd)) == 0) {
const char *type;
int dbl;
+ if (rec->FileIndex == 0 && rec->VolSessionId == 0 && rec->VolSessionTime == 0) {
+ return;
+ }
dbl = debug_level;
debug_level = 1;
switch (rec->FileIndex) {
dump_session_label(rec, type);
break;
case EOM_LABEL:
- Pmsg5(-1, "%s Record: SessId=%d SessTime=%d JobId=%d DataLen=%d\n",
- type, rec->VolSessionId, rec->VolSessionTime, rec->Stream, rec->data_len);
+ Pmsg7(-1, "%s Record: File:blk=%u:%u SessId=%d SessTime=%d JobId=%d DataLen=%d\n",
+ type, dev->file, dev->block_num, rec->VolSessionId,
+ rec->VolSessionTime, rec->Stream, rec->data_len);
break;
case EOT_LABEL:
Pmsg0(-1, _("End of physical tape.\n"));
break;
default:
- Pmsg5(-1, "%s Record: SessId=%d SessTime=%d JobId=%d DataLen=%d\n",
- type, rec->VolSessionId, rec->VolSessionTime, rec->Stream, rec->data_len);
+ Pmsg7(-1, "%s Record: File:blk=%u:%u SessId=%d SessTime=%d JobId=%d DataLen=%d\n",
+ type, dev->file, dev->block_num, rec->VolSessionId,
+ rec->VolSessionTime, rec->Stream, rec->data_len);
break;
}
} else {
switch (rec->FileIndex) {
case SOS_LABEL:
unser_session_label(&label, rec);
- Pmsg6(-1, "%s Record: SessId=%d SessTime=%d JobId=%d Level=%c Type=%c\n",
- type, rec->VolSessionId, rec->VolSessionTime, rec->Stream,
+ Pmsg8(-1, "%s Record: File:blk=%u:%u SessId=%d SessTime=%d JobId=%d Level=%c Type=%c\n",
+ type, dev->file, dev->block_num, rec->VolSessionId, rec->VolSessionTime, rec->Stream,
label.JobLevel, label.JobType);
break;
case EOS_LABEL:
char ed1[30], ed2[30];
unser_session_label(&label, rec);
- Pmsg6(-1, "%s Record: SessId=%d SessTime=%d JobId=%d Level=%c Type=%c\n",
- type, rec->VolSessionId, rec->VolSessionTime, rec->Stream,
+ Pmsg8(-1, "%s Record: File:blk=%u:%u SessId=%d SessTime=%d JobId=%d Level=%c Type=%c\n",
+ type, dev->file, dev->block_num, rec->VolSessionId, rec->VolSessionTime, rec->Stream,
label.JobLevel, label.JobType);
Pmsg4(-1, " Files=%s Bytes=%s Errors=%d Status=%c\n",
edit_uint64_with_commas(label.JobFiles, ed1),
case PRE_LABEL:
case VOL_LABEL:
default:
- Pmsg5(-1, "%s Record: SessId=%d SessTime=%d JobId=%d DataLen=%d\n",
- type, rec->VolSessionId, rec->VolSessionTime, rec->Stream, rec->data_len);
+ Pmsg7(-1, "%s Record: File:blk=%u:%u SessId=%d SessTime=%d JobId=%d DataLen=%d\n",
+ type, dev->file, dev->block_num, rec->VolSessionId, rec->VolSessionTime,
+ rec->Stream, rec->data_len);
break;
case EOT_LABEL:
break;
dcr->VolumeName, dev->print_name());
goto read_volume; /* read label we just wrote */
}
+ if (!dev_cap(dev, CAP_LABEL) && dcr->VolCatInfo.VolCatBytes == 0) {
+ Jmsg(jcr, M_INFO, 0, _("Warning device %s not configured to autolabel Volumes.\n"),
+ dev->print_name());
+ }
/* If not removable, Volume is broken */
if (!dev_cap(dev, CAP_REM)) {
Jmsg(jcr, M_WARNING, 0, _("Volume \"%s\" not on device %s.\n"),
void create_volume_list();
void free_volume_list();
void list_volumes(BSOCK *user);
-bool is_volume_in_use(const char *VolumeName);
+bool is_volume_in_use(DCR *dcr);
/* From spool.c */
/* Create the Volume list */
void create_volume_list()
{
- VOLRES *dummy;
+ VOLRES *dummy = NULL;
if (vol_list == NULL) {
vol_list = New(dlist(dummy, &dummy->link));
}
vol_list = NULL;
}
-bool is_volume_in_use(const char *VolumeName)
+bool is_volume_in_use(DCR *dcr)
{
- VOLRES *vol = find_volume(VolumeName);
+ VOLRES *vol = find_volume(dcr->VolumeName);
if (!vol) {
return false; /* vol not in list */
}
if (!vol->dev) { /* vol not attached to device */
return false;
}
+ if (dcr->dev == vol->dev) { /* same device OK */
+ return false;
+ }
if (!vol->dev->is_busy()) {
return false;
}
static uint32_t VolSessionId = 0;
uint32_t VolSessionTime;
char *configfile = NULL;
+bool init_done = false;
/* Global static variables */
static int foreground = 0;
/* Make sure on Solaris we can run concurrent, watch dog + servers + misc */
set_thread_concurrency(me->max_concurrent_jobs * 2 + 4);
- create_volume_list();
/*
* Start the device allocation thread
*/
Emsg1(M_ABORT, 0, _("Unable to create thread. ERR=%s\n"), strerror(errno));
}
+ create_volume_list();
start_watchdog(); /* start watchdog thread */
-
init_jcr_subsystem(); /* start JCR watchdogs etc. */
- /*
- * Sleep a bit to give device thread a chance to lock the resource
- * chain before we start the server.
- */
- bmicrosleep(1, 0);
-
- /* Wait for device initialization to complete */
- LockRes();
- UnlockRes();
-
/* Single server used for Director and File daemon */
bnet_thread_server(me->sdaddrs, me->max_concurrent_jobs * 2 + 1,
&dird_workq, handle_connection_request);
free_dcr(dcr);
}
free_jcr(jcr);
+ init_done = true;
UnlockRes();
return NULL;
}
/* */
#undef VERSION
-#define VERSION "1.37.28"
-#define BDATE "09 July 2005"
-#define LSMDATE "09Jul05"
+#define VERSION "1.37.29"
+#define BDATE "11 July 2005"
+#define LSMDATE "11Jul05"
/* Debug flags */
#undef DEBUG
/* The following are turned on for performance testing */
/* #define NO_ATTRIBUTES_TEST 1 */
/* #define NO_TAPE_WRITE_TEST 1 */
-/* #define FD_NO_SEND TEST 1 */
+/* #define FD_NO_SEND_TEST 1 */