Key material should have a consistent and safe format
The private keys produced by glome genkey (and the corresponding public keys from glome pubkey) are x25519 keys, i.e. 32 raw octets.
Key Exchange
Dealing with GLOME keys is inconvenient: transferring a public key to another system requires either a direct file transfer (e.g. scp) or an intermediate encoding into the printable range (e.g. base64). SSH keys, for comparison, are PEM encoded and can be easily copied or included in an email. Furthermore, given only the key file it is impossible to determine its nature, which could lead to accidental confusion of private and public keys. In the best case, you just cannot determine whether the 32B file in your home directory created two years ago is a GLOME key or something else.
Encoding Logic
All keys in the spec are hex-encoded, as are the keys in tests and for glome-login. The lack of encoding in the GLOME library causes a proliferation of encoding logic elsewhere, as can be seen by the definition of a decode_hex in glome_test.c, cli/commands.c and login/ui.c. Since parsing and deserialization logic is a common source of security vulnerabilities, it would be better to have one central piece of logic for dealing with encoding that is well tested.
Protocol Variants
The keys do not specify which protocol variant they are to be used with. If the two parties disagree on the variant to be used we would at least expect mismatching tags, while a deliberately introduced confusion by a person-in-the-middle could ostensibly lead to more severe outcomes.
I'd have been great if a) we could've used Tink and b) Tink had a storage format for these kinds of keys. But it's not like that would be in distributions either. https://crypto.stackexchange.com/questions/61777/distinguishing-x25519-public-keys-from-random also does not help us much here. ;-)
I guess I'd personally prefer the PEM encoding, which presumably should not be hard given that we already require OpenSSL?
Having an external PEM file might be easier for key rotation. Also we can use standard openssl tools like:
$ openssl genpkey -algorithm X25519 | openssl pkey -pubout
-----BEGIN PUBLIC KEY-----
MCowBQYDK2VuAyEArBAds6wHyUNsJymjrI9TYC02njCx8nR/NOPB9JHQClU=
-----END PUBLIC KEY-----
$ openssl genpkey -algorithm X25519 | openssl pkey -pubout | openssl asn1parse
0:d=0 hl=2 l= 42 cons: SEQUENCE
2:d=1 hl=2 l= 5 cons: SEQUENCE
4:d=2 hl=2 l= 3 prim: OBJECT :X25519
9:d=1 hl=2 l= 33 prim: BIT STRING
2024 update:
- Public keys at rest have a specified format according to RFD002.
- Private keys are still 32 raw bytes. Storing them as PKCS #8 would allow standard tools to manipulate it and enable passphrase protection.