OverTheWire Bandit: Anotações dos Níveis 0–12
Um walkthrough amigável do OverTheWire Bandit, níveis 0–12 — SSH, arquivos ocultos, find, stderr, codificações e um hexdump que não acaba. Senhas omitidas, conforme as regras.
Aviso de spoiler: Este post percorre os níveis 0–12 do OverTheWire Bandit. Se você está jogando, tente cada nível antes de ler. Seguindo as regras da OverTheWire para criadores de conteúdo, nenhuma senha é publicada aqui — toda credencial foi omitida. O Bandit é gratuito; se ele ajudar você, considere doar para a OverTheWire.
O Bandit é o wargame para iniciantes da OverTheWire e o primeiro que recomendo para quem quer ficar confortável na linha de comando do Linux. Não tem interface gráfica, não tem framework de exploração e não tem adivinhação: você se conecta por SSH, resolve um pequeno quebra-cabeça no sistema de arquivos e usa a senha encontrada para entrar no próximo nível.
Passei pelos níveis 0–12 ao longo de algumas noites. Estas são minhas anotações — organizadas, sem os becos sem saída e com os comandos que realmente usei. O objetivo não é decorar uma lista de respostas. É mostrar o ritmo: olhe para o que você tem, pergunte o que aquilo é e escolha a menor ferramenta que responde à pergunta.
Antes de Começar
Algumas notas práticas:
- O host do jogo é
bandit.labs.overthewire.orge a porta SSH é2220, não a padrão22. - Suas credenciais iniciais estão na página do nível 0 do Bandit. Não vou repetir a senha aqui.
- A senha de cada nível serve para entrar no próximo. O nome de usuário muda:
bandit0,bandit1,bandit2, e assim por diante. - Um terminal Linux/macOS é suficiente. No Windows, use o WSL.
- Leia as mensagens de erro. Normalmente elas dizem exatamente o que deu errado.
O comando de login é assim:
ssh [email protected] -p 2220
Na primeira conexão, o SSH pergunta se você confia na impressão digital do host:
The authenticity of host '[bandit.labs.overthewire.org]:2220' can't be established.
ED25519 key fingerprint is SHA256:...
Are you sure you want to continue connecting (yes/no/[fingerprint])?
Digite yes se a impressão digital corresponder ao que você espera (ou se aceitar o risco para um host de jogo) e cole a senha da página do nível. A senha não aparece na tela — isso é normal.
Quando terminar, exit fecha a sessão. Depois entre como o próximo usuário com a senha que você encontrou.
Nível 0 — Entre e Leia o README
Depois de entrar, olhe ao redor:
ls
Há um único arquivo chamado readme. Leia:
cat readme
O arquivo explica as regras e termina com a senha do bandit1. Omiti a senha aqui:
The password you are looking for is: [redacted]
Esse é o ciclo inteiro. Saia e entre novamente como bandit1 com essa senha.
Nível 1 — Um Arquivo Chamado -
O próximo nível diz que a senha está em um arquivo chamado -. Se você tentar o óbvio, o shell parece travar:
cat -
Isso acontece porque muitas ferramentas Unix tratam um - sozinho como "leia da entrada padrão", não como "leia um arquivo chamado -". Você precisa deixar isso inequívoco passando um caminho:
ls -l
cat ./-
O prefixo ./ diz "a entrada chamada - no diretório atual". $PWD/- também funciona. Eu também verifiquei o que era o arquivo antes de lê-lo:
du ./-
file ./-
file informa que é texto ASCII, o que é um bom sinal. O cat então imprime a próxima senha, novamente omitida.
Nível 2 — Espaços no Nome do Arquivo
Desta vez o arquivo tem espaços no nome, além de hífens no começo:
ls
cat ./"--spaces in this filename--"
As aspas mantêm o nome inteiro como um único argumento. Sem elas, o shell divide o nome em vários argumentos e o cat reclama. O autocompletar com Tab ajuda muito aqui: digite cat ./--sp e pressione Tab; o shell completa o nome e escapa os espaços para você.
Nível 3 — Arquivos Ocultos
ls mostra um diretório inhere, mas dentro dele parece não haver nada:
cd inhere
ls
Nada. O arquivo está oculto, o que no Unix significa simplesmente que o nome começa com um ponto. Peça ao ls para incluir entradas ocultas:
ls -a
Agora você vê ...Hiding-From-You junto com os habituais . e ... A forma longa confirma que é um arquivo regular:
ls -la
cat ...Hiding-From-You
Os pontos iniciais fazem parte do nome; eles não significam "subir um diretório" a menos que o nome seja exatamente . ou ...
Nível 4 — O Arquivo Legível por Humanos
O diretório inhere contém dez arquivos chamados -file00 até -file09. O nível diz que apenas um é legível por humanos. Antes de despejar todos no terminal, pergunte ao sistema o que eles são:
file ./-file*
file identifica o tipo de cada um. Exatamente um é reportado como texto ASCII; os outros são dados. Leia esse:
cat ./-file07
(A resposta usual é -file07; use o arquivo que o file reportar como texto ASCII.)
Se você fizer o que eu fiz primeiro e rodar cat ./-file*, vai receber uma tela cheia de lixo binário e talvez um terminal quebrado. A correção é reset, ou simplesmente fechar a sessão e conectar de novo. file é a primeira jogada mais inteligente.
Nível 5 — Encontrar por Tamanho
Agora a senha está em algum lugar dentro de inhere, em um arquivo legível por humanos, com exatamente 1033 bytes e sem permissão de execução. Há vinte diretórios maybehereNN, então ficar entrando em todos é perda de tempo.
O find consegue filtrar por tudo isso:
find . -type f -size 1033c ! -executable
Uma decodificação rápida:
-type fsignifica apenas arquivos regulares.-size 1033csignifica exatamente 1033 bytes; o sufixocé de bytes.! -executableexclui arquivos com qualquer bit de execução ligado.
Minha primeira tentativa usou apenas find . -size 1033c, que encontrou um único resultado — mas adicionar as outras propriedades faz o comando dizer exatamente o que você quer. Quando tiver o caminho, confirme e leia:
file ./maybehere07/.file2
cat ./maybehere07/.file2
Nível 6 — O Sistema de Arquivos Inteiro e uma Enxurrada de Erros
Agora o arquivo pode estar em qualquer lugar do servidor. O nível dá três propriedades: pertence ao usuário bandit7, pertence ao grupo bandit6 e tem 33 bytes. Busque a partir da raiz:
find / -type f -size 33c -user bandit7 -group bandit6
O resultado é uma parede de mensagens Permission denied. Isso é esperado: como bandit6, você não pode ler todos os diretórios do sistema. O importante é para onde vão essas mensagens. Elas são escritas na saída de erro padrão (descritor de arquivo 2), enquanto o resultado útil vai para a saída padrão (descritor de arquivo 1).
Você pode jogar os erros fora:
find / -type f -size 33c -user bandit7 -group bandit6 2>/dev/null
Entendendo a linha:
2>redireciona o descritor de arquivo 2 (stderr)./dev/nullé um dispositivo especial que descarta tudo o que recebe.- O resultado agora fica legível:
./var/lib/dpkg/info/bandit7.password.
Se quiser manter outros erros visíveis e esconder apenas os de permissão, junte o stderr ao stdout e filtre:
find / -type f -size 33c -user bandit7 -group bandit6 2>&1 | grep -v 'Permission denied'
2>&1 significa "mande o stderr para o mesmo lugar que o stdout", então o grep consegue ver os dois fluxos. grep -v inverte a correspondência e descarta as linhas que você não quer. Leia o arquivo:
cat ./var/lib/dpkg/info/bandit7.password
Nível 7 — Grep na Milionésima Palavra
data.txt tem cerca de 4 MB, com uma palavra por linha seguida de um valor. A senha está ao lado da palavra millionth. Não há motivo para ler o arquivo inteiro:
grep "millionth" data.txt
grep imprime a linha correspondente, e o valor depois da tabulação é a próxima senha. Nas minhas anotações eu usei cat data.txt | grep "millionth"; funciona, mas inicia um processo extra sem motivo. O grep consegue ler o arquivo diretamente.
Nível 8 — A Linha que Aparece Uma Única Vez
data.txt está cheio de strings aleatórias repetidas. A senha é a única linha que ocorre exatamente uma vez. O comando uniq consegue encontrar linhas únicas:
sort data.txt | uniq -u
O sort não é opcional. O uniq só compara linhas adjacentes, então duplicatas distantes são invisíveis para ele. Ordenar aproxima as linhas idênticas, e uniq -u imprime apenas as linhas que aparecem uma vez.
Uma distinção útil: sort -u remove duplicatas e imprime cada linha restante uma vez. sort | uniq -u imprime apenas as linhas que não tinham duplicata nenhuma. São perguntas diferentes.
Nível 9 — Strings em um Arquivo Binário
file data.txt diz que isto é data, não texto. cat despejaria ruído binário. O comando strings extrai sequências de caracteres imprimíveis de um arquivo binário, e o nível diz que a senha é uma das poucas strings legíveis, precedida por vários caracteres =:
strings data.txt | grep "="
A saída inclui linhas como ========== password e a própria linha da senha. grep "=" é suficiente para reduzir a busca; os sinais de igual fazem parte da dica, não são decoração.
Nível 10 — Base64
data.txt é texto ASCII, mas está codificado. O file não diz qual é a codificação; o nível diz. Base64 é uma forma comum de representar dados binários como texto, e é codificação, não criptografia:
base64 -d data.txt
A flag -d decodifica. A saída é uma frase legível terminando na próxima senha. Se você ver uma string que termina em = ou == e usa apenas letras, números, + e /, base64 é uma boa aposta.
Nível 11 — ROT13
Todas as letras deste arquivo foram rotacionadas em 13 posições. ROT13 é o inverso dele mesmo: aplicar duas vezes devolve o original. O comando tr mapeia um conjunto de caracteres para outro:
tr 'A-Za-z' 'N-ZA-Mn-za-m' < data.txt
O mapeamento é A → N, B → O, e assim por diante, dando a volta no Z; minúsculas funcionam do mesmo jeito. Eu originalmente escrevi cat data.txt | tr ..., que também funciona. O redirecionamento de entrada (<) é mais limpo porque o tr não precisa de um argumento de arquivo.
Nível 12 — O Hexdump que Continua se Desdobrando
Este é o nível que parece intimidador e é, na maior parte, paciência. data.txt é um hexdump de um arquivo que foi comprimido várias vezes. Seu trabalho é reverter o hexdump e depois ficar perguntando ao file o que é o resultado, descomprimindo com a ferramenta correspondente.
Primeiro, crie um diretório de trabalho em /tmp com um nome difícil de adivinhar e copie os dados para lá:
WORK=$(mktemp -d)
cp ~/data.txt "$WORK/"
cd "$WORK"
mktemp -d cria um diretório único e imprime o nome. A variável WORK guarda esse nome para você limpar tudo depois. Agora reverta o hexdump:
xxd -r data.txt data1
file data1
xxd -r transforma o hexdump de volta em binário. file diz que são dados gzip, então renomeie para a extensão .gz e descomprima:
mv data1 data.gz
gunzip data.gz
file data
gunzip remove o arquivo .gz e escreve data. O file agora diz bzip2. Repita o mesmo padrão: combine a ferramenta com o tipo.
mv data data.bz2
bzip2 -d data.bz2
file data
Agora é gzip de novo:
mv data data.gz
gunzip data.gz
file data
Desta vez é um arquivo tar POSIX:
mv data data.tar
tar xf data.tar
file *
tar xf extrai o arquivo; file * mostra o que saiu. É data5.bin, e é outro arquivo tar:
mv data5.bin data5.tar
tar xf data5.tar
file *
Agora data6.bin é bzip2:
mv data6.bin data6.bz2
bzip2 -d data6.bz2
file data6.bin
Ele volta como um arquivo tar, então extraia:
mv data6.bin data6.tar
tar xf data6.tar
file *
data8.bin é gzip. Mais uma rodada:
mv data8.bin data8.gz
gunzip data8.gz
file data8.bin
cat data8.bin
Desta vez file diz texto ASCII, e cat imprime a frase com a senha. Omiti o valor:
The password is [redacted]
Os nomes exatos dos arquivos podem variar um pouco entre execuções, mas o ritmo não muda: file → escolha gunzip, bzip2 -d ou tar xf → renomeie se a ferramenta exigir uma extensão → repita. O comando file é o mapa; as extensões são apenas pistas.
Duas notas práticas:
- O
gzipse recusa a descomprimir um arquivo sem o sufixo.gz, a menos que você diga o contrário. Renomear é a correção mais simples.gunzipé apenas outro nome paragzip -d. - Quando terminar, limpe o que você criou, como as regras da OverTheWire pedem:
cd ~ && rm -r "$WORK".
Nível 13 — Continua...
O nível 13 muda o padrão. Em vez de entregar uma senha, ele dá uma chave SSH privada que pode entrar como bandit14, e a próxima senha fica em um arquivo que só o bandit14 consegue ler. Isso significa permissões de chave, ssh -i e ler as mensagens de erro com atenção — o arquivo de dica do nível existe por um motivo.
Ainda não escrevi essa parte. Sim, este post termina em um cliffhanger. O próximo começa no nível 13.
O Que Eu Levo Disso
Nenhum desses níveis exigiu um exploit sofisticado. Eles exigiram saber qual pequena ferramenta responde à pergunta:
ls -apara nomes ocultos.fileantes decat, especialmente quando o "arquivo" pode não ser texto.findpor propriedades, não só por nomes.2>e2>&1para separar a saída útil do ruído.grep,sort,uniq,strings,base64etrpara filtrar e decodificar.xxd -rmaisfilepara descascar camadas de compressão.
A meta-habilidade é a mesma que importa no trabalho de segurança: observe, formule uma pequena hipótese, teste e leia o erro quando falhar. O Bandit é um lugar seguro para praticar esse ciclo.
Obrigado à comunidade OverTheWire por manter o Bandit gratuito e aberto. Se você está jogando, leia as regras e as páginas dos níveis, e não publique credenciais — é por isso que toda senha acima está omitida.
Bons estudos. Nível 13 na próxima.