Функция для определения является ли .exe или .dll файл .Net'овским или нет. Замечания, пожелания, комментарии, как всегда, приветствуются.
#include <windows.h>
#define EIT_IS_DLL(t) ((-1!=(t))&&((t) & 0x1))
#define EIT_IS_DOTNET(t) ((-1!=(t))&&((t) & 0x2))
//-------------------------------------------------------------------
// Функция для проверки типа исполняемого файла
//
// Параметры:
//
// fileName - путь к проверяемому файлу
//
// Возвращаемое значение:
//
// Если младший бит возвр.значения установлен, то файл является
// динамической библиотекой (dll), иначе это exe-файл. Для
// проверки можно использовать макрос EIT_IS_DLL();
//
// Второй бит возвр.значения установлен, то файл является
// файлом .NET;
//
// В случае неудачи возвращается -1.
//-------------------------------------------------------------------
WORD GetExecutableImageType(LPCTSTR fileName)
{
HANDLE hFile;
HANDLE hMap;
PBYTE pFileBase;
PIMAGE_DOS_HEADER pDosHeader;
PIMAGE_NT_HEADERS pNtHeader;
WORD result = 0;
// Открываем файл и отображаем его в память
hFile = CreateFile(fileName, GENERIC_READ, FILE_SHARE_READ, 0,
OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
if(INVALID_HANDLE_VALUE == hFile)
return -1;
hMap = CreateFileMapping(hFile, 0, PAGE_READONLY, 0, 0, 0);
if(!hMap)
{
CloseHandle(hFile);
return -1;
}
pFileBase = (PBYTE)MapViewOfFile(hMap, FILE_MAP_READ, 0, 0, 0);
if(!pFileBase)
{
CloseHandle(hMap);
CloseHandle(hFile);
return -1;
}
// Убеждаемся в корректности
pDosHeader = (PIMAGE_DOS_HEADER)pFileBase;
if(IMAGE_DOS_SIGNATURE == pDosHeader->e_magic)
{
pNtHeader = (PIMAGE_NT_HEADERS)(pFileBase + pDosHeader->e_lfanew);
if((!IsBadReadPtr(pNtHeader, sizeof(pNtHeader->Signature))) &&
(IMAGE_NT_SIGNATURE == pNtHeader->Signature) &&
(pNtHeader->FileHeader.Characteristics & IMAGE_FILE_EXECUTABLE_IMAGE))
{
// Делаем необходимые проверки
if(pNtHeader->FileHeader.Characteristics & IMAGE_FILE_DLL)
result |= 0x1;
if(!pNtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].Size)
result |= 0x2;
}
}
// Убираем после себя
UnmapViewOfFile(pFileBase);
CloseHandle(hMap);
CloseHandle(hFile);
return result;
}
Использование:
TCHAR testFile[] = _TEXT("System.Windows.Forms.dll");
WORD type = GetExecutableImageType(testFile);
if(!type)
cout<<"Error!"<<endl;
cout<<testFile<<" is ";
if(EIT_IS_DOTNET(type))
cout<<"not ";
cout<<".NET ";
if(EIT_IS_DLL(type))
cout<<"dll";
else
cout<<"exe";
cout<<endl;