//===------- EHFrameSupportImpl.h - JITLink eh-frame utils ------*- C++ -*-===//
//
// Part of the LLVM Project, 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
//
//===----------------------------------------------------------------------===//
//
// EHFrame registration support for JITLink.
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_LIB_EXECUTIONENGINE_JITLINK_EHFRAMESUPPORTIMPL_H
#define LLVM_LIB_EXECUTIONENGINE_JITLINK_EHFRAMESUPPORTIMPL_H

#include "llvm/ExecutionEngine/JITLink/EHFrameSupport.h"

#include "llvm/ExecutionEngine/JITLink/JITLink.h"
#include "llvm/Support/BinaryStreamReader.h"

namespace llvm {
namespace jitlink {

/// A LinkGraph pass that adds missing FDE-to-CIE, FDE-to-PC and FDE-to-LSDA
/// edges.
class EHFrameEdgeFixer {
public:
  /// Create an eh-frame edge fixer.
  /// Adds edges for implicit relocations on platforms where these are used
  /// (e.g. MachO/x86-64).
  ///
  /// If a given edge-kind is not supported on the target architecture then
  /// Edge::Invalid should be used.
  EHFrameEdgeFixer(StringRef EHFrameSectionName, unsigned PointerSize,
                   Edge::Kind Pointer32, Edge::Kind Pointer64,
                   Edge::Kind Delta32, Edge::Kind Delta64,
                   Edge::Kind NegDelta32);
  Error operator()(LinkGraph &G);

private:

  struct AugmentationInfo {
    bool AugmentationDataPresent = false;
    bool EHDataFieldPresent = false;
    uint8_t Fields[4] = {0x0, 0x0, 0x0, 0x0};
  };

  struct CIEInformation {
    CIEInformation() = default;
    CIEInformation(Symbol &CIESymbol) : CIESymbol(&CIESymbol) {}
    Symbol *CIESymbol = nullptr;
    bool AugmentationDataPresent = false;
    bool LSDAPresent = false;
    uint8_t LSDAEncoding = 0;
    uint8_t AddressEncoding = 0;
  };

  struct EdgeTarget {
    EdgeTarget() = default;
    EdgeTarget(const Edge &E) : Target(&E.getTarget()), Addend(E.getAddend()) {}

    Symbol *Target = nullptr;
    Edge::AddendT Addend = 0;
  };

  struct BlockEdgesInfo {
    DenseMap<Edge::OffsetT, EdgeTarget> TargetMap;
    DenseSet<Edge::OffsetT> Multiple;
  };

  using CIEInfosMap = DenseMap<orc::ExecutorAddr, CIEInformation>;

  struct ParseContext {
    ParseContext(LinkGraph &G) : G(G) {}

    Expected<CIEInformation *> findCIEInfo(orc::ExecutorAddr Address) {
      auto I = CIEInfos.find(Address);
      if (I == CIEInfos.end())
        return make_error<JITLinkError>("No CIE found at address " +
                                        formatv("{0:x16}", Address));
      return &I->second;
    }

    LinkGraph &G;
    CIEInfosMap CIEInfos;
    BlockAddressMap AddrToBlock;
    DenseMap<orc::ExecutorAddr, Symbol *> AddrToSym;
  };

  Error processBlock(ParseContext &PC, Block &B);
  Error processCIE(ParseContext &PC, Block &B, size_t CIEDeltaFieldOffset,
                   const BlockEdgesInfo &BlockEdges);
  Error processFDE(ParseContext &PC, Block &B, size_t CIEDeltaFieldOffset,
                   uint32_t CIEDelta, const BlockEdgesInfo &BlockEdges);

  Expected<AugmentationInfo>
  parseAugmentationString(BinaryStreamReader &RecordReader);

  Expected<uint8_t> readPointerEncoding(BinaryStreamReader &RecordReader,
                                        Block &InBlock, const char *FieldName);
  Error skipEncodedPointer(uint8_t PointerEncoding,
                           BinaryStreamReader &RecordReader);
  Expected<Symbol *> getOrCreateEncodedPointerEdge(
      ParseContext &PC, const BlockEdgesInfo &BlockEdges,
      uint8_t PointerEncoding, BinaryStreamReader &RecordReader,
      Block &BlockToFix, size_t PointerFieldOffset, const char *FieldName);

  Expected<Symbol &> getOrCreateSymbol(ParseContext &PC,
                                       orc::ExecutorAddr Addr);

  StringRef EHFrameSectionName;
  unsigned PointerSize;
  Edge::Kind Pointer32;
  Edge::Kind Pointer64;
  Edge::Kind Delta32;
  Edge::Kind Delta64;
  Edge::Kind NegDelta32;
};

/// Add a 32-bit null-terminator to the end of the eh-frame section.
class EHFrameNullTerminator {
public:
  EHFrameNullTerminator(StringRef EHFrameSectionName);
  Error operator()(LinkGraph &G);

private:
  static char NullTerminatorBlockContent[];
  StringRef EHFrameSectionName;
};

} // end namespace jitlink
} // end namespace llvm

#endif // LLVM_LIB_EXECUTIONENGINE_JITLINK_EHFRAMESUPPORTIMPL_H
