VeraCrypt
aboutsummaryrefslogtreecommitdiff
path: root/src/Common/Dlgcode.c
diff options
context:
space:
mode:
authorMounir IDRASSI <mounir.idrassi@idrix.fr>2016-12-30 12:17:09 +0100
committerMounir IDRASSI <mounir.idrassi@idrix.fr>2016-12-30 23:56:28 +0100
commitcdbe54e60542231f832d59389381bf9b56b710be (patch)
treecc71665cba8e86003f65c9385a166e787b8966aa /src/Common/Dlgcode.c
parentd116eba1607ca82d90874018037a19088a4bb26d (diff)
downloadVeraCrypt-cdbe54e60542231f832d59389381bf9b56b710be.tar.gz
VeraCrypt-cdbe54e60542231f832d59389381bf9b56b710be.zip
Windows: Implement Secure Desktop for password entry. Add option and command line switch to activate it.
Diffstat (limited to 'src/Common/Dlgcode.c')
-rw-r--r--src/Common/Dlgcode.c176
1 files changed, 176 insertions, 0 deletions
diff --git a/src/Common/Dlgcode.c b/src/Common/Dlgcode.c
index 001d7102..3fc5c06a 100644
--- a/src/Common/Dlgcode.c
+++ b/src/Common/Dlgcode.c
@@ -26,6 +26,11 @@
26#include <time.h> 26#include <time.h>
27#include <tchar.h> 27#include <tchar.h>
28#include <Richedit.h> 28#include <Richedit.h>
29#ifdef TCMOUNT
30#include <Shlwapi.h>
31#include <process.h>
32#include <Tlhelp32.h>
33#endif
29 34
30#include "Resource.h" 35#include "Resource.h"
31 36
@@ -108,6 +113,9 @@ BOOL bShowDisconnectedNetworkDrives = FALSE;
108BOOL bHideWaitingDialog = FALSE; 113BOOL bHideWaitingDialog = FALSE;
109BOOL bCmdHideWaitingDialog = FALSE; 114BOOL bCmdHideWaitingDialog = FALSE;
110BOOL bCmdHideWaitingDialogValid = FALSE; 115BOOL bCmdHideWaitingDialogValid = FALSE;
116BOOL bUseSecureDesktop = FALSE;
117BOOL bCmdUseSecureDesktop = FALSE;
118BOOL bCmdUseSecureDesktopValid = FALSE;
111BOOL bStartOnLogon = FALSE; 119BOOL bStartOnLogon = FALSE;
112BOOL bMountDevicesOnLogon = FALSE; 120BOOL bMountDevicesOnLogon = FALSE;
113BOOL bMountFavoritesOnLogon = FALSE; 121BOOL bMountFavoritesOnLogon = FALSE;
@@ -12225,3 +12233,171 @@ BOOL DeleteDirectory (const wchar_t* szDirName)
12225 } 12233 }
12226 return bStatus; 12234 return bStatus;
12227} 12235}
12236
12237#ifdef TCMOUNT
12238/*********************************************************************/
12239
12240static BOOL GenerateRandomString (HWND hwndDlg, LPTSTR szName, DWORD maxCharsCount)
12241{
12242 BOOL bRet = FALSE;
12243 if (Randinit () != ERR_SUCCESS)
12244 {
12245 handleError (hwndDlg, (CryptoAPILastError == ERROR_SUCCESS)? ERR_RAND_INIT_FAILED : ERR_CAPI_INIT_FAILED, SRC_POS);
12246 }
12247 else
12248 {
12249 BYTE* indexes = (BYTE*) malloc (maxCharsCount + 1);
12250 bRet = RandgetBytesFull (hwndDlg, indexes, maxCharsCount + 1, TRUE, TRUE);
12251 if (bRet)
12252 {
12253 static LPCTSTR chars = _T("0123456789@#$%^&_-*abcdefghijklmnopqrstuvwxyz");
12254 DWORD i, charsLen = (DWORD) _tcslen (chars);
12255 DWORD effectiveLen = (indexes[0] % (64 - 16)) + 16; // random length between 16 to 64
12256 effectiveLen = (effectiveLen > maxCharsCount)? maxCharsCount : effectiveLen;
12257
12258 for (i = 0; i < effectiveLen; i++)
12259 {
12260 szName[i] = chars[indexes[i + 1] % charsLen];
12261 }
12262
12263 szName[effectiveLen] = 0;
12264 }
12265 burn (indexes, maxCharsCount + 1);
12266 free (indexes);
12267 }
12268
12269 return bRet;
12270}
12271
12272typedef struct
12273{
12274 HDESK hDesk;
12275 HINSTANCE hInstance;
12276 LPCWSTR lpTemplateName;
12277 DLGPROC lpDialogFunc;
12278 LPARAM dwInitParam;
12279 INT_PTR retValue;
12280} SecureDesktopThreadParam;
12281
12282static DWORD WINAPI SecureDesktopThread(LPVOID lpThreadParameter)
12283{
12284 SecureDesktopThreadParam* pParam = (SecureDesktopThreadParam*) lpThreadParameter;
12285
12286 SetThreadDesktop (pParam->hDesk);
12287 SwitchDesktop (pParam->hDesk);
12288
12289 pParam->retValue = DialogBoxParamW (pParam->hInstance, pParam->lpTemplateName,
12290 NULL, pParam->lpDialogFunc, pParam->dwInitParam);
12291
12292 return 0;
12293}
12294
12295static void GetCtfMonProcessIdList (map<DWORD, BOOL>& processIdList)
12296{
12297 HANDLE hSnapShot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);
12298 PROCESSENTRY32 pEntry;
12299 BOOL hRes;
12300
12301 pEntry.dwSize = sizeof (pEntry);
12302 processIdList.clear();
12303 hRes = Process32First(hSnapShot, &pEntry);
12304 while (hRes)
12305 {
12306 LPTSTR szFileName = PathFindFileName (pEntry.szExeFile);
12307 if (_wcsicmp(szFileName, L"ctfmon.exe") == 0)
12308 {
12309 processIdList[pEntry.th32ProcessID] = TRUE;
12310 }
12311 hRes = Process32Next(hSnapShot, &pEntry);
12312 }
12313 CloseHandle(hSnapShot);
12314}
12315
12316static void KillProcess (DWORD dwProcessId)
12317{
12318 HANDLE hProcess = OpenProcess(PROCESS_TERMINATE, 0, dwProcessId);
12319 if (hProcess != NULL)
12320 {
12321 TerminateProcess(hProcess, (UINT) -1);
12322 CloseHandle(hProcess);
12323 }
12324}
12325
12326INT_PTR SecureDesktopDialogBoxParam(
12327 HINSTANCE hInstance,
12328 LPCWSTR lpTemplateName,
12329 HWND hWndParent,
12330 DLGPROC lpDialogFunc,
12331 LPARAM dwInitParam)
12332{
12333 TCHAR szDesktopName[65] = {0};
12334 BOOL bSuccess = FALSE;
12335 INT_PTR retValue = 0;
12336 BOOL bEffectiveUseSecureDesktop = bCmdUseSecureDesktopValid? bCmdUseSecureDesktop : bUseSecureDesktop;
12337
12338 if (bEffectiveUseSecureDesktop && GenerateRandomString (hWndParent, szDesktopName, 64))
12339 {
12340 map<DWORD, BOOL> ctfmonBeforeList, ctfmonAfterList;
12341 DWORD desktopAccess = DESKTOP_CREATEMENU | DESKTOP_CREATEWINDOW | DESKTOP_READOBJECTS | DESKTOP_SWITCHDESKTOP | DESKTOP_WRITEOBJECTS;
12342 HDESK hSecureDesk;
12343
12344 // get the initial list of ctfmon.exe processes before creating new desktop
12345 GetCtfMonProcessIdList (ctfmonBeforeList);
12346
12347 hSecureDesk = CreateDesktop (szDesktopName, NULL, NULL, 0, desktopAccess, NULL);
12348 if (hSecureDesk)
12349 {
12350 HDESK hOriginalDesk = GetThreadDesktop (GetCurrentThreadId ());
12351 SecureDesktopThreadParam param;
12352
12353 param.hDesk = hSecureDesk;
12354 param.hInstance = hInstance;
12355 param.lpTemplateName = lpTemplateName;
12356 param.lpDialogFunc = lpDialogFunc;
12357 param.dwInitParam = dwInitParam;
12358 param.retValue = 0;
12359
12360 HANDLE hThread = ::CreateThread (NULL, 0, SecureDesktopThread, (LPVOID) &param, 0, NULL);
12361 if (hThread)
12362 {
12363 WaitForSingleObject (hThread, INFINITE);
12364 CloseHandle (hThread);
12365
12366 SwitchDesktop (hOriginalDesk);
12367 SetThreadDesktop (hOriginalDesk);
12368
12369 retValue = param.retValue;
12370 bSuccess = TRUE;
12371 }
12372
12373 CloseDesktop (hSecureDesk);
12374
12375 // get the new list of ctfmon.exe processes in order to find the ID of the
12376 // ctfmon.exe instance that corresponds to the desktop we create so that
12377 // we can kill it, otherwise it would remain running
12378 GetCtfMonProcessIdList (ctfmonAfterList);
12379
12380 for (map<DWORD, BOOL>::iterator It = ctfmonAfterList.begin();
12381 It != ctfmonAfterList.end(); It++)
12382 {
12383 if (ctfmonBeforeList[It->first] != TRUE)
12384 {
12385 // Kill process
12386 KillProcess (It->first);
12387 }
12388 }
12389 }
12390
12391 burn (szDesktopName, sizeof (szDesktopName));
12392 }
12393
12394 if (!bSuccess)
12395 {
12396 // fallback to displaying in normal desktop
12397 retValue = DialogBoxParamW (hInstance, lpTemplateName, hWndParent, lpDialogFunc, dwInitParam);
12398 }
12399
12400 return retValue;
12401}
12402
12403#endif