/*
 * elf header parsing.
 *
 * Copyright (C) 2013 Google, Inc.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; version 2 of the License.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "elfparsing.h"
#include "common.h"
#include "cbfs.h"

/*
 * Short form: this is complicated, but we've tried making it simple
 * and we keep hitting problems with our ELF parsing.
 *
 * The ELF parsing situation has always been a bit tricky.  In fact,
 * we (and most others) have been getting it wrong in small ways for
 * years. Recently this has caused real trouble for the ARM V8 build.
 * In this file we attempt to finally get it right for all variations
 * of endian-ness and word size and target architectures and
 * architectures we might get run on. Phew!. To do this we borrow a
 * page from the FreeBSD NFS xdr model (see elf_ehdr and elf_phdr),
 * the Plan 9 endianness functions (see xdr.c), and Go interfaces (see
 * how we use buffer structs in this file). This ends up being a bit
 * wordy at the lowest level, but greatly simplifies the elf parsing
 * code and removes a common source of bugs, namely, forgetting to
 * flip type endianness when referencing a struct member.
 *
 * ELF files can have four combinations of data layout: 32/64, and
 * big/little endian.  Further, to add to the fun, depending on the
 * word size, the size of the ELF structs varies. The coreboot SELF
 * format is simpler in theory: it's supposed to be always BE, and the
 * various struct members allow room for growth: the entry point is
 * always 64 bits, for example, so the size of a SELF struct is
 * constant, regardless of target architecture word size.  Hence, we
 * need to do some transformation of the ELF files.
 *
 * A given architecture, realistically, only supports one of the four
 * combinations at a time as the 'native' format. Hence, our code has
 * been sprinkled with every variation of [nh]to[hn][sll] over the
 * years. We've never quite gotten it all right, however, and a quick
 * pass over this code revealed another bug.  It's all worked because,
 * until now, all the working platforms that had CBFS were 32 LE. Even then,
 * however, bugs crept in: we recently realized that we're not
 * transforming the entry point to big format when we store into the
 * SELF image.
 *
 * The problem is essentially an XDR operation:
 * we have something in a foreign format and need to transform it.
 * It's most like XDR because:
 * 1) the byte order can be wrong
 * 2) the word size can be wrong
 * 3) the size of elements in the stream depends on the value
 *    of other elements in the stream
 * it's not like XDR because:
 * 1) the byte order can be right
 * 2) the word size can be right
 * 3) the struct members are all on a natural alignment
 *
 * Hence, this new approach.  To cover word size issues, we *always*
 * transform the two structs we care about, the file header and
 * program header, into a native struct in the 64 bit format:
 *
 * [32,little] -> [Elf64_Ehdr, Elf64_Phdr]
 * [64,little] -> [Elf64_Ehdr, Elf64_Phdr]
 * [32,big] -> [Elf64_Ehdr, Elf64_Phdr]
 * [64,big] -> [Elf64_Ehdr, Elf64_Phdr]
 * Then we just use those structs, and all the need for inline ntoh* goes away,
 * as well as all the chances for error.
 * This works because all the SELF structs have fields large enough for
 * the largest ELF 64 struct members, and all the Elf64 struct members
 * are at least large enough for all ELF 32 struct members.
 * We end up with one function to do all our ELF parsing, and two functions
 * to transform the headers. For the put case, we also have
 * XDR functions, and hopefully we'll never again spend 5 years with the
 * wrong endian-ness on an output value :-)
 * This should work for all word sizes and endianness we hope to target.
 * I *really* don't want to be here for 128 bit addresses.
 *
 * The parse functions are called with a pointer to an input buffer
 * struct. One might ask: are there enough bytes in the input buffer?
 * We know there need to be at *least* sizeof(Elf32_Ehdr) +
 * sizeof(Elf32_Phdr) bytes. Realistically, there has to be some data
 * too.  If we start to worry, though we have not in the past, we
 * might apply the simple test: the input buffer needs to be at least
 * sizeof(Elf64_Ehdr) + sizeof(Elf64_Phdr) bytes because, even if it's
 * ELF 32, there's got to be *some* data! This is not theoretically
 * accurate but it is actually good enough in practice. It allows the
 * header transformation code to ignore the possibility of underrun.
 *
 * We also must accomodate different ELF files, and hence formats,
 * in the same cbfs invocation. We might load a 64-bit payload
 * on a 32-bit machine; we might even have a mixed armv7/armv8
 * SOC or even a system with an x86/ARM!
 *
 * A possibly problematic (though unlikely to be so) assumption
 * is that we expect the BIOS to remain in the lowest 32 bits
 * of the physical address space. Since ARMV8 has standardized
 * on that, and x86_64 also has, this seems a safe assumption.
 *
 * To repeat, ELF structs are different sizes because ELF struct
 * members are different sizes, depending on values in the ELF file
 * header. For this we use the functions defined in xdr.c, which
 * consume bytes, convert the endianness, and advance the data pointer
 * in the buffer struct.
 */


static int iself(const void *input)
{
	const Elf32_Ehdr *ehdr = input;
	return !memcmp(ehdr->e_ident, ELFMAG, 4);
}

/* Get the ident array, so we can figure out
 * endian-ness, word size, and in future other useful
 * parameters
 */
static void
elf_eident(struct buffer *input, Elf64_Ehdr *ehdr)
{
	bgets(input, ehdr->e_ident, sizeof(ehdr->e_ident));
}


static int
check_size(const struct buffer *b, size_t offset, size_t size, const char *desc)
{
	if (size == 0)
		return 0;

	if (offset >= buffer_size(b) || (offset + size) > buffer_size(b)) {
		ERROR("The file is not large enough for the '%s'. "
		      "%zu bytes @ offset %zu, input %zu bytes.\n",
		      desc, size, offset, buffer_size(b));
		return -1;
	}
	return 0;
}

