 80fe12fbe5
			
		
	
	80fe12fbe5
	
	
	
		
			
			This file required an editorial scrub. Poorly structured and formatted. Several instances of uncommented narrative text in code-blocks. Grammer and punct. errors. Etc. Signed-off-by: Ron Stone <ronald.stone@windriver.com> Change-Id: I3fdb3982b162fdc4ce50d4b034a649d0589648df
		
			
				
	
	
		
			383 lines
		
	
	
		
			15 KiB
		
	
	
	
		
			ReStructuredText
		
	
	
	
	
	
			
		
		
	
	
			383 lines
		
	
	
		
			15 KiB
		
	
	
	
		
			ReStructuredText
		
	
	
	
	
	
| 
 | |
| .. fyl1552681364538
 | |
| .. _use-uefi-secure-boot:
 | |
| 
 | |
| ====================
 | |
| Use UEFI Secure Boot
 | |
| ====================
 | |
| 
 | |
| Secure Boot is supported in |UEFI| installations only. It is not used when
 | |
| booting |prod| as a legacy boot target.
 | |
| 
 | |
| .. contents:: |minitoc|
 | |
|    :local:
 | |
|    :depth: 1
 | |
| 
 | |
| |prod| currently does not support switching from legacy to |UEFI| mode after a
 | |
| system has been installed. Doing so requires a reinstallation of the system.
 | |
| This also means that upgrading from a legacy install to a secure boot install
 | |
| (|UEFI|) is not supported.
 | |
| 
 | |
| When upgrading a |prod| system from a version which does not support secure
 | |
| boot to a version that does, do not enable secure boot in |UEFI| firmware until
 | |
| the upgrade is complete.
 | |
| 
 | |
| For each node that is going to use secure boot, you must populate the |prod|
 | |
| public certificate/key in the |UEFI| Secure Boot authorized database in
 | |
| accordance with the board manufacturer's process. This must be done for each
 | |
| node before starting installation.
 | |
| 
 | |
| You may need to work with your hardware vendor to have the certificate
 | |
| installed.
 | |
| 
 | |
| There is often an option in the |UEFI| setup utility which allows a user to
 | |
| browse to a file containing a certificate to be loaded in the authorized
 | |
| database. This option may be hidden in the |UEFI| setup utility unless |UEFI|
 | |
| mode is enabled, and secure boot is enabled.
 | |
| 
 | |
| Many motherboards ship with Microsoft secure boot certificates
 | |
| pre-programmed in the |UEFI| certificate database. These certificates may be
 | |
| required to boot |UEFI| drivers for video cards, RAID controllers, or NICs
 | |
| (for example, the |PXE| boot software for a NIC may have been signed by a
 | |
| Microsoft certificate). While certificates can usually be removed from the
 | |
| certificate database (again, this is |UEFI| implementation specific) it
 | |
| may be required that you keep the Microsoft certificates to allow for
 | |
| complete system operation.
 | |
| 
 | |
| Mixed combinations of secure boot and non-secure boot nodes are supported.
 | |
| For example, a controller node may secure boot, while a worker node may not.
 | |
| Secure boot must be enabled in the |UEFI| firmware of each node for that node
 | |
| to be protected.
 | |
| 
 | |
| .. only:: partner
 | |
| 
 | |
|     .. include:: /_includes/extract-certificate-from-iso-181be684e2e5.rest
 | |
| 
 | |
| .. only:: starlingx
 | |
| 
 | |
|     ------------------------------------------------------------------------------
 | |
|     Build considerations for signing packages for UEFI Secure Boot -- CentOS build
 | |
|     ------------------------------------------------------------------------------
 | |
| 
 | |
|     The |prod| build environment has provisions for calling out to a signing
 | |
|     server for purposes of creating a secure boot load.  At this time |prod|
 | |
|     does not include an implementation of the signing server.  The following
 | |
|     describes how the signing process is intended to work in the context of a
 | |
|     CentOS build. You may find it helpful in implementing your own signing
 | |
|     server.
 | |
| 
 | |
|     The following environmental variables should be defined before attempting
 | |
|     to request a secure boot signing:
 | |
