/*
 * Copyright (C) 2009 Michael Brown <mbrown@fensystems.co.uk>.
 *
 * 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; either version 2 of the
 * License, or any later version.
 *
 * 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.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 * 02110-1301, USA.
 */

#define FILE_LICENCE(...) extern void __file_licence ( void )
#include <stdint.h>
#include <stddef.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <errno.h>
#include <assert.h>
#include <getopt.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <fcntl.h>
#include <elf.h>
#include <libgen.h>

#define EFI_HOSTONLY
#include <ipxe/efi/Uefi.h>
#include <ipxe/efi/IndustryStandard/PeImage.h>

#define eprintf(...) fprintf ( stderr, __VA_ARGS__ )

#undef ELF_R_TYPE
#undef ELF_R_SYM

#ifdef EFI_TARGET32

#define EFI_IMAGE_NT_HEADERS		EFI_IMAGE_NT_HEADERS32
#define EFI_IMAGE_NT_OPTIONAL_HDR_MAGIC	EFI_IMAGE_NT_OPTIONAL_HDR32_MAGIC
#define EFI_IMAGE_FILE_MACHINE		EFI_IMAGE_FILE_32BIT_MACHINE
#define ELFCLASS   ELFCLASS32
#define Elf_Ehdr   Elf32_Ehdr
#define Elf_Shdr   Elf32_Shdr
#define Elf_Sym    Elf32_Sym
#define Elf_Addr   Elf32_Addr
#define Elf_Rel    Elf32_Rel
#define Elf_Rela   Elf32_Rela
#define ELF_R_TYPE ELF32_R_TYPE
#define ELF_R_SYM  ELF32_R_SYM

#elif defined(EFI_TARGET64)

#define EFI_IMAGE_NT_HEADERS		EFI_IMAGE_NT_HEADERS64
#define EFI_IMAGE_NT_OPTIONAL_HDR_MAGIC	EFI_IMAGE_NT_OPTIONAL_HDR64_MAGIC
#define EFI_IMAGE_FILE_MACHINE		0
#define ELFCLASS   ELFCLASS64
#define Elf_Ehdr   Elf64_Ehdr
#define Elf_Shdr   Elf64_Shdr
#define Elf_Sym    Elf64_Sym
#define Elf_Addr   Elf64_Addr
#define Elf_Rel    Elf64_Rel
#define Elf_Rela   Elf64_Rela
#define ELF_R_TYPE ELF64_R_TYPE
#define ELF_R_SYM  ELF64_R_SYM

#endif

#define ELF_MREL( mach, type ) ( (mach) | ( (type) << 16 ) )

/* Provide constants missing on some platforms */
#ifndef EM_AARCH64
#define EM_AARCH64 183
#endif
#ifndef R_AARCH64_NONE
#define R_AARCH64_NONE 0
#endif
#ifndef R_AARCH64_NULL
#define R_AARCH64_NULL 256
#endif
#ifndef R_AARCH64_ABS64
#define R_AARCH64_ABS64 257
#endif
#ifndef R_AARCH64_CALL26
#define R_AARCH64_CALL26 283
#endif
#ifndef R_AARCH64_JUMP26
#define R_AARCH64_JUMP26 282
#endif
#ifndef R_AARCH64_ADR_PREL_LO21
#define R_AARCH64_ADR_PREL_LO21 274
#endif
#ifndef R_AARCH64_ADR_PREL_PG_HI21
#define R_AARCH64_ADR_PREL_PG_HI21 275
#endif
#ifndef R_AARCH64_ADD_ABS_LO12_NC
#define R_AARCH64_ADD_ABS_LO12_NC 277
#endif
#ifndef R_AARCH64_LDST8_ABS_LO12_NC
#define R_AARCH64_LDST8_ABS_LO12_NC 278
#endif
#ifndef R_AARCH64_LDST16_ABS_LO12_NC
#define R_AARCH64_LDST16_ABS_LO12_NC 284
#endif
#ifndef R_AARCH64_LDST32_ABS_LO12_NC
#define R_AARCH64_LDST32_ABS_LO12_NC 285
#endif
#ifndef R_AARCH64_LDST64_ABS_LO12_NC
#define R_AARCH64_LDST64_ABS_LO12_NC 286
#endif
#ifndef R_ARM_CALL
#define R_ARM_CALL 28
#endif
#ifndef R_ARM_THM_JUMP24
#define R_ARM_THM_JUMP24 30
#endif
#ifndef R_ARM_V4BX
#define R_ARM_V4BX 40
#endif

/**
 * Alignment of raw data of sections in the image file
 *
 * Some versions of signtool.exe will spuriously complain if this
 * value is less than 512.
 */
#define EFI_FILE_ALIGN  0x200

/**
 * Alignment of sections when loaded into memory
 *
 * This must equal the architecture page size, in order to allow for
 * the possibility of the firmware using page-level protection to
 * enforce section attributes at runtime.
 */
#define EFI_IMAGE_ALIGN 0x1000