static void
elf_ehdr(struct buffer *input, Elf64_Ehdr *ehdr, struct xdr *xdr, int bit64)
{
	ehdr->e_type = xdr->get16(input);
	ehdr->e_machine = xdr->get16(input);
	ehdr->e_version = xdr->get32(input);
	if (bit64){
		ehdr->e_entry = xdr->get64(input);
		ehdr->e_phoff = xdr->get64(input);
		ehdr->e_shoff = xdr->get64(input);
	} else {
		ehdr->e_entry = xdr->get32(input);
		ehdr->e_phoff = xdr->get32(input);
		ehdr->e_shoff = xdr->get32(input);
	}
	ehdr->e_flags = xdr->get32(input);
	ehdr->e_ehsize = xdr->get16(input);
	ehdr->e_phentsize = xdr->get16(input);
	ehdr->e_phnum = xdr->get16(input);
	ehdr->e_shentsize = xdr->get16(input);
	ehdr->e_shnum = xdr->get16(input);
	ehdr->e_shstrndx = xdr->get16(input);
}

static void
elf_phdr(struct buffer *pinput, Elf64_Phdr *phdr,
	 int entsize, struct xdr *xdr, int bit64)
{
	/*
	 * The entsize need not be sizeof(*phdr).
	 * Hence, it is easier to keep a copy of the input,
	 * as the xdr functions may not advance the input
	 * pointer the full entsize; rather than get tricky
	 * we just advance it below.
	 */
	struct buffer input;
	buffer_clone(&input, pinput);
	if (bit64){
		phdr->p_type = xdr->get32(&input);
		phdr->p_flags = xdr->get32(&input);
		phdr->p_offset = xdr->get64(&input);
		phdr->p_vaddr = xdr->get64(&input);
		phdr->p_paddr = xdr->get64(&input);
		phdr->p_filesz = xdr->get64(&input);
		phdr->p_memsz = xdr->get64(&input);
		phdr->p_align = xdr->get64(&input);
	} else {
		phdr->p_type = xdr->get32(&input);
		phdr->p_offset = xdr->get32(&input);
		phdr->p_vaddr = xdr->get32(&input);
		phdr->p_paddr = xdr->get32(&input);
		phdr->p_filesz = xdr->get32(&input);
		phdr->p_memsz = xdr->get32(&input);
		phdr->p_flags = xdr->get32(&input);
		phdr->p_align = xdr->get32(&input);
	}
	buffer_seek(pinput, entsize);
}

static void
elf_shdr(struct buffer *pinput, Elf64_Shdr *shdr,
	 int entsize, struct xdr *xdr, int bit64)
{
	/*
	 * The entsize need not be sizeof(*shdr).
	 * Hence, it is easier to keep a copy of the input,
	 * as the xdr functions may not advance the input
	 * pointer the full entsize; rather than get tricky
	 * we just advance it below.
	 */
	struct buffer input = *pinput;
	if (bit64){
		shdr->sh_name = xdr->get32(&input);
		shdr->sh_type = xdr->get32(&input);
		shdr->sh_flags = xdr->get64(&input);
		shdr->sh_addr = xdr->get64(&input);
		shdr->sh_offset = xdr->get64(&input);
		shdr->sh_size= xdr->get64(&input);
		shdr->sh_link = xdr->get32(&input);
		shdr->sh_info = xdr->get32(&input);
		shdr->sh_addralign = xdr->get64(&input);
		shdr->sh_entsize = xdr->get64(&input);
	} else {
		shdr->sh_name = xdr->get32(&input);
		shdr->sh_type = xdr->get32(&input);
		shdr->sh_flags = xdr->get32(&input);
		shdr->sh_addr = xdr->get32(&input);
		shdr->sh_offset = xdr->get32(&input);
		shdr->sh_size = xdr->get32(&input);
		shdr->sh_link = xdr->get32(&input);
		shdr->sh_info = xdr->get32(&input);
		shdr->sh_addralign = xdr->get32(&input);
		shdr->sh_entsize = xdr->get32(&input);
	}
	buffer_seek(pinput, entsize);
}

static int
phdr_read(const struct buffer *in, struct parsed_elf *pelf,
          struct xdr *xdr, int bit64)
{
	struct buffer b;
	Elf64_Phdr *phdr;
	Elf64_Ehdr *ehdr;
	int i;

	ehdr = &pelf->ehdr;
	/* cons up an input buffer for the headers.
	 * Note that the program headers can be anywhere,
	 * per the ELF spec, You'd be surprised how many ELF
	 * readers miss this little detail.
	 */
	buffer_splice(&b, in, ehdr->e_phoff, ehdr->e_phentsize * ehdr->e_phnum);
	if (check_size(in, ehdr->e_phoff, buffer_size(&b), "program headers"))
		return -1;

	/* gather up all the phdrs.
	 * We do them all at once because there is more
	 * than one loop over all the phdrs.
	 */
	phdr = calloc(ehdr->e_phnum, sizeof(*phdr));
	for (i = 0; i < ehdr->e_phnum; i++) {
		DEBUG("Parsing segment %d\n", i);
		elf_phdr(&b, &phdr[i], ehdr->e_phentsize, xdr, bit64);

		/* Ensure the contents are valid within the elf file. */
		if (check_size(in, phdr[i].p_offset, phdr[i].p_filesz,
	                  "segment contents")) {
			free(phdr);
			return -1;
		}
	}

	pelf->phdr = phdr;

	return 0;
}

static int
shdr_read(const struct buffer *in, struct parsed_elf *pelf,
          struct xdr *xdr, int bit64)
{
	struct buffer b;
	Elf64_Shdr *shdr;
	Elf64_Ehdr *ehdr;
	int i;

	ehdr = &pelf->ehdr;

	/* cons up an input buffer for the section headers.
	 * Note that the section headers can be anywhere,
	 * per the ELF spec, You'd be surprised how many ELF
	 * readers miss this little detail.
	 */
	buffer_splice(&b, in, ehdr->e_shoff, ehdr->e_shentsize * ehdr->e_shnum);
	if (check_size(in, ehdr->e_shoff, buffer_size(&b), "section headers"))
		return -1;

	/* gather up all the shdrs. */
	shdr = calloc(ehdr->e_shnum, sizeof(*shdr));
	for (i = 0; i < ehdr->e_shnum; i++) {
		DEBUG("Parsing section %d\n", i);
		elf_shdr(&b, &shdr[i], ehdr->e_shentsize, xdr, bit64);
	}

	pelf->shdr = shdr;

	return 0;
}

static int
reloc_read(const struct buffer *in, struct parsed_elf *pelf,
           struct xdr *xdr, int bit64)
{
	struct buffer b;
	Elf64_Word i;
	Elf64_Ehdr *ehdr;

