Open Foxboron opened 4 years ago
Are the revocation lists signed in any way? Would be nice to check that. Also find some way of downloading the correct list for each architecture (potentially just run uname
).
They are, so we can use goefi
to actually validate the signature then remove it and apply it properly :)
https://paste.xinu.at/8BFRYyloBkeFQzHfQ/
I also need to write up some better support in goefi
to analyze them. It borks on the signed filed.
https://github.com/Foxboron/goefi/commit/7bd2151655c84ef4afe43d00261c8b7b87563b45
And now efianalyze
can read the signed siglist :)
https://github.com/Foxboron/goefi/commit/51986df877a4a3f81fbee79933fbb91eb31ee1cf
Nice!
Hi, is there a way to do this manually (download, read, sign & enroll) until sbctl supports it?
I've been trying to find some doc to do that with limited success.
If you enroll with Microsoft certificates you can just use dbxtools
to update the list manually. I'd assume enabling the testing feature from fwupd works as well but I haven't tested it.
However, implementing this feature should be straight forward. Just need to prioritize a bit of time to sbctl
soon :)
fwupd
Yeah, I stumbled upon some doc on that and have it installed but apparently it supports 0 device on my computer so not sure how useful it is to me atm.
I just tried dbxtool
but unfortunately, it always says my /sys/firmware/efi/efivars/dbx-xxx
file is missing and that it can't do anything thus.
However, implementing this feature should be straight forward. Just need to prioritize a bit of time to sbctl soon :)
Your project is a great help already, thanks a lot!
I managed to merge the "official" dbxupdate_x64.bin file (https://uefi.org/sites/default/files/resources/dbxupdate_x64.bin ) with the existing hashes in dbx and enroll both together again in UEFI SecureBoot NVRAM! I am really bad at scripting / programming, so please excuse any errors. Here is what I did:
# Install the necessary packages:
pacman -S dbxtool efitools sbsigntools e2fsprogs xxd
# Create the folders for dbx:
mkdir -p /etc/secureboot/keys/dbx/{old,new}
# Go to the folder for new dbx keys and hashes:
cd /etc/secureboot/keys/dbx/new/
# Download the UEFI revocation list:
wget https://uefi.org/sites/default/files/resources/dbxupdate_x64.bin
# Read the SHA256sums from the DBXupdate file with dbxtool and dump them into a file:
dbxtool -d dbxupdate_x64.bin -l \
| sed 's/ {microsoft} {sha256} //' \
| sed 's/ [ 0123456789][ 0123456789][ 0123456789]://' \
> new_dbx_sha256hashes.txt
# Make the directory for binary and hex codes:
mkdir /etc/secureboot/keys/dbx/new/{bin,hex}
# Create new text files containing the hashes:
cat new_dbx_sha256hashes.txt | while read LINE \
do \
SHA256HASH=$(echo $LINE | tr --delete '\n') \
touch hex/$SHA256HASH.txt \
echo $SHA256HASH | tr --delete '\n' > hex/$SHA256HASH.txt \
done
# Get the old dbx entries:
cd /etc/secureboot/keys/dbx/old/
sudo efi-readvar -v dbx -o /etc/secureboot/keys/dbx/old/old_dbx.esl
# Make the directory for binary and hex codes:
mkdir bin hex
sig-list-to-certs /etc/secureboot/keys/dbx/old/old_dbx.esl /etc/secureboot/keys/dbx/bin/old_dbx
# Making the old dbx hash files human-readable:
for NBR in {0..100}
do
SHA256HASH=$(xxd -ps -c 64 "bin/old_dbx-${NBR}.hash" | tr --delete '\n')
touch hex/$SHA256HASH.txt
echo $SHA256HASH | tr --delete '\n' > hex/$SHA256HASH.txt
done
# Syncing the folders with old and new dbx entries:
cd /etc/secureboot/keys/dbx/
mkdir -p synced/hex/
cp -f old/hex/* synced/hex/
cp -f new/hex/* synced/hex/
# How to make binary ESL files from SHA256 text files in hex code???
# hash-to-efi-sig-list can only handle efi binaries, but not text files!
# Let's do some reverse-engineering! What does hash-to-efi-sig-list do?
# Let's try it with the KeyTool efi binary (you can take any other EFI binary you like):
cp /usr/share/efitools/efi/KeyTool.efi /etc/secureboot/keys/
cd /etc/secureboot/keys/
sbverify --list KeyTool.efi
# > warning: data remaining[120832 vs 131840]: gaps between PE/COFF sections?
# > No signature table present
# So it is not signed!
hash-to-efi-sig-list KeyTool.efi KeyTool.esl
# > HASH IS ebfaa81e3c85bd930195ee018661325cf8f7051f450d61a6003506341d739f54
xxd -ps -c 128 KeyTool.esl
# > 2616c4c14c509240aca941f9369343284c000000000000003000000050ab5d6046e00043abb63dd810dd8b23ebfaa81e3c85bd930195ee018661325cf8f7051f450d61a6003506341d739f54
# according to https://media.defense.gov/2020/Sep/15/2002497594/-1/-1/0/CTR-UEFI-Secure-Boot-Customization-UOO168873-20.PDF, page 12
# the EFI_SIGLIST is structured 2616c4c14c509240aca941f9369343284c000000000000003000000050ab5d6046e00043abb63dd810dd8b23ebfaa81e3c85bd930195ee018661325cf8f7051f450d61a6003506341d739f54
# EFI_GUID Signature Type: 2616c4c14c509240aca941f936934328------------------------------------------------------------------------------------------------------------------------
# Signature List Size: --------------------------------4c000000----------------------------------------------------------------------------------------------------------------
# Signature Header Size: ----------------------------------------00000000--------------------------------------------------------------------------------------------------------
# Signature Size: ------------------------------------------------30000000------------------------------------------------------------------------------------------------
# Originator UUID: --------------------------------------------------------50ab5d6046e00043abb63dd810dd8b23----------------------------------------------------------------
# Payload (SHA256 hash): ----------------------------------------------------------------------------------------ebfaa81e3c85bd930195ee018661325cf8f7051f450d61a6003506341d739f54
# ... so our prefix is: 2616c4c14c509240aca941f9369343284c000000000000003000000050ab5d6046e00043abb63dd810dd8b23----------------------------------------------------------------
# The prefix for EFI Signature list files containing only SHA256 hashes, in hex code:
ESL_PREFIX=$(echo "2616c4c14c509240aca941f9369343284c000000000000003000000050ab5d6046e00043abb63dd810dd8b23" | tr --delete '\n')
# ... so in order to convert the text hash files into binary ESL files, we have to:
# 1. Add the ESL_PREFIX at the beginning
# 2. Dump the hex into a file
# 3. Convert the file into binary format
# Adding the hex code at the beginning of the hex files:
cd /etc/secureboot/keys/dbx/synced/hex/
for FILE in *.txt
do
SHA256HASH=$(basename -s .txt $FILE | tr --delete '\n')
echo "${ESL_PREFIX}${SHA256HASH}" | tr --delete '\n' > $SHA256HASH.esl.hex
done
# Convert the hex files into binary again and merge them into one big EFI Signature list file:
cd /etc/secureboot/keys/dbx/synced/bin/
for FILE in *.esl.hex
do
SHA256HASH=$(basename -s .esl.hex $FILE | tr --delete '\n')
xxd -r -p $FILE $SHA256HASH.esl
cat /etc/secureboot/keys/dbx/synced/bin/$SHA256HASH.esl > /etc/secureboot/keys/dbx/synced/bin/combined_dbx.esl
done
# Sign the dbx update:
MYGUID=$(cat /usr/share/secureboot/keys/GUID)
sign-efi-sig-list -g $MYGUID \
-c /usr/share/secureboot/keys/KEK/KEK.pem \
-k /usr/share/secureboot/keys/KEK/KEK.key \
dbx combined_dbx.esl combined_dbx.auth
# Remove the immutable flag to make EFIVARS writable:
sudo chattr -i /sys/firmware/efi/efivars/dbx-*
# Enroll the DBX SHA256 hashes in firmware:
sudo efi-updatevar -f combined_dbx.auth dbx
# If enrolling this way did not work, try KeyTool-signed.efi in your firmware!
This should be rather trivial: The official revocation list is signed by Microsoft Corporation KEK CA 2011. You just need to add that one to the KEK db if microsoft keys are used. In case where the user does not use microsoft keys, the whole revocation list is useless anyways. Also, updating this list could/should be left to fwupdmgr (though, I find it rather odd that it only offers version 77 when the official list is at 211 by now).
This should be rather trivial: The official revocation list is signed by Microsoft Corporation KEK CA 2011. You just need to add that one to the KEK db if microsoft keys are used. In case where the user does not use microsoft keys, the whole revocation list is useless anyways.
Nah, for the sake of doing it easy you just strip the Authentication header and resign it with the user-enrolled KEK. I don't think it's strictly useless as it would prevent users from signing old iterations of the Fedora shim. sbctl
can just tripple check with the dbx
when it attempts to verify the ESP.
Also, updating this list could/should be left to fwupdmgr (though, I find it rather odd that it only offers version 77 when the official list is at 211 by now).
Did this ever leave the testing branch? My impression was that it was sorta implemented once and never really progressed. It would also break unless the Microsoft KEK is enrolled, and I don't know how that failure mode looks like.
Nah, for the sake of doing it easy you just strip the Authentication header and resign it with the user-enrolled KEK. I don't think it's strictly useless as it would prevent users from signing old iterations of the Fedora shim.
sbctl
can just tripple check with thedbx
when it attempts to verify the ESP.
Why sign fedora shim in the first place when you use custom keys? Just add the fedora key to db. In fact, if you use shim, you'd be using ms keys anyways and therefore should really be adding the ms KEK key. And using shim with a custom key makes no sense to me when you do sbctl.
Did this ever leave the testing branch? My impression was that it was sorta implemented once and never really progressed. It would also break unless the Microsoft KEK is enrolled, and I don't know how that failure mode looks like.
The failure mode is very simple: If the dbx update is not trusted, the write is simply refused by the firmware and nothing happens.
Why sign fedora shim in the first place when you use custom keys? Just add the fedora key to db. In fact, if you use shim, you'd be using ms keys anyways and therefore should really be adding the ms KEK key. And using shim with a custom key makes no sense to me when you do sbctl.
It makes sense to sign the shim
even with self-enrolled keys because support for kernel module signatures with the lockdown
LSM is gated behind it. (I could rant at length about this).
It makes sense to sign the
shim
even with self-enrolled keys because support for kernel module signatures with thelockdown
LSM is gated behind it. (I could rant at length about this).
That sounds weird. Got a link for me?
https://access.redhat.com/documentation/en-us/red_hat_enterprise_linux/8/html/managing_monitoring_and_updating_the_kernel/signing-kernel-modules-for-secure-boot_managing-monitoring-and-updating-the-kernel says that the Secure Boot db is added to the kernel keyring and so any key in there should be usable for kernel module signing. So all you'd need to do is take the key that is backed into a distros shim (or whichever key is used to sign the modules) and add it to the db, no?
says that the Secure Boot db is added to the kernel keyring and so any key in there should be usable for kernel module signing. So all you'd need to do is take the key that is backed into a distros shim (or whichever key is used to sign the modules) and add it to the db, no?
No :)
This is because of an rejected upstream patch that RH/Fedora/Ubuntu/SUSE is backporting against the will/intention of the kernel maintainers. This functionality does not exist in the upstream kernel and was explicitly removed years ago.
See https://github.com/Foxboron/sbctl/issues/52#issuecomment-821537248
That sounds weird. Got a link for me?
Understandable! I have not figured out another way to load a key the kernel trusts for module signatures, which makes the entire scenario a bit bizzare.
See https://patchwork.kernel.org/project/keyrings/list/?series=608506
and https://github.com/Foxboron/sbctl/issues/52#issuecomment-1013966114
If you enroll with Microsoft certificates you can just use
dbxtools
to update the list manually. I'd assume enabling the testing feature from fwupd works as well but I haven't tested it.
I tried it with the motherboard shipped DBX combined with sbctl and Microsoft keys but haven't been able to get fwupd to give an update for it, but it does do so under other distros like Debian and Fedora with their stock secure boot setup. Is Microsoft Corporation KEK CA 2011 needed for that to work? Not sure if there would be a way to include that in the current setup if it is required.
For the dbx to be enrolled it needs to be signed by a trusted KEK. The revocation list as distributed by the UEFI forum is signed by the MS KEK, so that one has to be trusted. fwupd.efi also has to be trusted by a db key. On debian and fedora it's signed with the vendor key and relies on shim, on arch you'd have to sign it with sbctl.
Or one could resign the dbx update with the sbctl KEK. Afaik, it's the same format for the other db variables. Dunno if stripping the original signature is needed or not.
I'm quite sure the LVFS update capsules for dbx
works without the Microsoft KEK. I can implement support for enrolling the Microsoft KEK or have an update-dbx
feature though.
I'm quite sure the LVFS update capsules for
dbx
works without the Microsoft KEK. I can implement support for enrolling the Microsoft KEK or have anupdate-dbx
feature though.
I just checked, and the LVFS update contains the same dbx file as the one provided by the UEFI forum and from what I can tell are enrolled by writing to the efivar in userspace. So, MS KEK would have to be trusted for fwupd to work.
Ah I see, I did notice a while back Windows would try to push DBX updates like KB5012170 in particular but those would fail with the current MS enrolled keys sbctl has. To workaround that I cleared out the sbctl keys for factory and that update went through and I removed the MS keys again and reenrolled sbctl keys afterwards. I'm wondering in that case as well if using MS KEK might resolve that too.
it would be cool to load the lists into
dbx
.https://uefi.org/revocationlistfile