// Copyright 2023 The IREE Authors
//
// Licensed under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception

#include <stdio.h>

#include "iree/base/api.h"
#include "iree/base/internal/file_io.h"
#include "iree/base/internal/path.h"
#include "iree/hal/local/elf/fatelf.h"

// NOTE: we don't verify ELF information in here and just pass it along. Don't
// run this on untrusted ELFs.

// NOTE: errors are handled in here just enough to get error messages - we don't
// care about leaks on failure as the process is going to die right away.

// TODO(benvanik): make this based on the archs used? It needs to be the common
// page size across all targets used within the file.
#define IREE_FATELF_PAGE_SIZE 4096

#if defined(IREE_PLATFORM_WINDOWS)
#include <fcntl.h>
#include <io.h>
#define IREE_SET_BINARY_MODE(handle) _setmode(_fileno(handle), O_BINARY)
#else
#define IREE_SET_BINARY_MODE(handle) ((void)0)
#endif  // IREE_PLATFORM_WINDOWS

static int print_usage() {
  fprintf(stderr, "Syntax: iree-fatelf [join|split|select|dump] files...\n");
  fprintf(stderr, "\n");
  fprintf(stderr, "Join multiple ELFs into a FatELF:\n");
  fprintf(stderr, "  iree-fatelf join elf_a.so elf_b.so > fatelf.sos\n");
  fprintf(stderr, "\n");
  fprintf(stderr, "Split a FatELF into multiple ELF files (to dir):\n");
  fprintf(stderr, "  iree-fatelf split fatelf.sos\n");
  fprintf(stderr, "\n");
  fprintf(stderr, "Select a FatELF matching the current arch:\n");
  fprintf(stderr, "  iree-fatelf select fatelf.sos > elf.so\n");
  fprintf(stderr, "\n");
  fprintf(stderr, "Dump header records:\n");
  fprintf(stderr, "  iree-fatelf dump fatelf.sos\n");
  fprintf(stderr, "\n");
  return 1;
}

// NOTE: this is somewhat redundant with fatelf.c but that's ok - this is a
// developer tool and I'd rather have the implementation linked into every
// runtime be kept as simple as possible than not repeating 100 lines of code.
// The runtime version is also designed to gracefully accept ELF files where
// here we only want FatELF files.
static iree_status_t fatelf_parse(iree_const_byte_span_t file_data,
                                  iree_fatelf_header_t** out_header) {
  *out_header = NULL;

  if (file_data.data_length <
      sizeof(iree_fatelf_header_t) + sizeof(iree_fatelf_record_t)) {
    return iree_make_status(
        IREE_STATUS_INVALID_ARGUMENT,
        "file does not have enough data to even hold a FatELF header");
  }

  const iree_fatelf_header_t* raw_header =
      (const iree_fatelf_header_t*)file_data.data;
  iree_fatelf_header_t host_header = {
      .magic = iree_unaligned_load_le_u32(&raw_header->magic),
      .version = iree_unaligned_load_le_u16(&raw_header->version),
      .record_count = iree_unaligned_load_le_u8(&raw_header->record_count),
      .reserved = iree_unaligned_load_le_u8(&raw_header->reserved),
  };

  if (host_header.magic != IREE_FATELF_MAGIC) {
    return iree_make_status(
        IREE_STATUS_INVALID_ARGUMENT,
        "file magic %08X does not match expected FatELF magic %08X",
        host_header.magic, IREE_FATELF_MAGIC);
  }
  if (host_header.version != IREE_FATELF_FORMAT_VERSION) {
    return iree_make_status(
        IREE_STATUS_UNIMPLEMENTED,
        "FatELF has version %d but runtime only supports version %d",
        host_header.version, IREE_FATELF_FORMAT_VERSION);
  }

  iree_host_size_t required_bytes =
      sizeof(iree_fatelf_header_t) +
      host_header.record_count * sizeof(iree_fatelf_record_t);
  if (file_data.data_length < required_bytes) {
    return iree_make_status(IREE_STATUS_INVALID_ARGUMENT,
                            "FatELF file truncated, requires at least %" PRIhsz
                            "B for headers but only have %" PRIhsz
                            "B available",
                            required_bytes, file_data.data_length);
  }

  // Allocate storage for the parsed header and records.
  iree_fatelf_header_t* header = NULL;
  IREE_RETURN_IF_ERROR(iree_allocator_malloc(
      iree_allocator_system(),
      sizeof(iree_fatelf_header_t) +
          host_header.record_count * sizeof(iree_fatelf_record_t),
      (void**)&header));
  memcpy(header, &host_header, sizeof(*header));
  for (iree_elf64_byte_t i = 0; i < host_header.record_count; ++i) {
    const iree_fatelf_record_t* raw_record = &raw_header->records[i];
    const iree_fatelf_record_t host_record = {
        .machine = iree_unaligned_load_le_u16(&raw_record->machine),
        .osabi = iree_unaligned_load_le_u8(&raw_record->osabi),
        .osabi_version = iree_unaligned_load_le_u8(&raw_record->osabi_version),
        .word_size = iree_unaligned_load_le_u8(&raw_record->word_size),
        .byte_order = iree_unaligned_load_le_u8(&raw_record->byte_order),
        .reserved0 = iree_unaligned_load_le_u8(&raw_record->reserved0),
        .reserved1 = iree_unaligned_load_le_u8(&raw_record->reserved1),
        .offset = iree_unaligned_load_le_u64(&raw_record->offset),
        .size = iree_unaligned_load_le_u64(&raw_record->size),
    };
    memcpy(&header->records[i], &host_record, sizeof(host_record));
  }

  *out_header = header;
  return iree_ok_status();
}

