Daniel P. Berrangé | 491024a | 2021-02-23 15:35:45 +0000 | [diff] [blame] | 1 | .. _secret data: |
| 2 | |
| 3 | Providing secret data to QEMU |
| 4 | ----------------------------- |
| 5 | |
| 6 | There are a variety of objects in QEMU which require secret data to be provided |
| 7 | by the administrator or management application. For example, network block |
| 8 | devices often require a password, LUKS block devices require a passphrase to |
| 9 | unlock key material, remote desktop services require an access password. |
| 10 | QEMU has a general purpose mechanism for providing secret data to QEMU in a |
| 11 | secure manner, using the ``secret`` object type. |
| 12 | |
| 13 | At startup this can be done using the ``-object secret,...`` command line |
| 14 | argument. At runtime this can be done using the ``object_add`` QMP / HMP |
| 15 | monitor commands. The examples that follow will illustrate use of ``-object`` |
| 16 | command lines, but they all apply equivalentely in QMP / HMP. When creating |
| 17 | a ``secret`` object it must be given a unique ID string. This ID is then |
| 18 | used to identify the object when configuring the thing which need the data. |
| 19 | |
| 20 | |
| 21 | INSECURE: Passing secrets as clear text inline |
| 22 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 23 | |
| 24 | **The following should never be done in a production environment or on a |
| 25 | multi-user host. Command line arguments are usually visible in the process |
| 26 | listings and are often collected in log files by system monitoring agents |
| 27 | or bug reporting tools. QMP/HMP commands and their arguments are also often |
| 28 | logged and attached to bug reports. This all risks compromising secrets that |
| 29 | are passed inline.** |
| 30 | |
| 31 | For the convenience of people debugging / developing with QEMU, it is possible |
| 32 | to pass secret data inline on the command line. |
| 33 | |
| 34 | :: |
| 35 | |
| 36 | -object secret,id=secvnc0,data=87539319 |
| 37 | |
| 38 | |
| 39 | Again it is possible to provide the data in base64 encoded format, which is |
| 40 | particularly useful if the data contains binary characters that would clash |
| 41 | with argument parsing. |
| 42 | |
| 43 | :: |
| 44 | |
| 45 | -object secret,id=secvnc0,data=ODc1MzkzMTk=,format=base64 |
| 46 | |
| 47 | |
| 48 | **Note: base64 encoding does not provide any security benefit.** |
| 49 | |
| 50 | Passing secrets as clear text via a file |
| 51 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 52 | |
| 53 | The simplest approach to providing data securely is to use a file to store |
| 54 | the secret: |
| 55 | |
| 56 | :: |
| 57 | |
| 58 | -object secret,id=secvnc0,file=vnc-password.txt |
| 59 | |
| 60 | |
| 61 | In this example the file ``vnc-password.txt`` contains the plain text secret |
| 62 | data. It is important to note that the contents of the file are treated as an |
| 63 | opaque blob. The entire raw file contents is used as the value, thus it is |
| 64 | important not to mistakenly add any trailing newline character in the file if |
| 65 | this newline is not intended to be part of the secret data. |
| 66 | |
| 67 | In some cases it might be more convenient to pass the secret data in base64 |
| 68 | format and have QEMU decode to get the raw bytes before use: |
| 69 | |
| 70 | :: |
| 71 | |
| 72 | -object secret,id=sec0,file=vnc-password.txt,format=base64 |
| 73 | |
| 74 | |
| 75 | The file should generally be given mode ``0600`` or ``0400`` permissions, and |
| 76 | have its user/group ownership set to the same account that the QEMU process |
| 77 | will be launched under. If using mandatory access control such as SELinux, then |
| 78 | the file should be labelled to only grant access to the specific QEMU process |
| 79 | that needs access. This will prevent other processes/users from compromising the |
| 80 | secret data. |
| 81 | |
| 82 | |
| 83 | Passing secrets as cipher text inline |
| 84 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 85 | |
| 86 | To address the insecurity of passing secrets inline as clear text, it is |
| 87 | possible to configure a second secret as an AES key to use for decrypting |
| 88 | the data. |
| 89 | |
| 90 | The secret used as the AES key must always be configured using the file based |
| 91 | storage mechanism: |
| 92 | |
| 93 | :: |
| 94 | |
| 95 | -object secret,id=secmaster,file=masterkey.data,format=base64 |
| 96 | |
| 97 | |
| 98 | In this case the ``masterkey.data`` file would be initialized with 32 |
| 99 | cryptographically secure random bytes, which are then base64 encoded. |
| 100 | The contents of this file will by used as an AES-256 key to encrypt the |
| 101 | real secret that can now be safely passed to QEMU inline as cipher text |
| 102 | |
| 103 | :: |
| 104 | |
| 105 | -object secret,id=secvnc0,keyid=secmaster,data=BASE64-CIPHERTEXT,iv=BASE64-IV,format=base64 |
| 106 | |
| 107 | |
| 108 | In this example ``BASE64-CIPHERTEXT`` is the result of AES-256-CBC encrypting |
| 109 | the secret with ``masterkey.data`` and then base64 encoding the ciphertext. |
| 110 | The ``BASE64-IV`` data is 16 random bytes which have been base64 encrypted. |
| 111 | These bytes are used as the initialization vector for the AES-256-CBC value. |
| 112 | |
| 113 | A single master key can be used to encrypt all subsequent secrets, **but it is |
| 114 | critical that a different initialization vector is used for every secret**. |
| 115 | |
| 116 | Passing secrets via the Linux keyring |
| 117 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 118 | |
| 119 | The earlier mechanisms described are platform agnostic. If using QEMU on a Linux |
| 120 | host, it is further possible to pass secrets to QEMU using the Linux keyring: |
| 121 | |
| 122 | :: |
| 123 | |
| 124 | -object secret_keyring,id=secvnc0,serial=1729 |
| 125 | |
| 126 | |
| 127 | This instructs QEMU to load data from the Linux keyring secret identified by |
| 128 | the serial number ``1729``. It is possible to combine use of the keyring with |
| 129 | other features mentioned earlier such as base64 encoding: |
| 130 | |
| 131 | :: |
| 132 | |
| 133 | -object secret_keyring,id=secvnc0,serial=1729,format=base64 |
| 134 | |
| 135 | |
| 136 | and also encryption with a master key: |
| 137 | |
| 138 | :: |
| 139 | |
| 140 | -object secret_keyring,id=secvnc0,keyid=secmaster,serial=1729,iv=BASE64-IV |
| 141 | |
| 142 | |
| 143 | Best practice |
| 144 | ~~~~~~~~~~~~~ |
| 145 | |
| 146 | It is recommended for production deployments to use a master key secret, and |
| 147 | then pass all subsequent inline secrets encrypted with the master key. |
| 148 | |
| 149 | Each QEMU instance must have a distinct master key, and that must be generated |
| 150 | from a cryptographically secure random data source. The master key should be |
| 151 | deleted immediately upon QEMU shutdown. If passing the master key as a file, |
| 152 | the key file must have access control rules applied that restrict access to |
| 153 | just the one QEMU process that is intended to use it. Alternatively the Linux |
| 154 | keyring can be used to pass the master key to QEMU. |
| 155 | |
| 156 | The secrets for individual QEMU device backends must all then be encrypted |
| 157 | with this master key. |
| 158 | |
| 159 | This procedure helps ensure that the individual secrets for QEMU backends will |
| 160 | not be compromised, even if ``-object`` CLI args or ``object_add`` monitor |
| 161 | commands are collected in log files and attached to public bug support tickets. |
| 162 | The only item that needs strongly protecting is the master key file. |