1<?xml version='1.0'?> <!--*-nxml-*-->
2<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN"
3  "http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd">
4<!-- SPDX-License-Identifier: LGPL-2.1-or-later -->
5
6<refentry id="systemd-stub" conditional='HAVE_GNU_EFI'
7    xmlns:xi="http://www.w3.org/2001/XInclude">
8  <refentryinfo>
9    <title>systemd-stub</title>
10    <productname>systemd</productname>
11  </refentryinfo>
12
13  <refmeta>
14    <refentrytitle>systemd-stub</refentrytitle>
15    <manvolnum>7</manvolnum>
16  </refmeta>
17
18  <refnamediv>
19    <refname>systemd-stub</refname>
20    <refname>sd-stub</refname>
21    <refname>linuxx64.efi.stub</refname>
22    <refname>linuxia32.efi.stub</refname>
23    <refname>linuxaa64.efi.stub</refname>
24    <refpurpose>A simple UEFI kernel boot stub</refpurpose>
25  </refnamediv>
26
27  <refsynopsisdiv>
28    <para><filename>/usr/lib/systemd/boot/efi/linuxx64.efi.stub</filename></para>
29    <para><filename>/usr/lib/systemd/boot/efi/linuxia32.efi.stub</filename></para>
30    <para><filename>/usr/lib/systemd/boot/efi/linuxaa64.efi.stub</filename></para>
31    <para><filename><replaceable>ESP</replaceable>/.../<replaceable>foo</replaceable>.efi.extra.d/*.cred</filename></para>
32    <para><filename><replaceable>ESP</replaceable>/.../<replaceable>foo</replaceable>.efi.extra.d/*.raw</filename></para>
33    <para><filename><replaceable>ESP</replaceable>/loader/credentials/*.cred</filename></para>
34  </refsynopsisdiv>
35
36  <refsect1>
37    <title>Description</title>
38
39    <para><command>systemd-stub</command> (stored in per-architecture files
40    <filename>linuxx64.efi.stub</filename>, <filename>linuxia32.efi.stub</filename>,
41    <filename>linuxaa64.efi.stub</filename> on disk) is a simple UEFI boot stub. An UEFI boot stub is
42    attached to a Linux kernel binary image, and is a piece of code that runs in the UEFI firmware
43    environment before transitioning into the Linux kernel environment. The UEFI boot stub ensures a Linux
44    kernel is executable as regular UEFI binary, and is able to do various preparations before switching the
45    system into the Linux world.</para>
46
47    <para>The UEFI boot stub looks for various resources for the kernel invocation inside the UEFI PE binary
48    itself. This allows combining various resources inside a single PE binary image, which may then be signed
49    via UEFI SecureBoot as a whole, covering all individual resources at once. Specifically it may
50    include:</para>
51
52    <itemizedlist>
53      <listitem><para>The ELF Linux kernel images will be looked for in the <literal>.linux</literal> PE
54      section of the executed image.</para></listitem>
55
56      <listitem><para>The initial RAM disk (initrd) will be looked for in the <literal>.initrd</literal> PE
57      section.</para></listitem>
58
59      <listitem><para>A compiled binary DeviceTree will be looked for in the <literal>.dtb</literal> PE
60      section.</para></listitem>
61
62      <listitem><para>The kernel command line to pass to the invoked kernel will be looked for in the
63      <literal>.cmdline</literal> PE section.</para></listitem>
64
65      <listitem><para>A boot splash (in Windows <filename>.BMP</filename> format) to show on screen before
66      invoking the kernel will be looked for in the <literal>.splash</literal> PE section.</para></listitem>
67    </itemizedlist>
68
69    <para>If UEFI SecureBoot is enabled and the <literal>.cmdline</literal> section is present in the executed
70    image, any attempts to override the kernel command line by passing one as invocation parameters to the
71    EFI binary are ignored. Thus, in order to allow overriding the kernel command line, either disable UEFI
72    SecureBoot, or don't include a kernel command line PE section in the kernel image file. If a command line
73    is accepted via EFI invocation parameters to the EFI binary it is measured into TPM PCR 12 (if a TPM is
74    present).</para>
75
76    <para>If a DeviceTree is embedded in the <literal>.dtb</literal> section, it replaces an existing
77    DeviceTree in the corresponding EFI configuration table. systemd-stub will ask the firmware via the
78    <literal>EFI_DT_FIXUP_PROTOCOL</literal> for hardware specific fixups to the DeviceTree.</para>
79  </refsect1>
80
81  <refsect1>
82    <title>Companion Files</title>
83
84    <para>The <command>systemd-stub</command> UEFI boot stub automatically collects two types of auxiliary
85    companion files optionally placed in drop-in directories on the same partition as the EFI binary,
86    dynamically generates <command>cpio</command> initrd archives from them, and passes them to the kernel.
87    Specifically:</para>
88
89    <itemizedlist>
90      <listitem><para>For a kernel binary called <filename><replaceable>foo</replaceable>.efi</filename>, it
91      will look for files with the <filename>.cred</filename> suffix in a directory named
92      <filename><replaceable>foo</replaceable>.efi.extra.d/</filename> next to it. A <command>cpio</command>
93      archive is generated from all files found that way, placing them in the
94      <filename>/.extra/credentials/</filename> directory of the initrd file hierarchy. The main initrd may
95      then access them in this directory. This is supposed to be used to store auxiliary, encrypted,
96      authenticated credentials for use with <varname>LoadCredentialEncrypted=</varname> in the UEFI System
97      Partition. See
98      <citerefentry><refentrytitle>systemd.exec</refentrytitle><manvolnum>5</manvolnum></citerefentry>
99      and
100      <citerefentry><refentrytitle>systemd-creds</refentrytitle><manvolnum>1</manvolnum></citerefentry>
101      for
102      details on encrypted credentials. The generated <command>cpio</command> archive is measured into TPM
103      PCR 12 (if a TPM is present).</para></listitem>
104
105      <listitem><para>Similarly, files <filename><replaceable>foo</replaceable>.efi.extra.d/*.raw</filename>
106      are packed up in a <command>cpio</command> archive and placed in the <filename>/.extra/sysext/</filename>
107      directory in the initrd file hierarchy. This is supposed to be used to pass additional system extension
108      images to the initrd. See
109      <citerefentry><refentrytitle>systemd-sysext</refentrytitle><manvolnum>8</manvolnum></citerefentry> for
110      details on system extension images. The generated <command>cpio</command> archive containing these
111      system extension images is measured into TPM PCR 4 (if a TPM is present).</para></listitem>
112
113      <listitem><para>Files <filename>/loader/credentials/*.cred</filename> are packed up in a
114      <command>cpio</command> archive and placed in the <filename>/.extra/global_credentials/</filename>
115      directory of the initrd file hierarchy. This is supposed to be used to pass additional credentials to
116      the initrd, regardless of the kernel being booted. The generated <command>cpio</command> archive is
117      measured into TPM PCR 12 (if a TPM is present)</para></listitem>
118    </itemizedlist>
119
120    <para>These mechanisms may be used to parameterize and extend trusted (i.e. signed), immutable initrd
121    images in a reasonably safe way: all data they contain is measured into TPM PCRs. On access they should be
122    further validated: in case of the credentials case by encrypting/authenticating them via TPM, as exposed
123    by <command>systemd-creds encrypt -T</command> (see
124    <citerefentry><refentrytitle>systemd-creds</refentrytitle><manvolnum>1</manvolnum></citerefentry> for
125    details); in case of the system extension images by using signed Verity images.</para>
126  </refsect1>
127
128  <refsect1>
129    <title>TPM2 PCR Notes</title>
130
131    <para>Note that when a unified kernel using <command>systemd-stub</command> is invoked the firmware will
132    measure it as a whole to TPM PCR 4, covering all embedded resources, such as the stub code itself, the
133    core kernel, the embedded initrd and kernel command line (see above for a full list).</para>
134
135    <para>Also note that the Linux kernel will measure all initrds it receives into TPM PCR 9. This means
136    every type of initrd will be measured twice: the initrd embedded in the kernel image will be measured to
137    both PCR 4 and PCR 9; the initrd synthesized from credentials will be measured to both PCR 12 and PCR 9;
138    the initrd synthesized from system extensions will be measured to both PCR 4 and PCR 9. Let's summarize
139    the OS resources and the PCRs they are measured to:</para>
140
141    <table>
142      <title>OS Resource PCR Summary</title>
143
144      <tgroup cols='2' align='left' colsep='1' rowsep='1'>
145        <colspec colname="pcr" />
146        <colspec colname="definition" />
147
148        <thead>
149          <row>
150            <entry>OS Resource</entry>
151            <entry>Measurement PCR</entry>
152          </row>
153        </thead>
154
155        <tbody>
156          <row>
157            <entry><command>systemd-stub</command> code (the entry point of the unified PE binary)</entry>
158            <entry>4</entry>
159          </row>
160
161          <row>
162            <entry>Boot splash (embedded in the unified PE binary)</entry>
163            <entry>4</entry>
164          </row>
165
166          <row>
167            <entry>Core kernel code (embedded in unified PE binary)</entry>
168            <entry>4</entry>
169          </row>
170
171          <row>
172            <entry>Main initrd (embedded in unified PE binary)</entry>
173            <entry>4 + 9</entry>
174          </row>
175
176          <row>
177            <entry>Default kernel command line (embedded in unified PE binary)</entry>
178            <entry>4</entry>
179          </row>
180
181          <row>
182            <entry>Overridden kernel command line</entry>
183            <entry>12</entry>
184          </row>
185
186          <row>
187            <entry>Credentials (synthesized initrd from companion files)</entry>
188            <entry>12 + 9</entry>
189          </row>
190
191          <row>
192            <entry>System Extensions (synthesized initrd from companion files)</entry>
193            <entry>4 + 9</entry>
194          </row>
195        </tbody>
196      </tgroup>
197    </table>
198  </refsect1>
199
200  <refsect1>
201    <title>EFI Variables</title>
202
203    <para>The following EFI variables are defined, set and read by <command>systemd-stub</command>, under the
204    vendor UUID <literal>4a67b082-0a4c-41cf-b6c7-440b29bb8c4f</literal>, for communication between the boot
205    stub and the OS:</para>
206
207    <variablelist class='efi-variables'>
208      <varlistentry>
209        <term><varname>LoaderDevicePartUUID</varname></term>
210
211        <listitem><para>Contains the partition UUID of the EFI System Partition the EFI image was run
212        from. <citerefentry><refentrytitle>systemd-gpt-auto-generator</refentrytitle><manvolnum>8</manvolnum></citerefentry>
213        uses this information to automatically find the disk booted from, in order to discover various other
214        partitions on the same disk automatically.</para></listitem>
215      </varlistentry>
216
217      <varlistentry>
218        <term><varname>LoaderFirmwareInfo</varname></term>
219        <term><varname>LoaderFirmwareType</varname></term>
220
221        <listitem><para>Brief firmware information. Use
222        <citerefentry><refentrytitle>bootctl</refentrytitle><manvolnum>1</manvolnum></citerefentry> to view this
223        data.</para></listitem>
224      </varlistentry>
225
226      <varlistentry>
227        <term><varname>LoaderImageIdentifier</varname></term>
228
229        <listitem><para>The path of EFI executable, relative to the EFI System Partition's root
230        directory. Use
231        <citerefentry><refentrytitle>bootctl</refentrytitle><manvolnum>1</manvolnum></citerefentry> to view
232        this data.</para></listitem>
233      </varlistentry>
234
235      <varlistentry>
236        <term><varname>StubInfo</varname></term>
237
238        <listitem><para>Brief stub information. Use
239        <citerefentry><refentrytitle>bootctl</refentrytitle><manvolnum>1</manvolnum></citerefentry> to view
240        this data.</para></listitem>
241      </varlistentry>
242    </variablelist>
243
244    <para>Note that some of the variables above may also be set by the boot loader. The stub will only set
245    them if they aren't set already. Some of these variables are defined by the <ulink
246    url="https://systemd.io/BOOT_LOADER_INTERFACE">Boot Loader Interface</ulink>.</para>
247  </refsect1>
248
249  <refsect1>
250    <title>Assembling Kernel Images</title>
251
252    <para>In order to assemble an UEFI PE kernel image from various components as described above, use an
253    <citerefentry project='man-pages'><refentrytitle>objcopy</refentrytitle><manvolnum>1</manvolnum></citerefentry> command line
254    like this:</para>
255
256    <programlisting>objcopy \
257    --add-section .osrel=os-release --change-section-vma .osrel=0x20000 \
258    --add-section .cmdline=cmdline.txt --change-section-vma .cmdline=0x30000 \
259    --add-section .dtb=devicetree.dtb --change-section-vma .dtb=0x40000 \
260    --add-section .splash=splash.bmp --change-section-vma .splash=0x100000 \
261    --add-section .linux=vmlinux --change-section-vma .linux=0x2000000 \
262    --add-section .initrd=initrd.cpio --change-section-vma .initrd=0x3000000 \
263    /usr/lib/systemd/boot/efi/linuxx64.efi.stub \
264    foo-unsigned.efi</programlisting>
265
266    <para>This generates one PE executable file <filename>foo-unsigned.efi</filename> from the six individual
267    files for OS release information, kernel command line, boot splash image, kernel image, main initrd and
268    UEFI boot stub.</para>
269
270    <para>To then sign the resulting image for UEFI SecureBoot use an
271    <citerefentry project='archlinux'><refentrytitle>sbsign</refentrytitle><manvolnum>1</manvolnum></citerefentry> command like
272    the following:</para>
273
274    <programlisting>sbsign \
275    --key mykey.pem \
276    --cert mykey.crt \
277    --output foo.efi \
278    foo-unsigned.efi</programlisting>
279
280    <para>This expects a pair of X.509 private key and certificate as parameters and then signs the UEFI PE
281    executable we generated above for UEFI SecureBoot and generates a signed UEFI PE executable as
282    result.</para>
283  </refsect1>
284
285  <refsect1>
286    <title>See Also</title>
287    <para>
288      <citerefentry><refentrytitle>systemd-boot</refentrytitle><manvolnum>7</manvolnum></citerefentry>,
289      <citerefentry><refentrytitle>systemd.exec</refentrytitle><manvolnum>5</manvolnum></citerefentry>,
290      <citerefentry><refentrytitle>systemd-creds</refentrytitle><manvolnum>1</manvolnum></citerefentry>,
291      <citerefentry><refentrytitle>systemd-sysext</refentrytitle><manvolnum>8</manvolnum></citerefentry>,
292      <ulink url="https://systemd.io/BOOT_LOADER_SPECIFICATION">Boot Loader Specification</ulink>,
293      <ulink url="https://systemd.io/BOOT_LOADER_INTERFACE">Boot Loader Interface</ulink>,
294      <citerefentry project='man-pages'><refentrytitle>objcopy</refentrytitle><manvolnum>1</manvolnum></citerefentry>,
295      <citerefentry project='archlinux'><refentrytitle>sbsign</refentrytitle><manvolnum>1</manvolnum></citerefentry>
296    </para>
297  </refsect1>
298</refentry>
299