struct elf_file {
	void *data;
	size_t len;
	const Elf_Ehdr *ehdr;
};

struct pe_section {
	struct pe_section *next;
	EFI_IMAGE_SECTION_HEADER hdr;
	void ( * fixup ) ( struct pe_section *section );
	uint8_t contents[0];
};

struct pe_relocs {
	struct pe_relocs *next;
	unsigned long start_rva;
	unsigned int used_relocs;
	unsigned int total_relocs;
	uint16_t *relocs;
};

struct pe_header {
	EFI_IMAGE_DOS_HEADER dos;
	uint8_t padding[128];
	EFI_IMAGE_NT_HEADERS nt;
};

static struct pe_header efi_pe_header = {
	.dos = {
		.e_magic = EFI_IMAGE_DOS_SIGNATURE,
		.e_lfanew = offsetof ( typeof ( efi_pe_header ), nt ),
	},
	.nt = {
		.Signature = EFI_IMAGE_NT_SIGNATURE,
		.FileHeader = {
			.TimeDateStamp = 0x10d1a884,
			.SizeOfOptionalHeader =
				sizeof ( efi_pe_header.nt.OptionalHeader ),
			.Characteristics = ( EFI_IMAGE_FILE_DLL |
					     EFI_IMAGE_FILE_MACHINE |
					     EFI_IMAGE_FILE_EXECUTABLE_IMAGE ),
		},
		.OptionalHeader = {
			.Magic = EFI_IMAGE_NT_OPTIONAL_HDR_MAGIC,
			.MajorLinkerVersion = 42,
			.MinorLinkerVersion = 42,
			.SectionAlignment = EFI_IMAGE_ALIGN,
			.FileAlignment = EFI_FILE_ALIGN,
			.SizeOfImage = EFI_IMAGE_ALIGN,
			.SizeOfHeaders = sizeof ( efi_pe_header ),
			.NumberOfRvaAndSizes =
				EFI_IMAGE_NUMBER_OF_DIRECTORY_ENTRIES,
		},
	},
};

/** Command-line options */
struct options {
	unsigned int subsystem;
};

/**
 * Allocate memory
 *
 * @v len		Length of memory to allocate
 * @ret ptr		Pointer to allocated memory
 */
static void * xmalloc ( size_t len ) {
	void *ptr;

	ptr = malloc ( len );
	if ( ! ptr ) {
		eprintf ( "Could not allocate %zd bytes\n", len );
		exit ( 1 );
	}

	return ptr;
}

/**
 * Align section within PE file
 *
 * @v offset		Unaligned offset
 * @ret aligned_offset	Aligned offset
 */
static unsigned long efi_file_align ( unsigned long offset ) {
	return ( ( offset + EFI_FILE_ALIGN - 1 ) & ~( EFI_FILE_ALIGN - 1 ) );
}

/**
 * Align section within PE image
 *
 * @v offset		Unaligned offset
 * @ret aligned_offset	Aligned offset
 */
static unsigned long efi_image_align ( unsigned long offset ) {
	return ( ( offset + EFI_IMAGE_ALIGN - 1 ) & ~( EFI_IMAGE_ALIGN - 1 ) );
}

/**
 * Generate entry in PE relocation table
 *
 * @v pe_reltab		PE relocation table
 * @v rva		RVA
 * @v size		Size of relocation entry
 */
static void generate_pe_reloc ( struct pe_relocs **pe_reltab,
				unsigned long rva, size_t size ) {
	unsigned long start_rva;
	uint16_t reloc;
	struct pe_relocs *pe_rel;
	uint16_t *relocs;

	/* Construct */
	start_rva = ( rva & ~0xfff );
	reloc = ( rva & 0xfff );
	switch ( size ) {
	case 8:
		reloc |= 0xa000;
		break;
	case 4:
		reloc |= 0x3000;
		break;
	case 2:
		reloc |= 0x2000;
		break;
	default:
		eprintf ( "Unsupported relocation size %zd\n", size );
		exit ( 1 );
	}

	/* Locate or create PE relocation table */
	for ( pe_rel = *pe_reltab ; pe_rel ; pe_rel = pe_rel->next ) {
		if ( pe_rel->start_rva == start_rva )
			break;
	}
	if ( ! pe_rel ) {
		pe_rel = xmalloc ( sizeof ( *pe_rel ) );
		memset ( pe_rel, 0, sizeof ( *pe_rel ) );
		pe_rel->next = *pe_reltab;
		*pe_reltab = pe_rel;
		pe_rel->start_rva = start_rva;
	}

	/* Expand relocation list if necessary */
	if ( pe_rel->used_relocs < pe_rel->total_relocs ) {
		relocs = pe_rel->relocs;
	} else {
		pe_rel->total_relocs = ( pe_rel->total_relocs ?
					 ( pe_rel->total_relocs * 2 ) : 256 );
		relocs = xmalloc ( pe_rel->total_relocs *
				   sizeof ( pe_rel->relocs[0] ) );
		memset ( relocs, 0,
			 pe_rel->total_relocs * sizeof ( pe_rel->relocs[0] ) );
		memcpy ( relocs, pe_rel->relocs,
			 pe_rel->used_relocs * sizeof ( pe_rel->relocs[0] ) );
		free ( pe_rel->relocs );
		pe_rel->relocs = relocs;
	}

	/* Store relocation */
	pe_rel->relocs[ pe_rel->used_relocs++ ] = reloc;
}

