Skip to main content

Payy CVE-2026-48100

| EUVDEUVD-2026-88359 HIGH
Acceptance of Extraneous Untrusted Data With Trusted Data (CWE-349)
2026-09-28 GitHub_M
8.7
CVSS 4.0 · Vendor: GitHub_M
View

Attack ChainAIDerived

Hypothetical attack flow derived from CVE metadata – not a confirmed exploit chain

  1. Access
    Obtain prover status (allowlist today, stake under whitepaper model)
  2. Delivery
    Take an already-approved block + public validator approval data
  3. Exploit
    Build valid agg_final proof with extra burn message in unchecked tail
  4. Execution
    Submit proof to RollupV1.verifyRollup()
  5. Persist
    Contract parses forged burn as legitimate
  6. Impact
    USDC transferred from rollup contract to attacker

Vulnerability Assessment

Weakness
CWE
ASVS 5.0
V4 - API and Web Service Acceptance of extraneous untrusted data
Exploitation Conditions

Exploitation requires the attacker to be an authorized prover for the Payy rollup. On the current deployment, RollupV1.verifyRollup() is restricted to an existing allowlisted prover, so a public caller cannot submit the malicious proof - this is the primary limiting factor today. The attacker must also possess the ability to construct a valid agg_final proof for an already-approved rollup block and inject an extra burn message into the unchecked tail of the public messages[1000] array, which demands specialized zk-circuit knowledge. The condition broadens to effectively unauthenticated only under the permissionless prover model in the Payy whitepaper (§3.3.2 stake-to-join, §3.3.1 fallback submission by other nodes), where any staked party can register as a prover. Only affects Payy versions prior to 1.3.0.

Impact

This is a genuine, high-severity soundness flaw in a zk-rollup proof system, but its real-world exploitability is heavily gated. The vendor CVSS 4.0 score of 8.7 (VI:H, integrity-only) reflects that a successful attack lets a malicious prover steal USDC directly from the RollupV1 contract - a direct financial-loss/integrity impact, not confidentiality (VC:N) or availability (VA:N). However, the vendor's PR:N (unauthenticated) is misleading for the CURRENT deployment: the description explicitly states verifyRollup() is restricted to an allowlisted prover, so a fresh public caller cannot submit the invalid proof today - that is effectively PR:H right now. PR:N only becomes realistic under the permissionless prover model described in the Payy whitepaper (stake-to-join), which is a future/design condition, not the present state. Verify deployment mode with the vendor before treating this as unauthenticated. No EPSS score, no CISA KEV listing, and no public exploit code are provided - exploitation status is 'no public exploit identified at time of analysis.' Realistic priority is elevated for anyone running or integrating Payy (fund theft, patched), but the combination of prover-allowlist gating, the specialized zk-circuit knowledge needed to craft a malicious agg_final proof, and the tiny deployment footprint means this is a targeted, high-skill issue rather than a mass-exploitation threat.

Exploit ScenarioDerived

An entity that is (or becomes) a registered/allowlisted Payy prover takes an already-approved rollup block and its public validator approval data, then builds a valid agg_final proof while appending an extra burn message into the unchecked tail of the public messages array. When RollupV1.verifyRollup() parses that public input, it treats the injected burn as legitimate and transfers USDC from the rollup contract to the attacker's address. No public exploit code was identified at time of analysis; exploitation requires prover status and deep zk-circuit knowledge.

This Week Schedule remediation this week. Why: HIGH severity (CVSS 7.0-8.9).
Patch available 0.2% exploitation probability (EPSS)

Get an e-mail when this CVE is exploited, patched or re-scored. Free account.

Alert me

AnalysisAIv1 – Sep 28, 2026

Circuit soundness failure in Payy (polybase/payy) prior to 1.3.0 lets an authorized rollup prover smuggle an extra burn message into the public messages[1000] array accepted by RollupV1.verifyRollup(), causing the rollup contract to transfer USDC from the contract to an attacker-controlled recipient. The attacker must be a registered prover with the ability to construct a valid agg_final proof for an already-approved rollup block and to manipulate the unconstrained tail of the public input array, so the assessed vector is authenticated (CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:N/I:H/A:N, integrity-only impact with no confidentiality or availability loss). Exploitability today is further limited because verifyRollup() is restricted to the existing allowlisted prover, but the flaw becomes effectively unauthenticated under the permissionless prover model in the Payy whitepaper (Section 3.3.2 stake-to-join and Section 3.3.1 fallback submission by other nodes). No public exploit code had been identified at time of analysis, and the vendor-released patch is version 1.3.0.

