//===-- ObjectFileELF.h --------------------------------------- -*- C++ -*-===//
//
//                     The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//

#ifndef liblldb_ObjectFileELF_h_
#define liblldb_ObjectFileELF_h_

#include <stdint.h>
#include <vector>

#include "lldb/lldb-private.h"
#include "lldb/Host/FileSpec.h"
#include "lldb/Symbol/ObjectFile.h"
#include "lldb/Core/UUID.h"
#include "lldb/Core/ArchSpec.h"

#include "ELFHeader.h"

struct ELFNote
{
    elf::elf_word n_namesz;
    elf::elf_word n_descsz;
    elf::elf_word n_type;

    std::string n_name;

    ELFNote() : n_namesz(0), n_descsz(0), n_type(0)
    {
    }

    /// Parse an ELFNote entry from the given DataExtractor starting at position
    /// \p offset.
    ///
    /// @param[in] data
    ///    The DataExtractor to read from.
    ///
    /// @param[in,out] offset
    ///    Pointer to an offset in the data.  On return the offset will be
    ///    advanced by the number of bytes read.
    ///
    /// @return
    ///    True if the ELFRel entry was successfully read and false otherwise.
    bool
    Parse(const lldb_private::DataExtractor &data, lldb::offset_t *offset);
};

//------------------------------------------------------------------------------
/// @class ObjectFileELF
/// @brief Generic ELF object file reader.
///
/// This class provides a generic ELF (32/64 bit) reader plugin implementing the
/// ObjectFile protocol.
class ObjectFileELF :
    public lldb_private::ObjectFile
{
public:
    //------------------------------------------------------------------
    // Static Functions
    //------------------------------------------------------------------
    static void
    Initialize();

    static void
    Terminate();

    static lldb_private::ConstString
    GetPluginNameStatic();

    static const char *
    GetPluginDescriptionStatic();

    static lldb_private::ObjectFile *
    CreateInstance(const lldb::ModuleSP &module_sp,
                   lldb::DataBufferSP& data_sp,
                   lldb::offset_t data_offset,
                   const lldb_private::FileSpec* file,
                   lldb::offset_t file_offset,
                   lldb::offset_t length);

    static lldb_private::ObjectFile *
    CreateMemoryInstance (const lldb::ModuleSP &module_sp, 
                          lldb::DataBufferSP& data_sp, 
                          const lldb::ProcessSP &process_sp, 
                          lldb::addr_t header_addr);

    static size_t
    GetModuleSpecifications (const lldb_private::FileSpec& file,
                             lldb::DataBufferSP& data_sp,
                             lldb::offset_t data_offset,
                             lldb::offset_t file_offset,
                             lldb::offset_t length,
                             lldb_private::ModuleSpecList &specs);

    static bool
    MagicBytesMatch (lldb::DataBufferSP& data_sp,
                     lldb::addr_t offset, 
                     lldb::addr_t length);

    //------------------------------------------------------------------
    // PluginInterface protocol
    //------------------------------------------------------------------
    lldb_private::ConstString
    GetPluginName() override;

    uint32_t
    GetPluginVersion() override;

    //------------------------------------------------------------------
    // ObjectFile Protocol.
    //------------------------------------------------------------------
    virtual
    ~ObjectFileELF();

    bool
    ParseHeader() override;

    bool
    SetLoadAddress (lldb_private::Target &target,
                    lldb::addr_t value,
                    bool value_is_offset) override;

    lldb::ByteOrder
    GetByteOrder() const override;

    bool
    IsExecutable () const override;

    uint32_t
    GetAddressByteSize() const override;

    lldb::AddressClass
    GetAddressClass (lldb::addr_t file_addr) override;

    lldb_private::Symtab *
    GetSymtab() override;

    lldb_private::Symbol *
    ResolveSymbolForAddress(const lldb_private::Address& so_addr, bool verify_unique) override;

    bool
    IsStripped () override;

    void
    CreateSections (lldb_private::SectionList &unified_section_list) override;

    void
    Dump(lldb_private::Stream *s) override;

    bool
    GetArchitecture (lldb_private::ArchSpec &arch) override;

    bool
    GetUUID(lldb_private::UUID* uuid) override;

    lldb_private::FileSpecList
    GetDebugSymbolFilePaths() override;

    uint32_t
    GetDependentModules(lldb_private::FileSpecList& files) override;

    lldb_private::Address
    GetImageInfoAddress(lldb_private::Target *target) override;
    
    lldb_private::Address
    GetEntryPointAddress () override;
    
    ObjectFile::Type
    CalculateType() override;
    
    ObjectFile::Strata
    CalculateStrata() override;

    // Returns number of program headers found in the ELF file.
    size_t
    GetProgramHeaderCount();

    // Returns the program header with the given index.
    const elf::ELFProgramHeader *
    GetProgramHeaderByIndex(lldb::user_id_t id);

    // Returns segment data for the given index.
    lldb_private::DataExtractor
    GetSegmentDataByIndex(lldb::user_id_t id);

    std::string
    StripLinkerSymbolAnnotations(llvm::StringRef symbol_name) const override;

private:
    ObjectFileELF(const lldb::ModuleSP &module_sp,
                  lldb::DataBufferSP& data_sp,
                  lldb::offset_t data_offset,
                  const lldb_private::FileSpec* file,
                  lldb::offset_t offset,
                  lldb::offset_t length);

    ObjectFileELF (const lldb::ModuleSP &module_sp,
                   lldb::DataBufferSP& header_data_sp,
                   const lldb::ProcessSP &process_sp,
                   lldb::addr_t header_addr);

    typedef std::vector<elf::ELFProgramHeader>  ProgramHeaderColl;
    typedef ProgramHeaderColl::iterator         ProgramHeaderCollIter;
    typedef ProgramHeaderColl::const_iterator   ProgramHeaderCollConstIter;

    struct ELFSectionHeaderInfo : public elf::ELFSectionHeader
    {
        lldb_private::ConstString section_name;
    };
    typedef std::vector<ELFSectionHeaderInfo>   SectionHeaderColl;
    typedef SectionHeaderColl::iterator         SectionHeaderCollIter;
    typedef SectionHeaderColl::const_iterator   SectionHeaderCollConstIter;

    typedef std::vector<elf::ELFDynamic>        DynamicSymbolColl;
    typedef DynamicSymbolColl::iterator         DynamicSymbolCollIter;
    typedef DynamicSymbolColl::const_iterator   DynamicSymbolCollConstIter;

    typedef std::map<lldb::addr_t, lldb::AddressClass> FileAddressToAddressClassMap;

    /// Version of this reader common to all plugins based on this class.
    static const uint32_t m_plugin_version = 1;
    static const uint32_t g_core_uuid_magic;

    /// ELF file header.
    elf::ELFHeader m_header;

    /// ELF build ID.
    lldb_private::UUID m_uuid;

    /// ELF .gnu_debuglink file and crc data if available.
    std::string m_gnu_debuglink_file;
    uint32_t m_gnu_debuglink_crc;

    /// Collection of program headers.
    ProgramHeaderColl m_program_headers;

    /// Collection of section headers.
    SectionHeaderColl m_section_headers;

    /// Collection of symbols from the dynamic table.
    DynamicSymbolColl m_dynamic_symbols;

    /// List of file specifications corresponding to the modules (shared
    /// libraries) on which this object file depends.
    mutable std::unique_ptr<lldb_private::FileSpecList> m_filespec_ap;

    /// Cached value of the entry point for this module.
    lldb_private::Address  m_entry_point_address;

    /// The architecture detected from parsing elf file contents.
    lldb_private::ArchSpec m_arch_spec;

    /// The address class for each symbol in the elf file
    FileAddressToAddressClassMap m_address_class_map;

    /// Returns a 1 based index of the given section header.
    size_t
    SectionIndex(const SectionHeaderCollIter &I);

    /// Returns a 1 based index of the given section header.
    size_t
    SectionIndex(const SectionHeaderCollConstIter &I) const;

    // Parses the ELF program headers.
    static size_t
    GetProgramHeaderInfo(ProgramHeaderColl &program_headers,
                         lldb_private::DataExtractor &data,
                         const elf::ELFHeader &header);

    // Finds PT_NOTE segments and calculates their crc sum.
    static uint32_t
    CalculateELFNotesSegmentsCRC32(const ProgramHeaderColl& program_headers,
                                   lldb_private::DataExtractor &data);

    /// Parses all section headers present in this object file and populates
    /// m_program_headers.  This method will compute the header list only once.
    /// Returns the number of headers parsed.
    size_t
    ParseProgramHeaders();

    /// Parses all section headers present in this object file and populates
    /// m_section_headers.  This method will compute the header list only once.
    /// Returns the number of headers parsed.
    size_t
    ParseSectionHeaders();

    /// Parses the elf section headers and returns the uuid, debug link name, crc, archspec.
    static size_t
    GetSectionHeaderInfo(SectionHeaderColl &section_headers,
                         lldb_private::DataExtractor &data,
                         const elf::ELFHeader &header,
                         lldb_private::UUID &uuid,
                         std::string &gnu_debuglink_file,
                         uint32_t &gnu_debuglink_crc,
                         lldb_private::ArchSpec &arch_spec);

    /// Scans the dynamic section and locates all dependent modules (shared
    /// libraries) populating m_filespec_ap.  This method will compute the
    /// dependent module list only once.  Returns the number of dependent
    /// modules parsed.
    size_t
    ParseDependentModules();

    /// Parses the dynamic symbol table and populates m_dynamic_symbols.  The
    /// vector retains the order as found in the object file.  Returns the
    /// number of dynamic symbols parsed.
    size_t
    ParseDynamicSymbols();

    /// Populates m_symtab_ap will all non-dynamic linker symbols.  This method
    /// will parse the symbols only once.  Returns the number of symbols parsed.
    unsigned
    ParseSymbolTable(lldb_private::Symtab *symbol_table,
                     lldb::user_id_t start_id,
                     lldb_private::Section *symtab);

    /// Helper routine for ParseSymbolTable().
    unsigned
    ParseSymbols(lldb_private::Symtab *symbol_table, 
                 lldb::user_id_t start_id,
                 lldb_private::SectionList *section_list,
                 const size_t num_symbols,
                 const lldb_private::DataExtractor &symtab_data,
                 const lldb_private::DataExtractor &strtab_data);

    /// Scans the relocation entries and adds a set of artificial symbols to the
    /// given symbol table for each PLT slot.  Returns the number of symbols
    /// added.
    unsigned
    ParseTrampolineSymbols(lldb_private::Symtab *symbol_table, 
                           lldb::user_id_t start_id,
                           const ELFSectionHeaderInfo *rela_hdr,
                           lldb::user_id_t section_id);

    /// Relocates debug sections
    unsigned
    RelocateDebugSections(const elf::ELFSectionHeader *rel_hdr, lldb::user_id_t rel_id);

    unsigned
    RelocateSection(lldb_private::Symtab* symtab, const elf::ELFHeader *hdr, const elf::ELFSectionHeader *rel_hdr,
                    const elf::ELFSectionHeader *symtab_hdr, const elf::ELFSectionHeader *debug_hdr,
                    lldb_private::DataExtractor &rel_data, lldb_private::DataExtractor &symtab_data,
                    lldb_private::DataExtractor &debug_data, lldb_private::Section* rel_section);

    /// Loads the section name string table into m_shstr_data.  Returns the
    /// number of bytes constituting the table.
    size_t
    GetSectionHeaderStringTable();

    /// Utility method for looking up a section given its name.  Returns the
    /// index of the corresponding section or zero if no section with the given
    /// name can be found (note that section indices are always 1 based, and so
    /// section index 0 is never valid).
    lldb::user_id_t
    GetSectionIndexByName(const char *name);

    // Returns the ID of the first section that has the given type.
    lldb::user_id_t
    GetSectionIndexByType(unsigned type);

    /// Returns the section header with the given id or NULL.
    const ELFSectionHeaderInfo *
    GetSectionHeaderByIndex(lldb::user_id_t id);

    /// @name  ELF header dump routines
    //@{
    static void
    DumpELFHeader(lldb_private::Stream *s, const elf::ELFHeader& header);

    static void
    DumpELFHeader_e_ident_EI_DATA(lldb_private::Stream *s,
                                  unsigned char ei_data);

    static void
    DumpELFHeader_e_type(lldb_private::Stream *s, elf::elf_half e_type);
    //@}

    /// @name ELF program header dump routines
    //@{
    void
    DumpELFProgramHeaders(lldb_private::Stream *s);

    static void
    DumpELFProgramHeader(lldb_private::Stream *s, 
                         const elf::ELFProgramHeader &ph);

    static void
    DumpELFProgramHeader_p_type(lldb_private::Stream *s, elf::elf_word p_type);

    static void
    DumpELFProgramHeader_p_flags(lldb_private::Stream *s, 
                                 elf::elf_word p_flags);
    //@}

    /// @name ELF section header dump routines
    //@{
    void
    DumpELFSectionHeaders(lldb_private::Stream *s);

    static void
    DumpELFSectionHeader(lldb_private::Stream *s, 
                         const ELFSectionHeaderInfo& sh);

    static void
    DumpELFSectionHeader_sh_type(lldb_private::Stream *s, 
                                 elf::elf_word sh_type);

    static void
    DumpELFSectionHeader_sh_flags(lldb_private::Stream *s, 
                                  elf::elf_xword sh_flags);
    //@}

    /// ELF dependent module dump routine.
    void
    DumpDependentModules(lldb_private::Stream *s);

    const elf::ELFDynamic *
    FindDynamicSymbol(unsigned tag);
        
    unsigned
    PLTRelocationType();

    static lldb_private::Error
    RefineModuleDetailsFromNote (lldb_private::DataExtractor &data, lldb_private::ArchSpec &arch_spec, lldb_private::UUID &uuid);
};

#endif // #ifndef liblldb_ObjectFileELF_h_
