
PEACH
Uma estrutura de isolamento de inquilino
downloadToDir() sanitizes file/directory names returned by the FTP server using basename(file.name) !== file.name. However, path.basename("..") === "..", so the check evaluates to false for the literal name .., allowing the traversal protection to be bypassed. A malicious FTP server can list a directory entry named .., causing the client to descend outside the intended local destination directory.
src/Client.ts:737 — sanitization check does not handle ..:
const hasInvalidName = !file.name || basename(file.name) !== file.name
// BYPASS: basename("..") === ".." → hasInvalidName = false → not skippedsrc/Client.ts:743 — path constructed with unsanitized name:
const localPath = join(localDirPath, file.name)
// join("/home/user/downloads", "..") → "/home/user" (outside target dir)src/Client.ts:745-746 — recursive download outside target:
await this.cd(file.name) // cd("..") on the server
await this._downloadFromWorkingDir(localPath) // downloads to /home/user insteadconst { basename, join } = require("path");
// The check that is supposed to block traversal:
const fileName = "..";
const hasInvalidName = !fileName || basename(fileName) !== fileName;
console.log("hasInvalidName:", hasInvalidName);
// Output: hasInvalidName: false ← BYPASSED
const localPath = join("/home/user/downloads", fileName);
console.log("resolved path:", localPath);
// Output: resolved path: /home/user ← ESCAPED target directoryA malicious FTP server returning [{ name: "..", isDirectory: true }] from its LIST response triggers this code path, causing _downloadFromWorkingDir to be called with the parent directory path, writing server files outside the intended download location.
A client connecting to a malicious FTP server (e.g., via a user-supplied URL, a Man-in-the-Middle attack on unencrypted FTP, or a compromised server) and calling downloadToDir() may have files written outside the intended local directory, potentially overwriting system files or placing malicious files in sensitive locations.
v6.2.4 (latest) and earlier versions with downloadToDir().
Add an explicit check for . and .. in the name guard:
const hasInvalidName =
!file.name ||
file.name === "." ||
file.name === ".." || // add this line
basename(file.name) !== file.name;Or use a path containment check:
const resolvedLocal = resolve(localDirPath, file.name);
if (!resolvedLocal.startsWith(resolve(localDirPath) + sep)) {
this.ftp.log(`Unsafe filename skipped: ${JSON.stringify(file.name)}`);
continue;
}Origem: NVD
Avaliação Gratuita de Vulnerabilidades
Avalie suas práticas de segurança em nuvem em 9 domínios de segurança para avaliar seu nível de risco e identificar lacunas em suas defesas.
Marque uma demonstração personalizada
"A melhor experiência do usuário que eu já vi, fornece visibilidade total para cargas de trabalho na nuvem."
"A Wiz fornece um único painel de vidro para ver o que está acontecendo em nossos ambientes de nuvem."
"Sabemos que se a Wiz identifica algo como crítico, na verdade é."