runar-keys 0.1.0

Standards-compliant X.509 certificates and ECDSA P-256 key management for Runar
Documentation
### Core Cryptographic Strategy

**Single Algorithm**: ECDSA P-256 throughout the entire system
- All key generation uses ECDSA P-256
- All certificates use ECDSA with SHA-256 signatures
- Unified signature verification across all operations
- Excellent QUIC/TLS compatibility and performance

### Certificate Hierarchy

**Mobile CA Authority Structure**:
```
Mobile User CA (Self-signed root certificate)
└── Node TLS Certificate (signed by Mobile CA)
    └── Used for all QUIC/TLS operations
```

**Certificate Standards**:
- Standard X.509 certificates with proper extensions
- PKCS#10 Certificate Signing Requests (CSRs)
- DER encoding for all certificate storage and transmission
- Full compliance with RFC 5280 and related standards

## Implementation Architecture

### Technology Stack

**Core Libraries**:
- **OpenSSL**: Certificate authority operations and certificate signing
- **rcgen**: Self-signed certificate generation and CSR creation
- **x509-parser**: Certificate parsing and validation
- **rustls-pki-types**: QUIC/TLS compatibility types
- **p256**: ECDSA P-256 cryptographic operations

### Component 1: Mobile Key Manager

**Responsibilities**:
- Generate user root keys and self-signed CA certificate
- Process node CSRs and issue signed X.509 certificates
- Manage user profile and network encryption keys
- Secure communication with nodes through encrypted messages

**Core Operations**:
```rust
pub struct MobileKeyManager {
    ca_key_pair: EcdsaKeyPair,
    ca_certificate: X509Certificate,
    user_keys: HashMap<String, EcdsaKeyPair>,
    network_keys: HashMap<String, EcdsaKeyPair>,
}

impl MobileKeyManager {
    // Initialize with self-signed CA certificate
    pub fn new() -> Result<Self>;
    
    // Process node CSR and issue X.509 certificate
    pub fn process_setup_token(&mut self, setup_token: &SetupToken) -> Result<NodeCertificateMessage>;
    
    // Generate and distribute network keys
    pub fn generate_network_data_key(&mut self, network_id: &str) -> Result<()>;
    pub fn create_network_key_message(&self, network_id: &str, node_id: &str) -> Result<NetworkKeyMessage>;
}
```

### Component 2: Node Key Manager

**Responsibilities**:
- Generate node identity keys and create PKCS#10 CSRs
- Install and validate received certificates
- Provide QUIC-compatible certificate chains
- Handle digital signatures and peer validation

**Core Operations**:
```rust
pub struct NodeKeyManager {
    node_key_pair: EcdsaKeyPair,
    node_certificate: Option<X509Certificate>,
    ca_certificate: Option<X509Certificate>,
    certificate_validator: Option<CertificateValidator>,
    network_keys: HashMap<String, EcdsaKeyPair>,
}

impl NodeKeyManager {
    // Generate proper PKCS#10 CSR for node identity
    pub fn generate_csr(&mut self) -> Result<SetupToken>;
    
    // Install certificate and CA cert from mobile
    pub fn install_certificate(&mut self, cert_message: NodeCertificateMessage) -> Result<()>;
    
    // Get QUIC-compatible certificate configuration
    pub fn get_quic_certificate_config(&self) -> Result<QuicCertificateConfig>;
    
    // Validate peer certificates during QUIC handshake
    pub fn validate_peer_certificate(&self, peer_cert: &X509Certificate) -> Result<()>;
    
    // Digital signature operations
    pub fn sign_data(&self, data: &[u8]) -> Result<Vec<u8>>;
    pub fn verify_peer_signature(&self, data: &[u8], signature: &[u8], peer_cert: &X509Certificate) -> Result<()>;
}
```

### Component 3: Certificate Authority Operations

