code wiki / (root) / nx_antibody.nx

nx_antibody.nx source

↩ module page · 291 lines · 11093 B

1// nx_antibody.nx -- adaptive defense generation. 2// 3// Per [[feedback-unified-immune-architecture-three-tier]] item 2.7: 4// "adaptive defense GENERATION from observed attacks; the substrate's 5// defensive judo. Captures real attack samples → processes into 6// machine-readable defense definitions → affinity-matures across 7// encounters → distributes via peer mesh → composes legal/social 8// defense materials. Biology: clonal selection + affinity maturation 9// + memory cell formation. Defensive-only discipline: NEVER initiates 10// contact with attackers; only learns from contact attackers initiate." 11// 12// Per [[feedback-cell-immune-system-ransomware-judo-ddos-by-bit]]: 13// the judo is of INFORMATION not retaliation. We never attack back; 14// we make every attacker action visible + analyzable + distributable. 15// 16// Per [[feedback-captain-moroni-doctrine]]: DEFENSIVE ONLY. Substrate 17// refuses to compile offensive antibody operations -- antibodies are 18// detection signatures, not exploitation payloads. 19// 20// Lifecycle of an antibody (clonal-selection analog): 21// 1. nx_pamp or nx_pamp_meta detects an attack -- attack sample 22// captured into nx_xenocell signed observation 23// 2. nx_antibody_generate distills the sample into a detection 24// signature (hash + kind + Q10 affinity) 25// 3. Antibody added to nx_antibody_array; nx_crispr-style memory 26// 4. On each subsequent encounter, antibody's hit_count increments 27// and effectiveness Q10 updates (affinity maturation) 28// 5. V2: antibodies above effectiveness threshold federate via 29// peer-mesh (Citizen Lab analog -- community-shared intel) 30// 6. V2: antibodies compose into legal/social defense materials 31// (sub-poena docs, public advisories) via nx_evict_journal 32// forensic chain 33// 34// Composes: 35// nx_pamp / nx_pamp_meta -- detection feeds antibody generation 36// nx_xenocell -- attack samples come from signed observations 37// nx_crispr -- adaptive memory mechanism reused for antibodies 38// nx_lysis -- antibody confirms threat -> lysis selects mechanism 39// nx_restriction -- antibody-positive input refused at IO boundary 40// 41// V1 ships: 42// - struct NxAntibody with kind + signature_hash + affinity_q10 + 43// hit_count + effectiveness_q10 44// - generate (from a pamp hit or pamp_meta verdict) 45// - match (does this byte buffer trigger any antibody?) 46// - affinity_mature (after successful match, bump effectiveness) 47// - effectiveness_threshold predicate (above 768 = federation-ready) 48// 49// Gap list (V1 honest perf verdict): 50// - peer-mesh federation queued (V2) 51// - legal/social defense composition queued (V3) 52// - affinity maturation formula is linear (V2 uses learned rate) 53// - no antibody-class grouping (V2 antibodies cluster into 54// "antibody class A defends against attacker family X") 55// - signature is content_hash only; V2 adds behavioral fingerprint 56// 57// genealogy_id: cardinal_2026-05-19_unified_immune_architecture + 58// cardinal_2026-05-17_cell_immune_judo + 59// cardinal_2026-05-07_captain_moroni_defensive_only + 60// biology_clonal_selection_affinity_maturation 61// lineage_id: substrate_antibody_v1 62// 63// nx_safety_envelope: 64// intended_use: "Adaptive defense signature generation from 65// observed attack samples; DEFENSIVE ONLY; 66// Captain Moroni discipline enforced" 67// sil_target: SIL3 68// evidence: [no_offensive_path, signatures_are_detectors_not_exploits, 69// captain_moroni_aligned, peer_mesh_optional_not_required] 70// verdict: NOT_YET_EVALUATED 71 72import "nx_syscalls.nx" 73import "nx_tier.nx" 74import "nx_pamp.nx" 75import "nx_pamp_meta.nx" 76const NX_MAGIC_1024: i64 = 1024 77 78// ===== Sealed enum: NxAntibodyVerdict ============================= 79 80const NX_AB_VD_OK: nx_int = 0 81const NX_AB_VD_ERR_FULL: nx_int = 1 82const NX_AB_VD_MATCH: nx_int = 2 83const NX_AB_VD_NO_MATCH: nx_int = 3 84const NX_AB_VD_ERR_BAD_KIND: nx_int = 4 85 86// ===== Sealed enum: NxAntibodyState ============================== 87// 88// NAIVE = freshly generated, never matched in production 89// MATURE = matched >= 3 times, affinity above 614 (60%) 90// MEMORY = matched >= 10 times, affinity above 870 (85%); federation candidate 91 92const NX_AB_ST_NAIVE: nx_int = 0 93const NX_AB_ST_MATURE: nx_int = 1 94const NX_AB_ST_MEMORY: nx_int = 2 95const NX_AB_ST_N_STATES: nx_int = 3 96 97// Affinity-maturation thresholds (per Cardinal 11, named constants 98// for one-line tuning). 99const NX_AB_MATURE_HITS: nx_int = 3 100const NX_AB_MATURE_AFFINITY: nx_int = 614 101const NX_AB_MEMORY_HITS: nx_int = 10 102const NX_AB_MEMORY_AFFINITY: nx_int = 870 103const NX_AB_FEDERATION_AFFINITY: nx_int = 768 104 105// ===== Struct: NxAntibody ======================================== 106// 107// One detection signature with maturation metadata. kind aliases 108// NX_PAMP_* (or caller's extended taxonomy). signature_hash is 109// content-addressed (BLAKE3 of the attack body). affinity_q10 110// starts at "how confident was the initial detection" and matures 111// upward with successful repeats. 112 113struct NxAntibody { 114 kind: nx_int, 115 signature_hash: nx_size, 116 affinity_q10: nx_int, 117 hit_count: nx_int, 118 effectiveness_q10: nx_int, 119 state: nx_int, 120 generated_us: nx_size, 121 last_match_us: nx_size, 122} 123 124// ===== Struct: NxAntibodyArray =================================== 125 126struct NxAntibodyArray { 127 antibodies: *NxAntibody, 128 capacity: nx_size, 129 head: nx_size, 130 count: nx_size, 131} 132 133const NX_AB_BYTES: nx_size = 56 134const NX_AB_DEFAULT_CAPACITY: nx_size = 128 135 136// ===== Validators ================================================ 137 138func nx_ab_vd_state_is_valid(s: nx_int) -> nx_int { 139 if s < 0 { return 0 } 140 if s >= NX_AB_ST_N_STATES { return 0 } 141 return 1 142} 143 144// ===== nx_antibody_array_new ===================================== 145 146func nx_antibody_array_new(capacity: nx_size) -> *NxAntibodyArray { 147 let a: *NxAntibodyArray = (sys_mmap(32)) as *NxAntibodyArray 148 let bytes: nx_size = capacity * NX_AB_BYTES 149 a.antibodies = (sys_mmap(bytes)) as *NxAntibody 150 a.capacity = capacity 151 a.head = 0 152 a.count = 0 153 return a 154} 155 156// ===== _ab_at ==================================================== 157 158func _ab_at(a: *NxAntibodyArray, idx: nx_size) -> *NxAntibody { 159 return (a.antibodies as i64 + (idx as i64) * NX_AB_BYTES) as *NxAntibody 160} 161 162// ===== nx_antibody_generate ====================================== 163// 164// Distill a pamp hit (or pamp_meta verdict) into a new antibody. 165// The "affinity_q10" parameter is the initial detection confidence; 166// for nx_pamp hits this is the PampHit.confidence; for nx_pamp_meta 167// HIGH_DECEPTION it's the deception_q10. Returns the index of the 168// new antibody, or -1 if array is full. 169 170func nx_antibody_generate(arr: *NxAntibodyArray, 171 kind: nx_int, 172 signature_hash: nx_size, 173 initial_affinity_q10: nx_int, 174 now_us: nx_size) -> nx_int { 175 if arr.count >= arr.capacity { return -1 } 176 let ab: *NxAntibody = _ab_at(arr, arr.head) 177 ab.kind = kind 178 ab.signature_hash = signature_hash 179 ab.affinity_q10 = initial_affinity_q10 180 ab.hit_count = 0 181 ab.effectiveness_q10 = initial_affinity_q10 182 ab.state = NX_AB_ST_NAIVE 183 ab.generated_us = now_us 184 ab.last_match_us = now_us 185 let idx: nx_int = arr.head as i64 186 arr.head = arr.head + 1 187 if arr.head >= arr.capacity { arr.head = 0 } 188 arr.count = arr.count + 1 189 return idx 190} 191 192// ===== nx_antibody_match ========================================= 193// 194// Walk the array; find any antibody whose (kind, signature_hash) 195// matches the candidate. Returns the index on hit or -1 on miss. 196// Caller then calls nx_antibody_affinity_mature to update the 197// matched antibody's metadata. 198 199func nx_antibody_match(arr: *NxAntibodyArray, 200 kind: nx_int, 201 signature_hash: nx_size) -> nx_int { 202 var live: nx_size = arr.count 203 if live > arr.capacity { live = arr.capacity } 204 var i: nx_size = 0 205 while i < live { 206 let ab: *NxAntibody = _ab_at(arr, i) 207 if ab.kind == kind { 208 if ab.signature_hash == signature_hash { 209 return i as i64 210 } 211 } 212 i = i + 1 213 } 214 return -1 215} 216 217// ===== nx_antibody_affinity_mature =============================== 218// 219// Called after a successful match. Increments hit_count and bumps 220// affinity_q10 toward 1024 by a maturation rate (V1: +51 Q10 per 221// hit, ~5%). State transitions per the thresholds. 222 223func nx_antibody_affinity_mature(arr: *NxAntibodyArray, 224 idx: nx_int, 225 now_us: nx_size) -> nx_int { 226 if idx < 0 { return NX_AB_VD_ERR_BAD_KIND } 227 if (idx as nx_size) >= arr.capacity { return NX_AB_VD_ERR_BAD_KIND } 228 let ab: *NxAntibody = _ab_at(arr, idx as nx_size) 229 ab.hit_count = ab.hit_count + 1 230 ab.last_match_us = now_us 231 // affinity climbs +51 per hit, capped at 1024 232 ab.affinity_q10 = ab.affinity_q10 + 51 233 if ab.affinity_q10 > NX_MAGIC_1024 { ab.affinity_q10 = NX_MAGIC_1024 } 234 ab.effectiveness_q10 = ab.affinity_q10 235 // state transitions 236 if ab.hit_count >= NX_AB_MEMORY_HITS { 237 if ab.affinity_q10 >= NX_AB_MEMORY_AFFINITY { 238 ab.state = NX_AB_ST_MEMORY 239 } 240 } 241 if ab.state == NX_AB_ST_NAIVE { 242 if ab.hit_count >= NX_AB_MATURE_HITS { 243 if ab.affinity_q10 >= NX_AB_MATURE_AFFINITY { 244 ab.state = NX_AB_ST_MATURE 245 } 246 } 247 } 248 return NX_AB_VD_OK 249} 250 251// ===== nx_antibody_is_federation_ready ============================ 252// 253// Predicate: this antibody's affinity is high enough to share with 254// peer mesh / community intel. Used by V2 federation layer; today 255// just exposes the predicate so callers can plan. 256 257func nx_antibody_is_federation_ready(ab: *NxAntibody) -> nx_int { 258 if (ab as i64) == 0 { return 0 } 259 if ab.affinity_q10 >= NX_AB_FEDERATION_AFFINITY { return 1 } 260 return 0 261} 262 263// ===== nx_antibody_count_by_state ================================= 264 265func nx_antibody_count_by_state(arr: *NxAntibodyArray, state: nx_int) -> nx_int { 266 var hits: nx_int = 0 267 var live: nx_size = arr.count 268 if live > arr.capacity { live = arr.capacity } 269 var i: nx_size = 0 270 while i < live { 271 let ab: *NxAntibody = _ab_at(arr, i) 272 if ab.state == state { hits = hits + 1 } 273 i = i + 1 274 } 275 return hits 276} 277 278// ===== nx_antibody_total_hits ==================================== 279 280func nx_antibody_total_hits(arr: *NxAntibodyArray) -> nx_int { 281 var sum: nx_int = 0 282 var live: nx_size = arr.count 283 if live > arr.capacity { live = arr.capacity } 284 var i: nx_size = 0 285 while i < live { 286 let ab: *NxAntibody = _ab_at(arr, i) 287 sum = sum + ab.hit_count 288 i = i + 1 289 } 290 return sum 291}