RemediationAI

Upgrade to the vendor-released patch, Payy 1.3.0, which constrains the unused tail of the public messages[1000] array so the public statement is fully derived from the verified inner proofs (advisory: https://github.com/polybase/payy/security/advisories/GHSA-fhxc-63vg-9gwr). Until the upgrade is deployed, keep the verifyRollup() allowlist strictly enforced and do not enable stake-to-join or fallback proof submission as described in Payy whitepaper Sections 3.3.2 and 3.3.1, since that converts this authenticated issue into an effectively permissionless one; the trade-off is reduced liveness and decentralization, but the allowlist is the only barrier preventing a registered prover from draining USDC. Additionally, audit and rotate the current allowlisted prover keys, monitor RollupV1 burn events and USDC transfers out of the rollup contract for unexpected recipients, and consider adding an application-layer sanity check that rejects public inputs whose post-message tail is non-zero as a defense-in-depth measure, accepting that such a check is redundant once the circuit itself is fixed and must not be treated as a substitute for the 1.3.0 upgrade.

Affected VersionsENISA

payy < 1.3.0

Affected Packages

euvd payy fix: 1.3.0

Source: OSV (Open Source Vulnerabilities)

Affects your stack

Affects 1 package in euvd

Checking this CVE against your own stacks and servers is part of the Basic plan and up.

Technical ContextAI · show details

Payy is an Ethereum L2 zk-rollup focused on privacy-preserving, regulatory-compliant transactions; its proving pipeline aggregates inner proofs in a circuit called agg_agg and finalizes them in agg_final before the on-chain verifier RollupV1.verifyRollup() consumes the resulting public inputs. The agg_agg circuit copies the compacted message stream produced by the verified inner proofs into a fixed-size public array declared as messages: [Field; 1000], but it constrains only the populated prefix and never asserts that the unused tail elements are zero. That missing constraint is a proof-system soundness failure: the prover can satisfy the circuit and publish an arbitrary field element in the tail while still presenting a proof whose statement appears to be derived entirely from the verified inner proofs. RollupV1.verifyRollup() then decodes the public messages array as ordinary rollup operations, so a crafted tail element that parses as a burn instruction is executed by the rollup contract as a genuine burn, moving USDC out of the contract. The root-cause class maps to CWE-349, Acceptance of Extraneous Untrusted Data With Trusted Data, because attacker-chosen data is concatenated into a structure the verifier treats as fully authenticated by the proof. The CPE cpe:2.3:a:polybase:payy:*:*:*:*:*:*:*:* covers all Payy releases before 1.3.0.

Know when Payy gets its next vulnerability

  • Watch products and get an email when something new is published
  • Check this CVE against your own stack and servers
  • Exploit and PoC references, threat intelligence from 22 sources

No credit card · 7-day full trial

Severity by source

Vendor (GitHub_M) PRIMARY 8.7 HIGH
CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:H/VA:N/SC:N/SI:N/SA:N
vuln.today AI 6.5 MEDIUM

Requires registered/staked prover status so PR:L not PR:N; the injected-burn logic is deterministic (AC:L); impact is unauthorized fund transfer (I:H) with no confidentiality or availability effect.

3.1 AV:N/AC:L/PR:L/UI:N/S:U/C:N/I:H/A:N
4.0 AV:N/AC:L/AT:N/PR:L/UI:N/VC:N/VI:H/VA:N/SC:N/SI:N/SA:N

Primary rating from Vendor (GitHub_M).

CVSS VectorVendor: GitHub_M

Attack Vector
Network
Attack Complexity
Low
Attack Requirements
None
Privileges Required
None
User Interaction
None
Vulnerable system: Confidentiality
None
Vulnerable system: Integrity
High
Vulnerable system: Availability
None
Subsequent system: Confidentiality
None
Subsequent system: Integrity
None
Subsequent system: Availability
None

Lifecycle Timeline

2
Patch available
Sep 28, 2026 - 18:01 EUVD
CVE Published
Sep 28, 2026 - 16:43 cve.org
HIGH 8.7

DescriptionCVE.org

Payy is an Ethereum L2 zk-rollup for privacy preserving and regulatory compliant transactions. Prior to version 1.3.0, agg_agg forwards the compacted message stream from its inner proofs into a public messages: [Field; 1000] array, but it never checks that the unused tail of the outer array is zero. A registered prover can build a valid agg_final proof for an approved rollup block while inserting an extra burn message after the real messages. RollupV1.verifyRollup() then parses that public input as a normal burn and transfers USDC from the rollup contract to the attacker. This is a severe circuit soundness failure: the proof system accepts a public statement whose messages array is not fully derived from the verified inner proofs. On the current deployment, verifyRollup() is restricted to the existing allowlisted prover, so a fresh public caller cannot submit the invalid proof directly. That gate limits who can reach L1 today; it does not make the circuit statement sound. The issue becomes permissionless under the prover model described in the Payy whitepaper. Section 3.3.2 states: "To join as a prover, the prover is required to submit a small stake", and Section 3.3.1 states that if a prover fails to submit, "other nodes can submit the block proof instead." In that model, an attacker only needs to become a registered prover and use public validator approval data for an already approved block. This issue has been patched in version 1.3.0.

Technical POC Analysis

CWE-349 (Acceptance of Extraneous Untrusted Data With Trusted Data) implemented as a circuit soundness failure in the Noir recursive aggregate circuit payy/noir/aggagg/src/main.nr (loop at lines 53-7…

Full technical POC analysis - root cause, step-by-step exploitation and patch breakdown - is part of the Pro and Business plans.

Executive ViewAI

Why It Matters

Payy rollup contracts prior to 1.3.0 contain a circuit soundness flaw that allows an authorized prover to divert USDC held by the rollup contract to an attacker-controlled recipient, creating a material integrity and financial risk for any deployment relying on RollupV1.verifyRollup(). Because exploitation requires a registered or allowlisted prover today, immediate exposure is limited, but the planned permissionless prover model would broaden the attack surface and make the issue far more dangerous without a vendor patch. Leadership should prioritize determining whether affected Payy versions are in production, tightening prover access, and monitoring for unauthorized USDC outflows.

Business Impact: High
Compensating Controls

No vendor-released patch identified at time of analysis; interim mitigations include restricting RollupV1.verifyRollup() to a tightly controlled, audited allowlist of provers, implementing off-chain/on-chain validation that rejects public input arrays with unexpected tail elements or extra burn messages, adding real-time monitoring and alerting for anomalous USDC transfers and burn events, applying emergency pause/circuit-breaker or transfer timelocks/multisig controls, reducing TVL exposure, and engaging Payy for a patched release.

Threat Intelligence Overview

EPSS Score
0.2%
Top 93% exploitable
Prevalence
Rare
niche privacy-focused Ethereum L2 zk-rollup, tiny production footprint
Data Quality
6 sources
Confidence: High

How this decision was reached

The engine reads each signal below and applies a fixed list of rules from top to bottom. The first rule that matches sets the recommended action – like a statement, every line is shown.

SignalValue
Severity HIGH
CISA KEV No
Public POC No
EPSS 0.2%
Patch available Yes
Active threat No
Deciding rule
HIGH severity (CVSS 7.0-8.9)
What every action level means
Emergency Immediate action required. Criteria: CRITICAL + in CISA KEV (actively exploited) without patch, OR CRITICAL + EPSS > 30% without patch, OR CRITICAL + active threat signals without patch.
Act Now Prioritize within 24-48h. Criteria: in KEV with patch available, OR CRITICAL + public POC, OR HIGH + EPSS > 10%, OR CRITICAL + active threat, OR any CRITICAL severity.
This Week Schedule remediation this week. Criteria: HIGH severity (CVSS 7.0-8.9). Patch within normal change window.
This Month Plan within 30 days. Criteria: MEDIUM severity (CVSS 4.0-6.9), lower exploitation probability. Include in regular patch cycle.
Monitor Track and reassess. Criteria: LOW severity (CVSS 0.1-3.9), minimal exploitation risk. No immediate action needed.

SSVC AssessmentENISA

SSVC Decision
Scheduled
Exploitation
Poc
System Exposure· derived
Open
Automatable
Yes
Human Impact
High
Technical Impact
Partial

Priority Score

44
Low Medium High Critical
KEV: 0
EPSS: 0
CVSS: +44
PoC: 0
Weaponized: 0
Threat intel: 0
Gov advisory: 0

This site uses cookies essential for authentication and security. No tracking or analytics cookies are used. Privacy Policy