.. _mail_crypt_plugin: ================= mail-crypt-plugin ================= Introduction ============ The Mail crypt plugin is used to secure email messages stored in a Dovecot system. Messages are encrypted before written to storage and decrypted after reading. Both operations are transparent to the user. In case of unauthorized access to the storage backend, the messages will, without access to the decryption keys, be unreadable to the offending party. There can be a single encryption key for the whole system or each user can have a key of their own. The used cryptographical methods are widely used standards and keys are stored in portable formats, when possible. Functional Overview ------------------- The use of Mail crypt plugin depends on a user having a keypair, a private and a public key, for asymmetric cryptography. These keys are provisioned in a variable via the user database or directly from Dovecot configuration files. The public half of the provisioned keypairs are used to generate and encrypt keys for symmetric encryption. The symmetric keys are used to encrypt and decrypt individual files. Symmetric encryption is faster and more suitable for block mode storage encryption. The symmetric key used to encrypt a file is stored, after being encrypted with the public asymmetric key, together with the file. Encryption Technologies ----------------------- The Mail crypt plugin provides encryption at rest for emails. Encryption of the messages is performed using the symmetric Advanced Encryption Standard (AES) algorithm in Galois/Counter Mode (GCM) with 256 bit keys. Integrity of the data is ensured using Authenticated Encryption with Associated Data (AEAD) with SHA256 hashing. The encryption keys for the symmetric encryption are randomly generated. These keys in turn are encrypted using a key derived with from the provisioned private key. Provisioned private keys can be Elliptic Curve (EC) keys or RSA Encryption is done using the Integrated Encryption Scheme (IES). This algorithm is usable both with EC and RSA keys. Technical Requirements ====================== .. versionadded:: v2.2.27 Using per-folder keys is not considered production quality, but global keys are fine. .. Note:: Improper configuration or use can make your emails unrecoverable. Treat encryption with care and backups. This page assumes you are using configuring mail encryption from scratch with a recent version of Dovecot. If you are upgrading from an older version, see :dovecot_plugin:ref:`mail_crypt_save_version` for possible backwards compatibility issues. Settings ======== See :ref:`plugin-mail-crypt`. Plugin settings may also be dynamically set via :ref:`authentication-user_database_extra_fields`. To provide :dovecot_plugin:ref:`mail_crypt_global_private_key` and :dovecot_plugin:ref:`mail_crypt_global_public_key` as userdb attributes, you can base64 encode the original contents, such as PEM file. For example, .. code-block:: none cat ecprivkey.pem | base64 -w0 All external keys must be in PEM format, using pkey format. Modes Of Operation ================== Mail crypt plugin can operate using **either** global keys or folder keys. Using both is not supported. To perform any encryption, :dovecot_plugin:ref:`mail_crypt_save_version` must be specified and non-zero. Folder Keys ----------- In this mode, the user is generated a key pair, and each folder is generated a key pair, which is encrypted using the user's key pair. A user can have more than one key pair but only one can be active. :dovecot_plugin:ref:`mail_crypt_save_version` must be ``2``. :dovecot_plugin:ref:`mail_crypt_curve` must be set. :dovecot_core:ref:`mail_attribute_dict` must be set, as is is used to store the keys. Unencrypted User Keys ^^^^^^^^^^^^^^^^^^^^^ In this version of the folder keys mode, the users private key is stored unencrypted on the server. Example config for folder keys with Maildir: .. code-block:: none mail_attribute_dict = file:%h/Maildir/dovecot-attributes mail_plugins = $mail_plugins mail_crypt plugin { mail_crypt_curve = secp521r1 mail_crypt_save_version = 2 } Encrypted User Keys ^^^^^^^^^^^^^^^^^^^ In this version of the folder keys mode, the users private key is stored encrypted on the server. Example config for mandatory encrypted folder keys with Maildir: .. code-block:: none mail_attribute_dict = file:%h/Maildir/dovecot-attributes mail_plugins = $mail_plugins mail_crypt plugin { mail_crypt_curve = secp521r1 mail_crypt_save_version = 2 mail_crypt_require_encrypted_user_key = yes } The password that is used to decrypt the users master/private key, must be provided via password query: .. code-block:: none # File: /etc/dovecot/dovecot-sql.conf.ext password_query = SELECT \ email as user, password, \ '%w' AS userdb_mail_crypt_private_password \ FROM virtual_users WHERE email='%u'; Choosing encryption key ----------------------- DO NOT use password directly. It can contain % which is interpreted as variable expansion and can cause errors. Also, it might be visible in debug logging. Suggested approaches are base64 encoding, hex encoding or hashing the password. With hashing, you get the extra benefit that password won't be directly visible in logs. Another issue that you must consider when using user's password is that when the password changes, *you must* re-encrypt the user private key. Global keys =========== In this mode, all keying material is taken from plugin environment. You can use either Elliptic Curve (EC) keys (recommended) or RSA keys. No key generation is automatically performed. A good solution for environments where no user folder sharing is needed is to generate per-user EC key pair and encrypt that with something derived from user's password. The benefit is that it can be easier to do key management when you can do the EC re-encryption steps in case of password change in your user database instead of dovecot's database. You should not configure :dovecot_plugin:ref:`mail_crypt_curve` when using global keys. RSA key ------- .. note:: Use of RSA keys is discouraged, please use :ref:`mail_crypt_plugin_elliptic_curve_key` instead. You can generate an unencrypted RSA private key in the pkey format with the command: .. code-block:: none openssl genpkey -algorithm RSA -out rsaprivkey.pem Alternatively, you can generate a password encrypted private key with: .. code-block:: none openssl genpkey -algorithm RSA -out rsaprivkey.pem -aes-128-cbc -pass pass:qwerty This does make the password show up in the process listing, so it can be visible for everyone on the system. Regardless of whether you generated an unencrypted or password encrypted private key, you can generate a public key out of it with: .. code-block:: none openssl pkey -in rsaprivkey.pem -pubout -out rsapubkey.pem These keys can then be used with this configuration: .. code-block:: none mail_plugins = $mail_plugins mail_crypt plugin { mail_crypt_global_private_key = ecprivkey.pem base64 -d ecprivkey.pem | openssl ec -pubout | base64 -w0 > ecpubkey.pem .. code-block:: none passdb { driver = static args = password=pass mail_crypt_global_public_key= mail_crypt_global_private_key= } mail_plugins = $mail_plugins mail_crypt plugin { mail_crypt_save_version = 2 } Read-only Mode (``mail_crypt_save_version = 0``) ================================================ If you have encrypted mailboxes that you need to read, but no longer want to encrypt new mail, use ``mail_crypt_save_version=0``: .. code-block:: none plugin { mail_crypt_save_version = 0 mail_crypt_global_private_key = `__ to decrypt encrypted files. .. _fs_crypt: fs-crypt and fs-mail-crypt ========================== The fs-crypt is a lib-fs wrapper that can encrypt and decrypt files. It works similarly to the fs-compress wrapper. It can be used to encrypt e.g.: * FTS index objects (fts_dovecot_fs) * External mail attachments (mail_attachment_fs) fs-crypt comes in two flavors, ``mail-crypt`` and ``crypt``. (The differences between the two are technical and related to internal code contexts.) Note that fs-[mail-]crypt and the fs-compress wrapper can be also combined. Please make sure that compression is always applied before encryption. See :ref:`plugin-fs-compress` for an example and more details about compression. Currently the fs-crypt plugin requires that all the files it reads are encrypted. If it sees an unencrypted file it'll fail to read it. The plan is to fix this later. FS driver syntax:: crypt:[algo=:][set_prefix=:][private_key_path=/path:][public_key_path=/path:][password=password:]`` where: ===================== ======================================================== Key Value ===================== ======================================================== ``algo`` Encryption algorithm. Default is ``aes-256-gcm-sha256``. ``password`` Password for decrypting public key. ``private_key_path`` Path to private key. ``public_key_path`` Path to public key. ``set_prefix`` Read ``_public_key`` and ``_private_key``. Default is ``mail_crypt_global``. ===================== ======================================================== Example: .. code-block:: none plugin { fts_index_fs = crypt:set_prefix=fscrypt_index:posix:prefix=/tmp/fts fscrypt_index_public_key =