blob: fde610a09aec803d6ebb9a04ed3b0966b4fe5b2f [file] [log] [blame]
Sean Callanan3bfdaa22011-09-15 02:13:07 +00001//===-- IRForTarget.cpp -----------------------------------------*- C++ -*-===//
Sean Callanan2ab712f22010-07-03 01:35:46 +00002//
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
Sean Callanan4dbb2712015-09-25 20:35:58 +000010#include "IRForTarget.h"
11
12#include "ClangExpressionDeclMap.h"
Sean Callanan2ab712f22010-07-03 01:35:46 +000013
Chandler Carruth1e157582013-01-02 12:20:07 +000014#include "llvm/IR/Constants.h"
15#include "llvm/IR/DataLayout.h"
16#include "llvm/IR/InstrTypes.h"
17#include "llvm/IR/Instructions.h"
18#include "llvm/IR/Intrinsics.h"
Ilia Kc9a475d2015-02-13 10:49:18 +000019#include "llvm/IR/LegacyPassManager.h"
Zachary Turner543afa12014-12-09 22:29:47 +000020#include "llvm/IR/Metadata.h"
Kate Stoneb9c1b512016-09-06 20:57:50 +000021#include "llvm/IR/Module.h"
Chandler Carruth1e157582013-01-02 12:20:07 +000022#include "llvm/IR/ValueSymbolTable.h"
Kate Stoneb9c1b512016-09-06 20:57:50 +000023#include "llvm/Support/raw_ostream.h"
24#include "llvm/Transforms/IPO.h"
Sean Callanan549c9f72010-07-13 21:41:46 +000025
26#include "clang/AST/ASTContext.h"
Sean Callanan2ab712f22010-07-03 01:35:46 +000027
Zachary Turnerd133f6a2016-03-28 22:53:41 +000028#include "lldb/Core/dwarf.h"
Sean Callanan8dfb68e2013-03-19 00:10:07 +000029#include "lldb/Expression/IRExecutionUnit.h"
Sean Callanan3bfdaa22011-09-15 02:13:07 +000030#include "lldb/Expression/IRInterpreter.h"
Sean Callanan63697e52011-05-07 01:06:41 +000031#include "lldb/Symbol/ClangASTContext.h"
Zachary Turnerd133f6a2016-03-28 22:53:41 +000032#include "lldb/Symbol/ClangUtil.h"
Greg Claytona1e5dc82015-08-11 22:53:00 +000033#include "lldb/Symbol/CompilerType.h"
Zachary Turnerbf9a7732017-02-02 21:39:50 +000034#include "lldb/Utility/ConstString.h"
Zachary Turner666cc0b2017-03-04 01:30:05 +000035#include "lldb/Utility/DataBufferHeap.h"
Zachary Turner01c32432017-02-14 19:06:07 +000036#include "lldb/Utility/Endian.h"
Zachary Turner6f9e6902017-03-03 20:56:28 +000037#include "lldb/Utility/Log.h"
Pavel Labathd821c992018-08-07 11:07:21 +000038#include "lldb/Utility/Scalar.h"
Zachary Turnerbf9a7732017-02-02 21:39:50 +000039#include "lldb/Utility/StreamString.h"
Sean Callanan2ab712f22010-07-03 01:35:46 +000040
41#include <map>
42
43using namespace llvm;
44
Sean Callananeaacbc92010-08-18 18:50:51 +000045static char ID;
46
Kate Stoneb9c1b512016-09-06 20:57:50 +000047IRForTarget::FunctionValueCache::FunctionValueCache(Maker const &maker)
48 : m_maker(maker), m_values() {}
Sean Callanan1f9db3e2013-06-28 21:44:15 +000049
Kate Stoneb9c1b512016-09-06 20:57:50 +000050IRForTarget::FunctionValueCache::~FunctionValueCache() {}
Sean Callanan1f9db3e2013-06-28 21:44:15 +000051
Greg Clayton526ae042015-02-12 00:34:25 +000052llvm::Value *
Kate Stoneb9c1b512016-09-06 20:57:50 +000053IRForTarget::FunctionValueCache::GetValue(llvm::Function *function) {
54 if (!m_values.count(function)) {
55 llvm::Value *ret = m_maker(function);
56 m_values[function] = ret;
57 return ret;
58 }
59 return m_values[function];
Sean Callanan1f9db3e2013-06-28 21:44:15 +000060}
61
Kate Stoneb9c1b512016-09-06 20:57:50 +000062static llvm::Value *FindEntryInstruction(llvm::Function *function) {
63 if (function->empty())
64 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +000065
Kate Stoneb9c1b512016-09-06 20:57:50 +000066 return function->getEntryBlock().getFirstNonPHIOrDbg();
Sean Callanan1f9db3e2013-06-28 21:44:15 +000067}
68
Kate Stoneb9c1b512016-09-06 20:57:50 +000069IRForTarget::IRForTarget(lldb_private::ClangExpressionDeclMap *decl_map,
70 bool resolve_vars,
71 lldb_private::IRExecutionUnit &execution_unit,
72 lldb_private::Stream &error_stream,
73 const char *func_name)
74 : ModulePass(ID), m_resolve_vars(resolve_vars), m_func_name(func_name),
75 m_module(NULL), m_decl_map(decl_map), m_CFStringCreateWithBytes(NULL),
Sean Callananac900582016-09-29 00:45:33 +000076 m_sel_registerName(NULL), m_objc_getClass(NULL), m_intptr_ty(NULL),
77 m_error_stream(error_stream),
Kate Stoneb9c1b512016-09-06 20:57:50 +000078 m_execution_unit(execution_unit), m_result_store(NULL),
79 m_result_is_pointer(false), m_reloc_placeholder(NULL),
80 m_entry_instruction_finder(FindEntryInstruction) {}
Sean Callanan2ab712f22010-07-03 01:35:46 +000081
Sean Callanan038df5032010-09-30 21:18:25 +000082/* Handy utility functions used at several places in the code */
Sean Callanan2235f322010-08-11 03:57:18 +000083
Kate Stoneb9c1b512016-09-06 20:57:50 +000084static std::string PrintValue(const Value *value, bool truncate = false) {
85 std::string s;
86 if (value) {
Sean Callanan038df5032010-09-30 21:18:25 +000087 raw_string_ostream rso(s);
Kate Stoneb9c1b512016-09-06 20:57:50 +000088 value->print(rso);
Sean Callanan038df5032010-09-30 21:18:25 +000089 rso.flush();
90 if (truncate)
Kate Stoneb9c1b512016-09-06 20:57:50 +000091 s.resize(s.length() - 1);
92 }
93 return s;
Sean Callanan038df5032010-09-30 21:18:25 +000094}
95
Kate Stoneb9c1b512016-09-06 20:57:50 +000096static std::string PrintType(const llvm::Type *type, bool truncate = false) {
97 std::string s;
98 raw_string_ostream rso(s);
99 type->print(rso);
100 rso.flush();
101 if (truncate)
102 s.resize(s.length() - 1);
103 return s;
Sean Callanan2ab712f22010-07-03 01:35:46 +0000104}
105
Kate Stoneb9c1b512016-09-06 20:57:50 +0000106IRForTarget::~IRForTarget() {}
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000107
Kate Stoneb9c1b512016-09-06 20:57:50 +0000108bool IRForTarget::FixFunctionLinkage(llvm::Function &llvm_function) {
109 llvm_function.setLinkage(GlobalValue::ExternalLinkage);
110
111 return true;
Sean Callanan79763a42011-05-23 21:40:23 +0000112}
113
Kate Stoneb9c1b512016-09-06 20:57:50 +0000114clang::NamedDecl *IRForTarget::DeclForGlobal(const GlobalValue *global_val,
115 Module *module) {
116 NamedMDNode *named_metadata =
117 module->getNamedMetadata("clang.global.decl.ptrs");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000118
Kate Stoneb9c1b512016-09-06 20:57:50 +0000119 if (!named_metadata)
Sean Callanan63697e52011-05-07 01:06:41 +0000120 return NULL;
Sean Callanan63697e52011-05-07 01:06:41 +0000121
Kate Stoneb9c1b512016-09-06 20:57:50 +0000122 unsigned num_nodes = named_metadata->getNumOperands();
123 unsigned node_index;
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000124
Kate Stoneb9c1b512016-09-06 20:57:50 +0000125 for (node_index = 0; node_index < num_nodes; ++node_index) {
126 llvm::MDNode *metadata_node =
127 dyn_cast<llvm::MDNode>(named_metadata->getOperand(node_index));
128 if (!metadata_node)
129 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000130
Kate Stoneb9c1b512016-09-06 20:57:50 +0000131 if (metadata_node->getNumOperands() != 2)
132 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000133
Kate Stoneb9c1b512016-09-06 20:57:50 +0000134 if (mdconst::dyn_extract_or_null<GlobalValue>(
135 metadata_node->getOperand(0)) != global_val)
136 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000137
Kate Stoneb9c1b512016-09-06 20:57:50 +0000138 ConstantInt *constant_int =
139 mdconst::dyn_extract<ConstantInt>(metadata_node->getOperand(1));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000140
Sean Callanan2235f322010-08-11 03:57:18 +0000141 if (!constant_int)
Kate Stoneb9c1b512016-09-06 20:57:50 +0000142 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000143
Sean Callanan2235f322010-08-11 03:57:18 +0000144 uintptr_t ptr = constant_int->getZExtValue();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000145
Kate Stoneb9c1b512016-09-06 20:57:50 +0000146 return reinterpret_cast<clang::NamedDecl *>(ptr);
147 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000148
Kate Stoneb9c1b512016-09-06 20:57:50 +0000149 return NULL;
150}
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000151
Kate Stoneb9c1b512016-09-06 20:57:50 +0000152clang::NamedDecl *IRForTarget::DeclForGlobal(GlobalValue *global_val) {
153 return DeclForGlobal(global_val, m_module);
154}
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000155
Kate Stoneb9c1b512016-09-06 20:57:50 +0000156bool IRForTarget::CreateResultVariable(llvm::Function &llvm_function) {
157 lldb_private::Log *log(
158 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000159
Kate Stoneb9c1b512016-09-06 20:57:50 +0000160 if (!m_resolve_vars)
161 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000162
Kate Stoneb9c1b512016-09-06 20:57:50 +0000163 // Find the result variable. If it doesn't exist, we can give up right here.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000164
Kate Stoneb9c1b512016-09-06 20:57:50 +0000165 ValueSymbolTable &value_symbol_table = m_module->getValueSymbolTable();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000166
Kate Stoneb9c1b512016-09-06 20:57:50 +0000167 std::string result_name_str;
168 const char *result_name = NULL;
Sean Callanan2235f322010-08-11 03:57:18 +0000169
Kate Stoneb9c1b512016-09-06 20:57:50 +0000170 for (ValueSymbolTable::iterator vi = value_symbol_table.begin(),
171 ve = value_symbol_table.end();
172 vi != ve; ++vi) {
173 result_name_str = vi->first().str();
174 const char *value_name = result_name_str.c_str();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000175
Kate Stoneb9c1b512016-09-06 20:57:50 +0000176 if (strstr(value_name, "$__lldb_expr_result_ptr") &&
177 strncmp(value_name, "_ZGV", 4)) {
178 result_name = value_name;
179 m_result_is_pointer = true;
180 break;
181 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000182
Kate Stoneb9c1b512016-09-06 20:57:50 +0000183 if (strstr(value_name, "$__lldb_expr_result") &&
184 strncmp(value_name, "_ZGV", 4)) {
185 result_name = value_name;
186 m_result_is_pointer = false;
187 break;
188 }
189 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000190
Kate Stoneb9c1b512016-09-06 20:57:50 +0000191 if (!result_name) {
Sean Callanane1175b72011-01-13 21:23:32 +0000192 if (log)
Kate Stoneb9c1b512016-09-06 20:57:50 +0000193 log->PutCString("Couldn't find result variable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000194
Sean Callanan2235f322010-08-11 03:57:18 +0000195 return true;
Kate Stoneb9c1b512016-09-06 20:57:50 +0000196 }
Sean Callanan2235f322010-08-11 03:57:18 +0000197
Kate Stoneb9c1b512016-09-06 20:57:50 +0000198 if (log)
199 log->Printf("Result name: \"%s\"", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000200
Kate Stoneb9c1b512016-09-06 20:57:50 +0000201 Value *result_value = m_module->getNamedValue(result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000202
Kate Stoneb9c1b512016-09-06 20:57:50 +0000203 if (!result_value) {
204 if (log)
205 log->PutCString("Result variable had no data");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000206
Kate Stoneb9c1b512016-09-06 20:57:50 +0000207 m_error_stream.Printf("Internal error [IRForTarget]: Result variable's "
208 "name (%s) exists, but not its definition\n",
209 result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000210
Sean Callananc70ed462011-10-25 18:36:40 +0000211 return false;
Kate Stoneb9c1b512016-09-06 20:57:50 +0000212 }
Sean Callananc70ed462011-10-25 18:36:40 +0000213
Kate Stoneb9c1b512016-09-06 20:57:50 +0000214 if (log)
215 log->Printf("Found result in the IR: \"%s\"",
216 PrintValue(result_value, false).c_str());
217
218 GlobalVariable *result_global = dyn_cast<GlobalVariable>(result_value);
219
220 if (!result_global) {
221 if (log)
222 log->PutCString("Result variable isn't a GlobalVariable");
223
224 m_error_stream.Printf("Internal error [IRForTarget]: Result variable (%s) "
225 "is defined, but is not a global variable\n",
226 result_name);
227
228 return false;
229 }
230
231 clang::NamedDecl *result_decl = DeclForGlobal(result_global);
232 if (!result_decl) {
233 if (log)
234 log->PutCString("Result variable doesn't have a corresponding Decl");
235
236 m_error_stream.Printf("Internal error [IRForTarget]: Result variable (%s) "
237 "does not have a corresponding Clang entity\n",
238 result_name);
239
240 return false;
241 }
242
243 if (log) {
244 std::string decl_desc_str;
245 raw_string_ostream decl_desc_stream(decl_desc_str);
246 result_decl->print(decl_desc_stream);
247 decl_desc_stream.flush();
248
249 log->Printf("Found result decl: \"%s\"", decl_desc_str.c_str());
250 }
251
252 clang::VarDecl *result_var = dyn_cast<clang::VarDecl>(result_decl);
253 if (!result_var) {
254 if (log)
255 log->PutCString("Result variable Decl isn't a VarDecl");
256
257 m_error_stream.Printf("Internal error [IRForTarget]: Result variable "
258 "(%s)'s corresponding Clang entity isn't a "
259 "variable\n",
260 result_name);
261
262 return false;
263 }
264
265 // Get the next available result name from m_decl_map and create the
Adrian Prantl05097242018-04-30 16:49:04 +0000266 // persistent variable for it
Kate Stoneb9c1b512016-09-06 20:57:50 +0000267
268 // If the result is an Lvalue, it is emitted as a pointer; see
269 // ASTResultSynthesizer::SynthesizeBodyResult.
270 if (m_result_is_pointer) {
271 clang::QualType pointer_qual_type = result_var->getType();
272 const clang::Type *pointer_type = pointer_qual_type.getTypePtr();
273
274 const clang::PointerType *pointer_pointertype =
275 pointer_type->getAs<clang::PointerType>();
276 const clang::ObjCObjectPointerType *pointer_objcobjpointertype =
277 pointer_type->getAs<clang::ObjCObjectPointerType>();
278
279 if (pointer_pointertype) {
280 clang::QualType element_qual_type = pointer_pointertype->getPointeeType();
281
282 m_result_type = lldb_private::TypeFromParser(
283 element_qual_type.getAsOpaquePtr(),
284 lldb_private::ClangASTContext::GetASTContext(
285 &result_decl->getASTContext()));
286 } else if (pointer_objcobjpointertype) {
287 clang::QualType element_qual_type =
288 clang::QualType(pointer_objcobjpointertype->getObjectType(), 0);
289
290 m_result_type = lldb_private::TypeFromParser(
291 element_qual_type.getAsOpaquePtr(),
292 lldb_private::ClangASTContext::GetASTContext(
293 &result_decl->getASTContext()));
294 } else {
295 if (log)
296 log->PutCString("Expected result to have pointer type, but it did not");
297
298 m_error_stream.Printf("Internal error [IRForTarget]: Lvalue result (%s) "
299 "is not a pointer variable\n",
300 result_name);
301
302 return false;
303 }
304 } else {
305 m_result_type = lldb_private::TypeFromParser(
306 result_var->getType().getAsOpaquePtr(),
307 lldb_private::ClangASTContext::GetASTContext(
308 &result_decl->getASTContext()));
309 }
310
311 lldb::TargetSP target_sp(m_execution_unit.GetTarget());
312 lldb_private::ExecutionContext exe_ctx(target_sp, true);
313 if (m_result_type.GetBitSize(exe_ctx.GetBestExecutionContextScope()) == 0) {
314 lldb_private::StreamString type_desc_stream;
315 m_result_type.DumpTypeDescription(&type_desc_stream);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000316
Sean Callanand7a1ca22010-12-02 19:47:57 +0000317 if (log)
Kate Stoneb9c1b512016-09-06 20:57:50 +0000318 log->Printf("Result type has size 0");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000319
Kate Stoneb9c1b512016-09-06 20:57:50 +0000320 m_error_stream.Printf("Error [IRForTarget]: Size of result type '%s' "
321 "couldn't be determined\n",
322 type_desc_stream.GetData());
323 return false;
324 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000325
Kate Stoneb9c1b512016-09-06 20:57:50 +0000326 if (log) {
327 lldb_private::StreamString type_desc_stream;
328 m_result_type.DumpTypeDescription(&type_desc_stream);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000329
Kate Stoneb9c1b512016-09-06 20:57:50 +0000330 log->Printf("Result decl type: \"%s\"", type_desc_stream.GetData());
331 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000332
Kate Stoneb9c1b512016-09-06 20:57:50 +0000333 m_result_name = lldb_private::ConstString("$RESULT_NAME");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000334
Kate Stoneb9c1b512016-09-06 20:57:50 +0000335 if (log)
336 log->Printf("Creating a new result global: \"%s\" with size 0x%" PRIx64,
337 m_result_name.GetCString(), m_result_type.GetByteSize(nullptr));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000338
Kate Stoneb9c1b512016-09-06 20:57:50 +0000339 // Construct a new result global and set up its metadata
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000340
Kate Stoneb9c1b512016-09-06 20:57:50 +0000341 GlobalVariable *new_result_global = new GlobalVariable(
342 (*m_module), result_global->getType()->getElementType(),
343 false, /* not constant */
344 GlobalValue::ExternalLinkage, NULL, /* no initializer */
345 m_result_name.GetCString());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000346
Adrian Prantl05097242018-04-30 16:49:04 +0000347 // It's too late in compilation to create a new VarDecl for this, but we
348 // don't need to. We point the metadata at the old VarDecl. This creates an
349 // odd anomaly: a variable with a Value whose name is something like $0 and a
Kate Stoneb9c1b512016-09-06 20:57:50 +0000350 // Decl whose name is $__lldb_expr_result. This condition is handled in
351 // ClangExpressionDeclMap::DoMaterialize, and the name of the variable is
352 // fixed up.
Greg Clayton57ee3062013-07-11 22:46:58 +0000353
Kate Stoneb9c1b512016-09-06 20:57:50 +0000354 ConstantInt *new_constant_int =
355 ConstantInt::get(llvm::Type::getInt64Ty(m_module->getContext()),
356 reinterpret_cast<uint64_t>(result_decl), false);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000357
Kate Stoneb9c1b512016-09-06 20:57:50 +0000358 llvm::Metadata *values[2];
359 values[0] = ConstantAsMetadata::get(new_result_global);
360 values[1] = ConstantAsMetadata::get(new_constant_int);
Greg Clayton57ee3062013-07-11 22:46:58 +0000361
Kate Stoneb9c1b512016-09-06 20:57:50 +0000362 ArrayRef<Metadata *> value_ref(values, 2);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000363
Kate Stoneb9c1b512016-09-06 20:57:50 +0000364 MDNode *persistent_global_md = MDNode::get(m_module->getContext(), value_ref);
365 NamedMDNode *named_metadata =
366 m_module->getNamedMetadata("clang.global.decl.ptrs");
367 named_metadata->addOperand(persistent_global_md);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000368
Kate Stoneb9c1b512016-09-06 20:57:50 +0000369 if (log)
370 log->Printf("Replacing \"%s\" with \"%s\"",
371 PrintValue(result_global).c_str(),
372 PrintValue(new_result_global).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000373
Kate Stoneb9c1b512016-09-06 20:57:50 +0000374 if (result_global->use_empty()) {
375 // We need to synthesize a store for this variable, because otherwise
376 // there's nothing to put into its equivalent persistent variable.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000377
Greg Clayton1b95a6f2010-11-19 01:05:25 +0000378 BasicBlock &entry_block(llvm_function.getEntryBlock());
Kate Stoneb9c1b512016-09-06 20:57:50 +0000379 Instruction *first_entry_instruction(entry_block.getFirstNonPHIOrDbg());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000380
Kate Stoneb9c1b512016-09-06 20:57:50 +0000381 if (!first_entry_instruction)
382 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000383
Kate Stoneb9c1b512016-09-06 20:57:50 +0000384 if (!result_global->hasInitializer()) {
385 if (log)
386 log->Printf("Couldn't find initializer for unused variable");
387
388 m_error_stream.Printf("Internal error [IRForTarget]: Result variable "
389 "(%s) has no writes and no initializer\n",
390 result_name);
391
392 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +0000393 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000394
Kate Stoneb9c1b512016-09-06 20:57:50 +0000395 Constant *initializer = result_global->getInitializer();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000396
Kate Stoneb9c1b512016-09-06 20:57:50 +0000397 StoreInst *synthesized_store =
398 new StoreInst(initializer, new_result_global, first_entry_instruction);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000399
Kate Stoneb9c1b512016-09-06 20:57:50 +0000400 if (log)
401 log->Printf("Synthesized result store \"%s\"\n",
402 PrintValue(synthesized_store).c_str());
403 } else {
404 result_global->replaceAllUsesWith(new_result_global);
405 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000406
Kate Stoneb9c1b512016-09-06 20:57:50 +0000407 if (!m_decl_map->AddPersistentVariable(
408 result_decl, m_result_name, m_result_type, true, m_result_is_pointer))
409 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000410
Kate Stoneb9c1b512016-09-06 20:57:50 +0000411 result_global->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000412
Kate Stoneb9c1b512016-09-06 20:57:50 +0000413 return true;
414}
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000415
Kate Stoneb9c1b512016-09-06 20:57:50 +0000416bool IRForTarget::RewriteObjCConstString(llvm::GlobalVariable *ns_str,
417 llvm::GlobalVariable *cstr) {
418 lldb_private::Log *log(
419 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000420
Kate Stoneb9c1b512016-09-06 20:57:50 +0000421 Type *ns_str_ty = ns_str->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000422
Kate Stoneb9c1b512016-09-06 20:57:50 +0000423 Type *i8_ptr_ty = Type::getInt8PtrTy(m_module->getContext());
424 Type *i32_ty = Type::getInt32Ty(m_module->getContext());
425 Type *i8_ty = Type::getInt8Ty(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000426
Kate Stoneb9c1b512016-09-06 20:57:50 +0000427 if (!m_CFStringCreateWithBytes) {
428 lldb::addr_t CFStringCreateWithBytes_addr;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000429
Kate Stoneb9c1b512016-09-06 20:57:50 +0000430 static lldb_private::ConstString g_CFStringCreateWithBytes_str(
431 "CFStringCreateWithBytes");
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000432
Kate Stoneb9c1b512016-09-06 20:57:50 +0000433 CFStringCreateWithBytes_addr =
434 m_execution_unit.FindSymbol(g_CFStringCreateWithBytes_str);
435 if (CFStringCreateWithBytes_addr == LLDB_INVALID_ADDRESS) {
436 if (log)
437 log->PutCString("Couldn't find CFStringCreateWithBytes in the target");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000438
Kate Stoneb9c1b512016-09-06 20:57:50 +0000439 m_error_stream.Printf("Error [IRForTarget]: Rewriting an Objective-C "
440 "constant string requires "
441 "CFStringCreateWithBytes\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000442
Kate Stoneb9c1b512016-09-06 20:57:50 +0000443 return false;
Sean Callanan549c9f72010-07-13 21:41:46 +0000444 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000445
Sean Callanan549c9f72010-07-13 21:41:46 +0000446 if (log)
Kate Stoneb9c1b512016-09-06 20:57:50 +0000447 log->Printf("Found CFStringCreateWithBytes at 0x%" PRIx64,
448 CFStringCreateWithBytes_addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000449
Kate Stoneb9c1b512016-09-06 20:57:50 +0000450 // Build the function type:
451 //
452 // CFStringRef CFStringCreateWithBytes (
453 // CFAllocatorRef alloc,
454 // const UInt8 *bytes,
455 // CFIndex numBytes,
456 // CFStringEncoding encoding,
457 // Boolean isExternalRepresentation
458 // );
459 //
460 // We make the following substitutions:
461 //
462 // CFStringRef -> i8*
463 // CFAllocatorRef -> i8*
464 // UInt8 * -> i8*
465 // CFIndex -> long (i32 or i64, as appropriate; we ask the module for its
Adrian Prantl05097242018-04-30 16:49:04 +0000466 // pointer size for now) CFStringEncoding -> i32 Boolean -> i8
Kate Stoneb9c1b512016-09-06 20:57:50 +0000467
468 Type *arg_type_array[5];
469
470 arg_type_array[0] = i8_ptr_ty;
471 arg_type_array[1] = i8_ptr_ty;
472 arg_type_array[2] = m_intptr_ty;
473 arg_type_array[3] = i32_ty;
474 arg_type_array[4] = i8_ty;
475
476 ArrayRef<Type *> CFSCWB_arg_types(arg_type_array, 5);
477
478 llvm::Type *CFSCWB_ty =
479 FunctionType::get(ns_str_ty, CFSCWB_arg_types, false);
480
481 // Build the constant containing the pointer to the function
482 PointerType *CFSCWB_ptr_ty = PointerType::getUnqual(CFSCWB_ty);
483 Constant *CFSCWB_addr_int =
484 ConstantInt::get(m_intptr_ty, CFStringCreateWithBytes_addr, false);
485 m_CFStringCreateWithBytes =
486 ConstantExpr::getIntToPtr(CFSCWB_addr_int, CFSCWB_ptr_ty);
487 }
488
489 ConstantDataSequential *string_array = NULL;
490
491 if (cstr)
492 string_array = dyn_cast<ConstantDataSequential>(cstr->getInitializer());
493
494 Constant *alloc_arg = Constant::getNullValue(i8_ptr_ty);
495 Constant *bytes_arg = cstr ? ConstantExpr::getBitCast(cstr, i8_ptr_ty)
496 : Constant::getNullValue(i8_ptr_ty);
497 Constant *numBytes_arg = ConstantInt::get(
Sean Callanancd1eb722016-12-01 17:46:51 +0000498 m_intptr_ty, cstr ? (string_array->getNumElements() - 1) * string_array->getElementByteSize() : 0, false);
499 int encoding_flags = 0;
Sean Callanan01341522016-12-01 19:14:55 +0000500 switch (cstr ? string_array->getElementByteSize() : 1) {
Sean Callanancd1eb722016-12-01 17:46:51 +0000501 case 1:
502 encoding_flags = 0x08000100; /* 0x08000100 is kCFStringEncodingUTF8 */
503 break;
504 case 2:
505 encoding_flags = 0x0100; /* 0x0100 is kCFStringEncodingUTF16 */
506 break;
507 case 4:
508 encoding_flags = 0x0c000100; /* 0x0c000100 is kCFStringEncodingUTF32 */
509 break;
510 default:
511 encoding_flags = 0x0600; /* fall back to 0x0600, kCFStringEncodingASCII */
Pavel Labath107d9bb2017-01-18 11:00:26 +0000512 LLDB_LOG(log, "Encountered an Objective-C constant string with unusual "
Luke Drummond63dea592016-12-22 19:15:07 +0000513 "element size {0}",
Pavel Labath107d9bb2017-01-18 11:00:26 +0000514 string_array->getElementByteSize());
Sean Callanancd1eb722016-12-01 17:46:51 +0000515 }
516 Constant *encoding_arg = ConstantInt::get(i32_ty, encoding_flags, false);
517 Constant *isExternal_arg =
518 ConstantInt::get(i8_ty, 0x0, false); /* 0x0 is false */
Kate Stoneb9c1b512016-09-06 20:57:50 +0000519
Sean Callanancd1eb722016-12-01 17:46:51 +0000520 Value *argument_array[5];
Kate Stoneb9c1b512016-09-06 20:57:50 +0000521
Sean Callanancd1eb722016-12-01 17:46:51 +0000522 argument_array[0] = alloc_arg;
523 argument_array[1] = bytes_arg;
524 argument_array[2] = numBytes_arg;
525 argument_array[3] = encoding_arg;
526 argument_array[4] = isExternal_arg;
Kate Stoneb9c1b512016-09-06 20:57:50 +0000527
Sean Callanancd1eb722016-12-01 17:46:51 +0000528 ArrayRef<Value *> CFSCWB_arguments(argument_array, 5);
Kate Stoneb9c1b512016-09-06 20:57:50 +0000529
Sean Callanancd1eb722016-12-01 17:46:51 +0000530 FunctionValueCache CFSCWB_Caller(
531 [this, &CFSCWB_arguments](llvm::Function *function) -> llvm::Value * {
532 return CallInst::Create(
533 m_CFStringCreateWithBytes, CFSCWB_arguments,
534 "CFStringCreateWithBytes",
535 llvm::cast<Instruction>(
536 m_entry_instruction_finder.GetValue(function)));
537 });
Kate Stoneb9c1b512016-09-06 20:57:50 +0000538
Sean Callanancd1eb722016-12-01 17:46:51 +0000539 if (!UnfoldConstant(ns_str, nullptr, CFSCWB_Caller, m_entry_instruction_finder,
540 m_error_stream)) {
541 if (log)
542 log->PutCString(
543 "Couldn't replace the NSString with the result of the call");
Kate Stoneb9c1b512016-09-06 20:57:50 +0000544
Sean Callanancd1eb722016-12-01 17:46:51 +0000545 m_error_stream.Printf("error [IRForTarget internal]: Couldn't replace an "
546 "Objective-C constant string with a dynamic "
547 "string\n");
Kate Stoneb9c1b512016-09-06 20:57:50 +0000548
Sean Callanancd1eb722016-12-01 17:46:51 +0000549 return false;
Kate Stoneb9c1b512016-09-06 20:57:50 +0000550 }
551
552 ns_str->eraseFromParent();
553
554 return true;
Sean Callanan549c9f72010-07-13 21:41:46 +0000555}
556
Kate Stoneb9c1b512016-09-06 20:57:50 +0000557bool IRForTarget::RewriteObjCConstStrings() {
558 lldb_private::Log *log(
559 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000560
Kate Stoneb9c1b512016-09-06 20:57:50 +0000561 ValueSymbolTable &value_symbol_table = m_module->getValueSymbolTable();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000562
Kate Stoneb9c1b512016-09-06 20:57:50 +0000563 for (ValueSymbolTable::iterator vi = value_symbol_table.begin(),
564 ve = value_symbol_table.end();
565 vi != ve; ++vi) {
566 std::string value_name = vi->first().str();
567 const char *value_name_cstr = value_name.c_str();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000568
Kate Stoneb9c1b512016-09-06 20:57:50 +0000569 if (strstr(value_name_cstr, "_unnamed_cfstring_")) {
570 Value *nsstring_value = vi->second;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000571
Kate Stoneb9c1b512016-09-06 20:57:50 +0000572 GlobalVariable *nsstring_global =
573 dyn_cast<GlobalVariable>(nsstring_value);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000574
Kate Stoneb9c1b512016-09-06 20:57:50 +0000575 if (!nsstring_global) {
576 if (log)
577 log->PutCString("NSString variable is not a GlobalVariable");
578
579 m_error_stream.Printf("Internal error [IRForTarget]: An Objective-C "
580 "constant string is not a global variable\n");
581
582 return false;
583 }
584
585 if (!nsstring_global->hasInitializer()) {
586 if (log)
587 log->PutCString("NSString variable does not have an initializer");
588
589 m_error_stream.Printf("Internal error [IRForTarget]: An Objective-C "
590 "constant string does not have an initializer\n");
591
592 return false;
593 }
594
595 ConstantStruct *nsstring_struct =
596 dyn_cast<ConstantStruct>(nsstring_global->getInitializer());
597
598 if (!nsstring_struct) {
599 if (log)
600 log->PutCString(
601 "NSString variable's initializer is not a ConstantStruct");
602
603 m_error_stream.Printf("Internal error [IRForTarget]: An Objective-C "
604 "constant string is not a structure constant\n");
605
606 return false;
607 }
608
609 // We expect the following structure:
610 //
611 // struct {
612 // int *isa;
613 // int flags;
614 // char *str;
615 // long length;
616 // };
617
618 if (nsstring_struct->getNumOperands() != 4) {
619 if (log)
620 log->Printf("NSString variable's initializer structure has an "
621 "unexpected number of members. Should be 4, is %d",
622 nsstring_struct->getNumOperands());
623
624 m_error_stream.Printf("Internal error [IRForTarget]: The struct for an "
625 "Objective-C constant string is not as "
626 "expected\n");
627
628 return false;
629 }
630
631 Constant *nsstring_member = nsstring_struct->getOperand(2);
632
633 if (!nsstring_member) {
634 if (log)
635 log->PutCString("NSString initializer's str element was empty");
636
637 m_error_stream.Printf("Internal error [IRForTarget]: An Objective-C "
638 "constant string does not have a string "
639 "initializer\n");
640
641 return false;
642 }
643
644 ConstantExpr *nsstring_expr = dyn_cast<ConstantExpr>(nsstring_member);
645
646 if (!nsstring_expr) {
647 if (log)
648 log->PutCString(
649 "NSString initializer's str element is not a ConstantExpr");
650
651 m_error_stream.Printf("Internal error [IRForTarget]: An Objective-C "
652 "constant string's string initializer is not "
653 "constant\n");
654
655 return false;
656 }
657
Sean Callanancd1eb722016-12-01 17:46:51 +0000658 GlobalVariable *cstr_global = nullptr;
Kate Stoneb9c1b512016-09-06 20:57:50 +0000659
Sean Callanancd1eb722016-12-01 17:46:51 +0000660 if (nsstring_expr->getOpcode() == Instruction::GetElementPtr) {
661 Constant *nsstring_cstr = nsstring_expr->getOperand(0);
662 cstr_global = dyn_cast<GlobalVariable>(nsstring_cstr);
663 } else if (nsstring_expr->getOpcode() == Instruction::BitCast) {
664 Constant *nsstring_cstr = nsstring_expr->getOperand(0);
665 cstr_global = dyn_cast<GlobalVariable>(nsstring_cstr);
Kate Stoneb9c1b512016-09-06 20:57:50 +0000666 }
667
Kate Stoneb9c1b512016-09-06 20:57:50 +0000668 if (!cstr_global) {
669 if (log)
670 log->PutCString(
671 "NSString initializer's str element is not a GlobalVariable");
672
Sean Callanancd1eb722016-12-01 17:46:51 +0000673 m_error_stream.Printf("Internal error [IRForTarget]: Unhandled"
674 "constant string initializer\n");
Kate Stoneb9c1b512016-09-06 20:57:50 +0000675
676 return false;
677 }
678
679 if (!cstr_global->hasInitializer()) {
680 if (log)
681 log->PutCString("NSString initializer's str element does not have an "
682 "initializer");
683
684 m_error_stream.Printf("Internal error [IRForTarget]: An Objective-C "
685 "constant string's string initializer doesn't "
686 "point to initialized data\n");
687
688 return false;
689 }
690
691 /*
692 if (!cstr_array)
693 {
694 if (log)
695 log->PutCString("NSString initializer's str element is not a
696 ConstantArray");
697
698 if (m_error_stream)
699 m_error_stream.Printf("Internal error [IRForTarget]: An
700 Objective-C constant string's string initializer doesn't point to an
701 array\n");
702
703 return false;
704 }
705
706 if (!cstr_array->isCString())
707 {
708 if (log)
709 log->PutCString("NSString initializer's str element is not a C
710 string array");
711
712 if (m_error_stream)
713 m_error_stream.Printf("Internal error [IRForTarget]: An
714 Objective-C constant string's string initializer doesn't point to a C
715 string\n");
716
717 return false;
718 }
719 */
720
721 ConstantDataArray *cstr_array =
722 dyn_cast<ConstantDataArray>(cstr_global->getInitializer());
723
724 if (log) {
725 if (cstr_array)
726 log->Printf("Found NSString constant %s, which contains \"%s\"",
727 value_name_cstr, cstr_array->getAsString().str().c_str());
728 else
729 log->Printf("Found NSString constant %s, which contains \"\"",
730 value_name_cstr);
731 }
732
733 if (!cstr_array)
734 cstr_global = NULL;
735
736 if (!RewriteObjCConstString(nsstring_global, cstr_global)) {
737 if (log)
738 log->PutCString("Error rewriting the constant string");
739
740 // We don't print an error message here because RewriteObjCConstString
741 // has done so for us.
742
743 return false;
744 }
745 }
746 }
747
748 for (ValueSymbolTable::iterator vi = value_symbol_table.begin(),
749 ve = value_symbol_table.end();
750 vi != ve; ++vi) {
751 std::string value_name = vi->first().str();
752 const char *value_name_cstr = value_name.c_str();
753
754 if (!strcmp(value_name_cstr, "__CFConstantStringClassReference")) {
755 GlobalVariable *gv = dyn_cast<GlobalVariable>(vi->second);
756
757 if (!gv) {
758 if (log)
759 log->PutCString(
760 "__CFConstantStringClassReference is not a global variable");
761
762 m_error_stream.Printf("Internal error [IRForTarget]: Found a "
763 "CFConstantStringClassReference, but it is not a "
764 "global object\n");
765
766 return false;
767 }
768
769 gv->eraseFromParent();
770
771 break;
772 }
773 }
774
775 return true;
Sean Callanan79763a42011-05-23 21:40:23 +0000776}
777
Kate Stoneb9c1b512016-09-06 20:57:50 +0000778static bool IsObjCSelectorRef(Value *value) {
779 GlobalVariable *global_variable = dyn_cast<GlobalVariable>(value);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000780
Jonas Devliegherea6682a42018-12-15 00:15:33 +0000781 return !(!global_variable || !global_variable->hasName() ||
782 !global_variable->getName().startswith("OBJC_SELECTOR_REFERENCES_"));
Kate Stoneb9c1b512016-09-06 20:57:50 +0000783}
784
785// This function does not report errors; its callers are responsible.
786bool IRForTarget::RewriteObjCSelector(Instruction *selector_load) {
787 lldb_private::Log *log(
788 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
789
790 LoadInst *load = dyn_cast<LoadInst>(selector_load);
791
792 if (!load)
793 return false;
794
795 // Unpack the message name from the selector. In LLVM IR, an objc_msgSend
796 // gets represented as
797 //
Adrian Prantl05097242018-04-30 16:49:04 +0000798 // %tmp = load i8** @"OBJC_SELECTOR_REFERENCES_" ; <i8*> %call = call
799 // i8* (i8*, i8*, ...)* @objc_msgSend(i8* %obj, i8* %tmp, ...) ; <i8*>
Kate Stoneb9c1b512016-09-06 20:57:50 +0000800 //
801 // where %obj is the object pointer and %tmp is the selector.
802 //
803 // @"OBJC_SELECTOR_REFERENCES_" is a pointer to a character array called
804 // @"\01L_OBJC_llvm_moduleETH_VAR_NAllvm_moduleE_".
805 // @"\01L_OBJC_llvm_moduleETH_VAR_NAllvm_moduleE_" contains the string.
806
807 // Find the pointer's initializer (a ConstantExpr with opcode GetElementPtr)
808 // and get the string from its target
809
810 GlobalVariable *_objc_selector_references_ =
811 dyn_cast<GlobalVariable>(load->getPointerOperand());
812
813 if (!_objc_selector_references_ ||
814 !_objc_selector_references_->hasInitializer())
815 return false;
816
817 Constant *osr_initializer = _objc_selector_references_->getInitializer();
818
819 ConstantExpr *osr_initializer_expr = dyn_cast<ConstantExpr>(osr_initializer);
820
821 if (!osr_initializer_expr ||
822 osr_initializer_expr->getOpcode() != Instruction::GetElementPtr)
823 return false;
824
825 Value *osr_initializer_base = osr_initializer_expr->getOperand(0);
826
827 if (!osr_initializer_base)
828 return false;
829
830 // Find the string's initializer (a ConstantArray) and get the string from it
831
832 GlobalVariable *_objc_meth_var_name_ =
833 dyn_cast<GlobalVariable>(osr_initializer_base);
834
835 if (!_objc_meth_var_name_ || !_objc_meth_var_name_->hasInitializer())
836 return false;
837
838 Constant *omvn_initializer = _objc_meth_var_name_->getInitializer();
839
840 ConstantDataArray *omvn_initializer_array =
841 dyn_cast<ConstantDataArray>(omvn_initializer);
842
843 if (!omvn_initializer_array->isString())
844 return false;
845
846 std::string omvn_initializer_string = omvn_initializer_array->getAsString();
847
848 if (log)
849 log->Printf("Found Objective-C selector reference \"%s\"",
850 omvn_initializer_string.c_str());
851
852 // Construct a call to sel_registerName
853
854 if (!m_sel_registerName) {
855 lldb::addr_t sel_registerName_addr;
856
857 static lldb_private::ConstString g_sel_registerName_str("sel_registerName");
858 sel_registerName_addr = m_execution_unit.FindSymbol(g_sel_registerName_str);
859 if (sel_registerName_addr == LLDB_INVALID_ADDRESS)
860 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000861
Sean Callananc70ed462011-10-25 18:36:40 +0000862 if (log)
Kate Stoneb9c1b512016-09-06 20:57:50 +0000863 log->Printf("Found sel_registerName at 0x%" PRIx64,
864 sel_registerName_addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000865
Adrian Prantl05097242018-04-30 16:49:04 +0000866 // Build the function type: struct objc_selector
867 // *sel_registerName(uint8_t*)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000868
Kate Stoneb9c1b512016-09-06 20:57:50 +0000869 // The below code would be "more correct," but in actuality what's required
870 // is uint8_t*
871 // Type *sel_type = StructType::get(m_module->getContext());
872 // Type *sel_ptr_type = PointerType::getUnqual(sel_type);
873 Type *sel_ptr_type = Type::getInt8PtrTy(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000874
Kate Stoneb9c1b512016-09-06 20:57:50 +0000875 Type *type_array[1];
876
877 type_array[0] = llvm::Type::getInt8PtrTy(m_module->getContext());
878
879 ArrayRef<Type *> srN_arg_types(type_array, 1);
880
881 llvm::Type *srN_type =
882 FunctionType::get(sel_ptr_type, srN_arg_types, false);
883
884 // Build the constant containing the pointer to the function
885 PointerType *srN_ptr_ty = PointerType::getUnqual(srN_type);
886 Constant *srN_addr_int =
887 ConstantInt::get(m_intptr_ty, sel_registerName_addr, false);
888 m_sel_registerName = ConstantExpr::getIntToPtr(srN_addr_int, srN_ptr_ty);
889 }
890
891 Value *argument_array[1];
892
893 Constant *omvn_pointer = ConstantExpr::getBitCast(
894 _objc_meth_var_name_, Type::getInt8PtrTy(m_module->getContext()));
895
896 argument_array[0] = omvn_pointer;
897
898 ArrayRef<Value *> srN_arguments(argument_array, 1);
899
900 CallInst *srN_call = CallInst::Create(m_sel_registerName, srN_arguments,
901 "sel_registerName", selector_load);
902
903 // Replace the load with the call in all users
904
905 selector_load->replaceAllUsesWith(srN_call);
906
907 selector_load->eraseFromParent();
908
909 return true;
910}
911
912bool IRForTarget::RewriteObjCSelectors(BasicBlock &basic_block) {
913 lldb_private::Log *log(
914 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
915
916 BasicBlock::iterator ii;
917
918 typedef SmallVector<Instruction *, 2> InstrList;
919 typedef InstrList::iterator InstrIterator;
920
921 InstrList selector_loads;
922
923 for (ii = basic_block.begin(); ii != basic_block.end(); ++ii) {
924 Instruction &inst = *ii;
925
926 if (LoadInst *load = dyn_cast<LoadInst>(&inst))
927 if (IsObjCSelectorRef(load->getPointerOperand()))
928 selector_loads.push_back(&inst);
929 }
930
931 InstrIterator iter;
932
933 for (iter = selector_loads.begin(); iter != selector_loads.end(); ++iter) {
934 if (!RewriteObjCSelector(*iter)) {
935 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't change a "
936 "static reference to an Objective-C selector to a "
937 "dynamic reference\n");
938
939 if (log)
940 log->PutCString(
941 "Couldn't rewrite a reference to an Objective-C selector");
942
943 return false;
Sean Callananc70ed462011-10-25 18:36:40 +0000944 }
Kate Stoneb9c1b512016-09-06 20:57:50 +0000945 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000946
Kate Stoneb9c1b512016-09-06 20:57:50 +0000947 return true;
948}
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000949
Sean Callananac900582016-09-29 00:45:33 +0000950static bool IsObjCClassReference(Value *value) {
951 GlobalVariable *global_variable = dyn_cast<GlobalVariable>(value);
952
Jonas Devliegherea6682a42018-12-15 00:15:33 +0000953 return !(!global_variable || !global_variable->hasName() ||
954 !global_variable->getName().startswith("OBJC_CLASS_REFERENCES_"));
Sean Callananac900582016-09-29 00:45:33 +0000955}
956
957// This function does not report errors; its callers are responsible.
958bool IRForTarget::RewriteObjCClassReference(Instruction *class_load) {
959 lldb_private::Log *log(
960 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
961
962 LoadInst *load = dyn_cast<LoadInst>(class_load);
963
964 if (!load)
965 return false;
966
967 // Unpack the class name from the reference. In LLVM IR, a reference to an
968 // Objective-C class gets represented as
969 //
970 // %tmp = load %struct._objc_class*,
971 // %struct._objc_class** @OBJC_CLASS_REFERENCES_, align 4
972 //
973 // @"OBJC_CLASS_REFERENCES_ is a bitcast of a character array called
Adrian Prantl05097242018-04-30 16:49:04 +0000974 // @OBJC_CLASS_NAME_. @OBJC_CLASS_NAME contains the string.
Sean Callananac900582016-09-29 00:45:33 +0000975
Adrian Prantl05097242018-04-30 16:49:04 +0000976 // Find the pointer's initializer (a ConstantExpr with opcode BitCast) and
977 // get the string from its target
Sean Callananac900582016-09-29 00:45:33 +0000978
979 GlobalVariable *_objc_class_references_ =
980 dyn_cast<GlobalVariable>(load->getPointerOperand());
981
982 if (!_objc_class_references_ ||
983 !_objc_class_references_->hasInitializer())
984 return false;
985
986 Constant *ocr_initializer = _objc_class_references_->getInitializer();
987
988 ConstantExpr *ocr_initializer_expr = dyn_cast<ConstantExpr>(ocr_initializer);
989
990 if (!ocr_initializer_expr ||
991 ocr_initializer_expr->getOpcode() != Instruction::BitCast)
992 return false;
993
994 Value *ocr_initializer_base = ocr_initializer_expr->getOperand(0);
995
996 if (!ocr_initializer_base)
997 return false;
998
999 // Find the string's initializer (a ConstantArray) and get the string from it
1000
1001 GlobalVariable *_objc_class_name_ =
1002 dyn_cast<GlobalVariable>(ocr_initializer_base);
1003
1004 if (!_objc_class_name_ || !_objc_class_name_->hasInitializer())
1005 return false;
1006
1007 Constant *ocn_initializer = _objc_class_name_->getInitializer();
1008
1009 ConstantDataArray *ocn_initializer_array =
1010 dyn_cast<ConstantDataArray>(ocn_initializer);
1011
1012 if (!ocn_initializer_array->isString())
1013 return false;
1014
1015 std::string ocn_initializer_string = ocn_initializer_array->getAsString();
1016
1017 if (log)
1018 log->Printf("Found Objective-C class reference \"%s\"",
1019 ocn_initializer_string.c_str());
1020
1021 // Construct a call to objc_getClass
1022
1023 if (!m_objc_getClass) {
1024 lldb::addr_t objc_getClass_addr;
1025
1026 static lldb_private::ConstString g_objc_getClass_str("objc_getClass");
1027 objc_getClass_addr = m_execution_unit.FindSymbol(g_objc_getClass_str);
1028 if (objc_getClass_addr == LLDB_INVALID_ADDRESS)
1029 return false;
1030
1031 if (log)
1032 log->Printf("Found objc_getClass at 0x%" PRIx64,
1033 objc_getClass_addr);
1034
1035 // Build the function type: %struct._objc_class *objc_getClass(i8*)
1036
1037 Type *class_type = load->getType();
1038 Type *type_array[1];
1039 type_array[0] = llvm::Type::getInt8PtrTy(m_module->getContext());
1040
1041 ArrayRef<Type *> ogC_arg_types(type_array, 1);
1042
1043 llvm::Type *ogC_type =
1044 FunctionType::get(class_type, ogC_arg_types, false);
1045
1046 // Build the constant containing the pointer to the function
1047 PointerType *ogC_ptr_ty = PointerType::getUnqual(ogC_type);
1048 Constant *ogC_addr_int =
1049 ConstantInt::get(m_intptr_ty, objc_getClass_addr, false);
1050 m_objc_getClass = ConstantExpr::getIntToPtr(ogC_addr_int, ogC_ptr_ty);
1051 }
1052
1053 Value *argument_array[1];
1054
1055 Constant *ocn_pointer = ConstantExpr::getBitCast(
1056 _objc_class_name_, Type::getInt8PtrTy(m_module->getContext()));
1057
1058 argument_array[0] = ocn_pointer;
1059
1060 ArrayRef<Value *> ogC_arguments(argument_array, 1);
1061
1062 CallInst *ogC_call = CallInst::Create(m_objc_getClass, ogC_arguments,
1063 "objc_getClass", class_load);
1064
1065 // Replace the load with the call in all users
1066
1067 class_load->replaceAllUsesWith(ogC_call);
1068
1069 class_load->eraseFromParent();
1070
1071 return true;
1072}
1073
1074bool IRForTarget::RewriteObjCClassReferences(BasicBlock &basic_block) {
1075 lldb_private::Log *log(
1076 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1077
1078 BasicBlock::iterator ii;
1079
1080 typedef SmallVector<Instruction *, 2> InstrList;
1081 typedef InstrList::iterator InstrIterator;
1082
1083 InstrList class_loads;
1084
1085 for (ii = basic_block.begin(); ii != basic_block.end(); ++ii) {
1086 Instruction &inst = *ii;
1087
1088 if (LoadInst *load = dyn_cast<LoadInst>(&inst))
1089 if (IsObjCClassReference(load->getPointerOperand()))
1090 class_loads.push_back(&inst);
1091 }
1092
1093 InstrIterator iter;
1094
1095 for (iter = class_loads.begin(); iter != class_loads.end(); ++iter) {
1096 if (!RewriteObjCClassReference(*iter)) {
1097 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't change a "
1098 "static reference to an Objective-C class to a "
1099 "dynamic reference\n");
1100
1101 if (log)
1102 log->PutCString(
1103 "Couldn't rewrite a reference to an Objective-C class");
1104
1105 return false;
1106 }
1107 }
1108
1109 return true;
1110}
1111
Kate Stoneb9c1b512016-09-06 20:57:50 +00001112// This function does not report errors; its callers are responsible.
1113bool IRForTarget::RewritePersistentAlloc(llvm::Instruction *persistent_alloc) {
1114 lldb_private::Log *log(
1115 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001116
Kate Stoneb9c1b512016-09-06 20:57:50 +00001117 AllocaInst *alloc = dyn_cast<AllocaInst>(persistent_alloc);
Sean Callanan1f9db3e2013-06-28 21:44:15 +00001118
Kate Stoneb9c1b512016-09-06 20:57:50 +00001119 MDNode *alloc_md = alloc->getMetadata("clang.decl.ptr");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001120
Kate Stoneb9c1b512016-09-06 20:57:50 +00001121 if (!alloc_md || !alloc_md->getNumOperands())
1122 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001123
Kate Stoneb9c1b512016-09-06 20:57:50 +00001124 ConstantInt *constant_int =
1125 mdconst::dyn_extract<ConstantInt>(alloc_md->getOperand(0));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001126
Kate Stoneb9c1b512016-09-06 20:57:50 +00001127 if (!constant_int)
1128 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001129
Kate Stoneb9c1b512016-09-06 20:57:50 +00001130 // We attempt to register this as a new persistent variable with the DeclMap.
Sean Callanan1f9db3e2013-06-28 21:44:15 +00001131
Kate Stoneb9c1b512016-09-06 20:57:50 +00001132 uintptr_t ptr = constant_int->getZExtValue();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001133
Kate Stoneb9c1b512016-09-06 20:57:50 +00001134 clang::VarDecl *decl = reinterpret_cast<clang::VarDecl *>(ptr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001135
Kate Stoneb9c1b512016-09-06 20:57:50 +00001136 lldb_private::TypeFromParser result_decl_type(
1137 decl->getType().getAsOpaquePtr(),
1138 lldb_private::ClangASTContext::GetASTContext(&decl->getASTContext()));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001139
Kate Stoneb9c1b512016-09-06 20:57:50 +00001140 StringRef decl_name(decl->getName());
1141 lldb_private::ConstString persistent_variable_name(decl_name.data(),
1142 decl_name.size());
1143 if (!m_decl_map->AddPersistentVariable(decl, persistent_variable_name,
1144 result_decl_type, false, false))
1145 return false;
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001146
Kate Stoneb9c1b512016-09-06 20:57:50 +00001147 GlobalVariable *persistent_global = new GlobalVariable(
1148 (*m_module), alloc->getType(), false, /* not constant */
1149 GlobalValue::ExternalLinkage, NULL, /* no initializer */
Malcolm Parsons771ef6d2016-11-02 20:34:10 +00001150 alloc->getName().str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001151
Adrian Prantl05097242018-04-30 16:49:04 +00001152 // What we're going to do here is make believe this was a regular old
1153 // external variable. That means we need to make the metadata valid.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001154
Kate Stoneb9c1b512016-09-06 20:57:50 +00001155 NamedMDNode *named_metadata =
1156 m_module->getOrInsertNamedMetadata("clang.global.decl.ptrs");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001157
Kate Stoneb9c1b512016-09-06 20:57:50 +00001158 llvm::Metadata *values[2];
1159 values[0] = ConstantAsMetadata::get(persistent_global);
1160 values[1] = ConstantAsMetadata::get(constant_int);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001161
Kate Stoneb9c1b512016-09-06 20:57:50 +00001162 ArrayRef<llvm::Metadata *> value_ref(values, 2);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001163
Kate Stoneb9c1b512016-09-06 20:57:50 +00001164 MDNode *persistent_global_md = MDNode::get(m_module->getContext(), value_ref);
1165 named_metadata->addOperand(persistent_global_md);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001166
Kate Stoneb9c1b512016-09-06 20:57:50 +00001167 // Now, since the variable is a pointer variable, we will drop in a load of
Adrian Prantl05097242018-04-30 16:49:04 +00001168 // that pointer variable.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001169
Kate Stoneb9c1b512016-09-06 20:57:50 +00001170 LoadInst *persistent_load = new LoadInst(persistent_global, "", alloc);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001171
Kate Stoneb9c1b512016-09-06 20:57:50 +00001172 if (log)
1173 log->Printf("Replacing \"%s\" with \"%s\"", PrintValue(alloc).c_str(),
1174 PrintValue(persistent_load).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001175
Kate Stoneb9c1b512016-09-06 20:57:50 +00001176 alloc->replaceAllUsesWith(persistent_load);
1177 alloc->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001178
Kate Stoneb9c1b512016-09-06 20:57:50 +00001179 return true;
1180}
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001181
Kate Stoneb9c1b512016-09-06 20:57:50 +00001182bool IRForTarget::RewritePersistentAllocs(llvm::BasicBlock &basic_block) {
1183 if (!m_resolve_vars)
1184 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001185
Kate Stoneb9c1b512016-09-06 20:57:50 +00001186 lldb_private::Log *log(
1187 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001188
Kate Stoneb9c1b512016-09-06 20:57:50 +00001189 BasicBlock::iterator ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001190
Kate Stoneb9c1b512016-09-06 20:57:50 +00001191 typedef SmallVector<Instruction *, 2> InstrList;
1192 typedef InstrList::iterator InstrIterator;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001193
Kate Stoneb9c1b512016-09-06 20:57:50 +00001194 InstrList pvar_allocs;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001195
Kate Stoneb9c1b512016-09-06 20:57:50 +00001196 for (ii = basic_block.begin(); ii != basic_block.end(); ++ii) {
1197 Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001198
Kate Stoneb9c1b512016-09-06 20:57:50 +00001199 if (AllocaInst *alloc = dyn_cast<AllocaInst>(&inst)) {
1200 llvm::StringRef alloc_name = alloc->getName();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001201
Kate Stoneb9c1b512016-09-06 20:57:50 +00001202 if (alloc_name.startswith("$") && !alloc_name.startswith("$__lldb")) {
1203 if (alloc_name.find_first_of("0123456789") == 1) {
1204 if (log)
1205 log->Printf("Rejecting a numeric persistent variable.");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001206
Kate Stoneb9c1b512016-09-06 20:57:50 +00001207 m_error_stream.Printf("Error [IRForTarget]: Names starting with $0, "
1208 "$1, ... are reserved for use as result "
1209 "names\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001210
Kate Stoneb9c1b512016-09-06 20:57:50 +00001211 return false;
Sean Callanan00294b32016-03-22 21:05:51 +00001212 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001213
Kate Stoneb9c1b512016-09-06 20:57:50 +00001214 pvar_allocs.push_back(alloc);
1215 }
Sean Callanan17827832010-12-13 22:46:15 +00001216 }
Kate Stoneb9c1b512016-09-06 20:57:50 +00001217 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001218
Kate Stoneb9c1b512016-09-06 20:57:50 +00001219 InstrIterator iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001220
Kate Stoneb9c1b512016-09-06 20:57:50 +00001221 for (iter = pvar_allocs.begin(); iter != pvar_allocs.end(); ++iter) {
1222 if (!RewritePersistentAlloc(*iter)) {
1223 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't rewrite "
1224 "the creation of a persistent variable\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001225
Kate Stoneb9c1b512016-09-06 20:57:50 +00001226 if (log)
1227 log->PutCString(
1228 "Couldn't rewrite the creation of a persistent variable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001229
Kate Stoneb9c1b512016-09-06 20:57:50 +00001230 return false;
Sean Callanan2ab712f22010-07-03 01:35:46 +00001231 }
Kate Stoneb9c1b512016-09-06 20:57:50 +00001232 }
1233
1234 return true;
1235}
1236
1237bool IRForTarget::MaterializeInitializer(uint8_t *data, Constant *initializer) {
1238 if (!initializer)
1239 return true;
1240
1241 lldb_private::Log *log(
1242 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1243
1244 if (log && log->GetVerbose())
1245 log->Printf(" MaterializeInitializer(%p, %s)", (void *)data,
1246 PrintValue(initializer).c_str());
1247
1248 Type *initializer_type = initializer->getType();
1249
1250 if (ConstantInt *int_initializer = dyn_cast<ConstantInt>(initializer)) {
1251 size_t constant_size = m_target_data->getTypeStoreSize(initializer_type);
1252 lldb_private::Scalar scalar = int_initializer->getValue().zextOrTrunc(
1253 llvm::NextPowerOf2(constant_size) * 8);
1254
Zachary Turner97206d52017-05-12 04:51:55 +00001255 lldb_private::Status get_data_error;
Jonas Devliegherea6682a42018-12-15 00:15:33 +00001256 return scalar.GetAsMemoryData(data, constant_size,
1257 lldb_private::endian::InlHostByteOrder(),
1258 get_data_error) != 0;
Kate Stoneb9c1b512016-09-06 20:57:50 +00001259 } else if (ConstantDataArray *array_initializer =
1260 dyn_cast<ConstantDataArray>(initializer)) {
1261 if (array_initializer->isString()) {
1262 std::string array_initializer_string = array_initializer->getAsString();
1263 memcpy(data, array_initializer_string.c_str(),
1264 m_target_data->getTypeStoreSize(initializer_type));
1265 } else {
1266 ArrayType *array_initializer_type = array_initializer->getType();
1267 Type *array_element_type = array_initializer_type->getElementType();
1268
1269 size_t element_size = m_target_data->getTypeAllocSize(array_element_type);
1270
1271 for (unsigned i = 0; i < array_initializer->getNumOperands(); ++i) {
1272 Value *operand_value = array_initializer->getOperand(i);
1273 Constant *operand_constant = dyn_cast<Constant>(operand_value);
1274
1275 if (!operand_constant)
1276 return false;
1277
1278 if (!MaterializeInitializer(data + (i * element_size),
1279 operand_constant))
1280 return false;
1281 }
1282 }
1283 return true;
1284 } else if (ConstantStruct *struct_initializer =
1285 dyn_cast<ConstantStruct>(initializer)) {
1286 StructType *struct_initializer_type = struct_initializer->getType();
1287 const StructLayout *struct_layout =
1288 m_target_data->getStructLayout(struct_initializer_type);
1289
1290 for (unsigned i = 0; i < struct_initializer->getNumOperands(); ++i) {
1291 if (!MaterializeInitializer(data + struct_layout->getElementOffset(i),
1292 struct_initializer->getOperand(i)))
1293 return false;
1294 }
1295 return true;
1296 } else if (isa<ConstantAggregateZero>(initializer)) {
1297 memset(data, 0, m_target_data->getTypeStoreSize(initializer_type));
1298 return true;
1299 }
1300 return false;
Sean Callanan2ab712f22010-07-03 01:35:46 +00001301}
1302
Kate Stoneb9c1b512016-09-06 20:57:50 +00001303// This function does not report errors; its callers are responsible.
1304bool IRForTarget::MaybeHandleVariable(Value *llvm_value_ptr) {
1305 lldb_private::Log *log(
1306 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1307
1308 if (log)
1309 log->Printf("MaybeHandleVariable (%s)", PrintValue(llvm_value_ptr).c_str());
1310
1311 if (ConstantExpr *constant_expr = dyn_cast<ConstantExpr>(llvm_value_ptr)) {
1312 switch (constant_expr->getOpcode()) {
1313 default:
1314 break;
1315 case Instruction::GetElementPtr:
1316 case Instruction::BitCast:
1317 Value *s = constant_expr->getOperand(0);
1318 if (!MaybeHandleVariable(s))
1319 return false;
1320 }
1321 } else if (GlobalVariable *global_variable =
1322 dyn_cast<GlobalVariable>(llvm_value_ptr)) {
1323 if (!GlobalValue::isExternalLinkage(global_variable->getLinkage()))
1324 return true;
1325
1326 clang::NamedDecl *named_decl = DeclForGlobal(global_variable);
1327
1328 if (!named_decl) {
1329 if (IsObjCSelectorRef(llvm_value_ptr))
1330 return true;
1331
1332 if (!global_variable->hasExternalLinkage())
1333 return true;
1334
1335 if (log)
1336 log->Printf("Found global variable \"%s\" without metadata",
1337 global_variable->getName().str().c_str());
1338
1339 return false;
1340 }
1341
1342 std::string name(named_decl->getName().str());
1343
1344 clang::ValueDecl *value_decl = dyn_cast<clang::ValueDecl>(named_decl);
1345 if (value_decl == NULL)
1346 return false;
1347
1348 lldb_private::CompilerType compiler_type(&value_decl->getASTContext(),
1349 value_decl->getType());
1350
1351 const Type *value_type = NULL;
1352
1353 if (name[0] == '$') {
1354 // The $__lldb_expr_result name indicates the return value has allocated
Adrian Prantl05097242018-04-30 16:49:04 +00001355 // as a static variable. Per the comment at
1356 // ASTResultSynthesizer::SynthesizeBodyResult, accesses to this static
1357 // variable need to be redirected to the result of dereferencing a
1358 // pointer that is passed in as one of the arguments.
Kate Stoneb9c1b512016-09-06 20:57:50 +00001359 //
1360 // Consequently, when reporting the size of the type, we report a pointer
Adrian Prantl05097242018-04-30 16:49:04 +00001361 // type pointing to the type of $__lldb_expr_result, not the type itself.
Kate Stoneb9c1b512016-09-06 20:57:50 +00001362 //
1363 // We also do this for any user-declared persistent variables.
1364 compiler_type = compiler_type.GetPointerType();
1365 value_type = PointerType::get(global_variable->getType(), 0);
1366 } else {
1367 value_type = global_variable->getType();
1368 }
1369
1370 const uint64_t value_size = compiler_type.GetByteSize(nullptr);
1371 lldb::offset_t value_alignment =
1372 (compiler_type.GetTypeBitAlign() + 7ull) / 8ull;
1373
1374 if (log) {
1375 log->Printf("Type of \"%s\" is [clang \"%s\", llvm \"%s\"] [size %" PRIu64
1376 ", align %" PRIu64 "]",
1377 name.c_str(),
1378 lldb_private::ClangUtil::GetQualType(compiler_type)
1379 .getAsString()
1380 .c_str(),
1381 PrintType(value_type).c_str(), value_size, value_alignment);
1382 }
1383
1384 if (named_decl &&
1385 !m_decl_map->AddValueToStruct(
1386 named_decl, lldb_private::ConstString(name.c_str()), llvm_value_ptr,
1387 value_size, value_alignment)) {
1388 if (!global_variable->hasExternalLinkage())
1389 return true;
1390 else
1391 return true;
1392 }
1393 } else if (dyn_cast<llvm::Function>(llvm_value_ptr)) {
1394 if (log)
1395 log->Printf("Function pointers aren't handled right now");
1396
1397 return false;
1398 }
1399
1400 return true;
Sean Callanan2ab712f22010-07-03 01:35:46 +00001401}
1402
Kate Stoneb9c1b512016-09-06 20:57:50 +00001403// This function does not report errors; its callers are responsible.
1404bool IRForTarget::HandleSymbol(Value *symbol) {
1405 lldb_private::Log *log(
1406 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1407
1408 lldb_private::ConstString name(symbol->getName().str().c_str());
1409
1410 lldb::addr_t symbol_addr =
1411 m_decl_map->GetSymbolAddress(name, lldb::eSymbolTypeAny);
1412
1413 if (symbol_addr == LLDB_INVALID_ADDRESS) {
1414 if (log)
1415 log->Printf("Symbol \"%s\" had no address", name.GetCString());
1416
1417 return false;
1418 }
1419
1420 if (log)
1421 log->Printf("Found \"%s\" at 0x%" PRIx64, name.GetCString(), symbol_addr);
1422
1423 Type *symbol_type = symbol->getType();
1424
1425 Constant *symbol_addr_int = ConstantInt::get(m_intptr_ty, symbol_addr, false);
1426
1427 Value *symbol_addr_ptr =
1428 ConstantExpr::getIntToPtr(symbol_addr_int, symbol_type);
1429
1430 if (log)
1431 log->Printf("Replacing %s with %s", PrintValue(symbol).c_str(),
1432 PrintValue(symbol_addr_ptr).c_str());
1433
1434 symbol->replaceAllUsesWith(symbol_addr_ptr);
1435
1436 return true;
1437}
1438
1439bool IRForTarget::MaybeHandleCallArguments(CallInst *Old) {
1440 lldb_private::Log *log(
1441 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1442
1443 if (log)
1444 log->Printf("MaybeHandleCallArguments(%s)", PrintValue(Old).c_str());
1445
1446 for (unsigned op_index = 0, num_ops = Old->getNumArgOperands();
1447 op_index < num_ops; ++op_index)
1448 if (!MaybeHandleVariable(Old->getArgOperand(
1449 op_index))) // conservatively believe that this is a store
1450 {
1451 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't rewrite "
1452 "one of the arguments of a function call.\n");
1453
1454 return false;
1455 }
1456
1457 return true;
1458}
1459
1460bool IRForTarget::HandleObjCClass(Value *classlist_reference) {
1461 lldb_private::Log *log(
1462 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1463
1464 GlobalVariable *global_variable =
1465 dyn_cast<GlobalVariable>(classlist_reference);
1466
1467 if (!global_variable)
1468 return false;
1469
1470 Constant *initializer = global_variable->getInitializer();
1471
1472 if (!initializer)
1473 return false;
1474
1475 if (!initializer->hasName())
1476 return false;
1477
1478 StringRef name(initializer->getName());
1479 lldb_private::ConstString name_cstr(name.str().c_str());
1480 lldb::addr_t class_ptr =
1481 m_decl_map->GetSymbolAddress(name_cstr, lldb::eSymbolTypeObjCClass);
1482
1483 if (log)
1484 log->Printf("Found reference to Objective-C class %s (0x%llx)",
1485 name_cstr.AsCString(), (unsigned long long)class_ptr);
1486
1487 if (class_ptr == LLDB_INVALID_ADDRESS)
1488 return false;
1489
1490 if (global_variable->use_empty())
1491 return false;
1492
1493 SmallVector<LoadInst *, 2> load_instructions;
1494
1495 for (llvm::User *u : global_variable->users()) {
1496 if (LoadInst *load_instruction = dyn_cast<LoadInst>(u))
1497 load_instructions.push_back(load_instruction);
1498 }
1499
1500 if (load_instructions.empty())
1501 return false;
1502
1503 Constant *class_addr = ConstantInt::get(m_intptr_ty, (uint64_t)class_ptr);
1504
1505 for (LoadInst *load_instruction : load_instructions) {
1506 Constant *class_bitcast =
1507 ConstantExpr::getIntToPtr(class_addr, load_instruction->getType());
1508
1509 load_instruction->replaceAllUsesWith(class_bitcast);
1510
1511 load_instruction->eraseFromParent();
1512 }
1513
1514 return true;
1515}
1516
1517bool IRForTarget::RemoveCXAAtExit(BasicBlock &basic_block) {
1518 BasicBlock::iterator ii;
1519
1520 std::vector<CallInst *> calls_to_remove;
1521
1522 for (ii = basic_block.begin(); ii != basic_block.end(); ++ii) {
1523 Instruction &inst = *ii;
1524
1525 CallInst *call = dyn_cast<CallInst>(&inst);
1526
1527 // MaybeHandleCallArguments handles error reporting; we are silent here
1528 if (!call)
1529 continue;
1530
1531 bool remove = false;
1532
1533 llvm::Function *func = call->getCalledFunction();
1534
1535 if (func && func->getName() == "__cxa_atexit")
1536 remove = true;
1537
1538 llvm::Value *val = call->getCalledValue();
1539
1540 if (val && val->getName() == "__cxa_atexit")
1541 remove = true;
1542
1543 if (remove)
1544 calls_to_remove.push_back(call);
1545 }
1546
1547 for (std::vector<CallInst *>::iterator ci = calls_to_remove.begin(),
1548 ce = calls_to_remove.end();
1549 ci != ce; ++ci) {
1550 (*ci)->eraseFromParent();
1551 }
1552
1553 return true;
1554}
1555
1556bool IRForTarget::ResolveCalls(BasicBlock &basic_block) {
1557 /////////////////////////////////////////////////////////////////////////
1558 // Prepare the current basic block for execution in the remote process
1559 //
1560
1561 BasicBlock::iterator ii;
1562
1563 for (ii = basic_block.begin(); ii != basic_block.end(); ++ii) {
1564 Instruction &inst = *ii;
1565
1566 CallInst *call = dyn_cast<CallInst>(&inst);
1567
1568 // MaybeHandleCallArguments handles error reporting; we are silent here
1569 if (call && !MaybeHandleCallArguments(call))
1570 return false;
1571 }
1572
1573 return true;
1574}
1575
1576bool IRForTarget::ResolveExternals(Function &llvm_function) {
1577 lldb_private::Log *log(
1578 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1579
1580 for (GlobalVariable &global_var : m_module->globals()) {
1581 std::string global_name = global_var.getName().str();
1582
1583 if (log)
1584 log->Printf("Examining %s, DeclForGlobalValue returns %p",
1585 global_name.c_str(),
1586 static_cast<void *>(DeclForGlobal(&global_var)));
1587
1588 if (global_name.find("OBJC_IVAR") == 0) {
1589 if (!HandleSymbol(&global_var)) {
1590 m_error_stream.Printf("Error [IRForTarget]: Couldn't find Objective-C "
1591 "indirect ivar symbol %s\n",
1592 global_name.c_str());
1593
1594 return false;
1595 }
1596 } else if (global_name.find("OBJC_CLASSLIST_REFERENCES_$") !=
1597 global_name.npos) {
1598 if (!HandleObjCClass(&global_var)) {
1599 m_error_stream.Printf("Error [IRForTarget]: Couldn't resolve the class "
1600 "for an Objective-C static method call\n");
1601
1602 return false;
1603 }
1604 } else if (global_name.find("OBJC_CLASSLIST_SUP_REFS_$") !=
1605 global_name.npos) {
1606 if (!HandleObjCClass(&global_var)) {
1607 m_error_stream.Printf("Error [IRForTarget]: Couldn't resolve the class "
1608 "for an Objective-C static method call\n");
1609
1610 return false;
1611 }
1612 } else if (DeclForGlobal(&global_var)) {
1613 if (!MaybeHandleVariable(&global_var)) {
1614 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't rewrite "
1615 "external variable %s\n",
1616 global_name.c_str());
1617
1618 return false;
1619 }
1620 }
1621 }
1622
1623 return true;
1624}
1625
1626static bool isGuardVariableRef(Value *V) {
1627 Constant *Old = NULL;
1628
1629 if (!(Old = dyn_cast<Constant>(V)))
1630 return false;
1631
1632 ConstantExpr *CE = NULL;
1633
1634 if ((CE = dyn_cast<ConstantExpr>(V))) {
1635 if (CE->getOpcode() != Instruction::BitCast)
1636 return false;
1637
1638 Old = CE->getOperand(0);
1639 }
1640
1641 GlobalVariable *GV = dyn_cast<GlobalVariable>(Old);
1642
1643 if (!GV || !GV->hasName() ||
1644 (!GV->getName().startswith("_ZGV") && // Itanium ABI guard variable
1645 !GV->getName().endswith("@4IA"))) // Microsoft ABI guard variable
1646 {
1647 return false;
1648 }
1649
1650 return true;
1651}
1652
1653void IRForTarget::TurnGuardLoadIntoZero(llvm::Instruction *guard_load) {
1654 Constant *zero(Constant::getNullValue(guard_load->getType()));
1655 guard_load->replaceAllUsesWith(zero);
1656 guard_load->eraseFromParent();
1657}
1658
1659static void ExciseGuardStore(Instruction *guard_store) {
1660 guard_store->eraseFromParent();
1661}
1662
1663bool IRForTarget::RemoveGuards(BasicBlock &basic_block) {
1664 ///////////////////////////////////////////////////////
1665 // Eliminate any reference to guard variables found.
1666 //
1667
1668 BasicBlock::iterator ii;
1669
1670 typedef SmallVector<Instruction *, 2> InstrList;
1671 typedef InstrList::iterator InstrIterator;
1672
1673 InstrList guard_loads;
1674 InstrList guard_stores;
1675
1676 for (ii = basic_block.begin(); ii != basic_block.end(); ++ii) {
1677 Instruction &inst = *ii;
1678
1679 if (LoadInst *load = dyn_cast<LoadInst>(&inst))
1680 if (isGuardVariableRef(load->getPointerOperand()))
1681 guard_loads.push_back(&inst);
1682
1683 if (StoreInst *store = dyn_cast<StoreInst>(&inst))
1684 if (isGuardVariableRef(store->getPointerOperand()))
1685 guard_stores.push_back(&inst);
1686 }
1687
1688 InstrIterator iter;
1689
1690 for (iter = guard_loads.begin(); iter != guard_loads.end(); ++iter)
1691 TurnGuardLoadIntoZero(*iter);
1692
1693 for (iter = guard_stores.begin(); iter != guard_stores.end(); ++iter)
1694 ExciseGuardStore(*iter);
1695
1696 return true;
1697}
1698
1699// This function does not report errors; its callers are responsible.
1700bool IRForTarget::UnfoldConstant(Constant *old_constant,
1701 llvm::Function *llvm_function,
1702 FunctionValueCache &value_maker,
1703 FunctionValueCache &entry_instruction_finder,
1704 lldb_private::Stream &error_stream) {
1705 SmallVector<User *, 16> users;
1706
1707 // We do this because the use list might change, invalidating our iterator.
1708 // Much better to keep a work list ourselves.
1709 for (llvm::User *u : old_constant->users())
1710 users.push_back(u);
1711
1712 for (size_t i = 0; i < users.size(); ++i) {
1713 User *user = users[i];
1714
1715 if (Constant *constant = dyn_cast<Constant>(user)) {
1716 // synthesize a new non-constant equivalent of the constant
1717
1718 if (ConstantExpr *constant_expr = dyn_cast<ConstantExpr>(constant)) {
1719 switch (constant_expr->getOpcode()) {
1720 default:
1721 error_stream.Printf("error [IRForTarget internal]: Unhandled "
1722 "constant expression type: \"%s\"",
1723 PrintValue(constant_expr).c_str());
1724 return false;
1725 case Instruction::BitCast: {
1726 FunctionValueCache bit_cast_maker(
1727 [&value_maker, &entry_instruction_finder, old_constant,
1728 constant_expr](llvm::Function *function) -> llvm::Value * {
1729 // UnaryExpr
1730 // OperandList[0] is value
1731
1732 if (constant_expr->getOperand(0) != old_constant)
1733 return constant_expr;
1734
1735 return new BitCastInst(
1736 value_maker.GetValue(function), constant_expr->getType(),
1737 "", llvm::cast<Instruction>(
1738 entry_instruction_finder.GetValue(function)));
1739 });
1740
1741 if (!UnfoldConstant(constant_expr, llvm_function, bit_cast_maker,
1742 entry_instruction_finder, error_stream))
1743 return false;
1744 } break;
1745 case Instruction::GetElementPtr: {
1746 // GetElementPtrConstantExpr
1747 // OperandList[0] is base
1748 // OperandList[1]... are indices
1749
1750 FunctionValueCache get_element_pointer_maker(
1751 [&value_maker, &entry_instruction_finder, old_constant,
1752 constant_expr](llvm::Function *function) -> llvm::Value * {
1753 Value *ptr = constant_expr->getOperand(0);
1754
1755 if (ptr == old_constant)
1756 ptr = value_maker.GetValue(function);
1757
1758 std::vector<Value *> index_vector;
1759
1760 unsigned operand_index;
1761 unsigned num_operands = constant_expr->getNumOperands();
1762
1763 for (operand_index = 1; operand_index < num_operands;
1764 ++operand_index) {
1765 Value *operand = constant_expr->getOperand(operand_index);
1766
1767 if (operand == old_constant)
1768 operand = value_maker.GetValue(function);
1769
1770 index_vector.push_back(operand);
1771 }
1772
1773 ArrayRef<Value *> indices(index_vector);
1774
1775 return GetElementPtrInst::Create(
1776 nullptr, ptr, indices, "",
1777 llvm::cast<Instruction>(
1778 entry_instruction_finder.GetValue(function)));
1779 });
1780
1781 if (!UnfoldConstant(constant_expr, llvm_function,
1782 get_element_pointer_maker,
1783 entry_instruction_finder, error_stream))
1784 return false;
1785 } break;
1786 }
1787 } else {
1788 error_stream.Printf(
1789 "error [IRForTarget internal]: Unhandled constant type: \"%s\"",
1790 PrintValue(constant).c_str());
1791 return false;
1792 }
1793 } else {
1794 if (Instruction *inst = llvm::dyn_cast<Instruction>(user)) {
1795 if (llvm_function && inst->getParent()->getParent() != llvm_function) {
1796 error_stream.PutCString("error: Capturing non-local variables in "
1797 "expressions is unsupported.\n");
1798 return false;
1799 }
1800 inst->replaceUsesOfWith(
1801 old_constant, value_maker.GetValue(inst->getParent()->getParent()));
1802 } else {
1803 error_stream.Printf(
1804 "error [IRForTarget internal]: Unhandled non-constant type: \"%s\"",
1805 PrintValue(user).c_str());
1806 return false;
1807 }
1808 }
1809 }
1810
1811 if (!isa<GlobalValue>(old_constant)) {
1812 old_constant->destroyConstant();
1813 }
1814
1815 return true;
1816}
1817
1818bool IRForTarget::ReplaceVariables(Function &llvm_function) {
1819 if (!m_resolve_vars)
1820 return true;
1821
1822 lldb_private::Log *log(
1823 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
1824
1825 m_decl_map->DoStructLayout();
1826
1827 if (log)
1828 log->Printf("Element arrangement:");
1829
1830 uint32_t num_elements;
1831 uint32_t element_index;
1832
1833 size_t size;
1834 lldb::offset_t alignment;
1835
1836 if (!m_decl_map->GetStructInfo(num_elements, size, alignment))
1837 return false;
1838
Reid Kleckner20670ba2017-03-16 23:13:49 +00001839 Function::arg_iterator iter(llvm_function.arg_begin());
Kate Stoneb9c1b512016-09-06 20:57:50 +00001840
Reid Kleckner20670ba2017-03-16 23:13:49 +00001841 if (iter == llvm_function.arg_end()) {
Kate Stoneb9c1b512016-09-06 20:57:50 +00001842 m_error_stream.Printf("Internal error [IRForTarget]: Wrapper takes no "
1843 "arguments (should take at least a struct pointer)");
1844
1845 return false;
1846 }
1847
1848 Argument *argument = &*iter;
1849
1850 if (argument->getName().equals("this")) {
1851 ++iter;
1852
Reid Kleckner20670ba2017-03-16 23:13:49 +00001853 if (iter == llvm_function.arg_end()) {
Kate Stoneb9c1b512016-09-06 20:57:50 +00001854 m_error_stream.Printf("Internal error [IRForTarget]: Wrapper takes only "
1855 "'this' argument (should take a struct pointer "
1856 "too)");
1857
1858 return false;
1859 }
1860
1861 argument = &*iter;
1862 } else if (argument->getName().equals("self")) {
1863 ++iter;
1864
Reid Kleckner20670ba2017-03-16 23:13:49 +00001865 if (iter == llvm_function.arg_end()) {
Kate Stoneb9c1b512016-09-06 20:57:50 +00001866 m_error_stream.Printf("Internal error [IRForTarget]: Wrapper takes only "
1867 "'self' argument (should take '_cmd' and a struct "
1868 "pointer too)");
1869
1870 return false;
1871 }
1872
1873 if (!iter->getName().equals("_cmd")) {
1874 m_error_stream.Printf("Internal error [IRForTarget]: Wrapper takes '%s' "
1875 "after 'self' argument (should take '_cmd')",
1876 iter->getName().str().c_str());
1877
1878 return false;
1879 }
1880
1881 ++iter;
1882
Reid Kleckner20670ba2017-03-16 23:13:49 +00001883 if (iter == llvm_function.arg_end()) {
Kate Stoneb9c1b512016-09-06 20:57:50 +00001884 m_error_stream.Printf("Internal error [IRForTarget]: Wrapper takes only "
1885 "'self' and '_cmd' arguments (should take a struct "
1886 "pointer too)");
1887
1888 return false;
1889 }
1890
1891 argument = &*iter;
1892 }
1893
1894 if (!argument->getName().equals("$__lldb_arg")) {
1895 m_error_stream.Printf("Internal error [IRForTarget]: Wrapper takes an "
1896 "argument named '%s' instead of the struct pointer",
1897 argument->getName().str().c_str());
1898
1899 return false;
1900 }
1901
1902 if (log)
1903 log->Printf("Arg: \"%s\"", PrintValue(argument).c_str());
1904
1905 BasicBlock &entry_block(llvm_function.getEntryBlock());
1906 Instruction *FirstEntryInstruction(entry_block.getFirstNonPHIOrDbg());
1907
1908 if (!FirstEntryInstruction) {
1909 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't find the "
1910 "first instruction in the wrapper for use in "
1911 "rewriting");
1912
1913 return false;
1914 }
1915
1916 LLVMContext &context(m_module->getContext());
1917 IntegerType *offset_type(Type::getInt32Ty(context));
1918
1919 if (!offset_type) {
1920 m_error_stream.Printf(
1921 "Internal error [IRForTarget]: Couldn't produce an offset type");
1922
1923 return false;
1924 }
1925
1926 for (element_index = 0; element_index < num_elements; ++element_index) {
1927 const clang::NamedDecl *decl = NULL;
1928 Value *value = NULL;
1929 lldb::offset_t offset;
1930 lldb_private::ConstString name;
1931
1932 if (!m_decl_map->GetStructElement(decl, value, offset, name,
1933 element_index)) {
1934 m_error_stream.Printf(
1935 "Internal error [IRForTarget]: Structure information is incomplete");
1936
1937 return false;
1938 }
1939
1940 if (log)
1941 log->Printf(" \"%s\" (\"%s\") placed at %" PRIu64, name.GetCString(),
1942 decl->getNameAsString().c_str(), offset);
1943
1944 if (value) {
1945 if (log)
1946 log->Printf(" Replacing [%s]", PrintValue(value).c_str());
1947
1948 FunctionValueCache body_result_maker(
1949 [this, name, offset_type, offset, argument,
1950 value](llvm::Function *function) -> llvm::Value * {
Adrian Prantl05097242018-04-30 16:49:04 +00001951 // Per the comment at ASTResultSynthesizer::SynthesizeBodyResult,
1952 // in cases where the result variable is an rvalue, we have to
1953 // synthesize a dereference of the appropriate structure entry in
1954 // order to produce the static variable that the AST thinks it is
1955 // accessing.
Kate Stoneb9c1b512016-09-06 20:57:50 +00001956
1957 llvm::Instruction *entry_instruction = llvm::cast<Instruction>(
1958 m_entry_instruction_finder.GetValue(function));
1959
1960 ConstantInt *offset_int(
1961 ConstantInt::get(offset_type, offset, true));
1962 GetElementPtrInst *get_element_ptr = GetElementPtrInst::Create(
1963 nullptr, argument, offset_int, "", entry_instruction);
1964
1965 if (name == m_result_name && !m_result_is_pointer) {
1966 BitCastInst *bit_cast = new BitCastInst(
1967 get_element_ptr, value->getType()->getPointerTo(), "",
1968 entry_instruction);
1969
1970 LoadInst *load = new LoadInst(bit_cast, "", entry_instruction);
1971
1972 return load;
1973 } else {
1974 BitCastInst *bit_cast = new BitCastInst(
1975 get_element_ptr, value->getType(), "", entry_instruction);
1976
1977 return bit_cast;
1978 }
1979 });
1980
1981 if (Constant *constant = dyn_cast<Constant>(value)) {
1982 if (!UnfoldConstant(constant, &llvm_function, body_result_maker,
1983 m_entry_instruction_finder, m_error_stream)) {
1984 return false;
1985 }
1986 } else if (Instruction *instruction = dyn_cast<Instruction>(value)) {
1987 if (instruction->getParent()->getParent() != &llvm_function) {
1988 m_error_stream.PutCString("error: Capturing non-local variables in "
1989 "expressions is unsupported.\n");
1990 return false;
1991 }
1992 value->replaceAllUsesWith(
1993 body_result_maker.GetValue(instruction->getParent()->getParent()));
1994 } else {
1995 if (log)
1996 log->Printf("Unhandled non-constant type: \"%s\"",
1997 PrintValue(value).c_str());
1998 return false;
1999 }
2000
2001 if (GlobalVariable *var = dyn_cast<GlobalVariable>(value))
2002 var->eraseFromParent();
2003 }
2004 }
2005
2006 if (log)
2007 log->Printf("Total structure [align %" PRId64 ", size %" PRIu64 "]",
2008 (int64_t)alignment, (uint64_t)size);
2009
2010 return true;
2011}
2012
2013llvm::Constant *IRForTarget::BuildRelocation(llvm::Type *type,
2014 uint64_t offset) {
2015 llvm::Constant *offset_int = ConstantInt::get(m_intptr_ty, offset);
2016
2017 llvm::Constant *offset_array[1];
2018
2019 offset_array[0] = offset_int;
2020
2021 llvm::ArrayRef<llvm::Constant *> offsets(offset_array, 1);
2022 llvm::Type *char_type = llvm::Type::getInt8Ty(m_module->getContext());
2023 llvm::Type *char_pointer_type = char_type->getPointerTo();
2024
2025 llvm::Constant *reloc_placeholder_bitcast =
2026 ConstantExpr::getBitCast(m_reloc_placeholder, char_pointer_type);
2027 llvm::Constant *reloc_getelementptr = ConstantExpr::getGetElementPtr(
2028 char_type, reloc_placeholder_bitcast, offsets);
2029 llvm::Constant *reloc_bitcast =
2030 ConstantExpr::getBitCast(reloc_getelementptr, type);
2031
2032 return reloc_bitcast;
2033}
2034
2035bool IRForTarget::runOnModule(Module &llvm_module) {
2036 lldb_private::Log *log(
2037 lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS));
2038
2039 m_module = &llvm_module;
2040 m_target_data.reset(new DataLayout(m_module));
2041 m_intptr_ty = llvm::Type::getIntNTy(m_module->getContext(),
2042 m_target_data->getPointerSizeInBits());
2043
2044 if (log) {
2045 std::string s;
2046 raw_string_ostream oss(s);
2047
2048 m_module->print(oss, NULL);
2049
2050 oss.flush();
2051
2052 log->Printf("Module as passed in to IRForTarget: \n\"%s\"", s.c_str());
2053 }
2054
2055 Function *const main_function =
2056 m_func_name.IsEmpty() ? nullptr
2057 : m_module->getFunction(m_func_name.GetStringRef());
2058
2059 if (!m_func_name.IsEmpty() && !main_function) {
2060 if (log)
2061 log->Printf("Couldn't find \"%s()\" in the module",
2062 m_func_name.AsCString());
2063
2064 m_error_stream.Printf("Internal error [IRForTarget]: Couldn't find wrapper "
2065 "'%s' in the module",
2066 m_func_name.AsCString());
2067
2068 return false;
2069 }
2070
2071 if (main_function) {
2072 if (!FixFunctionLinkage(*main_function)) {
2073 if (log)
2074 log->Printf("Couldn't fix the linkage for the function");
2075
2076 return false;
2077 }
2078 }
2079
2080 llvm::Type *int8_ty = Type::getInt8Ty(m_module->getContext());
2081
2082 m_reloc_placeholder = new llvm::GlobalVariable(
2083 (*m_module), int8_ty, false /* IsConstant */,
2084 GlobalVariable::InternalLinkage, Constant::getNullValue(int8_ty),
2085 "reloc_placeholder", NULL /* InsertBefore */,
2086 GlobalVariable::NotThreadLocal /* ThreadLocal */, 0 /* AddressSpace */);
2087
2088 ////////////////////////////////////////////////////////////
2089 // Replace $__lldb_expr_result with a persistent variable
2090 //
2091
2092 if (main_function) {
2093 if (!CreateResultVariable(*main_function)) {
2094 if (log)
2095 log->Printf("CreateResultVariable() failed");
2096
2097 // CreateResultVariable() reports its own errors, so we don't do so here
2098
2099 return false;
2100 }
2101 }
2102
2103 if (log && log->GetVerbose()) {
2104 std::string s;
2105 raw_string_ostream oss(s);
2106
2107 m_module->print(oss, NULL);
2108
2109 oss.flush();
2110
2111 log->Printf("Module after creating the result variable: \n\"%s\"",
2112 s.c_str());
2113 }
2114
2115 for (Module::iterator fi = m_module->begin(), fe = m_module->end(); fi != fe;
2116 ++fi) {
2117 llvm::Function *function = &*fi;
2118
2119 if (function->begin() == function->end())
2120 continue;
2121
2122 Function::iterator bbi;
2123
2124 for (bbi = function->begin(); bbi != function->end(); ++bbi) {
2125 if (!RemoveGuards(*bbi)) {
2126 if (log)
2127 log->Printf("RemoveGuards() failed");
2128
2129 // RemoveGuards() reports its own errors, so we don't do so here
2130
2131 return false;
2132 }
2133
2134 if (!RewritePersistentAllocs(*bbi)) {
2135 if (log)
2136 log->Printf("RewritePersistentAllocs() failed");
2137
2138 // RewritePersistentAllocs() reports its own errors, so we don't do so
2139 // here
2140
2141 return false;
2142 }
2143
2144 if (!RemoveCXAAtExit(*bbi)) {
2145 if (log)
2146 log->Printf("RemoveCXAAtExit() failed");
2147
2148 // RemoveCXAAtExit() reports its own errors, so we don't do so here
2149
2150 return false;
2151 }
2152 }
2153 }
2154
2155 ///////////////////////////////////////////////////////////////////////////////
2156 // Fix all Objective-C constant strings to use NSStringWithCString:encoding:
2157 //
2158
2159 if (!RewriteObjCConstStrings()) {
2160 if (log)
2161 log->Printf("RewriteObjCConstStrings() failed");
2162
2163 // RewriteObjCConstStrings() reports its own errors, so we don't do so here
2164
2165 return false;
2166 }
2167
2168 for (Module::iterator fi = m_module->begin(), fe = m_module->end(); fi != fe;
2169 ++fi) {
2170 llvm::Function *function = &*fi;
2171
2172 for (llvm::Function::iterator bbi = function->begin(),
2173 bbe = function->end();
2174 bbi != bbe; ++bbi) {
2175 if (!RewriteObjCSelectors(*bbi)) {
2176 if (log)
2177 log->Printf("RewriteObjCSelectors() failed");
2178
Adrian Prantl05097242018-04-30 16:49:04 +00002179 // RewriteObjCSelectors() reports its own errors, so we don't do so
2180 // here
Kate Stoneb9c1b512016-09-06 20:57:50 +00002181
2182 return false;
2183 }
Sean Callananac900582016-09-29 00:45:33 +00002184
2185 if (!RewriteObjCClassReferences(*bbi)) {
2186 if (log)
2187 log->Printf("RewriteObjCClassReferences() failed");
2188
2189 // RewriteObjCClasses() reports its own errors, so we don't do so here
2190
2191 return false;
2192 }
Kate Stoneb9c1b512016-09-06 20:57:50 +00002193 }
2194 }
2195
2196 for (Module::iterator fi = m_module->begin(), fe = m_module->end(); fi != fe;
2197 ++fi) {
2198 llvm::Function *function = &*fi;
2199
2200 for (llvm::Function::iterator bbi = function->begin(),
2201 bbe = function->end();
2202 bbi != bbe; ++bbi) {
2203 if (!ResolveCalls(*bbi)) {
2204 if (log)
2205 log->Printf("ResolveCalls() failed");
2206
2207 // ResolveCalls() reports its own errors, so we don't do so here
2208
2209 return false;
2210 }
2211 }
2212 }
2213
2214 ////////////////////////////////////////////////////////////////////////
2215 // Run function-level passes that only make sense on the main function
2216 //
2217
2218 if (main_function) {
2219 if (!ResolveExternals(*main_function)) {
2220 if (log)
2221 log->Printf("ResolveExternals() failed");
2222
2223 // ResolveExternals() reports its own errors, so we don't do so here
2224
2225 return false;
2226 }
2227
2228 if (!ReplaceVariables(*main_function)) {
2229 if (log)
2230 log->Printf("ReplaceVariables() failed");
2231
2232 // ReplaceVariables() reports its own errors, so we don't do so here
2233
2234 return false;
2235 }
2236 }
2237
2238 if (log && log->GetVerbose()) {
2239 std::string s;
2240 raw_string_ostream oss(s);
2241
2242 m_module->print(oss, NULL);
2243
2244 oss.flush();
2245
2246 log->Printf("Module after preparing for execution: \n\"%s\"", s.c_str());
2247 }
2248
2249 return true;
2250}
2251
2252void IRForTarget::assignPassManager(PMStack &pass_mgr_stack,
2253 PassManagerType pass_mgr_type) {}
2254
2255PassManagerType IRForTarget::getPotentialPassManagerType() const {
2256 return PMT_ModulePassManager;
Sean Callanan2ab712f22010-07-03 01:35:46 +00002257}