A distributed trust system for gemini
2021-03-03
Thoughts about creating an alternative to TOFU or CA system.
Sparked from a discussion on IRC on how to improve status quo and in response to
Your Gemini Browser and Server are Probably Doing Certificates Wrong
TOFU does only bring a single guarantee:
If you've seen that host before, you can be sure it's the same host again.
So how can we strengthen this? One simple option is to just jack into the CA system of the web and use their certificate authorities and the full infrastructure.
But for one not everyone thinks the CA system is trustworthy. Another point is that it increases the bloat of the certificates and thus is also not appealing if we only look at the bandwidth.
My proposed solution is this:
We, the geminauts, create a distributed system of trusted hosts. This is done by consuming files in the following format:
# comment ${DOMAIN_1} ${PUBKEY_1} ${DOMAIN_2} ${PUBKEY_2} ...
Lines consist of the FQDN of the machine (e.g. "kristall.random-projects.net"), followed by a single space character (ASCII 0x20), then followed by a colon (ASCII 0x3A)-separated list of bytes for the public key of the server certificate, then followed by a single LF (ASCII 0x0A). Each entry must be terminated with a LF. Comments are allowed by inserting lines that start with a hash (ASCII 0x23) and are terminated also by a LF.
An example for kristall.random-projects.net:
# This is the host where you can download kristall. kristall.random-projects.net 04:c7:92:de:05:be:0b:45:ce:11:bf:cf:e7:55:cd:3b:7f:c6:b7:ae:24:fe:7a:ce:1d:c8:eb:01:01:a2:ab:3e:ea:75:ac:18:62:ae:57:22:89:3e:72:72:bb:fd:96:97:e5:0f:87:77:c1:8e:d8:02:44:89:43:ad:3a:41:71:c2:7a:02:dd:fc:eb:20:bc:75:0d:f1:10:db:34:cf:ab:8b:af:bf:bc:9b:58:81:9f:f7:5b:d5:43:52:08:d9:c2:68:7a
To use this trust database, a client can fetch these from the local disk, an already trusted gemini server or any other source one can imagine. It is allowed to load multiple of those trust sources and clients should verify that the host entries are both valid and the same in all sources. This allows detecting invalid host entry provided by a bad or outdated trust source.
There can be multiple ways of resolving conflicts:
- Ignore all hosts that conflict
- Resolve the host by "the most common public key wins" (this is only applicable when more than 2 sources are used)
- Resolve the host by prioritising databases and use a "first come, first serve" pattern, ignoring entries in later files
- Resolve by asking the user what to do
What do we gain from this?
- We now have a way to update server signatures by refreshing our trust files
- We can create a distributed set of trusted servers/hosts by serving them over gemini
- We can establish ways of updating those lists, either by hand or using automatic systems (check if the host ip matches the resolved dns entry)
- As this is entirely optional, people can do whatever they want