/**
 * Calculate size of binary PE relocation table
 *
 * @v pe_reltab		PE relocation table
 * @v buffer		Buffer to contain binary table, or NULL
 * @ret size		Size of binary table
 */
static size_t output_pe_reltab ( struct pe_relocs *pe_reltab,
				 void *buffer ) {
	struct pe_relocs *pe_rel;
	unsigned int num_relocs;
	size_t size;
	size_t total_size = 0;

	for ( pe_rel = pe_reltab ; pe_rel ; pe_rel = pe_rel->next ) {
		num_relocs = ( ( pe_rel->used_relocs + 1 ) & ~1 );
		size = ( sizeof ( uint32_t ) /* VirtualAddress */ +
			 sizeof ( uint32_t ) /* SizeOfBlock */ +
			 ( num_relocs * sizeof ( uint16_t ) ) );
		if ( buffer ) {
			*( (uint32_t *) ( buffer + total_size + 0 ) )
				= pe_rel->start_rva;
			*( (uint32_t *) ( buffer + total_size + 4 ) ) = size;
			memcpy ( ( buffer + total_size + 8 ), pe_rel->relocs,
				 ( num_relocs * sizeof ( uint16_t ) ) );
		}
		total_size += size;
	}

	return total_size;
}

/**
 * Read input ELF file
 *
 * @v name		File name
 * @v elf		ELF file
 */
static void read_elf_file ( const char *name, struct elf_file *elf ) {
	static const unsigned char ident[] = {
		ELFMAG0, ELFMAG1, ELFMAG2, ELFMAG3, ELFCLASS, ELFDATA2LSB
	};
	struct stat stat;
	const Elf_Ehdr *ehdr;
	const Elf_Shdr *shdr;
	void *data;
	size_t offset;
	unsigned int i;
	int fd;

	/* Open file */
	fd = open ( name, O_RDONLY );
	if ( fd < 0 ) {
		eprintf ( "Could not open %s: %s\n", name, strerror ( errno ) );
		exit ( 1 );
	}

	/* Get file size */
	if ( fstat ( fd, &stat ) < 0 ) {
		eprintf ( "Could not get size of %s: %s\n",
			  name, strerror ( errno ) );
		exit ( 1 );
	}
	elf->len = stat.st_size;

	/* Map file */
	data = mmap ( NULL, elf->len, PROT_READ, MAP_SHARED, fd, 0 );
	if ( data == MAP_FAILED ) {
		eprintf ( "Could not map %s: %s\n", name, strerror ( errno ) );
		exit ( 1 );
	}
	elf->data = data;

	/* Close file */
	close ( fd );

	/* Check header */
	ehdr = elf->data;
	if ( ( elf->len < sizeof ( *ehdr ) ) ||
	     ( memcmp ( ident, ehdr->e_ident, sizeof ( ident ) ) != 0 ) ) {
		eprintf ( "Invalid ELF header in %s\n", name );
		exit ( 1 );
	}
	elf->ehdr = ehdr;

	/* Check section headers */
	for ( i = 0 ; i < ehdr->e_shnum ; i++ ) {
		offset = ( ehdr->e_shoff + ( i * ehdr->e_shentsize ) );
		if ( elf->len < ( offset + sizeof ( *shdr ) ) ) {
			eprintf ( "ELF section header outside file in %s\n",
				  name );
			exit ( 1 );
		}
		shdr = ( data + offset );
		if ( ( shdr->sh_type != SHT_NOBITS ) &&
		     ( ( elf->len < shdr->sh_offset ) ||
		       ( ( ( elf->len - shdr->sh_offset ) < shdr->sh_size ) ))){
			eprintf ( "ELF section %d outside file in %s\n",
				  i, name );
			exit ( 1 );
		}
		if ( shdr->sh_link >= ehdr->e_shnum ) {
			eprintf ( "ELF section %d link section %d out of "
				  "range\n", i, shdr->sh_link );
			exit ( 1 );
		}
	}
}

/**
 * Get ELF string
 *
 * @v elf		ELF file
 * @v section		String table section number
 * @v offset		String table offset
 * @ret string		ELF string
 */
