bdc473369e1bb2a5666bd76626d449af50b81d40
braney
  Fri Jul 31 10:50:24 2026 -0700
resolve char * constants per file in the harvesters, not pooled refs #37925 refs #37923

Both harvesters merged file-scope "char *NAME = \"literal\";" definitions into
the same table as the #defines, keyed by identifier with setdefault, so one
program's private constant answered for every other file in the tree and
whichever file os.walk reached first won.  harvestCartVars.py already did this
per file; these two hoisted it and broke.

What it was getting wrong:

- hgConfCatalog listed encpipeline_prod as an hg.conf variable, verified,
cited at hgTracks.c:9867.  That line is cfgNamesWithPrefix(database), the
<db>_TopLink family, and encpipeline_prod is a hardcoded MySQL database
name in hg/encode/docId/docIdView/docIdView.c.  The row is gone and the
call site now reads {database}, a runtime value.
- Twelve URL records named the wrong variable.  Five cartRemove(cart,
varName) sites were reported as removing dnaLines, which is what an
assembly tool at primeMate.c:296 calls its own varName; three
cartRemove(cart, var) sites read as num.  They now read {varName} and
{var}.
- cfgValsWithPrefix passing its own prefix parameter through resolved to an
unrelated utility's "char *prefix = \"\";", and an empty string is falsy,
so the call site was dropped instead of reported.  It goes through
NAME_SKIP now like the other accessor plumbing.

The deliberate cost is the genuine cross-file constant: snp125ColorSourceOldVar
is defined in hg/cgilib/snp125Ui.c and declared extern in hg/inc/snp125Ui.h, so
its hgTrackUi call site now reads {snp125ColorSourceOldVar} rather than
snp125ColorSource.  Pooling only extern-declared names would recover it and
bring the collisions straight back, since database is extern in hgTracks and
separately initialized to a literal in that ENCODE tool.

hgConfCatalog --check still reports 0 problems and --reconcile is unchanged;
urlCommandCatalog --check still reports catalog ok with the persistence audit
at 41 known leaks, 0 unrecorded, 0 stale.

diff --git src/hg/utils/hgConfCatalog/hgConfCatalog.py src/hg/utils/hgConfCatalog/hgConfCatalog.py
index 06f4ffa6355..4916c771242 100755
--- src/hg/utils/hgConfCatalog/hgConfCatalog.py
+++ src/hg/utils/hgConfCatalog/hgConfCatalog.py
@@ -1069,33 +1069,30 @@
         h("suggest.secretKey", "credential",
           "hg/hgUserSuggestion/hgUserSuggestion.c:539", verified=True,
           family="suggest"),
         h("suggest.humanThreshold", "limit",
           "hg/hgUserSuggestion/hgUserSuggestion.c:543", default='"-0.1"',
           verified=True, family="suggest"),
         h("hgGateway.dbDbTaxonomy", "internal", "hg/hgGateway/hgGateway.c:407",
           default="defaultDbDbTree", verified=True),
         h("hgEncodeVocabDocBaseUrl", "url",
           "hg/encode/hgEncodeVocab/hgEncodeVocab.c:67", default='""',
           verified=True, deprecated=True),
         h("namedSessionAlt.", "internal", "hg/lib/cart.c:666", verified=True,
           note="A prefix family enumerated at runtime: alternative "
                "namedSessionDb locations to search when resolving a shared "
                "session."),
-        h("encpipeline_prod", "internal", "hg/hgTracks/hgTracks.c:9867",
-          verified=True, deprecated=True,
-          note="Read via cfgValsWithPrefix from the ENCODE pipeline era."),
     ],
 }
 
 
 # ---------------------------------------------------------------------------
 # retired: settings whose feature is gone or was never part of the browser
 # ---------------------------------------------------------------------------
 
 RETIRED = {
     "what": "Settings for features that are gone, or for CGIs that are not "
             "part of the browser release.  Kept in the catalog because the "
             "reads are still in the tree and a mirror's hg.conf may still "
             "carry them.  Deleting the code is a separate job from "
             "sunsetting a release gate, and these are candidates for it.",
     "vars": [