将文件写入 SD 卡(物理硬盘)失败并显示 ERROR_ACCESS_DENIED (0x5)
WriteFile to SD card (physical hard disk) fails with ERROR_ACCESS_DENIED (0x5)
我正在尝试直接使用 Windows API 写入物理硬盘(SD 卡/FAT32):WriteFile () 但它总是以 ERROR_ACCESS_DENIED (0x5) 失败。我已经尝试了一些其他帖子建议的许多选项,例如 unmount/lock 但似乎没有任何效果。
有没有人更清楚这个问题的根本原因是什么以及我们如何直接从 Windows API 访问物理驱动器?
这是我使用的示例代码:
#include <stdio.h>
#include <stdint.h>
#include <stdbool.h>
#include <stdlib.h>
#include <windows.h>
DWORD lastError;
int main (void) {
uint16_t x, y;
uint8_t buffer[512];
DWORD bytesWritten, status;
HANDLE sdCardHandle = CreateFile("\\.\PhysicalDrive2", GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if(sdCardHandle == INVALID_HANDLE_VALUE) {
CloseHandle(sdCardHandle);
return -1;
}
for (y = 1; y < 10001; y++) {
memset(buffer, y, sizeof(buffer));
if (WriteFile(sdCardHandle, buffer, sizeof(buffer), &bytesWritten, NULL) == 0) {
lastError = GetLastError();
printf("WriteFile error: 0x%X\n", lastError);
CloseHandle(sdCardHandle);
return -2;
}
printf("%d\n", y);
}
CloseHandle(sdCardHandle);
return 0;
}
谢谢!
感谢大家的评论。
所以我找到了解决这个问题的方法(在 Windows 10 中)。 解决方法 是 锁定、卸载并创建磁盘作为 GPT 以使 Windows 思考它是未分配的磁盘。无论出于何种原因,如果它被格式化为 FAT/FAT32,我将无法将文件写入卡。
以下是适用于我的示例代码:
#include <stdio.h>
#include <stdint.h>
#include <stdbool.h>
#include <stdlib.h>
#include <windows.h>
static CREATE_DISK raw; // dummy raw to create disk as GPT to trick Windows to see it as unallocated
static DWORD lastError;
static HANDLE sd_handle;
int main (void) {
uint16_t x, y;
uint8_t i, buffer[512];
DWORD bytes;
if ((sd_handle = CreateFile("\\.\PhysicalDrive2",
GENERIC_READ|GENERIC_WRITE,
FILE_SHARE_READ|FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
FILE_FLAG_NO_BUFFERING,
NULL)) == INVALID_HANDLE_VALUE) {
printf("Error 0x%X openning Physical Drive\n", GetLastError());
return -1;
}
// Workaround to lock, dismount, and create disk as GPT to trick Windows to see drive as unallocated
if (!DeviceIoControl(sd_handle, FSCTL_LOCK_VOLUME, NULL, 0, NULL, 0, &bytes, NULL)) {
puts("Error: Cannot lock volume");
CloseHandle(sd_handle);
return -2;
}
if (!DeviceIoControl(sd_handle, FSCTL_DISMOUNT_VOLUME , NULL, 0, NULL, 0, &bytes, NULL)) {
puts("Error: Cannot dismount volume");
CloseHandle(sd_handle);
return -3;
}
raw.PartitionStyle = PARTITION_STYLE_GPT;
if (!DeviceIoControl(sd_handle, IOCTL_DISK_CREATE_DISK, &raw, sizeof(raw), NULL, 0, &bytes, NULL)) {
puts("Error: Cannot create disk");
CloseHandle(sd_handle);
return -4;
}
// unlock, close, and reopen again to allow Windows to see it as newly unallocated drive
if (!DeviceIoControl(sd_handle, FSCTL_UNLOCK_VOLUME, NULL, 0, NULL, 0, &bytes, NULL)) {
puts("Error: Cannot unlock volume");
CloseHandle(sd_handle);
return -5;
}
CloseHandle(sd_handle);
if ((sd_handle = CreateFile("\\.\PhysicalDrive2",
GENERIC_READ|GENERIC_WRITE,
FILE_SHARE_READ|FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
FILE_FLAG_NO_BUFFERING,
NULL)) == INVALID_HANDLE_VALUE) {
printf("Error 0x%X openning Physical Drive\n", GetLastError());
return -6;
}
// Note for WriteFile:
// The GetLastError code ERROR_IO_PENDING is not a failure;
// it designates the write operation is pending completion asynchronously.
for (i = 1; i < 100; i++) {
memset(buffer, i, sizeof(buffer));
if (!WriteFile(sd_handle, buffer, sizeof(buffer), &bytes, NULL)
&&((lastError = GetLastError()) != ERROR_IO_PENDING)) {
printf("WriteFile error: 0x%X\n", lastError);
CloseHandle(sd_handle);
return -7;
}
}
}
同样,这只是我发现对我有用的解决方法,但我还不知道确切原因是什么。如果有人知道根本原因并愿意分享,那就太好了。
我正在尝试直接使用 Windows API 写入物理硬盘(SD 卡/FAT32):WriteFile () 但它总是以 ERROR_ACCESS_DENIED (0x5) 失败。我已经尝试了一些其他帖子建议的许多选项,例如 unmount/lock 但似乎没有任何效果。
有没有人更清楚这个问题的根本原因是什么以及我们如何直接从 Windows API 访问物理驱动器?
这是我使用的示例代码:
#include <stdio.h>
#include <stdint.h>
#include <stdbool.h>
#include <stdlib.h>
#include <windows.h>
DWORD lastError;
int main (void) {
uint16_t x, y;
uint8_t buffer[512];
DWORD bytesWritten, status;
HANDLE sdCardHandle = CreateFile("\\.\PhysicalDrive2", GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if(sdCardHandle == INVALID_HANDLE_VALUE) {
CloseHandle(sdCardHandle);
return -1;
}
for (y = 1; y < 10001; y++) {
memset(buffer, y, sizeof(buffer));
if (WriteFile(sdCardHandle, buffer, sizeof(buffer), &bytesWritten, NULL) == 0) {
lastError = GetLastError();
printf("WriteFile error: 0x%X\n", lastError);
CloseHandle(sdCardHandle);
return -2;
}
printf("%d\n", y);
}
CloseHandle(sdCardHandle);
return 0;
}
谢谢!
感谢大家的评论。
所以我找到了解决这个问题的方法(在 Windows 10 中)。 解决方法 是 锁定、卸载并创建磁盘作为 GPT 以使 Windows 思考它是未分配的磁盘。无论出于何种原因,如果它被格式化为 FAT/FAT32,我将无法将文件写入卡。
以下是适用于我的示例代码:
#include <stdio.h>
#include <stdint.h>
#include <stdbool.h>
#include <stdlib.h>
#include <windows.h>
static CREATE_DISK raw; // dummy raw to create disk as GPT to trick Windows to see it as unallocated
static DWORD lastError;
static HANDLE sd_handle;
int main (void) {
uint16_t x, y;
uint8_t i, buffer[512];
DWORD bytes;
if ((sd_handle = CreateFile("\\.\PhysicalDrive2",
GENERIC_READ|GENERIC_WRITE,
FILE_SHARE_READ|FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
FILE_FLAG_NO_BUFFERING,
NULL)) == INVALID_HANDLE_VALUE) {
printf("Error 0x%X openning Physical Drive\n", GetLastError());
return -1;
}
// Workaround to lock, dismount, and create disk as GPT to trick Windows to see drive as unallocated
if (!DeviceIoControl(sd_handle, FSCTL_LOCK_VOLUME, NULL, 0, NULL, 0, &bytes, NULL)) {
puts("Error: Cannot lock volume");
CloseHandle(sd_handle);
return -2;
}
if (!DeviceIoControl(sd_handle, FSCTL_DISMOUNT_VOLUME , NULL, 0, NULL, 0, &bytes, NULL)) {
puts("Error: Cannot dismount volume");
CloseHandle(sd_handle);
return -3;
}
raw.PartitionStyle = PARTITION_STYLE_GPT;
if (!DeviceIoControl(sd_handle, IOCTL_DISK_CREATE_DISK, &raw, sizeof(raw), NULL, 0, &bytes, NULL)) {
puts("Error: Cannot create disk");
CloseHandle(sd_handle);
return -4;
}
// unlock, close, and reopen again to allow Windows to see it as newly unallocated drive
if (!DeviceIoControl(sd_handle, FSCTL_UNLOCK_VOLUME, NULL, 0, NULL, 0, &bytes, NULL)) {
puts("Error: Cannot unlock volume");
CloseHandle(sd_handle);
return -5;
}
CloseHandle(sd_handle);
if ((sd_handle = CreateFile("\\.\PhysicalDrive2",
GENERIC_READ|GENERIC_WRITE,
FILE_SHARE_READ|FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
FILE_FLAG_NO_BUFFERING,
NULL)) == INVALID_HANDLE_VALUE) {
printf("Error 0x%X openning Physical Drive\n", GetLastError());
return -6;
}
// Note for WriteFile:
// The GetLastError code ERROR_IO_PENDING is not a failure;
// it designates the write operation is pending completion asynchronously.
for (i = 1; i < 100; i++) {
memset(buffer, i, sizeof(buffer));
if (!WriteFile(sd_handle, buffer, sizeof(buffer), &bytes, NULL)
&&((lastError = GetLastError()) != ERROR_IO_PENDING)) {
printf("WriteFile error: 0x%X\n", lastError);
CloseHandle(sd_handle);
return -7;
}
}
}
同样,这只是我发现对我有用的解决方法,但我还不知道确切原因是什么。如果有人知道根本原因并愿意分享,那就太好了。