Roy Golan has uploaded a new change for review.

Change subject: core: monitoring - Create a VM manager to co-ordinate 
monitoring and commands
......................................................................

core: monitoring - Create a VM manager to co-ordinate monitoring and
commands

Change-Id: I54c6091a3996c23a4b70c7ef89412d34f1b58e34
Signed-off-by: Roy Golan <[email protected]>
---
M 
backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/RemoveVmCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/CreateVmVDSCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/DestroyVmVDSCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HibernateVDSCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HostMonitoring.java
A 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ManagingVmCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/MigrateVDSCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResourceManager.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResumeVDSCommand.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VdsManager.java
A 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmManager.java
M 
backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmsMonitoring.java
12 files changed, 287 insertions(+), 149 deletions(-)


  git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/73/28173/1

diff --git 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/RemoveVmCommand.java
 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/RemoveVmCommand.java
index d14f7b3..e84ff1d 100644
--- 
a/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/RemoveVmCommand.java
+++ 
b/backend/manager/modules/bll/src/main/java/org/ovirt/engine/core/bll/RemoveVmCommand.java
@@ -45,6 +45,7 @@
 import org.ovirt.engine.core.dal.dbbroker.DbFacade;
 import org.ovirt.engine.core.utils.transaction.TransactionMethod;
 import org.ovirt.engine.core.utils.transaction.TransactionSupport;
+import org.ovirt.engine.core.vdsbroker.ResourceManager;
 
 @DisableInPrepareMode
 @LockIdNameAttribute
@@ -118,7 +119,7 @@
         }
 
         removeMemoryVolumes();
-
+        ResourceManager.getInstance().onVmDelete(getVmId());
         return true;
     }
 
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/CreateVmVDSCommand.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/CreateVmVDSCommand.java
index ebaf240..bb885bc 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/CreateVmVDSCommand.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/CreateVmVDSCommand.java
@@ -19,18 +19,13 @@
 import org.ovirt.engine.core.vdsbroker.vdsbroker.CreateVmFromSysPrepVDSCommand;
 import org.ovirt.engine.core.vdsbroker.vdsbroker.VDSGenericException;
 
