You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by ah...@apache.org on 2013/06/25 01:52:21 UTC
[45/50] [abbrv] merge is complete
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
----------------------------------------------------------------------
diff --cc engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
index 56a6651,1d36f93..95ca968
--- a/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
+++ b/engine/storage/volume/src/org/apache/cloudstack/storage/volume/VolumeServiceImpl.java
@@@ -24,15 -25,14 +25,17 @@@ import java.util.Map
import javax.inject.Inject;
+import org.apache.log4j.Logger;
+import org.springframework.stereotype.Component;
+
import org.apache.cloudstack.engine.cloud.entity.api.VolumeEntity;
- import org.apache.cloudstack.engine.subsystem.api.storage.CommandResult;
import org.apache.cloudstack.engine.subsystem.api.storage.CopyCommandResult;
import org.apache.cloudstack.engine.subsystem.api.storage.CreateCmdResult;
+ import org.apache.cloudstack.engine.subsystem.api.storage.DataMotionService;
import org.apache.cloudstack.engine.subsystem.api.storage.DataObject;
import org.apache.cloudstack.engine.subsystem.api.storage.DataStore;
+ import org.apache.cloudstack.engine.subsystem.api.storage.EndPoint;
+ import org.apache.cloudstack.engine.subsystem.api.storage.EndPointSelector;
import org.apache.cloudstack.engine.subsystem.api.storage.ObjectInDataStoreStateMachine.Event;
import org.apache.cloudstack.engine.subsystem.api.storage.SnapshotInfo;
import org.apache.cloudstack.engine.subsystem.api.storage.TemplateInfo;
@@@ -47,14 -49,28 +52,26 @@@ import org.apache.cloudstack.storage.da
import org.apache.cloudstack.storage.datastore.ObjectInDataStoreManager;
import org.apache.cloudstack.storage.datastore.PrimaryDataStore;
import org.apache.cloudstack.storage.datastore.PrimaryDataStoreProviderManager;
- import org.apache.cloudstack.storage.motion.DataMotionService;
+ import org.apache.cloudstack.storage.datastore.db.VolumeDataStoreDao;
+ import org.apache.cloudstack.storage.datastore.db.VolumeDataStoreVO;
+ import org.apache.cloudstack.storage.to.VolumeObjectTO;
-import org.apache.log4j.Logger;
-import org.springframework.stereotype.Component;
+ import com.cloud.agent.api.Answer;
+ import com.cloud.agent.api.storage.ListVolumeAnswer;
+ import com.cloud.agent.api.storage.ListVolumeCommand;
import com.cloud.agent.api.to.VirtualMachineTO;
+ import com.cloud.alert.AlertManager;
+ import com.cloud.configuration.Config;
+ import com.cloud.configuration.Resource.ResourceType;
+ import com.cloud.configuration.dao.ConfigurationDao;
import com.cloud.exception.ConcurrentOperationException;
+ import com.cloud.exception.ResourceAllocationException;
import com.cloud.host.Host;
+ import com.cloud.storage.DataStoreRole;
import com.cloud.storage.StoragePool;
+ import com.cloud.storage.VMTemplateStorageResourceAssoc;
+ import com.cloud.storage.VMTemplateStorageResourceAssoc.Status;
import com.cloud.storage.Volume;
- import com.cloud.storage.Volume.Type;
import com.cloud.storage.VolumeVO;
import com.cloud.storage.dao.VolumeDao;
import com.cloud.storage.snapshot.SnapshotManager;
@@@ -114,16 -143,17 +145,17 @@@ public class VolumeServiceImpl implemen
DataObject volumeOnStore = dataStore.create(volume);
volumeOnStore.processEvent(Event.CreateOnlyRequested);
- CreateVolumeContext<VolumeApiResult> context = new CreateVolumeContext<VolumeApiResult>(null, volumeOnStore, future);
+ CreateVolumeContext<VolumeApiResult> context = new CreateVolumeContext<VolumeApiResult>(null, volumeOnStore,
+ future);
AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> caller = AsyncCallbackDispatcher.create(this);
- caller.setCallback(caller.getTarget().createVolumeCallback(null, null))
- .setContext(context);
+ caller.setCallback(caller.getTarget().createVolumeCallback(null, null)).setContext(context);
-
+
dataStore.getDriver().createAsync(volumeOnStore, caller);
return future;
}
-
+
- protected Void createVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> callback, CreateVolumeContext<VolumeApiResult> context) {
+ protected Void createVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> callback,
+ CreateVolumeContext<VolumeApiResult> context) {
CreateCmdResult result = callback.getResult();
DataObject vo = context.getVolume();
String errMsg = null;
@@@ -172,14 -201,14 +204,14 @@@
future.complete(result);
return future;
}
-
+
- String vmName = null;
- VolumeVO vol = volDao.findById(volume.getId());
- if (vol.getVolumeType() == Type.ROOT && vol.getInstanceId() != null) {
- VirtualMachine vm = vmDao.findByIdIncludingRemoved(vol
- .getInstanceId());
- if (vm != null) {
- vmName = vm.getInstanceName();
+ // Find out if the volume is at state of download_in_progress on secondary storage
+ VolumeDataStoreVO volumeStore = _volumeStoreDao.findByVolume(volume.getId());
+ if (volumeStore != null) {
+ if (volumeStore.getDownloadState() == VMTemplateStorageResourceAssoc.Status.DOWNLOAD_IN_PROGRESS) {
+ s_logger.debug("Volume: " + volume.getName() + " is currently being uploaded; cant' delete it.");
+ future.complete(result);
+ return future;
}
}
@@@ -194,21 -224,20 +227,20 @@@
future.complete(result);
return future;
}
- VolumeObject vo = (VolumeObject)volume;
+ VolumeObject vo = (VolumeObject) volume;
-
+
volume.processEvent(Event.ExpungeRequested);
-
+
-
DeleteVolumeContext<VolumeApiResult> context = new DeleteVolumeContext<VolumeApiResult>(null, vo, future);
AsyncCallbackDispatcher<VolumeServiceImpl, CommandResult> caller = AsyncCallbackDispatcher.create(this);
- caller.setCallback(caller.getTarget().deleteVolumeCallback(null, null))
- .setContext(context);
+ caller.setCallback(caller.getTarget().deleteVolumeCallback(null, null)).setContext(context);
-
+
volume.getDataStore().getDriver().deleteAsync(volume, caller);
return future;
}
-
+
- public Void deleteVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CommandResult> callback, DeleteVolumeContext<VolumeApiResult> context) {
+ public Void deleteVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CommandResult> callback,
+ DeleteVolumeContext<VolumeApiResult> context) {
CommandResult result = callback.getResult();
VolumeObject vo = context.getVolume();
VolumeApiResult apiResult = new VolumeApiResult(vo);
@@@ -231,19 -260,9 +263,9 @@@
@Override
public VolumeEntity getVolumeEntity(long volumeId) {
- VolumeVO vo = volDao.findById(volumeId);
- if (vo == null) {
- return null;
- }
+ return null;
+ }
- if (vo.getPoolId() == null) {
- return new VolumeEntityImpl(VolumeObject.getVolumeObject(null, vo), this);
- } else {
- PrimaryDataStore dataStore = dataStoreMgr.getPrimaryDataStore(vo.getPoolId());
- return new VolumeEntityImpl(dataStore.getVolume(volumeId), this);
- }
- }
-
class CreateBaseImageContext<T> extends AsyncRpcConext<T> {
private final VolumeInfo volume;
private final PrimaryDataStore dataStore;
@@@ -276,31 -296,64 +299,64 @@@
public AsyncCallFuture<VolumeApiResult> getFuture() {
return this.future;
}
-
+
}
-
+
- static class CreateBaseImageResult extends CommandResult {
- final TemplateInfo template;
- public CreateBaseImageResult(TemplateInfo template) {
- super();
- this.template = template;
+ private TemplateInfo waitForTemplateDownloaded(PrimaryDataStore store, TemplateInfo template) {
+ int storagePoolMaxWaitSeconds = NumbersUtil.parseInt(
+ configDao.getValue(Config.StoragePoolMaxWaitSeconds.key()), 3600);
+ int sleepTime = 120;
+ int tries = storagePoolMaxWaitSeconds / sleepTime;
+ while (tries > 0) {
+ TemplateInfo tmpl = store.getTemplate(template.getId());
+ if (tmpl != null) {
+ return tmpl;
- }
++ }
+ try {
+ Thread.sleep(sleepTime * 1000);
+ } catch (InterruptedException e) {
+ s_logger.debug("waiting for template download been interrupted: " + e.toString());
+ }
+ tries--;
}
+ return null;
}
-
+
@DB
- protected void createBaseImageAsync(VolumeInfo volume, PrimaryDataStore dataStore, TemplateInfo template, AsyncCallFuture<VolumeApiResult> future) {
+ protected void createBaseImageAsync(VolumeInfo volume, PrimaryDataStore dataStore, TemplateInfo template,
+ AsyncCallFuture<VolumeApiResult> future) {
-
+
DataObject templateOnPrimaryStoreObj = dataStore.create(template);
CreateBaseImageContext<CreateCmdResult> context = new CreateBaseImageContext<CreateCmdResult>(null, volume,
- dataStore,
- template,
- future, templateOnPrimaryStoreObj);
+ dataStore, template, future, templateOnPrimaryStoreObj);
AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
- caller.setCallback(caller.getTarget().copyBaseImageCallback(null, null))
- .setContext(context);
+ caller.setCallback(caller.getTarget().copyBaseImageCallback(null, null)).setContext(context);
-
+
+ try {
- templateOnPrimaryStoreObj.processEvent(Event.CreateOnlyRequested);
+ templateOnPrimaryStoreObj.processEvent(Event.CreateOnlyRequested);
+ } catch (Exception e) {
+ s_logger.info("Got exception in case of multi-thread");
+ try {
+ templateOnPrimaryStoreObj = waitForTemplateDownloaded(dataStore, template);
+ } catch (Exception e1) {
+ s_logger.debug("wait for template:" + template.getId() + " downloading finished, but failed");
+ VolumeApiResult result = new VolumeApiResult(volume);
+ result.setResult(e1.toString());
+ future.complete(result);
+ return;
+ }
+ if (templateOnPrimaryStoreObj == null) {
+ VolumeApiResult result = new VolumeApiResult(volume);
+ result.setResult("wait for template:" + template.getId() + " downloading finished, but failed");
+ future.complete(result);
+ return;
+ } else {
+ s_logger.debug("waiting for template:" + template.getId() + " downloading finished, success");
+ createVolumeFromBaseImageAsync(volume, templateOnPrimaryStoreObj, dataStore, future);
+ return;
+ }
+ }
-
+
try {
motionSrv.copyAsync(template, templateOnPrimaryStoreObj, caller);
} catch (Exception e) {
@@@ -312,12 -365,13 +368,13 @@@
}
return;
}
-
+
@DB
- protected Void copyBaseImageCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback, CreateBaseImageContext<VolumeApiResult> context) {
+ protected Void copyBaseImageCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback,
+ CreateBaseImageContext<VolumeApiResult> context) {
CopyCommandResult result = callback.getResult();
VolumeApiResult res = new VolumeApiResult(context.getVolume());
-
+
AsyncCallFuture<VolumeApiResult> future = context.getFuture();
DataObject templateOnPrimaryStoreObj = context.destObj;
if (!result.isSuccess()) {
@@@ -326,60 -380,59 +383,59 @@@
future.complete(res);
return null;
}
-
+
- templateOnPrimaryStoreObj.processEvent(Event.OperationSuccessed);
+ templateOnPrimaryStoreObj.processEvent(Event.OperationSuccessed, result.getAnswer());
createVolumeFromBaseImageAsync(context.volume, templateOnPrimaryStoreObj, context.dataStore, future);
return null;
}
-
+
private class CreateVolumeFromBaseImageContext<T> extends AsyncRpcConext<T> {
- private final VolumeObject vo;
+ private final DataObject vo;
private final AsyncCallFuture<VolumeApiResult> future;
- private final DataStore primaryStore;
private final DataObject templateOnStore;
- public CreateVolumeFromBaseImageContext(AsyncCompletionCallback<T> callback, VolumeObject vo,
- DataStore primaryStore,
- DataObject templateOnStore,
- AsyncCallFuture<VolumeApiResult> future) {
+ private final SnapshotInfo snapshot;
+
+ public CreateVolumeFromBaseImageContext(AsyncCompletionCallback<T> callback, DataObject vo,
+ DataStore primaryStore, DataObject templateOnStore, AsyncCallFuture<VolumeApiResult> future,
+ SnapshotInfo snapshot) {
super(callback);
this.vo = vo;
this.future = future;
- this.primaryStore = primaryStore;
this.templateOnStore = templateOnStore;
+ this.snapshot = snapshot;
}
-
+
-
public AsyncCallFuture<VolumeApiResult> getFuture() {
return this.future;
}
}
-
+
@DB
- protected void createVolumeFromBaseImageAsync(VolumeInfo volume, DataObject templateOnPrimaryStore, PrimaryDataStore pd, AsyncCallFuture<VolumeApiResult> future) {
- VolumeObject vo = (VolumeObject)volume;
- CreateVolumeFromBaseImageContext<VolumeApiResult> context = new CreateVolumeFromBaseImageContext<VolumeApiResult>(null, vo, pd, templateOnPrimaryStore, future);
- AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
- caller.setCallback(caller.getTarget().copyBaseImageCallBack(null, null))
- .setContext(context);
-
+ protected void createVolumeFromBaseImageAsync(VolumeInfo volume, DataObject templateOnPrimaryStore,
+ PrimaryDataStore pd, AsyncCallFuture<VolumeApiResult> future) {
DataObject volumeOnPrimaryStorage = pd.create(volume);
- volume.processEvent(Event.CreateOnlyRequested);
+ volumeOnPrimaryStorage.processEvent(Event.CreateOnlyRequested);
+
+ CreateVolumeFromBaseImageContext<VolumeApiResult> context = new CreateVolumeFromBaseImageContext<VolumeApiResult>(
+ null, volumeOnPrimaryStorage, pd, templateOnPrimaryStore, future, null);
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
+ caller.setCallback(caller.getTarget().createVolumeFromBaseImageCallBack(null, null));
+ caller.setContext(context);
motionSrv.copyAsync(context.templateOnStore, volumeOnPrimaryStorage, caller);
return;
}
-
+
@DB
- public Void copyBaseImageCallBack(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback, CreateVolumeFromBaseImageContext<VolumeApiResult> context) {
- VolumeObject vo = context.vo;
+ protected Void createVolumeFromBaseImageCallBack(
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback,
+ CreateVolumeFromBaseImageContext<VolumeApiResult> context) {
+ DataObject vo = context.vo;
CopyCommandResult result = callback.getResult();
- VolumeApiResult volResult = new VolumeApiResult(vo);
+ VolumeApiResult volResult = new VolumeApiResult((VolumeObject) vo);
-
+
if (result.isSuccess()) {
- if (result.getPath() != null) {
- vo.setPath(result.getPath());
- }
- vo.processEvent(Event.OperationSuccessed);
+ vo.processEvent(Event.OperationSuccessed, result.getAnswer());
} else {
vo.processEvent(Event.OperationFailed);
volResult.setResult(result.getResult());
@@@ -396,8 -450,7 +453,7 @@@
PrimaryDataStore pd = dataStoreMgr.getPrimaryDataStore(dataStoreId);
TemplateInfo templateOnPrimaryStore = pd.getTemplate(template.getId());
AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
- VolumeApiResult result = new VolumeApiResult(volume);
-
+
if (templateOnPrimaryStore == null) {
createBaseImageAsync(volume, pd, template, future);
return future;
@@@ -409,9 -462,8 +465,8 @@@
@Override
@DB
- public boolean destroyVolume(long volumeId)
- throws ConcurrentOperationException {
+ public boolean destroyVolume(long volumeId) throws ConcurrentOperationException {
-
+
VolumeInfo vol = volFactory.getVolume(volumeId);
vol.processEvent(Event.DestroyRequested);
snapshotMgr.deletePoliciesForVolume(volumeId);
@@@ -422,55 -474,61 +477,61 @@@
}
@Override
- public AsyncCallFuture<VolumeApiResult> createVolumeFromSnapshot(
- VolumeInfo volume, DataStore store, SnapshotInfo snapshot) {
+ public AsyncCallFuture<VolumeApiResult> createVolumeFromSnapshot(VolumeInfo volume, DataStore store,
+ SnapshotInfo snapshot) {
AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
-
+
try {
- DataObject volumeOnStore = store.create(volume);
+ DataObject volumeOnStore = store.create(volume);
- volume = this.volFactory.getVolume(volume.getId(), store);
- volume.processEvent(Event.CreateOnlyRequested);
- CreateVolumeFromBaseImageContext<VolumeApiResult> context = new CreateVolumeFromBaseImageContext<VolumeApiResult>(null,
- (VolumeObject)volume, store, volumeOnStore, future);
+ volumeOnStore.processEvent(Event.CreateOnlyRequested);
+ snapshot.processEvent(Event.CopyingRequested);
+ CreateVolumeFromBaseImageContext<VolumeApiResult> context = new CreateVolumeFromBaseImageContext<VolumeApiResult>(
+ null, volume, store, volumeOnStore, future, snapshot);
- AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
- caller.setCallback(caller.getTarget().createVolumeFromSnapshotCallback(null, null))
- .setContext(context);
+ caller.setCallback(caller.getTarget().createVolumeFromSnapshotCallback(null, null)).setContext(context);
- motionSrv.copyAsync(snapshot, volumeOnStore, caller);
+ motionSrv.copyAsync(snapshot, volumeOnStore, caller);
} catch (Exception e) {
- s_logger.debug("create volume from snapshot failed", e);
- VolumeApiResult result = new VolumeApiResult(volume);
- result.setResult(e.toString());
- future.complete(result);
+ s_logger.debug("create volume from snapshot failed", e);
+ VolumeApiResult result = new VolumeApiResult(volume);
+ result.setResult(e.toString());
+ future.complete(result);
}
-
+
return future;
}
-
+
- protected Void createVolumeFromSnapshotCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback,
+ protected Void createVolumeFromSnapshotCallback(
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback,
- CreateVolumeFromBaseImageContext<VolumeApiResult> context) {
- CopyCommandResult result = callback.getResult();
+ CreateVolumeFromBaseImageContext<VolumeApiResult> context) {
+ CopyCommandResult result = callback.getResult();
- VolumeInfo volume = context.vo;
+ VolumeInfo volume = (VolumeInfo) context.templateOnStore;
+ SnapshotInfo snapshot = context.snapshot;
- VolumeApiResult apiResult = new VolumeApiResult(volume);
- Event event = null;
- if (result.isFailed()) {
- apiResult.setResult(result.getResult());
- event = Event.OperationFailed;
- } else {
- event = Event.OperationSuccessed;
- }
-
- try {
+ VolumeApiResult apiResult = new VolumeApiResult(volume);
+ Event event = null;
+ if (result.isFailed()) {
+ apiResult.setResult(result.getResult());
+ event = Event.OperationFailed;
+ } else {
+ event = Event.OperationSuccessed;
+ }
+
+ try {
+ if (result.isSuccess()) {
+ volume.processEvent(event, result.getAnswer());
+ } else {
- volume.processEvent(event);
+ volume.processEvent(event);
+ }
+ snapshot.processEvent(event);
- } catch (Exception e) {
- s_logger.debug("create volume from snapshot failed", e);
- apiResult.setResult(e.toString());
- }
-
- AsyncCallFuture<VolumeApiResult> future = context.future;
- future.complete(apiResult);
- return null;
+ } catch (Exception e) {
+ s_logger.debug("create volume from snapshot failed", e);
+ apiResult.setResult(e.toString());
+ }
+
+ AsyncCallFuture<VolumeApiResult> future = context.future;
+ future.complete(apiResult);
+ return null;
}
-
+
protected VolumeVO duplicateVolumeOnAnotherStorage(Volume volume, StoragePool pool) {
Long lastPoolId = volume.getPoolId();
VolumeVO newVol = new VolumeVO(volume);
@@@ -482,8 -540,7 +543,7 @@@
newVol.setPodId(pool.getPodId());
return volDao.persist(newVol);
}
-
+
-
private class CopyVolumeContext<T> extends AsyncRpcConext<T> {
final VolumeInfo srcVolume;
final VolumeInfo destVolume;
@@@ -497,14 -551,135 +554,135 @@@
super(callback);
this.srcVolume = srcVolume;
this.destVolume = destVolume;
- this.destStore = destStore;
this.future = future;
}
-
+
}
+
+ protected AsyncCallFuture<VolumeApiResult> copyVolumeFromImageToPrimary(VolumeInfo srcVolume, DataStore destStore) {
+ AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
+ VolumeApiResult res = new VolumeApiResult(srcVolume);
+ VolumeInfo destVolume = null;
+ try {
+ destVolume = (VolumeInfo) destStore.create(srcVolume);
+ destVolume.processEvent(Event.CopyingRequested);
+ srcVolume.processEvent(Event.CopyingRequested);
-
++
+ CopyVolumeContext<VolumeApiResult> context = new CopyVolumeContext<VolumeApiResult>(null, future,
+ srcVolume, destVolume, destStore);
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
+ caller.setCallback(caller.getTarget().copyVolumeFromImageToPrimaryCallback(null, null)).setContext(context);
+
+ motionSrv.copyAsync(srcVolume, destVolume, caller);
+ return future;
+ } catch (Exception e) {
+ s_logger.error("failed to copy volume from image store", e);
+ if (destVolume != null) {
+ destVolume.processEvent(Event.OperationFailed);
+ }
+
+ srcVolume.processEvent(Event.OperationFailed);
+ res.setResult(e.toString());
- future.complete(res);
- return future;
- }
++ future.complete(res);
++ return future;
++ }
+ }
+
+ protected Void copyVolumeFromImageToPrimaryCallback(
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback,
+ CopyVolumeContext<VolumeApiResult> context) {
+ VolumeInfo srcVolume = context.srcVolume;
+ VolumeInfo destVolume = context.destVolume;
+ CopyCommandResult result = callback.getResult();
+ AsyncCallFuture<VolumeApiResult> future = context.future;
+ VolumeApiResult res = new VolumeApiResult(destVolume);
+ try {
+ if (res.isFailed()) {
+ destVolume.processEvent(Event.OperationFailed);
+ srcVolume.processEvent(Event.OperationFailed);
+ res.setResult(result.getResult());
+ future.complete(res);
+ return null;
+ }
+
+ srcVolume.processEvent(Event.OperationSuccessed);
+ destVolume.processEvent(Event.OperationSuccessed, result.getAnswer());
+ srcVolume.getDataStore().delete(srcVolume);
+ future.complete(res);
+ } catch (Exception e) {
+ res.setResult(e.toString());
+ future.complete(res);
+ }
+ return null;
+ }
+
+
+ protected AsyncCallFuture<VolumeApiResult> copyVolumeFromPrimaryToImage(VolumeInfo srcVolume, DataStore destStore) {
+ AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
+ VolumeApiResult res = new VolumeApiResult(srcVolume);
+ VolumeInfo destVolume = null;
+ try {
+ destVolume = (VolumeInfo)destStore.create(srcVolume);
+ srcVolume.processEvent(Event.MigrationRequested); // this is just used for locking that src volume record in DB to avoid using lock
+ destVolume.processEventOnly(Event.CreateOnlyRequested);
+
+ CopyVolumeContext<VolumeApiResult> context = new CopyVolumeContext<VolumeApiResult>(null, future, srcVolume,
+ destVolume,
+ destStore);
+ AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> caller = AsyncCallbackDispatcher.create(this);
+ caller.setCallback(caller.getTarget().copyVolumeFromPrimaryToImageCallback(null, null))
+ .setContext(context);
+
+ motionSrv.copyAsync(srcVolume, destVolume, caller);
+ return future;
+ } catch (Exception e) {
+ s_logger.error("failed to copy volume to image store", e);
+ if (destVolume != null) {
+ destVolume.getDataStore().delete(destVolume);
+ }
+ srcVolume.processEvent(Event.OperationFailed); // unlock source volume record
+ res.setResult(e.toString());
+ future.complete(res);
+ return future;
+ }
+ }
+
+ protected Void copyVolumeFromPrimaryToImageCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback, CopyVolumeContext<VolumeApiResult> context) {
+ VolumeInfo srcVolume = context.srcVolume;
+ VolumeInfo destVolume = context.destVolume;
+ CopyCommandResult result = callback.getResult();
+ AsyncCallFuture<VolumeApiResult> future = context.future;
+ VolumeApiResult res = new VolumeApiResult(destVolume);
+ try {
+ if (res.isFailed()) {
+ srcVolume.processEvent(Event.OperationFailed); // back to Ready state in Volume table
+ destVolume.processEventOnly(Event.OperationFailed);
+ res.setResult(result.getResult());
+ future.complete(res);
+ }else{
+ srcVolume.processEvent(Event.OperationSuccessed); // back to Ready state in Volume table
+ destVolume.processEventOnly(Event.OperationSuccessed, result.getAnswer());
+ future.complete(res);
+ }
+ } catch (Exception e) {
+ res.setResult(e.toString());
+ future.complete(res);
+ }
+ return null;
+ }
+
+
@Override
- public AsyncCallFuture<VolumeApiResult> copyVolume(VolumeInfo srcVolume,
- DataStore destStore) {
+ public AsyncCallFuture<VolumeApiResult> copyVolume(VolumeInfo srcVolume, DataStore destStore) {
+
+ if (srcVolume.getState() == Volume.State.Uploaded) {
+ return copyVolumeFromImageToPrimary(srcVolume, destStore);
+ }
+
+ if (destStore.getRole() == DataStoreRole.Image) {
+ return copyVolumeFromPrimaryToImage(srcVolume, destStore);
+ }
+
AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
VolumeApiResult res = new VolumeApiResult(srcVolume);
try {
@@@ -536,8 -708,9 +711,9 @@@
}
return future;
}
-
+
- protected Void copyVolumeCallBack(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback, CopyVolumeContext<VolumeApiResult> context) {
+ protected Void copyVolumeCallBack(AsyncCallbackDispatcher<VolumeServiceImpl, CopyCommandResult> callback,
+ CopyVolumeContext<VolumeApiResult> context) {
VolumeInfo srcVolume = context.srcVolume;
VolumeInfo destVolume = context.destVolume;
CopyCommandResult result = callback.getResult();
@@@ -730,85 -901,250 +904,250 @@@
@Override
public AsyncCallFuture<VolumeApiResult> registerVolume(VolumeInfo volume, DataStore store) {
-
+
AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
- VolumeObject vo = (VolumeObject) volume;
+ DataObject volumeOnStore = store.create(volume);
- CreateVolumeContext<VolumeApiResult> context = new CreateVolumeContext<VolumeApiResult>(null, vo, future);
+ volumeOnStore.processEvent(Event.CreateOnlyRequested);
+
+ CreateVolumeContext<VolumeApiResult> context = new CreateVolumeContext<VolumeApiResult>(null, volumeOnStore,
+ future);
AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> caller = AsyncCallbackDispatcher.create(this);
- caller.setCallback(caller.getTarget().registerVolumeCallback(null, null))
- .setContext(context);
+ caller.setCallback(caller.getTarget().registerVolumeCallback(null, null));
+ caller.setContext(context);
-
+
- dataObjectMgr.createAsync(volume, store, caller, true);
+ store.getDriver().createAsync(volumeOnStore, caller);
return future;
}
-
+
- protected Void registerVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> callback, CreateVolumeContext<VolumeApiResult> context) {
+ protected Void registerVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> callback,
+ CreateVolumeContext<VolumeApiResult> context) {
CreateCmdResult result = callback.getResult();
- VolumeObject vo = (VolumeObject)context.volume;
+ try {
+ VolumeObject vo = (VolumeObject) context.volume;
- if (result.isFailed()) {
+ if (result.isFailed()) {
- vo.stateTransit(Volume.Event.OperationFailed);
+ vo.processEvent(Event.OperationFailed);
- } else {
+ } else {
- vo.stateTransit(Volume.Event.OperationSucceeded);
+ vo.processEvent(Event.OperationSuccessed, result.getAnswer());
- }
+ }
+
+ _resourceLimitMgr.incrementResourceCount(vo.getAccountId(), ResourceType.secondary_storage, vo.getSize());
- VolumeApiResult res = new VolumeApiResult(vo);
- context.future.complete(res);
- return null;
+ VolumeApiResult res = new VolumeApiResult(vo);
+ context.future.complete(res);
+ return null;
+ } catch (Exception e) {
+ s_logger.error("register volume failed: ", e);
+ VolumeApiResult res = new VolumeApiResult(null);
+ context.future.complete(res);
+ return null;
+ }
}
-
- @Override
- public AsyncCallFuture<VolumeApiResult> resize(VolumeInfo volume) {
- AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
- VolumeApiResult result = new VolumeApiResult(volume);
- try {
- volume.processEvent(Event.ResizeRequested);
- } catch (Exception e) {
- s_logger.debug("Failed to change state to resize", e);
- result.setResult(e.toString());
- future.complete(result);
- return future;
- }
- CreateVolumeContext<VolumeApiResult> context = new CreateVolumeContext<VolumeApiResult>(null, volume, future);
- AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> caller = AsyncCallbackDispatcher.create(this);
+ @Override
+ public AsyncCallFuture<VolumeApiResult> resize(VolumeInfo volume) {
+ AsyncCallFuture<VolumeApiResult> future = new AsyncCallFuture<VolumeApiResult>();
+ VolumeApiResult result = new VolumeApiResult(volume);
+ try {
+ volume.processEvent(Event.ResizeRequested);
+ } catch (Exception e) {
+ s_logger.debug("Failed to change state to resize", e);
+ result.setResult(e.toString());
+ future.complete(result);
+ return future;
+ }
+ CreateVolumeContext<VolumeApiResult> context = new CreateVolumeContext<VolumeApiResult>(null, volume, future);
+ AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> caller = AsyncCallbackDispatcher.create(this);
caller.setCallback(caller.getTarget().resizeVolumeCallback(caller, context)).setContext(context);
- volume.getDataStore().getDriver().resize(volume, caller);
- return future;
- }
-
+ volume.getDataStore().getDriver().resize(volume, caller);
+ return future;
+ }
+
- protected Void resizeVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> callback, CreateVolumeContext<VolumeApiResult> context) {
+ protected Void resizeVolumeCallback(AsyncCallbackDispatcher<VolumeServiceImpl, CreateCmdResult> callback,
+ CreateVolumeContext<VolumeApiResult> context) {
- CreateCmdResult result = callback.getResult();
- AsyncCallFuture<VolumeApiResult> future = context.future;
+ CreateCmdResult result = callback.getResult();
+ AsyncCallFuture<VolumeApiResult> future = context.future;
- VolumeInfo volume = (VolumeInfo)context.volume;
+ VolumeInfo volume = (VolumeInfo) context.volume;
-
- if (result.isFailed()) {
- try {
- volume.processEvent(Event.OperationFailed);
- } catch (Exception e) {
- s_logger.debug("Failed to change state", e);
- }
- VolumeApiResult res = new VolumeApiResult(volume);
- res.setResult(result.getResult());
- future.complete(res);
- return null;
- }
-
- try {
- volume.processEvent(Event.OperationSuccessed);
+
+ if (result.isFailed()) {
+ try {
+ volume.processEvent(Event.OperationFailed);
+ } catch (Exception e) {
+ s_logger.debug("Failed to change state", e);
+ }
+ VolumeApiResult res = new VolumeApiResult(volume);
+ res.setResult(result.getResult());
+ future.complete(res);
+ return null;
+ }
+
+ try {
+ volume.processEvent(Event.OperationSuccessed);
- } catch(Exception e) {
+ } catch (Exception e) {
- s_logger.debug("Failed to change state", e);
- VolumeApiResult res = new VolumeApiResult(volume);
- res.setResult(result.getResult());
- future.complete(res);
- return null;
- }
-
- VolumeApiResult res = new VolumeApiResult(volume);
- future.complete(res);
-
- return null;
- }
-
+ s_logger.debug("Failed to change state", e);
+ VolumeApiResult res = new VolumeApiResult(volume);
+ res.setResult(result.getResult());
+ future.complete(res);
+ return null;
+ }
+
+ VolumeApiResult res = new VolumeApiResult(volume);
+ future.complete(res);
+
+ return null;
+ }
+
+ @Override
+ public void handleVolumeSync(DataStore store) {
+ if (store == null) {
+ s_logger.warn("Huh? ssHost is null");
+ return;
+ }
+ long storeId = store.getId();
+
+ Map<Long, TemplateProp> volumeInfos = listVolume(store);
+ if (volumeInfos == null) {
+ return;
+ }
+
+ List<VolumeDataStoreVO> dbVolumes = _volumeStoreDao.listByStoreId(storeId);
+ List<VolumeDataStoreVO> toBeDownloaded = new ArrayList<VolumeDataStoreVO>(dbVolumes);
+ for (VolumeDataStoreVO volumeStore : dbVolumes) {
+ VolumeVO volume = _volumeDao.findById(volumeStore.getVolumeId());
+ // Exists then don't download
+ if (volumeInfos.containsKey(volume.getId())) {
+ TemplateProp volInfo = volumeInfos.remove(volume.getId());
+ toBeDownloaded.remove(volumeStore);
+ s_logger.info("Volume Sync found " + volume.getUuid() + " already in the volume image store table");
+ if (volumeStore.getDownloadState() != Status.DOWNLOADED) {
+ volumeStore.setErrorString("");
+ }
+ if (volInfo.isCorrupted()) {
+ volumeStore.setDownloadState(Status.DOWNLOAD_ERROR);
+ String msg = "Volume " + volume.getUuid() + " is corrupted on image store ";
+ volumeStore.setErrorString(msg);
+ s_logger.info("msg");
+ if (volumeStore.getDownloadUrl() == null) {
+ msg = "Volume (" + volume.getUuid() + ") with install path " + volInfo.getInstallPath()
+ + "is corrupted, please check in image store: " + volumeStore.getDataStoreId();
+ s_logger.warn(msg);
+ } else {
+ toBeDownloaded.add(volumeStore);
+ }
+
+ } else { // Put them in right status
+ volumeStore.setDownloadPercent(100);
+ volumeStore.setDownloadState(Status.DOWNLOADED);
+ volumeStore.setInstallPath(volInfo.getInstallPath());
+ volumeStore.setSize(volInfo.getSize());
+ volumeStore.setPhysicalSize(volInfo.getPhysicalSize());
+ volumeStore.setLastUpdated(new Date());
+ _volumeStoreDao.update(volumeStore.getId(), volumeStore);
+
+ if (volume.getSize() == 0) {
+ // Set volume size in volumes table
+ volume.setSize(volInfo.getSize());
+ _volumeDao.update(volumeStore.getVolumeId(), volume);
+ }
+
+ if (volInfo.getSize() > 0) {
+ try {
+ _resourceLimitMgr.checkResourceLimit(_accountMgr.getAccount(volume.getAccountId()),
+ com.cloud.configuration.Resource.ResourceType.secondary_storage, volInfo.getSize()
+ - volInfo.getPhysicalSize());
+ } catch (ResourceAllocationException e) {
+ s_logger.warn(e.getMessage());
+ _alertMgr.sendAlert(AlertManager.ALERT_TYPE_RESOURCE_LIMIT_EXCEEDED,
+ volume.getDataCenterId(), volume.getPodId(), e.getMessage(), e.getMessage());
+ } finally {
+ _resourceLimitMgr.recalculateResourceCount(volume.getAccountId(), volume.getDomainId(),
+ com.cloud.configuration.Resource.ResourceType.secondary_storage.getOrdinal());
+ }
+ }
+ }
+ continue;
+ }
+ // Volume is not on secondary but we should download.
+ if (volumeStore.getDownloadState() != Status.DOWNLOADED) {
+ s_logger.info("Volume Sync did not find " + volume.getName() + " ready on image store " + storeId
+ + ", will request download to start/resume shortly");
+ toBeDownloaded.add(volumeStore);
+ }
+ }
+
+ // Download volumes which haven't been downloaded yet.
+ if (toBeDownloaded.size() > 0) {
+ for (VolumeDataStoreVO volumeHost : toBeDownloaded) {
+ if (volumeHost.getDownloadUrl() == null) { // If url is null we
+ // can't initiate the
+ // download
+ continue;
+ }
+ s_logger.debug("Volume " + volumeHost.getVolumeId() + " needs to be downloaded to " + store.getName());
+ // TODO: pass a callback later
+ VolumeInfo vol = volFactory.getVolume(volumeHost.getVolumeId());
+ createVolumeAsync(vol, store);
+ }
+ }
+
+ // Delete volumes which are not present on DB.
+ for (Long uniqueName : volumeInfos.keySet()) {
+ TemplateProp tInfo = volumeInfos.get(uniqueName);
+
+ //we cannot directly call expungeVolumeAsync here to
+ // reuse delete logic since in this case, our db does not have
+ // this template at all.
+ VolumeObjectTO tmplTO = new VolumeObjectTO();
+ tmplTO.setDataStore(store.getTO());
+ tmplTO.setPath(tInfo.getInstallPath());
+ tmplTO.setId(tInfo.getId());
+ DeleteCommand dtCommand = new DeleteCommand(tmplTO);
+ EndPoint ep = _epSelector.select(store);
+ Answer answer = ep.sendMessage(dtCommand);
+ if (answer == null || !answer.getResult()) {
+ s_logger.info("Failed to deleted volume at store: " + store.getName());
+
+ } else {
+ String description = "Deleted volume " + tInfo.getTemplateName() + " on secondary storage " + storeId;
+ s_logger.info(description);
+ }
+ }
+ }
+
+ private Map<Long, TemplateProp> listVolume(DataStore store) {
+ ListVolumeCommand cmd = new ListVolumeCommand(store.getTO(), store.getUri());
+ EndPoint ep = _epSelector.select(store);
+ Answer answer = ep.sendMessage(cmd);
+ if (answer != null && answer.getResult()) {
+ ListVolumeAnswer tanswer = (ListVolumeAnswer) answer;
+ return tanswer.getTemplateInfo();
+ } else {
+ if (s_logger.isDebugEnabled()) {
+ s_logger.debug("Can not list volumes for image store " + store.getId());
+ }
+ }
+
+ return null;
+ }
+
+ @Override
+ public SnapshotInfo takeSnapshot(VolumeInfo volume) {
+ VolumeObject vol = (VolumeObject) volume;
+ vol.stateTransit(Volume.Event.SnapshotRequested);
-
+
+ SnapshotInfo snapshot = null;
+ try {
+ snapshot = snapshotMgr.takeSnapshot(volume);
+ } catch (Exception e) {
+ s_logger.debug("Take snapshot: " + volume.getId() + " failed: " + e.toString());
+ } finally {
+ if (snapshot != null) {
+ vol.stateTransit(Volume.Event.OperationSucceeded);
+ } else {
+ vol.stateTransit(Volume.Event.OperationFailed);
+ }
+ }
+
+ return snapshot;
+ }
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/framework/ipc/src/org/apache/cloudstack/framework/async/AsyncCallbackDispatcher.java
----------------------------------------------------------------------
diff --cc framework/ipc/src/org/apache/cloudstack/framework/async/AsyncCallbackDispatcher.java
index 8d91f5f,acbc5b6..dbfbd03
--- a/framework/ipc/src/org/apache/cloudstack/framework/async/AsyncCallbackDispatcher.java
+++ b/framework/ipc/src/org/apache/cloudstack/framework/async/AsyncCallbackDispatcher.java
@@@ -22,20 -22,24 +22,24 @@@ package org.apache.cloudstack.framework
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
- import net.sf.cglib.proxy.CallbackFilter;
-import org.apache.log4j.Logger;
-
-import net.sf.cglib.proxy.CallbackFilter;
import net.sf.cglib.proxy.Callback;
++import net.sf.cglib.proxy.CallbackFilter;
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
++import org.apache.log4j.Logger;
++
@SuppressWarnings("rawtypes")
public class AsyncCallbackDispatcher<T, R> implements AsyncCompletionCallback {
+ private static final Logger s_logger = Logger.getLogger(AsyncCallbackDispatcher.class);
+
- private Method _callbackMethod;
- private T _targetObject;
+ private Method _callbackMethod;
- private T _targetObject;
++ private final T _targetObject;
private Object _contextObject;
private Object _resultObject;
- private AsyncCallbackDriver _driver = new InplaceAsyncCallbackDriver();
-
+ private AsyncCallbackDriver _driver = new InplaceAsyncCallbackDriver();
+
private AsyncCallbackDispatcher(T target) {
assert(target != null);
_targetObject = target;
@@@ -55,8 -59,14 +59,13 @@@
@SuppressWarnings("unchecked")
public T getTarget() {
Enhancer en = new Enhancer();
- en.setSuperclass(_targetObject.getClass());
- en.setCallbacks(new Callback[] { new MethodInterceptor() {
-
+ Class<?> clz = _targetObject.getClass();
+ String clzName = clz.getName();
+ if(clzName.contains("EnhancerByCloudStack"))
+ clz = clz.getSuperclass();
+
+ en.setSuperclass(clz);
+ en.setCallbacks(new Callback[]{new MethodInterceptor() {
@Override
public Object intercept(Object arg0, Method arg1, Object[] arg2,
MethodProxy arg3) throws Throwable {
@@@ -74,14 -84,21 +83,22 @@@
}
});
en.setCallbackFilter(new CallbackFilter() {
-- public int accept(Method method) {
++ @Override
++ public int accept(Method method) {
if (method.getParameterTypes().length == 0 && method.getName().equals("finalize")) {
return 1;
}
return 0;
}}
);
+
+ try {
- return (T)en.create();
+ return (T)en.create();
+ } catch(Throwable e) {
+ s_logger.error("Unexpected exception", e);
+ }
+
+ return null;
}
public AsyncCallbackDispatcher<T, R> setCallback(Object useless) {
@@@ -97,8 -114,8 +114,9 @@@
public <P> P getContext() {
return (P)_contextObject;
}
-
- public void complete(Object resultObject) {
+
- public void complete(Object resultObject) {
++ @Override
++ public void complete(Object resultObject) {
_resultObject = resultObject;
_driver.performCompletionCallback(this);
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BareMetalPingServiceImpl.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BareMetalResourceBase.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalDhcpElement.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalDhcpElement.java
index e9d5499,96d702d..6d266fd
--- a/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalDhcpElement.java
+++ b/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalDhcpElement.java
@@@ -173,9 -167,9 +173,10 @@@ public class BaremetalDhcpElement exten
}
@Override
- public boolean configDhcpSupportForSubnet(Network network, NicProfile nic, VirtualMachineProfile<? extends VirtualMachine> vm, DeployDestination dest, ReservationContext context) throws ConcurrentOperationException, InsufficientCapacityException, ResourceUnavailableException {
+ public boolean configDhcpSupportForSubnet(Network network, NicProfile nic, VirtualMachineProfile vm, DeployDestination dest, ReservationContext context)
+ throws ConcurrentOperationException, InsufficientCapacityException, ResourceUnavailableException {
- return false; //To change body of implemented methods use File | Settings | File Templates.
+ //TODO Add support for baremetal
+ return true;
}
@Override
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalDhcpManager.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalDhcpManagerImpl.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalKickStartServiceImpl.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalPxeManager.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalPxeManagerImpl.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalPxeService.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalPxeService.java
index 6a03e88,efdd221..feb23be
--- a/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalPxeService.java
+++ b/plugins/hypervisors/baremetal/src/com/cloud/baremetal/networkservice/BaremetalPxeService.java
@@@ -24,8 -24,11 +24,10 @@@ package com.cloud.baremetal.networkserv
import java.util.List;
+ import org.apache.cloudstack.api.AddBaremetalPxeCmd;
+
import com.cloud.baremetal.database.BaremetalPxeVO;
import com.cloud.deploy.DeployDestination;
-import com.cloud.host.Host;
import com.cloud.uservm.UserVm;
import com.cloud.utils.component.Adapter;
import com.cloud.vm.NicProfile;
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalDhcpCmd.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalDhcpCmd.java
index 0000000,7c56a8a..04c9137
mode 000000,100755..100755
--- a/plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalDhcpCmd.java
+++ b/plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalDhcpCmd.java
@@@ -1,0 -1,155 +1,156 @@@
+ // Licensed to the Apache Software Foundation (ASF) under one
+ // or more contributor license agreements. See the NOTICE file
+ // distributed with this work for additional information
+ // regarding copyright ownership. The ASF licenses this file
+ // to you under the Apache License, Version 2.0 (the
+ // "License"); you may not use this file except in compliance
+ // with the License. You may obtain a copy of the License at
+ //
+ // http://www.apache.org/licenses/LICENSE-2.0
+ //
+ // Unless required by applicable law or agreed to in writing,
+ // software distributed under the License is distributed on an
+ // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ // KIND, either express or implied. See the License for the
+ // specific language governing permissions and limitations
+ // under the License.
+ //
+ // Automatically generated by addcopyright.py at 01/29/2013
+ package org.apache.cloudstack.api;
+
+ import javax.inject.Inject;
+
+ import org.apache.cloudstack.api.APICommand;
+ import org.apache.cloudstack.api.ApiConstants;
+ import org.apache.cloudstack.api.ApiErrorCode;
+ import org.apache.cloudstack.api.BaseAsyncCmd;
+ import org.apache.cloudstack.api.BaseCmd;
+ import org.apache.cloudstack.api.BaseCmd.CommandType;
+ import org.apache.cloudstack.api.response.PhysicalNetworkResponse;
+ import org.apache.cloudstack.api.response.PodResponse;
+ import org.apache.cloudstack.api.Parameter;
+ import org.apache.cloudstack.api.ServerApiException;
++import org.apache.cloudstack.context.CallContext;
++
+ import org.apache.log4j.Logger;
+
+ import com.cloud.baremetal.database.BaremetalDhcpVO;
+ import com.cloud.baremetal.networkservice.BaremetalDhcpManager;
+ import com.cloud.baremetal.networkservice.BaremetalDhcpResponse;
+ import com.cloud.event.EventTypes;
+ import com.cloud.exception.ConcurrentOperationException;
+ import com.cloud.exception.InsufficientCapacityException;
+ import com.cloud.exception.NetworkRuleConflictException;
+ import com.cloud.exception.ResourceAllocationException;
+ import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.user.UserContext;
+ @APICommand(name="addBaremetalDhcp", description="adds a baremetal dhcp server", responseObject = BaremetalDhcpResponse.class)
+ public class AddBaremetalDhcpCmd extends BaseAsyncCmd {
+ private static final String s_name = "addexternaldhcpresponse";
+ public static final Logger s_logger = Logger.getLogger(AddBaremetalDhcpCmd.class);
+
+ @Inject BaremetalDhcpManager mgr;
+
+ /////////////////////////////////////////////////////
+ //////////////// API parameters /////////////////////
+ /////////////////////////////////////////////////////
+ @Parameter(name=ApiConstants.PHYSICAL_NETWORK_ID, type=CommandType.UUID, entityType=PhysicalNetworkResponse.class, required=true, description="the Physical Network ID")
+ private Long physicalNetworkId;
+
+ @Parameter(name=ApiConstants.POD_ID, type=CommandType.UUID, entityType=PodResponse.class, required = true, description="Pod Id")
+ private Long podId;
+
+ @Parameter(name=ApiConstants.DHCP_SERVER_TYPE, type=CommandType.STRING, required = true, description="Type of dhcp device")
+ private String dhcpType;
+
+ @Parameter(name=ApiConstants.URL, type=CommandType.STRING, required = true, description="URL of the external dhcp appliance.")
+ private String url;
+
+ @Parameter(name=ApiConstants.USERNAME, type=CommandType.STRING, required = true, description="Credentials to reach external dhcp device")
+ private String username;
+
+ @Parameter(name=ApiConstants.PASSWORD, type=CommandType.STRING, required = true, description="Credentials to reach external dhcp device")
+ private String password;
+
+ @Override
+ public String getEventType() {
+ return EventTypes.EVENT_BAREMETAL_DHCP_SERVER_ADD;
+ }
+
+ @Override
+ public String getEventDescription() {
+ return "Adding an external DHCP server";
+ }
+
+ @Override
+ public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException,
+ ResourceAllocationException, NetworkRuleConflictException {
+ try {
+ BaremetalDhcpVO vo = mgr.addDchpServer(this);
+ BaremetalDhcpResponse response = mgr.generateApiResponse(vo);
+ response.setObjectName(s_name);
+ response.setResponseName(getCommandName());
+ this.setResponseObject(response);
+ } catch (Exception e) {
+ s_logger.warn("Unable to add external dhcp server with url: " + getUrl(), e);
+ throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.getMessage());
+ }
+ }
+
+ @Override
+ public String getCommandName() {
+ return s_name;
+ }
+
+ @Override
+ public long getEntityOwnerId() {
- return UserContext.current().getCaller().getId();
++ return CallContext.current().getCallingAccount().getId();
+ }
+
+ public Long getPodId() {
+ return podId;
+ }
+
+ public void setPodId(Long podId) {
+ this.podId = podId;
+ }
+
+ public String getDhcpType() {
+ return dhcpType;
+ }
+
+ public void setDhcpType(String dhcpType) {
+ this.dhcpType = dhcpType;
+ }
+
+ public String getUrl() {
+ return url;
+ }
+
+ public void setUrl(String url) {
+ this.url = url;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getPassword() {
+ return password;
+ }
+
+ public void setPassword(String password) {
+ this.password = password;
+ }
+
+ public Long getPhysicalNetworkId() {
+ return physicalNetworkId;
+ }
+
+ public void setPhysicalNetworkId(Long physicalNetworkId) {
+ this.physicalNetworkId = physicalNetworkId;
+ }
+ }
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalPxeCmd.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalPxeCmd.java
index 0000000,e1b39e9..49effca
mode 000000,100755..100755
--- a/plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalPxeCmd.java
+++ b/plugins/hypervisors/baremetal/src/org/apache/cloudstack/api/AddBaremetalPxeCmd.java
@@@ -1,0 -1,148 +1,149 @@@
+ // Licensed to the Apache Software Foundation (ASF) under one
+ // or more contributor license agreements. See the NOTICE file
+ // distributed with this work for additional information
+ // regarding copyright ownership. The ASF licenses this file
+ // to you under the Apache License, Version 2.0 (the
+ // "License"); you may not use this file except in compliance
+ // with the License. You may obtain a copy of the License at
+ //
+ // http://www.apache.org/licenses/LICENSE-2.0
+ //
+ // Unless required by applicable law or agreed to in writing,
+ // software distributed under the License is distributed on an
+ // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ // KIND, either express or implied. See the License for the
+ // specific language governing permissions and limitations
+ // under the License.
+ //
+ // Automatically generated by addcopyright.py at 01/29/2013
+ package org.apache.cloudstack.api;
+
+ import javax.inject.Inject;
+
+ import org.apache.cloudstack.api.APICommand;
+ import org.apache.cloudstack.api.ApiConstants;
+ import org.apache.cloudstack.api.ApiErrorCode;
+ import org.apache.cloudstack.api.BaseAsyncCmd;
+ import org.apache.cloudstack.api.BaseCmd;
+ import org.apache.cloudstack.api.BaseCmd.CommandType;
+ import org.apache.cloudstack.api.response.PhysicalNetworkResponse;
+ import org.apache.cloudstack.api.response.PodResponse;
+ import org.apache.cloudstack.api.Parameter;
+ import org.apache.cloudstack.api.ServerApiException;
++import org.apache.cloudstack.context.CallContext;
++
+ import org.apache.log4j.Logger;
+
+ import com.cloud.baremetal.database.BaremetalPxeVO;
+ import com.cloud.baremetal.networkservice.BaremetalPxeManager;
+ import com.cloud.event.EventTypes;
+ import com.cloud.exception.ConcurrentOperationException;
+ import com.cloud.exception.InsufficientCapacityException;
+ import com.cloud.exception.NetworkRuleConflictException;
+ import com.cloud.exception.ResourceAllocationException;
+ import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.user.UserContext;
+ public class AddBaremetalPxeCmd extends BaseAsyncCmd {
+ private static final String s_name = "addexternalpxeresponse";
+ public static final Logger s_logger = Logger.getLogger(AddBaremetalPxeCmd.class);
+
+ @Inject BaremetalPxeManager pxeMgr;
+ /////////////////////////////////////////////////////
+ //////////////// API parameters /////////////////////
+ /////////////////////////////////////////////////////
+ @Parameter(name=ApiConstants.PHYSICAL_NETWORK_ID, type=CommandType.UUID, entityType=PhysicalNetworkResponse.class, required=true, description="the Physical Network ID")
+ private Long physicalNetworkId;
+
+ @Parameter(name=ApiConstants.POD_ID, type=CommandType.UUID, entityType=PodResponse.class, description="Pod Id")
+ private Long podId;
+
+ @Parameter(name=ApiConstants.URL, type=CommandType.STRING, required = true, description="URL of the external pxe device")
+ private String url;
+
+ @Parameter(name=ApiConstants.PXE_SERVER_TYPE, type=CommandType.STRING, required = true, description="type of pxe device")
+ private String deviceType;
+
+ @Parameter(name=ApiConstants.USERNAME, type=CommandType.STRING, required = true, description="Credentials to reach external pxe device")
+ private String username;
+
+ @Parameter(name=ApiConstants.PASSWORD, type=CommandType.STRING, required = true, description="Credentials to reach external pxe device")
+ private String password;
+
+ @Override
+ public String getEventType() {
+ return EventTypes.EVENT_BAREMETAL_PXE_SERVER_ADD;
+ }
+
+ @Override
+ public String getEventDescription() {
+ return "Adding an external pxe server";
+ }
+
+ @Override
+ public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException,
+ ResourceAllocationException, NetworkRuleConflictException {
+ try {
+ BaremetalPxeVO vo = pxeMgr.addPxeServer(this);
+ } catch (Exception e) {
+ s_logger.warn("Unable to add external pxe server with url: " + getUrl(), e);
+ throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.getMessage());
+ }
+ }
+
+ @Override
+ public String getCommandName() {
+ return s_name;
+ }
+
+ @Override
+ public long getEntityOwnerId() {
- return UserContext.current().getCaller().getId();
++ return CallContext.current().getCallingAccount().getId();
+ }
+
+ public Long getPhysicalNetworkId() {
+ return physicalNetworkId;
+ }
+
+ public void setPhysicalNetworkId(Long physicalNetworkId) {
+ this.physicalNetworkId = physicalNetworkId;
+ }
+
+ public Long getPodId() {
+ return podId;
+ }
+
+ public void setPodId(Long podId) {
+ this.podId = podId;
+ }
+
+ public String getUrl() {
+ return url;
+ }
+
+ public void setUrl(String url) {
+ this.url = url;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getPassword() {
+ return password;
+ }
+
+ public void setPassword(String password) {
+ this.password = password;
+ }
+
+ public String getDeviceType() {
+ return deviceType;
+ }
+
+ public void setDeviceType(String deviceType) {
+ this.deviceType = deviceType;
+ }
+ }
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
index 1d847d1,46003e9..a5548c5
--- a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
+++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/LibvirtComputingResource.java
@@@ -66,11 -73,6 +66,14 @@@ import org.libvirt.DomainSnapshot
import org.libvirt.LibvirtException;
import org.libvirt.NodeInfo;
++import org.apache.cloudstack.storage.command.StorageSubSystemCommand;
++import org.apache.cloudstack.storage.to.PrimaryDataStoreTO;
++import org.apache.cloudstack.storage.to.VolumeObjectTO;
+import org.apache.cloudstack.utils.qemu.QemuImg;
+import org.apache.cloudstack.utils.qemu.QemuImg.PhysicalDiskFormat;
+import org.apache.cloudstack.utils.qemu.QemuImgException;
+import org.apache.cloudstack.utils.qemu.QemuImgFile;
+
import com.cloud.agent.api.Answer;
import com.cloud.agent.api.AttachIsoCommand;
import com.cloud.agent.api.AttachVolumeAnswer;
@@@ -832,6 -842,10 +844,10 @@@ ServerResource
configureVifDrivers(params);
- KVMStorageProcessor storageProcessor = new KVMStorageProcessor(this._storagePoolMgr, this);
++ KVMStorageProcessor storageProcessor = new KVMStorageProcessor(_storagePoolMgr, this);
+ storageProcessor.configure(name, params);
+ storageHandler = new StorageSubsystemCommandHandlerBase(storageProcessor);
+
return true;
}
@@@ -1243,6 -1252,8 +1254,8 @@@
return execute((CheckNetworkCommand) cmd);
} else if (cmd instanceof NetworkRulesVmSecondaryIpCommand) {
return execute((NetworkRulesVmSecondaryIpCommand) cmd);
+ } else if (cmd instanceof StorageSubSystemCommand) {
- return this.storageHandler.handleStorageCommands((StorageSubSystemCommand)cmd);
++ return storageHandler.handleStorageCommands((StorageSubSystemCommand)cmd);
} else if (cmd instanceof PvlanSetupCommand) {
return execute((PvlanSetupCommand) cmd);
} else {
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/OvsVifDriver.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/OvsVifDriver.java
index 3f153a0,951badd..2e23ba6
--- a/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/OvsVifDriver.java
+++ b/plugins/hypervisors/kvm/src/com/cloud/hypervisor/kvm/resource/OvsVifDriver.java
@@@ -93,12 -94,12 +94,12 @@@ public class OvsVifDriver extends VifDr
}
} else if (nic.getBroadcastType() == Networks.BroadcastDomainType.Lswitch) {
s_logger.debug("nic " + nic + " needs to be connected to LogicalSwitch " + logicalSwitchUuid);
- intf.setVirtualPortInterfaceId(nic.getUuid());
+ intf.setVirtualPortInterfaceId(nic.getNicUuid());
String brName = (trafficLabel != null && !trafficLabel.isEmpty()) ? _pifs.get(trafficLabel) : _pifs.get("private");
- intf.defBridgeNet(brName, null, nic.getMac(), getGuestNicModel(guestOsType));
+ intf.defBridgeNet(brName, null, nic.getMac(), getGuestNicModel(guestOsType), networkRateKBps);
}
else {
- intf.defBridgeNet(_bridges.get("guest"), null, nic.getMac(), getGuestNicModel(guestOsType));
+ intf.defBridgeNet(_bridges.get("guest"), null, nic.getMac(), getGuestNicModel(guestOsType), networkRateKBps);
}
} else if (nic.getType() == Networks.TrafficType.Control) {
/* Make sure the network is still there */
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/ovm/src/com/cloud/ovm/hypervisor/OvmResourceBase.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/ovm/src/com/cloud/ovm/hypervisor/OvmResourceBase.java
index 089d46d,59ba001..11fa65c
--- a/plugins/hypervisors/ovm/src/com/cloud/ovm/hypervisor/OvmResourceBase.java
+++ b/plugins/hypervisors/ovm/src/com/cloud/ovm/hypervisor/OvmResourceBase.java
@@@ -123,10 -129,8 +129,9 @@@ import com.cloud.utils.script.Script
import com.cloud.utils.ssh.SSHCmdHelper;
import com.cloud.vm.DiskProfile;
import com.cloud.vm.VirtualMachine;
+import com.cloud.vm.VirtualMachine.PowerState;
import com.cloud.vm.VirtualMachine.State;
import com.trilead.ssh2.SCPClient;
- import com.xensource.xenapi.Types.XenAPIException;
public class OvmResourceBase implements ServerResource, HypervisorResource {
private static final Logger s_logger = Logger.getLogger(OvmResourceBase.class);
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/simulator/src/com/cloud/resource/AgentRoutingResource.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/simulator/src/com/cloud/resource/AgentRoutingResource.java
index 58840c8,8a03c4b..1263d7d
--- a/plugins/hypervisors/simulator/src/com/cloud/resource/AgentRoutingResource.java
+++ b/plugins/hypervisors/simulator/src/com/cloud/resource/AgentRoutingResource.java
@@@ -51,9 -51,8 +51,9 @@@ import com.cloud.hypervisor.Hypervisor.
import com.cloud.network.Networks.RouterPrivateIpStrategy;
import com.cloud.simulator.MockVMVO;
import com.cloud.storage.Storage.StorageResourceType;
- import com.cloud.storage.template.TemplateInfo;
+ import com.cloud.storage.template.TemplateProp;
import com.cloud.utils.Pair;
+import com.cloud.vm.VirtualMachine.PowerState;
import com.cloud.vm.VirtualMachine.State;
public class AgentRoutingResource extends AgentStorageResource {
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/vmware/src/com/cloud/hypervisor/guru/VMwareGuru.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/vmware/src/com/cloud/hypervisor/guru/VMwareGuru.java
index 21ec998,95521e8..60839b1
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/guru/VMwareGuru.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/guru/VMwareGuru.java
@@@ -27,8 -27,11 +27,10 @@@ import java.util.Map
import javax.ejb.Local;
import javax.inject.Inject;
-import org.apache.cloudstack.api.ApiConstants.VMDetails;
-import org.apache.cloudstack.storage.command.CopyCommand;
import org.apache.log4j.Logger;
-import org.springframework.stereotype.Component;
+
++import org.apache.cloudstack.storage.command.CopyCommand;
+
import com.cloud.agent.api.BackupSnapshotCommand;
import com.cloud.agent.api.Command;
import com.cloud.agent.api.CreatePrivateTemplateFromSnapshotCommand;
@@@ -284,9 -291,26 +290,26 @@@ public class VMwareGuru extends Hypervi
cmd instanceof CopyVolumeCommand ||
cmd instanceof CreateVolumeOVACommand ||
cmd instanceof PrepareOVAPackingCommand ||
- cmd instanceof CreateVolumeFromSnapshotCommand) {
+ cmd instanceof CreateVolumeFromSnapshotCommand ||
+ cmd instanceof CopyCommand) {
+ if (cmd instanceof CopyCommand) {
+ CopyCommand cpyCommand = (CopyCommand)cmd;
+ DataTO srcData = cpyCommand.getSrcTO();
+ DataStoreTO srcStoreTO = srcData.getDataStore();
+ DataTO destData = cpyCommand.getDestTO();
+ DataStoreTO destStoreTO = destData.getDataStore();
+
+ if (destData.getObjectType() == DataObjectType.VOLUME && destStoreTO.getRole() == DataStoreRole.Primary &&
+ srcData.getObjectType() == DataObjectType.TEMPLATE && srcStoreTO.getRole() == DataStoreRole.Primary) {
+ needDelegation = false;
+ } else {
- needDelegation = true;
- }
+ needDelegation = true;
+ }
+ } else {
+ needDelegation = true;
+ }
+
+ }
/* Fang: remove this before checking in */
// needDelegation = false;
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/VmwareServerDiscoverer.java
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/7b7db056/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareStorageManagerImpl.java
----------------------------------------------------------------------
diff --cc plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareStorageManagerImpl.java
index 93e6b5f,4ae0f30..887c81d
--- a/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareStorageManagerImpl.java
+++ b/plugins/hypervisors/vmware/src/com/cloud/hypervisor/vmware/manager/VmwareStorageManagerImpl.java
@@@ -25,12 -25,12 +25,23 @@@ import java.rmi.RemoteException
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
--import java.util.Properties;
import java.util.Map;
++import java.util.Properties;
import java.util.UUID;
import org.apache.log4j.Logger;
++import com.vmware.vim25.ManagedObjectReference;
++import com.vmware.vim25.TaskInfo;
++import com.vmware.vim25.VirtualDeviceConfigSpec;
++import com.vmware.vim25.VirtualDeviceConfigSpecOperation;
++import com.vmware.vim25.VirtualDisk;
++import com.vmware.vim25.VirtualLsiLogicController;
++import com.vmware.vim25.VirtualMachineConfigSpec;
++import com.vmware.vim25.VirtualMachineFileInfo;
++import com.vmware.vim25.VirtualMachineGuestOsIdentifier;
++import com.vmware.vim25.VirtualSCSISharing;
++
import com.cloud.agent.api.Answer;
import com.cloud.agent.api.BackupSnapshotAnswer;
import com.cloud.agent.api.BackupSnapshotCommand;
@@@ -46,11 -46,11 +57,10 @@@ import com.cloud.agent.api.RevertToVMSn
import com.cloud.agent.api.RevertToVMSnapshotCommand;
import com.cloud.agent.api.storage.CopyVolumeAnswer;
import com.cloud.agent.api.storage.CopyVolumeCommand;
--import com.cloud.agent.api.storage.PrepareOVAPackingAnswer;
--import com.cloud.agent.api.storage.PrepareOVAPackingCommand;
++import com.cloud.agent.api.storage.CreatePrivateTemplateAnswer;
import com.cloud.agent.api.storage.CreateVolumeOVAAnswer;
import com.cloud.agent.api.storage.CreateVolumeOVACommand;
--import com.cloud.agent.api.storage.CreatePrivateTemplateAnswer;
++import com.cloud.agent.api.storage.PrepareOVAPackingCommand;
import com.cloud.agent.api.storage.PrimaryStorageDownloadAnswer;
import com.cloud.agent.api.storage.PrimaryStorageDownloadCommand;
import com.cloud.agent.api.to.StorageFilerTO;
@@@ -60,7 -60,7 +70,6 @@@ import com.cloud.hypervisor.vmware.mo.D
import com.cloud.hypervisor.vmware.mo.DatastoreMO;
import com.cloud.hypervisor.vmware.mo.HostMO;
import com.cloud.hypervisor.vmware.mo.HypervisorHostHelper;
--import com.cloud.hypervisor.vmware.mo.TaskMO;
import com.cloud.hypervisor.vmware.mo.VirtualMachineMO;
import com.cloud.hypervisor.vmware.mo.VmwareHypervisorHost;
import com.cloud.hypervisor.vmware.util.VmwareContext;
@@@ -76,17 -76,17 +85,6 @@@ import com.cloud.utils.Ternary
import com.cloud.utils.script.Script;
import com.cloud.vm.VirtualMachine;
import com.cloud.vm.snapshot.VMSnapshot;
--import com.vmware.vim25.ManagedObjectReference;
--import com.vmware.vim25.TaskEvent;
--import com.vmware.vim25.TaskInfo;
--import com.vmware.vim25.VirtualDeviceConfigSpec;
--import com.vmware.vim25.VirtualDeviceConfigSpecOperation;
--import com.vmware.vim25.VirtualDisk;
--import com.vmware.vim25.VirtualLsiLogicController;
--import com.vmware.vim25.VirtualMachineConfigSpec;
--import com.vmware.vim25.VirtualMachineFileInfo;
--import com.vmware.vim25.VirtualMachineGuestOsIdentifier;
--import com.vmware.vim25.VirtualSCSISharing;
public class VmwareStorageManagerImpl implements VmwareStorageManager {
private static final Logger s_logger = Logger.getLogger(VmwareStorageManagerImpl.class);
@@@ -111,7 -111,7 +109,7 @@@
//Fang note: use Answer here instead of the PrepareOVAPackingAnswer
@Override
public Answer execute(VmwareHostService hostService, PrepareOVAPackingCommand cmd) {
-- String secStorageUrl = ((PrepareOVAPackingCommand) cmd).getSecondaryStorageUrl();
++ String secStorageUrl = cmd.getSecondaryStorageUrl();
assert (secStorageUrl != null);
String installPath = cmd.getTemplatePath();
String details = null;
@@@ -165,7 -165,7 +163,7 @@@
// Important! we need to sync file system before we can safely use tar to work around a linux kernal bug(or feature)
@Override
public Answer execute(VmwareHostService hostService, CreateVolumeOVACommand cmd) {
-- String secStorageUrl = ((CreateVolumeOVACommand) cmd).getSecondaryStorageUrl();
++ String secStorageUrl = cmd.getSecondaryStorageUrl();
assert (secStorageUrl != null);
String installPath = cmd.getVolPath();
String details = null;
@@@ -1467,8 -1463,8 +1465,4 @@@
return command.execute();
}
}
--
-- private static String getVolumeRelativeDirInSecStroage(long volumeId) {
-- return "volumes/" + volumeId;
-- }
}