| 
 | |
|     .. code-block:: bash
 | |
| 
 | |
|         export SIGNING_SERVER=<signing-host>
 | |
|         export SIGNING_USER=<signing-user>
 | |
|         export SIGNING_SERVER_SCRIPT=<path-to-signing-script>
 | |
| 
 | |
|     ``build-pkgs`` further requires that ``$USER`` be set to "jenkins", and
 | |
|     :command:`export FORMAL_BUILD=1``.
 | |
| 
 | |
|     If the above criteria is met, it calls into ``sign-secure-boot``.
 | |
| 
 | |
|     This is an example of the call sequence:
 | |
| 
 | |
|     .. code-block:: bash
 | |
| 
 | |
|         # 1. Set up the server side directory for files transfers.
 | |
|         UPLOAD_PATH=`ssh $SIGNING_USER@$SIGNING_SERVER sudo $SIGNING_SCRIPT -r`
 | |
| 
 | |
|         # 2. upload the original package
 | |
|         scp -q $FILE $SIGNING_USER@$SIGNING_SERVER:$UPLOAD_PATH
 | |
| 
 | |
|         # 3. Request that the package be signed
 | |
|         ssh $SIGNING_USER@$SIGNING_SERVER sudo $SIGNING_SCRIPT -v -i $UPLOAD_PATH/$(basename $FILE) $UNSIGNED_OPTION -t $TYPE > $TMPFILE
 | |
| 
 | |
|         # 4. Download the file from the signing server
 | |
|         DOWNLOAD_FILENAME=$(basename $OUTPUT_FILE)
 | |
|         scp -q $SIGNING_USER@$SIGNING_SERVER:$OUTPUT_FILE $(dirname $FILE)
 | |
| 
 | |
| 
 | |
|     Within the signing server there are two keys used for signing, known as the
 | |
|     `boot` key and the `shim` key. The public `boot` key file must be manually
 | |
|     added to the secure boot keychain in the firmware. The `boot` key signs the
 | |
|     first executable loaded, contained in the `shim` package. The first
 | |
|     executable must then install the public `shim` key file (automatically)
 | |
|     before passing control to the grub, and ultimately the kernel, both of
 | |
|     which are signed by the private `shim` key.
 | |
| 
 | |
|     Three packages need to be passed to the signing server. The RPMs need to be
 | |
|     unpacked, the relevant binaries signed with the correct keys, and the RPMs
 | |
|     reassembled.
 | |
| 
 | |
|     .. table::
 | |
|        :widths: auto
 | |
| 
 | |
|        +---------+------+------------------------------------+
 | |
|        | Package | Key  | Files to sign                      |
 | |
|        +=========+======+====================================+
 | |
|        | shim    | boot | BOOTX64, shim, shimx64             |
 | |
|        |         | shim | MokManager, fallback, mmx64, fbx64 |
 | |
|        +---------+------+------------------------------------+
 | |
|        | grub    | shim | grubx64.efi, gcdx64.efi            |
 | |
|        +---------+------+------------------------------------+
 | |
|        | kernel  | shim |                                    |
 | |
|        +---------+------+------------------------------------+
 | |
| 
 | |
|     .. note::
 | |
| 
 | |
|         `shim` files that are required to be signed might might include a
 | |
|         ``.efi`` or ``.EFI`` suffix.
 | |
| 
 | |
|         Some files may be absent in newer packages.
 | |
| 
 | |
|     Example:
 | |
| 
 | |
|     .. code-block:: none
 | |
| 
 | |
|         sbsign --key $KEYPATH/$KEYNAME.key --cert $KEYPATH/$KEYNAME.crt  --output $SIGNEDFILE $UNSIGNEDFILE
 | |
| 
 | |
|     .. rubric:: Keys and certificates:
 | |
| 
 | |
|     * ``boot.crt`` - Certificate to boot (to be programmed in firmware)
 | |
| 
 | |
|     * ``boot.key`` - Private key with which to sign shim
 | |
| 
 | |
|     * ``shim.crt`` - Certificated embedded within shim used to validate kernel, grub
 | |
| 
 | |
|     * ``shim.key`` - Private key with which to sign kernel/grub
 | |
| 
 | |
|     .. rubric:: Key generation:
 | |
| 
 | |
|     .. code-block:: none
 | |
| 
 | |
|         openssl req -new -x509 -newkey rsa:2048 -keyout $KEY.key -out $KEY.pem -days 3650
 | |
|         openssl x509 -in $KEY.pem -out $KEY.crt -outform DER
 | |
| 
 | |
|     .. note::
 | |
| 
 | |
|         ``boot.crt`` should be copied to
 | |
|         ``cgcs-root/build-tools/certificates/TiBoot.crt`` for inclusion during the
 | |
|         ``build-iso`` step.
 | |
| 
 | |
|     ------------------------------------------------------------------------------
 | |
|     Build considerations for signing packages for UEFI Secure Boot -- Debian build
 | |
|     ------------------------------------------------------------------------------
 | |
| 
 | |
|     The |prod| build environment has provisions for calling out to a signing
 | |
|     server for purposes of creating a secure boot load.  At this time |prod|
 | |
|     does not include an implementation of the signing server.  The following
 | |
|     describes how the signing process is intended to work in the context of a
 | |
|     ``Debian`` build. You may find it helpful in implementing your own signing
 | |
|     server.
 | |
| 
 | |
|     The secure boot verification sequence of StarlingX Debian is:
 | |
| 
 | |
|     #. UEFI firmware verify shim image
 | |
| 
 | |
|     #. shim verify grub image
 | |
| 
 | |
|     #. grub verify kernel image and initramfs image
 | |
| 
 | |
|     The bootloader shim will enroll the public key to verify grub image.
 | |
| 
 | |
|     The bootloader grub-efi will enroll the public key to verify kernel and
 | |
|     initramfs image.
 | |
| 
 | |
|     The following process should be followed to request a secure boot signing:
 | |
| 
 | |
|     .. code-block:: none
 | |
| 
 | |
|         ......
 | |
|         stx control keys-add --key-type=signing-server --key=[key file]
 | |
|         stx shell
 | |
|         downloader
 | |
|         build-pkgs
 | |
|         export SIGNING_SERVER="signing_user@signing_server_ip"
 | |
|         sign-secure-boot_debian
 | |
|         build-image
 | |
| 
 | |
|     The "key file" is the private key generated by :command:`ssh-keygen -t rsa`
 | |
|     and used to setup signing server access without password.
 | |
| 
 | |
|     The signing script ``sign-secure-boot_debian`` does secure boot signing for
 | |
|     |prod| Debian as follows:
 | |
| 
 | |
| 
 | |
|     #. Sign shim / grub images
 | |
| 
 | |
|        The shim/grub efi images are obtained from extracted shim/grub
 | |
|        packages, and they are sent to signing server and signed there and
 | |
|        copied back. Then the shim/grub packages are repacked with the
 | |
|        signed efi images.
 | |
| 
 | |
|     #. Sign kernel images and ``LockDown.efi``
 | |
| 
 | |
|        The file sign_rootfs-post-scripts is inserted to where the hook script
 | |
|        "rootfs-post-scripts" is defined in the LAT config file
 | |
|        ``base-bullseye.yaml``. This will sign kernel images and
 | |
|        ``LockDown.efi`` on signing server in the LAT build process. The
 | |
|        "rootfs-post-scripts" is the hook in LAT tool running after rootfs is
 | |
|        created.
 | |
| 
 | |
|     #. Sign initramfs and mini initrd
 | |
| 
 | |
|        The file`` sign_initramfs-sign-script`` is inserted to where the hook
 | |
|        script ``initramfs-sign-script`` is defined in the LAT config file
 | |
|        ``base-bullseye.yaml``. This will sign initramfs and mini initrd on
 | |
|        signing server in the LAT build process. The ``initramfs-sign-script``
 | |
|        is the hook in LAT tool running after initramfs is created.
 | |
| 
 | |
|     **2** and **3** above prepare the signing codes in the LAT config file.
 | |
|     After build-image is triggered, the signing codes inserted into the LAT
 | |
|     config files will run on the LAT container in the correct sequence.
 | |
| 
 | |
|     Here is an example for signing an image file in sign-secure-boot_debian:
 | |
| 
 | |
|     .. code-block:: bash
 | |
| 
 | |
|         # Request upload path from signing server.
 | |
|         REQUEST=$(ssh ${SSH_OPTION_NOCHECKING} ${SIGNING_SERVER} sudo /opt/signing/sign-debian.sh -r)
 | |
|         UPLOAD_PATH=${REQUEST#*Upload: }
 | |
| 
 | |
|         # Copy shimx64.efi to signing server
 | |
|         scp ${SSH_OPTION_NOCHECKING} shimx64.efi ${SIGNING_SERVER}:${UPLOAD_PATH}
 | |
|         # Sign shimx64.efi
 | |
|         ssh ${SSH_OPTION_NOCHECKING} ${SIGNING_SERVER} sudo /opt/signing/sign-debian.sh -i ${UPLOAD_PATH}/shimx64.efi -t shim
 | |
|         # Copy back signed shimx64.efi which is renamed as bootx64.efi
 | |
|         sudo scp ${SSH_OPTION_NOCHECKING} ${SIGNING_SERVER}:${UPLOAD_PATH}/bootx64.efi ./
 | |
| 
 | |
|     ``sign-debian.sh``, above, is the script running on signing server whose
 | |
|     interface is defined as below:
 | |
| 
 | |
|     .. code-block:: none
 | |
| 
 | |
|         Usage:
 | |
|         sign-debian.sh [options]
 | |
| 
 | |
|         [-i <file>] - input unsigned file
 | |
|         [-t <type>] - type of signing to do
 | |
|         [-r]        - request an upload path
 | |
| 
 | |
|         Types of signing:
 | |
|         -t shim     - signs a shim EFI binary with the boot key
 | |
|         -t grub     - signs a GRUB EFI binary with the shim key
 | |
|         -t shimtool - signs a shim tool EFI binary with the shim key
 | |
|         -t grub-gpg - signs a kernel/initrd/grub.cfg with the grub gpg key
 | |
| 
 | |
|     .. _key-management-use-uefi-secure-boot:
 | |
| 
 | |
|     .. rubric:: Keys management:
 | |
| 
 | |
| 
 | |
|     Upstream stx public keys repo: https://opendev.org/starlingx/public-keys
 | |
| 
 | |
|     The keys under cgcs-root/public-keys are the public keys used in
 | |
|     the verification process of secure boot process for StarlingX
 | |
|     Debian.
 | |
| 
 | |
|     .. rubric:: Keys Introduction:
 | |
|     
 | |
|     ``tis-boot.crt``: The public key flashed into |UEFI| to verify
 | |
|       ``bootx64.efi`` (signed shim image ``shimx64.efi``)
 | |
| 
 | |
|     ``tis-shim.der``: The public key used by shim to verify
 | |
|       ``grubx64.efi`` (signed grub image) and ``mmx64.efi``
 | |
|       (signed shim tool image);
 | |
| 
 | |
|     ``boot_pub_key``: it is the public key used by grub to verify signed
 | |
|       kernel image and initramfs image and efitools image and so on.
 | |
| 
 | |
|     ``TiBoot.crt``: it is the same pub key with ``tis-boot.crt`` (pem) as a
 | |
|       der format. It is installed as ``/CERTS/TiBoot.crt`` in the ``efi.img``
 | |
|       which is in the iso image.
 | |
| 
 | |
|     The following methods can be used to create substitute keys:
 | |
| 
 | |
|     #. Example to create ``tis-boot.crt/TiBoot.crt``.
 | |
| 
 | |
|        .. code-block:: bash
 | |
|     
 | |
|            openssl req -new -x509 -newkey rsa:2048 -keyout BOOT.priv -outform DER -out BOOT.der -days 36500 -subj "/CN=My Boot/" -nodes
 | |
|            openssl x509 -inform der -in BOOT.der -out BOOT.pem
 | |
|            cp BOOT.pem tis-boot.crt
 | |
|            cp BOOT.priv tis-boot.key
 | |
|            cp BOOT.der TiBoot.crt
 | |
| 
 | |
| 
 | |
|        The ``tis-boot.crt`` and ``tis-boot.key`` are used to sign images
 | |
|        mentioned above (shim image).
 | |
| 
 | |
|        The ``tis-shim.crt``/``tis-shim.der``/``tis-shim.key`` can be created in
 | |
|        the same way, and used to sign images mentioned above (grub image and
 | |
|        shim tool image).
 | |
| 
 | |
|     #. Example to create ``boot_pub_key``.
 | |
| 
 | |
|        .. code-block:: bash
 | |
| 
 | |
|           #!/bin/bash
 | |
|           key_dir="./"
 | |
|           priv_key="${key_dir}/BOOT-GPG-PRIVKEY-SecureBootCore"
 | |
|           pub_key="${key_dir}/BOOT-GPG-KEY-SecureBootCore"
 | |
|           name_real="SecureBootCore"
 | |
|           pw="PASSWORD"
 | |
|           USE_PW="Passphrase: PASSWORD"
 | |
|           cat >"${key_dir}/gen_keyring" <<EOF
 | |
|           Key-Type: RSA
 | |
|           Key-Length: 4096
 | |
|           Name-Real: ${name_real}
 | |
|           Name-Comment: EXAMPLE
 | |
|           Name-Email: a@b.com
 | |
|           Expire-Date: 0
 | |
|           ${USE_PW}
 | |
|           %commit
 | |
|           %echo keyring ${name_real} created
 | |
|           EOF
 | |
|   
 | |
|           gpg --homedir "${key_dir}" --batch --yes --gen-key "${key_dir}/gen_keyring"
 | |
|           gpg --homedir "${key_dir}" -k
 | |
|           gpg --homedir "${key_dir}" --export --armor "${name_real}" > "${pub_key}"
 | |
|           gpg --homedir "${key_dir}" --export-secret-keys --pinentry-mode=loopback --passphrase "${pw}" --armor "${name_real}" > "${priv_key}"
 | |
|           gpg --homedir "${key_dir}" --export "${name_real}" > ${key_dir}/boot_pub_key
 | |
|   
 | |
|        The ``BOOT-GPG-PRIVKEY-SecureBootCore`` is used to sign images mentioned
 | |
|        above (kernel image, initramfs image and efitools image and so on).
 | |
| 
 | |
|     #. Signing commands to sign image files:
 | |
| 
 | |
|        * Signing command to sign type shim/grub/shimtool image files:
 | |
| 
 | |
|          .. code-block:: none
 | |
| 
 | |
|             sbsign --key $KEYPATH/$KEYNAME.key \
 | |
|                    --cert $KEYPATH/$KEYNAME.crt \
 | |
|                    --output $SIGNEDFILE \
 | |
|                    $UNSIGNEDFILE
 | |
| 
 | |
|          * for ``-t shim``, the output file name is ``bootx64.efi``
 | |
|  
 | |
|          * for ``-t grub``, the output file name is ``grubx64.efi``
 | |
|  
 | |
|          * for ``-t shimtool``, the output file name is ${UNSIGNEDFILE}.signed
 | |
| 
 | |
|        * Signing command to sign type grub-gpg files:
 | |
| 
 | |
|          .. code-block::
 | |
| 
 | |
|                 gpg2 --batch \
 | |
|                     --homedir ${GPGHOME} \
 | |
|                     --passphrase PASSWORD \
 | |
|                     --import ${KEYPATH}/${BOOT_GPG_PRI_KEY}
 | |
|                 echo 'PASSWORD' | \
 | |
|                 gpg2 --pinentry-mode loopback \
 | |
|                     --batch \
 | |
|                     --homedir ${GPGHOME} \
 | |
|                     -u SecureBootCore \
 | |
|                     --detach-sign \
 | |
|                     --passphrase-fd 0 \
 | |
|                         ${FILEIN}
 | |
| 
 | |
|          Refer to :ref:`Key management <key-management-use-uefi-secure-boot>`
 | |
|          to determine the keys they should use.
 |