mirror of
https://github.com/systemd/systemd.git
synced 2025-03-31 14:50:15 +03:00
sysupdate: Use sector size for partition size calculations
This commit is contained in:
parent
4b17f5c378
commit
eeee486159
@ -28,6 +28,7 @@ int read_partition_info(
|
||||
const char *label;
|
||||
struct fdisk_partition *p;
|
||||
uint64_t start, size, flags;
|
||||
unsigned long ssz;
|
||||
sd_id128_t ptid, id;
|
||||
GptPartitionType type;
|
||||
size_t partno;
|
||||
@ -54,12 +55,13 @@ int read_partition_info(
|
||||
partno = fdisk_partition_get_partno(p);
|
||||
|
||||
start = fdisk_partition_get_start(p);
|
||||
assert(start <= UINT64_MAX / 512U);
|
||||
start *= 512U;
|
||||
ssz = fdisk_get_sector_size(c);
|
||||
assert(start <= UINT64_MAX / ssz);
|
||||
start *= ssz;
|
||||
|
||||
size = fdisk_partition_get_size(p);
|
||||
assert(size <= UINT64_MAX / 512U);
|
||||
size *= 512U;
|
||||
assert(size <= UINT64_MAX / ssz);
|
||||
size *= ssz;
|
||||
|
||||
label = fdisk_partition_get_name(p);
|
||||
if (!label)
|
||||
|
@ -6,116 +6,55 @@ set -eux
|
||||
set -o pipefail
|
||||
|
||||
SYSUPDATE=/lib/systemd/systemd-sysupdate
|
||||
SECTOR_SIZES="512 4096"
|
||||
BACKING_FILE=/var/tmp/72-joined.raw
|
||||
export SYSTEMD_ESP_PATH=/var/tmp/72-esp
|
||||
export SYSTEMD_XBOOTLDR_PATH=/var/tmp/72-xbootldr
|
||||
export SYSTEMD_PAGER=cat
|
||||
export SYSTEMD_LOG_LEVEL=debug
|
||||
|
||||
if ! test -x "$SYSUPDATE"; then
|
||||
echo "no systemd-sysupdate" >/skipped
|
||||
exit 0
|
||||
fi
|
||||
|
||||
export SYSTEMD_PAGER=cat
|
||||
export SYSTEMD_LOG_LEVEL=debug
|
||||
# Loopback devices may not be supported. They are used because sfdisk cannot
|
||||
# change the sector size of a file, and we want to test both 512 and 4096 byte
|
||||
# sectors. If loopback devices are not supported, we can only test one sector
|
||||
# size, and the underlying device is likely to have a sector size of 512 bytes.
|
||||
if ! losetup --find >/dev/null 2>&1; then
|
||||
echo "No loopback device support"
|
||||
SECTOR_SIZES="512"
|
||||
fi
|
||||
|
||||
rm -f /var/tmp/72-joined.raw
|
||||
truncate -s 10M /var/tmp/72-joined.raw
|
||||
|
||||
sfdisk /var/tmp/72-joined.raw <<EOF
|
||||
label: gpt
|
||||
unit: sectors
|
||||
sector-size: 512
|
||||
|
||||
size=2048, type=4f68bce3-e8cd-4db1-96e7-fbcaf984b709, name=_empty
|
||||
size=2048, type=4f68bce3-e8cd-4db1-96e7-fbcaf984b709, name=_empty
|
||||
size=2048, type=2c7357ed-ebd2-46d9-aec1-23d437ec2bf5, name=_empty
|
||||
size=2048, type=2c7357ed-ebd2-46d9-aec1-23d437ec2bf5, name=_empty
|
||||
EOF
|
||||
|
||||
rm -rf /var/tmp/72-dirs
|
||||
mkdir -p /var/tmp/72-dirs
|
||||
|
||||
rm -rf /var/tmp/72-defs
|
||||
mkdir -p /var/tmp/72-defs
|
||||
|
||||
cat >/var/tmp/72-defs/01-first.conf <<"EOF"
|
||||
[Source]
|
||||
Type=regular-file
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=part1-@v.raw
|
||||
|
||||
[Target]
|
||||
Type=partition
|
||||
Path=/var/tmp/72-joined.raw
|
||||
MatchPattern=part1-@v
|
||||
MatchPartitionType=root-x86-64
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/02-second.conf <<"EOF"
|
||||
[Source]
|
||||
Type=regular-file
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=part2-@v.raw.gz
|
||||
|
||||
[Target]
|
||||
Type=partition
|
||||
Path=/var/tmp/72-joined.raw
|
||||
MatchPattern=part2-@v
|
||||
MatchPartitionType=root-x86-64-verity
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/03-third.conf <<"EOF"
|
||||
[Source]
|
||||
Type=directory
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=dir-@v
|
||||
|
||||
[Target]
|
||||
Type=directory
|
||||
Path=/var/tmp/72-dirs
|
||||
CurrentSymlink=/var/tmp/72-dirs/current
|
||||
MatchPattern=dir-@v
|
||||
InstancesMax=3
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/04-fourth.conf <<"EOF"
|
||||
[Source]
|
||||
Type=regular-file
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=uki-@v.efi
|
||||
|
||||
[Target]
|
||||
Type=regular-file
|
||||
Path=/EFI/Linux
|
||||
PathRelativeTo=boot
|
||||
MatchPattern=uki_@v+@l-@d.efi \
|
||||
uki_@v+@l.efi \
|
||||
uki_@v.efi
|
||||
Mode=0444
|
||||
TriesLeft=3
|
||||
TriesDone=0
|
||||
InstancesMax=2
|
||||
EOF
|
||||
|
||||
rm -rf /var/tmp/72-esp /var/tmp/72-xbootldr
|
||||
mkdir -p /var/tmp/72-esp/EFI/Linux /var/tmp/72-xbootldr/EFI/Linux
|
||||
export SYSTEMD_ESP_PATH=/var/tmp/72-esp
|
||||
export SYSTEMD_XBOOTLDR_PATH=/var/tmp/72-xbootldr
|
||||
|
||||
rm -rf /var/tmp/72-source
|
||||
mkdir -p /var/tmp/72-source
|
||||
trap cleanup ERR
|
||||
cleanup() {
|
||||
set +o pipefail
|
||||
blockdev="$( losetup --list --output NAME,BACK-FILE | grep $BACKING_FILE | cut -d' ' -f1)"
|
||||
[ -n "$blockdev" ] && losetup --detach "$blockdev"
|
||||
rm -f "$BACKING_FILE"
|
||||
rm -rf /var/tmp/72-{dirs,defs,source,xbootldr,esp}
|
||||
rm -f /testok
|
||||
}
|
||||
|
||||
new_version() {
|
||||
# Inputs:
|
||||
# $1: sector size
|
||||
# $2: version
|
||||
|
||||
# Create a pair of random partition payloads, and compress one
|
||||
dd if=/dev/urandom of="/var/tmp/72-source/part1-$1.raw" bs=1024 count=1024
|
||||
dd if=/dev/urandom of="/var/tmp/72-source/part2-$1.raw" bs=1024 count=1024
|
||||
gzip -k -f "/var/tmp/72-source/part2-$1.raw"
|
||||
dd if=/dev/urandom of="/var/tmp/72-source/part1-$2.raw" bs="$1" count=2048
|
||||
dd if=/dev/urandom of="/var/tmp/72-source/part2-$2.raw" bs="$1" count=2048
|
||||
gzip -k -f "/var/tmp/72-source/part2-$2.raw"
|
||||
|
||||
# Create a random "UKI" payload
|
||||
echo $RANDOM >"/var/tmp/72-source/uki-$1.efi"
|
||||
echo $RANDOM >"/var/tmp/72-source/uki-$2.efi"
|
||||
|
||||
# Create tarball of a directory
|
||||
mkdir -p "/var/tmp/72-source/dir-$1"
|
||||
echo $RANDOM >"/var/tmp/72-source/dir-$1/foo.txt"
|
||||
echo $RANDOM >"/var/tmp/72-source/dir-$1/bar.txt"
|
||||
tar --numeric-owner -C "/var/tmp/72-source/dir-$1/" -czf "/var/tmp/72-source/dir-$1.tar.gz" .
|
||||
mkdir -p "/var/tmp/72-source/dir-$2"
|
||||
echo $RANDOM >"/var/tmp/72-source/dir-$2/foo.txt"
|
||||
echo $RANDOM >"/var/tmp/72-source/dir-$2/bar.txt"
|
||||
tar --numeric-owner -C "/var/tmp/72-source/dir-$2/" -czf "/var/tmp/72-source/dir-$2.tar.gz" .
|
||||
|
||||
( cd /var/tmp/72-source/ && sha256sum uki* part* dir-*.tar.gz >SHA256SUMS )
|
||||
}
|
||||
@ -130,46 +69,153 @@ update_now() {
|
||||
}
|
||||
|
||||
verify_version() {
|
||||
# Expects: version ID + sector offset of both partitions to compare
|
||||
# Inputs:
|
||||
# $1: block device
|
||||
# $2: sector size
|
||||
# $3: version
|
||||
# $4: partiton number of part1
|
||||
# $5: partiton number of part2
|
||||
|
||||
gpt_reserved_sectors=$(( 1024 * 1024 / $2 ))
|
||||
part1_offset=$(( ( $4 - 1 ) * 2048 + gpt_reserved_sectors ))
|
||||
part2_offset=$(( ( $5 - 1 ) * 2048 + gpt_reserved_sectors ))
|
||||
|
||||
# Check the partitions
|
||||
dd if=/var/tmp/72-joined.raw bs=1024 skip="$2" count=1024 | cmp "/var/tmp/72-source/part1-$1.raw"
|
||||
dd if=/var/tmp/72-joined.raw bs=1024 skip="$3" count=1024 | cmp "/var/tmp/72-source/part2-$1.raw"
|
||||
dd if="$1" bs="$2" skip="$part1_offset" count=2048 | cmp "/var/tmp/72-source/part1-$3.raw"
|
||||
dd if="$1" bs="$2" skip="$part2_offset" count=2048 | cmp "/var/tmp/72-source/part2-$3.raw"
|
||||
|
||||
# Check the UKI
|
||||
cmp "/var/tmp/72-source/uki-$1.efi" "/var/tmp/72-xbootldr/EFI/Linux/uki_$1+3-0.efi"
|
||||
cmp "/var/tmp/72-source/uki-$3.efi" "/var/tmp/72-xbootldr/EFI/Linux/uki_$3+3-0.efi"
|
||||
test -z "$(ls -A /var/tmp/72-esp/EFI/Linux)"
|
||||
|
||||
# Check the directories
|
||||
cmp "/var/tmp/72-source/dir-$1/foo.txt" /var/tmp/72-dirs/current/foo.txt
|
||||
cmp "/var/tmp/72-source/dir-$1/bar.txt" /var/tmp/72-dirs/current/bar.txt
|
||||
cmp "/var/tmp/72-source/dir-$3/foo.txt" /var/tmp/72-dirs/current/foo.txt
|
||||
cmp "/var/tmp/72-source/dir-$3/bar.txt" /var/tmp/72-dirs/current/bar.txt
|
||||
}
|
||||
|
||||
# Install initial version and verify
|
||||
new_version v1
|
||||
update_now
|
||||
verify_version v1 1024 3072
|
||||
for sector_size in $SECTOR_SIZES ; do
|
||||
# Disk size of:
|
||||
# - 1MB for GPT
|
||||
# - 4 partitions of 2048 sectors each
|
||||
# - 1MB for backup GPT
|
||||
disk_size=$(( sector_size * 2048 * 4 + 1024 * 1024 * 2 ))
|
||||
rm -f "$BACKING_FILE"
|
||||
truncate -s "$disk_size" "$BACKING_FILE"
|
||||
|
||||
# Create second version, update and verify that it is added
|
||||
new_version v2
|
||||
update_now
|
||||
verify_version v2 2048 4096
|
||||
if losetup --find >/dev/null 2>&1; then
|
||||
# shellcheck disable=SC2086
|
||||
blockdev="$(losetup --find --show --sector-size $sector_size $BACKING_FILE)"
|
||||
else
|
||||
blockdev="$BACKING_FILE"
|
||||
fi
|
||||
|
||||
# Create third version, update and verify it replaced the first version
|
||||
new_version v3
|
||||
update_now
|
||||
verify_version v3 1024 3072
|
||||
test ! -f "/var/tmp/72-xbootldr/EFI/Linux/uki_v1+3-0.efi"
|
||||
sfdisk "$blockdev" <<EOF
|
||||
label: gpt
|
||||
unit: sectors
|
||||
sector-size: $sector_size
|
||||
|
||||
# Create fourth version, and update through a file:// URL. This should be
|
||||
# almost as good as testing HTTP, but is simpler for us to set up. file:// is
|
||||
# abstracted in curl for us, and since our main goal is to test our own code
|
||||
# (and not curl) this test should be quite good even if not comprehensive. This
|
||||
# will test the SHA256SUMS logic at least (we turn off GPG validation though,
|
||||
# see above)
|
||||
new_version v4
|
||||
size=2048, type=4f68bce3-e8cd-4db1-96e7-fbcaf984b709, name=_empty
|
||||
size=2048, type=4f68bce3-e8cd-4db1-96e7-fbcaf984b709, name=_empty
|
||||
size=2048, type=2c7357ed-ebd2-46d9-aec1-23d437ec2bf5, name=_empty
|
||||
size=2048, type=2c7357ed-ebd2-46d9-aec1-23d437ec2bf5, name=_empty
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/02-second.conf <<"EOF"
|
||||
rm -rf /var/tmp/72-dirs
|
||||
mkdir -p /var/tmp/72-dirs
|
||||
|
||||
rm -rf /var/tmp/72-defs
|
||||
mkdir -p /var/tmp/72-defs
|
||||
|
||||
cat >/var/tmp/72-defs/01-first.conf <<EOF
|
||||
[Source]
|
||||
Type=regular-file
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=part1-@v.raw
|
||||
|
||||
[Target]
|
||||
Type=partition
|
||||
Path=$blockdev
|
||||
MatchPattern=part1-@v
|
||||
MatchPartitionType=root-x86-64
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/02-second.conf <<EOF
|
||||
[Source]
|
||||
Type=regular-file
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=part2-@v.raw.gz
|
||||
|
||||
[Target]
|
||||
Type=partition
|
||||
Path=$blockdev
|
||||
MatchPattern=part2-@v
|
||||
MatchPartitionType=root-x86-64-verity
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/03-third.conf <<EOF
|
||||
[Source]
|
||||
Type=directory
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=dir-@v
|
||||
|
||||
[Target]
|
||||
Type=directory
|
||||
Path=/var/tmp/72-dirs
|
||||
CurrentSymlink=/var/tmp/72-dirs/current
|
||||
MatchPattern=dir-@v
|
||||
InstancesMax=3
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/04-fourth.conf <<EOF
|
||||
[Source]
|
||||
Type=regular-file
|
||||
Path=/var/tmp/72-source
|
||||
MatchPattern=uki-@v.efi
|
||||
|
||||
[Target]
|
||||
Type=regular-file
|
||||
Path=/EFI/Linux
|
||||
PathRelativeTo=boot
|
||||
MatchPattern=uki_@v+@l-@d.efi \
|
||||
uki_@v+@l.efi \
|
||||
uki_@v.efi
|
||||
Mode=0444
|
||||
TriesLeft=3
|
||||
TriesDone=0
|
||||
InstancesMax=2
|
||||
EOF
|
||||
|
||||
rm -rf /var/tmp/72-esp /var/tmp/72-xbootldr
|
||||
mkdir -p /var/tmp/72-esp/EFI/Linux /var/tmp/72-xbootldr/EFI/Linux
|
||||
|
||||
rm -rf /var/tmp/72-source
|
||||
mkdir -p /var/tmp/72-source
|
||||
|
||||
# Install initial version and verify
|
||||
new_version "$sector_size" v1
|
||||
update_now
|
||||
verify_version "$blockdev" "$sector_size" v1 1 3
|
||||
|
||||
# Create second version, update and verify that it is added
|
||||
new_version "$sector_size" v2
|
||||
update_now
|
||||
verify_version "$blockdev" "$sector_size" v2 2 4
|
||||
|
||||
# Create third version, update and verify it replaced the first version
|
||||
new_version "$sector_size" v3
|
||||
update_now
|
||||
verify_version "$blockdev" "$sector_size" v3 1 3
|
||||
test ! -f "/var/tmp/72-xbootldr/EFI/Linux/uki_v1+3-0.efi"
|
||||
|
||||
# Create fourth version, and update through a file:// URL. This should be
|
||||
# almost as good as testing HTTP, but is simpler for us to set up. file:// is
|
||||
# abstracted in curl for us, and since our main goal is to test our own code
|
||||
# (and not curl) this test should be quite good even if not comprehensive. This
|
||||
# will test the SHA256SUMS logic at least (we turn off GPG validation though,
|
||||
# see above)
|
||||
new_version "$sector_size" v4
|
||||
|
||||
cat >/var/tmp/72-defs/02-second.conf <<EOF
|
||||
[Source]
|
||||
Type=url-file
|
||||
Path=file:///var/tmp/72-source
|
||||
@ -177,12 +223,12 @@ MatchPattern=part2-@v.raw.gz
|
||||
|
||||
[Target]
|
||||
Type=partition
|
||||
Path=/var/tmp/72-joined.raw
|
||||
Path=$blockdev
|
||||
MatchPattern=part2-@v
|
||||
MatchPartitionType=root-x86-64-verity
|
||||
EOF
|
||||
|
||||
cat >/var/tmp/72-defs/03-third.conf <<"EOF"
|
||||
cat >/var/tmp/72-defs/03-third.conf <<EOF
|
||||
[Source]
|
||||
Type=url-tar
|
||||
Path=file:///var/tmp/72-source
|
||||
@ -196,10 +242,14 @@ MatchPattern=dir-@v
|
||||
InstancesMax=3
|
||||
EOF
|
||||
|
||||
update_now
|
||||
verify_version v4 2048 4096
|
||||
update_now
|
||||
verify_version "$blockdev" "$sector_size" v4 2 4
|
||||
|
||||
# Cleanup
|
||||
[ -b "$blockdev" ] && losetup --detach "$blockdev"
|
||||
rm "$BACKING_FILE"
|
||||
done
|
||||
|
||||
rm /var/tmp/72-joined.raw
|
||||
rm -r /var/tmp/72-{dirs,defs,source,xbootldr,esp}
|
||||
|
||||
touch /testok
|
||||
|
Loading…
x
Reference in New Issue
Block a user