static const char * elf_string ( struct elf_file *elf, unsigned int section,
				 size_t offset ) {
	const Elf_Ehdr *ehdr = elf->ehdr;
	const Elf_Shdr *shdr;
	char *string;
	char *last;

	/* Locate section header */
	if ( section >= ehdr->e_shnum ) {
		eprintf ( "Invalid ELF string section %d\n", section );
		exit ( 1 );
	}
	shdr = ( elf->data + ehdr->e_shoff + ( section * ehdr->e_shentsize ) );

	/* Sanity check section */
	if ( shdr->sh_type != SHT_STRTAB ) {
		eprintf ( "ELF section %d (type %d) is not a string table\n",
			  section, shdr->sh_type );
		exit ( 1 );
	}
	last = ( elf->data + shdr->sh_offset + shdr->sh_size - 1 );
	if ( *last != '\0' ) {
		eprintf ( "ELF section %d is not NUL-terminated\n", section );
		exit ( 1 );
	}

	/* Locate string */
	if ( offset >= shdr->sh_size ) {
		eprintf ( "Invalid ELF string offset %zd in section %d\n",
			  offset, section );
		exit ( 1 );
	}
	string = ( elf->data + shdr->sh_offset + offset );

	return string;
}

/**
 * Set machine architecture
 *
 * @v elf		ELF file
 * @v pe_header		PE file header
 */
static void set_machine ( struct elf_file *elf, struct pe_header *pe_header ) {
	const Elf_Ehdr *ehdr = elf->ehdr;
	uint16_t machine;

	/* Identify machine architecture */
	switch ( ehdr->e_machine ) {
	case EM_386:
		machine = EFI_IMAGE_MACHINE_IA32;
		break;
	case EM_X86_64:
		machine = EFI_IMAGE_MACHINE_X64;
		break;
	case EM_ARM:
		machine = EFI_IMAGE_MACHINE_ARMTHUMB_MIXED;
		break;
	case EM_AARCH64:
		machine = EFI_IMAGE_MACHINE_AARCH64;
		break;
	default:
		eprintf ( "Unknown ELF architecture %d\n", ehdr->e_machine );
		exit ( 1 );
	}

	/* Set machine architecture */
	pe_header->nt.FileHeader.Machine = machine;
}

/**
 * Process section
 *
 * @v elf		ELF file
 * @v shdr		ELF section header
 * @v pe_header		PE file header
 * @ret new		New PE section
 */
static struct pe_section * process_section ( struct elf_file *elf,
					     const Elf_Shdr *shdr,
					     struct pe_header *pe_header ) {
	struct pe_section *new;
	const char *name;
	size_t name_len;
	size_t section_memsz;
	size_t section_filesz;
	unsigned long code_start;
	unsigned long code_end;
	unsigned long data_start;
	unsigned long data_mid;
	unsigned long data_end;
	unsigned long start;
	unsigned long end;
	unsigned long *applicable_start;
	unsigned long *applicable_end;

	/* Get section name */
	name = elf_string ( elf, elf->ehdr->e_shstrndx, shdr->sh_name );

	/* Extract current RVA limits from file header */
	code_start = pe_header->nt.OptionalHeader.BaseOfCode;
	code_end = ( code_start + pe_header->nt.OptionalHeader.SizeOfCode );
#if defined(EFI_TARGET32)
	data_start = pe_header->nt.OptionalHeader.BaseOfData;
#elif defined(EFI_TARGET64)
	data_start = code_end;
#endif
	data_mid = ( data_start +
		     pe_header->nt.OptionalHeader.SizeOfInitializedData );
	data_end = ( data_mid +
		     pe_header->nt.OptionalHeader.SizeOfUninitializedData );

	/* Allocate PE section */
	section_memsz = shdr->sh_size;
	section_filesz = ( ( shdr->sh_type == SHT_PROGBITS ) ?
			   efi_file_align ( section_memsz ) : 0 );
	new = xmalloc ( sizeof ( *new ) + section_filesz );
	memset ( new, 0, sizeof ( *new ) + section_filesz );

	/* Fill in section header details */
	name_len = strlen ( name );
	if ( name_len > sizeof ( new->hdr.Name ) )
		name_len = sizeof ( new->hdr.Name );
	memcpy ( new->hdr.Name, name, name_len );
	new->hdr.Misc.VirtualSize = section_memsz;
	new->hdr.VirtualAddress = shdr->sh_addr;
	new->hdr.SizeOfRawData = section_filesz;

	/* Fill in section characteristics and update RVA limits */
	if ( ( shdr->sh_type == SHT_PROGBITS ) &&
	     ( shdr->sh_flags & SHF_EXECINSTR ) ) {
		/* .text-type section */
		new->hdr.Characteristics =
			( EFI_IMAGE_SCN_CNT_CODE |
			  EFI_IMAGE_SCN_MEM_NOT_PAGED |
			  EFI_IMAGE_SCN_MEM_EXECUTE |
			  EFI_IMAGE_SCN_MEM_READ );
		applicable_start = &code_start;
		applicable_end = &code_end;
	} else if ( ( shdr->sh_type == SHT_PROGBITS ) &&
		    ( shdr->sh_flags & SHF_WRITE ) ) {
		/* .data-type section */
		new->hdr.Characteristics =
			( EFI_IMAGE_SCN_CNT_INITIALIZED_DATA |
			  EFI_IMAGE_SCN_MEM_NOT_PAGED |
			  EFI_IMAGE_SCN_MEM_READ |
			  EFI_IMAGE_SCN_MEM_WRITE );
		applicable_start = &data_start;
		applicable_end = &data_mid;
	} else if ( shdr->sh_type == SHT_PROGBITS ) {
		/* .rodata-type section */
		new->hdr.Characteristics =
			( EFI_IMAGE_SCN_CNT_INITIALIZED_DATA |
			  EFI_IMAGE_SCN_MEM_NOT_PAGED |
			  EFI_IMAGE_SCN_MEM_READ );
		applicable_start = &data_start;
		applicable_end = &data_mid;
	} else if ( shdr->sh_type == SHT_NOBITS ) {
		/* .bss-type section */
		new->hdr.Characteristics =
			( EFI_IMAGE_SCN_CNT_UNINITIALIZED_DATA |
			  EFI_IMAGE_SCN_MEM_NOT_PAGED |
			  EFI_IMAGE_SCN_MEM_READ |
			  EFI_IMAGE_SCN_MEM_WRITE );
		applicable_start = &data_mid;
		applicable_end = &data_end;
	} else {
		eprintf ( "Unrecognised characteristics for section %s\n",
			  name );
		exit ( 1 );
	}

	/* Copy in section contents */
	if ( shdr->sh_type == SHT_PROGBITS ) {
		memcpy ( new->contents, ( elf->data + shdr->sh_offset ),
			 shdr->sh_size );
	}

	/* Update RVA limits */
	start = new->hdr.VirtualAddress;
	end = ( start + new->hdr.Misc.VirtualSize );
	if ( ( ! *applicable_start ) || ( *applicable_start >= start ) )
		*applicable_start = start;
	if ( *applicable_end < end )
		*applicable_end = end;
	if ( data_start < code_end )
		data_start = code_end;
	if ( data_mid < data_start )
		data_mid = data_start;
	if ( data_end < data_mid )
		data_end = data_mid;

	/* Write RVA limits back to file header */
	pe_header->nt.OptionalHeader.BaseOfCode = code_start;
	pe_header->nt.OptionalHeader.SizeOfCode = ( code_end - code_start );
#if defined(EFI_TARGET32)
	pe_header->nt.OptionalHeader.BaseOfData = data_start;
#endif
	pe_header->nt.OptionalHeader.SizeOfInitializedData =
		( data_mid - data_start );
	pe_header->nt.OptionalHeader.SizeOfUninitializedData =
		( data_end - data_mid );

	/* Update remaining file header fields */
	pe_header->nt.FileHeader.NumberOfSections++;
	pe_header->nt.OptionalHeader.SizeOfHeaders += sizeof ( new->hdr );
	pe_header->nt.OptionalHeader.SizeOfImage =
		efi_image_align ( data_end );

	return new;
}

