Browse Source

Rewrite the crypto keys abstraction

Until now, the crypto key abstraction used two different type: PublicKey
and PrivateKey. Unfortunately, it does not work with ring and should
therefore be rewrote with a single type: KeyPair.
pull/5/head
Rodolphe Breard 6 years ago
parent
commit
70df290306
  1. 2
      acme_common/src/crypto.rs
  2. 37
      acme_common/src/crypto/openssl_certificate.rs
  3. 89
      acme_common/src/crypto/openssl_keys.rs
  4. 8
      acmed/src/acme_proto.rs
  5. 24
      acmed/src/acme_proto/account.rs
  6. 20
      acmed/src/acme_proto/certificate.rs
  7. 20
      acmed/src/acme_proto/jws.rs
  8. 12
      acmed/src/acme_proto/jws/algorithms.rs
  9. 14
      acmed/src/acme_proto/structs/authorization.rs
  10. 39
      acmed/src/storage.rs
  11. 6
      tacd/src/openssl_server.rs

2
acme_common/src/crypto.rs

@ -19,4 +19,4 @@ pub use openssl_hash::sha256;
#[cfg(feature = "standalone")]
pub use standalone_hash::sha256;
pub use openssl_keys::{gen_keypair, KeyType, PrivateKey, PublicKey};
pub use openssl_keys::{gen_keypair, KeyPair, KeyType};

37
acme_common/src/crypto/openssl_certificate.rs

