code wiki / _hdl_build / nx_sitededup.nx

nx_sitededup.nx

buildroot/runtime/_hdl_build/nx_sitededup.nx

28823 B532 linesdepth 6pulls 22 transitivereach 0 importersview sourcekind tool
docsdependenciesstructsconstsfunctions

about

nx_sitededup.nx -- COLLAPSE DUPLICATE DOCUMENTS IN A SITE SEARCH SHARD. THE DEFECT, measured 2026-08-25 on a live scope=site SERP for "nishi search": of 30 results, SIX were the SAME document under two different cids -- e.g. "VORTEX RISC-V GPGPU -- COMPLETE PUBLICATION BIBLIOGRAPHY" as 7477184972746352550 AND 2839761502039440748, with IDENTICAL scores. ROOT CAUSE: a cid is a content hash of the RAW STORED BYTES, and TWO DIFFERENT HASH FUNCTIONS write the same doc:<cid> keyspace -- dp_cid (FNV-1a, nx_docportal_lib) and ci_hash (base-131 polynomial, nx_corpus_ingest). Two captures of one page that differ only in a Date: header or a revision line are therefore two different documents, and cross-path dedup is impossible by construction. Ingest has since been fixed FORWARD (dp_ingest_policy strips capture headers and runs bd_fit_text before hashing). That does nothing for rows already stored. This organ is the backward half. ---- WHY THE FIRST VERSION OF THIS ORGAN COULD NOT HAVE WORKED, AND HOW WE KNOW ---------------- The first cut fingerprinted the RAW stored bytes. Its own gate then measured the real capture pair -- one document, stored twice, the second copy carrying an HTTP header and a bumped revision line -- at SIX bits of Hamming distance against the published k=3 bar. It would have collapsed NOTHING. The published recipe has a step the fingerprint papers do not cover: NORMALISE THE TEXT BEFORE SHINGLING, and specifically normalise DIGITS TO A CONSTANT, which is what kills counter, date, revision and price near-duplicates. That is precisely our duplicate class. nx_textnorm_lib is that step, it is a SHARED lib so the gate proves the same normalisation the actuator ships, and this organ now reports the raw-vs-normalised comparison ON THE WHOLE POPULATION so the claim "normalisation is what made this work" is a measurement rather than an assertion. WHY SUPPRESSION AND NOT DELETION: rule 13, additive-only. Nothing is removed. A duplicate is marked by appending a pol:<cid> row with the public-search consent bit cleared -- the SAME row the search path ALREADY reads per candidate (dss_search, DSS_POL_SEARCH), so this needs no change to any serve organ and takes effect on the next query. It is reversible by appending a row with the bit set. Every other owner flag on that row is preserved (sdd_clear_search_bit). WHY DURABLE AND NOT AT RANK TIME: the alternative is fingerprinting every candidate on every query. Fingerprinting is a full pass over the document TEXT, and the serve path deliberately does not read doc bodies during candidate filtering (the site: filter's own comment: "Cheap: ss_hget per candidate, no doc reads"). Paying a text scan per candidate per query to rediscover a fact that does not change between queries is the wrong side of the trade. This pass pays it once. COMPOSES, NEVER RE-IMPLEMENTS: nx_simhash for the fingerprint (Charikar 2002 / Manku 2007), nx_textnorm_lib for the ONE copy of the normalisation decision, nx_sitededup_lib for the ONE copy of the collapse decision, dss_mkpolkey for the policy row, and ccz_cat_num as the integer emitter. THE FINGERPRINT PLANE IS DELIBERATELY A NEW KEYSPACE. Persisted fingerprints go to fpn:<cid>

dependencies 4 imports · 0 importers

nx_corpus_ingest.nx nx_sitededup_lib.nx nx_textnorm_lib.nx nx_itoa_lib.nx nx_sitededup.nx

imports: nx_corpus_ingest.nxnx_sitededup_lib.nxnx_textnorm_lib.nxnx_itoa_lib.nx

imported by: nobody (leaf or entry point)

call flow from main pre-order; caps 40 nodes / depth 6 declared; ↻ = already shown

main sd_usage sd_puts sdd_conf_k sdd_conf_int lcf_int_of sys_mmap nxa_die sys_write sys_exit nxa_lock_take nxa_lock_addr sys_write ↻ nxa_lock_give nxa_lock_addr ↻ nxa_report_overrun sys_write ↻ nxa_dump_printable nxa_dump_sizes sys_read_file sys_openat_rd sys_lseek sys_mmap ↻ sys_read sys_munmap sys_close lcf_int lcf_find sdd_confpath sdd_confpath_up sdd_conf_maxdocs sdd_conf_int ↻ sdd_conf_showrows sdd_conf_int ↻ sdd_conf_which lcf_int_of ↻ sdd_confpath ↻ sdd_confpath_up ↻ sdd_conf_missing sd_puts ↻

structs

none

consts

55const SD_KEYCAP: i64 = 64
56const SD_VALCAP: i64 = 32
57const SD_WORD: i64 = 8
58const SD_MINUS: i64 = 45
59const SD_ZERO: i64 = 48
60const SD_NINE: i64 = 57
61const SD_DEC: i64 = 10
62const SD_URL_MINKEY: i64 = 5
63const SD_URL_MAXKEY: i64 = 60
64const SD_C_U: i64 = 117
65const SD_C_R: i64 = 114
66const SD_C_L: i64 = 108
67const SD_C_COLON: i64 = 58
68const SD_C_C: i64 = 99
69const SD_C_A: i64 = 97
70const SD_C_P: i64 = 112
71const SD_C_D: i64 = 100
72const SD_C_O: i64 = 111
73const SD_PREFIXCAP: i64 = 512
74const SD_BOX: i64 = 8

functions

76func sd_puts(s: *u8) -> i64 { var n: i64 = 0; while s[n] != (0 as u8) { n = n + 1 } sys_write(1, s, n); return 0 }
called by 2: sd_usagemain
77func sd_num(v: i64) -> i64
called by 1: main calls 1: ccz_cat_num
84func sd_atoi(s: *u8) -> i64
called by 1: main
93func sd_parse_i64(p: *u8, n: i64) -> i64
called by 2: sd_fp_ofmain
106func sd_usage() -> i64
called by 1: main calls 1: sd_puts
122func sd_fp_of(h: *i64, cid: i64, fkey: *u8, dkey: *u8, ap: *i64, al: *i64, box: *i64, nb: *i64, out: *i64) -> i64
147func main(argc: i64, argv: *i64) -> i64