blob: 54a269915cb2b67736f30e76447feac7898a5035 [file] [view]
# SpdmCertStore Implementation Summary
## Completed Implementation
**File Structure Created:**
- `services/spdm/cert-store/src/lib.rs` - Main implementation
- `services/spdm/cert-store/BUILD.bazel` - Bazel build configuration
- `services/spdm/cert-store/Cargo.toml` - Cargo package manifest
- `services/spdm/cert-store/README.md` - Documentation
- Updated `Cargo.toml` workspace members
## Implementation Details
### Constants Defined
```rust
const CERT_CHAIN_PLACEHOLDER_SIZE: usize = 32;
```
### Imported Library Constants
- `SHA384_HASH_SIZE = 48` (from spdm-lib)
- `ECC_P384_SIGNATURE_SIZE = 96` (from spdm-lib)
- `ECDSA_P384_PRIVATE_KEY_SIZE = 48` (from crypto-api)
### Struct Definition
```rust
pub struct Ast1060CertStore {
crypto: CryptoClient,
}
```
### Static Data (Placeholder for Development)
- `SLOT_0_CERT_CHAIN: [u8; 32]` = `[0xAA; 32]`
- `SLOT_0_ROOT_HASH: [u8; 48]` = `[0xBB; 48]`
- `SLOT_0_PRIVATE_KEY: [u8; 48]` = `[0xCC; 48]`
### Trait Implementation: `SpdmCertStore`
#### Implemented Methods
1. **`slot_count() -> u8`**
- Returns: `2`
2. **`is_provisioned(slot_id: u8) -> bool`**
- Returns: `slot_id == 0`
3. **`cert_chain_len(&mut self, asym_algo, slot_id) -> Result<usize>`**
- Validates: slot ID, algorithm, provisioning status
- Returns: `CERT_CHAIN_PLACEHOLDER_SIZE` (32)
4. **`get_cert_chain(&mut self, slot_id, asym_algo, offset, cert_portion) -> Result<usize>`**
- Validates: slot, algorithm, offset
- Copies cert data from static array
- Zero-fills remaining buffer
- Returns: bytes copied
5. **`root_cert_hash(&mut self, slot_id, asym_algo, cert_hash) -> Result<()>`**
- Validates: slot and algorithm
- Copies pre-calculated hash
6. **`sign_hash(&self, slot_id, hash, signature) -> Result<()>`**
- Validates: slot ID
- Calls: `crypto.ecdsa_p384_sign(&SLOT_0_PRIVATE_KEY, hash)`
- Maps: `ClientError` `CertStoreError::PlatformError`
7. **`key_pair_id(&self, slot_id) -> Option<u8>`**
- Returns: `None`
8. **`cert_info(&self, slot_id) -> Option<CertificateInfo>`**
- Returns: `None`
9. **`key_usage_mask(&self, slot_id) -> Option<KeyUsageMask>`**
- Returns: `None`
### Error Handling
| Condition | Error Returned |
|-----------|----------------|
| `slot_id >= 2` | `CertStoreError::InvalidSlotId(slot_id)` |
| `slot_id == 1` | `CertStoreError::CertReadError` |
| `asym_algo != EccP384` | `CertStoreError::UnsupportedHashAlgo` |
| `offset >= cert_len` | `CertStoreError::InvalidOffset` |
| IPC failure | `CertStoreError::PlatformError` |
### Unit Tests Included
`test_slot_count()` - Verifies 2 slots
`test_is_provisioned()` - Slot 0 provisioned, others not
`test_invalid_slot()` - Rejects invalid slot IDs
`test_unprovisioned_slot()` - Rejects slot 1
`test_cert_chain_len()` - Returns correct length
`test_get_cert_chain_full()` - Full chain retrieval
`test_get_cert_chain_with_offset()` - Offset reading
`test_get_cert_chain_zero_fill()` - Zero-fill behavior
`test_get_cert_chain_invalid_offset()` - Offset validation
`test_root_hash_copy()` - Hash retrieval
`test_optional_methods_return_none()` - Optional methods
## Build Configuration
### BUILD.bazel
```python
rust_library(
name = "spdm_cert_store_lib",
srcs = glob(["src/**/*.rs"]),
crate_name = "openprot_spdm_cert_store",
edition = "2024",
visibility = ["//visibility:public"],
deps = [
"//services/crypto/api:crypto_api",
"//services/crypto/client:crypto_client",
"@rust_crates//:spdm-lib",
],
)
```
### Cargo.toml
```toml
[dependencies]
spdm-lib = { git = "https://github.com/9elements/spdm-lib.git", branch = "buildup" }
crypto-client = { path = "../../crypto/client" }
crypto-api = { path = "../../crypto/api" }
```
## Build Notes
The library cannot be built standalone using Bazel due to platform constraints:
- `crypto-client` depends on `pw_kernel/userspace`
- This requires building as part of a full system image with `--platforms=//target/ast1060-evb:ast1060-evb`
This is expected and correct - the library is meant to be used by userspace SPDM applications on the target platform.
## Integration Usage
To use in an SPDM server application:
```rust
use openprot_spdm_cert_store::Ast1060CertStore;
use spdm_lib::cert_store::SpdmCertStore;
// In your SPDM server init code:
let cert_store = Ast1060CertStore::new(handle::CRYPTO);
// Pass to SPDM responder
let responder = SpdmResponder::new(cert_store, ...);
```
## Next Steps
To verify the implementation:
1. **Create SPDM server application** that uses this cert store
2. **Build system image** with the SPDM server:
```bash
bazel build --platforms=//target/ast1060-evb:ast1060-evb \
//target/ast1060-evb/spdm:system_image
```
3. **Run integration tests** in QEMU or on hardware
4. **Test SPDM protocol operations** (GET_DIGESTS, GET_CERTIFICATE, CHALLENGE)
## Production Deployment
Before production use, replace placeholder data:
1. Generate real ECC P-384 key pair
2. Obtain X.509 certificate chain
3. Calculate SHA-384 root hash
4. Update static arrays with `include_bytes!()`
5. Consider secure key storage (OTP/HSM)
## Conformance to Plan
All planned methods implemented
Error handling complete
Unit tests included
Documentation complete
Build configuration correct
Following spdm-lib patterns
IPC integration with crypto service
Placeholder data for development