diff options
-rw-r--r-- | lib/leap_cli/commands/ca.rb | 23 |
1 files changed, 23 insertions, 0 deletions
diff --git a/lib/leap_cli/commands/ca.rb b/lib/leap_cli/commands/ca.rb index d5c6240d..3a0786e2 100644 --- a/lib/leap_cli/commands/ca.rb +++ b/lib/leap_cli/commands/ca.rb @@ -215,6 +215,10 @@ module LeapCli; module Commands return true else cert = load_certificate_file([:node_x509_cert, node.name]) + if !created_by_authority?(cert, ca_root) + log :updating, "cert for node '#{node.name}' because it was signed by an old CA root cert." + return true + end if cert.not_after < Time.now.advance(:months => 2) log :updating, "cert for node '#{node.name}' because it will expire soon" return true @@ -246,6 +250,25 @@ module LeapCli; module Commands return false end + def created_by_authority?(cert, ca) + authority_key_id = cert.extensions["authorityKeyIdentifier"].identifier.sub(/^keyid:/, '') + authority_key_id == public_key_id_for_ca(ca) + end + + # calculate the "key id" for a root CA, that matches the value + # Authority Key Identifier in the x509 extensions of a cert. + def public_key_id_for_ca(ca_cert) + @ca_key_ids ||= {} + @ca_key_ids[ca_cert.object_id] ||= begin + pubkey = ca_cert.key_material.public_key + seq = OpenSSL::ASN1::Sequence([ + OpenSSL::ASN1::Integer.new(pubkey.n), + OpenSSL::ASN1::Integer.new(pubkey.e) + ]) + Digest::SHA1.hexdigest(seq.to_der).upcase.scan(/../).join(':') + end + end + def warn_if_commercial_cert_will_soon_expire(node) dns_names_for_node(node).each do |domain| if file_exists?([:commercial_cert, domain]) |