/* grub-pe2elf.c - tool to convert pe image to elf.  */
/*
 *  GRUB  --  GRand Unified Bootloader
 *  Copyright (C) 2008,2009 Free Software Foundation, Inc.
 *
 *  GRUB 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 3 of the License, or
 *  (at your option) any later version.
 *
 *  GRUB 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 GRUB.  If not, see <http://www.gnu.org/licenses/>.
 */

#include <config.h>
#include <grub/types.h>
#include <grub/util/misc.h>
#include <grub/elf.h>
#include <grub/efi/pe32.h>
#include <grub/misc.h>

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


/* Please don't internationalise this file. It's pointless.  */

/*
 *  Section layout
 *
 *    null
 *    .text
 *    .rdata
 *    .data
 *    .bss
 *    .modname
 *    .moddeps
 *    .symtab
 *    .strtab
 *    relocation sections
 */

#if GRUB_TARGET_WORDSIZE == 64
typedef Elf64_Rela elf_reloc_t;
#define GRUB_PE32_MACHINE GRUB_PE32_MACHINE_X86_64
#else
typedef Elf32_Rel elf_reloc_t;
#define GRUB_PE32_MACHINE GRUB_PE32_MACHINE_I386
#endif

#define STRTAB_BLOCK	256

static char *strtab;
static int strtab_max, strtab_len;

static Elf_Ehdr ehdr;
static Elf_Shdr *shdr;
static int num_sections, first_reloc_section, reloc_sections_end, symtab_section, strtab_section;
static grub_uint32_t offset, image_base;

static int
insert_string (const char *name)
{
  int len, result;

  if (*name == '_')
    name++;

  len = strlen (name);
  if (strtab_len + len >= strtab_max)
    {
      strtab_max += STRTAB_BLOCK;
      strtab = xrealloc (strtab, strtab_max);
    }

  strcpy (strtab + strtab_len, name);
  result = strtab_len;
  strtab_len += len + 1;

  return result;
}

static int *
write_section_data (FILE* fp, const char *name, char *image,
                    struct grub_pe32_coff_header *pe_chdr,
                    struct grub_pe32_section_table *pe_shdr)
{
  int *section_map;
  int i;
  grub_uint32_t last_category = 0;
  grub_uint32_t idx, idx_reloc;
  char *pe_strtab = (image + pe_chdr->symtab_offset
		     + pe_chdr->num_symbols * sizeof (struct grub_pe32_symbol));

  section_map = xmalloc ((2 * pe_chdr->num_sections + 5) * sizeof (int));
  section_map[0] = 0;
  shdr = xmalloc ((2 * pe_chdr->num_sections + 5) * sizeof (shdr[0]));
  idx = 1;
  idx_reloc = pe_chdr->num_sections + 1;

  for (i = 0; i < pe_chdr->num_sections; i++, pe_shdr++)
    {
      grub_uint32_t category;
      const char *shname = pe_shdr->name;
      grub_size_t secsize;

      if (shname[0] == '/' && grub_isdigit (shname[1]))
      {
        char t[sizeof (pe_shdr->name) + 1];
        memcpy (t, shname, sizeof (pe_shdr->name));
        t[sizeof (pe_shdr->name)] = 0;
        shname = pe_strtab + atoi (t + 1);
      }

      secsize = pe_shdr->raw_data_size;

      shdr[idx].sh_type = SHT_PROGBITS;

      if (! strcmp (shname, ".text"))
        {
          category = 0;
          shdr[idx].sh_flags = SHF_ALLOC | SHF_EXECINSTR;
        }
      else if (! strncmp (shname, ".rdata", 6))
        {
          category = 1;
          shdr[idx].sh_flags = SHF_ALLOC;
        }
      else if (! strcmp (shname, ".data"))
        {
          category = 2;
          shdr[idx].sh_flags = SHF_ALLOC | SHF_WRITE;
        }
      else if (! strcmp (shname, ".bss"))
        {
          category = 3;
	  shdr[idx].sh_type = SHT_NOBITS;
          shdr[idx].sh_flags = SHF_ALLOC | SHF_WRITE;
	  if (secsize < pe_shdr->virtual_size)
	    secsize = pe_shdr->virtual_size;
        }
      else if (strcmp (shname, ".modname") == 0 || strcmp (shname, ".moddeps") == 0
	       || strcmp (shname, ".module_license") == 0)
        category = 4;
      else
        {
          section_map[i + 1] = -1;
          continue;
        }

      if (category < last_category)
	grub_util_error ("out of order sections");

      section_map[i + 1] = idx;

      if (pe_shdr->virtual_size
	  && pe_shdr->virtual_size < secsize)
	secsize = pe_shdr->virtual_size;

      shdr[idx].sh_size = secsize;
      shdr[idx].sh_addralign = 1 << (((pe_shdr->characteristics >>
                                       GRUB_PE32_SCN_ALIGN_SHIFT) &
                                      GRUB_PE32_SCN_ALIGN_MASK) - 1);
      shdr[idx].sh_addr = pe_shdr->virtual_address + image_base;

      if (shdr[idx].sh_type != SHT_NOBITS)
        {
          shdr[idx].sh_offset = offset;
          grub_util_write_image_at (image + pe_shdr->raw_data_offset,
                                    pe_shdr->raw_data_size, offset, fp,
				    shname);

          offset += secsize;
        }

      if (pe_shdr->relocations_offset)
        {
          char relname[5 + strlen (shname)];

          sprintf (relname, ".rel%s", shname);

          shdr[idx_reloc].sh_name = insert_string (relname);
          shdr[idx_reloc].sh_link = i;
          shdr[idx_reloc].sh_info = idx;

          shdr[idx].sh_name = shdr[idx_reloc].sh_name + 4;

          idx_reloc++;
        }
      else
        shdr[idx].sh_name = insert_string (shname);
      idx++;
    }