	ehdr = &pelf->ehdr;
	pelf->relocs = calloc(ehdr->e_shnum, sizeof(Elf64_Rela *));

	/* Allocate array for each section that contains relocation entries. */
	for (i = 0; i < ehdr->e_shnum; i++) {
		Elf64_Shdr *shdr;
		Elf64_Rela *rela;
		Elf64_Xword j;
		Elf64_Xword nrelocs;
		int is_rela;

		shdr = &pelf->shdr[i];

		/* Only process REL and RELA sections. */
		if (shdr->sh_type != SHT_REL && shdr->sh_type != SHT_RELA)
			continue;

		DEBUG("Checking relocation section %u\n", i);

		/* Ensure the section that relocations apply is a valid. */
		if (shdr->sh_info >= ehdr->e_shnum ||
		    shdr->sh_info == SHN_UNDEF) {
			ERROR("Relocations apply to an invalid section: %u\n",
			      shdr[i].sh_info);
			return -1;
		}

		is_rela = shdr->sh_type == SHT_RELA;

		/* Determine the number relocations in this section. */
		nrelocs = shdr->sh_size / shdr->sh_entsize;

		pelf->relocs[i] = calloc(nrelocs, sizeof(Elf64_Rela));

		buffer_splice(&b, in, shdr->sh_offset, shdr->sh_size);
		if (check_size(in, shdr->sh_offset, buffer_size(&b),
		               "relocation section")) {
			ERROR("Relocation section %u failed.\n", i);
			return -1;
		}

		rela = pelf->relocs[i];
		for (j = 0; j < nrelocs; j++) {
			if (bit64) {
				rela->r_offset = xdr->get64(&b);
				rela->r_info = xdr->get64(&b);
				if (is_rela)
					rela->r_addend = xdr->get64(&b);
			} else {
				uint32_t r_info;

				rela->r_offset = xdr->get32(&b);
				r_info = xdr->get32(&b);
				rela->r_info = ELF64_R_INFO(ELF32_R_SYM(r_info),
				                          ELF32_R_TYPE(r_info));
				if (is_rela)
					rela->r_addend = xdr->get32(&b);
			}
			rela++;
		}
	}

	return 0;
}

static int strtab_read(const struct buffer *in, struct parsed_elf *pelf)
{
	Elf64_Ehdr *ehdr;
	Elf64_Word i;

	ehdr = &pelf->ehdr;

	if (ehdr->e_shstrndx >= ehdr->e_shnum) {
		ERROR("Section header string table index out of range: %d\n",
		      ehdr->e_shstrndx);
		return -1;
	}

	/* For each section of type SHT_STRTAB create a symtab buffer. */
	pelf->strtabs = calloc(ehdr->e_shnum, sizeof(struct buffer *));

	for (i = 0; i < ehdr->e_shnum; i++) {
		struct buffer *b;
		Elf64_Shdr *shdr = &pelf->shdr[i];

		if (shdr->sh_type != SHT_STRTAB)
			continue;

		b = calloc(1, sizeof(*b));
		buffer_splice(b, in, shdr->sh_offset, shdr->sh_size);
		if (check_size(in, shdr->sh_offset, buffer_size(b), "strtab")) {
			ERROR("STRTAB section not within bounds: %d\n", i);
			free(b);
			return -1;
		}
		pelf->strtabs[i] = b;
	}

	return 0;
}

static int
symtab_read(const struct buffer *in, struct parsed_elf *pelf,
            struct xdr *xdr, int bit64)
{
	Elf64_Ehdr *ehdr;
	Elf64_Shdr *shdr;
	Elf64_Half i;
	Elf64_Xword nsyms;
	Elf64_Sym *sym;
	struct buffer b;

	ehdr = &pelf->ehdr;

	shdr = NULL;
	for (i = 0; i < ehdr->e_shnum; i++) {
		if (pelf->shdr[i].sh_type != SHT_SYMTAB)
			continue;

		if (shdr != NULL) {
			ERROR("Multiple symbol sections found. %u and %u\n",
			      (unsigned int)(shdr - pelf->shdr), i);
			return -1;
		}

		shdr = &pelf->shdr[i];
	}

	if (shdr == NULL) {
		ERROR("No symbol table found.\n");
		return -1;
	}

	buffer_splice(&b, in, shdr->sh_offset, shdr->sh_size);
	if (check_size(in, shdr->sh_offset, buffer_size(&b), "symtab"))
		return -1;

	nsyms = shdr->sh_size / shdr->sh_entsize;

	pelf->syms = calloc(nsyms, sizeof(Elf64_Sym));

	for (i = 0; i < nsyms; i++) {
		sym = &pelf->syms[i];

		if (bit64) {
			sym->st_name = xdr->get32(&b);
			sym->st_info = xdr->get8(&b);
			sym->st_other = xdr->get8(&b);
			sym->st_shndx = xdr->get16(&b);
			sym->st_value = xdr->get64(&b);
			sym->st_size = xdr->get64(&b);
		} else {
			sym->st_name = xdr->get32(&b);
			sym->st_value = xdr->get32(&b);
			sym->st_size = xdr->get32(&b);
			sym->st_info = xdr->get8(&b);
			sym->st_other = xdr->get8(&b);
			sym->st_shndx = xdr->get16(&b);
		}
	}

	return 0;
}

