//===- InProcessControllerAccessTest.cpp ----------------------------------===//
//
// 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
//
//===----------------------------------------------------------------------===//
//
// Tests for orc-rt's InProcessControllerAccess.
//
//===----------------------------------------------------------------------===//

#include "orc-rt/InProcessControllerAccess.h"
#include "orc-rt/QueueingRunner.h"

#include "gtest/gtest.h"

#include "CommonTestUtils.h"

#include <deque>
#include <optional>
#include <string>

using namespace orc_rt;

namespace {

// A minimal stand-in for llvm::orc::InProcessEPC. Registers itself on the
// Connection during OnConnect, exposes hooks for tests to drive cross-calls
// in either direction, and tears the connection down on destruction.
class MockIPEPC {
public:
  using Connection = InProcessControllerAccess::Connection;

  using OnCallJITDispatchFn =
      move_only_function<void(uint64_t CallId, orc_rt_ControllerHandlerTag T,
                              WrapperFunctionBuffer ArgBytes)>;
  using OnReturnWrapperResultFn = move_only_function<void(
      uint64_t CallId, WrapperFunctionBuffer ResultBytes)>;

  MockIPEPC(Connection *C) : C(C) {
    C->Retain(C);
    C->IPEPC = this;
    C->CallJITDispatch = &callJITDispatchEntry;
    C->ReturnWrapperResult = &returnWrapperResultEntry;
  }

  MockIPEPC(const MockIPEPC &) = delete;
  MockIPEPC &operator=(const MockIPEPC &) = delete;

  ~MockIPEPC() {
    C->Disconnect(C);
    C->Release(C);
  }

  void setOnCallJITDispatch(OnCallJITDispatchFn H) {
    OnCallJITDispatch = std::move(H);
  }
  void setOnReturnWrapperResult(OnReturnWrapperResultFn H) {
    OnReturnWrapperResult = std::move(H);
  }

  // Send a result back to a CallJITDispatch invocation.
  void respondToCall(uint64_t CallId, WrapperFunctionBuffer Result) {
    if (C->EnterMessageScope(C)) {
      C->ReturnJITDispatchResult(C->IPCA, CallId, Result.release());
      C->LeaveMessageScope(C);
    }
  }

  // Initiate a wrapper call into the executor, simulating a controller-side
  // wrapper invocation. Returns the CallId that ReturnWrapperResult will
  // refer back to.
  uint64_t callIntoExecutor(orc_rt_WrapperFunction Fn,
                            WrapperFunctionBuffer ArgBytes) {
    uint64_t CallId = NextCallId++;
    if (C->EnterMessageScope(C)) {
      C->CallWrapper(C->IPCA, CallId, reinterpret_cast<void *>(Fn),
                     ArgBytes.release());
      C->LeaveMessageScope(C);
    }
    return CallId;
  }

private:
  static void callJITDispatchEntry(void *IPEPC, uint64_t CallId,
                                   orc_rt_ControllerHandlerTag T,
                                   orc_rt_WrapperFunctionBuffer ArgBytes) {
    auto *Self = static_cast<MockIPEPC *>(IPEPC);
    WrapperFunctionBuffer Buf(ArgBytes);
    if (Self->OnCallJITDispatch)
      Self->OnCallJITDispatch(CallId, T, std::move(Buf));
  }

  static void
  returnWrapperResultEntry(void *IPEPC, uint64_t CallId,
                           orc_rt_WrapperFunctionBuffer ResultBytes) {
    auto *Self = static_cast<MockIPEPC *>(IPEPC);
    WrapperFunctionBuffer Buf(ResultBytes);
    if (Self->OnReturnWrapperResult)
      Self->OnReturnWrapperResult(CallId, std::move(Buf));
  }

  Connection *C;
  uint64_t NextCallId = 0;
  OnCallJITDispatchFn OnCallJITDispatch;
  OnReturnWrapperResultFn OnReturnWrapperResult;
};

// Convenience: attach an InProcessControllerAccess to S, constructing a
// MockIPEPC into MockOut from inside OnConnect.
void attachWithMock(Session &S, std::unique_ptr<MockIPEPC> &MockOut) {
  S.attach<InProcessControllerAccess>(
      BootstrapInfo(S),
      [&MockOut](InProcessControllerAccess &, BootstrapInfo &,
                 InProcessControllerAccess::Connection *C,
                 InProcessControllerAccess::BootstrapInfoAccess *) -> Error {
        MockOut = std::make_unique<MockIPEPC>(C);
        return Error::success();
      });
}

} // namespace

