From 63113661d1a54853fa4330be22b24cfa93597395 Mon Sep 17 00:00:00 2001 From: Alex Huang Date: Mon, 13 Jun 2011 17:04:16 -0700 Subject: [PATCH] bug 10260: propagate ha and deployment planner fixes --- .../cloud/vm/VirtualMachineManagerImpl.java | 25 +++++++++---------- .../com/cloud/vm/dao/VMInstanceDaoImpl.java | 17 ++++++------- .../src/com/cloud/utils/db/UpdateBuilder.java | 2 +- .../com/cloud/utils/fsm/StateMachine2.java | 7 ++++-- 4 files changed, 25 insertions(+), 26 deletions(-) diff --git a/server/src/com/cloud/vm/VirtualMachineManagerImpl.java b/server/src/com/cloud/vm/VirtualMachineManagerImpl.java index 9822e77d486..9db8d115d6d 100755 --- a/server/src/com/cloud/vm/VirtualMachineManagerImpl.java +++ b/server/src/com/cloud/vm/VirtualMachineManagerImpl.java @@ -912,7 +912,6 @@ public class VirtualMachineManagerImpl implements VirtualMachineManager, Listene @Override public boolean advanceStop(T vm, boolean forced, User user, Account account) throws AgentUnavailableException, OperationTimedoutException, ConcurrentOperationException { - long vmId = vm.getId(); State state = vm.getState(); if (state == State.Stopped) { if (s_logger.isDebugEnabled()) { @@ -927,25 +926,25 @@ public class VirtualMachineManagerImpl implements VirtualMachineManager, Listene } return true; } + + Long hostId = vm.getHostId(); + if (hostId == null) { + try { + stateTransitTo(vm, Event.AgentReportStopped, null, null); + } catch (NoTransitionException e) { + s_logger.warn(e.getMessage()); + } + return true; + } VirtualMachineGuru vmGuru = getVmGuru(vm); try { - if (!stateTransitTo(vm, Event.StopRequested, vm.getHostId())) { + if (!stateTransitTo(vm, forced ? Event.AgentReportStopped : Event.StopRequested, vm.getHostId(), null)) { throw new ConcurrentOperationException("VM is being operated on."); } } catch (NoTransitionException e1) { - if (!forced) { - throw new ConcurrentOperationException("VM is being operated on by someone else."); - } - - vm = vmGuru.findById(vmId); - if (vm == null) { - if (s_logger.isDebugEnabled()) { - s_logger.debug("Unable to find VM " + vmId); - } - return true; - } + throw new CloudRuntimeException("We cannot stop " + vm + " when it is in state " + vm.getState()); } VirtualMachineProfile profile = new VirtualMachineProfileImpl(vm); diff --git a/server/src/com/cloud/vm/dao/VMInstanceDaoImpl.java b/server/src/com/cloud/vm/dao/VMInstanceDaoImpl.java index a92a50191cd..ddfbd4baca8 100644 --- a/server/src/com/cloud/vm/dao/VMInstanceDaoImpl.java +++ b/server/src/com/cloud/vm/dao/VMInstanceDaoImpl.java @@ -207,7 +207,7 @@ public class VMInstanceDaoImpl extends GenericDaoBase implem SearchCriteria sc = HostIdUpTypesSearch.create(); sc.setParameters("hostid", hostid); sc.setParameters("types", (Object[]) types); - sc.setParameters("states", new Object[] {State.Destroyed, State.Stopped, State.Expunging}); + sc.setParameters("states", new Object[] {State.Destroyed, State.Stopped, State.Expunging}); return listBy(sc); } @@ -252,8 +252,7 @@ public class VMInstanceDaoImpl extends GenericDaoBase implem } @Override - public boolean updateState(State oldState, Event event, - State newState, VirtualMachine vm, Long hostId) { + public boolean updateState(State oldState, Event event, State newState, VirtualMachine vm, Long hostId) { if (newState == null) { if (s_logger.isDebugEnabled()) { s_logger.debug("There's no way to transition from old state: " + oldState.toString() + " event: " + event.toString()); @@ -263,6 +262,8 @@ public class VMInstanceDaoImpl extends GenericDaoBase implem VMInstanceVO vmi = (VMInstanceVO)vm; Long oldHostId = vmi.getHostId(); + Long oldUpdated = vmi.getUpdated(); + Date oldUpdateDate = vmi.getUpdateTime(); SearchCriteria sc = StateChangeSearch.create(); sc.setParameters("id", vmi.getId()); @@ -279,15 +280,11 @@ public class VMInstanceDaoImpl extends GenericDaoBase implem int result = update(vmi, sc); if (result == 0 && s_logger.isDebugEnabled()) { - /*update builder will change the state/hostid/updated, even update is failed*/ - vmi.setState(oldState); - vmi.setHostId(oldHostId); - vmi.decrUpdated(); - VMInstanceVO vo = findById(vm.getId()); StringBuilder str = new StringBuilder("Unable to update ").append(vo.toString()); - str.append(": DB Data={Host=").append(vo.getHostId()).append("; State=").append(vo.getState().toString()).append("; updated=").append(vo.getUpdated()); - str.append("} Stale Data: {Host=").append(vm.getHostId()).append("; State=").append(vm.getState().toString()).append("; updated=").append(vmi.getUpdated()).append("}"); + str.append(": DB Data={Host=").append(vo.getHostId()).append("; State=").append(vo.getState().toString()).append("; updated=").append(vo.getUpdated()).append("; time=").append(vo.getUpdateTime()); + str.append("} New Data: {Host=").append(vm.getHostId()).append("; State=").append(vm.getState().toString()).append("; updated=").append(vmi.getUpdated()).append("; time=").append(vo.getUpdateTime()); + str.append("} Stale Data: {Host=").append(oldHostId).append("; State=").append(oldState).append("; updated=").append(oldUpdated).append("; time=").append(oldUpdateDate).append("}"); s_logger.debug(str.toString()); } return result > 0; diff --git a/utils/src/com/cloud/utils/db/UpdateBuilder.java b/utils/src/com/cloud/utils/db/UpdateBuilder.java index 3ce48b912ff..ca4de72bd98 100755 --- a/utils/src/com/cloud/utils/db/UpdateBuilder.java +++ b/utils/src/com/cloud/utils/db/UpdateBuilder.java @@ -126,7 +126,7 @@ public class UpdateBuilder implements MethodInterceptor { return _collectionChanges; } - protected void clear() { + public void clear() { _changes.clear(); if (_collectionChanges != null) { _collectionChanges.clear(); diff --git a/utils/src/com/cloud/utils/fsm/StateMachine2.java b/utils/src/com/cloud/utils/fsm/StateMachine2.java index bac99232d80..d0ab1835486 100644 --- a/utils/src/com/cloud/utils/fsm/StateMachine2.java +++ b/utils/src/com/cloud/utils/fsm/StateMachine2.java @@ -114,12 +114,15 @@ public class StateMachine2> { Long oldHostId = vo.getHostId(); transitionStatus = dao.updateState(currentState, e, nextState, vo, id); + if (!transitionStatus) { + return false; + } for (StateListener listener : _listeners) { listener.postStateTransitionEvent(currentState, e, nextState, vo, transitionStatus, oldHostId); } - - return transitionStatus; + + return true; } public boolean registerListener(StateListener listener) {