int parse_elf(const struct buffer *pinput, struct parsed_elf *pelf, int flags)
{
	struct xdr *xdr = &xdr_le;
	int bit64 = 0;
	struct buffer input;
	Elf64_Ehdr *ehdr;

	/* Zero out the parsed elf structure. */
	memset(pelf, 0, sizeof(*pelf));

	if (!iself(buffer_get(pinput))) {
		ERROR("The stage file is not in ELF format!\n");
		return -1;
	}

	buffer_clone(&input, pinput);
	ehdr = &pelf->ehdr;
	elf_eident(&input, ehdr);
	bit64 = ehdr->e_ident[EI_CLASS] == ELFCLASS64;
	/* Assume LE unless we are sure otherwise.
	 * We're not going to take on the task of
	 * fully validating the ELF file. That way
	 * lies madness.
	 */
	if (ehdr->e_ident[EI_DATA] == ELFDATA2MSB)
		xdr = &xdr_be;

	elf_ehdr(&input, ehdr, xdr, bit64);

	/* Relocation processing requires section header parsing. */
	if (flags & ELF_PARSE_RELOC)
		flags |= ELF_PARSE_SHDR;

	/* String table processing requires section header parsing. */
	if (flags & ELF_PARSE_STRTAB)
		flags |= ELF_PARSE_SHDR;

	/* Symbole table processing requires section header parsing. */
	if (flags & ELF_PARSE_SYMTAB)
		flags |= ELF_PARSE_SHDR;

	if ((flags & ELF_PARSE_PHDR) && phdr_read(pinput, pelf, xdr, bit64))
		goto fail;

	if ((flags & ELF_PARSE_SHDR) && shdr_read(pinput, pelf, xdr, bit64))
		goto fail;

	if ((flags & ELF_PARSE_RELOC) && reloc_read(pinput, pelf, xdr, bit64))
		goto fail;

	if ((flags & ELF_PARSE_STRTAB) && strtab_read(pinput, pelf))
		goto fail;

	if ((flags & ELF_PARSE_SYMTAB) && symtab_read(pinput, pelf, xdr, bit64))
		goto fail;

	return 0;

fail:
	parsed_elf_destroy(pelf);
	return -1;
}

void parsed_elf_destroy(struct parsed_elf *pelf)
{
	Elf64_Half i;

	free(pelf->phdr);
	free(pelf->shdr);
	if (pelf->relocs != NULL) {
		for (i = 0; i < pelf->ehdr.e_shnum; i++)
			free(pelf->relocs[i]);
	}
	free(pelf->relocs);

	if (pelf->strtabs != NULL) {
		for (i = 0; i < pelf->ehdr.e_shnum; i++)
			free(pelf->strtabs[i]);
	}
	free(pelf->strtabs);
	free(pelf->syms);
}

/* Get the headers from the buffer.
 * Return -1 in the event of an error.
 * The section headers are optional; if NULL
 * is passed in for pshdr they won't be parsed.
 * We don't (yet) make payload parsing optional
 * because we've never seen a use case.
 */
int
elf_headers(const struct buffer *pinput,
	    Elf64_Ehdr *ehdr,
	    Elf64_Phdr **pphdr,
	    Elf64_Shdr **pshdr)
{
	struct parsed_elf pelf;
	int flags;

	flags = ELF_PARSE_PHDR;

	if (pshdr != NULL)
		flags |= ELF_PARSE_SHDR;

	if (parse_elf(pinput, &pelf, flags))
		return -1;

	/* Copy out the parsed elf header. */
	memcpy(ehdr, &pelf.ehdr, sizeof(*ehdr));

	*pphdr = calloc(ehdr->e_phnum, sizeof(Elf64_Phdr));
	memcpy(*pphdr, pelf.phdr, ehdr->e_phnum * sizeof(Elf64_Phdr));

	if (pshdr != NULL) {
		*pshdr = calloc(ehdr->e_shnum, sizeof(Elf64_Shdr));
		memcpy(*pshdr, pelf.shdr, ehdr->e_shnum * sizeof(Elf64_Shdr));
	}

	parsed_elf_destroy(&pelf);

	return 0;
}

/* ELF Writing  Support
 *
 * The ELF file is written according to the following layout:
 * +------------------+
 * |    ELF Header    |
 * +------------------+
 * | Section  Headers |
 * +------------------+
 * | Program  Headers |
 * +------------------+
 * |   String table   |
 * +------------------+ <- 4KiB Aligned
 * |     Code/Data    |
 * +------------------+
 */

void elf_init_eheader(Elf64_Ehdr *ehdr, int machine, int nbits, int endian)
{
	memset(ehdr, 0, sizeof(*ehdr));
	ehdr->e_ident[EI_MAG0] = ELFMAG0;
	ehdr->e_ident[EI_MAG1] = ELFMAG1;
	ehdr->e_ident[EI_MAG2] = ELFMAG2;
	ehdr->e_ident[EI_MAG3] = ELFMAG3;
	ehdr->e_ident[EI_CLASS] = nbits;
	ehdr->e_ident[EI_DATA] = endian;
	ehdr->e_ident[EI_VERSION] = EV_CURRENT;
	ehdr->e_type = ET_EXEC;
	ehdr->e_machine = machine;
	ehdr->e_version = EV_CURRENT;
	if (nbits == ELFCLASS64) {
		ehdr->e_ehsize = sizeof(Elf64_Ehdr);
		ehdr->e_phentsize = sizeof(Elf64_Phdr);
		ehdr->e_shentsize = sizeof(Elf64_Shdr);
	} else {
		ehdr->e_ehsize = sizeof(Elf32_Ehdr);
		ehdr->e_phentsize = sizeof(Elf32_Phdr);
		ehdr->e_shentsize = sizeof(Elf32_Shdr);
	}
}

/* Arbitray maximum number of sections. */
#define MAX_SECTIONS 16
struct elf_writer_section {
	Elf64_Shdr shdr;
	struct buffer content;
	const char *name;
};

struct elf_writer_string_table {
	size_t next_offset;
	size_t max_size;
	char *buffer;
};

struct elf_writer_sym_table {
	size_t max_entries;
	size_t num_entries;
	Elf64_Sym *syms;
};

#define MAX_REL_NAME 32
struct elf_writer_rel {
	size_t num_entries;
	size_t max_entries;
	Elf64_Rel *rels;
	struct elf_writer_section *sec;
	char name[MAX_REL_NAME];
};

struct elf_writer
{
	Elf64_Ehdr ehdr;
	struct xdr *xdr;
	size_t num_secs;
	struct elf_writer_section sections[MAX_SECTIONS];
	struct elf_writer_rel rel_sections[MAX_SECTIONS];
	Elf64_Phdr *phdrs;
	struct elf_writer_section *shstrtab_sec;
	struct elf_writer_section *strtab_sec;
	struct elf_writer_section *symtab_sec;
	struct elf_writer_string_table strtab;
	struct elf_writer_sym_table symtab;
	int bit64;
};

static size_t section_index(struct elf_writer *ew,
					struct elf_writer_section *sec)
{
	return sec - &ew->sections[0];
}

static struct elf_writer_section *last_section(struct elf_writer *ew)
{
	return &ew->sections[ew->num_secs - 1];
}

