hacktricks/pentesting-web/browser-extension-pentesting-methodology/README.md

594 lines
33 KiB
Markdown
Raw Normal View History

# Metodologia de Pentesting em Extensões de Navegador
<details>
<summary><strong>Aprenda hacking no AWS do zero ao herói com</strong> <a href="https://training.hacktricks.xyz/courses/arte"><strong>htARTE (HackTricks AWS Red Team Expert)</strong></a><strong>!</strong></summary>
Outras formas de apoiar o HackTricks:
* Se você quer ver sua **empresa anunciada no HackTricks** ou **baixar o HackTricks em PDF**, confira os [**PLANOS DE ASSINATURA**](https://github.com/sponsors/carlospolop)!
* Adquira o [**material oficial PEASS & HackTricks**](https://peass.creator-spring.com)
* Descubra [**A Família PEASS**](https://opensea.io/collection/the-peass-family), nossa coleção de [**NFTs**](https://opensea.io/collection/the-peass-family) exclusivos
* **Junte-se ao grupo** 💬 [**Discord**](https://discord.gg/hRep4RUj7f) ou ao grupo [**telegram**](https://t.me/peass) ou **siga-me** no **Twitter** 🐦 [**@carlospolopm**](https://twitter.com/carlospolopm)**.**
* **Compartilhe suas técnicas de hacking enviando PRs para os repositórios github do** [**HackTricks**](https://github.com/carlospolop/hacktricks) e [**HackTricks Cloud**](https://github.com/carlospolop/hacktricks-cloud).
</details>
## Informações Básicas
Extensões de navegador são escritas em JavaScript e carregadas pelo navegador em segundo plano. Possuem seu próprio [DOM](https://www.w3schools.com/js/js_htmldom.asp), mas podem interagir com o DOM de outros sites. Isso significa que podem comprometer a confidencialidade, integridade e disponibilidade (CIA) de outros sites.
## Principais Componentes
A estrutura de uma extensão é melhor visualizada e consiste em três componentes. Vamos analisar cada componente em detalhes.
<figure><img src="../../.gitbook/assets/image (4).png" alt=""><figcaption><p><a href="http://webblaze.cs.berkeley.edu/papers/Extensions.pdf">http://webblaze.cs.berkeley.edu/papers/Extensions.pdf</a></p></figcaption></figure>
### **Scripts de Conteúdo**
Cada script de conteúdo tem acesso direto ao DOM de uma **página web única** e, portanto, está exposto a **entradas potencialmente maliciosas**. No entanto, o script de conteúdo não contém permissões além da capacidade de enviar mensagens para o núcleo da extensão.
### **Núcleo da Extensão**
O núcleo da extensão contém a maioria dos privilégios/acessos da extensão, mas só pode interagir com o conteúdo da web por meio de [XMLHttpRequest](https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest) e scripts de conteúdo. Além disso, o núcleo da extensão não tem acesso direto à máquina hospedeira.
### **Binário Nativo**
A extensão permite um binário nativo que pode **acessar a máquina hospedeira com todos os privilégios do usuário.** O binário nativo interage com o núcleo da extensão através da Interface de Programação de Aplicativos de Plug-in Netscape padrão ([NPAPI](https://en.wikipedia.org/wiki/NPAPI)) usada pelo Flash e outros plug-ins de navegador.
### Limites
{% hint style="danger" %}
Para obter os privilégios completos do usuário, um atacante deve convencer a extensão a passar entradas maliciosas do script de conteúdo para o núcleo da extensão e do núcleo da extensão para o binário nativo.
{% endhint %}
Cada componente da extensão é separado um do outro por **fortes barreiras de proteção**. Cada componente executa em um **processo separado do sistema operacional**. Scripts de conteúdo e núcleos de extensão executam em **processos sandbox** inacessíveis à maioria dos serviços do sistema operacional.
Além disso, scripts de conteúdo são separados das páginas web associadas por **executarem em um heap JavaScript separado**. O script de conteúdo e a página web têm **acesso ao mesmo DOM subjacente**, mas os dois **nunca trocam ponteiros JavaScript**, prevenindo o vazamento de funcionalidades JavaScript.
## **`manifest.json`**
Uma extensão do Chrome é apenas uma pasta ZIP com uma extensão de arquivo [.crx](https://www.lifewire.com/crx-file-2620391). O núcleo da extensão é o arquivo **`manifest.json`** na raiz da pasta, que especifica o layout, permissões e outras opções de configuração.
Exemplo:
```json
{
"manifest_version": 2,
"name": "My extension",
"version": "1.0",
"permissions": [
"storage"
],
"content_scripts": [
{
"js": [
"script.js"
],
"matches": [
"https://example.com/*",
"https://www.example.com/*"
],
"exclude_matches": ["*://*/*business*"],
}
],
"background": {
"scripts": [
"background.js"
]
},
"options_ui": {
"page": "options.html"
}
}
```
### `content_scripts`
Os scripts de conteúdo são **carregados** sempre que o usuário **navega para uma página correspondente**, no nosso caso qualquer página que corresponda à expressão **`https://example.com/*`** e que não corresponda à regex **`*://*/*/business*`**. Eles executam **como os próprios scripts da página** e têm acesso arbitrário ao [Document Object Model (DOM)](https://developer.mozilla.org/en-US/docs/Web/API/Document\_Object\_Model) da página.
```json
"content_scripts": [
{
"js": [
"script.js"
],
"matches": [
"https://example.com/*",
"https://www.example.com/*"
],
"exclude_matches": ["*://*/*business*"],
}
],
```
Para incluir ou excluir mais URLs, também é possível usar **`include_globs`** e **`exclude_globs`**.
Este é um exemplo de script de conteúdo que adicionará um botão de explicação à página quando [a API de armazenamento](https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/API/storage) recuperar o valor `message` do armazenamento da extensão.
```js
chrome.storage.local.get("message", result =>
{
let div = document.createElement("div");
div.innerHTML = result.message + " <button>Explain</button>";
div.querySelector("button").addEventListener("click", () =>
{
chrome.runtime.sendMessage("explain");
});
document.body.appendChild(div);
});
```
<figure><img src="../../.gitbook/assets/image (7).png" alt=""><figcaption></figcaption></figure>
Quando este botão é clicado, o script de conteúdo **usa** a [**runtime.sendMessage() API**](https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/API/runtime/sendMessage) **para enviar uma mensagem às páginas da extensão**. Isso ocorre porque um script de conteúdo só tem acesso direto a um punhado de APIs, como `storage`. Tudo o mais precisa ser feito pelas páginas da extensão, às quais os scripts de conteúdo podem enviar mensagens.
{% hint style="warning" %}
As **capacidades do script de conteúdo** diferem ligeiramente dependendo do navegador. Para navegadores baseados em Chromium, você pode encontrar a lista na [documentação dos Desenvolvedores Chrome](https://developer.chrome.com/docs/extensions/mv3/content\_scripts/#capabilities), para o Firefox, [MDN](https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/Content\_scripts#webextension\_apis) é a fonte definitiva.\
Lembre-se de que o Script de Conteúdo também pode **comunicar com os scripts de fundo** para que eles realizem ações e enviem de volta a resposta.
{% endhint %}
Para visualizar e depurar scripts de conteúdo no Chrome, você pode abrir o menu de ferramentas de desenvolvedor do Chrome em Opções > Mais ferramentas > Ferramentas do desenvolvedor OU (Pressione - Ctrl + Shift + I).
Com as ferramentas de desenvolvedor exibidas, clique na **aba Fonte**, depois clique na aba **Scripts de Conteúdo**. Aqui você pode ver os scripts de conteúdo em execução das várias extensões e definir pontos de interrupção para monitorar o fluxo de execução.
<figure><img src="../../.gitbook/assets/image (1) (1).png" alt=""><figcaption></figcaption></figure>
### Scripts de conteúdo injetados
{% hint style="success" %}
Note que **Scripts de Conteúdo não são obrigatórios**, pois também é possível **injetar** scripts **dinamicamente** e **programaticamente** em páginas web via **`tabs.executeScript`**. Isso na verdade fornece controles mais **granulares**.
{% endhint %}
Para injetar um script de conteúdo programaticamente, sua extensão precisa de [permissões de host](https://developer.chrome.com/docs/extensions/reference/permissions) para a página na qual está tentando injetar scripts. As permissões de host podem ser concedidas **solicitando-as** como parte do manifesto da sua extensão ou temporariamente via [**activeTab**](https://developer.chrome.com/docs/extensions/reference/manifest/activeTab)**.**
#### Exemplo de extensão baseada em activeTab
{% code title="manifest.json" %}
```json
{
"name": "My extension",
...
"permissions": [
"activeTab",
"scripting"
],
"background": {
"service_worker": "background.js"
},
"action": {
"default_title": "Action Button"
}
}
```
* **Injetar um arquivo JS ao clicar:**
```javascript
// content-script.js
document.body.style.backgroundColor = "orange";
//service-worker.js - Inject the JS file
chrome.action.onClicked.addListener((tab) => {
chrome.scripting.executeScript({
target: { tabId: tab.id },
files: ["content-script.js"]
});
});
```
* **Injetar uma função** ao clicar:
```javascript
//service-worker.js - Inject a function
function injectedFunction() {
document.body.style.backgroundColor = "orange";
}
chrome.action.onClicked.addListener((tab) => {
chrome.scripting.executeScript({
target : {tabId : tab.id},
func : injectedFunction,
});
});
```
#### Exemplo com permissões de script
```javascript
// service-workser.js
chrome.scripting.registerContentScripts([{
id : "test",
matches : [ "https://*.nytimes.com/*" ],
excludeMatches : [ "*://*/*business*" ],
js : [ "contentScript.js" ],
}]);
// ANother example
chrome.tabs.executeScript(tabId, { file: "content_script.js" });
```
Para incluir ou excluir mais URLs, também é possível usar **`include_globs`** e **`exclude_globs`**.
### Scripts de Conteúdo `run_at`
O campo `run_at` controla **quando arquivos JavaScript são injetados na página web**. O valor preferido e padrão é `"document_idle"`.
Os valores possíveis são:
* **`document_idle`**: Sempre que possível
* **`document_start`**: Após quaisquer arquivos de `css`, mas antes de qualquer outro DOM ser construído ou qualquer outro script ser executado.
* **`document_end`**: Imediatamente após o DOM estar completo, mas antes de subrecursos como imagens e frames serem carregados.
#### Via `manifest.json`
```json
{
"name": "My extension",
...
"content_scripts": [
{
"matches": ["https://*.nytimes.com/*"],
"run_at": "document_idle",
"js": ["contentScript.js"]
}
],
...
}
```
Via **`service-worker.js`**
```javascript
chrome.scripting.registerContentScripts([{
id : "test",
matches : [ "https://*.nytimes.com/*" ],
runAt : "document_idle",
js : [ "contentScript.js" ],
}]);
```
### `background`
Quando scripts de conteúdo enviam uma mensagem, seu destino é a **página de background**. A página de background é uma página especial que está **sempre presente** a menos que especificado de outra forma no manifesto da extensão. Ela é invisível para o usuário, apesar de ser uma página regular com seu próprio DOM e tudo mais. Sua função é tipicamente coordenar todas as outras partes da extensão.
{% hint style="success" %}
Se uma página de background não for declarada explicitamente, o navegador irá gentilmente **gerar uma** automaticamente e garantir que todos os **scripts de background declarados sejam carregados** nela, como no exemplo anterior de manifest.json.
{% endhint %}
Exemplo de script de background:
```js
chrome.runtime.onMessage.addListener((request, sender, sendResponse) =>
{
if (request == "explain")
{
chrome.tabs.create({ url: "https://example.net/explanation" });
}
})
```
Ele utiliza a [API runtime.onMessage](https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/API/runtime/onMessage) para ouvir mensagens. Quando uma mensagem `"explain"` é recebida, ele usa a [API tabs](https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/API/tabs) para abrir uma página em uma nova aba.
Para depurar o script de background, você pode ir aos **detalhes da extensão e inspecionar o service worker,** isso abrirá as ferramentas de desenvolvedor com o script de background:
<figure><img src="broken-reference" alt=""><figcaption></figcaption></figure>
### Páginas de opções e outras
Extensões de navegador podem conter vários tipos de páginas:
* **Páginas de ação** são exibidas em um **menu suspenso quando o ícone da extensão** é clicado.
* Páginas que a extensão irá **carregar em uma nova aba**.
* **Páginas de Opções**: Esta página é exibida sobre a extensão quando clicada. No manifesto anterior, no meu caso, eu consegui acessar esta página em `chrome://extensions/?options=fadlhnelkbeojnebcbkacjilhnbjfjca` ou clicando:
<figure><img src="../../.gitbook/assets/image (8).png" alt="" width="375"><figcaption></figcaption></figure>
Ao contrário da página de background, essas páginas não são persistentes, mas sim carregadas quando necessário. No entanto, todas elas podem **receber mensagens de scripts de conteúdo**. E todas têm **acesso total às APIs específicas da extensão**, na medida em que as permissões da extensão permitem.
Juntando tudo, os contextos relevantes para extensões de navegador parecem assim:
<figure><img src="../../.gitbook/assets/image (9).png" alt="" width="563"><figcaption></figcaption></figure>
### `permissions` & `host_permissions`
**`permissions`** e **`host_permissions`** são entradas do `manifest.json` que indicarão **quais permissões** a extensão do navegador possui (armazenamento, localização...) e em **quais páginas da web**.
Como as extensões de navegador podem ser tão **privilegiadas**, uma maliciosa ou comprometida pode permitir ao atacante **diferentes meios para roubar informações sensíveis e espionar o usuário**.
Verifique como essas configurações funcionam e como elas podem ser abusadas em:
{% content-ref url="browext-permissions-and-host_permissions.md" %}
[browext-permissions-and-host\_permissions.md](browext-permissions-and-host\_permissions.md)
{% endcontent-ref %}
### `content_security_policy`
Uma **política de segurança de conteúdo** também pode ser declarada dentro do `manifest.json`. Se houver uma definida, ela pode ser **vulnerável**.
A configuração padrão para páginas de extensões de navegador é bastante restritiva:
```bash
script-src 'self'; object-src 'self';
```
Para mais informações sobre CSP e possíveis bypasses, confira:
{% content-ref url="../content-security-policy-csp-bypass/" %}
[content-security-policy-csp-bypass](../content-security-policy-csp-bypass/)
{% endcontent-ref %}
### `web_accessible_resources`
para que uma página da web acesse uma página de uma Extensão de Navegador, uma página `.html` por exemplo, esta página precisa ser mencionada no campo **`web_accessible_resources`** do `manifest.json`.\
Por exemplo:
```javascript
{
...
"web_accessible_resources": [
{
"resources": [ "images/*.png" ],
"matches": [ "https://example.com/*" ]
},
{
"resources": [ "fonts/*.woff" ],
"matches": [ "https://example.com/*" ]
}
],
...
}
```
Estas páginas são acessíveis em URLs como:
```
chrome-extension://<extension-id>/message.html
```
Nas extensões públicas, o **extension-id é acessível**:
<figure><img src="../../.gitbook/assets/image (722).png" alt="" width="375"><figcaption></figcaption></figure>
No entanto, se o parâmetro `manifest.json` **`use_dynamic_url`** for usado, este **id pode ser dinâmico**.
Ser permitido acessar essas páginas torna essas páginas **potencialmente vulneráveis a ClickJacking**:
{% content-ref url="browext-clickjacking.md" %}
[browext-clickjacking.md](browext-clickjacking.md)
{% endcontent-ref %}
{% hint style="success" %}
Permitir que essas páginas sejam carregadas apenas pela extensão e não por URLs aleatórias poderia prevenir ataques de ClickJacking.
{% endhint %}
### `externally_connectable`
Conforme a [**documentação**](https://developer.chrome.com/docs/extensions/reference/manifest/externally-connectable), a propriedade `"externally_connectable"` do manifesto declara **quais extensões e páginas da web podem se conectar** à sua extensão através de [runtime.connect](https://developer.chrome.com/docs/extensions/reference/runtime#method-connect) e [runtime.sendMessage](https://developer.chrome.com/docs/extensions/reference/runtime#method-sendMessage).
* Se a chave **`externally_connectable`** **não** for declarada no manifesto da sua extensão ou for declarada como **`"ids": ["*"]`**, **todas as extensões podem se conectar, mas nenhuma página da web pode se conectar**.
* Se **IDs específicos forem especificados**, como em `"ids": ["aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"]`, **apenas aquelas aplicações** poderão se conectar.
* Se **correspondências** forem especificadas, esses aplicativos da web poderão se conectar:
```json
"matches": [
"https://*.google.com/*",
"*://*.chromium.org/*",
```
* Se estiver especificado como vazio: **`"externally_connectable": {}`**, nenhum aplicativo ou página web poderá se conectar.
Quanto **menos extensões e URLs** indicadas aqui, **menor será a superfície de ataque**.
{% hint style="danger" %}
Se uma página web **vulnerável a XSS ou takeover** estiver indicada em **`externally_connectable`**, um atacante poderá **enviar mensagens diretamente para o script de background**, contornando completamente o Content Script e seu CSP.
Portanto, este é um **bypass muito poderoso**.
{% endhint %}
## Comunicação Web **↔︎** Content Script
Embora os ambientes de execução dos **content scripts e das páginas** que os hospedam sejam **isolados** um do outro, eles **compartilham acesso ao DOM da página**. Se a página deseja se comunicar com o content script, ou com a extensão através do content script, deve fazê-lo através do **DOM compartilhado**.
### Postar Mensagens
{% code title="content-script.js" %}
```javascript
var port = chrome.runtime.connect();
window.addEventListener("message", (event) => {
// We only accept messages from ourselves
if (event.source !== window) {
return;
}
if (event.data.type && (event.data.type === "FROM_PAGE")) {
console.log("Content script received: " + event.data.text);
port.postMessage(event.data.text);
}
}, false);
```
{% endcode %}
{% code title="example.js" %}
```javascript
document.getElementById("theButton").addEventListener("click", () => {
window.postMessage(
{type : "FROM_PAGE", text : "Hello from the webpage!"}, "*");
}, false);
```
{% endcode %}
Uma comunicação segura de Post Message deve verificar a autenticidade da mensagem recebida, isso pode ser feito verificando:
* **`event.isTrusted`**: Isso é verdadeiro apenas se o evento foi acionado por uma ação do usuário
* O script de conteúdo pode estar esperando uma mensagem apenas se o usuário realizar alguma ação
* **domínio de origem**: Pode ser verificado contra uma lista de permissões de domínios.
* Se um regex é usado, tenha muito cuidado
* **Fonte**: `received_message.source !== window` pode ser usado para verificar se a mensagem foi **da mesma janela** onde o Script de Conteúdo está ouvindo.
Os controles anteriores, mesmo que realizados, podem ser vulneráveis, então verifique na seguinte página **possíveis bypasses de Post Message**:
{% content-ref url="../postmessage-vulnerabilities/" %}
[postmessage-vulnerabilities](../postmessage-vulnerabilities/)
{% endcontent-ref %}
### Iframe
Outra possível forma de comunicação pode ser através de **URLs de Iframe**, você pode encontrar um exemplo em:
{% content-ref url="browext-xss-example.md" %}
[browext-xss-example.md](browext-xss-example.md)
{% endcontent-ref %}
### DOM
Isso não é "exatamente" uma forma de comunicação, mas a **web e o script de conteúdo terão acesso ao DOM da web**. Então, se o **script de conteúdo** está lendo alguma informação dele, **confiando no DOM da web**, a web poderia **modificar esses dados** (porque a web não deve ser confiável, ou porque a web é vulnerável a XSS) e **comprometer o Script de Conteúdo**.
Você também pode encontrar um exemplo de um **XSS baseado em DOM para comprometer uma extensão de navegador** em:
{% content-ref url="browext-xss-example.md" %}
[browext-xss-example.md](browext-xss-example.md)
{% endcontent-ref %}
## Informações Sensíveis na Memória/Código
Se uma Extensão de Navegador armazena **informações sensíveis dentro de sua memória**, isso poderia ser **despejado** (especialmente em máquinas Windows) e **procurado** por essas informações.
Portanto, a memória da Extensão de Navegador **não deve ser considerada segura** e **informações sensíveis** como credenciais ou frases mnemônicas **não devem ser armazenadas**.
Claro, **não coloque informações sensíveis no código**, pois elas serão **públicas**.
## Comunicação Script de Conteúdo **↔︎** Script de Fundo
Um Script de Conteúdo pode usar as funções [**runtime.sendMessage()**](https://developer.chrome.com/docs/extensions/reference/runtime#method-sendMessage) **ou** [**tabs.sendMessage()**](https://developer.chrome.com/docs/extensions/reference/tabs#method-sendMessage) para enviar uma mensagem **serializável em JSON de uso único**.
Para lidar com a **resposta**, use a **Promise** retornada. No entanto, para compatibilidade com versões anteriores, você ainda pode passar um **callback** como o último argumento.
Enviar uma solicitação de um **script de conteúdo** se parece com isso:
```javascript
(async () => {
const response = await chrome.runtime.sendMessage({greeting: "hello"});
// do something with response here, not outside the function
console.log(response);
})();
```
Enviando uma solicitação da **extensão** (geralmente um **script de background**) para um script de conteúdo é semelhante, exceto que você precisa especificar para qual aba enviá-la. Este exemplo demonstra o envio de uma mensagem para o script de conteúdo na aba selecionada.
```javascript
(async () => {
const [tab] = await chrome.tabs.query({active: true, lastFocusedWindow: true});
const response = await chrome.tabs.sendMessage(tab.id, {greeting: "hello"});
// do something with response here, not outside the function
console.log(response);
})();
```
No **lado receptor**, você precisa configurar um [**runtime.onMessage**](https://developer.chrome.com/docs/extensions/reference/runtime#event-onMessage) **ouvinte de evento** para lidar com a mensagem. Isso parece o mesmo de um script de conteúdo ou página de extensão.
```javascript
chrome.runtime.onMessage.addListener(
function(request, sender, sendResponse) {
console.log(sender.tab ?
"from a content script:" + sender.tab.url :
"from the extension");
if (request.greeting === "hello")
sendResponse({farewell: "goodbye"});
}
);
```
No exemplo acima, **`sendResponse()`** foi chamado de forma síncrona. Se você quiser usar `sendResponse()` de forma **assíncrona**, adicione `return true;` ao manipulador de eventos `onMessage`.
> Se múltiplas páginas estiverem ouvindo eventos `onMessage`, **apenas a primeira a chamar `sendResponse()`** para um evento específico terá sucesso em enviar a resposta. Todas as outras respostas para aquele evento serão ignoradas.
Para novas extensões, você deve preferir promessas em vez de callbacks. Se você estiver usando callbacks, o callback `sendResponse()` só é válido se usado de forma síncrona, ou se o manipulador de eventos retornar `true` para indicar que responderá de forma assíncrona. O callback da função `sendMessage()` será invocado automaticamente se nenhum manipulador retornar true ou se o callback `sendResponse()` for coletado como lixo.
## Carregando uma Extensão no Navegador
1. **Baixe** a Extensão do Navegador e descompacte
2. Vá para **`chrome://extensions/`** e **ative** o `Modo de Desenvolvedor`
3. Clique no botão **`Carregar descompactado`**
No **Firefox**, vá para **`about:debugging#/runtime/this-firefox`** e clique no botão **`Carregar Complemento Temporário`**.
## Obtendo o código-fonte da loja
A partir de [**aqui**](https://gist.github.com/paulirish/78d6c1406c901be02c2d):
### Opção 1: Download da extensão via linha de comando como zip e extração
{% code overflow="wrap" %}
```bash
extension_id=jifpbeccnghkjeaalbbjmodiffmgedin # change this ID
curl -L -o "$extension_id.zip" "https://clients2.google.com/service/update2/crx?response=redirect&os=mac&arch=x86-64&nacl_arch=x86-64&prod=chromecrx&prodchannel=stable&prodversion=44.0.2403.130&x=id%3D$extension_id%26uc"
unzip -d "$extension_id-source" "$extension_id.zip"
```
{% endcode %}
Obrigado ao crxviewer pelo [URL de download mágico](https://github.com/Rob--W/crxviewer/blob/6113c25e3569e1ec59365ad9a177aa97e2bcda61/src/cws\_pattern.js#L27-L74).
### Opção 2: Use o site CRX Viewer
[https://robwu.nl/crxviewer/](https://robwu.nl/crxviewer/)
### Opção 3: Use a extensão CRX Viewer
A [Chrome extension source viewer](https://chrome.google.com/webstore/detail/chrome-extension-source-v/jifpbeccnghkjeaalbbjmodiffmgedin?hl=en) é open source ([repositório github](https://github.com/Rob--W/crxviewer)) e facilita muito esse processo.
### Opção 3: Visualizar fonte da extensão instalada localmente
1. Encontre o diretório de perfil local do Chrome. Abra `chrome://version/` e localize o campo "Caminho do Perfil:". Abra essa pasta.
2. Abra a subpasta `Extensions/`
3. Todas as suas extensões estão aqui, com código-fonte geralmente legível.
#### Mapeamento entre IDs de extensões instaladas localmente e nomes
* Em `about:extensions`, ative o Modo Desenvolvedor e você verá IDs sob cada entrada
* Dentro das pastas `Extensions/`, o arquivo manifest.json tem um campo `name` legível
## Lista de Verificação de Auditoria de Segurança
Embora as Extensões de Navegador tenham uma **superfície de ataque limitada**, algumas delas podem conter **vulnerabilidades** ou **melhorias de proteção potenciais**. As mais comuns são:
* [ ] **Limite** o máximo possível as **`permissions`** solicitadas
* [ ] **Limite** o máximo possível as **`host_permissions`**
* [ ] Use uma **`content_security_policy`** **forte**
* [ ] **Limite** o máximo possível o **`externally_connectable`**, se nenhum for necessário e possível, não deixe por padrão, especifique **`{}`**
* [ ] Se **URL vulnerável a XSS ou a takeover** for mencionada aqui, um atacante poderá **enviar mensagens diretamente aos scripts de background**. Um bypass muito poderoso.
* [ ] **Limite** o máximo possível os **`web_accessible_resources`**, até mesmo vazio se possível.
* [ ] Se **`web_accessible_resources`** não for nenhum, verifique [**ClickJacking**](browext-clickjacking.md)
* [ ] Se houver alguma **comunicação** da **extensão** para a **página web**, [**verifique vulnerabilidades de XSS**](browext-xss-example.md) causadas na comunicação.
* [ ] Se Post Messages forem usados, verifique [**vulnerabilidades de Post Message**](../postmessage-vulnerabilities/)**.**
* [ ] Se o **Content Script acessar detalhes do DOM**, verifique se eles **não estão introduzindo um XSS** se forem **modificados** pela web
* [ ] Dê uma ênfase especial se essa comunicação também estiver envolvida na **comunicação Content Script -> Background script**
* [ ] **Informações sensíveis não devem ser armazenadas** no código da Extensão de Navegador
* [ ] **Informações sensíveis não devem ser armazenadas** na memória da Extensão de Navegador
## Ferramentas
### [**Tarnish**](https://thehackerblog.com/tarnish/)
* Baixa qualquer extensão do Chrome a partir de um link fornecido da Chrome webstore.
* **Visualizador de [**manifest.json**](https://developer.chrome.com/extensions/manifest)**: simplesmente exibe uma versão em JSON formatado do manifest da extensão.
* **Análise de Impressão Digital**: Detecção de [web\_accessible\_resources](https://developer.chrome.com/extensions/manifest/web\_accessible\_resources) e geração automática de JavaScript para fingerprinting de extensões do Chrome.
* **Análise Potencial de Clickjacking**: Detecção de páginas HTML de extensão com a diretiva [web\_accessible\_resources](https://developer.chrome.com/extensions/manifest/web\_accessible\_resources) definida. Estas são potencialmente vulneráveis a clickjacking, dependendo da finalidade das páginas.
* **Visualizador de Aviso(s) de Permissão**: que mostra uma lista de todos os avisos de prompt de permissão do Chrome que serão exibidos quando um usuário tentar instalar a extensão.
* **Função(ões) Perigosa(s)**: mostra a localização de funções perigosas que podem potencialmente ser exploradas por um atacante (por exemplo, funções como innerHTML, chrome.tabs.executeScript).
* **Ponto(s) de Entrada**: mostra onde a extensão recebe entrada de usuário/externa. Isso é útil para entender a área de superfície de uma extensão e procurar pontos potenciais para enviar dados maliciosamente elaborados para a extensão.
* Tanto o scanner de Função(ões) Perigosa(s) quanto o de Ponto(s) de Entrada têm o seguinte para seus alertas gerados:
* Trecho de código relevante e linha que causou o alerta.
* Descrição do problema.
* Um botão "Ver Arquivo" para visualizar o arquivo de código completo.
* O caminho do arquivo alertado.
* A URI completa da extensão do Chrome do arquivo alertado.
* O tipo de arquivo, como um script de Página de Fundo, Script de Conteúdo, Ação do Navegador, etc.
* Se a linha vulnerável estiver em um arquivo JavaScript, os caminhos de todas as páginas onde está incluído, bem como o tipo dessas páginas e status de [web\_accessible\_resource](https://developer.chrome.com/extensions/manifest/web\_accessible\_resources).
* **Analisador de Política de Segurança de Conteúdo (CSP) e verificador de bypass**: Isso apontará fraquezas na CSP da sua extensão e também iluminará quaisquer maneiras potenciais de contornar sua CSP devido a CDNs na lista branca, etc.
* **Bibliotecas Conhecidas Vulneráveis**: Isso usa [Retire.js](https://retirejs.github.io/retire.js/) para verificar o uso de bibliotecas JavaScript conhecidas por serem vulneráveis.
* Baixe a extensão e versões formatadas.
* Baixe a extensão original.
* Baixe uma versão embelezada da extensão (HTML e JavaScript automaticamente formatados).
* Cache automático dos resultados da análise, executar uma análise de extensão levará um bom tempo na primeira vez que você executá-la. No entanto, a segunda vez, assumindo que a extensão não foi atualizada, será quase instantânea devido aos resultados serem armazenados em cache.
* URLs de Relatório Linkáveis, facilmente vincule alguém a um relatório de extensão gerado pelo tarnish.
### [Neto](https://github.com/elevenpaths/neto)
O projeto Neto é um pacote Python 3 concebido para analisar e desvendar recursos ocultos de plugins e extensões de navegadores bem conhecidos, como Firefox e Chrome. Ele automatiza o processo de descompactar os arquivos empacotados para extrair esses recursos de recursos relevantes em uma extensão como `manifest.json`, pastas de localização ou arquivos de fonte Javascript e HTML.
## Referências
* **Agradecimentos a** [**@naivenom**](https://twitter.com/naivenom) **pela ajuda com esta metodologia**
* [https://www.cobalt.io/blog/introduction-to-chrome-browser-extension-security-testing](https://www.cobalt.io/blog/introduction-to-chrome-browser-extension-security-testing)
* [https://palant.info/2022/08/10/anatomy-of-a-basic-extension/](https://palant.info/2022/08/10/anatomy-of-a-basic-extension/)
* [https://palant.info/2022/08/24/attack-surface-of-extension-pages/](https://palant.info/2022/08/24/attack-surface-of-extension-pages/)
* [https://palant.info/2022/08/31/when-extension-pages-are-web-accessible/](https://palant.info/2022/08/31/when-extension-pages-are-web-accessible/)
* [https://help.passbolt.com/assets/files/PBL-02-report.pdf](https://help.passbolt.com/assets/files/PBL-02-report.pdf)
* [https://developer.chrome.com/docs/extensions/develop/concepts/content-scripts](https://developer.chrome.com/docs/extensions/develop/concepts/content-scripts)
* [https://developer.chrome.com/docs/extensions/mv2/background-pages](https://developer.chrome.com/docs/extensions/mv2/background-pages)
* [https://thehackerblog.com/kicking-the-rims-a-guide-for-securely-writing-and-auditing-chrome-extensions/](https://thehackerblog.com/kicking-the-rims-a-guide-for-securely-writing-and-auditing-chrome-extensions/)
<details>
<summary><strong>Aprenda hacking no AWS do zero ao herói com</strong> <a href="https://training.hacktricks.xyz/courses/arte"><strong>htARTE (HackTricks AWS Red Team Expert)</strong></a><strong>!</strong></summary>
Outras formas de apoiar o HackTricks:
* Se você quiser ver sua **empresa anunciada no HackTricks** ou **baixar o HackTricks em PDF**, confira os [**PLANOS DE ASSINATURA**](https://github.com/sponsors/carlospolop)!
* Adquira o [**merchandising oficial do PEASS & HackTricks**](https://peass.creator-spring.com)
* Descubra [**A Família PEASS**](https://opensea.io/collection/the-peass-family), nossa coleção de [**NFTs**](https://opensea.io/collection/the-peass-family) exclusivos
* **Junte-se ao grupo** 💬 [**Discord**](https://discord.gg/hRep4RUj7f) ou ao [**grupo do telegram**](https://t.me/peass) ou **siga-me** no **Twitter** 🐦 [**@carlospolopm**](https://twitter.com/carlospolopm)**.**
* **Compartilhe suas dicas de hacking enviando PRs para os repositórios github** [**HackTricks**](https://github.com/carlospolop/hacktricks) e [**HackTricks Cloud**](https://github.com/carlospolop/hacktricks-cloud).
</details>