mirror of
https://github.com/flatcar/scripts.git
synced 2025-08-19 13:31:28 +02:00
Merge pull request #92 from marineam/images
Lots of image building updates
This commit is contained in:
commit
63713f2eee
@ -95,14 +95,6 @@ DEFINE_boolean enable_rootfs_verification ${FLAGS_FALSE} \
|
|||||||
"Default all bootloaders to NOT use kernel-based root fs integrity checking."
|
"Default all bootloaders to NOT use kernel-based root fs integrity checking."
|
||||||
DEFINE_boolean enable_bootcache ${FLAGS_FALSE} \
|
DEFINE_boolean enable_bootcache ${FLAGS_FALSE} \
|
||||||
"Default all bootloaders to NOT use bootcache."
|
"Default all bootloaders to NOT use bootcache."
|
||||||
DEFINE_integer verity_error_behavior 3 \
|
|
||||||
"Kernel verified boot error behavior (0: I/O errors, 1: reboot, 2: nothing)"
|
|
||||||
DEFINE_integer verity_max_ios -1 \
|
|
||||||
"Number of outstanding I/O operations dm-verity caps at."
|
|
||||||
DEFINE_string verity_algorithm "sha1" \
|
|
||||||
"Cryptographic hash algorithm used for kernel vboot."
|
|
||||||
DEFINE_string verity_salt "" \
|
|
||||||
"Salt for rootfs hash tree."
|
|
||||||
|
|
||||||
DEFINE_string keys_dir "/usr/share/vboot/devkeys" \
|
DEFINE_string keys_dir "/usr/share/vboot/devkeys" \
|
||||||
"Directory containing the signing keys."
|
"Directory containing the signing keys."
|
||||||
@ -141,15 +133,11 @@ DEFINE_boolean enable_squashfs ${FLAGS_FALSE} \
|
|||||||
DEFINE_string squash_sort_file "" \
|
DEFINE_string squash_sort_file "" \
|
||||||
"Specify the priority of files when squashing the rootfs."
|
"Specify the priority of files when squashing the rootfs."
|
||||||
|
|
||||||
DEFINE_string enable_serial "" \
|
|
||||||
"Enable serial port for printks. Example values: ttyS0"
|
|
||||||
|
|
||||||
# Parse the boot.desc and any overrides
|
# Parse the boot.desc and any overrides
|
||||||
eval set -- "${BOOT_DESC} ${FLAG_OVERRIDES}"
|
eval set -- "${BOOT_DESC} ${FLAG_OVERRIDES}"
|
||||||
FLAGS "${@}" || exit 1
|
FLAGS "${@}" || exit 1
|
||||||
|
|
||||||
[ -z "${FLAGS_verity_salt}" ] && FLAGS_verity_salt=$(make_salt)
|
|
||||||
|
|
||||||
. "${BUILD_LIBRARY_DIR}/board_options.sh" || exit 1
|
. "${BUILD_LIBRARY_DIR}/board_options.sh" || exit 1
|
||||||
|
|
||||||
# Only now can we die on error. shflags functions leak non-zero error codes,
|
# Only now can we die on error. shflags functions leak non-zero error codes,
|
||||||
|
@ -29,10 +29,6 @@ DEFINE_string disk_layout "default" \
|
|||||||
"The disk layout type to use for this image."
|
"The disk layout type to use for this image."
|
||||||
DEFINE_boolean standard_backdoor ${FLAGS_TRUE} \
|
DEFINE_boolean standard_backdoor ${FLAGS_TRUE} \
|
||||||
"Install standard backdoor credentials for testing"
|
"Install standard backdoor credentials for testing"
|
||||||
DEFINE_string usb_disk /dev/sdb4 \
|
|
||||||
"Path syslinux should use to do a usb boot. Default: /dev/sdb4"
|
|
||||||
DEFINE_string enable_serial "" \
|
|
||||||
"Enable serial port for printks. Example values: ttyS0"
|
|
||||||
|
|
||||||
# include upload options
|
# include upload options
|
||||||
. "${BUILD_LIBRARY_DIR}/release_util.sh" || exit 1
|
. "${BUILD_LIBRARY_DIR}/release_util.sh" || exit 1
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
. "${SRC_ROOT}/platform/dev/toolchain_utils.sh" || exit 1
|
. "${SRC_ROOT}/platform/dev/toolchain_utils.sh" || exit 1
|
||||||
|
|
||||||
# Overlays are parts of the disk that live on the stateful partition
|
# Overlays are parts of the disk that live on the state partition
|
||||||
ROOT_OVERLAYS=(var opt srv home usr/local)
|
ROOT_OVERLAYS=(var opt srv home usr/local)
|
||||||
|
|
||||||
cleanup_mounts() {
|
cleanup_mounts() {
|
||||||
@ -28,10 +28,15 @@ cleanup_mounts() {
|
|||||||
|
|
||||||
echo "Cleaning up mounts"
|
echo "Cleaning up mounts"
|
||||||
safe_umount_tree "${root_fs_dir}"
|
safe_umount_tree "${root_fs_dir}"
|
||||||
safe_umount_tree "${stateful_fs_dir}"
|
safe_umount_tree "${state_fs_dir}"
|
||||||
safe_umount_tree "${esp_fs_dir}"
|
safe_umount_tree "${esp_fs_dir}"
|
||||||
safe_umount_tree "${oem_fs_dir}"
|
safe_umount_tree "${oem_fs_dir}"
|
||||||
|
|
||||||
|
if [[ -n "${loop_dev}" ]]; then
|
||||||
|
sudo losetup -d "${loop_dev}"
|
||||||
|
loop_dev=
|
||||||
|
fi
|
||||||
|
|
||||||
# Turn die on error back on.
|
# Turn die on error back on.
|
||||||
set -e
|
set -e
|
||||||
}
|
}
|
||||||
@ -40,14 +45,10 @@ create_base_image() {
|
|||||||
local image_name=$1
|
local image_name=$1
|
||||||
local rootfs_verification_enabled=$2
|
local rootfs_verification_enabled=$2
|
||||||
local bootcache_enabled=$3
|
local bootcache_enabled=$3
|
||||||
local image_type="usb"
|
local image_type="base"
|
||||||
|
|
||||||
if [[ "${FLAGS_disk_layout}" != "default" ]]; then
|
if [[ "${FLAGS_disk_layout}" != "default" ]]; then
|
||||||
image_type="${FLAGS_disk_layout}"
|
image_type="${FLAGS_disk_layout}"
|
||||||
else
|
|
||||||
if should_build_image ${CHROMEOS_FACTORY_INSTALL_SHIM_NAME}; then
|
|
||||||
image_type="factory_install"
|
|
||||||
fi
|
|
||||||
fi
|
fi
|
||||||
|
|
||||||
check_valid_layout "base"
|
check_valid_layout "base"
|
||||||
@ -56,43 +57,40 @@ create_base_image() {
|
|||||||
info "Using image type ${image_type}"
|
info "Using image type ${image_type}"
|
||||||
|
|
||||||
root_fs_dir="${BUILD_DIR}/rootfs"
|
root_fs_dir="${BUILD_DIR}/rootfs"
|
||||||
stateful_fs_dir="${BUILD_DIR}/stateful"
|
state_fs_dir="${BUILD_DIR}/state"
|
||||||
esp_fs_dir="${BUILD_DIR}/esp"
|
esp_fs_dir="${BUILD_DIR}/esp"
|
||||||
oem_fs_dir="${BUILD_DIR}/oem"
|
oem_fs_dir="${BUILD_DIR}/oem"
|
||||||
|
|
||||||
trap "cleanup_mounts && delete_prompt" EXIT
|
trap "cleanup_mounts && delete_prompt" EXIT
|
||||||
cleanup_mounts &> /dev/null
|
cleanup_mounts &> /dev/null
|
||||||
|
|
||||||
local root_fs_label="ROOT-A"
|
write_partition_table "${image_type}" "${BUILD_DIR}/${image_name}"
|
||||||
local root_fs_num=$(get_num ${image_type} ${root_fs_label})
|
loop_dev=$(sudo losetup -P -f --show "${BUILD_DIR}/${image_name}")
|
||||||
local root_fs_img="${BUILD_DIR}/rootfs.image"
|
|
||||||
local root_fs_bytes=$(get_filesystem_size ${image_type} ${root_fs_num})
|
|
||||||
|
|
||||||
local stateful_fs_label="STATE"
|
|
||||||
local stateful_fs_num=$(get_num ${image_type} ${stateful_fs_label})
|
|
||||||
local stateful_fs_img="${BUILD_DIR}/stateful.image"
|
|
||||||
local stateful_fs_bytes=$(get_filesystem_size ${image_type} ${stateful_fs_num})
|
|
||||||
local stateful_fs_uuid=$(uuidgen)
|
|
||||||
|
|
||||||
local esp_fs_label="EFI-SYSTEM"
|
|
||||||
local esp_fs_num=$(get_num ${image_type} ${esp_fs_label})
|
|
||||||
local esp_fs_img="${BUILD_DIR}/esp.image"
|
|
||||||
local esp_fs_bytes=$(get_filesystem_size ${image_type} ${esp_fs_num})
|
|
||||||
|
|
||||||
local oem_fs_label="OEM"
|
|
||||||
local oem_fs_num=$(get_num ${image_type} ${oem_fs_label})
|
|
||||||
local oem_fs_img="${BUILD_DIR}/oem.image"
|
|
||||||
local oem_fs_bytes=$(get_filesystem_size ${image_type} ${oem_fs_num})
|
|
||||||
local oem_fs_uuid=$(uuidgen)
|
|
||||||
|
|
||||||
local fs_block_size=$(get_fs_block_size)
|
local fs_block_size=$(get_fs_block_size)
|
||||||
|
|
||||||
|
local root_fs_label="ROOT-A"
|
||||||
|
local root_fs_num=$(get_num ${image_type} ${root_fs_label})
|
||||||
|
local root_fs_dev="${loop_dev}p${root_fs_num}"
|
||||||
|
local root_fs_bytes=$(get_filesystem_size ${image_type} ${root_fs_num})
|
||||||
|
local root_fs_blocks=$((root_fs_bytes / fs_block_size))
|
||||||
|
|
||||||
|
local state_fs_label="STATE"
|
||||||
|
local state_fs_num=$(get_num ${image_type} ${state_fs_label})
|
||||||
|
local state_fs_dev="${loop_dev}p${state_fs_num}"
|
||||||
|
|
||||||
|
local esp_fs_label="EFI-SYSTEM"
|
||||||
|
local esp_fs_num=$(get_num ${image_type} ${esp_fs_label})
|
||||||
|
local esp_fs_dev="${loop_dev}p${esp_fs_num}"
|
||||||
|
|
||||||
|
local oem_fs_label="OEM"
|
||||||
|
local oem_fs_num=$(get_num ${image_type} ${oem_fs_label})
|
||||||
|
local oem_fs_dev="${loop_dev}p${oem_fs_num}"
|
||||||
|
|
||||||
# Build root FS image.
|
# Build root FS image.
|
||||||
info "Building ${root_fs_img}"
|
info "Building ROOT filesystem"
|
||||||
truncate --size="${root_fs_bytes}" "${root_fs_img}"
|
sudo mkfs.ext2 -F -q -b ${fs_block_size} "${root_fs_dev}" "${root_fs_blocks}"
|
||||||
/sbin/mkfs.ext2 -F -q -b ${fs_block_size} "${root_fs_img}" \
|
sudo tune2fs -L "${root_fs_label}" \
|
||||||
"$((root_fs_bytes / fs_block_size))"
|
|
||||||
/sbin/tune2fs -L "${root_fs_label}" \
|
|
||||||
-U clear \
|
-U clear \
|
||||||
-T 20091119110000 \
|
-T 20091119110000 \
|
||||||
-c 0 \
|
-c 0 \
|
||||||
@ -100,57 +98,56 @@ create_base_image() {
|
|||||||
-m 0 \
|
-m 0 \
|
||||||
-r 0 \
|
-r 0 \
|
||||||
-e remount-ro \
|
-e remount-ro \
|
||||||
"${root_fs_img}"
|
"${root_fs_dev}"
|
||||||
mkdir -p "${root_fs_dir}"
|
mkdir -p "${root_fs_dir}"
|
||||||
sudo mount -o loop "${root_fs_img}" "${root_fs_dir}"
|
sudo mount "${root_fs_dev}" "${root_fs_dir}"
|
||||||
|
|
||||||
df -h "${root_fs_dir}"
|
# Build state FS disk image.
|
||||||
|
info "Building STATE filesystem"
|
||||||
# Build stateful FS disk image.
|
sudo mkfs.ext4 -F -q "${state_fs_dev}"
|
||||||
info "Building ${stateful_fs_img}"
|
sudo tune2fs -L "${state_fs_label}" \
|
||||||
truncate --size="${stateful_fs_bytes}" "${stateful_fs_img}"
|
-c 0 \
|
||||||
/sbin/mkfs.ext4 -F -q "${stateful_fs_img}"
|
-i 0 \
|
||||||
/sbin/tune2fs -L "${stateful_fs_label}" -U "${stateful_fs_uuid}" \
|
"${state_fs_dev}"
|
||||||
-c 0 -i 0 "${stateful_fs_img}"
|
mkdir -p "${state_fs_dir}"
|
||||||
mkdir -p "${stateful_fs_dir}"
|
sudo mount "${state_fs_dev}" "${state_fs_dir}"
|
||||||
sudo mount -o loop "${stateful_fs_img}" "${stateful_fs_dir}"
|
|
||||||
|
|
||||||
# Build ESP disk image.
|
# Build ESP disk image.
|
||||||
info "Building ${esp_fs_img}"
|
info "Building ESP filesystem"
|
||||||
truncate --size="${esp_fs_bytes}" "${esp_fs_img}"
|
sudo mkfs.vfat "${esp_fs_dev}"
|
||||||
/usr/sbin/mkfs.vfat "${esp_fs_img}"
|
|
||||||
|
|
||||||
# Build OEM FS disk image.
|
# Build OEM FS disk image.
|
||||||
info "Building ${oem_fs_img}"
|
info "Building OEM filesystem"
|
||||||
truncate --size="${oem_fs_bytes}" "${oem_fs_img}"
|
sudo mkfs.ext4 -F -q "${oem_fs_dev}"
|
||||||
/sbin/mkfs.ext4 -F -q "${oem_fs_img}"
|
sudo tune2fs -L "${oem_fs_label}" \
|
||||||
/sbin/tune2fs -L "${oem_fs_label}" -U "${oem_fs_uuid}" \
|
-c 0 \
|
||||||
-c 0 -i 0 "${oem_fs_img}"
|
-i 0 \
|
||||||
|
"${oem_fs_dev}"
|
||||||
mkdir -p "${oem_fs_dir}"
|
mkdir -p "${oem_fs_dir}"
|
||||||
sudo mount -o loop "${oem_fs_img}" "${oem_fs_dir}"
|
sudo mount "${oem_fs_dev}" "${oem_fs_dir}"
|
||||||
|
|
||||||
# Prepare stateful partition with some pre-created directories.
|
# Prepare state partition with some pre-created directories.
|
||||||
for i in ${ROOT_OVERLAYS}; do
|
for i in ${ROOT_OVERLAYS}; do
|
||||||
sudo mkdir -p "${stateful_fs_dir}/overlays/$i"
|
sudo mkdir -p "${state_fs_dir}/overlays/$i"
|
||||||
sudo mkdir -p "${root_fs_dir}/$i"
|
sudo mkdir -p "${root_fs_dir}/$i"
|
||||||
sudo mount --bind "${stateful_fs_dir}/overlays/$i" "${root_fs_dir}/$i"
|
sudo mount --bind "${state_fs_dir}/overlays/$i" "${root_fs_dir}/$i"
|
||||||
done
|
done
|
||||||
|
|
||||||
sudo mkdir -p "${stateful_fs_dir}/overlays/usr/local"
|
sudo mkdir -p "${state_fs_dir}/overlays/usr/local"
|
||||||
|
|
||||||
# Create symlinks so that /usr/local/usr based directories are symlinked to
|
# Create symlinks so that /usr/local/usr based directories are symlinked to
|
||||||
# /usr/local/ directories e.g. /usr/local/usr/bin -> /usr/local/bin, etc.
|
# /usr/local/ directories e.g. /usr/local/usr/bin -> /usr/local/bin, etc.
|
||||||
setup_symlinks_on_root "${stateful_fs_dir}/overlays/usr/local" \
|
setup_symlinks_on_root "${state_fs_dir}/overlays/usr/local" \
|
||||||
"${stateful_fs_dir}/overlays/var" \
|
"${state_fs_dir}/overlays/var" \
|
||||||
"${stateful_fs_dir}"
|
"${state_fs_dir}"
|
||||||
|
|
||||||
# Perform binding rather than symlinking because directories must exist
|
# Perform binding rather than symlinking because directories must exist
|
||||||
# on rootfs so that we can bind at run-time since rootfs is read-only.
|
# on rootfs so that we can bind at run-time since rootfs is read-only.
|
||||||
info "Binding directories from stateful partition onto the rootfs"
|
info "Binding directories from state partition onto the rootfs"
|
||||||
|
|
||||||
# Setup the dev image for developer tools
|
# Setup the dev image for developer tools
|
||||||
sudo mkdir -p "${root_fs_dir}/usr/local"
|
sudo mkdir -p "${root_fs_dir}/usr/local"
|
||||||
sudo mount --bind "${stateful_fs_dir}/overlays/usr/local" "${root_fs_dir}/usr/local"
|
sudo mount --bind "${state_fs_dir}/overlays/usr/local" "${root_fs_dir}/usr/local"
|
||||||
|
|
||||||
# TODO(bp): remove these temporary fixes for /mnt/stateful_partition going moving
|
# TODO(bp): remove these temporary fixes for /mnt/stateful_partition going moving
|
||||||
sudo mkdir -p "${root_fs_dir}/mnt/stateful_partition/"
|
sudo mkdir -p "${root_fs_dir}/mnt/stateful_partition/"
|
||||||
@ -212,10 +209,11 @@ create_base_image() {
|
|||||||
# trim the image size as much as possible.
|
# trim the image size as much as possible.
|
||||||
emerge_to_image --root="${root_fs_dir}" ${BASE_PACKAGE}
|
emerge_to_image --root="${root_fs_dir}" ${BASE_PACKAGE}
|
||||||
|
|
||||||
# Record directories installed to the stateful partition.
|
# Record directories installed to the state partition.
|
||||||
sudo "${SCRIPTS_DIR}/gen_tmpfiles.py" --root="${root_fs_dir}" \
|
# Ignore /var/tmp, systemd covers this entry.
|
||||||
|
sudo "${BUILD_LIBRARY_DIR}/gen_tmpfiles.py" --root="${root_fs_dir}" \
|
||||||
--output="${root_fs_dir}/usr/lib/tmpfiles.d/base_image.conf" \
|
--output="${root_fs_dir}/usr/lib/tmpfiles.d/base_image.conf" \
|
||||||
"${root_fs_dir}/var"
|
--ignore=/var/tmp "${root_fs_dir}/var"
|
||||||
|
|
||||||
# Set /etc/lsb-release on the image.
|
# Set /etc/lsb-release on the image.
|
||||||
"${BUILD_LIBRARY_DIR}/set_lsb_release" \
|
"${BUILD_LIBRARY_DIR}/set_lsb_release" \
|
||||||
@ -227,12 +225,6 @@ create_base_image() {
|
|||||||
# cros_make_image_bootable.
|
# cros_make_image_bootable.
|
||||||
create_boot_desc "${image_type}"
|
create_boot_desc "${image_type}"
|
||||||
|
|
||||||
# Write out the GPT creation script.
|
|
||||||
# This MUST be done before writing bootloader templates else we'll break
|
|
||||||
# the hash on the root FS.
|
|
||||||
write_partition_script "${image_type}" \
|
|
||||||
"${root_fs_dir}/${PARTITION_SCRIPT_PATH}"
|
|
||||||
|
|
||||||
# Populates the root filesystem with legacy bootloader templates
|
# Populates the root filesystem with legacy bootloader templates
|
||||||
# appropriate for the platform. The autoupdater and installer will
|
# appropriate for the platform. The autoupdater and installer will
|
||||||
# use those templates to update the legacy boot partition (12/ESP)
|
# use those templates to update the legacy boot partition (12/ESP)
|
||||||
@ -268,25 +260,15 @@ create_base_image() {
|
|||||||
# Clean up symlinks so they work on a running target rooted at "/".
|
# Clean up symlinks so they work on a running target rooted at "/".
|
||||||
# Here development packages are rooted at /usr/local. However, do not
|
# Here development packages are rooted at /usr/local. However, do not
|
||||||
# create /usr/local or /var on host (already exist on target).
|
# create /usr/local or /var on host (already exist on target).
|
||||||
setup_symlinks_on_root "/usr/local" "/var" "${stateful_fs_dir}"
|
setup_symlinks_on_root "/usr/local" "/var" "${state_fs_dir}"
|
||||||
|
|
||||||
# Zero all fs free space to make it more compressible so auto-update
|
# Zero all fs free space to make it more compressible so auto-update
|
||||||
# payloads become smaller, not fatal since it won't work on linux < 3.2
|
# payloads become smaller, not fatal since it won't work on linux < 3.2
|
||||||
sudo fstrim "${root_fs_dir}" || true
|
sudo fstrim "${root_fs_dir}" || true
|
||||||
sudo fstrim "${stateful_fs_dir}" || true
|
sudo fstrim "${state_fs_dir}" || true
|
||||||
|
|
||||||
cleanup_mounts
|
cleanup_mounts
|
||||||
|
|
||||||
# Create the GPT-formatted image.
|
|
||||||
build_gpt "${BUILD_DIR}/${image_name}" \
|
|
||||||
"${root_fs_img}" \
|
|
||||||
"${stateful_fs_img}" \
|
|
||||||
"${esp_fs_img}" \
|
|
||||||
"${oem_fs_img}"
|
|
||||||
|
|
||||||
# Clean up temporary files.
|
|
||||||
rm -f "${root_fs_img}" "${stateful_fs_img}" "${esp_fs_img}" "{oem_fs_img}"
|
|
||||||
|
|
||||||
# Emit helpful scripts for testers, etc.
|
# Emit helpful scripts for testers, etc.
|
||||||
emit_gpt_scripts "${BUILD_DIR}/${image_name}" "${BUILD_DIR}"
|
emit_gpt_scripts "${BUILD_DIR}/${image_name}" "${BUILD_DIR}"
|
||||||
|
|
||||||
|
@ -104,7 +104,6 @@ create_boot_desc() {
|
|||||||
enable_bootcache_flag=--enable_bootcache
|
enable_bootcache_flag=--enable_bootcache
|
||||||
fi
|
fi
|
||||||
|
|
||||||
[ -z "${FLAGS_verity_salt}" ] && FLAGS_verity_salt=$(make_salt)
|
|
||||||
cat <<EOF > ${BUILD_DIR}/boot.desc
|
cat <<EOF > ${BUILD_DIR}/boot.desc
|
||||||
--board=${BOARD}
|
--board=${BOARD}
|
||||||
--image_type=${image_type}
|
--image_type=${image_type}
|
||||||
@ -112,8 +111,6 @@ create_boot_desc() {
|
|||||||
--keys_dir="${DEVKEYSDIR}"
|
--keys_dir="${DEVKEYSDIR}"
|
||||||
--boot_args="${FLAGS_boot_args}"
|
--boot_args="${FLAGS_boot_args}"
|
||||||
--nocleanup_dirs
|
--nocleanup_dirs
|
||||||
--verity_algorithm=sha1
|
|
||||||
--enable_serial="${FLAGS_enable_serial}"
|
|
||||||
${enable_rootfs_verification_flag}
|
${enable_rootfs_verification_flag}
|
||||||
${enable_bootcache_flag}
|
${enable_bootcache_flag}
|
||||||
EOF
|
EOF
|
||||||
|
@ -3,10 +3,10 @@
|
|||||||
# Use of this source code is governed by a BSD-style license that can be
|
# Use of this source code is governed by a BSD-style license that can be
|
||||||
# found in the LICENSE file.
|
# found in the LICENSE file.
|
||||||
|
|
||||||
import copy
|
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
import re
|
import re
|
||||||
|
import subprocess
|
||||||
import sys
|
import sys
|
||||||
import uuid
|
import uuid
|
||||||
from optparse import OptionParser
|
from optparse import OptionParser
|
||||||
@ -93,41 +93,6 @@ def LoadPartitionConfig(filename):
|
|||||||
return config
|
return config
|
||||||
|
|
||||||
|
|
||||||
def GetTableTotals(config, partitions):
|
|
||||||
"""Calculates total sizes/counts for a partition table.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
config: Partition configuration file object
|
|
||||||
partitions: List of partitions to process
|
|
||||||
Returns:
|
|
||||||
Dict containing totals data
|
|
||||||
"""
|
|
||||||
|
|
||||||
ret = {
|
|
||||||
'expand_count': 0,
|
|
||||||
'expand_min': 0,
|
|
||||||
'block_count': START_SECTOR * config['metadata']['block_size']
|
|
||||||
}
|
|
||||||
|
|
||||||
# Total up the size of all non-expanding partitions to get the minimum
|
|
||||||
# required disk size.
|
|
||||||
for partition in partitions:
|
|
||||||
if 'features' in partition and 'expand' in partition['features']:
|
|
||||||
ret['expand_count'] += 1
|
|
||||||
ret['expand_min'] += partition['blocks']
|
|
||||||
else:
|
|
||||||
ret['block_count'] += partition['blocks']
|
|
||||||
|
|
||||||
# At present, only one expanding partition is permitted.
|
|
||||||
# Whilst it'd be possible to have two, we don't need this yet
|
|
||||||
# and it complicates things, so it's been left out for now.
|
|
||||||
if ret['expand_count'] > 1:
|
|
||||||
raise InvalidLayout('1 expand partition allowed, %d requested'
|
|
||||||
% ret['expand_count'])
|
|
||||||
|
|
||||||
ret['min_disk_size'] = ret['block_count'] + ret['expand_min']
|
|
||||||
|
|
||||||
return ret
|
|
||||||
|
|
||||||
|
|
||||||
def GetPartitionTable(options, config, image_type):
|
def GetPartitionTable(options, config, image_type):
|
||||||
@ -241,77 +206,72 @@ def GetPartitionTableFromConfig(options, layout_filename, image_type):
|
|||||||
|
|
||||||
return partitions
|
return partitions
|
||||||
|
|
||||||
def GetScriptShell():
|
|
||||||
"""Loads and returns the skeleton script for our output script.
|
|
||||||
|
|
||||||
Returns:
|
def WritePartitionTable(options, image_type, layout_filename, disk_filename):
|
||||||
A string containg the skeleton script
|
"""Writes the given partition table to a disk image or device.
|
||||||
"""
|
|
||||||
|
|
||||||
script_shell_path = os.path.join(os.path.dirname(__file__), 'cgpt_shell.sh')
|
|
||||||
with open(script_shell_path, 'r') as f:
|
|
||||||
script_shell = ''.join(f.readlines())
|
|
||||||
|
|
||||||
# Before we return, insert the path to this tool so somebody reading the
|
|
||||||
# script later can tell where it was generated.
|
|
||||||
script_shell = script_shell.replace('@SCRIPT_GENERATOR@', script_shell_path)
|
|
||||||
|
|
||||||
return script_shell
|
|
||||||
|
|
||||||
|
|
||||||
def WriteLayoutFunction(options, sfile, func_name, image_type, config):
|
|
||||||
"""Writes a shell script function to write out a given partition table.
|
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
options: Flags passed to the script
|
options: Flags passed to the script
|
||||||
sfile: File handle we're writing to
|
|
||||||
func_name: Function name to write out for specified layout
|
|
||||||
image_type: Type of image eg base/test/dev/factory_install
|
image_type: Type of image eg base/test/dev/factory_install
|
||||||
config: Partition configuration file object
|
layout_filename: Path to partition configuration file
|
||||||
|
disk_filename: Path to disk image or device file
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
def Cgpt(*args):
|
||||||
|
subprocess.check_call(['cgpt'] + [str(a) for a in args])
|
||||||
|
|
||||||
|
config = LoadPartitionConfig(layout_filename)
|
||||||
partitions = GetPartitionTable(options, config, image_type)
|
partitions = GetPartitionTable(options, config, image_type)
|
||||||
partition_totals = GetTableTotals(config, partitions)
|
disk_block_count = START_SECTOR * config['metadata']['block_size']
|
||||||
|
|
||||||
sfile.write('%s() {\ncreate_image $1 %d %s\n' % (
|
|
||||||
func_name, partition_totals['min_disk_size'],
|
|
||||||
config['metadata']['block_size']))
|
|
||||||
|
|
||||||
sfile.write('CURR=%d\n' % START_SECTOR)
|
|
||||||
sfile.write('$GPT create $1\n')
|
|
||||||
|
|
||||||
# Pass 1: Set up the expanding partition size.
|
|
||||||
for partition in partitions:
|
for partition in partitions:
|
||||||
partition['var'] = partition['blocks']
|
disk_block_count += partition['blocks']
|
||||||
|
|
||||||
if partition['type'] != 'blank':
|
sector = START_SECTOR
|
||||||
if partition['num'] == 1:
|
Cgpt('create', '-c', '-s', disk_block_count, disk_filename)
|
||||||
if 'features' in partition and 'expand' in partition['features']:
|
|
||||||
sfile.write('if [ -b $1 ]; then\n')
|
|
||||||
sfile.write('STATEFUL_SIZE=$(( $(numsectors $1) - %d))\n' %
|
|
||||||
partition_totals['block_count'])
|
|
||||||
sfile.write('else\n')
|
|
||||||
sfile.write('STATEFUL_SIZE=%s\n' % partition['blocks'])
|
|
||||||
sfile.write('fi\n')
|
|
||||||
partition['var'] = '$STATEFUL_SIZE'
|
|
||||||
|
|
||||||
sfile.write('STATEFUL_SIZE=$((STATEFUL_SIZE-(STATEFUL_SIZE %% %d)))\n' %
|
|
||||||
config['metadata']['fs_block_size'])
|
|
||||||
|
|
||||||
# Pass 2: Write out all the cgpt add commands.
|
|
||||||
for partition in partitions:
|
for partition in partitions:
|
||||||
if partition['type'] != 'blank':
|
if partition['type'] != 'blank':
|
||||||
sfile.write('$GPT add -i %d -b $CURR -s %s -t %s -l %s -u %s $1 && ' % (
|
Cgpt('add', '-i', partition['num'],
|
||||||
partition['num'], str(partition['var']), partition['type'],
|
'-b', sector,
|
||||||
partition['label'], partition['uuid']))
|
'-s', partition['blocks'],
|
||||||
|
'-t', partition['type'],
|
||||||
|
'-l', partition['label'],
|
||||||
|
'-u', partition['uuid'],
|
||||||
|
disk_filename)
|
||||||
|
|
||||||
|
sector += partition['blocks']
|
||||||
|
|
||||||
|
Cgpt('show', disk_filename)
|
||||||
|
|
||||||
|
|
||||||
|
def WriteMbrBoot(options, image_type, layout_filename,
|
||||||
|
disk_filename, mbr_filename):
|
||||||
|
"""Writes the protective MBR with the given boot code.
|
||||||
|
|
||||||
|
The EFI System Partition will be marked as the 'boot' partition.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
options: Flags passed to the script
|
||||||
|
image_type: Type of image eg base/test/dev/factory_install
|
||||||
|
layout_filename: Path to partition configuration file
|
||||||
|
disk_filename: Path to disk image or device file
|
||||||
|
mbr_filename: Path to boot code, usually gptmbr.bin from syslinux.
|
||||||
|
"""
|
||||||
|
|
||||||
|
config = LoadPartitionConfig(layout_filename)
|
||||||
|
partitions = GetPartitionTable(options, config, image_type)
|
||||||
|
|
||||||
|
esp_number = None
|
||||||
|
for partition in partitions:
|
||||||
if partition['type'] == 'efi':
|
if partition['type'] == 'efi':
|
||||||
sfile.write('$GPT boot -p -b $2 -i %d $1\n' % partition['num'])
|
esp_number = partition['num']
|
||||||
|
break
|
||||||
|
if esp_number is None:
|
||||||
|
raise InvalidLayout('Table does not include an EFI partition.')
|
||||||
|
|
||||||
# Increment the CURR counter ready for the next partition.
|
subprocess.check_call(['cgpt', 'boot', '-p', '-b', mbr_filename,
|
||||||
sfile.write('CURR=$(( $CURR + %s ))\n' % partition['var'])
|
'-i', str(partition['num']), disk_filename])
|
||||||
|
|
||||||
sfile.write('$GPT show $1\n')
|
|
||||||
sfile.write('}\n')
|
|
||||||
|
|
||||||
|
|
||||||
def GetPartitionByNumber(partitions, num):
|
def GetPartitionByNumber(partitions, num):
|
||||||
@ -350,26 +310,6 @@ def GetPartitionByLabel(partitions, label):
|
|||||||
raise PartitionNotFound('Partition not found')
|
raise PartitionNotFound('Partition not found')
|
||||||
|
|
||||||
|
|
||||||
def WritePartitionScript(options, image_type, layout_filename, sfilename):
|
|
||||||
"""Writes a shell script with functions for the base and requested layouts.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
options: Flags passed to the script
|
|
||||||
image_type: Type of image eg base/test/dev/factory_install
|
|
||||||
layout_filename: Path to partition configuration file
|
|
||||||
sfilename: Filename to write the finished script to
|
|
||||||
"""
|
|
||||||
|
|
||||||
config = LoadPartitionConfig(layout_filename)
|
|
||||||
|
|
||||||
with open(sfilename, 'w') as f:
|
|
||||||
script_shell = GetScriptShell()
|
|
||||||
f.write(script_shell)
|
|
||||||
|
|
||||||
WriteLayoutFunction(options, f, 'write_base_table', 'base', config)
|
|
||||||
WriteLayoutFunction(options, f, 'write_partition_table', image_type, config)
|
|
||||||
|
|
||||||
|
|
||||||
def GetBlockSize(options, layout_filename):
|
def GetBlockSize(options, layout_filename):
|
||||||
"""Returns the partition table block size.
|
"""Returns the partition table block size.
|
||||||
|
|
||||||
@ -549,9 +489,14 @@ def DoParseOnly(options, image_type, layout_filename):
|
|||||||
|
|
||||||
def main(argv):
|
def main(argv):
|
||||||
action_map = {
|
action_map = {
|
||||||
'write': {
|
'write_gpt': {
|
||||||
'usage': ['<image_type>', '<partition_config_file>', '<script_file>'],
|
'usage': ['<image_type>', '<partition_config_file>', '<disk_image>'],
|
||||||
'func': WritePartitionScript,
|
'func': WritePartitionTable,
|
||||||
|
},
|
||||||
|
'write_mbr': {
|
||||||
|
'usage': ['<image_type>', '<partition_config_file>', '<disk_image>',
|
||||||
|
'<mbr_boot_code>'],
|
||||||
|
'func': WriteMbrBoot,
|
||||||
},
|
},
|
||||||
'readblocksize': {
|
'readblocksize': {
|
||||||
'usage': ['<partition_config_file>'],
|
'usage': ['<partition_config_file>'],
|
||||||
|
@ -1,38 +0,0 @@
|
|||||||
#!/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 automatically generated by @SCRIPT_GENERATOR@
|
|
||||||
# Do not edit!
|
|
||||||
|
|
||||||
if ! type numsectors >/dev/null 2>&1; then
|
|
||||||
if [ -f "/usr/sbin/chromeos-common.sh" ]; then
|
|
||||||
. "/usr/sbin/chromeos-common.sh"
|
|
||||||
else
|
|
||||||
echo "Can't load chromeos-common.sh, dying!" 1>&2
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
locate_gpt
|
|
||||||
|
|
||||||
# Usage: create_image <device> <min_disk_size> <block_size>
|
|
||||||
# If <device> is a block device, wipes out the GPT
|
|
||||||
# If it's not, it creates a new file of the requested size
|
|
||||||
create_image() {
|
|
||||||
local dev=$1
|
|
||||||
local min_disk_size=$2
|
|
||||||
local block_size=$3
|
|
||||||
if [ -b "${dev}" ]; then
|
|
||||||
# Zap any old partitions (otherwise gpt complains).
|
|
||||||
dd if=/dev/zero of="${dev}" conv=notrunc bs=512 count=32
|
|
||||||
dd if=/dev/zero of="${dev}" conv=notrunc bs=512 \
|
|
||||||
seek=$((${min_disk_size} - 1 - 33)) count=33
|
|
||||||
else
|
|
||||||
if [ ! -e "${dev}" ]; then
|
|
||||||
dd if=/dev/zero of="${dev}" bs=${block_size} count=1 \
|
|
||||||
seek=$((${min_disk_size} - 1))
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
@ -18,19 +18,12 @@ DEFINE_string arch "x86" \
|
|||||||
"The boot architecture: arm or x86. (Default: x86)"
|
"The boot architecture: arm or x86. (Default: x86)"
|
||||||
DEFINE_string to "/tmp/boot" \
|
DEFINE_string to "/tmp/boot" \
|
||||||
"Path to populate with bootloader templates (Default: /tmp/boot)"
|
"Path to populate with bootloader templates (Default: /tmp/boot)"
|
||||||
DEFINE_string usb_disk /dev/sdb3 \
|
|
||||||
"Path syslinux should use to do a usb boot. Default: /dev/sdb3"
|
|
||||||
DEFINE_string boot_args "" \
|
DEFINE_string boot_args "" \
|
||||||
"Additional boot arguments to pass to the commandline (Default: '')"
|
"Additional boot arguments to pass to the commandline (Default: '')"
|
||||||
DEFINE_boolean enable_bootcache ${FLAGS_FALSE} \
|
DEFINE_boolean enable_bootcache ${FLAGS_FALSE} \
|
||||||
"Default all bootloaders to NOT use boot cache."
|
"Default all bootloaders to NOT use boot cache."
|
||||||
DEFINE_boolean enable_rootfs_verification ${FLAGS_FALSE} \
|
DEFINE_boolean enable_rootfs_verification ${FLAGS_FALSE} \
|
||||||
"Controls if verity is used for root filesystem checking (Default: false)"
|
"Controls if verity is used for root filesystem checking (Default: false)"
|
||||||
DEFINE_integer verity_error_behavior 3 \
|
|
||||||
"Verified boot error behavior [0: I/O errors, 1: reboot, 2: nothing] \
|
|
||||||
(Default: 3)"
|
|
||||||
DEFINE_integer verity_max_ios -1 \
|
|
||||||
"Optional number of outstanding I/O operations. (Default: 1024)"
|
|
||||||
|
|
||||||
# Parse flags
|
# Parse flags
|
||||||
FLAGS "$@" || exit 1
|
FLAGS "$@" || exit 1
|
||||||
|
@ -17,7 +17,7 @@ install_dev_packages() {
|
|||||||
trap "unmount_image ; delete_prompt" EXIT
|
trap "unmount_image ; delete_prompt" EXIT
|
||||||
|
|
||||||
mount_image "${BUILD_DIR}/${image_name}" "${root_fs_dir}" \
|
mount_image "${BUILD_DIR}/${image_name}" "${root_fs_dir}" \
|
||||||
"${stateful_fs_dir}" "${esp_fs_dir}"
|
"${state_fs_dir}" "${esp_fs_dir}"
|
||||||
|
|
||||||
# Determine the root dir for developer packages.
|
# Determine the root dir for developer packages.
|
||||||
local root_dev_dir="${root_fs_dir}/usr/local"
|
local root_dev_dir="${root_fs_dir}/usr/local"
|
||||||
@ -90,7 +90,7 @@ EOF
|
|||||||
|
|
||||||
# Zero all fs free space, not fatal since it won't work on linux < 3.2
|
# Zero all fs free space, not fatal since it won't work on linux < 3.2
|
||||||
sudo fstrim "${root_fs_dir}" || true
|
sudo fstrim "${root_fs_dir}" || true
|
||||||
sudo fstrim "${stateful_fs_dir}" || true
|
sudo fstrim "${state_fs_dir}" || true
|
||||||
|
|
||||||
info "Developer image built and stored at ${image_name}"
|
info "Developer image built and stored at ${image_name}"
|
||||||
|
|
||||||
|
@ -3,7 +3,6 @@
|
|||||||
# found in the LICENSE file.
|
# found in the LICENSE file.
|
||||||
|
|
||||||
CGPT_PY="${BUILD_LIBRARY_DIR}/cgpt.py"
|
CGPT_PY="${BUILD_LIBRARY_DIR}/cgpt.py"
|
||||||
PARTITION_SCRIPT_PATH="usr/sbin/write_gpt.sh"
|
|
||||||
|
|
||||||
cgpt_py() {
|
cgpt_py() {
|
||||||
if [[ -n "${FLAGS_adjust_part-}" ]]; then
|
if [[ -n "${FLAGS_adjust_part-}" ]]; then
|
||||||
@ -20,7 +19,6 @@ cgpt_py() {
|
|||||||
|
|
||||||
get_disk_layout_path() {
|
get_disk_layout_path() {
|
||||||
DISK_LAYOUT_PATH="${BUILD_LIBRARY_DIR}/legacy_disk_layout.json"
|
DISK_LAYOUT_PATH="${BUILD_LIBRARY_DIR}/legacy_disk_layout.json"
|
||||||
local partition_script_path=$(tempfile)
|
|
||||||
for overlay in $(cros_list_overlays --board "$BOARD"); do
|
for overlay in $(cros_list_overlays --board "$BOARD"); do
|
||||||
local disk_layout="${overlay}/scripts/disk_layout.json"
|
local disk_layout="${overlay}/scripts/disk_layout.json"
|
||||||
if [[ -e ${disk_layout} ]]; then
|
if [[ -e ${disk_layout} ]]; then
|
||||||
@ -29,23 +27,9 @@ get_disk_layout_path() {
|
|||||||
done
|
done
|
||||||
}
|
}
|
||||||
|
|
||||||
write_partition_script() {
|
write_partition_table() {
|
||||||
local image_type=$1
|
local image_type=$1
|
||||||
local partition_script_path=$2
|
local outdev=$2
|
||||||
get_disk_layout_path
|
|
||||||
|
|
||||||
local temp_script_file=$(mktemp)
|
|
||||||
|
|
||||||
sudo mkdir -p "$(dirname "${partition_script_path}")"
|
|
||||||
|
|
||||||
cgpt_py write "${image_type}" "${DISK_LAYOUT_PATH}" \
|
|
||||||
"${temp_script_file}"
|
|
||||||
sudo mv "${temp_script_file}" "${partition_script_path}"
|
|
||||||
}
|
|
||||||
|
|
||||||
run_partition_script() {
|
|
||||||
local outdev=$1
|
|
||||||
local root_fs_img=$2
|
|
||||||
|
|
||||||
local pmbr_img
|
local pmbr_img
|
||||||
case ${ARCH} in
|
case ${ARCH} in
|
||||||
@ -61,13 +45,10 @@ run_partition_script() {
|
|||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
|
|
||||||
if is_mounted "${root_fs_dir}"; then
|
get_disk_layout_path
|
||||||
safe_umount "${root_fs_dir}"
|
cgpt_py write_gpt "${image_type}" "${DISK_LAYOUT_PATH}" "${outdev}"
|
||||||
fi
|
cgpt_py write_mbr \
|
||||||
sudo mount -o loop "${root_fs_img}" "${root_fs_dir}"
|
"${image_type}" "${DISK_LAYOUT_PATH}" "${outdev}" "${pmbr_img}"
|
||||||
. "${root_fs_dir}/${PARTITION_SCRIPT_PATH}"
|
|
||||||
write_partition_table "${outdev}" "${pmbr_img}"
|
|
||||||
safe_umount "${root_fs_dir}"
|
|
||||||
}
|
}
|
||||||
|
|
||||||
get_fs_block_size() {
|
get_fs_block_size() {
|
||||||
@ -131,9 +112,6 @@ check_valid_layout() {
|
|||||||
|
|
||||||
get_disk_layout_type() {
|
get_disk_layout_type() {
|
||||||
DISK_LAYOUT_TYPE="base"
|
DISK_LAYOUT_TYPE="base"
|
||||||
if should_build_image ${CHROMEOS_FACTORY_INSTALL_SHIM_NAME}; then
|
|
||||||
DISK_LAYOUT_TYPE="factory_install"
|
|
||||||
fi
|
|
||||||
}
|
}
|
||||||
|
|
||||||
emit_gpt_scripts() {
|
emit_gpt_scripts() {
|
||||||
@ -204,7 +182,7 @@ build_gpt() {
|
|||||||
local oem_img="$5"
|
local oem_img="$5"
|
||||||
|
|
||||||
get_disk_layout_type
|
get_disk_layout_type
|
||||||
run_partition_script "${outdev}" "${rootfs_img}"
|
write_partition_table "${DISK_LAYOUT_TYPE}" "${outdev}"
|
||||||
|
|
||||||
local sudo=
|
local sudo=
|
||||||
if [ ! -w "$outdev" ] ; then
|
if [ ! -w "$outdev" ] ; then
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
#!/usr/bin/python
|
#!/usr/bin/python
|
||||||
'''Scan an existing directory tree and record installed directories.
|
'''Scan an existing directory tree and record installed directories.
|
||||||
|
|
||||||
During build a number of directories under /var are created in the stateful
|
During build a number of directories under /var are created in the state
|
||||||
partition. We want to make sure that those are always there so create a record
|
partition. We want to make sure that those are always there so create a record
|
||||||
of them using systemd's tempfiles config format so they are recreated during
|
of them using systemd's tempfiles config format so they are recreated during
|
||||||
boot if they go missing for any reason.
|
boot if they go missing for any reason.
|
||||||
@ -19,6 +19,8 @@ def main():
|
|||||||
parser = optparse.OptionParser(description=__doc__)
|
parser = optparse.OptionParser(description=__doc__)
|
||||||
parser.add_option('--root', help='Remove root prefix from output')
|
parser.add_option('--root', help='Remove root prefix from output')
|
||||||
parser.add_option('--output', help='Write output to the given file')
|
parser.add_option('--output', help='Write output to the given file')
|
||||||
|
parser.add_option('--ignore', action='append', default=[],
|
||||||
|
help='Ignore one or more paths (use multiple times)')
|
||||||
opts, args = parser.parse_args()
|
opts, args = parser.parse_args()
|
||||||
|
|
||||||
if opts.root:
|
if opts.root:
|
||||||
@ -56,6 +58,9 @@ def main():
|
|||||||
else:
|
else:
|
||||||
stripped = path
|
stripped = path
|
||||||
|
|
||||||
|
if stripped in opts.ignore:
|
||||||
|
continue
|
||||||
|
|
||||||
info = os.stat(path)
|
info = os.stat(path)
|
||||||
assert stat.S_ISDIR(info.st_mode)
|
assert stat.S_ISDIR(info.st_mode)
|
||||||
mode = stat.S_IMODE(info.st_mode)
|
mode = stat.S_IMODE(info.st_mode)
|
@ -23,7 +23,7 @@
|
|||||||
"label":"ROOT-A",
|
"label":"ROOT-A",
|
||||||
"uuid":"7130c94a-213a-4e5a-8e26-6cce9662f132",
|
"uuid":"7130c94a-213a-4e5a-8e26-6cce9662f132",
|
||||||
"type":"coreos-rootfs",
|
"type":"coreos-rootfs",
|
||||||
"blocks":"4194304",
|
"blocks":"2097152",
|
||||||
"fs_blocks":"262144"
|
"fs_blocks":"262144"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -31,7 +31,7 @@
|
|||||||
"label":"ROOT-B",
|
"label":"ROOT-B",
|
||||||
"uuid":"e03dd35c-7c2d-4a47-b3fe-27f15780a57c",
|
"uuid":"e03dd35c-7c2d-4a47-b3fe-27f15780a57c",
|
||||||
"type":"coreos-rootfs",
|
"type":"coreos-rootfs",
|
||||||
"blocks":"4194304",
|
"blocks":"2097152",
|
||||||
"fs_blocks":"262144"
|
"fs_blocks":"262144"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -63,73 +63,10 @@
|
|||||||
"num": 9,
|
"num": 9,
|
||||||
"label":"STATE",
|
"label":"STATE",
|
||||||
"type":"data",
|
"type":"data",
|
||||||
"blocks":"2097152",
|
"blocks":"2097152"
|
||||||
"features":["expand"]
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"usb": [
|
|
||||||
{
|
|
||||||
"num": 3,
|
|
||||||
"label":"ROOT-A",
|
|
||||||
"uuid":"7130c94a-213a-4e5a-8e26-6cce9662f132",
|
|
||||||
"type":"coreos-rootfs",
|
|
||||||
"blocks":"2539520",
|
|
||||||
"fs_blocks":"262144"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"num": 4,
|
|
||||||
"label":"ROOT-B",
|
|
||||||
"uuid":"e03dd35c-7c2d-4a47-b3fe-27f15780a57c",
|
|
||||||
"type":"coreos-rootfs",
|
|
||||||
"blocks":"1"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"factory_install": [
|
|
||||||
{
|
|
||||||
"num": 1,
|
|
||||||
"label":"EFI-SYSTEM",
|
|
||||||
"type":"efi",
|
|
||||||
"blocks":"65536"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"num": 3,
|
|
||||||
"label":"ROOT-A",
|
|
||||||
"uuid":"7130c94a-213a-4e5a-8e26-6cce9662f132",
|
|
||||||
"type":"coreos-rootfs",
|
|
||||||
"blocks":"860160",
|
|
||||||
"fs_blocks":"102400"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"num": 4,
|
|
||||||
"label":"ROOT-B",
|
|
||||||
"uuid":"e03dd35c-7c2d-4a47-b3fe-27f15780a57c",
|
|
||||||
"type":"coreos-rootfs",
|
|
||||||
"blocks":"1"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"num": 9,
|
|
||||||
"label":"STATE",
|
|
||||||
"type":"data",
|
|
||||||
"blocks":"286720"
|
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"vm": [
|
"vm": [
|
||||||
{
|
|
||||||
"num": 3,
|
|
||||||
"label":"ROOT-A",
|
|
||||||
"uuid":"7130c94a-213a-4e5a-8e26-6cce9662f132",
|
|
||||||
"type":"coreos-rootfs",
|
|
||||||
"blocks":"2097152",
|
|
||||||
"fs_blocks":"262144"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"num": 4,
|
|
||||||
"label":"ROOT-B",
|
|
||||||
"uuid":"e03dd35c-7c2d-4a47-b3fe-27f15780a57c",
|
|
||||||
"type":"coreos-rootfs",
|
|
||||||
"blocks":"2097152",
|
|
||||||
"fs_blocks":"262144"
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"num": 9,
|
"num": 9,
|
||||||
"label":"STATE",
|
"label":"STATE",
|
||||||
|
@ -180,14 +180,8 @@ unpack_source_disk() {
|
|||||||
cp --sparse=always "${alternate_state_image}" "${TEMP_STATE}"
|
cp --sparse=always "${alternate_state_image}" "${TEMP_STATE}"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
TEMP_PMBR="${VM_TMP_DIR}"/pmbr
|
|
||||||
dd if="${VM_SRC_IMG}" of="${TEMP_PMBR}" bs=512 count=1
|
|
||||||
|
|
||||||
info "Initializing new partition table..."
|
info "Initializing new partition table..."
|
||||||
TEMP_PARTITION_SCRIPT="${VM_TMP_DIR}/partition_script.sh"
|
write_partition_table "${disk_layout}" "${VM_TMP_IMG}"
|
||||||
write_partition_script "${disk_layout}" "${TEMP_PARTITION_SCRIPT}"
|
|
||||||
. "${TEMP_PARTITION_SCRIPT}"
|
|
||||||
write_partition_table "${VM_TMP_IMG}" "${TEMP_PMBR}"
|
|
||||||
}
|
}
|
||||||
|
|
||||||
resize_state_partition() {
|
resize_state_partition() {
|
||||||
@ -197,10 +191,10 @@ resize_state_partition() {
|
|||||||
local original_size=$(stat -c%s "${TEMP_STATE}")
|
local original_size=$(stat -c%s "${TEMP_STATE}")
|
||||||
|
|
||||||
if [[ "${original_size}" -gt "${size_in_bytes}" ]]; then
|
if [[ "${original_size}" -gt "${size_in_bytes}" ]]; then
|
||||||
die "Cannot resize stateful image to smaller than original."
|
die "Cannot resize state image to smaller than original."
|
||||||
fi
|
fi
|
||||||
|
|
||||||
info "Resizing stateful partition to ${size_in_mb}MB"
|
info "Resizing state partition to ${size_in_mb}MB"
|
||||||
/sbin/e2fsck -pf "${TEMP_STATE}"
|
/sbin/e2fsck -pf "${TEMP_STATE}"
|
||||||
/sbin/resize2fs "${TEMP_STATE}" "${size_in_sectors}s"
|
/sbin/resize2fs "${TEMP_STATE}" "${size_in_sectors}s"
|
||||||
}
|
}
|
||||||
|
@ -68,7 +68,9 @@ if [ -z "${FLAGS_board}" ] ; then
|
|||||||
die_notrace "--board is required."
|
die_notrace "--board is required."
|
||||||
fi
|
fi
|
||||||
|
|
||||||
BOARD="$FLAGS_board"
|
# Loaded after flags are parsed because board_options depends on --board
|
||||||
|
. "${BUILD_LIBRARY_DIR}/board_options.sh" || exit 1
|
||||||
|
|
||||||
|
|
||||||
IMAGES_DIR="${DEFAULT_BUILD_ROOT}/images/${FLAGS_board}"
|
IMAGES_DIR="${DEFAULT_BUILD_ROOT}/images/${FLAGS_board}"
|
||||||
# Default to the most recent image
|
# Default to the most recent image
|
||||||
|
@ -1,104 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
#
|
|
||||||
# Copyright (c) 2010 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.
|
|
||||||
|
|
||||||
# Script to verify integrity of root file system for a GPT-based image
|
|
||||||
|
|
||||||
SCRIPT_ROOT=$(dirname $(readlink -f "$0"))
|
|
||||||
. "${SCRIPT_ROOT}/common.sh" || exit 1
|
|
||||||
|
|
||||||
# Load functions and constants for chromeos-install
|
|
||||||
[ -f /usr/lib/installer/chromeos-common.sh ] && \
|
|
||||||
INSTALLER_ROOT=/usr/lib/installer || \
|
|
||||||
INSTALLER_ROOT=$(dirname "$(readlink -f "$0")")
|
|
||||||
|
|
||||||
. "${INSTALLER_ROOT}/chromeos-common.sh" || exit 1
|
|
||||||
|
|
||||||
# Needed for partoffset and partsize calls
|
|
||||||
locate_gpt
|
|
||||||
|
|
||||||
# Script must be run inside the chroot.
|
|
||||||
restart_in_chroot_if_needed "$@"
|
|
||||||
|
|
||||||
DEFINE_string image "" "Device or an image path. Default: (empty)."
|
|
||||||
|
|
||||||
# Parse command line.
|
|
||||||
FLAGS "$@" || exit 1
|
|
||||||
eval set -- "${FLAGS_ARGV}"
|
|
||||||
|
|
||||||
if [ -z $FLAGS_image ] ; then
|
|
||||||
die_notrace "Use --image to specify a device or an image file."
|
|
||||||
fi
|
|
||||||
|
|
||||||
# Turn path into an absolute path.
|
|
||||||
FLAGS_image=$(eval readlink -f ${FLAGS_image})
|
|
||||||
|
|
||||||
# Abort early if we can't find the image
|
|
||||||
if [ ! -b ${FLAGS_image} ] && [ ! -f $FLAGS_image ] ; then
|
|
||||||
die_notrace "No image found at $FLAGS_image"
|
|
||||||
fi
|
|
||||||
|
|
||||||
switch_to_strict_mode
|
|
||||||
|
|
||||||
get_partitions() {
|
|
||||||
if [ -b ${FLAGS_image} ] ; then
|
|
||||||
KERNEL_IMG=$(make_partition_dev "${FLAGS_image}" 2)
|
|
||||||
ROOTFS_IMG=$(make_partition_dev "${FLAGS_image}" 3)
|
|
||||||
return
|
|
||||||
fi
|
|
||||||
|
|
||||||
KERNEL_IMG=$(mktemp)
|
|
||||||
ROOTFS_IMG=$(mktemp)
|
|
||||||
local kernel_offset=$(partoffset "${FLAGS_image}" 2)
|
|
||||||
local kernel_count=$(partsize "${FLAGS_image}" 2)
|
|
||||||
local rootfs_offset=$(partoffset "${FLAGS_image}" 3)
|
|
||||||
local rootfs_count=$(partsize "${FLAGS_image}" 3)
|
|
||||||
|
|
||||||
# TODO(tgao): use loop device to save 1GB in temp space
|
|
||||||
dd if="${FLAGS_image}" of=${KERNEL_IMG} bs=512 skip=${kernel_offset} \
|
|
||||||
count=${kernel_count} &>/dev/null
|
|
||||||
dd if="${FLAGS_image}" of=${ROOTFS_IMG} bs=512 skip=${rootfs_offset} \
|
|
||||||
count=${rootfs_count} &>/dev/null
|
|
||||||
}
|
|
||||||
|
|
||||||
cleanup() {
|
|
||||||
for i in ${KERNEL_IMG} ${ROOTFS_IMG}; do
|
|
||||||
if [ ! -b ${i} ]; then
|
|
||||||
rm -f ${i}
|
|
||||||
fi
|
|
||||||
done
|
|
||||||
}
|
|
||||||
|
|
||||||
get_partitions
|
|
||||||
|
|
||||||
# Logic below extracted from src/platform/installer/chromeos-setimage
|
|
||||||
DUMP_KERNEL_CONFIG=/usr/bin/dump_kernel_config
|
|
||||||
KERNEL_CONFIG=$(sudo "${DUMP_KERNEL_CONFIG}" "${KERNEL_IMG}")
|
|
||||||
kernel_cfg="$(echo "${KERNEL_CONFIG}" | sed -e 's/.*dm="\([^"]*\)".*/\1/g' |
|
|
||||||
cut -f2- -d,)"
|
|
||||||
rootfs_sectors=$(echo ${kernel_cfg} | cut -f2 -d' ')
|
|
||||||
verity_algorithm=$(echo ${kernel_cfg} | cut -f8 -d' ')
|
|
||||||
|
|
||||||
# Compute the rootfs hash tree
|
|
||||||
VERITY=/bin/verity
|
|
||||||
# First argument to verity is reserved/unused and MUST be 0
|
|
||||||
table="vroot none ro,"$(sudo "${VERITY}" create 0 \
|
|
||||||
"${verity_algorithm}" \
|
|
||||||
"${ROOTFS_IMG}" \
|
|
||||||
$((rootfs_sectors / 8)) \
|
|
||||||
/dev/null)
|
|
||||||
|
|
||||||
expected_hash=$(echo ${kernel_cfg} | cut -f9 -d' ')
|
|
||||||
generated_hash=$(echo ${table} | cut -f2- -d, | cut -f9 -d' ')
|
|
||||||
|
|
||||||
cleanup
|
|
||||||
|
|
||||||
if [ "${expected_hash}" != "${generated_hash}" ]; then
|
|
||||||
warn "expected hash = ${expected_hash}"
|
|
||||||
warn "actual hash = ${generated_hash}"
|
|
||||||
die_notrace "Root filesystem has been modified unexpectedly!"
|
|
||||||
else
|
|
||||||
info "Root filesystem checksum match!"
|
|
||||||
fi
|
|
Loading…
x
Reference in New Issue
Block a user