| 1 | .. SPDX-License-Identifier: GPL-2.0-or-later |
| 2 | |
| 3 | s390 Secure IPL |
| 4 | =============== |
| 5 | |
| 6 | Secure IPL (a.k.a. secure boot) enables s390-ccw virtual machines to |
| 7 | leverage qcrypto libraries and z/Architecture emulation to verify the |
| 8 | integrity of signed kernels. The qcrypto libraries are used to perform |
| 9 | certificate validation and signature-verification, whereas the |
| 10 | z/Architecture emulation is used to ensure secure IPL data has not |
| 11 | been tampered with, convey data between QEMU and guest code, and set up |
| 12 | the relevant secure IPL data structures with verification results. |
| 13 | |
| 14 | To find out more about using this feature, see |
| 15 | :doc:`documentation </system/s390x/secure-ipl>`. |
| 16 | |
| 17 | Note that "guest code" will refer to the s390-ccw BIOS unless stated |
| 18 | otherwise. |
| 19 | |
| 20 | Both QEMU and guest code work in cooperation to perform secure IPL. The Secure |
| 21 | Code Loading Attributes Facility (SCLAF) is used to check the Secure Code |
| 22 | Loading Attribute Block (SCLAB) and ensure that secure IPL data has not |
| 23 | been tampered with. DIAGNOSE 'X'320' is invoked by guest code to query |
| 24 | the certificate store info and retrieve specific certificates from QEMU. |
| 25 | DIAGNOSE 'X'508' is used by guest code to leverage qcrypto libraries to |
| 26 | perform signature-verification in QEMU. Lastly, guest code generates and |
| 27 | appends an IPL Information Report Block (IIRB) at the end of the IPL |
| 28 | Parameter Block (IPLB), which is used by the kernel to store signed and |
| 29 | verified entries. |
| 30 | |
| 31 | The logical steps are as follows: |
| 32 | |
| 33 | - guest code reads data payload from disk (e.g. stage3 boot loader, kernel) |
| 34 | - guest code checks the validity of the SCLAB |
| 35 | - guest code invokes DIAG 508 subcode 1 and provides the payload |
| 36 | - QEMU handles DIAG 508 request by reading the payload and retrieving the |
| 37 | certificate store |
| 38 | - QEMU DIAG 508 utilizes handler qcrypto libraries to perform |
| 39 | signature-verification on the payload, attempting with each cert in the store |
| 40 | (until success or exhausted) |
| 41 | - QEMU DIAG 508 returns: |
| 42 | |
| 43 | - success: index of cert used to verify payload |
| 44 | - failure: error code |
| 45 | |
| 46 | - guest code is expected to respond to this operation by: |
| 47 | |
| 48 | - success: retrieves cert from store via DIAG 320 using returned index |
| 49 | - failure: reports with warning (audit mode), aborts with error (secure mode) |
| 50 | |
| 51 | - guest code appends IIRB at the end of the IPLB |
| 52 | - guest code kicks off IPL |
| 53 | |
| 54 | More information regarding the respective DIAGNOSE commands and IPL data |
| 55 | structures are outlined within this document. |
| 56 | |
| 57 | |
| 58 | s390 Certificate Store and Functions |
| 59 | ------------------------------------ |
| 60 | |
| 61 | s390 Certificate Store |
| 62 | ^^^^^^^^^^^^^^^^^^^^^^ |
| 63 | |
| 64 | A certificate store is implemented for s390-ccw guests to retain within |
| 65 | memory all certificates provided by the user via the command-line, which |
| 66 | are expected to be stored somewhere on the host's file system. The store |
| 67 | will keep track of the number of certificates, their respective size, |
| 68 | and a summation of the sizes. |
| 69 | |
| 70 | Each certificate is stored in an S390IPLCertificate struct, which has a |
| 71 | name (converted to EBCDIC), size fields of PEM and DER data, and the raw |
| 72 | PEM Base64 data. |
| 73 | |
| 74 | Note: A maximum of 64 certificates are allowed to be stored in the certificate |
| 75 | store. |
| 76 | |
| 77 | DIAGNOSE function code 'X'320' - Certificate Store Facility |
| 78 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
| 79 | |
| 80 | DIAGNOSE 'X'320' is used to provide support for guest code to directly |
| 81 | query the s390 certificate store. Guest code may be the s390-ccw BIOS or |
| 82 | the guest kernel. |
| 83 | |
| 84 | Subcode 0 - query installed subcodes |
| 85 | Returns a 256-bit installed subcodes mask (ISM) stored in the installed |
| 86 | subcodes block (ISB). This mask indicates which subcodes are currently |
| 87 | installed and available for use. |
| 88 | |
| 89 | Subcode 1 - query verification certificate storage information |
| 90 | Provides the information required to determine the amount of memory needed |
| 91 | to store one or more verification-certificates (VCs) from the certificate |
| 92 | store (CS). |
| 93 | |
| 94 | Upon successful completion, this subcode returns various storage size values |
| 95 | for verification-certificate blocks (VCBs). |
| 96 | |
| 97 | The output is returned in the verification-certificate-storage-size block |
| 98 | (VCSSB). A VCSSB length of 4 indicates that no certificates are available |
| 99 | in the CS. |
| 100 | |
| 101 | Subcode 2 - store verification certificates |
| 102 | Provides VCs that are in the certificate store. |
| 103 | |
| 104 | The output is provided in a VCB, which includes a common header followed by |
| 105 | zero or more verification-certificate entries (VCEs). |
| 106 | |
| 107 | The instruction expects the cert store to maintain an origin of 1 for the |
| 108 | index (i.e. a retrieval of the first certificate in the store should be |
| 109 | denoted by setting first-VC to 1). |
| 110 | |
| 111 | The first-VC and last-VC fields of the VCB specify the index range of |
| 112 | VCs to be stored in the VCB. Certs are stored sequentially, starting |
| 113 | with first-VC index. As each cert is stored, a "stored count" is |
| 114 | incremented. If there is not enough space to store all certs requested |
| 115 | by the index range, a "remaining count" will be recorded and no more |
| 116 | certificates will be stored. |
| 117 | |
| 118 | Each VCE contains a header followed by information extracted from a |
| 119 | certificate within the certificate store. The information includes: |
| 120 | key-id, hash, and certificate data. This information is stored |
| 121 | contiguously in a VCE (with zero-padding). Following the header, the |
| 122 | key-id is immediately stored. The hash and certificate data follow and |
| 123 | may be accessed via the respective offset fields stored in the VCE. |
| 124 | |
| 125 | |
| 126 | Secure IPL Data Structures, Facilities, and Functions |
| 127 | ----------------------------------------------------- |
| 128 | |
| 129 | DIAGNOSE function code 'X'508' - IPL extensions |
| 130 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
| 131 | |
| 132 | DIAGNOSE 'X'508' is reserved for guest use in order to facilitate communication |
| 133 | of additional IPL operations that cannot be handled by guest code, such as |
| 134 | signature verification for secure IPL. |
| 135 | |
| 136 | If the function code specifies 0x508, IPL extension functions are performed. |
| 137 | These functions are meant to provide extended functionality for s390 guest boot |
| 138 | that requires assistance from QEMU. |
| 139 | |
| 140 | Subcode 0 - query installed subcodes |
| 141 | Returns a 64-bit mask indicating which subcodes are supported. |
| 142 | |
| 143 | Subcode 1 - perform signature verification |
| 144 | Perform signature-verification on a signed component, using certificates |
| 145 | from the certificate store and leveraging qcrypto libraries to perform |
| 146 | this operation. |
| 147 | |
| 148 | Note: verification of initrd is not supported. |
| 149 | |
| 150 | A return code of 1 indicates success, and the index and length of the |
| 151 | corresponding certificate will be set in the Diag508SigVerifBlock. |
| 152 | The following values indicate failure: |
| 153 | |
| 154 | * ``0x0102``: no certificates are available in the store |
| 155 | * ``0x0202``: component data is invalid |
| 156 | * ``0x0302``: PKCS#7 format signature is invalid |
| 157 | * ``0x0402``: signature-verification failed |
| 158 | * ``0x0502``: length of Diag508SigVerifBlock is invalid |
| 159 | |
| 160 | IPL Information Report Block |
| 161 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
| 162 | |
| 163 | The IPL Parameter Block (IPLB), utilized for IPL operation, is extended with an |
| 164 | IPL Information Report Block (IIRB), which contains the results from secure IPL |
| 165 | operations such as: |
| 166 | |
| 167 | * component data |
| 168 | * verification results |
| 169 | * certificate data |
| 170 | |
| 171 | During early boot, the guest kernel reserves the memory region |
| 172 | containing the IIRB. This preserves the data while the guest kernel is |
| 173 | operating and during re-IPL. |
| 174 | |
| 175 | The guest kernel uses the contents in the IIRB for: |
| 176 | |
| 177 | * Boot logging: reports which components were loaded and verified. |
| 178 | * kexec operations: builds the next kernel’s IPL report from the existing one. |
| 179 | * Keying: installs IPL certificates into the platform trusted keyring. |
| 180 | |
| 181 | Secure Code Loading Attributes Facility |
| 182 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
| 183 | |
| 184 | The Secure Code Loading Attributes Facility (SCLAF) enhances system security |
| 185 | during the IPL by enforcing additional verification rules. |
| 186 | |
| 187 | When SCLAF is available, its behavior depends on the IPL mode. It introduces |
| 188 | verification of both signed and unsigned components to help ensure that only |
| 189 | authorized code is loaded during the IPL process. Any errors detected by SCLAF |
| 190 | are reported in the IIRB. |
| 191 | |
| 192 | Unsigned components are restricted to load addresses at or above absolute |
| 193 | storage address ``0x2000``. |
| 194 | |
| 195 | Signed components must include a Secure Code Loading Attribute Block (SCLAB), |
| 196 | which is appended at the very end of the component. The SCLAB defines security |
| 197 | attributes for handling the signed code. |