diff --git a/lagrange/INSTRUCTIONS.md b/lagrange/INSTRUCTIONS.md index b9d8bcc..b8a1232 100644 --- a/lagrange/INSTRUCTIONS.md +++ b/lagrange/INSTRUCTIONS.md @@ -1,16 +1,18 @@ # Instructions for Lagrange -Lagrange's trust store is `~/.config/lagrange/trusted.txt` on GNU/Linux systems. +As of v1.6.0 (2021-07-26), Lagrange's trust store is `~/.config/lagrange/trusted.2.txt` on GNU/Linux and BSD systems. -You can replace it with the generated `trusted.txt`, or merge them using the provided script: +You can replace it with the generated `trusted.2.txt`, or merge them using the provided script: ``` # First a test run: -./merge-trust-stores.sh ~/.config/lagrange/trusted.txt +./merge-trust-stores.sh ~/.config/lagrange/trusted.2.txt -# The entries in ~/.config/lagrange/trusted.txt that are not included in the +# The entries in Lagrange's trust store that are not in the # script-generated trust store will appear at the end of the output. # If it looks ok, then run: -./merge-trust-stores.sh ~/.config/lagrange/trusted.txt > ~/.config/lagrange/trusted.txt +./merge-trust-stores.sh ~/.config/lagrange/trusted.2.txt > ~/.config/lagrange/trusted.2.txt ``` + +The script works for both the old `trusted.txt` and the new `trusted.2.txt`. diff --git a/lagrange/generate-trust-store.sh b/lagrange/generate-trust-store.sh index 1cfa8c3..3711f16 100755 --- a/lagrange/generate-trust-store.sh +++ b/lagrange/generate-trust-store.sh @@ -4,15 +4,19 @@ # https://gmi.skyjake.fi/lagrange/ # ## Trust store format ## -# The file "~/.config/lagrange/trusted.txt" is used on GNU/Linux and BSD. +# The file "~/.config/lagrange/trusted.2.txt" is used on GNU/Linux and BSD. # For other platforms, see https://github.com/skyjake/lagrange#user-files -# This file contains one line for each host (ports are not taken into account): -# example.org expiry_timestamp cert:sha256 +# This file contains one line for each host: +# example.org;port expiry_timestamp pubkey:sha256 # IDNs are converted to punycode. # ## Example ## -# $ cat ~/.config/lagrange/trusted.txt -# gemini.circumlunar.space 1759495837 5b4086d6914231f55828c815faae1f10e28b8bd42af6a1e286a711e9b7d78326 +# $ cat ~/.config/lagrange/trusted2.txt +# gemini.circumlunar.space;1965 1759495837 5b4086d6914231f55828c815faae1f10e28b8bd42af6a1e286a711e9b7d78326 +# +# Prior to v1.6.0 (2021-07-26), the file "~/.config/lagrange/trusted.txt" +# was used, with entries in this format: +# example.org expiry_timestamp cert:sha256 set -o errexit # (-e) exit immediately if any command has a non-zero exit status set -o nounset # (-u) don't accept undefined variables @@ -21,10 +25,11 @@ set -o nounset # (-u) don't accept undefined variables # Go where this script is. cd "$(dirname "$0")" || exit -trust_store="trusted.txt" +trust_store1="trusted.txt" +trust_store2="trusted.2.txt" # since v1.6.0 (2021-07-26) -# Remove the old trust store. -rm -f "$trust_store" +# Remove the old trust stores. +rm -f "$trust_store1" "$trust_store2" # Add the "cert_is_not_within_expiry_boundaries" function. . ../expiry-boundaries.sh @@ -39,6 +44,7 @@ for cert_file in ../certs/*; do fi host=$(expr "$cert_file" : '^../certs\/\(.*\)\:[0-9]*\.pem$') + port=$(expr "$cert_file" : '^../certs\/.*\:\([0-9]*\)\.pem$') # Hostname to punycode. host=$(echo "$host" | idn --allow-unassigned) @@ -48,12 +54,20 @@ for cert_file in ../certs/*; do enddate=$(date -d "$enddate" +%s --utc) # Certificate fingerprint - fingerprint=$(echo "$cert" \ + cert_fingerprint=$(echo "$cert" \ | openssl x509 -outform der \ | sha256sum \ | cut -d ' ' -f 1) - echo "$host $enddate $fingerprint" >> "$trust_store" + # Certificate public key (SPKI) fingerprint + pubkey_fingerprint=$(echo "$cert" \ + | openssl x509 -pubkey -noout \ + | openssl pkey -pubin -outform der \ + | sha256sum \ + | cut -d ' ' -f 1) + + echo "$host $enddate $cert_fingerprint" >> "$trust_store1" + echo "$host;$port $enddate $pubkey_fingerprint" >> "$trust_store2" done diff --git a/lagrange/merge-trust-stores.sh b/lagrange/merge-trust-stores.sh index 5f86bc1..243270d 100755 --- a/lagrange/merge-trust-stores.sh +++ b/lagrange/merge-trust-stores.sh @@ -4,15 +4,23 @@ set -o errexit # (-e) exit immediately if any command has a non-zero exit statu set -o nounset # (-u) don't accept undefined variables #set -o xtrace # for debugging -if [ -z "${1:-}" ]; then - >&2 echo "The path to the user's trust store must be provided." - >&2 echo "The default on GNU/Linux is ~/.config/lagrange/trusted.txt" +input="${1:-}" + +if [ -z "$input" ]; then + >&2 echo "The path to Lagrange's trust store must be provided." + >&2 echo "The default on GNU/Linux is ~/.config/lagrange/trusted.2.txt" exit 1 fi dir="$(dirname "$0")" # directory where this script is -trust_store=$(cat "$dir/trusted.txt") # script-generated trust store +# Read the script-generated trust store. +# If input ends with "trusted.txt", then use the old trust store format. +if echo "$input" | grep -q trusted\\.txt$; then + trust_store=$(cat "$dir/trusted.txt") +else + trust_store=$(cat "$dir/trusted.2.txt") +fi # Loop through user's trust store. while read -r line; do @@ -24,7 +32,7 @@ while read -r line; do trust_store="$trust_store\n$line" fi -done < "${1:-}" +done < "$input" # Output to stdout. echo "$trust_store"