cbfstool: Handle elf with different virtual and physical address

Adds support in cbfstool to adjust the entry field based on the
virtual and physical address in program header.

BUG=chrome-os-partner:40713
BRANCH=None
TEST=Verified correct entry point address. Trusty loads and boots correctly.

Change-Id: I215b0bea689626deec65e15fb3280e369d816406
Signed-off-by: Patrick Georgi <pgeorgi@chromium.org>
Original-Commit-Id: 32a740f0b628c124d3251cc416e2fc133bb15c57
Original-Change-Id: Ia999b5c55887c86ef1e43794ceaef2d867957f4d
Original-Signed-off-by: Furquan Shaikh <furquan@google.com>
Original-Reviewed-on: https://chromium-review.googlesource.com/274087
Original-Trybot-Ready: Furquan Shaikh <furquan@chromium.org>
Original-Tested-by: Furquan Shaikh <furquan@chromium.org>
Original-Reviewed-by: Aaron Durbin <adurbin@chromium.org>
Original-Commit-Queue: Furquan Shaikh <furquan@chromium.org>
Reviewed-on: http://review.coreboot.org/10690
Tested-by: build bot (Jenkins)
Reviewed-by: Stefan Reinauer <stefan.reinauer@coreboot.org>
This commit is contained in:
Furquan Shaikh 2015-05-29 12:46:18 -07:00 committed by Patrick Georgi
parent 41e2499734
commit f7a5b56297
1 changed files with 9 additions and 1 deletions

View File

@ -102,6 +102,7 @@ int parse_elf_to_stage(const struct buffer *input, struct buffer *output,
Elf64_Phdr *phdr; Elf64_Phdr *phdr;
Elf64_Ehdr *ehdr; Elf64_Ehdr *ehdr;
Elf64_Shdr *shdr_ignored; Elf64_Shdr *shdr_ignored;
Elf64_Addr virt_to_phys;
char *buffer; char *buffer;
struct buffer outheader; struct buffer outheader;
int ret = -1; int ret = -1;
@ -143,6 +144,7 @@ int parse_elf_to_stage(const struct buffer *input, struct buffer *output,
data_start = ~0; data_start = ~0;
data_end = 0; data_end = 0;
mem_end = 0; mem_end = 0;
virt_to_phys = 0;
for (i = 0; i < headers; i++) { for (i = 0; i < headers; i++) {
unsigned int start, mend, rend; unsigned int start, mend, rend;
@ -169,6 +171,9 @@ int parse_elf_to_stage(const struct buffer *input, struct buffer *output,
if (mend > mem_end) if (mend > mem_end)
mem_end = mend; mem_end = mend;
if (virt_to_phys == 0)
virt_to_phys = phdr[i].p_paddr - phdr[i].p_vaddr;
} }
if (data_start < *location) { if (data_start < *location) {
@ -262,7 +267,10 @@ int parse_elf_to_stage(const struct buffer *input, struct buffer *output,
* Maybe we should just change the spec. * Maybe we should just change the spec.
*/ */
xdr_le.put32(&outheader, algo); xdr_le.put32(&outheader, algo);
xdr_le.put64(&outheader, ehdr->e_entry); /* Coreboot expects entry point to be physical address. Thus, adjust the
* entry point accordingly.
*/
xdr_le.put64(&outheader, ehdr->e_entry + virt_to_phys);
xdr_le.put64(&outheader, data_start); xdr_le.put64(&outheader, data_start);
xdr_le.put32(&outheader, outlen); xdr_le.put32(&outheader, outlen);
xdr_le.put32(&outheader, mem_end - data_start); xdr_le.put32(&outheader, mem_end - data_start);