Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .jules/sentinel.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
## 2024-08-11 - Use `verify_strict` for Ed25519 signature verification
**Vulnerability:** Signature malleability in Ed25519 signatures due to `verify` instead of `verify_strict`.
**Learning:** `ed25519-dalek` provides a standard `verify` method that doesn't strictly adhere to RFC 8032 requirements for non-malleability, leading to multiple valid signatures for the same message.
**Prevention:** Use `verify_strict` when verifying Ed25519 signatures using `ed25519-dalek` to ensure RFC 8032 compliance.
Comment on lines +1 to +4

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

πŸ”’ Security & Privacy | 🟑 Minor | ⚑ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -eu

printf '%s\n' '--- cited files ---'
for file in .jules/sentinel.md crates/gitlawb-attest/src/attestation.rs crates/gitlawb-core/src/identity.rs; do
  if [ -f "$file" ]; then
    echo "--- $file ---"
    wc -l "$file"
    case "$file" in
      .jules/sentinel.md) sed -n '1,12p' "$file" ;;
      *) sed -n '70,125p' "$file" ;;
    esac
  else
    echo "MISSING: $file"
  fi
done

printf '%s\n' '--- ed25519-dalek declarations ---'
rg -n --glob 'Cargo.toml' --glob 'Cargo.lock' 'ed25519-dalek|verify_strict|verify\(' .

Repository: euxaristia/node

Length of output: 5598


🌐 Web query:

ed25519-dalek verify_strict documentation RFC 8032 ZIP-215 non-RFC 8032 compliant

πŸ’‘ Result:

In the ed25519-dalek library, the verify_strict method is a specialized verification function designed to mitigate specific vulnerabilities, such as weak-key forgery [1][2][3]. It is explicitly documented as being "technically non-RFC 8032 compliant" because it enforces additional checks not mandated by the RFC [4][3]. The primary reasons for this non-compliance and the divergence from RFC 8032 are as follows: RFC 8032 Compliance: RFC 8032 mandates that signature verification must fail if the scalar s is not properly reduced modulo the group order L [4][3]. While ed25519-dalek's verification functions (including verify_strict) perform this check, the RFC also specifies optional malleability checks [4][3]. Strict Verification vs. RFC 8032: The verify_strict method performs extra checksβ€”specifically, it verifies that neither the public key A nor the signature point R are small-order (weak) points [3][5]. These checks are not strictly required by the base RFC 8032 specification but are necessary to prevent "weak-key forgery" attacks, where an attacker crafts a signature that is valid for almost any message [1][2][5]. Relationship to ZIP-215: ZIP-215 was introduced to resolve ambiguities and consensus-critical differences in how various Ed25519 implementations interpret RFC 8032 [6][7]. ZIP-215 mandates the use of a "cofactor-multiplied" verification equation ([8][S]B = [8]R + [8][k]A), whereas RFC 8032 allows an unmultiplied version ([S]B = R + [k]A) [9][6]. Current State in ed25519-dalek: As of the latest documentation, the verify_strict implementation in ed25519-dalek does not fully conform to the ZIP-215 validation criteria [4][3]. Specifically, it historically used the unmultiplied verification equation (without the cofactor) and performed different point encoding checks than those defined in ZIP-215 [9][8]. While there have been ongoing discussions and efforts to implement ZIP-215-compliant verification within the broader curve25519-dalek ecosystem, verify_strict is primarily intended for its original purpose of weak-key resistance rather than serving as a ZIP-215 implementation [9][3][8]. In summary, verify_strict is non-compliant with RFC 8032 because it adds defensive checks against weak-key forgery that the RFC does not enforce, and it currently does not align with the specific cofactor-multiplied verification rules required by ZIP-215 [4][9][3].

Citations:


Describe verify_strict as stricter than RFC 8032.

ed25519-dalek documents verify_strict as technically non-RFC 8032 compliant because it applies additional validation. Update .jules/sentinel.md and both Sentinel comments to describe the repository’s intentional stricter policy for rejecting malleable and weak-key encodings. Keep verify_strict.

πŸ“ Affects 3 files
  • .jules/sentinel.md#L1-L4 (this comment)
  • crates/gitlawb-attest/src/attestation.rs#L114-L115
  • crates/gitlawb-core/src/identity.rs#L82-L84
πŸ€– Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.jules/sentinel.md around lines 1 - 4, Update the Ed25519 verification
documentation to state that verify_strict intentionally applies validation
stricter than RFC 8032, rejecting malleable signatures and weak-key encodings;
keep verify_strict unchanged. Revise the corresponding Sentinel comments in
.jules/sentinel.md, crates/gitlawb-attest/src/attestation.rs (114-115), and
crates/gitlawb-core/src/identity.rs (82-84) consistently.

Source: MCP tools

5 changes: 3 additions & 2 deletions crates/gitlawb-attest/src/attestation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
//! by exact match.

use base64::{engine::general_purpose::URL_SAFE_NO_PAD as B64U, Engine};
use ed25519_dalek::{Signature, Signer, SigningKey, Verifier, VerifyingKey};
use ed25519_dalek::{Signature, Signer, SigningKey, VerifyingKey};
use serde::{de::DeserializeOwned, Deserialize, Serialize};

use crate::error::{Error, Result};
Expand Down Expand Up @@ -111,7 +111,8 @@ impl Attestation {
.try_into()
.map_err(|_| Error::Signature("signature must be 64 bytes".to_string()))?;
let sig = Signature::from_bytes(&sig_bytes);
vk.verify(&bytes, &sig)
// Sentinel: Use verify_strict to prevent signature malleability (RFC 8032 compliance)
vk.verify_strict(&bytes, &sig)
.map_err(|e| Error::Signature(format!("ed25519: {e}")))?;

Ok(vk)
Expand Down
4 changes: 2 additions & 2 deletions crates/gitlawb-core/src/identity.rs
Original file line number Diff line number Diff line change
Expand Up @@ -78,10 +78,10 @@ impl Keypair {

/// Verify an Ed25519 signature.
pub fn verify(verifying_key: &VerifyingKey, msg: &[u8], sig_bytes: &[u8; 64]) -> Result<()> {
use ed25519_dalek::Verifier;
let sig = Signature::from_bytes(sig_bytes);
// Sentinel: Use verify_strict to prevent signature malleability (RFC 8032 compliance)
verifying_key
.verify(msg, &sig)
.verify_strict(msg, &sig)
.map_err(|_| Error::SignatureInvalid)
}

Expand Down
Loading