diff --git a/src/locking/libvirt_lockd.aug b/src/locking/libvirt_lockd.aug index 3473862796..6a3bcba0ef 100644 --- a/src/locking/libvirt_lockd.aug +++ b/src/locking/libvirt_lockd.aug @@ -21,6 +21,7 @@ module Libvirt_lockd = | bool_entry "require_lease_for_disks" | str_entry "file_lockspace_dir" | str_entry "lvm_lockspace_dir" + | str_entry "scsi_lockspace_dir" let comment = [ label "#comment" . del /#[ \t]*/ "# " . store /([^ \t\n][^\n]*)?/ . del /\n/ "\n" ] let empty = [ label "#empty" . eol ] diff --git a/src/locking/lock_driver_lockd.c b/src/locking/lock_driver_lockd.c index e9f9071f8b..3902edee9f 100644 --- a/src/locking/lock_driver_lockd.c +++ b/src/locking/lock_driver_lockd.c @@ -74,6 +74,7 @@ struct _virLockManagerLockDaemonDriver { char *fileLockSpaceDir; char *lvmLockSpaceDir; + char *scsiLockSpaceDir; }; static virLockManagerLockDaemonDriverPtr driver = NULL; @@ -146,6 +147,17 @@ static int virLockManagerLockDaemonLoadConfig(const char *configFile) } } + p = virConfGetValue(conf, "scsi_lockspace_dir"); + CHECK_TYPE("scsi_lockspace_dir", VIR_CONF_STRING); + if (p && p->str) { + VIR_FREE(driver->scsiLockSpaceDir); + if (!(driver->scsiLockSpaceDir = strdup(p->str))) { + virReportOOMError(); + virConfFree(conf); + return -1; + } + } + p = virConfGetValue(conf, "require_lease_for_disks"); CHECK_TYPE("require_lease_for_disks", VIR_CONF_LONG); if (p) @@ -387,6 +399,10 @@ static int virLockManagerLockDaemonInit(unsigned int version, if (driver->lvmLockSpaceDir && virLockManagerLockDaemonSetupLockspace(driver->lvmLockSpaceDir) < 0) goto error; + + if (driver->scsiLockSpaceDir && + virLockManagerLockDaemonSetupLockspace(driver->scsiLockSpaceDir) < 0) + goto error; } return 0; @@ -581,6 +597,23 @@ static int virLockManagerLockDaemonAddResource(virLockManagerPtr lock, /* Fallback to generic non-block code */ } + if (STRPREFIX(name, "/dev") && + driver->scsiLockSpaceDir) { + VIR_DEBUG("Trying to find an SCSI ID for %s", name); + if (virStorageFileGetSCSIKey(name, &newName) < 0) + goto error; + + if (newName) { + VIR_DEBUG("Got an SCSI ID %s for %s", newName, name); + if (!(newLockspace = strdup(driver->scsiLockSpaceDir))) + goto no_memory; + autoCreate = true; + break; + } + virResetLastError(); + /* Fallback to generic non-block code */ + } + if (driver->fileLockSpaceDir) { if (!(newLockspace = strdup(driver->fileLockSpaceDir))) goto no_memory; diff --git a/src/locking/lockd.conf b/src/locking/lockd.conf index 00f9b495e1..85edb917a3 100644 --- a/src/locking/lockd.conf +++ b/src/locking/lockd.conf @@ -52,3 +52,17 @@ # storage. # #lvm_lockspace_dir = "/var/lib/libvirt/lockd/lvmvolumes" + + +# +# When using SCSI volumes that can be visible across +# multiple, it is desirable to do locking based on +# the unique UUID associated with each volume, instead +# of their paths. Setting this path causes libvirt to +# do UUID based locking for SCSI. +# +# Typically this directory would be located on a shared +# filesystem visible to all hosts accessing the same +# storage. +# +#scsi_lockspace_dir = "/var/lib/libvirt/lockd/scsivolumes" diff --git a/src/locking/test_libvirt_lockd.aug.in b/src/locking/test_libvirt_lockd.aug.in index 25cba68c07..52b37541cb 100644 --- a/src/locking/test_libvirt_lockd.aug.in +++ b/src/locking/test_libvirt_lockd.aug.in @@ -6,3 +6,4 @@ module Test_libvirt_lockd = { "require_lease_for_disks" = "1" } { "file_lockspace_dir" = "/var/lib/libvirt/lockd/files" } { "lvm_lockspace_dir" = "/var/lib/libvirt/lockd/lvmvolumes" } +{ "scsi_lockspace_dir" = "/var/lib/libvirt/lockd/scsivolumes" }