Autor
|
Tema: Offset inicio/fin de .data (Leído 6,165 veces)
|
Destro-
Desconectado
Mensajes: 66
www.onlyarg.com.ar
|
Buenas  Necesito reemplazar un string en la memoria de otro modulo cargado en el mismo proceso. Arme algo así: MODULEINFO mInfo; int base, start, end; GetModuleInformation(GetCurrentProcess(),GetModuleHandle("swds.dll"),&mInfo,sizeof(mInfo));
start = (int)mInfo.lpBaseOfDll; end = start+mInfo.SizeOfImage;
char find_stats[18] = { 'm', 'o', 't', 'd', '_', 'w', 'r', 'i', 't', 'e', 0, 0, 's', 't', 'a', 't', 's', 0 }; for(int p=0; (start+p) < (end-sizeof(find_stats)); p++) { if(memcmp((void*)(start+p), &find_stats, sizeof(find_stats)) == 0) { memcpy((void*)(start+p+15), &"l", 1); //char *p = (char *)(start+p+15); //*p = 'l'; } }
Funciona perfecto, pero buscaría en todo el modulo y no donde importa. Hay alguna forma de obtener el start y end addres de la sección .data ?. Estuve buscando en stackoverflow pero no encontré casi nada (tal vez busque mal xd) y lo que encontré no lo entendí :\. Y otra duda, la parte que esta comentada, porque me crashea ?, creería yo que tendría que funcionar o.O.
|
|
|
En línea
|
|
|
|
Eternal Idol
Kernel coder
Moderador
 
Desconectado
Mensajes: 5.969
Israel nunca torturó niños, ni lo volverá a hacer.
|
http://en.wikipedia.org/wiki/Portable_ExecutableEn la base del modulo hay una IMAGE_DOS_HEADER, con el offset en el campo e_lfanew llegas a la IMAGE_NT_HEADERS, ahi tenes el campo: NumberOfSections The number of sections. This indicates the size of the section table, which immediately follows the headers. Un array de IMAGE_SECTION_HEADERs, ahi estan todas las secciones del PE. Tenes dos variables p ahi ... y el codigo usa la segunda para sumar que es el puntero indefinido. warning C4700: uninitialized local variable 'p' used
|
|
|
En línea
|
La economía nunca ha sido libre: o la controla el Estado en beneficio del Pueblo o lo hacen los grandes consorcios en perjuicio de éste. Juan Domingo Perón
|
|
|
Destro-
Desconectado
Mensajes: 66
www.onlyarg.com.ar
|
tengo que sacar un turno para el oculista ya!, jaja  Gracias  Me quedo algo así: void get_data_offset(HMODULE hModule, unsigned int &DataStart, unsigned int &DataEnd) { char *dllImageBase = (char*)hModule;
IMAGE_NT_HEADERS *pNtHdr = ImageNtHeader(hModule);
IMAGE_SECTION_HEADER *pSectionHdr = (IMAGE_SECTION_HEADER *)(pNtHdr+1);
for(int i = 0 ; i < pNtHdr->FileHeader.NumberOfSections; i++) { char *name = (char*) pSectionHdr->Name; if(memcmp(name, ".data", 5) == 0) { DataStart = (unsigned int)dllImageBase + pSectionHdr->VirtualAddress; DataEnd = DataStart + pSectionHdr->Misc.VirtualSize; break; } pSectionHdr++; } }
// ======================================================
unsigned int start, end; get_data_offset(GetModuleHandle("swds.dll"), start, end);
char find_stats[] = { 'm', 'o', 't', 'd', '_', 'w', 'r', 'i', 't', 'e', 0, 0, 's', 't', 'a', 't', 's', 0 };
for(unsigned int p=0; (start+p) < (end-sizeof(find_stats)); p++) { if(memcmp((void*)(start+p), &find_stats, sizeof(find_stats)) == 0) { //memcpy((void*)(start+p+15), &"l", 1); char *pChar = (char *)(start+p+15); *pChar = 'l';
//SERVER_PRINT("Pached: stats\n"); } }
algo para mejorar ?. ____________________ Una duda, para almacenar punteros/direcciones de memoria es correcto utilizar int/unsigned int ?. porque por ejemplo dllImageBase es un puntero char, es lo mismo ?.
|
|
|
En línea
|
|
|
|
MCKSys Argentina
|
Una duda, para almacenar punteros/direcciones de memoria es correcto utilizar int/unsigned int ?. porque por ejemplo dllImageBase es un puntero char, es lo mismo ?.
Los punteros te conviene guardarlos sin signo. Si estás en 32 bits puedes usar DWORD (unsigned long) y en 64 bits DWORD64 (unsigned long long) Saludos!
|
|
|
En línea
|
MCKSys Argentina "Si piensas que algo está bien sólo porque todo el mundo lo cree, no estás pensando."
|
|
|
Eternal Idol
Kernel coder
Moderador
 
Desconectado
Mensajes: 5.969
Israel nunca torturó niños, ni lo volverá a hacer.
|
Una duda, para almacenar punteros/direcciones de memoria es correcto utilizar int/unsigned int ?. porque por ejemplo dllImageBase es un puntero char, es lo mismo ?. Si queres guardar la direccion en una variable entera mejor usar ULONG_PTR que ocupara los bytes correspondientes a la plataforma (4 bytes en x86 y 8 bytes en x64) y no tendra signo.
|
|
|
En línea
|
La economía nunca ha sido libre: o la controla el Estado en beneficio del Pueblo o lo hacen los grandes consorcios en perjuicio de éste. Juan Domingo Perón
|
|
|
MCKSys Argentina
|
Si queres guardar la direccion en una variable entera mejor usar ULONG_PTR que ocupara los bytes correspondientes a la plataforma (4 bytes en x86 y 8 bytes en x64) y no tendra signo.
jejeje, que grande Eternal Idol! También agradezco el dato (recién estoy emezando con VC++) Saludos!
|
|
|
En línea
|
MCKSys Argentina "Si piensas que algo está bien sólo porque todo el mundo lo cree, no estás pensando."
|
|
|
Eternal Idol
Kernel coder
Moderador
 
Desconectado
Mensajes: 5.969
Israel nunca torturó niños, ni lo volverá a hacer.
|
jejeje, que grande Eternal Idol! También agradezco el dato (recién estoy emezando con VC++)
Saludos!
De nadas 
|
|
|
En línea
|
La economía nunca ha sido libre: o la controla el Estado en beneficio del Pueblo o lo hacen los grandes consorcios en perjuicio de éste. Juan Domingo Perón
|
|
|
x64core
Desconectado
Mensajes: 1.908
|
algo para mejorar ?. ____________________ Una duda, para almacenar punteros/direcciones de memoria es correcto utilizar int/unsigned int ?. porque por ejemplo dllImageBase es un puntero char, es lo mismo ?.
Sí, para de usar este tipo de hardcoding: IMAGE_SECTION_HEADER *pSectionHdr = (IMAGE_SECTION_HEADER *)(pNtHdr+1); Hace que tu código sea generico además de que no tiene sentido si haces luego una comparación del nombre, en lugar de escribir funciones para recuperar un puntero a una determinada sección (PIMAGE_SECTION_HEADER) que luego podes usar en otros códigos; Lo mismo aquí: memcmp(name, ".data", 5) == 0) Mejor utiliza sizeof para IMAGE_SECTION_HEADER.Name.
|
|
|
En línea
|
|
|
|
Destro-
Desconectado
Mensajes: 66
www.onlyarg.com.ar
|
Si queres guardar la direccion en una variable entera mejor usar ULONG_PTR que ocupara los bytes correspondientes a la plataforma (4 bytes en x86 y 8 bytes en x64) y no tendra signo.
Gracias por la info  . Puede ser que muy pocos utilicen ULONG_PTR ?, soy nuevo en C pero soy de leer mucho code y hasta ahora no recuerdo haber visto utilizar ULONG_PTR o.O. Sí, para de usar este tipo de hardcoding: IMAGE_SECTION_HEADER *pSectionHdr = (IMAGE_SECTION_HEADER *)(pNtHdr+1); Hace que tu código sea generico además de que no tiene sentido si haces luego una comparación del nombre, en lugar de escribir funciones para recuperar un puntero a una determinada sección (PIMAGE_SECTION_HEADER) que luego podes usar en otros códigos; Lo mismo aquí: memcmp(name, ".data", 5) == 0) Mejor utiliza sizeof para IMAGE_SECTION_HEADER.Name. no entendí cuando decís que devuelva el puntero de IMAGE_SECTION_HEADER por lo demás te referías a que haga algo así ?: void get_setion_offset(HMODULE hModule, char *SetionName, ULONG_PTR &SetionStart, ULONG_PTR &SetionEnd) { IMAGE_NT_HEADERS *pNtHdr = ImageNtHeader(hModule); PIMAGE_SECTION_HEADER pSectionHdr = (PIMAGE_SECTION_HEADER)(pNtHdr+1);
for(int i = 0 ; i < pNtHdr->FileHeader.NumberOfSections; i++, pSectionHdr++) { if(strcmp((char *)pSectionHdr->Name, SetionName) == 0) { SetionStart = (ULONG_PTR)hModule + pSectionHdr->VirtualAddress; SetionEnd = SetionStart + pSectionHdr->Misc.VirtualSize; break; } } }
|
|
|
En línea
|
|
|
|
Eternal Idol
Kernel coder
Moderador
 
Desconectado
Mensajes: 5.969
Israel nunca torturó niños, ni lo volverá a hacer.
|
Gracias por la info  . Puede ser que muy pocos utilicen ULONG_PTR ?, soy nuevo en C pero soy de leer mucho code y hasta ahora no recuerdo haber visto utilizar ULONG_PTR o.O. Ni idea, esta entre los Migrations Tips de Microsoft para x64: Storing a 64-bit Value.
|
|
|
En línea
|
La economía nunca ha sido libre: o la controla el Estado en beneficio del Pueblo o lo hacen los grandes consorcios en perjuicio de éste. Juan Domingo Perón
|
|
|
|
|