Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 1 #!/bin/bash | |
| 2 | |
| 3 # Copyright (c) 2009 The Chromium OS Authors. All rights reserved. | |
|
petkov
2010/12/22 22:45:03
2010
gauravsh
2010/12/22 22:55:27
2010 (or rather 2011 if you end up submitting next
thieule
2010/12/23 19:26:28
Done.
thieule
2010/12/23 19:26:28
Done.
| |
| 4 # Use of this source code is governed by a BSD-style license that can be | |
| 5 # found in the LICENSE file. | |
| 6 | |
| 7 # Script to preserve the on-disk file layout of the specified image and | |
| 8 # the latest shipping image. | |
| 9 | |
| 10 # Load common constants. This should be the first executable line. | |
| 11 # The path to common.sh should be relative to your script's location. | |
| 12 . "$(dirname "$0")/common.sh" | |
| 13 . "$(dirname "$0")/chromeos-common.sh" | |
| 14 | |
| 15 # Script must be run inside the chroot because we need to use | |
| 16 # cros_make_image_bootable which requires this. | |
|
adlr
2010/12/22 22:49:50
i suspect this might be a problem for the build bo
thieule
2010/12/23 19:26:28
Done.
| |
| 17 assert_inside_chroot | |
| 18 | |
| 19 locate_gpt | |
| 20 get_default_board | |
| 21 | |
| 22 # Flags. | |
| 23 DEFINE_string board "${DEFAULT_BOARD}" \ | |
| 24 "The board of the latest shipping image to use." | |
| 25 DEFINE_string image "" \ | |
| 26 "The image that needs to be aligned to the latest shipping image." | |
| 27 | |
| 28 # Parse command line. | |
|
petkov
2010/12/22 22:45:03
you should do the flag processing inside main
thieule
2010/12/23 19:26:28
Done.
| |
| 29 FLAGS "$@" || exit 1 | |
| 30 eval set -- "${FLAGS_ARGV}" | |
| 31 | |
| 32 # Only now can we die on error. shflags functions leak non-zero error codes, | |
| 33 # so will die prematurely if 'set -e' is specified before now. | |
| 34 set -e | |
| 35 | |
| 36 # Make sure we have the required parameters. | |
| 37 if [ -z "${FLAGS_board}" ] ; then | |
| 38 error "--board is required." | |
|
petkov
2010/12/22 22:45:03
die instead of error and no exit
thieule
2010/12/23 19:26:28
Done.
| |
| 39 exit 1 | |
| 40 fi | |
| 41 | |
| 42 if [ ! -f "${FLAGS_image}" ] ; then | |
| 43 error "--image is required." | |
|
petkov
2010/12/22 22:45:03
die
also, did you mean to say that the image file
gauravsh
2010/12/22 22:55:27
the error displayed here is not accurate - since -
thieule
2010/12/23 19:26:28
Done.
thieule
2010/12/23 19:26:28
Done.
| |
| 44 exit 1 | |
| 45 fi | |
| 46 | |
| 47 HARDWARE_CLASS= | |
| 48 IMAGE_SEARCH_STRING= | |
| 49 RELEASE_URL= | |
| 50 RELEASE_ALT_URL= | |
| 51 | |
| 52 LATEST_SHIPPING_VERSION= | |
| 53 | |
| 54 declare -a cleanup_actions | |
| 55 | |
| 56 add_cleanup_action() { | |
|
gauravsh
2010/12/22 22:55:27
this trap setup and cleanup will conflict with vbo
thieule
2010/12/23 19:26:28
Done.
| |
| 57 # Add the clean up action to the end of the array. | |
| 58 # During clean up, the actions are executed in the reverse order of when | |
| 59 # they were added. | |
| 60 cleanup_actions[${#cleanup_actions[*]}]=$1 | |
| 61 } | |
| 62 | |
| 63 cleanup() { | |
| 64 set +e | |
| 65 | |
| 66 # Perform clean up actions in reverse order. | |
| 67 local num_actions=${#cleanup_actions[*]} | |
| 68 while [ $num_actions -gt 0 ] ; do | |
| 69 eval "${cleanup_actions[$num_actions-1]}" > /dev/null 2>&1 | |
| 70 unset cleanup_actions[$num_actions-1] | |
| 71 num_actions=${#cleanup_actions[*]} | |
| 72 done | |
| 73 | |
| 74 set -e | |
| 75 } | |
| 76 | |
| 77 initialize() { | |
| 78 # Set up environment variables specific to the board | |
| 79 if [ ${FLAGS_board} == "x86-mario" ] ; then | |
|
petkov
2010/12/22 22:45:03
this is a bit ugly. maybe it's better to remove th
gauravsh
2010/12/22 22:55:27
use '=' here
thieule
2010/12/23 19:26:28
Done.
thieule
2010/12/23 19:26:28
Done.
| |
| 80 HARDWARE_CLASS="IEC MARIO PONY 6101" | |
|
gauravsh
2010/12/22 22:55:27
this could be better called HARDWARE_ID.
gauravsh
2010/12/22 22:55:27
You might want to parameterize this now - as an op
thieule
2010/12/23 19:26:28
Done.
thieule
2010/12/23 19:26:28
Making this a required command line arg per petkov
| |
| 81 IMAGE_SEARCH_STRING="*SSD_MP_SIGNED.bin" | |
| 82 RELEASE_URL="http://chromeos-images/chromeos-official/dev-channel/x86-mario" | |
| 83 RELEASE_ALT_URL="${RELEASE_URL}-rc" | |
| 84 else | |
| 85 error "Board ${FLAGS_board} not supported" | |
|
petkov
2010/12/22 22:45:03
die
thieule
2010/12/23 19:26:28
Done.
| |
| 86 exit 1 | |
| 87 fi | |
| 88 } | |
| 89 | |
| 90 get_latest_shipping_version() { | |
|
gauravsh
2010/12/22 22:55:27
comment
thieule
2010/12/23 19:26:28
Done.
| |
| 91 info "Pinging Omaha for the latest shipping version." | |
|
petkov
2010/12/22 22:45:03
it might be easier/better to go through the recove
thieule
2010/12/23 19:26:28
Is the recovery image always the latest shipping i
| |
| 92 local auserver_url="https://tools.google.com/service/update2" | |
| 93 local au_request_file=$(mktemp "/tmp/align_rootfs_au_request.XXXX") | |
| 94 add_cleanup_action "sudo rm -f \"${au_request_file}\"" | |
| 95 cat > "${au_request_file}" << EOF | |
| 96 <?xml version="1.0" encoding="UTF-8"?> | |
| 97 <o:gupdate xmlns:o="http://www.google.com/update2/request" | |
| 98 version="ChromeOSUpdateEngine-0.1.0.0" | |
| 99 updaterversion="ChromeOSUpdateEngine-0.1.0.0" protocol="2.0" ismachine="1"> | |
| 100 <o:os version="Indy" platform="Chrome OS" sp="ForcedUpdate_i686"></o:os> | |
| 101 <o:app appid="{87efface-864d-49a5-9bb3-4b050a7c227a}" | |
|
petkov
2010/12/22 22:45:03
you're hardcoding an AppId that corresponds to Mar
thieule
2010/12/23 19:26:28
Done.
| |
| 102 version="ForcedUpdate" lang="en-US" track="dev-channel" | |
|
petkov
2010/12/22 22:45:03
if you use version="0.0.0.0" you should get the la
thieule
2010/12/23 19:26:28
Done.
| |
| 103 hardware_class="${HARDWARE_CLASS}" delta_okay="true"> | |
| 104 <o:ping a="-1" r="-1"></o:ping> | |
|
petkov
2010/12/22 22:45:03
remove this ping otherwise you'd be counted as an
thieule
2010/12/23 19:26:28
Done.
| |
| 105 <o:updatecheck></o:updatecheck> | |
| 106 </o:app> | |
| 107 </o:gupdate> | |
| 108 EOF | |
| 109 | |
| 110 LATEST_SHIPPING_VERSION=$(wget -q --header="Content-Type: text/xml" \ | |
|
petkov
2010/12/22 22:45:03
why is this a global? shouldn't you return this as
thieule
2010/12/23 19:26:28
Done.
| |
| 111 --post-file="${au_request_file}" -O - ${auserver_url} | \ | |
| 112 sed 's/.*\(ChromeOSVersion="\)\([0-9\.]*\)"\(.*\)/\2/') | |
| 113 } | |
| 114 | |
| 115 download_image() { | |
|
gauravsh
2010/12/22 22:55:27
add comment
thieule
2010/12/23 19:26:28
Done.
| |
| 116 # Since we don't know the exact name, we'll just download recursively based | |
| 117 # on a wildcard. Then we'll # rename that download file to the desired output | |
| 118 # file. It's important that the IMAGE_SEARCH_STRING matches only one file. | |
| 119 local url=$1 | |
| 120 local output_file=$2 | |
| 121 local retcode=0 | |
| 122 | |
| 123 local download_dir=$(mktemp -d "/tmp/align_rootfs_download_dir.XXXX") | |
| 124 add_cleanup_action "sudo rm -rf \"${download_dir}\"" | |
| 125 | |
| 126 wget -A "${IMAGE_SEARCH_STRING}" --progress=bar -r -l1 -nd \ | |
| 127 -P "${download_dir}" ${url} || retcode=$? | |
|
adlr
2010/12/22 22:49:50
cool trick to get the retcode! I'll have to rememb
| |
| 128 if [ ${retcode} -eq 0 ] ; then | |
| 129 mv -f "${download_dir}"/* "${output_file}" | |
| 130 else | |
| 131 return ${retcode} | |
| 132 fi | |
| 133 } | |
| 134 | |
| 135 get_shipping_image() { | |
| 136 # The image may reside in one of two URLs. We don't know exactly which one | |
| 137 # so we'll have to try both. | |
| 138 local version=$1 | |
| 139 local image=$2 | |
| 140 local url="${RELEASE_URL}/${version}" | |
| 141 download_image "${url}" "${image}" || retcode=$? | |
| 142 if [ ${retcode} -gt 0 ] ; then | |
| 143 url="${RELEASE_ALT_URL}/${version}" | |
| 144 download_image "${url}" "${image}" | |
| 145 fi | |
| 146 } | |
| 147 | |
| 148 extract_root_fs() { | |
| 149 local image=$1 | |
| 150 local root_fs=$2 | |
| 151 local root_fs_offset=$(partoffset "${image}" 3) | |
| 152 local root_fs_count=$(partsize "${image}" 3) | |
| 153 dd if="${image}" of="${root_fs}" bs=512 skip=${root_fs_offset} \ | |
| 154 count=${root_fs_count} | |
| 155 } | |
| 156 | |
| 157 copy_root_fs() { | |
|
gauravsh
2010/12/22 22:55:27
add comment about the arguments and what the funct
thieule
2010/12/23 19:26:28
Done.
| |
| 158 local src_image=$1 | |
| 159 local dst_root_fs=$2 | |
| 160 | |
| 161 # Mount the src and dst rootfs. | |
| 162 local src_root_fs_dir="/tmp/m" | |
| 163 local image_dir=$(dirname "${src_image}") | |
| 164 local image_name=$(basename "${src_image}") | |
| 165 ${SCRIPTS_DIR}/mount_gpt_image.sh -f "${image_dir}" -i "${image_name}" | |
|
gauravsh
2010/12/22 22:55:27
you can use mount_image_partition from vboot_refer
thieule
2010/12/23 19:26:28
Done.
| |
| 166 add_cleanup_action "${SCRIPTS_DIR}/mount_gpt_image.sh -u" | |
| 167 | |
| 168 local dst_root_fs_dir=$(mktemp -d "/tmp/align_root_fs_dest_mount_dir.XXXX") | |
| 169 add_cleanup_action "sudo rm -rf \"${dst_root_fs_dir}\"" | |
| 170 sudo mount -o loop "${dst_root_fs}" "${dst_root_fs_dir}" -o loop | |
| 171 add_cleanup_action "sudo umount -d \"${dst_root_fs_dir}\"" | |
| 172 | |
| 173 # Temporarily make immutable files on the dst rootfs mutable. | |
|
petkov
2010/12/22 22:45:03
do we have such files? do we care about mutable/im
thieule
2010/12/23 19:26:28
There is one immutable file /boot/extlinux.sys tha
| |
| 174 immutable_files=() | |
| 175 local dst_root_fs_dir_escaped=$(echo "${dst_root_fs_dir}" | \ | |
| 176 sed 's/\//\\\//g') | |
|
petkov
2010/12/22 22:45:03
use sed s,,, rather than sed s/// for readability?
adlr
2010/12/22 22:49:50
maybe this is clearer:
s_/_\\/_g
since you can us
thieule
2010/12/23 19:26:28
Ack, missed this on the original code review. Sos
| |
| 177 local enum_files_cmd='sudo find "${dst_root_fs_dir}" -xdev -type f' | |
| 178 eval $enum_files_cmd | sed "s/${dst_root_fs_dir_escaped}//" | \ | |
|
adlr
2010/12/22 22:49:50
comment on what this command does?
thieule
2010/12/23 19:26:28
I've removed this code. It was a leftover from so
| |
| 179 while read -r FILE ; do | |
|
petkov
2010/12/22 22:45:03
while is FILE all caps?
thieule
2010/12/23 19:26:28
Done.
| |
| 180 immutable=$(sudo lsattr "${dst_root_fs_dir}$FILE" | cut -d' ' -f1 | \ | |
| 181 grep -q i ; echo $?) | |
| 182 if [ $immutable -eq 0 ] ; then | |
| 183 immutable_files=("${immutable_files[@]}" "${dst_root_fs_dir}$FILE") | |
| 184 sudo chattr -i "${dst_root_fs_dir}$FILE" | |
| 185 fi | |
| 186 done | |
| 187 | |
| 188 # Copy files from the src rootfs over top of dst rootfs. | |
| 189 # Use the --inplace flag to preserve as much of the file system metadata | |
| 190 # as possible. | |
| 191 sudo rsync -v -a -H -A -x --force --inplace --numeric-ids --delete \ | |
| 192 "${src_root_fs_dir}"/ "${dst_root_fs_dir}" | |
| 193 | |
| 194 # Make immutable files immutable again. | |
| 195 for FILE in ${immutable_files[*]} ; do | |
|
petkov
2010/12/22 22:45:03
why is FILE all caps?
thieule
2010/12/23 19:26:28
Done.
| |
| 196 sudo chattr +i "${dst_root_fs_dir}$FILE" | |
| 197 done | |
| 198 | |
| 199 ${SCRIPTS_DIR}/mount_gpt_image.sh -u | |
|
petkov
2010/12/22 22:45:03
you'd try to unmount this twice, I think -- once h
thieule
2010/12/23 19:26:28
I need these unmounts because I'll be replacing th
| |
| 200 sudo umount -d "${dst_root_fs_dir}" | |
| 201 } | |
| 202 | |
| 203 replace_root_fs() { | |
|
gauravsh
2010/12/22 22:55:27
add comment about the arguments and what the funct
thieule
2010/12/23 19:26:28
I've removed this function and using replace_image
| |
| 204 local root_fs=$1 | |
| 205 local image=$2 | |
| 206 local root_fs_offset=$(partoffset "${image}" 3) | |
| 207 local root_fs_count=$(partsize "${image}" 3) | |
| 208 dd if="${root_fs}" of="${image}" bs=512 conv=notrunc \ | |
|
adlr
2010/12/22 22:49:50
maybe do bs=$((2 * 1024 * 1024)) ? take a look at
thieule
2010/12/23 19:26:28
Function removed.
| |
| 209 seek=${root_fs_offset} count=${root_fs_count} | |
| 210 } | |
| 211 | |
| 212 main() { | |
| 213 trap cleanup EXIT | |
|
adlr
2010/12/22 22:49:50
many script trap on more than just exit, (i think)
gauravsh
2010/12/22 22:55:27
if you use vboot_reference's common.sh, this will
thieule
2010/12/23 19:26:28
Done.
thieule
2010/12/23 19:26:28
Done.
| |
| 214 | |
| 215 initialize | |
| 216 | |
| 217 # Download the latest shipping image. | |
| 218 get_latest_shipping_version | |
| 219 | |
| 220 local latest_shipping_image=$(mktemp "/tmp/align_rootfs_shipping_image.XXXX") | |
| 221 add_cleanup_action "sudo rm -f \"${latest_shipping_image}\"" | |
|
petkov
2010/12/22 22:45:03
why do this special add_cleanup_action rather than
thieule
2010/12/23 19:26:28
I have other clean up actions that may need to be
| |
| 222 info "Downloading image (${LATEST_SHIPPING_VERSION})" | |
| 223 get_shipping_image "${LATEST_SHIPPING_VERSION}" "${latest_shipping_image}" | |
| 224 | |
| 225 # Make sure the two rootfs are the same size. | |
| 226 # If they are not, then there is nothing for us to do. | |
| 227 # Note: Exit with a zero code so we do not break the build workflow. | |
| 228 local shipping_root_fs_size=$(partsize "${latest_shipping_image}" 3) | |
| 229 local new_root_fs_size=$(partsize "${FLAGS_image}" 3) | |
| 230 if [ ${shipping_root_fs_size} -ne ${new_root_fs_size} ] ; then | |
| 231 info "The latest shipping rootfs and the new rootfs are not the same size." | |
|
petkov
2010/12/22 22:45:03
warn instead?
thieule
2010/12/23 19:26:28
Done.
| |
| 232 exit 0 | |
| 233 fi | |
| 234 | |
| 235 # Extract the rootfs from the shipping image and use this as a template | |
| 236 # for the new image. | |
| 237 temp_root_fs=$(mktemp "/tmp/align_rootfs_temp_rootfs.XXXX") | |
| 238 add_cleanup_action "sudo rm -f \"${temp_root_fs}\"" | |
| 239 info "Extracting rootfs from shipping image" | |
| 240 extract_root_fs "${latest_shipping_image}" "${temp_root_fs}" | |
|
gauravsh
2010/12/22 22:55:27
extract_partition can be used here
thieule
2010/12/23 19:26:28
Done.
| |
| 241 enable_rw_mount "${temp_root_fs}" | |
| 242 | |
| 243 # Copy the new rootfs over template rootfs to preserve as much of the | |
|
adlr
2010/12/22 22:49:50
this is a super high level comment that could go a
thieule
2010/12/23 19:26:28
Done.
| |
| 244 # metadata from the shipping rootfs as possible. This will ensure minimal | |
| 245 # disk shuffling when applying the auto-update. | |
| 246 info "Copying rootfs" | |
| 247 copy_root_fs "${FLAGS_image}" "${temp_root_fs}" | |
| 248 | |
| 249 # Replace the rootfs in the new image with the aligned version. | |
| 250 info "Replacing rootfs" | |
| 251 replace_root_fs "${temp_root_fs}" "${FLAGS_image}" | |
| 252 | |
| 253 # Make the image bootable again. | |
| 254 local image_dir=$(dirname "${FLAGS_image}") | |
| 255 local image_name=$(basename "${FLAGS_image}") | |
| 256 info "Make image bootable" | |
| 257 ${SCRIPTS_DIR}/bin/cros_make_image_bootable "${image_dir}" "${image_name}" | |
| 258 | |
| 259 trap - EXIT | |
| 260 | |
| 261 cleanup | |
| 262 } | |
| 263 | |
| 264 main | |
|
petkov
2010/12/22 22:45:03
main "$*"
thieule
2010/12/23 19:26:28
Done.
| |
| OLD | NEW |