X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;f=bacula%2Fsrc%2Fstored%2Fdircmd.c;h=f83263105b618a22451ed0ca75751f3ab17213d0;hb=22a5d43f2bf48e4d5c056dc17bd7cff90d84290e;hp=1243e24eea104b5dc2c3b4f7be2dd76d56e0041d;hpb=c9551616bc6691b48a2c9094f761243532ff987c;p=bacula%2Fbacula diff --git a/bacula/src/stored/dircmd.c b/bacula/src/stored/dircmd.c index 1243e24eea..f83263105b 100644 --- a/bacula/src/stored/dircmd.c +++ b/bacula/src/stored/dircmd.c @@ -43,8 +43,6 @@ extern BSOCK *filed_chan; extern int r_first, r_last; extern struct s_res resources[]; -extern char my_name[]; -extern time_t daemon_start_time; extern struct s_last_job last_job; extern bool init_done; @@ -209,7 +207,7 @@ void *handle_connection_request(void *arg) Dmsg1(200, "Do command: %s\n", cmds[i].cmd); if (!cmds[i].func(jcr)) { /* do command */ quit = true; /* error, get out */ - Dmsg1(190, "Command %s requsts quit\n", cmds[i].cmd); + Dmsg1(190, "Command %s reqeusts quit\n", cmds[i].cmd); } found = true; /* indicate command found */ break; @@ -281,6 +279,7 @@ static bool cancel_cmd(JCR *cjcr) pthread_cond_broadcast(&jcr->read_dcr->dev->wait_next_vol); pthread_cond_broadcast(&wait_device_release); } + Jmsg(jcr, M_INFO, 0, _("Job marked to be canceled.\n")); bnet_fsend(dir, _("3000 Job %s marked to be canceled.\n"), jcr->Job); free_jcr(jcr); } @@ -392,11 +391,15 @@ static void label_volume_if_ok(DCR *dcr, char *oldname, DEVICE *dev = dcr->dev; int label_status; int mode; + const char *volname = (relabel == 1) ? oldname : newname; + char ed1[50]; steal_device_lock(dev, &hold, BST_WRITING_LABEL); Dmsg1(100, "Stole device %s lock, writing label.\n", dev->print_name()); - if (!try_autoload_device(dcr->jcr, slot, newname)) { + + Dmsg0(90, "try_autoload_device - looking for volume_info\n"); + if (!try_autoload_device(dcr->jcr, slot, volname)) { goto bail_out; /* error */ } @@ -406,15 +409,23 @@ static void label_volume_if_ok(DCR *dcr, char *oldname, } else { mode = CREATE_READ_WRITE; } + + if (relabel) { + dev->truncating = true; /* let open() know we will truncate it */ + } + /* Set old volume name for open if relabeling */ + bstrncpy(dcr->VolCatInfo.VolCatName, volname, sizeof(dcr->VolCatInfo.VolCatName)); if (dev->open(dcr, mode) < 0) { bnet_fsend(dir, _("3910 Unable to open device %s: ERR=%s\n"), dev->print_name(), dev->strerror()); - return; + goto bail_out; } /* See what we have for a Volume */ label_status = read_dev_volume_label(dcr); + /* Set new volume name */ + bstrncpy(dcr->VolCatInfo.VolCatName, newname, sizeof(dcr->VolCatInfo.VolCatName)); switch(label_status) { case VOL_NAME_ERROR: case VOL_VERSION_ERROR: @@ -436,18 +447,19 @@ static void label_volume_if_ok(DCR *dcr, char *oldname, bnet_fsend(dir, _("3922 Cannot relabel an ANSI/IBM labeled Volume.\n")); break; } - free_volume(dev); /* release old volume name */ /* Fall through wanted! */ case VOL_IO_ERROR: case VOL_NO_LABEL: - if (!write_new_volume_label_to_dev(dcr, newname, poolname)) { + if (!write_new_volume_label_to_dev(dcr, newname, poolname, + relabel, true /* write dvd now */)) { bnet_fsend(dir, _("3912 Failed to label Volume: ERR=%s\n"), dev->bstrerror()); break; } bstrncpy(dcr->VolumeName, newname, sizeof(dcr->VolumeName)); /* The following 3000 OK label. string is scanned in ua_label.c */ - bnet_fsend(dir, "3000 OK label. Volume=%s Device=%s\n", - newname, dev->print_name()); + bnet_fsend(dir, "3000 OK label. VolBytes=%s DVD=%d Volume=\"%s\" Device=%s\n", + edit_uint64(dev->VolCatInfo.VolCatBytes, ed1), + dev->is_dvd()?1:0, newname, dev->print_name()); break; case VOL_NO_MEDIA: bnet_fsend(dir, _("3912 Failed to label Volume: ERR=%s\n"), dev->bstrerror()); @@ -582,8 +594,15 @@ static bool mount_cmd(JCR *jcr) DEVICE *dev; DCR *dcr; int drive; + int slot = 0; + bool ok; - if (sscanf(dir->msg, "mount %127s drive=%d", devname.c_str(), &drive) == 2) { + ok = sscanf(dir->msg, "mount %127s drive=%d slot=%d", devname.c_str(), + &drive, &slot) == 3; + if (!ok) { + ok = sscanf(dir->msg, "mount %127s drive=%d", devname.c_str(), &drive) == 2; + } + if (ok) { dcr = find_device(jcr, devname, drive); if (dcr) { dev = dcr->dev; @@ -603,6 +622,9 @@ static bool mount_cmd(JCR *jcr) /* In both of these two cases, we (the user) unmounted the Volume */ case BST_UNMOUNTED_WAITING_FOR_SYSOP: case BST_UNMOUNTED: + if (dev->is_autochanger() && slot > 0) { + try_autoload_device(jcr, slot, ""); + } /* We freed the device, so reopen it and wake any waiting threads */ if (dev->open(dcr, OPEN_READ_ONLY) < 0) { bnet_fsend(dir, _("3901 open device failed: ERR=%s\n"), @@ -647,6 +669,9 @@ static bool mount_cmd(JCR *jcr) break; case BST_NOT_BLOCKED: + if (dev->is_autochanger() && slot > 0) { + try_autoload_device(jcr, slot, ""); + } if (dev->is_open()) { if (dev->is_labeled()) { bnet_fsend(dir, _("3001 Device %s is mounted with Volume \"%s\"\n"), @@ -722,19 +747,31 @@ static bool unmount_cmd(JCR *jcr) if (!dev->is_busy()) { unload_autochanger(jcr->dcr, -1); } - Dmsg0(90, "Device already unmounted\n"); - bnet_fsend(dir, _("3901 Device %s is already unmounted.\n"), - dev->print_name()); - + if (dev->is_dvd()) { + if (unmount_dvd(dev, 0)) { + bnet_fsend(dir, _("3002 Device %s unmounted.\n"), + dev->print_name()); + } else { + bnet_fsend(dir, _("3907 %s"), dev->bstrerror()); + } + } else { + Dmsg0(90, "Device already unmounted\n"); + bnet_fsend(dir, _("3901 Device %s is already unmounted.\n"), + dev->print_name()); + } } else if (dev->dev_blocked == BST_WAITING_FOR_SYSOP) { Dmsg2(90, "%d waiter dev_block=%d. doing unmount\n", dev->num_waiting, dev->dev_blocked); if (!unload_autochanger(jcr->dcr, -1)) { dev->close(); } - dev->dev_blocked = BST_UNMOUNTED_WAITING_FOR_SYSOP; - bnet_fsend(dir, _("3001 Device %s unmounted.\n"), - dev->print_name()); + if (dev->is_dvd() && !unmount_dvd(dev, 0)) { + bnet_fsend(dir, _("3907 %s"), dev->bstrerror()); + } else { + dev->dev_blocked = BST_UNMOUNTED_WAITING_FOR_SYSOP; + bnet_fsend(dir, _("3001 Device %s unmounted.\n"), + dev->print_name()); + } } else if (dev->dev_blocked == BST_DOING_ACQUIRE) { bnet_fsend(dir, _("3902 Device %s is busy in acquire.\n"), @@ -759,8 +796,12 @@ static bool unmount_cmd(JCR *jcr) if (!unload_autochanger(jcr->dcr, -1)) { dev->close(); } - bnet_fsend(dir, _("3002 Device %s unmounted.\n"), - dev->print_name()); + if (dev->is_dvd() && !unmount_dvd(dev, 0)) { + bnet_fsend(dir, _("3907 %s"), dev->bstrerror()); + } else { + bnet_fsend(dir, _("3002 Device %s unmounted.\n"), + dev->print_name()); + } } V(dev->mutex); free_dcr(dcr); @@ -857,17 +898,21 @@ static bool changer_cmd(JCR *jcr) DCR *dcr; const char *cmd = NULL; bool ok = false; - bool dolist = false; + /* + * A safe_cmd may call autochanger script but does not load/unload + * slots so it can be done at the same time that the drive is open. + */ + bool safe_cmd = false; if (sscanf(dir->msg, "autochanger list %127s", devname.c_str()) == 1) { cmd = "list"; - dolist = ok = true; + safe_cmd = ok = true; } else if (sscanf(dir->msg, "autochanger slots %127s", devname.c_str()) == 1) { cmd = "slots"; - ok = true; + safe_cmd = ok = true; } else if (sscanf(dir->msg, "autochanger drives %127s", devname.c_str()) == 1) { cmd = "drives"; - ok = true; + safe_cmd = ok = true; } if (ok) { dcr = find_device(jcr, devname, -1); @@ -878,7 +923,7 @@ static bool changer_cmd(JCR *jcr) bnet_fsend(dir, _("3995 Device %s is not an autochanger.\n"), dev->print_name()); /* Under certain "safe" conditions, we can steal the lock */ - } else if (dolist || !dev->is_open() || dev->can_steal_lock()) { + } else if (safe_cmd || !dev->is_open() || dev->can_steal_lock()) { autochanger_cmd(dcr, dir, cmd); } else if (dev->is_busy() || dev->is_blocked()) { send_dir_busy_message(dir, dev);