[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [win-pv-devel] [PATCH] xenagent: re-register shutdown watch after resume from S4
When xenagent resumes in a VM that was put into S4 it needs to re- register the watch on control/shutdown and re-advertise all control/feature-XXX flags. Signed-off-by: Paul Durrant <paul.durrant@xxxxxxxxxx> --- src/xenagent/devicelist.cpp | 22 +++++++++++++ src/xenagent/devicelist.h | 3 ++ src/xenagent/service.cpp | 80 ++++++++++++++++++++++++++++++++------------- src/xenagent/service.h | 5 +++ 4 files changed, 88 insertions(+), 22 deletions(-) diff --git a/src/xenagent/devicelist.cpp b/src/xenagent/devicelist.cpp index 6b379e2..7053a96 100644 --- a/src/xenagent/devicelist.cpp +++ b/src/xenagent/devicelist.cpp @@ -237,6 +237,28 @@ void CDeviceList::OnDeviceEvent(DWORD evt, LPVOID data) } } +void CDeviceList::OnPowerEvent(DWORD evt, LPVOID data) +{ + switch (evt) { + case PBT_APMRESUMESUSPEND: + for (DeviceMap::iterator it = m_devs.begin(); + it != m_devs.end(); + ++it) + m_impl->OnDeviceResume(it->second); + break; + + case PBT_APMSUSPEND: + for (DeviceMap::iterator it = m_devs.begin(); + it != m_devs.end(); + ++it) + m_impl->OnDeviceSuspend(it->second); + break; + + default: + break; + } +} + CDevice* CDeviceList::GetFirstDevice() { DeviceMap::iterator it = m_devs.begin(); diff --git a/src/xenagent/devicelist.h b/src/xenagent/devicelist.h index ee1d8ab..893bd43 100644 --- a/src/xenagent/devicelist.h +++ b/src/xenagent/devicelist.h @@ -63,6 +63,8 @@ public: virtual CDevice* Create(const wchar_t* path) = 0; virtual void OnDeviceAdded(CDevice* dev) = 0; virtual void OnDeviceRemoved(CDevice* dev) = 0; + virtual void OnDeviceSuspend(CDevice* dev) = 0; + virtual void OnDeviceResume(CDevice* dev) = 0; }; class CDeviceList @@ -74,6 +76,7 @@ public: bool Start(HANDLE svc, IDeviceCreator* impl); void Stop(); void OnDeviceEvent(DWORD evt, LPVOID data); + void OnPowerEvent(DWORD evt, LPVOID data); CDevice* GetFirstDevice(); private: diff --git a/src/xenagent/service.cpp b/src/xenagent/service.cpp index 6132fe0..2d06008 100644 --- a/src/xenagent/service.cpp +++ b/src/xenagent/service.cpp @@ -187,7 +187,9 @@ CXenAgent::CXenAgent() : m_handle(NULL), m_evtlog(NULL), { m_status.dwServiceType = SERVICE_WIN32; m_status.dwCurrentState = SERVICE_START_PENDING; - m_status.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN; + m_status.dwControlsAccepted = SERVICE_ACCEPT_STOP | + SERVICE_ACCEPT_SHUTDOWN | + SERVICE_ACCEPT_POWEREVENT; m_status.dwWin32ExitCode = 0; m_status.dwServiceSpecificExitCode = 0; m_status.dwCheckPoint = 0; @@ -214,6 +216,34 @@ CXenAgent::~CXenAgent() return new CXenIfaceDevice(path); } +void CXenAgent::StartShutdownWatch() +{ + if (m_ctxt_shutdown) + return; + + m_device->StoreAddWatch("control/shutdown", m_evt_shutdown, &m_ctxt_shutdown); + + m_device->StoreWrite("control/feature-poweroff", "1"); + m_device->StoreWrite("control/feature-reboot", "1"); + m_device->StoreWrite("control/feature-s3", "1"); + m_device->StoreWrite("control/feature-s4", "1"); +} + +void CXenAgent::StopShutdownWatch() +{ + if (!m_ctxt_shutdown) + return; + + m_device->StoreRemove("control/feature-poweroff"); + m_device->StoreRemove("control/feature-reboot"); + m_device->StoreRemove("control/feature-s3"); + m_device->StoreRemove("control/feature-s4"); + + m_device->StoreRemoveWatch(m_ctxt_shutdown); + m_ctxt_shutdown = NULL; +} + + /*virtual*/ void CXenAgent::OnDeviceAdded(CDevice* dev) { CXenAgent::Log("OnDeviceAdded(%ws)\n", dev->Path()); @@ -222,16 +252,8 @@ CXenAgent::~CXenAgent() if (m_device == NULL) { m_device = (CXenIfaceDevice*)dev; - // shutdown - m_device->StoreAddWatch("control/shutdown", m_evt_shutdown, &m_ctxt_shutdown); - m_device->StoreWrite("control/feature-poweroff", "1"); - m_device->StoreWrite("control/feature-reboot", "1"); - m_device->StoreWrite("control/feature-s3", "1"); - m_device->StoreWrite("control/feature-s4", "1"); - - // suspend m_device->SuspendRegister(m_evt_suspend, &m_ctxt_suspend); - + StartShutdownWatch(); SetXenTime(); } } @@ -242,24 +264,28 @@ CXenAgent::~CXenAgent() CCritSec crit(&m_crit); if (m_device == dev) { - // suspend - if (m_ctxt_suspend) + if (m_ctxt_suspend) { m_device->SuspendDeregister(m_ctxt_suspend); - m_ctxt_suspend = NULL; - - // shutdown - m_device->StoreRemove("control/feature-poweroff"); - m_device->StoreRemove("control/feature-reboot"); - m_device->StoreRemove("control/feature-s3"); - m_device->StoreRemove("control/feature-s4"); - if (m_ctxt_shutdown) - m_device->StoreRemoveWatch(m_ctxt_shutdown); - m_ctxt_shutdown = NULL; + m_ctxt_suspend = NULL; + } + StopShutdownWatch(); m_device = NULL; } } +/*virtual*/ void CXenAgent::OnDeviceSuspend(CDevice* dev) +{ + CXenAgent::Log("OnDeviceSuspend(%ws)\n", dev->Path()); + StopShutdownWatch(); +} + +/*virtual*/ void CXenAgent::OnDeviceResume(CDevice* dev) +{ + CXenAgent::Log("OnDeviceResume(%ws)\n", dev->Path()); + StartShutdownWatch(); +} + void CXenAgent::OnServiceStart() { CXenAgent::Log("OnServiceStart()\n"); @@ -277,6 +303,11 @@ void CXenAgent::OnDeviceEvent(DWORD evt, LPVOID data) m_devlist.OnDeviceEvent(evt, data); } +void CXenAgent::OnPowerEvent(DWORD evt, LPVOID data) +{ + m_devlist.OnPowerEvent(evt, data); +} + bool CXenAgent::ServiceMainLoop() { HANDLE events[3] = { m_svc_stop, m_evt_shutdown, m_evt_suspend }; @@ -577,6 +608,11 @@ DWORD WINAPI CXenAgent::__ServiceControlHandlerEx(DWORD req, DWORD evt, LPVOID d OnDeviceEvent(evt, data); return NO_ERROR; + case SERVICE_CONTROL_POWEREVENT: + SetServiceStatus(SERVICE_RUNNING); + OnPowerEvent(evt, data); + return NO_ERROR; + case SERVICE_CONTROL_INTERROGATE: SetServiceStatus(SERVICE_RUNNING); return NO_ERROR; diff --git a/src/xenagent/service.h b/src/xenagent/service.h index 975662b..77a11d7 100644 --- a/src/xenagent/service.h +++ b/src/xenagent/service.h @@ -60,14 +60,19 @@ public: // IDeviceCreator virtual CDevice* Create(const wchar_t* path); virtual void OnDeviceAdded(CDevice* dev); virtual void OnDeviceRemoved(CDevice* dev); + virtual void OnDeviceSuspend(CDevice* dev); + virtual void OnDeviceResume(CDevice* dev); private: // service events void OnServiceStart(); void OnServiceStop(); void OnDeviceEvent(DWORD, LPVOID); + void OnPowerEvent(DWORD, LPVOID); bool ServiceMainLoop(); private: // helpers + void StartShutdownWatch(); + void StopShutdownWatch(); void AcquireShutdownPrivilege(); void EventLog(DWORD evt); bool IsHostTimeUTC(); -- 2.1.1 _______________________________________________ win-pv-devel mailing list win-pv-devel@xxxxxxxxxxxxxxxxxxxx https://lists.xenproject.org/cgi-bin/mailman/listinfo/win-pv-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |