diff options
author | Randall Spangler <rspangler@chromium.org> | 2011-05-12 15:37:45 -0700 |
---|---|---|
committer | Randall Spangler <rspangler@chromium.org> | 2011-05-13 12:49:22 -0700 |
commit | 7ecb39d419706756a7a9054fa151345f04c3a0a2 (patch) | |
tree | 2a0104e54b59b9881fb1e77cef314da17cbf0b7c | |
parent | ae87b92cbe41e7a0ac9927de06d722051130a35f (diff) | |
download | vboot-7ecb39d419706756a7a9054fa151345f04c3a0a2.tar.gz |
Check whether key block and preamble fit in padding.
Also add --pad as a valid option to --repack and --verify, so that
kernels with larger-than-normal padding can be verified.
BUG=chromium-os:13720
TEST=see bug 13720
Using the supplied kernel images from the bug,
vbutil_kernel --verify 007 --debug
vbutil_kernel --verify 008 --debug
These should now fail with an error that the key block extends past the padding.
Next, supply a large enough padding size that the key block and
preamble fit. For example:
vbutil_kernel --verify 007 --pad 0x900000 --debug
vbutil_kernel --verify 008 --pad 0x900000 --debug
These should now make it past the padding check, and fail on a
subsequent test (for example, no kernel blob found).
Change-Id: I7ec32b4def29970e302bf922b96d3e206d97fe82
Reviewed-on: http://gerrit.chromium.org/gerrit/810
Reviewed-by: Gaurav Shah <gauravsh@chromium.org>
Tested-by: Randall Spangler <rspangler@chromium.org>
-rw-r--r-- | utility/vbutil_kernel.c | 26 |
1 files changed, 18 insertions, 8 deletions
diff --git a/utility/vbutil_kernel.c b/utility/vbutil_kernel.c index 4904610a..c2b4a0fa 100644 --- a/utility/vbutil_kernel.c +++ b/utility/vbutil_kernel.c @@ -129,6 +129,7 @@ static int PrintHelp(char *progname) { " --keyblock <file>" " Outputs the verified key block, in .keyblock format\n" " --kloadaddr <address> Assign kernel body load address\n" + " --pad <number> Verification padding size in bytes\n" " --minversion <number> Minimum combined kernel key version\n" " and kernel version\n" "\n", @@ -407,7 +408,7 @@ static blob_t *NewBlob(uint64_t version, /* Pull the blob_t stuff out of a prepacked kernel blob file */ -static blob_t *OldBlob(const char* filename) { +static blob_t *OldBlob(const char* filename, uint64_t pad) { FILE* fp = NULL; blob_t *bp = NULL; struct stat statbuf; @@ -428,7 +429,7 @@ static blob_t *OldBlob(const char* filename) { } Debug("%s size is 0x%" PRIx64 "\n", filename, statbuf.st_size); - if (statbuf.st_size < DEFAULT_PADDING) { + if (statbuf.st_size < pad) { error("%s is too small to be a valid kernel blob\n"); return 0; } @@ -440,13 +441,13 @@ static blob_t *OldBlob(const char* filename) { return 0; } - buf = Malloc(DEFAULT_PADDING); + buf = Malloc(pad); if (!buf) { error("Unable to allocate padding\n"); goto unwind_oldblob; } - if (1 != fread(buf, DEFAULT_PADDING, 1, fp)) { + if (1 != fread(buf, pad, 1, fp)) { error("Unable to read header from %s: %s\n", filename, error_fread(fp)); goto unwind_oldblob; } @@ -459,6 +460,10 @@ static blob_t *OldBlob(const char* filename) { error("key_block_size advances past the end of the blob\n"); goto unwind_oldblob; } + if (now > pad) { + error("key_block_size advances past %" PRIu64 " byte padding\n", pad); + goto unwind_oldblob; + } /* Skip the preamble */ preamble = (VbKernelPreambleHeader*)(buf + now); @@ -468,6 +473,10 @@ static blob_t *OldBlob(const char* filename) { error("preamble_size advances past the end of the blob\n"); goto unwind_oldblob; } + if (now > pad) { + error("preamble_size advances past %" PRIu64 " byte padding\n", pad); + goto unwind_oldblob; + } /* Go find the kernel blob */ Debug("kernel blob is at offset 0x%" PRIx64 "\n", now); @@ -664,7 +673,8 @@ static int ReplaceConfig(blob_t* bp, const char* config_file, static int Verify(const char* infile, const char* signpubkey, int verbose, const char* key_block_file, - uint64_t kernel_body_load_address, uint64_t min_version) { + uint64_t kernel_body_load_address, uint64_t min_version, + uint64_t pad) { VbKeyBlockHeader* key_block; VbKernelPreambleHeader* preamble; @@ -690,7 +700,7 @@ static int Verify(const char* infile, const char* signpubkey, int verbose, } /* Read blob */ - bp = OldBlob(infile); + bp = OldBlob(infile, pad); if (!bp) { error("Error reading input file\n"); return 1; @@ -960,7 +970,7 @@ int main(int argc, char* argv[]) { return 1; } - bp = OldBlob(oldfile); + bp = OldBlob(oldfile, pad); if (!bp) return 1; r = ReplaceConfig(bp, config_file, kernel_body_load_address); @@ -976,7 +986,7 @@ int main(int argc, char* argv[]) { case OPT_MODE_VERIFY: return Verify(filename, signpubkey, verbose, key_block_file, - kernel_body_load_address, min_version); + kernel_body_load_address, min_version, pad); default: fprintf(stderr, |