From 62f94ac6a1404834ac6f0723ef57e25fcd5e67f9 Mon Sep 17 00:00:00 2001 From: Rasmus Dahlberg Date: Sat, 1 Jun 2024 15:35:45 +0200 Subject: Improve terminology and documentation --- README.md | 119 ++++++++++++++++++++++++++++++++------------------------------ 1 file changed, 62 insertions(+), 57 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index ef27a10..bda9f48 100644 --- a/README.md +++ b/README.md @@ -2,83 +2,83 @@ An implementation of a silent Certificate Transparency monitor. -**Status:** drafty prototype, please do not use for anything serious. +## Status + +Drafty prototype, please do not use for anything too serious yet. ## How it works A monitor downloads all certificates from Certificate Transparency logs. This -gives a concise view of which certificates have been issued for what domains. +provides a concise view of which certificates have been issued for what domains. -The monitor is configured to pull legitimately issued certificates from trusted -nodes. Each node packages its legitimate certificates as a single submission. -This submission is then made available for download on a URL via HTTP GET. +The monitor is configured to pull certificates from trusted systems that +legitimately request certificates. The legitimately issued certificates are +typically made available on HTTP(S) URLs that are polled periodically. -To convince the monitor that a submission was generated by a trusted node, a -shared secret is established between the node and the monitor. The node creates -a message authentication code using the shared secret. The monitor verifies it. +To convince the monitor that the file of legitimately issued certificates is +authentic, it is integrity protected using a message authentication code. So, +the monitor and its trusted systems need to be configured with shared secrets. -What makes this setup _silent_ is the fact that the monitor can compute the -difference between any discovered and legitimately issued certificates. If a -certificate is found that no node submitted, only then is an alert printed. +What makes this setup "silent" is that the monitor can compute the difference +between any downloaded and legitimately issued certificates. If a certificate +is found that no trusted system made available, only then an alert is emitted. -## Quick start +See the [silentct design](./docs/design.md) for a lengthier introduction. -### Setup a node +## Quickstart -You will need the `silentct-mac` tool to create submissions that the monitor can -pull. Install: +### Setup a trusted system - $ go install rgdd.se/silentct/cmd/silentct-mac@latest +Install the `silentct-mac` tool. -Locate the node's certificates that are still valid (i.e., not expired) and -prepare a submission for them: + $ go install rgdd.se/silentct/cmd/silentct-mac@latest - $ silentct-mac -n NAME -s SECRET /path/to/chain-1.pem /path/to/chain-2.pem ... +Mark all certificates that have yet to expire as legitimately issued. The below +specifies one certificate chain, but it is possible to list multiple ones. -`NAME` is an arbitrary name of the node. + $ silentct-mac -n example.org -s sikritpassword /etc/letsencrypt/live/example.org/fullchain.pem -`SECRET` is a secret that will only be shared with the monitor. +`-n` sets an arbitrary name of the trusted system. -The output includes the node name, the computed message authentication code, and -the list of certificate chains that was specified. Use the `-o` option if you -prefer to save the output directly to a file rather than getting it on stdout. +`-s` sets a secret that will be shared with the monitor. -Make the generated submission file available on a URL. Typically each node -already serves web content, in which case you can copy it into some directory. +The output includes the name, a message authentication code, and the list of +certificate chains that was specified. Record the output as a file the monitor +can pull, e.g., by saving it in a web root or transferring it to one. Ensure +that this file gets updated each time a new certificate is legitimately issued. +Below is an example that keeps the file up-to-date with `crontab` and `certbot`. -Finally, ensure that anytime the node requests a new certificate to be issued, -then a new submission is generated that replaces or extends the previous one. -For example, if `certbot` is run by `cron`, then that is a good place to hook. + # crontab -l + 35 3 * * * certbot renew --post-hook "silentct-mac -n example.org -s sikritpassword -o /var/www/example.org/silentct/allowlist /etc/letsencrypt/live/example.org/fullchain.pem" -Repeat this setup if there are multiple nodes. +**Note:** the `--post-hook` option can be specified per site in the +`[renewalparams]` section of `/etc/letsencrypt/renewal/example.org.conf`. ### Setup the monitor -Install on the system that will run the monitor: +Install the `silentct-mon` tool: $ go install rgdd.se/silentct/cmd/silentct-mon@latest -Create a monitor policy file in JSON format. Below is an example that looks for -all certificates related to `example.org`, expect for certificates that are -associated with `test.example.org`. You need at least one wildcard to match on. +Create a configuration file. - $ cat policy.json + $ cat config.json { "monitor": [ { "bootstrap_at": "2024-01-01T00:00:00Z", - "wildcard": "example.org", + "suffix": "example.org", "excludes": [ "test" ] } ], - "nodes": [ + "certificate_requesters": [ { - "name": "NODE_NAME", - "secret": "NODE_SECRET", - "url": "SUBMISSION_URL", - "issues": [ + "name": "example.org", + "secret": "sikritpassword", + "location": "https://www.example.org/silentct/allowlist", + "requests": [ "example.org", "www.example.org" ] @@ -86,30 +86,35 @@ associated with `test.example.org`. You need at least one wildcard to match on. ] } -The `excludes` keyword is optional. The `bootstrap_at` keyword is required, and -should be set to the current time of adding the wildcard for monitoring. Any -certificate that expired before the specified bootstrap time will be ignored. +`bootstrap_at` is the time the monitor started looking for certificates that +match `suffix`. The monitor considers a certificate to match iff (i) it expired +after the bootstrap time, and (ii) at least one subject alternative name ends +with the specified suffix without a longer match being available when taking the +optional `excludes` list of subdomains into account. For example, the above +configuration matches `www.example.org` but not `foo.test.example.org`. -Populate the list of nodes based on the names, secrets, and URLs selected during -your setup. Also add the domains each node is allowed to put into certificates. +Each entry in the `"certificate-requesters"` list corresponds to a trusted +system and the domains it requests certificates for. Set `name`, `secret`, +`location` (filename or URL to pull from), and `requests` to match the +configuration of each trusted system. The monitor will refuse to mark a +certificate as legitimate unless the trusted system that requested it had +permission to do so. This adds a layer of separation between trusted systems. -Bootstrap the monitor in a non-existent directory: +### Start the monitor - $ silentct-mon --bootstrap -f policy.json -d /path/to/directory -v INFO - ... +Start the monitor: -Leave the monitor running: + $ silentct-mon -c config.json -d ~/.local/lib/silentct - $ silentct-mon -f policy.json -d /path/to/directory +Use the `--bootstrap` flag when running the monitor for the first time. -Any noteworthy events (like a potentially mis-issued certificate that no node -submitted) will be printed on stdout. If you prefer to get the monitor's output -in a file, use the `-o` option. Please note that it is your job to watch the -output, and/or to hook it up to a notification system like email or similar. +Noteworthy events will be printed on stdout using the NOTICE level. If you +prefer to get the monitor's output in a file, use the `-o` option. -### Further documentation +### Stop the monitor - - A lengthier [introduction](./docs/introduction.md) to the overall design +Stop the monitor gracefully by sending the SIGINT or SIGTERM signals. Nothing +bad will happen on an ungraceful exit (just redundant work on next startup). ## Contact -- cgit v1.2.3