// Tries to parse basic ELF metadata from |elf_data|.
// Very little verification done. Note that this must support both 32 and 64-bit
// ELF files regardless of the tool host configuration.
// The returned fields match the ELF spec and may differ from FatELF.
static iree_status_t fatelf_parse_elf_metadata(
    iree_const_byte_span_t elf_data, iree_elf64_half_t* out_machine,
    iree_elf64_byte_t* out_osabi, iree_elf64_byte_t* out_osabi_version,
    iree_elf64_byte_t* out_elf_class, iree_elf64_byte_t* out_elf_data) {
  *out_machine = 0;
  *out_osabi = 0;
  *out_osabi_version = 0;
  *out_elf_data = 0;
  *out_elf_class = 0;

  if (elf_data.data_length < sizeof(iree_elf32_ehdr_t)) {
    return iree_make_status(IREE_STATUS_FAILED_PRECONDITION,
                            "ELF data provided (%" PRIhsz
                            ") is smaller than ehdr (%zu)",
                            elf_data.data_length, sizeof(iree_elf32_ehdr_t));
  }

  // The fields we're checking are the same in both 32 and 64 classes so we just
  // use 32 for consistency.
  const iree_elf32_ehdr_t* ehdr = (const iree_elf32_ehdr_t*)elf_data.data;
  static const iree_elf_byte_t elf_magic[4] = {0x7F, 'E', 'L', 'F'};
  if (memcmp(ehdr->e_ident, elf_magic, sizeof(elf_magic)) != 0) {
    return iree_make_status(
        IREE_STATUS_FAILED_PRECONDITION,
        "data provided does not contain the ELF identifier");
  }

  *out_osabi = ehdr->e_ident[IREE_ELF_EI_OSABI];
  *out_osabi_version = ehdr->e_ident[IREE_ELF_EI_ABIVERSION];
  *out_elf_class = ehdr->e_ident[IREE_ELF_EI_CLASS];
  *out_elf_data = ehdr->e_ident[IREE_ELF_EI_DATA];

  // Note machine is multibyte and respects the declared endianness.
  if (ehdr->e_ident[IREE_ELF_EI_DATA] == IREE_ELF_ELFDATA2LSB) {
    *out_machine = iree_unaligned_load_le_u16(&ehdr->e_machine);
  } else {
#if IREE_ENDIANNESS_BIG
// TODO(benvanik): helpers for big<->little endian
// *out_machine = iree_unaligned_load_be_u16(&ehdr->e_machine);
#error "ELF parsing support only available on little-endian systems today"
#endif  // IREE_ENDIANNESS_BIG
  }

  return iree_ok_status();
}

typedef struct {
  uint64_t offset;
  iree_file_contents_t* contents;
  iree_const_byte_span_t elf_data;
} fatelf_entry_t;

