summaryrefslogtreecommitdiffstats
path: root/remote
diff options
context:
space:
mode:
authorSimon Rettberg2016-03-14 15:10:07 +0100
committerSimon Rettberg2016-03-14 15:10:07 +0100
commit4228b42680d139afc64717b84c6544dc4c609aa9 (patch)
tree8b71dd9a272c43fc1e0115ce5044ee1d777dc2c8 /remote
parent[run-virt] Fix mapping of drive letter, shortcut on desktop (diff)
downloadtm-scripts-4228b42680d139afc64717b84c6544dc4c609aa9.tar.gz
tm-scripts-4228b42680d139afc64717b84c6544dc4c609aa9.tar.xz
tm-scripts-4228b42680d139afc64717b84c6544dc4c609aa9.zip
[run-virt] More progress on openslx.exe
Diffstat (limited to 'remote')
-rw-r--r--remote/modules/run-virt/data/opt/openslx/scripts/includes/setup_virtual_floppy.inc26
-rw-r--r--remote/modules/run-virt/data/opt/openslx/scripts/pam_script_auth.d/99-run_virt_credentials8
-rwxr-xr-xremote/modules/run-virt/data/opt/openslx/vmchooser/data/openslx.exebin52224 -> 57344 bytes
-rw-r--r--remote/modules/run-virt/winres.c349
4 files changed, 300 insertions, 83 deletions
diff --git a/remote/modules/run-virt/data/opt/openslx/scripts/includes/setup_virtual_floppy.inc b/remote/modules/run-virt/data/opt/openslx/scripts/includes/setup_virtual_floppy.inc
index d1343700..2fdebf4c 100644
--- a/remote/modules/run-virt/data/opt/openslx/scripts/includes/setup_virtual_floppy.inc
+++ b/remote/modules/run-virt/data/opt/openslx/scripts/includes/setup_virtual_floppy.inc
@@ -14,9 +14,26 @@ mkfs.fat "${FLOPPYIMG}" || mkfs.vfat "${FLOPPYIMG}" || mkdosfs "${FLOPPYIMG}"
# via virtual floppy
#mcopy -i "${FLOPPYIMG}" "$xmlfile" "::/config.xml"
-# Create file with resolution information
-xrandr | grep -o -E 'connected\s*(primary)?\s*[0-9]+x[0-9]+\+0\+0' \
- | grep -o -E -m1 '[0-9]+x[0-9]+' > "${TMPDIR}/hostres.txt"
+# Create file with resolution information etc.
+. "/opt/openslx/inc/shares"
+[ -z "$SHARE_REMAP_MODE" ] && SHARE_REMAP_MODE="1"
+[ -z "$SHARE_CREATE_MISSING_REMAP" ] && SHARE_CREATE_MISSING_REMAP="1"
+RESOLUTION=$(xrandr | grep -o -E 'connected\s*(primary)?\s*[0-9]+x[0-9]+\+0\+0' \
+ | grep -o -E -m1 '[0-9]+x[0-9]+')
+
+cat > "${TMPDIR}/geraffel.ini" <<-HIER
+[openslx]
+resolution=${RESOLUTION}
+createMissingRemap=${SHARE_CREATE_MISSING_REMAP}
+remapMode=${SHARE_REMAP_MODE}
+
+[remap]
+documents=${SHARE_DOCUMENTS}
+downloads=${SHARE_DOWNLOADS}
+desktop=${SHARE_DESKTOP}
+media=${SHARE_MEDIA}
+other=${SHARE_OTHER}
+HIER
# Create file for network shares to mount
SHARES="${TMPDIR}/shares.dat"
@@ -36,8 +53,9 @@ if pwdaemon --query "${TMPHOME}/.pwsocket" > "${SHARES}"; then
fi
# Copy all them files into floppy image
-mcopy -i "${FLOPPYIMG}" "${TMPDIR}/hostres.txt" "::/"
+mcopy -i "${FLOPPYIMG}" "${TMPDIR}/geraffel.ini" "::/"
mcopy -i "${FLOPPYIMG}" "$VMCHOOSER_DIR/data/openslx.exe" "::/"
mcopy -i "${FLOPPYIMG}" "${SHARES}" "::/"
+rm -f -- "${SHARES}"
unset SHARES VAR NETHOME
diff --git a/remote/modules/run-virt/data/opt/openslx/scripts/pam_script_auth.d/99-run_virt_credentials b/remote/modules/run-virt/data/opt/openslx/scripts/pam_script_auth.d/99-run_virt_credentials
index 1e2c18e7..a03d8886 100644
--- a/remote/modules/run-virt/data/opt/openslx/scripts/pam_script_auth.d/99-run_virt_credentials
+++ b/remote/modules/run-virt/data/opt/openslx/scripts/pam_script_auth.d/99-run_virt_credentials
@@ -18,17 +18,19 @@ if [ -n "$TEMP_HOME_DIR" ]; then
[ -z "$XUSER" ] && XUSER="${PAM_USER}"
# Guess domain
XDOMAIN=
- if [ -n "$PERSISTENT_OK" ]; then
+ if [ -n "$PERSISTENT_HOME_DIR" ]; then
XDOMAIN=$(grep -F " ${PERSISTENT_HOME_DIR} " "/proc/mounts" | grep -m1 -F 'domain=' | sed -r 's/^.*[ ,]domain=([^ ,]+)[ ,].*$/\1/g')
fi
if [ -z "$XDOMAIN" ]; then
- XDOMAIN=$(grep -m1 -i '^BASE\s*DC=' "/etc/ldap.conf" | sed -r 's/^BASE\s*DC=([^,;]+)[,;].*$/\1/I')
+ XDOMAIN=$(grep -m1 -i '^BASE\s*DC=' "/etc/ldap.conf" | sed -r 's/^BASE\s*DC=([^,;]+).*$/\1/I')
fi
if [ -z "$XDOMAIN" ]; then
- XDOMAIN=$(grep -m1 -i '^ldap_search_base\s*=' "/etc/sssd/sssd.conf" | sed -r 's/^ldap_search_base\s*=\s*DC=([^,;]+)[,;].*$/\1/I')
+ XDOMAIN=$(grep -m1 -i '^ldap_search_base\s*=\s*DC=' "/etc/sssd/sssd.conf" | sed -r 's/^ldap_search_base\s*=\s*DC=([^,;]+).*$/\1/I')
fi
if [ -n "$XDOMAIN" ]; then
XDOMAIN=$(echo "$XDOMAIN" | tr '[a-z]' '[A-Z]')
+ else
+ XDOMAIN="WORKGROUP"
fi
USERNAME="$XDOMAIN\\$XUSER" PASSWORD="$PAM_AUTHTOK" PWSOCKET="${TEMP_HOME_DIR}/.pwsocket" su -c 'pwdaemon --daemon &' "${PAM_USER}" &
unset XUSER XDOMAIN
diff --git a/remote/modules/run-virt/data/opt/openslx/vmchooser/data/openslx.exe b/remote/modules/run-virt/data/opt/openslx/vmchooser/data/openslx.exe
index 39928c92..7b71ba90 100755
--- a/remote/modules/run-virt/data/opt/openslx/vmchooser/data/openslx.exe
+++ b/remote/modules/run-virt/data/opt/openslx/vmchooser/data/openslx.exe
Binary files differ
diff --git a/remote/modules/run-virt/winres.c b/remote/modules/run-virt/winres.c
index 54c0ad1b..e4fce258 100644
--- a/remote/modules/run-virt/winres.c
+++ b/remote/modules/run-virt/winres.c
@@ -20,6 +20,7 @@
#include <shlobj.h>
#include <shlguid.h>
#include <strsafe.h>
+#include <tlhelp32.h>
DEFINE_GUID(ID_IAudioEndpointVolume, 0x5CDF2C82, 0x841E, 0x4546, 0x97, 0x22, 0x0C, 0xF7, 0x40, 0x78, 0x22, 0x9A);
DEFINE_GUID(ID_IMMDeviceEnumerator, 0xa95664d2, 0x9614, 0x4f35, 0xa7,0x46, 0xde,0x8d,0xb6,0x36,0x17,0xe6);
@@ -39,11 +40,32 @@ typedef struct {
static const ssize_t KEYLEN = 16;
#define DRIVEMAX (100)
#define LOGFILELEN (300)
+#define SETTINGS_FILE "B:\\GERAFFEL.INI"
+#define SETTINGS_FILE_W L"B:\\GERAFFEL.INI"
static BOOL bGetShares = FALSE;
static netdrive_t drives[DRIVEMAX];
static wchar_t desktopPath[MAX_PATH+1], tempPath[MAX_PATH+1], programsPath[MAX_PATH+1], windowsPath[MAX_PATH+1];
static wchar_t logFile[LOGFILELEN];
+static DWORD _startTime;
+#define FS_UNKNOWN (-1)
+#define FS_ERROR (0)
+#define FS_OK (1)
+static int _folderStatus = FS_UNKNOWN; // -1 = Not handled yet, 0 = patching failed, 1 = remapped ok
+#define RM_NONE (0)
+#define RM_NATIVE (1)
+#define RM_NATIVE_FALLBACK (2)
+#define RM_VMWARE (3)
+static int _remapMode = RM_NONE;
+
+struct {
+ BOOL documents;
+ BOOL downloads;
+ BOOL desktop;
+ BOOL media;
+ BOOL other;
+} remap;
+static BOOL _createMissingRemap = FALSE;
static int setResolution();
static int muteSound();
@@ -52,6 +74,9 @@ static void readShareFile();
static BOOL mountNetworkShares();
static int queryPasswordDaemon();
static BOOL fileExists(wchar_t* szPath);
+static BOOL folderExists(wchar_t* szPath);
+static void patchUserPaths(wchar_t *letter);
+static void remapViaSharedFolder();
static HRESULT createFolderShortcut(wchar_t* sTargetfile, wchar_t* sLinkfile, wchar_t* comment);
@@ -73,17 +98,30 @@ static void alog(const char *fmt, ...)
fclose(f);
}
-/*
static void wlog(const wchar_t *fmt, ...)
{
- char buffer[1000];
- if (MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)suser, -1, (LPWSTR)nuser, BUFLEN) == 0)
- return;
-}
-*/
+ wchar_t wbuffer[1000];
+ char abuffer[1000];
+ va_list args;
+ FILE *f = _wfopen(logFile, L"a+");
+ if (f == NULL) return;
+ time_t raw = time(NULL);
+ struct tm *tinf;
+ tinf = localtime(&raw);
+ strftime(abuffer, 1000, "%I:%M:%S ", tinf);
+ fputs(abuffer, f);
-// TODO: Figure out if no timers are running anymore so we can quit
+ va_start(args, fmt);
+ StringCchVPrintfW(wbuffer, 1000, fmt, args);
+ va_end(args);
+ if (WideCharToMultiByte(CP_UTF8, 0, wbuffer, -1, abuffer, 1000, NULL, NULL) == 0) {
+ snprintf(abuffer, 1000, "Cannot wlog: widechar to utf8 failed.");
+ }
+ fputs(abuffer, f);
+ fputc('\n', f);
+ fclose(f);
+}
static void CALLBACK resetShutdown(HWND hWnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
{
@@ -114,22 +152,40 @@ static void CALLBACK setupNetworkDrives(HWND hWnd, UINT uMsg, UINT_PTR idEvent,
if (bInProc)
return;
bInProc = TRUE;
- int ret = queryPasswordDaemon();
- if (ret != 0) {
- if (++fails < 10)
- goto exit_func;
- alog("queryPasswordDaemon returned %d", ret);
+ if (!bGetShares && (_remapMode == RM_NATIVE_FALLBACK || _remapMode == RM_VMWARE)) {
+ remapViaSharedFolder();
} else {
- if (!mountNetworkShares() && ++fails < 15)
- goto exit_func;
+ int ret = queryPasswordDaemon();
+ if (ret != 0) {
+ if (++fails < 10)
+ goto exit_func;
+ alog("queryPasswordDaemon returned %d", ret);
+ } else {
+ if (!mountNetworkShares()) {
+ if (GetTickCount() - _startTime < 30000 && ++fails < 15)
+ goto exit_func;
+ }
+ }
+ // Finished successfully or failed completely
+ if (_folderStatus != FS_OK) {
+ remapViaSharedFolder();
+ }
}
KillTimer(hWnd, idEvent);
+ if (_remapMode != RM_NONE) {
+ if (_folderStatus == FS_ERROR) {
+ MessageBoxA(NULL, "Fehler beim Einbinden des Home-Verzeichnisses. Bitte nichts Wichtiges in der VM speichern, sondern z.B. einen USB-Stick verwenden.", "Warnung", MB_ICONERROR);
+ } else if (_folderStatus == FS_UNKNOWN) {
+ MessageBoxA(NULL, "Kein Home-Verzeichnis gefunden. Bitte nichts Wichtiges in der VM speichern, sondern z.B. einen USB-Stick verwenden.", "Warnung", MB_ICONERROR);
+ }
+ }
exit_func:
bInProc = FALSE;
}
static void loadPaths()
{
+ // Determine a couple of default directories
if (SHGetFolderPathW(HWND_DESKTOP, CSIDL_PROGRAM_FILES, NULL, SHGFP_TYPE_CURRENT, programsPath) != S_OK) {
DWORD ret = GetEnvironmentVariableW(L"ProgramFiles", programsPath, MAX_PATH+1);
if (ret == 0 || ret > MAX_PATH) {
@@ -162,6 +218,14 @@ static void loadPaths()
_wremove(logFile);
}
}
+ // Read settings from ini file
+ remap.documents = GetPrivateProfileIntA("remap", "documents", 1, SETTINGS_FILE) != 0;
+ remap.downloads = GetPrivateProfileIntA("remap", "downloads", 1, SETTINGS_FILE) != 0;
+ remap.desktop = GetPrivateProfileIntA("remap", "desktop", 0, SETTINGS_FILE) != 0;
+ remap.media = GetPrivateProfileIntA("remap", "media", 1, SETTINGS_FILE) != 0;
+ remap.other = GetPrivateProfileIntA("remap", "other", 0, SETTINGS_FILE) != 0;
+ _createMissingRemap = GetPrivateProfileIntA("openslx", "createMissingRemap", 1, SETTINGS_FILE) != 0;
+ _remapMode = GetPrivateProfileIntA("openslx", "remapMode", RM_NATIVE_FALLBACK, SETTINGS_FILE);
}
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd)
@@ -170,6 +234,7 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine
version.dwOSVersionInfoSize = sizeof(version);
BOOL retVer = GetVersionEx(&version);
CoInitialize(NULL);
+ _startTime = GetTickCount();
loadPaths();
// Mute sound by default
if (retVer && version.dwMajorVersion >= 6)
@@ -184,8 +249,8 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine
}
// Any network shares to mount?
readShareFile();
- if (bGetShares) {
- UINT_PTR tRet = SetTimer(NULL, 0, 2550, (TIMERPROC)&setupNetworkDrives);
+ if (bGetShares || _remapMode != RM_NONE) {
+ UINT_PTR tRet = SetTimer(NULL, 0, 1550, (TIMERPROC)&setupNetworkDrives);
if (tRet == 0) {
alog("Could not create timer for mounting network shares: %d", (int)GetLastError());
}
@@ -194,13 +259,13 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine
if (retVer && version.dwMajorVersion == 6 && version.dwMinorVersion == 1) {
// Only on Windows 7
// Repeatedly set caption
- UINT_PTR tRet = SetTimer(NULL, 0, 5030, (TIMERPROC)&resetShutdown);
+ UINT_PTR tRet = SetTimer(NULL, 0, 5230, (TIMERPROC)&resetShutdown);
if (tRet == 0) {
alog("Could not create timer for shutdown button: %d", (int)GetLastError());
}
}
// Resolution
- if (fileExists(L"B:\\hostres.txt") && setResolution() != 0) {
+ if (fileExists(SETTINGS_FILE_W) && setResolution() != 0) {
UINT_PTR tRet = SetTimer(NULL, 0, 3111, (TIMERPROC)&tmrResolution);
if (tRet == 0) {
alog("Could not create timer for resolution setting: %d", (int)GetLastError());
@@ -218,7 +283,40 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine
static BOOL fileExists(wchar_t* szPath)
{
DWORD dwAttrib = GetFileAttributesW(szPath);
- return (dwAttrib != INVALID_FILE_ATTRIBUTES && !(dwAttrib & FILE_ATTRIBUTE_DIRECTORY));
+ return (dwAttrib != INVALID_FILE_ATTRIBUTES && (dwAttrib & FILE_ATTRIBUTE_DIRECTORY) == 0);
+}
+
+static BOOL folderExists(wchar_t* szPath)
+{
+ DWORD dwAttrib = GetFileAttributesW(szPath);
+ return (dwAttrib != INVALID_FILE_ATTRIBUTES && (dwAttrib & FILE_ATTRIBUTE_DIRECTORY) != 0);
+}
+
+static int execute(wchar_t *path, wchar_t *arguments)
+{
+ STARTUPINFOW si;
+ PROCESS_INFORMATION pi;
+ ZeroMemory(&si, sizeof(si));
+ ZeroMemory(&pi, sizeof(pi));
+ si.cb = sizeof(si);
+ if (!CreateProcessW(path, arguments, NULL, NULL, FALSE, NORMAL_PRIORITY_CLASS | CREATE_NO_WINDOW, NULL, NULL, &si, &pi)) {
+ return -1;
+ }
+ while (MsgWaitForMultipleObjects(1, &pi.hProcess, FALSE, INFINITE, QS_SENDMESSAGE) == WAIT_OBJECT_0+1) {
+ MSG Msg;
+ while(PeekMessage(&Msg, NULL, 0, 0, PM_REMOVE | PM_QS_SENDMESSAGE)) {
+ TranslateMessage(&Msg);
+ DispatchMessage(&Msg);
+ }
+ }
+ DWORD exitCode;
+ BOOL ret = GetExitCodeProcess(pi.hProcess, &exitCode);
+ CloseHandle(pi.hProcess);
+ CloseHandle(pi.hThread);
+ if (!ret) {
+ return -2;
+ }
+ return (int)exitCode;
}
static int setResolution()
@@ -227,24 +325,18 @@ static int setResolution()
static int width = 0, height = 0;
if (width == 0 && height == 0) {
// use config file in floppy
- FILE *h = fopen("B:\\hostres.txt", "rb");
- if (h == NULL) {
- alog("b:\\hostres.txt not found");
- return 0;
- }
char data[200] = "";
- fread(data, 200, 1, h);
- fclose(h);
+ GetPrivateProfileStringA("openslx", "resolution", "", data, sizeof(data), SETTINGS_FILE);
char *x = strchr(data, 'x');
if (x == NULL) {
- alog("Malformed resolution in hostres.txt: '%s'", data);
+ alog("Malformed resolution in " SETTINGS_FILE ": '%s'", data);
return 0;
}
*x++ = '\0';
width = atoi(data);
height = atoi(x);
if (width < 320 || height < 240) {
- alog("Invalid resolution in hostres.txt: '%s' (parsed width=%d, height=%d)", data, width, height);
+ alog("Invalid resolution in " SETTINGS_FILE ": '%s' (parsed width=%d, height=%d)", data, width, height);
return 0;
}
}
@@ -266,26 +358,13 @@ static int setResolution()
}
}
if (path[0] != 0 && fileExists(path)) {
- STARTUPINFOW si;
- PROCESS_INFORMATION pi;
wchar_t cmdline[MAX_PATH];
- ZeroMemory(&si, sizeof(si));
- ZeroMemory(&pi, sizeof(pi));
- si.cb = sizeof(si);
StringCchPrintfW(cmdline, MAX_PATH, L"VMwareResolutionSet.exe 0 1 , 0 0 %d %d", width, height);
- if (CreateProcessW(path, cmdline, NULL, NULL, FALSE, NORMAL_PRIORITY_CLASS | CREATE_NO_WINDOW, NULL, NULL, &si, &pi)) {
- WaitForSingleObject(pi.hProcess, INFINITE);
- DWORD exitCode;
- BOOL ret = GetExitCodeProcess(pi.hProcess, &exitCode);
- CloseHandle(pi.hProcess);
- CloseHandle(pi.hThread);
- if (ret && exitCode == 0) {
- return 0;
- }
- alog("vmware res set executed but failed (ret %d, code %d, lasterror %d)",
- (int)ret, (int)exitCode, (int)GetLastError());
- } else {
- alog("createprocess for vmware res set failed with code %d", (int)GetLastError());
+ int ret = execute(path, cmdline);
+ if (ret == -1) {
+ alog("VmwareRes: CreateProcess failed (%d)", (int)GetLastError());
+ } else if (ret == -2) {
+ alog("VmwareRes: GetExitCode failed (%d)", (int)GetLastError());
}
}
// Use WinAPI as fallback
@@ -518,6 +597,7 @@ static void udpReceived(SOCKET sock)
// Success
spass = xorString(buffer + 2, len, bkey2);
closesocket(sock);
+ mountNetworkShares();
}
#define BUFLEN (200)
@@ -526,20 +606,22 @@ static DWORD mount(LPNETRESOURCEW share, LPWSTR pass, LPWSTR user)
{
DWORD retval;
// Now try to mount
- retval = WNetAddConnection2W(share, pass, user, CONNECT_TEMPORARY | CONNECT_CURRENT_MEDIA);
- if (retval == NO_ERROR) {
- return retval;
- }
- if (retval != ERROR_INVALID_PASSWORD && retval != ERROR_LOGON_FAILURE
- && retval != ERROR_BAD_USERNAME && retval != ERROR_ACCESS_DENIED
- && retval != ERROR_SESSION_CREDENTIAL_CONFLICT) {
- return retval;
+ if ((pass && *pass) || (user && *user)) {
+ retval = WNetAddConnection2W(share, pass, user, CONNECT_TEMPORARY | CONNECT_CURRENT_MEDIA);
+ if (retval == NO_ERROR) {
+ return retval;
+ }
+ if (retval != ERROR_INVALID_PASSWORD && retval != ERROR_LOGON_FAILURE
+ && retval != ERROR_BAD_USERNAME && retval != ERROR_ACCESS_DENIED
+ && retval != ERROR_SESSION_CREDENTIAL_CONFLICT) {
+ return retval;
+ }
}
static wchar_t nuser[BUFLEN] = L"", npass[BUFLEN] = L"";
if (nuser[0] == 0 && npass[0] == 0) {
- int ok = -1;
- ok &= MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)suser, -1, (LPWSTR)nuser, BUFLEN) > 0;
- ok &= MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)spass, -1, (LPWSTR)npass, BUFLEN) > 0;
+ BOOL ok = TRUE;
+ ok = MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)suser, -1, (LPWSTR)nuser, BUFLEN) > 0 && ok;
+ ok = MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)spass, -1, (LPWSTR)npass, BUFLEN) > 0 && ok;
if (!ok)
return ERROR_INVALID_PARAMETER;
}
@@ -547,17 +629,26 @@ static DWORD mount(LPNETRESOURCEW share, LPWSTR pass, LPWSTR user)
return retval;
}
-static void mkshortcut(const netdrive_t *d, wchar_t *comment)
+static void postSuccessfulMount(const netdrive_t *d, wchar_t *letter)
{
- if (d->shortcut == NULL || strlen(d->shortcut) == 0)
- return;
- wchar_t tmp[MAX_PATH], wShortcut[MAX_PATH], wTarget[MAX_PATH];
- MultiByteToWideChar(CP_UTF8, 0, d->shortcut, -1, tmp, MAX_PATH);
- StringCchPrintfW(wShortcut, MAX_PATH, L"%s\\%s.lnk", desktopPath, tmp);
- MultiByteToWideChar(CP_UTF8, 0, d->path, -1, tmp, MAX_PATH);
- StringCchPrintfW(wTarget, MAX_PATH, L"\"%s\"", tmp);
- DeleteFileW(wShortcut);
- createFolderShortcut(wTarget, wShortcut, comment);
+ if (d->shortcut != NULL && strlen(d->shortcut) != 0) {
+ wchar_t tmp[MAX_PATH], wShortcut[MAX_PATH], wTarget[MAX_PATH];
+ MultiByteToWideChar(CP_UTF8, 0, d->shortcut, -1, tmp, MAX_PATH);
+ StringCchPrintfW(wShortcut, MAX_PATH, L"%s\\%s.lnk", desktopPath, tmp);
+ MultiByteToWideChar(CP_UTF8, 0, d->path, -1, tmp, MAX_PATH);
+ StringCchPrintfW(wTarget, MAX_PATH, L"\"%s\"", tmp);
+ DeleteFileW(wShortcut);
+ createFolderShortcut(wTarget, wShortcut, letter);
+ // Fix paths and kill explorer if it's the home directory
+ if (_folderStatus != FS_OK && strncmp(d->shortcut, "Home-", 5) == 0) {
+ BOOL isVmware = strcmp(d->path, "\\\\vmware-host\\Shared Folders\\home") == 0;
+ if (_remapMode == RM_NATIVE_FALLBACK
+ || (isVmware && _remapMode == RM_VMWARE)
+ || (!isVmware && _remapMode == RM_NATIVE)) {
+ patchUserPaths(letter);
+ }
+ }
+ }
}
static BOOL mountNetworkShare(const netdrive_t *d)
@@ -592,17 +683,10 @@ static BOOL mountNetworkShare(const netdrive_t *d)
letter[3] = 0;
if (letter[0] != 0) {
// Try with specific letter
- // Get anything there might be out of the way
- WNetCancelConnection2W(letter, CONNECT_UPDATE_PROFILE, TRUE);
- WNetCancelConnection2W(letter, 0, TRUE);
- letter[2] = '\\';
- WNetCancelConnection2W(letter, 0, TRUE);
- DeleteVolumeMountPointW(letter);
- letter[2] = 0;
// Connect defined share
retval = mount(&share, pass, user);
if (retval == NO_ERROR) {
- mkshortcut(d, letter);
+ postSuccessfulMount(d, letter);
return TRUE;
}
if (retval != ERROR_ALREADY_ASSIGNED && retval != ERROR_DEVICE_ALREADY_REMEMBERED
@@ -618,7 +702,7 @@ static BOOL mountNetworkShare(const netdrive_t *d)
|| retval == ERROR_CONNECTION_UNAVAIL)
continue;
if (retval == NO_ERROR) {
- mkshortcut(d, letter);
+ postSuccessfulMount(d, letter);
return TRUE;
}
alog("mountNetworkShare: without letter failed: %d", (int)retval);
@@ -656,6 +740,18 @@ static BOOL mountNetworkShares()
return TRUE;
}
+static void remapViaSharedFolder()
+{
+ netdrive_t d;
+ d.path = (char*)"\\\\vmware-host\\Shared Folders\\home";
+ d.letter = (char*)"H:";
+ d.shortcut = (char*)"Home-Verzeichnis";
+ d.user = NULL;
+ d.pass = NULL;
+ d.success = FALSE;
+ mountNetworkShare(&d);
+}
+
static char* xorString(const uint8_t* text, int len, const uint8_t* key)
{
int i;
@@ -734,3 +830,104 @@ static HRESULT createFolderShortcut(wchar_t* targetDir, wchar_t* linkFile, wchar
return (hRes);
}
+// Patch user directories
+
+static BOOL patchRegPath(HKEY hKey, wchar_t *letter, wchar_t *value, ...)
+{
+ wchar_t *folder = NULL;
+ wchar_t first[MAX_PATH] = {0};
+ wchar_t path[MAX_PATH];
+ va_list args;
+ va_start(args, value);
+ while ((folder = va_arg(args, wchar_t*)) != NULL) {
+ StringCchPrintfW(path, MAX_PATH, L"%s\\%s", letter, folder);
+ if (folderExists(path))
+ break;
+ if (*first == 0) {
+ wcsncpy(first, path, MAX_PATH);
+ }
+ }
+ va_end(args);
+ if (folder != NULL) {
+ // Found something existing
+ folder = path;
+ } else if (!_createMissingRemap) {
+ // Nothing found, must not create
+ wlog(L"Cannot remap %s to %s: target not found!", value, first);
+ return FALSE;
+ } else {
+ // Nothing found, use first element of list and create it
+ folder = first;
+ CreateDirectoryW(folder, NULL);
+ }
+ LONG ret = RegSetValueExW(hKey, value, 0, REG_SZ, (BYTE*)folder, (wcslen(folder) + 1) * sizeof(wchar_t));
+ if (ret != ERROR_SUCCESS) {
+ alog("Setting reg key failed (return value %ld)", (long)ret);
+ }
+ return ret == ERROR_SUCCESS;
+}
+
+static void patchUserPaths(wchar_t *letter)
+{
+ LONG ret;
+ HKEY hKey;
+ BOOL patchOk = TRUE;
+ BOOL killOk = FALSE;
+ _folderStatus = 0;
+ ret = RegOpenKeyExW(HKEY_CURRENT_USER,
+ L"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\User Shell Folders",
+ 0, KEY_WOW64_64KEY | KEY_READ | KEY_WRITE, &hKey);
+ if (ret != ERROR_SUCCESS) {
+ alog("Opening registry for patching of pathes failed with return code %ld", (long)ret);
+ return;
+ }
+ // Ha!
+ if (remap.other) {
+ patchOk = patchRegPath(hKey, letter, L"{56784854-C6CB-462B-8169-88E350ACB882}", L"Contacts", L"Profile\\Contacts", L"Kontakte", NULL) && patchOk;
+ patchOk = patchRegPath(hKey, letter, L"Favorites", L"Favorites", L"Profile\\Favorites", L"Favoriten", NULL) && patchOk;
+ patchOk = patchRegPath(hKey, letter, L"{7D1D3A04-DEBB-4115-95CF-2F29DA2920DA}", L"Searches", L"Profile\\Searches", NULL) && patchOk;
+ patchOk = patchRegPath(hKey, letter, L"{BFB9D5E0-C6A9-404C-B2B2-AE6DB6AF4968}", L"Links", L"Profile\\Links", NULL) && patchOk;
+ patchOk = patchRegPath(hKey, letter, L"{4C5C32FF-BB9D-43B0-B5B4-2D72E54EAAA4}", L"Saved Games", L"SavedGames", L"Profile\\SavedGames", NULL) && patchOk;
+ }
+ if (remap.media) {
+ patchOk = patchRegPath(hKey, letter, L"My Video", L"Videos", L"My Videos", L"Eigene Videos", NULL) && patchOk;
+ patchOk = patchRegPath(hKey, letter, L"My Pictures", L"Pictures", L"My Pictures", L"Eigene Bilder", L"Bilder", NULL) && patchOk;
+ patchOk = patchRegPath(hKey, letter, L"My Music", L"Music", L"My Music", L"Eigene Musik", L"Musik", NULL) && patchOk;
+ }
+ if (remap.downloads) {
+ patchOk = patchRegPath(hKey, letter, L"{374DE290-123F-4565-9164-39C4925E467B}", L"Downloads", L"Profile\\Downloads", NULL) && patchOk;
+ }
+ if (remap.documents) {
+ patchOk = patchRegPath(hKey, letter, L"Personal", L"Documents", L"Dokumente", L"My Documents", L"Eigene Dateien", NULL) && patchOk;
+ }
+ if (remap.desktop) {
+ patchOk = patchRegPath(hKey, letter, L"Desktop", L"Windows Desktop", L"Desktop", L"Arbeitsfl\u00E4che", NULL) && patchOk;
+ }
+ RegCloseKey(hKey);
+ // Kill explorer
+ PROCESSENTRY32W entry;
+ entry.dwSize = sizeof(PROCESSENTRY32W);
+ HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
+ if (snapshot != INVALID_HANDLE_VALUE && Process32FirstW(snapshot, &entry)) {
+ do {
+ if (_wcsicmp(entry.szExeFile, L"explorer.exe") == 0) {
+ HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, entry.th32ProcessID);
+ if (hProcess == NULL) {
+ alog("Opening explorer.exe failed");
+ } else {
+ if (TerminateProcess(hProcess, 23)) {
+ killOk = TRUE;
+ }
+ CloseHandle(hProcess);
+ }
+ }
+ } while (Process32NextW(snapshot, &entry));
+ } else {
+ alog("Could not get process list");
+ }
+ CloseHandle(snapshot);
+ if (patchOk && killOk) {
+ _folderStatus = 1;
+ }
+}
+