static void strtab_init(struct elf_writer *ew, size_t size)
{
	struct buffer b;
	Elf64_Shdr shdr;

	/* Start adding strings after the initial NUL entry. */
	ew->strtab.next_offset = 1;
	ew->strtab.max_size = size;
	ew->strtab.buffer = calloc(1, ew->strtab.max_size);

	buffer_init(&b, NULL, ew->strtab.buffer, ew->strtab.max_size);
	memset(&shdr, 0, sizeof(shdr));
	shdr.sh_type = SHT_STRTAB;
	shdr.sh_addralign = 1;
	shdr.sh_size = ew->strtab.max_size;
	elf_writer_add_section(ew, &shdr, &b, ".strtab");
	ew->strtab_sec = last_section(ew);
}

static void symtab_init(struct elf_writer *ew, size_t max_entries)
{
	struct buffer b;
	Elf64_Shdr shdr;

	memset(&shdr, 0, sizeof(shdr));
	shdr.sh_type = SHT_SYMTAB;

	if (ew->bit64) {
		shdr.sh_entsize = sizeof(Elf64_Sym);
		shdr.sh_addralign = sizeof(Elf64_Addr);
	} else {
		shdr.sh_entsize = sizeof(Elf32_Sym);
		shdr.sh_addralign = sizeof(Elf32_Addr);
	}

	shdr.sh_size = shdr.sh_entsize * max_entries;

	ew->symtab.syms = calloc(max_entries, sizeof(Elf64_Sym));
	ew->symtab.num_entries = 1;
	ew->symtab.max_entries = max_entries;

	buffer_init(&b, NULL, ew->symtab.syms, shdr.sh_size);

	elf_writer_add_section(ew, &shdr, &b, ".symtab");
	ew->symtab_sec = last_section(ew);
}

struct elf_writer *elf_writer_init(const Elf64_Ehdr *ehdr)
{
	struct elf_writer *ew;
	Elf64_Shdr shdr;
	struct buffer empty_buffer;

	if (!iself(ehdr))
		return NULL;

	ew = calloc(1, sizeof(*ew));

	memcpy(&ew->ehdr, ehdr, sizeof(ew->ehdr));

	ew->bit64 = ew->ehdr.e_ident[EI_CLASS] == ELFCLASS64;

	/* Set the endinan ops. */
	if (ew->ehdr.e_ident[EI_DATA] == ELFDATA2MSB)
		ew->xdr = &xdr_be;
	else
		ew->xdr = &xdr_le;

	/* Reset count and offsets */
	ew->ehdr.e_phoff = 0;
	ew->ehdr.e_shoff = 0;
	ew->ehdr.e_shnum = 0;
	ew->ehdr.e_phnum = 0;

	memset(&empty_buffer, 0, sizeof(empty_buffer));
	memset(&shdr, 0, sizeof(shdr));

	/* Add SHT_NULL section header. */
	shdr.sh_type = SHT_NULL;
	elf_writer_add_section(ew, &shdr, &empty_buffer, NULL);

	/* Add section header string table and maintain reference to it.  */
	shdr.sh_type = SHT_STRTAB;
	elf_writer_add_section(ew, &shdr, &empty_buffer, ".shstrtab");
	ew->shstrtab_sec = last_section(ew);
	ew->ehdr.e_shstrndx = section_index(ew, ew->shstrtab_sec);

	/* Add a small string table and symbol table. */
	strtab_init(ew, 4096);
	symtab_init(ew, 100);

	return ew;
}

/*
 * Clean up any internal state represented by ew. Aftewards the elf_writer
 * is invalid.
 */
void elf_writer_destroy(struct elf_writer *ew)
{
	int i;
	if (ew->phdrs != NULL)
		free(ew->phdrs);
	free(ew->strtab.buffer);
	free(ew->symtab.syms);
	for (i = 0; i < MAX_SECTIONS; i++)
		free(ew->rel_sections[i].rels);
	free(ew);
}

/*
 * Add a section to the ELF file. Section type, flags, and memsize are
 * maintained from the passed in Elf64_Shdr. The buffer represents the
 * content of the section while the name is the name of section itself.
 * Returns < 0 on error, 0 on success.
 */
int elf_writer_add_section(struct elf_writer *ew, const Elf64_Shdr *shdr,
                           struct buffer *contents, const char *name)
{
	struct elf_writer_section *newsh;

	if (ew->num_secs == MAX_SECTIONS)
		return -1;

	newsh = &ew->sections[ew->num_secs];
	ew->num_secs++;

	memcpy(&newsh->shdr, shdr, sizeof(newsh->shdr));
	newsh->shdr.sh_offset = 0;

	newsh->name = name;
	if (contents != NULL)
		buffer_clone(&newsh->content, contents);

	return 0;
}

static void ehdr_write(struct elf_writer *ew, struct buffer *m)
{
	int i;

	for (i = 0; i < EI_NIDENT; i++)
		ew->xdr->put8(m, ew->ehdr.e_ident[i]);
	ew->xdr->put16(m, ew->ehdr.e_type);
	ew->xdr->put16(m, ew->ehdr.e_machine);
	ew->xdr->put32(m, ew->ehdr.e_version);
	if (ew->bit64) {
		ew->xdr->put64(m, ew->ehdr.e_entry);
		ew->xdr->put64(m, ew->ehdr.e_phoff);
		ew->xdr->put64(m, ew->ehdr.e_shoff);
	} else {
		ew->xdr->put32(m, ew->ehdr.e_entry);
		ew->xdr->put32(m, ew->ehdr.e_phoff);
		ew->xdr->put32(m, ew->ehdr.e_shoff);
	}
	ew->xdr->put32(m, ew->ehdr.e_flags);
	ew->xdr->put16(m, ew->ehdr.e_ehsize);
	ew->xdr->put16(m, ew->ehdr.e_phentsize);
	ew->xdr->put16(m, ew->ehdr.e_phnum);
	ew->xdr->put16(m, ew->ehdr.e_shentsize);
	ew->xdr->put16(m, ew->ehdr.e_shnum);
	ew->xdr->put16(m, ew->ehdr.e_shstrndx);
}

