blob: eb4c919c2c3bb1c7ee9ddec922bd5f5e3827747f [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
10#include "lldb/Expression/IRForTarget.h"
11
12#include "llvm/Support/raw_ostream.h"
Chandler Carruth1e157582013-01-02 12:20:07 +000013#include "llvm/IR/Constants.h"
14#include "llvm/IR/DataLayout.h"
15#include "llvm/IR/InstrTypes.h"
16#include "llvm/IR/Instructions.h"
17#include "llvm/IR/Intrinsics.h"
18#include "llvm/IR/Module.h"
Ilia Kc9a475d2015-02-13 10:49:18 +000019#include "llvm/IR/LegacyPassManager.h"
Sean Callanan3d654b32012-09-24 22:25:51 +000020#include "llvm/Transforms/IPO.h"
Zachary Turner543afa12014-12-09 22:29:47 +000021#include "llvm/IR/Metadata.h"
Chandler Carruth1e157582013-01-02 12:20:07 +000022#include "llvm/IR/ValueSymbolTable.h"
Sean Callanan549c9f72010-07-13 21:41:46 +000023
24#include "clang/AST/ASTContext.h"
Sean Callanan2ab712f22010-07-03 01:35:46 +000025
26#include "lldb/Core/dwarf.h"
Sean Callanan8dfb68e2013-03-19 00:10:07 +000027#include "lldb/Core/ConstString.h"
28#include "lldb/Core/DataBufferHeap.h"
Sean Callanan2ab712f22010-07-03 01:35:46 +000029#include "lldb/Core/Log.h"
30#include "lldb/Core/Scalar.h"
31#include "lldb/Core/StreamString.h"
32#include "lldb/Expression/ClangExpressionDeclMap.h"
Sean Callanan8dfb68e2013-03-19 00:10:07 +000033#include "lldb/Expression/IRExecutionUnit.h"
Sean Callanan3bfdaa22011-09-15 02:13:07 +000034#include "lldb/Expression/IRInterpreter.h"
Sean Callanan79763a42011-05-23 21:40:23 +000035#include "lldb/Host/Endian.h"
Sean Callanan63697e52011-05-07 01:06:41 +000036#include "lldb/Symbol/ClangASTContext.h"
Greg Clayton57ee3062013-07-11 22:46:58 +000037#include "lldb/Symbol/ClangASTType.h"
Siva Chandra0f404e02015-04-09 18:48:34 +000038#include "lldb/Target/CPPLanguageRuntime.h"
Sean Callanan2ab712f22010-07-03 01:35:46 +000039
40#include <map>
41
42using namespace llvm;
43
Sean Callananeaacbc92010-08-18 18:50:51 +000044static char ID;
45
Sean Callanan8dfb68e2013-03-19 00:10:07 +000046IRForTarget::StaticDataAllocator::StaticDataAllocator(lldb_private::IRExecutionUnit &execution_unit) :
47 m_execution_unit(execution_unit),
Sean Callanan1582ee62013-04-18 22:06:33 +000048 m_stream_string(lldb_private::Stream::eBinary, execution_unit.GetAddressByteSize(), execution_unit.GetByteOrder()),
Sean Callanan8dfb68e2013-03-19 00:10:07 +000049 m_allocation(LLDB_INVALID_ADDRESS)
Sean Callanan79763a42011-05-23 21:40:23 +000050{
51}
52
Sean Callanan1f9db3e2013-06-28 21:44:15 +000053IRForTarget::FunctionValueCache::FunctionValueCache(Maker const &maker) :
54 m_maker(maker),
55 m_values()
56{
57}
58
59IRForTarget::FunctionValueCache::~FunctionValueCache()
60{
61}
62
Greg Clayton526ae042015-02-12 00:34:25 +000063llvm::Value *
64IRForTarget::FunctionValueCache::GetValue(llvm::Function *function)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +000065{
Sean Callanan1f9db3e2013-06-28 21:44:15 +000066 if (!m_values.count(function))
67 {
68 llvm::Value *ret = m_maker(function);
69 m_values[function] = ret;
70 return ret;
71 }
72 return m_values[function];
73}
74
Greg Clayton526ae042015-02-12 00:34:25 +000075lldb::addr_t
76IRForTarget::StaticDataAllocator::Allocate()
Sean Callanan79763a42011-05-23 21:40:23 +000077{
Sean Callanan8dfb68e2013-03-19 00:10:07 +000078 lldb_private::Error err;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +000079
Sean Callanan8dfb68e2013-03-19 00:10:07 +000080 if (m_allocation != LLDB_INVALID_ADDRESS)
81 {
82 m_execution_unit.FreeNow(m_allocation);
83 m_allocation = LLDB_INVALID_ADDRESS;
84 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +000085
Sean Callanan8dfb68e2013-03-19 00:10:07 +000086 m_allocation = m_execution_unit.WriteNow((const uint8_t*)m_stream_string.GetData(), m_stream_string.GetSize(), err);
87
88 return m_allocation;
Sean Callanan79763a42011-05-23 21:40:23 +000089}
90
Greg Clayton526ae042015-02-12 00:34:25 +000091lldb::TargetSP
92IRForTarget::StaticDataAllocator::GetTarget()
93{
94 return m_execution_unit.GetTarget();
95}
96
97static llvm::Value *
98FindEntryInstruction (llvm::Function *function)
Sean Callanan1f9db3e2013-06-28 21:44:15 +000099{
100 if (function->empty())
101 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000102
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000103 return function->getEntryBlock().getFirstNonPHIOrDbg();
104}
105
Greg Clayton1b95a6f2010-11-19 01:05:25 +0000106IRForTarget::IRForTarget (lldb_private::ClangExpressionDeclMap *decl_map,
107 bool resolve_vars,
Sean Callanan8dfb68e2013-03-19 00:10:07 +0000108 lldb_private::IRExecutionUnit &execution_unit,
Sean Callanan3989fb92011-01-27 01:07:04 +0000109 lldb_private::Stream *error_stream,
Greg Clayton1b95a6f2010-11-19 01:05:25 +0000110 const char *func_name) :
Sean Callanane2ef6e32010-09-23 03:01:22 +0000111 ModulePass(ID),
Stephen Wilson71c21d12011-04-11 19:41:40 +0000112 m_resolve_vars(resolve_vars),
113 m_func_name(func_name),
Sean Callanan79763a42011-05-23 21:40:23 +0000114 m_module(NULL),
Johnny Chen44805302011-07-19 19:48:13 +0000115 m_decl_map(decl_map),
Sean Callanan8dfb68e2013-03-19 00:10:07 +0000116 m_data_allocator(execution_unit),
Sean Callananafe16a72010-11-17 23:00:36 +0000117 m_CFStringCreateWithBytes(NULL),
Sean Callanan1a8d4092010-08-27 01:01:44 +0000118 m_sel_registerName(NULL),
Sean Callanan439dcae2013-12-20 19:55:02 +0000119 m_intptr_ty(NULL),
Stephen Wilson71c21d12011-04-11 19:41:40 +0000120 m_error_stream(error_stream),
Sean Callanan63697e52011-05-07 01:06:41 +0000121 m_result_store(NULL),
122 m_result_is_pointer(false),
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000123 m_reloc_placeholder(NULL),
124 m_entry_instruction_finder (FindEntryInstruction)
Sean Callanan2ab712f22010-07-03 01:35:46 +0000125{
126}
127
Sean Callanan038df5032010-09-30 21:18:25 +0000128/* Handy utility functions used at several places in the code */
Sean Callanan2235f322010-08-11 03:57:18 +0000129
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000130static std::string
Greg Clayton1b95a6f2010-11-19 01:05:25 +0000131PrintValue(const Value *value, bool truncate = false)
Sean Callanan2235f322010-08-11 03:57:18 +0000132{
133 std::string s;
Jim Ingham28eb5712012-10-12 17:34:26 +0000134 if (value)
135 {
136 raw_string_ostream rso(s);
137 value->print(rso);
138 rso.flush();
139 if (truncate)
140 s.resize(s.length() - 1);
141 }
Sean Callanan2235f322010-08-11 03:57:18 +0000142 return s;
143}
144
Sean Callanan038df5032010-09-30 21:18:25 +0000145static std::string
Greg Clayton57ee3062013-07-11 22:46:58 +0000146PrintType(const llvm::Type *type, bool truncate = false)
Sean Callanan038df5032010-09-30 21:18:25 +0000147{
148 std::string s;
149 raw_string_ostream rso(s);
Greg Clayton1b95a6f2010-11-19 01:05:25 +0000150 type->print(rso);
Sean Callanan038df5032010-09-30 21:18:25 +0000151 rso.flush();
152 if (truncate)
153 s.resize(s.length() - 1);
154 return s;
155}
156
Sean Callanan2ab712f22010-07-03 01:35:46 +0000157IRForTarget::~IRForTarget()
158{
159}
160
Sean Callanan79763a42011-05-23 21:40:23 +0000161bool
162IRForTarget::FixFunctionLinkage(llvm::Function &llvm_function)
163{
Sean Callanan79763a42011-05-23 21:40:23 +0000164 llvm_function.setLinkage(GlobalValue::ExternalLinkage);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000165
Sean Callanan7f27d602011-11-19 02:54:21 +0000166 std::string name = llvm_function.getName().str();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000167
Sean Callanan79763a42011-05-23 21:40:23 +0000168 return true;
169}
170
Greg Clayton23f8c952014-03-24 23:10:19 +0000171IRForTarget::LookupResult
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000172IRForTarget::GetFunctionAddress (llvm::Function *fun,
173 uint64_t &fun_addr,
174 lldb_private::ConstString &name,
175 Constant **&value_ptr)
176{
Greg Clayton5160ce52013-03-27 23:08:40 +0000177 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000178
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000179 fun_addr = LLDB_INVALID_ADDRESS;
180 name.Clear();
181 value_ptr = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000182
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000183 if (fun->isIntrinsic())
184 {
185 Intrinsic::ID intrinsic_id = (Intrinsic::ID)fun->getIntrinsicID();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000186
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000187 switch (intrinsic_id)
188 {
189 default:
190 if (log)
191 log->Printf("Unresolved intrinsic \"%s\"", Intrinsic::getName(intrinsic_id).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000192
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000193 if (m_error_stream)
194 m_error_stream->Printf("Internal error [IRForTarget]: Call to unhandled compiler intrinsic '%s'\n", Intrinsic::getName(intrinsic_id).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000195
Jason Molenda52d76032014-07-09 01:10:37 +0000196 return LookupResult::Fail;
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000197 case Intrinsic::memcpy:
198 {
199 static lldb_private::ConstString g_memcpy_str ("memcpy");
200 name = g_memcpy_str;
201 }
202 break;
Sean Callanana6cbf062011-11-16 00:20:50 +0000203 case Intrinsic::memset:
204 {
205 static lldb_private::ConstString g_memset_str ("memset");
206 name = g_memset_str;
207 }
208 break;
Greg Clayton23f8c952014-03-24 23:10:19 +0000209 case Intrinsic::dbg_declare:
Sean Callanan131be992014-04-09 00:59:41 +0000210 case Intrinsic::dbg_value:
Greg Clayton23f8c952014-03-24 23:10:19 +0000211 return LookupResult::Ignore;
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000212 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000213
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000214 if (log && name)
215 log->Printf("Resolved intrinsic name \"%s\"", name.GetCString());
216 }
217 else
218 {
219 name.SetCStringWithLength (fun->getName().data(), fun->getName().size());
220 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000221
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000222 // Find the address of the function.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000223
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000224 clang::NamedDecl *fun_decl = DeclForGlobal (fun);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000225
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000226 if (fun_decl)
227 {
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000228 if (!m_decl_map->GetFunctionInfo (fun_decl, fun_addr))
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000229 {
Siva Chandra0f404e02015-04-09 18:48:34 +0000230 std::vector<lldb_private::ConstString> alternates;
Greg Claytonf0705c82011-10-22 03:33:13 +0000231 bool found_it = m_decl_map->GetFunctionAddress (name, fun_addr);
232 if (!found_it)
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000233 {
Siva Chandra0f404e02015-04-09 18:48:34 +0000234 if (log)
235 log->Printf("Address of function \"%s\" not found.\n", name.GetCString());
236 // Check for an alternate mangling for names from the standard library.
237 // For example, "std::basic_string<...>" has an alternate mangling scheme per
238 // the Itanium C++ ABI.
239 lldb::ProcessSP process_sp = m_data_allocator.GetTarget()->GetProcessSP();
Sean Callanan235de0a2015-05-28 20:06:40 +0000240 if (process_sp)
Greg Claytonf0705c82011-10-22 03:33:13 +0000241 {
Sean Callanan235de0a2015-05-28 20:06:40 +0000242 lldb_private::CPPLanguageRuntime *cpp_runtime = process_sp->GetCPPLanguageRuntime();
243 if (cpp_runtime && cpp_runtime->GetAlternateManglings(name, alternates))
Siva Chandra0f404e02015-04-09 18:48:34 +0000244 {
Sean Callanan235de0a2015-05-28 20:06:40 +0000245 for (size_t i = 0; i < alternates.size(); ++i)
Siva Chandra0f404e02015-04-09 18:48:34 +0000246 {
Sean Callanan235de0a2015-05-28 20:06:40 +0000247 const lldb_private::ConstString &alternate_name = alternates[i];
Siva Chandra0f404e02015-04-09 18:48:34 +0000248 if (log)
Sean Callanan235de0a2015-05-28 20:06:40 +0000249 log->Printf("Looking up address of function \"%s\" with alternate name \"%s\"",
Siva Chandra0f404e02015-04-09 18:48:34 +0000250 name.GetCString(), alternate_name.GetCString());
Sean Callanan235de0a2015-05-28 20:06:40 +0000251 if ((found_it = m_decl_map->GetFunctionAddress (alternate_name, fun_addr)))
252 {
253 if (log)
254 log->Printf("Found address of function \"%s\" with alternate name \"%s\"",
255 name.GetCString(), alternate_name.GetCString());
256 break;
257 }
Siva Chandra0f404e02015-04-09 18:48:34 +0000258 }
259 }
Greg Claytonf0705c82011-10-22 03:33:13 +0000260 }
261 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000262
Greg Claytonf0705c82011-10-22 03:33:13 +0000263 if (!found_it)
264 {
Greg Clayton5e0c5e82012-07-18 20:47:40 +0000265 lldb_private::Mangled mangled_name(name);
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000266 if (m_error_stream)
Greg Claytonf0705c82011-10-22 03:33:13 +0000267 {
Siva Chandra0f404e02015-04-09 18:48:34 +0000268 if (mangled_name.GetMangledName())
Greg Claytonda1eb042013-04-23 21:48:38 +0000269 m_error_stream->Printf("error: call to a function '%s' ('%s') that is not present in the target\n",
270 mangled_name.GetName().GetCString(),
271 mangled_name.GetMangledName().GetCString());
Greg Claytonf0705c82011-10-22 03:33:13 +0000272 else
Greg Clayton5e0c5e82012-07-18 20:47:40 +0000273 m_error_stream->Printf("error: call to a function '%s' that is not present in the target\n",
274 mangled_name.GetName().GetCString());
Greg Claytonf0705c82011-10-22 03:33:13 +0000275 }
Greg Clayton23f8c952014-03-24 23:10:19 +0000276 return LookupResult::Fail;
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000277 }
278 }
279 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000280 else
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000281 {
282 if (!m_decl_map->GetFunctionAddress (name, fun_addr))
283 {
284 if (log)
285 log->Printf ("Metadataless function \"%s\" had no address", name.GetCString());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000286
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000287 if (m_error_stream)
288 m_error_stream->Printf("Error [IRForTarget]: Call to a symbol-only function '%s' that is not present in the target\n", name.GetCString());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000289
Greg Clayton23f8c952014-03-24 23:10:19 +0000290 return LookupResult::Fail;
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000291 }
292 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000293
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000294 if (log)
Daniel Malead01b2952012-11-29 21:49:15 +0000295 log->Printf("Found \"%s\" at 0x%" PRIx64, name.GetCString(), fun_addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000296
Greg Clayton23f8c952014-03-24 23:10:19 +0000297 return LookupResult::Success;
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000298}
299
300llvm::Constant *
301IRForTarget::BuildFunctionPointer (llvm::Type *type,
302 uint64_t ptr)
303{
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000304 PointerType *fun_ptr_ty = PointerType::getUnqual(type);
Sean Callanan439dcae2013-12-20 19:55:02 +0000305 Constant *fun_addr_int = ConstantInt::get(m_intptr_ty, ptr, false);
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000306 return ConstantExpr::getIntToPtr(fun_addr_int, fun_ptr_ty);
307}
308
Sean Callananfc8feb82011-10-31 22:11:40 +0000309void
310IRForTarget::RegisterFunctionMetadata(LLVMContext &context,
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000311 llvm::Value *function_ptr,
Sean Callananfc8feb82011-10-31 22:11:40 +0000312 const char *name)
313{
Ed Mastea8553092014-03-10 17:24:16 +0000314 for (llvm::User *user : function_ptr->users())
Sean Callananfc8feb82011-10-31 22:11:40 +0000315 {
Sean Callananfc8feb82011-10-31 22:11:40 +0000316 if (Instruction *user_inst = dyn_cast<Instruction>(user))
317 {
Daniel Maleaf051dbc2013-06-03 20:45:54 +0000318 MDString* md_name = MDString::get(context, StringRef(name));
319
320 MDNode *metadata = MDNode::get(context, md_name);
321
Sean Callananfc8feb82011-10-31 22:11:40 +0000322 user_inst->setMetadata("lldb.call.realName", metadata);
323 }
324 else
325 {
326 RegisterFunctionMetadata (context, user, name);
327 }
328 }
329}
330
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000331bool
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000332IRForTarget::ResolveFunctionPointers(llvm::Module &llvm_module)
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000333{
Greg Clayton5160ce52013-03-27 23:08:40 +0000334 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000335
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000336 for (llvm::Module::iterator fi = llvm_module.begin();
337 fi != llvm_module.end();
338 ++fi)
339 {
340 Function *fun = fi;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000341
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000342 bool is_decl = fun->isDeclaration();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000343
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000344 if (log)
Sean Callanan7f27d602011-11-19 02:54:21 +0000345 log->Printf("Examining %s function %s", (is_decl ? "declaration" : "non-declaration"), fun->getName().str().c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000346
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000347 if (!is_decl)
348 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000349
Sean Callanan339f6152014-03-11 19:19:16 +0000350 if (fun->use_empty())
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000351 continue; // ignore
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000352
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000353 uint64_t addr = LLDB_INVALID_ADDRESS;
354 lldb_private::ConstString name;
355 Constant **value_ptr = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000356
Greg Clayton23f8c952014-03-24 23:10:19 +0000357 LookupResult result = GetFunctionAddress(fun,
358 addr,
359 name,
360 value_ptr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000361
Greg Clayton23f8c952014-03-24 23:10:19 +0000362 switch (result)
363 {
364 case LookupResult::Fail:
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000365 return false; // GetFunctionAddress reports its own errors
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000366
Greg Clayton23f8c952014-03-24 23:10:19 +0000367 case LookupResult::Ignore:
368 break; // Nothing to do
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000369
Greg Clayton23f8c952014-03-24 23:10:19 +0000370 case LookupResult::Success:
371 {
372 Constant *value = BuildFunctionPointer(fun->getFunctionType(), addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000373
Greg Clayton23f8c952014-03-24 23:10:19 +0000374 RegisterFunctionMetadata (llvm_module.getContext(), fun, name.AsCString());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000375
Greg Clayton23f8c952014-03-24 23:10:19 +0000376 if (value_ptr)
377 *value_ptr = value;
Stefanus Du Toitfc6b7a02013-07-23 21:34:03 +0000378
Greg Clayton23f8c952014-03-24 23:10:19 +0000379 // If we are replacing a function with the nobuiltin attribute, it may
380 // be called with the builtin attribute on call sites. Remove any such
381 // attributes since it's illegal to have a builtin call to something
382 // other than a nobuiltin function.
383 if (fun->hasFnAttribute(llvm::Attribute::NoBuiltin)) {
384 llvm::Attribute builtin = llvm::Attribute::get(fun->getContext(), llvm::Attribute::Builtin);
Stefanus Du Toitfc6b7a02013-07-23 21:34:03 +0000385
Greg Clayton23f8c952014-03-24 23:10:19 +0000386 for (auto u : fun->users()) {
387 if (auto call = dyn_cast<CallInst>(u)) {
388 call->removeAttribute(AttributeSet::FunctionIndex, builtin);
389 }
390 }
Stefanus Du Toitfc6b7a02013-07-23 21:34:03 +0000391 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000392
Greg Clayton23f8c952014-03-24 23:10:19 +0000393 fun->replaceAllUsesWith(value);
Stefanus Du Toitfc6b7a02013-07-23 21:34:03 +0000394 }
Greg Clayton23f8c952014-03-24 23:10:19 +0000395 break;
Stefanus Du Toitfc6b7a02013-07-23 21:34:03 +0000396 }
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000397 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000398
Sean Callanan0c4d8d22011-08-04 21:37:47 +0000399 return true;
400}
401
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000402
Sean Callanan63697e52011-05-07 01:06:41 +0000403clang::NamedDecl *
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000404IRForTarget::DeclForGlobal (const GlobalValue *global_val, Module *module)
Sean Callanan63697e52011-05-07 01:06:41 +0000405{
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000406 NamedMDNode *named_metadata = module->getNamedMetadata("clang.global.decl.ptrs");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000407
Sean Callanan63697e52011-05-07 01:06:41 +0000408 if (!named_metadata)
409 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000410
Sean Callanan63697e52011-05-07 01:06:41 +0000411 unsigned num_nodes = named_metadata->getNumOperands();
412 unsigned node_index;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000413
Sean Callanan63697e52011-05-07 01:06:41 +0000414 for (node_index = 0;
415 node_index < num_nodes;
416 ++node_index)
417 {
Zachary Turner0d594e12014-11-05 18:37:53 +0000418 llvm::MDNode *metadata_node = dyn_cast<llvm::MDNode>(named_metadata->getOperand(node_index));
Sean Callanan63697e52011-05-07 01:06:41 +0000419 if (!metadata_node)
420 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000421
Sean Callanan63697e52011-05-07 01:06:41 +0000422 if (metadata_node->getNumOperands() != 2)
423 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000424
Zachary Turner543afa12014-12-09 22:29:47 +0000425 if (mdconst::dyn_extract_or_null<GlobalValue>(metadata_node->getOperand(0)) != global_val)
Sean Callanan63697e52011-05-07 01:06:41 +0000426 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000427
Zachary Turner543afa12014-12-09 22:29:47 +0000428 ConstantInt *constant_int = mdconst::dyn_extract<ConstantInt>(metadata_node->getOperand(1));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000429
Sean Callanan63697e52011-05-07 01:06:41 +0000430 if (!constant_int)
431 return NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000432
Sean Callanan63697e52011-05-07 01:06:41 +0000433 uintptr_t ptr = constant_int->getZExtValue();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000434
Sean Callanan63697e52011-05-07 01:06:41 +0000435 return reinterpret_cast<clang::NamedDecl *>(ptr);
436 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000437
Sean Callanan63697e52011-05-07 01:06:41 +0000438 return NULL;
439}
440
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000441clang::NamedDecl *
442IRForTarget::DeclForGlobal (GlobalValue *global_val)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000443{
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000444 return DeclForGlobal(global_val, m_module);
445}
446
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000447bool
Sean Callanan79763a42011-05-23 21:40:23 +0000448IRForTarget::CreateResultVariable (llvm::Function &llvm_function)
Sean Callanand1e5b432010-08-12 01:56:52 +0000449{
Greg Clayton5160ce52013-03-27 23:08:40 +0000450 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000451
Sean Callanan9e6ed532010-09-13 21:34:21 +0000452 if (!m_resolve_vars)
453 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000454
Sean Callanan9e6ed532010-09-13 21:34:21 +0000455 // Find the result variable. If it doesn't exist, we can give up right here.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000456
Sean Callanan79763a42011-05-23 21:40:23 +0000457 ValueSymbolTable& value_symbol_table = m_module->getValueSymbolTable();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000458
Sean Callanancc427fa2011-07-30 02:42:06 +0000459 std::string result_name_str;
Sean Callananfc55f5d2010-09-21 00:44:12 +0000460 const char *result_name = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000461
Sean Callananfc55f5d2010-09-21 00:44:12 +0000462 for (ValueSymbolTable::iterator vi = value_symbol_table.begin(), ve = value_symbol_table.end();
463 vi != ve;
464 ++vi)
465 {
Sean Callanancc427fa2011-07-30 02:42:06 +0000466 result_name_str = vi->first().str();
467 const char *value_name = result_name_str.c_str();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000468
Sean Callanancc427fa2011-07-30 02:42:06 +0000469 if (strstr(value_name, "$__lldb_expr_result_ptr") &&
Sean Callanan7273e2d2012-11-02 22:28:08 +0000470 strncmp(value_name, "_ZGV", 4))
Sean Callanan92adcac2011-01-13 08:53:35 +0000471 {
Sean Callanancc427fa2011-07-30 02:42:06 +0000472 result_name = value_name;
Sean Callanan92adcac2011-01-13 08:53:35 +0000473 m_result_is_pointer = true;
474 break;
475 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000476
Sean Callanancc427fa2011-07-30 02:42:06 +0000477 if (strstr(value_name, "$__lldb_expr_result") &&
Sean Callanan7273e2d2012-11-02 22:28:08 +0000478 strncmp(value_name, "_ZGV", 4))
Sean Callanan46ae9e52010-09-28 21:13:03 +0000479 {
Sean Callanancc427fa2011-07-30 02:42:06 +0000480 result_name = value_name;
Sean Callanan92adcac2011-01-13 08:53:35 +0000481 m_result_is_pointer = false;
Sean Callanan46ae9e52010-09-28 21:13:03 +0000482 break;
483 }
Sean Callananfc55f5d2010-09-21 00:44:12 +0000484 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000485
Sean Callananfc55f5d2010-09-21 00:44:12 +0000486 if (!result_name)
487 {
488 if (log)
489 log->PutCString("Couldn't find result variable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000490
Richard Mitton00dec202013-10-11 19:44:23 +0000491 return true;
Sean Callananfc55f5d2010-09-21 00:44:12 +0000492 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000493
Sean Callanan46ae9e52010-09-28 21:13:03 +0000494 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +0000495 log->Printf("Result name: \"%s\"", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000496
Sean Callanan79763a42011-05-23 21:40:23 +0000497 Value *result_value = m_module->getNamedValue(result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000498
Sean Callanand1e5b432010-08-12 01:56:52 +0000499 if (!result_value)
500 {
501 if (log)
Sean Callananfc55f5d2010-09-21 00:44:12 +0000502 log->PutCString("Result variable had no data");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000503
Sean Callanan3989fb92011-01-27 01:07:04 +0000504 if (m_error_stream)
505 m_error_stream->Printf("Internal error [IRForTarget]: Result variable's name (%s) exists, but not its definition\n", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000506
Sean Callananfc55f5d2010-09-21 00:44:12 +0000507 return false;
Sean Callanand1e5b432010-08-12 01:56:52 +0000508 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000509
Sean Callanand1e5b432010-08-12 01:56:52 +0000510 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +0000511 log->Printf("Found result in the IR: \"%s\"", PrintValue(result_value, false).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000512
Sean Callanand1e5b432010-08-12 01:56:52 +0000513 GlobalVariable *result_global = dyn_cast<GlobalVariable>(result_value);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000514
Sean Callanand1e5b432010-08-12 01:56:52 +0000515 if (!result_global)
516 {
517 if (log)
518 log->PutCString("Result variable isn't a GlobalVariable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000519
Sean Callanan3989fb92011-01-27 01:07:04 +0000520 if (m_error_stream)
521 m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s) is defined, but is not a global variable\n", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000522
Sean Callanand1e5b432010-08-12 01:56:52 +0000523 return false;
524 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000525
Sean Callanan79763a42011-05-23 21:40:23 +0000526 clang::NamedDecl *result_decl = DeclForGlobal (result_global);
Sean Callanan63697e52011-05-07 01:06:41 +0000527 if (!result_decl)
Sean Callanand1e5b432010-08-12 01:56:52 +0000528 {
529 if (log)
Sean Callanan63697e52011-05-07 01:06:41 +0000530 log->PutCString("Result variable doesn't have a corresponding Decl");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000531
Sean Callanan3989fb92011-01-27 01:07:04 +0000532 if (m_error_stream)
Sean Callanan63697e52011-05-07 01:06:41 +0000533 m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s) does not have a corresponding Clang entity\n", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000534
Sean Callanand1e5b432010-08-12 01:56:52 +0000535 return false;
536 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000537
Sean Callanan63697e52011-05-07 01:06:41 +0000538 if (log)
Sean Callanand1e5b432010-08-12 01:56:52 +0000539 {
Sean Callanan63697e52011-05-07 01:06:41 +0000540 std::string decl_desc_str;
541 raw_string_ostream decl_desc_stream(decl_desc_str);
542 result_decl->print(decl_desc_stream);
543 decl_desc_stream.flush();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000544
Sean Callanan63697e52011-05-07 01:06:41 +0000545 log->Printf("Found result decl: \"%s\"", decl_desc_str.c_str());
Sean Callanand1e5b432010-08-12 01:56:52 +0000546 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000547
Sean Callanan63697e52011-05-07 01:06:41 +0000548 clang::VarDecl *result_var = dyn_cast<clang::VarDecl>(result_decl);
549 if (!result_var)
Sean Callanand1e5b432010-08-12 01:56:52 +0000550 {
551 if (log)
Sean Callanan63697e52011-05-07 01:06:41 +0000552 log->PutCString("Result variable Decl isn't a VarDecl");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000553
Sean Callanan3989fb92011-01-27 01:07:04 +0000554 if (m_error_stream)
Sean Callanan63697e52011-05-07 01:06:41 +0000555 m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s)'s corresponding Clang entity isn't a variable\n", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000556
Sean Callanand1e5b432010-08-12 01:56:52 +0000557 return false;
558 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000559
Sean Callanand1e5b432010-08-12 01:56:52 +0000560 // Get the next available result name from m_decl_map and create the persistent
561 // variable for it
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000562
Sean Callanan63697e52011-05-07 01:06:41 +0000563 // If the result is an Lvalue, it is emitted as a pointer; see
564 // ASTResultSynthesizer::SynthesizeBodyResult.
Sean Callanan92adcac2011-01-13 08:53:35 +0000565 if (m_result_is_pointer)
566 {
Sean Callanan63697e52011-05-07 01:06:41 +0000567 clang::QualType pointer_qual_type = result_var->getType();
Sean Callanan78e37602011-01-27 04:42:51 +0000568 const clang::Type *pointer_type = pointer_qual_type.getTypePtr();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000569
Sean Callananfc4f2fb2011-12-14 01:13:04 +0000570 const clang::PointerType *pointer_pointertype = pointer_type->getAs<clang::PointerType>();
571 const clang::ObjCObjectPointerType *pointer_objcobjpointertype = pointer_type->getAs<clang::ObjCObjectPointerType>();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000572
Sean Callanan5780f9d2011-12-08 19:04:34 +0000573 if (pointer_pointertype)
574 {
575 clang::QualType element_qual_type = pointer_pointertype->getPointeeType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000576
Sean Callanan5780f9d2011-12-08 19:04:34 +0000577 m_result_type = lldb_private::TypeFromParser(element_qual_type.getAsOpaquePtr(),
Pavel Labathc33ae022015-06-08 22:27:10 +0000578 lldb_private::ClangASTContext::GetASTContext(&result_decl->getASTContext()));
Sean Callanan5780f9d2011-12-08 19:04:34 +0000579 }
580 else if (pointer_objcobjpointertype)
581 {
582 clang::QualType element_qual_type = clang::QualType(pointer_objcobjpointertype->getObjectType(), 0);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000583
Sean Callanan5780f9d2011-12-08 19:04:34 +0000584 m_result_type = lldb_private::TypeFromParser(element_qual_type.getAsOpaquePtr(),
Pavel Labathc33ae022015-06-08 22:27:10 +0000585 lldb_private::ClangASTContext::GetASTContext(&result_decl->getASTContext()));
Sean Callanan5780f9d2011-12-08 19:04:34 +0000586 }
587 else
Sean Callanan92adcac2011-01-13 08:53:35 +0000588 {
589 if (log)
590 log->PutCString("Expected result to have pointer type, but it did not");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000591
Sean Callanan3989fb92011-01-27 01:07:04 +0000592 if (m_error_stream)
593 m_error_stream->Printf("Internal error [IRForTarget]: Lvalue result (%s) is not a pointer variable\n", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000594
Sean Callanan92adcac2011-01-13 08:53:35 +0000595 return false;
596 }
Sean Callanan92adcac2011-01-13 08:53:35 +0000597 }
598 else
599 {
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000600 m_result_type = lldb_private::TypeFromParser(result_var->getType().getAsOpaquePtr(),
Pavel Labathc33ae022015-06-08 22:27:10 +0000601 lldb_private::ClangASTContext::GetASTContext(&result_decl->getASTContext()));
Sean Callanan00f43622011-11-18 03:28:09 +0000602 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000603
Greg Clayton526ae042015-02-12 00:34:25 +0000604
605 lldb::TargetSP target_sp (m_data_allocator.GetTarget());
Greg Claytonf9da9282015-02-27 00:12:22 +0000606 lldb_private::ExecutionContext exe_ctx (target_sp, true);
Greg Clayton526ae042015-02-12 00:34:25 +0000607 if (m_result_type.GetBitSize(exe_ctx.GetBestExecutionContextScope()) == 0)
Sean Callanan00f43622011-11-18 03:28:09 +0000608 {
609 lldb_private::StreamString type_desc_stream;
610 m_result_type.DumpTypeDescription(&type_desc_stream);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000611
Sean Callanan00f43622011-11-18 03:28:09 +0000612 if (log)
613 log->Printf("Result type has size 0");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000614
Sean Callanan00f43622011-11-18 03:28:09 +0000615 if (m_error_stream)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000616 m_error_stream->Printf("Error [IRForTarget]: Size of result type '%s' couldn't be determined\n",
Sean Callanan00f43622011-11-18 03:28:09 +0000617 type_desc_stream.GetData());
Sean Callanan960534c2011-12-21 23:44:05 +0000618 return false;
Sean Callanan92adcac2011-01-13 08:53:35 +0000619 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000620
Sean Callanan63697e52011-05-07 01:06:41 +0000621 if (log)
622 {
623 lldb_private::StreamString type_desc_stream;
Sean Callanan3bfdaa22011-09-15 02:13:07 +0000624 m_result_type.DumpTypeDescription(&type_desc_stream);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000625
Sean Callanan00f43622011-11-18 03:28:09 +0000626 log->Printf("Result decl type: \"%s\"", type_desc_stream.GetData());
Sean Callanan63697e52011-05-07 01:06:41 +0000627 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000628
Sean Callanan1582ee62013-04-18 22:06:33 +0000629 m_result_name = lldb_private::ConstString("$RESULT_NAME");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000630
Sean Callanand1e5b432010-08-12 01:56:52 +0000631 if (log)
Greg Claytonfaac1112013-03-14 18:31:44 +0000632 log->Printf("Creating a new result global: \"%s\" with size 0x%" PRIx64,
Sean Callanan00f43622011-11-18 03:28:09 +0000633 m_result_name.GetCString(),
Enrico Granata1cd5e922015-01-28 00:07:51 +0000634 m_result_type.GetByteSize(nullptr));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000635
Sean Callanand1e5b432010-08-12 01:56:52 +0000636 // Construct a new result global and set up its metadata
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000637
638 GlobalVariable *new_result_global = new GlobalVariable((*m_module),
Sean Callanand1e5b432010-08-12 01:56:52 +0000639 result_global->getType()->getElementType(),
640 false, /* not constant */
641 GlobalValue::ExternalLinkage,
642 NULL, /* no initializer */
Sean Callanan92adcac2011-01-13 08:53:35 +0000643 m_result_name.GetCString ());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000644
Sean Callanand1e5b432010-08-12 01:56:52 +0000645 // It's too late in compilation to create a new VarDecl for this, but we don't
646 // need to. We point the metadata at the old VarDecl. This creates an odd
647 // anomaly: a variable with a Value whose name is something like $0 and a
Greg Clayton7b462cc2010-10-15 22:48:33 +0000648 // Decl whose name is $__lldb_expr_result. This condition is handled in
Sean Callanand1e5b432010-08-12 01:56:52 +0000649 // ClangExpressionDeclMap::DoMaterialize, and the name of the variable is
650 // fixed up.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000651
Sean Callanan79763a42011-05-23 21:40:23 +0000652 ConstantInt *new_constant_int = ConstantInt::get(llvm::Type::getInt64Ty(m_module->getContext()),
Sean Callanan63697e52011-05-07 01:06:41 +0000653 reinterpret_cast<uint64_t>(result_decl),
Sean Callanand1e5b432010-08-12 01:56:52 +0000654 false);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000655
Zachary Turner543afa12014-12-09 22:29:47 +0000656 llvm::Metadata *values[2];
657 values[0] = ConstantAsMetadata::get(new_result_global);
658 values[1] = ConstantAsMetadata::get(new_constant_int);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000659
Zachary Turner543afa12014-12-09 22:29:47 +0000660 ArrayRef<Metadata *> value_ref(values, 2);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000661
Sean Callanan79763a42011-05-23 21:40:23 +0000662 MDNode *persistent_global_md = MDNode::get(m_module->getContext(), value_ref);
663 NamedMDNode *named_metadata = m_module->getNamedMetadata("clang.global.decl.ptrs");
Sean Callanand1e5b432010-08-12 01:56:52 +0000664 named_metadata->addOperand(persistent_global_md);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000665
Sean Callanand1e5b432010-08-12 01:56:52 +0000666 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +0000667 log->Printf("Replacing \"%s\" with \"%s\"",
Sean Callanan1e87fff2010-09-07 22:43:19 +0000668 PrintValue(result_global).c_str(),
Sean Callanand1e5b432010-08-12 01:56:52 +0000669 PrintValue(new_result_global).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000670
Sean Callanan339f6152014-03-11 19:19:16 +0000671 if (result_global->use_empty())
Sean Callanan1e87fff2010-09-07 22:43:19 +0000672 {
673 // We need to synthesize a store for this variable, because otherwise
674 // there's nothing to put into its equivalent persistent variable.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000675
Greg Clayton7b462cc2010-10-15 22:48:33 +0000676 BasicBlock &entry_block(llvm_function.getEntryBlock());
Sean Callanan1e87fff2010-09-07 22:43:19 +0000677 Instruction *first_entry_instruction(entry_block.getFirstNonPHIOrDbg());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000678
Sean Callanan1e87fff2010-09-07 22:43:19 +0000679 if (!first_entry_instruction)
680 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000681
Sean Callanan1e87fff2010-09-07 22:43:19 +0000682 if (!result_global->hasInitializer())
683 {
684 if (log)
685 log->Printf("Couldn't find initializer for unused variable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000686
Sean Callanan3989fb92011-01-27 01:07:04 +0000687 if (m_error_stream)
688 m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s) has no writes and no initializer\n", result_name);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000689
Sean Callanan1e87fff2010-09-07 22:43:19 +0000690 return false;
691 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000692
Sean Callanan1e87fff2010-09-07 22:43:19 +0000693 Constant *initializer = result_global->getInitializer();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000694
Greg Clayton9c139312011-02-05 02:28:58 +0000695 StoreInst *synthesized_store = new StoreInst(initializer,
696 new_result_global,
697 first_entry_instruction);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000698
Sean Callanan1e87fff2010-09-07 22:43:19 +0000699 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +0000700 log->Printf("Synthesized result store \"%s\"\n", PrintValue(synthesized_store).c_str());
Sean Callanan1e87fff2010-09-07 22:43:19 +0000701 }
702 else
703 {
704 result_global->replaceAllUsesWith(new_result_global);
705 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000706
Sean Callanan1582ee62013-04-18 22:06:33 +0000707 if (!m_decl_map->AddPersistentVariable(result_decl,
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000708 m_result_name,
Sean Callanan1582ee62013-04-18 22:06:33 +0000709 m_result_type,
710 true,
711 m_result_is_pointer))
712 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000713
Sean Callanand1e5b432010-08-12 01:56:52 +0000714 result_global->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000715
Sean Callanand1e5b432010-08-12 01:56:52 +0000716 return true;
717}
718
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000719bool
Sean Callanan79763a42011-05-23 21:40:23 +0000720IRForTarget::RewriteObjCConstString (llvm::GlobalVariable *ns_str,
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000721 llvm::GlobalVariable *cstr)
Sean Callananafe16a72010-11-17 23:00:36 +0000722{
Greg Clayton5160ce52013-03-27 23:08:40 +0000723 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000724
Sean Callanancc427fa2011-07-30 02:42:06 +0000725 Type *ns_str_ty = ns_str->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000726
Sean Callanancc427fa2011-07-30 02:42:06 +0000727 Type *i8_ptr_ty = Type::getInt8PtrTy(m_module->getContext());
Sean Callanancc427fa2011-07-30 02:42:06 +0000728 Type *i32_ty = Type::getInt32Ty(m_module->getContext());
729 Type *i8_ty = Type::getInt8Ty(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000730
Sean Callananafe16a72010-11-17 23:00:36 +0000731 if (!m_CFStringCreateWithBytes)
732 {
733 lldb::addr_t CFStringCreateWithBytes_addr;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000734
Sean Callananafe16a72010-11-17 23:00:36 +0000735 static lldb_private::ConstString g_CFStringCreateWithBytes_str ("CFStringCreateWithBytes");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000736
Sean Callananafe16a72010-11-17 23:00:36 +0000737 if (!m_decl_map->GetFunctionAddress (g_CFStringCreateWithBytes_str, CFStringCreateWithBytes_addr))
738 {
739 if (log)
740 log->PutCString("Couldn't find CFStringCreateWithBytes in the target");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000741
Sean Callanan3989fb92011-01-27 01:07:04 +0000742 if (m_error_stream)
743 m_error_stream->Printf("Error [IRForTarget]: Rewriting an Objective-C constant string requires CFStringCreateWithBytes\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000744
Sean Callananafe16a72010-11-17 23:00:36 +0000745 return false;
746 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000747
Sean Callananafe16a72010-11-17 23:00:36 +0000748 if (log)
Daniel Malead01b2952012-11-29 21:49:15 +0000749 log->Printf("Found CFStringCreateWithBytes at 0x%" PRIx64, CFStringCreateWithBytes_addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000750
Sean Callananafe16a72010-11-17 23:00:36 +0000751 // Build the function type:
752 //
753 // CFStringRef CFStringCreateWithBytes (
754 // CFAllocatorRef alloc,
755 // const UInt8 *bytes,
756 // CFIndex numBytes,
757 // CFStringEncoding encoding,
758 // Boolean isExternalRepresentation
759 // );
760 //
761 // We make the following substitutions:
762 //
763 // CFStringRef -> i8*
764 // CFAllocatorRef -> i8*
765 // UInt8 * -> i8*
766 // CFIndex -> long (i32 or i64, as appropriate; we ask the module for its pointer size for now)
767 // CFStringEncoding -> i32
768 // Boolean -> i8
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000769
Sean Callanancc427fa2011-07-30 02:42:06 +0000770 Type *arg_type_array[5];
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000771
Sean Callanancc427fa2011-07-30 02:42:06 +0000772 arg_type_array[0] = i8_ptr_ty;
773 arg_type_array[1] = i8_ptr_ty;
Sean Callanan439dcae2013-12-20 19:55:02 +0000774 arg_type_array[2] = m_intptr_ty;
Sean Callanancc427fa2011-07-30 02:42:06 +0000775 arg_type_array[3] = i32_ty;
776 arg_type_array[4] = i8_ty;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000777
Sean Callanancc427fa2011-07-30 02:42:06 +0000778 ArrayRef<Type *> CFSCWB_arg_types(arg_type_array, 5);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000779
Sean Callanan79763a42011-05-23 21:40:23 +0000780 llvm::Type *CFSCWB_ty = FunctionType::get(ns_str_ty, CFSCWB_arg_types, false);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000781
Sean Callananafe16a72010-11-17 23:00:36 +0000782 // Build the constant containing the pointer to the function
783 PointerType *CFSCWB_ptr_ty = PointerType::getUnqual(CFSCWB_ty);
Sean Callanan439dcae2013-12-20 19:55:02 +0000784 Constant *CFSCWB_addr_int = ConstantInt::get(m_intptr_ty, CFStringCreateWithBytes_addr, false);
Sean Callananafe16a72010-11-17 23:00:36 +0000785 m_CFStringCreateWithBytes = ConstantExpr::getIntToPtr(CFSCWB_addr_int, CFSCWB_ptr_ty);
786 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000787
Sean Callanand2b465f2012-02-09 03:22:41 +0000788 ConstantDataSequential *string_array = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000789
Sean Callanan229ce2d2011-02-10 22:17:53 +0000790 if (cstr)
Sean Callanand2b465f2012-02-09 03:22:41 +0000791 string_array = dyn_cast<ConstantDataSequential>(cstr->getInitializer());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000792
Sean Callananafe16a72010-11-17 23:00:36 +0000793 Constant *alloc_arg = Constant::getNullValue(i8_ptr_ty);
Sean Callanan229ce2d2011-02-10 22:17:53 +0000794 Constant *bytes_arg = cstr ? ConstantExpr::getBitCast(cstr, i8_ptr_ty) : Constant::getNullValue(i8_ptr_ty);
Sean Callanan439dcae2013-12-20 19:55:02 +0000795 Constant *numBytes_arg = ConstantInt::get(m_intptr_ty, cstr ? string_array->getNumElements() - 1 : 0, false);
Sean Callananafe16a72010-11-17 23:00:36 +0000796 Constant *encoding_arg = ConstantInt::get(i32_ty, 0x0600, false); /* 0x0600 is kCFStringEncodingASCII */
797 Constant *isExternal_arg = ConstantInt::get(i8_ty, 0x0, false); /* 0x0 is false */
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000798
Sean Callanancc427fa2011-07-30 02:42:06 +0000799 Value *argument_array[5];
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000800
Sean Callanancc427fa2011-07-30 02:42:06 +0000801 argument_array[0] = alloc_arg;
802 argument_array[1] = bytes_arg;
803 argument_array[2] = numBytes_arg;
804 argument_array[3] = encoding_arg;
805 argument_array[4] = isExternal_arg;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000806
Sean Callanancc427fa2011-07-30 02:42:06 +0000807 ArrayRef <Value *> CFSCWB_arguments(argument_array, 5);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000808
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000809 FunctionValueCache CFSCWB_Caller ([this, &CFSCWB_arguments] (llvm::Function *function)->llvm::Value * {
810 return CallInst::Create(m_CFStringCreateWithBytes,
811 CFSCWB_arguments,
812 "CFStringCreateWithBytes",
813 llvm::cast<Instruction>(m_entry_instruction_finder.GetValue(function)));
814 });
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000815
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000816 if (!UnfoldConstant(ns_str, CFSCWB_Caller, m_entry_instruction_finder))
Sean Callananafe16a72010-11-17 23:00:36 +0000817 {
818 if (log)
819 log->PutCString("Couldn't replace the NSString with the result of the call");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000820
Sean Callanan3989fb92011-01-27 01:07:04 +0000821 if (m_error_stream)
822 m_error_stream->Printf("Error [IRForTarget]: Couldn't replace an Objective-C constant string with a dynamic string\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000823
Sean Callananafe16a72010-11-17 23:00:36 +0000824 return false;
825 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000826
Greg Clayton1b95a6f2010-11-19 01:05:25 +0000827 ns_str->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000828
Sean Callananafe16a72010-11-17 23:00:36 +0000829 return true;
830}
831
832bool
Sean Callanan1f9db3e2013-06-28 21:44:15 +0000833IRForTarget::RewriteObjCConstStrings()
Sean Callananafe16a72010-11-17 23:00:36 +0000834{
Greg Clayton5160ce52013-03-27 23:08:40 +0000835 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000836
Sean Callanan79763a42011-05-23 21:40:23 +0000837 ValueSymbolTable& value_symbol_table = m_module->getValueSymbolTable();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000838
Sean Callananafe16a72010-11-17 23:00:36 +0000839 for (ValueSymbolTable::iterator vi = value_symbol_table.begin(), ve = value_symbol_table.end();
840 vi != ve;
841 ++vi)
842 {
Sean Callanancc427fa2011-07-30 02:42:06 +0000843 std::string value_name = vi->first().str();
844 const char *value_name_cstr = value_name.c_str();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000845
Sean Callanancc427fa2011-07-30 02:42:06 +0000846 if (strstr(value_name_cstr, "_unnamed_cfstring_"))
Sean Callananafe16a72010-11-17 23:00:36 +0000847 {
848 Value *nsstring_value = vi->second;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000849
Sean Callananafe16a72010-11-17 23:00:36 +0000850 GlobalVariable *nsstring_global = dyn_cast<GlobalVariable>(nsstring_value);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000851
Sean Callananafe16a72010-11-17 23:00:36 +0000852 if (!nsstring_global)
853 {
854 if (log)
855 log->PutCString("NSString variable is not a GlobalVariable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000856
Sean Callanan3989fb92011-01-27 01:07:04 +0000857 if (m_error_stream)
858 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string is not a global variable\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000859
Sean Callananafe16a72010-11-17 23:00:36 +0000860 return false;
861 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000862
Sean Callananafe16a72010-11-17 23:00:36 +0000863 if (!nsstring_global->hasInitializer())
864 {
865 if (log)
866 log->PutCString("NSString variable does not have an initializer");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000867
Sean Callanan3989fb92011-01-27 01:07:04 +0000868 if (m_error_stream)
869 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string does not have an initializer\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000870
Sean Callananafe16a72010-11-17 23:00:36 +0000871 return false;
872 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000873
Sean Callananafe16a72010-11-17 23:00:36 +0000874 ConstantStruct *nsstring_struct = dyn_cast<ConstantStruct>(nsstring_global->getInitializer());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000875
Sean Callananafe16a72010-11-17 23:00:36 +0000876 if (!nsstring_struct)
877 {
878 if (log)
879 log->PutCString("NSString variable's initializer is not a ConstantStruct");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000880
Sean Callanan3989fb92011-01-27 01:07:04 +0000881 if (m_error_stream)
882 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string is not a structure constant\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000883
Sean Callananafe16a72010-11-17 23:00:36 +0000884 return false;
885 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000886
Sean Callananafe16a72010-11-17 23:00:36 +0000887 // We expect the following structure:
888 //
889 // struct {
890 // int *isa;
891 // int flags;
892 // char *str;
893 // long length;
894 // };
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000895
Sean Callananafe16a72010-11-17 23:00:36 +0000896 if (nsstring_struct->getNumOperands() != 4)
897 {
898 if (log)
899 log->Printf("NSString variable's initializer structure has an unexpected number of members. Should be 4, is %d", nsstring_struct->getNumOperands());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000900
Sean Callanan3989fb92011-01-27 01:07:04 +0000901 if (m_error_stream)
902 m_error_stream->Printf("Internal error [IRForTarget]: The struct for an Objective-C constant string is not as expected\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000903
Sean Callananafe16a72010-11-17 23:00:36 +0000904 return false;
905 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000906
Sean Callananafe16a72010-11-17 23:00:36 +0000907 Constant *nsstring_member = nsstring_struct->getOperand(2);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000908
Sean Callananafe16a72010-11-17 23:00:36 +0000909 if (!nsstring_member)
910 {
911 if (log)
912 log->PutCString("NSString initializer's str element was empty");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000913
Sean Callanan3989fb92011-01-27 01:07:04 +0000914 if (m_error_stream)
915 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string does not have a string initializer\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000916
Sean Callananafe16a72010-11-17 23:00:36 +0000917 return false;
918 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000919
Sean Callananafe16a72010-11-17 23:00:36 +0000920 ConstantExpr *nsstring_expr = dyn_cast<ConstantExpr>(nsstring_member);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000921
Sean Callananafe16a72010-11-17 23:00:36 +0000922 if (!nsstring_expr)
923 {
924 if (log)
925 log->PutCString("NSString initializer's str element is not a ConstantExpr");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000926
Sean Callanan3989fb92011-01-27 01:07:04 +0000927 if (m_error_stream)
928 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string's string initializer is not constant\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000929
Sean Callananafe16a72010-11-17 23:00:36 +0000930 return false;
931 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000932
Sean Callananafe16a72010-11-17 23:00:36 +0000933 if (nsstring_expr->getOpcode() != Instruction::GetElementPtr)
934 {
935 if (log)
936 log->Printf("NSString initializer's str element is not a GetElementPtr expression, it's a %s", nsstring_expr->getOpcodeName());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000937
Sean Callanan3989fb92011-01-27 01:07:04 +0000938 if (m_error_stream)
939 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string's string initializer is not an array\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000940
Sean Callananafe16a72010-11-17 23:00:36 +0000941 return false;
942 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000943
Sean Callananafe16a72010-11-17 23:00:36 +0000944 Constant *nsstring_cstr = nsstring_expr->getOperand(0);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000945
Sean Callananafe16a72010-11-17 23:00:36 +0000946 GlobalVariable *cstr_global = dyn_cast<GlobalVariable>(nsstring_cstr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000947
Sean Callananafe16a72010-11-17 23:00:36 +0000948 if (!cstr_global)
949 {
950 if (log)
951 log->PutCString("NSString initializer's str element is not a GlobalVariable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000952
Sean Callanan3989fb92011-01-27 01:07:04 +0000953 if (m_error_stream)
954 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string's string initializer doesn't point to a global\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000955
Sean Callananafe16a72010-11-17 23:00:36 +0000956 return false;
957 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000958
Sean Callananafe16a72010-11-17 23:00:36 +0000959 if (!cstr_global->hasInitializer())
960 {
961 if (log)
962 log->PutCString("NSString initializer's str element does not have an initializer");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000963
Sean Callanan3989fb92011-01-27 01:07:04 +0000964 if (m_error_stream)
965 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string's string initializer doesn't point to initialized data\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000966
Sean Callananafe16a72010-11-17 23:00:36 +0000967 return false;
968 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000969
Sean Callanan229ce2d2011-02-10 22:17:53 +0000970 /*
Sean Callananafe16a72010-11-17 23:00:36 +0000971 if (!cstr_array)
972 {
973 if (log)
974 log->PutCString("NSString initializer's str element is not a ConstantArray");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000975
Sean Callanan3989fb92011-01-27 01:07:04 +0000976 if (m_error_stream)
977 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string's string initializer doesn't point to an array\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000978
Sean Callananafe16a72010-11-17 23:00:36 +0000979 return false;
980 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000981
Sean Callananafe16a72010-11-17 23:00:36 +0000982 if (!cstr_array->isCString())
983 {
984 if (log)
985 log->PutCString("NSString initializer's str element is not a C string array");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000986
Sean Callanan3989fb92011-01-27 01:07:04 +0000987 if (m_error_stream)
988 m_error_stream->Printf("Internal error [IRForTarget]: An Objective-C constant string's string initializer doesn't point to a C string\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000989
Sean Callananafe16a72010-11-17 23:00:36 +0000990 return false;
991 }
Sean Callanan229ce2d2011-02-10 22:17:53 +0000992 */
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000993
Sean Callanand2b465f2012-02-09 03:22:41 +0000994 ConstantDataArray *cstr_array = dyn_cast<ConstantDataArray>(cstr_global->getInitializer());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +0000995
Sean Callananafe16a72010-11-17 23:00:36 +0000996 if (log)
Sean Callanan229ce2d2011-02-10 22:17:53 +0000997 {
998 if (cstr_array)
Sean Callanand2b465f2012-02-09 03:22:41 +0000999 log->Printf("Found NSString constant %s, which contains \"%s\"", value_name_cstr, cstr_array->getAsString().str().c_str());
Sean Callanan229ce2d2011-02-10 22:17:53 +00001000 else
Sean Callanancc427fa2011-07-30 02:42:06 +00001001 log->Printf("Found NSString constant %s, which contains \"\"", value_name_cstr);
Sean Callanan229ce2d2011-02-10 22:17:53 +00001002 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001003
Sean Callanan229ce2d2011-02-10 22:17:53 +00001004 if (!cstr_array)
1005 cstr_global = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001006
Sean Callanan1f9db3e2013-06-28 21:44:15 +00001007 if (!RewriteObjCConstString(nsstring_global, cstr_global))
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001008 {
Sean Callananafe16a72010-11-17 23:00:36 +00001009 if (log)
1010 log->PutCString("Error rewriting the constant string");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001011
Sean Callanan3989fb92011-01-27 01:07:04 +00001012 // We don't print an error message here because RewriteObjCConstString has done so for us.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001013
Sean Callananafe16a72010-11-17 23:00:36 +00001014 return false;
1015 }
Sean Callananafe16a72010-11-17 23:00:36 +00001016 }
1017 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001018
Sean Callananafe16a72010-11-17 23:00:36 +00001019 for (ValueSymbolTable::iterator vi = value_symbol_table.begin(), ve = value_symbol_table.end();
1020 vi != ve;
1021 ++vi)
1022 {
Sean Callanancc427fa2011-07-30 02:42:06 +00001023 std::string value_name = vi->first().str();
1024 const char *value_name_cstr = value_name.c_str();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001025
Sean Callanancc427fa2011-07-30 02:42:06 +00001026 if (!strcmp(value_name_cstr, "__CFConstantStringClassReference"))
Sean Callananafe16a72010-11-17 23:00:36 +00001027 {
1028 GlobalVariable *gv = dyn_cast<GlobalVariable>(vi->second);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001029
Sean Callananafe16a72010-11-17 23:00:36 +00001030 if (!gv)
1031 {
1032 if (log)
1033 log->PutCString("__CFConstantStringClassReference is not a global variable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001034
Sean Callanan3989fb92011-01-27 01:07:04 +00001035 if (m_error_stream)
1036 m_error_stream->Printf("Internal error [IRForTarget]: Found a CFConstantStringClassReference, but it is not a global object\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001037
Sean Callananafe16a72010-11-17 23:00:36 +00001038 return false;
1039 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001040
Sean Callananafe16a72010-11-17 23:00:36 +00001041 gv->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001042
Sean Callananafe16a72010-11-17 23:00:36 +00001043 break;
1044 }
1045 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001046
Sean Callananafe16a72010-11-17 23:00:36 +00001047 return true;
1048}
1049
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001050static bool IsObjCSelectorRef (Value *value)
Sean Callanan5300d372010-07-31 01:32:05 +00001051{
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001052 GlobalVariable *global_variable = dyn_cast<GlobalVariable>(value);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001053
Greg Claytonbd549162014-11-10 21:45:59 +00001054 if (!global_variable || !global_variable->hasName() || !global_variable->getName().startswith("OBJC_SELECTOR_REFERENCES_"))
Sean Callanan5300d372010-07-31 01:32:05 +00001055 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001056
Sean Callanan5300d372010-07-31 01:32:05 +00001057 return true;
1058}
1059
Sean Callanan3989fb92011-01-27 01:07:04 +00001060// This function does not report errors; its callers are responsible.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001061bool
Sean Callanan79763a42011-05-23 21:40:23 +00001062IRForTarget::RewriteObjCSelector (Instruction* selector_load)
Sean Callanan5300d372010-07-31 01:32:05 +00001063{
Greg Clayton5160ce52013-03-27 23:08:40 +00001064 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanan5300d372010-07-31 01:32:05 +00001065
1066 LoadInst *load = dyn_cast<LoadInst>(selector_load);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001067
Sean Callanan5300d372010-07-31 01:32:05 +00001068 if (!load)
1069 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001070
Sean Callanan5300d372010-07-31 01:32:05 +00001071 // Unpack the message name from the selector. In LLVM IR, an objc_msgSend gets represented as
1072 //
Greg Clayton45f4f8b2014-11-10 21:48:12 +00001073 // %tmp = load i8** @"OBJC_SELECTOR_REFERENCES_" ; <i8*>
Sean Callanan5300d372010-07-31 01:32:05 +00001074 // %call = call i8* (i8*, i8*, ...)* @objc_msgSend(i8* %obj, i8* %tmp, ...) ; <i8*>
1075 //
1076 // where %obj is the object pointer and %tmp is the selector.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001077 //
Greg Clayton45f4f8b2014-11-10 21:48:12 +00001078 // @"OBJC_SELECTOR_REFERENCES_" is a pointer to a character array called @"\01L_OBJC_llvm_moduleETH_VAR_NAllvm_moduleE_".
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001079 // @"\01L_OBJC_llvm_moduleETH_VAR_NAllvm_moduleE_" contains the string.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001080
Sean Callanan5300d372010-07-31 01:32:05 +00001081 // Find the pointer's initializer (a ConstantExpr with opcode GetElementPtr) and get the string from its target
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001082
Sean Callanan5300d372010-07-31 01:32:05 +00001083 GlobalVariable *_objc_selector_references_ = dyn_cast<GlobalVariable>(load->getPointerOperand());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001084
Sean Callanan5300d372010-07-31 01:32:05 +00001085 if (!_objc_selector_references_ || !_objc_selector_references_->hasInitializer())
1086 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001087
Sean Callanan5300d372010-07-31 01:32:05 +00001088 Constant *osr_initializer = _objc_selector_references_->getInitializer();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001089
Sean Callanan5300d372010-07-31 01:32:05 +00001090 ConstantExpr *osr_initializer_expr = dyn_cast<ConstantExpr>(osr_initializer);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001091
Sean Callanan5300d372010-07-31 01:32:05 +00001092 if (!osr_initializer_expr || osr_initializer_expr->getOpcode() != Instruction::GetElementPtr)
1093 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001094
Sean Callanan5300d372010-07-31 01:32:05 +00001095 Value *osr_initializer_base = osr_initializer_expr->getOperand(0);
1096
1097 if (!osr_initializer_base)
1098 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001099
Sean Callanan5300d372010-07-31 01:32:05 +00001100 // Find the string's initializer (a ConstantArray) and get the string from it
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001101
Sean Callanan5300d372010-07-31 01:32:05 +00001102 GlobalVariable *_objc_meth_var_name_ = dyn_cast<GlobalVariable>(osr_initializer_base);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001103
Sean Callanan5300d372010-07-31 01:32:05 +00001104 if (!_objc_meth_var_name_ || !_objc_meth_var_name_->hasInitializer())
1105 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001106
Sean Callanan5300d372010-07-31 01:32:05 +00001107 Constant *omvn_initializer = _objc_meth_var_name_->getInitializer();
1108
Sean Callanand2b465f2012-02-09 03:22:41 +00001109 ConstantDataArray *omvn_initializer_array = dyn_cast<ConstantDataArray>(omvn_initializer);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001110
Sean Callanan5300d372010-07-31 01:32:05 +00001111 if (!omvn_initializer_array->isString())
1112 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001113
Sean Callanan5300d372010-07-31 01:32:05 +00001114 std::string omvn_initializer_string = omvn_initializer_array->getAsString();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001115
Sean Callanan5300d372010-07-31 01:32:05 +00001116 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +00001117 log->Printf("Found Objective-C selector reference \"%s\"", omvn_initializer_string.c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001118
Sean Callanan5300d372010-07-31 01:32:05 +00001119 // Construct a call to sel_registerName
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001120
Sean Callanan5300d372010-07-31 01:32:05 +00001121 if (!m_sel_registerName)
1122 {
Greg Claytoncb7e3b32010-11-15 01:47:11 +00001123 lldb::addr_t sel_registerName_addr;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001124
Greg Clayton7b462cc2010-10-15 22:48:33 +00001125 static lldb_private::ConstString g_sel_registerName_str ("sel_registerName");
Greg Claytoncb7e3b32010-11-15 01:47:11 +00001126 if (!m_decl_map->GetFunctionAddress (g_sel_registerName_str, sel_registerName_addr))
Sean Callanan5300d372010-07-31 01:32:05 +00001127 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001128
Sean Callananbe3a1b12010-10-26 00:31:56 +00001129 if (log)
Daniel Malead01b2952012-11-29 21:49:15 +00001130 log->Printf("Found sel_registerName at 0x%" PRIx64, sel_registerName_addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001131
Sean Callanan5300d372010-07-31 01:32:05 +00001132 // Build the function type: struct objc_selector *sel_registerName(uint8_t*)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001133
Sean Callanan5300d372010-07-31 01:32:05 +00001134 // The below code would be "more correct," but in actuality what's required is uint8_t*
Sean Callanan79763a42011-05-23 21:40:23 +00001135 //Type *sel_type = StructType::get(m_module->getContext());
Sean Callanan5300d372010-07-31 01:32:05 +00001136 //Type *sel_ptr_type = PointerType::getUnqual(sel_type);
Sean Callanancc427fa2011-07-30 02:42:06 +00001137 Type *sel_ptr_type = Type::getInt8PtrTy(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001138
Sean Callanancc427fa2011-07-30 02:42:06 +00001139 Type *type_array[1];
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001140
Sean Callanancc427fa2011-07-30 02:42:06 +00001141 type_array[0] = llvm::Type::getInt8PtrTy(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001142
Sean Callanancc427fa2011-07-30 02:42:06 +00001143 ArrayRef<Type *> srN_arg_types(type_array, 1);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001144
Sean Callanan5300d372010-07-31 01:32:05 +00001145 llvm::Type *srN_type = FunctionType::get(sel_ptr_type, srN_arg_types, false);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001146
Sean Callanan5300d372010-07-31 01:32:05 +00001147 // Build the constant containing the pointer to the function
Sean Callanan5300d372010-07-31 01:32:05 +00001148 PointerType *srN_ptr_ty = PointerType::getUnqual(srN_type);
Sean Callanan439dcae2013-12-20 19:55:02 +00001149 Constant *srN_addr_int = ConstantInt::get(m_intptr_ty, sel_registerName_addr, false);
Sean Callanan5300d372010-07-31 01:32:05 +00001150 m_sel_registerName = ConstantExpr::getIntToPtr(srN_addr_int, srN_ptr_ty);
1151 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001152
Sean Callanancc427fa2011-07-30 02:42:06 +00001153 Value *argument_array[1];
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001154
Sean Callanan79763a42011-05-23 21:40:23 +00001155 Constant *omvn_pointer = ConstantExpr::getBitCast(_objc_meth_var_name_, Type::getInt8PtrTy(m_module->getContext()));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001156
Sean Callanancc427fa2011-07-30 02:42:06 +00001157 argument_array[0] = omvn_pointer;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001158
Sean Callanancc427fa2011-07-30 02:42:06 +00001159 ArrayRef<Value *> srN_arguments(argument_array, 1);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001160
1161 CallInst *srN_call = CallInst::Create(m_sel_registerName,
Sean Callanancc427fa2011-07-30 02:42:06 +00001162 srN_arguments,
Sean Callananafe16a72010-11-17 23:00:36 +00001163 "sel_registerName",
Sean Callanan5300d372010-07-31 01:32:05 +00001164 selector_load);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001165
Sean Callanan5300d372010-07-31 01:32:05 +00001166 // Replace the load with the call in all users
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001167
Sean Callanan5300d372010-07-31 01:32:05 +00001168 selector_load->replaceAllUsesWith(srN_call);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001169
Sean Callanan5300d372010-07-31 01:32:05 +00001170 selector_load->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001171
Sean Callanan5300d372010-07-31 01:32:05 +00001172 return true;
1173}
1174
1175bool
Sean Callanan79763a42011-05-23 21:40:23 +00001176IRForTarget::RewriteObjCSelectors (BasicBlock &basic_block)
Sean Callanan5300d372010-07-31 01:32:05 +00001177{
Greg Clayton5160ce52013-03-27 23:08:40 +00001178 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanan5300d372010-07-31 01:32:05 +00001179
1180 BasicBlock::iterator ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001181
Sean Callanan5300d372010-07-31 01:32:05 +00001182 typedef SmallVector <Instruction*, 2> InstrList;
1183 typedef InstrList::iterator InstrIterator;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001184
Sean Callanan5300d372010-07-31 01:32:05 +00001185 InstrList selector_loads;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001186
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001187 for (ii = basic_block.begin();
1188 ii != basic_block.end();
Sean Callanan5300d372010-07-31 01:32:05 +00001189 ++ii)
1190 {
1191 Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001192
Sean Callanan5300d372010-07-31 01:32:05 +00001193 if (LoadInst *load = dyn_cast<LoadInst>(&inst))
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001194 if (IsObjCSelectorRef(load->getPointerOperand()))
Sean Callanan5300d372010-07-31 01:32:05 +00001195 selector_loads.push_back(&inst);
1196 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001197
Sean Callanan5300d372010-07-31 01:32:05 +00001198 InstrIterator iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001199
Sean Callanan5300d372010-07-31 01:32:05 +00001200 for (iter = selector_loads.begin();
1201 iter != selector_loads.end();
1202 ++iter)
1203 {
Sean Callanan79763a42011-05-23 21:40:23 +00001204 if (!RewriteObjCSelector(*iter))
Sean Callanan5300d372010-07-31 01:32:05 +00001205 {
Sean Callanan3989fb92011-01-27 01:07:04 +00001206 if (m_error_stream)
1207 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't change a static reference to an Objective-C selector to a dynamic reference\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001208
Enrico Granata20edcdb2011-07-19 18:03:25 +00001209 if (log)
Sean Callanan5300d372010-07-31 01:32:05 +00001210 log->PutCString("Couldn't rewrite a reference to an Objective-C selector");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001211
Sean Callanan5300d372010-07-31 01:32:05 +00001212 return false;
1213 }
1214 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001215
Sean Callanan5300d372010-07-31 01:32:05 +00001216 return true;
1217}
1218
Sean Callanan3989fb92011-01-27 01:07:04 +00001219// This function does not report errors; its callers are responsible.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001220bool
Sean Callanan79763a42011-05-23 21:40:23 +00001221IRForTarget::RewritePersistentAlloc (llvm::Instruction *persistent_alloc)
Sean Callanan2235f322010-08-11 03:57:18 +00001222{
Greg Clayton5160ce52013-03-27 23:08:40 +00001223 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanane1175b72011-01-13 21:23:32 +00001224
Sean Callanan2235f322010-08-11 03:57:18 +00001225 AllocaInst *alloc = dyn_cast<AllocaInst>(persistent_alloc);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001226
Duncan P. N. Exon Smith68caa7d2014-11-12 01:59:53 +00001227 MDNode *alloc_md = alloc->getMetadata("clang.decl.ptr");
Sean Callanan2235f322010-08-11 03:57:18 +00001228
1229 if (!alloc_md || !alloc_md->getNumOperands())
1230 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001231
Zachary Turner543afa12014-12-09 22:29:47 +00001232 ConstantInt *constant_int = mdconst::dyn_extract<ConstantInt>(alloc_md->getOperand(0));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001233
Sean Callanan2235f322010-08-11 03:57:18 +00001234 if (!constant_int)
1235 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001236
Sean Callanan2235f322010-08-11 03:57:18 +00001237 // We attempt to register this as a new persistent variable with the DeclMap.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001238
Sean Callanan2235f322010-08-11 03:57:18 +00001239 uintptr_t ptr = constant_int->getZExtValue();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001240
Sean Callanand1e5b432010-08-12 01:56:52 +00001241 clang::VarDecl *decl = reinterpret_cast<clang::VarDecl *>(ptr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001242
Sean Callanand1e5b432010-08-12 01:56:52 +00001243 lldb_private::TypeFromParser result_decl_type (decl->getType().getAsOpaquePtr(),
Pavel Labathc33ae022015-06-08 22:27:10 +00001244 lldb_private::ClangASTContext::GetASTContext(&decl->getASTContext()));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001245
Greg Clayton7b462cc2010-10-15 22:48:33 +00001246 StringRef decl_name (decl->getName());
1247 lldb_private::ConstString persistent_variable_name (decl_name.data(), decl_name.size());
Sean Callanan92adcac2011-01-13 08:53:35 +00001248 if (!m_decl_map->AddPersistentVariable(decl, persistent_variable_name, result_decl_type, false, false))
Sean Callanan2235f322010-08-11 03:57:18 +00001249 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001250
Sean Callanan79763a42011-05-23 21:40:23 +00001251 GlobalVariable *persistent_global = new GlobalVariable((*m_module),
Sean Callanane1175b72011-01-13 21:23:32 +00001252 alloc->getType(),
Sean Callanan2235f322010-08-11 03:57:18 +00001253 false, /* not constant */
1254 GlobalValue::ExternalLinkage,
1255 NULL, /* no initializer */
1256 alloc->getName().str().c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001257
Sean Callanan2235f322010-08-11 03:57:18 +00001258 // What we're going to do here is make believe this was a regular old external
1259 // variable. That means we need to make the metadata valid.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001260
Sean Callanan585c0ec82012-07-04 01:26:26 +00001261 NamedMDNode *named_metadata = m_module->getOrInsertNamedMetadata("clang.global.decl.ptrs");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001262
Zachary Turner543afa12014-12-09 22:29:47 +00001263 llvm::Metadata *values[2];
1264 values[0] = ConstantAsMetadata::get(persistent_global);
1265 values[1] = ConstantAsMetadata::get(constant_int);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001266
Zachary Turner543afa12014-12-09 22:29:47 +00001267 ArrayRef<llvm::Metadata *> value_ref(values, 2);
Sean Callanan2235f322010-08-11 03:57:18 +00001268
Sean Callanan79763a42011-05-23 21:40:23 +00001269 MDNode *persistent_global_md = MDNode::get(m_module->getContext(), value_ref);
Sean Callanan2235f322010-08-11 03:57:18 +00001270 named_metadata->addOperand(persistent_global_md);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001271
Sean Callanane1175b72011-01-13 21:23:32 +00001272 // Now, since the variable is a pointer variable, we will drop in a load of that
1273 // pointer variable.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001274
Sean Callanane1175b72011-01-13 21:23:32 +00001275 LoadInst *persistent_load = new LoadInst (persistent_global, "", alloc);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001276
Sean Callanane1175b72011-01-13 21:23:32 +00001277 if (log)
1278 log->Printf("Replacing \"%s\" with \"%s\"",
1279 PrintValue(alloc).c_str(),
1280 PrintValue(persistent_load).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001281
Sean Callanane1175b72011-01-13 21:23:32 +00001282 alloc->replaceAllUsesWith(persistent_load);
Sean Callanan2235f322010-08-11 03:57:18 +00001283 alloc->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001284
Sean Callanan2235f322010-08-11 03:57:18 +00001285 return true;
1286}
1287
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001288bool
Sean Callanan79763a42011-05-23 21:40:23 +00001289IRForTarget::RewritePersistentAllocs(llvm::BasicBlock &basic_block)
Sean Callanan2235f322010-08-11 03:57:18 +00001290{
Sean Callanan9e6ed532010-09-13 21:34:21 +00001291 if (!m_resolve_vars)
1292 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001293
Greg Clayton5160ce52013-03-27 23:08:40 +00001294 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001295
Sean Callanan2235f322010-08-11 03:57:18 +00001296 BasicBlock::iterator ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001297
Sean Callanan2235f322010-08-11 03:57:18 +00001298 typedef SmallVector <Instruction*, 2> InstrList;
1299 typedef InstrList::iterator InstrIterator;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001300
Sean Callanan2235f322010-08-11 03:57:18 +00001301 InstrList pvar_allocs;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001302
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001303 for (ii = basic_block.begin();
1304 ii != basic_block.end();
Sean Callanan2235f322010-08-11 03:57:18 +00001305 ++ii)
1306 {
1307 Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001308
Sean Callanan2235f322010-08-11 03:57:18 +00001309 if (AllocaInst *alloc = dyn_cast<AllocaInst>(&inst))
Sean Callananf694a552011-01-21 22:30:25 +00001310 {
1311 llvm::StringRef alloc_name = alloc->getName();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001312
Sean Callananf694a552011-01-21 22:30:25 +00001313 if (alloc_name.startswith("$") &&
1314 !alloc_name.startswith("$__lldb"))
1315 {
1316 if (alloc_name.find_first_of("0123456789") == 1)
1317 {
1318 if (log)
1319 log->Printf("Rejecting a numeric persistent variable.");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001320
Sean Callanan3989fb92011-01-27 01:07:04 +00001321 if (m_error_stream)
1322 m_error_stream->Printf("Error [IRForTarget]: Names starting with $0, $1, ... are reserved for use as result names\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001323
Sean Callananf694a552011-01-21 22:30:25 +00001324 return false;
1325 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001326
Sean Callanan2235f322010-08-11 03:57:18 +00001327 pvar_allocs.push_back(alloc);
Sean Callananf694a552011-01-21 22:30:25 +00001328 }
1329 }
Sean Callanan2235f322010-08-11 03:57:18 +00001330 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001331
Sean Callanan2235f322010-08-11 03:57:18 +00001332 InstrIterator iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001333
Sean Callanan2235f322010-08-11 03:57:18 +00001334 for (iter = pvar_allocs.begin();
1335 iter != pvar_allocs.end();
1336 ++iter)
1337 {
Sean Callanan79763a42011-05-23 21:40:23 +00001338 if (!RewritePersistentAlloc(*iter))
Sean Callanan2235f322010-08-11 03:57:18 +00001339 {
Sean Callanan3989fb92011-01-27 01:07:04 +00001340 if (m_error_stream)
1341 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't rewrite the creation of a persistent variable\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001342
Enrico Granata20edcdb2011-07-19 18:03:25 +00001343 if (log)
Sean Callanan2235f322010-08-11 03:57:18 +00001344 log->PutCString("Couldn't rewrite the creation of a persistent variable");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001345
Sean Callanan2235f322010-08-11 03:57:18 +00001346 return false;
1347 }
1348 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001349
Sean Callanan2235f322010-08-11 03:57:18 +00001350 return true;
1351}
1352
Sean Callananc70ed462011-10-25 18:36:40 +00001353bool
1354IRForTarget::MaterializeInitializer (uint8_t *data, Constant *initializer)
1355{
1356 if (!initializer)
1357 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001358
Greg Clayton5160ce52013-03-27 23:08:40 +00001359 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callananc70ed462011-10-25 18:36:40 +00001360
1361 if (log && log->GetVerbose())
David Blaikie129b8392015-04-08 20:23:52 +00001362 log->Printf(" MaterializeInitializer(%p, %s)", (void *)data, PrintValue(initializer).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001363
Sean Callananc70ed462011-10-25 18:36:40 +00001364 Type *initializer_type = initializer->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001365
Sean Callananc70ed462011-10-25 18:36:40 +00001366 if (ConstantInt *int_initializer = dyn_cast<ConstantInt>(initializer))
1367 {
1368 memcpy (data, int_initializer->getValue().getRawData(), m_target_data->getTypeStoreSize(initializer_type));
1369 return true;
1370 }
Sean Callanand2b465f2012-02-09 03:22:41 +00001371 else if (ConstantDataArray *array_initializer = dyn_cast<ConstantDataArray>(initializer))
Sean Callananc70ed462011-10-25 18:36:40 +00001372 {
1373 if (array_initializer->isString())
1374 {
1375 std::string array_initializer_string = array_initializer->getAsString();
1376 memcpy (data, array_initializer_string.c_str(), m_target_data->getTypeStoreSize(initializer_type));
1377 }
1378 else
1379 {
1380 ArrayType *array_initializer_type = array_initializer->getType();
1381 Type *array_element_type = array_initializer_type->getElementType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001382
Sean Callananc70ed462011-10-25 18:36:40 +00001383 size_t element_size = m_target_data->getTypeAllocSize(array_element_type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001384
Andy Gibbsa297a972013-06-19 19:04:53 +00001385 for (unsigned i = 0; i < array_initializer->getNumOperands(); ++i)
Sean Callananc70ed462011-10-25 18:36:40 +00001386 {
Sean Callanand2b465f2012-02-09 03:22:41 +00001387 Value *operand_value = array_initializer->getOperand(i);
1388 Constant *operand_constant = dyn_cast<Constant>(operand_value);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001389
Sean Callanand2b465f2012-02-09 03:22:41 +00001390 if (!operand_constant)
1391 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001392
Sean Callanand2b465f2012-02-09 03:22:41 +00001393 if (!MaterializeInitializer(data + (i * element_size), operand_constant))
Sean Callananc70ed462011-10-25 18:36:40 +00001394 return false;
1395 }
1396 }
1397 return true;
1398 }
1399 else if (ConstantStruct *struct_initializer = dyn_cast<ConstantStruct>(initializer))
1400 {
1401 StructType *struct_initializer_type = struct_initializer->getType();
1402 const StructLayout *struct_layout = m_target_data->getStructLayout(struct_initializer_type);
1403
Andy Gibbsa297a972013-06-19 19:04:53 +00001404 for (unsigned i = 0;
Sean Callananc70ed462011-10-25 18:36:40 +00001405 i < struct_initializer->getNumOperands();
1406 ++i)
1407 {
1408 if (!MaterializeInitializer(data + struct_layout->getElementOffset(i), struct_initializer->getOperand(i)))
1409 return false;
1410 }
1411 return true;
1412 }
Sean Callanan76ee3e72013-04-24 19:50:12 +00001413 else if (isa<ConstantAggregateZero>(initializer))
1414 {
1415 memset(data, 0, m_target_data->getTypeStoreSize(initializer_type));
1416 return true;
1417 }
Sean Callananc70ed462011-10-25 18:36:40 +00001418 return false;
1419}
1420
1421bool
1422IRForTarget::MaterializeInternalVariable (GlobalVariable *global_variable)
1423{
1424 if (GlobalVariable::isExternalLinkage(global_variable->getLinkage()))
1425 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001426
Sean Callananfe5d1392011-11-15 19:13:54 +00001427 if (global_variable == m_reloc_placeholder)
1428 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001429
Sean Callanan8dfb68e2013-03-19 00:10:07 +00001430 uint64_t offset = m_data_allocator.GetStream().GetSize();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001431
Sean Callananc70ed462011-10-25 18:36:40 +00001432 llvm::Type *variable_type = global_variable->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001433
Sean Callananc70ed462011-10-25 18:36:40 +00001434 Constant *initializer = global_variable->getInitializer();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001435
Sean Callananc70ed462011-10-25 18:36:40 +00001436 llvm::Type *initializer_type = initializer->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001437
Sean Callananc70ed462011-10-25 18:36:40 +00001438 size_t size = m_target_data->getTypeAllocSize(initializer_type);
Sean Callanane3333d62012-06-08 22:20:41 +00001439 size_t align = m_target_data->getPrefTypeAlignment(initializer_type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001440
Sean Callanane3333d62012-06-08 22:20:41 +00001441 const size_t mask = (align - 1);
1442 uint64_t aligned_offset = (offset + mask) & ~mask;
Sean Callanan8dfb68e2013-03-19 00:10:07 +00001443 m_data_allocator.GetStream().PutNHex8(aligned_offset - offset, 0);
Sean Callanane3333d62012-06-08 22:20:41 +00001444 offset = aligned_offset;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001445
Sean Callananc70ed462011-10-25 18:36:40 +00001446 lldb_private::DataBufferHeap data(size, '\0');
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001447
Sean Callananc70ed462011-10-25 18:36:40 +00001448 if (initializer)
1449 if (!MaterializeInitializer(data.GetBytes(), initializer))
1450 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001451
Sean Callanan8dfb68e2013-03-19 00:10:07 +00001452 m_data_allocator.GetStream().Write(data.GetBytes(), data.GetByteSize());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001453
Sean Callananc70ed462011-10-25 18:36:40 +00001454 Constant *new_pointer = BuildRelocation(variable_type, offset);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001455
Sean Callananc70ed462011-10-25 18:36:40 +00001456 global_variable->replaceAllUsesWith(new_pointer);
1457
1458 global_variable->eraseFromParent();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001459
Sean Callananc70ed462011-10-25 18:36:40 +00001460 return true;
1461}
1462
Sean Callanan3989fb92011-01-27 01:07:04 +00001463// This function does not report errors; its callers are responsible.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001464bool
Sean Callanan79763a42011-05-23 21:40:23 +00001465IRForTarget::MaybeHandleVariable (Value *llvm_value_ptr)
Sean Callanan2ab712f22010-07-03 01:35:46 +00001466{
Greg Clayton5160ce52013-03-27 23:08:40 +00001467 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001468
Sean Callanand7a1ca22010-12-02 19:47:57 +00001469 if (log)
Sean Callanan88339f02010-12-06 22:16:55 +00001470 log->Printf("MaybeHandleVariable (%s)", PrintValue(llvm_value_ptr).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001471
Greg Clayton7b462cc2010-10-15 22:48:33 +00001472 if (ConstantExpr *constant_expr = dyn_cast<ConstantExpr>(llvm_value_ptr))
Sean Callanan4cf04d22010-08-03 00:23:29 +00001473 {
Sean Callanan5666b672010-08-04 01:02:13 +00001474 switch (constant_expr->getOpcode())
Sean Callanan4cf04d22010-08-03 00:23:29 +00001475 {
Sean Callanan5666b672010-08-04 01:02:13 +00001476 default:
1477 break;
1478 case Instruction::GetElementPtr:
1479 case Instruction::BitCast:
Sean Callanan4cf04d22010-08-03 00:23:29 +00001480 Value *s = constant_expr->getOperand(0);
Sean Callanan79763a42011-05-23 21:40:23 +00001481 if (!MaybeHandleVariable(s))
Sean Callanand7a1ca22010-12-02 19:47:57 +00001482 return false;
Sean Callanan4cf04d22010-08-03 00:23:29 +00001483 }
1484 }
Sean Callanand6e04ae2010-12-03 19:51:05 +00001485 else if (GlobalVariable *global_variable = dyn_cast<GlobalVariable>(llvm_value_ptr))
Sean Callanan5300d372010-07-31 01:32:05 +00001486 {
Sean Callananc70ed462011-10-25 18:36:40 +00001487 if (!GlobalValue::isExternalLinkage(global_variable->getLinkage()))
1488 return MaterializeInternalVariable(global_variable);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001489
Sean Callanan79763a42011-05-23 21:40:23 +00001490 clang::NamedDecl *named_decl = DeclForGlobal(global_variable);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001491
Sean Callanan5300d372010-07-31 01:32:05 +00001492 if (!named_decl)
1493 {
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001494 if (IsObjCSelectorRef(llvm_value_ptr))
Sean Callanan5300d372010-07-31 01:32:05 +00001495 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001496
Sean Callanan14f0b0e2010-12-06 00:56:39 +00001497 if (!global_variable->hasExternalLinkage())
1498 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001499
Sean Callanan5300d372010-07-31 01:32:05 +00001500 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +00001501 log->Printf("Found global variable \"%s\" without metadata", global_variable->getName().str().c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001502
Sean Callanan5300d372010-07-31 01:32:05 +00001503 return false;
1504 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001505
Greg Clayton7b462cc2010-10-15 22:48:33 +00001506 std::string name (named_decl->getName().str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001507
Greg Clayton57ee3062013-07-11 22:46:58 +00001508 clang::ValueDecl *value_decl = dyn_cast<clang::ValueDecl>(named_decl);
1509 if (value_decl == NULL)
Sean Callananea22d422010-07-16 00:09:46 +00001510 return false;
Greg Clayton57ee3062013-07-11 22:46:58 +00001511
1512 lldb_private::ClangASTType clang_type(&value_decl->getASTContext(), value_decl->getType());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001513
Sean Callanan77eaf442011-07-08 00:39:14 +00001514 const Type *value_type = NULL;
Greg Clayton57ee3062013-07-11 22:46:58 +00001515
Sean Callanane1175b72011-01-13 21:23:32 +00001516 if (name[0] == '$')
Sean Callanan92adcac2011-01-13 08:53:35 +00001517 {
1518 // The $__lldb_expr_result name indicates the the return value has allocated as
1519 // a static variable. Per the comment at ASTResultSynthesizer::SynthesizeBodyResult,
1520 // accesses to this static variable need to be redirected to the result of dereferencing
1521 // a pointer that is passed in as one of the arguments.
1522 //
1523 // Consequently, when reporting the size of the type, we report a pointer type pointing
1524 // to the type of $__lldb_expr_result, not the type itself.
Sean Callanane1175b72011-01-13 21:23:32 +00001525 //
1526 // We also do this for any user-declared persistent variables.
Greg Clayton57ee3062013-07-11 22:46:58 +00001527 clang_type = clang_type.GetPointerType();
Sean Callanan92adcac2011-01-13 08:53:35 +00001528 value_type = PointerType::get(global_variable->getType(), 0);
1529 }
1530 else
1531 {
Sean Callanan92adcac2011-01-13 08:53:35 +00001532 value_type = global_variable->getType();
1533 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001534
Enrico Granata1cd5e922015-01-28 00:07:51 +00001535 const uint64_t value_size = clang_type.GetByteSize(nullptr);
Zachary Turnera746e8e2014-07-02 17:24:07 +00001536 lldb::offset_t value_alignment = (clang_type.GetTypeBitAlign() + 7ull) / 8ull;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001537
Sean Callanan038df5032010-09-30 21:18:25 +00001538 if (log)
Greg Clayton57ee3062013-07-11 22:46:58 +00001539 {
Zachary Turnera746e8e2014-07-02 17:24:07 +00001540 log->Printf("Type of \"%s\" is [clang \"%s\", llvm \"%s\"] [size %" PRIu64 ", align %" PRIu64 "]",
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001541 name.c_str(),
Pavel Labathc33ae022015-06-08 22:27:10 +00001542 lldb_private::ClangASTContext::GetQualType(clang_type).getAsString().c_str(),
Greg Clayton57ee3062013-07-11 22:46:58 +00001543 PrintType(value_type).c_str(),
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001544 value_size,
Sean Callanan038df5032010-09-30 21:18:25 +00001545 value_alignment);
Greg Clayton57ee3062013-07-11 22:46:58 +00001546 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001547
1548
Sean Callanan64dfc9a2010-08-23 23:09:38 +00001549 if (named_decl && !m_decl_map->AddValueToStruct(named_decl,
Greg Clayton7b462cc2010-10-15 22:48:33 +00001550 lldb_private::ConstString (name.c_str()),
1551 llvm_value_ptr,
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001552 value_size,
Sean Callanan4edba2d2010-07-27 02:07:53 +00001553 value_alignment))
Sean Callananaf8e96c2011-08-01 17:41:38 +00001554 {
1555 if (!global_variable->hasExternalLinkage())
1556 return true;
Sean Callanan0ff3bf92013-04-11 17:57:16 +00001557 else if (HandleSymbol (global_variable))
1558 return true;
Sean Callananaf8e96c2011-08-01 17:41:38 +00001559 else
1560 return false;
1561 }
Sean Callanan549c9f72010-07-13 21:41:46 +00001562 }
Sean Callanan4a5fcbb2010-12-03 03:02:31 +00001563 else if (dyn_cast<llvm::Function>(llvm_value_ptr))
Sean Callanand7a1ca22010-12-02 19:47:57 +00001564 {
1565 if (log)
1566 log->Printf("Function pointers aren't handled right now");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001567
Sean Callanand7a1ca22010-12-02 19:47:57 +00001568 return false;
1569 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001570
Sean Callanan549c9f72010-07-13 21:41:46 +00001571 return true;
1572}
1573
Sean Callanan3989fb92011-01-27 01:07:04 +00001574// This function does not report errors; its callers are responsible.
Sean Callanan549c9f72010-07-13 21:41:46 +00001575bool
Sean Callanan79763a42011-05-23 21:40:23 +00001576IRForTarget::HandleSymbol (Value *symbol)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001577{
Greg Clayton5160ce52013-03-27 23:08:40 +00001578 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001579
Sean Callananc3a16002011-01-17 23:42:46 +00001580 lldb_private::ConstString name(symbol->getName().str().c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001581
Sean Callanan947ccc72011-12-01 02:04:16 +00001582 lldb::addr_t symbol_addr = m_decl_map->GetSymbolAddress (name, lldb::eSymbolTypeAny);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001583
Greg Clayton084db102011-06-23 04:25:29 +00001584 if (symbol_addr == LLDB_INVALID_ADDRESS)
Sean Callananc3a16002011-01-17 23:42:46 +00001585 {
1586 if (log)
1587 log->Printf ("Symbol \"%s\" had no address", name.GetCString());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001588
Sean Callananc3a16002011-01-17 23:42:46 +00001589 return false;
1590 }
1591
1592 if (log)
Daniel Malead01b2952012-11-29 21:49:15 +00001593 log->Printf("Found \"%s\" at 0x%" PRIx64, name.GetCString(), symbol_addr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001594
Sean Callanancc427fa2011-07-30 02:42:06 +00001595 Type *symbol_type = symbol->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001596
Sean Callanan439dcae2013-12-20 19:55:02 +00001597 Constant *symbol_addr_int = ConstantInt::get(m_intptr_ty, symbol_addr, false);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001598
Sean Callananc3a16002011-01-17 23:42:46 +00001599 Value *symbol_addr_ptr = ConstantExpr::getIntToPtr(symbol_addr_int, symbol_type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001600
Sean Callananc3a16002011-01-17 23:42:46 +00001601 if (log)
1602 log->Printf("Replacing %s with %s", PrintValue(symbol).c_str(), PrintValue(symbol_addr_ptr).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001603
Sean Callananc3a16002011-01-17 23:42:46 +00001604 symbol->replaceAllUsesWith(symbol_addr_ptr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001605
Sean Callananc3a16002011-01-17 23:42:46 +00001606 return true;
1607}
1608
1609bool
Sean Callanan79763a42011-05-23 21:40:23 +00001610IRForTarget::MaybeHandleCallArguments (CallInst *Old)
Sean Callanan85a0a832010-10-05 22:26:43 +00001611{
Greg Clayton5160ce52013-03-27 23:08:40 +00001612 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001613
Sean Callanand7a1ca22010-12-02 19:47:57 +00001614 if (log)
1615 log->Printf("MaybeHandleCallArguments(%s)", PrintValue(Old).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001616
Sean Callananafe16a72010-11-17 23:00:36 +00001617 for (unsigned op_index = 0, num_ops = Old->getNumArgOperands();
Sean Callanan85a0a832010-10-05 22:26:43 +00001618 op_index < num_ops;
1619 ++op_index)
Sean Callanan79763a42011-05-23 21:40:23 +00001620 if (!MaybeHandleVariable(Old->getArgOperand(op_index))) // conservatively believe that this is a store
Sean Callanan3989fb92011-01-27 01:07:04 +00001621 {
1622 if (m_error_stream)
1623 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't rewrite one of the arguments of a function call.\n");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001624
Sean Callanan85a0a832010-10-05 22:26:43 +00001625 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00001626 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001627
Sean Callanan85a0a832010-10-05 22:26:43 +00001628 return true;
1629}
1630
1631bool
Sean Callananfc89c142011-11-01 23:38:03 +00001632IRForTarget::HandleObjCClass(Value *classlist_reference)
1633{
Greg Clayton5160ce52013-03-27 23:08:40 +00001634 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callananfc89c142011-11-01 23:38:03 +00001635
1636 GlobalVariable *global_variable = dyn_cast<GlobalVariable>(classlist_reference);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001637
Sean Callananfc89c142011-11-01 23:38:03 +00001638 if (!global_variable)
1639 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001640
Sean Callananfc89c142011-11-01 23:38:03 +00001641 Constant *initializer = global_variable->getInitializer();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001642
Sean Callananfc89c142011-11-01 23:38:03 +00001643 if (!initializer)
1644 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001645
Sean Callananfc89c142011-11-01 23:38:03 +00001646 if (!initializer->hasName())
1647 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001648
Sean Callananfc89c142011-11-01 23:38:03 +00001649 StringRef name(initializer->getName());
1650 lldb_private::ConstString name_cstr(name.str().c_str());
Greg Clayton1075aca2011-12-03 20:02:42 +00001651 lldb::addr_t class_ptr = m_decl_map->GetSymbolAddress(name_cstr, lldb::eSymbolTypeObjCClass);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001652
Sean Callananfc89c142011-11-01 23:38:03 +00001653 if (log)
1654 log->Printf("Found reference to Objective-C class %s (0x%llx)", name_cstr.AsCString(), (unsigned long long)class_ptr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001655
Sean Callananfc89c142011-11-01 23:38:03 +00001656 if (class_ptr == LLDB_INVALID_ADDRESS)
1657 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001658
Ed Mastea8553092014-03-10 17:24:16 +00001659 if (global_variable->use_empty())
Sean Callananfc89c142011-11-01 23:38:03 +00001660 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001661
Sean Callanan719a4d52013-03-23 01:01:16 +00001662 SmallVector<LoadInst *, 2> load_instructions;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001663
Ed Mastea8553092014-03-10 17:24:16 +00001664 for (llvm::User *u : global_variable->users())
Sean Callananfc89c142011-11-01 23:38:03 +00001665 {
Ed Mastea8553092014-03-10 17:24:16 +00001666 if (LoadInst *load_instruction = dyn_cast<LoadInst>(u))
Sean Callanan719a4d52013-03-23 01:01:16 +00001667 load_instructions.push_back(load_instruction);
Sean Callananfc89c142011-11-01 23:38:03 +00001668 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001669
Sean Callanan719a4d52013-03-23 01:01:16 +00001670 if (load_instructions.empty())
Sean Callananfc89c142011-11-01 23:38:03 +00001671 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001672
Sean Callanan439dcae2013-12-20 19:55:02 +00001673 Constant *class_addr = ConstantInt::get(m_intptr_ty, (uint64_t)class_ptr);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001674
Sean Callanan719a4d52013-03-23 01:01:16 +00001675 for (LoadInst *load_instruction : load_instructions)
1676 {
1677 Constant *class_bitcast = ConstantExpr::getIntToPtr(class_addr, load_instruction->getType());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001678
Sean Callanan719a4d52013-03-23 01:01:16 +00001679 load_instruction->replaceAllUsesWith(class_bitcast);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001680
Sean Callanan719a4d52013-03-23 01:01:16 +00001681 load_instruction->eraseFromParent();
1682 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001683
Sean Callananfc89c142011-11-01 23:38:03 +00001684 return true;
1685}
1686
1687bool
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001688IRForTarget::RemoveCXAAtExit (BasicBlock &basic_block)
1689{
1690 BasicBlock::iterator ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001691
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001692 std::vector<CallInst *> calls_to_remove;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001693
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001694 for (ii = basic_block.begin();
1695 ii != basic_block.end();
1696 ++ii)
1697 {
1698 Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001699
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001700 CallInst *call = dyn_cast<CallInst>(&inst);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001701
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001702 // MaybeHandleCallArguments handles error reporting; we are silent here
1703 if (!call)
1704 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001705
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001706 bool remove = false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001707
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001708 llvm::Function *func = call->getCalledFunction();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001709
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001710 if (func && func->getName() == "__cxa_atexit")
1711 remove = true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001712
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001713 llvm::Value *val = call->getCalledValue();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001714
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001715 if (val && val->getName() == "__cxa_atexit")
1716 remove = true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001717
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001718 if (remove)
1719 calls_to_remove.push_back(call);
1720 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001721
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001722 for (std::vector<CallInst *>::iterator ci = calls_to_remove.begin(), ce = calls_to_remove.end();
1723 ci != ce;
1724 ++ci)
1725 {
1726 (*ci)->eraseFromParent();
1727 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001728
Sean Callanan6e6d4a62012-07-21 02:02:15 +00001729 return true;
1730}
1731
1732bool
Sean Callanan79763a42011-05-23 21:40:23 +00001733IRForTarget::ResolveCalls(BasicBlock &basic_block)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001734{
Sean Callanan2ab712f22010-07-03 01:35:46 +00001735 /////////////////////////////////////////////////////////////////////////
1736 // Prepare the current basic block for execution in the remote process
1737 //
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001738
Sean Callanan7ea35012010-07-27 21:39:39 +00001739 BasicBlock::iterator ii;
Sean Callanan549c9f72010-07-13 21:41:46 +00001740
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001741 for (ii = basic_block.begin();
1742 ii != basic_block.end();
Sean Callanan549c9f72010-07-13 21:41:46 +00001743 ++ii)
Sean Callanan2ab712f22010-07-03 01:35:46 +00001744 {
Sean Callanan549c9f72010-07-13 21:41:46 +00001745 Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001746
Sean Callanana4e55172010-11-08 00:31:32 +00001747 CallInst *call = dyn_cast<CallInst>(&inst);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001748
Sean Callanan3989fb92011-01-27 01:07:04 +00001749 // MaybeHandleCallArguments handles error reporting; we are silent here
Sean Callanan79763a42011-05-23 21:40:23 +00001750 if (call && !MaybeHandleCallArguments(call))
Sean Callanand7a1ca22010-12-02 19:47:57 +00001751 return false;
Sean Callanan2ab712f22010-07-03 01:35:46 +00001752 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001753
Sean Callanan2ab712f22010-07-03 01:35:46 +00001754 return true;
1755}
1756
Sean Callanana4e55172010-11-08 00:31:32 +00001757bool
Sean Callanan79763a42011-05-23 21:40:23 +00001758IRForTarget::ResolveExternals (Function &llvm_function)
Sean Callanana4e55172010-11-08 00:31:32 +00001759{
Greg Clayton5160ce52013-03-27 23:08:40 +00001760 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001761
Sean Callanan339f6152014-03-11 19:19:16 +00001762 for (GlobalVariable &global_var : m_module->globals())
Sean Callanana4e55172010-11-08 00:31:32 +00001763 {
Sean Callanan339f6152014-03-11 19:19:16 +00001764 std::string global_name = global_var.getName().str();
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001765
Greg Clayton1b95a6f2010-11-19 01:05:25 +00001766 if (log)
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001767 log->Printf("Examining %s, DeclForGlobalValue returns %p",
Sean Callanan694e2442011-12-22 21:24:49 +00001768 global_name.c_str(),
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001769 static_cast<void*>(DeclForGlobal(&global_var)));
1770
Sean Callananfc89c142011-11-01 23:38:03 +00001771 if (global_name.find("OBJC_IVAR") == 0)
Sean Callananc3a16002011-01-17 23:42:46 +00001772 {
Sean Callanan339f6152014-03-11 19:19:16 +00001773 if (!HandleSymbol(&global_var))
Sean Callanan3989fb92011-01-27 01:07:04 +00001774 {
1775 if (m_error_stream)
Sean Callanan694e2442011-12-22 21:24:49 +00001776 m_error_stream->Printf("Error [IRForTarget]: Couldn't find Objective-C indirect ivar symbol %s\n", global_name.c_str());
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001777
Sean Callananc3a16002011-01-17 23:42:46 +00001778 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00001779 }
Sean Callananc3a16002011-01-17 23:42:46 +00001780 }
Sean Callananfc89c142011-11-01 23:38:03 +00001781 else if (global_name.find("OBJC_CLASSLIST_REFERENCES_$") != global_name.npos)
1782 {
Sean Callanan339f6152014-03-11 19:19:16 +00001783 if (!HandleObjCClass(&global_var))
Sean Callananfc89c142011-11-01 23:38:03 +00001784 {
1785 if (m_error_stream)
1786 m_error_stream->Printf("Error [IRForTarget]: Couldn't resolve the class for an Objective-C static method call\n");
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001787
Sean Callananfc89c142011-11-01 23:38:03 +00001788 return false;
1789 }
1790 }
Sean Callanan2ad66912013-04-24 21:25:20 +00001791 else if (global_name.find("OBJC_CLASSLIST_SUP_REFS_$") != global_name.npos)
1792 {
Sean Callanan339f6152014-03-11 19:19:16 +00001793 if (!HandleObjCClass(&global_var))
Sean Callanan2ad66912013-04-24 21:25:20 +00001794 {
1795 if (m_error_stream)
1796 m_error_stream->Printf("Error [IRForTarget]: Couldn't resolve the class for an Objective-C static method call\n");
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001797
Sean Callanan2ad66912013-04-24 21:25:20 +00001798 return false;
1799 }
1800 }
Sean Callanan339f6152014-03-11 19:19:16 +00001801 else if (DeclForGlobal(&global_var))
Sean Callananc3a16002011-01-17 23:42:46 +00001802 {
Sean Callanan339f6152014-03-11 19:19:16 +00001803 if (!MaybeHandleVariable (&global_var))
Sean Callanan3989fb92011-01-27 01:07:04 +00001804 {
1805 if (m_error_stream)
Sean Callanan694e2442011-12-22 21:24:49 +00001806 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't rewrite external variable %s\n", global_name.c_str());
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001807
Sean Callananc3a16002011-01-17 23:42:46 +00001808 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00001809 }
Sean Callananc3a16002011-01-17 23:42:46 +00001810 }
Sean Callanana4e55172010-11-08 00:31:32 +00001811 }
Saleem Abdulrasool324a1032014-04-04 04:06:10 +00001812
Sean Callanana4e55172010-11-08 00:31:32 +00001813 return true;
1814}
1815
Sean Callanan79763a42011-05-23 21:40:23 +00001816bool
1817IRForTarget::ReplaceStrings ()
1818{
Greg Clayton5160ce52013-03-27 23:08:40 +00001819 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001820
Sean Callanan79763a42011-05-23 21:40:23 +00001821 typedef std::map <GlobalVariable *, size_t> OffsetsTy;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001822
Sean Callanan79763a42011-05-23 21:40:23 +00001823 OffsetsTy offsets;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001824
Sean Callanan339f6152014-03-11 19:19:16 +00001825 for (GlobalVariable &gv : m_module->globals())
Sean Callanan79763a42011-05-23 21:40:23 +00001826 {
Sean Callanan339f6152014-03-11 19:19:16 +00001827 if (!gv.hasInitializer())
Sean Callanan79763a42011-05-23 21:40:23 +00001828 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001829
Sean Callanan339f6152014-03-11 19:19:16 +00001830 Constant *gc = gv.getInitializer();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001831
Sean Callanan5207a342011-08-10 21:05:52 +00001832 std::string str;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001833
Sean Callanan5207a342011-08-10 21:05:52 +00001834 if (gc->isNullValue())
1835 {
1836 Type *gc_type = gc->getType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001837
Sean Callanan5207a342011-08-10 21:05:52 +00001838 ArrayType *gc_array_type = dyn_cast<ArrayType>(gc_type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001839
Sean Callanan5207a342011-08-10 21:05:52 +00001840 if (!gc_array_type)
1841 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001842
Sean Callanan5207a342011-08-10 21:05:52 +00001843 Type *gc_element_type = gc_array_type->getElementType();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001844
Sean Callanan5207a342011-08-10 21:05:52 +00001845 IntegerType *gc_integer_type = dyn_cast<IntegerType>(gc_element_type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001846
Sean Callanan5207a342011-08-10 21:05:52 +00001847 if (gc_integer_type->getBitWidth() != 8)
1848 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001849
Sean Callanan5207a342011-08-10 21:05:52 +00001850 str = "";
1851 }
1852 else
1853 {
Sean Callanand2b465f2012-02-09 03:22:41 +00001854 ConstantDataArray *gc_array = dyn_cast<ConstantDataArray>(gc);
Sean Callanan5207a342011-08-10 21:05:52 +00001855
1856 if (!gc_array)
1857 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001858
Sean Callanan5207a342011-08-10 21:05:52 +00001859 if (!gc_array->isCString())
1860 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001861
Sean Callanan5207a342011-08-10 21:05:52 +00001862 if (log)
1863 log->Printf("Found a GlobalVariable with string initializer %s", PrintValue(gc).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001864
Sean Callanan5207a342011-08-10 21:05:52 +00001865 str = gc_array->getAsString();
1866 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001867
Sean Callanan339f6152014-03-11 19:19:16 +00001868 offsets[&gv] = m_data_allocator.GetStream().GetSize();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001869
Sean Callanan8dfb68e2013-03-19 00:10:07 +00001870 m_data_allocator.GetStream().Write(str.c_str(), str.length() + 1);
Sean Callanan79763a42011-05-23 21:40:23 +00001871 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001872
Sean Callanancc427fa2011-07-30 02:42:06 +00001873 Type *char_ptr_ty = Type::getInt8PtrTy(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001874
Sean Callanan79763a42011-05-23 21:40:23 +00001875 for (OffsetsTy::iterator oi = offsets.begin(), oe = offsets.end();
1876 oi != oe;
1877 ++oi)
1878 {
1879 GlobalVariable *gv = oi->first;
1880 size_t offset = oi->second;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001881
Sean Callanan79763a42011-05-23 21:40:23 +00001882 Constant *new_initializer = BuildRelocation(char_ptr_ty, offset);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001883
Sean Callanan79763a42011-05-23 21:40:23 +00001884 if (log)
1885 log->Printf("Replacing GV %s with %s", PrintValue(gv).c_str(), PrintValue(new_initializer).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001886
Ed Mastea8553092014-03-10 17:24:16 +00001887 for (llvm::User *u : gv->users())
Sean Callanan79763a42011-05-23 21:40:23 +00001888 {
1889 if (log)
Ed Mastea8553092014-03-10 17:24:16 +00001890 log->Printf("Found use %s", PrintValue(u).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001891
Ed Mastea8553092014-03-10 17:24:16 +00001892 ConstantExpr *const_expr = dyn_cast<ConstantExpr>(u);
1893 StoreInst *store_inst = dyn_cast<StoreInst>(u);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001894
Sean Callanan79763a42011-05-23 21:40:23 +00001895 if (const_expr)
1896 {
1897 if (const_expr->getOpcode() != Instruction::GetElementPtr)
1898 {
1899 if (log)
1900 log->Printf("Use (%s) of string variable is not a GetElementPtr constant", PrintValue(const_expr).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001901
Sean Callanan79763a42011-05-23 21:40:23 +00001902 return false;
1903 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001904
Sean Callanan5207a342011-08-10 21:05:52 +00001905 Constant *bit_cast = ConstantExpr::getBitCast(new_initializer, const_expr->getOperand(0)->getType());
1906 Constant *new_gep = const_expr->getWithOperandReplaced(0, bit_cast);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001907
Sean Callanan5207a342011-08-10 21:05:52 +00001908 const_expr->replaceAllUsesWith(new_gep);
Sean Callanan79763a42011-05-23 21:40:23 +00001909 }
1910 else if (store_inst)
1911 {
1912 Constant *bit_cast = ConstantExpr::getBitCast(new_initializer, store_inst->getValueOperand()->getType());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001913
Sean Callanan79763a42011-05-23 21:40:23 +00001914 store_inst->setOperand(0, bit_cast);
1915 }
1916 else
1917 {
1918 if (log)
1919 log->Printf("Use (%s) of string variable is neither a constant nor a store", PrintValue(const_expr).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001920
Sean Callanan79763a42011-05-23 21:40:23 +00001921 return false;
1922 }
1923 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001924
Sean Callanan79763a42011-05-23 21:40:23 +00001925 gv->eraseFromParent();
1926 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001927
Sean Callanan79763a42011-05-23 21:40:23 +00001928 return true;
1929}
1930
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001931bool
Sean Callanan79763a42011-05-23 21:40:23 +00001932IRForTarget::ReplaceStaticLiterals (llvm::BasicBlock &basic_block)
1933{
Greg Clayton5160ce52013-03-27 23:08:40 +00001934 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001935
Sean Callanan79763a42011-05-23 21:40:23 +00001936 typedef SmallVector <Value*, 2> ConstantList;
1937 typedef SmallVector <llvm::Instruction*, 2> UserList;
1938 typedef ConstantList::iterator ConstantIterator;
1939 typedef UserList::iterator UserIterator;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001940
Sean Callanan79763a42011-05-23 21:40:23 +00001941 ConstantList static_constants;
1942 UserList static_users;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001943
Sean Callanan79763a42011-05-23 21:40:23 +00001944 for (BasicBlock::iterator ii = basic_block.begin(), ie = basic_block.end();
1945 ii != ie;
1946 ++ii)
1947 {
1948 llvm::Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001949
Sean Callanan339f6152014-03-11 19:19:16 +00001950 for (Value *operand_val : inst.operand_values())
Sean Callanan79763a42011-05-23 21:40:23 +00001951 {
Sean Callanan79763a42011-05-23 21:40:23 +00001952 ConstantFP *operand_constant_fp = dyn_cast<ConstantFP>(operand_val);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001953
Sean Callanan822944c2012-04-26 20:51:20 +00001954 if (operand_constant_fp/* && operand_constant_fp->getType()->isX86_FP80Ty()*/)
Sean Callanan79763a42011-05-23 21:40:23 +00001955 {
1956 static_constants.push_back(operand_val);
1957 static_users.push_back(ii);
1958 }
1959 }
1960 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001961
Sean Callanan79763a42011-05-23 21:40:23 +00001962 ConstantIterator constant_iter;
1963 UserIterator user_iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001964
Sean Callanan79763a42011-05-23 21:40:23 +00001965 for (constant_iter = static_constants.begin(), user_iter = static_users.begin();
1966 constant_iter != static_constants.end();
1967 ++constant_iter, ++user_iter)
1968 {
1969 Value *operand_val = *constant_iter;
1970 llvm::Instruction *inst = *user_iter;
1971
1972 ConstantFP *operand_constant_fp = dyn_cast<ConstantFP>(operand_val);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001973
Sean Callanan79763a42011-05-23 21:40:23 +00001974 if (operand_constant_fp)
1975 {
Sean Callanan1582ee62013-04-18 22:06:33 +00001976 Type *operand_type = operand_constant_fp->getType();
1977
Sean Callanan79763a42011-05-23 21:40:23 +00001978 APFloat operand_apfloat = operand_constant_fp->getValueAPF();
1979 APInt operand_apint = operand_apfloat.bitcastToAPInt();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001980
Sean Callanan79763a42011-05-23 21:40:23 +00001981 const uint8_t* operand_raw_data = (const uint8_t*)operand_apint.getRawData();
1982 size_t operand_data_size = operand_apint.getBitWidth() / 8;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001983
Sean Callanan79763a42011-05-23 21:40:23 +00001984 if (log)
1985 {
1986 std::string s;
1987 raw_string_ostream ss(s);
1988 for (size_t index = 0;
1989 index < operand_data_size;
1990 ++index)
1991 {
1992 ss << (uint32_t)operand_raw_data[index];
1993 ss << " ";
1994 }
1995 ss.flush();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001996
Greg Clayton6fea17e2014-03-03 19:15:20 +00001997 log->Printf("Found ConstantFP with size %" PRIu64 " and raw data %s", (uint64_t)operand_data_size, s.c_str());
Sean Callanan79763a42011-05-23 21:40:23 +00001998 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00001999
Sean Callanan79763a42011-05-23 21:40:23 +00002000 lldb_private::DataBufferHeap data(operand_data_size, 0);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002001
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002002 if (lldb::endian::InlHostByteOrder() != m_data_allocator.GetStream().GetByteOrder())
Sean Callanan79763a42011-05-23 21:40:23 +00002003 {
2004 uint8_t *data_bytes = data.GetBytes();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002005
Sean Callanan79763a42011-05-23 21:40:23 +00002006 for (size_t index = 0;
2007 index < operand_data_size;
2008 ++index)
2009 {
2010 data_bytes[index] = operand_raw_data[operand_data_size - (1 + index)];
2011 }
2012 }
2013 else
2014 {
2015 memcpy(data.GetBytes(), operand_raw_data, operand_data_size);
2016 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002017
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002018 uint64_t offset = m_data_allocator.GetStream().GetSize();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002019
Sean Callanane3333d62012-06-08 22:20:41 +00002020 size_t align = m_target_data->getPrefTypeAlignment(operand_type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002021
Sean Callanane3333d62012-06-08 22:20:41 +00002022 const size_t mask = (align - 1);
2023 uint64_t aligned_offset = (offset + mask) & ~mask;
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002024 m_data_allocator.GetStream().PutNHex8(aligned_offset - offset, 0);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002025
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002026 m_data_allocator.GetStream().Write(data.GetBytes(), operand_data_size);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002027
Sean Callanancc427fa2011-07-30 02:42:06 +00002028 llvm::Type *fp_ptr_ty = operand_constant_fp->getType()->getPointerTo();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002029
Sean Callanan1582ee62013-04-18 22:06:33 +00002030 Constant *new_pointer = BuildRelocation(fp_ptr_ty, aligned_offset);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002031
Sean Callanan79763a42011-05-23 21:40:23 +00002032 llvm::LoadInst *fp_load = new llvm::LoadInst(new_pointer, "fp_load", inst);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002033
Sean Callanan79763a42011-05-23 21:40:23 +00002034 operand_constant_fp->replaceAllUsesWith(fp_load);
2035 }
2036 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002037
Sean Callanan79763a42011-05-23 21:40:23 +00002038 return true;
2039}
2040
Sean Callanan7ea35012010-07-27 21:39:39 +00002041static bool isGuardVariableRef(Value *V)
Sean Callananddb46ef2010-07-24 01:37:44 +00002042{
Sean Callanan77eaf442011-07-08 00:39:14 +00002043 Constant *Old = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002044
Sean Callananafe16a72010-11-17 23:00:36 +00002045 if (!(Old = dyn_cast<Constant>(V)))
Sean Callananddb46ef2010-07-24 01:37:44 +00002046 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002047
Sean Callanan77eaf442011-07-08 00:39:14 +00002048 ConstantExpr *CE = NULL;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002049
Sean Callanane2ef6e32010-09-23 03:01:22 +00002050 if ((CE = dyn_cast<ConstantExpr>(V)))
2051 {
2052 if (CE->getOpcode() != Instruction::BitCast)
2053 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002054
Sean Callananafe16a72010-11-17 23:00:36 +00002055 Old = CE->getOperand(0);
Sean Callanane2ef6e32010-09-23 03:01:22 +00002056 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002057
Sean Callananafe16a72010-11-17 23:00:36 +00002058 GlobalVariable *GV = dyn_cast<GlobalVariable>(Old);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002059
Zachary Turnerf16ae602015-01-09 21:12:22 +00002060 if (!GV || !GV->hasName() ||
2061 (!GV->getName().startswith("_ZGV") && // Itanium ABI guard variable
2062 !GV->getName().endswith("@4IA"))) // Microsoft ABI guard variable
2063 {
Sean Callananddb46ef2010-07-24 01:37:44 +00002064 return false;
Zachary Turnerf16ae602015-01-09 21:12:22 +00002065 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002066
Sean Callananddb46ef2010-07-24 01:37:44 +00002067 return true;
2068}
2069
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002070void
Sean Callanan79763a42011-05-23 21:40:23 +00002071IRForTarget::TurnGuardLoadIntoZero(llvm::Instruction* guard_load)
Sean Callananddb46ef2010-07-24 01:37:44 +00002072{
Zachary Turnerf16ae602015-01-09 21:12:22 +00002073 Constant *zero(Constant::getNullValue(guard_load->getType()));
2074 guard_load->replaceAllUsesWith(zero);
Sean Callananddb46ef2010-07-24 01:37:44 +00002075 guard_load->eraseFromParent();
2076}
2077
2078static void ExciseGuardStore(Instruction* guard_store)
2079{
2080 guard_store->eraseFromParent();
2081}
2082
2083bool
Sean Callanan79763a42011-05-23 21:40:23 +00002084IRForTarget::RemoveGuards(BasicBlock &basic_block)
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002085{
Sean Callananddb46ef2010-07-24 01:37:44 +00002086 ///////////////////////////////////////////////////////
2087 // Eliminate any reference to guard variables found.
2088 //
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002089
Sean Callanan7ea35012010-07-27 21:39:39 +00002090 BasicBlock::iterator ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002091
Sean Callanan7ea35012010-07-27 21:39:39 +00002092 typedef SmallVector <Instruction*, 2> InstrList;
Sean Callananddb46ef2010-07-24 01:37:44 +00002093 typedef InstrList::iterator InstrIterator;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002094
Sean Callananddb46ef2010-07-24 01:37:44 +00002095 InstrList guard_loads;
2096 InstrList guard_stores;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002097
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002098 for (ii = basic_block.begin();
2099 ii != basic_block.end();
Sean Callananddb46ef2010-07-24 01:37:44 +00002100 ++ii)
2101 {
2102 Instruction &inst = *ii;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002103
Sean Callananddb46ef2010-07-24 01:37:44 +00002104 if (LoadInst *load = dyn_cast<LoadInst>(&inst))
2105 if (isGuardVariableRef(load->getPointerOperand()))
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002106 guard_loads.push_back(&inst);
2107
2108 if (StoreInst *store = dyn_cast<StoreInst>(&inst))
Sean Callananddb46ef2010-07-24 01:37:44 +00002109 if (isGuardVariableRef(store->getPointerOperand()))
2110 guard_stores.push_back(&inst);
2111 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002112
Sean Callananddb46ef2010-07-24 01:37:44 +00002113 InstrIterator iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002114
Sean Callananddb46ef2010-07-24 01:37:44 +00002115 for (iter = guard_loads.begin();
2116 iter != guard_loads.end();
2117 ++iter)
Sean Callanan79763a42011-05-23 21:40:23 +00002118 TurnGuardLoadIntoZero(*iter);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002119
Sean Callananddb46ef2010-07-24 01:37:44 +00002120 for (iter = guard_stores.begin();
2121 iter != guard_stores.end();
2122 ++iter)
2123 ExciseGuardStore(*iter);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002124
Sean Callananddb46ef2010-07-24 01:37:44 +00002125 return true;
2126}
2127
Sean Callanan3989fb92011-01-27 01:07:04 +00002128// This function does not report errors; its callers are responsible.
Sean Callananafe16a72010-11-17 23:00:36 +00002129bool
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002130IRForTarget::UnfoldConstant(Constant *old_constant,
2131 FunctionValueCache &value_maker,
2132 FunctionValueCache &entry_instruction_finder)
Sean Callanan7618f4e2010-07-14 23:40:29 +00002133{
Greg Clayton5160ce52013-03-27 23:08:40 +00002134 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanan7618f4e2010-07-14 23:40:29 +00002135
Sean Callanan2235f322010-08-11 03:57:18 +00002136 SmallVector<User*, 16> users;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002137
Sean Callanan2235f322010-08-11 03:57:18 +00002138 // We do this because the use list might change, invalidating our iterator.
2139 // Much better to keep a work list ourselves.
Ed Maste80e8cc62014-03-10 14:23:10 +00002140 for (llvm::User *u : old_constant->users())
2141 users.push_back(u);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002142
Johnny Chen44805302011-07-19 19:48:13 +00002143 for (size_t i = 0;
Sean Callanan2235f322010-08-11 03:57:18 +00002144 i < users.size();
2145 ++i)
2146 {
2147 User *user = users[i];
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002148
Sean Callanan7618f4e2010-07-14 23:40:29 +00002149 if (Constant *constant = dyn_cast<Constant>(user))
2150 {
2151 // synthesize a new non-constant equivalent of the constant
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002152
Sean Callanan7618f4e2010-07-14 23:40:29 +00002153 if (ConstantExpr *constant_expr = dyn_cast<ConstantExpr>(constant))
2154 {
2155 switch (constant_expr->getOpcode())
2156 {
2157 default:
2158 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +00002159 log->Printf("Unhandled constant expression type: \"%s\"", PrintValue(constant_expr).c_str());
Sean Callanan7618f4e2010-07-14 23:40:29 +00002160 return false;
2161 case Instruction::BitCast:
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002162 {
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002163 FunctionValueCache bit_cast_maker ([&value_maker, &entry_instruction_finder, old_constant, constant_expr] (llvm::Function *function)->llvm::Value* {
2164 // UnaryExpr
2165 // OperandList[0] is value
2166
2167 if (constant_expr->getOperand(0) != old_constant)
2168 return constant_expr;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002169
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002170 return new BitCastInst(value_maker.GetValue(function),
2171 constant_expr->getType(),
2172 "",
2173 llvm::cast<Instruction>(entry_instruction_finder.GetValue(function)));
2174 });
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002175
Sean Callanan0e016fe2013-07-15 23:31:47 +00002176 if (!UnfoldConstant(constant_expr, bit_cast_maker, entry_instruction_finder))
2177 return false;
Sean Callanan7618f4e2010-07-14 23:40:29 +00002178 }
2179 break;
2180 case Instruction::GetElementPtr:
2181 {
2182 // GetElementPtrConstantExpr
2183 // OperandList[0] is base
2184 // OperandList[1]... are indices
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002185
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002186 FunctionValueCache get_element_pointer_maker ([&value_maker, &entry_instruction_finder, old_constant, constant_expr] (llvm::Function *function)->llvm::Value* {
2187 Value *ptr = constant_expr->getOperand(0);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002188
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002189 if (ptr == old_constant)
2190 ptr = value_maker.GetValue(function);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002191
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002192 std::vector<Value*> index_vector;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002193
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002194 unsigned operand_index;
2195 unsigned num_operands = constant_expr->getNumOperands();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002196
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002197 for (operand_index = 1;
2198 operand_index < num_operands;
2199 ++operand_index)
2200 {
2201 Value *operand = constant_expr->getOperand(operand_index);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002202
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002203 if (operand == old_constant)
2204 operand = value_maker.GetValue(function);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002205
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002206 index_vector.push_back(operand);
2207 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002208
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002209 ArrayRef <Value*> indices(index_vector);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002210
Vince Harron0fc6c672015-03-16 03:54:22 +00002211 return GetElementPtrInst::Create(nullptr, ptr, indices, "", llvm::cast<Instruction>(entry_instruction_finder.GetValue(function)));
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002212 });
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002213
Sean Callanan0e016fe2013-07-15 23:31:47 +00002214 if (!UnfoldConstant(constant_expr, get_element_pointer_maker, entry_instruction_finder))
2215 return false;
Sean Callanan7618f4e2010-07-14 23:40:29 +00002216 }
2217 break;
2218 }
2219 }
2220 else
2221 {
2222 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +00002223 log->Printf("Unhandled constant type: \"%s\"", PrintValue(constant).c_str());
Sean Callanan7618f4e2010-07-14 23:40:29 +00002224 return false;
2225 }
2226 }
2227 else
2228 {
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002229 if (Instruction *inst = llvm::dyn_cast<Instruction>(user))
2230 {
2231 inst->replaceUsesOfWith(old_constant, value_maker.GetValue(inst->getParent()->getParent()));
2232 }
2233 else
2234 {
2235 if (log)
2236 log->Printf("Unhandled non-constant type: \"%s\"", PrintValue(user).c_str());
2237 return false;
2238 }
Sean Callanan7618f4e2010-07-14 23:40:29 +00002239 }
2240 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002241
Sean Callanan0e016fe2013-07-15 23:31:47 +00002242 if (!isa<GlobalValue>(old_constant))
2243 {
2244 old_constant->destroyConstant();
2245 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002246
Sean Callanan7618f4e2010-07-14 23:40:29 +00002247 return true;
2248}
2249
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002250bool
Sean Callanan79763a42011-05-23 21:40:23 +00002251IRForTarget::ReplaceVariables (Function &llvm_function)
Sean Callanan549c9f72010-07-13 21:41:46 +00002252{
Sean Callanan9e6ed532010-09-13 21:34:21 +00002253 if (!m_resolve_vars)
2254 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002255
Greg Clayton5160ce52013-03-27 23:08:40 +00002256 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanan549c9f72010-07-13 21:41:46 +00002257
2258 m_decl_map->DoStructLayout();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002259
Sean Callanan549c9f72010-07-13 21:41:46 +00002260 if (log)
2261 log->Printf("Element arrangement:");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002262
Sean Callanan549c9f72010-07-13 21:41:46 +00002263 uint32_t num_elements;
2264 uint32_t element_index;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002265
Sean Callanan549c9f72010-07-13 21:41:46 +00002266 size_t size;
Zachary Turnera746e8e2014-07-02 17:24:07 +00002267 lldb::offset_t alignment;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002268
Sean Callanan549c9f72010-07-13 21:41:46 +00002269 if (!m_decl_map->GetStructInfo (num_elements, size, alignment))
2270 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002271
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002272 Function::arg_iterator iter(llvm_function.getArgumentList().begin());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002273
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002274 if (iter == llvm_function.getArgumentList().end())
Sean Callanan3989fb92011-01-27 01:07:04 +00002275 {
2276 if (m_error_stream)
2277 m_error_stream->Printf("Internal error [IRForTarget]: Wrapper takes no arguments (should take at least a struct pointer)");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002278
Sean Callanan549c9f72010-07-13 21:41:46 +00002279 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002280 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002281
Sean Callanan7ea35012010-07-27 21:39:39 +00002282 Argument *argument = iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002283
Sean Callananfc55f5d2010-09-21 00:44:12 +00002284 if (argument->getName().equals("this"))
2285 {
2286 ++iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002287
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002288 if (iter == llvm_function.getArgumentList().end())
Sean Callanan3989fb92011-01-27 01:07:04 +00002289 {
2290 if (m_error_stream)
2291 m_error_stream->Printf("Internal error [IRForTarget]: Wrapper takes only 'this' argument (should take a struct pointer too)");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002292
Sean Callananfc55f5d2010-09-21 00:44:12 +00002293 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002294 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002295
Sean Callananfc55f5d2010-09-21 00:44:12 +00002296 argument = iter;
2297 }
Sean Callanan17827832010-12-13 22:46:15 +00002298 else if (argument->getName().equals("self"))
2299 {
2300 ++iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002301
Sean Callanan17827832010-12-13 22:46:15 +00002302 if (iter == llvm_function.getArgumentList().end())
Sean Callanan3989fb92011-01-27 01:07:04 +00002303 {
2304 if (m_error_stream)
2305 m_error_stream->Printf("Internal error [IRForTarget]: Wrapper takes only 'self' argument (should take '_cmd' and a struct pointer too)");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002306
Sean Callanan17827832010-12-13 22:46:15 +00002307 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002308 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002309
Sean Callanan17827832010-12-13 22:46:15 +00002310 if (!iter->getName().equals("_cmd"))
Sean Callanan3989fb92011-01-27 01:07:04 +00002311 {
2312 if (m_error_stream)
2313 m_error_stream->Printf("Internal error [IRForTarget]: Wrapper takes '%s' after 'self' argument (should take '_cmd')", iter->getName().str().c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002314
Sean Callanan17827832010-12-13 22:46:15 +00002315 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002316 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002317
Sean Callanan17827832010-12-13 22:46:15 +00002318 ++iter;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002319
Sean Callanan17827832010-12-13 22:46:15 +00002320 if (iter == llvm_function.getArgumentList().end())
Sean Callanan3989fb92011-01-27 01:07:04 +00002321 {
2322 if (m_error_stream)
2323 m_error_stream->Printf("Internal error [IRForTarget]: Wrapper takes only 'self' and '_cmd' arguments (should take a struct pointer too)");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002324
Sean Callanan17827832010-12-13 22:46:15 +00002325 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002326 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002327
Sean Callanan17827832010-12-13 22:46:15 +00002328 argument = iter;
2329 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002330
Greg Clayton7b462cc2010-10-15 22:48:33 +00002331 if (!argument->getName().equals("$__lldb_arg"))
Sean Callanan3989fb92011-01-27 01:07:04 +00002332 {
2333 if (m_error_stream)
2334 m_error_stream->Printf("Internal error [IRForTarget]: Wrapper takes an argument named '%s' instead of the struct pointer", argument->getName().str().c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002335
Sean Callanan549c9f72010-07-13 21:41:46 +00002336 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002337 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002338
Sean Callanan549c9f72010-07-13 21:41:46 +00002339 if (log)
Greg Claytoncb7e3b32010-11-15 01:47:11 +00002340 log->Printf("Arg: \"%s\"", PrintValue(argument).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002341
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002342 BasicBlock &entry_block(llvm_function.getEntryBlock());
Sean Callananafe16a72010-11-17 23:00:36 +00002343 Instruction *FirstEntryInstruction(entry_block.getFirstNonPHIOrDbg());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002344
Sean Callananafe16a72010-11-17 23:00:36 +00002345 if (!FirstEntryInstruction)
Sean Callanan3989fb92011-01-27 01:07:04 +00002346 {
2347 if (m_error_stream)
2348 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't find the first instruction in the wrapper for use in rewriting");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002349
Sean Callanan549c9f72010-07-13 21:41:46 +00002350 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002351 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002352
Sean Callanan79763a42011-05-23 21:40:23 +00002353 LLVMContext &context(m_module->getContext());
Sean Callanancc427fa2011-07-30 02:42:06 +00002354 IntegerType *offset_type(Type::getInt32Ty(context));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002355
Sean Callanan549c9f72010-07-13 21:41:46 +00002356 if (!offset_type)
Sean Callanan3989fb92011-01-27 01:07:04 +00002357 {
2358 if (m_error_stream)
2359 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't produce an offset type");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002360
Sean Callanan549c9f72010-07-13 21:41:46 +00002361 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002362 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002363
Sean Callanan549c9f72010-07-13 21:41:46 +00002364 for (element_index = 0; element_index < num_elements; ++element_index)
2365 {
Sean Callanan77eaf442011-07-08 00:39:14 +00002366 const clang::NamedDecl *decl = NULL;
2367 Value *value = NULL;
Zachary Turnera746e8e2014-07-02 17:24:07 +00002368 lldb::offset_t offset;
Greg Clayton7b462cc2010-10-15 22:48:33 +00002369 lldb_private::ConstString name;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002370
Sean Callanan823bb4c2010-08-30 22:17:16 +00002371 if (!m_decl_map->GetStructElement (decl, value, offset, name, element_index))
Sean Callanan3989fb92011-01-27 01:07:04 +00002372 {
2373 if (m_error_stream)
2374 m_error_stream->Printf("Internal error [IRForTarget]: Structure information is incomplete");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002375
Sean Callanan549c9f72010-07-13 21:41:46 +00002376 return false;
Sean Callanan3989fb92011-01-27 01:07:04 +00002377 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002378
Sean Callanan549c9f72010-07-13 21:41:46 +00002379 if (log)
Zachary Turnera746e8e2014-07-02 17:24:07 +00002380 log->Printf(" \"%s\" (\"%s\") placed at %" PRIu64,
Greg Clayton7b462cc2010-10-15 22:48:33 +00002381 name.GetCString(),
Sean Callananc70ed462011-10-25 18:36:40 +00002382 decl->getNameAsString().c_str(),
Sean Callanan549c9f72010-07-13 21:41:46 +00002383 offset);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002384
Sean Callananc70ed462011-10-25 18:36:40 +00002385 if (value)
Sean Callanan92adcac2011-01-13 08:53:35 +00002386 {
Sean Callananc70ed462011-10-25 18:36:40 +00002387 if (log)
2388 log->Printf(" Replacing [%s]", PrintValue(value).c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002389
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002390 FunctionValueCache body_result_maker ([this, name, offset_type, offset, argument, value] (llvm::Function *function)->llvm::Value * {
2391 // Per the comment at ASTResultSynthesizer::SynthesizeBodyResult, in cases where the result
2392 // variable is an rvalue, we have to synthesize a dereference of the appropriate structure
2393 // entry in order to produce the static variable that the AST thinks it is accessing.
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002394
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002395 llvm::Instruction *entry_instruction = llvm::cast<Instruction>(m_entry_instruction_finder.GetValue(function));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002396
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002397 ConstantInt *offset_int(ConstantInt::get(offset_type, offset, true));
Vince Harron0fc6c672015-03-16 03:54:22 +00002398 GetElementPtrInst *get_element_ptr = GetElementPtrInst::Create(nullptr,
2399 argument,
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002400 offset_int,
2401 "",
2402 entry_instruction);
2403
2404 if (name == m_result_name && !m_result_is_pointer)
2405 {
2406 BitCastInst *bit_cast = new BitCastInst(get_element_ptr,
2407 value->getType()->getPointerTo(),
2408 "",
2409 entry_instruction);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002410
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002411 LoadInst *load = new LoadInst(bit_cast, "", entry_instruction);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002412
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002413 return load;
2414 }
2415 else
2416 {
2417 BitCastInst *bit_cast = new BitCastInst(get_element_ptr, value->getType(), "", entry_instruction);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002418
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002419 return bit_cast;
2420 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002421 });
2422
Sean Callananc70ed462011-10-25 18:36:40 +00002423 if (Constant *constant = dyn_cast<Constant>(value))
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002424 {
2425 UnfoldConstant(constant, body_result_maker, m_entry_instruction_finder);
2426 }
2427 else if (Instruction *instruction = dyn_cast<Instruction>(value))
2428 {
2429 value->replaceAllUsesWith(body_result_maker.GetValue(instruction->getParent()->getParent()));
2430 }
Sean Callananc70ed462011-10-25 18:36:40 +00002431 else
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002432 {
2433 if (log)
2434 log->Printf("Unhandled non-constant type: \"%s\"", PrintValue(value).c_str());
2435 return false;
2436 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002437
Sean Callananc70ed462011-10-25 18:36:40 +00002438 if (GlobalVariable *var = dyn_cast<GlobalVariable>(value))
2439 var->eraseFromParent();
2440 }
Sean Callanan549c9f72010-07-13 21:41:46 +00002441 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002442
Sean Callanan549c9f72010-07-13 21:41:46 +00002443 if (log)
Greg Clayton6fea17e2014-03-03 19:15:20 +00002444 log->Printf("Total structure [align %" PRId64 ", size %" PRIu64 "]", (int64_t)alignment, (uint64_t)size);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002445
Sean Callanan549c9f72010-07-13 21:41:46 +00002446 return true;
2447}
2448
Sean Callanan79763a42011-05-23 21:40:23 +00002449llvm::Constant *
Greg Clayton5160ce52013-03-27 23:08:40 +00002450IRForTarget::BuildRelocation(llvm::Type *type, uint64_t offset)
Sean Callanan79763a42011-05-23 21:40:23 +00002451{
Sean Callanan439dcae2013-12-20 19:55:02 +00002452 llvm::Constant *offset_int = ConstantInt::get(m_intptr_ty, offset);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002453
Sean Callanancc427fa2011-07-30 02:42:06 +00002454 llvm::Constant *offset_array[1];
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002455
Sean Callanancc427fa2011-07-30 02:42:06 +00002456 offset_array[0] = offset_int;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002457
Sean Callanancc427fa2011-07-30 02:42:06 +00002458 llvm::ArrayRef<llvm::Constant *> offsets(offset_array, 1);
Sean Callanan507b5882015-04-14 18:17:35 +00002459 llvm::Type *char_type = llvm::Type::getInt8Ty(m_module->getContext());
2460 llvm::Type *char_pointer_type = char_type->getPointerTo();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002461
Sean Callanan507b5882015-04-14 18:17:35 +00002462 llvm::Constant *reloc_placeholder_bitcast = ConstantExpr::getBitCast(m_reloc_placeholder, char_pointer_type);
2463 llvm::Constant *reloc_getelementptr = ConstantExpr::getGetElementPtr(char_type, reloc_placeholder_bitcast, offsets);
Sean Callanana85f0e82015-04-06 23:51:08 +00002464 llvm::Constant *reloc_bitcast = ConstantExpr::getBitCast(reloc_getelementptr, type);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002465
Sean Callanana85f0e82015-04-06 23:51:08 +00002466 return reloc_bitcast;
Sean Callanan79763a42011-05-23 21:40:23 +00002467}
2468
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002469bool
Sean Callanan79763a42011-05-23 21:40:23 +00002470IRForTarget::CompleteDataAllocation ()
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002471{
Greg Clayton5160ce52013-03-27 23:08:40 +00002472 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanan79763a42011-05-23 21:40:23 +00002473
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002474 if (!m_data_allocator.GetStream().GetSize())
Sean Callanan79763a42011-05-23 21:40:23 +00002475 return true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002476
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002477 lldb::addr_t allocation = m_data_allocator.Allocate();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002478
Sean Callanan79763a42011-05-23 21:40:23 +00002479 if (log)
2480 {
2481 if (allocation)
2482 log->Printf("Allocated static data at 0x%llx", (unsigned long long)allocation);
2483 else
2484 log->Printf("Failed to allocate static data");
2485 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002486
Sean Callanan8dfb68e2013-03-19 00:10:07 +00002487 if (!allocation || allocation == LLDB_INVALID_ADDRESS)
Sean Callanan79763a42011-05-23 21:40:23 +00002488 return false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002489
Sean Callanan439dcae2013-12-20 19:55:02 +00002490 Constant *relocated_addr = ConstantInt::get(m_intptr_ty, (uint64_t)allocation);
Sean Callanan79763a42011-05-23 21:40:23 +00002491 Constant *relocated_bitcast = ConstantExpr::getIntToPtr(relocated_addr, llvm::Type::getInt8PtrTy(m_module->getContext()));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002492
Sean Callanan79763a42011-05-23 21:40:23 +00002493 m_reloc_placeholder->replaceAllUsesWith(relocated_bitcast);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002494
Sean Callanan79763a42011-05-23 21:40:23 +00002495 m_reloc_placeholder->eraseFromParent();
2496
2497 return true;
2498}
2499
Sean Callanan2ab712f22010-07-03 01:35:46 +00002500bool
Sean Callanan3d654b32012-09-24 22:25:51 +00002501IRForTarget::StripAllGVs (Module &llvm_module)
2502{
Greg Clayton5160ce52013-03-27 23:08:40 +00002503 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sean Callanan3d654b32012-09-24 22:25:51 +00002504 std::vector<GlobalVariable *> global_vars;
2505 std::set<GlobalVariable *>erased_vars;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002506
Sean Callanan3d654b32012-09-24 22:25:51 +00002507 bool erased = true;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002508
Sean Callanan3d654b32012-09-24 22:25:51 +00002509 while (erased)
2510 {
2511 erased = false;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002512
Sean Callanan339f6152014-03-11 19:19:16 +00002513 for (GlobalVariable &global_var : llvm_module.globals())
Sean Callanan3d654b32012-09-24 22:25:51 +00002514 {
Sean Callanan339f6152014-03-11 19:19:16 +00002515 global_var.removeDeadConstantUsers();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002516
Sean Callanan339f6152014-03-11 19:19:16 +00002517 if (global_var.use_empty())
Sean Callanan3d654b32012-09-24 22:25:51 +00002518 {
2519 if (log)
2520 log->Printf("Did remove %s",
Sean Callanan339f6152014-03-11 19:19:16 +00002521 PrintValue(&global_var).c_str());
2522 global_var.eraseFromParent();
Sean Callanan3d654b32012-09-24 22:25:51 +00002523 erased = true;
2524 break;
2525 }
2526 }
2527 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002528
Sean Callanan339f6152014-03-11 19:19:16 +00002529 for (GlobalVariable &global_var : llvm_module.globals())
Sean Callanan3d654b32012-09-24 22:25:51 +00002530 {
Sean Callanan339f6152014-03-11 19:19:16 +00002531 GlobalValue::user_iterator ui = global_var.user_begin();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002532
Jim Inghamd77557d2012-11-26 19:54:04 +00002533 if (log)
2534 log->Printf("Couldn't remove %s because of %s",
Sean Callanan339f6152014-03-11 19:19:16 +00002535 PrintValue(&global_var).c_str(),
Jim Inghamd77557d2012-11-26 19:54:04 +00002536 PrintValue(*ui).c_str());
Sean Callanan3d654b32012-09-24 22:25:51 +00002537 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002538
Sean Callanan3d654b32012-09-24 22:25:51 +00002539 return true;
2540}
2541
2542bool
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002543IRForTarget::runOnModule (Module &llvm_module)
Sean Callanan2ab712f22010-07-03 01:35:46 +00002544{
Greg Clayton5160ce52013-03-27 23:08:40 +00002545 lldb_private::Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002546
Sean Callanan79763a42011-05-23 21:40:23 +00002547 m_module = &llvm_module;
Micah Villmow8468dbe2012-10-08 16:28:57 +00002548 m_target_data.reset(new DataLayout(m_module));
Sean Callanan439dcae2013-12-20 19:55:02 +00002549 m_intptr_ty = llvm::Type::getIntNTy(m_module->getContext(), m_target_data->getPointerSizeInBits());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002550
Sean Callananc70ed462011-10-25 18:36:40 +00002551 if (log)
2552 {
2553 std::string s;
2554 raw_string_ostream oss(s);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002555
Sean Callananc70ed462011-10-25 18:36:40 +00002556 m_module->print(oss, NULL);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002557
Sean Callananc70ed462011-10-25 18:36:40 +00002558 oss.flush();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002559
Sean Callananc70ed462011-10-25 18:36:40 +00002560 log->Printf("Module as passed in to IRForTarget: \n\"%s\"", s.c_str());
2561 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002562
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002563 Function* main_function = m_module->getFunction(StringRef(m_func_name.c_str()));
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002564
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002565 if (!main_function)
2566 {
2567 if (log)
2568 log->Printf("Couldn't find \"%s()\" in the module", m_func_name.c_str());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002569
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002570 if (m_error_stream)
2571 m_error_stream->Printf("Internal error [IRForTarget]: Couldn't find wrapper '%s' in the module", m_func_name.c_str());
2572
2573 return false;
2574 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002575
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002576 if (!FixFunctionLinkage (*main_function))
2577 {
2578 if (log)
2579 log->Printf("Couldn't fix the linkage for the function");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002580
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002581 return false;
2582 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002583
Sean Callanan439dcae2013-12-20 19:55:02 +00002584 llvm::Type *int8_ty = Type::getInt8Ty(m_module->getContext());
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002585
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002586 m_reloc_placeholder = new llvm::GlobalVariable((*m_module),
Sean Callanan439dcae2013-12-20 19:55:02 +00002587 int8_ty,
Sean Callanan3d654b32012-09-24 22:25:51 +00002588 false /* IsConstant */,
Sean Callanan79763a42011-05-23 21:40:23 +00002589 GlobalVariable::InternalLinkage,
Sean Callanan439dcae2013-12-20 19:55:02 +00002590 Constant::getNullValue(int8_ty),
Sean Callanan79763a42011-05-23 21:40:23 +00002591 "reloc_placeholder",
2592 NULL /* InsertBefore */,
Sean Callanan3d654b32012-09-24 22:25:51 +00002593 GlobalVariable::NotThreadLocal /* ThreadLocal */,
Sean Callanan79763a42011-05-23 21:40:23 +00002594 0 /* AddressSpace */);
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002595
Sean Callanand1e5b432010-08-12 01:56:52 +00002596 ////////////////////////////////////////////////////////////
Greg Clayton7b462cc2010-10-15 22:48:33 +00002597 // Replace $__lldb_expr_result with a persistent variable
Sean Callanand1e5b432010-08-12 01:56:52 +00002598 //
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002599
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002600 if (!CreateResultVariable(*main_function))
Sean Callanan17827832010-12-13 22:46:15 +00002601 {
2602 if (log)
2603 log->Printf("CreateResultVariable() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002604
Sean Callanan3989fb92011-01-27 01:07:04 +00002605 // CreateResultVariable() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002606
Sean Callanand1e5b432010-08-12 01:56:52 +00002607 return false;
Sean Callanan17827832010-12-13 22:46:15 +00002608 }
Sean Callanan6e6d4a62012-07-21 02:02:15 +00002609
Sean Callananea685ae2011-11-01 17:33:54 +00002610 if (log && log->GetVerbose())
Sean Callanan79763a42011-05-23 21:40:23 +00002611 {
2612 std::string s;
2613 raw_string_ostream oss(s);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002614
Sean Callanan79763a42011-05-23 21:40:23 +00002615 m_module->print(oss, NULL);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002616
Sean Callanan79763a42011-05-23 21:40:23 +00002617 oss.flush();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002618
Sean Callanan79763a42011-05-23 21:40:23 +00002619 log->Printf("Module after creating the result variable: \n\"%s\"", s.c_str());
2620 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002621
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002622 for (Module::iterator fi = m_module->begin(), fe = m_module->end();
2623 fi != fe;
2624 ++fi)
2625 {
2626 llvm::Function *function = fi;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002627
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002628 if (function->begin() == function->end())
2629 continue;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002630
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002631 Function::iterator bbi;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002632
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002633 for (bbi = function->begin();
2634 bbi != function->end();
2635 ++bbi)
2636 {
2637 if (!RemoveGuards(*bbi))
2638 {
2639 if (log)
2640 log->Printf("RemoveGuards() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002641
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002642 // RemoveGuards() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002643
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002644 return false;
2645 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002646
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002647 if (!RewritePersistentAllocs(*bbi))
2648 {
2649 if (log)
2650 log->Printf("RewritePersistentAllocs() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002651
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002652 // RewritePersistentAllocs() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002653
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002654 return false;
2655 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002656
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002657 if (!RemoveCXAAtExit(*bbi))
2658 {
2659 if (log)
2660 log->Printf("RemoveCXAAtExit() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002661
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002662 // RemoveCXAAtExit() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002663
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002664 return false;
2665 }
2666 }
2667 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002668
Sean Callananafe16a72010-11-17 23:00:36 +00002669 ///////////////////////////////////////////////////////////////////////////////
2670 // Fix all Objective-C constant strings to use NSStringWithCString:encoding:
2671 //
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002672
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002673 if (!RewriteObjCConstStrings())
Sean Callanan17827832010-12-13 22:46:15 +00002674 {
2675 if (log)
2676 log->Printf("RewriteObjCConstStrings() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002677
Sean Callanan3989fb92011-01-27 01:07:04 +00002678 // RewriteObjCConstStrings() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002679
Sean Callananafe16a72010-11-17 23:00:36 +00002680 return false;
Sean Callanan17827832010-12-13 22:46:15 +00002681 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002682
Sean Callanan0c4d8d22011-08-04 21:37:47 +00002683 ///////////////////////////////
2684 // Resolve function pointers
2685 //
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002686
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002687 if (!ResolveFunctionPointers(llvm_module))
Sean Callanan0c4d8d22011-08-04 21:37:47 +00002688 {
2689 if (log)
2690 log->Printf("ResolveFunctionPointers() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002691
Sean Callanan0c4d8d22011-08-04 21:37:47 +00002692 // ResolveFunctionPointers() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002693
Sean Callanan0c4d8d22011-08-04 21:37:47 +00002694 return false;
2695 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002696
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002697 for (Module::iterator fi = m_module->begin(), fe = m_module->end();
2698 fi != fe;
2699 ++fi)
Sean Callanan2ab712f22010-07-03 01:35:46 +00002700 {
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002701 llvm::Function *function = fi;
2702
2703 for (llvm::Function::iterator bbi = function->begin(), bbe = function->end();
2704 bbi != bbe;
2705 ++bbi)
Sean Callanan17827832010-12-13 22:46:15 +00002706 {
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002707 if (!RewriteObjCSelectors(*bbi))
2708 {
2709 if (log)
2710 log->Printf("RewriteObjCSelectors() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002711
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002712 // RewriteObjCSelectors() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002713
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002714 return false;
2715 }
Sean Callanan17827832010-12-13 22:46:15 +00002716 }
Sean Callananbad134f2012-07-27 19:25:24 +00002717 }
Sean Callanan2235f322010-08-11 03:57:18 +00002718
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002719 for (Module::iterator fi = m_module->begin(), fe = m_module->end();
2720 fi != fe;
2721 ++fi)
Sean Callananbad134f2012-07-27 19:25:24 +00002722 {
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002723 llvm::Function *function = fi;
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002724
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002725 for (llvm::Function::iterator bbi = function->begin(), bbe = function->end();
2726 bbi != bbe;
2727 ++bbi)
Sean Callanan79763a42011-05-23 21:40:23 +00002728 {
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002729 if (!ResolveCalls(*bbi))
2730 {
2731 if (log)
2732 log->Printf("ResolveCalls() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002733
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002734 // ResolveCalls() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002735
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002736 return false;
2737 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002738
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002739 if (!ReplaceStaticLiterals(*bbi))
2740 {
2741 if (log)
2742 log->Printf("ReplaceStaticLiterals() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002743
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002744 return false;
2745 }
Sean Callanan79763a42011-05-23 21:40:23 +00002746 }
Sean Callanan549c9f72010-07-13 21:41:46 +00002747 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002748
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002749 ////////////////////////////////////////////////////////////////////////
2750 // Run function-level passes that only make sense on the main function
Sean Callanan038df5032010-09-30 21:18:25 +00002751 //
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002752
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002753 if (!ResolveExternals(*main_function))
Sean Callanan17827832010-12-13 22:46:15 +00002754 {
2755 if (log)
2756 log->Printf("ResolveExternals() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002757
Sean Callanan3989fb92011-01-27 01:07:04 +00002758 // ResolveExternals() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002759
Sean Callanana4e55172010-11-08 00:31:32 +00002760 return false;
Sean Callanan17827832010-12-13 22:46:15 +00002761 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002762
Sean Callanan1f9db3e2013-06-28 21:44:15 +00002763 if (!ReplaceVariables(*main_function))
Sean Callanan17827832010-12-13 22:46:15 +00002764 {
2765 if (log)
2766 log->Printf("ReplaceVariables() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002767
Sean Callanan3989fb92011-01-27 01:07:04 +00002768 // ReplaceVariables() reports its own errors, so we don't do so here
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002769
Sean Callanan038df5032010-09-30 21:18:25 +00002770 return false;
Sean Callanan17827832010-12-13 22:46:15 +00002771 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002772
Sean Callanan79763a42011-05-23 21:40:23 +00002773 if (!ReplaceStrings())
2774 {
2775 if (log)
2776 log->Printf("ReplaceStrings() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002777
Sean Callanan79763a42011-05-23 21:40:23 +00002778 return false;
2779 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002780
Sean Callanan79763a42011-05-23 21:40:23 +00002781 if (!CompleteDataAllocation())
2782 {
2783 if (log)
2784 log->Printf("CompleteDataAllocation() failed");
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002785
Sean Callanan79763a42011-05-23 21:40:23 +00002786 return false;
2787 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002788
Sean Callanan3d654b32012-09-24 22:25:51 +00002789 if (!StripAllGVs(llvm_module))
2790 {
2791 if (log)
2792 log->Printf("StripAllGVs() failed");
2793 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002794
Sean Callananea685ae2011-11-01 17:33:54 +00002795 if (log && log->GetVerbose())
Sean Callanan549c9f72010-07-13 21:41:46 +00002796 {
Sean Callanancc54bd32010-07-28 01:00:59 +00002797 std::string s;
2798 raw_string_ostream oss(s);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002799
Sean Callanan79763a42011-05-23 21:40:23 +00002800 m_module->print(oss, NULL);
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002801
Sean Callanancc54bd32010-07-28 01:00:59 +00002802 oss.flush();
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002803
Greg Claytoncb7e3b32010-11-15 01:47:11 +00002804 log->Printf("Module after preparing for execution: \n\"%s\"", s.c_str());
Sean Callanan2ab712f22010-07-03 01:35:46 +00002805 }
Sylvestre Ledruceab3ac2014-07-06 17:54:58 +00002806
2807 return true;
Sean Callanan2ab712f22010-07-03 01:35:46 +00002808}
2809
2810void
Greg Clayton1b95a6f2010-11-19 01:05:25 +00002811IRForTarget::assignPassManager (PMStack &pass_mgr_stack, PassManagerType pass_mgr_type)
Sean Callanan2ab712f22010-07-03 01:35:46 +00002812{
2813}
2814
2815PassManagerType
2816IRForTarget::getPotentialPassManagerType() const
2817{
2818 return PMT_ModulePassManager;
2819}