TEST(InProcessControllerAccessTest, ConstructAndDestroyWithoutConnect) {
  // An InProcessControllerAccess that is never attached to a Session (so its
  // connect method is never called) must still destroy cleanly. The
  // destructor's `if (C)` guard is what makes this safe.
  Session S(mockExecutorProcessInfo(), noDispatch, noErrors);

  InProcessControllerAccess IPCA(
      S,
      [](InProcessControllerAccess &, BootstrapInfo &,
         InProcessControllerAccess::Connection *,
         InProcessControllerAccess::BootstrapInfoAccess *) -> Error {
        ADD_FAILURE() << "OnConnect should not be called";
        return Error::success();
      });

  // IPCA is destroyed at scope exit; test passes if there's no crash.
}

TEST(InProcessControllerAccessTest, AttachAndShutdownViaSession) {
  // Smoke test: attach with a successful OnConnect, verify the mock was
  // constructed, then let scope exit drive shutdown.
  Session S(mockExecutorProcessInfo(), noDispatch, noErrors);

  std::unique_ptr<MockIPEPC> Mock;
  attachWithMock(S, Mock);
  EXPECT_TRUE(Mock) << "Expected OnConnect to construct MockIPEPC";
}

TEST(InProcessControllerAccessTest, OnConnectFailureIsReportedAndDetaches) {
  // If OnConnect returns an Error, IPCA::connect should:
  //   (1) Forward the error through Session::reportError.
  //   (2) Trigger disconnect (so the Session ends up detached and no further
  //       calls into the controller succeed).
  Error Reported = Error::success();
  cantFail(std::move(Reported)); // force checked state

  Session S(mockExecutorProcessInfo(), noDispatch,
            [&](Error E) { Reported = std::move(E); });

  S.attach<InProcessControllerAccess>(
      BootstrapInfo(S),
      [](InProcessControllerAccess &, BootstrapInfo &,
         InProcessControllerAccess::Connection *,
         InProcessControllerAccess::BootstrapInfoAccess *) -> Error {
        return make_error<StringError>("fake connect failure");
      });

  if (Reported)
    EXPECT_EQ(toString(std::move(Reported)), "fake connect failure");
  else
    ADD_FAILURE() << "Expected OnConnect error to be reported";

  // A subsequent call to the controller should now fail with "no controller
  // attached" (i.e. the Session detached on the OnConnect error).
  std::optional<std::string> CallErr;
  S.callController(
      [&](WrapperFunctionBuffer R) {
        if (const char *Msg = R.getOutOfBandError())
          CallErr = Msg;
      },
      reinterpret_cast<orc_rt_ControllerHandlerTag>(0xdeadbeef),
      WrapperFunctionBuffer::copyFrom("x", 1));

  ASSERT_TRUE(CallErr);
  EXPECT_EQ(*CallErr, "no controller attached");
}

TEST(InProcessControllerAccessTest, CallControllerSuccess) {
  // A callController call routed through MockIPEPC, which echoes the args
  // back as the result. Verify OnComplete fires with the payload.
  Session S(mockExecutorProcessInfo(), inlineDispatch, noErrors);

  std::unique_ptr<MockIPEPC> Mock;
  attachWithMock(S, Mock);
  ASSERT_TRUE(Mock);

  Mock->setOnCallJITDispatch(
      [&](uint64_t CallId, void *, WrapperFunctionBuffer ArgBytes) {
        Mock->respondToCall(CallId, std::move(ArgBytes));
      });

  std::optional<std::string> Result;
  S.callController(
      [&](WrapperFunctionBuffer R) {
        ASSERT_FALSE(R.getOutOfBandError())
            << "Unexpected out-of-band error: " << R.getOutOfBandError();
        Result = std::string(R.data(), R.size());
      },
      reinterpret_cast<orc_rt_ControllerHandlerTag>(0xdeadbeef),
      WrapperFunctionBuffer::copyFrom("hello", 5));

  ASSERT_TRUE(Result);
  EXPECT_EQ(*Result, "hello");
}

