-
Notifications
You must be signed in to change notification settings - Fork 0
feat: derive signing key from kms #346
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
Summary of ChangesHello @hanakannzashi, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed! This pull request significantly refactors the Highlights
Using Gemini Code AssistThe full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips. Invoking Gemini You can request assistance from Gemini at any point by creating a comment using either
Customization To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a Limitations & Feedback Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here. You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension. Footnotes
|
Code Review - PR #346I've reviewed this PR which refactors the AttestationService to derive cryptographic keys from dstack/KMS. Here are my findings:
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Code Review
This pull request introduces a significant security and stability improvement by refactoring the AttestationService to derive signing keys from a Key Management Service (dstack) instead of generating ephemeral keys on startup. This ensures key stability across service instances. The implementation correctly uses HKDF for key derivation and includes a sensible fallback to ephemeral keys if derivation fails. The code is well-structured, includes appropriate logging, and the changes are sound. I have one minor suggestion to improve code conciseness.
| let normalized_info: Vec<u8> = if ctr == 0 { | ||
| GATEWAY_KEY_INFO_ECDSA.to_vec() | ||
| } else { | ||
| // Include counter in info to get different output for each retry attempt | ||
| let mut info = Vec::with_capacity(GATEWAY_KEY_INFO_ECDSA.len() + 2); | ||
| info.extend_from_slice(GATEWAY_KEY_INFO_ECDSA); | ||
| info.extend_from_slice(&ctr.to_be_bytes()); | ||
| info | ||
| }; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For improved readability and conciseness, the creation of normalized_info can be simplified. The else block can be replaced with a call to concat(), which achieves the same result with less code while maintaining similar performance characteristics for this non-hot path.
let normalized_info: Vec<u8> = if ctr == 0 {
GATEWAY_KEY_INFO_ECDSA.to_vec()
} else {
// Include counter in info to get different output for each retry attempt
[GATEWAY_KEY_INFO_ECDSA, &ctr.to_be_bytes()].concat()
};There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull request overview
This PR refactors the AttestationService to derive cryptographic signing keys from dstack KMS instead of generating ephemeral keys on each service startup. This ensures stable signing addresses across multiple instances of the same application running in TEE environments.
Key changes:
- Changed
AttestationService::new()toAttestationService::init()(async) to support key derivation - Implemented HKDF-based key derivation from dstack KMS for both Ed25519 and ECDSA signing keys
- Added graceful fallback to ephemeral keys in DEV mode when dstack is unavailable
- Refactored nonce generation code to use
unwrap_or_elsepattern for better readability
Reviewed changes
Copilot reviewed 3 out of 4 changed files in this pull request and generated 4 comments.
| File | Description |
|---|---|
| crates/services/src/attestation/mod.rs | Core refactoring: added init() method with dstack key derivation, HKDF-based key generation, and fallback logic. Includes helper methods for key derivation and ephemeral key generation. Minor refactoring of nonce generation using unwrap_or_else. |
| crates/services/Cargo.toml | Added hkdf = "0.12" dependency for secure key derivation |
| crates/api/src/lib.rs | Updated call site to use async init() method instead of new() |
| Cargo.lock | Updated lockfile with hkdf dependency |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
…refactor/use-key-from-kms
|
@claude review |
Code ReviewCritical Issues Found1. Production Safety: Unwrap in Service Initialization (CRITICAL)Location: crates/api/src/lib.rs:294-302 The .unwrap() will panic and crash the server during startup if init() returns an error in production (non-DEV) environments when dstack is unavailable. This violates the production safety requirement for multi-cluster deployments. Impact: Complete service outage during rolling updates or infrastructure issues. Fix: Properly propagate the error instead of unwrapping. The init_domain_services_with_pool function should return Result and propagate this error up the call chain. 2. Cryptographic Security: Ed25519 All-Zeros Key Check is InsufficientLocation: crates/services/src/attestation/mod.rs:145-150 Ed25519 has other weak keys beyond all-zeros. The check only validates against one failure mode. While HKDF-SHA256 output should be cryptographically random, relying solely on an all-zeros check is insufficient. Recommendation: Either remove the check entirely and trust HKDF cryptographic properties (preferred), or add comprehensive validation using ed25519-dalek key validation APIs. 3. Code Quality: Inconsistent Counter InitializationLocation: crates/services/src/attestation/mod.rs Both ed25519 and ECDSA derivation loops always include counter=0 in the first derivation. Clarification needed: Should the first derivation attempt use an empty counter (for reproducibility) and only add counters for retries? 4. Performance: Unnecessary Allocation in Derivation LoopLocation: crates/services/src/attestation/mod.rs:140-145, 170-175 Allocates a new Vec on every iteration. Fix: Reuse the buffer by declaring it before the loop and using clear() inside. Strengths
SummaryMUST FIX before merge: Issue 1 (unwrap removal) SHOULD FIX: Issues 2, 3, 4 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This PR is being reviewed by Cursor Bugbot
Details
Your team is on the Bugbot Free tier. On this plan, Bugbot will review limited PRs each billing cycle for each member of your team.
To receive Bugbot reviews on all of your PRs, visit the Cursor dashboard to activate Pro and start your 14-day free trial.
|
We can switch to the build-in |
| return Err(AttestationError::InternalError(format!( | ||
| "Failed to derive signing keys from dstack: {}. \ | ||
| Ensure this service runs in a CVM/TEE with dstack available.", | ||
| e |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It should be fine to keep the errors in response and logs because the signing keys failed to generate. The error details is helpful to understand why the keys fail to create.
Fix #309
Note
Introduces TEE/KMS-backed signing keys and async initialization for attestation.
AttestationService::newwith asyncinitthat loads VPC info and derives ed25519/secp256k1 keys from dstack; falls back to ephemeral keys only inDEVand errors otherwisecrates/api/src/lib.rsto awaitAttestationService::initget_attestation_reportWritten by Cursor Bugbot for commit d6880c8. This will update automatically on new commits. Configure here.