Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve TA handling #1237

Open
wants to merge 8 commits into
base: main
Choose a base branch
from
Open
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
89 changes: 77 additions & 12 deletions doc/manual/source/trust-anchor.rst
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,20 @@ any other set up that you need to do:
Then run Krill as usual so that it can accessed by ``krillc``, ``krillta``
and the UI.

Optionally, timings can be adjusted by including the following snippet at
the end of your ``krill.conf``:

.. code-block:: text
[ta_timing]
certificate_validity_years = 100
issued_certificate_validity_weeks = 52
issued_certificate_reissue_weeks_before = 26
mft_next_update_weeks = 12
signed_message_validity_days = 14

Make sure that these timings match the ones in the configuration for your
signer, as otherwise unexpected behaviour may occur.

Initialise TA Proxy
-------------------

Expand Down Expand Up @@ -208,11 +222,7 @@ The configuration file must at least contain a setting for the data
directory. Other settings are optional - you only need to change them
if you want to change the default logging and/or use an HSM.

.. NOTE:: At this moment "timing" parameters for the TA are hard coded. Child
CA certificates are signed (and re-signed) with a validity of 52 weeks.
The CRL and MFT next update and MFT EE certificate not after time are
set to 12 weeks after the moment of signing. We may add support for
overriding these values if desired.
.. NOTE::

Example configuration file:

Expand Down Expand Up @@ -271,6 +281,55 @@ Example configuration file:
# support for the TA. This may be implemented in future in which case we would
# also support RPKI Signed TALs for this process.

######################################################################################
# #
# TIMING #
# #
######################################################################################

#
# Include the following section '[timing_config]' if the default TA
# timing settings need to be changed.
#
# !!!!!IMPORTANT!!!!!!
#
# If you include this, make sure that both the TA signer and your Krill
# server where the TA Proxy lives use the same configuration.
#
[timing_config]

# The number of years the TA certificate is valid for. The TA certificate
# is only generated once, so set this value before initialising the TA.
#
### certificate_validity_years = 100,

# The validity time in weeks for certificates issued under the TA. Note
# that these certifcates get re-issued by request of the child before
# they would expire.
#
### issued_certificate_validity_weeks = 52

# The threshold in weeks before expiry of a current issued certificate
# used to determine when a new certificate should be requested.
# The hardcoded minimum is 10% more than the current expiration.
#
### issued_certificate_reissue_weeks_before = 26

# The time before the manifest and CRL expire for objects published by
# the TA. This determines the minimal re-signing frequency needed.
#
### mft_next_update_weeks = 12

# The validity time for signed messages between the online and offline
# TA components (TA Proxy and TA Signer). This determines how fast messages
# need to exchanged between the components.
#
# Note that there is replay protection in addition to this constraint, meaning
# that a message that has been previously processed cannot be applied again,
# even if it's still cryptographically valid.
#
### signed_message_validity_days = 14


Initialise the TA Signer
------------------------
Expand All @@ -284,13 +343,13 @@ Step 1: Get the proxy ID

.. code-block:: bash

krillta proxy id --format json > ./proxy-id.json
krillta proxy --format json id > ./proxy-id.json

Step 2: Get the proxy repo contact

.. code-block:: bash

krillta proxy repo contact --format json >./proxy-repo.json
krillta proxy --format json repo contact >./proxy-repo.json

Step 3: Initialise

Expand All @@ -313,10 +372,10 @@ endpoints for the TA certificate.

.. code-block:: bash

krillta signer init --proxy_id ./proxy-id.json \
--proxy_repository_contact ./proxy-repo.json \
--tal_https <HTTPS URI for TA cert on TAL> \
--tal_rsync <RSYNC URI for TA cert on TAL>
krillta signer init --proxy-id ./proxy-id.json \
--proxy-repository-contact ./proxy-repo.json \
--tal-https <HTTPS URI for TA cert on TAL> \
--tal-rsync <RSYNC URI for TA cert on TAL>


Associate the TA Signer with the Proxy
Expand Down Expand Up @@ -421,12 +480,18 @@ Make a TA Proxy Request
*Note that the ``krillta`` subcommand combination ``proxy signer`` is
used for actions for the ``proxy`` relating to its associated ``signer``.

It might be worth to force all CAs to ask their parents for updated
certificates first. This can be done using:

.. code-block:: bash
krillc bulk refresh

