code wiki / (root) / nx_decoy.nx

nx_decoy.nx source

↩ module page · 204 lines · 8425 B

1// nx_decoy.nx -- honeypot tripwires (aggressive-mimicry inverted). 2// 3// Biology: aggressive mimicry is when a PREDATOR mimics something 4// harmless to lure prey close (anglerfish lure resembling a worm, 5// photuris firefly mimicking female photinus flash patterns to eat 6// the responding males). Substrate INVERTS this: WE are not the 7// predator. WE are the prey. We plant fake-but-attractive artifacts 8// that lure THE PREDATOR (Intel ME / vendor scanner / state-actor 9// scraper). When the predator reads the lure, a tripwire fires. 10// 11// Per user 2026-05-19: "make sure that we have the system designed 12// with mimicry and obsfucation so these predatory programs get 13// nonsense or get scared off." The decoy IS the nonsense. Reading 14// it is fine -- but the read is observed, signed, and recorded as 15// confirmed-exfiltration into the forensic ledger. 16// 17// V1 decoy kinds (modeled on what surveillance scrapers target): 18// - FAKE_CREDENTIALS_FILE (.aws/credentials shape; tripwire keys) 19// - FAKE_SSH_PRIVATE_KEY (-----BEGIN OPENSSH PRIVATE KEY-----) 20// - FAKE_BROWSER_COOKIES (Chrome SQLite shape; tripwire UUIDs) 21// - FAKE_WALLET_FILE (Bitcoin wallet.dat shape; tripwire hashes) 22// - FAKE_KEYSTORE (Java keystore / PKCS12 shape) 23// - FAKE_SECRETS_BLOB (generic high-entropy looks-like-keys) 24// - FAKE_PASSWORD_MANAGER (KeePass kdbx shape) 25// 26// The decoy payload is STATISTICALLY plausible (high entropy, right 27// magic bytes, right size class) but FUNCTIONALLY useless. Any 28// "credential" extracted is a tripwire token. If that token ever 29// shows up downstream (auth attempt, dark-net listing, vendor 30// research paper), it's confirmed forgery from THIS host THIS 31// session. 32// 33// Composes: 34// nx_methyl -- decoys carry deliberately-invalid methyl marks 35// so leaked decoys are detectable as forgery 36// nx_aposematism -- decoys ALSO carry warning displays so vendor 37// ML might back off; if it doesn't, we get the 38// forensic tripwire instead -- either outcome 39// is a win 40// nx_xenocell -- a decoy read promotes the reading xenocell to 41// EXFILTRATING intrusion state 42// nx_pamp + nx_crispr -- recognize-then-remember decoy patterns so 43// our own decoys don't false-fire our scanners 44// nx_evict_journal -- tripwire fires logged as defensive wins 45// 46// V1 ships: 47// - decoy creation with kind + size + tripwire token 48// - access-observation hook (caller invokes when a read is detected) 49// - tripwire-fire detection (returns 1 if anyone read the decoy) 50// 51// Gap list (V1 honest perf verdict): 52// - decoy payload generation is caller's job (V2 substrate-managed 53// random fixtures sized appropriately per kind) 54// - no file-system / kernel binding (today nx_decoy is purely 55// in-memory; OS-binding is the integration layer's job) 56// - no peer-mesh tripwire-token registry (V2 federates so a token 57// read on one host can be flagged on every host) 58// - access-detection is caller-driven (V2 wires kernel watchers) 59// 60// genealogy_id: cardinal_2026-05-19_mimicry_obfuscation_directive + 61// cardinal_2026-05-17_cell_immune_judo + 62// biology_aggressive_mimicry_inverted 63// lineage_id: substrate_decoy_v1 64// 65// nx_safety_envelope: 66// intended_use: "Honeypot tripwires for confirmed-exfiltration 67// detection; DEFENSIVE ONLY -- never bait that 68// triggers offensive action" 69// sil_target: SIL3 70// evidence: [no_offensive_payload, tripwire_only, 71// captain_moroni_aligned, judo_of_information] 72// hazard_register: [bug-tape-decoy-leak-detected-elsewhere, 73// bug-tape-decoy-false-fires-on-own-scanner] 74// verdict: NOT_YET_EVALUATED 75 76import "nx_syscalls.nx" 77import "nx_tier.nx" 78 79// ===== Sealed enum: NxDecoyKind ================================== 80 81const NX_DK_FAKE_CREDENTIALS: nx_int = 0 82const NX_DK_FAKE_SSH_KEY: nx_int = 1 83const NX_DK_FAKE_BROWSER_COOKIES: nx_int = 2 84const NX_DK_FAKE_WALLET: nx_int = 3 85const NX_DK_FAKE_KEYSTORE: nx_int = 4 86const NX_DK_FAKE_SECRETS_BLOB: nx_int = 5 87const NX_DK_FAKE_PASSWORD_MGR: nx_int = 6 88const NX_DK_N_KINDS: nx_int = 7 89 90// ===== Sealed enum: NxDecoyVerdict =============================== 91 92const NX_DECOY_OK: nx_int = 0 93const NX_DECOY_ERR_BAD_KIND: nx_int = 1 94const NX_DECOY_TRIPWIRE_FIRED: nx_int = 2 95const NX_DECOY_ERR_BAD_TOKEN: nx_int = 3 96 97// ===== Struct: NxDecoy =========================================== 98// 99// One planted decoy. tripwire_token is the unique identifier embedded 100// in the payload that, if it shows up downstream, confirms this 101// specific decoy was read. payload_ptr + payload_len point to the 102// caller-allocated fixture bytes. 103// 104// read_count is incremented each time the substrate observes someone 105// reading the decoy; first_read_us / last_read_us bracket the access 106// window. xeno_id is the xenocell (if any) that did the reading -- 107// caller supplies via nx_decoy_on_read. 108 109struct NxDecoy { 110 kind: nx_int, 111 tripwire_token: nx_size, 112 payload_ptr: *u8, 113 payload_len: nx_size, 114 read_count: nx_int, 115 first_read_us: nx_size, 116 last_read_us: nx_size, 117 reader_xeno_id: nx_int, 118} 119 120// ===== nx_decoy_kind_is_valid ==================================== 121 122func nx_decoy_kind_is_valid(k: nx_int) -> nx_int { 123 if k < 0 { return 0 } 124 if k >= NX_DK_N_KINDS { return 0 } 125 return 1 126} 127 128// ===== nx_decoy_plant ============================================ 129// 130// Plant a decoy of the given kind with caller-supplied payload bytes 131// and a unique tripwire token. Returns NULL on bad kind. 132 133func nx_decoy_plant(kind: nx_int, 134 tripwire_token: nx_size, 135 payload_ptr: *u8, 136 payload_len: nx_size) -> *NxDecoy { 137 if nx_decoy_kind_is_valid(kind) == 0 { return (0 as i64) as *NxDecoy } 138 if tripwire_token == 0 { return (0 as i64) as *NxDecoy } 139 let d: *NxDecoy = (sys_mmap(72)) as *NxDecoy 140 d.kind = kind 141 d.tripwire_token = tripwire_token 142 d.payload_ptr = payload_ptr 143 d.payload_len = payload_len 144 d.read_count = 0 145 d.first_read_us = 0 146 d.last_read_us = 0 147 d.reader_xeno_id = 0 148 return d 149} 150 151// ===== nx_decoy_on_read ========================================== 152// 153// Caller invokes this when access to the decoy is observed (e.g., 154// kernel inotify fired on the decoy file, or in-memory access 155// watcher detected a read). reader_xeno_id is the suspect xenocell; 156// 0 if unknown. Returns NX_DECOY_TRIPWIRE_FIRED so the caller knows 157// to escalate (record signed observation in xenocell, log to evict 158// journal, propagate token to peer-mesh). 159 160func nx_decoy_on_read(d: *NxDecoy, 161 reader_xeno_id: nx_int, 162 now_us: nx_size) -> nx_int { 163 if d.read_count == 0 { d.first_read_us = now_us } 164 d.read_count = d.read_count + 1 165 d.last_read_us = now_us 166 if reader_xeno_id != 0 { d.reader_xeno_id = reader_xeno_id } 167 return NX_DECOY_TRIPWIRE_FIRED 168} 169 170// ===== nx_decoy_was_read ========================================= 171 172func nx_decoy_was_read(d: *NxDecoy) -> nx_int { 173 if d.read_count > 0 { return 1 } 174 return 0 175} 176 177// ===== nx_decoy_token_matches ==================================== 178// 179// Given a candidate token (e.g., received in an inbound auth attempt 180// or scraped from a paste-site by a peer), check whether it matches 181// this decoy's tripwire. Returns 1 on match. Used by downstream 182// integration layer to confirm "yes, this is the token we planted 183// in decoy id X on host Y at time T." 184 185func nx_decoy_token_matches(d: *NxDecoy, token: nx_size) -> nx_int { 186 if d.tripwire_token == 0 { return 0 } 187 if d.tripwire_token == token { return 1 } 188 return 0 189} 190 191// ===== nx_decoy_read_count ======================================= 192 193func nx_decoy_read_count(d: *NxDecoy) -> nx_int { 194 return d.read_count 195} 196 197// ===== nx_decoy_reader ======================================= 198// 199// Returns the xeno_id of the most recent reader, or 0 if no read 200// has been observed or reader_xeno_id was unknown when recorded. 201 202func nx_decoy_reader(d: *NxDecoy) -> nx_int { 203 return d.reader_xeno_id 204}