Skip to content

OOT modules sign #2636

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Apr 30, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions run_sdk_container
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,7 @@ if [[ -z ${stat} ]] ; then
docker_flags=(
"${tty[@]}"
-i
--mount type=tmpfs,destination=/tmp
-v /dev:/dev
-v "${PWD}/sdk_container:/mnt/host/source/"
-v "${PWD}/__build__/images:/mnt/host/source/src/build"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -136,20 +136,41 @@ getconfig() {
echo "${value}"
}

get_sig_key() {
local sig_key="$(getconfig MODULE_SIG_KEY)"

if [[ "${sig_key}" == "build/certs/signing_key.pem" ]]; then
die "MODULE_SIG_KEY is using the default value"
fi

if [[ ${sig_key} != /tmp/* ]]; then
die "Refusing to to continue with modules key outside of /tmp, so that it stays in RAM only."
fi
if [ "$sig_key" != "${MODULES_SIGN_KEY}" ]; then
die "MODULES_SIGN_KEY variable is different than MODULE_SIG_KEY in kernel config."
fi

echo $sig_key
}

validate_sig_key() {
get_sig_key > /dev/null
}

# Generate the module signing key for this build.
setup_keys() {
local sig_hash sig_key
sig_hash=$(getconfig MODULE_SIG_HASH)
sig_key="build/$(getconfig MODULE_SIG_KEY)"
sig_key="$(get_sig_key)"

if [[ "${sig_key}" == "build/certs/signing_key.pem" ]]; then
die "MODULE_SIG_KEY is using the default value"
fi
echo "Preparing keys at $sig_key"

mkdir -p certs "${sig_key%/*}" || die
mkdir -p $MODULE_SIGNING_KEY_DIR
pushd $MODULE_SIGNING_KEY_DIR

mkdir -p gen_certs || die
# based on the default config the kernel auto-generates
cat >certs/modules.cnf <<-EOF
cat >gen_certs/modules.cnf <<-EOF
[ req ]
default_bits = 4096
distinguished_name = req_distinguished_name
Expand All @@ -169,19 +190,20 @@ setup_keys() {
EOF
openssl req -new -nodes -utf8 -days 36500 -batch -x509 \
"-${sig_hash}" -outform PEM \
-config certs/modules.cnf \
-out certs/modules.pub.pem \
-keyout certs/modules.key.pem \
-config gen_certs/modules.cnf \
-out gen_certs/modules.pub.pem \
-keyout gen_certs/modules.key.pem \
|| die "Generating module signing key failed"
cat certs/modules.pub.pem certs/modules.key.pem > "${sig_key}"
}

# Discard the module signing key but keep public certificate.
shred_keys() {
local sig_key
sig_key="build/$(getconfig MODULE_SIG_KEY)"
shred -u certs/modules.key.pem "${sig_key}" || die
cp certs/modules.pub.pem "${sig_key}" || die
# copy the cert/key to desired location
mkdir -p "${MODULES_SIGN_CERT%/*}" "${MODULES_SIGN_KEY%/*}" || die
cat gen_certs/modules.pub.pem gen_certs/modules.key.pem > "$MODULES_SIGN_KEY" || die
cp gen_certs/modules.pub.pem $MODULES_SIGN_CERT || die

shred -u gen_certs/* || die
rmdir gen_certs || die

popd
}

# Populate /lib/modules/$(uname -r)/{build,source}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -124,3 +124,10 @@ CGO_ENABLED=1

# Keep using old binary format for now.
BINPKG_FORMAT=xpak

# move signing key and cert to /tmp so that the ephemeral key is not stored on a disk
MODULES_SIGN_KEY="/tmp/certs/modules.pem"
MODULES_SIGN_CERT="/tmp/certs/modules.pub.pem"

# enable signing kernel modules from portage
USE="${USE} modules-sign"
Original file line number Diff line number Diff line change
Expand Up @@ -59,9 +59,7 @@ src_prepare() {
# Pull in the config and public module signing key
KV_OUT_DIR="${ESYSROOT}/lib/modules/${COREOS_SOURCE_NAME#linux-}/build"
cp -v "${KV_OUT_DIR}/.config" build/ || die
local sig_key="$(getconfig MODULE_SIG_KEY)"
mkdir -p "build/${sig_key%/*}" || die
cp -v "${KV_OUT_DIR}/${sig_key}" "build/${sig_key}" || die
validate_sig_key

config_update 'CONFIG_INITRAMFS_SOURCE="bootengine.cpio"'

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ src_prepare() {
local archconfig="$(find_archconfig)"
local commonconfig="$(find_commonconfig)"
elog "Building using config ${archconfig} and ${commonconfig}"
cat "${archconfig}" "${commonconfig}" >> build/.config || die
cat "${archconfig}" "${commonconfig}" | envsubst '$MODULE_SIGNING_KEY_DIR' >> build/.config || die
fi
cpio -ov </dev/null >build/bootengine.cpio

Expand Down Expand Up @@ -52,7 +52,6 @@ src_install() {
rm "${D}/usr/lib/debug/usr/lib/modules/${KV_FULL}/build" || die

# Clean up the build tree
shred_keys
kmake clean

# TODO: ensure that fixdep and kbuild tools shipped inside the image
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -498,7 +498,7 @@ CONFIG_MMC_SDHCI_PCI=m
CONFIG_MODULES=y
CONFIG_MODULE_COMPRESS_XZ=y
CONFIG_MODULE_SIG=y
CONFIG_MODULE_SIG_KEY="certs/modules.pem"
CONFIG_MODULE_SIG_KEY="${MODULE_SIGNING_KEY_DIR}/certs/modules.pem"
CONFIG_MODULE_SIG_SHA256=y
CONFIG_MODULE_UNLOAD=y
CONFIG_MOUSE_PS2=m
Expand Down
14 changes: 14 additions & 0 deletions sdk_lib/sdk_entry.sh
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,20 @@ sed -i -r '/^masters =/s/\bcoreos(\s|$)/coreos-overlay\1/g' /usr/local/portage/c
fi
)

# SDK container is launched using the su command below, which does not preserve environment
# moreover, if multiple shells are attached to the same container,
# we want all of them to share the same value of the variable, therefore we need to save it in .bashrc
grep -q 'export MODULE_SIGNING_KEY_DIR' /home/sdk/.bashrc || {
MODULE_SIGNING_KEY_DIR=$(su sdk -c "mktemp -d")
if [[ ! "$MODULE_SIGNING_KEY_DIR" || ! -d "$MODULE_SIGNING_KEY_DIR" ]]; then
echo "Failed to create temporary directory for secure boot keys."
else
echo "export MODULE_SIGNING_KEY_DIR='$MODULE_SIGNING_KEY_DIR'" >> /home/sdk/.bashrc
echo "export MODULES_SIGN_KEY='${MODULE_SIGNING_KEY_DIR}/certs/modules.pem'" >> /home/sdk/.bashrc
echo "export MODULES_SIGN_CERT='${MODULE_SIGNING_KEY_DIR}/certs/modules.pub.pem'" >> /home/sdk/.bashrc
fi
}

# This is ugly.
# We need to sudo su - sdk -c so the SDK user gets a fresh login.
# 'sdk' is member of multiple groups, and plain docker USER only
Expand Down
Loading