/**
 * Process relocation record
 *
 * @v elf		ELF file
 * @v shdr		ELF section header
 * @v syms		Symbol table
 * @v nsyms		Number of symbol table entries
 * @v rel		Relocation record
 * @v pe_reltab		PE relocation table to fill in
 */
static void process_reloc ( struct elf_file *elf, const Elf_Shdr *shdr,
			    const Elf_Sym *syms, unsigned int nsyms,
			    const Elf_Rel *rel, struct pe_relocs **pe_reltab ) {
	unsigned int type = ELF_R_TYPE ( rel->r_info );
	unsigned int sym = ELF_R_SYM ( rel->r_info );
	unsigned int mrel = ELF_MREL ( elf->ehdr->e_machine, type );
	size_t offset = ( shdr->sh_addr + rel->r_offset );

	/* Look up symbol and process relocation */
	if ( sym >= nsyms ) {
		eprintf ( "Symbol out of range\n" );
		exit ( 1 );
	}
	if ( syms[sym].st_shndx == SHN_ABS ) {
		/* Skip absolute symbols; the symbol value won't
		 * change when the object is loaded.
		 */
	} else {
		switch ( mrel ) {
		case ELF_MREL ( EM_386, R_386_NONE ) :
		case ELF_MREL ( EM_ARM, R_ARM_NONE ) :
		case ELF_MREL ( EM_X86_64, R_X86_64_NONE ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_NONE ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_NULL ) :
			/* Ignore dummy relocations used by REQUIRE_SYMBOL() */
			break;
		case ELF_MREL ( EM_386, R_386_32 ) :
		case ELF_MREL ( EM_ARM, R_ARM_ABS32 ) :
			/* Generate a 4-byte PE relocation */
			generate_pe_reloc ( pe_reltab, offset, 4 );
			break;
		case ELF_MREL ( EM_X86_64, R_X86_64_64 ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_ABS64 ) :
			/* Generate an 8-byte PE relocation */
			generate_pe_reloc ( pe_reltab, offset, 8 );
			break;
		case ELF_MREL ( EM_386, R_386_PC32 ) :
		case ELF_MREL ( EM_ARM, R_ARM_CALL ) :
		case ELF_MREL ( EM_ARM, R_ARM_REL32 ) :
		case ELF_MREL ( EM_ARM, R_ARM_THM_PC22 ) :
		case ELF_MREL ( EM_ARM, R_ARM_THM_JUMP24 ) :
		case ELF_MREL ( EM_ARM, R_ARM_V4BX ):
		case ELF_MREL ( EM_X86_64, R_X86_64_PC32 ) :
		case ELF_MREL ( EM_X86_64, R_X86_64_PLT32 ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_CALL26 ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_JUMP26 ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_ADR_PREL_LO21 ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_ADR_PREL_PG_HI21 ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_ADD_ABS_LO12_NC ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_LDST8_ABS_LO12_NC ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_LDST16_ABS_LO12_NC ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_LDST32_ABS_LO12_NC ) :
		case ELF_MREL ( EM_AARCH64, R_AARCH64_LDST64_ABS_LO12_NC ) :
			/* Skip PC-relative relocations; all relative
			 * offsets remain unaltered when the object is
			 * loaded.
			 */
			break;
		default:
			eprintf ( "Unrecognised relocation type %d\n", type );
			exit ( 1 );
		}
	}
}

