$Id: key-management.txt,v 1.10 2005/12/09 22:41:24 droggo Exp $ [This document is deprecated. There have been design modifications since its last update, so information can be inaccurate.] Key management in BPG - BSD Privacy Guard ========================================= 1. Introduction --------------- Key management divides up into several different parts: * Interpreting the key format--basically, being able to read OpenPGP packets containing keys. Covered by sections 4 and 5 of RFC 2440. * Specifying from where we should try to fetch keys, and how we should fetch them. Examples: - Use a keyring in a given format, in some sort of default place (such as defined by the GNUPGHOME environment variable). - Read OpenPGP packets from an arbitrary file - Fetch the key from a keyserver, using a given protocol * Specifying how we search for keys, and what to do when the search does not produce an unambiguous result. E.g., - specify a specific key ID, using that key if only one match is found, or offering the user a choice if more than one match is found - specify a substring to match within a UserID, and use all top-level keys that have a matching UserID. * Specifying how we determine our level of trust in a selected key, what minimum level of trust we require to use the key for the given purpose, and and what to do if we cannot achieve that level of trust (warn? fail?). We'll separate this tasks into several submodules. We'll try to make the things "pluggable," so that code to parse PGP packets and construct the key information doesn't need to know if the key itself came from a file, a keyring or a key server. 2. Submodules ------------- 2.1. Key fetcher It receives petitions for obtaining a key given an ID. Then it uses the other modules to take a decission and return the requested key. 2.2. Key generator This module receives petitions for generating asymmetric and symmetric keys. For symmetric keys the work is pretty simple: it only expands a given password. For asymmetric keys there are more elements that come to scene (read 3.2). 2.3. Key importer/exporter This module receives petitions from the user to take a key from a location A and insert it into location B, where A and B can be files, keyrings or key servers. 2.4. Key interpreter Reads/writes OpenPGP packets containing keys and translates them into/from the internal data structures. 2.5. Key deliverer With no public functions, this module performs the internal checkouts and commits of keys from and to a file, keyring or key server. 3. Internal working ------------------- 3.1. Fetching * The user asks the key fetcher for a key, passing the user ID, the sources to search it (by default, the user keyring) and the minimum accepted level of trust (by default, [FILL THIS]). * The key fetcher asks the key deliverer to find keys with the given user ID and in the given sources. * The key deliverer returns the keys found in a buffer or temporary file, and the number of keys found. * If the number of keys found is zero, the fetcher ends this operation returning a "key not found" error value to the user. * The key fetcher asks the trust library to determine the trust level of found key. * The key fetcher selects the most trusted key. If there are more than one in the highest obtained level, [FILL THIS]. * The key fetcher asks the key interpreter to fill the in-memory data structure of the key. * If interpreter returns a "key locked" error state, ask the user for the passphrase [HOW?]. Then repeat the call to the key interpreter. * The key fetcher returns the key in its data structure, ready to be used with other BPG modules. 3.2. Generation (asymmetric keys) * The user asks the key generator to create a new key pair, passing the algorithm, the size and the location where the key will be stored. * The key generator asks the BPG algorithms library to generate a key pair passing the algorithm and the size. * The key generator fills the in-memory key data structure with the new data. * The key generator encrypts the private key by asking the user for a passphrase [HOW?]. * The key generator asks the key interpreter to translate the in-memory key to a string suitable for being stored. * The key generator asks the key deliverer to store the new key in the given location. * The key generator returns the error state (ok / location not found / unknown algorithm / invalid size / ...). 3.3. Generation (symmetric keys) * The user asks the key generator to create a new key, passing the size of the key and a flag that determines if the key is password-dependent (user-defined keys vs session keys). * If the key is password-dependent, the key generator asks the user for a password [HOW?]. * If the key is not password-dependent, the key generator creates a random session key [HOW? INCLUDE A RANDOM GENERATOR IN THE ALGORITHMS LIBRARY?] * The key generator expands the key. * The key generator returns the key and an error state. 3.4. Importing * The user asks the key importer/exporter to import the key with ID 'x', from location A, and store it location B (by default the user keyring). * It asks the key deliverer to take the key out of the source location. * It asks the key deliverer to insert the key into the destination. * The key importer/exporter returns an error state (ok / key not found / ambiguous ID / source location not found / destination not found / ...). 3.5. Exporting * The user asks the key importer/exporter to export the key with ID 'y', from location C (by default, the user keyring), and store it location D. * It asks the key deliverer to take the key out of the source location. * It asks the key deliverer to insert the key into the destination. * The key importer/exporter returns an error state (ok / key not found / ambiguous ID / source location not found / destination not found / ...). 4. Key storage -------------- [How will the keys be stored in the system.] All the BPG configuration will be placed in the .bpg directory in the home directory of the user. So, user keyrings and trust databases will be stored in this directory. 4.1. Keyrings A keyring is an entity that contains keys. In BPG, a keyring is a directory that contains a list of files, containing one key each [MORE EXPERIENCED REVISORS, PLEASE TELL ME IF THIS IS A GOOD THING]. Public and private keys are separated in public an private keyrings. For example, Alice has three keyrings: * ~/.bpg/keyrings/private/alice, for her private keys. * ~/.bpg/keyrings/public/alice, for her public keys. * ~/.bpg/keyrings/public/world, for alt public keys. [ANOTHER OPTION IS HAVING ONLY TWO KEYRINGS, ONE FOR PRIVATE KEYS AND ANOTHER FOR PUBLIC KEYS, LIKE GPG DOES. IS THERE ANY ADVANTADGE IN ALLOWING MULTIPLE KEYRINGS?.] Then, inside each keyring directory, there will be a bunch of files, named each with the key ID. The name thing just for having a uniform nomenclature, the program must read all the files in the keyring directory (if two keys have the same key ID, which can happen according to OpenPGP, BPG will consider both with no problem, just add a "[2]" or something like that to the key filename). For adding new keys to the keyring we must use the "import" function of the key management library (via the command-line interface or whatever). If the user is more confortable copying the key files directly to the keyring, it's ok. Finally, the private keyrings will have one difference from public ones, and it's that private keys are symmetrically encrypted with a passphrase that the user must enter once he/she wants to use the key. 4.2. Keys Each key inside a keyring is a public or private key packet as defined in OpenPGP. The keys can be signed. 5. Trust model -------------- How much we trust a key is resolved by asking how much we trust the person who signed that key. BPG implements trust via the BPG trust library. That library defines the policy of the trust system. The trust library interacts with the trust database, which contains how much a user trusts another. 5.1. Trust database Trust of the system is stored in the trust database, placed in .bpg/trustdb. This database contains a pair of values, userID - trust level. [WOULD IT BE BETTER TO MAKE THE DATABASE MULTI-USER AND HAVE THREE VALUES PER ROW: SOURCE USER, DESTINATION USER, TRUST LEVEL?] The trust database must be signed by the user that trusts it. This signature will be verified by the trust library each time the database is accesed. The signer's user ID will always be trusted with level "ultimate". TrustDB example: Dst Level --- ----- alice@foo.com high alice@bar.com high bob@yuhuu.com low 5.2. Policy The trust database only stores how much we trust in somebody. But what does this means? How do we define how much we trust *a key* from this information? For this BPG implements the trust policy. The trust policy is a set of rules that defines the trust level of a key depending on how much we trust its signer. Policies are interchangeable. By default, BPG uses the OpenPGP web of trust policy (i.e. if we trust bob@foo.com and we have a key signed by bob@foo.com, we trust that key). Other policies can be implemented in the future, as the X.509 hierarchical trust model. 5.3. A trust query * The user calls the trust library for obtaining the level of trust in the key 0x389A2E82 from bob@foo.com, which is placed on our keyring and signed by trend@trust.com. * The trust library checks the signature of the trust database. * The trust library queries the trust database on how much we trust trend@trust.com. * The trust library processes the response with the trust policy (in this case, OpenPGP policy). * The trust library returns to the user the final level of trust for that key.