// Joins one or more ELF files together and writes the output to stdout.
static iree_status_t fatelf_join(int argc, char** argv) {
  IREE_SET_BINARY_MODE(stdout);  // ensure binary output mode

#if IREE_ENDIANNESS_BIG
#error "FatELF writing support only available on little-endian systems today"
#endif  // IREE_ENDIANNESS_BIG

  // Load all source files.
  iree_elf64_byte_t entry_count = argc;
  fatelf_entry_t* entries =
      (fatelf_entry_t*)iree_alloca(entry_count * sizeof(fatelf_entry_t));
  memset(entries, 0, entry_count * sizeof(*entries));
  for (iree_elf64_byte_t i = 0; i < entry_count; ++i) {
    IREE_RETURN_IF_ERROR(iree_file_read_contents(
        argv[i], iree_allocator_system(), &entries[i].contents));
    entries[i].elf_data = entries[i].contents->const_buffer;
  }

  // Compute offsets of all files based on their size and padding.
  uint64_t file_offset = iree_host_align(
      sizeof(iree_fatelf_header_t) + entry_count * sizeof(iree_fatelf_record_t),
      IREE_FATELF_PAGE_SIZE);
  for (iree_elf64_byte_t i = 0; i < entry_count; ++i) {
    entries[i].offset = file_offset;
    file_offset += iree_host_align(
        entries[i].contents->const_buffer.data_length, IREE_FATELF_PAGE_SIZE);
  }

  // Write header without records.
  iree_fatelf_header_t host_header = {
      .magic = IREE_FATELF_MAGIC,
      .version = IREE_FATELF_FORMAT_VERSION,
      .record_count = entry_count,
      .reserved = 0,
  };
  fwrite(&host_header, 1, sizeof(host_header), stdout);

  // Write all records.
  for (iree_elf64_byte_t i = 0; i < entry_count; ++i) {
    iree_elf64_half_t machine = 0;
    iree_elf64_byte_t osabi = 0;
    iree_elf64_byte_t osabi_version = 0;
    iree_elf64_byte_t elf_class = 0;
    iree_elf64_byte_t elf_data = 0;
    IREE_RETURN_IF_ERROR(
        fatelf_parse_elf_metadata(entries[i].elf_data, &machine, &osabi,
                                  &osabi_version, &elf_class, &elf_data));
    iree_fatelf_record_t host_record = {
        .machine = machine,
        .osabi = osabi,
        .osabi_version = osabi_version,
        .word_size = elf_class == IREE_ELF_ELFCLASS32
                         ? IREE_FATELF_WORD_SIZE_32
                         : IREE_FATELF_WORD_SIZE_64,
        .byte_order = elf_data == IREE_ELF_ELFDATA2LSB
                          ? IREE_FATELF_BYTE_ORDER_LSB
                          : IREE_FATELF_BYTE_ORDER_MSB,
        .reserved0 = 0,
        .reserved1 = 0,
        .offset = (iree_elf64_off_t)entries[i].offset,
        .size = (iree_elf64_xword_t)entries[i].elf_data.data_length,
    };
    fwrite(&host_record, 1, sizeof(host_record), stdout);
  }

  // Write all files, padding with zeros in-between as needed.
  uint64_t write_offset =
      sizeof(iree_fatelf_header_t) + entry_count * sizeof(iree_fatelf_record_t);
  for (iree_elf64_byte_t i = 0; i < entry_count; ++i) {
    uint64_t padding = entries[i].offset - write_offset;
    for (uint64_t i = 0; i < padding; ++i) fputc(0, stdout);
    write_offset += padding;
    if (write_offset != entries[i].offset) {
      return iree_make_status(IREE_STATUS_INTERNAL,
                              "actual offset does not match expected");
    }
    fwrite(entries[i].elf_data.data, 1, entries[i].elf_data.data_length,
           stdout);
    write_offset += entries[i].elf_data.data_length;
  }
  fflush(stdout);

  for (iree_elf64_byte_t i = 0; i < entry_count; ++i) {
    iree_file_contents_free(entries[i].contents);
  }
  return iree_ok_status();
}

static const char* fatelf_machine_id_str(iree_elf64_half_t value) {
  // TODO(benvanik): include a full table from the spec?
  // http://formats.kaitai.io/elf/ has a good source of canonical short names.
  // For now we just support what we have in our ELF loader.
  switch (value) {
    case 0x03:  // EM_386 / 3
      return "x86";
    case 0x28:  // EM_ARM / 40
      return "arm";
    case 0xB7:  // EM_AARCH64 / 183
      return "aarch64";
    case 0xF3:  // EM_RISCV / 243
      return "risvc";
    case 0x3E:  // EM_X86_64 / 62
      return "x86_64";
    default:
      return "unknown";
  }
}