/**
 * Process relocation records
 *
 * @v elf		ELF file
 * @v shdr		ELF section header
 * @v stride		Relocation record size
 * @v pe_reltab		PE relocation table to fill in
 */
static void process_relocs ( struct elf_file *elf, const Elf_Shdr *shdr,
			     size_t stride, struct pe_relocs **pe_reltab ) {
	const Elf_Shdr *symtab;
	const Elf_Sym *syms;
	const Elf_Rel *rel;
	unsigned int nsyms;
	unsigned int nrels;
	unsigned int i;

	/* Identify symbol table */
	symtab = ( elf->data + elf->ehdr->e_shoff +
		   ( shdr->sh_link * elf->ehdr->e_shentsize ) );
	syms = ( elf->data + symtab->sh_offset );
	nsyms = ( symtab->sh_size / sizeof ( syms[0] ) );

	/* Process each relocation */
	rel = ( elf->data + shdr->sh_offset );
	nrels = ( shdr->sh_size / stride );
	for ( i = 0 ; i < nrels ; i++ ) {
		process_reloc ( elf, shdr, syms, nsyms, rel, pe_reltab );
		rel = ( ( ( const void * ) rel ) + stride );
	}
}

/**
 * Create relocations section
 *
 * @v pe_header		PE file header
 * @v pe_reltab		PE relocation table
 * @ret section		Relocation section
 */
static struct pe_section *
create_reloc_section ( struct pe_header *pe_header,
		       struct pe_relocs *pe_reltab ) {
	struct pe_section *reloc;
	size_t section_memsz;
	size_t section_filesz;
	EFI_IMAGE_DATA_DIRECTORY *relocdir;

	/* Allocate PE section */
	section_memsz = output_pe_reltab ( pe_reltab, NULL );
	section_filesz = efi_file_align ( section_memsz );
	reloc = xmalloc ( sizeof ( *reloc ) + section_filesz );
	memset ( reloc, 0, sizeof ( *reloc ) + section_filesz );

	/* Fill in section header details */
	strncpy ( ( char * ) reloc->hdr.Name, ".reloc",
		  sizeof ( reloc->hdr.Name ) );
	reloc->hdr.Misc.VirtualSize = section_memsz;
	reloc->hdr.VirtualAddress = pe_header->nt.OptionalHeader.SizeOfImage;
	reloc->hdr.SizeOfRawData = section_filesz;
	reloc->hdr.Characteristics = ( EFI_IMAGE_SCN_CNT_INITIALIZED_DATA |
				       EFI_IMAGE_SCN_MEM_DISCARDABLE |
				       EFI_IMAGE_SCN_MEM_NOT_PAGED |
				       EFI_IMAGE_SCN_MEM_READ );

	/* Copy in section contents */
	output_pe_reltab ( pe_reltab, reloc->contents );

	/* Update file header details */
	pe_header->nt.FileHeader.NumberOfSections++;
	pe_header->nt.OptionalHeader.SizeOfHeaders += sizeof ( reloc->hdr );
	pe_header->nt.OptionalHeader.SizeOfImage +=
		efi_image_align ( section_memsz );
	relocdir = &(pe_header->nt.OptionalHeader.DataDirectory
		     [EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC]);
	relocdir->VirtualAddress = reloc->hdr.VirtualAddress;
	relocdir->Size = section_memsz;

	return reloc;
}

/**
 * Fix up debug section
 *
 * @v debug		Debug section
 */
static void fixup_debug_section ( struct pe_section *debug ) {
	EFI_IMAGE_DEBUG_DIRECTORY_ENTRY *contents;

	/* Fix up FileOffset */
	contents = ( ( void * ) debug->contents );
	contents->FileOffset += ( debug->hdr.PointerToRawData -
				  debug->hdr.VirtualAddress );
}

