У меня есть буфер памяти, который содержит действительное изображение файла exe, и я хочу извлечь из него некоторые ресурсы.
Для этого я использую функцию FindResource
, но функция ожидает HMODULE и сбой при подаче буфера памяти с помощью exe.
Есть ли способ заставить его работать с буфером памяти вместо того, чтобы писать exe во временный файл, загружая его с помощью LoadLibrary
, а затем выполнив необходимую работу?Использование FindResource с буфером памяти
ответ
Я есть буфер памяти, который содержит действительный файл изображения
в какой форме? я думаю, чем в сыром (как на диске). но для использования FindResource вам нужно «отобразить как изображение». не трудно на карту вы сырое изображение самовывоза (, если вы хотите только ресурс доступа, но не выполнить его из памяти) примера кода:
PVOID MapImage(PIMAGE_DOS_HEADER pvRawData, ULONG cbRawData)
{
if (cbRawData < sizeof(IMAGE_DOS_HEADER))
{
return 0;
}
if (pvRawData->e_magic != IMAGE_DOS_SIGNATURE)
{
return 0;
}
ULONG e_lfanew = pvRawData->e_lfanew, s = e_lfanew + sizeof(IMAGE_NT_HEADERS);
if (e_lfanew >= s || s > cbRawData)
{
return 0;
}
PIMAGE_NT_HEADERS pinth = (PIMAGE_NT_HEADERS)RtlOffsetToPointer(pvRawData, e_lfanew);
if (pinth->Signature != IMAGE_NT_SIGNATURE)
{
return 0;
}
ULONG SizeOfImage = pinth->OptionalHeader.SizeOfImage, SizeOfHeaders = pinth->OptionalHeader.SizeOfHeaders;
s = e_lfanew + SizeOfHeaders;
if (SizeOfHeaders > SizeOfImage || SizeOfHeaders >= s || s > cbRawData)
{
return 0;
}
s = FIELD_OFFSET(IMAGE_NT_HEADERS, OptionalHeader) + pinth->FileHeader.SizeOfOptionalHeader;
if (s > SizeOfHeaders)
{
return 0;
}
ULONG NumberOfSections = pinth->FileHeader.NumberOfSections;
PIMAGE_SECTION_HEADER pish = (PIMAGE_SECTION_HEADER)RtlOffsetToPointer(pinth, s);
ULONG Size;
if (NumberOfSections)
{
if (e_lfanew + s + NumberOfSections * sizeof(IMAGE_SECTION_HEADER) > SizeOfHeaders)
{
return 0;
}
do
{
if (Size = min(pish->Misc.VirtualSize, pish->SizeOfRawData))
{
union {
ULONG VirtualAddress, PointerToRawData;
};
VirtualAddress = pish->VirtualAddress, s = VirtualAddress + Size;
if (VirtualAddress > s || s > SizeOfImage)
{
return 0;
}
PointerToRawData = pish->PointerToRawData, s = PointerToRawData + Size;
if (PointerToRawData > s || s > cbRawData)
{
return 0;
}
}
} while (pish++, --NumberOfSections);
}
PVOID ImageBase = VirtualAlloc(0, SizeOfImage, MEM_COMMIT, PAGE_READWRITE);
if (!ImageBase)
{
return 0;
}
memcpy(ImageBase, pvRawData, SizeOfHeaders);
if (NumberOfSections = pinth->FileHeader.NumberOfSections)
{
do
{
--pish;
if (Size = min(pish->Misc.VirtualSize, pish->SizeOfRawData))
{
memcpy(RtlOffsetToPointer(ImageBase, pish->VirtualAddress),
RtlOffsetToPointer(pvRawData, pish->PointerToRawData), Size);
}
} while (--NumberOfSections);
}
return ImageBase;
}
void Test(PVOID pvRawData, ULONG cbRawData, PCWSTR lpType, PCWSTR lpName)
{
if (HMODULE ImageBase = (HMODULE)MapImage((PIMAGE_DOS_HEADER)pvRawData, cbRawData))
{
if (HRSRC hResInfo = FindResource(ImageBase, lpName, lpType))
{
if (HGLOBAL hg = LoadResource(ImageBase, hResInfo))
{
__nop();
}
}
VirtualFree(ImageBase, 0, MEM_RELEASE);
}
}
MapImage содержащей проверку допустимых размеров данных. Однако, если вы уверены, что (pvRawData, cbRawData) является 100% правильно - вы можете пропустить эту проверку и упростить код
// я редактирую Test
функция, основанная на @IInspectable комментарий - удалить __try/__ исключением - он не нужен здесь
Почему существует SEH в функции 'Test'? Ни одна из вызываемых функций не документирована для получения исключений Win32. – IInspectable
@Inspectable - потому что, если данные изображения неверны - 'FindResource' может вызвать нарушение прав доступа. но если мы уверены, что данные верны (у нас есть изображение как внедренный ресурс, но он не читается с диска или сети), мы можем пропустить __try/__ except. в MapImage я проверяю только допустимые размеры для карты. но, например, что будет, если 'pinth-> НеобязательныйHeader.DataDirectory [IMAGE_DIRECTORY_ENTRY_RESOURCE] .VirtualAddress' некорректный? exception в 'FindResource' – RbMm
@IInspectable - однако вы правы - теперь я проверяю - исключение внутреннего дескриптора FindResource, поэтому мы можем удалить __try \ __ except block – RbMm
Ваши варианты:
- Сохранить временный файл и загрузки с
LoadLibraryEx
. - Разберите файл PE и найдите ресурс самостоятельно.
- Повторите необходимые действия для загрузки модуля из памяти в виде одной из библиотек модулей памяти.
- 1. Аварии с буфером памяти с общей памятью
- 2. Использование Snappy сжатия с буфером
- 3. Использование Three.js с буфером трафарета
- 4. Проблемы с FindResource()
- 5. Использование fscanf с динамически выделенным буфером
- 6. Адресная памяти и связь с переполнением буфером
- 7. XGetImage с предварительно выделенным буфером памяти
- 8. overriding findResource
- 9. FindResource() не работает с DataTemplate
- 10. Windows, FindResource error 1814
- 11. Ошибка FindResource PNG?
- 12. Ошибка FindResource 1813 RC_DATA
- 13. FindResource возвращает пустое изображение
- 14. FindResource() не работает
- 15. (wpf) Application.Current.Resources vs FindResource
- 16. Не может найти CollectionViewSource с помощью FindResource
- 17. WPF нового View против FindResource
- 18. Проблема с буфером обмена
- 19. Проблемы с буфером вершин
- 20. Работа с буфером обмена
- 21. Сокет с таинственным буфером
- 22. Confustion с буфером realpath()
- 23. имитировать генераторы с протокольным буфером
- 24. matlab bytesAvailableCallback с пустым буфером
- 25. Использование памяти фреймов памяти
- 26. Использование памяти с указателями
- 27. Объединение объекта Vertex Array с буфером вершин и указательным буфером
- 28. Проблемы с буфером глубины и буфером шаблонов QML
- 29. Воспроизведение музыки с буфером AudioTrack буфером на Eclipse - без звука
- 30. Использование распознавания речи для Android с микрофонным буфером
Вы можете проанализировать формат PE и найти ресурсы самостоятельно. –
Теперь это недокументировано, и вы не должны этого делать, но если ваш блок памяти выровнен по DWORD (как и должно быть), вы должны иметь возможность получить действительный только ресурс «HMODULE», просто взяв начальный адрес и установив свой младший бит на 1. –