1#!/bin/bash -u
2#
3# Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
4# Use of this source code is governed by a BSD-style license that can be
5# found in the LICENSE file.
6#
7# Quick test of vbutil_kernel args, to make sure we can pack and unpack
8# less-than-full-sized components.
9#
10
11# Load common constants and variables for tests.
12. "$(dirname "$0")/common.sh"
13
14# directories
15DEVKEYS="${ROOT_DIR}/tests/devkeys"
16DATA_DIR="${SCRIPT_DIR}/preamble_tests/data"
17TMPDIR="${TEST_DIR}/vbutil_kernel_arg_tests_dir"
18[ -d "${TMPDIR}" ] || mkdir -p "${TMPDIR}"
19
20# Arbitrarily chosen keys and config file.
21KEYBLOCK="${DATA_DIR}/kb_0_0.keyblock"
22SIGNPRIVATE="${DATA_DIR}/data_0.vbprivk"
23SIGNPUBLIC="${DATA_DIR}/root_0.vbpubk"
24CONFIG="${DATA_DIR}/dummy_config.txt"
25
26# Create some big and little files for the kernel and bootloader
27BIG="${TMPDIR}/big.bin"
28dd if=/dev/urandom bs=32768 count=1 of="${BIG}" 2>/dev/null
29SMALL="${TMPDIR}/small.bin"
30dd if=/dev/urandom bs=16 count=1 of="${SMALL}" 2>/dev/null
31
32declare -a KERN_VALS
33declare -a BOOT_VALS
34KERN_VALS=("--vmlinuz=${BIG}" "--vmlinuz=${SMALL}")
35BOOT_VALS=("--bootloader=${BIG}" "--bootloader=${SMALL}")
36
37tests=0
38errs=0
39
40# Pack a bunch of stuff
41k=0
42while [ "$k" -lt "${#KERN_VALS[*]}" ]; do
43  b=0
44  while [ "$b" -lt "${#BOOT_VALS[*]}" ]; do
45    echo -n "pack kern_${k}_${b}.vblock ... "
46    : $(( tests++ ))
47      "${FUTILITY}" vbutil_kernel \
48        --pack "${TMPDIR}/kern_${k}_${b}.vblock" \
49        --keyblock "${KEYBLOCK}" \
50        --signprivate "${SIGNPRIVATE}" \
51        --version 1 \
52        --arch arm \
53        --config "${CONFIG}" \
54        "${KERN_VALS[$k]}" \
55        "${BOOT_VALS[$k]}" >/dev/null
56      if [ "$?" -ne 0 ]; then
57        echo -e "${COL_RED}FAILED${COL_STOP}"
58        : $(( errs++ ))
59      else
60        echo -e "${COL_GREEN}PASSED${COL_STOP}"
61      fi
62    : $(( b++ ))
63  done
64  : $(( k++ ))
65done
66
67# Now unpack it
68for v in ${TMPDIR}/kern_*.vblock; do
69  : $(( tests++ ))
70  vv=$(basename "$v")
71  echo -n "verify $vv ... "
72  "${FUTILITY}" vbutil_kernel --verify "$v" >/dev/null
73  if [ "$?" -ne 0 ]; then
74    echo -e "${COL_RED}FAILED${COL_STOP}"
75    : $(( errs++ ))
76  else
77    echo -e "${COL_GREEN}PASSED${COL_STOP}"
78  fi
79  : $(( tests++ ))
80  echo -n "verify $vv signed ... "
81  "${FUTILITY}" vbutil_kernel --verify "$v" \
82    --signpubkey "${SIGNPUBLIC}" >/dev/null
83  if [ "$?" -ne 0 ]; then
84    echo -e "${COL_RED}FAILED${COL_STOP}"
85    : $(( errs++ ))
86  else
87    echo -e "${COL_GREEN}PASSED${COL_STOP}"
88  fi
89done
90
91
92
93# Test repacking a USB image for the SSD, the way the installer does.
94
95set -e
96# Pack for USB
97USB_KERN="${TMPDIR}/usb_kern.bin"
98USB_KEYBLOCK="${DEVKEYS}/recovery_kernel.keyblock"
99USB_SIGNPRIVATE="${DEVKEYS}/recovery_kernel_data_key.vbprivk"
100USB_SIGNPUBKEY="${DEVKEYS}/recovery_key.vbpubk"
101echo -n "pack USB kernel ... "
102: $(( tests++ ))
103"${FUTILITY}" vbutil_kernel \
104  --pack "${USB_KERN}" \
105  --keyblock "${USB_KEYBLOCK}" \
106  --signprivate "${USB_SIGNPRIVATE}" \
107  --version 1 \
108  --config "${CONFIG}" \
109  --bootloader "${BIG}" \
110  --vmlinuz "${BIG}" \
111  --arch arm
112if [ "$?" -ne 0 ]; then
113  echo -e "${COL_RED}FAILED${COL_STOP}"
114  : $(( errs++ ))
115else
116  echo -e "${COL_GREEN}PASSED${COL_STOP}"
117fi
118
119# And verify it.
120echo -n "verify USB kernel ... "
121: $(( tests++ ))
122"${FUTILITY}" vbutil_kernel \
123  --verify "${USB_KERN}" \
124  --signpubkey "${USB_SIGNPUBKEY}" >/dev/null
125if [ "$?" -ne 0 ]; then
126  echo -e "${COL_RED}FAILED${COL_STOP}"
127  : $(( errs++ ))
128else
129  echo -e "${COL_GREEN}PASSED${COL_STOP}"
130fi
131
132# Now we re-sign the same image using the normal keys. This is the kernel
133# image that is put on the hard disk by the installer. Note: To save space on
134# the USB image, we're only emitting the new verfication block, and the
135# installer just replaces that part of the hard disk's kernel partition.
136SSD_KERN="${TMPDIR}/ssd_kern.bin"
137SSD_KEYBLOCK="${DEVKEYS}/kernel.keyblock"
138SSD_SIGNPRIVATE="${DEVKEYS}/kernel_data_key.vbprivk"
139SSD_SIGNPUBKEY="${DEVKEYS}/kernel_subkey.vbpubk"
140echo -n "repack to SSD kernel ... "
141: $(( tests++ ))
142"${FUTILITY}" vbutil_kernel \
143  --repack "${SSD_KERN}" \
144  --vblockonly \
145  --keyblock "${SSD_KEYBLOCK}" \
146  --signprivate "${SSD_SIGNPRIVATE}" \
147  --oldblob "${TMPDIR}/usb_kern.bin" >/dev/null
148if [ "$?" -ne 0 ]; then
149  echo -e "${COL_RED}FAILED${COL_STOP}"
150  : $(( errs++ ))
151else
152  echo -e "${COL_GREEN}PASSED${COL_STOP}"
153fi
154
155# To verify it, we have to replace the vblock from the original image.
156tempfile="${TMPDIR}/foo.bin"
157cat "${SSD_KERN}" > "$tempfile"
158dd if="${USB_KERN}" bs=65536 skip=1 >> $tempfile 2>/dev/null
159
160echo -n "verify SSD kernel ... "
161: $(( tests++ ))
162"${FUTILITY}" vbutil_kernel \
163  --verify "$tempfile" \
164  --signpubkey "${SSD_SIGNPUBKEY}" >/dev/null
165if [ "$?" -ne 0 ]; then
166  echo -e "${COL_RED}FAILED${COL_STOP}"
167  : $(( errs++ ))
168else
169  echo -e "${COL_GREEN}PASSED${COL_STOP}"
170fi
171
172# Finally make sure that the kernel command line stays good.
173orig=$(cat "${CONFIG}" | tr '\012' ' ')
174packed=$("${FUTILITY}" dump_kernel_config "${USB_KERN}")
175echo -n "check USB kernel config ..."
176: $(( tests++ ))
177if [ "$orig" != "$packed" ]; then
178  echo -e "${COL_RED}FAILED${COL_STOP}"
179  : $(( errs++ ))
180else
181  echo -e "${COL_GREEN}PASSED${COL_STOP}"
182fi
183
184repacked=$("${FUTILITY}" dump_kernel_config "${tempfile}")
185echo -n "check SSD kernel config ..."
186: $(( tests++ ))
187if [ "$orig" != "$packed" ]; then
188  echo -e "${COL_RED}FAILED${COL_STOP}"
189  : $(( errs++ ))
190else
191  echo -e "${COL_GREEN}PASSED${COL_STOP}"
192fi
193
194# Summary
195ME=$(basename "$0")
196if [ "$errs" -ne 0 ]; then
197  echo -e "${COL_RED}${ME}: ${errs}/${tests} tests failed${COL_STOP}"
198  exit 1
199fi
200happy "${ME}: All ${tests} tests passed"
201exit 0
202