  idx_reloc -= pe_chdr->num_sections + 1;
  num_sections = idx + idx_reloc + 2;
  first_reloc_section = idx;
  reloc_sections_end = idx + idx_reloc;
  memmove (shdr + idx, shdr + pe_chdr->num_sections + 1,
	   idx_reloc * sizeof (shdr[0]));
  memset (shdr + idx + idx_reloc, 0, 3 * sizeof (shdr[0]));
  memset (shdr, 0, sizeof (shdr[0]));

  symtab_section = idx + idx_reloc;
  strtab_section = idx + idx_reloc + 1;

  return section_map;
}

static void
write_reloc_section (FILE* fp, const char *name, char *image,
                     struct grub_pe32_coff_header *pe_chdr,
                     struct grub_pe32_section_table  *pe_shdr,
                     Elf_Sym *symtab,
                     int *symtab_map)
{
  int i;

  for (i = first_reloc_section; i < reloc_sections_end; i++)
    {
      struct grub_pe32_section_table *pe_sec;
      struct grub_pe32_reloc *pe_rel;
      elf_reloc_t *rel;
      int num_rels, j, modified;

      pe_sec = pe_shdr + shdr[i].sh_link;
      pe_rel = (struct grub_pe32_reloc *) (image + pe_sec->relocations_offset);
      rel = (elf_reloc_t *) xmalloc (pe_sec->num_relocations * sizeof (elf_reloc_t));
      num_rels = 0;
      modified = 0;

      for (j = 0; j < pe_sec->num_relocations; j++, pe_rel++)
        {
          int type;
          grub_uint32_t ofs, *addr;

          if ((pe_rel->symtab_index >= pe_chdr->num_symbols) ||
              (symtab_map[pe_rel->symtab_index] == -1))
            grub_util_error ("invalid symbol");

          ofs = pe_rel->offset - pe_sec->virtual_address;
          addr = (grub_uint32_t *)(image + pe_sec->raw_data_offset + ofs);

          switch (pe_rel->type)
	    {
#if GRUB_TARGET_WORDSIZE == 64
	    case 1:
	      type = R_X86_64_64;
	      rel[num_rels].r_addend = *(grub_int64_t *)addr;
	      *(grub_int64_t *)addr = 0;
	      modified = 1;
	      break;
	    case 4:
	      type = R_X86_64_PC32;
	      rel[num_rels].r_addend = *(grub_int32_t *)addr;
	      *addr = 0;
	      modified = 1;
	      break;
	    case 14:
	      type = R_X86_64_PC64;
	      rel[num_rels].r_addend = *(grub_uint64_t *)addr - 8;
	      *(grub_uint64_t *)addr = 0;
	      modified = 1;
	      break;
#else
	    case GRUB_PE32_REL_I386_DIR32:
	      type = R_386_32;
	      break;
	    case GRUB_PE32_REL_I386_REL32:
	      type = R_386_PC32;
	      break;
#endif
	    default:
	      grub_util_error ("unknown pe relocation type %d", pe_rel->type);
	    }

          if (type ==
#if GRUB_TARGET_WORDSIZE == 64
	      R_386_PC32
#else
	      R_X86_64_PC32
#endif

	      )
            {
              unsigned char code;

              code = image[pe_sec->raw_data_offset + ofs - 1];

#if GRUB_TARGET_WORDSIZE == 32
              if (((code != 0xe8) && (code != 0xe9)) || (*addr))
                grub_util_error ("invalid relocation (%x %x)", code, *addr);
#endif

              if (symtab[symtab_map[pe_rel->symtab_index]].st_shndx
		  && symtab[symtab_map[pe_rel->symtab_index]].st_shndx
		  == shdr[i].sh_info)
                {
		  modified = 1;
                  *addr += (symtab[symtab_map[pe_rel->symtab_index]].st_value
			    - ofs - 4);

                  continue;
                }
              else
		{
#if GRUB_TARGET_WORDSIZE == 64
		  rel[num_rels].r_addend -= 4;
#else
		  modified = 1;
		  *addr = -4;
#endif
		}
            }

          rel[num_rels].r_offset = ofs;
          rel[num_rels].r_info = ELF_R_INFO (symtab_map[pe_rel->symtab_index],
					     type);
          num_rels++;
        }

      if (modified)
        grub_util_write_image_at (image + pe_sec->raw_data_offset,
                                  shdr[shdr[i].sh_info].sh_size,
                                  shdr[shdr[i].sh_info].sh_offset,
                                  fp, name);

#if GRUB_TARGET_WORDSIZE == 64
      shdr[i].sh_type = SHT_RELA;
#else
      shdr[i].sh_type = SHT_REL;
#endif
      shdr[i].sh_offset = offset;
      shdr[i].sh_link = symtab_section;
      shdr[i].sh_addralign = 4;
      shdr[i].sh_entsize = sizeof (elf_reloc_t);
      shdr[i].sh_size = num_rels * sizeof (elf_reloc_t);

      grub_util_write_image_at (rel, shdr[i].sh_size, offset, fp, name);
      offset += shdr[i].sh_size;
      free (rel);
    }
}

