]> git.sur5r.net Git - bacula/bacula/commitdiff
Lock read acquire in SD to prevent to read jobs getting the same thing
authorKern Sibbald <kern@sibbald.com>
Sat, 4 Feb 2012 15:28:16 +0000 (16:28 +0100)
committerKern Sibbald <kern@sibbald.com>
Sat, 4 Feb 2012 15:28:43 +0000 (16:28 +0100)
bacula/src/stored/acquire.c
bacula/src/stored/dev.c
bacula/src/stored/dev.h

index fcd0f33b3a08c68de013c33854a997c2ea77b79b..96bdc062da6171280a67742eb12df8e3ed98442a 100644 (file)
@@ -1,7 +1,7 @@
 /*
    Bacula(R) - The Network Backup Solution
 
-   Copyright (C) 2002-2011 Free Software Foundation Europe e.V.
+   Copyright (C) 2002-2012 Free Software Foundation Europe e.V.
 
    The main author of Bacula is Kern Sibbald, with contributions from
    many others, a complete list can be found in the file AUTHORS.
@@ -40,7 +40,6 @@ static void attach_dcr_to_dev(DCR *dcr);
 static void detach_dcr_from_dev(DCR *dcr);
 static void set_dcr_from_vol(DCR *dcr, VOL_LIST *vol);
 
-
 /*********************************************************************
  * Acquire device for reading. 
  *  The drive should have previously been reserved by calling 
@@ -62,6 +61,7 @@ bool acquire_device_for_read(DCR *dcr)
    int vol_label_status;
    int retry = 0;
    
+   P(dev->read_acquire_mutex);
    Dmsg2(950, "dcr=%p dev=%p\n", dcr, dcr->dev);
    Dmsg2(950, "MediaType dcr=%s dev=%s\n", dcr->media_type, dev->device->media_type);
    dev->dblock(BST_DOING_ACQUIRE);
@@ -151,7 +151,13 @@ bool acquire_device_for_read(DCR *dcr)
       release_reserve_messages(jcr);         /* release queued messages */
       unlock_reservations();
 
-      if (stat == 1) {
+      if (stat == 1) { /* found new device to use */
+         /*
+          * Switching devices, so acquire lock on new device,
+          *   then release the old one.
+          */
+         P(dcr->dev->read_acquire_mutex);
+         V(dev->read_acquire_mutex);
          dev = dcr->dev;                     /* get new device pointer */
          dev->dblock(BST_DOING_ACQUIRE); 
 
@@ -349,6 +355,7 @@ get_out:
    }
    Dmsg2(950, "dcr=%p dev=%p\n", dcr, dcr->dev);
    Dmsg2(950, "MediaType dcr=%s dev=%s\n", dcr->media_type, dev->device->media_type);
+   V(dev->read_acquire_mutex);
    return ok;
 }
 
index cece9f2476f6547c59ceb44aa3d98bd326904b7f..8bf46d396a9775eb407e31f3e9ea1dd0335f511c 100644 (file)
@@ -1,7 +1,7 @@
 /*
    Bacula® - The Network Backup Solution
 
-   Copyright (C) 2000-2010 Free Software Foundation Europe e.V.
+   Copyright (C) 2000-2012 Free Software Foundation Europe e.V.
 
    The main author of Bacula is Kern Sibbald, with contributions from
    many others, a complete list can be found in the file AUTHORS.
@@ -291,6 +291,12 @@ init_dev(JCR *jcr, DEVRES *device)
    bthread_mutex_set_priority(&dev->m_mutex,       PRIO_SD_DEV_ACCESS);
    bthread_mutex_set_priority(&dev->spool_mutex,   PRIO_SD_DEV_SPOOL);
    bthread_mutex_set_priority(&dev->acquire_mutex, PRIO_SD_DEV_ACQUIRE);
+   if ((errstat = pthread_mutex_init(&dev->read_acquire_mutex, NULL)) != 0) {
+      berrno be;
+      dev->dev_errno = errstat;
+      Mmsg1(dev->errmsg, _("Unable to init mutex: ERR=%s\n"), be.bstrerror(errstat));
+      Jmsg0(jcr, M_ERROR_TERM, 0, dev->errmsg);
+   }
 #ifdef xxx
    if ((errstat = rwl_init(&dev->lock)) != 0) {
       berrno be;
index 28c378820bd3a99e7a1cb378d3eff3665f2904a9..d6d1004ee53a223cf418dc6215b9dcdbcd8f4da8 100644 (file)
@@ -1,7 +1,7 @@
 /*
    Bacula® - The Network Backup Solution
 
-   Copyright (C) 2000-2011 Free Software Foundation Europe e.V.
+   Copyright (C) 2000-2012 Free Software Foundation Europe e.V.
 
    The main author of Bacula is Kern Sibbald, with contributions from
    many others, a complete list can be found in the file AUTHORS.
@@ -225,6 +225,7 @@ public:
    bthread_mutex_t m_mutex;           /* access control */
    bthread_mutex_t spool_mutex;       /* mutex for updating spool_size */
    bthread_mutex_t acquire_mutex;     /* mutex for acquire code */
+   pthread_mutex_t read_acquire_mutex; /* mutex for acquire read code */
    pthread_cond_t wait;               /* thread wait variable */
    pthread_cond_t wait_next_vol;      /* wait for tape to be mounted */
    pthread_t no_wait_id;              /* this thread must not wait */