TEST(InProcessControllerAccessTest, CallControllerOutOfBandError) {
  // A callController call where the mock responds with an out-of-band error.
  // OnComplete should observe the error message intact.
  Session S(mockExecutorProcessInfo(), inlineDispatch, noErrors);

  std::unique_ptr<MockIPEPC> Mock;
  attachWithMock(S, Mock);
  ASSERT_TRUE(Mock);

  Mock->setOnCallJITDispatch(
      [&](uint64_t CallId, void *, WrapperFunctionBuffer) {
        Mock->respondToCall(CallId, WrapperFunctionBuffer::createOutOfBandError(
                                        "simulated failure"));
      });

  std::optional<std::string> ErrMsg;
  S.callController(
      [&](WrapperFunctionBuffer R) {
        if (const char *Msg = R.getOutOfBandError())
          ErrMsg = Msg;
      },
      reinterpret_cast<orc_rt_ControllerHandlerTag>(0xdeadbeef),
      WrapperFunctionBuffer::copyFrom("payload", 7));

  ASSERT_TRUE(ErrMsg);
  EXPECT_EQ(*ErrMsg, "simulated failure");
}

TEST(InProcessControllerAccessTest, DisconnectDrainsPendingCalls) {
  // A callController call is in-flight when the connection drops (the mock
  // never responds). Verify that doDisconnect drains the pending handler with
  // a "disconnected" out-of-band error rather than leaving it stranded.
  Session S(mockExecutorProcessInfo(), inlineDispatch, noErrors);

  std::unique_ptr<MockIPEPC> Mock;
  attachWithMock(S, Mock);
  ASSERT_TRUE(Mock);

  // Mock receives the call but never sends a result.
  Mock->setOnCallJITDispatch([](uint64_t, void *, WrapperFunctionBuffer) {});

  std::optional<std::string> ErrMsg;
  S.callController(
      [&](WrapperFunctionBuffer R) {
        if (const char *Msg = R.getOutOfBandError())
          ErrMsg = Msg;
      },
      reinterpret_cast<orc_rt_ControllerHandlerTag>(0xdeadbeef),
      WrapperFunctionBuffer::copyFrom("payload", 7));

  ASSERT_FALSE(ErrMsg) << "OnComplete fired prematurely";

  // Tearing down the mock triggers C->Disconnect, which routes through
  // ConnectionImpl::disconnect → IPCA::doDisconnect and drains the pending
  // OnComplete with a "disconnected" error.
  Mock.reset();

  ASSERT_TRUE(ErrMsg);
  EXPECT_EQ(*ErrMsg, "disconnected");
}

// Wrapper function that echoes ArgBytes back as the result. Used to exercise
// the controller-initiated wrapper-call path without pulling in SPS.
static void echoWrapper(orc_rt_SessionRef S,
                        orc_rt_WrapperFunctionBuffer ArgBytes,
                        orc_rt_WrapperFunctionReturn Return, uint64_t CallId) {
  Return(S, ArgBytes, CallId);
}

TEST(InProcessControllerAccessTest, CallFromControllerSuccess) {
  // The mock IPEPC initiates a wrapper call into IPCA. The Session's
  // dispatch hook (a QueueingRunner over `Tasks`) enqueues the
  // invocation; draining the queue runs the wrapper, which echoes its
  // arguments back. Verify the mock receives the echoed bytes via
  // ReturnWrapperResult.
  QueueingRunner<>::WorkQueue Tasks;
  Session S(mockExecutorProcessInfo(), QueueingRunner(Tasks), noErrors);

  std::unique_ptr<MockIPEPC> Mock;
  attachWithMock(S, Mock);
  ASSERT_TRUE(Mock);

  std::optional<std::string> Result;
  Mock->setOnReturnWrapperResult(
      [&](uint64_t, WrapperFunctionBuffer ResultBytes) {
        Result = std::string(ResultBytes.data(), ResultBytes.size());
      });

  Mock->callIntoExecutor(echoWrapper,
                         WrapperFunctionBuffer::copyFrom("world", 5));

  // Nothing has run yet -- the wrapper is sitting in `Tasks` waiting to be
  // dispatched.
  ASSERT_FALSE(Result);

  QueueingRunner<>::runFIFOUntilEmpty(Tasks);

  ASSERT_TRUE(Result);
  EXPECT_EQ(*Result, "world");
}