static const char* fatelf_osabi_id_str(iree_elf64_byte_t value) {
  switch (value) {
    case IREE_ELF_ELFOSABI_NONE:
      return "none";
    case IREE_ELF_ELFOSABI_LINUX:
      return "linux";
    case IREE_ELF_ELFOSABI_STANDALONE:
      return "standalone";
    default:
      return "unknown";
  }
}

static const char* fatelf_word_size_id_str(iree_elf64_byte_t value) {
  switch (value) {
    case IREE_FATELF_WORD_SIZE_32:
      return "lp32";
    case IREE_FATELF_WORD_SIZE_64:
      return "lp64";
    default:
      return "lpUNK";
  }
}

static const char* fatelf_byte_order_id_str(iree_elf64_byte_t value) {
  switch (value) {
    case IREE_FATELF_BYTE_ORDER_MSB:
      return "be";
    case IREE_FATELF_BYTE_ORDER_LSB:
      return "le";
    default:
      return "xx";
  }
}

// Splits a FatELF into multiple files, writing each beside the input file.
static iree_status_t fatelf_split(int argc, char** argv) {
  iree_file_contents_t* fatelf_contents = NULL;
  IREE_RETURN_IF_ERROR(iree_file_read_contents(argv[0], iree_allocator_system(),
                                               &fatelf_contents));
  iree_fatelf_header_t* header = NULL;
  IREE_RETURN_IF_ERROR(fatelf_parse(fatelf_contents->const_buffer, &header));

  iree_string_view_t dirname, basename;
  iree_file_path_split(iree_make_cstring_view(argv[0]), &dirname, &basename);
  iree_string_view_t stem, extension;
  iree_file_path_split_basename(basename, &stem, &extension);

  for (iree_elf64_byte_t i = 0; i < header->record_count; ++i) {
    const iree_fatelf_record_t* record = &header->records[i];

    const char* machine_str = fatelf_machine_id_str(record->machine);
    const char* osabi_str = fatelf_osabi_id_str(record->osabi);
    const char* word_size_str = fatelf_word_size_id_str(record->word_size);
    const char* byte_order_str = fatelf_byte_order_id_str(record->byte_order);

    char record_path[2048];
    iree_host_size_t record_path_length =
        snprintf(record_path, IREE_ARRAYSIZE(record_path),
                 "%.*s%s%.*s.%s_%s_%s%s.so", (int)dirname.size, dirname.data,
                 dirname.size ? "/" : "", (int)stem.size, stem.data,
                 machine_str, osabi_str, word_size_str, byte_order_str);
    record_path_length =
        iree_file_path_canonicalize(record_path, record_path_length);

    fprintf(stdout, "Writing record[%d] to '%.*s'...\n", i,
            (int)record_path_length, record_path);

    iree_const_byte_span_t record_data = iree_make_const_byte_span(
        fatelf_contents->const_buffer.data + record->offset, record->size);
    IREE_RETURN_IF_ERROR(iree_file_write_contents(record_path, record_data));
  }

  fprintf(stdout, "Wrote %d records to %.*s!\n", header->record_count,
          (int)dirname.size, dirname.data);
  iree_allocator_free(iree_allocator_system(), header);
  iree_file_contents_free(fatelf_contents);
  return iree_ok_status();
}

// Selects the ELF matching the current host config from a FatELF and writes
// it to stdout.
static iree_status_t fatelf_select(int argc, char** argv) {
  IREE_SET_BINARY_MODE(stdout);  // ensure binary output mode
  iree_file_contents_t* fatelf_contents = NULL;
  IREE_RETURN_IF_ERROR(iree_file_read_contents(argv[0], iree_allocator_system(),
                                               &fatelf_contents));
  iree_const_byte_span_t elf_data = iree_const_byte_span_empty();
  IREE_RETURN_IF_ERROR(
      iree_fatelf_select(fatelf_contents->const_buffer, &elf_data));
  fwrite(elf_data.data, 1, elf_data.data_length, stdout);
  iree_file_contents_free(fatelf_contents);
  return iree_ok_status();
}