static void
write_symbol_table (FILE* fp, const char *name, char *image,
                    struct grub_pe32_coff_header *pe_chdr,
                    struct grub_pe32_section_table *pe_shdr,
                    int *section_map)
{
  struct grub_pe32_symbol *pe_symtab;
  char *pe_strtab;
  Elf_Sym *symtab;
  int *symtab_map, num_syms;
  int i;

  pe_symtab = (struct grub_pe32_symbol *) (image + pe_chdr->symtab_offset);
  pe_strtab = (char *) (pe_symtab + pe_chdr->num_symbols);

  symtab = (Elf_Sym *) xmalloc ((pe_chdr->num_symbols + 1) *
				sizeof (Elf_Sym));
  memset (symtab, 0, (pe_chdr->num_symbols + 1) * sizeof (Elf_Sym));
  num_syms = 1;

  symtab_map = (int *) xmalloc (pe_chdr->num_symbols * sizeof (int));

  for (i = 0; i < (int) pe_chdr->num_symbols;
       i += pe_symtab->num_aux + 1, pe_symtab += pe_symtab->num_aux + 1)
    {
      int bind, type;

      symtab_map[i] = -1;
      if ((pe_symtab->section > pe_chdr->num_sections) ||
          (section_map[pe_symtab->section] == -1))
        continue;

      if (! pe_symtab->section)
        type = STT_NOTYPE;
      else if (pe_symtab->type == GRUB_PE32_DT_FUNCTION)
        type = STT_FUNC;
      else
        type = STT_OBJECT;

      if (pe_symtab->storage_class == GRUB_PE32_SYM_CLASS_EXTERNAL)
        bind = STB_GLOBAL;
      else
        bind = STB_LOCAL;

      if ((pe_symtab->type != GRUB_PE32_DT_FUNCTION) && (pe_symtab->num_aux))
        {
          if (! pe_symtab->value)
            type = STT_SECTION;

          symtab[num_syms].st_name = shdr[section_map[pe_symtab->section]].sh_name;
        }
      else
        {
	  char short_name[9];
          char *symname;

	  if (pe_symtab->long_name[0])
	    {
	      strncpy (short_name, pe_symtab->short_name, 8);
	      short_name[8] = 0;
	      symname = short_name;
	    }
	  else
	    symname = pe_strtab + pe_symtab->long_name[1];

          if ((strcmp (symname, "_grub_mod_init")) &&
              (strcmp (symname, "_grub_mod_fini")) &&
	      (strcmp (symname, "grub_mod_init")) &&
              (strcmp (symname, "grub_mod_fini")) &&
              (bind == STB_LOCAL))
              continue;

          symtab[num_syms].st_name = insert_string (symname);
        }

      symtab[num_syms].st_shndx = section_map[pe_symtab->section];
      symtab[num_syms].st_value = pe_symtab->value;
      symtab[num_syms].st_info = ELF_ST_INFO (bind, type);

      symtab_map[i] = num_syms;
      num_syms++;
    }

  write_reloc_section (fp, name, image, pe_chdr, pe_shdr,
		       symtab, symtab_map);

  shdr[symtab_section].sh_name = insert_string (".symtab");
  shdr[symtab_section].sh_type = SHT_SYMTAB;
  shdr[symtab_section].sh_offset = offset;
  shdr[symtab_section].sh_size = num_syms * sizeof (Elf_Sym);
  shdr[symtab_section].sh_entsize = sizeof (Elf_Sym);
  shdr[symtab_section].sh_link = strtab_section;
  shdr[symtab_section].sh_addralign = 4;

  grub_util_write_image_at (symtab, shdr[symtab_section].sh_size,
                            offset, fp, name);
  offset += shdr[symtab_section].sh_size;

  free (symtab);
  free (symtab_map);
}

