简而言之,我尝试使用Visual C ++以编程方式修改现有的NTFS符号链接目标。在此代码段中,我实际上并未对链接执行任何操作。为简单起见,我只是将结构读入缓冲区,然后将该缓冲区写回自身。我在第二次ERROR_ACCESS_DENIED
来电时收到DeviceIoControl
。在我看来,手柄正在打开具有完全权限的链接,所以我很困惑,一定有别的东西我做错了吗?
#include "stdafx.h"
#include <stdio.h>
#include <ole2.h>
typedef struct _REPARSE_DATA_BUFFER {
ULONG ReparseTag;
USHORT ReparseDataLength;
USHORT Reserved;
union {
struct {
USHORT SubstituteNameOffset;
USHORT SubstituteNameLength;
USHORT PrintNameOffset;
USHORT PrintNameLength;
ULONG Flags;
WCHAR PathBuffer[1];
} SymbolicLinkReparseBuffer;
struct {
USHORT SubstituteNameOffset;
USHORT SubstituteNameLength;
USHORT PrintNameOffset;
USHORT PrintNameLength;
WCHAR PathBuffer[1];
} MountPointReparseBuffer;
struct {
UCHAR DataBuffer[1];
} GenericReparseBuffer;
};
} REPARSE_DATA_BUFFER;
#define REPARSE_MOUNTPOINT_HEADER_SIZE 8
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE hFile;
LPCTSTR szMyFile = _T("C:\\Users\\Weston\\Desktop\\New folder\\SymbolicLink of test.txt");
hFile = CreateFile(szMyFile, GENERIC_ALL, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS | FILE_FLAG_OPEN_REPARSE_POINT, NULL);
if (hFile == INVALID_HANDLE_VALUE)
{
_tprintf(_T("Could not open dir '%s'; error: %d\n"), szMyFile, GetLastError());
CloseHandle(hFile);
return 1;
}
REPARSE_DATA_BUFFER* rdata = (REPARSE_DATA_BUFFER*)malloc(MAXIMUM_REPARSE_DATA_BUFFER_SIZE);
DWORD dwRetLen = 0;
BOOL bRet = DeviceIoControl(hFile, FSCTL_GET_REPARSE_POINT, NULL, 0, rdata, MAXIMUM_REPARSE_DATA_BUFFER_SIZE, &dwRetLen, NULL);
if (bRet == FALSE)
{
_tprintf(_T("DeviceIoControl1 failed with error: %d\n"), GetLastError());
CloseHandle(hFile);
return 1;
}
DWORD ioctl_return = 0xdeadbeef;
if (!DeviceIoControl(hFile,
FSCTL_SET_REPARSE_POINT,
rdata,
REPARSE_MOUNTPOINT_HEADER_SIZE + rdata->ReparseDataLength,
NULL,
0,
&ioctl_return,
NULL)) {
_tprintf(_T("DeviceIoControl2 failed with error: %d\n"), GetLastError());
CloseHandle(hFile);
return 1;
}
CloseHandle(hFile);
return 0;
}