|
|
|
IMAGE_DOS_HEADER *mz_head; IMAGE_FILE_HEADER *pe_head; IMAGE_OPTIONAL_HEADER *pe_opt_head; IMAGE_SECTION_HEADER *sect; char pe[] = "PE\0\0"; HANDLE f = NULL; //Открываем файл f = CreateFile(openF->FileName.c_str(), GENERIC_READ | GENERIC_WRITE, FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); if (f == INVALID_HANDLE_VALUE) { Log->Lines->Add("Ошибка при открытии файла: "); parse_error(); return; } //Создаем отображение файла HANDLE fMap = CreateFileMapping( f, NULL, PAGE_READWRITE, 0, 0, NULL); CloseHandle(f); if (fMap == NULL) { Log->Lines->Add("Ошибка при вызове CreateFileMapping(): "); parse_error(); return; } int size = sizeof( IMAGE_DOS_HEADER ); //Отображаем начало файла в память LPVOID fBeg = MapViewOfFile( fMap, FILE_MAP_WRITE, 0, 0, size); if (fBeg == NULL) { Log->Lines->Add("Ошибка при вызове MapViewOfFile(): "); parse_error(); return; } |
//Определяем смещение РЕ-заголовка. mz_head = (IMAGE_DOS_HEADER *)fBeg; DWORD peOffset = mz_head->e_lfanew; UnmapViewOfFile(fBeg); //Отображаем в память с учетом смещения до РЕ-заголовка size = peOffset + sizeof( DWORD ) + sizeof( IMAGE_FILE_HEADER ) + sizeof( IMAGE_OPTIONAL_HEADER ); fBeg = MapViewOfFile( fMap, FILE_MAP_READ, 0, 0, size); if (fBeg == NULL) { Log->Lines->Add("Ошибка при вызове MapViewOfFile(): "); parse_error(); CloseHandle(fMap);return; } mz_head = (IMAGE_DOS_HEADER *)fBeg; (DWORD)pe_head = (DWORD)fBeg + peOffset; //Проверяем, PE или не PE файл if ( strcmp(pe,(const char *)pe_head) != 0) { Log->Lines->Add("Этот файл не является Portable Executable - файлом."); UnmapViewOfFile(fBeg);CloseHandle(fMap); return; } UnmapViewOfFile(fBeg); //По новой отображаем файл в память полностью fBeg = MapViewOfFile( fMap, FILE_MAP_WRITE, 0, 0, 0); if (fBeg == NULL) { Log->Lines->Add("Ошибка при вызове MapViewOfFile(): "); parse_error(); CloseHandle(fMap); return; } |
mz_head = (IMAGE_DOS_HEADER *)fBeg; (DWORD)pe_head = (DWORD)fBeg + peOffset + sizeof(DWORD); (DWORD)pe_opt_head = (DWORD)pe_head + sizeof(IMAGE_FILE_HEADER); //Определяем расположение таблицы импорта в секции импорта... DWORD ImportRVA = pe_opt_head-> DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress; int sect_num = -1; //Ищем секцию с таблицей импорта... (DWORD)sect = (DWORD)pe_opt_head + sizeof(IMAGE_OPTIONAL_HEADER); int i; for ( i=0; i |
//Вычисляем размер новой таблицы импорта: //Суммируем количество уже используемых DLL + наша DLL + zero запись. DWORD NewImportTableSize = sizeof(IMAGE_IMPORT_DESCRIPTOR)*(DLLCounter+2); char dllName[] = "azx"; NewImportTableSize += strlen(dllName)+1; //Получаем файловый указатель на конец секции импорта. LPVOID pos; (DWORD)pos = AfterImportSecBeg-1; DWORD maxFree = 0; DWORD prevPtr; LPVOID FreePtr = NULL; //Ищем максимальный кусок свободного места в секции... while ( pos >= ImportSecBeg ) { if ( *(BYTE *)pos == 0x00 ) { prevPtr = (DWORD)pos; while (*(BYTE *)pos == 0x00) (DWORD)pos -= 1; if ( ((DWORD)prevPtr - (DWORD)pos) > maxFree ) { maxFree = ((DWORD)prevPtr - (DWORD)pos); (DWORD)FreePtr = (DWORD)pos + 1; } } (DWORD)pos -= 1; } //Модифицируем полученный указатель на свободный блок, т.к. //он может указывать на завершающий нулевой DWORD //какой-либо структуры (LPDWORD)FreePtr +=1; maxFree -=4; //Проверяем объем свободного места if ( maxFree < NewImportTableSize ) { Log->Lines->Add("Недостаточно свободного места в таблице импорта \ для занесения информации об дополнительной библиотеке."); UnmapViewOfFile(fBeg); CloseHandle(fMap); return; } else Log->Lines->Add("Достаточно свободного \ места для занесения дополнительной информации."); Application->ProcessMessages(); |
//1. Копируем старую таблицу импорта в новое место memcpy(FreePtr, ImportTable, sizeof(IMAGE_IMPORT_DESCRIPTOR)*DLLCounter); //2.1 Сохраняем строку с именем нашей DLL в старой таблице импорта //(для экономии места) memcpy(ImportTable, OUR_DLL_NAME, strlen(OUR_DLL_NAME)); LPDWORD zeroPtr; (DWORD)zeroPtr = (DWORD)ImportTable + strlen(OUR_DLL_NAME); //2.2 Сохраняем структуру IMAGE_IMPORT_BY_NAME в старой таблице импорта. //(так же для экономии места) IMAGE_IMPORT_BY_NAME myName; myName.Hint = 0x00; myName.Name[0] = 0x00; WORD Hint = 0; char myFuncName[] = OUR_FUNC_NAME; hackRec patch; patch.ZeroDword = NULL; patch.IAT = ImportRVA + strlen(OUR_DLL_NAME) + sizeof(hackRec); patch.IATEnd = NULL; DWORD IIBN_Table; memcpy(zeroPtr, &patch, sizeof(patch)); (DWORD)zeroPtr += sizeof(patch); memcpy(zeroPtr, &Hint, sizeof(WORD)); (DWORD)zeroPtr += sizeof(WORD); memcpy(zeroPtr, myFuncName, strlen(myFuncName)+1 ); (DWORD)zeroPtr += strlen(myFuncName)+1; memcpy(zeroPtr, &myName, sizeof(IMAGE_IMPORT_BY_NAME) ); //2.3. Заполняем структуру IMAGE_IMPORT_DESCRIPTOR данными об нашей DLL IMAGE_IMPORT_DESCRIPTOR myDLL; //Вычисляем указатель на нашу структуру IMAGE_IMPORT_BY_NAME: //это адрес начала старой таблицы импорта + длинна строки с именем //нашей DLL + нулевой DWORD IIBN_Table = ImportRVA + strlen( OUR_DLL_NAME ) + sizeof(DWORD); //Указатель на таблицу Characteristics myDLL.Characteristics = IIBN_Table; myDLL.TimeDateStamp = NULL; myDLL.ForwarderChain = NULL; //Записываем адрес строки с именем файла нашей DLL myDLL.Name = ImportRVA; //Указатель на таблицу FirstThunk myDLL.FirstThunk = IIBN_Table; //Записываем в новую таблицу импорта запись о нашей DLL LPVOID OldFreePtr = FreePtr; (DWORD)FreePtr +=sizeof(IMAGE_IMPORT_DESCRIPTOR)*DLLCounter; memcpy(FreePtr, &myDLL, sizeof(IMAGE_IMPORT_DESCRIPTOR)); //Создаем "финальную" нулевую запись со всеми полями равными нулю myDLL.Characteristics = NULL; myDLL.TimeDateStamp = NULL; myDLL.ForwarderChain = NULL; myDLL.Name = NULL; myDLL.FirstThunk = NULL; //И записываем её в конец новой таблицы импорта. (DWORD)FreePtr +=sizeof(IMAGE_IMPORT_DESCRIPTOR)*DLLCounter; memcpy(FreePtr, &myDLL, sizeof(IMAGE_IMPORT_DESCRIPTOR)); //3. Устанавливаем указатель на нашу таблицу импорта. // Вычисляем RVA нашей таблицы DWORD NewImportTableRVA = (DWORD)OldFreePtr - (DWORD)ImportSecBeg + sect->VirtualAddress; // Заносим его в DataDirectory pe_opt_head->DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress = NewImportTableRVA; pe_opt_head->DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].Size = (DLLCounter + 1) * sizeof(IMAGE_IMPORT_DESCRIPTOR); UnmapViewOfFile(fBeg); CloseHandle(fMap); |
обсудить | все отзывы (1) | |
[56851; 143; 6.21] |
|
|