static void shdr_write(struct elf_writer *ew, size_t n, struct buffer *m)
{
	struct xdr *xdr = ew->xdr;
	int bit64 = ew->bit64;
	struct elf_writer_section *sec = &ew->sections[n];
	Elf64_Shdr *shdr = &sec->shdr;

	xdr->put32(m, shdr->sh_name);
	xdr->put32(m, shdr->sh_type);
	if (bit64) {
		xdr->put64(m, shdr->sh_flags);
		xdr->put64(m, shdr->sh_addr);
		xdr->put64(m, shdr->sh_offset);
		xdr->put64(m, shdr->sh_size);
		xdr->put32(m, shdr->sh_link);
		xdr->put32(m, shdr->sh_info);
		xdr->put64(m, shdr->sh_addralign);
		xdr->put64(m, shdr->sh_entsize);
	} else {
		xdr->put32(m, shdr->sh_flags);
		xdr->put32(m, shdr->sh_addr);
		xdr->put32(m, shdr->sh_offset);
		xdr->put32(m, shdr->sh_size);
		xdr->put32(m, shdr->sh_link);
		xdr->put32(m, shdr->sh_info);
		xdr->put32(m, shdr->sh_addralign);
		xdr->put32(m, shdr->sh_entsize);
	}
}

static void
phdr_write(struct elf_writer *ew, struct buffer *m, Elf64_Phdr *phdr)
{
	if (ew->bit64) {
		ew->xdr->put32(m, phdr->p_type);
		ew->xdr->put32(m, phdr->p_flags);
		ew->xdr->put64(m, phdr->p_offset);
		ew->xdr->put64(m, phdr->p_vaddr);
		ew->xdr->put64(m, phdr->p_paddr);
		ew->xdr->put64(m, phdr->p_filesz);
		ew->xdr->put64(m, phdr->p_memsz);
		ew->xdr->put64(m, phdr->p_align);
	} else {
		ew->xdr->put32(m, phdr->p_type);
		ew->xdr->put32(m, phdr->p_offset);
		ew->xdr->put32(m, phdr->p_vaddr);
		ew->xdr->put32(m, phdr->p_paddr);
		ew->xdr->put32(m, phdr->p_filesz);
		ew->xdr->put32(m, phdr->p_memsz);
		ew->xdr->put32(m, phdr->p_flags);
		ew->xdr->put32(m, phdr->p_align);
	}

}

static int section_consecutive(struct elf_writer *ew, Elf64_Half secidx)
{
	Elf64_Half i;
	struct elf_writer_section *prev_alloc = NULL;

	if (secidx == 0)
		return 0;

	for (i = 0; i < secidx; i++) {
		if (ew->sections[i].shdr.sh_flags & SHF_ALLOC)
			prev_alloc = &ew->sections[i];
	}

	if (prev_alloc == NULL)
		return 0;

	if (prev_alloc->shdr.sh_addr + prev_alloc->shdr.sh_size ==
	    ew->sections[secidx].shdr.sh_addr)
		return 1;

	return 0;
}

static void write_phdrs(struct elf_writer *ew, struct buffer *phdrs)
{
	Elf64_Half i;
	Elf64_Phdr phdr;
	size_t num_written = 0;

	for (i = 0; i < ew->num_secs; i++) {
		struct elf_writer_section *sec = &ew->sections[i];

		if (!(sec->shdr.sh_flags & SHF_ALLOC))
			continue;

		if (!section_consecutive(ew, i)) {
			/* Write out previously set phdr. */
			if (num_written != 0) {
				phdr_write(ew, phdrs, &phdr);
				num_written++;
			}
			phdr.p_type = PT_LOAD;
			phdr.p_offset = sec->shdr.sh_offset;
			phdr.p_vaddr = sec->shdr.sh_addr;
			phdr.p_paddr = sec->shdr.sh_addr;
			phdr.p_filesz = buffer_size(&sec->content);
			phdr.p_memsz = sec->shdr.sh_size;
			phdr.p_flags = 0;
			if (sec->shdr.sh_flags & SHF_EXECINSTR)
				phdr.p_flags |= PF_X | PF_R;
			if (sec->shdr.sh_flags & SHF_WRITE)
				phdr.p_flags |= PF_W;
			phdr.p_align = sec->shdr.sh_addralign;
		} else {
			/* Accumulate file size and memsize. The assumption
			 * is that each section is either NOBITS or full
			 * (sh_size == file size). This is standard in that
			 * an ELF section doesn't have a file size component. */
			if (sec->shdr.sh_flags & SHF_EXECINSTR)
				phdr.p_flags |= PF_X | PF_R;
			if (sec->shdr.sh_flags & SHF_WRITE)
				phdr.p_flags |= PF_W;
			phdr.p_filesz += buffer_size(&sec->content);
			phdr.p_memsz += sec->shdr.sh_size;
		}
	}

	/* Write out the last phdr. */
	if (num_written != ew->ehdr.e_phnum)
		phdr_write(ew, phdrs, &phdr);
}

static void fixup_symbol_table(struct elf_writer *ew)
{
	struct elf_writer_section *sec = ew->symtab_sec;

	/* If there is only the NULL section, mark section as inactive. */
	if (ew->symtab.num_entries == 1) {
		sec->shdr.sh_type = SHT_NULL;
		sec->shdr.sh_size = 0;
	} else {
		size_t i;
		struct buffer wr;

		buffer_clone(&wr, &sec->content);
		/* To appease xdr. */
		buffer_set_size(&wr, 0);
		for (i = 0; i < ew->symtab.num_entries; i++) {
			/* Create local copy as were over-writing backing
			 * store of the symbol. */
			Elf64_Sym sym = ew->symtab.syms[i];
			if (ew->bit64) {
				ew->xdr->put32(&wr, sym.st_name);
				ew->xdr->put8(&wr, sym.st_info);
				ew->xdr->put8(&wr, sym.st_other);
				ew->xdr->put16(&wr, sym.st_shndx);
				ew->xdr->put64(&wr, sym.st_value);
				ew->xdr->put64(&wr, sym.st_size);
			} else {
				ew->xdr->put32(&wr, sym.st_name);
				ew->xdr->put32(&wr, sym.st_value);
				ew->xdr->put32(&wr, sym.st_size);
				ew->xdr->put8(&wr, sym.st_info);
				ew->xdr->put8(&wr, sym.st_other);
				ew->xdr->put16(&wr, sym.st_shndx);
			}
		}

		/* Update section size. */
		sec->shdr.sh_size = sec->shdr.sh_entsize;
		sec->shdr.sh_size *= ew->symtab.num_entries;

		/* Fix up sh_link to point to string table. */
		sec->shdr.sh_link = section_index(ew, ew->strtab_sec);
		/* sh_info is supposed to be 1 greater than symbol table
		 * index of last local binding. Just use max symbols. */
		sec->shdr.sh_info = ew->symtab.num_entries;
	}

	buffer_set_size(&sec->content, sec->shdr.sh_size);
}

