diff --git a/components/security-map/securityMap.generated.ts b/components/security-map/securityMap.generated.ts index 8c5e3d3d..181a92c1 100644 --- a/components/security-map/securityMap.generated.ts +++ b/components/security-map/securityMap.generated.ts @@ -273,6 +273,30 @@ export const securityMapGraph = { "normal-operations" ] }, + { + "id": "component-ai-agent", + "type": "component", + "title": "AI agent", + "summary": "A model that reads untrusted text and can call tools, write files, or construct transactions. Prompt templates do not bound what it does next.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "agent", + "llm" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "development", + "normal-operations" + ], + "framework": "ai-security" + }, { "id": "component-ci-cd", "type": "component", @@ -759,6 +783,30 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "devsecops" }, + { + "id": "control-bug-bounty-program", + "type": "control", + "title": "Bug bounty program", + "summary": "Pay independent researchers under clear scope, rewards, and triage capacity. Pair it with a durable security contact. This is not Safe Harbor for live exploits.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "bounty", + "disclosure" + ], + "roles": [ + "security-engineer" + ], + "lifecycle": [ + "normal-operations" + ], + "controlClass": "detective", + "assessmentEligible": true, + "framework": "vulnerability-disclosure" + }, { "id": "control-cloud-hardening", "type": "control", @@ -1081,6 +1129,57 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "multisig-for-protocols" }, + { + "id": "control-ensip15-normalization", + "type": "control", + "title": "ENSIP-15 name normalization", + "summary": "Normalize names with ENSIP-15 before any namehash, and warn on confusable scripts. Homographs survive if the UI skips this.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "normalization", + "homograph" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "development" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ens" + }, + { + "id": "control-execution-path-enforcement", + "type": "control", + "title": "Execution-path enforcement", + "summary": "Allow, warn, or block where the agent is about to act. Monitoring after the fact is too late for irreversible tool calls and transactions.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "runtime", + "allowlist" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "normal-operations" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ai-security" + }, { "id": "control-external-security-review", "type": "control", @@ -1330,6 +1429,31 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "devsecops" }, + { + "id": "control-l1-ens-resolution", + "type": "control", + "title": "L1-backed ENS resolution", + "summary": "For fund movement, resolve from Ethereum L1, not a stale indexer. Verify reverse records with a matching forward lookup before the send.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "l1", + "reverse-record" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "normal-operations" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ens" + }, { "id": "control-least-privilege-review", "type": "control", @@ -1379,6 +1503,33 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "wallet-security" }, + { + "id": "control-living-threat-model", + "type": "control", + "title": "Living threat model", + "summary": "Name assets, threats, and mitigations before build, then update the model when architecture or value at risk changes. A one-time workshop is not this control.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "threat-model", + "stride" + ], + "roles": [ + "engineer-developer", + "security-engineer" + ], + "lifecycle": [ + "design", + "development", + "upgrade" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "threat-modeling" + }, { "id": "control-multi-channel-transfer-confirm", "type": "control", @@ -1503,6 +1654,29 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "monitoring" }, + { + "id": "control-peer-code-review", + "type": "control", + "title": "Peer code review", + "summary": "Required human review of production changes, with a checklist that covers authz, input handling, and irreversible Web3 paths. Branch rules without actual review are theater.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "review", + "sdlc" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "development" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "secure-software-development" + }, { "id": "control-phishing-resistant-mfa", "type": "control", @@ -1530,6 +1704,30 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "iam" }, + { + "id": "control-prompt-input-constraint", + "type": "control", + "title": "Prompt input constraint", + "summary": "Classify and constrain model inputs at the execution boundary. Do not rely on boilerplate system prompts. Treat on-chain data and retrieved documents as untrusted.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "ai", + "prompt-injection" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "development" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ai-security" + }, { "id": "control-published-recovery-address", "type": "control", @@ -1557,6 +1755,30 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "safe-harbor" }, + { + "id": "control-published-security-contact", + "type": "control", + "title": "Published security contact", + "summary": "SECURITY.md, a monitored security mailbox, and .well-known/security.txt. Someone skilled acknowledges reports quickly and keeps them confidential until a fix ships.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "security.txt", + "contact" + ], + "roles": [ + "security-engineer" + ], + "lifecycle": [ + "normal-operations" + ], + "controlClass": "detective", + "assessmentEligible": true, + "framework": "vulnerability-disclosure" + }, { "id": "control-registrar-hardening", "type": "control", @@ -1919,6 +2141,39 @@ export const securityMapGraph = { "assessmentEligible": true, "framework": "treasury-operations" }, + { + "id": "guidance-account-management", + "type": "guidance", + "title": "Account management guides", + "summary": "High-value SaaS and community accounts need strong MFA, session hygiene, least privilege, and admin separation.", + "domains": [ + "devices-identity", + "community-communications" + ], + "status": "proposed", + "tags": [ + "accounts", + "mfa" + ], + "href": "/guides/account-management/overview", + "framework": "guides" + }, + { + "id": "guidance-ai-security", + "type": "guidance", + "title": "AI Security", + "summary": "Agentic AI turns instruction-following into irreversible actions. Prefer runtime execution-path controls and isolation over prompt templates alone.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai" + ], + "href": "/ai-security/overview", + "framework": "ai-security" + }, { "id": "guidance-awareness", "type": "guidance", @@ -1934,6 +2189,22 @@ export const securityMapGraph = { "href": "/awareness/overview", "framework": "awareness" }, + { + "id": "guidance-bug-bounties", + "type": "guidance", + "title": "Bug bounties", + "summary": "Bug bounties work when scope, rewards, and triage capacity match the asset risk, and researchers can report under explicit safe harbor and disclosure rules.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "bounty" + ], + "href": "/vulnerability-disclosure/bug-bounties", + "framework": "vulnerability-disclosure" + }, { "id": "guidance-cicd", "type": "guidance", @@ -1981,6 +2252,21 @@ export const securityMapGraph = { "href": "/encryption/cloud-data-encryption", "framework": "encryption" }, + { + "id": "guidance-code-reviews", + "type": "guidance", + "title": "Code reviews and peer audits", + "summary": "Review cadence, checklists, automation assist, and a culture that treats unreviewed production merges as a defect.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "review" + ], + "href": "/secure-software-development/code-reviews-peer-audits", + "framework": "secure-software-development" + }, { "id": "guidance-code-signing", "type": "guidance", @@ -2058,6 +2344,22 @@ export const securityMapGraph = { "href": "/governance/council-best-practices", "framework": "governance" }, + { + "id": "guidance-create-maintain-threat-models", + "type": "guidance", + "title": "Create and maintain threat models", + "summary": "A useful threat model is a maintained artifact. Redefine scope and mitigations when architecture or value at risk changes.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "threat-model", + "maintenance" + ], + "href": "/threat-modeling/create-maintain-threat-models", + "framework": "threat-modeling" + }, { "id": "guidance-dependency-runbook", "type": "guidance", @@ -2406,6 +2708,70 @@ export const securityMapGraph = { "href": "/encryption/encryption-in-transit", "framework": "encryption" }, + { + "id": "guidance-ens", + "type": "guidance", + "title": "ENS best practices", + "summary": "Secure ENS use means fresh L1-backed resolution for funds moves, correct name normalization, and verified bidirectional records.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens" + ], + "href": "/ens/overview", + "framework": "ens" + }, + { + "id": "guidance-ens-integrity", + "type": "guidance", + "title": "ENS data integrity", + "summary": "For fund movement, resolve from Ethereum L1 and always verify reverse records with a matching forward lookup.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "integrity" + ], + "href": "/ens/data-integrity-verification", + "framework": "ens" + }, + { + "id": "guidance-ens-normalization", + "type": "guidance", + "title": "ENS name handling", + "summary": "Normalize with ENSIP-15 before any namehash, and warn on confusable scripts that enable homograph phishing.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "normalization" + ], + "href": "/ens/name-handling-normalization", + "framework": "ens" + }, + { + "id": "guidance-execution-path", + "type": "guidance", + "title": "Execution-path enforcement", + "summary": "Enforce allow, warn, or block where the agent is about to act. Monitoring after the fact is too late for irreversible actions.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "runtime" + ], + "href": "/ai-security/execution-path-enforcement", + "framework": "ai-security" + }, { "id": "guidance-exploit-runbook", "type": "guidance", @@ -2485,13 +2851,30 @@ export const securityMapGraph = { "framework": "governance" }, { - "id": "guidance-hardware-encryption", + "id": "guidance-guides", "type": "guidance", - "title": "Hardware encryption", - "summary": "TPM, self-encrypting drives, and HSMs keep encryption keys out of host memory when they are deployed and managed correctly.", + "title": "Guides", + "summary": "Product-specific checklists for account management and endpoint controls. Follow the steps for each tool, then review settings when vendors change defaults.", "domains": [ "devices-identity", - "infrastructure" + "community-communications" + ], + "status": "proposed", + "tags": [ + "guides", + "checklists" + ], + "href": "/guides/overview", + "framework": "guides" + }, + { + "id": "guidance-hardware-encryption", + "type": "guidance", + "title": "Hardware encryption", + "summary": "TPM, self-encrypting drives, and HSMs keep encryption keys out of host memory when they are deployed and managed correctly.", + "domains": [ + "devices-identity", + "infrastructure" ], "status": "proposed", "tags": [ @@ -2501,6 +2884,23 @@ export const securityMapGraph = { "href": "/encryption/hardware-encryption", "framework": "encryption" }, + { + "id": "guidance-hardware-security-keys", + "type": "guidance", + "title": "Hardware security keys", + "summary": "Use FIDO2/WebAuthn keys on high-value accounts, register at least two keys, disable SMS fallback where possible, and test recovery before you need it.", + "domains": [ + "devices-identity" + ], + "status": "proposed", + "tags": [ + "fido2", + "webauthn", + "mfa" + ], + "href": "/guides/endpoint-security/hardware-security-keys", + "framework": "guides" + }, { "id": "guidance-iam", "type": "guidance", @@ -2516,6 +2916,23 @@ export const securityMapGraph = { "href": "/iam/overview", "framework": "iam" }, + { + "id": "guidance-identify-mitigate-threats", + "type": "guidance", + "title": "Identify and mitigate threats", + "summary": "STRIDE-oriented enumeration, attack surface analysis, and mitigation patterns for the system under review.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "stride", + "mitigation" + ], + "href": "/threat-modeling/identity-mitigate-threats", + "framework": "threat-modeling" + }, { "id": "guidance-incident-playbooks", "type": "guidance", @@ -2785,6 +3202,22 @@ export const securityMapGraph = { "href": "/privacy/overview", "framework": "privacy" }, + { + "id": "guidance-prompt-injection", + "type": "guidance", + "title": "Prompt injection defenses", + "summary": "Prompt injection succeeds because models treat text as instructions. Constrain and classify inputs at the execution boundary.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "ai", + "prompt-injection" + ], + "href": "/ai-security/prompt-injection-defenses", + "framework": "ai-security" + }, { "id": "guidance-public-networks", "type": "guidance", @@ -2887,6 +3320,54 @@ export const securityMapGraph = { "href": "/privacy/secure-browsing", "framework": "privacy" }, + { + "id": "guidance-secure-coding", + "type": "guidance", + "title": "Secure coding standards", + "summary": "Input validation, encoding, authz checks, error handling, least privilege in code, and secure data handling.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "coding", + "standards" + ], + "href": "/secure-software-development/secure-coding-standards-guidelines", + "framework": "secure-software-development" + }, + { + "id": "guidance-secure-repos", + "type": "guidance", + "title": "Secure code repositories", + "summary": "Repository compromise is supply-chain compromise. Enforce least privilege, strong authentication, protected branches, and review-required merges.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "github", + "branch-protection" + ], + "href": "/secure-software-development/secure-code-repositories-version-control", + "framework": "secure-software-development" + }, + { + "id": "guidance-security-contact", + "type": "guidance", + "title": "Security contact", + "summary": "A security contact is useless unless someone skilled monitors it, acknowledges reports quickly, and keeps findings confidential until fixes ship.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "contact", + "security.txt" + ], + "href": "/vulnerability-disclosure/security-contact", + "framework": "vulnerability-disclosure" + }, { "id": "guidance-security-culture", "type": "guidance", @@ -2983,6 +3464,37 @@ export const securityMapGraph = { "href": "/wallet-security/smart-contract-interaction-security", "framework": "wallet-security" }, + { + "id": "guidance-ssdlc", + "type": "guidance", + "title": "Secure software development", + "summary": "Security in the SDLC is continuous: design, code, review, and repository controls. It is not a final gate before ship.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "sdlc" + ], + "href": "/secure-software-development/overview", + "framework": "secure-software-development" + }, + { + "id": "guidance-ssdlc-threat-design", + "type": "guidance", + "title": "Threat modeling and secure design", + "summary": "Threat modeling before build chooses which controls matter. Secure design principles keep residual risk from depending on a single check.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "threat-model", + "design" + ], + "href": "/secure-software-development/threat-modeling-secure-design-principles", + "framework": "secure-software-development" + }, { "id": "guidance-supply-chain-overview", "type": "guidance", @@ -3032,6 +3544,22 @@ export const securityMapGraph = { "href": "/security-automation/threat-detection-response", "framework": "security-automation" }, + { + "id": "guidance-threat-modeling", + "type": "guidance", + "title": "Threat modeling", + "summary": "A structured way to decide which abuses matter before they happen. Name assets, threats, and mitigations, then keep the model current as the system changes.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "threat-model" + ], + "href": "/threat-modeling/overview", + "framework": "threat-modeling" + }, { "id": "guidance-threat-vectors", "type": "guidance", @@ -3156,6 +3684,22 @@ export const securityMapGraph = { "href": "/privacy/vpns/overview", "framework": "privacy" }, + { + "id": "guidance-vulnerability-disclosure", + "type": "guidance", + "title": "Vulnerability disclosure", + "summary": "Make fixed issues public on a deliberate timeline. Before that, teams need inbound reporting paths, triage, and a plan when quiet disclosure is no longer safe.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "disclosure" + ], + "href": "/vulnerability-disclosure/overview", + "framework": "vulnerability-disclosure" + }, { "id": "guidance-wallet-security", "type": "guidance", @@ -3370,6 +3914,30 @@ export const securityMapGraph = { ], "framework": "safe-harbor" }, + { + "id": "surface-agent-tool-path", + "type": "attack-surface", + "title": "Agent tool path", + "summary": "The moment an agent is about to call a tool, write a file, or build a transaction. After-the-fact monitoring is too late if the action is irreversible.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "tools", + "runtime" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "development", + "normal-operations" + ], + "framework": "ai-security" + }, { "id": "surface-ci-cd-secrets", "type": "attack-surface", @@ -3594,6 +4162,27 @@ export const securityMapGraph = { ], "framework": "encryption" }, + { + "id": "surface-ens-resolution", + "type": "attack-surface", + "title": "ENS name resolution", + "summary": "Turning a human-readable name into an address before a send. Stale indexers, skipped reverse checks, and confusable scripts all produce a valid-looking wrong destination.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "resolution" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "normal-operations" + ], + "framework": "ens" + }, { "id": "surface-executive-communications", "type": "attack-surface", @@ -3843,6 +4432,29 @@ export const securityMapGraph = { ], "framework": "privacy" }, + { + "id": "surface-researcher-inbound", + "type": "attack-surface", + "title": "Researcher inbound path", + "summary": "How an external researcher reaches the team with a vulnerability. Public issues, social DMs, or a dead mailbox all leak the finding before a fix exists.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "disclosure", + "contact" + ], + "roles": [ + "security-engineer", + "engineer-developer" + ], + "lifecycle": [ + "normal-operations" + ], + "framework": "vulnerability-disclosure" + }, { "id": "surface-rpc-trust-boundary", "type": "attack-surface", @@ -4266,6 +4878,24 @@ export const securityMapGraph = { "severityBasis": "Default triage is high because a stolen laptop is common and the disk holds whatever the operator used. FDE does not stop a logged-in malware session.", "framework": "encryption" }, + { + "id": "threat-prompt-injection", + "type": "threat", + "title": "Prompt injection", + "summary": "Untrusted text, including on-chain data or retrieved documents, is treated as instructions. The agent then leaks secrets or takes an action the operator did not intend.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "prompt-injection" + ], + "severity": "high", + "severityBasis": "Default triage is high because injection rides the model's instruction-following. Blast radius is whatever the agent can sign, send, or read. Prompt templates are not a control.", + "framework": "ai-security" + }, { "id": "threat-seed-phrase-compromise", "type": "threat", @@ -4345,6 +4975,42 @@ export const securityMapGraph = { ], "framework": "awareness" }, + { + "id": "threat-spoofed-ens-resolution", + "type": "threat", + "title": "Spoofed ENS resolution", + "summary": "The UI shows a trusted name while the resolved address is attacker-controlled, from a stale indexer, a reverse record that does not loop, or a homograph.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "homograph", + "spoofing" + ], + "severity": "high", + "severityBasis": "Default triage is high because the send is valid and irreversible. The bug is in resolution, not in the signature.", + "framework": "ens" + }, + { + "id": "threat-stale-threat-model", + "type": "threat", + "title": "Stale threat model", + "summary": "Architecture or value at risk changed and the model did not. New trust boundaries, admin paths, or bridges ship without named abuses or owners.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "threat-model", + "design" + ], + "severity": "high", + "severityBasis": "Default triage is high because Web3 design misses become irreversible production loss. The failure is skipped analysis, not a missing scanner.", + "framework": "threat-modeling" + }, { "id": "threat-supply-chain-compromise", "type": "threat", @@ -4366,6 +5032,24 @@ export const securityMapGraph = { ], "framework": "supply-chain" }, + { + "id": "threat-uncontactable-disclosure", + "type": "threat", + "title": "Uncontactable disclosure", + "summary": "A researcher finds a bug and cannot reach a monitored security contact. The report goes public, gets sold, or sits unread while the bug stays live.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "disclosure", + "contact" + ], + "severity": "high", + "severityBasis": "Default triage is high because inbound silence turns a fixable finding into an uncoordinated release. A bounty platform does not replace a monitored contact.", + "framework": "vulnerability-disclosure" + }, { "id": "threat-unlimited-token-approval", "type": "threat", @@ -4442,6 +5126,13 @@ export const securityMapGraph = { "type": "contains", "status": "proposed" }, + { + "id": "depends-on:component-ai-agent:component-developer-devices", + "source": "component-ai-agent", + "target": "component-developer-devices", + "type": "depends-on", + "status": "proposed" + }, { "id": "depends-on:component-ci-cd:component-dependency-graph", "source": "component-ci-cd", @@ -4583,6 +5274,27 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:component-ai-agent:guidance-ai-security", + "source": "component-ai-agent", + "target": "guidance-ai-security", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:component-ci-cd:guidance-secure-repos", + "source": "component-ci-cd", + "target": "guidance-secure-repos", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:component-community-channels:guidance-account-management", + "source": "component-community-channels", + "target": "guidance-account-management", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:component-community-channels:guidance-encrypted-communication", "source": "component-community-channels", @@ -4611,6 +5323,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:component-frontend:guidance-ens", + "source": "component-frontend", + "target": "guidance-ens", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:component-governance-module:guidance-safe-harbor-adoption", "source": "component-governance-module", @@ -4632,6 +5351,20 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:component-identity-accounts:guidance-account-management", + "source": "component-identity-accounts", + "target": "guidance-account-management", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:component-identity-accounts:guidance-guides", + "source": "component-identity-accounts", + "target": "guidance-guides", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:component-multisig:guidance-safe-harbor-scope", "source": "component-multisig", @@ -4653,6 +5386,20 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-branch-protection:guidance-secure-repos", + "source": "control-branch-protection", + "target": "guidance-secure-repos", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-bug-bounty-program:guidance-bug-bounties", + "source": "control-bug-bounty-program", + "target": "guidance-bug-bounties", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-cloud-hardening:guidance-cloud", "source": "control-cloud-hardening", @@ -4800,6 +5547,27 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-ensip15-normalization:guidance-ens-normalization", + "source": "control-ensip15-normalization", + "target": "guidance-ens-normalization", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-execution-path-enforcement:guidance-execution-path", + "source": "control-execution-path-enforcement", + "target": "guidance-execution-path", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-external-security-review:guidance-bug-bounties", + "source": "control-external-security-review", + "target": "guidance-bug-bounties", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-external-security-review:guidance-external-security-reviews", "source": "control-external-security-review", @@ -4807,6 +5575,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-external-security-review:guidance-ssdlc", + "source": "control-external-security-review", + "target": "guidance-ssdlc", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-frontend-integrity-monitoring:guidance-frontend", "source": "control-frontend-integrity-monitoring", @@ -4919,6 +5694,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-l1-ens-resolution:guidance-ens-integrity", + "source": "control-l1-ens-resolution", + "target": "guidance-ens-integrity", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-least-privilege-review:guidance-dprk-mitigation", "source": "control-least-privilege-review", @@ -4940,6 +5722,34 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-living-threat-model:guidance-create-maintain-threat-models", + "source": "control-living-threat-model", + "target": "guidance-create-maintain-threat-models", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-living-threat-model:guidance-identify-mitigate-threats", + "source": "control-living-threat-model", + "target": "guidance-identify-mitigate-threats", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-living-threat-model:guidance-ssdlc-threat-design", + "source": "control-living-threat-model", + "target": "guidance-ssdlc-threat-design", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-living-threat-model:guidance-threat-modeling", + "source": "control-living-threat-model", + "target": "guidance-threat-modeling", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-multi-channel-transfer-confirm:guidance-treasury-transaction-verification", "source": "control-multi-channel-transfer-confirm", @@ -4989,6 +5799,27 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-peer-code-review:guidance-code-reviews", + "source": "control-peer-code-review", + "target": "guidance-code-reviews", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-phishing-resistant-mfa:guidance-account-management", + "source": "control-phishing-resistant-mfa", + "target": "guidance-account-management", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-phishing-resistant-mfa:guidance-hardware-security-keys", + "source": "control-phishing-resistant-mfa", + "target": "guidance-hardware-security-keys", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-phishing-resistant-mfa:guidance-iam", "source": "control-phishing-resistant-mfa", @@ -5010,6 +5841,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-prompt-input-constraint:guidance-prompt-injection", + "source": "control-prompt-input-constraint", + "target": "guidance-prompt-injection", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-published-recovery-address:guidance-safe-harbor-scope", "source": "control-published-recovery-address", @@ -5017,6 +5855,20 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-published-security-contact:guidance-safe-harbor-scope", + "source": "control-published-security-contact", + "target": "guidance-safe-harbor-scope", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-published-security-contact:guidance-security-contact", + "source": "control-published-security-contact", + "target": "guidance-security-contact", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-registrar-hardening:guidance-dns-cert", "source": "control-registrar-hardening", @@ -5045,6 +5897,20 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-safe-harbor-adoption:guidance-vulnerability-disclosure", + "source": "control-safe-harbor-adoption", + "target": "guidance-vulnerability-disclosure", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-secure-sdlc-testing:guidance-secure-coding", + "source": "control-secure-sdlc-testing", + "target": "guidance-secure-coding", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-secure-sdlc-testing:guidance-security-testing", "source": "control-secure-sdlc-testing", @@ -5052,6 +5918,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-secure-sdlc-testing:guidance-ssdlc", + "source": "control-secure-sdlc-testing", + "target": "guidance-ssdlc", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-security-awareness-training:guidance-security-culture", "source": "control-security-awareness-training", @@ -5094,6 +5967,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-simulate-before-sign:guidance-ens-integrity", + "source": "control-simulate-before-sign", + "target": "guidance-ens-integrity", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-simulate-before-sign:guidance-signing-verification", "source": "control-simulate-before-sign", @@ -5388,6 +6268,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:threat-prompt-injection:guidance-prompt-injection", + "source": "threat-prompt-injection", + "target": "guidance-prompt-injection", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:threat-seed-phrase-compromise:guidance-seed-phrase-management", "source": "threat-seed-phrase-compromise", @@ -5423,6 +6310,27 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:threat-spoofed-ens-resolution:guidance-ens-integrity", + "source": "threat-spoofed-ens-resolution", + "target": "guidance-ens-integrity", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:threat-stale-threat-model:guidance-create-maintain-threat-models", + "source": "threat-stale-threat-model", + "target": "guidance-create-maintain-threat-models", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:threat-uncontactable-disclosure:guidance-vulnerability-disclosure", + "source": "threat-uncontactable-disclosure", + "target": "guidance-vulnerability-disclosure", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:threat-unlimited-token-approval:guidance-smart-contract-interaction", "source": "threat-unlimited-token-approval", @@ -5437,6 +6345,13 @@ export const securityMapGraph = { "type": "documented-by", "status": "proposed" }, + { + "id": "exposes:component-ai-agent:surface-agent-tool-path", + "source": "component-ai-agent", + "target": "surface-agent-tool-path", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-ci-cd:surface-ci-cd-secrets", "source": "component-ci-cd", @@ -5549,6 +6464,13 @@ export const securityMapGraph = { "type": "exposes", "status": "proposed" }, + { + "id": "exposes:component-frontend:surface-ens-resolution", + "source": "component-frontend", + "target": "surface-ens-resolution", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-frontend:surface-frontend-deployment", "source": "component-frontend", @@ -5598,6 +6520,13 @@ export const securityMapGraph = { "type": "exposes", "status": "proposed" }, + { + "id": "exposes:component-rpc-endpoints:surface-ens-resolution", + "source": "component-rpc-endpoints", + "target": "surface-ens-resolution", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-rpc-endpoints:surface-rpc-trust-boundary", "source": "component-rpc-endpoints", @@ -5647,6 +6576,13 @@ export const securityMapGraph = { "type": "exposes", "status": "proposed" }, + { + "id": "exposes:component-smart-contracts:surface-researcher-inbound", + "source": "component-smart-contracts", + "target": "surface-researcher-inbound", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-software-wallet:surface-token-approvals", "source": "component-software-wallet", @@ -5668,6 +6604,13 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-bug-bounty-program:threat-uncontactable-disclosure", + "source": "control-bug-bounty-program", + "target": "threat-uncontactable-disclosure", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-cloud-hardening:threat-infrastructure-compromise", "source": "control-cloud-hardening", @@ -5766,6 +6709,20 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-ensip15-normalization:threat-spoofed-ens-resolution", + "source": "control-ensip15-normalization", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-execution-path-enforcement:threat-prompt-injection", + "source": "control-execution-path-enforcement", + "target": "threat-prompt-injection", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-external-security-review:threat-smart-contract-exploits", "source": "control-external-security-review", @@ -5864,6 +6821,20 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-l1-ens-resolution:threat-misdirected-transfer", + "source": "control-l1-ens-resolution", + "target": "threat-misdirected-transfer", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-l1-ens-resolution:threat-spoofed-ens-resolution", + "source": "control-l1-ens-resolution", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-least-privilege-review:threat-dprk-it-worker-infiltration", "source": "control-least-privilege-review", @@ -5885,6 +6856,20 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-living-threat-model:threat-smart-contract-exploits", + "source": "control-living-threat-model", + "target": "threat-smart-contract-exploits", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-living-threat-model:threat-stale-threat-model", + "source": "control-living-threat-model", + "target": "threat-stale-threat-model", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-multi-channel-transfer-confirm:threat-misdirected-transfer", "source": "control-multi-channel-transfer-confirm", @@ -5927,6 +6912,20 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-peer-code-review:threat-smart-contract-exploits", + "source": "control-peer-code-review", + "target": "threat-smart-contract-exploits", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-peer-code-review:threat-supply-chain-compromise", + "source": "control-peer-code-review", + "target": "threat-supply-chain-compromise", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-phishing-resistant-mfa:threat-custody-access-abuse", "source": "control-phishing-resistant-mfa", @@ -5948,6 +6947,13 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-prompt-input-constraint:threat-prompt-injection", + "source": "control-prompt-input-constraint", + "target": "threat-prompt-injection", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-published-recovery-address:threat-whitehat-legal-freeze", "source": "control-published-recovery-address", @@ -5955,6 +6961,13 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-published-security-contact:threat-uncontactable-disclosure", + "source": "control-published-security-contact", + "target": "threat-uncontactable-disclosure", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-registrar-hardening:threat-frontend-dns-hijacking", "source": "control-registrar-hardening", @@ -6039,6 +7052,13 @@ export const securityMapGraph = { "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-simulate-before-sign:threat-spoofed-ens-resolution", + "source": "control-simulate-before-sign", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-test-transfer:threat-misdirected-transfer", "source": "control-test-transfer", @@ -6102,6 +7122,13 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-bug-bounty-program:asset-user-funds", + "source": "control-bug-bounty-program", + "target": "asset-user-funds", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-cloud-hardening:component-cloud-infrastructure", "source": "control-cloud-hardening", @@ -6186,6 +7213,20 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-ensip15-normalization:surface-ens-resolution", + "source": "control-ensip15-normalization", + "target": "surface-ens-resolution", + "type": "protects", + "status": "proposed" + }, + { + "id": "protects:control-execution-path-enforcement:surface-agent-tool-path", + "source": "control-execution-path-enforcement", + "target": "surface-agent-tool-path", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-external-security-review:component-smart-contracts", "source": "control-external-security-review", @@ -6291,6 +7332,20 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-l1-ens-resolution:asset-user-funds", + "source": "control-l1-ens-resolution", + "target": "asset-user-funds", + "type": "protects", + "status": "proposed" + }, + { + "id": "protects:control-l1-ens-resolution:surface-ens-resolution", + "source": "control-l1-ens-resolution", + "target": "surface-ens-resolution", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-limited-token-approvals:surface-token-approvals", "source": "control-limited-token-approvals", @@ -6298,6 +7353,13 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-living-threat-model:asset-source-code", + "source": "control-living-threat-model", + "target": "asset-source-code", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-multi-channel-transfer-confirm:surface-large-transfer", "source": "control-multi-channel-transfer-confirm", @@ -6326,6 +7388,13 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-peer-code-review:asset-source-code", + "source": "control-peer-code-review", + "target": "asset-source-code", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-phishing-resistant-mfa:component-identity-accounts", "source": "control-phishing-resistant-mfa", @@ -6340,6 +7409,13 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-prompt-input-constraint:component-ai-agent", + "source": "control-prompt-input-constraint", + "target": "component-ai-agent", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-published-recovery-address:asset-user-funds", "source": "control-published-recovery-address", @@ -6354,6 +7430,13 @@ export const securityMapGraph = { "type": "protects", "status": "proposed" }, + { + "id": "protects:control-published-security-contact:surface-researcher-inbound", + "source": "control-published-security-contact", + "target": "surface-researcher-inbound", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-registrar-hardening:asset-domain-control", "source": "control-registrar-hardening", @@ -6739,6 +7822,13 @@ export const securityMapGraph = { "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-misdirected-transfer:surface-ens-resolution", + "source": "threat-misdirected-transfer", + "target": "surface-ens-resolution", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-misdirected-transfer:surface-large-transfer", "source": "threat-misdirected-transfer", @@ -6858,6 +7948,27 @@ export const securityMapGraph = { "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-prompt-injection:asset-secrets-credentials", + "source": "threat-prompt-injection", + "target": "asset-secrets-credentials", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-prompt-injection:asset-user-funds", + "source": "threat-prompt-injection", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-prompt-injection:surface-agent-tool-path", + "source": "threat-prompt-injection", + "target": "surface-agent-tool-path", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-seed-phrase-compromise:asset-seed-secrets", "source": "threat-seed-phrase-compromise", @@ -6963,6 +8074,41 @@ export const securityMapGraph = { "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-spoofed-ens-resolution:asset-user-funds", + "source": "threat-spoofed-ens-resolution", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-spoofed-ens-resolution:surface-ens-resolution", + "source": "threat-spoofed-ens-resolution", + "target": "surface-ens-resolution", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-stale-threat-model:asset-source-code", + "source": "threat-stale-threat-model", + "target": "asset-source-code", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-stale-threat-model:asset-user-funds", + "source": "threat-stale-threat-model", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-stale-threat-model:surface-contract-upgrade-path", + "source": "threat-stale-threat-model", + "target": "surface-contract-upgrade-path", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-supply-chain-compromise:asset-deployment-authority", "source": "threat-supply-chain-compromise", @@ -6991,6 +8137,27 @@ export const securityMapGraph = { "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-uncontactable-disclosure:asset-source-code", + "source": "threat-uncontactable-disclosure", + "target": "asset-source-code", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-uncontactable-disclosure:asset-user-funds", + "source": "threat-uncontactable-disclosure", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-uncontactable-disclosure:surface-researcher-inbound", + "source": "threat-uncontactable-disclosure", + "target": "surface-researcher-inbound", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-unlimited-token-approval:asset-user-funds", "source": "threat-unlimited-token-approval", diff --git a/docs/data/security-map/README.md b/docs/data/security-map/README.md index b92e48b5..e58a39d9 100644 --- a/docs/data/security-map/README.md +++ b/docs/data/security-map/README.md @@ -121,10 +121,12 @@ The first seed is `proposed` on purpose. ## Follow-up 1. Run `pnpm run coverage:security-map` and treat the lists as the work queue. -2. Map one framework per PR (`feat/security-map-`). Steward review for security semantics. - Wallet Security, Physical Security (duress), Treasury Operations, DPRK IT Workers, Encryption, - Privacy, and Safe Harbor are seeded. Eligibility checklist and on-chain adoption walkthrough - stay unmapped. No Nomad incident node without a sourced evidence PR. +2. Map one framework per PR (`feat/security-map-`) unless the remaining empty list + is small enough to seed together. Steward review for security semantics. Current seed covers + Wallet, Physical (duress), Treasury, DPRK IT Workers, Encryption, Privacy, Safe Harbor, AI + Security, ENS, Guides, SSDLC, Threat Modeling, and Vulnerability Disclosure. Product-level + guide pages, AI browsers/exfil, ENS cross-chain, and sourced incidents stay unmapped. + diff --git a/docs/data/security-map/edges/ai-security.json b/docs/data/security-map/edges/ai-security.json new file mode 100644 index 00000000..e1b675db --- /dev/null +++ b/docs/data/security-map/edges/ai-security.json @@ -0,0 +1,69 @@ +{ + "edges": [ + { + "source": "component-ai-agent", + "target": "component-developer-devices", + "type": "depends-on" + }, + { + "source": "component-ai-agent", + "target": "surface-agent-tool-path", + "type": "exposes" + }, + { + "source": "threat-prompt-injection", + "target": "surface-agent-tool-path", + "type": "targets" + }, + { + "source": "threat-prompt-injection", + "target": "asset-secrets-credentials", + "type": "targets" + }, + { + "source": "threat-prompt-injection", + "target": "asset-user-funds", + "type": "targets" + }, + { + "source": "control-prompt-input-constraint", + "target": "threat-prompt-injection", + "type": "mitigates" + }, + { + "source": "control-execution-path-enforcement", + "target": "threat-prompt-injection", + "type": "mitigates" + }, + { + "source": "control-execution-path-enforcement", + "target": "surface-agent-tool-path", + "type": "protects" + }, + { + "source": "control-prompt-input-constraint", + "target": "component-ai-agent", + "type": "protects" + }, + { + "source": "control-prompt-input-constraint", + "target": "guidance-prompt-injection", + "type": "documented-by" + }, + { + "source": "control-execution-path-enforcement", + "target": "guidance-execution-path", + "type": "documented-by" + }, + { + "source": "threat-prompt-injection", + "target": "guidance-prompt-injection", + "type": "documented-by" + }, + { + "source": "component-ai-agent", + "target": "guidance-ai-security", + "type": "documented-by" + } + ] +} diff --git a/docs/data/security-map/edges/ens.json b/docs/data/security-map/edges/ens.json new file mode 100644 index 00000000..acc66e59 --- /dev/null +++ b/docs/data/security-map/edges/ens.json @@ -0,0 +1,89 @@ +{ + "edges": [ + { + "source": "component-frontend", + "target": "surface-ens-resolution", + "type": "exposes" + }, + { + "source": "component-rpc-endpoints", + "target": "surface-ens-resolution", + "type": "exposes" + }, + { + "source": "threat-spoofed-ens-resolution", + "target": "surface-ens-resolution", + "type": "targets" + }, + { + "source": "threat-spoofed-ens-resolution", + "target": "asset-user-funds", + "type": "targets" + }, + { + "source": "threat-misdirected-transfer", + "target": "surface-ens-resolution", + "type": "targets" + }, + { + "source": "control-l1-ens-resolution", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates" + }, + { + "source": "control-ensip15-normalization", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates" + }, + { + "source": "control-l1-ens-resolution", + "target": "threat-misdirected-transfer", + "type": "mitigates" + }, + { + "source": "control-simulate-before-sign", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates" + }, + { + "source": "control-l1-ens-resolution", + "target": "surface-ens-resolution", + "type": "protects" + }, + { + "source": "control-ensip15-normalization", + "target": "surface-ens-resolution", + "type": "protects" + }, + { + "source": "control-l1-ens-resolution", + "target": "asset-user-funds", + "type": "protects" + }, + { + "source": "control-l1-ens-resolution", + "target": "guidance-ens-integrity", + "type": "documented-by" + }, + { + "source": "control-ensip15-normalization", + "target": "guidance-ens-normalization", + "type": "documented-by" + }, + { + "source": "threat-spoofed-ens-resolution", + "target": "guidance-ens-integrity", + "type": "documented-by" + }, + { + "source": "component-frontend", + "target": "guidance-ens", + "type": "documented-by" + }, + { + "source": "control-simulate-before-sign", + "target": "guidance-ens-integrity", + "type": "documented-by" + } + ] +} diff --git a/docs/data/security-map/edges/guides.json b/docs/data/security-map/edges/guides.json new file mode 100644 index 00000000..9e0278a6 --- /dev/null +++ b/docs/data/security-map/edges/guides.json @@ -0,0 +1,29 @@ +{ + "edges": [ + { + "source": "control-phishing-resistant-mfa", + "target": "guidance-hardware-security-keys", + "type": "documented-by" + }, + { + "source": "control-phishing-resistant-mfa", + "target": "guidance-account-management", + "type": "documented-by" + }, + { + "source": "component-identity-accounts", + "target": "guidance-guides", + "type": "documented-by" + }, + { + "source": "component-identity-accounts", + "target": "guidance-account-management", + "type": "documented-by" + }, + { + "source": "component-community-channels", + "target": "guidance-account-management", + "type": "documented-by" + } + ] +} diff --git a/docs/data/security-map/edges/ssdlc.json b/docs/data/security-map/edges/ssdlc.json new file mode 100644 index 00000000..b36b25f5 --- /dev/null +++ b/docs/data/security-map/edges/ssdlc.json @@ -0,0 +1,49 @@ +{ + "edges": [ + { + "source": "control-peer-code-review", + "target": "threat-supply-chain-compromise", + "type": "mitigates" + }, + { + "source": "control-peer-code-review", + "target": "threat-smart-contract-exploits", + "type": "mitigates" + }, + { + "source": "control-peer-code-review", + "target": "asset-source-code", + "type": "protects" + }, + { + "source": "control-peer-code-review", + "target": "guidance-code-reviews", + "type": "documented-by" + }, + { + "source": "control-branch-protection", + "target": "guidance-secure-repos", + "type": "documented-by" + }, + { + "source": "control-secure-sdlc-testing", + "target": "guidance-ssdlc", + "type": "documented-by" + }, + { + "source": "control-secure-sdlc-testing", + "target": "guidance-secure-coding", + "type": "documented-by" + }, + { + "source": "control-external-security-review", + "target": "guidance-ssdlc", + "type": "documented-by" + }, + { + "source": "component-ci-cd", + "target": "guidance-secure-repos", + "type": "documented-by" + } + ] +} diff --git a/docs/data/security-map/edges/threat-modeling.json b/docs/data/security-map/edges/threat-modeling.json new file mode 100644 index 00000000..85ea8396 --- /dev/null +++ b/docs/data/security-map/edges/threat-modeling.json @@ -0,0 +1,59 @@ +{ + "edges": [ + { + "source": "threat-stale-threat-model", + "target": "surface-contract-upgrade-path", + "type": "targets" + }, + { + "source": "threat-stale-threat-model", + "target": "asset-source-code", + "type": "targets" + }, + { + "source": "threat-stale-threat-model", + "target": "asset-user-funds", + "type": "targets" + }, + { + "source": "control-living-threat-model", + "target": "threat-stale-threat-model", + "type": "mitigates" + }, + { + "source": "control-living-threat-model", + "target": "threat-smart-contract-exploits", + "type": "mitigates" + }, + { + "source": "control-living-threat-model", + "target": "asset-source-code", + "type": "protects" + }, + { + "source": "control-living-threat-model", + "target": "guidance-threat-modeling", + "type": "documented-by" + }, + { + "source": "control-living-threat-model", + "target": "guidance-create-maintain-threat-models", + "type": "documented-by" + }, + { + "source": "control-living-threat-model", + "target": "guidance-identify-mitigate-threats", + "type": "documented-by" + }, + { + "source": "control-living-threat-model", + "target": "guidance-ssdlc-threat-design", + "type": "documented-by" + }, + { + "source": "threat-stale-threat-model", + "target": "guidance-create-maintain-threat-models", + "type": "documented-by" + } + ] +} diff --git a/docs/data/security-map/edges/vulnerability-disclosure.json b/docs/data/security-map/edges/vulnerability-disclosure.json new file mode 100644 index 00000000..4ea3a1f2 --- /dev/null +++ b/docs/data/security-map/edges/vulnerability-disclosure.json @@ -0,0 +1,74 @@ +{ + "edges": [ + { + "source": "component-smart-contracts", + "target": "surface-researcher-inbound", + "type": "exposes" + }, + { + "source": "threat-uncontactable-disclosure", + "target": "surface-researcher-inbound", + "type": "targets" + }, + { + "source": "threat-uncontactable-disclosure", + "target": "asset-source-code", + "type": "targets" + }, + { + "source": "threat-uncontactable-disclosure", + "target": "asset-user-funds", + "type": "targets" + }, + { + "source": "control-published-security-contact", + "target": "threat-uncontactable-disclosure", + "type": "mitigates" + }, + { + "source": "control-bug-bounty-program", + "target": "threat-uncontactable-disclosure", + "type": "mitigates" + }, + { + "source": "control-published-security-contact", + "target": "surface-researcher-inbound", + "type": "protects" + }, + { + "source": "control-bug-bounty-program", + "target": "asset-user-funds", + "type": "protects" + }, + { + "source": "control-published-security-contact", + "target": "guidance-security-contact", + "type": "documented-by" + }, + { + "source": "control-bug-bounty-program", + "target": "guidance-bug-bounties", + "type": "documented-by" + }, + { + "source": "threat-uncontactable-disclosure", + "target": "guidance-vulnerability-disclosure", + "type": "documented-by" + }, + { + "source": "control-safe-harbor-adoption", + "target": "guidance-vulnerability-disclosure", + "type": "documented-by" + }, + { + "source": "control-published-security-contact", + "target": "guidance-safe-harbor-scope", + "type": "documented-by" + }, + { + "source": "control-external-security-review", + "target": "guidance-bug-bounties", + "type": "documented-by" + } + ] +} diff --git a/docs/data/security-map/nodes/ai-security.json b/docs/data/security-map/nodes/ai-security.json new file mode 100644 index 00000000..e1013062 --- /dev/null +++ b/docs/data/security-map/nodes/ai-security.json @@ -0,0 +1,101 @@ +{ + "nodes": [ + { + "id": "component-ai-agent", + "type": "component", + "title": "AI agent", + "summary": "A model that reads untrusted text and can call tools, write files, or construct transactions. Prompt templates do not bound what it does next.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["ai", "agent", "llm"], + "roles": ["engineer-developer"], + "lifecycle": ["development", "normal-operations"], + "framework": "ai-security" + }, + { + "id": "surface-agent-tool-path", + "type": "attack-surface", + "title": "Agent tool path", + "summary": "The moment an agent is about to call a tool, write a file, or build a transaction. After-the-fact monitoring is too late if the action is irreversible.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["ai", "tools", "runtime"], + "roles": ["engineer-developer"], + "lifecycle": ["development", "normal-operations"], + "framework": "ai-security" + }, + { + "id": "threat-prompt-injection", + "type": "threat", + "title": "Prompt injection", + "summary": "Untrusted text, including on-chain data or retrieved documents, is treated as instructions. The agent then leaks secrets or takes an action the operator did not intend.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["ai", "prompt-injection"], + "severity": "high", + "severityBasis": "Default triage is high because injection rides the model's instruction-following. Blast radius is whatever the agent can sign, send, or read. Prompt templates are not a control.", + "framework": "ai-security" + }, + { + "id": "control-prompt-input-constraint", + "type": "control", + "title": "Prompt input constraint", + "summary": "Classify and constrain model inputs at the execution boundary. Do not rely on boilerplate system prompts. Treat on-chain data and retrieved documents as untrusted.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["ai", "prompt-injection"], + "controlClass": "preventive", + "assessmentEligible": true, + "roles": ["engineer-developer"], + "lifecycle": ["design", "development"], + "framework": "ai-security" + }, + { + "id": "control-execution-path-enforcement", + "type": "control", + "title": "Execution-path enforcement", + "summary": "Allow, warn, or block where the agent is about to act. Monitoring after the fact is too late for irreversible tool calls and transactions.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["ai", "runtime", "allowlist"], + "controlClass": "preventive", + "assessmentEligible": true, + "roles": ["engineer-developer"], + "lifecycle": ["design", "normal-operations"], + "framework": "ai-security" + }, + { + "id": "guidance-ai-security", + "type": "guidance", + "title": "AI Security", + "summary": "Agentic AI turns instruction-following into irreversible actions. Prefer runtime execution-path controls and isolation over prompt templates alone.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["ai"], + "href": "/ai-security/overview", + "framework": "ai-security" + }, + { + "id": "guidance-prompt-injection", + "type": "guidance", + "title": "Prompt injection defenses", + "summary": "Prompt injection succeeds because models treat text as instructions. Constrain and classify inputs at the execution boundary.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["ai", "prompt-injection"], + "href": "/ai-security/prompt-injection-defenses", + "framework": "ai-security" + }, + { + "id": "guidance-execution-path", + "type": "guidance", + "title": "Execution-path enforcement", + "summary": "Enforce allow, warn, or block where the agent is about to act. Monitoring after the fact is too late for irreversible actions.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["ai", "runtime"], + "href": "/ai-security/execution-path-enforcement", + "framework": "ai-security" + } + ] +} diff --git a/docs/data/security-map/nodes/ens.json b/docs/data/security-map/nodes/ens.json new file mode 100644 index 00000000..1f3ac98c --- /dev/null +++ b/docs/data/security-map/nodes/ens.json @@ -0,0 +1,89 @@ +{ + "nodes": [ + { + "id": "surface-ens-resolution", + "type": "attack-surface", + "title": "ENS name resolution", + "summary": "Turning a human-readable name into an address before a send. Stale indexers, skipped reverse checks, and confusable scripts all produce a valid-looking wrong destination.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens", "resolution"], + "roles": ["engineer-developer"], + "lifecycle": ["normal-operations"], + "framework": "ens" + }, + { + "id": "threat-spoofed-ens-resolution", + "type": "threat", + "title": "Spoofed ENS resolution", + "summary": "The UI shows a trusted name while the resolved address is attacker-controlled, from a stale indexer, a reverse record that does not loop, or a homograph.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens", "homograph", "spoofing"], + "severity": "high", + "severityBasis": "Default triage is high because the send is valid and irreversible. The bug is in resolution, not in the signature.", + "framework": "ens" + }, + { + "id": "control-l1-ens-resolution", + "type": "control", + "title": "L1-backed ENS resolution", + "summary": "For fund movement, resolve from Ethereum L1, not a stale indexer. Verify reverse records with a matching forward lookup before the send.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens", "l1", "reverse-record"], + "controlClass": "preventive", + "assessmentEligible": true, + "roles": ["engineer-developer"], + "lifecycle": ["design", "normal-operations"], + "framework": "ens" + }, + { + "id": "control-ensip15-normalization", + "type": "control", + "title": "ENSIP-15 name normalization", + "summary": "Normalize names with ENSIP-15 before any namehash, and warn on confusable scripts. Homographs survive if the UI skips this.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens", "normalization", "homograph"], + "controlClass": "preventive", + "assessmentEligible": true, + "roles": ["engineer-developer"], + "lifecycle": ["design", "development"], + "framework": "ens" + }, + { + "id": "guidance-ens", + "type": "guidance", + "title": "ENS best practices", + "summary": "Secure ENS use means fresh L1-backed resolution for funds moves, correct name normalization, and verified bidirectional records.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens"], + "href": "/ens/overview", + "framework": "ens" + }, + { + "id": "guidance-ens-integrity", + "type": "guidance", + "title": "ENS data integrity", + "summary": "For fund movement, resolve from Ethereum L1 and always verify reverse records with a matching forward lookup.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens", "integrity"], + "href": "/ens/data-integrity-verification", + "framework": "ens" + }, + { + "id": "guidance-ens-normalization", + "type": "guidance", + "title": "ENS name handling", + "summary": "Normalize with ENSIP-15 before any namehash, and warn on confusable scripts that enable homograph phishing.", + "domains": ["onchain-systems"], + "status": "proposed", + "tags": ["ens", "normalization"], + "href": "/ens/name-handling-normalization", + "framework": "ens" + } + ] +} diff --git a/docs/data/security-map/nodes/guides.json b/docs/data/security-map/nodes/guides.json new file mode 100644 index 00000000..0ad4042d --- /dev/null +++ b/docs/data/security-map/nodes/guides.json @@ -0,0 +1,37 @@ +{ + "nodes": [ + { + "id": "guidance-guides", + "type": "guidance", + "title": "Guides", + "summary": "Product-specific checklists for account management and endpoint controls. Follow the steps for each tool, then review settings when vendors change defaults.", + "domains": ["devices-identity", "community-communications"], + "status": "proposed", + "tags": ["guides", "checklists"], + "href": "/guides/overview", + "framework": "guides" + }, + { + "id": "guidance-account-management", + "type": "guidance", + "title": "Account management guides", + "summary": "High-value SaaS and community accounts need strong MFA, session hygiene, least privilege, and admin separation.", + "domains": ["devices-identity", "community-communications"], + "status": "proposed", + "tags": ["accounts", "mfa"], + "href": "/guides/account-management/overview", + "framework": "guides" + }, + { + "id": "guidance-hardware-security-keys", + "type": "guidance", + "title": "Hardware security keys", + "summary": "Use FIDO2/WebAuthn keys on high-value accounts, register at least two keys, disable SMS fallback where possible, and test recovery before you need it.", + "domains": ["devices-identity"], + "status": "proposed", + "tags": ["fido2", "webauthn", "mfa"], + "href": "/guides/endpoint-security/hardware-security-keys", + "framework": "guides" + } + ] +} diff --git a/docs/data/security-map/nodes/ssdlc.json b/docs/data/security-map/nodes/ssdlc.json new file mode 100644 index 00000000..eba97177 --- /dev/null +++ b/docs/data/security-map/nodes/ssdlc.json @@ -0,0 +1,73 @@ +{ + "nodes": [ + { + "id": "control-peer-code-review", + "type": "control", + "title": "Peer code review", + "summary": "Required human review of production changes, with a checklist that covers authz, input handling, and irreversible Web3 paths. Branch rules without actual review are theater.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["review", "sdlc"], + "controlClass": "preventive", + "assessmentEligible": true, + "roles": ["engineer-developer"], + "lifecycle": ["development"], + "framework": "secure-software-development" + }, + { + "id": "guidance-ssdlc", + "type": "guidance", + "title": "Secure software development", + "summary": "Security in the SDLC is continuous: design, code, review, and repository controls. It is not a final gate before ship.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["sdlc"], + "href": "/secure-software-development/overview", + "framework": "secure-software-development" + }, + { + "id": "guidance-secure-coding", + "type": "guidance", + "title": "Secure coding standards", + "summary": "Input validation, encoding, authz checks, error handling, least privilege in code, and secure data handling.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["coding", "standards"], + "href": "/secure-software-development/secure-coding-standards-guidelines", + "framework": "secure-software-development" + }, + { + "id": "guidance-code-reviews", + "type": "guidance", + "title": "Code reviews and peer audits", + "summary": "Review cadence, checklists, automation assist, and a culture that treats unreviewed production merges as a defect.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["review"], + "href": "/secure-software-development/code-reviews-peer-audits", + "framework": "secure-software-development" + }, + { + "id": "guidance-secure-repos", + "type": "guidance", + "title": "Secure code repositories", + "summary": "Repository compromise is supply-chain compromise. Enforce least privilege, strong authentication, protected branches, and review-required merges.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["github", "branch-protection"], + "href": "/secure-software-development/secure-code-repositories-version-control", + "framework": "secure-software-development" + }, + { + "id": "guidance-ssdlc-threat-design", + "type": "guidance", + "title": "Threat modeling and secure design", + "summary": "Threat modeling before build chooses which controls matter. Secure design principles keep residual risk from depending on a single check.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["threat-model", "design"], + "href": "/secure-software-development/threat-modeling-secure-design-principles", + "framework": "secure-software-development" + } + ] +} diff --git a/docs/data/security-map/nodes/threat-modeling.json b/docs/data/security-map/nodes/threat-modeling.json new file mode 100644 index 00000000..2a6ff530 --- /dev/null +++ b/docs/data/security-map/nodes/threat-modeling.json @@ -0,0 +1,63 @@ +{ + "nodes": [ + { + "id": "threat-stale-threat-model", + "type": "threat", + "title": "Stale threat model", + "summary": "Architecture or value at risk changed and the model did not. New trust boundaries, admin paths, or bridges ship without named abuses or owners.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["threat-model", "design"], + "severity": "high", + "severityBasis": "Default triage is high because Web3 design misses become irreversible production loss. The failure is skipped analysis, not a missing scanner.", + "framework": "threat-modeling" + }, + { + "id": "control-living-threat-model", + "type": "control", + "title": "Living threat model", + "summary": "Name assets, threats, and mitigations before build, then update the model when architecture or value at risk changes. A one-time workshop is not this control.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["threat-model", "stride"], + "controlClass": "preventive", + "assessmentEligible": true, + "roles": ["engineer-developer", "security-engineer"], + "lifecycle": ["design", "development", "upgrade"], + "framework": "threat-modeling" + }, + { + "id": "guidance-threat-modeling", + "type": "guidance", + "title": "Threat modeling", + "summary": "A structured way to decide which abuses matter before they happen. Name assets, threats, and mitigations, then keep the model current as the system changes.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["threat-model"], + "href": "/threat-modeling/overview", + "framework": "threat-modeling" + }, + { + "id": "guidance-create-maintain-threat-models", + "type": "guidance", + "title": "Create and maintain threat models", + "summary": "A useful threat model is a maintained artifact. Redefine scope and mitigations when architecture or value at risk changes.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["threat-model", "maintenance"], + "href": "/threat-modeling/create-maintain-threat-models", + "framework": "threat-modeling" + }, + { + "id": "guidance-identify-mitigate-threats", + "type": "guidance", + "title": "Identify and mitigate threats", + "summary": "STRIDE-oriented enumeration, attack surface analysis, and mitigation patterns for the system under review.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["stride", "mitigation"], + "href": "/threat-modeling/identity-mitigate-threats", + "framework": "threat-modeling" + } + ] +} diff --git a/docs/data/security-map/nodes/vulnerability-disclosure.json b/docs/data/security-map/nodes/vulnerability-disclosure.json new file mode 100644 index 00000000..f207fc94 --- /dev/null +++ b/docs/data/security-map/nodes/vulnerability-disclosure.json @@ -0,0 +1,89 @@ +{ + "nodes": [ + { + "id": "surface-researcher-inbound", + "type": "attack-surface", + "title": "Researcher inbound path", + "summary": "How an external researcher reaches the team with a vulnerability. Public issues, social DMs, or a dead mailbox all leak the finding before a fix exists.", + "domains": ["development-supply-chain", "detection-incident-response"], + "status": "proposed", + "tags": ["disclosure", "contact"], + "roles": ["security-engineer", "engineer-developer"], + "lifecycle": ["normal-operations"], + "framework": "vulnerability-disclosure" + }, + { + "id": "threat-uncontactable-disclosure", + "type": "threat", + "title": "Uncontactable disclosure", + "summary": "A researcher finds a bug and cannot reach a monitored security contact. The report goes public, gets sold, or sits unread while the bug stays live.", + "domains": ["development-supply-chain", "detection-incident-response"], + "status": "proposed", + "tags": ["disclosure", "contact"], + "severity": "high", + "severityBasis": "Default triage is high because inbound silence turns a fixable finding into an uncoordinated release. A bounty platform does not replace a monitored contact.", + "framework": "vulnerability-disclosure" + }, + { + "id": "control-published-security-contact", + "type": "control", + "title": "Published security contact", + "summary": "SECURITY.md, a monitored security mailbox, and .well-known/security.txt. Someone skilled acknowledges reports quickly and keeps them confidential until a fix ships.", + "domains": ["development-supply-chain", "detection-incident-response"], + "status": "proposed", + "tags": ["security.txt", "contact"], + "controlClass": "detective", + "assessmentEligible": true, + "roles": ["security-engineer"], + "lifecycle": ["normal-operations"], + "framework": "vulnerability-disclosure" + }, + { + "id": "control-bug-bounty-program", + "type": "control", + "title": "Bug bounty program", + "summary": "Pay independent researchers under clear scope, rewards, and triage capacity. Pair it with a durable security contact. This is not Safe Harbor for live exploits.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["bounty", "disclosure"], + "controlClass": "detective", + "assessmentEligible": true, + "roles": ["security-engineer"], + "lifecycle": ["normal-operations"], + "framework": "vulnerability-disclosure" + }, + { + "id": "guidance-vulnerability-disclosure", + "type": "guidance", + "title": "Vulnerability disclosure", + "summary": "Make fixed issues public on a deliberate timeline. Before that, teams need inbound reporting paths, triage, and a plan when quiet disclosure is no longer safe.", + "domains": ["development-supply-chain", "detection-incident-response"], + "status": "proposed", + "tags": ["disclosure"], + "href": "/vulnerability-disclosure/overview", + "framework": "vulnerability-disclosure" + }, + { + "id": "guidance-security-contact", + "type": "guidance", + "title": "Security contact", + "summary": "A security contact is useless unless someone skilled monitors it, acknowledges reports quickly, and keeps findings confidential until fixes ship.", + "domains": ["development-supply-chain"], + "status": "proposed", + "tags": ["contact", "security.txt"], + "href": "/vulnerability-disclosure/security-contact", + "framework": "vulnerability-disclosure" + }, + { + "id": "guidance-bug-bounties", + "type": "guidance", + "title": "Bug bounties", + "summary": "Bug bounties work when scope, rewards, and triage capacity match the asset risk, and researchers can report under explicit safe harbor and disclosure rules.", + "domains": ["development-supply-chain", "onchain-systems"], + "status": "proposed", + "tags": ["bounty"], + "href": "/vulnerability-disclosure/bug-bounties", + "framework": "vulnerability-disclosure" + } + ] +} diff --git a/public/security-map.json b/public/security-map.json index 510d0b0f..26eb99f1 100644 --- a/public/security-map.json +++ b/public/security-map.json @@ -270,6 +270,30 @@ "normal-operations" ] }, + { + "id": "component-ai-agent", + "type": "component", + "title": "AI agent", + "summary": "A model that reads untrusted text and can call tools, write files, or construct transactions. Prompt templates do not bound what it does next.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "agent", + "llm" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "development", + "normal-operations" + ], + "framework": "ai-security" + }, { "id": "component-ci-cd", "type": "component", @@ -756,6 +780,30 @@ "assessmentEligible": true, "framework": "devsecops" }, + { + "id": "control-bug-bounty-program", + "type": "control", + "title": "Bug bounty program", + "summary": "Pay independent researchers under clear scope, rewards, and triage capacity. Pair it with a durable security contact. This is not Safe Harbor for live exploits.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "bounty", + "disclosure" + ], + "roles": [ + "security-engineer" + ], + "lifecycle": [ + "normal-operations" + ], + "controlClass": "detective", + "assessmentEligible": true, + "framework": "vulnerability-disclosure" + }, { "id": "control-cloud-hardening", "type": "control", @@ -1078,6 +1126,57 @@ "assessmentEligible": true, "framework": "multisig-for-protocols" }, + { + "id": "control-ensip15-normalization", + "type": "control", + "title": "ENSIP-15 name normalization", + "summary": "Normalize names with ENSIP-15 before any namehash, and warn on confusable scripts. Homographs survive if the UI skips this.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "normalization", + "homograph" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "development" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ens" + }, + { + "id": "control-execution-path-enforcement", + "type": "control", + "title": "Execution-path enforcement", + "summary": "Allow, warn, or block where the agent is about to act. Monitoring after the fact is too late for irreversible tool calls and transactions.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "runtime", + "allowlist" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "normal-operations" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ai-security" + }, { "id": "control-external-security-review", "type": "control", @@ -1327,6 +1426,31 @@ "assessmentEligible": true, "framework": "devsecops" }, + { + "id": "control-l1-ens-resolution", + "type": "control", + "title": "L1-backed ENS resolution", + "summary": "For fund movement, resolve from Ethereum L1, not a stale indexer. Verify reverse records with a matching forward lookup before the send.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "l1", + "reverse-record" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "normal-operations" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ens" + }, { "id": "control-least-privilege-review", "type": "control", @@ -1376,6 +1500,33 @@ "assessmentEligible": true, "framework": "wallet-security" }, + { + "id": "control-living-threat-model", + "type": "control", + "title": "Living threat model", + "summary": "Name assets, threats, and mitigations before build, then update the model when architecture or value at risk changes. A one-time workshop is not this control.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "threat-model", + "stride" + ], + "roles": [ + "engineer-developer", + "security-engineer" + ], + "lifecycle": [ + "design", + "development", + "upgrade" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "threat-modeling" + }, { "id": "control-multi-channel-transfer-confirm", "type": "control", @@ -1500,6 +1651,29 @@ "assessmentEligible": true, "framework": "monitoring" }, + { + "id": "control-peer-code-review", + "type": "control", + "title": "Peer code review", + "summary": "Required human review of production changes, with a checklist that covers authz, input handling, and irreversible Web3 paths. Branch rules without actual review are theater.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "review", + "sdlc" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "development" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "secure-software-development" + }, { "id": "control-phishing-resistant-mfa", "type": "control", @@ -1527,6 +1701,30 @@ "assessmentEligible": true, "framework": "iam" }, + { + "id": "control-prompt-input-constraint", + "type": "control", + "title": "Prompt input constraint", + "summary": "Classify and constrain model inputs at the execution boundary. Do not rely on boilerplate system prompts. Treat on-chain data and retrieved documents as untrusted.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "ai", + "prompt-injection" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "design", + "development" + ], + "controlClass": "preventive", + "assessmentEligible": true, + "framework": "ai-security" + }, { "id": "control-published-recovery-address", "type": "control", @@ -1554,6 +1752,30 @@ "assessmentEligible": true, "framework": "safe-harbor" }, + { + "id": "control-published-security-contact", + "type": "control", + "title": "Published security contact", + "summary": "SECURITY.md, a monitored security mailbox, and .well-known/security.txt. Someone skilled acknowledges reports quickly and keeps them confidential until a fix ships.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "security.txt", + "contact" + ], + "roles": [ + "security-engineer" + ], + "lifecycle": [ + "normal-operations" + ], + "controlClass": "detective", + "assessmentEligible": true, + "framework": "vulnerability-disclosure" + }, { "id": "control-registrar-hardening", "type": "control", @@ -1916,6 +2138,39 @@ "assessmentEligible": true, "framework": "treasury-operations" }, + { + "id": "guidance-account-management", + "type": "guidance", + "title": "Account management guides", + "summary": "High-value SaaS and community accounts need strong MFA, session hygiene, least privilege, and admin separation.", + "domains": [ + "devices-identity", + "community-communications" + ], + "status": "proposed", + "tags": [ + "accounts", + "mfa" + ], + "href": "/guides/account-management/overview", + "framework": "guides" + }, + { + "id": "guidance-ai-security", + "type": "guidance", + "title": "AI Security", + "summary": "Agentic AI turns instruction-following into irreversible actions. Prefer runtime execution-path controls and isolation over prompt templates alone.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai" + ], + "href": "/ai-security/overview", + "framework": "ai-security" + }, { "id": "guidance-awareness", "type": "guidance", @@ -1931,6 +2186,22 @@ "href": "/awareness/overview", "framework": "awareness" }, + { + "id": "guidance-bug-bounties", + "type": "guidance", + "title": "Bug bounties", + "summary": "Bug bounties work when scope, rewards, and triage capacity match the asset risk, and researchers can report under explicit safe harbor and disclosure rules.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "bounty" + ], + "href": "/vulnerability-disclosure/bug-bounties", + "framework": "vulnerability-disclosure" + }, { "id": "guidance-cicd", "type": "guidance", @@ -1978,6 +2249,21 @@ "href": "/encryption/cloud-data-encryption", "framework": "encryption" }, + { + "id": "guidance-code-reviews", + "type": "guidance", + "title": "Code reviews and peer audits", + "summary": "Review cadence, checklists, automation assist, and a culture that treats unreviewed production merges as a defect.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "review" + ], + "href": "/secure-software-development/code-reviews-peer-audits", + "framework": "secure-software-development" + }, { "id": "guidance-code-signing", "type": "guidance", @@ -2055,6 +2341,22 @@ "href": "/governance/council-best-practices", "framework": "governance" }, + { + "id": "guidance-create-maintain-threat-models", + "type": "guidance", + "title": "Create and maintain threat models", + "summary": "A useful threat model is a maintained artifact. Redefine scope and mitigations when architecture or value at risk changes.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "threat-model", + "maintenance" + ], + "href": "/threat-modeling/create-maintain-threat-models", + "framework": "threat-modeling" + }, { "id": "guidance-dependency-runbook", "type": "guidance", @@ -2403,6 +2705,70 @@ "href": "/encryption/encryption-in-transit", "framework": "encryption" }, + { + "id": "guidance-ens", + "type": "guidance", + "title": "ENS best practices", + "summary": "Secure ENS use means fresh L1-backed resolution for funds moves, correct name normalization, and verified bidirectional records.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens" + ], + "href": "/ens/overview", + "framework": "ens" + }, + { + "id": "guidance-ens-integrity", + "type": "guidance", + "title": "ENS data integrity", + "summary": "For fund movement, resolve from Ethereum L1 and always verify reverse records with a matching forward lookup.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "integrity" + ], + "href": "/ens/data-integrity-verification", + "framework": "ens" + }, + { + "id": "guidance-ens-normalization", + "type": "guidance", + "title": "ENS name handling", + "summary": "Normalize with ENSIP-15 before any namehash, and warn on confusable scripts that enable homograph phishing.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "normalization" + ], + "href": "/ens/name-handling-normalization", + "framework": "ens" + }, + { + "id": "guidance-execution-path", + "type": "guidance", + "title": "Execution-path enforcement", + "summary": "Enforce allow, warn, or block where the agent is about to act. Monitoring after the fact is too late for irreversible actions.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "runtime" + ], + "href": "/ai-security/execution-path-enforcement", + "framework": "ai-security" + }, { "id": "guidance-exploit-runbook", "type": "guidance", @@ -2482,13 +2848,30 @@ "framework": "governance" }, { - "id": "guidance-hardware-encryption", + "id": "guidance-guides", "type": "guidance", - "title": "Hardware encryption", - "summary": "TPM, self-encrypting drives, and HSMs keep encryption keys out of host memory when they are deployed and managed correctly.", + "title": "Guides", + "summary": "Product-specific checklists for account management and endpoint controls. Follow the steps for each tool, then review settings when vendors change defaults.", "domains": [ "devices-identity", - "infrastructure" + "community-communications" + ], + "status": "proposed", + "tags": [ + "guides", + "checklists" + ], + "href": "/guides/overview", + "framework": "guides" + }, + { + "id": "guidance-hardware-encryption", + "type": "guidance", + "title": "Hardware encryption", + "summary": "TPM, self-encrypting drives, and HSMs keep encryption keys out of host memory when they are deployed and managed correctly.", + "domains": [ + "devices-identity", + "infrastructure" ], "status": "proposed", "tags": [ @@ -2498,6 +2881,23 @@ "href": "/encryption/hardware-encryption", "framework": "encryption" }, + { + "id": "guidance-hardware-security-keys", + "type": "guidance", + "title": "Hardware security keys", + "summary": "Use FIDO2/WebAuthn keys on high-value accounts, register at least two keys, disable SMS fallback where possible, and test recovery before you need it.", + "domains": [ + "devices-identity" + ], + "status": "proposed", + "tags": [ + "fido2", + "webauthn", + "mfa" + ], + "href": "/guides/endpoint-security/hardware-security-keys", + "framework": "guides" + }, { "id": "guidance-iam", "type": "guidance", @@ -2513,6 +2913,23 @@ "href": "/iam/overview", "framework": "iam" }, + { + "id": "guidance-identify-mitigate-threats", + "type": "guidance", + "title": "Identify and mitigate threats", + "summary": "STRIDE-oriented enumeration, attack surface analysis, and mitigation patterns for the system under review.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "stride", + "mitigation" + ], + "href": "/threat-modeling/identity-mitigate-threats", + "framework": "threat-modeling" + }, { "id": "guidance-incident-playbooks", "type": "guidance", @@ -2782,6 +3199,22 @@ "href": "/privacy/overview", "framework": "privacy" }, + { + "id": "guidance-prompt-injection", + "type": "guidance", + "title": "Prompt injection defenses", + "summary": "Prompt injection succeeds because models treat text as instructions. Constrain and classify inputs at the execution boundary.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "ai", + "prompt-injection" + ], + "href": "/ai-security/prompt-injection-defenses", + "framework": "ai-security" + }, { "id": "guidance-public-networks", "type": "guidance", @@ -2884,6 +3317,54 @@ "href": "/privacy/secure-browsing", "framework": "privacy" }, + { + "id": "guidance-secure-coding", + "type": "guidance", + "title": "Secure coding standards", + "summary": "Input validation, encoding, authz checks, error handling, least privilege in code, and secure data handling.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "coding", + "standards" + ], + "href": "/secure-software-development/secure-coding-standards-guidelines", + "framework": "secure-software-development" + }, + { + "id": "guidance-secure-repos", + "type": "guidance", + "title": "Secure code repositories", + "summary": "Repository compromise is supply-chain compromise. Enforce least privilege, strong authentication, protected branches, and review-required merges.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "github", + "branch-protection" + ], + "href": "/secure-software-development/secure-code-repositories-version-control", + "framework": "secure-software-development" + }, + { + "id": "guidance-security-contact", + "type": "guidance", + "title": "Security contact", + "summary": "A security contact is useless unless someone skilled monitors it, acknowledges reports quickly, and keeps findings confidential until fixes ship.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "contact", + "security.txt" + ], + "href": "/vulnerability-disclosure/security-contact", + "framework": "vulnerability-disclosure" + }, { "id": "guidance-security-culture", "type": "guidance", @@ -2980,6 +3461,37 @@ "href": "/wallet-security/smart-contract-interaction-security", "framework": "wallet-security" }, + { + "id": "guidance-ssdlc", + "type": "guidance", + "title": "Secure software development", + "summary": "Security in the SDLC is continuous: design, code, review, and repository controls. It is not a final gate before ship.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "sdlc" + ], + "href": "/secure-software-development/overview", + "framework": "secure-software-development" + }, + { + "id": "guidance-ssdlc-threat-design", + "type": "guidance", + "title": "Threat modeling and secure design", + "summary": "Threat modeling before build chooses which controls matter. Secure design principles keep residual risk from depending on a single check.", + "domains": [ + "development-supply-chain" + ], + "status": "proposed", + "tags": [ + "threat-model", + "design" + ], + "href": "/secure-software-development/threat-modeling-secure-design-principles", + "framework": "secure-software-development" + }, { "id": "guidance-supply-chain-overview", "type": "guidance", @@ -3029,6 +3541,22 @@ "href": "/security-automation/threat-detection-response", "framework": "security-automation" }, + { + "id": "guidance-threat-modeling", + "type": "guidance", + "title": "Threat modeling", + "summary": "A structured way to decide which abuses matter before they happen. Name assets, threats, and mitigations, then keep the model current as the system changes.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "threat-model" + ], + "href": "/threat-modeling/overview", + "framework": "threat-modeling" + }, { "id": "guidance-threat-vectors", "type": "guidance", @@ -3153,6 +3681,22 @@ "href": "/privacy/vpns/overview", "framework": "privacy" }, + { + "id": "guidance-vulnerability-disclosure", + "type": "guidance", + "title": "Vulnerability disclosure", + "summary": "Make fixed issues public on a deliberate timeline. Before that, teams need inbound reporting paths, triage, and a plan when quiet disclosure is no longer safe.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "disclosure" + ], + "href": "/vulnerability-disclosure/overview", + "framework": "vulnerability-disclosure" + }, { "id": "guidance-wallet-security", "type": "guidance", @@ -3367,6 +3911,30 @@ ], "framework": "safe-harbor" }, + { + "id": "surface-agent-tool-path", + "type": "attack-surface", + "title": "Agent tool path", + "summary": "The moment an agent is about to call a tool, write a file, or build a transaction. After-the-fact monitoring is too late if the action is irreversible.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "tools", + "runtime" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "development", + "normal-operations" + ], + "framework": "ai-security" + }, { "id": "surface-ci-cd-secrets", "type": "attack-surface", @@ -3591,6 +4159,27 @@ ], "framework": "encryption" }, + { + "id": "surface-ens-resolution", + "type": "attack-surface", + "title": "ENS name resolution", + "summary": "Turning a human-readable name into an address before a send. Stale indexers, skipped reverse checks, and confusable scripts all produce a valid-looking wrong destination.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "resolution" + ], + "roles": [ + "engineer-developer" + ], + "lifecycle": [ + "normal-operations" + ], + "framework": "ens" + }, { "id": "surface-executive-communications", "type": "attack-surface", @@ -3840,6 +4429,29 @@ ], "framework": "privacy" }, + { + "id": "surface-researcher-inbound", + "type": "attack-surface", + "title": "Researcher inbound path", + "summary": "How an external researcher reaches the team with a vulnerability. Public issues, social DMs, or a dead mailbox all leak the finding before a fix exists.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "disclosure", + "contact" + ], + "roles": [ + "security-engineer", + "engineer-developer" + ], + "lifecycle": [ + "normal-operations" + ], + "framework": "vulnerability-disclosure" + }, { "id": "surface-rpc-trust-boundary", "type": "attack-surface", @@ -4263,6 +4875,24 @@ "severityBasis": "Default triage is high because a stolen laptop is common and the disk holds whatever the operator used. FDE does not stop a logged-in malware session.", "framework": "encryption" }, + { + "id": "threat-prompt-injection", + "type": "threat", + "title": "Prompt injection", + "summary": "Untrusted text, including on-chain data or retrieved documents, is treated as instructions. The agent then leaks secrets or takes an action the operator did not intend.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ai", + "prompt-injection" + ], + "severity": "high", + "severityBasis": "Default triage is high because injection rides the model's instruction-following. Blast radius is whatever the agent can sign, send, or read. Prompt templates are not a control.", + "framework": "ai-security" + }, { "id": "threat-seed-phrase-compromise", "type": "threat", @@ -4342,6 +4972,42 @@ ], "framework": "awareness" }, + { + "id": "threat-spoofed-ens-resolution", + "type": "threat", + "title": "Spoofed ENS resolution", + "summary": "The UI shows a trusted name while the resolved address is attacker-controlled, from a stale indexer, a reverse record that does not loop, or a homograph.", + "domains": [ + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "ens", + "homograph", + "spoofing" + ], + "severity": "high", + "severityBasis": "Default triage is high because the send is valid and irreversible. The bug is in resolution, not in the signature.", + "framework": "ens" + }, + { + "id": "threat-stale-threat-model", + "type": "threat", + "title": "Stale threat model", + "summary": "Architecture or value at risk changed and the model did not. New trust boundaries, admin paths, or bridges ship without named abuses or owners.", + "domains": [ + "development-supply-chain", + "onchain-systems" + ], + "status": "proposed", + "tags": [ + "threat-model", + "design" + ], + "severity": "high", + "severityBasis": "Default triage is high because Web3 design misses become irreversible production loss. The failure is skipped analysis, not a missing scanner.", + "framework": "threat-modeling" + }, { "id": "threat-supply-chain-compromise", "type": "threat", @@ -4363,6 +5029,24 @@ ], "framework": "supply-chain" }, + { + "id": "threat-uncontactable-disclosure", + "type": "threat", + "title": "Uncontactable disclosure", + "summary": "A researcher finds a bug and cannot reach a monitored security contact. The report goes public, gets sold, or sits unread while the bug stays live.", + "domains": [ + "development-supply-chain", + "detection-incident-response" + ], + "status": "proposed", + "tags": [ + "disclosure", + "contact" + ], + "severity": "high", + "severityBasis": "Default triage is high because inbound silence turns a fixable finding into an uncoordinated release. A bounty platform does not replace a monitored contact.", + "framework": "vulnerability-disclosure" + }, { "id": "threat-unlimited-token-approval", "type": "threat", @@ -4439,6 +5123,13 @@ "type": "contains", "status": "proposed" }, + { + "id": "depends-on:component-ai-agent:component-developer-devices", + "source": "component-ai-agent", + "target": "component-developer-devices", + "type": "depends-on", + "status": "proposed" + }, { "id": "depends-on:component-ci-cd:component-dependency-graph", "source": "component-ci-cd", @@ -4580,6 +5271,27 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:component-ai-agent:guidance-ai-security", + "source": "component-ai-agent", + "target": "guidance-ai-security", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:component-ci-cd:guidance-secure-repos", + "source": "component-ci-cd", + "target": "guidance-secure-repos", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:component-community-channels:guidance-account-management", + "source": "component-community-channels", + "target": "guidance-account-management", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:component-community-channels:guidance-encrypted-communication", "source": "component-community-channels", @@ -4608,6 +5320,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:component-frontend:guidance-ens", + "source": "component-frontend", + "target": "guidance-ens", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:component-governance-module:guidance-safe-harbor-adoption", "source": "component-governance-module", @@ -4629,6 +5348,20 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:component-identity-accounts:guidance-account-management", + "source": "component-identity-accounts", + "target": "guidance-account-management", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:component-identity-accounts:guidance-guides", + "source": "component-identity-accounts", + "target": "guidance-guides", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:component-multisig:guidance-safe-harbor-scope", "source": "component-multisig", @@ -4650,6 +5383,20 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-branch-protection:guidance-secure-repos", + "source": "control-branch-protection", + "target": "guidance-secure-repos", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-bug-bounty-program:guidance-bug-bounties", + "source": "control-bug-bounty-program", + "target": "guidance-bug-bounties", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-cloud-hardening:guidance-cloud", "source": "control-cloud-hardening", @@ -4797,6 +5544,27 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-ensip15-normalization:guidance-ens-normalization", + "source": "control-ensip15-normalization", + "target": "guidance-ens-normalization", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-execution-path-enforcement:guidance-execution-path", + "source": "control-execution-path-enforcement", + "target": "guidance-execution-path", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-external-security-review:guidance-bug-bounties", + "source": "control-external-security-review", + "target": "guidance-bug-bounties", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-external-security-review:guidance-external-security-reviews", "source": "control-external-security-review", @@ -4804,6 +5572,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-external-security-review:guidance-ssdlc", + "source": "control-external-security-review", + "target": "guidance-ssdlc", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-frontend-integrity-monitoring:guidance-frontend", "source": "control-frontend-integrity-monitoring", @@ -4916,6 +5691,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-l1-ens-resolution:guidance-ens-integrity", + "source": "control-l1-ens-resolution", + "target": "guidance-ens-integrity", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-least-privilege-review:guidance-dprk-mitigation", "source": "control-least-privilege-review", @@ -4937,6 +5719,34 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-living-threat-model:guidance-create-maintain-threat-models", + "source": "control-living-threat-model", + "target": "guidance-create-maintain-threat-models", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-living-threat-model:guidance-identify-mitigate-threats", + "source": "control-living-threat-model", + "target": "guidance-identify-mitigate-threats", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-living-threat-model:guidance-ssdlc-threat-design", + "source": "control-living-threat-model", + "target": "guidance-ssdlc-threat-design", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-living-threat-model:guidance-threat-modeling", + "source": "control-living-threat-model", + "target": "guidance-threat-modeling", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-multi-channel-transfer-confirm:guidance-treasury-transaction-verification", "source": "control-multi-channel-transfer-confirm", @@ -4986,6 +5796,27 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-peer-code-review:guidance-code-reviews", + "source": "control-peer-code-review", + "target": "guidance-code-reviews", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-phishing-resistant-mfa:guidance-account-management", + "source": "control-phishing-resistant-mfa", + "target": "guidance-account-management", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-phishing-resistant-mfa:guidance-hardware-security-keys", + "source": "control-phishing-resistant-mfa", + "target": "guidance-hardware-security-keys", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-phishing-resistant-mfa:guidance-iam", "source": "control-phishing-resistant-mfa", @@ -5007,6 +5838,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-prompt-input-constraint:guidance-prompt-injection", + "source": "control-prompt-input-constraint", + "target": "guidance-prompt-injection", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-published-recovery-address:guidance-safe-harbor-scope", "source": "control-published-recovery-address", @@ -5014,6 +5852,20 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-published-security-contact:guidance-safe-harbor-scope", + "source": "control-published-security-contact", + "target": "guidance-safe-harbor-scope", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-published-security-contact:guidance-security-contact", + "source": "control-published-security-contact", + "target": "guidance-security-contact", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-registrar-hardening:guidance-dns-cert", "source": "control-registrar-hardening", @@ -5042,6 +5894,20 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-safe-harbor-adoption:guidance-vulnerability-disclosure", + "source": "control-safe-harbor-adoption", + "target": "guidance-vulnerability-disclosure", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:control-secure-sdlc-testing:guidance-secure-coding", + "source": "control-secure-sdlc-testing", + "target": "guidance-secure-coding", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-secure-sdlc-testing:guidance-security-testing", "source": "control-secure-sdlc-testing", @@ -5049,6 +5915,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-secure-sdlc-testing:guidance-ssdlc", + "source": "control-secure-sdlc-testing", + "target": "guidance-ssdlc", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-security-awareness-training:guidance-security-culture", "source": "control-security-awareness-training", @@ -5091,6 +5964,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:control-simulate-before-sign:guidance-ens-integrity", + "source": "control-simulate-before-sign", + "target": "guidance-ens-integrity", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:control-simulate-before-sign:guidance-signing-verification", "source": "control-simulate-before-sign", @@ -5385,6 +6265,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:threat-prompt-injection:guidance-prompt-injection", + "source": "threat-prompt-injection", + "target": "guidance-prompt-injection", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:threat-seed-phrase-compromise:guidance-seed-phrase-management", "source": "threat-seed-phrase-compromise", @@ -5420,6 +6307,27 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "documented-by:threat-spoofed-ens-resolution:guidance-ens-integrity", + "source": "threat-spoofed-ens-resolution", + "target": "guidance-ens-integrity", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:threat-stale-threat-model:guidance-create-maintain-threat-models", + "source": "threat-stale-threat-model", + "target": "guidance-create-maintain-threat-models", + "type": "documented-by", + "status": "proposed" + }, + { + "id": "documented-by:threat-uncontactable-disclosure:guidance-vulnerability-disclosure", + "source": "threat-uncontactable-disclosure", + "target": "guidance-vulnerability-disclosure", + "type": "documented-by", + "status": "proposed" + }, { "id": "documented-by:threat-unlimited-token-approval:guidance-smart-contract-interaction", "source": "threat-unlimited-token-approval", @@ -5434,6 +6342,13 @@ "type": "documented-by", "status": "proposed" }, + { + "id": "exposes:component-ai-agent:surface-agent-tool-path", + "source": "component-ai-agent", + "target": "surface-agent-tool-path", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-ci-cd:surface-ci-cd-secrets", "source": "component-ci-cd", @@ -5546,6 +6461,13 @@ "type": "exposes", "status": "proposed" }, + { + "id": "exposes:component-frontend:surface-ens-resolution", + "source": "component-frontend", + "target": "surface-ens-resolution", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-frontend:surface-frontend-deployment", "source": "component-frontend", @@ -5595,6 +6517,13 @@ "type": "exposes", "status": "proposed" }, + { + "id": "exposes:component-rpc-endpoints:surface-ens-resolution", + "source": "component-rpc-endpoints", + "target": "surface-ens-resolution", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-rpc-endpoints:surface-rpc-trust-boundary", "source": "component-rpc-endpoints", @@ -5644,6 +6573,13 @@ "type": "exposes", "status": "proposed" }, + { + "id": "exposes:component-smart-contracts:surface-researcher-inbound", + "source": "component-smart-contracts", + "target": "surface-researcher-inbound", + "type": "exposes", + "status": "proposed" + }, { "id": "exposes:component-software-wallet:surface-token-approvals", "source": "component-software-wallet", @@ -5665,6 +6601,13 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-bug-bounty-program:threat-uncontactable-disclosure", + "source": "control-bug-bounty-program", + "target": "threat-uncontactable-disclosure", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-cloud-hardening:threat-infrastructure-compromise", "source": "control-cloud-hardening", @@ -5763,6 +6706,20 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-ensip15-normalization:threat-spoofed-ens-resolution", + "source": "control-ensip15-normalization", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-execution-path-enforcement:threat-prompt-injection", + "source": "control-execution-path-enforcement", + "target": "threat-prompt-injection", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-external-security-review:threat-smart-contract-exploits", "source": "control-external-security-review", @@ -5861,6 +6818,20 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-l1-ens-resolution:threat-misdirected-transfer", + "source": "control-l1-ens-resolution", + "target": "threat-misdirected-transfer", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-l1-ens-resolution:threat-spoofed-ens-resolution", + "source": "control-l1-ens-resolution", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-least-privilege-review:threat-dprk-it-worker-infiltration", "source": "control-least-privilege-review", @@ -5882,6 +6853,20 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-living-threat-model:threat-smart-contract-exploits", + "source": "control-living-threat-model", + "target": "threat-smart-contract-exploits", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-living-threat-model:threat-stale-threat-model", + "source": "control-living-threat-model", + "target": "threat-stale-threat-model", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-multi-channel-transfer-confirm:threat-misdirected-transfer", "source": "control-multi-channel-transfer-confirm", @@ -5924,6 +6909,20 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-peer-code-review:threat-smart-contract-exploits", + "source": "control-peer-code-review", + "target": "threat-smart-contract-exploits", + "type": "mitigates", + "status": "proposed" + }, + { + "id": "mitigates:control-peer-code-review:threat-supply-chain-compromise", + "source": "control-peer-code-review", + "target": "threat-supply-chain-compromise", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-phishing-resistant-mfa:threat-custody-access-abuse", "source": "control-phishing-resistant-mfa", @@ -5945,6 +6944,13 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-prompt-input-constraint:threat-prompt-injection", + "source": "control-prompt-input-constraint", + "target": "threat-prompt-injection", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-published-recovery-address:threat-whitehat-legal-freeze", "source": "control-published-recovery-address", @@ -5952,6 +6958,13 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-published-security-contact:threat-uncontactable-disclosure", + "source": "control-published-security-contact", + "target": "threat-uncontactable-disclosure", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-registrar-hardening:threat-frontend-dns-hijacking", "source": "control-registrar-hardening", @@ -6036,6 +7049,13 @@ "type": "mitigates", "status": "proposed" }, + { + "id": "mitigates:control-simulate-before-sign:threat-spoofed-ens-resolution", + "source": "control-simulate-before-sign", + "target": "threat-spoofed-ens-resolution", + "type": "mitigates", + "status": "proposed" + }, { "id": "mitigates:control-test-transfer:threat-misdirected-transfer", "source": "control-test-transfer", @@ -6099,6 +7119,13 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-bug-bounty-program:asset-user-funds", + "source": "control-bug-bounty-program", + "target": "asset-user-funds", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-cloud-hardening:component-cloud-infrastructure", "source": "control-cloud-hardening", @@ -6183,6 +7210,20 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-ensip15-normalization:surface-ens-resolution", + "source": "control-ensip15-normalization", + "target": "surface-ens-resolution", + "type": "protects", + "status": "proposed" + }, + { + "id": "protects:control-execution-path-enforcement:surface-agent-tool-path", + "source": "control-execution-path-enforcement", + "target": "surface-agent-tool-path", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-external-security-review:component-smart-contracts", "source": "control-external-security-review", @@ -6288,6 +7329,20 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-l1-ens-resolution:asset-user-funds", + "source": "control-l1-ens-resolution", + "target": "asset-user-funds", + "type": "protects", + "status": "proposed" + }, + { + "id": "protects:control-l1-ens-resolution:surface-ens-resolution", + "source": "control-l1-ens-resolution", + "target": "surface-ens-resolution", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-limited-token-approvals:surface-token-approvals", "source": "control-limited-token-approvals", @@ -6295,6 +7350,13 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-living-threat-model:asset-source-code", + "source": "control-living-threat-model", + "target": "asset-source-code", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-multi-channel-transfer-confirm:surface-large-transfer", "source": "control-multi-channel-transfer-confirm", @@ -6323,6 +7385,13 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-peer-code-review:asset-source-code", + "source": "control-peer-code-review", + "target": "asset-source-code", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-phishing-resistant-mfa:component-identity-accounts", "source": "control-phishing-resistant-mfa", @@ -6337,6 +7406,13 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-prompt-input-constraint:component-ai-agent", + "source": "control-prompt-input-constraint", + "target": "component-ai-agent", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-published-recovery-address:asset-user-funds", "source": "control-published-recovery-address", @@ -6351,6 +7427,13 @@ "type": "protects", "status": "proposed" }, + { + "id": "protects:control-published-security-contact:surface-researcher-inbound", + "source": "control-published-security-contact", + "target": "surface-researcher-inbound", + "type": "protects", + "status": "proposed" + }, { "id": "protects:control-registrar-hardening:asset-domain-control", "source": "control-registrar-hardening", @@ -6736,6 +7819,13 @@ "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-misdirected-transfer:surface-ens-resolution", + "source": "threat-misdirected-transfer", + "target": "surface-ens-resolution", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-misdirected-transfer:surface-large-transfer", "source": "threat-misdirected-transfer", @@ -6855,6 +7945,27 @@ "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-prompt-injection:asset-secrets-credentials", + "source": "threat-prompt-injection", + "target": "asset-secrets-credentials", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-prompt-injection:asset-user-funds", + "source": "threat-prompt-injection", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-prompt-injection:surface-agent-tool-path", + "source": "threat-prompt-injection", + "target": "surface-agent-tool-path", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-seed-phrase-compromise:asset-seed-secrets", "source": "threat-seed-phrase-compromise", @@ -6960,6 +8071,41 @@ "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-spoofed-ens-resolution:asset-user-funds", + "source": "threat-spoofed-ens-resolution", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-spoofed-ens-resolution:surface-ens-resolution", + "source": "threat-spoofed-ens-resolution", + "target": "surface-ens-resolution", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-stale-threat-model:asset-source-code", + "source": "threat-stale-threat-model", + "target": "asset-source-code", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-stale-threat-model:asset-user-funds", + "source": "threat-stale-threat-model", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-stale-threat-model:surface-contract-upgrade-path", + "source": "threat-stale-threat-model", + "target": "surface-contract-upgrade-path", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-supply-chain-compromise:asset-deployment-authority", "source": "threat-supply-chain-compromise", @@ -6988,6 +8134,27 @@ "type": "targets", "status": "proposed" }, + { + "id": "targets:threat-uncontactable-disclosure:asset-source-code", + "source": "threat-uncontactable-disclosure", + "target": "asset-source-code", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-uncontactable-disclosure:asset-user-funds", + "source": "threat-uncontactable-disclosure", + "target": "asset-user-funds", + "type": "targets", + "status": "proposed" + }, + { + "id": "targets:threat-uncontactable-disclosure:surface-researcher-inbound", + "source": "threat-uncontactable-disclosure", + "target": "surface-researcher-inbound", + "type": "targets", + "status": "proposed" + }, { "id": "targets:threat-unlimited-token-approval:asset-user-funds", "source": "threat-unlimited-token-approval", diff --git a/utils/security-map.test.cjs b/utils/security-map.test.cjs index 26f31e1f..db0655a9 100644 --- a/utils/security-map.test.cjs +++ b/utils/security-map.test.cjs @@ -144,7 +144,8 @@ describe('production catalogue', () => { assert.equal(first.graph.license, 'CC-BY-SA-4.0') assert.doesNotMatch(serializeGraph(first.graph), /\/home\/|generatedAt|C:\\/) const threats = first.graph.nodes.filter((n) => n.type === 'threat') - assert.equal(threats.length, 23) + assert.equal(threats.length, 27) + @@ -168,6 +169,11 @@ describe('production catalogue', () => { assert.ok(first.graph.nodes.some((n) => n.id === 'control-full-disk-encryption')) assert.ok(first.graph.nodes.some((n) => n.id === 'control-default-e2ee-messaging')) assert.ok(first.graph.nodes.some((n) => n.id === 'control-safe-harbor-adoption')) + assert.ok(first.graph.nodes.some((n) => n.id === 'control-execution-path-enforcement')) + assert.ok(first.graph.nodes.some((n) => n.id === 'control-l1-ens-resolution')) + assert.ok(first.graph.nodes.some((n) => n.id === 'control-living-threat-model')) + assert.ok(first.graph.nodes.some((n) => n.id === 'control-published-security-contact')) +