mirror of
https://github.com/linux-apfs/apfstests.git
synced 2026-05-01 15:01:44 -07:00
98a3b42b42
These have been scripted conversions then cleaned up by hand as there was no consistency to the formatting of the license headers in the common/ directory. Author information was also removed (it's in the git history) and so now the header format is consistently: ##/bin/bash # SPDX-License-Identifier: GPL-2.0(+) # Copyright (c) <date> <owner>. All Rights Reserved. # # <file description> Signed-off-by: Dave Chinner <dchinner@redhat.com>
178 lines
5.1 KiB
Plaintext
178 lines
5.1 KiB
Plaintext
##/bin/bash
|
|
# SPDX-License-Identifier: GPL-2.0
|
|
# Copyright (c) 2016 Google, Inc. All Rights Reserved.
|
|
#
|
|
# Functions for setting up and testing file encryption
|
|
|
|
_require_scratch_encryption()
|
|
{
|
|
_require_scratch
|
|
|
|
_require_xfs_io_command "set_encpolicy"
|
|
|
|
# The 'test_dummy_encryption' mount option interferes with trying to use
|
|
# encryption for real, even if we are just trying to get/set policies
|
|
# and never put any keys in the keyring. So skip the real encryption
|
|
# tests if the 'test_dummy_encryption' mount option was specified.
|
|
_exclude_scratch_mount_option "test_dummy_encryption"
|
|
|
|
# Make a filesystem on the scratch device with the encryption feature
|
|
# enabled. If this fails then probably the userspace tools (e.g.
|
|
# e2fsprogs or f2fs-tools) are too old to understand encryption.
|
|
if ! _scratch_mkfs_encrypted &>>$seqres.full; then
|
|
_notrun "$FSTYP userspace tools do not support encryption"
|
|
fi
|
|
|
|
# Try to mount the filesystem. If this fails then either the kernel
|
|
# isn't aware of encryption, or the mkfs options were not compatible
|
|
# with encryption (e.g. ext4 with block size != PAGE_SIZE).
|
|
if ! _try_scratch_mount &>>$seqres.full; then
|
|
_notrun "kernel is unaware of $FSTYP encryption feature," \
|
|
"or mkfs options are not compatible with encryption"
|
|
fi
|
|
|
|
# The kernel may be aware of encryption without supporting it. For
|
|
# example, for ext4 this is the case with kernels configured with
|
|
# CONFIG_EXT4_FS_ENCRYPTION=n. Detect support for encryption by trying
|
|
# to set an encryption policy. (For ext4 we could instead check for the
|
|
# presence of /sys/fs/ext4/features/encryption, but this is broken on
|
|
# some older kernels and is ext4-specific anyway.)
|
|
mkdir $SCRATCH_MNT/tmpdir
|
|
if $XFS_IO_PROG -c set_encpolicy $SCRATCH_MNT/tmpdir \
|
|
2>&1 >>$seqres.full | \
|
|
egrep -q 'Inappropriate ioctl for device|Operation not supported'
|
|
then
|
|
_notrun "kernel does not support $FSTYP encryption"
|
|
fi
|
|
rmdir $SCRATCH_MNT/tmpdir
|
|
_scratch_unmount
|
|
}
|
|
|
|
_scratch_mkfs_encrypted()
|
|
{
|
|
case $FSTYP in
|
|
ext4|f2fs)
|
|
_scratch_mkfs -O encrypt
|
|
;;
|
|
ubifs)
|
|
# erase the UBI volume; reformated automatically on next mount
|
|
$UBIUPDATEVOL_PROG ${SCRATCH_DEV} -t
|
|
;;
|
|
*)
|
|
_notrun "No encryption support for $FSTYP"
|
|
;;
|
|
esac
|
|
}
|
|
|
|
_scratch_mkfs_sized_encrypted()
|
|
{
|
|
case $FSTYP in
|
|
ext4|f2fs)
|
|
MKFS_OPTIONS="$MKFS_OPTIONS -O encrypt" _scratch_mkfs_sized $*
|
|
;;
|
|
*)
|
|
_notrun "Filesystem $FSTYP not supported in _scratch_mkfs_sized_encrypted"
|
|
;;
|
|
esac
|
|
}
|
|
|
|
# Give the invoking shell a new session keyring. This makes any keys we add to
|
|
# the session keyring scoped to the lifetime of the test script.
|
|
_new_session_keyring()
|
|
{
|
|
$KEYCTL_PROG new_session >>$seqres.full
|
|
}
|
|
|
|
# Generate a key descriptor (16 character hex string)
|
|
_generate_key_descriptor()
|
|
{
|
|
local keydesc=""
|
|
local i
|
|
for ((i = 0; i < 8; i++)); do
|
|
keydesc="${keydesc}$(printf "%02x" $(( $RANDOM % 256 )))"
|
|
done
|
|
echo $keydesc
|
|
}
|
|
|
|
# Generate a raw encryption key, but don't add it to the keyring yet.
|
|
_generate_raw_encryption_key()
|
|
{
|
|
local raw=""
|
|
local i
|
|
for ((i = 0; i < 64; i++)); do
|
|
raw="${raw}\\x$(printf "%02x" $(( $RANDOM % 256 )))"
|
|
done
|
|
echo $raw
|
|
}
|
|
|
|
# Add the specified raw encryption key to the session keyring, using the
|
|
# specified key descriptor.
|
|
_add_encryption_key()
|
|
{
|
|
local keydesc=$1
|
|
local raw=$2
|
|
|
|
#
|
|
# Add the key to the session keyring. The required structure is:
|
|
#
|
|
# #define FS_MAX_KEY_SIZE 64
|
|
# struct fscrypt_key {
|
|
# u32 mode;
|
|
# u8 raw[FS_MAX_KEY_SIZE];
|
|
# u32 size;
|
|
# } __packed;
|
|
#
|
|
# The kernel ignores 'mode' but requires that 'size' be 64.
|
|
#
|
|
# Keys are named $FSTYP:KEYDESC where KEYDESC is the 16-character key
|
|
# descriptor hex string. Newer kernels (ext4 4.8 and later, f2fs 4.6
|
|
# and later) also allow the common key prefix "fscrypt:" in addition to
|
|
# their filesystem-specific key prefix ("ext4:", "f2fs:"). It would be
|
|
# nice to use the common key prefix, but for now use the filesystem-
|
|
# specific prefix to make it possible to test older kernels...
|
|
#
|
|
local big_endian=$(echo -ne '\x11' | od -tx2 | head -1 | \
|
|
cut -f2 -d' ' | cut -c1 )
|
|
if (( big_endian )); then
|
|
local mode='\x00\x00\x00\x00'
|
|
local size='\x00\x00\x00\x40'
|
|
else
|
|
local mode='\x00\x00\x00\x00'
|
|
local size='\x40\x00\x00\x00'
|
|
fi
|
|
echo -n -e "${mode}${raw}${size}" |
|
|
$KEYCTL_PROG padd logon $FSTYP:$keydesc @s >>$seqres.full
|
|
}
|
|
|
|
#
|
|
# Generate a random encryption key, add it to the session keyring, and print out
|
|
# the resulting key descriptor (example: "8bf798e1a494e1ec"). Requires the
|
|
# keyctl program. It's assumed the caller has already set up a test-scoped
|
|
# session keyring using _new_session_keyring.
|
|
#
|
|
_generate_encryption_key()
|
|
{
|
|
local keydesc=$(_generate_key_descriptor)
|
|
local raw=$(_generate_raw_encryption_key)
|
|
|
|
_add_encryption_key $keydesc $raw
|
|
|
|
echo $keydesc
|
|
}
|
|
|
|
# Unlink an encryption key from the session keyring, given its key descriptor.
|
|
_unlink_encryption_key()
|
|
{
|
|
local keydesc=$1
|
|
local keyid=$($KEYCTL_PROG search @s logon $FSTYP:$keydesc)
|
|
$KEYCTL_PROG unlink $keyid >>$seqres.full
|
|
}
|
|
|
|
# Revoke an encryption key from the keyring, given its key descriptor.
|
|
_revoke_encryption_key()
|
|
{
|
|
local keydesc=$1
|
|
local keyid=$($KEYCTL_PROG search @s logon $FSTYP:$keydesc)
|
|
$KEYCTL_PROG revoke $keyid >>$seqres.full
|
|
}
|