summaryrefslogtreecommitdiff
path: root/src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp
diff options
context:
space:
mode:
authorLorry Tar Creator <lorry-tar-importer@baserock.org>2014-03-26 19:21:20 +0000
committer <>2014-05-08 15:03:54 +0000
commitfb123f93f9f5ce42c8e5785d2f8e0edaf951740e (patch)
treec2103d76aec5f1f10892cd1d3a38e24f665ae5db /src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp
parent58ed4748338f9466599adfc8a9171280ed99e23f (diff)
downloadVirtualBox-master.tar.gz
Imported from /home/lorry/working-area/delta_VirtualBox/VirtualBox-4.3.10.tar.bz2.HEADVirtualBox-4.3.10master
Diffstat (limited to 'src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp')
-rw-r--r--src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp185
1 files changed, 116 insertions, 69 deletions
diff --git a/src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp b/src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp
index 5a27edf4..61492be0 100644
--- a/src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp
+++ b/src/VBox/Additions/WINNT/Installer/InstallHelper/VBoxGuestInstallHelper.cpp
@@ -4,7 +4,7 @@
*/
/*
- * Copyright (C) 2011 Oracle Corporation
+ * Copyright (C) 2011-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;
@@ -25,6 +25,12 @@
#include <strsafe.h>
#include "exdll.h"
+#include <iprt/err.h>
+#include <iprt/initterm.h>
+#include <iprt/localipc.h>
+#include <iprt/mem.h>
+#include <iprt/string.h>
+
/* Required structures/defines of VBoxTray. */
#include "../../VBoxTray/VBoxTrayMsg.h"
@@ -48,6 +54,9 @@ HINSTANCE g_hInstance;
HWND g_hwndParent;
PFNSFCFILEEXCEPTION g_pfnSfcFileException = NULL;
+/**
+ * @todo Clean up this DLL, use more IPRT in here!
+ */
/**
* Pops (gets) a value from the internal NSIS stack.
@@ -62,7 +71,7 @@ static HRESULT vboxPopString(TCHAR *pszDest, size_t cchDest)
{
HRESULT hr = S_OK;
if (!g_stacktop || !*g_stacktop)
- hr = __HRESULT_FROM_WIN32(ERROR_EMPTY);
+ hr = __HRESULT_FROM_WIN32(ERROR_INVALID_HANDLE);
else
{
stack_t *pStack = (*g_stacktop);
@@ -75,6 +84,8 @@ static HRESULT vboxPopString(TCHAR *pszDest, size_t cchDest)
GlobalFree((HGLOBAL)pStack);
}
}
+ else
+ hr = __HRESULT_FROM_WIN32(ERROR_INVALID_HANDLE);
}
return hr;
}
@@ -114,6 +125,45 @@ static void vboxPushResultAsString(HRESULT hr)
pushstring(szErr);
}
+/**
+ * Connects to VBoxTray IPC under the behalf of the user running
+ * in the current thread context.
+ *
+ * @return IPRT status code.
+ * @param phSession Where to store the IPC session.
+ */
+static int vboxConnectToVBoxTray(RTLOCALIPCSESSION *phSession)
+{
+ int rc = VINF_SUCCESS;
+
+ RTUTF16 wszUserName[255];
+ DWORD cchUserName = sizeof(wszUserName) / sizeof(RTUTF16);
+ BOOL fRc = GetUserNameW(wszUserName, &cchUserName);
+ if (!fRc)
+ rc = RTErrConvertFromWin32(GetLastError());
+
+ if (RT_SUCCESS(rc))
+ {
+ char *pszUserName;
+ rc = RTUtf16ToUtf8(wszUserName, &pszUserName);
+ if (RT_SUCCESS(rc))
+ {
+ char szPipeName[255];
+ if (RTStrPrintf(szPipeName, sizeof(szPipeName), "%s%s",
+ VBOXTRAY_IPC_PIPE_PREFIX, pszUserName))
+ {
+ rc = RTLocalIpcSessionConnect(phSession, szPipeName, 0 /* Flags */);
+ }
+ else
+ rc = VERR_NO_MEMORY;
+
+ RTStrFree(pszUserName);
+ }
+ }
+
+ return rc;
+}
+
static void vboxChar2WCharFree(PWCHAR pwString)
{
if (pwString)
@@ -143,56 +193,22 @@ static HRESULT vboxChar2WCharAlloc(const char *pszString, PWCHAR *ppwString)
return hr;
}
-static HANDLE vboxIPCConnect(void)
+/**
+ * Loads a system DLL.
+ *
+ * @returns Module handle or NULL
+ * @param pszName The DLL name.
+ */
+static HMODULE loadSystemDll(const char *pszName)
{
- HANDLE hPipe = NULL;
- while (1)
- {
- hPipe = CreateFile(VBOXTRAY_PIPE_IPC, /* Pipe name. */
- GENERIC_READ | /* Read and write access. */
- GENERIC_WRITE,
- 0, /* No sharing. */
- NULL, /* Default security attributes. */
- OPEN_EXISTING, /* Opens existing pipe. */
- 0, /* Default attributes. */
- NULL); /* No template file. */
-
- /* Break if the pipe handle is valid. */
- if (hPipe != INVALID_HANDLE_VALUE)
- break;
-
- /* Exit if an error other than ERROR_PIPE_BUSY occurs. */
- if (GetLastError() != ERROR_PIPE_BUSY)
- return NULL;
-
- /* All pipe instances are busy, so wait for 20 seconds. */
- if (!WaitNamedPipe(VBOXTRAY_PIPE_IPC, 20000))
- return NULL;
- }
-
- /* The pipe connected; change to message-read mode. */
- DWORD dwMode = PIPE_READMODE_MESSAGE;
- BOOL fSuccess = SetNamedPipeHandleState(hPipe, /* Pipe handle. */
- &dwMode, /* New pipe mode. */
- NULL, /* Don't set maximum bytes. */
- NULL); /* Don't set maximum time. */
- if (!fSuccess)
+ char szPath[MAX_PATH];
+ UINT cchPath = GetSystemDirectoryA(szPath, sizeof(szPath));
+ size_t cbName = strlen(pszName) + 1;
+ if (cchPath + 1 + cbName > sizeof(szPath))
return NULL;
- return hPipe;
-}
-
-static void vboxIPCDisconnect(HANDLE hPipe)
-{
- CloseHandle(hPipe);
-}
-
-static HRESULT vboxIPCWriteMessage(HANDLE hPipe, BYTE *pMessage, DWORD cbMessage)
-{
- HRESULT hr = S_OK;
- DWORD cbWritten = 0;
- if (!WriteFile(hPipe, pMessage, cbMessage - cbWritten, &cbWritten, 0))
- hr = HRESULT_FROM_WIN32(GetLastError());
- return hr;
+ szPath[cchPath] = '\\';
+ memcpy(&szPath[cchPath + 1], pszName, cbName);
+ return LoadLibraryA(szPath);
}
/**
@@ -213,7 +229,7 @@ VBOXINSTALLHELPER_EXPORT DisableWFP(HWND hwndParent, int string_size,
HRESULT hr = vboxPopString(szFile, sizeof(szFile) / sizeof(TCHAR));
if (SUCCEEDED(hr))
{
- HMODULE hSFC = LoadLibrary("sfc_os.dll");
+ HMODULE hSFC = loadSystemDll("sfc_os.dll"); /** @todo Replace this by RTLdr APIs. */
if (NULL != hSFC)
{
g_pfnSfcFileException = (PFNSFCFILEEXCEPTION)GetProcAddress(hSFC, "SfcFileException");
@@ -426,31 +442,62 @@ VBOXINSTALLHELPER_EXPORT VBoxTrayShowBallonMsg(HWND hwndParent, int string_size,
{
EXDLL_INIT();
- VBOXTRAYIPCHEADER hdr;
- hdr.ulMsg = VBOXTRAYIPCMSGTYPE_SHOWBALLOONMSG;
- hdr.cbBody = sizeof(VBOXTRAYIPCMSG_SHOWBALLOONMSG);
-
- VBOXTRAYIPCMSG_SHOWBALLOONMSG msg;
- HRESULT hr = vboxPopString(msg.szContent, sizeof(msg.szContent) / sizeof(TCHAR));
- if (SUCCEEDED(hr))
- hr = vboxPopString(msg.szTitle, sizeof(msg.szTitle) / sizeof(TCHAR));
+ char szMsg[256];
+ char szTitle[128];
+ HRESULT hr = vboxPopString(szMsg, sizeof(szMsg) / sizeof(char));
if (SUCCEEDED(hr))
- hr = vboxPopULong(&msg.ulType);
- if (SUCCEEDED(hr))
- hr = vboxPopULong(&msg.ulShowMS);
+ hr = vboxPopString(szTitle, sizeof(szTitle) / sizeof(char));
+
+ /** @todo Do we need to restore the stack on failure? */
if (SUCCEEDED(hr))
{
- msg.ulFlags = 0;
-
- HANDLE hPipe = vboxIPCConnect();
- if (hPipe)
+ RTR3InitDll(0);
+
+ uint32_t cbMsg = sizeof(VBOXTRAYIPCMSG_SHOWBALLOONMSG)
+ + strlen(szMsg) + 1 /* Include terminating zero */
+ + strlen(szTitle) + 1; /* Dito. */
+ Assert(cbMsg);
+ PVBOXTRAYIPCMSG_SHOWBALLOONMSG pIpcMsg =
+ (PVBOXTRAYIPCMSG_SHOWBALLOONMSG)RTMemAlloc(cbMsg);
+ if (pIpcMsg)
{
- hr = vboxIPCWriteMessage(hPipe, (BYTE*)&hdr, sizeof(VBOXTRAYIPCHEADER));
+ /* Stuff in the strings. */
+ memcpy(pIpcMsg->szMsgContent, szMsg, strlen(szMsg) + 1);
+ memcpy(pIpcMsg->szMsgTitle, szTitle, strlen(szTitle) + 1);
+
+ /* Pop off the values in reverse order from the stack. */
+ if (SUCCEEDED(hr))
+ hr = vboxPopULong((ULONG*)&pIpcMsg->uType);
+ if (SUCCEEDED(hr))
+ hr = vboxPopULong((ULONG*)&pIpcMsg->uShowMS);
+
if (SUCCEEDED(hr))
- hr = vboxIPCWriteMessage(hPipe, (BYTE*)&msg, sizeof(VBOXTRAYIPCMSG_SHOWBALLOONMSG));
- vboxIPCDisconnect(hPipe);
+ {
+ RTLOCALIPCSESSION hSession = 0;
+ int rc = vboxConnectToVBoxTray(&hSession);
+ if (RT_SUCCESS(rc))
+ {
+ VBOXTRAYIPCHEADER ipcHdr = { VBOXTRAY_IPC_HDR_MAGIC, 0 /* Header version */,
+ VBOXTRAYIPCMSGTYPE_SHOWBALLOONMSG, cbMsg };
+
+ rc = RTLocalIpcSessionWrite(hSession, &ipcHdr, sizeof(ipcHdr));
+ if (RT_SUCCESS(rc))
+ rc = RTLocalIpcSessionWrite(hSession, pIpcMsg, cbMsg);
+
+ int rc2 = RTLocalIpcSessionClose(hSession);
+ if (RT_SUCCESS(rc))
+ rc = rc2;
+ }
+
+ if (RT_FAILURE(rc))
+ hr = __HRESULT_FROM_WIN32(ERROR_BROKEN_PIPE);
+ }
+
+ RTMemFree(pIpcMsg);
}
+ else
+ hr = __HRESULT_FROM_WIN32(ERROR_NOT_ENOUGH_MEMORY);
}
/* Push simple return value on stack. */