//===-- DynamicLoaderMacOSXDYLD.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_DynamicLoaderMacOSXDYLD_h_
#define liblldb_DynamicLoaderMacOSXDYLD_h_

// C Includes
// C++ Includes
#include <vector>

// Other libraries and framework includes
// Project includes
#include "lldb/Target/DynamicLoader.h"
#include "lldb/Host/FileSpec.h"
#include "lldb/Core/StructuredData.h"
#include "lldb/Core/UUID.h"
#include "lldb/Host/Mutex.h"
#include "lldb/Target/Process.h"
#include "lldb/Utility/SafeMachO.h"

class DynamicLoaderMacOSXDYLD : public lldb_private::DynamicLoader
{
public:
    DynamicLoaderMacOSXDYLD(lldb_private::Process *process);

    ~DynamicLoaderMacOSXDYLD() override;

    //------------------------------------------------------------------
    // Static Functions
    //------------------------------------------------------------------
    static void
    Initialize();

    static void
    Terminate();

    static lldb_private::ConstString
    GetPluginNameStatic();

    static const char *
    GetPluginDescriptionStatic();

    static lldb_private::DynamicLoader *
    CreateInstance (lldb_private::Process *process, bool force);

    //------------------------------------------------------------------
    /// Called after attaching a process.
    ///
    /// Allow DynamicLoader plug-ins to execute some code after
    /// attaching to a process.
    //------------------------------------------------------------------
    void
    DidAttach() override;

    void
    DidLaunch() override;

    bool
    ProcessDidExec() override;

    lldb::ThreadPlanSP
    GetStepThroughTrampolinePlan(lldb_private::Thread &thread,
                                 bool stop_others) override;

    size_t
    FindEquivalentSymbols(lldb_private::Symbol *original_symbol,
                          lldb_private::ModuleList &module_list,
                          lldb_private::SymbolContextList &equivalent_symbols) override;
    
    lldb_private::Error
    CanLoadImage() override;

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

    uint32_t
    GetPluginVersion() override;

    bool
    AlwaysRelyOnEHUnwindInfo(lldb_private::SymbolContext &sym_ctx) override;

protected:
    void
    PrivateInitialize (lldb_private::Process *process);

    void
    PrivateProcessStateChanged (lldb_private::Process *process,
                                lldb::StateType state);

    bool
    LocateDYLD ();

    bool
    DidSetNotificationBreakpoint () const;

    void
    Clear (bool clear_process);

    void
    PutToLog (lldb_private::Log *log) const;

    bool
    ReadDYLDInfoFromMemoryAndSetNotificationCallback (lldb::addr_t addr);

    static bool
    NotifyBreakpointHit (void *baton,
                         lldb_private::StoppointCallbackContext *context,
                         lldb::user_id_t break_id,
                         lldb::user_id_t break_loc_id);

    uint32_t
    AddrByteSize();

    static lldb::ByteOrder
    GetByteOrderFromMagic (uint32_t magic);

    bool
    ReadMachHeader (lldb::addr_t addr,
                    llvm::MachO::mach_header *header,
                    lldb_private::DataExtractor *load_command_data);

    class Segment
    {
    public:
        Segment() :
            name(),
            vmaddr(LLDB_INVALID_ADDRESS),
            vmsize(0),
            fileoff(0),
            filesize(0),
            maxprot(0),
            initprot(0),
            nsects(0),
            flags(0)
        {
        }

        lldb_private::ConstString name;
        lldb::addr_t vmaddr;
        lldb::addr_t vmsize;
        lldb::addr_t fileoff;
        lldb::addr_t filesize;
        uint32_t maxprot;
        uint32_t initprot;
        uint32_t nsects;
        uint32_t flags;

        bool
        operator==(const Segment& rhs) const
        {
            return name == rhs.name && vmaddr == rhs.vmaddr && vmsize == rhs.vmsize;
        }

        void
        PutToLog (lldb_private::Log *log,
                  lldb::addr_t slide) const;

    };

    struct DYLDImageInfo
    {
        lldb::addr_t address;               // Address of mach header for this dylib
        lldb::addr_t slide;                 // The amount to slide all segments by if there is a global slide.
        lldb::addr_t mod_date;              // Modification date for this dylib
        lldb_private::FileSpec file_spec;   // Resolved path for this dylib
        lldb_private::UUID uuid;            // UUID for this dylib if it has one, else all zeros
        llvm::MachO::mach_header header;    // The mach header for this image
        std::vector<Segment> segments;      // All segment vmaddr and vmsize pairs for this executable (from memory of inferior)
        uint32_t load_stop_id;              // The process stop ID that the sections for this image were loaded

        DYLDImageInfo() :
            address(LLDB_INVALID_ADDRESS),
            slide(0),
            mod_date(0),
            file_spec(),
            uuid(),
            header(),
            segments(),
            load_stop_id(0)
        {
        }

        void
        Clear(bool load_cmd_data_only)
        {
            if (!load_cmd_data_only)
            {
                address = LLDB_INVALID_ADDRESS;
                slide = 0;
                mod_date = 0;
                file_spec.Clear();
                ::memset (&header, 0, sizeof(header));
            }
            uuid.Clear();
            segments.clear();
            load_stop_id = 0;
        }

        bool
        operator == (const DYLDImageInfo& rhs) const
        {
            return  address == rhs.address
                && slide == rhs.slide
                && mod_date == rhs.mod_date
                && file_spec == rhs.file_spec
                && uuid == rhs.uuid
                && memcmp(&header, &rhs.header, sizeof(header)) == 0
                && segments == rhs.segments;
        }

