• Jason A. Donenfeld's avatar
    x86/setup: Use rng seeds from setup_data · 68b8e971
    Jason A. Donenfeld authored
    Currently, the only way x86 can get an early boot RNG seed is via EFI,
    which is generally always used now for physical machines, but is very
    rarely used in VMs, especially VMs that are optimized for starting
    "instantaneously", such as Firecracker's MicroVM. For tiny fast booting
    VMs, EFI is not something you generally need or want.
    
    Rather, the image loader or firmware should be able to pass a single
    random seed, exactly as device tree platforms do with the "rng-seed"
    property. Additionally, this is something that bootloaders can append,
    with their own seed file management, which is something every other
    major OS ecosystem has that Linux does not (yet).
    
    Add SETUP_RNG_SEED, similar to the other eight setup_data entries that
    are parsed at boot. It also takes care to zero out the seed immediately
    after using, in order to retain forward secrecy. This all takes about 7
    trivial lines of code.
    
    Then, on kexec_file_load(), a new fresh seed is generated and passed to
    the next kernel, just as is done on device tree architectures when
    using kexec. And, importantly, I've tested that QEMU is able to properly
    pass SETUP_RNG_SEED as well, making this work for every step of the way.
    This code too is pretty straight forward.
    
    Together these measures ensure that VMs and nested kexec()'d kernels
    always receive a proper boot time RNG seed at the earliest possible
    stage from their parents:
    
       - Host [already has strongly initialized RNG]
         - QEMU [passes fresh seed in SETUP_RNG_SEED field]
           - Linux [uses parent's seed and gathers entropy of its own]
             - kexec [passes this in SETUP_RNG_SEED field]
               - Linux [uses parent's seed and gathers entropy of its own]
                 - kexec [passes this in SETUP_RNG_SEED field]
                   - Linux [uses parent's seed and gathers entropy of its own]
                     - kexec [passes this in SETUP_RNG_SEED field]
    		   - ...
    
    I've verified in several scenarios that this works quite well from a
    host kernel to QEMU and down inwards, mixing and matching loaders, with
    every layer providing a seed to the next.
    
      [ bp: Massage commit message. ]
    Signed-off-by: default avatarJason A. Donenfeld <Jason@zx2c4.com>
    Signed-off-by: default avatarBorislav Petkov <bp@suse.de>
    Acked-by: default avatarH. Peter Anvin (Intel) <hpa@zytor.com>
    Link: https://lore.kernel.org/r/20220630113300.1892799-1-Jason@zx2c4.com
    68b8e971
kexec-bzimage64.c 17.2 KB