LLVM  14.0.0git
SimpleRemoteEPCServer.h
Go to the documentation of this file.
1 //===---- SimpleRemoteEPCServer.h - EPC over abstract channel ---*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // EPC over simple abstract channel.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #ifndef LLVM_EXECUTIONENGINE_ORC_TARGETPROCESS_SIMPLEREMOTEEPCSERVER_H
14 #define LLVM_EXECUTIONENGINE_ORC_TARGETPROCESS_SIMPLEREMOTEEPCSERVER_H
15 
16 #include "llvm/ADT/DenseMap.h"
18 #include "llvm/Config/llvm-config.h"
25 #include "llvm/Support/Error.h"
26 
27 #include <condition_variable>
28 #include <future>
29 #include <memory>
30 #include <mutex>
31 
32 namespace llvm {
33 namespace orc {
34 
35 /// A simple EPC server implementation.
37 public:
39 
40  /// Dispatches calls to runWrapper.
41  class Dispatcher {
42  public:
43  virtual ~Dispatcher();
44  virtual void dispatch(unique_function<void()> Work) = 0;
45  virtual void shutdown() = 0;
46  };
47 
48 #if LLVM_ENABLE_THREADS
49  class ThreadDispatcher : public Dispatcher {
50  public:
51  void dispatch(unique_function<void()> Work) override;
52  void shutdown() override;
53 
54  private:
55  std::mutex DispatchMutex;
56  bool Running = true;
57  size_t Outstanding = 0;
58  std::condition_variable OutstandingCV;
59  };
60 #endif
61 
62  class Setup {
63  friend class SimpleRemoteEPCServer;
64 
65  public:
67  StringMap<ExecutorAddr> &bootstrapSymbols() { return BootstrapSymbols; }
68  std::vector<std::unique_ptr<ExecutorBootstrapService>> &services() {
69  return Services;
70  }
71  void setDispatcher(std::unique_ptr<Dispatcher> D) { S.D = std::move(D); }
72  void setErrorReporter(unique_function<void(Error)> ReportError) {
73  S.ReportError = std::move(ReportError);
74  }
75 
76  private:
79  StringMap<ExecutorAddr> BootstrapSymbols;
80  std::vector<std::unique_ptr<ExecutorBootstrapService>> Services;
81  };
82 
84 
85  template <typename TransportT, typename... TransportTCtorArgTs>
87  Create(unique_function<Error(Setup &S)> SetupFunction,
88  TransportTCtorArgTs &&...TransportTCtorArgs) {
89  auto Server = std::make_unique<SimpleRemoteEPCServer>();
90  Setup S(*Server);
91  if (auto Err = SetupFunction(S))
92  return std::move(Err);
93 
94  // Set ReportError up-front so that it can be used if construction
95  // process fails.
96  if (!Server->ReportError)
97  Server->ReportError = [](Error Err) {
98  logAllUnhandledErrors(std::move(Err), errs(), "SimpleRemoteEPCServer ");
99  };
100 
101  // Attempt to create transport.
102  auto T = TransportT::Create(
103  *Server, std::forward<TransportTCtorArgTs>(TransportTCtorArgs)...);
104  if (!T)
105  return T.takeError();
106  Server->T = std::move(*T);
107  if (auto Err = Server->T->start())
108  return std::move(Err);
109 
110  // If transport creation succeeds then start up services.
111  Server->Services = std::move(S.services());
112  Server->Services.push_back(
113  std::make_unique<rt_bootstrap::SimpleExecutorDylibManager>());
114  for (auto &Service : Server->Services)
115  Service->addBootstrapSymbols(S.bootstrapSymbols());
116 
117  if (auto Err = Server->sendSetupMessage(std::move(S.BootstrapSymbols)))
118  return std::move(Err);
119  return std::move(Server);
120  }
121 
122  /// Set an error reporter for this server.
124  this->ReportError = std::move(ReportError);
125  }
126 
127  /// Call to handle an incoming message.
128  ///
129  /// Returns 'Disconnect' if the message is a 'detach' message from the remote
130  /// otherwise returns 'Continue'. If the server has moved to an error state,
131  /// returns an error, which should be reported and treated as a 'Disconnect'.
134  SimpleRemoteEPCArgBytesVector ArgBytes) override;
135 
137 
138  void handleDisconnect(Error Err) override;
139 
140 private:
141  Error sendMessage(SimpleRemoteEPCOpcode OpC, uint64_t SeqNo,
142  ExecutorAddr TagAddr, ArrayRef<char> ArgBytes);
143 
144  Error sendSetupMessage(StringMap<ExecutorAddr> BootstrapSymbols);
145 
146  Error handleResult(uint64_t SeqNo, ExecutorAddr TagAddr,
148  void handleCallWrapper(uint64_t RemoteSeqNo, ExecutorAddr TagAddr,
150 
152  doJITDispatch(const void *FnTag, const char *ArgData, size_t ArgSize);
153 
154  static shared::CWrapperFunctionResult jitDispatchEntry(void *DispatchCtx,
155  const void *FnTag,
156  const char *ArgData,
157  size_t ArgSize);
158 
159  uint64_t getNextSeqNo() { return NextSeqNo++; }
160  void releaseSeqNo(uint64_t) {}
161 
162  using PendingJITDispatchResultsMap =
163  DenseMap<uint64_t, std::promise<shared::WrapperFunctionResult> *>;
164 
165  std::mutex ServerStateMutex;
166  std::condition_variable ShutdownCV;
167  enum { ServerRunning, ServerShuttingDown, ServerShutDown } RunState;
168  Error ShutdownErr = Error::success();
169  std::unique_ptr<SimpleRemoteEPCTransport> T;
170  std::unique_ptr<Dispatcher> D;
171  std::vector<std::unique_ptr<ExecutorBootstrapService>> Services;
172  ReportErrorFunction ReportError;
173 
174  uint64_t NextSeqNo = 0;
175  PendingJITDispatchResultsMap PendingJITDispatchResults;
176  std::vector<sys::DynamicLibrary> Dylibs;
177 };
178 
179 } // end namespace orc
180 } // end namespace llvm
181 
182 #endif // LLVM_EXECUTIONENGINE_ORC_TARGETPROCESS_SIMPLEREMOTEEPCSERVER_H
llvm::orc::ExecutorAddr
Represents an address in the executor process.
Definition: ExecutorAddress.h:37
llvm::orc::SimpleRemoteEPCServer::defaultBootstrapSymbols
static StringMap< ExecutorAddr > defaultBootstrapSymbols()
Definition: SimpleRemoteEPCServer.cpp:54
TargetProcessControlTypes.h
llvm
This is an optimization pass for GlobalISel generic memory operations.
Definition: AllocatorList.h:23
llvm::orc::SimpleRemoteEPCOpcode
SimpleRemoteEPCOpcode
Definition: SimpleRemoteEPCUtils.h:37
llvm::lltok::Error
@ Error
Definition: LLToken.h:21
FunctionExtras.h
llvm::orc::shared::CWrapperFunctionResult
Definition: WrapperFunctionUtils.h:33
llvm::unique_function< void(Error)>
llvm::SmallVector
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1168
SimpleExecutorDylibManager.h
SimpleRemoteEPCUtils.h
llvm::Error::success
static ErrorSuccess success()
Create a success value.
Definition: Error.h:331
Error.h
WrapperFunctionUtils.h
DynamicLibrary.h
DenseMap.h
llvm::orc::SimpleRemoteEPCServer::handleMessage
Expected< HandleMessageAction > handleMessage(SimpleRemoteEPCOpcode OpC, uint64_t SeqNo, ExecutorAddr TagAddr, SimpleRemoteEPCArgBytesVector ArgBytes) override
Call to handle an incoming message.
Definition: SimpleRemoteEPCServer.cpp:61
T
#define T
Definition: Mips16ISelLowering.cpp:341
llvm::errs
raw_fd_ostream & errs()
This returns a reference to a raw_ostream for standard error.
Definition: raw_ostream.cpp:893
llvm::Expected
Tagged union holding either a T or a Error.
Definition: APFloat.h:42
llvm::orc::SimpleRemoteEPCServer::Setup::setDispatcher
void setDispatcher(std::unique_ptr< Dispatcher > D)
Definition: SimpleRemoteEPCServer.h:71
llvm::orc::SimpleRemoteEPCServer::Create
static Expected< std::unique_ptr< SimpleRemoteEPCServer > > Create(unique_function< Error(Setup &S)> SetupFunction, TransportTCtorArgTs &&...TransportTCtorArgs)
Definition: SimpleRemoteEPCServer.h:87
llvm::orc::SimpleRemoteEPCServer::Setup::setErrorReporter
void setErrorReporter(unique_function< void(Error)> ReportError)
Definition: SimpleRemoteEPCServer.h:72
llvm::orc::SimpleRemoteEPCServer
A simple EPC server implementation.
Definition: SimpleRemoteEPCServer.h:36
ExecutorBootstrapService.h
llvm::orc::SimpleRemoteEPCServer::Dispatcher
Dispatches calls to runWrapper.
Definition: SimpleRemoteEPCServer.h:41
llvm::orc::SimpleRemoteEPCServer::ThreadDispatcher
Definition: SimpleRemoteEPCServer.h:49
llvm::orc::SimpleRemoteEPCServer::Setup
Definition: SimpleRemoteEPCServer.h:62
llvm::StringMap
StringMap - This is an unconventional map that is specialized for handling keys that are "strings",...
Definition: StringMap.h:108
llvm::orc::SimpleRemoteEPCServer::ReportErrorFunction
unique_function< void(Error)> ReportErrorFunction
Definition: SimpleRemoteEPCServer.h:38
llvm::orc::shared::WrapperFunctionResult
C++ wrapper function result: Same as CWrapperFunctionResult but auto-releases memory.
Definition: WrapperFunctionUtils.h:40
uint64_t
D
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
move
compiles ldr LCPI1_0 ldr ldr mov lsr tst moveq r1 ldr LCPI1_1 and r0 bx lr It would be better to do something like to fold the shift into the conditional move
Definition: README.txt:546
llvm::orc::SimpleRemoteEPCServer::Setup::services
std::vector< std::unique_ptr< ExecutorBootstrapService > > & services()
Definition: SimpleRemoteEPCServer.h:68
llvm::orc::SimpleRemoteEPCServer::setErrorReporter
void setErrorReporter(ReportErrorFunction ReportError)
Set an error reporter for this server.
Definition: SimpleRemoteEPCServer.h:123
llvm::orc::SimpleRemoteEPCServer::ThreadDispatcher::shutdown
void shutdown() override
llvm::ArrayRef< char >
S
add sub stmia L5 ldr r0 bl L_printf $stub Instead of a and a wouldn t it be better to do three moves *Return an aggregate type is even return S
Definition: README.txt:210
llvm::orc::SimpleRemoteEPCServer::ThreadDispatcher::dispatch
void dispatch(unique_function< void()> Work) override
llvm::logAllUnhandledErrors
void logAllUnhandledErrors(Error E, raw_ostream &OS, Twine ErrorBanner={})
Log all errors (if any) in E to OS.
Definition: Error.cpp:61
llvm::Error
Lightweight error class with error context and mandatory checking.
Definition: Error.h:157
llvm::orc::SimpleRemoteEPCServer::Dispatcher::shutdown
virtual void shutdown()=0
llvm::orc::SimpleRemoteEPCServer::handleDisconnect
void handleDisconnect(Error Err) override
Handle a disconnection from the underlying transport.
Definition: SimpleRemoteEPCServer.cpp:121
llvm::orc::SimpleRemoteEPCServer::Dispatcher::dispatch
virtual void dispatch(unique_function< void()> Work)=0
llvm::orc::SimpleRemoteEPCTransportClient
Definition: SimpleRemoteEPCUtils.h:53
llvm::orc::SimpleRemoteEPCServer::Setup::server
SimpleRemoteEPCServer & server()
Definition: SimpleRemoteEPCServer.h:66
llvm::orc::SimpleRemoteEPCServer::waitForDisconnect
Error waitForDisconnect()
Definition: SimpleRemoteEPCServer.cpp:115
llvm::orc::SimpleRemoteEPCServer::Setup::bootstrapSymbols
StringMap< ExecutorAddr > & bootstrapSymbols()
Definition: SimpleRemoteEPCServer.h:67
llvm::orc::SimpleRemoteEPCServer::Dispatcher::~Dispatcher
virtual ~Dispatcher()
Definition: SimpleRemoteEPCServer.cpp:27