static const char* fatelf_word_size_enum_str(iree_elf64_byte_t value) {
  switch (value) {
    case IREE_FATELF_WORD_SIZE_32:
      return "ELFCLASS32";
    case IREE_FATELF_WORD_SIZE_64:
      return "ELFCLASS64";
    default:
      return "<unknown>";
  }
}

static const char* fatelf_byte_order_enum_str(iree_elf64_byte_t value) {
  switch (value) {
    case IREE_FATELF_BYTE_ORDER_MSB:
      return "ELFDATA2MSB (big-endian)";
    case IREE_FATELF_BYTE_ORDER_LSB:
      return "ELFDATA2LSB (little-endian)";
    default:
      return "<unknown>";
  }
}

// Dumps the FatELF file records.
static iree_status_t fatelf_dump(int argc, char** argv) {
  iree_file_contents_t* fatelf_contents = NULL;
  IREE_RETURN_IF_ERROR(iree_file_read_contents(argv[0], iree_allocator_system(),
                                               &fatelf_contents));
  iree_fatelf_header_t* header = NULL;
  IREE_RETURN_IF_ERROR(fatelf_parse(fatelf_contents->const_buffer, &header));

  fprintf(stdout, "iree_fatelf_header_t:\n");
  fprintf(stdout, "    magic: %" PRIX32 "\n", header->magic);
  fprintf(stdout, "  version: %d\n", header->version);
  fprintf(stdout, "  records: %d\n", header->record_count);
  fprintf(stdout, " reserved: %" PRIX8 "\n", header->reserved);
  fprintf(stdout, "\n");

  for (iree_elf64_byte_t i = 0; i < header->record_count; ++i) {
    const iree_fatelf_record_t* record = &header->records[i];
    fprintf(stdout, "iree_fatelf_record_t[%d]:\n", i);
    fprintf(stdout, "    machine: %d / %04X = %s\n", record->machine,
            record->machine, fatelf_machine_id_str(record->machine));
    fprintf(stdout, "      osabi: %d / %02X = %s\n", record->osabi,
            record->osabi, fatelf_osabi_id_str(record->osabi));
    fprintf(stdout, "    version: %d / %02X\n", record->osabi_version,
            record->osabi_version);
    fprintf(stdout, "  word_size: %d / %02X = %s\n", record->word_size,
            record->word_size, fatelf_word_size_enum_str(record->word_size));
    fprintf(stdout, " byte_order: %d / %02X = %s\n", record->byte_order,
            record->byte_order, fatelf_byte_order_enum_str(record->byte_order));
    fprintf(stdout, "  reserved0: %d / %02X\n", record->reserved0,
            record->reserved0);
    fprintf(stdout, "  reserved1: %d / %02X\n", record->reserved1,
            record->reserved1);
    fprintf(stdout, "     offset: %" PRIu64 " / %016" PRIX64 "\n",
            record->offset, record->offset);
    fprintf(stdout, "       size: %" PRIu64 " / %016" PRIX64 "\n", record->size,
            record->size);
    fprintf(stdout, "\n");
  }

  iree_allocator_free(iree_allocator_system(), header);
  iree_file_contents_free(fatelf_contents);
  return iree_ok_status();
}

int main(int argc, char** argv) {
  if (argc < 2) {
    return print_usage();
  }

  char* command = argv[1];
  int command_argc = argc - 2;
  char** command_argv = argv + 2;

  iree_status_t status = iree_ok_status();
  if (strcmp(command, "join") == 0) {
    if (command_argc < 1) return print_usage();
    status = fatelf_join(command_argc, command_argv);
  } else if (strcmp(command, "split") == 0) {
    if (command_argc != 1) return print_usage();
    status = fatelf_split(command_argc, command_argv);
  } else if (strcmp(command, "select") == 0) {
    if (command_argc != 1) return print_usage();
    status = fatelf_select(command_argc, command_argv);
  } else if (strcmp(command, "dump") == 0) {
    if (command_argc != 1) return print_usage();
    status = fatelf_dump(command_argc, command_argv);
  } else {
    return print_usage();
  }

  if (!iree_status_is_ok(status)) {
    fprintf(stderr, "iree-fatelf encountered error:\n");
    iree_status_fprint(stderr, status);
    iree_status_free(status);
    return 1;
  }
  return 0;
}
