feat: e3 refund timeout mechanism [skip-line-limit]#1161
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
📝 WalkthroughWalkthroughRenames submission_deadline → committee_deadline across events and readers, replaces startWindow/duration/expiration with inputWindow in E3 APIs, adds E3 lifecycle/enums/events and E3RefundManager with refund/claim logic, and updates many clients, indexer, contracts, tests, and templates to use the new lifecycle, deadlines, and input publication flow. Changes
Sequence Diagram(s)sequenceDiagram
participant Registry as CiphernodeRegistry
participant Enclave as Enclave Contract
participant Indexer as Indexer
participant DB as Repository/DB
participant Refund as E3RefundManager
participant Client as CRISP/SDK
Registry-->>Enclave: emit CommitteePublished(e3Id, nodes, publicKey) (committeeDeadline)
Indexer->>Registry: listen CommitteePublished
Indexer->>Enclave: getE3(e3Id) (read inputWindow, params)
Enclave-->>Indexer: return E3{ inputWindow, requester, params, ... }
Indexer->>DB: create E3 record (use inputWindow[1] as end_time)
Indexer-->>Client: notify/emit session scheduling (schedule processing)
Note over Enclave,Refund: (on failure)
Enclave->>Refund: processE3Failure(e3Id) / markE3Failed(e3Id, reason)
Refund-->>DB: store RefundDistribution
DB-->>Client: allow claims (claimRequesterRefund / claimHonestNodeReward)
Estimated code review effort🎯 5 (Critical) | ⏱️ ~120 minutes Possibly related PRs
Suggested labels
Suggested reviewers
Poem
🚥 Pre-merge checks | ✅ 2 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
6ed3647 to
3b31481
Compare
ctrlc03
left a comment
There was a problem hiding this comment.
Nice work, left some suggestions
00b75af to
c1557ee
Compare
6d5615c to
fea80b5
Compare
When an E3 computation fails - whether the committee never forms, DKG times out, or decryption
fails - there was no way to detect it, refund the requester, or compensate honest nodes for work
they already did. This PR adds that whole infrastructure.
The core idea comes from BlockScience's research, when deciding refunds. If a requester paid for an E3 but the committee failed to decrypt, they shouldn't lose everything - they should get most of it back, minus what honest nodes earned for the
work they completed.
New State Flow
A state machine that tracks every E3 through its stages:
Each stage has a deadline. When a deadline passes without progressing, anyone can call
markE3Failed()to transition the E3 to the Failed state.New
E3RefundManager.solContractHandles the money side. When an E3 fails, this contract:
The work value percentages come from the
WorkValueAllocationconfiguration:The allocation breakdown:
Sequence Diagram
sequenceDiagram autonumber participant R as Requester participant Enc as Enclave participant Reg as CiphernodeRegistry Note over R, Reg: Happy Path: E3 Completes Successfully R->>Enc: request(params, payment) Enc->>Enc: e3Payments[e3Id] = payment Enc->>Enc: _e3Stages[e3Id] = Requested Enc->>Enc: _e3Requesters[e3Id] = msg.sender Enc->>Enc: computeDeadline = inputWindow[1] + computeWindow Enc->>Reg: requestCommittee(e3Id, seed, threshold) Enc-->>R: E3Requested, E3StageChanged(None → Requested) Note over Reg: Committee forms via sortition... Reg->>Enc: onCommitteeFinalized(e3Id) Enc->>Enc: stage = CommitteeFinalized Enc->>Enc: dkgDeadline = now + dkgWindow Enc-->>Reg: CommitteeFinalized, E3StageChanged(Requested → CommitteeFinalized) Note over Reg: DKG completes, key published... Reg->>Enc: onCommitteePublished(e3Id) Enc->>Enc: stage = KeyPublished Enc-->>Reg: CommitteeFormed, E3StageChanged(CommitteeFinalized → KeyPublished) Note over Enc: Inputs submitted during inputWindow, computation runs... Enc->>Enc: publishCiphertextOutput(e3Id, output, proof) Enc->>Enc: stage = CiphertextReady Enc->>Enc: decryptionDeadline = now + decryptionWindow Enc-->>R: CiphertextOutputPublished, E3StageChanged(KeyPublished → CiphertextReady) Enc->>Enc: publishPlaintextOutput(e3Id, plaintext, proof) Enc->>Enc: stage = Complete ✓ Enc->>Enc: _distributeRewards(e3Id) Enc-->>R: PlaintextOutputPublished, E3StageChanged(CiphertextReady → Complete)sequenceDiagram autonumber participant Anyone participant R as Requester participant Enc as Enclave participant Ref as E3RefundManager Note over Anyone, Ref: Failure Path: Timeout Detected rect rgb(255, 230, 230) Note over Enc: Deadline has passed without progress Anyone->>Enc: markE3Failed(e3Id) Enc->>Enc: Check: block.timestamp > deadline? Enc->>Enc: _e3Stages[e3Id] = Failed Enc->>Enc: _e3FailureReasons[e3Id] = reason Enc-->>Anyone: E3Failed(e3Id, stage, reason) end rect rgb(255, 245, 200) Note over Enc: Process the failure Anyone->>Enc: processE3Failure(e3Id) Enc->>Enc: require(_e3Stages[e3Id] == Failed) Enc->>Enc: payment = e3Payments[e3Id] Enc->>Enc: e3Payments[e3Id] = 0 Enc->>Enc: honestNodes = _getHonestNodes(e3Id) Enc->>Ref: transfer(feeToken, payment) Enc->>Ref: calculateRefund(e3Id, payment, honestNodes) Ref->>Ref: workDone = calculateWorkValue(failedStage) Ref->>Ref: requesterAmt = payment × (100% - workDone - 5%) Ref->>Ref: nodeAmt = payment × workDone Ref->>Ref: protocolAmt = payment × 5% Ref->>Ref: transfer(treasury, protocolAmt) Ref-->>Enc: RefundDistributionCalculated end rect rgb(230, 255, 230) Note over R: Claim refunds R->>Ref: claimRequesterRefund(e3Id) Ref->>Ref: Verify caller == requester Ref->>R: transfer(requesterAmt) Ref-->>R: RefundClaimed ✓ endflowchart TD subgraph Stages A[None] --> B[Requested] B --> C[CommitteeFinalized] C --> D[KeyPublished] D --> E[CiphertextReady] E --> F[Complete ✓] end subgraph Failures B -.->|committeeDeadline passed| X[Failed] C -.->|dkgDeadline passed| X D -.->|computeDeadline passed| X E -.->|decryptionDeadline passed| X end style F fill:#90EE90 style X fill:#FFB6C1Summary by CodeRabbit
New Features
Improvements