/*
 * Copyright 2017, Data61, CSIRO (ABN 41 687 119 230)
 *
 * SPDX-License-Identifier: BSD-2-Clause
 */
#pragma once

#include <autoconf.h>
#include <sel4utils/gen_config.h>

#include <vka/vka.h>

#include <vspace/vspace.h>
#include <elf/elf.h>

#if CONFIG_WORD_SIZE == 64
#define Elf_Phdr Elf64_Phdr
#elif CONFIG_WORD_SIZE == 32
#define Elf_Phdr Elf32_Phdr
#else
#error "Word size unsupported"
#endif /* CONFIG_WORD_SIZE */


typedef struct sel4utils_elf_region {
    seL4_CapRights_t rights;
    /* These two vstarts may differ if the elf was not mapped 1to1. Such an elf is not
     * runnable, but allows it to be loaded into a vspace where it is not intended to be run.
     * This is also as reported by the elf file. */
    void *elf_vstart;
    /* Start of the reservation. This will be 4k aligned */
    void *reservation_vstart;
    /* Size of the elf segment as reported by elf file */
    uint32_t size;
    /* Size of the reservation.  This will be a multple of 4k */
    size_t reservation_size;
    reservation_t reservation;
    int cacheable;
    /* Index of this elf segment in the section header */
    int segment_index;
} sel4utils_elf_region_t;

/**
 * Load an elf file into a vspace.
 *
 * The loader vspace and vka allocation will be preserved (no extra cslots or objects or vaddrs
 * will leak from this function), even in the case of an error.
 *
 * The loadee vspace and vka will alter: cslots will be allocated for each frame to be
 * mapped into the address space and frames will be allocated. In case of failure the entire
 * virtual address space is left in the state where it failed.
 *
 * @param loadee the vspace to load the elf file into
 * @param loader the vspace we are loading from
 * @param loadee_vka allocator to use for allocation in the loadee vspace
 * @param loader_vka allocator to use for loader vspace. Can be the same as loadee_vka.
 * @param image_name name of the image in the cpio archive to load.
 * @param regions Optional array for list of regions to be placed. Assumed to be the correct
                  size as reported by a call to sel4utils_elf_num_regions
 * @param mapanywhere If true allows the elf to be loaded anywhere in the vspace. Regions will
                      still be contiguous
 *
 * @return The entry point of the new process, NULL on error
 */
void *
sel4utils_elf_load_record_regions(vspace_t *loadee, vspace_t *loader, vka_t *loadee_vka,
                                  vka_t *loader_vka, elf_t *elf, sel4utils_elf_region_t *regions, int mapanywhere);

/**
 * Wrapper for sel4utils_elf_load_record_regions. Does not record/perform reservations and
 * maps into the correct virtual addresses
 *
 * @param loadee the vspace to load the elf file into
 * @param loader the vspace we are loading from
 * @param loadee_vka allocator to use for allocation in the loadee vspace
 * @param loader_vka allocator to use for loader vspace. Can be the same as loadee_vka.
 * @param image_name name of the image in the cpio archive to load.
 *
 * @return The entry point of the new process, NULL on error
 */
void *
sel4utils_elf_load(vspace_t *loadee, vspace_t *loader, vka_t *loadee_vka,
                   vka_t *loader_vka, elf_t *elf);

/**
 * Parses an elf file but does not actually load it. Merely reserves the regions in the vspace
 * for where the elf segments would go. This is used for lazy loading / copy on write

 * @param loadee the vspace to reserve the elf regions in
 * @param image_name name of the image in the cpio archive to parse.
 * @param regions Array for list of regions to be placed. Assumed to be the correct
                  size as reported by a call to sel4utils_elf_num_regions
 *
 * @return The entry point of the elf, NULL on error
 */
void *
sel4utils_elf_reserve(vspace_t *loadee, elf_t *elf, sel4utils_elf_region_t *regions);

/**
 * Parses an elf file and returns the number of loadable regions. The result of this
 * is used to calculate the number of regions to pass to sel4utils_elf_reserve and
 * sel4utils_elf_load_record_regions
 *
 * @param image_name name of the image in the cpio archive to inspect
 * @return Number of loadable regions in the elf
 */
int
sel4utils_elf_num_regions(elf_t *elf);

/**
 * Looks for the __vsyscall section in an elf file and returns the value. This
 * is used to set the __sysinfo value when launching the elf
 *
 * @param image_name name of the image in the cpio archive to inspect
 *
 * @return Address of vsyscall function or 0 if not found
 */
uintptr_t sel4utils_elf_get_vsyscall(elf_t *elf);

/**
 * Finds the section_name section in an elf file and returns the address.
 *
 * @param image_name name of the image in the cpio archive to inspect
 *
 * @param section_name name of the section to find
 *
 * @param section_size optional pointer to uint64_t to return the section size
 *
 * @return Address of section or 0 if not found
 */
uintptr_t sel4utils_elf_get_section(elf_t *elf, const char *section_name, uint64_t *section_size);

/**
 * Parses an elf file and returns the number of phdrs. The result of this
 * can be used prior to a call to sel4utils_elf_read_phdrs
 *
 * @param image_name name of the image in the cpio archive to inspect
 * @return Number of phdrs in the elf
 */
uint32_t sel4utils_elf_num_phdrs(elf_t *elf);

/**
 * Parse an elf file and retrieve all the phdrs
 *
 * @param image_name name of the image in the cpio archive to inspect
 * @param max_phdrs Maximum number of phdrs to retrieve
 * @param phdrs Array to store the loaded phdrs into
 *
 * @return Number of phdrs retrieved
 */
void sel4utils_elf_read_phdrs(elf_t *elf, size_t max_phdrs, Elf_Phdr *phdrs);

