summaryrefslogtreecommitdiff
path: root/src/VBox/Main/src-server/HostPower.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/VBox/Main/src-server/HostPower.cpp')
-rw-r--r--src/VBox/Main/src-server/HostPower.cpp144
1 files changed, 82 insertions, 62 deletions
diff --git a/src/VBox/Main/src-server/HostPower.cpp b/src/VBox/Main/src-server/HostPower.cpp
index 830729a0..3146a7ae 100644
--- a/src/VBox/Main/src-server/HostPower.cpp
+++ b/src/VBox/Main/src-server/HostPower.cpp
@@ -4,7 +4,7 @@
*/
/*
- * Copyright (C) 2006-2007 Oracle Corporation
+ * Copyright (C) 2006-2013 Oracle Corporation
*
* This file is part of VirtualBox Open Source Edition (OSE), as
* available from http://www.virtualbox.org. This file is free software;
@@ -26,10 +26,11 @@
#include <VBox/com/ptr.h>
#include "VirtualBoxImpl.h"
+#include "MachineImpl.h"
#include <iprt/mem.h>
-HostPowerService::HostPowerService (VirtualBox *aVirtualBox)
+HostPowerService::HostPowerService(VirtualBox *aVirtualBox)
{
Assert(aVirtualBox != NULL);
mVirtualBox = aVirtualBox;
@@ -39,18 +40,18 @@ HostPowerService::~HostPowerService()
{
}
-void HostPowerService::notify(HostPowerEvent aEvent)
+void HostPowerService::notify(Reason_T aReason)
{
SessionMachinesList machines;
VirtualBox::InternalControlList controls;
HRESULT rc = S_OK;
- switch (aEvent)
+ switch (aReason)
{
- case HostPowerEvent_Suspend:
+ case Reason_HostSuspend:
{
- LogFunc (("SUSPEND\n"));
+ LogFunc(("HOST SUSPEND\n"));
#ifdef VBOX_WITH_RESOURCE_USAGE_API
/* Suspend performance sampling to avoid unnecessary callbacks due to jumps in time. */
@@ -68,49 +69,41 @@ void HostPowerService::notify(HostPowerEvent aEvent)
{
ComPtr<IInternalSessionControl> pControl = *it;
- /* get the remote console */
- ComPtr<IConsole> console;
- rc = pControl->GetRemoteConsole(console.asOutParam());
- /* the VM could have been powered down and closed or whatever */
- if (FAILED(rc))
- continue;
-
- /* note that Pause() will simply return a failure if the VM is
- * in an inappropriate state */
- rc = console->Pause();
+ /* PauseWithReason() will simply return a failure if
+ * the VM is in an inappropriate state */
+ rc = pControl->PauseWithReason(Reason_HostSuspend);
if (FAILED(rc))
continue;
/* save the control to un-pause the VM later */
- mConsoles.push_back(console);
+ mSessionControls.push_back(pControl);
}
- LogFunc (("Suspended %d VMs\n", mConsoles.size()));
-
+ LogRel(("Host suspending: Paused %d VMs\n", mSessionControls.size()));
break;
}
- case HostPowerEvent_Resume:
+ case Reason_HostResume:
{
- LogFunc (("RESUME\n"));
+ LogFunc(("HOST RESUME\n"));
size_t resumed = 0;
/* go through VMs we paused on Suspend */
- for (size_t i = 0; i < mConsoles.size(); ++i)
+ for (size_t i = 0; i < mSessionControls.size(); ++i)
{
/* note that Resume() will simply return a failure if the VM is
* in an inappropriate state (it will also fail if the VM has
* been somehow closed by this time already so that the
* console reference we have is dead) */
- rc = mConsoles[i]->Resume();
+ rc = mSessionControls[i]->ResumeWithReason(Reason_HostResume);
if (FAILED(rc))
continue;
- ++ resumed;
+ ++resumed;
}
- LogFunc (("Resumed %d VMs\n", resumed));
+ LogRel(("Host resumed: Resumed %d VMs\n", resumed));
#ifdef VBOX_WITH_RESOURCE_USAGE_API
/* Resume the performance sampling. */
@@ -120,60 +113,87 @@ void HostPowerService::notify(HostPowerEvent aEvent)
perfcollector->resumeSampling();
#endif
- mConsoles.clear();
-
+ mSessionControls.clear();
break;
}
- case HostPowerEvent_BatteryLow:
+ case Reason_HostBatteryLow:
{
- LogFunc (("BATTERY LOW\n"));
+ LogFunc(("BATTERY LOW\n"));
- mVirtualBox->getOpenedMachines(machines, &controls);
+ Bstr value;
+ rc = mVirtualBox->GetExtraData(Bstr("VBoxInternal2/SavestateOnBatteryLow").raw(),
+ value.asOutParam());
+ int fGlobal = 0;
+ if (SUCCEEDED(rc) && !value.isEmpty())
+ {
+ if (value != "0")
+ fGlobal = 1;
+ else if (value == "0")
+ fGlobal = -1;
+ }
+ mVirtualBox->getOpenedMachines(machines, &controls);
size_t saved = 0;
/* save running VMs */
+ SessionMachinesList::const_iterator it2 = machines.begin();
for (VirtualBox::InternalControlList::const_iterator it = controls.begin();
- it != controls.end();
- ++it)
+ it != controls.end() && it2 != machines.end();
+ ++it, ++it2)
{
- ComPtr<IInternalSessionControl> pControl = *it;
- /* get the remote console */
- ComPtr<IConsole> console;
- rc = pControl->GetRemoteConsole (console.asOutParam());
- /* the VM could have been powered down and closed or whatever */
- if (FAILED(rc))
- continue;
-
- ComPtr<IProgress> progress;
-
- /* note that SaveState() will simply return a failure if the VM
- * is in an inappropriate state */
- rc = console->SaveState (progress.asOutParam());
- if (FAILED(rc))
- continue;
-
- /* Wait until the operation has been completed. */
- rc = progress->WaitForCompletion(-1);
- if (SUCCEEDED(rc))
+ ComPtr<SessionMachine> pMachine = *it2;
+ rc = pMachine->GetExtraData(Bstr("VBoxInternal2/SavestateOnBatteryLow").raw(),
+ value.asOutParam());
+ int fPerVM = 0;
+ if (SUCCEEDED(rc) && !value.isEmpty())
{
- LONG iRc;
- progress->COMGETTER(ResultCode)(&iRc);
- rc = iRc;
+ /* per-VM overrides global */
+ if (value != "0")
+ fPerVM = 2;
+ else if (value == "0")
+ fPerVM = -2;
}
- AssertMsg (SUCCEEDED(rc), ("SaveState WaitForCompletion "
- "failed with %Rhrc (%#08X)\n", rc, rc));
-
- if (SUCCEEDED(rc))
- ++ saved;
+ /* default is true */
+ if (fGlobal + fPerVM >= 0)
+ {
+ ComPtr<IInternalSessionControl> pControl = *it;
+ ComPtr<IProgress> progress;
+
+ /* note that SaveStateWithReason() will simply return a failure
+ * if the VM is in an inappropriate state */
+ rc = pControl->SaveStateWithReason(Reason_HostBatteryLow, progress.asOutParam());
+ if (FAILED(rc))
+ {
+ LogRel(("SaveState '%s' failed with %Rhrc\n", pMachine->getName().c_str(), rc));
+ continue;
+ }
+
+ /* Wait until the operation has been completed. */
+ rc = progress->WaitForCompletion(-1);
+ if (SUCCEEDED(rc))
+ {
+ LONG iRc;
+ progress->COMGETTER(ResultCode)(&iRc);
+ rc = iRc;
+ }
+
+ AssertMsg(SUCCEEDED(rc), ("SaveState WaitForCompletion failed with %Rhrc (%#08X)\n", rc, rc));
+
+ if (SUCCEEDED(rc))
+ {
+ LogRel(("SaveState '%s' succeeded\n", pMachine->getName().c_str()));
+ ++saved;
+ }
+ }
}
-
- LogFunc (("Saved %d VMs\n", saved));
-
+ LogRel(("Battery Low: saved %d VMs\n", saved));
break;
}
+
+ default:
+ /* nothing */;
}
}
/* vi: set tabstop=4 shiftwidth=4 expandtab: */