blob: 4498182e7547fbfcea49b0f4f84b9aa680ce2aec [file] [log] [blame]
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001//===-- PluginManager.cpp ---------------------------------------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
Daniel Malea93a64302012-12-05 00:20:57 +000010#include "lldb/lldb-python.h"
11
Chris Lattner30fdc8d2010-06-08 16:52:24 +000012#include "lldb/Core/PluginManager.h"
13
Stephen Wilson8acdbb82011-04-08 13:36:44 +000014#include <limits.h>
15
Chris Lattner30fdc8d2010-06-08 16:52:24 +000016#include <string>
17#include <vector>
18
Greg Claytone8cd0c92012-10-19 18:02:49 +000019#include "lldb/Core/Debugger.h"
Greg Clayton4272cc72011-02-02 02:24:04 +000020#include "lldb/Core/Error.h"
Greg Clayton53239f02011-02-08 05:05:52 +000021#include "lldb/Host/FileSpec.h"
Greg Clayton4272cc72011-02-02 02:24:04 +000022#include "lldb/Host/Host.h"
23#include "lldb/Host/Mutex.h"
Greg Claytone8cd0c92012-10-19 18:02:49 +000024#include "lldb/Interpreter/OptionValueProperties.h"
Greg Clayton4272cc72011-02-02 02:24:04 +000025
Greg Claytonab65b342011-04-13 22:47:15 +000026#include "llvm/ADT/StringRef.h"
27
Greg Clayton4272cc72011-02-02 02:24:04 +000028using namespace lldb;
Chris Lattner30fdc8d2010-06-08 16:52:24 +000029using namespace lldb_private;
30
Jason Molenda743e86a2010-06-11 23:44:18 +000031enum PluginAction
Chris Lattner30fdc8d2010-06-08 16:52:24 +000032{
33 ePluginRegisterInstance,
34 ePluginUnregisterInstance,
35 ePluginGetInstanceAtIndex
36};
37
Greg Clayton03da4cc2013-04-19 21:31:16 +000038
39typedef bool (*PluginInitCallback) (void);
40typedef void (*PluginTermCallback) (void);
41
Greg Clayton4272cc72011-02-02 02:24:04 +000042struct PluginInfo
43{
44 void *plugin_handle;
Greg Clayton03da4cc2013-04-19 21:31:16 +000045 PluginInitCallback plugin_init_callback;
46 PluginTermCallback plugin_term_callback;
Greg Clayton4272cc72011-02-02 02:24:04 +000047};
48
49typedef std::map<FileSpec, PluginInfo> PluginTerminateMap;
50
51static Mutex &
52GetPluginMapMutex ()
53{
54 static Mutex g_plugin_map_mutex (Mutex::eMutexTypeRecursive);
55 return g_plugin_map_mutex;
56}
57
58static PluginTerminateMap &
59GetPluginMap ()
60{
61 static PluginTerminateMap g_plugin_map;
62 return g_plugin_map;
63}
64
65static bool
66PluginIsLoaded (const FileSpec &plugin_file_spec)
67{
68 Mutex::Locker locker (GetPluginMapMutex ());
69 PluginTerminateMap &plugin_map = GetPluginMap ();
70 return plugin_map.find (plugin_file_spec) != plugin_map.end();
71}
72
73static void
74SetPluginInfo (const FileSpec &plugin_file_spec, const PluginInfo &plugin_info)
75{
76 Mutex::Locker locker (GetPluginMapMutex ());
77 PluginTerminateMap &plugin_map = GetPluginMap ();
78 assert (plugin_map.find (plugin_file_spec) != plugin_map.end());
79 plugin_map[plugin_file_spec] = plugin_info;
80}
81
82
83static FileSpec::EnumerateDirectoryResult
84LoadPluginCallback
85(
86 void *baton,
87 FileSpec::FileType file_type,
88 const FileSpec &file_spec
89)
90{
91// PluginManager *plugin_manager = (PluginManager *)baton;
92 Error error;
93
94 // If we have a regular file, a symbolic link or unknown file type, try
95 // and process the file. We must handle unknown as sometimes the directory
96 // enumeration might be enumerating a file system that doesn't have correct
97 // file type information.
98 if (file_type == FileSpec::eFileTypeRegular ||
99 file_type == FileSpec::eFileTypeSymbolicLink ||
100 file_type == FileSpec::eFileTypeUnknown )
101 {
102 FileSpec plugin_file_spec (file_spec);
103 plugin_file_spec.ResolvePath();
104
105 if (PluginIsLoaded (plugin_file_spec))
106 return FileSpec::eEnumerateDirectoryResultNext;
107 else
108 {
109 PluginInfo plugin_info = { NULL, NULL, NULL };
Greg Clayton45319462011-02-08 00:35:34 +0000110 uint32_t flags = Host::eDynamicLibraryOpenOptionLazy |
111 Host::eDynamicLibraryOpenOptionLocal |
112 Host::eDynamicLibraryOpenOptionLimitGetSymbol;
113
114 plugin_info.plugin_handle = Host::DynamicLibraryOpen (plugin_file_spec, flags, error);
Greg Clayton4272cc72011-02-02 02:24:04 +0000115 if (plugin_info.plugin_handle)
116 {
117 bool success = false;
Greg Clayton03da4cc2013-04-19 21:31:16 +0000118 plugin_info.plugin_init_callback = (PluginInitCallback)Host::DynamicLibraryGetSymbol (plugin_info.plugin_handle, "LLDBPluginInitialize", error);
Greg Clayton4272cc72011-02-02 02:24:04 +0000119 if (plugin_info.plugin_init_callback)
120 {
121 // Call the plug-in "bool LLDBPluginInitialize(void)" function
Greg Clayton03da4cc2013-04-19 21:31:16 +0000122 success = plugin_info.plugin_init_callback();
Greg Clayton4272cc72011-02-02 02:24:04 +0000123 }
124
125 if (success)
126 {
127 // It is ok for the "LLDBPluginTerminate" symbol to be NULL
Greg Clayton03da4cc2013-04-19 21:31:16 +0000128 plugin_info.plugin_term_callback = (PluginTermCallback)Host::DynamicLibraryGetSymbol (plugin_info.plugin_handle, "LLDBPluginTerminate", error);
Greg Clayton4272cc72011-02-02 02:24:04 +0000129 }
130 else
131 {
132 // The initialize function returned FALSE which means the
133 // plug-in might not be compatible, or might be too new or
134 // too old, or might not want to run on this machine.
135 Host::DynamicLibraryClose (plugin_info.plugin_handle);
136 plugin_info.plugin_handle = NULL;
137 plugin_info.plugin_init_callback = NULL;
138 }
139
140 // Regardless of success or failure, cache the plug-in load
141 // in our plug-in info so we don't try to load it again and
142 // again.
143 SetPluginInfo (plugin_file_spec, plugin_info);
144
145 return FileSpec::eEnumerateDirectoryResultNext;
146 }
147 }
148 }
149
150 if (file_type == FileSpec::eFileTypeUnknown ||
151 file_type == FileSpec::eFileTypeDirectory ||
152 file_type == FileSpec::eFileTypeSymbolicLink )
153 {
154 // Try and recurse into anything that a directory or symbolic link.
155 // We must also do this for unknown as sometimes the directory enumeration
156 // might be enurating a file system that doesn't have correct file type
157 // information.
158 return FileSpec::eEnumerateDirectoryResultEnter;
159 }
160
161 return FileSpec::eEnumerateDirectoryResultNext;
162}
163
164
165void
166PluginManager::Initialize ()
167{
Greg Clayton1cb64962011-03-24 04:28:38 +0000168#if 1
Greg Clayton4272cc72011-02-02 02:24:04 +0000169 FileSpec dir_spec;
170 const bool find_directories = true;
171 const bool find_files = true;
172 const bool find_other = true;
173 char dir_path[PATH_MAX];
174 if (Host::GetLLDBPath (ePathTypeLLDBSystemPlugins, dir_spec))
175 {
176 if (dir_spec.Exists() && dir_spec.GetPath(dir_path, sizeof(dir_path)))
177 {
178 FileSpec::EnumerateDirectory (dir_path,
179 find_directories,
180 find_files,
181 find_other,
182 LoadPluginCallback,
183 NULL);
184 }
185 }
186
187 if (Host::GetLLDBPath (ePathTypeLLDBUserPlugins, dir_spec))
188 {
189 if (dir_spec.Exists() && dir_spec.GetPath(dir_path, sizeof(dir_path)))
190 {
191 FileSpec::EnumerateDirectory (dir_path,
192 find_directories,
193 find_files,
194 find_other,
195 LoadPluginCallback,
196 NULL);
197 }
198 }
Greg Clayton1cb64962011-03-24 04:28:38 +0000199#endif
Greg Clayton4272cc72011-02-02 02:24:04 +0000200}
201
202void
203PluginManager::Terminate ()
204{
205 Mutex::Locker locker (GetPluginMapMutex ());
206 PluginTerminateMap &plugin_map = GetPluginMap ();
207
208 PluginTerminateMap::const_iterator pos, end = plugin_map.end();
209 for (pos = plugin_map.begin(); pos != end; ++pos)
210 {
211 // Call the plug-in "void LLDBPluginTerminate (void)" function if there
212 // is one (if the symbol was not NULL).
213 if (pos->second.plugin_handle)
214 {
215 if (pos->second.plugin_term_callback)
Greg Clayton03da4cc2013-04-19 21:31:16 +0000216 pos->second.plugin_term_callback();
Greg Clayton4272cc72011-02-02 02:24:04 +0000217 Host::DynamicLibraryClose (pos->second.plugin_handle);
218 }
219 }
220 plugin_map.clear();
221}
222
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000223
224#pragma mark ABI
225
226
Jason Molenda743e86a2010-06-11 23:44:18 +0000227struct ABIInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000228{
229 ABIInstance() :
230 name(),
231 description(),
232 create_callback(NULL)
233 {
234 }
235
236 std::string name;
237 std::string description;
238 ABICreateInstance create_callback;
239};
240
241typedef std::vector<ABIInstance> ABIInstances;
242
Greg Claytonded470d2011-03-19 01:12:21 +0000243static Mutex &
244GetABIInstancesMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000245{
Greg Claytonded470d2011-03-19 01:12:21 +0000246 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
247 return g_instances_mutex;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000248}
249
Greg Claytonded470d2011-03-19 01:12:21 +0000250static ABIInstances &
251GetABIInstances ()
252{
253 static ABIInstances g_instances;
254 return g_instances;
255}
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000256
257bool
258PluginManager::RegisterPlugin
Greg Clayton4272cc72011-02-02 02:24:04 +0000259(
260 const char *name,
261 const char *description,
262 ABICreateInstance create_callback
263)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000264{
265 if (create_callback)
266 {
267 ABIInstance instance;
268 assert (name && name[0]);
Greg Claytonab65b342011-04-13 22:47:15 +0000269 instance.name.assign (name);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000270 if (description && description[0])
271 instance.description = description;
272 instance.create_callback = create_callback;
Greg Claytonded470d2011-03-19 01:12:21 +0000273 Mutex::Locker locker (GetABIInstancesMutex ());
274 GetABIInstances ().push_back (instance);
275 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000276 }
277 return false;
278}
279
280bool
281PluginManager::UnregisterPlugin (ABICreateInstance create_callback)
282{
283 if (create_callback)
284 {
Greg Claytonded470d2011-03-19 01:12:21 +0000285 Mutex::Locker locker (GetABIInstancesMutex ());
286 ABIInstances &instances = GetABIInstances ();
287
288 ABIInstances::iterator pos, end = instances.end();
289 for (pos = instances.begin(); pos != end; ++ pos)
290 {
291 if (pos->create_callback == create_callback)
292 {
293 instances.erase(pos);
294 return true;
295 }
296 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000297 }
298 return false;
299}
300
301ABICreateInstance
302PluginManager::GetABICreateCallbackAtIndex (uint32_t idx)
303{
Greg Claytonded470d2011-03-19 01:12:21 +0000304 Mutex::Locker locker (GetABIInstancesMutex ());
305 ABIInstances &instances = GetABIInstances ();
Greg Claytonded470d2011-03-19 01:12:21 +0000306 if (idx < instances.size())
307 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +0000308 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000309}
310
311ABICreateInstance
312PluginManager::GetABICreateCallbackForPluginName (const char *name)
313{
314 if (name && name[0])
315 {
Greg Claytonded470d2011-03-19 01:12:21 +0000316 Mutex::Locker locker (GetABIInstancesMutex ());
Greg Claytonab65b342011-04-13 22:47:15 +0000317 llvm::StringRef name_sref(name);
Greg Claytonded470d2011-03-19 01:12:21 +0000318 ABIInstances &instances = GetABIInstances ();
319
320 ABIInstances::iterator pos, end = instances.end();
321 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000322 {
Greg Claytonab65b342011-04-13 22:47:15 +0000323 if (name_sref.equals (pos->name))
Greg Claytonded470d2011-03-19 01:12:21 +0000324 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000325 }
326 }
327 return NULL;
328}
329
330
331#pragma mark Disassembler
332
333
Jason Molenda743e86a2010-06-11 23:44:18 +0000334struct DisassemblerInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000335{
336 DisassemblerInstance() :
337 name(),
338 description(),
339 create_callback(NULL)
340 {
341 }
342
343 std::string name;
344 std::string description;
345 DisassemblerCreateInstance create_callback;
346};
347
348typedef std::vector<DisassemblerInstance> DisassemblerInstances;
349
Greg Claytonab65b342011-04-13 22:47:15 +0000350static Mutex &
351GetDisassemblerMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000352{
Greg Claytonab65b342011-04-13 22:47:15 +0000353 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
354 return g_instances_mutex;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000355}
356
Greg Claytonab65b342011-04-13 22:47:15 +0000357static DisassemblerInstances &
358GetDisassemblerInstances ()
359{
360 static DisassemblerInstances g_instances;
361 return g_instances;
362}
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000363
364bool
365PluginManager::RegisterPlugin
366(
367 const char *name,
368 const char *description,
369 DisassemblerCreateInstance create_callback
370)
371{
372 if (create_callback)
373 {
374 DisassemblerInstance instance;
375 assert (name && name[0]);
376 instance.name = name;
377 if (description && description[0])
378 instance.description = description;
379 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +0000380 Mutex::Locker locker (GetDisassemblerMutex ());
381 GetDisassemblerInstances ().push_back (instance);
382 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000383 }
384 return false;
385}
386
387bool
388PluginManager::UnregisterPlugin (DisassemblerCreateInstance create_callback)
389{
390 if (create_callback)
391 {
Greg Claytonab65b342011-04-13 22:47:15 +0000392 Mutex::Locker locker (GetDisassemblerMutex ());
393 DisassemblerInstances &instances = GetDisassemblerInstances ();
394
395 DisassemblerInstances::iterator pos, end = instances.end();
396 for (pos = instances.begin(); pos != end; ++ pos)
397 {
398 if (pos->create_callback == create_callback)
399 {
400 instances.erase(pos);
401 return true;
402 }
403 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000404 }
405 return false;
406}
407
408DisassemblerCreateInstance
409PluginManager::GetDisassemblerCreateCallbackAtIndex (uint32_t idx)
410{
Greg Claytonab65b342011-04-13 22:47:15 +0000411 Mutex::Locker locker (GetDisassemblerMutex ());
412 DisassemblerInstances &instances = GetDisassemblerInstances ();
413 if (idx < instances.size())
414 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +0000415 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000416}
417
418DisassemblerCreateInstance
419PluginManager::GetDisassemblerCreateCallbackForPluginName (const char *name)
420{
421 if (name && name[0])
422 {
Greg Claytonab65b342011-04-13 22:47:15 +0000423 llvm::StringRef name_sref(name);
424 Mutex::Locker locker (GetDisassemblerMutex ());
425 DisassemblerInstances &instances = GetDisassemblerInstances ();
426
427 DisassemblerInstances::iterator pos, end = instances.end();
428 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000429 {
Greg Claytonab65b342011-04-13 22:47:15 +0000430 if (name_sref.equals (pos->name))
431 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000432 }
433 }
434 return NULL;
435}
436
437
438
439#pragma mark DynamicLoader
440
441
Jason Molenda743e86a2010-06-11 23:44:18 +0000442struct DynamicLoaderInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000443{
444 DynamicLoaderInstance() :
445 name(),
446 description(),
Greg Claytone8cd0c92012-10-19 18:02:49 +0000447 create_callback(NULL),
448 debugger_init_callback (NULL)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000449 {
450 }
451
452 std::string name;
453 std::string description;
454 DynamicLoaderCreateInstance create_callback;
Greg Claytone8cd0c92012-10-19 18:02:49 +0000455 DebuggerInitializeCallback debugger_init_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000456};
457
458typedef std::vector<DynamicLoaderInstance> DynamicLoaderInstances;
459
Greg Claytonab65b342011-04-13 22:47:15 +0000460
461static Mutex &
462GetDynamicLoaderMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000463{
Greg Claytonab65b342011-04-13 22:47:15 +0000464 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
465 return g_instances_mutex;
466}
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000467
Greg Claytonab65b342011-04-13 22:47:15 +0000468static DynamicLoaderInstances &
469GetDynamicLoaderInstances ()
470{
471 static DynamicLoaderInstances g_instances;
472 return g_instances;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000473}
474
475
476bool
477PluginManager::RegisterPlugin
478(
479 const char *name,
480 const char *description,
Greg Claytone8cd0c92012-10-19 18:02:49 +0000481 DynamicLoaderCreateInstance create_callback,
482 DebuggerInitializeCallback debugger_init_callback
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000483)
484{
485 if (create_callback)
486 {
487 DynamicLoaderInstance instance;
488 assert (name && name[0]);
489 instance.name = name;
490 if (description && description[0])
491 instance.description = description;
492 instance.create_callback = create_callback;
Greg Claytone8cd0c92012-10-19 18:02:49 +0000493 instance.debugger_init_callback = debugger_init_callback;
Greg Claytonab65b342011-04-13 22:47:15 +0000494 Mutex::Locker locker (GetDynamicLoaderMutex ());
495 GetDynamicLoaderInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000496 }
497 return false;
498}
499
500bool
501PluginManager::UnregisterPlugin (DynamicLoaderCreateInstance create_callback)
502{
503 if (create_callback)
504 {
Greg Claytonab65b342011-04-13 22:47:15 +0000505 Mutex::Locker locker (GetDynamicLoaderMutex ());
506 DynamicLoaderInstances &instances = GetDynamicLoaderInstances ();
507
508 DynamicLoaderInstances::iterator pos, end = instances.end();
509 for (pos = instances.begin(); pos != end; ++ pos)
510 {
511 if (pos->create_callback == create_callback)
512 {
513 instances.erase(pos);
514 return true;
515 }
516 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000517 }
518 return false;
519}
520
521DynamicLoaderCreateInstance
522PluginManager::GetDynamicLoaderCreateCallbackAtIndex (uint32_t idx)
523{
Greg Claytonab65b342011-04-13 22:47:15 +0000524 Mutex::Locker locker (GetDynamicLoaderMutex ());
525 DynamicLoaderInstances &instances = GetDynamicLoaderInstances ();
526 if (idx < instances.size())
527 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +0000528 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000529}
530
531DynamicLoaderCreateInstance
532PluginManager::GetDynamicLoaderCreateCallbackForPluginName (const char *name)
533{
534 if (name && name[0])
535 {
Greg Claytonab65b342011-04-13 22:47:15 +0000536 llvm::StringRef name_sref(name);
537 Mutex::Locker locker (GetDynamicLoaderMutex ());
538 DynamicLoaderInstances &instances = GetDynamicLoaderInstances ();
539
540 DynamicLoaderInstances::iterator pos, end = instances.end();
541 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000542 {
Greg Claytonab65b342011-04-13 22:47:15 +0000543 if (name_sref.equals (pos->name))
544 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000545 }
546 }
547 return NULL;
548}
549
Greg Claytonf03bbe22011-02-01 01:37:45 +0000550#pragma mark EmulateInstruction
551
552
553struct EmulateInstructionInstance
554{
555 EmulateInstructionInstance() :
556 name(),
557 description(),
558 create_callback(NULL)
559 {
560 }
561
562 std::string name;
563 std::string description;
564 EmulateInstructionCreateInstance create_callback;
565};
566
567typedef std::vector<EmulateInstructionInstance> EmulateInstructionInstances;
568
Greg Claytonab65b342011-04-13 22:47:15 +0000569static Mutex &
570GetEmulateInstructionMutex ()
Greg Claytonf03bbe22011-02-01 01:37:45 +0000571{
Greg Claytonab65b342011-04-13 22:47:15 +0000572 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
573 return g_instances_mutex;
574}
575
576static EmulateInstructionInstances &
577GetEmulateInstructionInstances ()
578{
579 static EmulateInstructionInstances g_instances;
580 return g_instances;
Greg Claytonf03bbe22011-02-01 01:37:45 +0000581}
582
583
584bool
585PluginManager::RegisterPlugin
586(
Greg Clayton4272cc72011-02-02 02:24:04 +0000587 const char *name,
588 const char *description,
589 EmulateInstructionCreateInstance create_callback
590)
Greg Claytonf03bbe22011-02-01 01:37:45 +0000591{
592 if (create_callback)
593 {
594 EmulateInstructionInstance instance;
595 assert (name && name[0]);
596 instance.name = name;
597 if (description && description[0])
598 instance.description = description;
599 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +0000600 Mutex::Locker locker (GetEmulateInstructionMutex ());
601 GetEmulateInstructionInstances ().push_back (instance);
Greg Claytonf03bbe22011-02-01 01:37:45 +0000602 }
603 return false;
604}
605
606bool
607PluginManager::UnregisterPlugin (EmulateInstructionCreateInstance create_callback)
608{
609 if (create_callback)
610 {
Greg Claytonab65b342011-04-13 22:47:15 +0000611 Mutex::Locker locker (GetEmulateInstructionMutex ());
612 EmulateInstructionInstances &instances = GetEmulateInstructionInstances ();
613
614 EmulateInstructionInstances::iterator pos, end = instances.end();
615 for (pos = instances.begin(); pos != end; ++ pos)
616 {
617 if (pos->create_callback == create_callback)
618 {
619 instances.erase(pos);
620 return true;
621 }
622 }
Greg Claytonf03bbe22011-02-01 01:37:45 +0000623 }
624 return false;
625}
626
627EmulateInstructionCreateInstance
628PluginManager::GetEmulateInstructionCreateCallbackAtIndex (uint32_t idx)
629{
Greg Claytonab65b342011-04-13 22:47:15 +0000630 Mutex::Locker locker (GetEmulateInstructionMutex ());
631 EmulateInstructionInstances &instances = GetEmulateInstructionInstances ();
632 if (idx < instances.size())
633 return instances[idx].create_callback;
Greg Claytonf03bbe22011-02-01 01:37:45 +0000634 return NULL;
635}
636
637EmulateInstructionCreateInstance
638PluginManager::GetEmulateInstructionCreateCallbackForPluginName (const char *name)
639{
640 if (name && name[0])
641 {
Greg Claytonab65b342011-04-13 22:47:15 +0000642 llvm::StringRef name_sref(name);
643 Mutex::Locker locker (GetEmulateInstructionMutex ());
644 EmulateInstructionInstances &instances = GetEmulateInstructionInstances ();
645
646 EmulateInstructionInstances::iterator pos, end = instances.end();
647 for (pos = instances.begin(); pos != end; ++ pos)
Greg Claytonf03bbe22011-02-01 01:37:45 +0000648 {
Greg Claytonab65b342011-04-13 22:47:15 +0000649 if (name_sref.equals (pos->name))
650 return pos->create_callback;
Greg Claytonf03bbe22011-02-01 01:37:45 +0000651 }
652 }
653 return NULL;
654}
Greg Clayton56d9a1b2011-08-22 02:49:39 +0000655#pragma mark OperatingSystem
656
657
658struct OperatingSystemInstance
659{
660 OperatingSystemInstance() :
661 name(),
662 description(),
663 create_callback(NULL)
664 {
665 }
666
667 std::string name;
668 std::string description;
669 OperatingSystemCreateInstance create_callback;
670};
671
672typedef std::vector<OperatingSystemInstance> OperatingSystemInstances;
673
674static Mutex &
675GetOperatingSystemMutex ()
676{
677 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
678 return g_instances_mutex;
679}
680
681static OperatingSystemInstances &
682GetOperatingSystemInstances ()
683{
684 static OperatingSystemInstances g_instances;
685 return g_instances;
686}
687
688bool
689PluginManager::RegisterPlugin
690(
691 const char *name,
692 const char *description,
693 OperatingSystemCreateInstance create_callback
694 )
695{
696 if (create_callback)
697 {
698 OperatingSystemInstance instance;
699 assert (name && name[0]);
700 instance.name = name;
701 if (description && description[0])
702 instance.description = description;
703 instance.create_callback = create_callback;
704 Mutex::Locker locker (GetOperatingSystemMutex ());
705 GetOperatingSystemInstances ().push_back (instance);
706 }
707 return false;
708}
709
710bool
711PluginManager::UnregisterPlugin (OperatingSystemCreateInstance create_callback)
712{
713 if (create_callback)
714 {
715 Mutex::Locker locker (GetOperatingSystemMutex ());
716 OperatingSystemInstances &instances = GetOperatingSystemInstances ();
717
718 OperatingSystemInstances::iterator pos, end = instances.end();
719 for (pos = instances.begin(); pos != end; ++ pos)
720 {
721 if (pos->create_callback == create_callback)
722 {
723 instances.erase(pos);
724 return true;
725 }
726 }
727 }
728 return false;
729}
730
731OperatingSystemCreateInstance
732PluginManager::GetOperatingSystemCreateCallbackAtIndex (uint32_t idx)
733{
734 Mutex::Locker locker (GetOperatingSystemMutex ());
735 OperatingSystemInstances &instances = GetOperatingSystemInstances ();
736 if (idx < instances.size())
737 return instances[idx].create_callback;
738 return NULL;
739}
740
741OperatingSystemCreateInstance
742PluginManager::GetOperatingSystemCreateCallbackForPluginName (const char *name)
743{
744 if (name && name[0])
745 {
746 llvm::StringRef name_sref(name);
747 Mutex::Locker locker (GetOperatingSystemMutex ());
748 OperatingSystemInstances &instances = GetOperatingSystemInstances ();
749
750 OperatingSystemInstances::iterator pos, end = instances.end();
751 for (pos = instances.begin(); pos != end; ++ pos)
752 {
753 if (name_sref.equals (pos->name))
754 return pos->create_callback;
755 }
756 }
757 return NULL;
758}
Greg Claytonf03bbe22011-02-01 01:37:45 +0000759
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000760
Jim Ingham22777012010-09-23 02:01:19 +0000761#pragma mark LanguageRuntime
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000762
763
Jim Ingham22777012010-09-23 02:01:19 +0000764struct LanguageRuntimeInstance
765{
766 LanguageRuntimeInstance() :
767 name(),
768 description(),
769 create_callback(NULL)
770 {
771 }
772
773 std::string name;
774 std::string description;
775 LanguageRuntimeCreateInstance create_callback;
776};
777
778typedef std::vector<LanguageRuntimeInstance> LanguageRuntimeInstances;
779
Greg Claytonab65b342011-04-13 22:47:15 +0000780static Mutex &
781GetLanguageRuntimeMutex ()
Jim Ingham22777012010-09-23 02:01:19 +0000782{
Greg Claytonab65b342011-04-13 22:47:15 +0000783 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
784 return g_instances_mutex;
Jim Ingham22777012010-09-23 02:01:19 +0000785}
786
Greg Claytonab65b342011-04-13 22:47:15 +0000787static LanguageRuntimeInstances &
788GetLanguageRuntimeInstances ()
789{
790 static LanguageRuntimeInstances g_instances;
791 return g_instances;
792}
Jim Ingham22777012010-09-23 02:01:19 +0000793
794bool
795PluginManager::RegisterPlugin
Greg Clayton4272cc72011-02-02 02:24:04 +0000796(
797 const char *name,
798 const char *description,
799 LanguageRuntimeCreateInstance create_callback
800)
Jim Ingham22777012010-09-23 02:01:19 +0000801{
802 if (create_callback)
803 {
804 LanguageRuntimeInstance instance;
805 assert (name && name[0]);
806 instance.name = name;
807 if (description && description[0])
808 instance.description = description;
809 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +0000810 Mutex::Locker locker (GetLanguageRuntimeMutex ());
811 GetLanguageRuntimeInstances ().push_back (instance);
Jim Ingham22777012010-09-23 02:01:19 +0000812 }
813 return false;
814}
815
816bool
817PluginManager::UnregisterPlugin (LanguageRuntimeCreateInstance create_callback)
818{
819 if (create_callback)
820 {
Greg Claytonab65b342011-04-13 22:47:15 +0000821 Mutex::Locker locker (GetLanguageRuntimeMutex ());
822 LanguageRuntimeInstances &instances = GetLanguageRuntimeInstances ();
823
824 LanguageRuntimeInstances::iterator pos, end = instances.end();
825 for (pos = instances.begin(); pos != end; ++ pos)
826 {
827 if (pos->create_callback == create_callback)
828 {
829 instances.erase(pos);
830 return true;
831 }
832 }
Jim Ingham22777012010-09-23 02:01:19 +0000833 }
834 return false;
835}
836
837LanguageRuntimeCreateInstance
838PluginManager::GetLanguageRuntimeCreateCallbackAtIndex (uint32_t idx)
839{
Greg Claytonab65b342011-04-13 22:47:15 +0000840 Mutex::Locker locker (GetLanguageRuntimeMutex ());
841 LanguageRuntimeInstances &instances = GetLanguageRuntimeInstances ();
842 if (idx < instances.size())
843 return instances[idx].create_callback;
Jim Ingham22777012010-09-23 02:01:19 +0000844 return NULL;
845}
846
847LanguageRuntimeCreateInstance
848PluginManager::GetLanguageRuntimeCreateCallbackForPluginName (const char *name)
849{
850 if (name && name[0])
851 {
Greg Claytonab65b342011-04-13 22:47:15 +0000852 llvm::StringRef name_sref(name);
853 Mutex::Locker locker (GetLanguageRuntimeMutex ());
854 LanguageRuntimeInstances &instances = GetLanguageRuntimeInstances ();
855
856 LanguageRuntimeInstances::iterator pos, end = instances.end();
857 for (pos = instances.begin(); pos != end; ++ pos)
Jim Ingham22777012010-09-23 02:01:19 +0000858 {
Greg Claytonab65b342011-04-13 22:47:15 +0000859 if (name_sref.equals (pos->name))
860 return pos->create_callback;
Jim Ingham22777012010-09-23 02:01:19 +0000861 }
862 }
863 return NULL;
864}
865
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000866#pragma mark ObjectFile
867
Jason Molenda743e86a2010-06-11 23:44:18 +0000868struct ObjectFileInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000869{
870 ObjectFileInstance() :
871 name(),
872 description(),
873 create_callback(NULL)
874 {
875 }
876
877 std::string name;
878 std::string description;
879 ObjectFileCreateInstance create_callback;
Greg Claytonc9660542012-02-05 02:38:54 +0000880 ObjectFileCreateMemoryInstance create_memory_callback;
881
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000882};
883
884typedef std::vector<ObjectFileInstance> ObjectFileInstances;
885
Greg Claytonab65b342011-04-13 22:47:15 +0000886static Mutex &
887GetObjectFileMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000888{
Greg Claytonab65b342011-04-13 22:47:15 +0000889 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
890 return g_instances_mutex;
891}
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000892
Greg Claytonab65b342011-04-13 22:47:15 +0000893static ObjectFileInstances &
894GetObjectFileInstances ()
895{
896 static ObjectFileInstances g_instances;
897 return g_instances;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000898}
899
900
901bool
902PluginManager::RegisterPlugin
903(
904 const char *name,
905 const char *description,
Greg Claytonc9660542012-02-05 02:38:54 +0000906 ObjectFileCreateInstance create_callback,
907 ObjectFileCreateMemoryInstance create_memory_callback
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000908)
909{
910 if (create_callback)
911 {
912 ObjectFileInstance instance;
913 assert (name && name[0]);
914 instance.name = name;
915 if (description && description[0])
916 instance.description = description;
917 instance.create_callback = create_callback;
Greg Claytonc9660542012-02-05 02:38:54 +0000918 instance.create_memory_callback = create_memory_callback;
Greg Claytonab65b342011-04-13 22:47:15 +0000919 Mutex::Locker locker (GetObjectFileMutex ());
920 GetObjectFileInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000921 }
922 return false;
923}
924
925bool
926PluginManager::UnregisterPlugin (ObjectFileCreateInstance create_callback)
927{
928 if (create_callback)
929 {
Greg Claytonab65b342011-04-13 22:47:15 +0000930 Mutex::Locker locker (GetObjectFileMutex ());
931 ObjectFileInstances &instances = GetObjectFileInstances ();
932
933 ObjectFileInstances::iterator pos, end = instances.end();
934 for (pos = instances.begin(); pos != end; ++ pos)
935 {
936 if (pos->create_callback == create_callback)
937 {
938 instances.erase(pos);
939 return true;
940 }
941 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000942 }
943 return false;
944}
945
946ObjectFileCreateInstance
947PluginManager::GetObjectFileCreateCallbackAtIndex (uint32_t idx)
948{
Greg Claytonab65b342011-04-13 22:47:15 +0000949 Mutex::Locker locker (GetObjectFileMutex ());
950 ObjectFileInstances &instances = GetObjectFileInstances ();
951 if (idx < instances.size())
952 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +0000953 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000954}
Greg Claytonab65b342011-04-13 22:47:15 +0000955
Greg Claytonc9660542012-02-05 02:38:54 +0000956
957ObjectFileCreateMemoryInstance
958PluginManager::GetObjectFileCreateMemoryCallbackAtIndex (uint32_t idx)
959{
960 Mutex::Locker locker (GetObjectFileMutex ());
961 ObjectFileInstances &instances = GetObjectFileInstances ();
962 if (idx < instances.size())
963 return instances[idx].create_memory_callback;
964 return NULL;
965}
966
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000967ObjectFileCreateInstance
968PluginManager::GetObjectFileCreateCallbackForPluginName (const char *name)
969{
970 if (name && name[0])
971 {
Greg Claytonab65b342011-04-13 22:47:15 +0000972 llvm::StringRef name_sref(name);
973 Mutex::Locker locker (GetObjectFileMutex ());
974 ObjectFileInstances &instances = GetObjectFileInstances ();
975
976 ObjectFileInstances::iterator pos, end = instances.end();
977 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000978 {
Greg Claytonab65b342011-04-13 22:47:15 +0000979 if (name_sref.equals (pos->name))
980 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000981 }
982 }
983 return NULL;
984}
985
986
Greg Claytonc9660542012-02-05 02:38:54 +0000987ObjectFileCreateMemoryInstance
988PluginManager::GetObjectFileCreateMemoryCallbackForPluginName (const char *name)
989{
990 if (name && name[0])
991 {
992 llvm::StringRef name_sref(name);
993 Mutex::Locker locker (GetObjectFileMutex ());
994 ObjectFileInstances &instances = GetObjectFileInstances ();
995
996 ObjectFileInstances::iterator pos, end = instances.end();
997 for (pos = instances.begin(); pos != end; ++ pos)
998 {
999 if (name_sref.equals (pos->name))
1000 return pos->create_memory_callback;
1001 }
1002 }
1003 return NULL;
1004}
1005
1006
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001007
1008#pragma mark ObjectContainer
1009
Jason Molenda743e86a2010-06-11 23:44:18 +00001010struct ObjectContainerInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001011{
1012 ObjectContainerInstance() :
1013 name(),
1014 description(),
1015 create_callback(NULL)
1016 {
1017 }
1018
1019 std::string name;
1020 std::string description;
1021 ObjectContainerCreateInstance create_callback;
1022};
1023
1024typedef std::vector<ObjectContainerInstance> ObjectContainerInstances;
1025
Greg Claytonab65b342011-04-13 22:47:15 +00001026static Mutex &
1027GetObjectContainerMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001028{
Greg Claytonab65b342011-04-13 22:47:15 +00001029 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
1030 return g_instances_mutex;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001031}
1032
Greg Claytonab65b342011-04-13 22:47:15 +00001033static ObjectContainerInstances &
1034GetObjectContainerInstances ()
1035{
1036 static ObjectContainerInstances g_instances;
1037 return g_instances;
1038}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001039
1040bool
1041PluginManager::RegisterPlugin
1042(
1043 const char *name,
1044 const char *description,
1045 ObjectContainerCreateInstance create_callback
1046)
1047{
1048 if (create_callback)
1049 {
1050 ObjectContainerInstance instance;
1051 assert (name && name[0]);
1052 instance.name = name;
1053 if (description && description[0])
1054 instance.description = description;
1055 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +00001056 Mutex::Locker locker (GetObjectContainerMutex ());
1057 GetObjectContainerInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001058 }
1059 return false;
1060}
1061
1062bool
1063PluginManager::UnregisterPlugin (ObjectContainerCreateInstance create_callback)
1064{
1065 if (create_callback)
1066 {
Greg Claytonab65b342011-04-13 22:47:15 +00001067 Mutex::Locker locker (GetObjectContainerMutex ());
1068 ObjectContainerInstances &instances = GetObjectContainerInstances ();
1069
1070 ObjectContainerInstances::iterator pos, end = instances.end();
1071 for (pos = instances.begin(); pos != end; ++ pos)
1072 {
1073 if (pos->create_callback == create_callback)
1074 {
1075 instances.erase(pos);
1076 return true;
1077 }
1078 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001079 }
1080 return false;
1081}
1082
1083ObjectContainerCreateInstance
1084PluginManager::GetObjectContainerCreateCallbackAtIndex (uint32_t idx)
1085{
Greg Claytonab65b342011-04-13 22:47:15 +00001086 Mutex::Locker locker (GetObjectContainerMutex ());
1087 ObjectContainerInstances &instances = GetObjectContainerInstances ();
1088 if (idx < instances.size())
1089 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +00001090 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001091}
Greg Claytonab65b342011-04-13 22:47:15 +00001092
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001093ObjectContainerCreateInstance
1094PluginManager::GetObjectContainerCreateCallbackForPluginName (const char *name)
1095{
1096 if (name && name[0])
1097 {
Greg Claytonab65b342011-04-13 22:47:15 +00001098 llvm::StringRef name_sref(name);
1099 Mutex::Locker locker (GetObjectContainerMutex ());
1100 ObjectContainerInstances &instances = GetObjectContainerInstances ();
1101
1102 ObjectContainerInstances::iterator pos, end = instances.end();
1103 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001104 {
Greg Claytonab65b342011-04-13 22:47:15 +00001105 if (name_sref.equals (pos->name))
1106 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001107 }
1108 }
1109 return NULL;
1110}
1111
1112#pragma mark LogChannel
1113
Greg Claytonab65b342011-04-13 22:47:15 +00001114struct LogInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001115{
Greg Claytonab65b342011-04-13 22:47:15 +00001116 LogInstance() :
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001117 name(),
1118 description(),
1119 create_callback(NULL)
1120 {
1121 }
1122
1123 std::string name;
1124 std::string description;
1125 LogChannelCreateInstance create_callback;
1126};
1127
Greg Claytonab65b342011-04-13 22:47:15 +00001128typedef std::vector<LogInstance> LogInstances;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001129
Greg Claytonab65b342011-04-13 22:47:15 +00001130static Mutex &
1131GetLogMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001132{
Greg Claytonab65b342011-04-13 22:47:15 +00001133 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
1134 return g_instances_mutex;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001135}
1136
Greg Claytonab65b342011-04-13 22:47:15 +00001137static LogInstances &
1138GetLogInstances ()
1139{
1140 static LogInstances g_instances;
1141 return g_instances;
1142}
1143
1144
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001145
1146bool
1147PluginManager::RegisterPlugin
1148(
1149 const char *name,
1150 const char *description,
1151 LogChannelCreateInstance create_callback
1152)
1153{
1154 if (create_callback)
1155 {
Greg Claytonab65b342011-04-13 22:47:15 +00001156 LogInstance instance;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001157 assert (name && name[0]);
1158 instance.name = name;
1159 if (description && description[0])
1160 instance.description = description;
1161 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +00001162 Mutex::Locker locker (GetLogMutex ());
1163 GetLogInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001164 }
1165 return false;
1166}
1167
1168bool
1169PluginManager::UnregisterPlugin (LogChannelCreateInstance create_callback)
1170{
1171 if (create_callback)
1172 {
Greg Claytonab65b342011-04-13 22:47:15 +00001173 Mutex::Locker locker (GetLogMutex ());
1174 LogInstances &instances = GetLogInstances ();
1175
1176 LogInstances::iterator pos, end = instances.end();
1177 for (pos = instances.begin(); pos != end; ++ pos)
1178 {
1179 if (pos->create_callback == create_callback)
1180 {
1181 instances.erase(pos);
1182 return true;
1183 }
1184 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001185 }
1186 return false;
1187}
1188
1189const char *
1190PluginManager::GetLogChannelCreateNameAtIndex (uint32_t idx)
1191{
Greg Claytonab65b342011-04-13 22:47:15 +00001192 Mutex::Locker locker (GetLogMutex ());
1193 LogInstances &instances = GetLogInstances ();
1194 if (idx < instances.size())
1195 return instances[idx].name.c_str();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001196 return NULL;
1197}
1198
1199
1200LogChannelCreateInstance
1201PluginManager::GetLogChannelCreateCallbackAtIndex (uint32_t idx)
1202{
Greg Claytonab65b342011-04-13 22:47:15 +00001203 Mutex::Locker locker (GetLogMutex ());
1204 LogInstances &instances = GetLogInstances ();
1205 if (idx < instances.size())
1206 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +00001207 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001208}
1209
1210LogChannelCreateInstance
1211PluginManager::GetLogChannelCreateCallbackForPluginName (const char *name)
1212{
1213 if (name && name[0])
1214 {
Greg Claytonab65b342011-04-13 22:47:15 +00001215 llvm::StringRef name_sref(name);
1216 Mutex::Locker locker (GetLogMutex ());
1217 LogInstances &instances = GetLogInstances ();
1218
1219 LogInstances::iterator pos, end = instances.end();
1220 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001221 {
Greg Claytonab65b342011-04-13 22:47:15 +00001222 if (name_sref.equals (pos->name))
1223 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001224 }
1225 }
1226 return NULL;
1227}
1228
Greg Claytone996fd32011-03-08 22:40:15 +00001229#pragma mark Platform
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001230
Greg Claytone996fd32011-03-08 22:40:15 +00001231struct PlatformInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001232{
Greg Claytone996fd32011-03-08 22:40:15 +00001233 PlatformInstance() :
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001234 name(),
1235 description(),
Jason Molenda9b837a12013-04-05 05:06:39 +00001236 create_callback(NULL),
1237 debugger_init_callback (NULL)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001238 {
1239 }
Greg Claytone996fd32011-03-08 22:40:15 +00001240
1241 std::string name;
1242 std::string description;
1243 PlatformCreateInstance create_callback;
Jason Molenda9b837a12013-04-05 05:06:39 +00001244 DebuggerInitializeCallback debugger_init_callback;
Greg Claytone996fd32011-03-08 22:40:15 +00001245};
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001246
Greg Claytone996fd32011-03-08 22:40:15 +00001247typedef std::vector<PlatformInstance> PlatformInstances;
1248
Greg Claytonded470d2011-03-19 01:12:21 +00001249static Mutex &
1250GetPlatformInstancesMutex ()
Greg Claytone996fd32011-03-08 22:40:15 +00001251{
Greg Claytonded470d2011-03-19 01:12:21 +00001252 static Mutex g_platform_instances_mutex (Mutex::eMutexTypeRecursive);
1253 return g_platform_instances_mutex;
Greg Claytone996fd32011-03-08 22:40:15 +00001254}
1255
Greg Claytonded470d2011-03-19 01:12:21 +00001256static PlatformInstances &
1257GetPlatformInstances ()
1258{
1259 static PlatformInstances g_platform_instances;
1260 return g_platform_instances;
1261}
Greg Claytone996fd32011-03-08 22:40:15 +00001262
Greg Claytonab65b342011-04-13 22:47:15 +00001263
Greg Claytone996fd32011-03-08 22:40:15 +00001264bool
1265PluginManager::RegisterPlugin (const char *name,
1266 const char *description,
Jason Molenda9b837a12013-04-05 05:06:39 +00001267 PlatformCreateInstance create_callback,
1268 DebuggerInitializeCallback debugger_init_callback)
Greg Claytone996fd32011-03-08 22:40:15 +00001269{
1270 if (create_callback)
1271 {
Greg Claytonded470d2011-03-19 01:12:21 +00001272 Mutex::Locker locker (GetPlatformInstancesMutex ());
1273
Greg Claytone996fd32011-03-08 22:40:15 +00001274 PlatformInstance instance;
1275 assert (name && name[0]);
1276 instance.name = name;
1277 if (description && description[0])
1278 instance.description = description;
1279 instance.create_callback = create_callback;
Jason Molenda9b837a12013-04-05 05:06:39 +00001280 instance.debugger_init_callback = debugger_init_callback;
Greg Claytonded470d2011-03-19 01:12:21 +00001281 GetPlatformInstances ().push_back (instance);
1282 return true;
Greg Claytone996fd32011-03-08 22:40:15 +00001283 }
1284 return false;
1285}
1286
Jason Molenda9b837a12013-04-05 05:06:39 +00001287
Greg Claytone996fd32011-03-08 22:40:15 +00001288const char *
1289PluginManager::GetPlatformPluginNameAtIndex (uint32_t idx)
1290{
Greg Claytonded470d2011-03-19 01:12:21 +00001291 Mutex::Locker locker (GetPlatformInstancesMutex ());
Greg Claytonab65b342011-04-13 22:47:15 +00001292 PlatformInstances &instances = GetPlatformInstances ();
1293 if (idx < instances.size())
1294 return instances[idx].name.c_str();
Greg Claytone996fd32011-03-08 22:40:15 +00001295 return NULL;
1296}
1297
1298const char *
1299PluginManager::GetPlatformPluginDescriptionAtIndex (uint32_t idx)
1300{
Greg Claytonded470d2011-03-19 01:12:21 +00001301 Mutex::Locker locker (GetPlatformInstancesMutex ());
Greg Claytonab65b342011-04-13 22:47:15 +00001302 PlatformInstances &instances = GetPlatformInstances ();
1303 if (idx < instances.size())
1304 return instances[idx].description.c_str();
Greg Claytone996fd32011-03-08 22:40:15 +00001305 return NULL;
1306}
1307
1308bool
1309PluginManager::UnregisterPlugin (PlatformCreateInstance create_callback)
1310{
1311 if (create_callback)
1312 {
Greg Claytonded470d2011-03-19 01:12:21 +00001313 Mutex::Locker locker (GetPlatformInstancesMutex ());
Greg Claytonab65b342011-04-13 22:47:15 +00001314 PlatformInstances &instances = GetPlatformInstances ();
Greg Claytonded470d2011-03-19 01:12:21 +00001315
Greg Claytonab65b342011-04-13 22:47:15 +00001316 PlatformInstances::iterator pos, end = instances.end();
1317 for (pos = instances.begin(); pos != end; ++ pos)
Greg Claytonded470d2011-03-19 01:12:21 +00001318 {
1319 if (pos->create_callback == create_callback)
1320 {
Greg Claytonab65b342011-04-13 22:47:15 +00001321 instances.erase(pos);
Greg Claytonded470d2011-03-19 01:12:21 +00001322 return true;
1323 }
1324 }
Greg Claytone996fd32011-03-08 22:40:15 +00001325 }
1326 return false;
1327}
1328
1329PlatformCreateInstance
1330PluginManager::GetPlatformCreateCallbackAtIndex (uint32_t idx)
1331{
Greg Claytonded470d2011-03-19 01:12:21 +00001332 Mutex::Locker locker (GetPlatformInstancesMutex ());
Greg Claytonab65b342011-04-13 22:47:15 +00001333 PlatformInstances &instances = GetPlatformInstances ();
1334 if (idx < instances.size())
1335 return instances[idx].create_callback;
Greg Claytone996fd32011-03-08 22:40:15 +00001336 return NULL;
1337}
1338
1339PlatformCreateInstance
1340PluginManager::GetPlatformCreateCallbackForPluginName (const char *name)
1341{
1342 if (name && name[0])
1343 {
Greg Claytonded470d2011-03-19 01:12:21 +00001344 Mutex::Locker locker (GetPlatformInstancesMutex ());
Greg Claytonab65b342011-04-13 22:47:15 +00001345 PlatformInstances &instances = GetPlatformInstances ();
1346 llvm::StringRef name_sref(name);
Greg Claytonded470d2011-03-19 01:12:21 +00001347
Greg Claytonab65b342011-04-13 22:47:15 +00001348 PlatformInstances::iterator pos, end = instances.end();
1349 for (pos = instances.begin(); pos != end; ++ pos)
Greg Claytone996fd32011-03-08 22:40:15 +00001350 {
Greg Clayton7260f622011-04-18 08:33:37 +00001351 if (name_sref.equals (pos->name))
Greg Claytonded470d2011-03-19 01:12:21 +00001352 return pos->create_callback;
Greg Claytone996fd32011-03-08 22:40:15 +00001353 }
1354 }
1355 return NULL;
1356}
1357
Greg Claytonc7bece562013-01-25 18:06:21 +00001358size_t
Greg Claytonab65b342011-04-13 22:47:15 +00001359PluginManager::AutoCompletePlatformName (const char *name, StringList &matches)
1360{
1361 if (name && name[0])
1362 {
1363 Mutex::Locker locker (GetPlatformInstancesMutex ());
1364 PlatformInstances &instances = GetPlatformInstances ();
1365 llvm::StringRef name_sref(name);
1366
1367 PlatformInstances::iterator pos, end = instances.end();
1368 for (pos = instances.begin(); pos != end; ++ pos)
1369 {
Greg Clayton7260f622011-04-18 08:33:37 +00001370 llvm::StringRef plugin_name (pos->name);
1371 if (plugin_name.startswith(name_sref))
1372 matches.AppendString (plugin_name.data());
Greg Claytonab65b342011-04-13 22:47:15 +00001373 }
1374 }
1375 return matches.GetSize();
1376}
Greg Claytone996fd32011-03-08 22:40:15 +00001377#pragma mark Process
1378
1379struct ProcessInstance
1380{
1381 ProcessInstance() :
1382 name(),
1383 description(),
1384 create_callback(NULL)
1385 {
1386 }
1387
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001388 std::string name;
1389 std::string description;
1390 ProcessCreateInstance create_callback;
1391};
1392
1393typedef std::vector<ProcessInstance> ProcessInstances;
1394
Greg Claytonab65b342011-04-13 22:47:15 +00001395static Mutex &
1396GetProcessMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001397{
Greg Claytonab65b342011-04-13 22:47:15 +00001398 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
1399 return g_instances_mutex;
1400}
1401
1402static ProcessInstances &
1403GetProcessInstances ()
1404{
1405 static ProcessInstances g_instances;
1406 return g_instances;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001407}
1408
1409
1410bool
1411PluginManager::RegisterPlugin
1412(
Greg Claytone996fd32011-03-08 22:40:15 +00001413 const char *name,
1414 const char *description,
1415 ProcessCreateInstance create_callback
1416 )
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001417{
1418 if (create_callback)
1419 {
1420 ProcessInstance instance;
1421 assert (name && name[0]);
1422 instance.name = name;
1423 if (description && description[0])
1424 instance.description = description;
1425 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +00001426 Mutex::Locker locker (GetProcessMutex ());
1427 GetProcessInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001428 }
1429 return false;
1430}
1431
Greg Claytonbfe5f3b2011-02-18 01:44:25 +00001432const char *
1433PluginManager::GetProcessPluginNameAtIndex (uint32_t idx)
1434{
Greg Claytonab65b342011-04-13 22:47:15 +00001435 Mutex::Locker locker (GetProcessMutex ());
1436 ProcessInstances &instances = GetProcessInstances ();
1437 if (idx < instances.size())
1438 return instances[idx].name.c_str();
Greg Claytonbfe5f3b2011-02-18 01:44:25 +00001439 return NULL;
1440}
1441
1442const char *
1443PluginManager::GetProcessPluginDescriptionAtIndex (uint32_t idx)
1444{
Greg Claytonab65b342011-04-13 22:47:15 +00001445 Mutex::Locker locker (GetProcessMutex ());
1446 ProcessInstances &instances = GetProcessInstances ();
1447 if (idx < instances.size())
1448 return instances[idx].description.c_str();
Greg Claytonbfe5f3b2011-02-18 01:44:25 +00001449 return NULL;
1450}
1451
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001452bool
1453PluginManager::UnregisterPlugin (ProcessCreateInstance create_callback)
1454{
1455 if (create_callback)
1456 {
Greg Claytonab65b342011-04-13 22:47:15 +00001457 Mutex::Locker locker (GetProcessMutex ());
1458 ProcessInstances &instances = GetProcessInstances ();
1459
1460 ProcessInstances::iterator pos, end = instances.end();
1461 for (pos = instances.begin(); pos != end; ++ pos)
1462 {
1463 if (pos->create_callback == create_callback)
1464 {
1465 instances.erase(pos);
1466 return true;
1467 }
1468 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001469 }
1470 return false;
1471}
1472
1473ProcessCreateInstance
1474PluginManager::GetProcessCreateCallbackAtIndex (uint32_t idx)
1475{
Greg Claytonab65b342011-04-13 22:47:15 +00001476 Mutex::Locker locker (GetProcessMutex ());
1477 ProcessInstances &instances = GetProcessInstances ();
1478 if (idx < instances.size())
1479 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +00001480 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001481}
1482
Greg Claytonab65b342011-04-13 22:47:15 +00001483
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001484ProcessCreateInstance
1485PluginManager::GetProcessCreateCallbackForPluginName (const char *name)
1486{
1487 if (name && name[0])
1488 {
Greg Claytonab65b342011-04-13 22:47:15 +00001489 llvm::StringRef name_sref(name);
1490 Mutex::Locker locker (GetProcessMutex ());
1491 ProcessInstances &instances = GetProcessInstances ();
1492
1493 ProcessInstances::iterator pos, end = instances.end();
1494 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001495 {
Greg Claytonab65b342011-04-13 22:47:15 +00001496 if (name_sref.equals (pos->name))
1497 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001498 }
1499 }
1500 return NULL;
1501}
1502
1503#pragma mark SymbolFile
1504
Jason Molenda743e86a2010-06-11 23:44:18 +00001505struct SymbolFileInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001506{
1507 SymbolFileInstance() :
1508 name(),
1509 description(),
1510 create_callback(NULL)
1511 {
1512 }
1513
1514 std::string name;
1515 std::string description;
1516 SymbolFileCreateInstance create_callback;
1517};
1518
1519typedef std::vector<SymbolFileInstance> SymbolFileInstances;
1520
Greg Claytonab65b342011-04-13 22:47:15 +00001521static Mutex &
1522GetSymbolFileMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001523{
Greg Claytonab65b342011-04-13 22:47:15 +00001524 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
1525 return g_instances_mutex;
1526}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001527
Greg Claytonab65b342011-04-13 22:47:15 +00001528static SymbolFileInstances &
1529GetSymbolFileInstances ()
1530{
1531 static SymbolFileInstances g_instances;
1532 return g_instances;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001533}
1534
1535
1536bool
1537PluginManager::RegisterPlugin
1538(
1539 const char *name,
1540 const char *description,
1541 SymbolFileCreateInstance create_callback
1542)
1543{
1544 if (create_callback)
1545 {
1546 SymbolFileInstance instance;
1547 assert (name && name[0]);
1548 instance.name = name;
1549 if (description && description[0])
1550 instance.description = description;
1551 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +00001552 Mutex::Locker locker (GetSymbolFileMutex ());
1553 GetSymbolFileInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001554 }
1555 return false;
1556}
1557
1558bool
1559PluginManager::UnregisterPlugin (SymbolFileCreateInstance create_callback)
1560{
1561 if (create_callback)
1562 {
Greg Claytonab65b342011-04-13 22:47:15 +00001563 Mutex::Locker locker (GetSymbolFileMutex ());
1564 SymbolFileInstances &instances = GetSymbolFileInstances ();
1565
1566 SymbolFileInstances::iterator pos, end = instances.end();
1567 for (pos = instances.begin(); pos != end; ++ pos)
1568 {
1569 if (pos->create_callback == create_callback)
1570 {
1571 instances.erase(pos);
1572 return true;
1573 }
1574 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001575 }
1576 return false;
1577}
1578
1579SymbolFileCreateInstance
1580PluginManager::GetSymbolFileCreateCallbackAtIndex (uint32_t idx)
1581{
Greg Claytonab65b342011-04-13 22:47:15 +00001582 Mutex::Locker locker (GetSymbolFileMutex ());
1583 SymbolFileInstances &instances = GetSymbolFileInstances ();
1584 if (idx < instances.size())
1585 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +00001586 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001587}
Greg Claytonab65b342011-04-13 22:47:15 +00001588
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001589SymbolFileCreateInstance
1590PluginManager::GetSymbolFileCreateCallbackForPluginName (const char *name)
1591{
1592 if (name && name[0])
1593 {
Greg Claytonab65b342011-04-13 22:47:15 +00001594 llvm::StringRef name_sref(name);
1595 Mutex::Locker locker (GetSymbolFileMutex ());
1596 SymbolFileInstances &instances = GetSymbolFileInstances ();
1597
1598 SymbolFileInstances::iterator pos, end = instances.end();
1599 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001600 {
Greg Claytonab65b342011-04-13 22:47:15 +00001601 if (name_sref.equals (pos->name))
1602 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001603 }
1604 }
1605 return NULL;
1606}
1607
1608
1609
1610#pragma mark SymbolVendor
1611
Jason Molenda743e86a2010-06-11 23:44:18 +00001612struct SymbolVendorInstance
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001613{
1614 SymbolVendorInstance() :
1615 name(),
1616 description(),
1617 create_callback(NULL)
1618 {
1619 }
1620
1621 std::string name;
1622 std::string description;
1623 SymbolVendorCreateInstance create_callback;
1624};
1625
1626typedef std::vector<SymbolVendorInstance> SymbolVendorInstances;
1627
Greg Claytonab65b342011-04-13 22:47:15 +00001628static Mutex &
1629GetSymbolVendorMutex ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001630{
Greg Claytonab65b342011-04-13 22:47:15 +00001631 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
1632 return g_instances_mutex;
1633}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001634
Greg Claytonab65b342011-04-13 22:47:15 +00001635static SymbolVendorInstances &
1636GetSymbolVendorInstances ()
1637{
1638 static SymbolVendorInstances g_instances;
1639 return g_instances;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001640}
1641
1642bool
1643PluginManager::RegisterPlugin
1644(
1645 const char *name,
1646 const char *description,
1647 SymbolVendorCreateInstance create_callback
1648)
1649{
1650 if (create_callback)
1651 {
1652 SymbolVendorInstance instance;
1653 assert (name && name[0]);
1654 instance.name = name;
1655 if (description && description[0])
1656 instance.description = description;
1657 instance.create_callback = create_callback;
Greg Claytonab65b342011-04-13 22:47:15 +00001658 Mutex::Locker locker (GetSymbolVendorMutex ());
1659 GetSymbolVendorInstances ().push_back (instance);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001660 }
1661 return false;
1662}
1663
1664bool
1665PluginManager::UnregisterPlugin (SymbolVendorCreateInstance create_callback)
1666{
1667 if (create_callback)
1668 {
Greg Claytonab65b342011-04-13 22:47:15 +00001669 Mutex::Locker locker (GetSymbolVendorMutex ());
1670 SymbolVendorInstances &instances = GetSymbolVendorInstances ();
1671
1672 SymbolVendorInstances::iterator pos, end = instances.end();
1673 for (pos = instances.begin(); pos != end; ++ pos)
1674 {
1675 if (pos->create_callback == create_callback)
1676 {
1677 instances.erase(pos);
1678 return true;
1679 }
1680 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001681 }
1682 return false;
1683}
1684
1685SymbolVendorCreateInstance
1686PluginManager::GetSymbolVendorCreateCallbackAtIndex (uint32_t idx)
1687{
Greg Claytonab65b342011-04-13 22:47:15 +00001688 Mutex::Locker locker (GetSymbolVendorMutex ());
1689 SymbolVendorInstances &instances = GetSymbolVendorInstances ();
1690 if (idx < instances.size())
1691 return instances[idx].create_callback;
Jason Molenda743e86a2010-06-11 23:44:18 +00001692 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001693}
1694
Greg Claytonab65b342011-04-13 22:47:15 +00001695
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001696SymbolVendorCreateInstance
1697PluginManager::GetSymbolVendorCreateCallbackForPluginName (const char *name)
1698{
1699 if (name && name[0])
1700 {
Greg Claytonab65b342011-04-13 22:47:15 +00001701 llvm::StringRef name_sref(name);
1702 Mutex::Locker locker (GetSymbolVendorMutex ());
1703 SymbolVendorInstances &instances = GetSymbolVendorInstances ();
1704
1705 SymbolVendorInstances::iterator pos, end = instances.end();
1706 for (pos = instances.begin(); pos != end; ++ pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001707 {
Greg Claytonab65b342011-04-13 22:47:15 +00001708 if (name_sref.equals (pos->name))
1709 return pos->create_callback;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001710 }
1711 }
1712 return NULL;
1713}
1714
1715
Greg Clayton7be25422011-04-25 21:14:26 +00001716#pragma mark UnwindAssembly
Jason Molendafbcb7f22010-09-10 07:49:16 +00001717
Greg Clayton7be25422011-04-25 21:14:26 +00001718struct UnwindAssemblyInstance
Jason Molendafbcb7f22010-09-10 07:49:16 +00001719{
Greg Clayton7be25422011-04-25 21:14:26 +00001720 UnwindAssemblyInstance() :
Jason Molendafbcb7f22010-09-10 07:49:16 +00001721 name(),
1722 description(),
1723 create_callback(NULL)
1724 {
1725 }
1726
1727 std::string name;
1728 std::string description;
Greg Clayton7be25422011-04-25 21:14:26 +00001729 UnwindAssemblyCreateInstance create_callback;
Jason Molendafbcb7f22010-09-10 07:49:16 +00001730};
1731
Greg Clayton7be25422011-04-25 21:14:26 +00001732typedef std::vector<UnwindAssemblyInstance> UnwindAssemblyInstances;
Jason Molendafbcb7f22010-09-10 07:49:16 +00001733
Greg Claytonab65b342011-04-13 22:47:15 +00001734static Mutex &
Greg Clayton7be25422011-04-25 21:14:26 +00001735GetUnwindAssemblyMutex ()
Jason Molendafbcb7f22010-09-10 07:49:16 +00001736{
Greg Claytonab65b342011-04-13 22:47:15 +00001737 static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive);
1738 return g_instances_mutex;
1739}
Jason Molendafbcb7f22010-09-10 07:49:16 +00001740
Greg Clayton7be25422011-04-25 21:14:26 +00001741static UnwindAssemblyInstances &
1742GetUnwindAssemblyInstances ()
Greg Claytonab65b342011-04-13 22:47:15 +00001743{
Greg Clayton7be25422011-04-25 21:14:26 +00001744 static UnwindAssemblyInstances g_instances;
Greg Claytonab65b342011-04-13 22:47:15 +00001745 return g_instances;
Jason Molendafbcb7f22010-09-10 07:49:16 +00001746}
1747
1748bool
1749PluginManager::RegisterPlugin
1750(
1751 const char *name,
1752 const char *description,
Greg Clayton7be25422011-04-25 21:14:26 +00001753 UnwindAssemblyCreateInstance create_callback
Jason Molendafbcb7f22010-09-10 07:49:16 +00001754)
1755{
1756 if (create_callback)
1757 {
Greg Clayton7be25422011-04-25 21:14:26 +00001758 UnwindAssemblyInstance instance;
Jason Molendafbcb7f22010-09-10 07:49:16 +00001759 assert (name && name[0]);
1760 instance.name = name;
1761 if (description && description[0])
1762 instance.description = description;
1763 instance.create_callback = create_callback;
Greg Clayton7be25422011-04-25 21:14:26 +00001764 Mutex::Locker locker (GetUnwindAssemblyMutex ());
1765 GetUnwindAssemblyInstances ().push_back (instance);
Jason Molendafbcb7f22010-09-10 07:49:16 +00001766 }
1767 return false;
1768}
1769
1770bool
Greg Clayton7be25422011-04-25 21:14:26 +00001771PluginManager::UnregisterPlugin (UnwindAssemblyCreateInstance create_callback)
Jason Molendafbcb7f22010-09-10 07:49:16 +00001772{
1773 if (create_callback)
1774 {
Greg Clayton7be25422011-04-25 21:14:26 +00001775 Mutex::Locker locker (GetUnwindAssemblyMutex ());
1776 UnwindAssemblyInstances &instances = GetUnwindAssemblyInstances ();
Greg Claytonab65b342011-04-13 22:47:15 +00001777
Greg Clayton7be25422011-04-25 21:14:26 +00001778 UnwindAssemblyInstances::iterator pos, end = instances.end();
Greg Claytonab65b342011-04-13 22:47:15 +00001779 for (pos = instances.begin(); pos != end; ++ pos)
1780 {
1781 if (pos->create_callback == create_callback)
1782 {
1783 instances.erase(pos);
1784 return true;
1785 }
1786 }
Jason Molendafbcb7f22010-09-10 07:49:16 +00001787 }
1788 return false;
1789}
1790
Greg Clayton7be25422011-04-25 21:14:26 +00001791UnwindAssemblyCreateInstance
1792PluginManager::GetUnwindAssemblyCreateCallbackAtIndex (uint32_t idx)
Jason Molendafbcb7f22010-09-10 07:49:16 +00001793{
Greg Clayton7be25422011-04-25 21:14:26 +00001794 Mutex::Locker locker (GetUnwindAssemblyMutex ());
1795 UnwindAssemblyInstances &instances = GetUnwindAssemblyInstances ();
Greg Claytonab65b342011-04-13 22:47:15 +00001796 if (idx < instances.size())
1797 return instances[idx].create_callback;
Jason Molendafbcb7f22010-09-10 07:49:16 +00001798 return NULL;
1799}
1800
Greg Claytonab65b342011-04-13 22:47:15 +00001801
Greg Clayton7be25422011-04-25 21:14:26 +00001802UnwindAssemblyCreateInstance
1803PluginManager::GetUnwindAssemblyCreateCallbackForPluginName (const char *name)
Jason Molendafbcb7f22010-09-10 07:49:16 +00001804{
1805 if (name && name[0])
1806 {
Greg Claytonab65b342011-04-13 22:47:15 +00001807 llvm::StringRef name_sref(name);
Greg Clayton7be25422011-04-25 21:14:26 +00001808 Mutex::Locker locker (GetUnwindAssemblyMutex ());
1809 UnwindAssemblyInstances &instances = GetUnwindAssemblyInstances ();
Greg Claytonab65b342011-04-13 22:47:15 +00001810
Greg Clayton7be25422011-04-25 21:14:26 +00001811 UnwindAssemblyInstances::iterator pos, end = instances.end();
Greg Claytonab65b342011-04-13 22:47:15 +00001812 for (pos = instances.begin(); pos != end; ++ pos)
Jason Molendafbcb7f22010-09-10 07:49:16 +00001813 {
Greg Claytonab65b342011-04-13 22:47:15 +00001814 if (name_sref.equals (pos->name))
1815 return pos->create_callback;
Jason Molendafbcb7f22010-09-10 07:49:16 +00001816 }
1817 }
1818 return NULL;
1819}
1820
Greg Claytone8cd0c92012-10-19 18:02:49 +00001821void
1822PluginManager::DebuggerInitialize (Debugger &debugger)
1823{
Jason Molenda9b837a12013-04-05 05:06:39 +00001824 // Initialize the DynamicLoader plugins
Greg Claytone8cd0c92012-10-19 18:02:49 +00001825 {
Jason Molenda9b837a12013-04-05 05:06:39 +00001826 Mutex::Locker locker (GetDynamicLoaderMutex ());
1827 DynamicLoaderInstances &instances = GetDynamicLoaderInstances ();
1828
1829 DynamicLoaderInstances::iterator pos, end = instances.end();
1830 for (pos = instances.begin(); pos != end; ++ pos)
1831 {
1832 if (pos->debugger_init_callback)
1833 pos->debugger_init_callback (debugger);
1834 }
1835 }
1836
1837 // Initialize the Platform plugins
1838 {
1839 Mutex::Locker locker (GetPlatformInstancesMutex ());
1840 PlatformInstances &instances = GetPlatformInstances ();
1841
1842 PlatformInstances::iterator pos, end = instances.end();
1843 for (pos = instances.begin(); pos != end; ++ pos)
1844 {
1845 if (pos->debugger_init_callback)
1846 pos->debugger_init_callback (debugger);
1847 }
Greg Claytone8cd0c92012-10-19 18:02:49 +00001848 }
1849}
1850
Jason Molenda3b59f5c2013-04-05 22:40:42 +00001851// This will put a plugin's settings under e.g. "plugin.dynamic-loader.darwin-kernel.SETTINGNAME".
1852// The new preferred ordering is to put plugins under "dynamic-loader.plugin.darwin-kernel.SETTINGNAME"
1853// and if there were a generic dynamic-loader setting, it would be "dynamic-loader.SETTINGNAME".
Greg Claytone8cd0c92012-10-19 18:02:49 +00001854static lldb::OptionValuePropertiesSP
Jason Molenda3b59f5c2013-04-05 22:40:42 +00001855GetDebuggerPropertyForPluginsOldStyle (Debugger &debugger,
1856 const ConstString &plugin_type_name,
1857 const ConstString &plugin_type_desc,
1858 bool can_create)
Greg Claytone8cd0c92012-10-19 18:02:49 +00001859{
1860 lldb::OptionValuePropertiesSP parent_properties_sp (debugger.GetValueProperties());
1861 if (parent_properties_sp)
1862 {
1863 static ConstString g_property_name("plugin");
1864
1865 OptionValuePropertiesSP plugin_properties_sp = parent_properties_sp->GetSubProperty (NULL, g_property_name);
1866 if (!plugin_properties_sp && can_create)
1867 {
1868 plugin_properties_sp.reset (new OptionValueProperties (g_property_name));
1869 parent_properties_sp->AppendProperty (g_property_name,
1870 ConstString("Settings specify to plugins."),
1871 true,
1872 plugin_properties_sp);
1873 }
1874
1875 if (plugin_properties_sp)
1876 {
1877 lldb::OptionValuePropertiesSP plugin_type_properties_sp = plugin_properties_sp->GetSubProperty (NULL, plugin_type_name);
1878 if (!plugin_type_properties_sp && can_create)
1879 {
1880 plugin_type_properties_sp.reset (new OptionValueProperties (plugin_type_name));
1881 plugin_properties_sp->AppendProperty (plugin_type_name,
1882 plugin_type_desc,
1883 true,
1884 plugin_type_properties_sp);
1885 }
1886 return plugin_type_properties_sp;
1887 }
1888 }
1889 return lldb::OptionValuePropertiesSP();
1890}
1891
Jason Molenda3b59f5c2013-04-05 22:40:42 +00001892// This is the preferred new way to register plugin specific settings. e.g.
1893// "platform.plugin.darwin-kernel.SETTINGNAME"
1894// and Platform generic settings would be under "platform.SETTINGNAME".
1895static lldb::OptionValuePropertiesSP
1896GetDebuggerPropertyForPlugins (Debugger &debugger,
1897 const ConstString &plugin_type_name,
1898 const ConstString &plugin_type_desc,
1899 bool can_create)
1900{
1901 static ConstString g_property_name("plugin");
1902 lldb::OptionValuePropertiesSP parent_properties_sp (debugger.GetValueProperties());
1903 if (parent_properties_sp)
1904 {
1905 OptionValuePropertiesSP plugin_properties_sp = parent_properties_sp->GetSubProperty (NULL, plugin_type_name);
1906 if (!plugin_properties_sp && can_create)
1907 {
1908 plugin_properties_sp.reset (new OptionValueProperties (plugin_type_name));
1909 parent_properties_sp->AppendProperty (plugin_type_name,
1910 plugin_type_desc,
1911 true,
1912 plugin_properties_sp);
1913 }
1914
1915 if (plugin_properties_sp)
1916 {
1917 lldb::OptionValuePropertiesSP plugin_type_properties_sp = plugin_properties_sp->GetSubProperty (NULL, g_property_name);
1918 if (!plugin_type_properties_sp && can_create)
1919 {
1920 plugin_type_properties_sp.reset (new OptionValueProperties (g_property_name));
1921 plugin_properties_sp->AppendProperty (g_property_name,
1922 ConstString("Settings specific to plugins"),
1923 true,
1924 plugin_type_properties_sp);
1925 }
1926 return plugin_type_properties_sp;
1927 }
1928 }
1929 return lldb::OptionValuePropertiesSP();
1930}
1931
1932
Greg Claytone8cd0c92012-10-19 18:02:49 +00001933lldb::OptionValuePropertiesSP
1934PluginManager::GetSettingForDynamicLoaderPlugin (Debugger &debugger, const ConstString &setting_name)
1935{
1936 lldb::OptionValuePropertiesSP properties_sp;
Jason Molenda3b59f5c2013-04-05 22:40:42 +00001937 lldb::OptionValuePropertiesSP plugin_type_properties_sp (GetDebuggerPropertyForPluginsOldStyle (debugger,
Greg Claytone8cd0c92012-10-19 18:02:49 +00001938 ConstString("dynamic-loader"),
1939 ConstString(), // not creating to so we don't need the description
1940 false));
1941 if (plugin_type_properties_sp)
1942 properties_sp = plugin_type_properties_sp->GetSubProperty (NULL, setting_name);
1943 return properties_sp;
1944}
1945
1946bool
1947PluginManager::CreateSettingForDynamicLoaderPlugin (Debugger &debugger,
1948 const lldb::OptionValuePropertiesSP &properties_sp,
1949 const ConstString &description,
1950 bool is_global_property)
1951{
1952 if (properties_sp)
1953 {
Jason Molenda3b59f5c2013-04-05 22:40:42 +00001954 lldb::OptionValuePropertiesSP plugin_type_properties_sp (GetDebuggerPropertyForPluginsOldStyle (debugger,
Greg Claytone8cd0c92012-10-19 18:02:49 +00001955 ConstString("dynamic-loader"),
1956 ConstString("Settings for dynamic loader plug-ins"),
1957 true));
1958 if (plugin_type_properties_sp)
1959 {
1960 plugin_type_properties_sp->AppendProperty (properties_sp->GetName(),
1961 description,
1962 is_global_property,
1963 properties_sp);
1964 return true;
1965 }
1966 }
1967 return false;
1968}
1969
Jason Molenda9b837a12013-04-05 05:06:39 +00001970
1971lldb::OptionValuePropertiesSP
1972PluginManager::GetSettingForPlatformPlugin (Debugger &debugger, const ConstString &setting_name)
1973{
1974 lldb::OptionValuePropertiesSP properties_sp;
1975 lldb::OptionValuePropertiesSP plugin_type_properties_sp (GetDebuggerPropertyForPlugins (debugger,
1976 ConstString("platform"),
1977 ConstString(), // not creating to so we don't need the description
1978 false));
1979 if (plugin_type_properties_sp)
1980 properties_sp = plugin_type_properties_sp->GetSubProperty (NULL, setting_name);
1981 return properties_sp;
1982}
1983
1984bool
1985PluginManager::CreateSettingForPlatformPlugin (Debugger &debugger,
1986 const lldb::OptionValuePropertiesSP &properties_sp,
1987 const ConstString &description,
1988 bool is_global_property)
1989{
1990 if (properties_sp)
1991 {
1992 lldb::OptionValuePropertiesSP plugin_type_properties_sp (GetDebuggerPropertyForPlugins (debugger,
1993 ConstString("platform"),
1994 ConstString("Settings for platform plug-ins"),
1995 true));
1996 if (plugin_type_properties_sp)
1997 {
1998 plugin_type_properties_sp->AppendProperty (properties_sp->GetName(),
1999 description,
2000 is_global_property,
2001 properties_sp);
2002 return true;
2003 }
2004 }
2005 return false;
2006}
2007