Changeset 71716 in vbox for trunk/src/VBox/Main
- Timestamp:
- Apr 6, 2018 6:16:30 PM (7 years ago)
- Location:
- trunk/src/VBox/Main
- Files:
-
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Main/include/RpcChannelHook.h
r71160 r71716 26 26 27 27 28 typedef void *PRPC_CHANNEL_HOOK;28 typedef void *PRPC_CHANNEL_HOOK; 29 29 30 30 // {CEDA3E95-A46A-4C41-AA01-EFFD856E455C} … … 32 32 { 0xceda3e95, 0xa46a, 0x4c41,{ 0xaa, 0x1, 0xef, 0xfd, 0x85, 0x6e, 0x45, 0x5c } }; 33 33 34 #if defined(__cplusplus) 35 extern "C" 36 { 37 #endif // #if defined(__cplusplus) 38 39 // C wrapper for using in proxy 40 void SetupClientRpcChannelHook(void); 41 42 #if defined(__cplusplus) 43 } 44 #endif // #if defined(__cplusplus) 34 RT_C_DECLS_BEGIN 35 // C wrapper for using in proxy 36 void SetupClientRpcChannelHook(void); 37 RT_C_DECLS_END 45 38 46 39 … … 78 71 protected: 79 72 const GUID m_ChannelHookID; 80 static volatile bool s_ bChannelRegistered;81 static volatile bool s_ bVBpoxSDSCalledOnce;73 static volatile bool s_fChannelRegistered; 74 static volatile bool s_fVBpoxSDSCalledOnce; 82 75 static CRpcChannelHook s_RpcChannelHook; 83 76 -
trunk/src/VBox/Main/src-all/win/RpcChannelHook.cpp
r71160 r71716 31 31 #ifdef RT_OS_WINDOWS 32 32 33 volatile bool CRpcChannelHook::s_ bChannelRegistered = false;34 volatile bool CRpcChannelHook::s_ bVBpoxSDSCalledOnce = false;33 volatile bool CRpcChannelHook::s_fChannelRegistered = false; 34 volatile bool CRpcChannelHook::s_fVBpoxSDSCalledOnce = false; 35 35 CRpcChannelHook CRpcChannelHook::s_RpcChannelHook; 36 36 37 37 38 /* 38 * RpcChannelHook IUnknown interface implementation. 39 */ 40 39 * RpcChannelHook IUnknown interface implementation. 40 */ 41 41 42 42 STDMETHODIMP CRpcChannelHook::QueryInterface(REFIID riid, void **ppv) … … 69 69 } 70 70 71 72 /** 73 * This is a function that we can call from non-C++ proxy stub code. 74 * 75 * @note Warning! function is not thread safe! 76 * @todo Consider using RTONCE to serialize this (though it's likely unncessary 77 * due to COM). 78 */ 79 void SetupClientRpcChannelHook(void) 80 { 81 // register single hook only 82 if (!CRpcChannelHook::IsChannelHookRegistered()) 83 { 84 HRESULT hr = CoRegisterChannelHook(RPC_CHANNEL_EXTENSION_GUID, &CRpcChannelHook::s_RpcChannelHook); 85 NOREF(hr); 86 Assert(SUCCEEDED(hr)); 87 CRpcChannelHook::RegisterChannelHook(); 88 LogFunc(("Registered RPC client channel hook \n")); 89 } 90 } 91 92 71 93 /* 72 * C wrapper functions. 73 */ 74 75 // Warning: functions below are not thread safe 76 extern "C" 77 { 78 void SetupClientRpcChannelHook(void) 79 { 80 // register single hook only 81 if (!CRpcChannelHook::IsChannelHookRegistered()) 82 { 83 HRESULT hr = CoRegisterChannelHook(RPC_CHANNEL_EXTENSION_GUID, 84 &CRpcChannelHook::s_RpcChannelHook); 85 NOREF(hr); 86 Assert(SUCCEEDED(hr)); 87 CRpcChannelHook::RegisterChannelHook(); 88 LogFunc(("Registered RPC client channel hook \n")); 89 } 90 } 91 } 92 93 94 /* 95 * Internal functions. 96 */ 94 * Internal methods. 95 */ 97 96 98 97 bool CRpcChannelHook::IsChannelHookRegistered() 99 98 { 100 return ASMAtomicReadBool(&s_ bChannelRegistered);99 return ASMAtomicReadBool(&s_fChannelRegistered); 101 100 } 102 101 … … 104 103 void CRpcChannelHook::RegisterChannelHook() 105 104 { 106 ASMAtomicWriteBool(&s_ bChannelRegistered, true);105 ASMAtomicWriteBool(&s_fChannelRegistered, true); 107 106 } 108 107 … … 124 123 } 125 124 126 /* 127 * This is callback of RPC channel hook called on COM client when COM method call 128 * finished on server and response returned. 129 * We use it to catch a moment when a new VirtualBox object sucessfully instantiated. 130 * This callback is called in client process - VirtualBox.exe, VBoxManage or custom client 131 * If it happend we register new API client in VBoxSDS. 132 * Parameters: 133 * uExtent - unique ID of our RPC channel 134 * rIID - IID of called server interface (IVirtualBox in our case) 135 * pDataBuffer - NULL, such as we have nothing to transfer from server side 136 * hrFault - result of called COM server method 137 */ 138 STDMETHODIMP_(void) CRpcChannelHook::ClientNotify(REFGUID uExtent, REFIID riid, 139 ULONG cbDataSize, void *pDataBuffer, DWORD lDataRep, HRESULT hrFault) 125 /** 126 * This is callback of RPC channel hook called on COM client when COM method call 127 * finished on server and response returned. 128 * We use it to catch a moment when a new VirtualBox object sucessfully instantiated. 129 * This callback is called in client process - VirtualBox.exe, VBoxManage or custom client 130 * If it happend we register new API client in VBoxSDS. 131 * Parameters: 132 * @param uExtent Unique ID of our RPC channel. 133 * @param riid Interface ID of called server interface (IVirtualBox 134 * in our case). 135 * @param cbDataBuffer ??????????????????? 136 * @param pDataBuffer NULL, such as we have nothing to transfer from 137 * server side. 138 * @param lDataRep ??????????? 139 * @param hrFault result of called COM server method. 140 */ 141 STDMETHODIMP_(void) CRpcChannelHook::ClientNotify(REFGUID uExtent, REFIID riid, ULONG cbDataSize, void *pDataBuffer, 142 DWORD lDataRep, HRESULT hrFault) 140 143 { 141 144 NOREF(cbDataSize); … … 143 146 NOREF(lDataRep); 144 147 145 // Check that it created VirtualBox and this is first method called on server 146 // (CreateInstance) 147 if (uExtent == m_ChannelHookID && 148 riid == IID_IVirtualBox && 149 !ASMAtomicReadBool(&s_bVBpoxSDSCalledOnce) && 150 SUCCEEDED(hrFault) ) 148 /* 149 * Check that it created VirtualBox and this is first method called on server 150 * (CreateInstance) 151 */ 152 if ( riid == IID_IVirtualBox 153 && uExtent == m_ChannelHookID 154 && SUCCEEDED(hrFault) 155 && !ASMAtomicReadBool(&s_fVBpoxSDSCalledOnce) ) 151 156 { 152 157 LogFunc(("Finished call of VirtualBox method\n")); 153 158 154 ASMAtomicWriteBool(&s_bVBpoxSDSCalledOnce, true); 159 ASMAtomicWriteBool(&s_fVBpoxSDSCalledOnce, true); 160 161 /* 162 * Connect to VBoxSDS. 163 * Note: VBoxSDS can handle duplicate calls 164 */ 155 165 ComPtr<IVirtualBoxClientList> ptrClientList; 156 /*157 * Connect to VBoxSDS.158 * Note: VBoxSDS can handle duplicate calls159 */160 166 HRESULT hrc = CoCreateInstance(CLSID_VirtualBoxClientList, NULL, CLSCTX_LOCAL_SERVER, IID_IVirtualBoxClientList, 161 (void **)ptrClientList.asOutParam());167 (void **)ptrClientList.asOutParam()); 162 168 if (SUCCEEDED(hrc)) 163 169 { … … 173 179 } 174 180 175 STDMETHODIMP_(void) CRpcChannelHook::ClientFillBuffer(REFGUID uExtent, REFIID riid, 176 ULONG *pDataSize, void *pDataBuffer) 177 { 178 NOREF(uExtent); 179 NOREF(riid); 180 NOREF(pDataSize); 181 NOREF(pDataBuffer); 182 } 183 184 STDMETHODIMP_(void) CRpcChannelHook::ServerGetSize(REFGUID uExtent, REFIID riid, 185 HRESULT hrFault, ULONG *pDataSize) 181 STDMETHODIMP_(void) CRpcChannelHook::ClientFillBuffer(REFGUID uExtent, REFIID riid, ULONG *pDataSize, void *pDataBuffer) 182 { 183 RT_NOREF(uExtent, riid, pDataSize, pDataBuffer); 184 } 185 186 STDMETHODIMP_(void) CRpcChannelHook::ServerGetSize(REFGUID uExtent, REFIID riid, HRESULT hrFault, ULONG *pDataSize) 186 187 { 187 188 // Nothing to send to client side from server side 188 NOREF(uExtent); 189 NOREF(riid); 190 NOREF(hrFault); 189 RT_NOREF(uExtent, riid, hrFault); 191 190 *pDataSize = 0; 192 191 } 193 192 194 STDMETHODIMP_(void) CRpcChannelHook::ServerNotify(REFGUID uExtent, REFIID riid, 195 ULONG cbDataSize, void *pDataBuffer,DWORD lDataRep)193 STDMETHODIMP_(void) CRpcChannelHook::ServerNotify(REFGUID uExtent, REFIID riid, ULONG cbDataSize, void *pDataBuffer, 194 DWORD lDataRep) 196 195 { 197 196 // Nothing to do on server side 198 NOREF(uExtent); 199 NOREF(riid); 200 NOREF(cbDataSize); 201 NOREF(pDataBuffer); 202 NOREF(lDataRep); 203 } 204 205 STDMETHODIMP_(void) CRpcChannelHook::ServerFillBuffer(REFGUID uExtent, REFIID riid, 206 ULONG *pDataSize, void *pDataBuffer, HRESULT hrFault) 197 RT_NOREF(uExtent, riid, cbDataSize, pDataBuffer, lDataRep); 198 } 199 200 STDMETHODIMP_(void) CRpcChannelHook::ServerFillBuffer(REFGUID uExtent, REFIID riid, ULONG *pDataSize, void *pDataBuffer, 201 HRESULT hrFault) 207 202 { 208 203 // Nothing to send to client side from server side 209 NOREF(uExtent); 210 NOREF(riid); 211 NOREF(pDataSize); 212 NOREF(pDataBuffer); 213 NOREF(hrFault); 204 RT_NOREF(uExtent, riid, pDataSize, pDataBuffer, hrFault); 214 205 } 215 206 -
trunk/src/VBox/Main/src-all/win/VBoxProxyStub.c
r71715 r71716 148 148 }; 149 149 150 BOOL IsVBoxServiceProcess(void)151 {152 if (GetEnvironmentVariable(L"VBOX_SERVICE_PROCESS", NULL, 0) == 0)153 {154 int res = GetLastError();155 if (res != ERROR_ENVVAR_NOT_FOUND)156 LogRel(("Error: cannot get service environment variable: %Rrwa\n", res));157 return false;158 }159 return true;160 }161 162 150 163 151 /** … … 185 173 Log12(("VBoxProxyStub[%u]/DllMain: DLL_PROCESS_ATTACH\n", GetCurrentProcessId())); 186 174 187 /* Install RPC channel hook to intercept a moment just after VirtualBox object activation.188 It's reports to VBoxSDS that a new VirtualBox API client started. */189 175 #ifdef VBOX_SDS_CLIENTS_WATCHER 190 if(!IsVBoxServiceProcess()) 176 /* 177 * Install RPC channel hook to intercept a moment just after VirtualBox object activation. 178 * It's reports to VBoxSDS that a new VirtualBox API client started. 179 */ 180 if (GetProcAddress(GetModuleHandle(NULL), "Is_VirtualBox_service_process_like_VBoxSDS_And_VBoxSDS") == NULL) 191 181 SetupClientRpcChannelHook(); 192 182 #endif -
trunk/src/VBox/Main/src-global/win/VBoxSDS.cpp
r71160 r71716 695 695 696 696 697 int SetServiceEnvFlag() 697 /** Special export that make VBoxProxyStub not register this process as one that 698 * VBoxSDS should be watching. 699 */ 700 extern "C" DECLEXPORT(void) VBOXCALL Is_VirtualBox_service_process_like_VBoxSDS_And_VBoxSDS(void) 698 701 { 699 int rc = VINF_SUCCESS; 700 if (!SetEnvironmentVariable(L"VBOX_SERVICE_PROCESS", L"")) 701 { 702 rc = RTErrConvertFromWin32(GetLastError()); 703 LogRel(("Error: cannot set service environment flag: %Rrs\n", rc)); 704 } 705 return rc; 702 /* never called, just need to be here */ 706 703 } 707 704 … … 728 725 */ 729 726 RTR3InitExe(argc, &argv, 0); 730 731 SetServiceEnvFlag();732 727 733 728 static const RTGETOPTDEF s_aOptions[] = -
trunk/src/VBox/Main/src-server/win/svcmain.cpp
r71317 r71716 516 516 void VirtualBoxClassFactory::i_finishVBoxSvc() 517 517 { 518 LogRelFunc(("Finish work of VBoxSV cand VBoxSDS\n"));518 LogRelFunc(("Finish work of VBoxSVC and VBoxSDS\n")); 519 519 if (m_ptrVirtualBoxSDS.isNotNull()) 520 520 { … … 787 787 788 788 789 int SetServiceEnvFlag() 790 { 791 int rc = VINF_SUCCESS; 792 if (!SetEnvironmentVariable(L"VBOX_SERVICE_PROCESS", L"")) 793 { 794 rc = RTErrConvertFromWin32(GetLastError()); 795 LogRel(("Error: cannot set service environment flag: %Rrs\n", rc)); 796 } 797 return rc; 789 /** Special export that make VBoxProxyStub not register this process as one that 790 * VBoxSDS should be watching. 791 */ 792 extern "C" DECLEXPORT(void) VBOXCALL Is_VirtualBox_service_process_like_VBoxSDS_And_VBoxSDS(void) 793 { 794 /* never called, just need to be here */ 798 795 } 799 796 … … 834 831 */ 835 832 RTR3InitExe(argc, &argv, 0); 836 837 SetServiceEnvFlag();838 833 839 834 static const RTGETOPTDEF s_aOptions[] =
Note:
See TracChangeset
for help on using the changeset viewer.