static void
write_string_table (FILE *fp, const char *name)
{
  shdr[strtab_section].sh_name = insert_string (".strtab");
  shdr[strtab_section].sh_type = SHT_STRTAB;
  shdr[strtab_section].sh_offset = offset;
  shdr[strtab_section].sh_size = strtab_len;
  shdr[strtab_section].sh_addralign = 1;
  grub_util_write_image_at (strtab, strtab_len, offset, fp,
			    name);
  offset += strtab_len;

  free (strtab);
}

static void
write_section_header (FILE *fp, const char *name)
{
  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_VERSION] = EV_CURRENT;
  ehdr.e_version = EV_CURRENT;
  ehdr.e_type = ET_REL;

#if GRUB_TARGET_WORDSIZE == 64
  ehdr.e_ident[EI_CLASS] = ELFCLASS64;
  ehdr.e_ident[EI_DATA] = ELFDATA2LSB;
  ehdr.e_machine = EM_X86_64;
#else
  ehdr.e_ident[EI_CLASS] = ELFCLASS32;
  ehdr.e_ident[EI_DATA] = ELFDATA2LSB;
  ehdr.e_machine = EM_386;
#endif
  ehdr.e_ehsize = sizeof (ehdr);
  ehdr.e_shentsize = sizeof (Elf_Shdr);
  ehdr.e_shstrndx = strtab_section;

  ehdr.e_shoff = offset;
  ehdr.e_shnum = num_sections;
  grub_util_write_image_at (shdr, sizeof (Elf_Shdr) * num_sections,
                            offset, fp, name);

  grub_util_write_image_at (&ehdr, sizeof (Elf_Ehdr), 0, fp, name);
}

static void
convert_pe (FILE* fp, const char *name, char *image)
{
  struct grub_pe32_coff_header *pe_chdr;
  struct grub_pe32_section_table *pe_shdr;
  int *section_map;

  if (image[0] == 'M' && image[1] == 'Z')
    pe_chdr = (struct grub_pe32_coff_header *) (image + (grub_le_to_cpu32 (((grub_uint32_t *)image)[0xf]) + 4));
  else
    pe_chdr = (struct grub_pe32_coff_header *) image;
  if (grub_le_to_cpu16 (pe_chdr->machine) != GRUB_PE32_MACHINE)
    grub_util_error ("invalid coff image (%x != %x)",
		     grub_le_to_cpu16 (pe_chdr->machine), GRUB_PE32_MACHINE);

  strtab = xmalloc (STRTAB_BLOCK);
  strtab_max = STRTAB_BLOCK;
  strtab[0] = 0;
  strtab_len = 1;

  offset = sizeof (ehdr);
  if (pe_chdr->optional_header_size)
    {
#if GRUB_TARGET_WORDSIZE == 64
      struct grub_pe64_optional_header *o;
#else
      struct grub_pe32_optional_header *o;
#endif
      o = (void *) (pe_chdr + 1);
      image_base = o->image_base;
    }
  pe_shdr = (struct grub_pe32_section_table *) ((char *) (pe_chdr + 1) + pe_chdr->optional_header_size);

  section_map = write_section_data (fp, name, image, pe_chdr, pe_shdr);

  write_symbol_table (fp, name, image, pe_chdr, pe_shdr, section_map);
  free (section_map);

  write_string_table (fp, name);

  write_section_header (fp, name);
}

int
main (int argc, char *argv[])
{
  char *image;
  FILE* fp;
  char *in, *out;

  /* Obtain PATH.  */
  if (1 >= argc)
    {
      fprintf (stderr, "Filename not specified.\n");
      return 1;
    }

  in = argv[1];
  if (argc > 2)
    out = argv[2];
  else
    out = in;
  image = grub_util_read_image (in);

  fp = grub_util_fopen (out, "wb");
  if (! fp)
    grub_util_error ("cannot open %s", out);

  convert_pe (fp, out, image);

  fclose (fp);

  return 0;
}
