cbfstool: add unprocessed flag for file exporting
Add an unprocessed flag (-U) which modifies how files are exported. In the case of a compressed raw file, extract without decompressing. In the case of a stage or payload, extract without decompressing or converting to an ELF. This can be useful for verifying the integrity of a stage or payload, since converting to an ELF may not be a deterministic process on different platforms or coreboot versions. BUG=b:111577108 TEST=USE=cb_legacy_tianocore emerge-eve edk2 coreboot-utils chromeos-bootimage cd /build/eve/firmware /build/eve/usr/bin/cbfstool image.bin extract -r RW_LEGACY \ -n payload -f /tmp/payload_1 -U START=$((16#`xxd -s 20 -l 4 -p tianocore.cbfs`)) SIZE=$((16#`xxd -s 8 -l 4 -p tianocore.cbfs`)) dd if=tianocore.cbfs skip=$START count=$SIZE bs=1 > /tmp/payload_2 diff /tmp/payload_1 /tmp/payload_2 rm /tmp/payload_1 /tmp/payload_2 Change-Id: I351d471d699daedd51adf4a860661877f25607e6 Signed-off-by: Joel Kitching <kitching@chromium.org> Reviewed-on: https://review.coreboot.org/29616 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Aaron Durbin <adurbin@chromium.org> Reviewed-by: Patrick Georgi <pgeorgi@google.com> Reviewed-by: Julius Werner <jwerner@chromium.org>
This commit is contained in:
committed by
Patrick Georgi
parent
73bbcee932
commit
21fdd89b0c
@@ -1286,7 +1286,7 @@ out:
|
||||
}
|
||||
|
||||
int cbfs_export_entry(struct cbfs_image *image, const char *entry_name,
|
||||
const char *filename, uint32_t arch)
|
||||
const char *filename, uint32_t arch, bool do_processing)
|
||||
{
|
||||
struct cbfs_file *entry = cbfs_get_entry(image, entry_name);
|
||||
struct buffer buffer;
|
||||
@@ -1295,26 +1295,37 @@ int cbfs_export_entry(struct cbfs_image *image, const char *entry_name,
|
||||
return -1;
|
||||
}
|
||||
|
||||
unsigned int compressed_size = ntohl(entry->len);
|
||||
unsigned int decompressed_size = 0;
|
||||
unsigned int compression = cbfs_file_get_compression_info(entry,
|
||||
&decompressed_size);
|
||||
unsigned int buffer_size;
|
||||
decomp_func_ptr decompress;
|
||||
|
||||
decomp_func_ptr decompress = decompression_function(compression);
|
||||
if (!decompress) {
|
||||
ERROR("looking up decompression routine failed\n");
|
||||
return -1;
|
||||
if (do_processing) {
|
||||
decompress = decompression_function(compression);
|
||||
if (!decompress) {
|
||||
ERROR("looking up decompression routine failed\n");
|
||||
return -1;
|
||||
}
|
||||
buffer_size = decompressed_size;
|
||||
} else {
|
||||
/* Force nop decompression */
|
||||
decompress = decompression_function(CBFS_COMPRESS_NONE);
|
||||
buffer_size = compressed_size;
|
||||
}
|
||||
|
||||
LOG("Found file %.30s at 0x%x, type %.12s, size %d\n",
|
||||
LOG("Found file %.30s at 0x%x, type %.12s, compressed %d, size %d\n",
|
||||
entry_name, cbfs_get_entry_addr(image, entry),
|
||||
get_cbfs_entry_type_name(ntohl(entry->type)), decompressed_size);
|
||||
get_cbfs_entry_type_name(ntohl(entry->type)), compressed_size,
|
||||
decompressed_size);
|
||||
|
||||
buffer_init(&buffer, strdup("(cbfs_export_entry)"), NULL, 0);
|
||||
buffer.data = malloc(buffer_size);
|
||||
buffer.size = buffer_size;
|
||||
|
||||
buffer.data = malloc(decompressed_size);
|
||||
buffer.size = decompressed_size;
|
||||
if (decompress(CBFS_SUBHEADER(entry), ntohl(entry->len),
|
||||
buffer.data, buffer.size, NULL)) {
|
||||
if (decompress(CBFS_SUBHEADER(entry), compressed_size,
|
||||
buffer.data, buffer.size, NULL)) {
|
||||
ERROR("decompression failed for %s\n", entry_name);
|
||||
buffer_delete(&buffer);
|
||||
return -1;
|
||||
@@ -1326,13 +1337,19 @@ int cbfs_export_entry(struct cbfs_image *image, const char *entry_name,
|
||||
* one has to do a second pass for stages to potentially decompress
|
||||
* the stage data to make it more meaningful.
|
||||
*/
|
||||
if (ntohl(entry->type) == CBFS_COMPONENT_STAGE) {
|
||||
if (cbfs_stage_make_elf(&buffer, arch)) {
|
||||
buffer_delete(&buffer);
|
||||
return -1;
|
||||
if (do_processing) {
|
||||
int (*make_elf)(struct buffer *, uint32_t) = NULL;
|
||||
switch (ntohl(entry->type)) {
|
||||
case CBFS_COMPONENT_STAGE:
|
||||
make_elf = cbfs_stage_make_elf;
|
||||
break;
|
||||
case CBFS_COMPONENT_SELF:
|
||||
make_elf = cbfs_payload_make_elf;
|
||||
break;
|
||||
}
|
||||
} else if (ntohl(entry->type) == CBFS_COMPONENT_SELF) {
|
||||
if (cbfs_payload_make_elf(&buffer, arch)) {
|
||||
if (make_elf && make_elf(&buffer, arch)) {
|
||||
ERROR("Failed to write %s into %s.\n",
|
||||
entry_name, filename);
|
||||
buffer_delete(&buffer);
|
||||
return -1;
|
||||
}
|
||||
|
Reference in New Issue
Block a user