Merge tag 'u-boot-imx-20200825' of https://gitlab.denx.de/u-boot/custodians/u-boot-imx
[platform/kernel/u-boot.git] / test / py / tests / test_efi_secboot / test_signed.py
1 # SPDX-License-Identifier:      GPL-2.0+
2 # Copyright (c) 2019, Linaro Limited
3 # Author: AKASHI Takahiro <takahiro.akashi@linaro.org>
4 #
5 # U-Boot UEFI: Signed Image Authentication Test
6
7 """
8 This test verifies image authentication for signed images.
9 """
10
11 import pytest
12
13
14 @pytest.mark.boardspec('sandbox')
15 @pytest.mark.buildconfigspec('efi_secure_boot')
16 @pytest.mark.buildconfigspec('cmd_efidebug')
17 @pytest.mark.buildconfigspec('cmd_fat')
18 @pytest.mark.buildconfigspec('cmd_nvedit_efi')
19 @pytest.mark.slow
20 class TestEfiSignedImage(object):
21     def test_efi_signed_image_auth1(self, u_boot_console, efi_boot_env):
22         """
23         Test Case 1 - Secure boot is not in force
24         """
25         u_boot_console.restart_uboot()
26         disk_img = efi_boot_env
27         with u_boot_console.log.section('Test Case 1a'):
28             # Test Case 1a, run signed image if no PK
29             output = u_boot_console.run_command_list([
30                 'host bind 0 %s' % disk_img,
31                 'efidebug boot add 1 HELLO1 host 0:1 /helloworld.efi.signed ""',
32                 'efidebug boot next 1',
33                 'bootefi bootmgr'])
34             assert 'Hello, world!' in ''.join(output)
35
36         with u_boot_console.log.section('Test Case 1b'):
37             # Test Case 1b, run unsigned image if no PK
38             output = u_boot_console.run_command_list([
39                 'efidebug boot add 2 HELLO2 host 0:1 /helloworld.efi ""',
40                 'efidebug boot next 2',
41                 'bootefi bootmgr'])
42             assert 'Hello, world!' in ''.join(output)
43
44     def test_efi_signed_image_auth2(self, u_boot_console, efi_boot_env):
45         """
46         Test Case 2 - Secure boot is in force,
47                       authenticated by db (TEST_db certificate in db)
48         """
49         u_boot_console.restart_uboot()
50         disk_img = efi_boot_env
51         with u_boot_console.log.section('Test Case 2a'):
52             # Test Case 2a, db is not yet installed
53             output = u_boot_console.run_command_list([
54                 'host bind 0 %s' % disk_img,
55                 'fatload host 0:1 4000000 KEK.auth',
56                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize KEK',
57                 'fatload host 0:1 4000000 PK.auth',
58                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize PK'])
59             assert 'Failed to set EFI variable' not in ''.join(output)
60             output = u_boot_console.run_command_list([
61                 'efidebug boot add 1 HELLO1 host 0:1 /helloworld.efi.signed ""',
62                 'efidebug boot next 1',
63                 'efidebug test bootmgr'])
64             assert('\'HELLO1\' failed' in ''.join(output))
65             assert('efi_start_image() returned: 26' in ''.join(output))
66             output = u_boot_console.run_command_list([
67                 'efidebug boot add 2 HELLO2 host 0:1 /helloworld.efi ""',
68                 'efidebug boot next 2',
69                 'efidebug test bootmgr'])
70             assert '\'HELLO2\' failed' in ''.join(output)
71             assert 'efi_start_image() returned: 26' in ''.join(output)
72
73         with u_boot_console.log.section('Test Case 2b'):
74             # Test Case 2b, authenticated by db
75             output = u_boot_console.run_command_list([
76                 'fatload host 0:1 4000000 db.auth',
77                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize db'])
78             assert 'Failed to set EFI variable' not in ''.join(output)
79             output = u_boot_console.run_command_list([
80                 'efidebug boot next 2',
81                 'efidebug test bootmgr'])
82             assert '\'HELLO2\' failed' in ''.join(output)
83             assert 'efi_start_image() returned: 26' in ''.join(output)
84             output = u_boot_console.run_command_list([
85                 'efidebug boot next 1',
86                 'bootefi bootmgr'])
87             assert 'Hello, world!' in ''.join(output)
88
89     def test_efi_signed_image_auth3(self, u_boot_console, efi_boot_env):
90         """
91         Test Case 3 - rejected by dbx (TEST_db certificate in dbx)
92         """
93         u_boot_console.restart_uboot()
94         disk_img = efi_boot_env
95         with u_boot_console.log.section('Test Case 3a'):
96             # Test Case 3a, rejected by dbx
97             output = u_boot_console.run_command_list([
98                 'host bind 0 %s' % disk_img,
99                 'fatload host 0:1 4000000 db.auth',
100                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize dbx',
101                 'fatload host 0:1 4000000 KEK.auth',
102                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize KEK',
103                 'fatload host 0:1 4000000 PK.auth',
104                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize PK'])
105             assert 'Failed to set EFI variable' not in ''.join(output)
106             output = u_boot_console.run_command_list([
107                 'efidebug boot add 1 HELLO host 0:1 /helloworld.efi.signed ""',
108                 'efidebug boot next 1',
109                 'efidebug test bootmgr'])
110             assert '\'HELLO\' failed' in ''.join(output)
111             assert 'efi_start_image() returned: 26' in ''.join(output)
112
113         with u_boot_console.log.section('Test Case 3b'):
114             # Test Case 3b, rejected by dbx even if db allows
115             output = u_boot_console.run_command_list([
116                 'fatload host 0:1 4000000 db.auth',
117                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize db'])
118             assert 'Failed to set EFI variable' not in ''.join(output)
119             output = u_boot_console.run_command_list([
120                 'efidebug boot next 1',
121                 'efidebug test bootmgr'])
122             assert '\'HELLO\' failed' in ''.join(output)
123             assert 'efi_start_image() returned: 26' in ''.join(output)
124
125     def test_efi_signed_image_auth4(self, u_boot_console, efi_boot_env):
126         """
127         Test Case 4 - revoked by dbx (digest of TEST_db certificate in dbx)
128         """
129         u_boot_console.restart_uboot()
130         disk_img = efi_boot_env
131         with u_boot_console.log.section('Test Case 4'):
132             # Test Case 4, rejected by dbx
133             output = u_boot_console.run_command_list([
134                 'host bind 0 %s' % disk_img,
135                 'fatload host 0:1 4000000 dbx_hash.auth',
136                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize dbx',
137                 'fatload host 0:1 4000000 db.auth',
138                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize db',
139                 'fatload host 0:1 4000000 KEK.auth',
140                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize KEK',
141                 'fatload host 0:1 4000000 PK.auth',
142                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize PK'])
143             assert 'Failed to set EFI variable' not in ''.join(output)
144             output = u_boot_console.run_command_list([
145                 'efidebug boot add 1 HELLO host 0:1 /helloworld.efi.signed ""',
146                 'efidebug boot next 1',
147                 'efidebug test bootmgr'])
148             assert '\'HELLO\' failed' in ''.join(output)
149             assert 'efi_start_image() returned: 26' in ''.join(output)
150
151     def test_efi_signed_image_auth5(self, u_boot_console, efi_boot_env):
152         """
153         Test Case 5 - multiple signatures
154                         one signed with TEST_db, and
155                         one signed with TEST_db1
156         """
157         u_boot_console.restart_uboot()
158         disk_img = efi_boot_env
159         with u_boot_console.log.section('Test Case 5a'):
160             # Test Case 5a, authenticated even if only one of signatures
161             # is verified
162             output = u_boot_console.run_command_list([
163                 'host bind 0 %s' % disk_img,
164                 'fatload host 0:1 4000000 db.auth',
165                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize db',
166                 'fatload host 0:1 4000000 KEK.auth',
167                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize KEK',
168                 'fatload host 0:1 4000000 PK.auth',
169                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize PK'])
170             assert 'Failed to set EFI variable' not in ''.join(output)
171             output = u_boot_console.run_command_list([
172                 'efidebug boot add 1 HELLO host 0:1 /helloworld.efi.signed_2sigs ""',
173                 'efidebug boot next 1',
174                 'efidebug test bootmgr'])
175             assert 'Hello, world!' in ''.join(output)
176
177         with u_boot_console.log.section('Test Case 5b'):
178             # Test Case 5b, authenticated if both signatures are verified
179             output = u_boot_console.run_command_list([
180                 'fatload host 0:1 4000000 db1.auth',
181                 'setenv -e -nv -bs -rt -at -a -i 4000000:$filesize db'])
182             assert 'Failed to set EFI variable' not in ''.join(output)
183             output = u_boot_console.run_command_list([
184                 'efidebug boot next 1',
185                 'efidebug test bootmgr'])
186             assert 'Hello, world!' in ''.join(output)
187
188         with u_boot_console.log.section('Test Case 5c'):
189             # Test Case 5c, not rejected if one of signatures (digest of
190             # certificate) is revoked
191             output = u_boot_console.run_command_list([
192                 'fatload host 0:1 4000000 dbx_hash.auth',
193                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize dbx'])
194             assert 'Failed to set EFI variable' not in ''.join(output)
195             output = u_boot_console.run_command_list([
196                 'efidebug boot next 1',
197                 'efidebug test bootmgr'])
198             assert 'Hello, world!' in ''.join(output)
199
200         with u_boot_console.log.section('Test Case 5d'):
201             # Test Case 5d, rejected if both of signatures are revoked
202             output = u_boot_console.run_command_list([
203                 'fatload host 0:1 4000000 dbx_hash1.auth',
204                 'setenv -e -nv -bs -rt -at -a -i 4000000:$filesize dbx'])
205             assert 'Failed to set EFI variable' not in ''.join(output)
206             output = u_boot_console.run_command_list([
207                 'efidebug boot next 1',
208                 'efidebug test bootmgr'])
209             assert '\'HELLO\' failed' in ''.join(output)
210             assert 'efi_start_image() returned: 26' in ''.join(output)
211
212     def test_efi_signed_image_auth6(self, u_boot_console, efi_boot_env):
213         """
214         Test Case 6 - using digest of signed image in database
215         """
216         u_boot_console.restart_uboot()
217         disk_img = efi_boot_env
218         with u_boot_console.log.section('Test Case 6a'):
219             # Test Case 6a, verified by image's digest in db
220             output = u_boot_console.run_command_list([
221                 'host bind 0 %s' % disk_img,
222                 'fatload host 0:1 4000000 db_hello_signed.auth',
223                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize db',
224                 'fatload host 0:1 4000000 KEK.auth',
225                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize KEK',
226                 'fatload host 0:1 4000000 PK.auth',
227                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize PK'])
228             assert 'Failed to set EFI variable' not in ''.join(output)
229             output = u_boot_console.run_command_list([
230                 'efidebug boot add 1 HELLO host 0:1 /helloworld.efi.signed ""',
231                 'efidebug boot next 1',
232                 'bootefi bootmgr'])
233             assert 'Hello, world!' in ''.join(output)
234
235         with u_boot_console.log.section('Test Case 6b'):
236             # Test Case 6b, rejected by TEST_db certificate in dbx
237             output = u_boot_console.run_command_list([
238                 'fatload host 0:1 4000000 dbx_db.auth',
239                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize dbx'])
240             assert 'Failed to set EFI variable' not in ''.join(output)
241             output = u_boot_console.run_command_list([
242                 'efidebug boot next 1',
243                 'efidebug test bootmgr'])
244             assert '\'HELLO\' failed' in ''.join(output)
245             assert 'efi_start_image() returned: 26' in ''.join(output)
246
247         with u_boot_console.log.section('Test Case 6c'):
248             # Test Case 6c, rejected by image's digest in dbx
249             output = u_boot_console.run_command_list([
250                 'fatload host 0:1 4000000 db.auth',
251                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize db',
252                 'fatload host 0:1 4000000 dbx_hello_signed.auth',
253                 'setenv -e -nv -bs -rt -at -i 4000000:$filesize dbx'])
254             assert 'Failed to set EFI variable' not in ''.join(output)
255             output = u_boot_console.run_command_list([
256                 'efidebug boot next 1',
257                 'efidebug test bootmgr'])
258             assert '\'HELLO\' failed' in ''.join(output)
259             assert 'efi_start_image() returned: 26' in ''.join(output)