diff options
author | Mounir IDRASSI <mounir.idrassi@idrix.fr> | 2019-10-18 00:55:32 +0200 |
---|---|---|
committer | Mounir IDRASSI <mounir.idrassi@idrix.fr> | 2019-10-18 00:56:39 +0200 |
commit | 5b88a183ac297cbb7d332b23a6800bd4681da7db (patch) | |
tree | 40a73594bd50fbf4631c2680e1e676e7a8ce6c19 /src | |
parent | 4119521f9e7e11f6bae29963605b9acb2960fa8c (diff) | |
download | VeraCrypt-5b88a183ac297cbb7d332b23a6800bd4681da7db.tar.gz VeraCrypt-5b88a183ac297cbb7d332b23a6800bd4681da7db.zip |
Windows: handle case of DcsProp configuration file for EFI system encryption contains wrong "ActionSuccess" entry that points towards bootmgfw.efi which is now our bootloader and not Microsoft one.
Diffstat (limited to 'src')
-rw-r--r-- | src/Common/BootEncryption.cpp | 121 | ||||
-rw-r--r-- | src/Common/BootEncryption.h | 2 |
2 files changed, 93 insertions, 30 deletions
diff --git a/src/Common/BootEncryption.cpp b/src/Common/BootEncryption.cpp index cc3caa92..597a567d 100644 --- a/src/Common/BootEncryption.cpp +++ b/src/Common/BootEncryption.cpp @@ -2364,6 +2364,35 @@ namespace VeraCrypt WriteConfigInteger (configFile, configContent, "AuthorizeRetry", authorizeRetry); WriteConfigInteger (configFile, configContent, "DcsBmlLockFlags", bmlLockFlags); WriteConfigInteger (configFile, configContent, "DcsBmlDriver", bmlDriverEnabled); + + string fieldValue; + if (IsPostExecFileField(actionSuccessValue, fieldValue) && (0 == _stricmp(fieldValue.c_str(), "\\EFI\\Microsoft\\Boot\\bootmgfw.efi"))) + { + // fix wrong configuration file since bootmgfw.efi is now a copy of VeraCrypt and if we don't fix the DcsProp + // file, veraCrypt bootloader will call itself + // We first check if bootmgfw.efi is original Microsoft one. If yes, we don't do anything, otherwise we set the field to bootmgfw_ms.vc + unsigned __int64 loaderSize = 0; + bool bModifiedMsBoot = true; + EfiBootInst.GetFileSize(L"\\EFI\\Microsoft\\Boot\\bootmgfw.efi", loaderSize); + + if (loaderSize > 32768) + { + std::vector<byte> bootLoaderBuf ((size_t) loaderSize); + + EfiBootInst.ReadFile(L"\\EFI\\Microsoft\\Boot\\bootmgfw.efi", &bootLoaderBuf[0], (DWORD) loaderSize); + + // look for bootmgfw.efi identifiant string + const char* g_szMsBootString = "bootmgfw.pdb"; + if (BufferHasPattern (bootLoaderBuf.data (), (size_t) loaderSize, g_szMsBootString, strlen (g_szMsBootString))) + { + bModifiedMsBoot = false; + } + } + + if (bModifiedMsBoot) + actionSuccessValue = "postexec file(EFI\\Microsoft\\Boot\\bootmgfw_ms.vc)"; + } + WriteConfigString (configFile, configContent, "ActionSuccess", actionSuccessValue.c_str()); // Write unmodified values @@ -2396,6 +2425,55 @@ namespace VeraCrypt return bRet; } + BOOL EfiBootConf::IsPostExecFileField (const string& fieldValue, string& filePath) + { + BOOL bRet = FALSE; + filePath = ""; + + if (!fieldValue.empty() && strlen (fieldValue.c_str())) + { + string copieValue = fieldValue; + std::transform(copieValue.begin(), copieValue.end(), copieValue.begin(), ::tolower); + + if (strstr (copieValue.c_str(), "postexec") && strstr (copieValue.c_str(), "file(")) + { + char c; + const char* ptr = strstr (copieValue.c_str(), "file("); + + filePath = "\\"; + ptr += 5; + while ((c = *ptr)) + { + if (c == ')') + break; + if (c == '/') + c = '\\'; + filePath += c; + ptr++; + } + + if (c == ')') + bRet = TRUE; + else + filePath = ""; + } + } + + return bRet; + } + + BOOL EfiBootConf::IsPostExecFileField (const string& fieldValue, wstring& filePath) + { + string aPath; + BOOL bRet = IsPostExecFileField (fieldValue, aPath); + if (bRet) + filePath = wstring(aPath.begin(), aPath.end()); + else + filePath = L""; + + return bRet; + } + static const wchar_t* EfiVarGuid = L"{8BE4DF61-93CA-11D2-AA0D-00E098032B8C}"; void @@ -3120,24 +3198,15 @@ namespace VeraCrypt EfiBootConf conf; if (EfiBootInst.ReadConfig (L"\\EFI\\VeraCrypt\\DcsProp", conf) && strlen (conf.actionSuccessValue.c_str())) { - string actionValue = conf.actionSuccessValue; - std::transform(actionValue.begin(), actionValue.end(), actionValue.begin(), ::tolower); - - if (strstr (actionValue.c_str(), "postexec") && strstr (actionValue.c_str(), "file(")) + wstring loaderPath; + if (EfiBootConf::IsPostExecFileField (conf.actionSuccessValue, loaderPath)) { - char c; - const char* ptr = strstr (actionValue.c_str(), "file("); - ptr += 5; - wstring loaderPath = L"\\"; - while ((c = *ptr)) + // check that it is not bootmgfw.efi + if (0 != _wcsicmp (loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw.efi")) { - if (c == ')' || c == ' ') - break; - loaderPath += (wchar_t) c; - ptr++; + bFound = true; + EfiBootInst.RenameFile(loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw_ms.vc", TRUE); } - bFound = true; - EfiBootInst.RenameFile(loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw_ms.vc", TRUE); } } @@ -4230,24 +4299,16 @@ namespace VeraCrypt EfiBootConf conf; if (EfiBootInst.ReadConfig (L"\\EFI\\VeraCrypt\\DcsProp", conf) && strlen (conf.actionSuccessValue.c_str())) { - string actionValue = conf.actionSuccessValue; - std::transform(actionValue.begin(), actionValue.end(), actionValue.begin(), ::tolower); - - if (strstr (actionValue.c_str(), "postexec") && strstr (actionValue.c_str(), "file(")) + wstring loaderPath; + if (EfiBootConf::IsPostExecFileField (conf.actionSuccessValue, loaderPath)) { - char c; - const char* ptr = strstr (actionValue.c_str(), "file("); - ptr += 5; - wstring loaderPath = L"\\"; - while ((c = *ptr)) + // check that it is not bootmgfw_ms.vc or bootmgfw.efi + if ( (0 != _wcsicmp (loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw_ms.vc")) + && (0 != _wcsicmp (loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw.efi")) + ) { - if (c == ')' || c == ' ') - break; - loaderPath += (wchar_t) c; - ptr++; + EfiBootInst.RenameFile(loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw.efi", TRUE); } - - EfiBootInst.RenameFile(loaderPath.c_str(), L"\\EFI\\Microsoft\\Boot\\bootmgfw.efi", TRUE); } } } diff --git a/src/Common/BootEncryption.h b/src/Common/BootEncryption.h index 0b5fe4f0..de4f7489 100644 --- a/src/Common/BootEncryption.h +++ b/src/Common/BootEncryption.h @@ -189,6 +189,8 @@ namespace VeraCrypt BOOL Load (const wchar_t* fileName); void Load (char* configContent); BOOL Save (const wchar_t* fileName, HWND hwnd); + static BOOL IsPostExecFileField (const string& szFieldValue, string& filePath); + static BOOL IsPostExecFileField (const string& szFieldValue, wstring& filePath); }; void GetVolumeESP(wstring& path); |