FSCTL_LOCK_VOLUME завершается с ошибкой ERROR_ACCESS_DENIED на смонтированном VHD - PullRequest
1 голос
/ 23 июля 2011

Я работаю над программой, которая устанавливает FreeDOS на виртуальный жесткий диск. Он создает и выполняет сценарий DiskPart для создания виртуального жесткого диска, его разбиения, форматирования и назначения буквы диска.

Это отлично работает. Мой установщик копирует все на VHD, но теперь мне нужно написать загрузочный сектор, который требует прямого доступа к тому. Перед началом этого процесса я пытаюсь заблокировать том с помощью FSCTL_LOCK_VOLUME.

Проблема в следующем: DeviceIoControl возвращает ERROR_ACCESS_DENIED, что (согласно MSDN) означает, что на томе открыты файлы. Но мой установщик закрывает каждый файл, как только копирует его, поэтому я не уверен, что еще может быть причиной этого. Это как-то связано с тем, как DiskPart смонтировал виртуальный жесткий диск?

Пример скрипта DiskPart

create vdisk file=E:\Dev\freedos.vhd maximum=128 type=fixed
select vdisk file=E:\Dev\freedos.vhd
attach vdisk
create partition primary
select partition 1
format quick fs=FAT
assign letter=A

Примечание. Путь к файлу, размер диска, файловая система и буква диска изменяются в зависимости от параметров, предоставленных программе.

Код C

HANDLE volume;
char volName[MAX_PATH];
DWORD bytesReturned;

if (!GetVolumeNameForVolumeMountPoint(config.volRoot, volName, sizeof(volName)))
    ThrowError(1, "Failed to get volume name (error %d)!", GetLastError());

/*
* CreateFile will fail if the volume name has a trailing backslash
*/
PathRemoveBackslash(volName);

volume = CreateFile(volName, (GENERIC_READ | GENERIC_WRITE),
    (FILE_SHARE_READ | FILE_SHARE_WRITE), NULL, OPEN_EXISTING,
    FILE_ATTRIBUTE_NORMAL, NULL);

if (volume == INVALID_HANDLE_VALUE)
    ThrowError(1, "Failed to open installation volume (error %d)!", GetLastError());

if (!DeviceIoControl(volume, FSCTL_LOCK_VOLUME, NULL, 0, NULL, 0, &bytesReturned, NULL))
    ThrowError(1, "Failed to lock installation volume (error %d)!", GetLastError());

CloseHandle(volume);

1 Ответ

0 голосов
/ 24 июля 2011

Это на самом деле не отвечает на ваш вопрос, но на самом деле может быть лучше создать VHD напрямую сначала , а затем смонтировать его. VHD - это очень простой формат, вы, вероятно, могли бы написать программу для непосредственного создания VHD с уже написанным загрузчиком (т. Е. Просто с помощью CreateFile / WriteFile), а затем смонтировать его и создать файловую систему.

...