        bool
        UUIDValid() const
        {
            return uuid.IsValid();
        }

        uint32_t
        GetAddressByteSize ()
        {
            if (header.cputype)
            {
                if (header.cputype & llvm::MachO::CPU_ARCH_ABI64)
                    return 8;
                else
                    return 4;
            }
            return 0;
        }

        lldb::ByteOrder
        GetByteOrder();

        lldb_private::ArchSpec
        GetArchitecture () const
        {
            return lldb_private::ArchSpec (lldb_private::eArchTypeMachO, header.cputype, header.cpusubtype);
        }

        const Segment *
        FindSegment (const lldb_private::ConstString &name) const;

        void
        PutToLog (lldb_private::Log *log) const;

        typedef std::vector<DYLDImageInfo> collection;
        typedef collection::iterator iterator;
        typedef collection::const_iterator const_iterator;
    };

    struct DYLDAllImageInfos
    {
        uint32_t version;
        uint32_t dylib_info_count;              // Version >= 1
        lldb::addr_t dylib_info_addr;           // Version >= 1
        lldb::addr_t notification;              // Version >= 1
        bool processDetachedFromSharedRegion;   // Version >= 1
        bool libSystemInitialized;              // Version >= 2
        lldb::addr_t dyldImageLoadAddress;      // Version >= 2

        DYLDAllImageInfos() :
            version (0),
            dylib_info_count (0),
            dylib_info_addr (LLDB_INVALID_ADDRESS),
            notification (LLDB_INVALID_ADDRESS),
            processDetachedFromSharedRegion (false),
            libSystemInitialized (false),
            dyldImageLoadAddress (LLDB_INVALID_ADDRESS)
        {
        }

        void
        Clear()
        {
            version = 0;
            dylib_info_count = 0;
            dylib_info_addr = LLDB_INVALID_ADDRESS;
            notification = LLDB_INVALID_ADDRESS;
            processDetachedFromSharedRegion = false;
            libSystemInitialized = false;
            dyldImageLoadAddress = LLDB_INVALID_ADDRESS;
        }

        bool
        IsValid() const
        {
            return version >= 1 || version <= 6;
        }
    };

    void
    RegisterNotificationCallbacks();

    void
    UnregisterNotificationCallbacks();

    uint32_t
    ParseLoadCommands (const lldb_private::DataExtractor& data,
                       DYLDImageInfo& dylib_info,
                       lldb_private::FileSpec *lc_id_dylinker);

    bool
    UpdateImageLoadAddress(lldb_private::Module *module,
                           DYLDImageInfo& info);

    bool
    UnloadImageLoadAddress (lldb_private::Module *module,
                            DYLDImageInfo& info);

    lldb::ModuleSP
    FindTargetModuleForDYLDImageInfo (DYLDImageInfo &image_info,
                                      bool can_create,
                                      bool *did_create_ptr);

    DYLDImageInfo *
    GetImageInfo (lldb_private::Module *module);

    bool
    NeedToLocateDYLD () const;

    bool
    SetNotificationBreakpoint ();

    // There is a little tricky bit where you might initially attach while dyld is updating
    // the all_image_infos, and you can't read the infos, so you have to continue and pick it
    // up when you hit the update breakpoint.  At that point, you need to run this initialize
    // function, but when you do it that way you DON'T need to do the extra work you would at
    // the breakpoint.
    // So this function will only do actual work if the image infos haven't been read yet.
    // If it does do any work, then it will return true, and false otherwise.  That way you can
    // call it in the breakpoint action, and if it returns true you're done.
    bool
    InitializeFromAllImageInfos ();

    bool
    ReadAllImageInfosStructure ();
    
    bool
    AddModulesUsingInfosFromDebugserver (lldb_private::StructuredData::ObjectSP image_details, DYLDImageInfo::collection &image_infos);

    bool
    AddModulesUsingImageInfosAddress (lldb::addr_t image_infos_addr, uint32_t image_infos_count);
    
    bool
    AddModulesUsingImageInfos (DYLDImageInfo::collection &image_infos);
    
    bool
    RemoveModulesUsingImageInfosAddress (lldb::addr_t image_infos_addr, uint32_t image_infos_count);

    void
    UpdateImageInfosHeaderAndLoadCommands(DYLDImageInfo::collection &image_infos, 
                                          uint32_t infos_count, 
                                          bool update_executable);

    bool
    ReadImageInfos (lldb::addr_t image_infos_addr, 
                    uint32_t image_infos_count, 
                    DYLDImageInfo::collection &image_infos);


    DYLDImageInfo m_dyld;               // Info about the current dyld being used
    lldb::ModuleWP m_dyld_module_wp;
    lldb::addr_t m_dyld_all_image_infos_addr;
    DYLDAllImageInfos m_dyld_all_image_infos;
    uint32_t m_dyld_all_image_infos_stop_id;
    lldb::user_id_t m_break_id;
    DYLDImageInfo::collection m_dyld_image_infos;   // Current shared libraries information
    uint32_t m_dyld_image_infos_stop_id;    // The process stop ID that "m_dyld_image_infos" is valid for
    mutable lldb_private::Mutex m_mutex;
    lldb_private::Process::Notifications m_notification_callbacks;
    bool m_process_image_addr_is_all_images_infos;

private:
    DISALLOW_COPY_AND_ASSIGN (DynamicLoaderMacOSXDYLD);
};

#endif // liblldb_DynamicLoaderMacOSXDYLD_h_
