mirror of
https://github.com/norandom/OpenUltraSAST.git
synced 2026-10-20 05:29:28 +00:00
perf(model): one Joern invocation per query kind, not one per region
JVM startup dominated a scan: a call per region per family put a ten-line file at 275s over three regions, and would have put a thousand regions at roughly fifty hours. The queries themselves are milliseconds once the CPG is loaded, so the cost was almost entirely process starts. scan_repository() is now collect -> batch -> arbitrate. The three .sc scripts accept a `requests` JSON map and answer all of them in one run, keeping the single-request form so the committed measurements stay reproducible byte-for-byte. Arbiters are untouched: each is handed a CpgResult whose `run` returns its own prefetched rows. The batcher builds parameters by calling request_params() extracted from taint.py, dominance.py and config_value.py rather than reconstructing them. A second copy that drifts from the arbiter's is the exact shape of the five family-assumption bugs the predecessor spec spent a session finding; there is now one definition per family and the batcher borrows it. Regions are also deduplicated by (path, function), collapsing the nameless entry-point rows that were producing `model:injection:?:10`. Measured on the same ten-line file: 275s -> 106s, three duplicate findings -> one `model:injection:ping:10`, rung unchanged at model_entailed. Gates byte-identical. Server mode is recorded as task 2.3, deliberately sequenced after the repository measurement: whether the remaining ~100s floor is worth a process model, a weakened subprocess seam and a Scala-evaluating HTTP endpoint depends on a build-time-to-query-time ratio only 2.2 produces. Co-Authored-By: Claude Opus 5 (1M context) <[email protected]> Claude-Session: https://claude.ai/code/session_01T7XD7x5KonMdmGRkp63EQG
This commit is contained in:
co-authored by
Claude Opus 5
parent
e67f3ee2f0
commit
c35426e186
@@ -19,6 +19,21 @@ from .ladder import Rung, Verdict
|
||||
from .specs import TaintSpec
|
||||
|
||||
|
||||
def request_params(spec: TaintSpec, *, function: str = "", parameter_sources: bool = False) -> dict[str, object]:
|
||||
"""The query parameters this arbiter sends. Shared with the batcher so there is one definition, not two.
|
||||
|
||||
Two copies of a parameter dict is precisely the duplication that produced five bugs of one shape in the
|
||||
predecessor: a change made in one place and not its sibling.
|
||||
"""
|
||||
return {
|
||||
"sources": spec.sources,
|
||||
"sinks": spec.sinks,
|
||||
"sanitizers": spec.sanitizers,
|
||||
"function": function,
|
||||
"parameterSources": "true" if parameter_sources else "false",
|
||||
}
|
||||
|
||||
|
||||
def verdict(cpg: CpgResult, spec: TaintSpec, *, function: str = "", parameter_sources: bool = False) -> Verdict | None:
|
||||
"""The strongest verdict the taint query supports for ``spec`` in ``function``, or ``None`` to stay at suspicion.
|
||||
|
||||
@@ -26,16 +41,7 @@ def verdict(cpg: CpgResult, spec: TaintSpec, *, function: str = "", parameter_so
|
||||
for a function-level pair, where the function boundary *is* the trust boundary, and wrong for a whole
|
||||
repository, where most parameters carry internal values — so it is off by default and the caller opts in.
|
||||
"""
|
||||
rows = cpg.run(
|
||||
"taint",
|
||||
{
|
||||
"sources": spec.sources,
|
||||
"sinks": spec.sinks,
|
||||
"sanitizers": spec.sanitizers,
|
||||
"function": function,
|
||||
"parameterSources": "true" if parameter_sources else "false",
|
||||
},
|
||||
)
|
||||
rows = cpg.run("taint", request_params(spec, function=function, parameter_sources=parameter_sources))
|
||||
flows = _flows(rows, function=function)
|
||||
# A sink whose *shape* is safe is the fix, not the bug. `execute(sql, params)` binds rather than
|
||||
# interpolates and `printf("literal", x)` has a constant format string, so the flow that reaches them is
|
||||
@@ -146,4 +152,4 @@ def _witness(flow: Mapping[str, object]) -> str:
|
||||
return f"{flow['source']} -> {flow['sink']} (line {line}, {flow['length']} steps)"
|
||||
|
||||
|
||||
__all__ = ["verdict"]
|
||||
__all__ = ["request_params", "verdict"]
|
||||
|
||||
Reference in New Issue
Block a user