Source-linked AI summary
P2Patch: Exploit-Guided Vulnerability Repair
Mohsen Iranmanesh, Sina Moradi Sabet, Sina Marefat, Ali Javidi Ghasr, Maxime Newman Nereyabagabo, Kousha Amouzesh, Jaivir Malhi, Vinci Velasco, Alex Chung, Mohammad A. Tayebi
TL;DR
Automated vulnerability repair often constructs and judges patches using the same evidence, although a single alert or PoV does not define the full security boundary. P2PATCH grows repair requirements when execution confirms new bypasses and evaluates final patches using independent held-out PoVs. Across 101 C/C++ and Java subjects, it improves held-out coverage over single-pass repair and finds distinct bypasses after original PoVs are blocked.
Problem
Repair systems often reuse construction evidence to judge success, although individual alerts, PoVs, and tests do not specify the full security boundary.
Source: §1 · p. 1Method
P2PATCH makes each execution-confirmed same-vulnerability bypass a permanent repair requirement and evaluates final patches with separate held-out PoV suites.
Source: §1 · p. 2, §3.1 · p. 5, §4 · p. 6Results
Held-out fix-closed coverage rises from 78.1% to 84.7% and beyond-upstream coverage from 42.1% to 62.5% versus single-pass repair from the same finding.
Source: §1 · p. 2Takeaways & Limitations
Under the same held-out oracles, P2PATCH exposes patches accepted by prior validation that leave certified attack paths open.
Source: §1 · p. 2P2PATCH offers bounded testing rather than proof: its exploiter is budgeted, and held-out suites contain human-authored paths rather than the full input space.
Source: §7 · p. 12
Abstract
from arXiv · showhide
Large language models are increasingly deployed as autonomous agents for automated program repair, patching software vulnerabilities through multi-step reasoning and tool use. Yet these systems typically validate a patch against the same evidence used to construct it -- a static alert, sanitizer trace, published exploit, or test suite. A patch that blocks that one piece of evidence can therefore look successful while remaining vulnerable to the same vulnerability with some variation. We present P2Patch, a generative adversarial repair system that treats each patch as a new attack target. Starting from a normalized vulnerability finding, an exploitation agent constructs a reproducing proof of vulnerability (PoV), a patching agent repairs the program, and the exploitation agent then attacks the patched program for a distinct same-vulnerability exploit. Every successful exploit becomes a permanent repair requirement, and the final patch must block all PoVs accumulated during the patching process, with construction-time PoVs kept strictly separate from held-out evaluation oracles. Across 101 C/C++ and Java CVE subjects, this adversarial loop surfaces a distinct confirmed exploit in 41% of runs after the patch has already blocked its original construction-time PoV. Against single-pass repair from the same finding using Claude Code, P2Patch raises held-out fix-closed coverage from 78.1% to 84.7% and beyond-upstream coverage from 42.1% to 62.5%. Under the same held-out oracles, it also certifies more attack paths as blocked than recent state-of-the-art agentic repair systems on overlapping subjects. These results show that adversarial testing and independent security oracles expose repair gaps that one-shot validation misses.
1 Introduction
Static alerts, PoVs, and tests can motivate repairs without defining the full security boundary, and reusing construction evidence can make incomplete patches appear successful. P2PATCH adapts repair requirements to confirmed bypasses and evaluates final patches with separate held-out oracles; on 101 C/C++ and Java subjects, it improves held-out coverage over single-pass repair.
1 Introduction
- Static alerts and individual PoVs identify suspicious flows or failing executions, but do not specify every payload, entry point, or sibling path a complete repair should block.Reusing the same evidence for construction and validation risks accepting a patch that specializes to that evidence.Source: §1 · p. 1
- Unlike systems with a fixed repair objective, P2PATCH treats a distinct same-vulnerability exploit against the current patch as new evidence and a permanent repair requirement.The exploiter constructs a reproducing PoV, the patcher repairs the program, and the exploiter then attacks the patched program.Source: §1 · pp. 1–2
- An execution-mediated orchestrator runs PoVs, distinguishes reproduction, blocking, and inconclusive outcomes, checks regressions, protects role-specific artifacts, and replays accumulated PoVs.Agents propose patches and PoVs, but do not certify success.Source: §1 · p. 2
- P2PATCH keeps construction-time PoVs separate from held-out evaluation oracles, which independently measure final patch coverage.Fix-closed PoVs measure held-out attack-path coverage; residual PoVs measure hardening beyond the official fix.Source: §1 · p. 2
- P2PATCH raises held-out fix-closed coverage from 78.1% to 84.7% and beyond-upstream coverage from 42.1% to 62.5% versus single-pass repair from the same finding.Across 101 C/C++ and Java CVE subjects, it finds a distinct execution-confirmed bypass in 41% of runs after blocking the original PoV.Source: §1 · p. 2
2 Motivation and Problem Setting
The task is to turn partial vulnerability findings into executable repair requirements and assess security with evidence independent of construction. The plexus-utils example shows how a patch can stop the reported path yet leave a sibling path open.
2 Motivation and Problem Setting
- P2PATCH targets reported vulnerabilities in pinned C/C++ and Java revisions, using normalized findings and project execution contracts while withholding upstream fixes and evaluation PoVs.The setup assumes the finding describes the target vulnerability and the revision can be built and exercised under the project contract.Source: §2 · p. 2
THE VULNERABILITY
- In plexus-utils, the 2016 check blocks ../ traversal above the extraction directory but misses a sibling path whose name extends that directory’s name.String.startsWith compares characters, not path components, and the check omits a trailing separator.Source: THE VULNERABILITY · p. 3, THE BYPASS — A SIBLING, NOT A DESCENDANT · p. 3
THE SECOND FIX, 2025
- The later fix canonicalizes both paths and adds a separator boundary, rejecting the sibling while allowing genuine descendants.The separator makes the protected directory path an actual component boundary rather than a character prefix.Source: THE BYPASS — A SIBLING, NOT A DESCENDANT · p. 3, THE SECOND FIX, 2025 · p. 3
2.2 From Findings to Repair Requirements
- A proof of vulnerability (PoV) turns a finding into an executable predicate, but demonstrates only one path, payload, and environment.A valid PoV must exercise a real product entry point and observe the relevant security effect; inconclusive execution is not evidence of blocking.Source: §2.2 · p. 4
2.3 Growing Objective and Scope
- When execution confirms a distinct same-vulnerability bypass, it becomes a persistent repair requirement, potentially covering a different payload, encoding, entry point, or sibling path.The search is bounded: finding no counterexample does not prove that no bypass exists.Source: §2.3 · p. 4
2.4 Threat Model and Non-Goals
- The evaluation assumes a buildable, exercisable revision and observable vulnerability effect; regression checks establish compatibility only for the behaviors they exercise.The system also does not claim host containment against a malicious repository, and pretraining knowledge cannot be eliminated by its leakage controls.Source: §2.4 · p. 4
3 Counterexample-Guided Repair Protocol
P2PATCH makes vulnerability repair an execution-refereed loop: it bootstraps a reproducing PoV, patches accumulated requirements, and searches the patched program for confirmed bypasses. Confirmed PoVs remain obligations, while execution—not agent claims—determines outcomes.
3 Counterexample-Guided Repair Protocol
- The protocol makes a finding executable, patches the current requirements, attacks the patched program for a same-vulnerability bypass, and repeats only when execution confirms one.The protocol is a bounded repair process over a changing executable program.Source: §3 · p. 4, Figure 2 · p. 5
3.1 Protocol State and Invariants
- Each execution-confirmed live PoV remains a repair obligation, and the append-only requirement set does not establish completeness because final coverage is measured separately.The orchestrator decides reproduction, blocking, regression outcomes, and final replay through execution.Source: §3.1 · pp. 4–5
3.2 Bootstrap: Making the Finding Executable
- Bootstrap accepts a PoV only when it reproduces on the pinned vulnerable revision; otherwise, the system returns a structured failure rather than asking the patcher to repair an unexecuted claim.The patcher receives the finding, PoV, source tree, and execution feedback, but not the CVE identifier, upstream patch, advisory exploit text, or held-out PoVs.Source: §3.2 · p. 5
3.3 Patching Current Requirements
- A candidate patch must block the protected PoVs and pass differential regression checks; a patch that fails replay of an earlier bypass is rejected without another correction attempt.The per-round gate checks the newest bypass with the bootstrap PoV, and earlier confirmed bypasses are replayed after hardening.Source: §3.3 · pp. 5–6
3.4 Adversarial Hardening
- After a patch passes its current gate, the exploiter searches it for a distinct same-vulnerability bypass, which joins the requirements if execution confirms it.The loop has a fixed round limit, so finding no additional bypass before the budget expires is not proof of vulnerability absence.Source: §3.4 · p. 6
3.5 Execution Referee
- The orchestrator distinguishes reproduced, blocked, and inconclusive executions; inconclusive outcomes receive no security credit.Bootstrap requires reproduction, while patch convergence requires all protected PoVs to be blocked and regression checks to pass.Source: §3.5 · p. 6
3.6 Artifact Integrity and Implementation
- Role-specific guards prevent the exploiter from weakening product code and the patcher from altering protected PoVs; the Python runner records run artifacts and disables web retrieval.Build metadata supplies project-specific toolchains and commands as ecosystem adapters rather than language-specific repair logic.Source: §3.6 · p. 6
4 Independent Security Oracles
P2PATCH separates live PoVs used to construct a patch from independently certified, held-out suites used to score it. The suites measure both paths the official fix closes and candidate gaps it leaves open.
4 Independent Security Oracles
- Held-out PoV suites are finalized before scoring and never shown to agents, so a patch can pass every live gate yet still fail paths unavailable during repair.The suites check behavior under the project execution contract, not complete semantic proofs.Source: §4 · pp. 6–7
4.1 Fix-Closed Oracles
- Fix-closed PoVs reproduce on the vulnerable revision and are blocked by the official fix, measuring whether a generated patch covers independently constructed paths that fix closes.Evaluation is behavioral, not a syntactic comparison with the upstream patch.Source: §4.1 · p. 7
4.2 Residual Oracles
- Residual PoVs reproduce on both the vulnerable and officially fixed revisions, identifying candidate gaps that appear to survive the recorded fix.Later upstream commits closing the same behavior provide additional evidence of security relevance but are not required for inclusion.Source: §4.2 · p. 7
4.3 Coverage and Leakage Control
- Coverage uses only conclusive executions, while held-out suites are mounted after repair and agents cannot inspect them, although pretraining knowledge cannot be ruled out.Inconclusive outcomes are excluded from the denominator and receive no security credit.Source: §4.3 · p. 7
5 Experimental Setup
The experimental setup compares repair configurations under shared subjects, harness controls, and held-out oracles. VULNREPAIRBENCH supplies 101 scored CVE subjects, with both fix-closed suites and residual suites where the official fix leaves a demonstrated gap.
Internal configurations
- The evaluation varies whether repair uses no executable PoV, a bootstrap PoV, or accumulated confirmed bypasses, while holding subjects, findings, contracts, and held-out suites constant.The full P2PATCH configuration uses four hardening rounds.Source: §5 · pp. 7–8
Patch acceptance and manual review
- Manual reviewers assess patches only after automated gates, using a fixed rubric while blinded to the model and configuration; held-out oracles do not influence acceptance.Reviewers adjudicate disagreements jointly.Source: §5 · p. 8
Benchmark
- VULNREPAIRBENCH contains 101 CVEs across 61 repositories and 20 weakness classes; all subjects have fix-closed suites, and 40 also have residual suites where official fixes leave demonstrated gaps.Source: Table 1 · p. 8, §5 · p. 8
Published baselines
- Published repair systems are rescored on overlapping subjects with the same held-out suites, measuring paths their original validation may not have tested rather than claiming they failed their original criteria.The comparisons include SAN2PATCH, PATCHAGENT, and LoopRepair where artifacts or shared subjects are available.Source: §5 · p. 8
Models and cost
- The main comparisons use Claude Haiku 4.5, and the study also runs the full configuration on three unrelated model families.Configurations share the Claude Code harness, pinned model settings, applicable budgets, and held-out suites; the main hardening limit is four rounds.Source: §5 · pp. 8–9
Metrics and tests
- Macro coverage averages per-subject coverage over conclusive PoVs, and subjects without an accepted patch receive zero in paired comparisons.Primary tests use exact Wilcoxon signed-rank tests on per-subject deltas for Cfix and Cres, with Holm adjustment within primary and language-family groups.Source: §5 · p. 9
6 Evaluation
The evaluation tests whether adversarial hardening finds bypasses, improves held-out security coverage over single-pass repair, and generalizes across models and published systems.
6.1 Bypasses After Accepted Repair (RQ1)
- 41 of 101 runs (41%) produced a distinct, execution-confirmed bypass after the patch blocked its bootstrap PoV; the exploiter found 68 bypasses total.The reported rate is an upper bound on semantically distinct bypasses because semantic novelty is prompted but not machine-checked.Source: §6.1 · p. 9
6.2 Held-Out Coverage and Cost (RQ2)
- 98 of 101 subjects yielded accepted repairs; full-protocol mean cost was $2.09 per subject versus $0.45 for SINGLEPASS.Acceptance required a build, blocking every live PoV, passing differential regression checks, and surviving manual review.Source: §6.2 · p. 10
- 0.781→0.847 fix-closed coverage across 101 subjects and 0.421→0.625 beyond-upstream coverage across 40 residual subjects; both primary tests survive Holm adjustment.These are macro-averaged held-out coverage results under intention-to-treat scoring.Source: Table 2 · p. 9, §6.2 · p. 10
6.3 Attributing the Gains (RQ3)
- +0.038 fix-closed-path coverage and +0.154 residual-path coverage came from adversarial hardening; both loop gains were statistically detectable.The loop step had p = 0.0020 and p = 0.0156, respectively; Table 3 reports attribution deltas relative to the preceding row.Source: §6.3 · p. 10, Table 3 · p. 11
- The bootstrap-PoV contribution was detectable on neither oracle, while the loop improved 10 subjects on Cfix and 7 on Cres without lowering coverage.Most residual benefit arrived in the first two hardening rounds, with diminishing returns afterward.Source: §6.3 · p. 10
6.4 Model Dependence (RQ4)
- Across four models, bypass rates were 47%, 41%, 35%, and 31%; GLM 5.2 led the sweep with Cfix = 0.921 and Cres = 0.795.The bypass result was not specific to one of the four tested model families.Source: §6.4 · pp. 10–11, Table 4 · p. 11
6.5 Published Baselines (RQ5)
- P2PATCH had higher Cfix and Cres in every pairwise comparison on shared subjects; its largest fix-closed separation was +0.605 against LoopRepair.Residual gains ranged from +0.454 to +0.500 across published systems; these comparisons are not a global ranking because subject sets and artifacts differ.Source: §6.5 · p. 11, Table 5 · p. 12
7 Discussion and Limitations
P2PATCH’s evaluation is bounded by finite, human-authored attack suites and a budgeted exploiter, so it measures tested hardening rather than proving patch completeness. The authors also qualify oracle curation, published-system comparisons, and possible model memorization.
Limitations
- A stable run is a testing result, not proof: the exploiter is budgeted, live PoVs are finite, and held-out suites do not cover the full input space.The suites contain human-authored attack paths; the final patch is assessed against those certified suites.Source: §7 · p. 12
Oracle curation
- Held-out suites may omit relevant paths; later upstream fixes corroborate 14 residual gaps, but execution confirmed closure for only 8.Confirming the remaining cases is future work.Source: §7 · p. 12
Published-system comparison
- Rescoring published patches measures coverage under shared certified oracles, not a universal ranking, because systems differ in modality, protocol, budget, maturity, and validation policy.The comparison is intended to show gaps that independent oracles expose, not to claim prior systems failed their original criteria.Source: §7 · p. 12
Model memorization
- Pretraining exposure to public CVEs, fixes, or exploits cannot be excluded and may inflate absolute coverage across configurations.Redacting identifiers and public materials reduces prompt leakage but cannot remove knowledge already encoded in a model.Source: §7 · p. 12
8 Related Work
Prior vulnerability-repair work uses varied evidence and feedback, while P2PATCH changes the repair target as exploits are found. The related work also distinguishes exploit generation, validation, and benchmark choices that shape what repairs are measured.
Automated vulnerability repair
- Recent agentic repair systems use code, warnings, traces, or reproduction artifacts and iterate on compiler, test, sanitizer, or reviewer feedback [26].Earlier approaches include learning- and analysis-based repair, as well as systems using concrete failures or vulnerability witnesses.Source: §8 · pp. 12–13
What repair loops optimize
- Unlike loops that search for a patch against a fixed target, P2PATCH makes the patched program the next attack target and adds each confirmed bypass as a repair requirement.Its exploiter is budgeted rather than a complete verifier.Source: §8 · p. 13
Exploit and PoV generation
Patch validation and overfitting
- Blocking one PoV or passing functional tests does not establish the security boundary; P2PATCH separates construction-time PoVs from held-out evaluation suites [72] [58] [60].Official-fix-based evaluations can leave paths open when the official fix itself does not close them [60] [72].Source: §8 · p. 13
9 Conclusion
P2PATCH grows its repair objective when execution confirms a bypass and evaluates patches with independent oracles, while remaining a bounded testing method. The paper also describes dual-use safeguards, artifact withholding, and a bounded orchestration protocol.
9 Conclusion
- 0.781 to 0.847 fix-closed coverage and 0.421 to 0.625 residual coverage were achieved by P2PATCH relative to single-pass repair from the same finding.Across 101 C/C++ and Java subjects, accepted patches were bypassed in 41% of runs; published-system patches also left attack paths open under the shared certified oracles.Source: §9 · p. 13
A Ethical Considerations
- The evaluation uses pinned historical revisions and excludes live-service scanning; residual PoVs can indicate paths left open by an official fix, so open artifacts are withheld pending a fix.The authors state that a residual PoV establishes reproducibility under the benchmark contract, not exploitability in every deployment.Source: A Ethical Considerations · p. 19
B Open Science and Artifact Release
- The released artifact includes orchestration code, prompts, scoring scripts, pinned revisions, containers, and certified PoV suites, but withholds 18 of 40 residual suites and 4 fix-closed suites that exercise withheld paths.The withheld suites contain 30 of 66 residual PoVs and 16 of 324 fix-closed PoVs.Source: B Open Science and Artifact Release · p. 19
C Protocol and Orchestration Details
- The evaluation protocol uses 3 attacker attempts, 3 gate evaluations per convergence call, and 4 adversarial rounds unless otherwise stated; failed gates or replay reject the repair.The appendix describes the control flow as including bootstrap, patch convergence, adversarial hardening, and post-hardening replay.Source: C Protocol and Orchestration Details · p. 19
D Benchmark and Oracle Construction
The benchmark combines pinned, reproducible subjects with independently authored held-out PoVs certified against vulnerable and official-fixed revisions. The appendix also records the bounded orchestration protocol and the scope of its comparison with prior systems.
D Benchmark and Oracle Construction
- The bounded protocol takes a pinned vulnerable revision, normalized finding, and budgets, and returns a hardened program with requirements or a rejected repair; the orchestrator controls transitions through execution.The protocol records execution outcomes as REPRO, BLOCKED, or INCON, and rejects runs with a failure, agent crash, or refusal.Source: D Benchmark and Oracle Construction · p. 20
- 101 of 138 authored findings reached a reproducible subject and certified fix-closed suite; 40 of those subjects also have residual suites where the official fix leaves a demonstrated path open.A fix-closed PoV reproduces on the vulnerable revision and is blocked by the official fix; a residual PoV reproduces on both revisions.Source: D Benchmark and Oracle Construction · p. 20
E Comparison with Prior Repair Systems
- Table 10 reports shared-subject held-out outcomes and Figure 5 relates outcomes to repair cost for four systems; Table 11 compares repair-loop targets and feedback.The appendix identifies these as empirical and conceptual comparisons, respectively.Source: E Comparison with Prior Repair Systems · p. 20
E.1 Empirical Re-Scoring Details
The subsection makes prior-system comparisons auditable by re-scoring available patches under shared held-out oracles and reporting outcomes case by case. Its cost–coverage view is diagnostic, not the primary claim, and reflects several end-to-end differences beyond the hardening loop.
Case-level re-scoring
- Table 10 reports full, partial, or no blocking for each of 41 C/C++ subjects under fix-closed and residual oracle suites.Its symbols distinguish unrepaired patches, inapplicable subjects, and unmeasured cases; unrepaired subjects remain in the paper’s subject set.Source: §E.1 · p. 20
Comparator scope
- Comparator coverage is limited to each system’s benchmark subjects: 33 for SAN2PATCH, 40 for LoopRepair, and 17 for PATCHAGENT.PATCHAGENT’s coreutils gnu19784 case was unmeasured because its functional gate was unusable; it is excluded from the denominator.Source: §E.1 · p. 20
Shared-oracle re-scoring
- Prior systems are re-scored on available patches or rerun artifacts under the same held-out suites, rather than under their original evaluation criteria.Those systems used differing inputs and validation criteria, including crashing inputs and sanitizer traces.Source: §E.1 · p. 20
Benchmark scope
- VULNREPAIRBENCH contains 101 subjects—60 Java and 41 C/C++—with CWE labels and certified fix-closed and residual PoV-suite sizes.A dash indicates no certified residual suite.Source: Table 7 · p. 21
Cost–coverage diagnostic
- Figure 5 contrasts operational cost with strict fix-closed coverage, counting unrepaired subjects as uncovered; it diagnoses coverage obtained for extra work, not cheaper repair.The end-to-end comparison also reflects input modality, repair protocol, implementation maturity, and validation policy.Source: §E.1 · p. 21
E.2 Conceptual Comparison
P2PATCH differs from recent iterative repair systems because its repair target can expand when execution confirms a bypass of the current patch. The accompanying comparisons describe round dynamics and per-subject outcomes, while the language breakdown is explicitly exploratory.
E.2 Conceptual Comparison
- Table 8’s language breakdown is a descriptive diagnostic under intention-to-treat scoring, with coverage macro-averaged per subject rather than a separate inferential result.The comparison covers Java and C/C++ subjects.Source: Table 8 · p. 22
- 42% (68/163) is the pooled execution-confirmed bypass rate among runs entering a round, distinct from the 41% run-level rate; Figure 4 also plots held-out coverage by round budget.The round-budget analysis includes subjects measured at every budget and scores runs that shipped nothing as zero.Source: Figure 4 · p. 22, Table 9 · p. 22
- Prior systems iterate over reasoning paths, actions, candidate patches, or failed patches while keeping the success target fixed; P2PATCH adds each execution-confirmed bypass as a repair requirement.The empirical re-scoring concerns prior patches under held-out oracles, while the conceptual comparison explains how P2PATCH’s target can change after a patch is accepted.Source: §E.2 · p. 22
- Figure 5 plots operational cost against strict fix-closed coverage, defined as the fraction of subjects blocking every certified path.P2PATCH points use all 41 subjects, while published systems use their measurable shared-subject sets; cost is mean spend per actual run.Source: Figure 5 · p. 22
F Per-Subject Outcomes
- Tables 12 and 13 report outcomes for all 101 subjects—60 Java and 41 C/C++—and include P2PATCH’s three unrepaired subjects as zero-coverage cases.Their aggregates can be checked against the Section 6 results and sum to Table 2.Source: F Per-Subject Outcomes · p. 22
G Residual Gaps and Upstream History
The authors manually reviewed certified residual gaps against upstream history to assess whether the paths mattered beyond surviving the official fix. Upstream later closed many of those paths, while others remained at head, subject to reachability and timing caveats.
Review scope and figure
- The review settled 37 PoVs across 23 gaps in 19 projects, excluding gaps absent from released trees, unsettled cases, and claims outside the CVE scope.Figure 6 depicts each gap’s duration until upstream closed the path or until August 2026 if it remained open; hollow markers indicate closure without a recorded defect.Source: G Residual Gaps and Upstream History · p. 22, Figure 6 · p. 24
Upstream dispositions
- 14 gaps covering 25 PoVs were later closed upstream on the same paths, with a median detection lead of just over two years and one case reaching nine and a half years.Twelve closing commits or the issues they close name the same defect; the plexus-utils gap was independently assigned CVE-2025-67030.Source: G Residual Gaps and Upstream History · pp. 22–23
- Nine gaps covering 12 PoVs remained at upstream head between one and a half and ten years after the fix, and all nine were reported to their projects.One gap was in a maintained, widely deployed dependency-scanning tool.Source: G Residual Gaps and Upstream History · p. 23
Caveats
- An open gap at upstream head does not itself establish exploitability: reachability from attacker-controlled input must be assessed case by case.Commit-to-commit intervals can differ from release exposure; the antisamy gap appeared in two releases despite only 13 days between commits.Source: G Residual Gaps and Upstream History · p. 23