You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by mt...@apache.org on 2013/10/04 23:42:17 UTC
git commit: updated refs/heads/master to bced4c7
Updated Branches:
refs/heads/master 66b853789 -> bced4c7e8
Add support for hypervisor snapshots to CloudStack-managed storage (for XenServer and VMware)
Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/bced4c7e
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/bced4c7e
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/bced4c7e
Branch: refs/heads/master
Commit: bced4c7e8ba791ebcd5a8117cf30445388233d68
Parents: 66b8537
Author: Mike Tutkowski <mi...@solidfire.com>
Authored: Wed Oct 2 00:07:48 2013 -0600
Committer: Mike Tutkowski <mi...@solidfire.com>
Committed: Fri Oct 4 15:41:20 2013 -0600
----------------------------------------------------------------------
.../cloud/agent/api/AttachVolumeCommand.java | 8 +-
.../api/agent/test/AttachVolumeAnswerTest.java | 2 +-
.../api/agent/test/AttachVolumeCommandTest.java | 2 +-
.../vmware/manager/VmwareHostService.java | 6 +-
.../vmware/resource/VmwareResource.java | 66 +++++++-------
.../VmwareSecondaryStorageResourceHandler.java | 9 +-
.../resource/VmwareStorageProcessor.java | 43 +++++++---
.../xen/resource/CitrixResourceBase.java | 90 ++++++++++----------
.../xen/resource/XenServerStorageProcessor.java | 14 ++-
.../driver/SolidfirePrimaryDataStoreDriver.java | 4 +-
.../storage/datastore/util/SolidFireUtil.java | 22 +++--
.../com/cloud/storage/VolumeApiServiceImpl.java | 13 ++-
12 files changed, 172 insertions(+), 107 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/core/src/com/cloud/agent/api/AttachVolumeCommand.java
----------------------------------------------------------------------
diff --git a/core/src/com/cloud/agent/api/AttachVolumeCommand.java b/core/src/com/cloud/agent/api/AttachVolumeCommand.java
index 49b2a70..e927619 100644
--- a/core/src/com/cloud/agent/api/AttachVolumeCommand.java
+++ b/core/src/com/cloud/agent/api/AttachVolumeCommand.java
@@ -25,6 +25,7 @@ public class AttachVolumeCommand extends Command {
private StoragePoolType pooltype;
private String volumePath;
private String volumeName;
+ private Long volumeSize;
private Long deviceId;
private String chainInfo;
private String poolUuid;
@@ -45,13 +46,14 @@ public class AttachVolumeCommand extends Command {
public AttachVolumeCommand(boolean attach, boolean managed, String vmName,
StoragePoolType pooltype, String volumePath, String volumeName,
- Long deviceId, String chainInfo) {
+ Long volumeSize, Long deviceId, String chainInfo) {
this.attach = attach;
this._managed = managed;
this.vmName = vmName;
this.pooltype = pooltype;
this.volumePath = volumePath;
this.volumeName = volumeName;
+ this.volumeSize = volumeSize;
this.deviceId = deviceId;
this.chainInfo = chainInfo;
}
@@ -85,6 +87,10 @@ public class AttachVolumeCommand extends Command {
return volumeName;
}
+ public Long getVolumeSize() {
+ return volumeSize;
+ }
+
public Long getDeviceId() {
return deviceId;
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeAnswerTest.java
----------------------------------------------------------------------
diff --git a/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeAnswerTest.java b/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeAnswerTest.java
index 0b2bb1f..5262d3b 100644
--- a/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeAnswerTest.java
+++ b/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeAnswerTest.java
@@ -27,7 +27,7 @@ import com.cloud.storage.Storage.StoragePoolType;
public class AttachVolumeAnswerTest {
AttachVolumeCommand avc = new AttachVolumeCommand(true, false, "vmname",
- StoragePoolType.Filesystem, "vPath", "vName",
+ StoragePoolType.Filesystem, "vPath", "vName", 1073741824L,
123456789L, "chainInfo");
AttachVolumeAnswer ava1 = new AttachVolumeAnswer(avc);
String results = "";
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeCommandTest.java
----------------------------------------------------------------------
diff --git a/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeCommandTest.java b/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeCommandTest.java
index 6f413c0..1c5caca 100644
--- a/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeCommandTest.java
+++ b/core/test/org/apache/cloudstack/api/agent/test/AttachVolumeCommandTest.java
@@ -26,7 +26,7 @@ import com.cloud.storage.Storage.StoragePoolType;
public class AttachVolumeCommandTest {
AttachVolumeCommand avc = new AttachVolumeCommand(true, false, "vmname",
- StoragePoolType.Filesystem, "vPath", "vName",
+ StoragePoolType.Filesystem, "vPath", "vName", 1073741824L,
123456789L, "chainInfo");
@Test
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareHostService.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareHostService.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareHostService.java
index 2b44071..d0147d1 100644
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareHostService.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareHostService.java
@@ -17,6 +17,7 @@
package com.cloud.hypervisor.vmware.manager;
import com.cloud.agent.api.Command;
+import com.cloud.hypervisor.vmware.mo.DatastoreMO;
import com.cloud.hypervisor.vmware.mo.VmwareHypervisorHost;
import com.cloud.hypervisor.vmware.util.VmwareContext;
import com.vmware.vim25.ManagedObjectReference;
@@ -28,7 +29,8 @@ public interface VmwareHostService {
String getWorkerName(VmwareContext context, Command cmd, int workerSequence);
- ManagedObjectReference handleDatastoreAndVmdkAttach(Command cmd, String iqn, String storageHost, int storagePort,
- String initiatorUsername, String initiatorPassword, String targetUsername, String targetPassword) throws Exception;
+ ManagedObjectReference getVmfsDatastore(VmwareHypervisorHost hyperHost, String datastoreName, String storageIpAddress, int storagePortNumber,
+ String iqn, String initiatorChapName, String initiatorChapSecret, String mutualChapName, String mutualChapSecret) throws Exception;
+ void createVmdk(Command cmd, DatastoreMO dsMo, String volumeDatastorePath, Long volumeSize) throws Exception;
void handleDatastoreAndVmdkDetach(String iqn, String storageHost, int storagePort) throws Exception;
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
index 83dcc58..6b3731ce 100755
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/resource/VmwareResource.java
@@ -4439,7 +4439,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
return str.replace('/', '-');
}
- private String trimIqn(String iqn) {
+ public static String trimIqn(String iqn) {
String[] tmp = iqn.split("/");
if (tmp.length != 3) {
@@ -4454,36 +4454,23 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
}
@Override
- public ManagedObjectReference handleDatastoreAndVmdkAttach(Command cmd, String iqn, String storageHost, int storagePort,
- String initiatorUsername, String initiatorPassword, String targetUsername, String targetPassword) throws Exception {
+ public void createVmdk(Command cmd, DatastoreMO dsMo, String vmdkDatastorePath, Long volumeSize) throws Exception {
VmwareContext context = getServiceContext();
VmwareHypervisorHost hyperHost = getHyperHost(context);
- ManagedObjectReference morDs = createVmfsDatastore(hyperHost, getDatastoreName(iqn),
- storageHost, storagePort, trimIqn(iqn),
- initiatorUsername, initiatorPassword,
- targetUsername, targetPassword);
+ String dummyVmName = getWorkerName(context, cmd, 0);
- DatastoreMO dsMo = new DatastoreMO(context, morDs);
+ VirtualMachineMO vmMo = HypervisorHostHelper.createWorkerVM(hyperHost, dsMo, dummyVmName);
- String volumeDatastorePath = String.format("[%s] %s.vmdk", dsMo.getName(), dsMo.getName());
-
- if (!dsMo.fileExists(volumeDatastorePath)) {
- String dummyVmName = getWorkerName(context, cmd, 0);
-
- VirtualMachineMO vmMo = HypervisorHostHelper.createWorkerVM(hyperHost, dsMo, dummyVmName);
-
- if (vmMo == null) {
- throw new Exception("Unable to create a dummy VM for volume creation");
- }
-
- vmMo.createDisk(volumeDatastorePath, getMBsFromBytes(dsMo.getSummary().getFreeSpace()),
- morDs, vmMo.getScsiDeviceControllerKey());
- vmMo.detachDisk(volumeDatastorePath, false);
- vmMo.destroy();
+ if (vmMo == null) {
+ throw new Exception("Unable to create a dummy VM for volume creation");
}
- return morDs;
+ Long volumeSizeToUse = volumeSize < dsMo.getSummary().getFreeSpace() ? volumeSize : dsMo.getSummary().getFreeSpace();
+
+ vmMo.createDisk(vmdkDatastorePath, getMBsFromBytes(volumeSizeToUse), dsMo.getMor(), vmMo.getScsiDeviceControllerKey());
+ vmMo.detachDisk(vmdkDatastorePath, false);
+ vmMo.destroy();
}
@Override
@@ -4516,9 +4503,16 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
ManagedObjectReference morDs = null;
if (cmd.getAttach() && cmd.isManaged()) {
- morDs = handleDatastoreAndVmdkAttach(cmd, cmd.get_iScsiName(), cmd.getStorageHost(), cmd.getStoragePort(),
- cmd.getChapInitiatorUsername(), cmd.getChapInitiatorPassword(),
- cmd.getChapTargetUsername(), cmd.getChapTargetPassword());
+ morDs = getVmfsDatastore(hyperHost, getDatastoreName(cmd.get_iScsiName()), cmd.getStorageHost(), cmd.getStoragePort(), trimIqn(cmd.get_iScsiName()),
+ cmd.getChapInitiatorUsername(), cmd.getChapInitiatorPassword(), cmd.getChapTargetUsername(), cmd.getChapTargetPassword());
+
+ DatastoreMO dsMo = new DatastoreMO(getServiceContext(), morDs);
+
+ String volumeDatastorePath = String.format("[%s] %s.vmdk", dsMo.getName(), dsMo.getName());
+
+ if (!dsMo.fileExists(volumeDatastorePath)) {
+ createVmdk(cmd, dsMo, VmwareResource.getDatastoreName(cmd.get_iScsiName()), cmd.getVolumeSize());
+ }
}
else {
morDs = HypervisorHostHelper.findDatastoreWithBackwardsCompatibility(hyperHost, cmd.getPoolUuid());
@@ -4531,10 +4525,18 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
}
DatastoreMO dsMo = new DatastoreMO(getServiceContext(), morDs);
- VmwareStorageLayoutHelper.syncVolumeToVmDefaultFolder(dsMo.getOwnerDatacenter().first(), cmd.getVmName(),
- dsMo, cmd.getVolumePath());
-
- String datastoreVolumePath = dsMo.searchFileInSubFolders(cmd.getVolumePath() + ".vmdk", true);
+
+ String datastoreVolumePath = null;
+
+ if (cmd.isManaged()) {
+ datastoreVolumePath = dsMo.getDatastorePath(dsMo.getName() + ".vmdk");
+ }
+ else {
+ VmwareStorageLayoutHelper.syncVolumeToVmDefaultFolder(dsMo.getOwnerDatacenter().first(), cmd.getVmName(), dsMo, cmd.getVolumePath());
+
+ datastoreVolumePath = dsMo.searchFileInSubFolders(cmd.getVolumePath() + ".vmdk", true);
+ }
+
assert (datastoreVolumePath != null) : "Virtual disk file must exist in specified datastore for attach/detach operations.";
if (datastoreVolumePath == null) {
throw new CloudRuntimeException("Unable to find file " + cmd.getVolumePath() + ".vmdk in datastore " + dsMo.getName());
@@ -4687,7 +4689,7 @@ public class VmwareResource implements StoragePoolResource, ServerResource, Vmwa
}
}
- private ManagedObjectReference createVmfsDatastore(VmwareHypervisorHost hyperHost, String datastoreName, String storageIpAddress,
+ public ManagedObjectReference getVmfsDatastore(VmwareHypervisorHost hyperHost, String datastoreName, String storageIpAddress,
int storagePortNumber, String iqn, String chapName, String chapSecret, String mutualChapName, String mutualChapSecret) throws Exception {
VmwareContext context = getServiceContext();
ManagedObjectReference morCluster = hyperHost.getHyperHostCluster();
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java b/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
index 2c302ab..c84813f 100644
--- a/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareSecondaryStorageResourceHandler.java
@@ -37,6 +37,7 @@ import com.cloud.hypervisor.vmware.manager.VmwareStorageManager;
import com.cloud.hypervisor.vmware.manager.VmwareStorageManagerImpl;
import com.cloud.hypervisor.vmware.manager.VmwareStorageMount;
import com.cloud.hypervisor.vmware.mo.ClusterMO;
+import com.cloud.hypervisor.vmware.mo.DatastoreMO;
import com.cloud.hypervisor.vmware.mo.HostMO;
import com.cloud.hypervisor.vmware.mo.VmwareHostType;
import com.cloud.hypervisor.vmware.mo.VmwareHypervisorHost;
@@ -347,8 +348,12 @@ public class VmwareSecondaryStorageResourceHandler implements SecondaryStorageRe
return true;
}
- public ManagedObjectReference handleDatastoreAndVmdkAttach(Command cmd, String iqn, String storageHost, int storagePort,
- String initiatorUsername, String initiatorPassword, String targetUsername, String targetPassword) throws Exception {
+ public ManagedObjectReference getVmfsDatastore(VmwareHypervisorHost hyperHost, String datastoreName, String storageIpAddress, int storagePortNumber,
+ String iqn, String initiatorChapName, String initiatorChapSecret, String mutualChapName, String mutualChapSecret) throws Exception {
+ throw new OperationNotSupportedException();
+ }
+
+ public void createVmdk(Command cmd, DatastoreMO dsMo, String volumeDatastorePath, Long volumeSize) throws Exception {
throw new OperationNotSupportedException();
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareStorageProcessor.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareStorageProcessor.java b/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareStorageProcessor.java
index a14c403..34bfe18 100644
--- a/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareStorageProcessor.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/storage/resource/VmwareStorageProcessor.java
@@ -1191,8 +1191,16 @@ public class VmwareStorageProcessor implements StorageProcessor {
ManagedObjectReference morDs = null;
if (isAttach && isManaged) {
- morDs = hostService.handleDatastoreAndVmdkAttach(cmd, iScsiName, storageHost, storagePort,
- initiatorUsername, initiatorPassword, targetUsername, targetPassword);
+ morDs = hostService.getVmfsDatastore(hyperHost, VmwareResource.getDatastoreName(iScsiName), storageHost, storagePort,
+ VmwareResource.trimIqn(iScsiName), initiatorUsername, initiatorPassword, targetUsername, targetPassword);
+
+ DatastoreMO dsMo = new DatastoreMO(hostService.getServiceContext(null), morDs);
+
+ String volumeDatastorePath = String.format("[%s] %s.vmdk", dsMo.getName(), dsMo.getName());
+
+ if (!dsMo.fileExists(volumeDatastorePath)) {
+ hostService.createVmdk(cmd, dsMo, VmwareResource.getDatastoreName(iScsiName), volumeTO.getSize());
+ }
}
else {
morDs = HypervisorHostHelper.findDatastoreWithBackwardsCompatibility(hyperHost, isManaged ? VmwareResource.getDatastoreName(iScsiName) : primaryStore.getUuid());
@@ -1207,24 +1215,35 @@ public class VmwareStorageProcessor implements StorageProcessor {
DatastoreMO dsMo = new DatastoreMO(this.hostService.getServiceContext(null), morDs);
String datastoreVolumePath;
- if(isAttach) {
- if(!isManaged)
- datastoreVolumePath = VmwareStorageLayoutHelper.syncVolumeToVmDefaultFolder(dsMo.getOwnerDatacenter().first(), vmName,
- dsMo, volumeTO.getPath());
- else
+ if (isAttach) {
+ if (isManaged) {
datastoreVolumePath = dsMo.getDatastorePath(dsMo.getName() + ".vmdk");
- } else {
- datastoreVolumePath = VmwareStorageLayoutHelper.getLegacyDatastorePathFromVmdkFileName(dsMo, volumeTO.getPath() + ".vmdk");
- if(!dsMo.fileExists(datastoreVolumePath))
- datastoreVolumePath = VmwareStorageLayoutHelper.getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, volumeTO.getPath() + ".vmdk");
+ }
+ else {
+ datastoreVolumePath = VmwareStorageLayoutHelper.syncVolumeToVmDefaultFolder(dsMo.getOwnerDatacenter().first(), vmName, dsMo, volumeTO.getPath());
+ }
+ }
+ else {
+ if (isManaged) {
+ datastoreVolumePath = dsMo.getDatastorePath(dsMo.getName() + ".vmdk");
+ }
+ else {
+ datastoreVolumePath = VmwareStorageLayoutHelper.getLegacyDatastorePathFromVmdkFileName(dsMo, volumeTO.getPath() + ".vmdk");
+
+ if (!dsMo.fileExists(datastoreVolumePath)) {
+ datastoreVolumePath = VmwareStorageLayoutHelper.getVmwareDatastorePathFromVmdkFileName(dsMo, vmName, volumeTO.getPath() + ".vmdk");
+ }
+ }
}
disk.setVdiUuid(datastoreVolumePath);
AttachAnswer answer = new AttachAnswer(disk);
+
if (isAttach) {
vmMo.attachDisk(new String[] { datastoreVolumePath }, morDs);
- } else {
+ }
+ else {
vmMo.removeAllSnapshots();
vmMo.detachDisk(datastoreVolumePath, false);
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/CitrixResourceBase.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/CitrixResourceBase.java b/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/CitrixResourceBase.java
index 6b81c25..92fbab2 100644
--- a/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/CitrixResourceBase.java
+++ b/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/CitrixResourceBase.java
@@ -5348,7 +5348,7 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
if (pool.getType() == StoragePoolType.NetworkFilesystem) {
getNfsSR(conn, pool);
} else if (pool.getType() == StoragePoolType.IscsiLUN) {
- getIscsiSR(conn, pool.getUuid(), pool.getHost(), pool.getPath(), null, null, new Boolean[1]);
+ getIscsiSR(conn, pool.getUuid(), pool.getHost(), pool.getPath(), null, null);
} else if (pool.getType() == StoragePoolType.PreSetup) {
} else {
return new Answer(cmd, false, "The pool type: " + pool.getType().name() + " is not supported.");
@@ -6166,17 +6166,27 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
}
protected VDI getVDIbyUuid(Connection conn, String uuid) {
+ return getVDIbyUuid(conn, uuid, true);
+ }
+
+ protected VDI getVDIbyUuid(Connection conn, String uuid, boolean throwExceptionIfNotFound) {
try {
return VDI.getByUuid(conn, uuid);
} catch (Exception e) {
- String msg = "Catch Exception " + e.getClass().getName() + " :VDI getByUuid for uuid: " + uuid + " failed due to " + e.toString();
- s_logger.debug(msg);
- throw new CloudRuntimeException(msg, e);
+ if (throwExceptionIfNotFound) {
+ String msg = "Catch Exception " + e.getClass().getName() + " :VDI getByUuid for uuid: " + uuid + " failed due to " + e.toString();
+
+ s_logger.debug(msg);
+
+ throw new CloudRuntimeException(msg, e);
+ }
+
+ return null;
}
}
protected SR getIscsiSR(Connection conn, String srNameLabel, String target, String path,
- String chapInitiatorUsername, String chapInitiatorPassword, Boolean[] created) {
+ String chapInitiatorUsername, String chapInitiatorPassword) {
synchronized (srNameLabel.intern()) {
Map<String, String> deviceConfig = new HashMap<String, String>();
try {
@@ -6280,8 +6290,6 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
{
sr = SR.create(conn, host, deviceConfig, new Long(0), srNameLabel, srNameLabel, type, "user", true,
smConfig);
-
- created[0] = true; // note that the SR was created (as opposed to introduced)
} else {
sr = SR.introduce(conn, pooluuid, srNameLabel, srNameLabel,
type, "user", true, smConfig);
@@ -6459,54 +6467,41 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
}
}
- protected VDI handleSrAndVdiAttach(String iqn, String storageHostName,
- String chapInitiatorName, String chapInitiatorPassword) throws Types.XenAPIException, XmlRpcException {
+ protected VDI createVdi(SR sr, String vdiNameLabel, Long volumeSize) throws Types.XenAPIException, XmlRpcException {
VDI vdi = null;
Connection conn = getConnection();
- Boolean[] created = { false };
-
- SR sr = getIscsiSR(conn, iqn,
- storageHostName, iqn,
- chapInitiatorName, chapInitiatorPassword, created);
-
- // if created[0] is true, this means the SR was actually created...as opposed to introduced
- if (created[0]) {
- VDI.Record vdir = new VDI.Record();
-
- vdir.nameLabel = iqn;
- vdir.SR = sr;
- vdir.type = Types.VdiType.USER;
+ VDI.Record vdir = new VDI.Record();
- long totalSpace = sr.getPhysicalSize(conn);
- long unavailableSpace = sr.getPhysicalUtilisation(conn);
+ vdir.nameLabel = vdiNameLabel;
+ vdir.SR = sr;
+ vdir.type = Types.VdiType.USER;
- vdir.virtualSize = totalSpace - unavailableSpace;
+ long totalSrSpace = sr.getPhysicalSize(conn);
+ long unavailableSrSpace = sr.getPhysicalUtilisation(conn);
+ long availableSrSpace = totalSrSpace - unavailableSrSpace;
- if (vdir.virtualSize < 0) {
- throw new CloudRuntimeException("VDI virtual size cannot be less than 0.");
- }
+ if (availableSrSpace < volumeSize) {
+ throw new CloudRuntimeException("Available space for SR cannot be less than " + volumeSize + ".");
+ }
- long maxNumberOfTries = (totalSpace / unavailableSpace >= 1) ? (totalSpace / unavailableSpace) : 1;
- long tryNumber = 0;
+ vdir.virtualSize = volumeSize;
- while (tryNumber <= maxNumberOfTries) {
- try {
- vdi = VDI.create(conn, vdir);
+ long maxNumberOfTries = (totalSrSpace / unavailableSrSpace >= 1) ? (totalSrSpace / unavailableSrSpace) : 1;
+ long tryNumber = 0;
- break;
- }
- catch (Exception ex) {
- tryNumber++;
+ while (tryNumber <= maxNumberOfTries) {
+ try {
+ vdi = VDI.create(conn, vdir);
- vdir.virtualSize -= unavailableSpace;
- }
+ break;
}
+ catch (Exception ex) {
+ tryNumber++;
- }
- else {
- vdi = sr.getVDIs(conn).iterator().next();
+ vdir.virtualSize -= unavailableSrSpace;
+ }
}
return vdi;
@@ -6534,12 +6529,17 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
}
try {
- // Look up the VDI
VDI vdi = null;
if (cmd.getAttach() && cmd.isManaged()) {
- vdi = handleSrAndVdiAttach(cmd.get_iScsiName(), cmd.getStorageHost(),
- cmd.getChapInitiatorUsername(), cmd.getChapInitiatorPassword());
+ SR sr = getIscsiSR(conn, cmd.get_iScsiName(), cmd.getStorageHost(), cmd.get_iScsiName(),
+ cmd.getChapInitiatorUsername(), cmd.getChapInitiatorPassword());
+
+ vdi = getVDIbyUuid(conn, cmd.getVolumePath(), false);
+
+ if (vdi == null) {
+ vdi = createVdi(sr, cmd.get_iScsiName(), cmd.getVolumeSize());
+ }
}
else {
vdi = getVDIbyUuid(conn, cmd.getVolumePath());
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageProcessor.java
----------------------------------------------------------------------
diff --git a/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageProcessor.java b/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageProcessor.java
index 5da0571..2d4c86e 100644
--- a/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageProcessor.java
+++ b/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageProcessor.java
@@ -167,12 +167,20 @@ public class XenServerStorageProcessor implements StorageProcessor {
try {
Connection conn = this.hypervisorResource.getConnection();
- // Look up the VDI
+
VDI vdi = null;
if (cmd.isManaged()) {
- vdi = this.hypervisorResource.handleSrAndVdiAttach(cmd.get_iScsiName(), cmd.getStorageHost(),
- cmd.getChapInitiatorUsername(), cmd.getChapInitiatorPassword());
+ SR sr = this.hypervisorResource.getIscsiSR(conn, cmd.get_iScsiName(), cmd.getStorageHost(), cmd.get_iScsiName(),
+ cmd.getChapInitiatorUsername(), cmd.getChapInitiatorPassword());
+
+ vdi = this.hypervisorResource.getVDIbyUuid(conn, data.getPath(), false);
+
+ if (vdi == null) {
+ VolumeObjectTO volume = (VolumeObjectTO)data;
+
+ vdi = this.hypervisorResource.createVdi(sr, cmd.get_iScsiName(), volume.getSize());
+ }
}
else {
vdi = this.hypervisorResource.mount(conn, null, null, data.getPath());
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/driver/SolidfirePrimaryDataStoreDriver.java
----------------------------------------------------------------------
diff --git a/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/driver/SolidfirePrimaryDataStoreDriver.java b/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/driver/SolidfirePrimaryDataStoreDriver.java
index c73e409..8046b6c 100644
--- a/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/driver/SolidfirePrimaryDataStoreDriver.java
+++ b/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/driver/SolidfirePrimaryDataStoreDriver.java
@@ -277,8 +277,10 @@ public class SolidfirePrimaryDataStoreDriver implements PrimaryDataStoreDriver {
iops = new Iops(volumeInfo.getMinIops(), volumeInfo.getMaxIops(), getDefaultBurstIops(storagePoolId, volumeInfo.getMaxIops()));
}
+ long volumeSize = volumeInfo.getSize() * 2; // in reality, use a multiplier that's at cluster-level scope
+
long sfVolumeId = SolidFireUtil.createSolidFireVolume(mVip, mPort, clusterAdminUsername, clusterAdminPassword,
- getSolidFireVolumeName(volumeInfo.getName()), sfAccountId, volumeInfo.getSize(), true,
+ getSolidFireVolumeName(volumeInfo.getName()), sfAccountId, volumeSize, true, volumeInfo.getSize().toString(),
iops.getMinIops(), iops.getMaxIops(), iops.getBurstIops());
return SolidFireUtil.getSolidFireVolume(mVip, mPort, clusterAdminUsername, clusterAdminPassword, sfVolumeId);
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/util/SolidFireUtil.java
----------------------------------------------------------------------
diff --git a/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/util/SolidFireUtil.java b/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/util/SolidFireUtil.java
index ac11272..6659f98 100644
--- a/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/util/SolidFireUtil.java
+++ b/plugins/storage/volume/solidfire/src/org/apache/cloudstack/storage/datastore/util/SolidFireUtil.java
@@ -78,13 +78,13 @@ public class SolidFireUtil
public static final String USE_MUTUAL_CHAP_FOR_VMWARE = "useMutualChapForVMware";
public static long createSolidFireVolume(String strSfMvip, int iSfPort, String strSfAdmin, String strSfPassword,
- String strSfVolumeName, long lSfAccountId, long lTotalSize, boolean bEnable512e,
+ String strSfVolumeName, long lSfAccountId, long lTotalSize, boolean bEnable512e, final String strCloudStackVolumeSize,
long lMinIops, long lMaxIops, long lBurstIops)
{
final Gson gson = new GsonBuilder().create();
VolumeToCreate volumeToCreate = new VolumeToCreate(strSfVolumeName, lSfAccountId, lTotalSize, bEnable512e,
- lMinIops, lMaxIops, lBurstIops);
+ strCloudStackVolumeSize, lMinIops, lMaxIops, lBurstIops);
String strVolumeToCreateJson = gson.toJson(volumeToCreate);
@@ -443,10 +443,10 @@ public class SolidFireUtil
private final VolumeToCreateParams params;
private VolumeToCreate(final String strVolumeName, final long lAccountId, final long lTotalSize,
- final boolean bEnable512e, final long lMinIOPS, final long lMaxIOPS, final long lBurstIOPS)
+ final boolean bEnable512e, final String strCloudStackVolumeSize, final long lMinIOPS, final long lMaxIOPS, final long lBurstIOPS)
{
params = new VolumeToCreateParams(strVolumeName, lAccountId, lTotalSize, bEnable512e,
- lMinIOPS, lMaxIOPS, lBurstIOPS);
+ strCloudStackVolumeSize, lMinIOPS, lMaxIOPS, lBurstIOPS);
}
private static final class VolumeToCreateParams
@@ -456,18 +456,30 @@ public class SolidFireUtil
private final long totalSize;
private final boolean enable512e;
private final VolumeToCreateParamsQoS qos;
+ private final VolumeToCreateParamsAttributes attributes;
private VolumeToCreateParams(final String strVolumeName, final long lAccountId, final long lTotalSize,
- final boolean bEnable512e, final long lMinIOPS, final long lMaxIOPS, final long lBurstIOPS)
+ final boolean bEnable512e, final String strCloudStackVolumeSize, final long lMinIOPS, final long lMaxIOPS, final long lBurstIOPS)
{
name = strVolumeName;
accountID = lAccountId;
totalSize = lTotalSize;
enable512e = bEnable512e;
+ attributes = new VolumeToCreateParamsAttributes(strCloudStackVolumeSize);
qos = new VolumeToCreateParamsQoS(lMinIOPS, lMaxIOPS, lBurstIOPS);
}
+ private static final class VolumeToCreateParamsAttributes
+ {
+ private final String CloudStackVolumeSize;
+
+ private VolumeToCreateParamsAttributes(final String strCloudStackVolumeSize)
+ {
+ CloudStackVolumeSize = strCloudStackVolumeSize;
+ }
+ }
+
private static final class VolumeToCreateParamsQoS
{
private final long minIOPS;
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/bced4c7e/server/src/com/cloud/storage/VolumeApiServiceImpl.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/storage/VolumeApiServiceImpl.java b/server/src/com/cloud/storage/VolumeApiServiceImpl.java
index faff10f..5161ca5 100644
--- a/server/src/com/cloud/storage/VolumeApiServiceImpl.java
+++ b/server/src/com/cloud/storage/VolumeApiServiceImpl.java
@@ -1047,8 +1047,17 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic
HypervisorType rootDiskHyperType = vm.getHypervisorType();
HypervisorType dataDiskHyperType = _volsDao.getHypervisorType(volume.getId());
- if (dataDiskHyperType != HypervisorType.None && rootDiskHyperType != dataDiskHyperType) {
- throw new InvalidParameterValueException("Can't attach a volume created by: " + dataDiskHyperType + " to a " + rootDiskHyperType + " vm");
+
+ VolumeVO dataDiskVol = _volsDao.findById(volume.getId());
+ StoragePoolVO dataDiskStoragePool = _storagePoolDao.findById(dataDiskVol.getPoolId());
+
+ // managed storage can be used for different types of hypervisors
+ // only perform this check if the volume's storage pool is not null and not managed
+ if (dataDiskStoragePool != null && !dataDiskStoragePool.isManaged()) {
+ if (dataDiskHyperType != HypervisorType.None && rootDiskHyperType != dataDiskHyperType) {
+ throw new InvalidParameterValueException("Can't attach a volume created by: " + dataDiskHyperType +
+ " to a " + rootDiskHyperType + " vm");
+ }
}
deviceId = getDeviceId(vmId, deviceId);