diff --git a/api/src/com/cloud/storage/Volume.java b/api/src/com/cloud/storage/Volume.java
index f54dfef865f..18edbc3a1b3 100755
--- a/api/src/com/cloud/storage/Volume.java
+++ b/api/src/com/cloud/storage/Volume.java
@@ -35,7 +35,8 @@ public interface Volume extends ControlledEntity, BasedOn, StateObject
+
diff --git a/engine/storage/src/org/apache/cloudstack/storage/command/CommandResult.java b/engine/storage/src/org/apache/cloudstack/storage/command/CommandResult.java
index 998f35dd06b..d1528635945 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/command/CommandResult.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/command/CommandResult.java
@@ -23,7 +23,7 @@ public class CommandResult {
private String result;
public CommandResult() {
- this.success = false;
+ this.success = true;
this.result = "";
}
diff --git a/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeAnswer.java b/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeAnswer.java
index cfed00c60ab..42674de3cf2 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeAnswer.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeAnswer.java
@@ -32,6 +32,10 @@ public class CreateVolumeAnswer extends Answer {
super(cmd);
this.volumeUuid = volumeUuid;
}
+
+ public CreateVolumeAnswer(Command cmd, boolean status, String result) {
+ super(cmd, status, result);
+ }
public String getVolumeUuid() {
return this.volumeUuid;
diff --git a/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeCommand.java b/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeCommand.java
index e42d2651f51..c44970e36ff 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeCommand.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/command/CreateVolumeCommand.java
@@ -23,11 +23,11 @@ import org.apache.cloudstack.storage.to.VolumeTO;
import com.cloud.agent.api.Command;
public class CreateVolumeCommand extends Command implements StorageSubSystemCommand {
- protected VolumeTO volumeInfo;
+ protected VolumeTO volumeTO;
- public CreateVolumeCommand(VolumeTO volumeInfo) {
+ public CreateVolumeCommand(VolumeTO volumeTO) {
super();
- this.volumeInfo = volumeInfo;
+ this.volumeTO = volumeTO;
}
protected CreateVolumeCommand() {
@@ -39,5 +39,9 @@ public class CreateVolumeCommand extends Command implements StorageSubSystemComm
// TODO Auto-generated method stub
return false;
}
+
+ public VolumeTO getVolume() {
+ return this.volumeTO;
+ }
}
diff --git a/engine/storage/src/org/apache/cloudstack/storage/command/DeleteVolume.java b/engine/storage/src/org/apache/cloudstack/storage/command/DeleteVolumeCommand.java
similarity index 74%
rename from engine/storage/src/org/apache/cloudstack/storage/command/DeleteVolume.java
rename to engine/storage/src/org/apache/cloudstack/storage/command/DeleteVolumeCommand.java
index 755d7f8294b..a30a83b1448 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/command/DeleteVolume.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/command/DeleteVolumeCommand.java
@@ -18,17 +18,17 @@
*/
package org.apache.cloudstack.storage.command;
-import org.apache.cloudstack.engine.subsystem.api.storage.VolumeInfo;
+import org.apache.cloudstack.storage.to.VolumeTO;
import com.cloud.agent.api.Command;
-public class DeleteVolume extends Command {
-
- public DeleteVolume(VolumeInfo volume) {
-
+public class DeleteVolumeCommand extends Command implements StorageSubSystemCommand {
+ private VolumeTO volume;
+ public DeleteVolumeCommand(VolumeTO volume) {
+ this.volume = volume;
}
- protected DeleteVolume() {
+ protected DeleteVolumeCommand() {
}
@Override
@@ -36,5 +36,9 @@ public class DeleteVolume extends Command {
// TODO Auto-generated method stub
return false;
}
+
+ public VolumeTO getVolume() {
+ return this.volume;
+ }
}
diff --git a/engine/storage/src/org/apache/cloudstack/storage/datastore/PrimaryDataStore.java b/engine/storage/src/org/apache/cloudstack/storage/datastore/PrimaryDataStore.java
index fca97916032..51c8696b421 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/datastore/PrimaryDataStore.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/datastore/PrimaryDataStore.java
@@ -36,7 +36,7 @@ public interface PrimaryDataStore extends PrimaryDataStoreInfo {
List getVolumes();
- boolean deleteVolume(VolumeInfo volume);
+ void deleteVolumeAsync(VolumeInfo volume, AsyncCompletionCallback callback);
void createVolumeAsync(VolumeInfo vo, VolumeDiskType diskType, AsyncCompletionCallback callback);
diff --git a/engine/storage/src/org/apache/cloudstack/storage/to/VolumeTO.java b/engine/storage/src/org/apache/cloudstack/storage/to/VolumeTO.java
index 6b8ab759f50..8ec117c605d 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/to/VolumeTO.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/to/VolumeTO.java
@@ -11,6 +11,7 @@ public class VolumeTO {
private final VolumeDiskType diskType;
private PrimaryDataStoreTO dataStore;
private final String name;
+ private final long size;
public VolumeTO(VolumeInfo volume) {
this.uuid = volume.getUuid();
this.path = volume.getPath();
@@ -22,6 +23,7 @@ public class VolumeTO {
this.dataStore = null;
}
this.name = volume.getName();
+ this.size = volume.getSize();
}
public String getUuid() {
@@ -51,4 +53,8 @@ public class VolumeTO {
public String getName() {
return this.name;
}
+
+ public long getSize() {
+ return this.size;
+ }
}
diff --git a/engine/storage/src/org/apache/cloudstack/storage/volume/VolumeEntityImpl.java b/engine/storage/src/org/apache/cloudstack/storage/volume/VolumeEntityImpl.java
index c3bdf4e059a..f3e07e74d0d 100644
--- a/engine/storage/src/org/apache/cloudstack/storage/volume/VolumeEntityImpl.java
+++ b/engine/storage/src/org/apache/cloudstack/storage/volume/VolumeEntityImpl.java
@@ -146,10 +146,6 @@ public class VolumeEntityImpl implements VolumeEntity {
}
- @Override
- public void destroy() {
- //vs.deleteVolume(volumeInfo);
- }
@Override
public long getSize() {
@@ -190,7 +186,7 @@ public class VolumeEntityImpl implements VolumeEntity {
}
- private Void createVolumeFromTemplateAsyncCallback(AsyncCallbackDispatcher callback, Object context) {
+ public Object createVolumeFromTemplateAsyncCallback(AsyncCallbackDispatcher callback, Object context) {
synchronized (volumeInfo) {
volumeInfo.notify();
}
@@ -216,7 +212,33 @@ public class VolumeEntityImpl implements VolumeEntity {
}
}
- private Void createVolumeCallback(AsyncCallbackDispatcher callback, Object context) {
+ public Void createVolumeCallback(AsyncCallbackDispatcher callback, Object context) {
+ synchronized (volumeInfo) {
+ this.result = callback.getResult();
+ volumeInfo.notify();
+ }
+ return null;
+ }
+
+
+ @Override
+ public void destroy() {
+ AsyncCallbackDispatcher caller = AsyncCallbackDispatcher.create(this);
+ caller.setCallback(caller.getTarget().destroyCallback(null, null));
+ vs.deleteVolumeAsync(volumeInfo, caller);
+ try {
+ synchronized (volumeInfo) {
+ volumeInfo.wait();
+ }
+ if (!result.isSuccess()) {
+ throw new CloudRuntimeException("Failed to create volume:" + result.getResult());
+ }
+ } catch (InterruptedException e) {
+ throw new CloudRuntimeException("wait volume info failed", e);
+ }
+ }
+
+ public Void destroyCallback(AsyncCallbackDispatcher callback, Object context) {
synchronized (volumeInfo) {
this.result = callback.getResult();
volumeInfo.notify();
diff --git a/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/DefaultPrimaryDataStore.java b/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/DefaultPrimaryDataStore.java
index 3d3ce68cc55..571f227667a 100644
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/DefaultPrimaryDataStore.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/DefaultPrimaryDataStore.java
@@ -111,8 +111,13 @@ public class DefaultPrimaryDataStore implements PrimaryDataStore {
}
@Override
- public boolean deleteVolume(VolumeInfo volume) {
- return this.driver.deleteVolume((VolumeObject)volume);
+ public void deleteVolumeAsync(VolumeInfo volume, AsyncCompletionCallback callback) {
+ CommandResult result = new CommandResult();
+ if (volume.isAttachedVM()) {
+ result.setResult("Can't delete volume: " + volume.getId() + ", if it's attached to a VM");
+ callback.complete(result);
+ }
+ this.driver.deleteVolumeAsync((VolumeObject)volume, callback);
}
@Override
diff --git a/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/DefaultPrimaryDataStoreDriverImpl.java b/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/DefaultPrimaryDataStoreDriverImpl.java
index 88eeca250f8..5567037501e 100644
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/DefaultPrimaryDataStoreDriverImpl.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/DefaultPrimaryDataStoreDriverImpl.java
@@ -12,7 +12,7 @@ import org.apache.cloudstack.storage.command.CommandResult;
import org.apache.cloudstack.storage.command.CreateVolumeAnswer;
import org.apache.cloudstack.storage.command.CreateVolumeCommand;
import org.apache.cloudstack.storage.command.CreateVolumeFromBaseImageCommand;
-import org.apache.cloudstack.storage.command.DeleteVolume;
+import org.apache.cloudstack.storage.command.DeleteVolumeCommand;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
import org.apache.cloudstack.storage.to.ImageOnPrimayDataStoreTO;
import org.apache.cloudstack.storage.to.VolumeTO;
@@ -72,7 +72,7 @@ public class DefaultPrimaryDataStoreDriverImpl implements PrimaryDataStoreDriver
ep.sendMessageAsync(createCmd, caller);
}
- protected Void createVolumeAsyncCallback(AsyncCallbackDispatcher callback, CreateVolumeContext context) {
+ public Void createVolumeAsyncCallback(AsyncCallbackDispatcher callback, CreateVolumeContext context) {
CommandResult result = new CommandResult();
CreateVolumeAnswer volAnswer = (CreateVolumeAnswer) callback.getResult();
if (volAnswer.getResult()) {
@@ -85,14 +85,27 @@ public class DefaultPrimaryDataStoreDriverImpl implements PrimaryDataStoreDriver
context.getParentCallback().complete(result);
return null;
}
-
+
@Override
- public boolean deleteVolume(VolumeObject vo) {
- DeleteVolume cmd = new DeleteVolume((VolumeInfo)vo);
+ public void deleteVolumeAsync(VolumeObject vo, AsyncCompletionCallback callback) {
+ DeleteVolumeCommand cmd = new DeleteVolumeCommand(this.dataStore.getVolumeTO(vo));
List endPoints = vo.getDataStore().getEndPoints();
- sendOutCommand(cmd, endPoints);
-
- return true;
+ EndPoint ep = endPoints.get(0);
+ AsyncRpcConext context = new AsyncRpcConext(callback);
+ AsyncCallbackDispatcher caller = AsyncCallbackDispatcher.create(this);
+ caller.setCallback(caller.getTarget().deleteVolumeCallback(null, null))
+ .setContext(context);
+ ep.sendMessageAsync(cmd, caller);
+ }
+
+ public Void deleteVolumeCallback(AsyncCallbackDispatcher callback, AsyncRpcConext context) {
+ CommandResult result = new CommandResult();
+ Answer answer = callback.getResult();
+ if (!answer.getResult()) {
+ result.setResult(answer.getDetails());
+ }
+ context.getParentCallback().complete(result);
+ return null;
}
@Override
@@ -106,33 +119,6 @@ public class DefaultPrimaryDataStoreDriverImpl implements PrimaryDataStoreDriver
// TODO Auto-generated method stub
return true;
}
-
- protected Answer sendOutCommand(Command cmd, List endPoints) {
- Answer answer = null;
- int retries = 3;
- int i = 0;
- for (EndPoint ep : endPoints) {
- answer = ep.sendMessage(cmd);
- if (answer == null || answer.getDetails() != null) {
- if (i < retries) {
- s_logger.debug("create volume failed, retrying: " + i);
- }
- i++;
- } else {
- break;
- }
- }
-
- if (answer == null || answer.getDetails() != null) {
- if (answer == null) {
- throw new CloudRuntimeException("Failed to created volume");
- } else {
- throw new CloudRuntimeException(answer.getDetails());
- }
- }
-
- return answer;
- }
private class CreateVolumeFromBaseImageContext extends AsyncRpcConext {
private final VolumeObject volume;
diff --git a/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/PrimaryDataStoreDriver.java b/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/PrimaryDataStoreDriver.java
index 96e629e2447..eca7d798cf6 100644
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/PrimaryDataStoreDriver.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/datastore/driver/PrimaryDataStoreDriver.java
@@ -14,7 +14,7 @@ public interface PrimaryDataStoreDriver {
void createVolumeFromBaseImageAsync(VolumeObject volume, TemplateOnPrimaryDataStoreInfo template, AsyncCompletionCallback callback);
- boolean deleteVolume(VolumeObject vo);
+ void deleteVolumeAsync(VolumeObject vo, AsyncCompletionCallback callback);
String grantAccess(VolumeObject vol, EndPoint ep);
diff --git a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeManagerImpl.java b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeManagerImpl.java
index 76f0b034cb4..98c6b69ee0f 100644
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeManagerImpl.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeManagerImpl.java
@@ -54,18 +54,18 @@ public class VolumeManagerImpl implements VolumeManager {
private void initStateMachine() {
s_fsm.addTransition(Volume.State.Allocated, Event.CreateRequested, Volume.State.Creating);
- s_fsm.addTransition(Volume.State.Allocated, Event.DestroyRequested, Volume.State.Destroy);
+ s_fsm.addTransition(Volume.State.Allocated, Event.DestroyRequested, Volume.State.Destroying);
s_fsm.addTransition(Volume.State.Creating, Event.OperationRetry, Volume.State.Creating);
s_fsm.addTransition(Volume.State.Creating, Event.OperationFailed, Volume.State.Allocated);
s_fsm.addTransition(Volume.State.Creating, Event.OperationSucceeded, Volume.State.Ready);
- s_fsm.addTransition(Volume.State.Creating, Event.DestroyRequested, Volume.State.Destroy);
+ s_fsm.addTransition(Volume.State.Creating, Event.DestroyRequested, Volume.State.Destroying);
s_fsm.addTransition(Volume.State.Creating, Event.CreateRequested, Volume.State.Creating);
s_fsm.addTransition(Volume.State.Allocated, Event.UploadRequested, Volume.State.UploadOp);
s_fsm.addTransition(Volume.State.UploadOp, Event.CopyRequested, Volume.State.Creating);// CopyRequested for volume from sec to primary storage
s_fsm.addTransition(Volume.State.Creating, Event.CopySucceeded, Volume.State.Ready);
s_fsm.addTransition(Volume.State.Creating, Event.CopyFailed, Volume.State.UploadOp);// Copying volume from sec to primary failed.
- s_fsm.addTransition(Volume.State.UploadOp, Event.DestroyRequested, Volume.State.Destroy);
- s_fsm.addTransition(Volume.State.Ready, Event.DestroyRequested, Volume.State.Destroy);
+ s_fsm.addTransition(Volume.State.UploadOp, Event.DestroyRequested, Volume.State.Destroying);
+ s_fsm.addTransition(Volume.State.Ready, Event.DestroyRequested, Volume.State.Destroying);
s_fsm.addTransition(Volume.State.Destroy, Event.ExpungingRequested, Volume.State.Expunging);
s_fsm.addTransition(Volume.State.Ready, Event.SnapshotRequested, Volume.State.Snapshotting);
s_fsm.addTransition(Volume.State.Snapshotting, Event.OperationSucceeded, Volume.State.Ready);
@@ -74,6 +74,9 @@ public class VolumeManagerImpl implements VolumeManager {
s_fsm.addTransition(Volume.State.Migrating, Event.OperationSucceeded, Volume.State.Ready);
s_fsm.addTransition(Volume.State.Migrating, Event.OperationFailed, Volume.State.Ready);
s_fsm.addTransition(Volume.State.Destroy, Event.OperationSucceeded, Volume.State.Destroy);
+ s_fsm.addTransition(Volume.State.Destroying, Event.OperationSucceeded, Volume.State.Destroy);
+ s_fsm.addTransition(Volume.State.Destroying, Event.OperationFailed, Volume.State.Destroying);
+ s_fsm.addTransition(Volume.State.Destroying, Event.DestroyRequested, Volume.State.Destroying);
}
@Override
diff --git a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeObject.java b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeObject.java
index b8c76316e30..a1eeb65b487 100644
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeObject.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeObject.java
@@ -158,4 +158,9 @@ public class VolumeObject implements VolumeInfo {
public String getName() {
return this.volumeVO.getName();
}
+
+ @Override
+ public boolean isAttachedVM() {
+ return (this.volumeVO.getInstanceId() == null) ? false : true;
+ }
}
diff --git a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
index 815033a477a..445e6b3d9b3 100644
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
@@ -98,7 +98,7 @@ public class VolumeServiceImpl implements VolumeService {
dataStore.createVolumeAsync(vo, diskType, caller);
}
- protected Void createVolumeCallback(AsyncCallbackDispatcher callback, CreateVolumeContext context) {
+ public Void createVolumeCallback(AsyncCallbackDispatcher callback, CreateVolumeContext context) {
CommandResult result = callback.getResult();
VolumeObject vo = context.getVolume();
VolumeApiResult volResult = new VolumeApiResult(vo);
@@ -112,11 +112,55 @@ public class VolumeServiceImpl implements VolumeService {
context.getParentCallback().complete(volResult);
return null;
}
+
+ private class DeleteVolumeContext extends AsyncRpcConext {
+ private final VolumeObject volume;
+ /**
+ * @param callback
+ */
+ public DeleteVolumeContext(AsyncCompletionCallback callback, VolumeObject volume) {
+ super(callback);
+ this.volume = volume;
+ }
+
+ public VolumeObject getVolume() {
+ return this.volume;
+ }
+ }
@DB
@Override
public void deleteVolumeAsync(VolumeInfo volume, AsyncCompletionCallback callback) {
+ VolumeObject vo = (VolumeObject)volume;
+ PrimaryDataStore dataStore = vo.getDataStore();
+ vo.stateTransit(Volume.Event.DestroyRequested);
+ if (dataStore == null) {
+ vo.stateTransit(Volume.Event.OperationSucceeded);
+ volDao.remove(vo.getId());
+ return;
+ }
+ DeleteVolumeContext context = new DeleteVolumeContext(callback, vo);
+ AsyncCallbackDispatcher caller = AsyncCallbackDispatcher.create(this);
+ caller.setCallback(caller.getTarget().deleteVolumeCallback(null, null))
+ .setContext(context);
+
+ dataStore.deleteVolumeAsync(volume, caller);
+ }
+
+ public Void deleteVolumeCallback(AsyncCallbackDispatcher callback, DeleteVolumeContext context) {
+ CommandResult result = callback.getResult();
+ VolumeObject vo = context.getVolume();
+ VolumeApiResult apiResult = new VolumeApiResult(vo);
+ if (result.isSuccess()) {
+ vo.stateTransit(Volume.Event.OperationSucceeded);
+ volDao.remove(vo.getId());
+ } else {
+ vo.stateTransit(Volume.Event.OperationFailed);
+ apiResult.setResult(result.getResult());
+ }
+ context.getParentCallback().complete(apiResult);
+ return null;
}
@Override
diff --git a/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageResource.java b/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageResource.java
index 031d0e00e76..7322e02808d 100644
--- a/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageResource.java
+++ b/plugins/hypervisors/xen/src/com/cloud/hypervisor/xen/resource/XenServerStorageResource.java
@@ -34,7 +34,9 @@ import org.apache.cloudstack.storage.command.CopyTemplateToPrimaryStorageCmd;
import org.apache.cloudstack.storage.command.CopyTemplateToPrimaryStorageAnswer;
import org.apache.cloudstack.storage.command.CreatePrimaryDataStoreCmd;
import org.apache.cloudstack.storage.command.CreateVolumeAnswer;
+import org.apache.cloudstack.storage.command.CreateVolumeCommand;
import org.apache.cloudstack.storage.command.CreateVolumeFromBaseImageCommand;
+import org.apache.cloudstack.storage.command.DeleteVolumeCommand;
import org.apache.cloudstack.storage.command.StorageSubSystemCommand;
import org.apache.cloudstack.storage.datastore.protocol.DataStoreProtocol;
import org.apache.cloudstack.storage.to.ImageDataStoreTO;
@@ -72,6 +74,7 @@ import com.xensource.xenapi.PBD;
import com.xensource.xenapi.Pool;
import com.xensource.xenapi.SR;
import com.xensource.xenapi.Types;
+import com.xensource.xenapi.VBD;
import com.xensource.xenapi.Types.BadServerResponse;
import com.xensource.xenapi.Types.XenAPIException;
import com.xensource.xenapi.VDI;
@@ -93,11 +96,96 @@ public class XenServerStorageResource {
return execute((CreatePrimaryDataStoreCmd) command);
} else if (command instanceof CreateVolumeFromBaseImageCommand) {
return execute((CreateVolumeFromBaseImageCommand)command);
+ } else if (command instanceof CreateVolumeCommand) {
+ return execute((CreateVolumeCommand) command);
+ } else if (command instanceof DeleteVolumeCommand) {
+ return execute((DeleteVolumeCommand)command);
}
return new Answer((Command)command, false, "not implemented yet");
}
- public Answer execute(CreateVolumeFromBaseImageCommand cmd) {
+ protected SR getSRByNameLabel(Connection conn, String nameLabel) throws BadServerResponse, XenAPIException, XmlRpcException {
+ Set srs = SR.getByNameLabel(conn, nameLabel);
+ if (srs.size() != 1) {
+ throw new CloudRuntimeException("storage uuid: " + nameLabel + " is not unique");
+ }
+ SR poolsr = srs.iterator().next();
+ return poolsr;
+ }
+
+ protected VDI createVdi(Connection conn, String vdiName, SR sr, long size) throws BadServerResponse, XenAPIException, XmlRpcException {
+ VDI.Record vdir = new VDI.Record();
+ vdir.nameLabel = vdiName;
+ vdir.SR = sr;
+ vdir.type = Types.VdiType.USER;
+
+ vdir.virtualSize = size;
+ VDI vdi = VDI.create(conn, vdir);
+ return vdi;
+ }
+
+ protected void deleteVDI(Connection conn, VDI vdi) throws BadServerResponse, XenAPIException, XmlRpcException {
+ vdi.destroy(conn);
+ }
+
+ protected CreateVolumeAnswer execute(CreateVolumeCommand cmd) {
+ VolumeTO volume = cmd.getVolume();
+ PrimaryDataStoreTO primaryDataStore = volume.getDataStore();
+ Connection conn = hypervisorResource.getConnection();
+ VDI vdi = null;
+ boolean result = false;
+ String errorMsg = null;
+ try {
+ SR primaryDataStoreSR = getSRByNameLabel(conn, primaryDataStore.getUuid());
+ vdi = createVdi(conn, volume.getName(), primaryDataStoreSR, volume.getSize());
+ VDI.Record record = vdi.getRecord(conn);
+ result = true;
+ return new CreateVolumeAnswer(cmd, record.uuid);
+ } catch (BadServerResponse e) {
+ s_logger.debug("Failed to create volume", e);
+ errorMsg = e.toString();
+ } catch (XenAPIException e) {
+ s_logger.debug("Failed to create volume", e);
+ errorMsg = e.toString();
+ } catch (XmlRpcException e) {
+ s_logger.debug("Failed to create volume", e);
+ errorMsg = e.toString();
+ } finally {
+ if (!result && vdi != null) {
+ try {
+ deleteVDI(conn, vdi);
+ } catch (Exception e) {
+ s_logger.debug("Faled to delete vdi: " + vdi.toString());
+ }
+ }
+ }
+
+ return new CreateVolumeAnswer(cmd, false, errorMsg);
+ }
+
+ protected Answer execute(DeleteVolumeCommand cmd) {
+ VolumeTO volume = cmd.getVolume();
+ Connection conn = hypervisorResource.getConnection();
+ String errorMsg = null;
+ try {
+ VDI vdi = VDI.getByUuid(conn, volume.getUuid());
+ deleteVDI(conn, vdi);
+ return new Answer(cmd);
+ } catch (BadServerResponse e) {
+ s_logger.debug("Failed to delete volume", e);
+ errorMsg = e.toString();
+ } catch (XenAPIException e) {
+ s_logger.debug("Failed to delete volume", e);
+ errorMsg = e.toString();
+ } catch (XmlRpcException e) {
+ s_logger.debug("Failed to delete volume", e);
+ errorMsg = e.toString();
+ }
+
+ return new Answer(cmd, false, errorMsg);
+ }
+
+ protected Answer execute(CreateVolumeFromBaseImageCommand cmd) {
VolumeTO volume = cmd.getVolume();
ImageOnPrimayDataStoreTO baseImage = cmd.getImage();
Connection conn = hypervisorResource.getConnection();
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 54d12c97fc9..afee8b03a96 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
@@ -11,11 +11,6 @@ import org.apache.cloudstack.storage.volume.VolumeObject;
public class SolidfirePrimaryDataStoreDriver implements PrimaryDataStoreDriver {
- @Override
- public boolean deleteVolume(VolumeObject vo) {
- // TODO Auto-generated method stub
- return false;
- }
@Override
public String grantAccess(VolumeObject vol, EndPoint ep) {
@@ -77,4 +72,10 @@ public class SolidfirePrimaryDataStoreDriver implements PrimaryDataStoreDriver {
}
+ @Override
+ public void deleteVolumeAsync(VolumeObject vo, AsyncCompletionCallback callback) {
+ // TODO Auto-generated method stub
+
+ }
+
}