static void fixup_relocations(struct elf_writer *ew)
{
	int i;
	Elf64_Xword type;

	switch (ew->ehdr.e_machine) {
	case EM_386:
		type = R_386_32;
		break;
	case EM_ARM:
		type = R_ARM_ABS32;
		break;
	case EM_AARCH64:
		type = R_AARCH64_ABS64;
		break;
	case EM_MIPS:
		type = R_MIPS_32;
		break;
	case EM_RISCV:
		type = R_RISCV_32;
		break;
	case EM_PPC64:
		type = R_PPC64_ADDR32;
		break;
	default:
		ERROR("Unable to handle relocations for e_machine %x\n",
			ew->ehdr.e_machine);
		return;
	}

	for (i = 0; i < MAX_SECTIONS; i++) {
		struct elf_writer_rel *rel_sec = &ew->rel_sections[i];
		struct elf_writer_section *sec = rel_sec->sec;
		struct buffer writer;
		size_t j;

		if (sec == NULL)
			continue;

		/* Update section header size as well as content size. */
		buffer_init(&sec->content, sec->content.name, rel_sec->rels,
				rel_sec->num_entries * sec->shdr.sh_entsize);
		sec->shdr.sh_size = buffer_size(&sec->content);
		buffer_clone(&writer, &sec->content);
		/* To make xdr happy. */
		buffer_set_size(&writer, 0);

		for (j = 0; j < ew->rel_sections[i].num_entries; j++) {
			/* Make copy as we're overwriting backing store. */
			Elf64_Rel rel = rel_sec->rels[j];
			rel.r_info = ELF64_R_INFO(ELF64_R_SYM(rel.r_info),
						  ELF64_R_TYPE(type));

			if (ew->bit64) {
				ew->xdr->put64(&writer, rel.r_offset);
				ew->xdr->put64(&writer, rel.r_info);
			} else {
				Elf32_Rel rel32;
				rel32.r_offset = rel.r_offset;
				rel32.r_info =
					ELF32_R_INFO(ELF64_R_SYM(rel.r_info),
						     ELF64_R_TYPE(rel.r_info));
				ew->xdr->put32(&writer, rel32.r_offset);
				ew->xdr->put32(&writer, rel32.r_info);
			}
		}
	}
}

/*
 * Serialize the ELF file to the output buffer. Return < 0 on error,
 * 0 on success.
 */
int elf_writer_serialize(struct elf_writer *ew, struct buffer *out)
{
	Elf64_Half i;
	Elf64_Xword metadata_size;
	Elf64_Xword program_size;
	Elf64_Off shstroffset;
	size_t shstrlen;
	struct buffer metadata;
	struct buffer phdrs;
	struct buffer data;
	struct buffer *strtab;

	INFO("Writing %zu sections.\n", ew->num_secs);

	/* Perform any necessary work for special sections. */
	fixup_symbol_table(ew);
	fixup_relocations(ew);

	/* Determine size of sections to be written. */
	program_size = 0;
	/* Start with 1 byte for first byte of section header string table. */
	shstrlen = 1;
	for (i = 0; i < ew->num_secs; i++) {
		struct elf_writer_section *sec = &ew->sections[i];

		if (sec->shdr.sh_flags & SHF_ALLOC) {
			if (!section_consecutive(ew, i))
				ew->ehdr.e_phnum++;
		}

		program_size += buffer_size(&sec->content);

		/* Keep track of the length sections' names. */
		if (sec->name != NULL) {
			sec->shdr.sh_name = shstrlen;
			shstrlen += strlen(sec->name) + 1;
		}
	}
	ew->ehdr.e_shnum = ew->num_secs;
	metadata_size = 0;
	metadata_size += ew->ehdr.e_ehsize;
	metadata_size += ew->ehdr.e_shnum * ew->ehdr.e_shentsize;
	metadata_size += ew->ehdr.e_phnum * ew->ehdr.e_phentsize;
	shstroffset = metadata_size;
	/* Align up section header string size and metadata size to 4KiB */
	metadata_size = ALIGN(metadata_size + shstrlen, 4096);

	if (buffer_create(out, metadata_size + program_size, "elfout")) {
		ERROR("Could not create output buffer for ELF.\n");
		return -1;
	}

	INFO("Created %zu output buffer for ELF file.\n", buffer_size(out));

	/*
	 * Write out ELF header. Section headers come right after ELF header
	 * followed by the program headers. Buffers need to be created first
	 * to do the writing.
	 */
	ew->ehdr.e_shoff = ew->ehdr.e_ehsize;
	ew->ehdr.e_phoff = ew->ehdr.e_shoff +
	                   ew->ehdr.e_shnum * ew->ehdr.e_shentsize;

	buffer_splice(&metadata, out, 0, metadata_size);
	buffer_splice(&phdrs, out, ew->ehdr.e_phoff,
	              ew->ehdr.e_phnum * ew->ehdr.e_phentsize);
	buffer_splice(&data, out, metadata_size, program_size);
	/* Set up the section header string table contents. */
	strtab = &ew->shstrtab_sec->content;
	buffer_splice(strtab, out, shstroffset, shstrlen);
	ew->shstrtab_sec->shdr.sh_size = shstrlen;

	/* Reset current locations. */
	buffer_set_size(&metadata, 0);
	buffer_set_size(&data, 0);
	buffer_set_size(&phdrs, 0);
	buffer_set_size(strtab, 0);

	/* ELF Header */
	ehdr_write(ew, &metadata);

	/* Write out section headers, section strings, section content, and
	 * program headers. */
	ew->xdr->put8(strtab, 0);
	for (i = 0; i < ew->num_secs; i++) {
		struct elf_writer_section *sec = &ew->sections[i];

		/* Update section offsets. Be sure to not update SHN_UNDEF. */
		if (sec == ew->shstrtab_sec)
			sec->shdr.sh_offset = shstroffset;
		else if (i != SHN_UNDEF)
			sec->shdr.sh_offset = buffer_size(&data) +
			                      metadata_size;

		shdr_write(ew, i, &metadata);

		/* Add section name to string table. */
		if (sec->name != NULL)
			bputs(strtab, sec->name, strlen(sec->name) + 1);

		/* Output section data for all sections but SHN_UNDEF and
		 * section header string table. */
		if (i != SHN_UNDEF && sec != ew->shstrtab_sec)
			bputs(&data, buffer_get(&sec->content),
			      buffer_size(&sec->content));
	}

	write_phdrs(ew, &phdrs);

	return 0;
}

