blob: 59ad2d34329b0a0ae8f6e2503c99ebfa13b98409 [file] [log] [blame]
Andrew Kaylor0ab5c6c2013-10-02 17:12:36 +00001//===---- RemoteTargetExternal.cpp - LLVM out-of-process JIT execution ----===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// Implementation of the RemoteTargetExternal class which executes JITed code
11// in a separate process from where it was built.
12//
13//===----------------------------------------------------------------------===//
14
15#include "llvm/Config/config.h"
16
17#include "RemoteTarget.h"
18#include "RemoteTargetExternal.h"
19
20#include "llvm/ADT/StringRef.h"
21#include "llvm/Support/DataTypes.h"
22#include "llvm/Support/Memory.h"
23#include "llvm/Support/Program.h"
24#include "llvm/Support/raw_ostream.h"
25#include <string>
26
27using namespace llvm;
28
29bool RemoteTargetExternal::allocateSpace(size_t Size, unsigned Alignment,
30 uint64_t &Address) {
31 SendAllocateSpace(Alignment, Size);
32 Receive(LLI_AllocationResult, Address);
33 return false;
34}
35
36bool RemoteTargetExternal::loadData(uint64_t Address, const void *Data, size_t Size) {
37 SendLoadSection(Address, Data, (uint32_t)Size, false);
38 Receive(LLI_LoadComplete);
39 return false;
40}
41
42bool RemoteTargetExternal::loadCode(uint64_t Address, const void *Data, size_t Size) {
43 SendLoadSection(Address, Data, (uint32_t)Size, true);
44 Receive(LLI_LoadComplete);
45 return false;
46}
47
48bool RemoteTargetExternal::executeCode(uint64_t Address, int &RetVal) {
49 SendExecute(Address);
50
51 Receive(LLI_ExecutionResult, RetVal);
52 return false;
53}
54
55void RemoteTargetExternal::stop() {
56 SendTerminate();
57 Wait();
58}
59
60void RemoteTargetExternal::SendAllocateSpace(uint32_t Alignment, uint32_t Size) {
61 int rc;
62 uint32_t MsgType = (uint32_t)LLI_AllocateSpace;
63 rc = WriteBytes(&MsgType, 4);
64 assert(rc == 4 && "Error writing message type.");
65
66 uint32_t DataSize = 8;
67 rc = WriteBytes(&DataSize, 4);
68 assert(rc == 4 && "Error writing data size.");
69
70 rc = WriteBytes(&Alignment, 4);
71 assert(rc == 4 && "Error writing alignment data.");
72
73 rc = WriteBytes(&Size, 4);
74 assert(rc == 4 && "Error writing size data.");
75}
76
77void RemoteTargetExternal::SendLoadSection(uint64_t Addr,
78 const void *Data,
79 uint32_t Size,
80 bool IsCode) {
81 int rc;
82 uint32_t MsgType = IsCode ? LLI_LoadCodeSection : LLI_LoadDataSection;
83 rc = WriteBytes(&MsgType, 4);
84 assert(rc == 4 && "Error writing message type.");
85
86 uint32_t DataSize = Size + 8;
87 rc = WriteBytes(&DataSize, 4);
88 assert(rc == 4 && "Error writing data size.");
89
90 rc = WriteBytes(&Addr, 8);
91 assert(rc == 8 && "Error writing data.");
92
93 rc = WriteBytes(Data, Size);
94 assert(rc == (int)Size && "Error writing data.");
95}
96
97void RemoteTargetExternal::SendExecute(uint64_t Addr) {
98 int rc;
99 uint32_t MsgType = (uint32_t)LLI_Execute;
100 rc = WriteBytes(&MsgType, 4);
101 assert(rc == 4 && "Error writing message type.");
102
103 uint32_t DataSize = 8;
104 rc = WriteBytes(&DataSize, 4);
105 assert(rc == 4 && "Error writing data size.");
106
107 rc = WriteBytes(&Addr, 8);
108 assert(rc == 8 && "Error writing data.");
109}
110
111void RemoteTargetExternal::SendTerminate() {
112 int rc;
113 uint32_t MsgType = (uint32_t)LLI_Terminate;
114 rc = WriteBytes(&MsgType, 4);
115 assert(rc == 4 && "Error writing message type.");
116
117 // No data or data size is sent with Terminate
118}
119
120
121void RemoteTargetExternal::Receive(LLIMessageType ExpectedMsgType) {
122 int rc;
123 uint32_t MsgType;
124 rc = ReadBytes(&MsgType, 4);
125 assert(rc == 4 && "Error reading message type.");
126 assert(MsgType == ExpectedMsgType && "Error: received unexpected message type.");
127
128 uint32_t DataSize;
129 rc = ReadBytes(&DataSize, 4);
130 assert(rc == 4 && "Error reading data size.");
131 assert(DataSize == 0 && "Error: unexpected data size.");
132}
133
134void RemoteTargetExternal::Receive(LLIMessageType ExpectedMsgType, int &Data) {
135 uint64_t Temp;
136 Receive(ExpectedMsgType, Temp);
137 Data = (int)(int64_t)Temp;
138}
139
140void RemoteTargetExternal::Receive(LLIMessageType ExpectedMsgType, uint64_t &Data) {
141 int rc;
142 uint32_t MsgType;
143 rc = ReadBytes(&MsgType, 4);
144 assert(rc == 4 && "Error reading message type.");
145 assert(MsgType == ExpectedMsgType && "Error: received unexpected message type.");
146
147 uint32_t DataSize;
148 rc = ReadBytes(&DataSize, 4);
149 assert(rc == 4 && "Error reading data size.");
150 assert(DataSize == 8 && "Error: unexpected data size.");
151
152 rc = ReadBytes(&Data, 8);
153 assert(DataSize == 8 && "Error: unexpected data.");
154}
155
156#ifdef LLVM_ON_UNIX
157#include "Unix/RemoteTargetExternal.inc"
158#endif
159
160#ifdef LLVM_ON_WIN32
161#include "Windows/RemoteTargetExternal.inc"
162#endif