**Certificate Authority Implementation**:
```rust
pub struct CertificateAuthority {
    ca_key_pair: EcdsaKeyPair,
    ca_certificate: X509Certificate,
}

impl CertificateAuthority {
    // Create CA with self-signed certificate
    pub fn new(subject: &str) -> Result<Self>;
    
    // Sign CSR using OpenSSL to create proper X.509 certificate
    pub fn sign_certificate_request(&self, csr_der: &[u8], validity_days: u32) -> Result<X509Certificate>;
    
    // Get CA certificate for distribution
    pub fn ca_certificate(&self) -> &X509Certificate;
}
```

**Certificate Validation**:
```rust
pub struct CertificateValidator {
    trusted_ca_certificates: Vec<X509Certificate>,
}

impl CertificateValidator {
    // Full cryptographic validation with DN normalization
    pub fn validate_certificate(&self, certificate: &X509Certificate) -> Result<()>;
    
    // Complete certificate chain validation
    pub fn validate_certificate_chain(&self, certificate: &X509Certificate, chain: &[X509Certificate]) -> Result<()>;
    
    // TLS-specific validation
    pub fn validate_for_tls_server(&self, certificate: &X509Certificate) -> Result<()>;
}
```

## Certificate Workflow

### Phase 1: CA Initialization
```mermaid
flowchart TD
    A[Mobile App Start] --> B[Generate ECDSA P-256 Key Pair]
    B --> C[Create Self-signed CA Certificate]
    C --> D[CA Ready to Issue Certificates]
```

### Phase 2: Node Certificate Issuance
```mermaid
sequenceDiagram
    participant M as Mobile CA
    participant N as Node
    
    N->>N: Generate ECDSA key pair
    N->>N: Create PKCS#10 CSR
    N->>M: Send CSR in setup token
    M->>M: Validate CSR
    M->>M: Sign CSR with OpenSSL
    M->>M: Create X.509 certificate
    M->>N: Send certificate + CA cert
    N->>N: Install and validate certificates
    N->>N: Ready for QUIC transport
```

### Phase 3: QUIC Transport Setup
```mermaid
sequenceDiagram
    participant N1 as Node 1
    participant N2 as Node 2
    
    Note over N1,N2: Both nodes have certificates from same CA
    
    N1->>N2: QUIC connection with TLS handshake
    N2->>N2: Validate N1 certificate against CA
    N2->>N1: Send own certificate in response
    N1->>N1: Validate N2 certificate against CA
    
    Note over N1,N2: Secure QUIC transport established
```

## Technical Implementation Details

### OpenSSL Certificate Signing

The certificate authority uses OpenSSL for proper CA operations:

```rust
pub fn sign_certificate_request(&self, csr_der: &[u8], validity_days: u32) -> Result<X509Certificate> {
    // Parse CSR and extract public key
    let req = X509Req::from_der(csr_der)?;
    let req_public_key = req.public_key()?;
    
    // Create certificate builder
    let mut cert_builder = X509Builder::new()?;
    
    // Set the public key from CSR
    cert_builder.set_pubkey(&req_public_key)?;
    cert_builder.set_subject_name(req.subject_name())?;
    cert_builder.set_issuer_name(&self.create_ca_name()?)?;
    
    // Set validity period
    cert_builder.set_not_before(&openssl::asn1::Asn1Time::days_from_now(0)?)?;
    cert_builder.set_not_after(&openssl::asn1::Asn1Time::days_from_now(validity_days)?)?;
    
    // Add X.509v3 extensions for TLS compatibility
    cert_builder.append_extension(
        X509Extension::new_nid(None, None, Nid::KEY_USAGE, "digitalSignature,keyEncipherment")?
    )?;
    cert_builder.append_extension(
        X509Extension::new_nid(None, None, Nid::EXT_KEY_USAGE, "serverAuth,clientAuth")?
    )?;
    
    // Sign with CA private key
    let ca_private_key = self.ca_key_pair_to_openssl_pkey()?;
    cert_builder.sign(&ca_private_key, MessageDigest::sha256())?;
    
    // Return signed certificate
    let cert_der = cert_builder.build().to_der()?;
    X509Certificate::from_der(cert_der)
}
```

### DN Normalization for Certificate Validation

Handles different DN component ordering between certificate sources:

```rust
fn normalize_dn(&self, dn: &str) -> String {
    let mut components = Vec::new();
    for component in dn.split(',') {
        let component = component.trim();
        if !component.is_empty() {
            components.push(component);
        }
    }
    components.sort(); // Normalize component order
    components.join(",")
}

pub fn validate_certificate(&self, certificate: &X509Certificate) -> Result<()> {
    for ca_cert in &self.trusted_ca_certificates {
        // Try exact match first
        if certificate.issuer() == ca_cert.subject() {
            let ca_public_key = ca_cert.public_key()?;
            return certificate.validate(&ca_public_key);
        }
        
        // Handle DN component order differences
        if self.normalize_dn(certificate.issuer()) == self.normalize_dn(ca_cert.subject()) {
            let ca_public_key = ca_cert.public_key()?;
            return certificate.validate(&ca_public_key);
        }
    }
    
    Err(KeyError::ChainValidationError("No trusted CA found for certificate".to_string()))
}
```

### QUIC Integration

Seamless integration with Quinn/rustls:

```rust
pub struct QuicCertificateConfig {
    pub certificate_chain: Vec<CertificateDer<'static>>, // Node cert + CA cert
    pub private_key: PrivateKeyDer<'static>,            // Node private key
    pub certificate_validator: CertificateValidator,     // For peer validation
}

pub fn get_quic_certificate_config(&self) -> Result<QuicCertificateConfig> {
    let node_cert = self.node_certificate.as_ref()
        .ok_or_else(|| KeyError::CertificateNotFound("Node certificate not installed".to_string()))?;
    let ca_cert = self.ca_certificate.as_ref()
        .ok_or_else(|| KeyError::CertificateNotFound("CA certificate not installed".to_string()))?;
    
    let certificate_chain = vec![
        node_cert.to_rustls_certificate(),
        ca_cert.to_rustls_certificate(),
    ];
    
    let private_key = self.node_key_pair.to_rustls_private_key()?;
    let validator = self.certificate_validator.as_ref()
        .ok_or_else(|| KeyError::InvalidOperation("Certificate validator not initialized".to_string()))?;
    
    Ok(QuicCertificateConfig {
        certificate_chain,
        private_key,
        certificate_validator: validator.clone(),
    })
}
```

## Security Features

**Cryptographic Validation**:
- Full signature verification using ECDSA P-256
- Certificate chain validation against trusted CA
- Proper X.509v3 extension validation
- Time-based validity checking

**PKI Security Model**:
- Mobile device acts as trusted root CA
- All node certificates must be signed by Mobile CA
- CSR-based certificate issuance ensures key ownership
- Standard cryptographic implementations (OpenSSL)

**Network Security**:
- Separate network keys for different network contexts
- Encrypted key distribution from Mobile to nodes
- Peer certificate validation during QUIC handshake

## QUIC Transport Compatibility

**Certificate Chain Structure**:
1. **Node Certificate**: End-entity certificate for the specific node
2. **CA Certificate**: Mobile CA certificate for chain validation

**TLS Integration**:
- Standard X.509 certificates work with all TLS implementations
- ECDSA P-256 has excellent performance characteristics
- Proper key usage extensions for TLS server/client operations

**Peer Validation**:
- Automatic certificate validation during QUIC handshake
- DN normalization handles format differences between implementations
- Comprehensive error reporting for debugging

## Data Types and Serialization

**Key Management**:
```rust
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct EcdsaKeyPair {
    signing_key: SigningKey,
    verifying_key: VerifyingKey,
}

#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct X509Certificate {
    der_bytes: Vec<u8>,
    subject: String,
    issuer: String,
}
```

**Message Types**:
```rust
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct SetupToken {
    pub node_id: String,
    pub csr_der: Vec<u8>,
    pub timestamp: u64,
}

#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct NodeCertificateMessage {
    pub node_certificate_der: Vec<u8>,
    pub ca_certificate_der: Vec<u8>,
    pub issue_timestamp: u64,
    pub validity_days: u32,
}

#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct NetworkKeyMessage {
    pub network_id: String,
    pub encrypted_network_key: Vec<u8>,
    pub timestamp: u64,
}
```