@ -1,4 +1,4 @@
use super::{gen_keypair, KeyType, PrivateKey, PublicKey};
use super::{gen_keypair, KeyPair, KeyType};
use crate::b64_encode;
use crate::error::Error;
use openssl::asn1::Asn1Time;
@ -22,13 +22,9 @@ pub struct Csr {
}
impl Csr {
pub fn new(
pub_key: &PublicKey,
priv_key: &PrivateKey,
domains: &[String],
) -> Result<Self, Error> {
pub fn new(key_pair: &KeyPair, domains: &[String]) -> Result<Self, Error> {
let mut builder = X509ReqBuilder::new()?;
builder.set_pubkey(&pub_key.inner_key)?;
builder.set_pubkey(&key_pair.inner_key)?;
let ctx = builder.x509v3_context(None);
let mut san = SubjectAlternativeName::new();
for dns in domains.iter() {
@ -38,7 +34,7 @@ impl Csr {
let mut ext_stack = Stack::new()?;
ext_stack.push(san)?;
builder.add_extensions(&ext_stack)?;
builder.sign(&priv_key.inner_key, MessageDigest::sha256())?;
builder.sign(&key_pair.inner_key, MessageDigest::sha256())?;
Ok(Csr {
inner_csr: builder.build(),
})
@ -62,17 +58,11 @@ impl X509Certificate {
})
}
pub fn from_acme_ext(domain: &str, acme_ext: &str) -> Result<(PrivateKey, Self), Error> {
let (pub_key, priv_key) = gen_keypair(KeyType::EcdsaP256)?;
let inner_cert = gen_certificate(domain, &pub_key, &priv_key, acme_ext)?;
pub fn from_acme_ext(domain: &str, acme_ext: &str) -> Result<(KeyPair, Self), Error> {
let key_pair = gen_keypair(KeyType::EcdsaP256)?;
let inner_cert = gen_certificate(domain, &key_pair, acme_ext)?;
let cert = X509Certificate { inner_cert };
Ok((priv_key, cert))
}
pub fn public_key(&self) -> Result<PublicKey, Error> {
let raw_key = self.inner_cert.public_key()?.public_key_to_pem()?;
let pub_key = PublicKey::from_pem(&raw_key)?;
Ok(pub_key)
Ok((key_pair, cert))
}
pub fn not_after(&self) -> Result<time::Tm, Error> {
@ -93,12 +83,7 @@ impl X509Certificate {
}
}
fn gen_certificate(
domain: &str,
public_key: &PublicKey,
private_key: &PrivateKey,
acme_ext: &str,
) -> Result<X509, Error> {
fn gen_certificate(domain: &str, key_pair: &KeyPair, acme_ext: &str) -> Result<X509, Error> {
let mut x509_name = X509NameBuilder::new()?;
x509_name.append_entry_by_text("O", APP_ORG)?;
let ca_name = format!("{} TLS-ALPN-01 Authority", APP_NAME);
@ -115,7 +100,7 @@ fn gen_certificate(
builder.set_serial_number(&serial_number)?;
builder.set_subject_name(&x509_name)?;
builder.set_issuer_name(&x509_name)?;
builder.set_pubkey(&public_key.inner_key)?;
builder.set_pubkey(&key_pair.inner_key)?;
let not_before = Asn1Time::days_from_now(0)?;
builder.set_not_before(&not_before)?;
let not_after = Asn1Time::days_from_now(CRT_NB_DAYS_VALIDITY)?;
@ -138,7 +123,7 @@ fn gen_certificate(
builder
.append_extension(acme_ext)
.map_err(|_| Error::from(INVALID_EXT_MSG))?;
builder.sign(&private_key.inner_key, MessageDigest::sha256())?;
builder.sign(&key_pair.inner_key, MessageDigest::sha256())?;
let cert = builder.build();
Ok(cert)
}

89
acme_common/src/crypto/openssl_keys.rs

@ -4,7 +4,7 @@ use openssl::bn::{BigNum, BigNumContext};
use openssl::ec::{EcGroup, EcKey};
use openssl::ecdsa::EcdsaSig;
use openssl::nid::Nid;
use openssl::pkey::{Id, PKey, Private, Public};
use openssl::pkey::{Id, PKey, Private};
use openssl::rsa::Rsa;
use serde_json::json;
use std::fmt;
@ -36,10 +36,10 @@ macro_rules! get_key_type {
#[derive(Clone, Copy, Debug)]
pub enum KeyType {
Rsa2048,
Rsa4096,
EcdsaP256,
EcdsaP384,
Rsa2048,
Rsa4096,
}
impl FromStr for KeyType {
@ -47,10 +47,10 @@ impl FromStr for KeyType {
fn from_str(s: &str) -> Result<Self, Error> {
match s.to_lowercase().as_str() {
"rsa2048" => Ok(KeyType::Rsa2048),
"rsa4096" => Ok(KeyType::Rsa4096),
"ecdsa_p256" => Ok(KeyType::EcdsaP256),
"ecdsa_p384" => Ok(KeyType::EcdsaP384),
"rsa2048" => Ok(KeyType::Rsa2048),
"rsa4096" => Ok(KeyType::Rsa4096),
_ => Err(format!("{}: unknown algorithm.", s).into()),
}
}
@ -59,56 +59,40 @@ impl FromStr for KeyType {
impl fmt::Display for KeyType {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let s = match self {
KeyType::Rsa2048 => "rsa2048",
KeyType::Rsa4096 => "rsa4096",
KeyType::EcdsaP256 => "ecdsa-p256",
KeyType::EcdsaP384 => "ecdsa-p384",
KeyType::Rsa2048 => "rsa2048",
KeyType::Rsa4096 => "rsa4096",
};
write!(f, "{}", s)
}
}
pub struct PublicKey {
pub key_type: KeyType,
pub inner_key: PKey<Public>,
}
impl PublicKey {
pub fn from_pem(pem_data: &[u8]) -> Result<Self, Error> {
let inner_key = PKey::public_key_from_pem(pem_data)?;
let key_type = get_key_type!(inner_key);
Ok(PublicKey {
key_type,
inner_key,
})
}
pub fn to_pem(&self) -> Result<Vec<u8>, Error> {
self.inner_key.public_key_to_pem().map_err(Error::from)
}
}
pub struct PrivateKey {
pub struct KeyPair {
pub key_type: KeyType,
pub inner_key: PKey<Private>,
}
impl PrivateKey {
impl KeyPair {
pub fn from_pem(pem_data: &[u8]) -> Result<Self, Error> {
let inner_key = PKey::private_key_from_pem(pem_data)?;
let key_type = get_key_type!(inner_key);
Ok(PrivateKey {
Ok(KeyPair {
key_type,
inner_key,
})
}
pub fn to_pem(&self) -> Result<Vec<u8>, Error> {
pub fn private_key_to_pem(&self) -> Result<Vec<u8>, Error> {
self.inner_key
.private_key_to_pem_pkcs8()
.map_err(Error::from)
}
pub fn public_key_to_pem(&self) -> Result<Vec<u8>, Error> {
self.inner_key.public_key_to_pem().map_err(Error::from)
}
pub fn sign(&self, data: &[u8]) -> Result<Vec<u8>, Error> {
match self.key_type {
KeyType::Rsa2048 | KeyType::Rsa4096 => {
@ -177,45 +161,32 @@ impl PrivateKey {
}
}
fn gen_rsa_pair(nb_bits: u32) -> Result<(PKey<Public>, PKey<Private>), Error> {
let priv_key = Rsa::generate(nb_bits).unwrap();
let pub_key = Rsa::from_public_components(
priv_key.n().to_owned().unwrap(),
priv_key.e().to_owned().unwrap(),
)
.unwrap();
Ok((
PKey::from_rsa(pub_key).unwrap(),
PKey::from_rsa(priv_key).unwrap(),
))
fn gen_rsa_pair(nb_bits: u32) -> Result<PKey<Private>, Error> {
// TODO: check if map_err is required
let priv_key = Rsa::generate(nb_bits).map_err(|_| Error::from(""))?;
let pk = PKey::from_rsa(priv_key).map_err(|_| Error::from(""))?;
Ok(pk)
}
fn gen_ec_pair(nid: Nid) -> Result<(PKey<Public>, PKey<Private>), Error> {
let group = EcGroup::from_curve_name(nid).unwrap();
let ec_priv_key = EcKey::generate(&group).unwrap();
let public_key_point = ec_priv_key.public_key();
let ec_pub_key = EcKey::from_public_key(&group, public_key_point).unwrap();
Ok((
PKey::from_ec_key(ec_pub_key).unwrap(),
PKey::from_ec_key(ec_priv_key).unwrap(),
))
fn gen_ec_pair(nid: Nid) -> Result<PKey<Private>, Error> {
// TODO: check if map_err is required
let group = EcGroup::from_curve_name(nid).map_err(|_| Error::from(""))?;
let ec_priv_key = EcKey::generate(&group).map_err(|_| Error::from(""))?;
let pk = PKey::from_ec_key(ec_priv_key).map_err(|_| Error::from(""))?;
Ok(pk)
}
pub fn gen_keypair(key_type: KeyType) -> Result<(PublicKey, PrivateKey), Error> {
let (pub_key, priv_key) = match key_type {
pub fn gen_keypair(key_type: KeyType) -> Result<KeyPair, Error> {
let priv_key = match key_type {
KeyType::Rsa2048 => gen_rsa_pair(2048),
KeyType::Rsa4096 => gen_rsa_pair(4096),
KeyType::EcdsaP256 => gen_ec_pair(Nid::X9_62_PRIME256V1),
KeyType::EcdsaP384 => gen_ec_pair(Nid::SECP384R1),
}
.map_err(|_| Error::from(format!("Unable to generate a {} key pair.", key_type)))?;
let pub_key = PublicKey {
key_type,
inner_key: pub_key,
};
let priv_key = PrivateKey {
let key_pair = KeyPair {
key_type,
inner_key: priv_key,
};
Ok((pub_key, priv_key))
Ok(key_pair)
}

8
acmed/src/acme_proto.rs

@ -58,7 +58,7 @@ impl PartialEq<structs::Challenge> for Challenge {
macro_rules! set_data_builder {
($account: ident, $data: expr, $url: expr) => {
|n: &str| encode_kid(&$account.priv_key, &$account.account_url, $data, &$url, n)
|n: &str| encode_kid(&$account.key_pair, &$account.account_url, $data, &$url, n)
};
}
macro_rules! set_empty_data_builder {
@ -124,7 +124,7 @@ pub fn request_certificate(cert: &Certificate, root_certs: &[String]) -> Result<
let current_challenge = cert.get_domain_challenge(&auth.identifier.value)?;
for challenge in auth.challenges.iter() {
if current_challenge == *challenge {
let proof = challenge.get_proof(&account.priv_key)?;
let proof = challenge.get_proof(&account.key_pair)?;
let file_name = challenge.get_file_name();
let domain = auth.identifier.value.to_owned();
@ -178,10 +178,10 @@ pub fn request_certificate(cert: &Certificate, root_certs: &[String]) -> Result<
)?;
// 11. Finalize the order by sending the CSR
let (pub_key, priv_key) = certificate::get_key_pair(cert)?;
let key_pair = certificate::get_key_pair(cert)?;
let domains: Vec<String> = cert.domains.iter().map(|e| e.dns.to_owned()).collect();
let csr = json!({
"csr": Csr::new(&pub_key, &priv_key, domains.as_slice())?.to_der_base64()?,
"csr": Csr::new(&key_pair, domains.as_slice())?.to_der_base64()?,
});
let csr = csr.to_string();
let data_builder = set_data_builder!(account, csr.as_bytes(), order.finalize);

24
acmed/src/acme_proto/account.rs

@ -4,13 +4,12 @@ use crate::acme_proto::jws::encode_jwk;
use crate::acme_proto::structs::{Account, AccountResponse, Directory};
use crate::certificate::Certificate;
use crate::storage;
use acme_common::crypto::{PrivateKey, PublicKey};
use acme_common::crypto::KeyPair;
use acme_common::error::Error;
use std::str::FromStr;
pub struct AccountManager {
pub pub_key: PublicKey,
pub priv_key: PrivateKey,
pub key_pair: KeyPair,
pub account_url: String,
pub orders_url: String,
}
@ -23,25 +22,21 @@ impl AccountManager {
root_certs: &[String],
) -> Result<(Self, String), Error> {
// TODO: store the key id (account url)
let (pub_key, priv_key) = if storage::account_files_exists(cert) {
let key_pair = if storage::account_files_exists(cert) {
// TODO: check if the keys are suitable for the specified signature algorithm
// and, if not, initiate a key rollover.
(
storage::get_account_pub_key(cert)?,
storage::get_account_priv_key(cert)?,
)
storage::get_account_keypair(cert)?
} else {
// TODO: allow to change the signature algo
let sign_alg = SignatureAlgorithm::from_str(crate::DEFAULT_JWS_SIGN_ALGO)?;
let (pub_key, priv_key) = sign_alg.gen_key_pair()?;
storage::set_account_priv_key(cert, &priv_key)?;
storage::set_account_pub_key(cert, &pub_key)?;
(pub_key, priv_key)
let key_pair = sign_alg.gen_key_pair()?;
storage::set_account_keypair(cert, &key_pair)?;
key_pair
};
let account = Account::new(cert);
let account = serde_json::to_string(&account)?;
let data_builder =
|n: &str| encode_jwk(&priv_key, account.as_bytes(), &directory.new_account, n);
|n: &str| encode_jwk(&key_pair, account.as_bytes(), &directory.new_account, n);
let (acc_rep, account_url, nonce): (AccountResponse, String, String) = http::get_obj_loc(
cert,
root_certs,
@ -50,8 +45,7 @@ impl AccountManager {
&nonce,
)?;
let ac = AccountManager {
pub_key,
priv_key,
key_pair,
account_url,
orders_url: acc_rep.orders.unwrap_or_default(),
};

20
acmed/src/acme_proto/certificate.rs

@ -1,30 +1,28 @@
use crate::certificate::{Algorithm, Certificate};
use crate::storage;
use acme_common::crypto::{gen_keypair, KeyType, PrivateKey, PublicKey};
use acme_common::crypto::{gen_keypair, KeyPair, KeyType};
use acme_common::error::Error;
fn gen_key_pair(cert: &Certificate) -> Result<(PublicKey, PrivateKey), Error> {
fn gen_key_pair(cert: &Certificate) -> Result<KeyPair, Error> {
let key_type = match cert.algo {
Algorithm::Rsa2048 => KeyType::Rsa2048,
Algorithm::Rsa4096 => KeyType::Rsa4096,
Algorithm::EcdsaP256 => KeyType::EcdsaP256,
Algorithm::EcdsaP384 => KeyType::EcdsaP384,
};
let (pub_key, priv_key) = gen_keypair(key_type)?;
storage::set_priv_key(cert, &priv_key)?;
Ok((pub_key, priv_key))
let key_pair = gen_keypair(key_type)?;
storage::set_keypair(cert, &key_pair)?;
Ok(key_pair)
}
fn read_key_pair(cert: &Certificate) -> Result<(PublicKey, PrivateKey), Error> {
let pub_key = storage::get_pub_key(cert)?;
let priv_key = storage::get_priv_key(cert)?;
Ok((pub_key, priv_key))
fn read_key_pair(cert: &Certificate) -> Result<KeyPair, Error> {
storage::get_keypair(cert)
}
pub fn get_key_pair(cert: &Certificate) -> Result<(PublicKey, PrivateKey), Error> {
pub fn get_key_pair(cert: &Certificate) -> Result<KeyPair, Error> {
if cert.kp_reuse {
match read_key_pair(cert) {
Ok((priv_key, pub_key)) => Ok((priv_key, pub_key)),
Ok(key_pair) => Ok(key_pair),
Err(_) => gen_key_pair(cert),
}
} else {

20
acmed/src/acme_proto/jws.rs

@ -1,6 +1,6 @@
use crate::acme_proto::jws::algorithms::{EdDsaVariant, SignatureAlgorithm};
use acme_common::b64_encode;
use acme_common::crypto::{sha256, PrivateKey};
use acme_common::crypto::{sha256, KeyPair};
use acme_common::error::Error;
use serde::Serialize;
@ -30,12 +30,12 @@ struct JwsProtectedHeaderKid {
url: String,
}
fn get_data(private_key: &PrivateKey, protected: &str, payload: &[u8]) -> Result<String, Error> {
fn get_data(key_pair: &KeyPair, protected: &str, payload: &[u8]) -> Result<String, Error> {
let protected = b64_encode(protected);
let payload = b64_encode(payload);
let signing_input = format!("{}.{}", protected, payload);
let fingerprint = sha256(signing_input.as_bytes());
let signature = private_key.sign(&fingerprint)?;
let signature = key_pair.sign(&fingerprint)?;
let signature = b64_encode(&signature);
let data = JwsData {
protected,
@ -47,30 +47,30 @@ fn get_data(private_key: &PrivateKey, protected: &str, payload: &[u8]) -> Result
}
pub fn encode_jwk(
private_key: &PrivateKey,
key_pair: &KeyPair,
payload: &[u8],
url: &str,
nonce: &str,
) -> Result<String, Error> {
let sign_alg = SignatureAlgorithm::from_pkey(private_key)?;
let sign_alg = SignatureAlgorithm::from_pkey(key_pair)?;
let protected = JwsProtectedHeaderJwk {
alg: sign_alg.to_string(),
jwk: sign_alg.get_jwk(private_key)?,
jwk: sign_alg.get_jwk(key_pair)?,
nonce: nonce.into(),
url: url.into(),
};
let protected = serde_json::to_string(&protected)?;
get_data(private_key, &protected, payload)
get_data(key_pair, &protected, payload)
}
pub fn encode_kid(
private_key: &PrivateKey,
key_pair: &KeyPair,
key_id: &str,
payload: &[u8],
url: &str,
nonce: &str,
) -> Result<String, Error> {
let sign_alg = SignatureAlgorithm::from_pkey(private_key)?;
let sign_alg = SignatureAlgorithm::from_pkey(key_pair)?;
let protected = JwsProtectedHeaderKid {
alg: sign_alg.to_string(),
kid: key_id.to_string(),
@ -78,7 +78,7 @@ pub fn encode_kid(
url: url.into(),
};
let protected = serde_json::to_string(&protected)?;
get_data(private_key, &protected, payload)
get_data(key_pair, &protected, payload)
}
#[cfg(test)]

12
acmed/src/acme_proto/jws/algorithms.rs

@ -1,5 +1,5 @@
use super::jwk::{EdDsaEd25519Jwk, Es256Jwk, Jwk};
use acme_common::crypto::{gen_keypair, KeyType, PrivateKey, PublicKey};
use acme_common::crypto::{gen_keypair, KeyPair, KeyType};
use acme_common::error::Error;
use std::fmt;
use std::str::FromStr;
@ -47,20 +47,20 @@ impl FromStr for SignatureAlgorithm {
}
impl SignatureAlgorithm {
pub fn from_pkey(private_key: &PrivateKey) -> Result<Self, Error> {
match private_key.key_type {
pub fn from_pkey(key_pair: &KeyPair) -> Result<Self, Error> {
match key_pair.key_type {
KeyType::EcdsaP256 => Ok(SignatureAlgorithm::Es256),
t => Err(format!("{}: unsupported key type", t).into()),
}
}
pub fn get_jwk(&self, private_key: &PrivateKey) -> Result<Jwk, Error> {
let (x, y) = private_key.get_nist_ec_coordinates()?;
pub fn get_jwk(&self, key_pair: &KeyPair) -> Result<Jwk, Error> {
let (x, y) = key_pair.get_nist_ec_coordinates()?;
let jwk = Jwk::Es256(Es256Jwk::new(&x, &y));
Ok(jwk)
}
pub fn gen_key_pair(&self) -> Result<(PublicKey, PrivateKey), Error> {
pub fn gen_key_pair(&self) -> Result<KeyPair, Error> {
match self {
SignatureAlgorithm::Es256 => gen_keypair(KeyType::EcdsaP256),
SignatureAlgorithm::EdDsa(EdDsaVariant::Ed25519) => Err("Not implemented".into()),

14
acmed/src/acme_proto/structs/authorization.rs

@ -1,6 +1,6 @@
use crate::acme_proto::structs::{ApiError, HttpApiError, Identifier};
use acme_common::b64_encode;
use acme_common::crypto::{sha256, PrivateKey};
use acme_common::crypto::{sha256, KeyPair};
use acme_common::error::Error;
use serde::Deserialize;
use std::fmt;
@ -92,18 +92,18 @@ impl Challenge {
}
}
pub fn get_proof(&self, private_key: &PrivateKey) -> Result<String, Error> {
pub fn get_proof(&self, key_pair: &KeyPair) -> Result<String, Error> {
match self {
Challenge::Http01(tc) => tc.key_authorization(private_key),
Challenge::Http01(tc) => tc.key_authorization(key_pair),
Challenge::Dns01(tc) => {
let ka = tc.key_authorization(private_key)?;
let ka = tc.key_authorization(key_pair)?;
let a = sha256(ka.as_bytes());
let a = b64_encode(&a);
Ok(a)
}
Challenge::TlsAlpn01(tc) => {
let acme_ext_name = format!("{}.{}", ACME_OID, ID_PE_ACME_ID);
let ka = tc.key_authorization(private_key)?;
let ka = tc.key_authorization(key_pair)?;
let proof = sha256(ka.as_bytes());
let proof_str = proof
.iter()
@ -154,8 +154,8 @@ pub struct TokenChallenge {
}
impl TokenChallenge {
fn key_authorization(&self, private_key: &PrivateKey) -> Result<String, Error> {
let thumbprint = private_key.get_jwk_thumbprint()?;
fn key_authorization(&self, key_pair: &KeyPair) -> Result<String, Error> {
let thumbprint = key_pair.get_jwk_thumbprint()?;
let thumbprint = sha256(thumbprint.as_bytes());
let thumbprint = b64_encode(&thumbprint);
let auth = format!("{}.{}", self.token, thumbprint);

39
acmed/src/storage.rs

@ -2,7 +2,7 @@ use crate::certificate::Certificate;
use crate::config::HookType;
use crate::hooks::{self, FileStorageHookData, HookEnvData};
use acme_common::b64_encode;
use acme_common::crypto::{PrivateKey, PublicKey, X509Certificate};
use acme_common::crypto::{KeyPair, X509Certificate};
use acme_common::error::Error;
use std::collections::HashMap;
use std::fmt;
@ -174,46 +174,33 @@ fn write_file(cert: &Certificate, file_type: FileType, data: &[u8]) -> Result<()
Ok(())
}
pub fn get_account_priv_key(cert: &Certificate) -> Result<PrivateKey, Error> {
pub fn get_account_keypair(cert: &Certificate) -> Result<KeyPair, Error> {
let path = get_file_path(cert, FileType::AccountPrivateKey)?;
let raw_key = read_file(cert, &path)?;
let key = PrivateKey::from_pem(&raw_key)?;
let key = KeyPair::from_pem(&raw_key)?;
Ok(key)
}
pub fn set_account_priv_key(cert: &Certificate, key: &PrivateKey) -> Result<(), Error> {
let data = key.to_pem()?;
write_file(cert, FileType::AccountPrivateKey, &data)
}
pub fn get_account_pub_key(cert: &Certificate) -> Result<PublicKey, Error> {
let path = get_file_path(cert, FileType::AccountPublicKey)?;
let raw_key = read_file(cert, &path)?;
let key = PublicKey::from_pem(&raw_key)?;
Ok(key)
}
pub fn set_account_pub_key(cert: &Certificate, key: &PublicKey) -> Result<(), Error> {
let data = key.to_pem()?;
write_file(cert, FileType::AccountPublicKey, &data)
pub fn set_account_keypair(cert: &Certificate, key_pair: &KeyPair) -> Result<(), Error> {
let pem_pub_key = key_pair.private_key_to_pem()?;
let pem_priv_key = key_pair.public_key_to_pem()?;
write_file(cert, FileType::AccountPublicKey, &pem_priv_key)?;
write_file(cert, FileType::AccountPrivateKey, &pem_pub_key)?;
Ok(())
}
pub fn get_priv_key(cert: &Certificate) -> Result<PrivateKey, Error> {
pub fn get_keypair(cert: &Certificate) -> Result<KeyPair, Error> {
let path = get_file_path(cert, FileType::PrivateKey)?;
let raw_key = read_file(cert, &path)?;
let key = PrivateKey::from_pem(&raw_key)?;
let key = KeyPair::from_pem(&raw_key)?;
Ok(key)
}
pub fn set_priv_key(cert: &Certificate, key: &PrivateKey) -> Result<(), Error> {
let data = key.to_pem()?;
pub fn set_keypair(cert: &Certificate, key_pair: &KeyPair) -> Result<(), Error> {
let data = key_pair.private_key_to_pem()?;
write_file(cert, FileType::PrivateKey, &data)
}
pub fn get_pub_key(cert: &Certificate) -> Result<PublicKey, Error> {
get_certificate(cert)?.public_key()
}
pub fn get_certificate(cert: &Certificate) -> Result<X509Certificate, Error> {
let path = get_file_path(cert, FileType::Certificate)?;
let raw_crt = read_file(cert, &path)?;

6
tacd/src/openssl_server.rs

@ -1,4 +1,4 @@
use acme_common::crypto::{PrivateKey, X509Certificate};
use acme_common::crypto::{KeyPair, X509Certificate};
use acme_common::error::Error;
use log::debug;
use openssl::ssl::{self, AlpnError, SslAcceptor, SslMethod};
@ -32,14 +32,14 @@ macro_rules! listen_and_accept {
pub fn start(
listen_addr: &str,
certificate: &X509Certificate,
private_key: &PrivateKey,
key_pair: &KeyPair,
) -> Result<(), Error> {
let mut acceptor = SslAcceptor::mozilla_intermediate(SslMethod::tls())?;
acceptor.set_alpn_select_callback(|_, client| {
debug!("ALPN negociation");
ssl::select_next_proto(crate::ALPN_ACME_PROTO_NAME, client).ok_or(ALPN_ERROR)
});
acceptor.set_private_key(&private_key.inner_key)?;
acceptor.set_private_key(&key_pair.inner_key)?;
acceptor.set_certificate(&certificate.inner_cert)?;
acceptor.check_private_key()?;
let acceptor = Arc::new(acceptor.build());

Loading…
Cancel
Save