一、更新流程及操作
我们烧录新系统的时候有时希望连同BIOS 和EC一起更新,但是按照之前的操作我们制作完USB包、recovery包和OTA包烧录完成后发现BIOS和EC并没有更新,所以这个问题着实影响到我们系统的后续升级。factory包会直接安装firmware,所以原理在此不讨论。
其实谷歌已经为我们提供了一套自动更新BIOS和EC的firmwareupdate的流程框架,我们直接调用已有的工具即可达到我们烧录固件同时更新firmware的目的。其为我们提供了让系统烧录后更新firmware的工具:tag_image.sh 位于: /src/platform/vboot_reference/scripts/image_signing/tag_image.sh
烧录同时更新firmware的用法:
tag_image.sh --from=/path_to_/image.bin --update_firmware 1 (ps: 加不加“=”都可以;设置update_firmware为1就是更新,设为0不更新)
例如:
bijunqiang@ubuntu ~/trunk/src/scripts $ ../platform/vboot_reference/scripts/image_signing/tag_image.sh \
- -from =/mnt/host/source/src/build/images/coral_cvte/latest/chromiumos_base_image.bin --update_firmware 1
|
流程如下:
此工具为我们提供了几种功能可让系统包实现固件开发者模式的转换、是否强制更新firmware等功能。见tag_image.sh谷歌源码。
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
# Script to manipulate the tag files in the output of build_image
# Load common constants. This should be the first executable line.
# The path to common.sh should be relative to your script's location.
. "$(dirname " $0 ")/common.sh"
load_shflags
DEFINE_string from "chromiumos_image.bin" \
"Input file name of Chrome OS image to tag/stamp."
DEFINE_string dev_mode "" \
"(build-info) Tag as a developer mode build (1 to enable, 0 to disable)"
DEFINE_string update_firmware "" \
"(auto-update) Force updating firmware (1 to enable, 0 to disable)"
DEFINE_string leave_firmware_alone "" \
"(auto-update) For BIOS development use ONLY (1 to enable, 0 to disable)"
DEFINE_string leave_core "" \
"(crash-reporter) Leave core dumps (1 to enable, 0 to disable)"
DEFINE_string crosh_workarounds "" \
"(crosh) Keep crosh (1 to keep, 0 to disable *irreversible*)"
|
其他用法可参考Chromium Code Reviews介绍。
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
二、整套更新firmware的框架流程
首先我们用此工具来设置我们编译好的bin文件,tag_image执行了一个在镜像rootfs目录中/root/新建了一个.force_update_firmware的文件,用来标记自动更新。
138
139
140
141
142
|
process_tag "${do_modification}" \
"(auto-update) update_firmware" \
"${rootfs}" \
/root/ .force_update_firmware \
"${FLAGS_update_firmware}"
|
我们烧录完成后可在chromeosbook的中看到此目录下确实有此文件。
这之后就要交给update_engine的cros_installer服务完成了。系统each AU or recovery, 都会运行 /usr/sbin/chromeos-postinst。我们在此代码中可以看到:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
|
#!/bin/sh
# Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
# This script is called after an AutoUpdate or USB install. This script is a
# simple wrapper to convert from the hardcoded command line to the new
# executable command line.
INSTALL_ROOT=$( dirname "$0" )
# Set up the mount points userland needs/expects.
MOUNTS= "/proc /dev /sys /tmp /run /var /mnt/stateful_partition"
cleanup() {
local d
for d in ${MOUNTS}; do
umount -lf "./${d}" || :
done
}
main() {
cd "${INSTALL_ROOT}" || exit 1
trap cleanup EXIT
local d
for d in ${MOUNTS}; do
mount -n --bind "${d}" "./${d}"
mount -- make -slave "./${d}"
done
chroot . /usr/bin/cros_installer postinst "/" "$@"
}
main "$@"
|
程序中的34行最后运行了cros_installer服务。此服务是由chromeos-base/chromeos-installer编译生成的。谷歌介绍:
Files in this folder will be compiled by chromeos-base/chromeos-installer
package into few programs, including:
- chromeos-install: A shell script for manual installation from USB.
- chromeos-recovery: The main command for recovery shim to install image.
- chromeos-postinst: The script executed by auto update or recovery shim after image installation is completed, being the symbolic link of /postinst.
- cros_installer: A program meant to be the backend of above commands (but it currently only supports post-install).
这个包中的chromeos_postinst.cc程序对我们之前见到的.force_update_firmware文件标志进行了检查。
368
369
370
|
// In postinst in future, we may provide an option (ex, --update_firmware).
string firmware_tag_file = (install_config.root. mount () +
"/root/.force_update_firmware" );
|
检查到标志之后通过读取安装过程中设置的环境变量来判断firmware更新模式。
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
|
string command = install_dir + "/usr/sbin/chromeos-firmwareupdate" ;
if (access(command.c_str(), X_OK) != 0) {
printf ( "No firmware updates available.\n" );
return true ;
}
if (is_update) {
// Background auto update by Update Engine.
mode = "autoupdate" ;
} else {
// Recovery image, or from command "chromeos-install".
mode = "recovery" ;
}
command += " --mode=" ;
command += mode;
printf ( "Starting firmware updater (%s)\n" , command.c_str());
result = RunCommand(command);
|
运行/usr/sbin/chromeos-firmwareupdate来更新firmware。更新完成后chromeos-setgoodfirmware程序会mark active firmware as "good" as well。
至此整个固件更新firmware完成,下次重启虽然还有/root/.force_update_firmware文件,但是系统不会运行只有更新完系统才运行的cros_installer服务。
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
chromeos-firmwareupdate是由chromeos-base/chromeos-firmware-coral ebuild包生成的shellball。其中包含了bios和ec的镜像文件。
ChromeOS Firmware Updater相关介绍和操作:
https://chromium.googlesource.com/chromiumos/platform/firmware/+/refs/heads/firmware-coral-10068.B
其中还包括chromeos-firmwareupdate相关模式的介绍: