
Corrige a vulnerabilidade de poluição de protótipo (CVE-2023-26136) no pacote tough-cookie
Poluição de protótipo é uma vulnerabilidade JavaScript que permite a um atacante adicionar propriedades arbitrárias a protótipos de objetos globais, que podem então ser herdadas por objetos definidos pelo usuário. Uma fonte de poluição de protótipo é qualquer entrada controlável pelo usuário que permita adicionar propriedades arbitrárias a objetos de protótipo. As fontes mais comuns são as seguintes: URL JSON Mensagens da Web
Para o pacote tough-cookies ( v2.5.0), o mais relevante é o primeiro, via URL. Acontece da seguinte forma:
Aqui está uma requisição:
https://vulnerable-website.com/?__proto__[badProperty]=payload
Ao dividir a string de consulta em pares chave:valor, um parser de URL pode interpretar proto como uma string arbitrária.
Em algum momento, a operação de mesclagem recursiva pode atribuir o valor de evilProperty usando uma declaração equivalente à seguinte:
targetObject.__proto__.badProperty = 'payload';
__proto__ tem um uso especial em JavaScript. Como sabemos, se para algum objeto alguma propriedade P1 não for encontrada, ela será procurada no protótipo desse objeto.
Exemplo
function myClass() {
this.P1 = 'value';
}
let mc = new myClass();
console.log(mc.P1); //Value
console.log(mc.P2); //Undefined
mc.__proto__.P2 = 'value2';
let mc2 = new myClass();
console.log(mc.P2); //value2
Após alterar __proto__ - todas as instâncias criadas de myClass terão a propriedade P2.
Para o pacote tough-cookies ( v2.5.0 ), essa vulnerabilidade de poluição de protótipo pode ser vista no trecho de código:
await new Promise((resolve, reject) => {
cookiejar.setCookie(
"Slonser=polluted; Domain=__proto__; Path=/notauth",
"https://__proto__/admin",
{ loose: true },
(err, cookie) => {
if (err) {
reject(err);
} else {
resolve(cookie);
}
}
);
});
Foi descoberto que a classe CookieJar usa MemoryCookieStore como armazenamento por padrão. E em vários métodos, objetos de MemoryCookieStore são inicializados da seguinte forma:
this.idx = {};
Isso significa que propriedades com valores (que podem ser valores problemáticos) podem ser adicionadas ao protótipo de this.idx via __proto__. Para evitar isso, em vários lugares a inicialização foi alterada da seguinte forma:
this.idx = Object.create(null);
Isso cria um objeto vazio sem protótipo. Foi adicionado o teste memstore_vulnerability_fix_test.js verificando a correção.