/* Add a string to the string table returning index on success, < 0 on error. */
static int elf_writer_add_string(struct elf_writer *ew, const char *new)
{
	size_t current_offset;
	size_t new_len;

	for (current_offset = 0; current_offset < ew->strtab.next_offset; ) {
		const char *str = ew->strtab.buffer + current_offset;
		size_t len = strlen(str) + 1;

		if (!strcmp(str, new))
			return current_offset;
		current_offset += len;
	}

	new_len = strlen(new) + 1;

	if (current_offset + new_len > ew->strtab.max_size) {
		ERROR("No space for string in .strtab.\n");
		return -1;
	}

	memcpy(ew->strtab.buffer + current_offset, new, new_len);
	ew->strtab.next_offset = current_offset + new_len;

	return current_offset;
}

static int elf_writer_section_index(struct elf_writer *ew, const char *name)
{
	size_t i;

	for (i = 0; i < ew->num_secs; i++) {
		if (ew->sections[i].name == NULL)
			continue;
		if (!strcmp(ew->sections[i].name, name))
			return i;
	}

	ERROR("ELF Section not found: %s\n", name);

	return -1;
}

int elf_writer_add_symbol(struct elf_writer *ew, const char *name,
				const char *section_name,
				Elf64_Addr value, Elf64_Word size,
				int binding, int type)
{
	int i;
	Elf64_Sym sym = {
		.st_value = value,
		.st_size = size,
		.st_info = ELF64_ST_INFO(binding, type),
	};

	if (ew->symtab.max_entries == ew->symtab.num_entries) {
		ERROR("No more symbol entries left.\n");
		return -1;
	}

	i = elf_writer_add_string(ew, name);
	if (i < 0)
		return -1;
	sym.st_name = i;

	i = elf_writer_section_index(ew, section_name);
	if (i < 0)
		return -1;
	sym.st_shndx = i;

	ew->symtab.syms[ew->symtab.num_entries++] = sym;

	return 0;
}

static int elf_sym_index(struct elf_writer *ew, const char *sym)
{
	int j;
	size_t i;
	Elf64_Word st_name;

	/* Determine index of symbol in the string table. */
	j = elf_writer_add_string(ew, sym);
	if (j < 0)
		return -1;

	st_name = j;

	for (i = 0; i < ew->symtab.num_entries; i++)
		if (ew->symtab.syms[i].st_name == st_name)
			return i;

	return -1;
}

static struct elf_writer_rel *rel_section(struct elf_writer *ew,
						const Elf64_Rel *r)
{
	Elf64_Sym *sym;
	struct elf_writer_rel *rel;
	Elf64_Shdr shdr;
	struct buffer b;

	sym = &ew->symtab.syms[ELF64_R_SYM(r->r_info)];

	/* Determine if section has been initialized yet. */
	rel = &ew->rel_sections[sym->st_shndx];
	if (rel->sec != NULL)
		return rel;

	memset(&shdr, 0, sizeof(shdr));
	shdr.sh_type = SHT_REL;
	shdr.sh_link = section_index(ew, ew->symtab_sec);
	shdr.sh_info = sym->st_shndx;

	if (ew->bit64) {
		shdr.sh_addralign = sizeof(Elf64_Addr);
		shdr.sh_entsize = sizeof(Elf64_Rel);
	} else {
		shdr.sh_addralign = sizeof(Elf32_Addr);
		shdr.sh_entsize = sizeof(Elf32_Rel);
	}

	if ((strlen(".rel") + strlen(ew->sections[sym->st_shndx].name) + 1) >
	    MAX_REL_NAME) {
		ERROR("Rel Section name won't fit\n");
		return NULL;
	}

	strcat(rel->name, ".rel");
	strcat(rel->name, ew->sections[sym->st_shndx].name);
	buffer_init(&b, rel->name, NULL, 0);

	elf_writer_add_section(ew, &shdr, &b, rel->name);
	rel->sec = last_section(ew);

	return rel;
}

static int add_rel(struct elf_writer_rel *rel_sec, const Elf64_Rel *rel)
{
	if (rel_sec->num_entries == rel_sec->max_entries) {
		size_t num = rel_sec->max_entries * 2;
		Elf64_Rel *old_rels;

		if (num == 0)
			num = 128;

		old_rels = rel_sec->rels;
		rel_sec->rels = calloc(num, sizeof(Elf64_Rel));

		memcpy(rel_sec->rels, old_rels,
			rel_sec->num_entries * sizeof(Elf64_Rel));
		free(old_rels);

		rel_sec->max_entries = num;
	}

	rel_sec->rels[rel_sec->num_entries] = *rel;
	rel_sec->num_entries++;

	return 0;
}

int elf_writer_add_rel(struct elf_writer *ew, const char *sym, Elf64_Addr addr)
{
	Elf64_Rel rel;
	Elf64_Xword sym_info;
	int sym_index;
	struct elf_writer_rel *rel_sec;

	sym_index = elf_sym_index(ew, sym);

	if (sym_index < 0) {
		ERROR("Unable to locate symbol: %s\n", sym);
		return -1;
	}

	sym_info = sym_index;

	/* The relocation type will get fixed prior to serialization. */
	rel.r_offset = addr;
	rel.r_info = ELF64_R_INFO(sym_info, 0);

	rel_sec = rel_section(ew, &rel);

	if (rel_sec == NULL)
		return -1;

	return add_rel(rel_sec, &rel);
}