/**
 * Create debug section
 *
 * @v pe_header		PE file header
 * @ret section		Debug section
 */
static struct pe_section *
create_debug_section ( struct pe_header *pe_header, const char *filename ) {
	struct pe_section *debug;
	size_t section_memsz;
	size_t section_filesz;
	EFI_IMAGE_DATA_DIRECTORY *debugdir;
	struct {
		EFI_IMAGE_DEBUG_DIRECTORY_ENTRY debug;
		EFI_IMAGE_DEBUG_CODEVIEW_RSDS_ENTRY rsds;
		char name[ strlen ( filename ) + 1 ];
	} *contents;

	/* Allocate PE section */
	section_memsz = sizeof ( *contents );
	section_filesz = efi_file_align ( section_memsz );
	debug = xmalloc ( sizeof ( *debug ) + section_filesz );
	memset ( debug, 0, sizeof ( *debug ) + section_filesz );
	contents = ( void * ) debug->contents;

	/* Fill in section header details */
	strncpy ( ( char * ) debug->hdr.Name, ".debug",
		  sizeof ( debug->hdr.Name ) );
	debug->hdr.Misc.VirtualSize = section_memsz;
	debug->hdr.VirtualAddress = pe_header->nt.OptionalHeader.SizeOfImage;
	debug->hdr.SizeOfRawData = section_filesz;
	debug->hdr.Characteristics = ( EFI_IMAGE_SCN_CNT_INITIALIZED_DATA |
				       EFI_IMAGE_SCN_MEM_DISCARDABLE |
				       EFI_IMAGE_SCN_MEM_NOT_PAGED |
				       EFI_IMAGE_SCN_MEM_READ );
	debug->fixup = fixup_debug_section;

	/* Create section contents */
	contents->debug.TimeDateStamp = 0x10d1a884;
	contents->debug.Type = EFI_IMAGE_DEBUG_TYPE_CODEVIEW;
	contents->debug.SizeOfData =
		( sizeof ( *contents ) - sizeof ( contents->debug ) );
	contents->debug.RVA = ( debug->hdr.VirtualAddress +
				offsetof ( typeof ( *contents ), rsds ) );
	contents->debug.FileOffset = contents->debug.RVA;
	contents->rsds.Signature = CODEVIEW_SIGNATURE_RSDS;
	snprintf ( contents->name, sizeof ( contents->name ), "%s",
		   filename );

	/* Update file header details */
	pe_header->nt.FileHeader.NumberOfSections++;
	pe_header->nt.OptionalHeader.SizeOfHeaders += sizeof ( debug->hdr );
	pe_header->nt.OptionalHeader.SizeOfImage +=
		efi_image_align ( section_memsz );
	debugdir = &(pe_header->nt.OptionalHeader.DataDirectory
		     [EFI_IMAGE_DIRECTORY_ENTRY_DEBUG]);
	debugdir->VirtualAddress = debug->hdr.VirtualAddress;
	debugdir->Size = sizeof ( contents->debug );

	return debug;
}

/**
 * Write out PE file
 *
 * @v pe_header		PE file header
 * @v pe_sections	List of PE sections
 * @v pe		Output file
 */
static void write_pe_file ( struct pe_header *pe_header,
			    struct pe_section *pe_sections,
			    FILE *pe ) {
	struct pe_section *section;
	unsigned long fpos = 0;

	/* Align length of headers */
	fpos = pe_header->nt.OptionalHeader.SizeOfHeaders =
		efi_file_align ( pe_header->nt.OptionalHeader.SizeOfHeaders );

	/* Assign raw data pointers */
	for ( section = pe_sections ; section ; section = section->next ) {
		if ( section->hdr.SizeOfRawData ) {
			section->hdr.PointerToRawData = fpos;
			fpos += section->hdr.SizeOfRawData;
			fpos = efi_file_align ( fpos );
		}
		if ( section->fixup )
			section->fixup ( section );
	}

	/* Write file header */
	if ( fwrite ( pe_header, sizeof ( *pe_header ), 1, pe ) != 1 ) {
		perror ( "Could not write PE header" );
		exit ( 1 );
	}

	/* Write section headers */
	for ( section = pe_sections ; section ; section = section->next ) {
		if ( fwrite ( &section->hdr, sizeof ( section->hdr ),
			      1, pe ) != 1 ) {
			perror ( "Could not write section header" );
			exit ( 1 );
		}
	}

	/* Write sections */
	for ( section = pe_sections ; section ; section = section->next ) {
		if ( fseek ( pe, section->hdr.PointerToRawData,
			     SEEK_SET ) != 0 ) {
			eprintf ( "Could not seek to %x: %s\n",
				  section->hdr.PointerToRawData,
				  strerror ( errno ) );
			exit ( 1 );
		}
		if ( section->hdr.SizeOfRawData &&
		     ( fwrite ( section->contents, section->hdr.SizeOfRawData,
				1, pe ) != 1 ) ) {
			eprintf ( "Could not write section %.8s: %s\n",
				  section->hdr.Name, strerror ( errno ) );
			exit ( 1 );
		}
	}
}

