]> git.sur5r.net Git - bacula/bacula/blob - bacula/src/stored/reserve.c
bc590e210ad2a010bc1882951b76104cd38cfbd9
[bacula/bacula] / bacula / src / stored / reserve.c
1 /*
2    Bacula® - The Network Backup Solution
3
4    Copyright (C) 2000-2007 Free Software Foundation Europe e.V.
5
6    The main author of Bacula is Kern Sibbald, with contributions from
7    many others, a complete list can be found in the file AUTHORS.
8    This program is Free Software; you can redistribute it and/or
9    modify it under the terms of version two of the GNU General Public
10    License as published by the Free Software Foundation plus additions
11    that are listed in the file LICENSE.
12
13    This program is distributed in the hope that it will be useful, but
14    WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16    General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21    02110-1301, USA.
22
23    Bacula® is a registered trademark of John Walker.
24    The licensor of Bacula is the Free Software Foundation Europe
25    (FSFE), Fiduciary Program, Sumatrastrasse 25, 8006 Zürich,
26    Switzerland, email:ftf@fsfeurope.org.
27 */
28 /*
29  *   Drive reservation functions for Storage Daemon
30  *
31  *   Kern Sibbald, MM
32  *
33  *   Split from job.c and acquire.c June 2005
34  *
35  *   Version $Id$
36  *
37  */
38
39 #include "bacula.h"
40 #include "stored.h"
41
42 static dlist *vol_list = NULL;
43 static pthread_mutex_t vol_list_lock = PTHREAD_MUTEX_INITIALIZER;
44
45 /* Forward referenced functions */
46 static int can_reserve_drive(DCR *dcr, RCTX &rctx);
47 static int reserve_device(RCTX &rctx);
48 static bool reserve_device_for_read(DCR *dcr);
49 static bool reserve_device_for_append(DCR *dcr, RCTX &rctx);
50 static bool use_storage_cmd(JCR *jcr);
51 static void queue_reserve_message(JCR *jcr);
52
53 /* Requests from the Director daemon */
54 static char use_storage[]  = "use storage=%127s media_type=%127s "
55    "pool_name=%127s pool_type=%127s append=%d copy=%d stripe=%d\n";
56 static char use_device[]  = "use device=%127s\n";
57
58 /* Responses sent to Director daemon */
59 static char OK_device[] = "3000 OK use device device=%s\n";
60 static char NO_device[] = "3924 Device \"%s\" not in SD Device resources.\n";
61 static char BAD_use[]   = "3913 Bad use command: %s\n";
62
63 bool use_cmd(JCR *jcr) 
64 {
65    /*
66     * Get the device, media, and pool information
67     */
68    if (!use_storage_cmd(jcr)) {
69       set_jcr_job_status(jcr, JS_ErrorTerminated);
70       memset(jcr->sd_auth_key, 0, strlen(jcr->sd_auth_key));
71       return false;
72    }
73    return true;
74 }
75
76 static int my_compare(void *item1, void *item2)
77 {
78    return strcmp(((VOLRES *)item1)->vol_name, ((VOLRES *)item2)->vol_name);
79 }
80
81 static brwlock_t reservation_lock;
82
83 void init_reservations_lock()
84 {
85    int errstat;
86    if ((errstat=rwl_init(&reservation_lock)) != 0) {
87       berrno be;
88       Emsg1(M_ABORT, 0, _("Unable to initialize reservation lock. ERR=%s\n"),
89             be.strerror(errstat));
90    }
91
92 }
93
94 void term_reservations_lock()
95 {
96    rwl_destroy(&reservation_lock);
97 }
98
99 int reservations_lock_count = 0;
100
101 /* This applies to a drive and to Volumes */
102 void _lock_reservations()
103 {
104    int errstat;
105    reservations_lock_count++;
106    if ((errstat=rwl_writelock(&reservation_lock)) != 0) {
107       berrno be;
108       Emsg2(M_ABORT, 0, "rwl_writelock failure. stat=%d: ERR=%s\n",
109            errstat, be.strerror(errstat));
110    }
111 }
112
113 void _unlock_reservations()
114 {
115    int errstat;
116    reservations_lock_count--;
117    if ((errstat=rwl_writeunlock(&reservation_lock)) != 0) {
118       berrno be;
119       Emsg2(M_ABORT, 0, "rwl_writeunlock failure. stat=%d: ERR=%s\n",
120            errstat, be.strerror(errstat));
121    }
122 }
123
124 /*
125  * List Volumes -- this should be moved to status.c
126  */
127 enum {
128    debug_lock = true,
129    debug_nolock = false
130 };
131
132 static void debug_list_volumes(const char *imsg, bool do_lock)
133 {
134    VOLRES *vol;
135    POOL_MEM msg(PM_MESSAGE);
136    int count = 0;
137    DEVICE *dev = NULL;
138
139    if (do_lock) P(vol_list_lock);
140    for (vol=(VOLRES *)vol_list->first(); vol; vol=(VOLRES *)vol_list->next(vol)) {
141       if (vol->dev) {
142          Mmsg(msg, "List from %s: %s at %p on device %s\n", imsg, 
143               vol->vol_name, vol->vol_name, vol->dev->print_name());
144       } else {
145          Mmsg(msg, "List from %s: %s at %p no dev\n", imsg, vol->vol_name, vol->vol_name);
146       }
147       Dmsg1(100, "%s", msg.c_str());
148       count++;
149    }
150
151    for (vol=(VOLRES *)vol_list->first(); vol; vol=(VOLRES *)vol_list->next(vol)) {
152       if (vol->dev == dev) {
153          Dmsg0(000, "Two Volumes on same device.\n");
154          ASSERT(1);
155          dev = vol->dev;
156       }
157    }
158
159    Dmsg2(100, "List from %s: %d volumes\n", imsg, count);
160    if (do_lock) V(vol_list_lock);
161 }
162
163
164 /*
165  * List Volumes -- this should be moved to status.c
166  */
167 void list_volumes(void sendit(const char *msg, int len, void *sarg), void *arg)
168 {
169    VOLRES *vol;
170    POOL_MEM msg(PM_MESSAGE);
171    int len;
172
173    P(vol_list_lock);
174    for (vol=(VOLRES *)vol_list->first(); vol; vol=(VOLRES *)vol_list->next(vol)) {
175       if (vol->dev) {
176          len = Mmsg(msg, "%s on device %s\n", vol->vol_name, vol->dev->print_name());
177          sendit(msg.c_str(), len, arg);
178       } else {
179          len = Mmsg(msg, "%s no dev\n", vol->vol_name);
180          sendit(msg.c_str(), len, arg);
181       }
182    }
183    V(vol_list_lock);
184 }
185
186 /*
187  * Create a Volume item to put in the Volume list
188  *   Ensure that the device points to it.
189  */
190 static VOLRES *new_vol_item(DCR *dcr, const char *VolumeName)
191 {
192    VOLRES *vol;
193    vol = (VOLRES *)malloc(sizeof(VOLRES));
194    memset(vol, 0, sizeof(VOLRES));
195    vol->vol_name = bstrdup(VolumeName);
196    vol->dev = dcr->dev;
197    Dmsg4(100, "New Vol=%s at %p dev=%s JobId=%u\n", VolumeName, vol->vol_name,
198          vol->dev->print_name(), (int)dcr->jcr->JobId);
199    return vol;
200 }
201
202 static void free_vol_item(VOLRES *vol)
203 {
204    free(vol->vol_name);
205    free(vol);
206 }
207
208
209 /*
210  * Put a new Volume entry in the Volume list. This
211  *  effectively reserves the volume so that it will
212  *  not be mounted again.
213  *
214  * If the device has any current volume associated with it,
215  *  and it is a different Volume, and the device is not busy,
216  *  we release the old Volume item and insert the new one.
217  * 
218  * It is assumed that the device is free and locked so that
219  *  we can change the device structure.
220  *
221  * Some details of the Volume list handling:
222  *
223  *  1. The Volume list entry must be attached to the drive (rather than 
224  *       attached to a job as it currently is. I.e. the drive that "owns" 
225  *       the volume (reserved, in use, mounted)
226  *       must point to the volume (still to be maintained in a list).
227  *
228  *  2. The Volume is entered in the list when a drive is reserved.  
229  *
230  *  3. When a drive is in use, the device code must appropriately update the
231  *      volume name as it changes (currently the list is static -- an entry is
232  *      removed when the Volume is no longer reserved, in use or mounted).  
233  *      The new code must keep the same list entry as long as the drive
234  *       has any volume associated with it but the volume name in the list
235  *       must be updated when the drive has a different volume mounted.
236  *
237  *  4. A job that has reserved a volume, can un-reserve the volume, and if the 
238  *      volume is not mounted, and not reserved, and not in use, it will be
239  *      removed from the list.
240  *
241  *  5. If a job wants to reserve a drive with a different Volume from the one on
242  *      the drive, it can re-use the drive for the new Volume.
243  *
244  *  6. If a job wants a Volume that is in a different drive, it can either use the
245  *      other drive or take the volume, only if the other drive is not in use or
246  *      not reserved.
247  *
248  *  One nice aspect of this is that the reserve use count and the writer use count 
249  *  already exist and are correctly programmed and will need no changes -- use 
250  *  counts are always very tricky.
251  *
252  *  The old code had a concept of "reserving" a Volume, but it needs to be changed 
253  *  to reserving and using a drive.  A volume is must be attached to (owned by) a 
254  *  drive and can move from drive to drive or be unused given certain specific 
255  *  conditions of the drive.  The key is that the drive must "own" the Volume.  
256  *  The old code has the job (dcr) owning the volume (more or less).  The job is 
257  *  to change the insertion and removal of the volumes from the list to be based 
258  *  on the drive rather than the job.  The new logic described above needs to be 
259  *  reviewed a couple more times for completeness and correctness.  Then I can 
260  *  program it.
261
262  *
263  *  Return: VOLRES entry on success
264  *          NULL error
265  */
266 VOLRES *reserve_volume(DCR *dcr, const char *VolumeName)
267 {
268    VOLRES *vol, *nvol;
269    DEVICE *dev = dcr->dev;
270
271    ASSERT(dev != NULL);
272
273    Dmsg1(100, "reserve_volume %s\n", VolumeName);
274    /* 
275     * We lock the reservations system here to ensure
276     *  when adding a new volume that no newly scheduled
277     *  job can reserve it.
278     */
279    lock_reservations();
280    P(vol_list_lock);
281    debug_list_volumes("begin reserve_volume", debug_nolock);
282    /* 
283     * First, remove any old volume attached to this device as it
284     *  is no longer used.
285     */
286    if (dev->vol) {
287       vol = dev->vol;
288       /*
289        * Make sure we don't remove the current volume we are inserting
290        *  because it was probably inserted by another job.
291        */
292       if (strcmp(vol->vol_name, VolumeName) == 0) {
293          goto get_out;                  /* Volume already on this device */
294       } else {
295          Dmsg3(100, "reserve_vol free vol=%s at %p JobId=%u\n", vol->vol_name,
296                vol->vol_name, (int)dcr->jcr->JobId);
297          debug_list_volumes("reserve_vol free", debug_nolock);
298          vol_list->remove(vol);
299          free_vol_item(vol);
300       }
301    }
302
303    /* Create a new Volume entry */
304    nvol = new_vol_item(dcr, VolumeName);
305
306    /*
307     * Now try to insert the new Volume
308     */
309    vol = (VOLRES *)vol_list->binary_insert(nvol, my_compare);
310    if (vol != nvol) {
311       Dmsg2(100, "Found vol=%s dev-same=%d\n", vol->vol_name, dev==vol->dev);
312       /*
313        * At this point, a Volume with this name already is in the list,
314        *   so we simply release our new Volume entry. Note, this should
315        *   only happen if we are moving the volume from one drive to another.
316        */
317       Dmsg3(100, "reserve_vol free-tmp vol=%s at %p JobId=%u\n", vol->vol_name,
318             vol->vol_name, (int)dcr->jcr->JobId);
319       free_vol_item(nvol);
320
321       /* Check if we are trying to use the Volume on a different drive */
322       if (dev != vol->dev) {
323          /* Caller wants to switch Volume to another device */
324          if (!dev->is_busy()) {
325             /* OK to move it */
326             Dmsg3(100, "Swap vol=%s from dev=%s to %s\n", VolumeName,
327                dev->print_name(), dev->print_name());
328             vol->dev = dev;
329             dev->VolHdr.VolumeName[0] = 0;
330          } else {
331             vol = NULL;                /* device busy */
332             Dmsg3(100, "Logic ERROR!!!! could not swap vol=%s from dev=%s to %s\n", VolumeName,
333                dev->print_name(), dcr->dev->print_name());
334             ASSERT(1);     /* blow up!!! */
335          }
336       }
337    }
338    dev->vol = vol;
339
340 get_out:
341    debug_list_volumes("end new volume", debug_nolock);
342    V(vol_list_lock);
343    unlock_reservations();
344    return vol;
345 }
346
347 /*
348  * Search for a Volume name in the Volume list.
349  *
350  *  Returns: VOLRES entry on success
351  *           NULL if the Volume is not in the list
352  */
353 VOLRES *find_volume(const char *VolumeName)
354 {
355    VOLRES vol, *fvol;
356    /* Do not lock reservations here */
357    P(vol_list_lock);
358    vol.vol_name = bstrdup(VolumeName);
359    fvol = (VOLRES *)vol_list->binary_search(&vol, my_compare);
360    free(vol.vol_name);
361    Dmsg2(100, "find_vol=%s found=%d\n", VolumeName, fvol!=NULL);
362    debug_list_volumes("find_volume", debug_nolock);
363    V(vol_list_lock);
364    return fvol;
365 }
366
367 /* 
368  * Remove any reservation from a drive and tell the system
369  *  that the volume is unused at least by us.
370  */
371 void unreserve_device(DCR *dcr)
372 {
373    DEVICE *dev = dcr->dev;
374    dev->dlock();
375    if (dcr->reserved_device) {
376       dcr->reserved_device = false;
377       dev->reserved_device--;
378       Dmsg2(100, "Dec reserve=%d dev=%s\n", dev->reserved_device, dev->print_name());
379       dcr->reserved_device = false;
380       /* If we set read mode in reserving, remove it */
381       if (dev->can_read()) {
382          dev->clear_read();
383       }
384       if (dev->num_writers < 0) {
385          Jmsg1(dcr->jcr, M_ERROR, 0, _("Hey! num_writers=%d!!!!\n"), dev->num_writers);
386          dev->num_writers = 0;
387       }
388    }
389
390    volume_unused(dcr);
391    dev->dunlock();
392 }
393
394 /*  
395  * Free a Volume from the Volume list if it is no longer used
396  *
397  *  Returns: true if the Volume found and removed from the list
398  *           false if the Volume is not in the list or is in use
399  */
400 bool volume_unused(DCR *dcr)
401 {
402    DEVICE *dev = dcr->dev;
403
404    if (dev->vol == NULL) {
405       Dmsg1(100, " unreserve_volume: no vol on %s\n", dev->print_name());
406       debug_list_volumes("null return unreserve_volume", debug_lock);
407       return false;
408    }
409
410    if (dev->is_busy()) {
411       Dmsg1(100, "unreserve_volume: dev is busy %s\n", dev->print_name());
412       debug_list_volumes("dev busy return unreserve_volume", debug_lock);
413       return false;
414    }
415
416    return free_volume(dev);
417 }
418
419 /*
420  * Unconditionally release the volume
421  */
422 bool free_volume(DEVICE *dev)
423 {
424    VOLRES *vol;
425
426    if (dev->vol == NULL) {
427       Dmsg1(100, "No vol on dev %s\n", dev->print_name());
428       return false;
429    }
430    P(vol_list_lock);
431    vol = dev->vol;
432    dev->vol = NULL;
433    Dmsg1(100, "free_volume %s\n", vol->vol_name);
434    vol_list->remove(vol);
435    Dmsg3(100, "free_volume %s at %p dev=%s\n", vol->vol_name, vol->vol_name,
436          dev->print_name());
437    free_vol_item(vol);
438    debug_list_volumes("free_volume", debug_nolock);
439    V(vol_list_lock);
440    return vol != NULL;
441 }
442
443       
444 /* Create the Volume list */
445 void create_volume_list()
446 {
447    VOLRES *dummy = NULL;
448    if (vol_list == NULL) {
449       vol_list = New(dlist(dummy, &dummy->link));
450    }
451 }
452
453 /* Release all Volumes from the list */
454 void free_volume_list()
455 {
456    VOLRES *vol;
457    if (!vol_list) {
458       return;
459    }
460    P(vol_list_lock);
461    for (vol=(VOLRES *)vol_list->first(); vol; vol=(VOLRES *)vol_list->next(vol)) {
462       Dmsg2(100, "Unreleased Volume=%s dev=%p\n", vol->vol_name, vol->dev);
463       free(vol->vol_name);
464       vol->vol_name = NULL;
465    }
466    delete vol_list;
467    vol_list = NULL;
468    V(vol_list_lock);
469 }
470
471 bool is_volume_in_use(DCR *dcr)
472 {
473    VOLRES *vol = find_volume(dcr->VolumeName);
474    if (!vol) {
475       Dmsg1(100, "Vol=%s not in use.\n", dcr->VolumeName);
476       return false;                   /* vol not in list */
477    }
478    ASSERT(vol->dev != NULL);
479
480    if (dcr->dev == vol->dev) {        /* same device OK */
481       Dmsg1(100, "Vol=%s on same dev.\n", dcr->VolumeName);
482       return false;
483    }
484    if (!vol->dev->is_busy()) {
485       Dmsg2(100, "Vol=%s dev=%s not busy.\n", dcr->VolumeName, vol->dev->print_name());
486       return false;
487    }
488    Dmsg2(100, "Vol=%s used by %s.\n", dcr->VolumeName, vol->dev->print_name());
489    return true;
490 }
491
492
493 /*
494  * We get the following type of information:
495  *
496  * use storage=xxx media_type=yyy pool_name=xxx pool_type=yyy append=1 copy=0 strip=0
497  *  use device=zzz
498  *  use device=aaa
499  *  use device=bbb
500  * use storage=xxx media_type=yyy pool_name=xxx pool_type=yyy append=0 copy=0 strip=0
501  *  use device=bbb
502  *
503  */
504 static bool use_storage_cmd(JCR *jcr)
505 {
506    POOL_MEM store_name, dev_name, media_type, pool_name, pool_type;
507    BSOCK *dir = jcr->dir_bsock;
508    int append;
509    bool ok;       
510    int Copy, Stripe;
511    DIRSTORE *store;
512    RCTX rctx;
513    char *msg;
514    alist *msgs;
515    alist *dirstore;
516
517    memset(&rctx, 0, sizeof(RCTX));
518    rctx.jcr = jcr;
519    /*
520     * If there are multiple devices, the director sends us
521     *   use_device for each device that it wants to use.
522     */
523    dirstore = New(alist(10, not_owned_by_alist));
524 // Dmsg2(000, "dirstore=%p JobId=%u\n", dirstore, jcr->JobId);
525    msgs = jcr->reserve_msgs = New(alist(10, not_owned_by_alist));  
526    do {
527       Dmsg1(100, "<dird: %s", dir->msg);
528       ok = sscanf(dir->msg, use_storage, store_name.c_str(), 
529                   media_type.c_str(), pool_name.c_str(), 
530                   pool_type.c_str(), &append, &Copy, &Stripe) == 7;
531       if (!ok) {
532          break;
533       }
534       if (append) {
535          jcr->write_store = dirstore;
536       } else {
537          jcr->read_store = dirstore;
538       }
539       rctx.append = append;
540       unbash_spaces(store_name);
541       unbash_spaces(media_type);
542       unbash_spaces(pool_name);
543       unbash_spaces(pool_type);
544       store = new DIRSTORE;
545       dirstore->append(store);
546       memset(store, 0, sizeof(DIRSTORE));
547       store->device = New(alist(10));
548       bstrncpy(store->name, store_name, sizeof(store->name));
549       bstrncpy(store->media_type, media_type, sizeof(store->media_type));
550       bstrncpy(store->pool_name, pool_name, sizeof(store->pool_name));
551       bstrncpy(store->pool_type, pool_type, sizeof(store->pool_type));
552       store->append = append;
553
554       /* Now get all devices */
555       while (dir->recv() >= 0) {
556          Dmsg1(100, "<dird device: %s", dir->msg);
557          ok = sscanf(dir->msg, use_device, dev_name.c_str()) == 1;
558          if (!ok) {
559             break;
560          }
561          unbash_spaces(dev_name);
562          store->device->append(bstrdup(dev_name.c_str()));
563       }
564    }  while (ok && dir->recv() >= 0);
565
566 #ifdef DEVELOPER
567    /* This loop is debug code and can be removed */
568    /* ***FIXME**** remove after 1.38 release */
569    char *device_name;
570    foreach_alist(store, dirstore) {
571       Dmsg5(110, "Storage=%s media_type=%s pool=%s pool_type=%s append=%d\n", 
572          store->name, store->media_type, store->pool_name, 
573          store->pool_type, store->append);
574       foreach_alist(device_name, store->device) {
575          Dmsg1(110, "   Device=%s\n", device_name);
576       }
577    }
578 #endif
579
580    init_jcr_device_wait_timers(jcr);
581    /*                    
582     * At this point, we have a list of all the Director's Storage
583     *  resources indicated for this Job, which include Pool, PoolType,
584     *  storage name, and Media type.     
585     * Then for each of the Storage resources, we have a list of
586     *  device names that were given.
587     *
588     * Wiffle through them and find one that can do the backup.
589     */
590    if (ok) {
591       bool first = true;           /* print wait message once */
592       bool fail = false;
593       rctx.notify_dir = true;
594       lock_reservations();
595       for ( ; !fail && !job_canceled(jcr); ) {
596          while ((msg = (char *)msgs->pop())) {
597             free(msg);
598          }
599          rctx.suitable_device = false;
600          rctx.have_volume = false;
601          rctx.VolumeName[0] = 0;
602          rctx.any_drive = false;
603          if (!jcr->PreferMountedVols) {
604             /* Look for unused drives in autochangers */
605             rctx.num_writers = 20000000;   /* start with impossible number */
606             rctx.low_use_drive = NULL;
607             rctx.PreferMountedVols = false;                
608             rctx.exact_match = false;
609             rctx.autochanger_only = true;
610             Dmsg5(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d any=%d\n",
611                rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
612                rctx.autochanger_only, rctx.any_drive);
613             if ((ok = find_suitable_device_for_job(jcr, rctx))) {
614                break;
615             }
616             /* Look through all drives possibly for low_use drive */
617             if (rctx.low_use_drive) {
618                rctx.try_low_use_drive = true;
619                if ((ok = find_suitable_device_for_job(jcr, rctx))) {
620                   break;
621                }
622                rctx.try_low_use_drive = false;
623             }
624             rctx.autochanger_only = false;
625             Dmsg5(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d any=%d\n",
626                rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
627                rctx.autochanger_only, rctx.any_drive);
628             if ((ok = find_suitable_device_for_job(jcr, rctx))) {
629                break;
630             }
631          }
632          /* Look for an exact match all drives */
633          rctx.PreferMountedVols = true;
634          rctx.exact_match = true;
635          rctx.autochanger_only = false;
636          Dmsg5(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d any=%d\n",
637             rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
638             rctx.autochanger_only, rctx.any_drive);
639          if ((ok = find_suitable_device_for_job(jcr, rctx))) {
640             break;
641          }
642          /* Look for any mounted drive */
643          rctx.exact_match = false;
644          Dmsg5(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d any=%d\n",
645             rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
646             rctx.autochanger_only, rctx.any_drive);
647          if ((ok = find_suitable_device_for_job(jcr, rctx))) {
648             break;
649          }
650          /* Try any drive */
651          rctx.any_drive = true;
652          Dmsg5(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d any=%d\n",
653             rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
654             rctx.autochanger_only, rctx.any_drive);
655          if ((ok = find_suitable_device_for_job(jcr, rctx))) {
656             break;
657          }
658          /* Keep reservations locked *except* during wait_for_device() */
659          unlock_reservations();
660          if (!rctx.suitable_device || !wait_for_device(jcr, first)) {
661             Dmsg0(100, "Fail. !suitable_device || !wait_for_device\n");
662             fail = true;
663          }   
664          lock_reservations();
665          first = false;
666          bnet_sig(dir, BNET_HEARTBEAT);  /* Inform Dir that we are alive */
667       }
668       unlock_reservations();
669       if (!ok) {
670          /*
671           * If we get here, there are no suitable devices available, which
672           *  means nothing configured.  If a device is suitable but busy
673           *  with another Volume, we will not come here.
674           */
675          unbash_spaces(dir->msg);
676          pm_strcpy(jcr->errmsg, dir->msg);
677          Jmsg(jcr, M_INFO, 0, _("Failed command: %s\n"), jcr->errmsg);
678          Jmsg(jcr, M_FATAL, 0, _("\n"
679             "     Device \"%s\" with MediaType \"%s\" requested by DIR not found in SD Device resources.\n"),
680               dev_name.c_str(), media_type.c_str());
681          bnet_fsend(dir, NO_device, dev_name.c_str());
682
683          Dmsg1(100, ">dird: %s", dir->msg);
684       }
685    } else {
686       unbash_spaces(dir->msg);
687       pm_strcpy(jcr->errmsg, dir->msg);
688       Jmsg(jcr, M_FATAL, 0, _("Failed command: %s\n"), jcr->errmsg);
689       bnet_fsend(dir, BAD_use, jcr->errmsg);
690       Dmsg1(100, ">dird: %s", dir->msg);
691    }
692
693    release_msgs(jcr);
694    return ok;
695 }
696
697 void release_msgs(JCR *jcr)
698 {
699    alist *msgs = jcr->reserve_msgs;
700    char *msg;
701
702    if (!msgs) {
703       return;
704    }
705    lock_reservations();
706    while ((msg = (char *)msgs->pop())) {
707       free(msg);
708    }
709    delete msgs;
710    jcr->reserve_msgs = NULL;
711    unlock_reservations();
712 }
713
714 /*
715  * Search for a device suitable for this job.
716  */
717 bool find_suitable_device_for_job(JCR *jcr, RCTX &rctx)
718 {
719    bool ok;
720    DIRSTORE *store;
721    char *device_name;
722    alist *dirstore;
723
724    if (rctx.append) {
725       dirstore = jcr->write_store;
726    } else {
727       dirstore = jcr->read_store;
728    }
729    /* 
730     * For each storage device that the user specified, we
731     *  search and see if there is a resource for that device.
732     */
733    Dmsg4(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d\n",
734       rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
735       rctx.autochanger_only);
736    ok = false;
737    foreach_alist(store, dirstore) {
738       rctx.store = store;
739       foreach_alist(device_name, store->device) {
740          int stat;
741          rctx.device_name = device_name;
742          stat = search_res_for_device(rctx); 
743          if (stat == 1) {             /* found available device */
744             Dmsg1(100, "Suitable device found=%s\n", device_name);
745             ok = true;
746             break;
747          } else if (stat == 0) {      /* device busy */
748             Dmsg1(110, "Suitable device=%s, busy: not use\n", device_name);
749          } else {
750             /* otherwise error */
751             Dmsg0(110, "No suitable device found.\n");
752          }
753       }
754       if (ok) {
755          break;
756       }
757    }
758    return ok;
759 }
760
761 /*
762  * Search for a particular storage device with particular storage
763  *  characteristics (MediaType).
764  */
765 int search_res_for_device(RCTX &rctx) 
766 {
767    AUTOCHANGER *changer;
768    BSOCK *dir = rctx.jcr->dir_bsock;
769    bool ok;
770    int stat;
771
772    Dmsg1(110, "Search res for %s\n", rctx.device_name);
773    /* Look through Autochangers first */
774    foreach_res(changer, R_AUTOCHANGER) {
775       Dmsg1(150, "Try match changer res=%s\n", changer->hdr.name);
776       /* Find resource, and make sure we were able to open it */
777       if (fnmatch(rctx.device_name, changer->hdr.name, 0) == 0) {
778          /* Try each device in this AutoChanger */
779          foreach_alist(rctx.device, changer->device) {
780             Dmsg1(110, "Try changer device %s\n", rctx.device->hdr.name);
781             stat = reserve_device(rctx);
782             if (stat != 1) {             /* try another device */
783                continue;
784             }
785             POOL_MEM dev_name;
786             if (rctx.store->append == SD_APPEND) {
787                Dmsg2(100, "Device %s reserved=%d for append.\n", rctx.device->hdr.name,
788                   rctx.jcr->dcr->dev->reserved_device);
789             } else {
790                Dmsg2(100, "Device %s reserved=%d for read.\n", rctx.device->hdr.name,
791                   rctx.jcr->read_dcr->dev->reserved_device);
792             }
793             if (rctx.notify_dir) {
794                pm_strcpy(dev_name, rctx.device->hdr.name);
795                bash_spaces(dev_name);
796                ok = bnet_fsend(dir, OK_device, dev_name.c_str());  /* Return real device name */
797                Dmsg1(100, ">dird changer: %s", dir->msg);
798             } else {
799                ok = true;
800             }
801             return ok ? 1 : -1;
802          }
803       }
804    }
805
806    /* Now if requested look through regular devices */
807    if (!rctx.autochanger_only) {
808       foreach_res(rctx.device, R_DEVICE) {
809          Dmsg1(150, "Try match res=%s\n", rctx.device->hdr.name);
810          /* Find resource, and make sure we were able to open it */
811          if (fnmatch(rctx.device_name, rctx.device->hdr.name, 0) == 0) {
812             stat = reserve_device(rctx);
813             if (stat != 1) {
814                return stat;
815             }
816             if (rctx.notify_dir) {
817                bash_spaces(rctx.device_name);
818                ok = bnet_fsend(dir, OK_device, rctx.device_name);
819                Dmsg1(100, ">dird dev: %s", dir->msg);
820             } else {
821                ok = true;
822             }
823             return ok ? 1 : -1;
824          }
825       }
826    }
827    return -1;                    /* nothing found */
828 }
829
830 /*
831  *  Try to reserve a specific device.
832  *
833  *  Returns: 1 -- OK, have DCR
834  *           0 -- must wait
835  *          -1 -- fatal error
836  */
837 static int reserve_device(RCTX &rctx)
838 {
839    bool ok;
840    DCR *dcr;
841    const int name_len = MAX_NAME_LENGTH;
842
843    /* Make sure MediaType is OK */
844    Dmsg2(110, "MediaType device=%s request=%s\n",
845          rctx.device->media_type, rctx.store->media_type);
846    if (strcmp(rctx.device->media_type, rctx.store->media_type) != 0) {
847       return -1;
848    }
849
850    /* Make sure device exists -- i.e. we can stat() it */
851    if (!rctx.device->dev) {
852       rctx.device->dev = init_dev(rctx.jcr, rctx.device);
853    }
854    if (!rctx.device->dev) {
855       if (rctx.device->changer_res) {
856         Jmsg(rctx.jcr, M_WARNING, 0, _("\n"
857            "     Device \"%s\" in changer \"%s\" requested by DIR could not be opened or does not exist.\n"),
858              rctx.device->hdr.name, rctx.device_name);
859       } else {
860          Jmsg(rctx.jcr, M_WARNING, 0, _("\n"
861             "     Device \"%s\" requested by DIR could not be opened or does not exist.\n"),
862               rctx.device_name);
863       }
864       return -1;  /* no use waiting */
865    }  
866
867    rctx.suitable_device = true;
868    Dmsg2(110, "Try reserve %s JobId=%u\n", rctx.device->hdr.name,
869          rctx.jcr->JobId);
870    dcr = new_dcr(rctx.jcr, rctx.device->dev);
871    if (!dcr) {
872       BSOCK *dir = rctx.jcr->dir_bsock;
873       bnet_fsend(dir, _("3926 Could not get dcr for device: %s\n"), rctx.device_name);
874       Dmsg1(100, ">dird: %s", dir->msg);
875       return -1;
876    }
877    bstrncpy(dcr->pool_name, rctx.store->pool_name, name_len);
878    bstrncpy(dcr->pool_type, rctx.store->pool_type, name_len);
879    bstrncpy(dcr->media_type, rctx.store->media_type, name_len);
880    bstrncpy(dcr->dev_name, rctx.device_name, name_len);
881    if (rctx.store->append == SD_APPEND) {
882       Dmsg2(100, "have_vol=%d vol=%s\n", rctx.have_volume, rctx.VolumeName);
883       if (!rctx.have_volume) {
884          dcr->any_volume = true;
885          if (dir_find_next_appendable_volume(dcr)) {
886             bstrncpy(rctx.VolumeName, dcr->VolumeName, sizeof(rctx.VolumeName));
887             Dmsg2(100, "JobId=%u looking for Volume=%s\n", (int)rctx.jcr->JobId, rctx.VolumeName);
888             rctx.have_volume = true;
889          } else {
890             Dmsg0(100, "No next volume found\n");
891             rctx.have_volume = false;
892             rctx.VolumeName[0] = 0;
893         }
894       }
895       ok = reserve_device_for_append(dcr, rctx);
896       if (ok) {
897          rctx.jcr->dcr = dcr;
898          Dmsg5(100, "Reserved=%d dev_name=%s mediatype=%s pool=%s ok=%d\n",
899                dcr->dev->reserved_device,
900                dcr->dev_name, dcr->media_type, dcr->pool_name, ok);
901       }
902    } else {
903       ok = reserve_device_for_read(dcr);
904       if (ok) {
905          rctx.jcr->read_dcr = dcr;
906          Dmsg5(100, "Read reserved=%d dev_name=%s mediatype=%s pool=%s ok=%d\n",
907                dcr->dev->reserved_device,
908                dcr->dev_name, dcr->media_type, dcr->pool_name, ok);
909       }
910    }
911    if (!ok) {
912       rctx.have_volume = false;
913       free_dcr(dcr);
914       Dmsg0(110, "Not OK.\n");
915       return 0;
916    }
917    return 1;
918 }
919
920 /*
921  * We "reserve" the drive by setting the ST_READ bit. No one else
922  *  should touch the drive until that is cleared.
923  *  This allows the DIR to "reserve" the device before actually
924  *  starting the job. 
925  */
926 static bool reserve_device_for_read(DCR *dcr)
927 {
928    DEVICE *dev = dcr->dev;
929    JCR *jcr = dcr->jcr;
930    bool ok = false;
931
932    ASSERT(dcr);
933
934    /* Get locks in correct order */
935    unlock_reservations();
936    dev->dlock();  
937    lock_reservations();
938
939    if (is_device_unmounted(dev)) {             
940       Dmsg1(200, "Device %s is BLOCKED due to user unmount.\n", dev->print_name());
941       Mmsg(jcr->errmsg, _("3601 JobId=%u device %s is BLOCKED due to user unmount.\n"),
942            jcr->JobId, dev->print_name());
943       queue_reserve_message(jcr);
944       goto bail_out;
945    }
946
947    if (dev->is_busy()) {
948       Dmsg4(200, "Device %s is busy ST_READ=%d num_writers=%d reserved=%d.\n", dev->print_name(),
949          dev->state & ST_READ?1:0, dev->num_writers, dev->reserved_device);
950       Mmsg(jcr->errmsg, _("3602 JobId=%u device %s is busy (already reading/writing).\n"),
951             jcr->JobId, dev->print_name());
952       queue_reserve_message(jcr);
953       goto bail_out;
954    }
955
956    dev->clear_append();
957    dev->set_read();
958    ok = true;
959    dev->reserved_device++;
960    Dmsg3(100, "Inc reserve=%d dev=%s %p\n", dev->reserved_device, 
961       dev->print_name(), dev);
962    dcr->reserved_device = true;
963
964 bail_out:
965    dev->dunlock();
966    return ok;
967 }
968
969
970 /*
971  * We reserve the device for appending by incrementing the 
972  *  reserved_device. We do virtually all the same work that
973  *  is done in acquire_device_for_append(), but we do
974  *  not attempt to mount the device. This routine allows
975  *  the DIR to reserve multiple devices before *really* 
976  *  starting the job. It also permits the SD to refuse 
977  *  certain devices (not up, ...).
978  *
979  * Note, in reserving a device, if the device is for the
980  *  same pool and the same pool type, then it is acceptable.
981  *  The Media Type has already been checked. If we are
982  *  the first tor reserve the device, we put the pool
983  *  name and pool type in the device record.
984  */
985 static bool reserve_device_for_append(DCR *dcr, RCTX &rctx)
986 {
987    JCR *jcr = dcr->jcr;
988    DEVICE *dev = dcr->dev;
989    bool ok = false;
990
991    ASSERT(dcr);
992
993    /* Get locks in correct order */
994    unlock_reservations();
995    dev->dlock();
996    lock_reservations();
997
998    /* If device is being read, we cannot write it */
999    if (dev->can_read()) {
1000       Mmsg(jcr->errmsg, _("3603 JobId=%u device %s is busy reading.\n"), 
1001          jcr->JobId, dev->print_name());
1002       Dmsg1(110, "%s", jcr->errmsg);
1003       queue_reserve_message(jcr);
1004       goto bail_out;
1005    }
1006
1007    /* If device is unmounted, we are out of luck */
1008    if (is_device_unmounted(dev)) {
1009       Mmsg(jcr->errmsg, _("3604 JobId=%u device %s is BLOCKED due to user unmount.\n"), 
1010          jcr->JobId, dev->print_name());
1011       Dmsg1(110, "%s", jcr->errmsg);
1012       queue_reserve_message(jcr);
1013       goto bail_out;
1014    }
1015
1016    Dmsg1(110, "reserve_append device is %s\n", dev->is_tape()?"tape":"disk");
1017
1018    /* Now do detailed tests ... */
1019    if (can_reserve_drive(dcr, rctx) != 1) {
1020       Dmsg0(110, "can_reserve_drive!=1\n");
1021       goto bail_out;
1022    }
1023
1024    dev->reserved_device++;
1025    Dmsg3(100, "Inc reserve=%d dev=%s %p\n", dev->reserved_device, 
1026       dev->print_name(), dev);
1027    dcr->reserved_device = true;
1028    ok = true;
1029
1030 bail_out:
1031    dev->dunlock();
1032    return ok;
1033 }
1034
1035 /*
1036  * Returns: 1 if drive can be reserved
1037  *          0 if we should wait
1038  *         -1 on error or impossibility
1039  */
1040 static int can_reserve_drive(DCR *dcr, RCTX &rctx) 
1041 {
1042    DEVICE *dev = dcr->dev;
1043    JCR *jcr = dcr->jcr;
1044
1045    Dmsg5(110, "PrefMnt=%d exact=%d suitable=%d chgronly=%d any=%d\n",
1046          rctx.PreferMountedVols, rctx.exact_match, rctx.suitable_device,
1047          rctx.autochanger_only, rctx.any_drive);
1048
1049    /* setting any_drive overrides PreferMountedVols flag */
1050    if (!rctx.any_drive) {
1051       /*
1052        * When PreferMountedVols is set, we keep track of the 
1053        *  drive in use that has the least number of writers, then if
1054        *  no unmounted drive is found, we try that drive. This   
1055        *  helps spread the load to the least used drives.  
1056        */
1057       if (rctx.try_low_use_drive && dev == rctx.low_use_drive) {
1058          Dmsg3(110, "OK dev=%s == low_drive=%s. JobId=%u\n",
1059             dev->print_name(), rctx.low_use_drive->print_name(), jcr->JobId);
1060          return 1;
1061       }
1062       /* If he wants a free drive, but this one is busy, no go */
1063       if (!rctx.PreferMountedVols && dev->is_busy()) {
1064          /* Save least used drive */
1065          if ((dev->num_writers + dev->reserved_device) < rctx.num_writers) {
1066             rctx.num_writers = dev->num_writers + dev->reserved_device;
1067             rctx.low_use_drive = dev;
1068             Dmsg2(110, "set low use drive=%s num_writers=%d\n", dev->print_name(),
1069                rctx.num_writers);
1070          } else {
1071             Dmsg1(110, "not low use num_writers=%d\n", dev->num_writers+ 
1072                dev->reserved_device);
1073          }
1074          Dmsg1(110, "failed: !prefMnt && busy. JobId=%u\n", jcr->JobId);
1075          Mmsg(jcr->errmsg, _("3605 JobId=%u wants free drive but device %s is busy.\n"), 
1076             jcr->JobId, dev->print_name());
1077          queue_reserve_message(jcr);
1078          return 0;
1079       }
1080
1081       /* Check for prefer mounted volumes */
1082       if (rctx.PreferMountedVols && !dev->VolHdr.VolumeName[0] && dev->is_tape()) {
1083          Mmsg(jcr->errmsg, _("3606 JobId=%u prefers mounted drives, but drive %s has no Volume.\n"), 
1084             jcr->JobId, dev->print_name());
1085          queue_reserve_message(jcr);
1086          Dmsg1(110, "failed: want mounted -- no vol JobId=%u\n", jcr->JobId);
1087          return 0;                 /* No volume mounted */
1088       }
1089
1090       /* Check for exact Volume name match */
1091       if (rctx.exact_match && rctx.have_volume &&
1092           strcmp(dev->VolHdr.VolumeName, rctx.VolumeName) != 0) {
1093          Mmsg(jcr->errmsg, _("3607 JobId=%u wants Vol=\"%s\" drive has Vol=\"%s\" on drive %s.\n"), 
1094             jcr->JobId, rctx.VolumeName, dev->VolHdr.VolumeName, 
1095             dev->print_name());
1096          queue_reserve_message(jcr);
1097          Dmsg2(110, "failed: Not exact match have=%s want=%s\n",
1098                dev->VolHdr.VolumeName, rctx.VolumeName);
1099          return 0;
1100       }
1101    }
1102
1103    /* Check for unused autochanger drive */
1104    if (rctx.autochanger_only && dev->num_writers == 0 &&
1105        dev->VolHdr.VolumeName[0] == 0) {
1106       /* Device is available but not yet reserved, reserve it for us */
1107       Dmsg2(100, "OK Res Unused autochanger %s JobId=%u.\n",
1108          dev->print_name(), jcr->JobId);
1109       bstrncpy(dev->pool_name, dcr->pool_name, sizeof(dev->pool_name));
1110       bstrncpy(dev->pool_type, dcr->pool_type, sizeof(dev->pool_type));
1111       return 1;                       /* reserve drive */
1112    }
1113
1114    /*
1115     * Handle the case that there are no writers
1116     */
1117    if (dev->num_writers == 0) {
1118       /* Now check if there are any reservations on the drive */
1119       if (dev->reserved_device) {           
1120          /* Now check if we want the same Pool and pool type */
1121          if (strcmp(dev->pool_name, dcr->pool_name) == 0 &&
1122              strcmp(dev->pool_type, dcr->pool_type) == 0) {
1123             /* OK, compatible device */
1124             Dmsg2(100, "OK dev: %s num_writers=0, reserved, pool matches JobId=%u\n",
1125                dev->print_name(), jcr->JobId);
1126             return 1;
1127          } else {
1128             /* Drive Pool not suitable for us */
1129             Mmsg(jcr->errmsg, _(
1130 "3608 JobId=%u wants Pool=\"%s\" but have Pool=\"%s\" nreserve=%d on drive %s.\n"), 
1131                   jcr->JobId, dcr->pool_name, dev->pool_name,
1132                   dev->reserved_device, dev->print_name());
1133             queue_reserve_message(jcr);
1134             Dmsg2(110, "failed: busy num_writers=0, reserved, pool=%s wanted=%s\n",
1135                dev->pool_name, dcr->pool_name);
1136             return 0;                 /* wait */
1137          }
1138       } else if (dev->can_append()) {
1139          /* Device in append mode, check if changing pool */
1140          if (strcmp(dev->pool_name, dcr->pool_name) == 0 &&
1141              strcmp(dev->pool_type, dcr->pool_type) == 0) {
1142             Dmsg2(100, "OK dev: %s num_writers=0, can_append, pool matches. JobId=%u\n",
1143                dev->print_name(), jcr->JobId);
1144             /* OK, compatible device */
1145             return 1;
1146          } else {
1147             /* Changing pool, unload old tape if any in drive */
1148             Dmsg0(100, "OK dev: num_writers=0, not reserved, pool change, unload changer\n");
1149             unload_autochanger(dcr, 0);
1150          }
1151       }
1152       /* Device is available but not yet reserved, reserve it for us */
1153       Dmsg2(100, "OK Dev avail reserved %s JobId=%u\n", dev->print_name(),
1154          jcr->JobId);
1155       bstrncpy(dev->pool_name, dcr->pool_name, sizeof(dev->pool_name));
1156       bstrncpy(dev->pool_type, dcr->pool_type, sizeof(dev->pool_type));
1157       return 1;                       /* reserve drive */
1158    }
1159
1160    /*
1161     * Check if the device is in append mode with writers (i.e.
1162     *  available if pool is the same).
1163     */
1164    if (dev->can_append() || dev->num_writers > 0) {
1165       /* Yes, now check if we want the same Pool and pool type */
1166       if (strcmp(dev->pool_name, dcr->pool_name) == 0 &&
1167           strcmp(dev->pool_type, dcr->pool_type) == 0) {
1168          Dmsg2(100, "OK dev: %s num_writers>=0, can_append, pool matches. JobId=%u\n",
1169             dev->print_name(), jcr->JobId);
1170          /* OK, compatible device */
1171          return 1;
1172       } else {
1173          /* Drive Pool not suitable for us */
1174          Mmsg(jcr->errmsg, _("3609 JobId=%u wants Pool=\"%s\" but has Pool=\"%s\" on drive %s.\n"), 
1175                jcr->JobId, dcr->pool_name, dev->pool_name, dev->print_name());
1176          queue_reserve_message(jcr);
1177          Dmsg2(110, "failed: busy num_writers>0, can_append, pool=%s wanted=%s\n",
1178             dev->pool_name, dcr->pool_name);
1179          return 0;                    /* wait */
1180       }
1181    } else {
1182       Pmsg0(000, _("Logic error!!!! Should not get here.\n"));
1183       Mmsg(jcr->errmsg, _("3910 JobId=%u Logic error!!!! drive %s Should not get here.\n"),
1184             jcr->JobId, dev->print_name());
1185       queue_reserve_message(jcr);
1186       Jmsg0(jcr, M_FATAL, 0, _("Logic error!!!! Should not get here.\n"));
1187       return -1;                      /* error, should not get here */
1188    }
1189    Mmsg(jcr->errmsg, _("3911 JobId=%u failed reserve drive %s.\n"), 
1190          jcr->JobId, dev->print_name());
1191    queue_reserve_message(jcr);
1192    Dmsg2(110, "failed: No reserve %s JobId=%u\n", dev->print_name(), jcr->JobId);
1193    return 0;
1194 }
1195
1196 /*
1197  * search_lock is already set on entering this routine 
1198  */
1199 static void queue_reserve_message(JCR *jcr)
1200 {
1201    int i;   
1202    alist *msgs = jcr->reserve_msgs;
1203    char *msg;
1204
1205    if (!msgs) {
1206       return;
1207    }
1208    /*
1209     * Look for duplicate message.  If found, do
1210     * not insert
1211     */
1212    for (i=msgs->size()-1; i >= 0; i--) {
1213       msg = (char *)msgs->get(i);
1214       if (!msg) {
1215          return;
1216       }
1217       /* Comparison based on 4 digit message number */
1218       if (strncmp(msg, jcr->errmsg, 4) == 0) {
1219          return;
1220       }
1221    }      
1222    /* Message unique, so insert it */
1223    jcr->reserve_msgs->push(bstrdup(jcr->errmsg));
1224 }
1225
1226 /*
1227  * Send any reservation messages queued for this jcr
1228  */
1229 void send_drive_reserve_messages(JCR *jcr, void sendit(const char *msg, int len, void *sarg), void *arg)
1230 {
1231    int i;
1232    alist *msgs;
1233    char *msg;
1234
1235    lock_reservations();
1236    msgs = jcr->reserve_msgs;
1237    if (!msgs || msgs->size() == 0) {
1238       unlock_reservations();
1239       return;
1240    }
1241    for (i=msgs->size()-1; i >= 0; i--) {
1242       msg = (char *)msgs->get(i);
1243       if (msg) {
1244          sendit("   ", 3, arg);
1245          sendit(msg, strlen(msg), arg);
1246       } else {
1247          break;
1248       }
1249    }
1250    unlock_reservations();
1251 }