W
wallino
Guest
This code searches a machine's raw physical drives (\\.\PhysicalDriveX) using CreateFile and reads a specific sector to scan for a unique signature that I've encoded on the disk that I'd like to access. In all cases the disk I'm needing to access happens to be an external drive (i.e. SD card or USB stick). It works fine on any Window 7 machine (x86 or x64) without errors. However, when I run it on Window 10, ReadFile returns 0 with the error code 0x57 ERROR_INVALID_PARAMETER for only external drives. Since the disk I want to access is always external, this is a problem. In other words, ReadFile returns success when it reads the HDD but it returns 0 with error code 0x57 when it reads any external drive. Its almost like Windows 10 has a new security setting that blocks raw access to external drives. I did confirm the sector size for the external drive is 512 so that is why I have it hard-coded. I tried both Windows 10 Home and Pro editions with the same results. Any suggestions?
BOOL FindDisks(CComboBox* pListBox)
{
HANDLE hDevice = INVALID_HANDLE_VALUE;
BOOL bResult = FALSE;
DWORD nBytesRead = 0;
CString drive;
WCHAR wszPath[MAX_PATH] = L"";
WORD nsectors = 0;
/* refresh list drop box */
pListBox->ResetContent();
drive.Format(L"[No Disk]");
pListBox->InsertString(0,drive);
/* search for valid disks */
for (int DiskNum = 0; DiskNum < MAX_DISKS; DiskNum++)
{
/* unicode version of sprintf */
wsprintf(wszPath,L"\\\\.\\PhysicalDrive%d",DiskNum);
hDevice = CreateFileW(wszPath, // drive to open
GENERIC_READ, // no access to the drive
FILE_SHARE_READ | // share mode
FILE_SHARE_WRITE,
NULL, // default security attributes
OPEN_EXISTING, // disposition
FILE_FLAG_NO_BUFFERING | // file attributes
FILE_FLAG_RANDOM_ACCESS, // file attributes
NULL); // do not copy file attributes
if (hDevice != INVALID_HANDLE_VALUE)
{
/* disk geometry structure info */
GET_LENGTH_INFORMATION *DiskLength = (GET_LENGTH_INFORMATION*) calloc(sizeof(GET_LENGTH_INFORMATION),sizeof(CHAR));
/* get disk size to show the user */
bResult = DeviceIoControl(hDevice, // device to be queried
IOCTL_DISK_GET_LENGTH_INFO, // operation to perform
NULL, 0, // no input buffer
DiskLength,
sizeof(GET_LENGTH_INFORMATION),
&nBytesRead, // # bytes returned
(LPOVERLAPPED) NULL); // synchronous I/O
/* calculate disk size in giga-bytes */
float DiskSize_GB = (float)DiskLength->Length.QuadPart/(1<<30);
free(DiskLength);
if (bResult)
{
/* attempt to verify the disk by analyzing static log */
bResult = SetFilePointer(hDevice,
534841855LL,
0,
FILE_BEGIN);
if (bResult)
{
PCHAR StaticLogData = (PCHAR) calloc(ELOG_SECTOR_SIZE,sizeof(CHAR));
bResult = ReadFile(hDevice,
StaticLogData,
512U,
&nBytesRead,
(LPOVERLAPPED) NULL);
/* extract last written sector; least significant byte first */
DWORD StaticLog_EndSector = (DWORD) (((StaticLogData[3] << 24) & 0xFF000000) |
((StaticLogData[2] << 16) & 0x00FF0000) |
((StaticLogData[1] << 8) & 0x0000FF00) |
(StaticLogData[0] & 0x000000FF));
/* extract last written byte w/in sector; least significant byte first */
WORD StaticLog_EndIdx = (WORD) (((StaticLogData[5] << 8) & 0xFF00) |
(StaticLogData[4] & 0x00FF));
WORD StaticLog_Checksum = (WORD) (((StaticLogData[511] << 8) & 0xFF00) |
(StaticLogData[510] & 0x00FF));
/* calculate checksum */
CHAR Zeros[2] = {0,0};
WORD Calc = 0;
/* exclude checksum itself so size is minus 2 */
Calc = Slow_CRC16(0,&StaticLogData[0], ELOG_SECTOR_SIZE-2);
/* rotate out answer */
Calc = Slow_CRC16(Calc, Zeros, 2);
/* 2-step disk verification */
if (Calc == StaticLog_Checksum)
{
/* now add verified disk to drop list */
drive.Format(L"Disk [%d]: %.2fGB",DiskNum,DiskSize_GB);
pListBox->InsertString(DiskNum,drive);
}
free(StaticLogData);
}
}
/* done examining current disk */
CloseHandle(hDevice);
}
}
return (bResult);
}
Continue reading...
BOOL FindDisks(CComboBox* pListBox)
{
HANDLE hDevice = INVALID_HANDLE_VALUE;
BOOL bResult = FALSE;
DWORD nBytesRead = 0;
CString drive;
WCHAR wszPath[MAX_PATH] = L"";
WORD nsectors = 0;
/* refresh list drop box */
pListBox->ResetContent();
drive.Format(L"[No Disk]");
pListBox->InsertString(0,drive);
/* search for valid disks */
for (int DiskNum = 0; DiskNum < MAX_DISKS; DiskNum++)
{
/* unicode version of sprintf */
wsprintf(wszPath,L"\\\\.\\PhysicalDrive%d",DiskNum);
hDevice = CreateFileW(wszPath, // drive to open
GENERIC_READ, // no access to the drive
FILE_SHARE_READ | // share mode
FILE_SHARE_WRITE,
NULL, // default security attributes
OPEN_EXISTING, // disposition
FILE_FLAG_NO_BUFFERING | // file attributes
FILE_FLAG_RANDOM_ACCESS, // file attributes
NULL); // do not copy file attributes
if (hDevice != INVALID_HANDLE_VALUE)
{
/* disk geometry structure info */
GET_LENGTH_INFORMATION *DiskLength = (GET_LENGTH_INFORMATION*) calloc(sizeof(GET_LENGTH_INFORMATION),sizeof(CHAR));
/* get disk size to show the user */
bResult = DeviceIoControl(hDevice, // device to be queried
IOCTL_DISK_GET_LENGTH_INFO, // operation to perform
NULL, 0, // no input buffer
DiskLength,
sizeof(GET_LENGTH_INFORMATION),
&nBytesRead, // # bytes returned
(LPOVERLAPPED) NULL); // synchronous I/O
/* calculate disk size in giga-bytes */
float DiskSize_GB = (float)DiskLength->Length.QuadPart/(1<<30);
free(DiskLength);
if (bResult)
{
/* attempt to verify the disk by analyzing static log */
bResult = SetFilePointer(hDevice,
534841855LL,
0,
FILE_BEGIN);
if (bResult)
{
PCHAR StaticLogData = (PCHAR) calloc(ELOG_SECTOR_SIZE,sizeof(CHAR));
bResult = ReadFile(hDevice,
StaticLogData,
512U,
&nBytesRead,
(LPOVERLAPPED) NULL);
/* extract last written sector; least significant byte first */
DWORD StaticLog_EndSector = (DWORD) (((StaticLogData[3] << 24) & 0xFF000000) |
((StaticLogData[2] << 16) & 0x00FF0000) |
((StaticLogData[1] << 8) & 0x0000FF00) |
(StaticLogData[0] & 0x000000FF));
/* extract last written byte w/in sector; least significant byte first */
WORD StaticLog_EndIdx = (WORD) (((StaticLogData[5] << 8) & 0xFF00) |
(StaticLogData[4] & 0x00FF));
WORD StaticLog_Checksum = (WORD) (((StaticLogData[511] << 8) & 0xFF00) |
(StaticLogData[510] & 0x00FF));
/* calculate checksum */
CHAR Zeros[2] = {0,0};
WORD Calc = 0;
/* exclude checksum itself so size is minus 2 */
Calc = Slow_CRC16(0,&StaticLogData[0], ELOG_SECTOR_SIZE-2);
/* rotate out answer */
Calc = Slow_CRC16(Calc, Zeros, 2);
/* 2-step disk verification */
if (Calc == StaticLog_Checksum)
{
/* now add verified disk to drop list */
drive.Format(L"Disk [%d]: %.2fGB",DiskNum,DiskSize_GB);
pListBox->InsertString(DiskNum,drive);
}
free(StaticLogData);
}
}
/* done examining current disk */
CloseHandle(hDevice);
}
}
return (bResult);
}
Continue reading...