/**
 * Convert ELF to PE
 *
 * @v elf_name		ELF file name
 * @v pe_name		PE file name
 */
static void elf2pe ( const char *elf_name, const char *pe_name,
		     struct options *opts ) {
	char pe_name_tmp[ strlen ( pe_name ) + 1 ];
	struct pe_relocs *pe_reltab = NULL;
	struct pe_section *pe_sections = NULL;
	struct pe_section **next_pe_section = &pe_sections;
	struct pe_header pe_header;
	struct elf_file elf;
	const Elf_Shdr *shdr;
	size_t offset;
	unsigned int i;
	FILE *pe;

	/* Create a modifiable copy of the PE name */
	memcpy ( pe_name_tmp, pe_name, sizeof ( pe_name_tmp ) );

	/* Read ELF file */
	read_elf_file ( elf_name, &elf );

	/* Initialise the PE header */
	memcpy ( &pe_header, &efi_pe_header, sizeof ( pe_header ) );
	set_machine ( &elf, &pe_header );
	pe_header.nt.OptionalHeader.AddressOfEntryPoint = elf.ehdr->e_entry;
	pe_header.nt.OptionalHeader.Subsystem = opts->subsystem;

	/* Process input sections */
	for ( i = 0 ; i < elf.ehdr->e_shnum ; i++ ) {
		offset = ( elf.ehdr->e_shoff + ( i * elf.ehdr->e_shentsize ) );
		shdr = ( elf.data + offset );

		/* Process section */
		if ( shdr->sh_flags & SHF_ALLOC ) {

			/* Create output section */
			*(next_pe_section) = process_section ( &elf, shdr,
							       &pe_header );
			next_pe_section = &(*next_pe_section)->next;

		} else if ( shdr->sh_type == SHT_REL ) {

			/* Process .rel relocations */
			process_relocs ( &elf, shdr, sizeof ( Elf_Rel ),
					 &pe_reltab );

		} else if ( shdr->sh_type == SHT_RELA ) {

			/* Process .rela relocations */
			process_relocs ( &elf, shdr, sizeof ( Elf_Rela ),
					 &pe_reltab );
		}
	}

	/* Create the .reloc section */
	*(next_pe_section) = create_reloc_section ( &pe_header, pe_reltab );
	next_pe_section = &(*next_pe_section)->next;

	/* Create the .debug section */
	*(next_pe_section) = create_debug_section ( &pe_header,
						    basename ( pe_name_tmp ) );
	next_pe_section = &(*next_pe_section)->next;

	/* Write out PE file */
	pe = fopen ( pe_name, "w" );
	if ( ! pe ) {
		eprintf ( "Could not open %s for writing: %s\n",
			  pe_name, strerror ( errno ) );
		exit ( 1 );
	}
	write_pe_file ( &pe_header, pe_sections, pe );
	fclose ( pe );

	/* Unmap ELF file */
	munmap ( elf.data, elf.len );
}

/**
 * Print help
 *
 * @v program_name	Program name
 */
static void print_help ( const char *program_name ) {
	eprintf ( "Syntax: %s [--subsystem=<number>] infile outfile\n",
		  program_name );
}

/**
 * Parse command-line options
 *
 * @v argc		Argument count
 * @v argv		Argument list
 * @v opts		Options structure to populate
 */
static int parse_options ( const int argc, char **argv,
			   struct options *opts ) {
	char *end;
	int c;

	while (1) {
		int option_index = 0;
		static struct option long_options[] = {
			{ "subsystem", required_argument, NULL, 's' },
			{ "help", 0, NULL, 'h' },
			{ 0, 0, 0, 0 }
		};

		if ( ( c = getopt_long ( argc, argv, "s:h",
					 long_options,
					 &option_index ) ) == -1 ) {
			break;
		}

		switch ( c ) {
		case 's':
			opts->subsystem = strtoul ( optarg, &end, 0 );
			if ( *end || ( ! *optarg ) ) {
				eprintf ( "Invalid subsytem \"%s\"\n",
					  optarg );
				exit ( 2 );
			}
			break;
		case 'h':
			print_help ( argv[0] );
			exit ( 0 );
		case '?':
		default:
			exit ( 2 );
		}
	}
	return optind;
}

int main ( int argc, char **argv ) {
	struct options opts = {
		.subsystem = EFI_IMAGE_SUBSYSTEM_EFI_APPLICATION,
	};
	int infile_index;
	const char *infile;
	const char *outfile;

	/* Parse command-line arguments */
	infile_index = parse_options ( argc, argv, &opts );
	if ( argc != ( infile_index + 2 ) ) {
		print_help ( argv[0] );
		exit ( 2 );
	}
	infile = argv[infile_index];
	outfile = argv[infile_index + 1];

	/* Convert file */
	elf2pe ( infile, outfile, &opts );

	return 0;
}
