{
 "number": 34520,
 "input_hash": "b62f101145fba866",
 "model": "ledger",
 "prompt_hash": null,
 "created": "2026-10-25T01:14:06+00:00",
 "result": {
  "summary": "Annotate legacy getter and signing functions that return a boolean success flag alongside mutable out-parameters with the C++17 `[[nodiscard]]` attribute across the codebase. Address callers that previously ignored the return value by asserting success in witness sigop counting, checking descriptor cache return status, and wrapping test iteration in `BOOST_REQUIRE`.",
  "problem": "Legacy getters using the `bool Get...(..., mut& out)` idiom allow callers to ignore return values and inadvertently use uninitialized or invalid out-parameters when retrieval fails.",
  "card": "This PR adds [[nodiscard]] attributes across the codebase to legacy getter functions that return a boolean success flag alongside mutable out-parameters. It prevents callers from inadvertently ignoring failure status and using invalid out-parameters. The PR also fixes existing call sites where return values were previously ignored, including adding an assertion inside script witness sigop counting and checking cache retrieval results during descriptor evaluation.",
  "evidence": [
   "PR description: \"To ensure that the 'imaginary optional' is not unwrapped when the getter returns false, add a C++17 `[[nodiscard]]` attribute to all those legacy functions.\"",
   "Commit 90a82662a9 notes that ignoring the return value of `GetOp` triggers compiler warnings once annotated: `warning: ignoring return value of function declared with 'nodiscard' attribute [-Wunused-result]`"
  ],
  "scope_notes": "Touches diverse subsystems including script interpretation, descriptor caching, wallet interfaces, and networking to add compiler attributes.",
  "changed_since_previous": "No substantive changes; commits and approach remain unchanged from the previous version.",
  "thread": {
   "last_event_at": "2026-04-08T12:57:33Z",
   "events": 19,
   "head_sha": "1bd568e2c70840f606eab1157b35b1f06dab1e29",
   "schema_floor": 1,
   "schema": 2
  },
  "waiting_on": [],
  "risk": {
   "level": "medium",
   "touches": [
    "consensus",
    "wallet",
    "p2p"
   ],
   "why": "It introduces an Assert in CountWitnessSigOps within consensus-critical interpreter code; if the invariant on IsPushOnly fails under any condition, nodes would crash."
  },
  "discussion": {
   "author_status": "last statement processed 2026-04-08",
   "open_concerns": [],
   "resolved_concerns": [
    "ajtowns: proxy.m_tor_stream_isolation was not conditional on is_valid (fixed by maflcko 2026-03-05)",
    "ajtowns: declaring nodiscard but casting to void in consensus code discards safety guarantees (fixed by maflcko 2026-03-13)",
    "ajtowns: descriptor cache misses or invalid cached pubkeys are not handled properly (fixed by maflcko 2026-03-13)",
    "ryanofsky: using Assume or Assert introduces unwanted library dependencies into libbitcoin_consensus or inconsistent release/debug behavior (answered)"
   ]
  },
  "reviewability": {
   "state": "Ready",
   "label": "CI failing",
   "reason": "CI is red; check whether the failure is the PR's before a deep review."
  },
  "agreement": {
   "state": "Strong",
   "summary": "Strong: substantive support, no open objection (sedited, ryanofsky)",
   "reason": "Initial assessment. Multiple concerns from ajtowns were addressed by pushing fixes or spinning off PR #34741. ryanofsky raised an objection regarding Assume/Assert in libbitcoin_consensus (CountWitnessSigOps), which caused check-deps failures in CI; the author agreed to use assert for now, but a fix has not yet been pushed, leaving the claim open.",
   "evidence": [
    "HowHsu: ACK \u2014 ACK fac5685",
    "yuvicc: ACK \u2014 ACK fac5685e867b4a9ec334ed1ee31aabacd1c3124e",
    "sedited: Concept ACK \u2014 This looks like a good thing to add, but I wonder if handling these cases incrementally is the correct approach.",
    "ajtowns: Concept ACK \u2014 Concept ACK",
    "ryanofsky: ACK \u2014 FIrst commit does not seem right to me but otherwise these are nice changes that could prevent bugs."
   ],
   "objections": [
    {
     "reviewer": "ajtowns",
     "association": "MEMBER",
     "type": "objection",
     "kind": "correctness",
     "harm": "proxy.m_tor_stream_isolation was not conditional on is_valid",
     "request": "",
     "question": "",
     "text": "proxy.m_tor_stream_isolation was not conditional on is_valid",
     "clears_with": "answer",
     "blocking": false,
     "status": "fixed",
     "status_note": "",
     "cleared": true,
     "author_replied": true,
     "others_replied": false,
     "fix_pushed": true,
     "replies": [
      "rc:2889732879"
     ],
     "evidence": "2026-03-05: 'Shouldn't `proxy.m_tor_stream_isolation` also be conditional on `is_valid` ?'",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#discussion_r2888516177",
     "id": "rc:2888516177",
     "at": "2026-03-05",
     "status_at": "2026-03-05",
     "status_by": "maflcko",
     "resolution_evidence": "2026-03-05: maflcko: 'Yeah, but I guess `std::optional` could make more sense. Done in https://github.com/bitcoin/bitcoin/pull/34741 and moved this into draft for now. edit: now merged'",
     "pin": null,
     "from_schema": 1
    },
    {
     "reviewer": "ajtowns",
     "association": "MEMBER",
     "type": "objection",
     "kind": "approach",
     "harm": "declaring nodiscard but casting to void in consensus code discards safety guarantees",
     "request": "",
     "question": "",
     "text": "declaring nodiscard but casting to void in consensus code discards safety guarantees",
     "clears_with": "answer",
     "blocking": false,
     "status": "fixed",
     "status_note": "",
     "cleared": true,
     "author_replied": true,
     "others_replied": false,
     "fix_pushed": true,
     "replies": [
      "rc:2931655499"
     ],
     "evidence": "2026-03-05: 'I'm uncomfortable with both declaring `[[nodiscard] bool GetOp(...)` and then discarding the return value in consensus code (or non-test code in general).'",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#discussion_r2888547507",
     "id": "rc:2888547507",
     "at": "2026-03-05",
     "status_at": "2026-03-13",
     "status_by": "maflcko",
     "resolution_evidence": "2026-03-13: maflcko: 'thx, done'",
     "pin": null,
     "from_schema": 1
    },
    {
     "reviewer": "ajtowns",
     "association": "MEMBER",
     "type": "objection",
     "kind": "correctness",
     "harm": "descriptor cache misses or invalid cached pubkeys are not handled properly",
     "request": "",
     "question": "",
     "text": "descriptor cache misses or invalid cached pubkeys are not handled properly",
     "clears_with": "answer",
     "blocking": false,
     "status": "fixed",
     "status_note": "",
     "cleared": true,
     "author_replied": true,
     "others_replied": false,
     "fix_pushed": true,
     "replies": [
      "rc:2931656052"
     ],
     "evidence": "2026-03-05: 'if (cache == nullptr || !cache->GetCachedLastHardenedExtPubKey(m_expr_index,xpub) || !xpub.pubkey.IsValid())'",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#discussion_r2888567547",
     "id": "rc:2888567547",
     "at": "2026-03-05",
     "status_at": "2026-03-13",
     "status_by": "maflcko",
     "resolution_evidence": "2026-03-13: maflcko: 'edit: thx, done'",
     "pin": null,
     "from_schema": 1
    },
    {
     "reviewer": "ryanofsky",
     "association": "MEMBER",
     "type": "objection",
     "kind": "approach",
     "harm": "using Assume or Assert introduces unwanted library dependencies into libbitcoin_consensus or inconsistent release/debug behavior",
     "request": "",
     "question": "",
     "text": "using Assume or Assert introduces unwanted library dependencies into libbitcoin_consensus or inconsistent release/debug behavior",
     "clears_with": "answer",
     "blocking": false,
     "status": "answered",
     "status_note": "reply on record; standing not assessed yet",
     "cleared": true,
     "author_replied": true,
     "others_replied": false,
     "fix_pushed": false,
     "replies": [
      "rc:3047316414",
      "rc:3047849591"
     ],
     "evidence": "2026-04-07: 'I don't think it makes sense to use Assume here. Logically `CountWitnessSigOps` could either be intended to tolerate malformed scripts, in which case it should ignore the GetOp return value, or intended not to tolerate them, in which case it should abort or raise an exception.'",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#discussion_r3045778124",
     "id": "rc:3045778124",
     "at": "2026-04-07",
     "status_at": null,
     "status_by": null,
     "resolution_evidence": "",
     "pin": null,
     "from_schema": 1
    }
   ],
   "support": [
    {
     "reviewer": "HowHsu",
     "reason": "ACK fac5685",
     "substantive": false,
     "verdict": "ACK",
     "id": "c:3859820155",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#issuecomment-3859820155",
     "at": "2026-02-06",
     "association": "CONTRIBUTOR",
     "evidence": null,
     "areas": []
    },
    {
     "reviewer": "yuvicc",
     "reason": "ACK fac5685e867b4a9ec334ed1ee31aabacd1c3124e",
     "substantive": false,
     "verdict": "ACK",
     "id": "c:3918951595",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#issuecomment-3918951595",
     "at": "2026-02-18",
     "association": "CONTRIBUTOR",
     "evidence": null,
     "areas": []
    },
    {
     "reviewer": "sedited",
     "reason": "This looks like a good thing to add, but I wonder if handling these cases incrementally is the correct approach.",
     "substantive": true,
     "verdict": "Concept ACK",
     "id": "c:3958551668",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#issuecomment-3958551668",
     "at": "2026-02-25",
     "association": "MEMBER",
     "evidence": null,
     "areas": []
    },
    {
     "reviewer": "ajtowns",
     "reason": "Concept ACK",
     "substantive": false,
     "verdict": "Concept ACK",
     "id": "r:3894819258",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#pullrequestreview-3894819258",
     "at": "2026-03-05",
     "association": "MEMBER",
     "evidence": null,
     "areas": []
    },
    {
     "reviewer": "ryanofsky",
     "reason": "FIrst commit does not seem right to me but otherwise these are nice changes that could prevent bugs.",
     "substantive": true,
     "verdict": "ACK",
     "id": "r:4068977553",
     "url": "https://github.com/bitcoin/bitcoin/pull/34520#pullrequestreview-4068977553",
     "at": "2026-04-07",
     "association": "MEMBER",
     "evidence": null,
     "areas": []
    }
   ],
   "participants": [
    {
     "login": "HowHsu",
     "stance": "support",
     "note": "ACKed commit fac5685",
     "association": "CONTRIBUTOR",
     "comments": 1,
     "first": "2026-02-06",
     "last": "2026-02-06"
    },
    {
     "login": "yuvicc",
     "stance": "support",
     "note": "ACKed commit fac5685",
     "association": "CONTRIBUTOR",
     "comments": 1,
     "first": "2026-02-18",
     "last": "2026-02-18"
    },
    {
     "login": "sedited",
     "stance": "support",
     "note": "Concept ACKed, suggested considering clang-tidy tooling and noted extra getter candidates",
     "association": "MEMBER",
     "comments": 1,
     "first": "2026-02-25",
     "last": "2026-02-25"
    },
    {
     "login": "ajtowns",
     "stance": "support",
     "note": "Concept ACKed, raised concerns about proxy isolation, consensus GetOp return handling, and descriptor cache handling",
     "association": "MEMBER",
     "comments": 4,
     "first": "2026-03-05",
     "last": "2026-03-05"
    },
    {
     "login": "ryanofsky",
     "stance": "support",
     "note": "Approved with comments; objected to Assume/Assert in consensus CountWitnessSigOps triggering library dependency issues",
     "association": "MEMBER",
     "comments": 5,
     "first": "2026-04-07",
     "last": "2026-04-08"
    }
   ],
   "derivation": "substantive support, no open objection (sedited, ryanofsky)",
   "model_state": null,
   "corrections": [],
   "notes": "Initial assessment. Multiple concerns from ajtowns were addressed by pushing fixes or spinning off PR #34741. ryanofsky raised an objection regarding Assume/Assert in libbitcoin_consensus (CountWitnessSigOps), which caused check-deps failures in CI; the author agreed to use assert for now, but a fix has not yet been pushed, leaving the claim open."
  },
  "dependencies": {
   "depends_on": [],
   "enables": []
  },
  "categories": [
   {
    "name": "ipc",
    "member": false,
    "evidence": "Touches src/interfaces/node.h and src/interfaces/wallet.h only to add [[nodiscard]], which does not affect IPC infrastructure or process separation mechanics.",
    "band": "Unranked",
    "reason_tag": "cleanup",
    "score": 0.0,
    "factors": {
     "bug_severity": 0,
     "leverage": 0,
     "performance": 0,
     "security_stability": 1,
     "user_value": 0
    },
    "rationale": "Mechanical addition of compiler attributes to interface declarations does not touch IPC behavior."
   },
   {
    "name": "p2p",
    "member": false,
    "evidence": "Incidental annotation of helper methods in src/net_processing.h and src/netaddress.h without changing P2P protocol or relay behavior.",
    "band": "Unranked",
    "reason_tag": "cleanup",
    "score": 0.0,
    "factors": {
     "bug_severity": 0,
     "leverage": 0,
     "performance": 0,
     "security_stability": 1,
     "user_value": 0
    },
    "rationale": "Does not touch P2P protocol logic, message processing, or networking behavior."
   },
   {
    "name": "rpc",
    "member": false,
    "evidence": "No RPC interface methods or RPC server files are modified.",
    "band": "Unranked",
    "reason_tag": "cleanup",
    "score": 0.0,
    "factors": {
     "bug_severity": 0,
     "leverage": 0,
     "performance": 0,
     "security_stability": 1,
     "user_value": 0
    },
    "rationale": "Does not touch RPC methods, client logic, or server infrastructure."
   },
   {
    "name": "utils",
    "member": false,
    "evidence": "Touches src/common/args.h and src/common/config.cpp only to annotate existing getter methods.",
    "band": "Unranked",
    "reason_tag": "cleanup",
    "score": 0.0,
    "factors": {
     "bug_severity": 0,
     "leverage": 0,
     "performance": 0,
     "security_stability": 1,
     "user_value": 0
    },
    "rationale": "Does not change utility libraries, logging, or shared infrastructure primitives."
   },
   {
    "name": "validation",
    "member": false,
    "evidence": "Touches src/script/interpreter.cpp and src/txdb.cpp only for compiler attribute annotations and assert cleanups; validation guidelines explicitly exclude structural refactors that pass through validation without altering behavior.",
    "band": "Unranked",
    "reason_tag": "cleanup",
    "score": 0.0,
    "factors": {
     "bug_severity": 0,
     "leverage": 0,
     "performance": 0,
     "security_stability": 1,
     "user_value": 0
    },
    "rationale": "Does not alter validation rules, consensus logic, or chainstate invariants."
   },
   {
    "name": "wallet",
    "member": true,
    "evidence": "Annotates legacy key and script retrieval interfaces across src/script/signingprovider.h, src/wallet/scriptpubkeyman.h, and src/wallet/wallet.h with [[nodiscard]].",
    "band": "P4",
    "reason_tag": "cleanup",
    "score": 0.2,
    "factors": {
     "bug_severity": 0,
     "leverage": 0,
     "performance": 0,
     "security_stability": 1,
     "user_value": 0
    },
    "rationale": "Adds `[[nodiscard]]` to key and script retrieval interfaces in `SigningProvider` and `ScriptPubKeyMan` to ensure callers do not ignore return values. While useful defensive hygiene to prevent using uninitialized or invalid out-parameters, it is an internal compiler-attribute refactor with no active wallet bug fix."
   }
  ],
  "confidence": "high",
  "uncertainties": [],
  "needs": []
 },
 "cost_usd": 0.0,
 "source": {
  "record": "2026-10-25T01:14:06+00:00",
  "code": "2026-10-25T01:16:37+00:00",
  "judgments": 6
 }
}