]>
Commit | Line | Data |
---|---|---|
c7320ed5 SG |
1 | Verified Boot on the Beaglebone Black |
2 | ===================================== | |
3 | ||
4 | Introduction | |
5 | ------------ | |
6 | ||
7 | Before reading this, please read verified-boot.txt and signature.txt. These | |
8 | instructions are for mainline U-Boot from v2014.07 onwards. | |
9 | ||
10 | There is quite a bit of documentation in this directory describing how | |
11 | verified boot works in U-Boot. There is also a test which runs through the | |
12 | entire process of signing an image and running U-Boot (sandbox) to check it. | |
13 | However, it might be useful to also have an example on a real board. | |
14 | ||
15 | Beaglebone Black is a fairly common board so seems to be a reasonable choice | |
16 | for an example of how to enable verified boot using U-Boot. | |
17 | ||
18 | First a note that may to help avoid confusion. U-Boot and Linux both use | |
19 | device tree. They may use the same device tree source, but it is seldom useful | |
20 | for them to use the exact same binary from the same place. More typically, | |
21 | U-Boot has its device tree packaged wtih it, and the kernel's device tree is | |
22 | packaged with the kernel. In particular this is important with verified boot, | |
23 | since U-Boot's device tree must be immutable. If it can be changed then the | |
24 | public keys can be changed and verified boot is useless. An attacker can | |
25 | simply generate a new key and put his public key into U-Boot so that | |
26 | everything verifies. On the other hand the kernel's device tree typically | |
27 | changes when the kernel changes, so it is useful to package an updated device | |
28 | tree with the kernel binary. U-Boot supports the latter with its flexible FIT | |
29 | format (Flat Image Tree). | |
30 | ||
31 | ||
32 | Overview | |
33 | -------- | |
34 | ||
35 | The steps are roughly as follows: | |
36 | ||
37 | 1. Build U-Boot for the board, with the verified boot options enabled. | |
38 | ||
39 | 2. Obtain a suitable Linux kernel | |
40 | ||
41 | 3. Create a Image Tree Source file (ITS) file describing how you want the | |
42 | kernel to be packaged, compressed and signed. | |
43 | ||
44 | 4. Create a key pair | |
45 | ||
46 | 5. Sign the kernel | |
47 | ||
48 | 6. Put the public key into U-Boot's image | |
49 | ||
50 | 7. Put U-Boot and the kernel onto the board | |
51 | ||
52 | 8. Try it | |
53 | ||
54 | ||
55 | Step 1: Build U-Boot | |
56 | -------------------- | |
57 | ||
58 | a. Set up the environment variable to point to your toolchain. You will need | |
59 | this for U-Boot and also for the kernel if you build it. For example if you | |
60 | installed a Linaro version manually it might be something like: | |
61 | ||
62 | export CROSS_COMPILE=/opt/linaro/gcc-linaro-arm-linux-gnueabihf-4.8-2013.08_linux/bin/arm-linux-gnueabihf- | |
63 | ||
64 | or if you just installed gcc-arm-linux-gnueabi then it might be | |
65 | ||
66 | export CROSS_COMPILE=arm-linux-gnueabi- | |
67 | ||
68 | b. Configure and build U-Boot with verified boot enabled: | |
69 | ||
c7320ed5 SG |
70 | export UBOOT=/path/to/u-boot |
71 | cd $UBOOT | |
72 | # You can add -j10 if you have 10 CPUs to make it faster | |
73 | make O=b/am335x_boneblack_vboot am335x_boneblack_vboot_config all | |
74 | export UOUT=$UBOOT/b/am335x_boneblack_vboot | |
75 | ||
76 | c. You will now have a U-Boot image: | |
77 | ||
78 | file b/am335x_boneblack_vboot/u-boot-dtb.img | |
79 | b/am335x_boneblack_vboot/u-boot-dtb.img: u-boot legacy uImage, U-Boot 2014.07-rc2-00065-g2f69f8, Firmware/ARM, Firmware Image (Not compressed), 395375 bytes, Sat May 31 16:19:04 2014, Load Address: 0x80800000, Entry Point: 0x00000000, Header CRC: 0x0ABD6ACA, Data CRC: 0x36DEF7E4 | |
80 | ||
81 | ||
82 | Step 2: Build Linux | |
83 | -------------------- | |
84 | ||
85 | a. Find the kernel image ('Image') and device tree (.dtb) file you plan to | |
86 | use. In our case it is am335x-boneblack.dtb and it is built with the kernel. | |
87 | At the time of writing an SD Boot image can be obtained from here: | |
88 | ||
89 | http://www.elinux.org/Beagleboard:Updating_The_Software#Image_For_Booting_From_microSD | |
90 | ||
91 | You can write this to an SD card and then mount it to extract the kernel and | |
92 | device tree files. | |
93 | ||
94 | You can also build a kernel. Instructions for this are are here: | |
95 | ||
96 | http://elinux.org/Building_BBB_Kernel | |
97 | ||
98 | or you can use your favourite search engine. Following these instructions | |
99 | produces a kernel Image and device tree files. For the record the steps were: | |
100 | ||
101 | export KERNEL=/path/to/kernel | |
102 | cd $KERNEL | |
103 | git clone git://github.com/beagleboard/kernel.git . | |
104 | git checkout v3.14 | |
105 | ./patch.sh | |
106 | cp configs/beaglebone kernel/arch/arm/configs/beaglebone_defconfig | |
107 | cd kernel | |
108 | make beaglebone_defconfig | |
109 | make uImage dtbs # -j10 if you have 10 CPUs | |
110 | export OKERNEL=$KERNEL/kernel/arch/arm/boot | |
111 | ||
112 | c. You now have the 'Image' and 'am335x-boneblack.dtb' files needed to boot. | |
113 | ||
114 | ||
115 | Step 3: Create the ITS | |
116 | ---------------------- | |
117 | ||
118 | Set up a directory for your work. | |
119 | ||
120 | export WORK=/path/to/dir | |
121 | cd $WORK | |
122 | ||
123 | Put this into a file in that directory called sign.its: | |
124 | ||
125 | /dts-v1/; | |
126 | ||
127 | / { | |
128 | description = "Beaglebone black"; | |
129 | #address-cells = <1>; | |
130 | ||
131 | images { | |
83840405 | 132 | kernel { |
c7320ed5 SG |
133 | data = /incbin/("Image.lzo"); |
134 | type = "kernel"; | |
135 | arch = "arm"; | |
136 | os = "linux"; | |
137 | compression = "lzo"; | |
138 | load = <0x80008000>; | |
139 | entry = <0x80008000>; | |
83840405 | 140 | hash-1 { |
c7320ed5 SG |
141 | algo = "sha1"; |
142 | }; | |
143 | }; | |
83840405 | 144 | fdt-1 { |
c7320ed5 SG |
145 | description = "beaglebone-black"; |
146 | data = /incbin/("am335x-boneblack.dtb"); | |
147 | type = "flat_dt"; | |
148 | arch = "arm"; | |
149 | compression = "none"; | |
83840405 | 150 | hash-1 { |
c7320ed5 SG |
151 | algo = "sha1"; |
152 | }; | |
153 | }; | |
154 | }; | |
155 | configurations { | |
83840405 AP |
156 | default = "conf-1"; |
157 | conf-1 { | |
158 | kernel = "kernel"; | |
159 | fdt = "fdt-1"; | |
160 | signature-1 { | |
c7320ed5 SG |
161 | algo = "sha1,rsa2048"; |
162 | key-name-hint = "dev"; | |
163 | sign-images = "fdt", "kernel"; | |
164 | }; | |
165 | }; | |
166 | }; | |
167 | }; | |
168 | ||
169 | ||
170 | The explanation for this is all in the documentation you have already read. | |
171 | But briefly it packages a kernel and device tree, and provides a single | |
172 | configuration to be signed with a key named 'dev'. The kernel is compressed | |
173 | with LZO to make it smaller. | |
174 | ||
175 | ||
176 | Step 4: Create a key pair | |
177 | ------------------------- | |
178 | ||
179 | See signature.txt for details on this step. | |
180 | ||
181 | cd $WORK | |
182 | mkdir keys | |
183 | openssl genrsa -F4 -out keys/dev.key 2048 | |
184 | openssl req -batch -new -x509 -key keys/dev.key -out keys/dev.crt | |
185 | ||
186 | Note: keys/dev.key contains your private key and is very secret. If anyone | |
187 | gets access to that file they can sign kernels with it. Keep it secure. | |
188 | ||
189 | ||
190 | Step 5: Sign the kernel | |
191 | ----------------------- | |
192 | ||
193 | We need to use mkimage (which was built when you built U-Boot) to package the | |
194 | Linux kernel into a FIT (Flat Image Tree, a flexible file format that U-Boot | |
195 | can load) using the ITS file you just created. | |
196 | ||
197 | At the same time we must put the public key into U-Boot device tree, with the | |
198 | 'required' property, which tells U-Boot that this key must be verified for the | |
199 | image to be valid. You will make this key available to U-Boot for booting in | |
200 | step 6. | |
201 | ||
202 | ln -s $OKERNEL/dts/am335x-boneblack.dtb | |
203 | ln -s $OKERNEL/Image | |
204 | ln -s $UOUT/u-boot-dtb.img | |
205 | cp $UOUT/arch/arm/dts/am335x-boneblack.dtb am335x-boneblack-pubkey.dtb | |
206 | lzop Image | |
207 | $UOUT/tools/mkimage -f sign.its -K am335x-boneblack-pubkey.dtb -k keys -r image.fit | |
208 | ||
209 | You should see something like this: | |
210 | ||
211 | FIT description: Beaglebone black | |
212 | Created: Sun Jun 1 12:50:30 2014 | |
83840405 | 213 | Image 0 (kernel) |
c7320ed5 SG |
214 | Description: unavailable |
215 | Created: Sun Jun 1 12:50:30 2014 | |
216 | Type: Kernel Image | |
217 | Compression: lzo compressed | |
218 | Data Size: 7790938 Bytes = 7608.34 kB = 7.43 MB | |
219 | Architecture: ARM | |
220 | OS: Linux | |
221 | Load Address: 0x80008000 | |
222 | Entry Point: 0x80008000 | |
223 | Hash algo: sha1 | |
224 | Hash value: c94364646427e10f423837e559898ef02c97b988 | |
83840405 | 225 | Image 1 (fdt-1) |
c7320ed5 SG |
226 | Description: beaglebone-black |
227 | Created: Sun Jun 1 12:50:30 2014 | |
228 | Type: Flat Device Tree | |
229 | Compression: uncompressed | |
230 | Data Size: 31547 Bytes = 30.81 kB = 0.03 MB | |
231 | Architecture: ARM | |
232 | Hash algo: sha1 | |
233 | Hash value: cb09202f889d824f23b8e4404b781be5ad38a68d | |
83840405 AP |
234 | Default Configuration: 'conf-1' |
235 | Configuration 0 (conf-1) | |
c7320ed5 | 236 | Description: unavailable |
83840405 AP |
237 | Kernel: kernel |
238 | FDT: fdt-1 | |
c7320ed5 SG |
239 | |
240 | ||
241 | Now am335x-boneblack-pubkey.dtb contains the public key and image.fit contains | |
242 | the signed kernel. Jump to step 6 if you like, or continue reading to increase | |
243 | your understanding. | |
244 | ||
245 | You can also run fit_check_sign to check it: | |
246 | ||
247 | $UOUT/tools/fit_check_sign -f image.fit -k am335x-boneblack-pubkey.dtb | |
248 | ||
249 | which results in: | |
250 | ||
251 | Verifying Hash Integrity ... sha1,rsa2048:dev+ | |
252 | ## Loading kernel from FIT Image at 7fc6ee469000 ... | |
83840405 | 253 | Using 'conf-1' configuration |
c7320ed5 SG |
254 | Verifying Hash Integrity ... |
255 | sha1,rsa2048:dev+ | |
256 | OK | |
257 | ||
83840405 | 258 | Trying 'kernel' kernel subimage |
c7320ed5 SG |
259 | Description: unavailable |
260 | Created: Sun Jun 1 12:50:30 2014 | |
261 | Type: Kernel Image | |
262 | Compression: lzo compressed | |
263 | Data Size: 7790938 Bytes = 7608.34 kB = 7.43 MB | |
264 | Architecture: ARM | |
265 | OS: Linux | |
266 | Load Address: 0x80008000 | |
267 | Entry Point: 0x80008000 | |
268 | Hash algo: sha1 | |
269 | Hash value: c94364646427e10f423837e559898ef02c97b988 | |
270 | Verifying Hash Integrity ... | |
271 | sha1+ | |
272 | OK | |
273 | ||
274 | Unimplemented compression type 4 | |
275 | ## Loading fdt from FIT Image at 7fc6ee469000 ... | |
83840405 AP |
276 | Using 'conf-1' configuration |
277 | Trying 'fdt-1' fdt subimage | |
c7320ed5 SG |
278 | Description: beaglebone-black |
279 | Created: Sun Jun 1 12:50:30 2014 | |
280 | Type: Flat Device Tree | |
281 | Compression: uncompressed | |
282 | Data Size: 31547 Bytes = 30.81 kB = 0.03 MB | |
283 | Architecture: ARM | |
284 | Hash algo: sha1 | |
285 | Hash value: cb09202f889d824f23b8e4404b781be5ad38a68d | |
286 | Verifying Hash Integrity ... | |
287 | sha1+ | |
288 | OK | |
289 | ||
290 | Loading Flat Device Tree ... OK | |
291 | ||
292 | ## Loading ramdisk from FIT Image at 7fc6ee469000 ... | |
83840405 | 293 | Using 'conf-1' configuration |
c7320ed5 SG |
294 | Could not find subimage node |
295 | ||
296 | Signature check OK | |
297 | ||
298 | ||
299 | At the top, you see "sha1,rsa2048:dev+". This means that it checked an RSA key | |
300 | of size 2048 bits using SHA1 as the hash algorithm. The key name checked was | |
301 | 'dev' and the '+' means that it verified. If it showed '-' that would be bad. | |
302 | ||
303 | Once the configuration is verified it is then possible to rely on the hashes | |
304 | in each image referenced by that configuration. So fit_check_sign goes on to | |
305 | load each of the images. We have a kernel and an FDT but no ramkdisk. In each | |
306 | case fit_check_sign checks the hash and prints sha1+ meaning that the SHA1 | |
307 | hash verified. This means that none of the images has been tampered with. | |
308 | ||
309 | There is a test in test/vboot which uses U-Boot's sandbox build to verify that | |
310 | the above flow works. | |
311 | ||
312 | But it is fun to do this by hand, so you can load image.fit into a hex editor | |
313 | like ghex, and change a byte in the kernel: | |
314 | ||
83840405 AP |
315 | $UOUT/tools/fit_info -f image.fit -n /images/kernel -p data |
316 | NAME: kernel | |
c7320ed5 SG |
317 | LEN: 7790938 |
318 | OFF: 168 | |
319 | ||
320 | This tells us that the kernel starts at byte offset 168 (decimal) in image.fit | |
321 | and extends for about 7MB. Try changing a byte at 0x2000 (say) and run | |
322 | fit_check_sign again. You should see something like: | |
323 | ||
324 | Verifying Hash Integrity ... sha1,rsa2048:dev+ | |
325 | ## Loading kernel from FIT Image at 7f5a39571000 ... | |
83840405 | 326 | Using 'conf-1' configuration |
c7320ed5 SG |
327 | Verifying Hash Integrity ... |
328 | sha1,rsa2048:dev+ | |
329 | OK | |
330 | ||
83840405 | 331 | Trying 'kernel' kernel subimage |
c7320ed5 SG |
332 | Description: unavailable |
333 | Created: Sun Jun 1 13:09:21 2014 | |
334 | Type: Kernel Image | |
335 | Compression: lzo compressed | |
336 | Data Size: 7790938 Bytes = 7608.34 kB = 7.43 MB | |
337 | Architecture: ARM | |
338 | OS: Linux | |
339 | Load Address: 0x80008000 | |
340 | Entry Point: 0x80008000 | |
341 | Hash algo: sha1 | |
342 | Hash value: c94364646427e10f423837e559898ef02c97b988 | |
343 | Verifying Hash Integrity ... | |
344 | sha1 error | |
83840405 | 345 | Bad hash value for 'hash-1' hash node in 'kernel' image node |
c7320ed5 SG |
346 | Bad Data Hash |
347 | ||
348 | ## Loading fdt from FIT Image at 7f5a39571000 ... | |
83840405 AP |
349 | Using 'conf-1' configuration |
350 | Trying 'fdt-1' fdt subimage | |
c7320ed5 SG |
351 | Description: beaglebone-black |
352 | Created: Sun Jun 1 13:09:21 2014 | |
353 | Type: Flat Device Tree | |
354 | Compression: uncompressed | |
355 | Data Size: 31547 Bytes = 30.81 kB = 0.03 MB | |
356 | Architecture: ARM | |
357 | Hash algo: sha1 | |
358 | Hash value: cb09202f889d824f23b8e4404b781be5ad38a68d | |
359 | Verifying Hash Integrity ... | |
360 | sha1+ | |
361 | OK | |
362 | ||
363 | Loading Flat Device Tree ... OK | |
364 | ||
365 | ## Loading ramdisk from FIT Image at 7f5a39571000 ... | |
83840405 | 366 | Using 'conf-1' configuration |
c7320ed5 SG |
367 | Could not find subimage node |
368 | ||
369 | Signature check Bad (error 1) | |
370 | ||
371 | ||
372 | It has detected the change in the kernel. | |
373 | ||
374 | You can also be sneaky and try to switch images, using the libfdt utilities | |
375 | that come with dtc (package name is device-tree-compiler but you will need a | |
376 | recent version like 1.4: | |
377 | ||
378 | dtc -v | |
379 | Version: DTC 1.4.0 | |
380 | ||
381 | First we can check which nodes are actually hashed by the configuration: | |
382 | ||
383 | fdtget -l image.fit / | |
384 | images | |
385 | configurations | |
386 | ||
387 | fdtget -l image.fit /configurations | |
83840405 AP |
388 | conf-1 |
389 | fdtget -l image.fit /configurations/conf-1 | |
390 | signature-1 | |
c7320ed5 | 391 | |
83840405 | 392 | fdtget -p image.fit /configurations/conf-1/signature-1 |
c7320ed5 SG |
393 | hashed-strings |
394 | hashed-nodes | |
395 | timestamp | |
396 | signer-version | |
397 | signer-name | |
398 | value | |
399 | algo | |
400 | key-name-hint | |
401 | sign-images | |
402 | ||
83840405 AP |
403 | fdtget image.fit /configurations/conf-1/signature-1 hashed-nodes |
404 | / /configurations/conf-1 /images/fdt-1 /images/fdt-1/hash /images/kernel /images/kernel/hash-1 | |
c7320ed5 SG |
405 | |
406 | This gives us a bit of a look into the signature that mkimage added. Note you | |
407 | can also use fdtdump to list the entire device tree. | |
408 | ||
409 | Say we want to change the kernel that this configuration uses | |
83840405 | 410 | (/images/kernel). We could just put a new kernel in the image, but we will |
c7320ed5 SG |
411 | need to change the hash to match. Let's simulate that by changing a byte of |
412 | the hash: | |
413 | ||
83840405 | 414 | fdtget -tx image.fit /images/kernel/hash-1 value |
c7320ed5 | 415 | c9436464 6427e10f 423837e5 59898ef0 2c97b988 |
83840405 | 416 | fdtput -tx image.fit /images/kernel/hash-1 value c9436464 6427e10f 423837e5 59898ef0 2c97b981 |
c7320ed5 SG |
417 | |
418 | Now check it again: | |
419 | ||
420 | $UOUT/tools/fit_check_sign -f image.fit -k am335x-boneblack-pubkey.dtb | |
421 | Verifying Hash Integrity ... sha1,rsa2048:devrsa_verify_with_keynode: RSA failed to verify: -13 | |
422 | rsa_verify_with_keynode: RSA failed to verify: -13 | |
423 | - | |
424 | Failed to verify required signature 'key-dev' | |
425 | Signature check Bad (error 1) | |
426 | ||
427 | This time we don't even get as far as checking the images, since the | |
428 | configuration signature doesn't match. We can't change any hashes without the | |
429 | signature check noticing. The configuration is essentially locked. U-Boot has | |
430 | a public key for which it requires a match, and will not permit the use of any | |
431 | configuration that does not match that public key. The only way the | |
432 | configuration will match is if it was signed by the matching private key. | |
433 | ||
434 | It would also be possible to add a new signature node that does match your new | |
435 | configuration. But that won't work since you are not allowed to change the | |
436 | configuration in any way. Try it with a fresh (valid) image if you like by | |
437 | running the mkimage link again. Then: | |
438 | ||
83840405 | 439 | fdtput -p image.fit /configurations/conf-1/signature-1 value fred |
c7320ed5 SG |
440 | $UOUT/tools/fit_check_sign -f image.fit -k am335x-boneblack-pubkey.dtb |
441 | Verifying Hash Integrity ... - | |
442 | sha1,rsa2048:devrsa_verify_with_keynode: RSA failed to verify: -13 | |
443 | rsa_verify_with_keynode: RSA failed to verify: -13 | |
444 | - | |
445 | Failed to verify required signature 'key-dev' | |
446 | Signature check Bad (error 1) | |
447 | ||
448 | ||
449 | Of course it would be possible to add an entirely new configuration and boot | |
450 | with that, but it still needs to be signed, so it won't help. | |
451 | ||
452 | ||
453 | 6. Put the public key into U-Boot's image | |
454 | ----------------------------------------- | |
455 | ||
456 | Having confirmed that the signature is doing its job, let's try it out in | |
457 | U-Boot on the board. U-Boot needs access to the public key corresponding to | |
458 | the private key that you signed with so that it can verify any kernels that | |
459 | you sign. | |
460 | ||
461 | cd $UBOOT | |
462 | make O=b/am335x_boneblack_vboot EXT_DTB=${WORK}/am335x-boneblack-pubkey.dtb | |
463 | ||
612e9912 | 464 | Here we are overriding the normal device tree file with our one, which |
c7320ed5 SG |
465 | contains the public key. |
466 | ||
467 | Now you have a special U-Boot image with the public key. It can verify can | |
468 | kernel that you sign with the private key as in step 5. | |
469 | ||
470 | If you like you can take a look at the public key information that mkimage | |
471 | added to U-Boot's device tree: | |
472 | ||
473 | fdtget -p am335x-boneblack-pubkey.dtb /signature/key-dev | |
474 | required | |
475 | algo | |
476 | rsa,r-squared | |
477 | rsa,modulus | |
478 | rsa,n0-inverse | |
479 | rsa,num-bits | |
480 | key-name-hint | |
481 | ||
482 | This has information about the key and some pre-processed values which U-Boot | |
483 | can use to verify against it. These values are obtained from the public key | |
484 | certificate by mkimage, but require quite a bit of code to generate. To save | |
485 | code space in U-Boot, the information is extracted and written in raw form for | |
486 | U-Boot to easily use. The same mechanism is used in Google's Chrome OS. | |
487 | ||
488 | Notice the 'required' property. This marks the key as required - U-Boot will | |
489 | not boot any image that does not verify against this key. | |
490 | ||
491 | ||
492 | 7. Put U-Boot and the kernel onto the board | |
493 | ------------------------------------------- | |
494 | ||
495 | The method here varies depending on how you are booting. For this example we | |
496 | are booting from an micro-SD card with two partitions, one for U-Boot and one | |
497 | for Linux. Put it into your machine and write U-Boot and the kernel to it. | |
498 | Here the card is /dev/sde: | |
499 | ||
500 | cd $WORK | |
501 | export UDEV=/dev/sde1 # Change thes two lines to the correct device | |
502 | export KDEV=/dev/sde2 | |
503 | sudo mount $UDEV /mnt/tmp && sudo cp $UOUT/u-boot-dtb.img /mnt/tmp/u-boot.img && sleep 1 && sudo umount $UDEV | |
504 | sudo mount $KDEV /mnt/tmp && sudo cp $WORK/image.fit /mnt/tmp/boot/image.fit && sleep 1 && sudo umount $KDEV | |
505 | ||
506 | ||
507 | 8. Try it | |
508 | --------- | |
509 | ||
510 | Boot the board using the commands below: | |
511 | ||
512 | setenv bootargs console=ttyO0,115200n8 quiet root=/dev/mmcblk0p2 ro rootfstype=ext4 rootwait | |
513 | ext2load mmc 0:2 82000000 /boot/image.fit | |
514 | bootm 82000000 | |
515 | ||
516 | You should then see something like this: | |
517 | ||
518 | U-Boot# setenv bootargs console=ttyO0,115200n8 quiet root=/dev/mmcblk0p2 ro rootfstype=ext4 rootwait | |
519 | U-Boot# ext2load mmc 0:2 82000000 /boot/image.fit | |
520 | 7824930 bytes read in 589 ms (12.7 MiB/s) | |
521 | U-Boot# bootm 82000000 | |
522 | ## Loading kernel from FIT Image at 82000000 ... | |
83840405 | 523 | Using 'conf-1' configuration |
c7320ed5 | 524 | Verifying Hash Integrity ... sha1,rsa2048:dev+ OK |
83840405 | 525 | Trying 'kernel' kernel subimage |
c7320ed5 SG |
526 | Description: unavailable |
527 | Created: 2014-06-01 19:32:54 UTC | |
528 | Type: Kernel Image | |
529 | Compression: lzo compressed | |
530 | Data Start: 0x820000a8 | |
531 | Data Size: 7790938 Bytes = 7.4 MiB | |
532 | Architecture: ARM | |
533 | OS: Linux | |
534 | Load Address: 0x80008000 | |
535 | Entry Point: 0x80008000 | |
536 | Hash algo: sha1 | |
537 | Hash value: c94364646427e10f423837e559898ef02c97b988 | |
538 | Verifying Hash Integrity ... sha1+ OK | |
539 | ## Loading fdt from FIT Image at 82000000 ... | |
83840405 AP |
540 | Using 'conf-1' configuration |
541 | Trying 'fdt-1' fdt subimage | |
c7320ed5 SG |
542 | Description: beaglebone-black |
543 | Created: 2014-06-01 19:32:54 UTC | |
544 | Type: Flat Device Tree | |
545 | Compression: uncompressed | |
546 | Data Start: 0x8276e2ec | |
547 | Data Size: 31547 Bytes = 30.8 KiB | |
548 | Architecture: ARM | |
549 | Hash algo: sha1 | |
550 | Hash value: cb09202f889d824f23b8e4404b781be5ad38a68d | |
551 | Verifying Hash Integrity ... sha1+ OK | |
552 | Booting using the fdt blob at 0x8276e2ec | |
553 | Uncompressing Kernel Image ... OK | |
554 | Loading Device Tree to 8fff5000, end 8ffffb3a ... OK | |
555 | ||
556 | Starting kernel ... | |
557 | ||
558 | [ 0.582377] omap_init_mbox: hwmod doesn't have valid attrs | |
559 | [ 2.589651] musb-hdrc musb-hdrc.0.auto: Failed to request rx1. | |
560 | [ 2.595830] musb-hdrc musb-hdrc.0.auto: musb_init_controller failed with status -517 | |
561 | [ 2.606470] musb-hdrc musb-hdrc.1.auto: Failed to request rx1. | |
562 | [ 2.612723] musb-hdrc musb-hdrc.1.auto: musb_init_controller failed with status -517 | |
563 | [ 2.940808] drivers/rtc/hctosys.c: unable to open rtc device (rtc0) | |
564 | [ 7.248889] libphy: PHY 4a101000.mdio:01 not found | |
565 | [ 7.253995] net eth0: phy 4a101000.mdio:01 not found on slave 1 | |
566 | systemd-fsck[83]: Angstrom: clean, 50607/218160 files, 306348/872448 blocks | |
567 | ||
568 | .---O---. | |
569 | | | .-. o o | |
570 | | | |-----.-----.-----.| | .----..-----.-----. | |
571 | | | | __ | ---'| '--.| .-'| | | | |
572 | | | | | | |--- || --'| | | ' | | | | | |
573 | '---'---'--'--'--. |-----''----''--' '-----'-'-'-' | |
574 | -' | | |
575 | '---' | |
576 | ||
577 | The Angstrom Distribution beaglebone ttyO0 | |
578 | ||
579 | Angstrom v2012.12 - Kernel 3.14.1+ | |
580 | ||
581 | beaglebone login: | |
582 | ||
583 | At this point your kernel has been verified and you can be sure that it is one | |
584 | that you signed. As an exercise, try changing image.fit as in step 5 and see | |
585 | what happens. | |
586 | ||
587 | ||
588 | Further Improvements | |
589 | -------------------- | |
590 | ||
591 | Several of the steps here can be easily automated. In particular it would be | |
592 | capital if signing and packaging a kernel were easy, perhaps a simple make | |
593 | target in the kernel. | |
594 | ||
595 | Some mention of how to use multiple .dtb files in a FIT might be useful. | |
596 | ||
597 | U-Boot's verified boot mechanism has not had a robust and independent security | |
598 | review. Such a review should look at the implementation and its resistance to | |
599 | attacks. | |
600 | ||
601 | Perhaps the verified boot feature could could be integrated into the Amstrom | |
602 | distribution. | |
603 | ||
604 | ||
605 | Simon Glass | |
606 | [email protected] | |
607 | 2-June-14 |