在網(wǎng)上搜索此類(lèi)問(wèn)題,,搜索到有用的內(nèi)容相當(dāng)少,可能是因?yàn)楸容^少人發(fā)表這種文章,,也不排除比較少人使用內(nèi)核模式的辦法,。今晚通過(guò)在網(wǎng)上看到的一點(diǎn)資料,結(jié)合自己近期研究的課題,,使用NtQueryInformationFile實(shí)現(xiàn)了根據(jù)文件的Handle獲取文件路徑,,程序在VC2008下調(diào)試通過(guò),源代碼如下:
#include "stdafx.h" #include <windows.h> #include <tchar.h> typedef long NTSTATUS; #define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0) // Define the base asynchronous I/O argument types typedef struct _IO_STATUS_BLOCK { union { NTSTATUS Status; PVOID Pointer; }; ULONG_PTR Information; } IO_STATUS_BLOCK, *PIO_STATUS_BLOCK; typedef enum _FILE_INFORMATION_CLASS { // end_wdm FileDirectoryInformation = 1, FileFullDirectoryInformation, // 2 FileBothDirectoryInformation, // 3 FileBasicInformation, // 4 wdm FileStandardInformation, // 5 wdm FileInternalInformation, // 6 FileEaInformation, // 7 FileAccessInformation, // 8 FileNameInformation, // 9 FileRenameInformation, // 10 FileLinkInformation, // 11 FileNamesInformation, // 12 FileDispositionInformation, // 13 FilePositionInformation, // 14 wdm FileFullEaInformation, // 15 FileModeInformation, // 16 FileAlignmentInformation, // 17 FileAllInformation, // 18 FileAllocationInformation, // 19 FileEndOfFileInformation, // 20 wdm FileAlternateNameInformation, // 21 FileStreamInformation, // 22 FilePipeInformation, // 23 FilePipeLocalInformation, // 24 FilePipeRemoteInformation, // 25 FileMailslotQueryInformation, // 26 FileMailslotSetInformation, // 27 FileCompressionInformation, // 28 FileObjectIdInformation, // 29 FileCompletionInformation, // 30 FileMoveClusterInformation, // 31 FileQuotaInformation, // 32 FileReparsePointInformation, // 33 FileNetworkOpenInformation, // 34 FileAttributeTagInformation, // 35 FileTrackingInformation, // 36 FileIdBothDirectoryInformation, // 37 FileIdFullDirectoryInformation, // 38 FileValidDataLengthInformation, // 39 FileShortNameInformation, // 40 FileMaximumInformation // begin_wdm } FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS; typedef struct _UNICODE_STRING { USHORT Length; USHORT MaximumLength; #ifdef MIDL_PASS [size_is(MaximumLength / 2), length_is((Length) / 2) ] USHORT * Buffer; #else // MIDL_PASS PWSTR Buffer; #endif // MIDL_PASS } UNICODE_STRING, *PUNICODE_STRING; typedef struct _OBJECT_NAME_INFORMATION { UNICODE_STRING Name; } OBJECT_NAME_INFORMATION, *POBJECT_NAME_INFORMATION; typedef NTSTATUS (NTAPI *NTQUERYINFORMATIONFILE)( IN HANDLE FileHandle, OUT PIO_STATUS_BLOCK IoStatusBlock, OUT PVOID FileInformation, IN DWORD Length, IN FILE_INFORMATION_CLASS FileInformationClass ); NTQUERYINFORMATIONFILE NtQueryInformationFile = NULL; void _tmain(int argc, _TCHAR* argv[]) { _tsetlocale(0, _T("chs")); NTSTATUS status = -1; HMODULE hNtdll = NULL; HANDLE hFile = INVALID_HANDLE_VALUE; IO_STATUS_BLOCK IoStatus = {0}; POBJECT_NAME_INFORMATION pfni = NULL; size_t allocSize = 0; hNtdll = LoadLibrary(_T("ntdll.dll")); NtQueryInformationFile = (NTQUERYINFORMATIONFILE)GetProcAddress(hNtdll, "NtQueryInformationFile"); hFile = CreateFile(_T("E:\\test\\Debug\\test.txt"), GENERIC_WRITE, FILE_SHARE_READ, NULL, CREATE_ALWAYS, 0, NULL); if (hFile != INVALID_HANDLE_VALUE) { allocSize = sizeof(OBJECT_NAME_INFORMATION) + MAX_PATH * sizeof(WCHAR); pfni = (POBJECT_NAME_INFORMATION)malloc(allocSize); if (pfni != NULL) { RtlZeroMemory(pfni, allocSize); status = NtQueryInformationFile(hFile, &IoStatus, pfni, allocSize, FileNameInformation); if (NT_SUCCESS(status)) wprintf(L"文件名: %s\n", pfni->Name.Buffer); free(pfni); } CloseHandle(hFile); } FreeLibrary(hNtdll); } 雖然沒(méi)有使用編寫(xiě)驅(qū)動(dòng)程序,,但使用的API跟內(nèi)核模式的一樣的,,使用ntdll.dll里的API。類(lèi)型定義全部從DDK 2003 SP1中摘出來(lái)的,。 對(duì)于NtQueryInformationFile獲取到的文件路徑,,是不帶盤(pán)符的,如“\test\Debug\test.txt”,。還有一個(gè)內(nèi)核API可以根據(jù)文件的Handle獲取文件路徑,,就是NtQueryObject,使用它獲取的路徑是MS-DOS設(shè)備路徑,,如“\Device\HarddiskVolume3\test\Debug\test.txt”,。 |
|