Proposal for an interface for communicating keys from loader to kernel

Eric McCorkle eric at metricspace.net
Sun May 15 22:06:07 UTC 2016


I've developed a plan for a general interface for communicating keys from loader to kernel as part of my ongoing work.  As it involves creating an interface between kernel and loader, I wanted to put it out for discussion before I start writing code on it.

I'm aware of the current solution based on environment variables.  It has a number of shortcomings I aim to address with this proposal:
* It communicates only a single key to the kernel
* It could lead to accidental key disclosure by debugging (also, when last I checked, the memory holding the key isn't properly zeroed out, which is a security risk)
* It is incompatible with hardware security modules (HSMs)

The basic idea is that the interface for doing this will look like a KMS (key management system) to loader.  In EFI land, this will be accomplished using the EFI_KMS_PROTOCOL interface (see UEFI spec 2.6).  This should allow loader to treat a software-based approach and one that uses a hardware security module of some kind as similarly as possible (some difference in the exact client data may be necessary, but the interface as a whole should be the same).

In EFI land, GELI (and any other crypto module) will be able to be configured to store keys into a KMS with a given name.  There will be a software kernel injection driver which implements EFI_KMS_PROTOCOL which functions as follows:
* The kernel (or a module) will have a static key buffer added, which includes space for some number of keys and their descriptors.  The exact format of this is TBD.  It will have a specified name, and will be exposed as a linkable symbol.
* The loader-side driver (which implements EFI_KMS_PROTOCOL) will maintain this data in a buffer whose size and format exactly matches the one in the kernel.
* boot1 and loader will store keys for any system that requests them (such as GELI) using the EFI_KMS_PROTOCOL functions.
* Adding a client named "kernel", with the client data being a pointer to an ELF image will cause the driver to resolve the symbol for the kernel key buffer and copy all the data into place.  Updating the client data will cause the driver to zero out the previous data and perform the lookup and copy again.
* During boot, the kernel is expected to check this buffer for keys first when initializing any system that may require key input (such as GELI).  It is expected to zero out the buffer at the end of boot.

This could alternately be implemented as a device driver.  If there is an existing generic KMS interface, then I should use it as a template for such a system (I am not aware of one, but that doesn't mean it doesn't exist).

Should support for some kind of HSM device be added, this approach should require minimal modification to support it fully.  This should also be orthogonal to the current environment variable solution, so that approach can continue to be used for as long as necessary.

I anticipate having GELI probing and access working by next weekend, after which I will implement the system I've described here.  So I wanted to get this out for consideration before then.

Comments and suggestions are welcome.  Feel free to forward this proposal to anyone or any list that should see it.


More information about the freebsd-hackers mailing list