//===- CompileUtils.h - Utilities for compiling IR in the JIT ---*- 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
//
//===----------------------------------------------------------------------===//
//
// Contains utilities for compiling IR to object files.
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_EXECUTIONENGINE_ORC_COMPILEUTILS_H
#define LLVM_EXECUTIONENGINE_ORC_COMPILEUTILS_H

#include "llvm/ADT/SmallVector.h"
#include "llvm/ExecutionEngine/ObjectCache.h"
#include "llvm/ExecutionEngine/Orc/JITTargetMachineBuilder.h"
#include "llvm/IR/LegacyPassManager.h"
#include "llvm/Object/Binary.h"
#include "llvm/Object/ObjectFile.h"
#include "llvm/Support/Error.h"
#include "llvm/Support/ErrorHandling.h"
#include "llvm/Support/MemoryBuffer.h"
#include "llvm/Support/SmallVectorMemoryBuffer.h"
#include "llvm/Support/raw_ostream.h"
#include "llvm/Target/TargetMachine.h"
#include <algorithm>
#include <memory>

namespace llvm {

class MCContext;
class Module;

namespace orc {

/// Simple compile functor: Takes a single IR module and returns an ObjectFile.
/// This compiler supports a single compilation thread and LLVMContext only.
/// For multithreaded compilation, use ConcurrentIRCompiler below.
class SimpleCompiler {
public:
  using CompileResult = std::unique_ptr<MemoryBuffer>;

  /// Construct a simple compile functor with the given target.
  SimpleCompiler(TargetMachine &TM, ObjectCache *ObjCache = nullptr)
    : TM(TM), ObjCache(ObjCache) {}

  /// Set an ObjectCache to query before compiling.
  void setObjectCache(ObjectCache *NewCache) { ObjCache = NewCache; }

  /// Compile a Module to an ObjectFile.
  CompileResult operator()(Module &M) {
    CompileResult CachedObject = tryToLoadFromObjectCache(M);
    if (CachedObject)
      return CachedObject;

    SmallVector<char, 0> ObjBufferSV;

    {
      raw_svector_ostream ObjStream(ObjBufferSV);

      legacy::PassManager PM;
      MCContext *Ctx;
      if (TM.addPassesToEmitMC(PM, Ctx, ObjStream))
        llvm_unreachable("Target does not support MC emission.");
      PM.run(M);
    }

    auto ObjBuffer =
        llvm::make_unique<SmallVectorMemoryBuffer>(std::move(ObjBufferSV));
    auto Obj =
        object::ObjectFile::createObjectFile(ObjBuffer->getMemBufferRef());

    if (Obj) {
      notifyObjectCompiled(M, *ObjBuffer);
      return std::move(ObjBuffer);
    }

    // TODO: Actually report errors helpfully.
    consumeError(Obj.takeError());
    return nullptr;
  }

private:

  CompileResult tryToLoadFromObjectCache(const Module &M) {
    if (!ObjCache)
      return CompileResult();

    return ObjCache->getObject(&M);
  }

  void notifyObjectCompiled(const Module &M, const MemoryBuffer &ObjBuffer) {
    if (ObjCache)
      ObjCache->notifyObjectCompiled(&M, ObjBuffer.getMemBufferRef());
  }

  TargetMachine &TM;
  ObjectCache *ObjCache = nullptr;
};

/// A thread-safe version of SimpleCompiler.
///
/// This class creates a new TargetMachine and SimpleCompiler instance for each
/// compile.
class ConcurrentIRCompiler {
public:
  ConcurrentIRCompiler(JITTargetMachineBuilder JTMB,
                       ObjectCache *ObjCache = nullptr)
      : JTMB(std::move(JTMB)), ObjCache(ObjCache) {}

  void setObjectCache(ObjectCache *ObjCache) { this->ObjCache = ObjCache; }

  std::unique_ptr<MemoryBuffer> operator()(Module &M) {
    auto TM = cantFail(JTMB.createTargetMachine());
    SimpleCompiler C(*TM, ObjCache);
    return C(M);
  }

private:
  JITTargetMachineBuilder JTMB;
  ObjectCache *ObjCache = nullptr;
};

} // end namespace orc

} // end namespace llvm

#endif // LLVM_EXECUTIONENGINE_ORC_COMPILEUTILS_H
