diff options
Diffstat (limited to 'src/Common/BootEncryption.cpp')
-rw-r--r-- | src/Common/BootEncryption.cpp | 32 |
1 files changed, 19 insertions, 13 deletions
diff --git a/src/Common/BootEncryption.cpp b/src/Common/BootEncryption.cpp index 1a467eed..0fec2878 100644 --- a/src/Common/BootEncryption.cpp +++ b/src/Common/BootEncryption.cpp @@ -15,40 +15,42 @@ #include <shlobj.h>
#include <atlbase.h>
#include "BootEncryption.h"
#include "Boot/Windows/BootCommon.h"
#include "Common/Resource.h"
#include "Crc.h"
#include "Crypto.h"
#include "Dlgcode.h"
#include "Endian.h"
#include "Language.h"
#include "Random.h"
#include "Registry.h"
#include "Volumes.h"
#ifdef VOLFORMAT
#include "Format/FormatCom.h"
#elif defined (TCMOUNT)
#include "Mount/MainCom.h"
#endif
+#include <Strsafe.h>
+
namespace VeraCrypt
{
#if !defined (SETUP)
class Elevator
{
public:
static void AddReference ()
{
++ReferenceCount;
}
static void CallDriver (DWORD ioctl, void *input, DWORD inputSize, void *output, DWORD outputSize)
{
Elevate();
CComBSTR inputBstr;
if (input && inputBstr.AppendBytes ((const char *) input, inputSize) != S_OK)
@@ -587,100 +589,100 @@ namespace VeraCrypt throw_sys_if (!ChangeServiceConfig (service, SERVICE_NO_CHANGE, SERVICE_NO_CHANGE,
startOnBoot ? SERVICE_ERROR_SEVERE : SERVICE_ERROR_NORMAL,
driverPath.empty() ? NULL : driverPath.c_str(),
startOnBoot ? "Filter" : NULL,
NULL, NULL, NULL, NULL, NULL));
// ChangeServiceConfig() rejects SERVICE_BOOT_START with ERROR_INVALID_PARAMETER
throw_sys_if (!WriteLocalMachineRegistryDword ("SYSTEM\\CurrentControlSet\\Services\\veracrypt", "Start", startType));
}
void BootEncryption::ProbeRealSystemDriveSize ()
{
if (RealSystemDriveSizeValid)
return;
GetSystemDriveConfiguration();
ProbeRealDriveSizeRequest request;
- _snwprintf (request.DeviceName, array_capacity (request.DeviceName), L"%hs", DriveConfig.DrivePartition.DevicePath.c_str());
+ StringCbPrintfW (request.DeviceName, sizeof (request.DeviceName), L"%hs", DriveConfig.DrivePartition.DevicePath.c_str());
CallDriver (TC_IOCTL_PROBE_REAL_DRIVE_SIZE, &request, sizeof (request), &request, sizeof (request));
DriveConfig.DrivePartition.Info.PartitionLength = request.RealDriveSize;
RealSystemDriveSizeValid = true;
if (request.TimeOut)
throw TimeOut (SRC_POS);
}
void BootEncryption::InvalidateCachedSysDriveProperties ()
{
DriveConfigValid = false;
RealSystemDriveSizeValid = false;
}
PartitionList BootEncryption::GetDrivePartitions (int driveNumber)
{
PartitionList partList;
for (int partNumber = 0; partNumber < 64; ++partNumber)
{
stringstream partPath;
partPath << "\\Device\\Harddisk" << driveNumber << "\\Partition" << partNumber;
DISK_PARTITION_INFO_STRUCT diskPartInfo;
- _snwprintf (diskPartInfo.deviceName, array_capacity (diskPartInfo.deviceName), L"%hs", partPath.str().c_str());
+ StringCbPrintfW (diskPartInfo.deviceName, sizeof (diskPartInfo.deviceName), L"%hs", partPath.str().c_str());
try
{
CallDriver (TC_IOCTL_GET_DRIVE_PARTITION_INFO, &diskPartInfo, sizeof (diskPartInfo), &diskPartInfo, sizeof (diskPartInfo));
}
catch (...)
{
continue;
}
Partition part;
part.DevicePath = partPath.str();
part.Number = partNumber;
part.Info = diskPartInfo.partInfo;
part.IsGPT = diskPartInfo.IsGPT;
// Mount point
wstringstream ws;
ws << partPath.str().c_str();
int driveNumber = GetDiskDeviceDriveLetter ((wchar_t *) ws.str().c_str());
if (driveNumber >= 0)
{
part.MountPoint += (char) (driveNumber + 'A');
part.MountPoint += ":";
}
// Volume ID
wchar_t volumePath[TC_MAX_PATH];
- if (ResolveSymbolicLink ((wchar_t *) ws.str().c_str(), volumePath))
+ if (ResolveSymbolicLink ((wchar_t *) ws.str().c_str(), volumePath, sizeof(volumePath)))
{
wchar_t volumeName[TC_MAX_PATH];
HANDLE fh = FindFirstVolumeW (volumeName, array_capacity (volumeName));
if (fh != INVALID_HANDLE_VALUE)
{
do
{
wstring volumeNameStr = volumeName;
wchar_t devicePath[TC_MAX_PATH];
if (QueryDosDeviceW (volumeNameStr.substr (4, volumeNameStr.size() - 1 - 4).c_str(), devicePath, array_capacity (devicePath)) != 0
&& wcscmp (volumePath, devicePath) == 0)
{
part.VolumeNameId = volumeName;
break;
}
} while (FindNextVolumeW (fh, volumeName, array_capacity (volumeName)));
FindVolumeClose (fh);
@@ -725,42 +727,42 @@ namespace VeraCrypt }
uint16 BootEncryption::GetInstalledBootLoaderVersion ()
{
uint16 version;
CallDriver (TC_IOCTL_GET_BOOT_LOADER_VERSION, NULL, 0, &version, sizeof (version));
return version;
}
// Note that this does not require admin rights (it just requires the driver to be running)
bool BootEncryption::IsBootLoaderOnDrive (char *devicePath)
{
try
{
OPEN_TEST_STRUCT openTestStruct;
memset (&openTestStruct, 0, sizeof (openTestStruct));
DWORD dwResult;
- strcpy ((char *) &openTestStruct.wszFileName[0], devicePath);
- ToUNICODE ((char *) &openTestStruct.wszFileName[0]);
+ StringCbCopyA ((char *) &openTestStruct.wszFileName[0], sizeof(openTestStruct.wszFileName),devicePath);
+ ToUNICODE ((char *) &openTestStruct.wszFileName[0], sizeof(openTestStruct.wszFileName));
openTestStruct.bDetectTCBootLoader = TRUE;
return (DeviceIoControl (hDriver, TC_IOCTL_OPEN_TEST,
&openTestStruct, sizeof (OPEN_TEST_STRUCT),
&openTestStruct, sizeof (OPEN_TEST_STRUCT),
&dwResult, NULL) && openTestStruct.TCBootLoaderDetected);
}
catch (...)
{
return false;
}
}
BootEncryptionStatus BootEncryption::GetStatus ()
{
/* IMPORTANT: Do NOT add any potentially time-consuming operations to this function. */
BootEncryptionStatus status;
@@ -827,41 +829,41 @@ namespace VeraCrypt case PARTITION_HUGE:
case PARTITION_IFS:
case PARTITION_FAT32:
case PARTITION_FAT32_XINT13:
case PARTITION_XINT13:
case PARTITION_XINT13_EXTENDED:
continue;
}
if (SystemDriveContainsPartitionType ((byte) partitionType))
return true;
}
return false;
}
bool BootEncryption::SystemDriveIsDynamic ()
{
GetSystemDriveConfigurationRequest request;
- _snwprintf (request.DevicePath, array_capacity (request.DevicePath), L"%hs", GetSystemDriveConfiguration().DeviceKernelPath.c_str());
+ StringCbPrintfW (request.DevicePath, sizeof (request.DevicePath), L"%hs", GetSystemDriveConfiguration().DeviceKernelPath.c_str());
CallDriver (TC_IOCTL_GET_SYSTEM_DRIVE_CONFIG, &request, sizeof (request), &request, sizeof (request));
return request.DriveIsDynamic ? true : false;
}
SystemDriveConfiguration BootEncryption::GetSystemDriveConfiguration ()
{
if (DriveConfigValid)
return DriveConfig;
SystemDriveConfiguration config;
string winDir = GetWindowsDirectory();
// Scan all drives
for (int driveNumber = 0; driveNumber < 32; ++driveNumber)
{
bool windowsFound = false;
bool activePartitionFound = false;
@@ -1078,41 +1080,41 @@ namespace VeraCrypt if (size + TC_BOOT_LOADER_DECOMPRESSOR_SECTOR_COUNT * TC_SECTOR_SIZE_BIOS <= TC_BOOT_LOADER_BACKUP_SECTOR_COUNT * TC_SECTOR_SIZE_BIOS)
{
memcpy (buffer + TC_SECTOR_SIZE_BIOS + TC_BOOT_LOADER_BACKUP_SECTOR_COUNT * TC_SECTOR_SIZE_BIOS,
buffer + TC_SECTOR_SIZE_BIOS, TC_BOOT_LOADER_BACKUP_SECTOR_COUNT * TC_SECTOR_SIZE_BIOS);
buffer[TC_BOOT_SECTOR_CONFIG_OFFSET] |= TC_BOOT_CFG_FLAG_BACKUP_LOADER_AVAILABLE;
}
else if (!rescueDisk && bootLoaderId != IDR_BOOT_LOADER)
{
throw ParameterIncorrect (SRC_POS);
}
}
void BootEncryption::ReadBootSectorConfig (byte *config, size_t bufLength, byte *userConfig, string *customUserMessage, uint16 *bootLoaderVersion)
{
if (config && bufLength < TC_BOOT_CFG_FLAG_AREA_SIZE)
throw ParameterIncorrect (SRC_POS);
GetSystemDriveConfigurationRequest request;
- _snwprintf (request.DevicePath, array_capacity (request.DevicePath), L"%hs", GetSystemDriveConfiguration().DeviceKernelPath.c_str());
+ StringCbPrintfW (request.DevicePath, sizeof (request.DevicePath), L"%hs", GetSystemDriveConfiguration().DeviceKernelPath.c_str());
try
{
CallDriver (TC_IOCTL_GET_SYSTEM_DRIVE_CONFIG, &request, sizeof (request), &request, sizeof (request));
if (config)
*config = request.Configuration;
if (userConfig)
*userConfig = request.UserConfiguration;
if (customUserMessage)
{
request.CustomUserMessage[TC_BOOT_SECTOR_USER_MESSAGE_MAX_LENGTH] = 0;
*customUserMessage = request.CustomUserMessage;
}
if (bootLoaderVersion)
*bootLoaderVersion = request.BootLoaderVersion;
}
catch (...)
@@ -1385,63 +1387,67 @@ namespace VeraCrypt if (FileExists (path.c_str()) && !FileExists (GetSystemLoaderBackupPath().c_str()))
throw_sys_if (rename (path.c_str(), GetSystemLoaderBackupPath().c_str()) != 0);
}
}
#ifndef SETUP
void BootEncryption::CreateRescueIsoImage (bool initialSetup, const string &isoImagePath)
{
BootEncryptionStatus encStatus = GetStatus();
if (encStatus.SetupInProgress)
throw ParameterIncorrect (SRC_POS);
Buffer imageBuf (RescueIsoImageSize);
byte *image = imageBuf.Ptr();
memset (image, 0, RescueIsoImageSize);
// Primary volume descriptor
- strcpy ((char *)image + 0x8000, "\001CD001\001");
- strcpy ((char *)image + 0x7fff + 41, "VeraCrypt Rescue Disk ");
+ const char* szPrimVolDesc = "\001CD001\001";
+ const char* szPrimVolLabel = "VeraCrypt Rescue Disk ";
+ memcpy (image + 0x8000, szPrimVolDesc, strlen(szPrimVolDesc) + 1);
+ memcpy (image + 0x7fff + 41, szPrimVolLabel, strlen(szPrimVolLabel) + 1);
*(uint32 *) (image + 0x7fff + 81) = RescueIsoImageSize / 2048;
*(uint32 *) (image + 0x7fff + 85) = BE32 (RescueIsoImageSize / 2048);
image[0x7fff + 121] = 1;
image[0x7fff + 124] = 1;
image[0x7fff + 125] = 1;
image[0x7fff + 128] = 1;
image[0x7fff + 130] = 8;
image[0x7fff + 131] = 8;
image[0x7fff + 133] = 10;
image[0x7fff + 140] = 10;
image[0x7fff + 141] = 0x14;
image[0x7fff + 157] = 0x22;
image[0x7fff + 159] = 0x18;
// Boot record volume descriptor
- strcpy ((char *)image + 0x8801, "CD001\001EL TORITO SPECIFICATION");
+ const char* szBootRecDesc = "CD001\001EL TORITO SPECIFICATION";
+ memcpy (image + 0x8801, szBootRecDesc, strlen(szBootRecDesc) + 1);
image[0x8800 + 0x47] = 0x19;
// Volume descriptor set terminator
- strcpy ((char *)image + 0x9000, "\377CD001\001");
+ const char* szVolDescTerm = "\377CD001\001";
+ memcpy (image + 0x9000, szVolDescTerm, strlen(szVolDescTerm) + 1);
// Path table
image[0xA000 + 0] = 1;
image[0xA000 + 2] = 0x18;
image[0xA000 + 6] = 1;
// Root directory
image[0xc000 + 0] = 0x22;
image[0xc000 + 2] = 0x18;
image[0xc000 + 9] = 0x18;
image[0xc000 + 11] = 0x08;
image[0xc000 + 16] = 0x08;
image[0xc000 + 25] = 0x02;
image[0xc000 + 28] = 0x01;
image[0xc000 + 31] = 0x01;
image[0xc000 + 32] = 0x01;
image[0xc000 + 34] = 0x22;
image[0xc000 + 36] = 0x18;
image[0xc000 + 43] = 0x18;
image[0xc000 + 45] = 0x08;
@@ -1705,41 +1711,41 @@ namespace VeraCrypt SetLastError (RegOpenKeyEx (HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Control\\CrashControl", 0, KEY_READ | KEY_WRITE, ®Key));
throw_sys_if (GetLastError() != ERROR_SUCCESS);
break;
default:
throw ParameterIncorrect (SRC_POS);
}
finally_do_arg (HKEY, regKey, { RegCloseKey (finally_arg); });
if (registerFilter && filterType != DumpFilter)
{
// Register class filter below all other filters in the stack
size_t strSize = filter.size() + 1;
byte regKeyBuf[65536];
DWORD size = sizeof (regKeyBuf) - strSize;
// SetupInstallFromInfSection() does not support prepending of values so we have to modify the registry directly
- strncpy ((char *) regKeyBuf, filter.c_str(), sizeof (regKeyBuf));
+ StringCbCopyA ((char *) regKeyBuf, sizeof(regKeyBuf), filter.c_str());
if (RegQueryValueEx (regKey, filterReg.c_str(), NULL, NULL, regKeyBuf + strSize, &size) != ERROR_SUCCESS)
size = 1;
SetLastError (RegSetValueEx (regKey, filterReg.c_str(), 0, REG_MULTI_SZ, regKeyBuf, strSize + size));
throw_sys_if (GetLastError() != ERROR_SUCCESS);
}
else
{
string infFileName = GetTempPath() + "\\veracrypt_driver_setup.inf";
File infFile (infFileName, false, true);
finally_do_arg (string, infFileName, { DeleteFile (finally_arg.c_str()); });
string infTxt = "[veracrypt]\r\n"
+ string (registerFilter ? "Add" : "Del") + "Reg=veracrypt_reg\r\n\r\n"
"[veracrypt_reg]\r\n"
"HKR,,\"" + filterReg + "\",0x0001" + string (registerFilter ? "0008" : "8002") + ",\"" + filter + "\"\r\n";
infFile.Write ((byte *) infTxt.c_str(), infTxt.size());
@@ -2301,41 +2307,41 @@ namespace VeraCrypt }
SelectedEncryptionAlgorithmId = ea;
CreateVolumeHeader (volumeSize, encryptedAreaStart, &password, ea, mode, pkcs5);
if (!rescueIsoImagePath.empty())
CreateRescueIsoImage (true, rescueIsoImagePath);
}
bool BootEncryption::IsPagingFileActive (BOOL checkNonWindowsPartitionsOnly)
{
if (!IsAdmin() && IsUacSupported())
return Elevator::IsPagingFileActive (checkNonWindowsPartitionsOnly) ? true : false;
return ::IsPagingFileActive (checkNonWindowsPartitionsOnly) ? true : false;
}
void BootEncryption::RestrictPagingFilesToSystemPartition ()
{
char pagingFiles[128];
- strncpy (pagingFiles, "X:\\pagefile.sys 0 0", sizeof (pagingFiles));
+ StringCbCopyA (pagingFiles, sizeof(pagingFiles), "X:\\pagefile.sys 0 0");
pagingFiles[0] = GetWindowsDirectory()[0];
throw_sys_if (!WriteLocalMachineRegistryMultiString ("System\\CurrentControlSet\\Control\\Session Manager\\Memory Management", "PagingFiles", pagingFiles, strlen (pagingFiles) + 2));
}
void BootEncryption::WriteLocalMachineRegistryDwordValue (char *keyPath, char *valueName, DWORD value)
{
if (!IsAdmin() && IsUacSupported())
{
Elevator::WriteLocalMachineRegistryDwordValue (keyPath, valueName, value);
return;
}
throw_sys_if (!WriteLocalMachineRegistryDword (keyPath, valueName, value));
}
void BootEncryption::SetDriverConfigurationFlag (uint32 flag, bool state)
{
DWORD configMap = ReadDriverConfigurationFlags();
|