mirror of
https://github.com/flatcar/scripts.git
synced 2025-08-09 22:16:58 +02:00
crosutils: refine factory and imaging scripts
In order to support building arbitrary image, the partition copying scripts has been changed to support "copying partitions in same size" and "overwriting partitions in different size", and "copying partition from external file". We need these APIs to create disk/usb image with release images that is using partition with different size (ex, recovery images). Image copying buffer selection and disk image creation time are also improved. BUG=chromium-os:15050 TEST=./make_factory_package.sh ... --diskimg preimage.bin ./make_factory_package.sh ... --usbimg rma.bin ./make_factory_package.sh ... # omaha mode Change-Id: I6a4c820abf59e780985c95dc35f9340b347bd952 Reviewed-on: http://gerrit.chromium.org/gerrit/5981 Reviewed-by: Nick Sanders <nsanders@chromium.org> Tested-by: Hung-Te Lin <hungte@chromium.org>
This commit is contained in:
parent
5c67986738
commit
28a753b22c
@ -92,15 +92,13 @@ image_dump_partial_file() {
|
||||
local sectors="$3"
|
||||
local bs=512
|
||||
|
||||
# Try to use larger buffer if offset/size can be re-aligned.
|
||||
# 2M / 512 = 4096
|
||||
local buffer_ratio=4096
|
||||
if [ $((offset % buffer_ratio)) -eq 0 -a \
|
||||
$((sectors % buffer_ratio)) -eq 0 ]; then
|
||||
offset=$((offset / buffer_ratio))
|
||||
sectors=$((sectors / buffer_ratio))
|
||||
bs=$((bs * buffer_ratio))
|
||||
fi
|
||||
# Increase buffer size as much as possible until 8M
|
||||
while [ $((bs < (8 * 1024 * 1024) && sectors > 0 &&
|
||||
offset % 2 == 0 && sectors % 2 == 0)) = "1" ]; do
|
||||
bs=$((bs * 2))
|
||||
offset=$((offset / 2))
|
||||
sectors=$((sectors / 2))
|
||||
done
|
||||
|
||||
if image_has_command pv; then
|
||||
dd if="$file" bs=$bs skip="$offset" count="$sectors" \
|
||||
@ -124,6 +122,43 @@ image_dump_partition() {
|
||||
image_dump_partial_file "$file" "$offset" "$size"
|
||||
}
|
||||
|
||||
# Updates a file (from stdin) by given offset and size (in sectors)
|
||||
image_update_partial_file() {
|
||||
local file="$1"
|
||||
local offset="$2"
|
||||
local sectors="$3"
|
||||
local bs=512
|
||||
|
||||
# Increase buffer size as much as possible until 8M
|
||||
while [ $((bs < (8 * 1024 * 1024) && sectors > 0 &&
|
||||
offset % 2 == 0 && sectors % 2 == 0)) = "1" ]; do
|
||||
bs=$((bs * 2))
|
||||
offset=$((offset / 2))
|
||||
sectors=$((sectors / 2))
|
||||
done
|
||||
|
||||
if image_has_command pv; then
|
||||
pv -ptreb -B $bs -s $((sectors * bs)) |
|
||||
dd of="$file" bs=$bs seek="$offset" count="$sectors" \
|
||||
iflag=fullblock oflag=dsync conv=notrunc status=noxfer 2>/dev/null
|
||||
else
|
||||
dd of="$file" bs=$bs seek="$offset" count="$sectors" \
|
||||
iflag=fullblock oflag=dsync conv=notrunc status=noxfer 2>/dev/null
|
||||
fi
|
||||
}
|
||||
|
||||
# Updates a specific partition in given image file (from stdin)
|
||||
image_update_partition() {
|
||||
local file="$1"
|
||||
local part_num="$2"
|
||||
local offset="$(image_part_offset "$file" "$part_num")" ||
|
||||
image_die "failed to find partition #$part_num from: $file"
|
||||
local size="$(image_part_size "$file" "$part_num")" ||
|
||||
image_die "failed to find partition #$part_num from: $file"
|
||||
|
||||
image_update_partial_file "$file" "$offset" "$size"
|
||||
}
|
||||
|
||||
# Maps a specific partition from given image file to a loop device
|
||||
image_map_partition() {
|
||||
local file="$1"
|
||||
@ -173,34 +208,39 @@ image_umount_partition() {
|
||||
sudo umount -d "$mount_point"
|
||||
}
|
||||
|
||||
# Copy a partition from one image to another.
|
||||
# Copy a partition from one image to another (size must be equal)
|
||||
image_partition_copy() {
|
||||
local src="$1"
|
||||
local srcpart="$2"
|
||||
local dst="$3"
|
||||
local dstpart="$4"
|
||||
|
||||
local srcoffset=$(image_part_offset "${src}" "${srcpart}")
|
||||
local dstoffset=$(image_part_offset "${dst}" "${dstpart}")
|
||||
local length=$(image_part_size "${src}" "${srcpart}")
|
||||
local dstlength=$(image_part_size "${dst}" "${dstpart}")
|
||||
|
||||
if [ "${length}" -gt "${dstlength}" ]; then
|
||||
exit 1
|
||||
local src="$1" src_part="$2" dst="$3" dst_part="$4"
|
||||
local size1="$(image_part_size "$src" "$src_part")"
|
||||
local size2="$(image_part_size "$dst" "$dst_part")"
|
||||
if [ "$size1" != "$size2" ]; then
|
||||
die "Partition size different: ($size1 != $size2)"
|
||||
fi
|
||||
image_dump_partition "$src" "$src_part" 2>/dev/null |
|
||||
image_update_partition "$dst" "$dst_part"
|
||||
}
|
||||
|
||||
# Try to use larger buffer if offset/size can be re-aligned.
|
||||
# 2M / 512 = 4096
|
||||
local buffer_ratio=4096
|
||||
local bs=512
|
||||
if [ $((dstoffset % buffer_ratio)) -eq 0 -a \
|
||||
$((length % buffer_ratio)) -eq 0 ]; then
|
||||
dstoffset=$((dstoffset / buffer_ratio))
|
||||
bs=$((bs * buffer_ratio))
|
||||
# Copy a partition from one image to another (source <= dest)
|
||||
image_partition_overwrite() {
|
||||
local src="$1" src_part="$2" dst="$3" dst_part="$4"
|
||||
local size1="$(image_part_size "$src" "$src_part")"
|
||||
local size2="$(image_part_size "$dst" "$dst_part")"
|
||||
if [ "$size1" -gt "$size2" ]; then
|
||||
die "Destination is too small: ($size1 > $size2)"
|
||||
fi
|
||||
image_dump_partition "$src" "$src_part" 2>/dev/null |
|
||||
image_update_partition "$dst" "$dst_part"
|
||||
}
|
||||
|
||||
image_dump_partition "${src}" "${srcpart}" |
|
||||
dd of="${dst}" bs="${bs}" seek="${dstoffset}" conv=notrunc oflag=dsync
|
||||
# Copy a partition image from file to a full disk image.
|
||||
image_partition_copy_from_file() {
|
||||
local src="$1" dst="$2" dst_part="$3"
|
||||
local size1="$(($(stat -c"%s" "$src") / 512))"
|
||||
local size2="$(image_part_size "$dst" "$dst_part")"
|
||||
if [ "$size1" != "$size2" ]; then
|
||||
die "Partition size different: ($size1 != $size2)"
|
||||
fi
|
||||
cat "$src" | image_update_partition "$dst" "$dst_part"
|
||||
}
|
||||
|
||||
# Temporary object management
|
||||
|
@ -230,8 +230,8 @@ prepare_img() {
|
||||
"$(stat -c %s ${outdev})" != "$(( ${sectors} * 512 ))" -o \
|
||||
"$FLAGS_preserve" = "$FLAGS_FALSE" ]; then
|
||||
echo "Generating empty image file"
|
||||
image_dump_partial_file /dev/zero 0 "${sectors}" |
|
||||
dd of="${outdev}" bs=8M
|
||||
truncate -s "0" "$outdev"
|
||||
truncate -s "$((sectors * 512))" "$outdev"
|
||||
else
|
||||
echo "Reusing $outdev"
|
||||
fi
|
||||
@ -381,28 +381,23 @@ generate_img() {
|
||||
local release_image="${RELEASE_DIR}/${RELEASE_IMAGE}"
|
||||
echo "Release Kernel"
|
||||
if [ -n "$RELEASE_KERNEL" ]; then
|
||||
local newkernel="$(image_map_partition "${outdev}" "4")"
|
||||
local failed=""
|
||||
sudo dd if="$RELEASE_KERNEL" of="$newkernel" bs=512 ||
|
||||
failed="TRUE"
|
||||
image_unmap_partition "$newkernel"
|
||||
[ -z "$failed" ] || die "Failed to build release kernel."
|
||||
image_partition_copy_from_file "${RELEASE_KERNEL}" "${outdev}" 4
|
||||
else
|
||||
image_partition_copy "${release_image}" 2 "${outdev}" 4
|
||||
fi
|
||||
echo "Release Rootfs"
|
||||
image_partition_copy "${release_image}" 3 "${outdev}" 5
|
||||
image_partition_overwrite "${release_image}" 3 "${outdev}" 5
|
||||
echo "OEM parition"
|
||||
image_partition_copy "${release_image}" 8 "${outdev}" 8
|
||||
image_partition_overwrite "${release_image}" 8 "${outdev}" 8
|
||||
|
||||
# Go to retrieve the factory test image.
|
||||
local factory_image="${FACTORY_DIR}/${FACTORY_IMAGE}"
|
||||
echo "Factory Kernel"
|
||||
image_partition_copy "${factory_image}" 2 "${outdev}" 2
|
||||
echo "Factory Rootfs"
|
||||
image_partition_copy "${factory_image}" 3 "${outdev}" 3
|
||||
image_partition_overwrite "${factory_image}" 3 "${outdev}" 3
|
||||
echo "Factory Stateful"
|
||||
image_partition_copy "${factory_image}" 1 "${outdev}" 1
|
||||
image_partition_overwrite "${factory_image}" 1 "${outdev}" 1
|
||||
echo "EFI Partition"
|
||||
image_partition_copy "${factory_image}" 12 "${outdev}" 12
|
||||
apply_hwid_updater "${hwid_updater}" "${outdev}"
|
||||
|
Loading…
Reference in New Issue
Block a user