-public class CreateVmVDSCommand<P extends CreateVmVDSCommandParameters> 
extends VdsIdVDSCommandBase<P> {
+public class CreateVmVDSCommand<P extends CreateVmVDSCommandParameters> 
extends ManagingVmCommand<P> {
     public CreateVmVDSCommand(P parameters) {
         super(parameters);
     }
 
     @Override
-    protected void executeVdsIdCommand() {
-        if (_vdsManager == null) {
-            getVDSReturnValue().setSucceeded(false);
-            return;
-        }
-
+    protected void executeVmCommand() {
         final VM vm = getParameters().getVm();
         vm.setLastStartTime(new Date());
         // if the VM is not suspended, it means that if there is 'hibernation 
volume'
@@ -46,11 +41,11 @@
                     saveSetInitializedToDb(vm.getId());
 
                     vm.setInitialized(true);
-                    vm.setRunOnVds(getVdsId());
+                    vm.setRunOnVds(getParameters().getVdsId());
                     if (clearHibernationVolume) {
                         vm.setHibernationVolHandle(StringUtils.EMPTY);
                     }
-                    
DbFacade.getInstance().getVmDynamicDao().update(vm.getDynamicData());
+                    vmManager.update(vm.getDynamicData());
                 } else {
                     handleCommandResult(command);
                     
ResourceManager.getInstance().RemoveAsyncRunningVm(getParameters().getVmId());
@@ -72,7 +67,7 @@
             // use answer file to run after sysprep.
             CreateVmVDSCommandParameters createVmFromSysPrepParam =
                     new CreateVmVDSCommandParameters(
-                            getVdsId(),
+                            getParameters().getVdsId(),
                             vm);
             
createVmFromSysPrepParam.setSysPrepParams(getParameters().getSysPrepParams());
             return new 
CreateVmFromSysPrepVDSCommand<CreateVmVDSCommandParameters>(createVmFromSysPrepParam);
@@ -121,8 +116,8 @@
     private void handleCommandResult(CreateVDSCommand<?> command) {
         if (!command.getVDSReturnValue().getSucceeded() && 
command.getVDSReturnValue().getExceptionObject() != null) {
             if (command.getVDSReturnValue().getExceptionObject() instanceof 
VDSGenericException) {
-                log.errorFormat("VDS::create Failed creating vm '{0}' in vds = 
{1} : {2} error = {3}",
-                        getParameters().getVm().getName(), getVds().getId(), 
getVds().getName(),
+                log.errorFormat("VDS::create Failed creating vm '{0}' in vds = 
{1} error = {2}",
+                        getParameters().getVm().getName(), 
getParameters().getVdsId(),
                         command.getVDSReturnValue().getExceptionString());
                 getVDSReturnValue().setReturnValue(VMStatus.Down);
                 getVDSReturnValue().setSucceeded(false);
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/DestroyVmVDSCommand.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/DestroyVmVDSCommand.java
index aebb925..42faf01 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/DestroyVmVDSCommand.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/DestroyVmVDSCommand.java
@@ -14,85 +14,81 @@
 import org.ovirt.engine.core.utils.transaction.TransactionSupport;
 import org.ovirt.engine.core.vdsbroker.vdsbroker.DestroyVDSCommand;
 
-public class DestroyVmVDSCommand<P extends DestroyVmVDSCommandParameters> 
extends VdsIdVDSCommandBase<P> {
+public class DestroyVmVDSCommand<P extends DestroyVmVDSCommandParameters> 
extends ManagingVmCommand<P> {
     public DestroyVmVDSCommand(P parameters) {
         super(parameters);
     }
 
     @Override
-    protected void executeVdsIdCommand() {
+    protected void executeVmCommand() {
 
-        if (_vdsManager != null) {
+        final DestroyVmVDSCommandParameters parameters = getParameters();
+        
ResourceManager.getInstance().RemoveAsyncRunningVm(parameters.getVmId());
 
-            final DestroyVmVDSCommandParameters parameters = getParameters();
-            
ResourceManager.getInstance().RemoveAsyncRunningVm(parameters.getVmId());
+        final VM curVm = 
DbFacade.getInstance().getVmDao().get(parameters.getVmId());
+        
curVm.setInterfaces(DbFacade.getInstance().getVmNetworkInterfaceDao().getAllForVm(curVm.getId()));
 
-            final VM curVm = 
DbFacade.getInstance().getVmDao().get(parameters.getVmId());
-            
curVm.setInterfaces(DbFacade.getInstance().getVmNetworkInterfaceDao().getAllForVm(curVm.getId()));
+        DestroyVDSCommand<DestroyVmVDSCommandParameters> vdsBrokerCommand =
+                new 
DestroyVDSCommand<DestroyVmVDSCommandParameters>(parameters);
+        vdsBrokerCommand.execute();
+        if (vdsBrokerCommand.getVDSReturnValue().getSucceeded()) {
+            if (curVm.getStatus() == VMStatus.Down) {
+                getVDSReturnValue().setReturnValue(VMStatus.Down);
+            }
 
-            DestroyVDSCommand<DestroyVmVDSCommandParameters> vdsBrokerCommand =
-                    new 
DestroyVDSCommand<DestroyVmVDSCommandParameters>(parameters);
-            vdsBrokerCommand.execute();
-            if (vdsBrokerCommand.getVDSReturnValue().getSucceeded()) {
-                if (curVm.getStatus() == VMStatus.Down) {
-                    getVDSReturnValue().setReturnValue(VMStatus.Down);
-                }
+            changeStatus(parameters, curVm);
 
-                changeStatus(parameters, curVm);
+            TransactionSupport.executeInNewTransaction(new 
TransactionMethod<Void>() {
+                @Override
+                public Void runInTransaction() {
 
-                TransactionSupport.executeInNewTransaction(new 
TransactionMethod<Void>() {
-                    @Override
-                    public Void runInTransaction() {
-
-                        curVm.guestLogoutTimeTreatmentAfterDestroy();
-                        curVm.setStopReason(getParameters().getReason());
-                        // SaveVmDynamicToDBThreaded(curVm);
-                        
DbFacade.getInstance().getVmDynamicDao().update(curVm.getDynamicData());
-                        
DbFacade.getInstance().getVmStatisticsDao().update(curVm.getStatisticsData());
-                        List<VmNetworkInterface> interfaces = 
curVm.getInterfaces();
-                        if (interfaces != null && interfaces.size() > 0) {
-                            for (VmNetworkInterface ifc : interfaces) {
-                                VmNetworkStatistics stats = 
ifc.getStatistics();
-                                
DbFacade.getInstance().getVmNetworkStatisticsDao().update(stats);
-                            }
+                    curVm.guestLogoutTimeTreatmentAfterDestroy();
+                    curVm.setStopReason(getParameters().getReason());
+                    // SaveVmDynamicToDBThreaded(curVm);
+                    vmManager.update(curVm.getDynamicData());
+                    vmManager.update(curVm.getStatisticsData());
+                    List<VmNetworkInterface> interfaces = 
curVm.getInterfaces();
+                    if (interfaces != null && interfaces.size() > 0) {
+                        for (VmNetworkInterface ifc : interfaces) {
+                            VmNetworkStatistics stats = ifc.getStatistics();
+                            vmManager.update(stats);
                         }
+                    }
+                    synchronized 
(ResourceManager.getInstance().GetVdsManager(parameters.getVdsId()).getLockObj())
 {
                         DbFacade.getInstance()
                                 .getVdsDynamicDao()
-                                .updatePartialVdsDynamicCalc(getVdsId(), 0, 0, 
0,
+                                
.updatePartialVdsDynamicCalc(getParameters().getVdsId(), 0, 0, 0,
                                         -curVm.getVmMemSizeMb(), 
-curVm.getNumOfCpus());
-                        return null;
                     }
-                });
-
-                // if using stop then call to ProcessOnVmStop because
-                // will not be called from UpdateRunTimeInfo
-                if (!parameters.getGracefully()) {
-                    onVmStop(curVm);
+                    return null;
                 }
+            });
 
-                getVDSReturnValue().setReturnValue(curVm.getStatus());
-            } else if 
(vdsBrokerCommand.getVDSReturnValue().getExceptionObject() != null) {
-                log.errorFormat("VDS::destroy Failed destroying vm '{0}' in 
vds = {1} : {2}, error = {3}",
-                        parameters.getVmId(),
-                        getVds().getId(),
-                        getVds().getName(),
-                        vdsBrokerCommand
-                                .getVDSReturnValue().getExceptionString());
-                getVDSReturnValue().setSucceeded(false);
-                
getVDSReturnValue().setExceptionString(vdsBrokerCommand.getVDSReturnValue()
-                        .getExceptionString());
-                
getVDSReturnValue().setExceptionObject(vdsBrokerCommand.getVDSReturnValue()
-                        .getExceptionObject());
-                
getVDSReturnValue().setVdsError(vdsBrokerCommand.getVDSReturnValue().getVdsError());
+            // if using stop then call to ProcessOnVmStop because
+            // will not be called from UpdateRunTimeInfo
+            if (!parameters.getGracefully()) {
+                onVmStop(curVm);
             }
-        } else {
+
+            getVDSReturnValue().setReturnValue(curVm.getStatus());
+        } else if (vdsBrokerCommand.getVDSReturnValue().getExceptionObject() 
!= null) {
+            log.errorFormat("VDS::destroy Failed destroying vm '{0}' in vds = 
{1} , error = {2}",
+                    parameters.getVmId(),
+                    getParameters().getVdsId(),
+                    vdsBrokerCommand
+                            .getVDSReturnValue().getExceptionString());
             getVDSReturnValue().setSucceeded(false);
+            
getVDSReturnValue().setExceptionString(vdsBrokerCommand.getVDSReturnValue()
+                    .getExceptionString());
+            
getVDSReturnValue().setExceptionObject(vdsBrokerCommand.getVDSReturnValue()
+                    .getExceptionObject());
+            
getVDSReturnValue().setVdsError(vdsBrokerCommand.getVDSReturnValue().getVdsError());
         }
     }
 
     private void changeStatus(DestroyVmVDSCommandParameters parameters, VM 
curVm) {
         // do the state transition only if that VM is really running on SRC
-        if (getVdsId().equals(curVm.getRunOnVds())) {
+        if (getParameters().getVdsId().equals(curVm.getRunOnVds())) {
             ResourceManager.getInstance().InternalSetVmStatus(curVm,
                     parameters.getGracefully() ? VMStatus.PoweringDown : 
VMStatus.Down);
         }
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HibernateVDSCommand.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HibernateVDSCommand.java
index e852546..ee379bc 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HibernateVDSCommand.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HibernateVDSCommand.java
@@ -1,35 +1,25 @@
 package org.ovirt.engine.core.vdsbroker;
 
-import org.ovirt.engine.core.common.businessentities.VMStatus;
-import org.ovirt.engine.core.common.businessentities.VmDynamic;
 import org.ovirt.engine.core.common.vdscommands.HibernateVDSCommandParameters;
 import org.ovirt.engine.core.common.vdscommands.VDSReturnValue;
-import org.ovirt.engine.core.dal.dbbroker.DbFacade;
-import org.ovirt.engine.core.utils.transaction.TransactionMethod;
-import org.ovirt.engine.core.utils.transaction.TransactionSupport;
 import org.ovirt.engine.core.vdsbroker.vdsbroker.HibernateBrokerVDSCommand;
 
-public class HibernateVDSCommand<P extends HibernateVDSCommandParameters> 
extends VdsIdVDSCommandBase<P> {
+public class HibernateVDSCommand<P extends HibernateVDSCommandParameters> 
extends ManagingVmCommand<P> {
 
     public HibernateVDSCommand(P parameters) {
         super(parameters);
     }
 
     @Override
-    protected void executeVdsIdCommand() {
-        if (_vdsManager == null) {
-            getVDSReturnValue().setSucceeded(false);
-            return;
-        }
-
+    protected void executeVmCommand() {
         VDSReturnValue retVal = runHibernateBrokerVDSCommand();
         if (retVal.getSucceeded()) {
-            changeVmStatusToSavingState();
+            vmManager.succededToHibernate();
             getVDSReturnValue().setSucceeded(true);
         }
         else {
-            log.errorFormat("Failed to hibernate vm '{0}' in vds = {1} : {2}, 
error = {3}",
-                    getParameters().getVmId(), getVds().getId(), 
getVds().getName(), retVal.getExceptionString());
+            log.errorFormat("Failed to hibernate vm '{0}' in vds = {1} : error 
= {2}",
+                    getParameters().getVmId(), getParameters().getVdsId(), 
retVal.getExceptionString());
             getVDSReturnValue().setSucceeded(false);
             
getVDSReturnValue().setExceptionString(retVal.getExceptionString());
             
getVDSReturnValue().setExceptionObject(retVal.getExceptionObject());
@@ -42,18 +32,5 @@
                 new 
HibernateBrokerVDSCommand<HibernateVDSCommandParameters>(getParameters());
         command.execute();
         return command.getVDSReturnValue();
-    }
-
-    private void changeVmStatusToSavingState() {
-        TransactionSupport.executeInNewTransaction(
-                new TransactionMethod<Object>() {
-                    @Override
-                    public Object runInTransaction() {
-                        VmDynamic vmDynamic = 
DbFacade.getInstance().getVmDynamicDao().get(getParameters().getVmId());
-                        vmDynamic.setStatus(VMStatus.SavingState);
-                        _vdsManager.updateVmDynamic(vmDynamic);
-                        return null;
-                    }
-                });
     }
 }
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HostMonitoring.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HostMonitoring.java
index 048f659..a270d2f 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HostMonitoring.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/HostMonitoring.java
@@ -57,7 +57,6 @@
     private boolean saveVdsStatistics;
     private boolean processHardwareCapsNeeded;
     private boolean refreshedCapabilities = false;
-    private VmsMonitoring vmsMonitoring;
     private static Map<Guid, Long> hostDownTimes = new HashMap<>();
 
     private static final Log log = LogFactory.getLog(HostMonitoring.class);
@@ -67,7 +66,6 @@
         this.vds = vds;
         firstStatus = vds.getStatus();
         this.monitoringStrategy = monitoringStrategy;
-        vmsMonitoring = new VmsMonitoring(vdsManager, vds);
     }
 
     public void refresh() {
@@ -123,7 +121,6 @@
                 saveVdsDynamic = true;
             }
             beforeFirstRefreshTreatment(isVdsUpOrGoingToMaintenance);
-            vmsMonitoring.refreshVmStats();
             updateVirtualMemAndCpu();
         } catch (VDSRecoveringException e) {
             // if PreparingForMaintenance and vds is in install failed keep to
@@ -184,8 +181,6 @@
             saveCpuStatisticsDataToDb();
             saveNumaStatisticsDataToDb();
         }
-
-        vmsMonitoring.saveVmsToDb();
     }
 
     private void saveCpuStatisticsDataToDb() {
@@ -441,8 +436,6 @@
                                     : "unknown");
                 }
             }
-            vmsMonitoring.afterVMsRefreshTreatment();
-
         } catch (IRSErrorException ex) {
             logFailureMessage("ResourceManager::RerunFailedCommand:", ex);
             if (log.isDebugEnabled()) {
@@ -732,12 +725,12 @@
     }
 
     private void updateVirtualMemAndCpu() {
-        if (vmsMonitoring.getMemCommited() != vds.getMemCommited()) {
-            vds.setMemCommited(vmsMonitoring.getMemCommited());
+        if (vdsManager.getMemCommited() != vds.getMemCommited()) {
+            vds.setMemCommited(vdsManager.getMemCommited());
             saveVdsDynamic = true;
         }
-        if (vmsMonitoring.getVmsCoresCount() != vds.getVmsCoresCount()) {
-            vds.setVmsCoresCount(vmsMonitoring.getVmsCoresCount());
+        if (vdsManager.getVmsCoresCount() != vds.getVmsCoresCount()) {
+            vds.setVmsCoresCount(vdsManager.getVmsCoresCount());
             saveVdsDynamic = true;
         }
     }
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ManagingVmCommand.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ManagingVmCommand.java
new file mode 100644
index 0000000..ea47acd
--- /dev/null
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ManagingVmCommand.java
@@ -0,0 +1,24 @@
+package org.ovirt.engine.core.vdsbroker;
+
+import org.ovirt.engine.core.common.vdscommands.VdsAndVmIDVDSParametersBase;
+
+public abstract class ManagingVmCommand<P extends VdsAndVmIDVDSParametersBase> 
extends VDSCommandBase<P> {
+
+    protected final VmManager vmManager;
+
+    public ManagingVmCommand(P parameters) {
+        super(parameters);
+        vmManager = 
ResourceManager.getInstance().getVmManager(parameters.getVmId());
+    }
+
+    protected void executeVDSCommand() {
+        try {
+            vmManager.lock();
+            executeVmCommand();
+        } finally {
+            vmManager.unlock();
+        }
+    }
+
+    protected abstract void executeVmCommand();
+}
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/MigrateVDSCommand.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/MigrateVDSCommand.java
index ec0bc0d..dbbe963 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/MigrateVDSCommand.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/MigrateVDSCommand.java
@@ -11,7 +11,7 @@
 import org.ovirt.engine.core.utils.log.LogFactory;
 import org.ovirt.engine.core.vdsbroker.vdsbroker.MigrateBrokerVDSCommand;
 
-public class MigrateVDSCommand<P extends MigrateVDSCommandParameters> extends 
VdsIdVDSCommandBase<P> {
+public class MigrateVDSCommand<P extends MigrateVDSCommandParameters> extends 
ManagingVmCommand<P> {
 
     private static final Log log = LogFactory.getLog(MigrateVDSCommand.class);
 
@@ -20,12 +20,7 @@
     }
 
     @Override
-    protected void executeVdsIdCommand() {
-        if (_vdsManager == null) {
-            getVDSReturnValue().setSucceeded(false);
-            return;
-        }
-
+    protected void executeVmCommand() {
         MigrateBrokerVDSCommand<?> command = new 
MigrateBrokerVDSCommand<>(getParameters());
         command.execute();
         VDSReturnValue vdsReturnValue = command.getVDSReturnValue();
@@ -34,11 +29,9 @@
 
         if (vdsReturnValue.getSucceeded()) {
             
ResourceManager.getInstance().AddAsyncRunningVm(getParameters().getVmId());
-
             ResourceManager.getInstance().InternalSetVmStatus(vm, 
VMStatus.MigratingFrom);
             vm.setMigratingToVds(getParameters().getDstVdsId());
-            getVmDynamicDAO().update(vm.getDynamicData());
-
+            vmManager.update(vm.getDynamicData());
             getVDSReturnValue().setReturnValue(VMStatus.MigratingFrom);
         } else {
             log.error("Failed Vm migration");
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResourceManager.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResourceManager.java
index 79a239c..27c55c1 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResourceManager.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResourceManager.java
@@ -52,6 +52,7 @@
     private final Map<Guid, VdsManager> vdsManagersDict = new 
ConcurrentHashMap<>();
     private final Set<Guid> asyncRunningVms =
             Collections.newSetFromMap(new ConcurrentHashMap<Guid, Boolean>());
+    private ConcurrentHashMap<Guid, VmManager> vmManagers;
 
     private static final String VDSCommandPrefix = "VDSCommand";
 
@@ -424,4 +425,12 @@
 
         return null;
     }
+
+    public VmManager getVmManager(Guid vmId) {
+        return vmManagers.putIfAbsent(vmId, new VmManager(vmId));
+    }
+
+    public void onVmDelete(Guid vmId) {
+        vmManagers.remove(vmId);
+    }
 }
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResumeVDSCommand.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResumeVDSCommand.java
index 55514e4..1a8ed89 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResumeVDSCommand.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/ResumeVDSCommand.java
@@ -7,35 +7,31 @@
 import org.ovirt.engine.core.utils.log.LogFactory;
 import org.ovirt.engine.core.vdsbroker.vdsbroker.ResumeBrokerVDSCommand;
 
-public class ResumeVDSCommand<P extends ResumeVDSCommandParameters> extends 
VdsIdVDSCommandBase<P> {
+public class ResumeVDSCommand<P extends ResumeVDSCommandParameters> extends 
ManagingVmCommand<P> {
     public ResumeVDSCommand(P parameters) {
         super(parameters);
     }
 
     @Override
-    protected void executeVdsIdCommand() {
+    protected void executeVmCommand() {
         ResumeVDSCommandParameters parameters = getParameters();
-        if (_vdsManager != null) {
-            VMStatus retval = VMStatus.Unknown;
-            ResumeBrokerVDSCommand<VdsAndVmIDVDSParametersBase> command =
-                    new 
ResumeBrokerVDSCommand<VdsAndVmIDVDSParametersBase>(parameters);
-            command.execute();
-            if (command.getVDSReturnValue().getSucceeded()) {
-                retval = VMStatus.PoweringUp;
-                
ResourceManager.getInstance().AddAsyncRunningVm(parameters.getVmId());
-            } else if (command.getVDSReturnValue().getExceptionObject() != 
null) {
-                log.errorFormat("VDS::pause Failed resume vm '{0}' in vds = 
{1} : {2}, error = {3}", parameters
-                        .getVmId(), getVds().getId(), getVds().getName(), 
command.getVDSReturnValue()
-                        .getExceptionString());
-                getVDSReturnValue().setSucceeded(false);
-                
getVDSReturnValue().setExceptionString(command.getVDSReturnValue().getExceptionString());
-                
getVDSReturnValue().setExceptionObject(command.getVDSReturnValue().getExceptionObject());
-                
getVDSReturnValue().setVdsError(command.getVDSReturnValue().getVdsError());
-            }
-            getVDSReturnValue().setReturnValue(retval);
-        } else {
+        VMStatus retval = VMStatus.Unknown;
+        ResumeBrokerVDSCommand<VdsAndVmIDVDSParametersBase> command =
+                new 
ResumeBrokerVDSCommand<VdsAndVmIDVDSParametersBase>(parameters);
+        command.execute();
+        if (command.getVDSReturnValue().getSucceeded()) {
+            retval = VMStatus.PoweringUp;
+            
ResourceManager.getInstance().AddAsyncRunningVm(parameters.getVmId());
+        } else if (command.getVDSReturnValue().getExceptionObject() != null) {
+            log.errorFormat("VDS::pause Failed resume vm '{0}' in vds = {1} 
error = {2}", parameters
+                    .getVmId(), getParameters().getVdsId(), 
command.getVDSReturnValue()
+                    .getExceptionString());
             getVDSReturnValue().setSucceeded(false);
+            
getVDSReturnValue().setExceptionString(command.getVDSReturnValue().getExceptionString());
+            
getVDSReturnValue().setExceptionObject(command.getVDSReturnValue().getExceptionObject());
+            
getVDSReturnValue().setVdsError(command.getVDSReturnValue().getVdsError());
         }
+        getVDSReturnValue().setReturnValue(retval);
     }
 
     private static final Log log = LogFactory.getLog(ResumeVDSCommand.class);
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VdsManager.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VdsManager.java
index 0661c72..91ea671 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VdsManager.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VdsManager.java
@@ -71,6 +71,7 @@
     private long updateStartTime;
     private long nextMaintenanceAttemptTime;
     private String onTimerJobId;
+    private String vmsMonitoringJobId;
     private int refreshIteration = 1;
     private boolean isSetNonOperationalExecuted;
     private MonitoringStrategy monitoringStrategy;
@@ -79,6 +80,8 @@
     private IVdsServer vdsProxy;
     private boolean mBeforeFirstRefresh = true;
     private HostMonitoring hostMonitoring;
+    private AtomicInteger memCommited;
+    private AtomicInteger vmsCoresCount;
 
     private VdsManager(VDS vds) {
         log.info("Entered VdsManager constructor");
@@ -139,6 +142,16 @@
                 sched.scheduleAFixedDelayJob(
                         this,
                         "onTimer",
+                        new Class[0],
+                        new Object[0],
+                        refreshRate,
+                        refreshRate,
+                        TimeUnit.MILLISECONDS);
+
+        vmsMonitoringJobId =
+                sched.scheduleAFixedDelayJob(
+                        this,
+                        "vmsMonitoring",
                         new Class[0],
                         new Object[0],
                         refreshRate,
@@ -238,6 +251,11 @@
                 
LockManagerFactory.getLockManager().releaseLock(monitoringLock);
             }
         }
+    }
+
+    @OnTimerMethodAnnotation("vmsMonitoring")
+    public void vmsMonitoring() {
+        new VmsMonitoring(this, vds).begin();
     }
 
     private void logFailureMessage(RuntimeException ex) {
@@ -660,9 +678,15 @@
         return true;
     }
 
+    protected void updateMetrics(int memCommited, int vmsCoresCount) {
+        this.memCommited.set(memCommited);
+        this.vmsCoresCount.set(vmsCoresCount);
+    }
+
     public void dispose() {
         log.info("vdsManager::disposing");
         SchedulerUtilQuartzImpl.getInstance().deleteJob(onTimerJobId);
+        SchedulerUtilQuartzImpl.getInstance().deleteJob(vmsMonitoringJobId);
         XmlRpcUtils.shutDownConnection(((VdsServerWrapper) 
vdsProxy).getHttpClient());
     }
 
@@ -791,4 +815,12 @@
     public void setbeforeFirstRefresh(boolean value) {
         mBeforeFirstRefresh = value;
     }
+
+    public int getMemCommited() {
+        return this.memCommited.get();
+    }
+
+    public int getVmsCoresCount() {
+        return this.vmsCoresCount.get();
+    }
 }
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmManager.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmManager.java
new file mode 100644
index 0000000..1569ca0
--- /dev/null
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmManager.java
@@ -0,0 +1,79 @@
+package org.ovirt.engine.core.vdsbroker;
+
+import org.ovirt.engine.core.common.businessentities.VMStatus;
+import org.ovirt.engine.core.common.businessentities.VmDynamic;
+import org.ovirt.engine.core.common.businessentities.VmStatistics;
+import 
org.ovirt.engine.core.common.businessentities.network.VmNetworkStatistics;
+import org.ovirt.engine.core.compat.Guid;
+import org.ovirt.engine.core.dal.dbbroker.DbFacade;
+import org.ovirt.engine.core.dao.VmDynamicDAO;
+import org.ovirt.engine.core.dao.VmStatisticsDAO;
+import org.ovirt.engine.core.dao.network.VmNetworkStatisticsDao;
+import org.ovirt.engine.core.utils.transaction.TransactionMethod;
+import org.ovirt.engine.core.utils.transaction.TransactionSupport;
+
+import java.util.concurrent.locks.ReentrantLock;
+
+public class VmManager {
+
+    private Guid id;
+    private final ReentrantLock lock = new ReentrantLock();
+
+    public VmManager(Guid id) {
+        this.id = id;
+    }
+
+    public void succededToHibernate() {
+        TransactionSupport.executeInNewTransaction(
+                new TransactionMethod<Object>() {
+                    @Override
+                    public Object runInTransaction() {
+                        VmDynamic vmDynamic = db().getVmDynamicDao().get(id);
+                        vmDynamic.setStatus(VMStatus.SavingState);
+                        update(vmDynamic);
+                        return null;
+                    }
+                }
+                );
+    }
+
+    public void lock() {
+        lock.lock();
+    }
+
+    public void unlock() {
+        lock.unlock();
+    }
+
+    public boolean trylock() {
+        return lock.tryLock();
+    }
+
+    public void update(VmDynamic dynamic) {
+        getVmDynamicDao().update(dynamic);
+    }
+
+    public void update(VmStatistics statistics) {
+        getVmStatisticsDao().update(statistics);
+    }
+
+    public void update(VmNetworkStatistics networkStatistics) {
+        getVmNetworkStatisticsDao().update(networkStatistics);
+    }
+
+    private VmDynamicDAO getVmDynamicDao() {
+        return db().getVmDynamicDao();
+    }
+
+    private VmStatisticsDAO getVmStatisticsDao() {
+        return db().getVmStatisticsDao();
+    }
+
+    private VmNetworkStatisticsDao getVmNetworkStatisticsDao() {
+        return db().getVmNetworkStatisticsDao();
+    }
+
+    protected DbFacade db() {
+        return DbFacade.getInstance();
+    }
+}
diff --git 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmsMonitoring.java
 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmsMonitoring.java
index de38dfd..7ff8692 100644
--- 
a/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmsMonitoring.java
+++ 
b/backend/manager/modules/vdsbroker/src/main/java/org/ovirt/engine/core/vdsbroker/VmsMonitoring.java
@@ -77,6 +77,7 @@
     private VdsManager vdsManager;
     private final Map<Guid, VM> vmDict;
     private Map<Guid, VmInternalData> runningVms;
+    private Map<Guid, VmManager> vmManagers;
 
     private int memCommited;
     private int vmsCoresCount;
@@ -123,15 +124,49 @@
         this.vds = vds;
         this.vdsManager = vdsManager;
         this.vmDict = getDbFacade().getVmDao().getAllRunningByVds(vds.getId());
+        vmManagers = new HashMap<>(vmDict.size()); // max size is the one's 
that in the db
     }
 
-    public void refreshVmStats() {
+    public void begin() {
+        try {
+            lockVmsManager();
+            refreshVmStats();
+            saveVmsToDb();
+            afterVMsRefreshTreatment();
+            vdsManager.updateMetrics(memCommited, vmsCoresCount);
+        } finally {
+            unlockVmsManager();
+        }
+
+    }
+
+    private void lockVmsManager() {
+        for (Guid vmId : vmDict.keySet()) {
+            VmManager vmManager = 
ResourceManager.getInstance().getVmManager(vmId);
+            if (!vmManager.trylock()) {
+                // if we can't hold this vm lock than skip this monitoring 
cycle for it.
+                // so remove it from both vmDict and the list returned from 
vdsm
+                vmManagers.put(vmId, vmManager);
+            }
+        }
+    }
+
+    private void unlockVmsManager() {
+        for (VmManager vmManager : vmManagers.values()) {
+            vmManager.unlock();
+        }
+    }
+
+    private void refreshVmStats() {
         log.debug("refresh VMs list entered");
 
         if (fetchRunningVms()) {
             // refreshCommitedMemory must be called before we modify 
runningVms, because
             // we iterate over it there, assuming it is the same as it was 
received from VDSM
             refreshCommitedMemory();
+
+            filterVmsFromMonitoringCycle();
+
             List<Guid> staleRunningVms = checkVmsStatusChanged();
 
             proceedWatchdogEvents();
@@ -161,13 +196,29 @@
 
             updateLunDisks();
         }
+        saveVmsToDb();
+    }
+
+    /**
+     * if we can't hold this VM lock we filter it out and
+     * so we don't try to detect state-transition and so on.
+     * - VMs which are anyway not exist in db should never be filtered out
+     * - metrics calculation like memCommited and vmsCoresCount should be 
calculated *before*
+     *   this filtering.
+     */
+    private void filterVmsFromMonitoringCycle() {
+        for (Guid vmId : runningVms.keySet()) {
+            if (!vmManagers.containsKey(vmId)) {
+                runningVms.remove(vmId);
+            }
+        }
     }
 
     /**
      * fetch running VMs and populate the internal structure. if we fail, 
handle the error
      * @return true if we could get vms otherwise false
      */
-    public boolean fetchRunningVms() {
+    protected boolean fetchRunningVms() {
         VDSCommandType commandType =
                 vdsManager.getRefreshStatistics()
                         ? VDSCommandType.GetAllVmStats
@@ -753,7 +804,7 @@
         }
     }
 
-    void saveVmsToDb() {
+    private void saveVmsToDb() {
         
getDbFacade().getVmDynamicDao().updateAllInBatch(vmDynamicToSave.values());
         
getDbFacade().getVmStatisticsDao().updateAllInBatch(vmStatisticsToSave.values());
 
@@ -773,7 +824,7 @@
         getVdsEventListener().addExternallyManagedVms(externalVmsToAdd);
     }
 
-    void afterVMsRefreshTreatment() {
+    private void afterVMsRefreshTreatment() {
         // rerun all vms from rerun list
         for (Guid vm_guid : vmsToRerun) {
             log.errorFormat("Rerun vm {0}. Called from vds {1}", vm_guid, 
vds.getName());
@@ -1473,13 +1524,5 @@
 
     protected IVdsEventListener getVdsEventListener() {
         return ResourceManager.getInstance().getEventListener();
-    }
-
-    public int getMemCommited() {
-        return memCommited;
-    }
-
-    public int getVmsCoresCount() {
-        return vmsCoresCount;
     }
 }


-- 
To view, visit http://gerrit.ovirt.org/28173
To unsubscribe, visit http://gerrit.ovirt.org/settings

Gerrit-MessageType: newchange
Gerrit-Change-Id: I54c6091a3996c23a4b70c7ef89412d34f1b58e34
Gerrit-PatchSet: 1
Gerrit-Project: ovirt-engine
Gerrit-Branch: master
Gerrit-Owner: Roy Golan <[email protected]>
_______________________________________________
Engine-patches mailing list
[email protected]
http://lists.ovirt.org/mailman/listinfo/engine-patches

Reply via email to