Download the TA Proxy Request
-----------------------------

.. code-block:: bash

krillta proxy signer show-request --format json > ./request.json
krillta proxy --format json signer show-request > ./request.json

.. Note:: the request JSON includes both a readable representation of the
request that is made by the ``proxy`` for the ``signer``, and a
Expand Down
7 changes: 7 additions & 0 deletions src/daemon/ca/keys.rs
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,8 @@ impl CertifiedKey {
|| (remaining_seconds_on_eligible as f64
/ remaining_seconds_on_current as f64)
> 1.1_f64
|| (remaining_seconds_on_eligible
- remaining_seconds_on_current >= 604_800)
{
info!(
"Will request new certificate for CA '{}' under RC '{}'. Not after time increased to: {}",
Expand All @@ -184,6 +186,11 @@ impl CertifiedKey {
new_not_after.to_rfc3339()
);
true
} else if self.incoming_cert().resources().contains(&ResourceSet::all()) {
debug!(
"It is technically too early for a new update, but request one anyway since it's the ta"
);
true
} else {
debug!(
"Will not request new certificate for CA '{}' under RC '{}'. Remaining not after time changed by less than 10%. From: {} To: {}",
Expand Down
34 changes: 32 additions & 2 deletions src/daemon/ca/manager.rs
Original file line number Diff line number Diff line change
Expand Up @@ -471,10 +471,21 @@ impl CaManager {
&self,
actor: &Actor,
) -> KrillResult<TrustAnchorSignedRequest> {
let cas = self.ta_obtain_children().await;

if let Ok(cas) = cas {
for (ca, parent) in cas {
self.ca_sync_parent(&ca, 0, &parent, actor).await?;
}
}

// This is a very ugly solution to ensure that the sync parent
// finishes first.
tokio::time::sleep(tokio::time::Duration::from_millis(100)).await;

let cmd =
TrustAnchorProxyCommand::make_signer_request(&ta_handle(), actor);
let proxy = self.send_ta_proxy_command(cmd).await?;

proxy.get_signer_request(self.config.ta_timing, &self.signer)
}

Expand Down Expand Up @@ -1143,7 +1154,7 @@ impl CaManager {
ResourceClassListResponse::new(vec![entitlements])
})
}?;

Ok(provisioning::Message::list_response(
ca_handle.convert(),
child.convert(),
Expand Down Expand Up @@ -1288,6 +1299,7 @@ impl CaManager {
request,
actor,
);

self.send_ta_proxy_command(cmd).await?;

provisioning::Message::not_performed_response(
Expand Down Expand Up @@ -1479,6 +1491,24 @@ impl CaManager {
}
}

async fn ta_obtain_children(
&self
) -> KrillResult<Vec<(CaHandle, ParentHandle)>> {
let mut children = vec![];
if let Ok(cas) = self.ca_store.list() {
for ca_handle in cas {
if let Ok(ca) = self.get_ca(&ca_handle).await {
for parent in ca.parents() {
if parent.as_str() == TA_NAME {
children.push((ca_handle.clone(), parent.clone()));
}
}
}
}
}
Ok(children)
}

/// Synchronizes a CA with its parents - up to the configures batch size.
/// Remaining parents will be done in a future run.
async fn ca_schedule_sync_parents(
Expand Down
10 changes: 10 additions & 0 deletions src/daemon/mq.rs
Original file line number Diff line number Diff line change
Expand Up @@ -346,6 +346,16 @@ impl TaskQueue {
self.q.finish_running_task(task).map_err(Error::from)
}

/// Check whether a task still exists in execution
pub fn finished(&self, task_name: &str) -> KrillResult<bool> {
for key in self.q.running_tasks_keys()? {
if key.name().as_str().ends_with(task_name) {
return Ok(false);
}
}
Ok(true)
}

/// Reschedule a running task, without finishing it.
pub fn reschedule(
&self,
Expand Down
2 changes: 1 addition & 1 deletion src/ta/common.rs
Original file line number Diff line number Diff line change
Expand Up @@ -723,7 +723,7 @@ impl fmt::Display for TrustAnchorSignerResponse {
}
}
writeln!(f)?;
writeln!(f, "NOTE: use the json format for the proxy.")?;
writeln!(f, "NOTE: use the JSON format for the proxy.")?;

Ok(())
}
Expand Down
Loading