Vorrei sapere bene come funziona questa tecnica e come applicarla.
Allora, il programma inietta nello spazio di un'altro programma il codice della dll, giusto?
ecco, tale codice quand'è che viene eseguito?
cioè, questo è il codice che ho usato per fare un'esperimento:
Dllinjector.c
Functions.hcodice:#include <stdio.h> #include <windows.h> #include "functions.h" int main(){ char processName[] = "calc.exe"; /* Nome processo su cui effettuare injection */ char logFile[]= "log.log"; /* Nome del file di log per controllare successo o fallimento operazioni */ char dllName[]="dll.dll"; /* Nome dll da cui prelevare il codice da iniettare */ HANDLE proc, thread; DWORD threadId, bWritten; BOOL check; VOID *remoteBuff; DWORD pid; FILE *fp; fp = fopen(logFile, "w"); fprintf(fp, "Looking for: %s\n\n", processName); pid = trovaPid(processName, fp); if(pid == 0xFFFFFFFF){ fprintf(fp, "\nProcess not found\n"); return 0; } check = abilitaSeDebugName(fp); if (check == 0){ fprintf(fp, "\nAbilitazione privilegio SE_DEBUG_NAME fallita\n"); } proc = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pid); if (proc == NULL){ fprintf(fp, "Errore OpenProcess() %d\n", GetLastError()); return -1; } remoteBuff = VirtualAllocEx(proc, NULL, strlen(dllName), MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); if (remoteBuff == NULL){ fprintf(fp, "Errore VirtualAllocEx() %d\n", GetLastError()); return -1; } else fprintf(fp, "\nCreati %d bytes all' indirizzo 0x%x\n", strlen(dllName), (ULONG)remoteBuff); check = WriteProcessMemory(proc, remoteBuff, dllName, strlen(dllName), &bWritten); if (check == 0){ fprintf(fp, "Errore WriteProcessMemory() %d\n", GetLastError()); return -1; } thread = CreateRemoteThread(proc, NULL, 0, (LPTHREAD_START_ROUTINE)GetProcAddress(LoadLibrary("kernel32.dll"), "LoadLibraryA"), remoteBuff, 0, &threadId); if (thread == NULL) fprintf(fp, "Errore CreateRemoteThread() %d\n", GetLastError()); fprintf(fp, "\nInjection eseguita\n"); fclose(fp); return 0; }
e la dll mostra una semplice messagebox:codice:int trovaPid(char *procName, FILE *log) { typedef struct _LSA_UNICODE_STRING { /* struttura dati di una stringa Unicode */ USHORT Length; USHORT MaximumLength; PWSTR Buffer; } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; typedef struct _STRING { /* struttura dati di una stringa Ansi */ USHORT Length; USHORT MaximumLength; PCHAR Buffer; } ANSI_STRING, *PANSI_STRING; typedef enum _SYSTEM_INFORMATION_CLASS { SystemBasicInformation, SystemProcessorInformation, SystemPerformanceInformation, SystemTimeOfDayInformation, SystemNotImplemented1, SystemProcessesAndThreadsInformation, SystemCallCounts, SystemConfigurationInformation, SystemProcessorTimes, SystemGlobalFlag, SystemNotImplemented2, SystemModuleInformation, }SYSTEM_INFORMATION_CLASS; typedef struct _SYSTEM_PROCESSES { /* Informazioni sui processi di sistema (struttura non completa) */ ULONG NextEntryDelta; ULONG ThreadCount; ULONG Reserved1[6]; LARGE_INTEGER CreateTime; LARGE_INTEGER UserTime; LARGE_INTEGER KernelTime; UNICODE_STRING ProcessName; ULONG BasePriority; ULONG ProcessId; } SYSTEM_PROCESSES, *PSYSTEM_PROCESSES; /* Definizione delle funzioni non presenti nei compilatori tradizionali */ typedef DWORD (WINAPI *PfZwQuerySystemInformation)(SYSTEM_INFORMATION_CLASS, PBYTE, ULONG, PULONG); typedef DWORD (WINAPI *PfRtlAnsiStringToUnicodeString)(PUNICODE_STRING, PANSI_STRING, BOOL); typedef DWORD (WINAPI *PfRtlUnicodeStringToAnsiString)(PANSI_STRING, PUNICODE_STRING, BOOL); typedef DWORD (WINAPI *PfRtlCompareUnicodeString)(PUNICODE_STRING, PUNICODE_STRING, BOOL); PfZwQuerySystemInformation MyZwQuerySystemInformation; PfRtlAnsiStringToUnicodeString MyRtlAnsiStringToUnicodeString; PfRtlUnicodeStringToAnsiString MyRtlUnicodeStringToAnsiString; PfRtlCompareUnicodeString MyRtlCompareUnicodeString; BOOL check; DWORD pid = 0xFFFFFFFF; void *pStruct; /* buffer per contenere la struttura delle informazioni sui processi */ ULONG dimBuffer = 0x8000; /* dimensione del buffer pStruct */ PSYSTEM_PROCESSES sp; ANSI_STRING buffAnsi; UNICODE_STRING buffUni; ULONG dimRich; buffAnsi.Buffer = (PCHAR)malloc(lstrlenA(procName) + 1); lstrcpyA(buffAnsi.Buffer, procName); buffAnsi.Length = lstrlenA(buffAnsi.Buffer); buffAnsi.MaximumLength = lstrlenA(buffAnsi.Buffer); MyRtlAnsiStringToUnicodeString = (PfRtlAnsiStringToUnicodeString)GetProcAddress(LoadLibrary("ntdll.dll"), "RtlAnsiStringToUnicodeString"); MyRtlAnsiStringToUnicodeString(&buffUni, &buffAnsi, TRUE); pStruct = (void *)malloc(dimBuffer); MyZwQuerySystemInformation = (PfZwQuerySystemInformation)GetProcAddress(LoadLibrary("ntdll.dll"), "ZwQuerySystemInformation"); check = MyZwQuerySystemInformation(SystemProcessesAndThreadsInformation, (PBYTE)pStruct, dimBuffer, &dimRich); if (check != 0){ fprintf(log, "Errore ZwQuerySystemInformation() dimensione minima buffer: 0x%x\n", dimRich); return -1; } /* ciclo di ricerca del processo da terminare */ do{ sp = (PSYSTEM_PROCESSES) pStruct; MyRtlUnicodeStringToAnsiString = (PfRtlUnicodeStringToAnsiString)GetProcAddress(LoadLibrary("ntdll.dll"), "RtlUnicodeStringToAnsiString"); MyRtlUnicodeStringToAnsiString(&buffAnsi, &(sp->ProcessName), TRUE); fprintf(log, "Process Name: %s\tProcess ID: %d\n", buffAnsi.Buffer, sp->ProcessId); MyRtlCompareUnicodeString = (PfRtlCompareUnicodeString)GetProcAddress(LoadLibrary("ntdll.dll"), "RtlCompareUnicodeString"); check = MyRtlCompareUnicodeString(&buffUni, &(sp->ProcessName), TRUE); if (check == 0){ fprintf(log, "FOUND!!\n"); pid = sp->ProcessId; } pStruct = (void*)((ULONG)pStruct + sp->NextEntryDelta); } while(sp->NextEntryDelta != 0); return pid; } int abilitaSeDebugName(FILE *log){ BOOL check; HANDLE currProc, tok; LUID lu_sdn; TOKEN_PRIVILEGES tp; LUID_AND_ATTRIBUTES luaa; currProc = GetCurrentProcess(); if (currProc == NULL){ fprintf(log, "\nErrore GetCurrentProcess() %d\n", GetLastError()); return 0; } check = OpenProcessToken(currProc, TOKEN_ALL_ACCESS, &tok); if (check == 0){ fprintf(log, "\nErrore OpenProcessToken() %d\n", GetLastError()); return 0; } check = LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &lu_sdn); if (check == 0){ fprintf(log, "\nErrore LookupPrivilegeValue() %d\n", GetLastError()); return 0; } /* abilitazione del privilegio SE_DEBUG_NAME */ tp.PrivilegeCount = 1; luaa.Luid = lu_sdn; luaa.Attributes = SE_PRIVILEGE_ENABLED; tp.Privileges[0] = luaa; check = AdjustTokenPrivileges(tok, FALSE, &tp, sizeof(tp), NULL, NULL); if (check == 0){ fprintf(log, "\nErrore AdjustTokenPrivileges() %d\n", GetLastError()); return 0; } return 1; }
allora,io avvio calc.exe poi eseguo dllinjector.exe che nel log conferma che l'operazione è stata completata con successo, ora? dove e quando verrà eseguito il codice della dll?codice:#include <windows.h> BOOL APIENTRY DllMain(HINSTANCE hDLLInst, DWORD fdwReason, LPVOID lpvReserved) { switch (fdwReason) { case DLL_PROCESS_ATTACH: { MessageBox(0, "Codice eseguito!!!!", "DLL Loaded", MB_OK); return TRUE; } case DLL_PROCESS_DETACH: /* operazioni di rilascio della dll */ break; } return TRUE; }
help me please! :master:

Rispondi quotando