blob: cf55db8d2433ed39869ec41a833c75d1c5692cc4 [file] [log] [blame]
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001//===-- ClangASTContext.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
Eli Friedman932197d2010-06-13 19:06:42 +000010#include "lldb/Symbol/ClangASTContext.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000011
12// C Includes
13// C++ Includes
14#include <string>
15
16// Other libraries and framework includes
Greg Clayton6beaaa62011-01-17 03:46:26 +000017
18// Clang headers like to use NDEBUG inside of them to enable/disable debug
19// releated features using "#ifndef NDEBUG" preprocessor blocks to do one thing
20// or another. This is bad because it means that if clang was built in release
21// mode, it assumes that you are building in release mode which is not always
22// the case. You can end up with functions that are defined as empty in header
23// files when NDEBUG is not defined, and this can cause link errors with the
24// clang .a files that you have since you might be missing functions in the .a
25// file. So we have to define NDEBUG when including clang headers to avoid any
26// mismatches. This is covered by rdar://problem/8691220
27
28#ifndef NDEBUG
29#define LLDB_DEFINED_NDEBUG_FOR_CLANG
Sean Callanan246549c2010-07-08 18:16:16 +000030#define NDEBUG
Greg Clayton6beaaa62011-01-17 03:46:26 +000031// Need to include assert.h so it is as clang would expect it to be (disabled)
32#include <assert.h>
33#endif
34
Chris Lattner30fdc8d2010-06-08 16:52:24 +000035#include "clang/AST/ASTContext.h"
36#include "clang/AST/ASTImporter.h"
37#include "clang/AST/CXXInheritance.h"
Greg Clayton8cf05932010-07-22 18:30:50 +000038#include "clang/AST/DeclObjC.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000039#include "clang/AST/RecordLayout.h"
40#include "clang/AST/Type.h"
41#include "clang/Basic/Builtins.h"
42#include "clang/Basic/FileManager.h"
Sean Callanan79439e82010-11-18 02:56:27 +000043#include "clang/Basic/FileSystemOptions.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000044#include "clang/Basic/SourceManager.h"
45#include "clang/Basic/TargetInfo.h"
46#include "clang/Basic/TargetOptions.h"
47#include "clang/Frontend/FrontendOptions.h"
48#include "clang/Frontend/LangStandard.h"
Greg Clayton6beaaa62011-01-17 03:46:26 +000049
50#ifdef LLDB_DEFINED_NDEBUG_FOR_CLANG
Sean Callanan246549c2010-07-08 18:16:16 +000051#undef NDEBUG
Greg Clayton6beaaa62011-01-17 03:46:26 +000052#undef LLDB_DEFINED_NDEBUG_FOR_CLANG
53// Need to re-include assert.h so it is as _we_ would expect it to be (enabled)
54#include <assert.h>
55#endif
Chris Lattner30fdc8d2010-06-08 16:52:24 +000056
Greg Clayton514487e2011-02-15 21:59:32 +000057#include "lldb/Core/ArchSpec.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000058#include "lldb/Core/dwarf.h"
Greg Clayton73b472d2010-10-27 03:32:59 +000059#include "lldb/Core/Flags.h"
Sean Callananfb8b7092010-10-28 18:19:36 +000060#include "lldb/Core/Log.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000061
Eli Friedman932197d2010-06-13 19:06:42 +000062#include <stdio.h>
63
Greg Claytonc86103d2010-08-05 01:57:25 +000064using namespace lldb;
Chris Lattner30fdc8d2010-06-08 16:52:24 +000065using namespace lldb_private;
66using namespace llvm;
67using namespace clang;
68
Greg Clayton6beaaa62011-01-17 03:46:26 +000069
70static bool
71GetCompleteQualType (clang::ASTContext *ast, clang::QualType qual_type)
72{
73 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
74 switch (type_class)
75 {
76 case clang::Type::Record:
77 case clang::Type::Enum:
78 {
Sean Callanan78e37602011-01-27 04:42:51 +000079 const clang::TagType *tag_type = dyn_cast<clang::TagType>(qual_type.getTypePtr());
Greg Clayton6beaaa62011-01-17 03:46:26 +000080 if (tag_type)
81 {
82 clang::TagDecl *tag_decl = tag_type->getDecl();
83 if (tag_decl)
84 {
85 if (tag_decl->getDefinition())
86 return true;
87
88 if (tag_decl->hasExternalLexicalStorage())
89 {
Greg Clayton007d5be2011-05-30 00:49:24 +000090 if (ast)
Greg Clayton6beaaa62011-01-17 03:46:26 +000091 {
Greg Clayton007d5be2011-05-30 00:49:24 +000092 ExternalASTSource *external_ast_source = ast->getExternalSource();
93 if (external_ast_source)
94 {
95 external_ast_source->CompleteType(tag_decl);
96 return !tag_type->isIncompleteType();
97 }
Greg Clayton6beaaa62011-01-17 03:46:26 +000098 }
99 }
100 return false;
101 }
102 }
103
104 }
105 break;
106
107 case clang::Type::ObjCObject:
108 case clang::Type::ObjCInterface:
109 {
Sean Callanan78e37602011-01-27 04:42:51 +0000110 const clang::ObjCObjectType *objc_class_type = dyn_cast<clang::ObjCObjectType>(qual_type);
Greg Clayton6beaaa62011-01-17 03:46:26 +0000111 if (objc_class_type)
112 {
113 clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
114 // We currently can't complete objective C types through the newly added ASTContext
115 // because it only supports TagDecl objects right now...
116 bool is_forward_decl = class_interface_decl->isForwardDecl();
117 if (is_forward_decl && class_interface_decl->hasExternalLexicalStorage())
118 {
Greg Clayton007d5be2011-05-30 00:49:24 +0000119 if (ast)
Greg Clayton6beaaa62011-01-17 03:46:26 +0000120 {
Greg Clayton007d5be2011-05-30 00:49:24 +0000121 ExternalASTSource *external_ast_source = ast->getExternalSource();
122 if (external_ast_source)
123 {
124 external_ast_source->CompleteType (class_interface_decl);
125 is_forward_decl = class_interface_decl->isForwardDecl();
126 }
Greg Clayton6beaaa62011-01-17 03:46:26 +0000127 }
Greg Claytonc432c192011-01-20 04:18:48 +0000128 return is_forward_decl == false;
Greg Clayton6beaaa62011-01-17 03:46:26 +0000129 }
Greg Claytonc432c192011-01-20 04:18:48 +0000130 return true;
Greg Clayton6beaaa62011-01-17 03:46:26 +0000131 }
132 }
133 break;
134
135 case clang::Type::Typedef:
136 return GetCompleteQualType (ast, cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType());
137
138 default:
139 break;
140 }
141
142 return true;
143}
144
145
Greg Clayton8cf05932010-07-22 18:30:50 +0000146static AccessSpecifier
Greg Claytonc86103d2010-08-05 01:57:25 +0000147ConvertAccessTypeToAccessSpecifier (AccessType access)
Greg Clayton8cf05932010-07-22 18:30:50 +0000148{
149 switch (access)
150 {
Greg Claytonc86103d2010-08-05 01:57:25 +0000151 default: break;
152 case eAccessNone: return AS_none;
153 case eAccessPublic: return AS_public;
154 case eAccessPrivate: return AS_private;
155 case eAccessProtected: return AS_protected;
Greg Clayton8cf05932010-07-22 18:30:50 +0000156 }
157 return AS_none;
158}
159
160static ObjCIvarDecl::AccessControl
Greg Claytonc86103d2010-08-05 01:57:25 +0000161ConvertAccessTypeToObjCIvarAccessControl (AccessType access)
Greg Clayton8cf05932010-07-22 18:30:50 +0000162{
163 switch (access)
164 {
Greg Claytonc86103d2010-08-05 01:57:25 +0000165 default: break;
166 case eAccessNone: return ObjCIvarDecl::None;
167 case eAccessPublic: return ObjCIvarDecl::Public;
168 case eAccessPrivate: return ObjCIvarDecl::Private;
169 case eAccessProtected: return ObjCIvarDecl::Protected;
170 case eAccessPackage: return ObjCIvarDecl::Package;
Greg Clayton8cf05932010-07-22 18:30:50 +0000171 }
172 return ObjCIvarDecl::None;
173}
174
175
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000176static void
177ParseLangArgs
178(
179 LangOptions &Opts,
Greg Clayton94e5d782010-06-13 17:34:29 +0000180 InputKind IK
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000181)
182{
183 // FIXME: Cleanup per-file based stuff.
184
185 // Set some properties which depend soley on the input kind; it would be nice
186 // to move these to the language standard, and have the driver resolve the
187 // input kind + language standard.
Greg Clayton94e5d782010-06-13 17:34:29 +0000188 if (IK == IK_Asm) {
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000189 Opts.AsmPreprocessor = 1;
Greg Clayton94e5d782010-06-13 17:34:29 +0000190 } else if (IK == IK_ObjC ||
191 IK == IK_ObjCXX ||
192 IK == IK_PreprocessedObjC ||
193 IK == IK_PreprocessedObjCXX) {
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000194 Opts.ObjC1 = Opts.ObjC2 = 1;
195 }
196
197 LangStandard::Kind LangStd = LangStandard::lang_unspecified;
198
199 if (LangStd == LangStandard::lang_unspecified) {
200 // Based on the base language, pick one.
201 switch (IK) {
Greg Clayton94e5d782010-06-13 17:34:29 +0000202 case IK_None:
203 case IK_AST:
Sean Callananfb0b7582011-03-15 00:17:19 +0000204 case IK_LLVM_IR:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000205 assert (!"Invalid input kind!");
Greg Clayton94e5d782010-06-13 17:34:29 +0000206 case IK_OpenCL:
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000207 LangStd = LangStandard::lang_opencl;
208 break;
Sean Callananfb0b7582011-03-15 00:17:19 +0000209 case IK_CUDA:
210 LangStd = LangStandard::lang_cuda;
211 break;
Greg Clayton94e5d782010-06-13 17:34:29 +0000212 case IK_Asm:
213 case IK_C:
214 case IK_PreprocessedC:
215 case IK_ObjC:
216 case IK_PreprocessedObjC:
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000217 LangStd = LangStandard::lang_gnu99;
218 break;
Greg Clayton94e5d782010-06-13 17:34:29 +0000219 case IK_CXX:
220 case IK_PreprocessedCXX:
221 case IK_ObjCXX:
222 case IK_PreprocessedObjCXX:
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000223 LangStd = LangStandard::lang_gnucxx98;
224 break;
225 }
226 }
227
228 const LangStandard &Std = LangStandard::getLangStandardForKind(LangStd);
229 Opts.BCPLComment = Std.hasBCPLComments();
230 Opts.C99 = Std.isC99();
231 Opts.CPlusPlus = Std.isCPlusPlus();
232 Opts.CPlusPlus0x = Std.isCPlusPlus0x();
233 Opts.Digraphs = Std.hasDigraphs();
234 Opts.GNUMode = Std.isGNUMode();
235 Opts.GNUInline = !Std.isC99();
236 Opts.HexFloats = Std.hasHexFloats();
237 Opts.ImplicitInt = Std.hasImplicitInt();
238
239 // OpenCL has some additional defaults.
240 if (LangStd == LangStandard::lang_opencl) {
241 Opts.OpenCL = 1;
242 Opts.AltiVec = 1;
243 Opts.CXXOperatorNames = 1;
244 Opts.LaxVectorConversions = 1;
245 }
246
247 // OpenCL and C++ both have bool, true, false keywords.
248 Opts.Bool = Opts.OpenCL || Opts.CPlusPlus;
249
250// if (Opts.CPlusPlus)
251// Opts.CXXOperatorNames = !Args.hasArg(OPT_fno_operator_names);
252//
253// if (Args.hasArg(OPT_fobjc_gc_only))
254// Opts.setGCMode(LangOptions::GCOnly);
255// else if (Args.hasArg(OPT_fobjc_gc))
256// Opts.setGCMode(LangOptions::HybridGC);
257//
258// if (Args.hasArg(OPT_print_ivar_layout))
259// Opts.ObjCGCBitmapPrint = 1;
260//
261// if (Args.hasArg(OPT_faltivec))
262// Opts.AltiVec = 1;
263//
264// if (Args.hasArg(OPT_pthread))
265// Opts.POSIXThreads = 1;
266//
267// llvm::StringRef Vis = getLastArgValue(Args, OPT_fvisibility,
268// "default");
269// if (Vis == "default")
Sean Callanan31e851c2010-10-29 18:38:40 +0000270 Opts.setVisibilityMode(DefaultVisibility);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000271// else if (Vis == "hidden")
272// Opts.setVisibilityMode(LangOptions::Hidden);
273// else if (Vis == "protected")
274// Opts.setVisibilityMode(LangOptions::Protected);
275// else
276// Diags.Report(diag::err_drv_invalid_value)
277// << Args.getLastArg(OPT_fvisibility)->getAsString(Args) << Vis;
278
279// Opts.OverflowChecking = Args.hasArg(OPT_ftrapv);
280
281 // Mimicing gcc's behavior, trigraphs are only enabled if -trigraphs
282 // is specified, or -std is set to a conforming mode.
283 Opts.Trigraphs = !Opts.GNUMode;
284// if (Args.hasArg(OPT_trigraphs))
285// Opts.Trigraphs = 1;
286//
287// Opts.DollarIdents = Args.hasFlag(OPT_fdollars_in_identifiers,
288// OPT_fno_dollars_in_identifiers,
289// !Opts.AsmPreprocessor);
290// Opts.PascalStrings = Args.hasArg(OPT_fpascal_strings);
291// Opts.Microsoft = Args.hasArg(OPT_fms_extensions);
292// Opts.WritableStrings = Args.hasArg(OPT_fwritable_strings);
293// if (Args.hasArg(OPT_fno_lax_vector_conversions))
294// Opts.LaxVectorConversions = 0;
295// Opts.Exceptions = Args.hasArg(OPT_fexceptions);
296// Opts.RTTI = !Args.hasArg(OPT_fno_rtti);
297// Opts.Blocks = Args.hasArg(OPT_fblocks);
298// Opts.CharIsSigned = !Args.hasArg(OPT_fno_signed_char);
299// Opts.ShortWChar = Args.hasArg(OPT_fshort_wchar);
300// Opts.Freestanding = Args.hasArg(OPT_ffreestanding);
301// Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding;
302// Opts.AssumeSaneOperatorNew = !Args.hasArg(OPT_fno_assume_sane_operator_new);
303// Opts.HeinousExtensions = Args.hasArg(OPT_fheinous_gnu_extensions);
304// Opts.AccessControl = Args.hasArg(OPT_faccess_control);
305// Opts.ElideConstructors = !Args.hasArg(OPT_fno_elide_constructors);
306// Opts.MathErrno = !Args.hasArg(OPT_fno_math_errno);
307// Opts.InstantiationDepth = getLastArgIntValue(Args, OPT_ftemplate_depth, 99,
308// Diags);
309// Opts.NeXTRuntime = !Args.hasArg(OPT_fgnu_runtime);
310// Opts.ObjCConstantStringClass = getLastArgValue(Args,
311// OPT_fconstant_string_class);
312// Opts.ObjCNonFragileABI = Args.hasArg(OPT_fobjc_nonfragile_abi);
313// Opts.CatchUndefined = Args.hasArg(OPT_fcatch_undefined_behavior);
314// Opts.EmitAllDecls = Args.hasArg(OPT_femit_all_decls);
315// Opts.PICLevel = getLastArgIntValue(Args, OPT_pic_level, 0, Diags);
316// Opts.Static = Args.hasArg(OPT_static_define);
317 Opts.OptimizeSize = 0;
318
319 // FIXME: Eliminate this dependency.
320// unsigned Opt =
321// Args.hasArg(OPT_Os) ? 2 : getLastArgIntValue(Args, OPT_O, 0, Diags);
322// Opts.Optimize = Opt != 0;
323 unsigned Opt = 0;
324
325 // This is the __NO_INLINE__ define, which just depends on things like the
326 // optimization level and -fno-inline, not actually whether the backend has
327 // inlining enabled.
328 //
329 // FIXME: This is affected by other options (-fno-inline).
330 Opts.NoInline = !Opt;
331
332// unsigned SSP = getLastArgIntValue(Args, OPT_stack_protector, 0, Diags);
333// switch (SSP) {
334// default:
335// Diags.Report(diag::err_drv_invalid_value)
336// << Args.getLastArg(OPT_stack_protector)->getAsString(Args) << SSP;
337// break;
338// case 0: Opts.setStackProtectorMode(LangOptions::SSPOff); break;
339// case 1: Opts.setStackProtectorMode(LangOptions::SSPOn); break;
340// case 2: Opts.setStackProtectorMode(LangOptions::SSPReq); break;
341// }
342}
343
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000344
Greg Clayton6beaaa62011-01-17 03:46:26 +0000345ClangASTContext::ClangASTContext (const char *target_triple) :
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000346 m_target_triple(),
Greg Clayton6beaaa62011-01-17 03:46:26 +0000347 m_ast_ap(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000348 m_language_options_ap(),
349 m_source_manager_ap(),
350 m_diagnostic_ap(),
351 m_target_options_ap(),
352 m_target_info_ap(),
353 m_identifier_table_ap(),
354 m_selector_table_ap(),
Greg Clayton6beaaa62011-01-17 03:46:26 +0000355 m_builtins_ap(),
356 m_callback_tag_decl (NULL),
357 m_callback_objc_decl (NULL),
358 m_callback_baton (NULL)
359
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000360{
361 if (target_triple && target_triple[0])
362 m_target_triple.assign (target_triple);
363}
364
365//----------------------------------------------------------------------
366// Destructor
367//----------------------------------------------------------------------
368ClangASTContext::~ClangASTContext()
369{
370 m_builtins_ap.reset();
371 m_selector_table_ap.reset();
372 m_identifier_table_ap.reset();
373 m_target_info_ap.reset();
374 m_target_options_ap.reset();
375 m_diagnostic_ap.reset();
376 m_source_manager_ap.reset();
377 m_language_options_ap.reset();
Greg Clayton6beaaa62011-01-17 03:46:26 +0000378 m_ast_ap.reset();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000379}
380
381
382void
383ClangASTContext::Clear()
384{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000385 m_ast_ap.reset();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000386 m_language_options_ap.reset();
387 m_source_manager_ap.reset();
388 m_diagnostic_ap.reset();
389 m_target_options_ap.reset();
390 m_target_info_ap.reset();
391 m_identifier_table_ap.reset();
392 m_selector_table_ap.reset();
393 m_builtins_ap.reset();
394}
395
396const char *
397ClangASTContext::GetTargetTriple ()
398{
399 return m_target_triple.c_str();
400}
401
402void
403ClangASTContext::SetTargetTriple (const char *target_triple)
404{
405 Clear();
406 m_target_triple.assign(target_triple);
407}
408
Greg Clayton514487e2011-02-15 21:59:32 +0000409void
410ClangASTContext::SetArchitecture (const ArchSpec &arch)
411{
412 Clear();
413 m_target_triple.assign(arch.GetTriple().str());
414}
415
Greg Clayton6beaaa62011-01-17 03:46:26 +0000416bool
417ClangASTContext::HasExternalSource ()
418{
419 ASTContext *ast = getASTContext();
420 if (ast)
421 return ast->getExternalSource () != NULL;
422 return false;
423}
424
425void
426ClangASTContext::SetExternalSource (llvm::OwningPtr<ExternalASTSource> &ast_source_ap)
427{
428 ASTContext *ast = getASTContext();
429 if (ast)
430 {
431 ast->setExternalSource (ast_source_ap);
432 ast->getTranslationUnitDecl()->setHasExternalLexicalStorage(true);
433 //ast->getTranslationUnitDecl()->setHasExternalVisibleStorage(true);
434 }
435}
436
437void
438ClangASTContext::RemoveExternalSource ()
439{
440 ASTContext *ast = getASTContext();
441
442 if (ast)
443 {
444 llvm::OwningPtr<ExternalASTSource> empty_ast_source_ap;
445 ast->setExternalSource (empty_ast_source_ap);
446 ast->getTranslationUnitDecl()->setHasExternalLexicalStorage(false);
447 //ast->getTranslationUnitDecl()->setHasExternalVisibleStorage(false);
448 }
449}
450
451
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000452
453ASTContext *
454ClangASTContext::getASTContext()
455{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000456 if (m_ast_ap.get() == NULL)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000457 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000458 m_ast_ap.reset(new ASTContext (*getLanguageOptions(),
459 *getSourceManager(),
460 *getTargetInfo(),
461 *getIdentifierTable(),
462 *getSelectorTable(),
463 *getBuiltinContext(),
464 0));
Sean Callanan7fddd4c2010-12-11 00:08:56 +0000465
Greg Clayton6beaaa62011-01-17 03:46:26 +0000466 if ((m_callback_tag_decl || m_callback_objc_decl) && m_callback_baton)
467 {
468 m_ast_ap->getTranslationUnitDecl()->setHasExternalLexicalStorage();
469 //m_ast_ap->getTranslationUnitDecl()->setHasExternalVisibleStorage();
470 }
471
472 m_ast_ap->getDiagnostics().setClient(getDiagnosticClient(), false);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000473 }
Greg Clayton6beaaa62011-01-17 03:46:26 +0000474 return m_ast_ap.get();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000475}
476
477Builtin::Context *
478ClangASTContext::getBuiltinContext()
479{
480 if (m_builtins_ap.get() == NULL)
481 m_builtins_ap.reset (new Builtin::Context(*getTargetInfo()));
482 return m_builtins_ap.get();
483}
484
485IdentifierTable *
486ClangASTContext::getIdentifierTable()
487{
488 if (m_identifier_table_ap.get() == NULL)
489 m_identifier_table_ap.reset(new IdentifierTable (*ClangASTContext::getLanguageOptions(), NULL));
490 return m_identifier_table_ap.get();
491}
492
493LangOptions *
494ClangASTContext::getLanguageOptions()
495{
496 if (m_language_options_ap.get() == NULL)
497 {
498 m_language_options_ap.reset(new LangOptions());
Greg Clayton94e5d782010-06-13 17:34:29 +0000499 ParseLangArgs(*m_language_options_ap, IK_ObjCXX);
500// InitializeLangOptions(*m_language_options_ap, IK_ObjCXX);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000501 }
502 return m_language_options_ap.get();
503}
504
505SelectorTable *
506ClangASTContext::getSelectorTable()
507{
508 if (m_selector_table_ap.get() == NULL)
509 m_selector_table_ap.reset (new SelectorTable());
510 return m_selector_table_ap.get();
511}
512
Sean Callanan79439e82010-11-18 02:56:27 +0000513clang::FileManager *
514ClangASTContext::getFileManager()
515{
516 if (m_file_manager_ap.get() == NULL)
Greg Clayton38a61402010-12-02 23:20:03 +0000517 {
518 clang::FileSystemOptions file_system_options;
519 m_file_manager_ap.reset(new clang::FileManager(file_system_options));
520 }
Sean Callanan79439e82010-11-18 02:56:27 +0000521 return m_file_manager_ap.get();
522}
523
Greg Claytone1a916a2010-07-21 22:12:05 +0000524clang::SourceManager *
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000525ClangASTContext::getSourceManager()
526{
527 if (m_source_manager_ap.get() == NULL)
Greg Clayton38a61402010-12-02 23:20:03 +0000528 m_source_manager_ap.reset(new clang::SourceManager(*getDiagnostic(), *getFileManager()));
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000529 return m_source_manager_ap.get();
530}
531
532Diagnostic *
533ClangASTContext::getDiagnostic()
534{
535 if (m_diagnostic_ap.get() == NULL)
Greg Claytona651b532010-11-19 21:46:54 +0000536 {
537 llvm::IntrusiveRefCntPtr<DiagnosticIDs> diag_id_sp(new DiagnosticIDs());
538 m_diagnostic_ap.reset(new Diagnostic(diag_id_sp));
539 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000540 return m_diagnostic_ap.get();
541}
542
Sean Callanan7fddd4c2010-12-11 00:08:56 +0000543class NullDiagnosticClient : public DiagnosticClient
544{
545public:
546 NullDiagnosticClient ()
547 {
548 m_log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS);
549 }
550
551 void HandleDiagnostic (Diagnostic::Level DiagLevel, const DiagnosticInfo &info)
552 {
553 if (m_log)
554 {
555 llvm::SmallVectorImpl<char> diag_str(10);
556 info.FormatDiagnostic(diag_str);
557 diag_str.push_back('\0');
558 m_log->Printf("Compiler diagnostic: %s\n", diag_str.data());
559 }
560 }
561private:
562 LogSP m_log;
563};
564
565DiagnosticClient *
566ClangASTContext::getDiagnosticClient()
567{
568 if (m_diagnostic_client_ap.get() == NULL)
569 m_diagnostic_client_ap.reset(new NullDiagnosticClient);
570
571 return m_diagnostic_client_ap.get();
572}
573
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000574TargetOptions *
575ClangASTContext::getTargetOptions()
576{
577 if (m_target_options_ap.get() == NULL && !m_target_triple.empty())
578 {
579 m_target_options_ap.reset (new TargetOptions());
580 if (m_target_options_ap.get())
581 m_target_options_ap->Triple = m_target_triple;
582 }
583 return m_target_options_ap.get();
584}
585
586
587TargetInfo *
588ClangASTContext::getTargetInfo()
589{
590 // target_triple should be something like "x86_64-apple-darwin10"
591 if (m_target_info_ap.get() == NULL && !m_target_triple.empty())
592 m_target_info_ap.reset (TargetInfo::CreateTargetInfo(*getDiagnostic(), *getTargetOptions()));
593 return m_target_info_ap.get();
594}
595
596#pragma mark Basic Types
597
598static inline bool
Greg Clayton6beaaa62011-01-17 03:46:26 +0000599QualTypeMatchesBitSize(const uint64_t bit_size, ASTContext *ast, QualType qual_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000600{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000601 uint64_t qual_type_bit_size = ast->getTypeSize(qual_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000602 if (qual_type_bit_size == bit_size)
603 return true;
604 return false;
605}
606
Greg Clayton1be10fc2010-09-29 01:12:09 +0000607clang_type_t
Greg Claytonc86103d2010-08-05 01:57:25 +0000608ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (Encoding encoding, uint32_t bit_size)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000609{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000610 ASTContext *ast = getASTContext();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000611
Greg Clayton6beaaa62011-01-17 03:46:26 +0000612 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000613
Greg Clayton6beaaa62011-01-17 03:46:26 +0000614 return GetBuiltinTypeForEncodingAndBitSize (ast, encoding, bit_size);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000615}
616
Greg Clayton1be10fc2010-09-29 01:12:09 +0000617clang_type_t
Greg Clayton6beaaa62011-01-17 03:46:26 +0000618ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (ASTContext *ast, Encoding encoding, uint32_t bit_size)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000619{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000620 if (!ast)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000621 return NULL;
622
623 switch (encoding)
624 {
Greg Claytonc86103d2010-08-05 01:57:25 +0000625 case eEncodingInvalid:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000626 if (QualTypeMatchesBitSize (bit_size, ast, ast->VoidPtrTy))
627 return ast->VoidPtrTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000628 break;
629
Greg Claytonc86103d2010-08-05 01:57:25 +0000630 case eEncodingUint:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000631 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
632 return ast->UnsignedCharTy.getAsOpaquePtr();
633 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
634 return ast->UnsignedShortTy.getAsOpaquePtr();
635 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
636 return ast->UnsignedIntTy.getAsOpaquePtr();
637 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongTy))
638 return ast->UnsignedLongTy.getAsOpaquePtr();
639 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongLongTy))
640 return ast->UnsignedLongLongTy.getAsOpaquePtr();
641 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedInt128Ty))
642 return ast->UnsignedInt128Ty.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000643 break;
644
Greg Claytonc86103d2010-08-05 01:57:25 +0000645 case eEncodingSint:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000646 if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
647 return ast->CharTy.getAsOpaquePtr();
648 if (QualTypeMatchesBitSize (bit_size, ast, ast->ShortTy))
649 return ast->ShortTy.getAsOpaquePtr();
650 if (QualTypeMatchesBitSize (bit_size, ast, ast->IntTy))
651 return ast->IntTy.getAsOpaquePtr();
652 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongTy))
653 return ast->LongTy.getAsOpaquePtr();
654 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongLongTy))
655 return ast->LongLongTy.getAsOpaquePtr();
656 if (QualTypeMatchesBitSize (bit_size, ast, ast->Int128Ty))
657 return ast->Int128Ty.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000658 break;
659
Greg Claytonc86103d2010-08-05 01:57:25 +0000660 case eEncodingIEEE754:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000661 if (QualTypeMatchesBitSize (bit_size, ast, ast->FloatTy))
662 return ast->FloatTy.getAsOpaquePtr();
663 if (QualTypeMatchesBitSize (bit_size, ast, ast->DoubleTy))
664 return ast->DoubleTy.getAsOpaquePtr();
665 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleTy))
666 return ast->LongDoubleTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000667 break;
668
Greg Claytonc86103d2010-08-05 01:57:25 +0000669 case eEncodingVector:
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000670 default:
671 break;
672 }
673
674 return NULL;
675}
676
Greg Clayton1be10fc2010-09-29 01:12:09 +0000677clang_type_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000678ClangASTContext::GetBuiltinTypeForDWARFEncodingAndBitSize (const char *type_name, uint32_t dw_ate, uint32_t bit_size)
679{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000680 ASTContext *ast = getASTContext();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000681
682 #define streq(a,b) strcmp(a,b) == 0
Greg Clayton6beaaa62011-01-17 03:46:26 +0000683 assert (ast != NULL);
684 if (ast)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000685 {
686 switch (dw_ate)
687 {
688 default:
689 break;
690
691 case DW_ATE_address:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000692 if (QualTypeMatchesBitSize (bit_size, ast, ast->VoidPtrTy))
693 return ast->VoidPtrTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000694 break;
695
696 case DW_ATE_boolean:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000697 if (QualTypeMatchesBitSize (bit_size, ast, ast->BoolTy))
698 return ast->BoolTy.getAsOpaquePtr();
699 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
700 return ast->UnsignedCharTy.getAsOpaquePtr();
701 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
702 return ast->UnsignedShortTy.getAsOpaquePtr();
703 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
704 return ast->UnsignedIntTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000705 break;
706
Greg Clayton49462ea2011-01-15 02:52:14 +0000707 case DW_ATE_lo_user:
708 // This has been seen to mean DW_AT_complex_integer
Greg Clayton5732f242011-01-27 09:15:11 +0000709 if (::strstr(type_name, "complex"))
Greg Clayton49462ea2011-01-15 02:52:14 +0000710 {
711 clang_type_t complex_int_clang_type = GetBuiltinTypeForDWARFEncodingAndBitSize ("int", DW_ATE_signed, bit_size/2);
Greg Clayton6beaaa62011-01-17 03:46:26 +0000712 return ast->getComplexType (QualType::getFromOpaquePtr(complex_int_clang_type)).getAsOpaquePtr();
Greg Clayton49462ea2011-01-15 02:52:14 +0000713 }
714 break;
715
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000716 case DW_ATE_complex_float:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000717 if (QualTypeMatchesBitSize (bit_size, ast, ast->FloatComplexTy))
718 return ast->FloatComplexTy.getAsOpaquePtr();
719 else if (QualTypeMatchesBitSize (bit_size, ast, ast->DoubleComplexTy))
720 return ast->DoubleComplexTy.getAsOpaquePtr();
721 else if (QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleComplexTy))
722 return ast->LongDoubleComplexTy.getAsOpaquePtr();
Greg Clayton49462ea2011-01-15 02:52:14 +0000723 else
724 {
725 clang_type_t complex_float_clang_type = GetBuiltinTypeForDWARFEncodingAndBitSize ("float", DW_ATE_float, bit_size/2);
Greg Clayton6beaaa62011-01-17 03:46:26 +0000726 return ast->getComplexType (QualType::getFromOpaquePtr(complex_float_clang_type)).getAsOpaquePtr();
Greg Clayton49462ea2011-01-15 02:52:14 +0000727 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000728 break;
729
730 case DW_ATE_float:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000731 if (QualTypeMatchesBitSize (bit_size, ast, ast->FloatTy))
732 return ast->FloatTy.getAsOpaquePtr();
733 if (QualTypeMatchesBitSize (bit_size, ast, ast->DoubleTy))
734 return ast->DoubleTy.getAsOpaquePtr();
735 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleTy))
736 return ast->LongDoubleTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000737 break;
738
739 case DW_ATE_signed:
740 if (type_name)
741 {
Greg Clayton19de37f2010-11-02 03:48:39 +0000742 if (strstr(type_name, "long long"))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000743 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000744 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongLongTy))
745 return ast->LongLongTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000746 }
Greg Clayton19de37f2010-11-02 03:48:39 +0000747 else if (strstr(type_name, "long"))
748 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000749 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongTy))
750 return ast->LongTy.getAsOpaquePtr();
Greg Clayton19de37f2010-11-02 03:48:39 +0000751 }
752 else if (strstr(type_name, "short"))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000753 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000754 if (QualTypeMatchesBitSize (bit_size, ast, ast->ShortTy))
755 return ast->ShortTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000756 }
Greg Clayton19de37f2010-11-02 03:48:39 +0000757 else if (strstr(type_name, "char"))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000758 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000759 if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
760 return ast->CharTy.getAsOpaquePtr();
761 if (QualTypeMatchesBitSize (bit_size, ast, ast->SignedCharTy))
762 return ast->SignedCharTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000763 }
Greg Clayton19de37f2010-11-02 03:48:39 +0000764 else if (strstr(type_name, "int"))
765 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000766 if (QualTypeMatchesBitSize (bit_size, ast, ast->IntTy))
767 return ast->IntTy.getAsOpaquePtr();
768 if (QualTypeMatchesBitSize (bit_size, ast, ast->Int128Ty))
769 return ast->Int128Ty.getAsOpaquePtr();
Greg Clayton19de37f2010-11-02 03:48:39 +0000770 }
771 else if (streq(type_name, "wchar_t"))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000772 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000773 if (QualTypeMatchesBitSize (bit_size, ast, ast->WCharTy))
774 return ast->WCharTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000775 }
Greg Clayton7bd65b92011-02-09 23:39:34 +0000776 else if (streq(type_name, "void"))
777 {
778 if (QualTypeMatchesBitSize (bit_size, ast, ast->VoidTy))
779 return ast->VoidTy.getAsOpaquePtr();
780 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000781 }
782 // We weren't able to match up a type name, just search by size
Greg Clayton6beaaa62011-01-17 03:46:26 +0000783 if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
784 return ast->CharTy.getAsOpaquePtr();
785 if (QualTypeMatchesBitSize (bit_size, ast, ast->ShortTy))
786 return ast->ShortTy.getAsOpaquePtr();
787 if (QualTypeMatchesBitSize (bit_size, ast, ast->IntTy))
788 return ast->IntTy.getAsOpaquePtr();
789 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongTy))
790 return ast->LongTy.getAsOpaquePtr();
791 if (QualTypeMatchesBitSize (bit_size, ast, ast->LongLongTy))
792 return ast->LongLongTy.getAsOpaquePtr();
793 if (QualTypeMatchesBitSize (bit_size, ast, ast->Int128Ty))
794 return ast->Int128Ty.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000795 break;
796
797 case DW_ATE_signed_char:
798 if (type_name)
799 {
800 if (streq(type_name, "signed char"))
801 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000802 if (QualTypeMatchesBitSize (bit_size, ast, ast->SignedCharTy))
803 return ast->SignedCharTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000804 }
805 }
Greg Clayton6beaaa62011-01-17 03:46:26 +0000806 if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
807 return ast->CharTy.getAsOpaquePtr();
808 if (QualTypeMatchesBitSize (bit_size, ast, ast->SignedCharTy))
809 return ast->SignedCharTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000810 break;
811
812 case DW_ATE_unsigned:
813 if (type_name)
814 {
Greg Clayton19de37f2010-11-02 03:48:39 +0000815 if (strstr(type_name, "long long"))
816 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000817 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongLongTy))
818 return ast->UnsignedLongLongTy.getAsOpaquePtr();
Greg Clayton19de37f2010-11-02 03:48:39 +0000819 }
820 else if (strstr(type_name, "long"))
821 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000822 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongTy))
823 return ast->UnsignedLongTy.getAsOpaquePtr();
Greg Clayton19de37f2010-11-02 03:48:39 +0000824 }
825 else if (strstr(type_name, "short"))
826 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000827 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
828 return ast->UnsignedShortTy.getAsOpaquePtr();
Greg Clayton19de37f2010-11-02 03:48:39 +0000829 }
830 else if (strstr(type_name, "char"))
831 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000832 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
833 return ast->UnsignedCharTy.getAsOpaquePtr();
Greg Clayton19de37f2010-11-02 03:48:39 +0000834 }
835 else if (strstr(type_name, "int"))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000836 {
Greg Clayton6beaaa62011-01-17 03:46:26 +0000837 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
838 return ast->UnsignedIntTy.getAsOpaquePtr();
839 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedInt128Ty))
840 return ast->UnsignedInt128Ty.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000841 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000842 }
843 // We weren't able to match up a type name, just search by size
Greg Clayton6beaaa62011-01-17 03:46:26 +0000844 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
845 return ast->UnsignedCharTy.getAsOpaquePtr();
846 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
847 return ast->UnsignedShortTy.getAsOpaquePtr();
848 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
849 return ast->UnsignedIntTy.getAsOpaquePtr();
850 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongTy))
851 return ast->UnsignedLongTy.getAsOpaquePtr();
852 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongLongTy))
853 return ast->UnsignedLongLongTy.getAsOpaquePtr();
854 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedInt128Ty))
855 return ast->UnsignedInt128Ty.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000856 break;
857
858 case DW_ATE_unsigned_char:
Greg Clayton6beaaa62011-01-17 03:46:26 +0000859 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
860 return ast->UnsignedCharTy.getAsOpaquePtr();
Greg Clayton7bd65b92011-02-09 23:39:34 +0000861 if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
862 return ast->UnsignedShortTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000863 break;
864
865 case DW_ATE_imaginary_float:
866 break;
867 }
868 }
869 // This assert should fire for anything that we don't catch above so we know
870 // to fix any issues we run into.
Greg Claytondc968d12011-05-17 18:15:05 +0000871 if (type_name)
872 {
873 fprintf (stderr, "error: need to add support for DW_TAG_base_type '%s' encoded with DW_ATE = 0x%x, bit_size = %u\n", type_name, dw_ate, bit_size);
874 }
875 else
876 {
877 fprintf (stderr, "error: need to add support for DW_TAG_base_type encoded with DW_ATE = 0x%x, bit_size = %u\n", dw_ate, bit_size);
878 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000879 return NULL;
880}
881
Greg Clayton1be10fc2010-09-29 01:12:09 +0000882clang_type_t
Greg Clayton6beaaa62011-01-17 03:46:26 +0000883ClangASTContext::GetBuiltInType_void(ASTContext *ast)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000884{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000885 return ast->VoidTy.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000886}
887
Greg Clayton1be10fc2010-09-29 01:12:09 +0000888clang_type_t
Sean Callananf7c3e272010-11-19 02:52:21 +0000889ClangASTContext::GetBuiltInType_bool()
890{
891 return getASTContext()->BoolTy.getAsOpaquePtr();
892}
893
894clang_type_t
Greg Claytonb0b9fe62010-08-03 00:35:52 +0000895ClangASTContext::GetBuiltInType_objc_id()
896{
Sean Callananf6c73082010-12-06 23:53:20 +0000897 return getASTContext()->getPointerType(getASTContext()->ObjCBuiltinIdTy).getAsOpaquePtr();
Greg Claytonb0b9fe62010-08-03 00:35:52 +0000898}
899
Greg Clayton1be10fc2010-09-29 01:12:09 +0000900clang_type_t
Greg Claytonb0b9fe62010-08-03 00:35:52 +0000901ClangASTContext::GetBuiltInType_objc_Class()
902{
Sean Callanana2424172010-10-25 00:29:48 +0000903 return getASTContext()->ObjCBuiltinClassTy.getAsOpaquePtr();
Greg Claytonb0b9fe62010-08-03 00:35:52 +0000904}
905
Greg Clayton1be10fc2010-09-29 01:12:09 +0000906clang_type_t
Greg Claytonb0b9fe62010-08-03 00:35:52 +0000907ClangASTContext::GetBuiltInType_objc_selector()
908{
Sean Callananf6c73082010-12-06 23:53:20 +0000909 return getASTContext()->getPointerType(getASTContext()->ObjCBuiltinSelTy).getAsOpaquePtr();
Greg Claytonb0b9fe62010-08-03 00:35:52 +0000910}
911
Greg Clayton1be10fc2010-09-29 01:12:09 +0000912clang_type_t
Sean Callanan77502262011-05-12 23:54:16 +0000913ClangASTContext::GetUnknownAnyType(clang::ASTContext *ast)
914{
915 return ast->UnknownAnyTy.getAsOpaquePtr();
916}
917
918clang_type_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000919ClangASTContext::GetCStringType (bool is_const)
920{
921 QualType char_type(getASTContext()->CharTy);
922
923 if (is_const)
924 char_type.addConst();
925
926 return getASTContext()->getPointerType(char_type).getAsOpaquePtr();
927}
928
Greg Clayton1be10fc2010-09-29 01:12:09 +0000929clang_type_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000930ClangASTContext::GetVoidPtrType (bool is_const)
931{
932 return GetVoidPtrType(getASTContext(), is_const);
933}
934
Greg Clayton1be10fc2010-09-29 01:12:09 +0000935clang_type_t
Greg Clayton6beaaa62011-01-17 03:46:26 +0000936ClangASTContext::GetVoidPtrType (ASTContext *ast, bool is_const)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000937{
Greg Clayton6beaaa62011-01-17 03:46:26 +0000938 QualType void_ptr_type(ast->VoidPtrTy);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000939
940 if (is_const)
941 void_ptr_type.addConst();
942
943 return void_ptr_type.getAsOpaquePtr();
944}
945
Greg Clayton1be10fc2010-09-29 01:12:09 +0000946clang_type_t
Greg Clayton38a61402010-12-02 23:20:03 +0000947ClangASTContext::CopyType (ASTContext *dst_ast,
948 ASTContext *src_ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +0000949 clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000950{
Sean Callanan79439e82010-11-18 02:56:27 +0000951 FileSystemOptions file_system_options;
Greg Clayton38a61402010-12-02 23:20:03 +0000952 FileManager file_manager (file_system_options);
953 ASTImporter importer(*dst_ast, file_manager,
Sean Callanan2c777c42011-01-18 23:32:05 +0000954 *src_ast, file_manager,
955 false);
Sean Callanan0617fcb2010-11-09 22:37:10 +0000956
Greg Clayton38a61402010-12-02 23:20:03 +0000957 QualType src (QualType::getFromOpaquePtr(clang_type));
958 QualType dst (importer.Import(src));
Sean Callanan0617fcb2010-11-09 22:37:10 +0000959
960 return dst.getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000961}
962
Greg Clayton526e5af2010-11-13 03:52:47 +0000963
964clang::Decl *
Greg Clayton38a61402010-12-02 23:20:03 +0000965ClangASTContext::CopyDecl (ASTContext *dst_ast,
966 ASTContext *src_ast,
Greg Clayton526e5af2010-11-13 03:52:47 +0000967 clang::Decl *source_decl)
Sean Callanan7fddd4c2010-12-11 00:08:56 +0000968{
Sean Callanan79439e82010-11-18 02:56:27 +0000969 FileSystemOptions file_system_options;
Greg Clayton38a61402010-12-02 23:20:03 +0000970 FileManager file_manager (file_system_options);
971 ASTImporter importer(*dst_ast, file_manager,
Sean Callanan2c777c42011-01-18 23:32:05 +0000972 *src_ast, file_manager,
973 false);
Greg Clayton526e5af2010-11-13 03:52:47 +0000974
975 return importer.Import(source_decl);
976}
977
Sean Callanan23a30272010-07-16 00:00:27 +0000978bool
Greg Clayton6beaaa62011-01-17 03:46:26 +0000979ClangASTContext::AreTypesSame(ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +0000980 clang_type_t type1,
981 clang_type_t type2)
Sean Callanan4dcca2622010-07-15 22:30:52 +0000982{
Greg Claytonf4ecaa52011-02-16 23:00:21 +0000983 return ast->hasSameType (QualType::getFromOpaquePtr(type1),
984 QualType::getFromOpaquePtr(type2));
Sean Callanan4dcca2622010-07-15 22:30:52 +0000985}
986
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000987#pragma mark CVR modifiers
988
Greg Clayton1be10fc2010-09-29 01:12:09 +0000989clang_type_t
990ClangASTContext::AddConstModifier (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000991{
992 if (clang_type)
993 {
994 QualType result(QualType::getFromOpaquePtr(clang_type));
995 result.addConst();
996 return result.getAsOpaquePtr();
997 }
998 return NULL;
999}
1000
Greg Clayton1be10fc2010-09-29 01:12:09 +00001001clang_type_t
1002ClangASTContext::AddRestrictModifier (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001003{
1004 if (clang_type)
1005 {
1006 QualType result(QualType::getFromOpaquePtr(clang_type));
1007 result.getQualifiers().setRestrict (true);
1008 return result.getAsOpaquePtr();
1009 }
1010 return NULL;
1011}
1012
Greg Clayton1be10fc2010-09-29 01:12:09 +00001013clang_type_t
1014ClangASTContext::AddVolatileModifier (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001015{
1016 if (clang_type)
1017 {
1018 QualType result(QualType::getFromOpaquePtr(clang_type));
1019 result.getQualifiers().setVolatile (true);
1020 return result.getAsOpaquePtr();
1021 }
1022 return NULL;
1023}
1024
Greg Clayton6beaaa62011-01-17 03:46:26 +00001025
1026clang_type_t
1027ClangASTContext::GetTypeForDecl (TagDecl *decl)
1028{
1029 // No need to call the getASTContext() accessor (which can create the AST
1030 // if it isn't created yet, because we can't have created a decl in this
1031 // AST if our AST didn't already exist...
1032 if (m_ast_ap.get())
1033 return m_ast_ap->getTagDeclType(decl).getAsOpaquePtr();
1034 return NULL;
1035}
1036
1037clang_type_t
1038ClangASTContext::GetTypeForDecl (ObjCInterfaceDecl *decl)
1039{
1040 // No need to call the getASTContext() accessor (which can create the AST
1041 // if it isn't created yet, because we can't have created a decl in this
1042 // AST if our AST didn't already exist...
1043 if (m_ast_ap.get())
1044 return m_ast_ap->getObjCInterfaceType(decl).getAsOpaquePtr();
1045 return NULL;
1046}
1047
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001048#pragma mark Structure, Unions, Classes
1049
Greg Clayton1be10fc2010-09-29 01:12:09 +00001050clang_type_t
Greg Claytonc86103d2010-08-05 01:57:25 +00001051ClangASTContext::CreateRecordType (const char *name, int kind, DeclContext *decl_ctx, LanguageType language)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001052{
Greg Clayton6beaaa62011-01-17 03:46:26 +00001053 ASTContext *ast = getASTContext();
1054 assert (ast != NULL);
Sean Callanana2424172010-10-25 00:29:48 +00001055
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001056 if (decl_ctx == NULL)
Greg Clayton6beaaa62011-01-17 03:46:26 +00001057 decl_ctx = ast->getTranslationUnitDecl();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001058
Greg Clayton9e409562010-07-28 02:04:09 +00001059
Greg Claytonc86103d2010-08-05 01:57:25 +00001060 if (language == eLanguageTypeObjC)
Greg Clayton9e409562010-07-28 02:04:09 +00001061 {
Greg Claytonaaf99e02010-10-11 02:25:34 +00001062 bool isForwardDecl = true;
Greg Clayton9e409562010-07-28 02:04:09 +00001063 bool isInternal = false;
1064 return CreateObjCClass (name, decl_ctx, isForwardDecl, isInternal);
1065 }
1066
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001067 // NOTE: Eventually CXXRecordDecl will be merged back into RecordDecl and
1068 // we will need to update this code. I was told to currently always use
1069 // the CXXRecordDecl class since we often don't know from debug information
1070 // if something is struct or a class, so we default to always use the more
1071 // complete definition just in case.
Greg Clayton6beaaa62011-01-17 03:46:26 +00001072 CXXRecordDecl *decl = CXXRecordDecl::Create(*ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001073 (TagDecl::TagKind)kind,
1074 decl_ctx,
1075 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00001076 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00001077 name && name[0] ? &ast->Idents.get(name) : NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001078
Greg Clayton6beaaa62011-01-17 03:46:26 +00001079 return ast->getTagDeclType(decl).getAsOpaquePtr();
1080}
1081
1082bool
1083ClangASTContext::SetHasExternalStorage (clang_type_t clang_type, bool has_extern)
1084{
1085 if (clang_type == NULL)
1086 return false;
1087
1088 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
1089
1090 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
1091 switch (type_class)
1092 {
1093 case clang::Type::Record:
1094 {
1095 CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
1096 if (cxx_record_decl)
1097 {
1098 cxx_record_decl->setHasExternalLexicalStorage (has_extern);
Greg Claytonc432c192011-01-20 04:18:48 +00001099 cxx_record_decl->setHasExternalVisibleStorage (has_extern);
Greg Clayton6beaaa62011-01-17 03:46:26 +00001100 return true;
1101 }
1102 }
1103 break;
1104
1105 case clang::Type::Enum:
1106 {
1107 EnumDecl *enum_decl = cast<EnumType>(qual_type)->getDecl();
1108 if (enum_decl)
1109 {
1110 enum_decl->setHasExternalLexicalStorage (has_extern);
Greg Claytonc432c192011-01-20 04:18:48 +00001111 enum_decl->setHasExternalVisibleStorage (has_extern);
Greg Clayton6beaaa62011-01-17 03:46:26 +00001112 return true;
1113 }
1114 }
1115 break;
1116
1117 case clang::Type::ObjCObject:
1118 case clang::Type::ObjCInterface:
1119 {
Sean Callanan78e37602011-01-27 04:42:51 +00001120 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr());
Greg Clayton6beaaa62011-01-17 03:46:26 +00001121 assert (objc_class_type);
1122 if (objc_class_type)
1123 {
1124 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
1125
1126 if (class_interface_decl)
1127 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001128 class_interface_decl->setHasExternalLexicalStorage (has_extern);
Greg Claytonc432c192011-01-20 04:18:48 +00001129 class_interface_decl->setHasExternalVisibleStorage (has_extern);
Greg Clayton6beaaa62011-01-17 03:46:26 +00001130 return true;
1131 }
1132 }
1133 }
1134 break;
1135
1136 case clang::Type::Typedef:
1137 return ClangASTContext::SetHasExternalStorage (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), has_extern);
1138
1139 default:
1140 break;
1141 }
1142 return false;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001143}
1144
Greg Claytona3c444a2010-10-01 23:13:49 +00001145static bool
1146IsOperator (const char *name, OverloadedOperatorKind &op_kind)
1147{
1148 if (name == NULL || name[0] == '\0')
1149 return false;
1150
Sean Callanana43f20d2010-12-10 19:51:54 +00001151#define OPERATOR_PREFIX "operator"
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00001152#define OPERATOR_PREFIX_LENGTH (sizeof (OPERATOR_PREFIX) - 1)
Sean Callananbfeff8c2010-12-10 02:15:55 +00001153
1154 const char *post_op_name = NULL;
1155
Sean Callanana43f20d2010-12-10 19:51:54 +00001156 bool no_space = true;
Sean Callananbfeff8c2010-12-10 02:15:55 +00001157
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00001158 if (::strncmp(name, OPERATOR_PREFIX, OPERATOR_PREFIX_LENGTH))
Greg Claytona3c444a2010-10-01 23:13:49 +00001159 return false;
1160
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00001161 post_op_name = name + OPERATOR_PREFIX_LENGTH;
1162
Sean Callanana43f20d2010-12-10 19:51:54 +00001163 if (post_op_name[0] == ' ')
1164 {
1165 post_op_name++;
1166 no_space = false;
1167 }
1168
1169#undef OPERATOR_PREFIX
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00001170#undef OPERATOR_PREFIX_LENGTH
Sean Callanana43f20d2010-12-10 19:51:54 +00001171
Greg Claytona3c444a2010-10-01 23:13:49 +00001172 // This is an operator, set the overloaded operator kind to invalid
1173 // in case this is a conversion operator...
1174 op_kind = NUM_OVERLOADED_OPERATORS;
1175
1176 switch (post_op_name[0])
1177 {
Sean Callananbfeff8c2010-12-10 02:15:55 +00001178 default:
1179 if (no_space)
1180 return false;
1181 break;
Greg Claytona3c444a2010-10-01 23:13:49 +00001182 case 'n':
Sean Callananbfeff8c2010-12-10 02:15:55 +00001183 if (no_space)
1184 return false;
Greg Claytona3c444a2010-10-01 23:13:49 +00001185 if (strcmp (post_op_name, "new") == 0)
1186 op_kind = OO_New;
1187 else if (strcmp (post_op_name, "new[]") == 0)
1188 op_kind = OO_Array_New;
1189 break;
1190
1191 case 'd':
Sean Callananbfeff8c2010-12-10 02:15:55 +00001192 if (no_space)
1193 return false;
Greg Claytona3c444a2010-10-01 23:13:49 +00001194 if (strcmp (post_op_name, "delete") == 0)
1195 op_kind = OO_Delete;
1196 else if (strcmp (post_op_name, "delete[]") == 0)
1197 op_kind = OO_Array_Delete;
1198 break;
1199
1200 case '+':
1201 if (post_op_name[1] == '\0')
1202 op_kind = OO_Plus;
1203 else if (post_op_name[2] == '\0')
1204 {
1205 if (post_op_name[1] == '=')
1206 op_kind = OO_PlusEqual;
1207 else if (post_op_name[1] == '+')
1208 op_kind = OO_PlusPlus;
1209 }
1210 break;
1211
1212 case '-':
1213 if (post_op_name[1] == '\0')
1214 op_kind = OO_Minus;
1215 else if (post_op_name[2] == '\0')
1216 {
1217 switch (post_op_name[1])
1218 {
1219 case '=': op_kind = OO_MinusEqual; break;
1220 case '-': op_kind = OO_MinusMinus; break;
1221 case '>': op_kind = OO_Arrow; break;
1222 }
1223 }
1224 else if (post_op_name[3] == '\0')
1225 {
1226 if (post_op_name[2] == '*')
1227 op_kind = OO_ArrowStar; break;
1228 }
1229 break;
1230
1231 case '*':
1232 if (post_op_name[1] == '\0')
1233 op_kind = OO_Star;
1234 else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
1235 op_kind = OO_StarEqual;
1236 break;
1237
1238 case '/':
1239 if (post_op_name[1] == '\0')
1240 op_kind = OO_Slash;
1241 else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
1242 op_kind = OO_SlashEqual;
1243 break;
1244
1245 case '%':
1246 if (post_op_name[1] == '\0')
1247 op_kind = OO_Percent;
1248 else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
1249 op_kind = OO_PercentEqual;
1250 break;
1251
1252
1253 case '^':
1254 if (post_op_name[1] == '\0')
1255 op_kind = OO_Caret;
1256 else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
1257 op_kind = OO_CaretEqual;
1258 break;
1259
1260 case '&':
1261 if (post_op_name[1] == '\0')
1262 op_kind = OO_Amp;
1263 else if (post_op_name[2] == '\0')
1264 {
1265 switch (post_op_name[1])
1266 {
1267 case '=': op_kind = OO_AmpEqual; break;
1268 case '&': op_kind = OO_AmpAmp; break;
1269 }
1270 }
1271 break;
1272
1273 case '|':
1274 if (post_op_name[1] == '\0')
1275 op_kind = OO_Pipe;
1276 else if (post_op_name[2] == '\0')
1277 {
1278 switch (post_op_name[1])
1279 {
1280 case '=': op_kind = OO_PipeEqual; break;
1281 case '|': op_kind = OO_PipePipe; break;
1282 }
1283 }
1284 break;
1285
1286 case '~':
1287 if (post_op_name[1] == '\0')
1288 op_kind = OO_Tilde;
1289 break;
1290
1291 case '!':
1292 if (post_op_name[1] == '\0')
1293 op_kind = OO_Exclaim;
1294 else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
1295 op_kind = OO_ExclaimEqual;
1296 break;
1297
1298 case '=':
1299 if (post_op_name[1] == '\0')
1300 op_kind = OO_Equal;
1301 else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
1302 op_kind = OO_EqualEqual;
1303 break;
1304
1305 case '<':
1306 if (post_op_name[1] == '\0')
1307 op_kind = OO_Less;
1308 else if (post_op_name[2] == '\0')
1309 {
1310 switch (post_op_name[1])
1311 {
1312 case '<': op_kind = OO_LessLess; break;
1313 case '=': op_kind = OO_LessEqual; break;
1314 }
1315 }
1316 else if (post_op_name[3] == '\0')
1317 {
1318 if (post_op_name[2] == '=')
1319 op_kind = OO_LessLessEqual;
1320 }
1321 break;
1322
1323 case '>':
1324 if (post_op_name[1] == '\0')
1325 op_kind = OO_Greater;
1326 else if (post_op_name[2] == '\0')
1327 {
1328 switch (post_op_name[1])
1329 {
1330 case '>': op_kind = OO_GreaterGreater; break;
1331 case '=': op_kind = OO_GreaterEqual; break;
1332 }
1333 }
1334 else if (post_op_name[1] == '>' &&
1335 post_op_name[2] == '=' &&
1336 post_op_name[3] == '\0')
1337 {
1338 op_kind = OO_GreaterGreaterEqual;
1339 }
1340 break;
1341
1342 case ',':
1343 if (post_op_name[1] == '\0')
1344 op_kind = OO_Comma;
1345 break;
1346
1347 case '(':
1348 if (post_op_name[1] == ')' && post_op_name[2] == '\0')
1349 op_kind = OO_Call;
1350 break;
1351
1352 case '[':
1353 if (post_op_name[1] == ']' && post_op_name[2] == '\0')
1354 op_kind = OO_Subscript;
1355 break;
1356 }
1357
1358 return true;
1359}
Greg Clayton6beaaa62011-01-17 03:46:26 +00001360
Greg Claytona51ed9b2010-09-23 01:09:21 +00001361CXXMethodDecl *
Sean Callanan61da09b2010-09-17 02:58:26 +00001362ClangASTContext::AddMethodToCXXRecordType
1363(
Greg Clayton6beaaa62011-01-17 03:46:26 +00001364 ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001365 clang_type_t record_opaque_type,
Greg Claytona51ed9b2010-09-23 01:09:21 +00001366 const char *name,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001367 clang_type_t method_opaque_type,
Greg Claytona51ed9b2010-09-23 01:09:21 +00001368 lldb::AccessType access,
Greg Clayton0fffff52010-09-24 05:15:53 +00001369 bool is_virtual,
1370 bool is_static,
Greg Claytonf51de672010-10-01 02:31:07 +00001371 bool is_inline,
1372 bool is_explicit
Greg Claytona51ed9b2010-09-23 01:09:21 +00001373)
Sean Callanan61da09b2010-09-17 02:58:26 +00001374{
Sean Callananfc55f5d2010-09-21 00:44:12 +00001375 if (!record_opaque_type || !method_opaque_type || !name)
Johnny Chend440bcc2010-09-28 16:10:54 +00001376 return NULL;
Sean Callanan61da09b2010-09-17 02:58:26 +00001377
Greg Clayton6beaaa62011-01-17 03:46:26 +00001378 assert(ast);
Sean Callanan61da09b2010-09-17 02:58:26 +00001379
Greg Clayton6beaaa62011-01-17 03:46:26 +00001380 IdentifierTable *identifier_table = &ast->Idents;
Sean Callanan61da09b2010-09-17 02:58:26 +00001381
1382 assert(identifier_table);
1383
Sean Callananfc55f5d2010-09-21 00:44:12 +00001384 QualType record_qual_type(QualType::getFromOpaquePtr(record_opaque_type));
Greg Clayton0fffff52010-09-24 05:15:53 +00001385
Greg Clayton6beaaa62011-01-17 03:46:26 +00001386 CXXRecordDecl *cxx_record_decl = record_qual_type->getAsCXXRecordDecl();
Sean Callanan61da09b2010-09-17 02:58:26 +00001387
Greg Clayton0fffff52010-09-24 05:15:53 +00001388 if (cxx_record_decl == NULL)
Greg Claytona51ed9b2010-09-23 01:09:21 +00001389 return NULL;
Sean Callanan61da09b2010-09-17 02:58:26 +00001390
Greg Clayton0fffff52010-09-24 05:15:53 +00001391 QualType method_qual_type (QualType::getFromOpaquePtr (method_opaque_type));
Sean Callananfc55f5d2010-09-21 00:44:12 +00001392
Greg Claytonf51de672010-10-01 02:31:07 +00001393 CXXMethodDecl *cxx_method_decl = NULL;
Sean Callanan61da09b2010-09-17 02:58:26 +00001394
Greg Claytonf51de672010-10-01 02:31:07 +00001395 DeclarationName decl_name (&identifier_table->get(name));
Greg Clayton878eaf12010-10-01 03:45:20 +00001396
Greg Clayton878eaf12010-10-01 03:45:20 +00001397 const bool is_implicitly_declared = false;
Greg Claytonf51de672010-10-01 02:31:07 +00001398
Sean Callanan78e37602011-01-27 04:42:51 +00001399 const clang::FunctionType *function_Type = dyn_cast<FunctionType>(method_qual_type.getTypePtr());
Greg Clayton878eaf12010-10-01 03:45:20 +00001400
Greg Clayton90a2acd2010-10-02 01:40:05 +00001401 if (function_Type == NULL)
Greg Clayton878eaf12010-10-01 03:45:20 +00001402 return NULL;
1403
Sean Callanan78e37602011-01-27 04:42:51 +00001404 const FunctionProtoType *method_function_prototype (dyn_cast<FunctionProtoType>(function_Type));
Greg Clayton878eaf12010-10-01 03:45:20 +00001405
1406 if (!method_function_prototype)
1407 return NULL;
1408
1409 unsigned int num_params = method_function_prototype->getNumArgs();
1410
1411 if (name[0] == '~')
Greg Claytonf51de672010-10-01 02:31:07 +00001412 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001413 cxx_method_decl = CXXDestructorDecl::Create (*ast,
Greg Clayton878eaf12010-10-01 03:45:20 +00001414 cxx_record_decl,
Sean Callananfb0b7582011-03-15 00:17:19 +00001415 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00001416 DeclarationNameInfo (ast->DeclarationNames.getCXXDestructorName (ast->getCanonicalType (record_qual_type)), SourceLocation()),
Greg Clayton878eaf12010-10-01 03:45:20 +00001417 method_qual_type,
Sean Callanan31e851c2010-10-29 18:38:40 +00001418 NULL,
Greg Clayton878eaf12010-10-01 03:45:20 +00001419 is_inline,
1420 is_implicitly_declared);
1421 }
Greg Clayton6beaaa62011-01-17 03:46:26 +00001422 else if (decl_name == cxx_record_decl->getDeclName())
Greg Clayton878eaf12010-10-01 03:45:20 +00001423 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001424 cxx_method_decl = CXXConstructorDecl::Create (*ast,
Greg Claytonf51de672010-10-01 02:31:07 +00001425 cxx_record_decl,
Sean Callananfb0b7582011-03-15 00:17:19 +00001426 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00001427 DeclarationNameInfo (ast->DeclarationNames.getCXXConstructorName (ast->getCanonicalType (record_qual_type)), SourceLocation()),
Greg Claytonf51de672010-10-01 02:31:07 +00001428 method_qual_type,
1429 NULL, // TypeSourceInfo *
1430 is_explicit,
1431 is_inline,
1432 is_implicitly_declared);
1433 }
1434 else
Greg Clayton878eaf12010-10-01 03:45:20 +00001435 {
Greg Claytona3c444a2010-10-01 23:13:49 +00001436
1437 OverloadedOperatorKind op_kind = NUM_OVERLOADED_OPERATORS;
1438 if (IsOperator (name, op_kind))
Greg Clayton878eaf12010-10-01 03:45:20 +00001439 {
Greg Claytona3c444a2010-10-01 23:13:49 +00001440 if (op_kind != NUM_OVERLOADED_OPERATORS)
1441 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001442 cxx_method_decl = CXXMethodDecl::Create (*ast,
Greg Clayton878eaf12010-10-01 03:45:20 +00001443 cxx_record_decl,
Sean Callananfb0b7582011-03-15 00:17:19 +00001444 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00001445 DeclarationNameInfo (ast->DeclarationNames.getCXXOperatorName (op_kind), SourceLocation()),
Greg Clayton878eaf12010-10-01 03:45:20 +00001446 method_qual_type,
1447 NULL, // TypeSourceInfo *
Greg Claytona3c444a2010-10-01 23:13:49 +00001448 is_static,
1449 SC_None,
Sean Callananfb0b7582011-03-15 00:17:19 +00001450 is_inline,
1451 SourceLocation());
Greg Claytona3c444a2010-10-01 23:13:49 +00001452 }
1453 else if (num_params == 0)
1454 {
1455 // Conversion operators don't take params...
Greg Clayton6beaaa62011-01-17 03:46:26 +00001456 cxx_method_decl = CXXConversionDecl::Create (*ast,
Greg Claytona3c444a2010-10-01 23:13:49 +00001457 cxx_record_decl,
Sean Callananfb0b7582011-03-15 00:17:19 +00001458 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00001459 DeclarationNameInfo (ast->DeclarationNames.getCXXConversionFunctionName (ast->getCanonicalType (function_Type->getResultType())), SourceLocation()),
Greg Claytona3c444a2010-10-01 23:13:49 +00001460 method_qual_type,
1461 NULL, // TypeSourceInfo *
1462 is_inline,
Sean Callananfb0b7582011-03-15 00:17:19 +00001463 is_explicit,
1464 SourceLocation());
Greg Claytona3c444a2010-10-01 23:13:49 +00001465 }
Greg Clayton878eaf12010-10-01 03:45:20 +00001466 }
Greg Claytona3c444a2010-10-01 23:13:49 +00001467
1468 if (cxx_method_decl == NULL)
Greg Clayton878eaf12010-10-01 03:45:20 +00001469 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001470 cxx_method_decl = CXXMethodDecl::Create (*ast,
Greg Clayton878eaf12010-10-01 03:45:20 +00001471 cxx_record_decl,
Sean Callananfb0b7582011-03-15 00:17:19 +00001472 SourceLocation(),
Greg Claytona3c444a2010-10-01 23:13:49 +00001473 DeclarationNameInfo (decl_name, SourceLocation()),
Greg Clayton878eaf12010-10-01 03:45:20 +00001474 method_qual_type,
1475 NULL, // TypeSourceInfo *
1476 is_static,
1477 SC_None,
Sean Callananfb0b7582011-03-15 00:17:19 +00001478 is_inline,
1479 SourceLocation());
Greg Clayton878eaf12010-10-01 03:45:20 +00001480 }
Greg Claytonf51de672010-10-01 02:31:07 +00001481 }
Greg Claytona3c444a2010-10-01 23:13:49 +00001482
Greg Clayton1be10fc2010-09-29 01:12:09 +00001483 AccessSpecifier access_specifier = ConvertAccessTypeToAccessSpecifier (access);
Greg Clayton0fffff52010-09-24 05:15:53 +00001484
1485 cxx_method_decl->setAccess (access_specifier);
1486 cxx_method_decl->setVirtualAsWritten (is_virtual);
Sean Callanane2ef6e32010-09-23 03:01:22 +00001487
Sean Callananfc55f5d2010-09-21 00:44:12 +00001488 // Populate the method decl with parameter decls
Sean Callananfc55f5d2010-09-21 00:44:12 +00001489
Charles Davis8c444c42011-05-19 23:33:46 +00001490 llvm::SmallVector<ParmVarDecl *, 12> params;
Sean Callananfc55f5d2010-09-21 00:44:12 +00001491
1492 for (int param_index = 0;
1493 param_index < num_params;
1494 ++param_index)
1495 {
Charles Davis8c444c42011-05-19 23:33:46 +00001496 params.push_back (ParmVarDecl::Create (*ast,
1497 cxx_method_decl,
1498 SourceLocation(),
1499 SourceLocation(),
1500 NULL, // anonymous
1501 method_function_prototype->getArgType(param_index),
1502 NULL,
1503 SC_None,
1504 SC_None,
1505 NULL));
Sean Callananfc55f5d2010-09-21 00:44:12 +00001506 }
1507
Charles Davis8c444c42011-05-19 23:33:46 +00001508 cxx_method_decl->setParams (params.data(), num_params);
Sean Callananfc55f5d2010-09-21 00:44:12 +00001509
Greg Clayton0fffff52010-09-24 05:15:53 +00001510 cxx_record_decl->addDecl (cxx_method_decl);
Greg Claytonc432c192011-01-20 04:18:48 +00001511
1512// printf ("decl->isPolymorphic() = %i\n", cxx_record_decl->isPolymorphic());
1513// printf ("decl->isAggregate() = %i\n", cxx_record_decl->isAggregate());
1514// printf ("decl->isPOD() = %i\n", cxx_record_decl->isPOD());
1515// printf ("decl->isEmpty() = %i\n", cxx_record_decl->isEmpty());
1516// printf ("decl->isAbstract() = %i\n", cxx_record_decl->isAbstract());
1517// printf ("decl->hasTrivialConstructor() = %i\n", cxx_record_decl->hasTrivialConstructor());
1518// printf ("decl->hasTrivialCopyConstructor() = %i\n", cxx_record_decl->hasTrivialCopyConstructor());
1519// printf ("decl->hasTrivialCopyAssignment() = %i\n", cxx_record_decl->hasTrivialCopyAssignment());
1520// printf ("decl->hasTrivialDestructor() = %i\n", cxx_record_decl->hasTrivialDestructor());
Greg Claytona51ed9b2010-09-23 01:09:21 +00001521 return cxx_method_decl;
Sean Callanan61da09b2010-09-17 02:58:26 +00001522}
1523
1524bool
Greg Clayton8cf05932010-07-22 18:30:50 +00001525ClangASTContext::AddFieldToRecordType
1526(
Greg Clayton6beaaa62011-01-17 03:46:26 +00001527 ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001528 clang_type_t record_clang_type,
Greg Clayton8cf05932010-07-22 18:30:50 +00001529 const char *name,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001530 clang_type_t field_type,
Greg Clayton8cf05932010-07-22 18:30:50 +00001531 AccessType access,
1532 uint32_t bitfield_bit_size
1533)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001534{
1535 if (record_clang_type == NULL || field_type == NULL)
1536 return false;
1537
Greg Clayton6beaaa62011-01-17 03:46:26 +00001538 IdentifierTable *identifier_table = &ast->Idents;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001539
Greg Clayton6beaaa62011-01-17 03:46:26 +00001540 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001541 assert (identifier_table != NULL);
1542
1543 QualType record_qual_type(QualType::getFromOpaquePtr(record_clang_type));
1544
Sean Callanan78e37602011-01-27 04:42:51 +00001545 const clang::Type *clang_type = record_qual_type.getTypePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001546 if (clang_type)
1547 {
1548 const RecordType *record_type = dyn_cast<RecordType>(clang_type);
1549
1550 if (record_type)
1551 {
1552 RecordDecl *record_decl = record_type->getDecl();
1553
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001554 clang::Expr *bit_width = NULL;
1555 if (bitfield_bit_size != 0)
1556 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001557 APInt bitfield_bit_size_apint(ast->getTypeSize(ast->IntTy), bitfield_bit_size);
1558 bit_width = new (*ast)IntegerLiteral (*ast, bitfield_bit_size_apint, ast->IntTy, SourceLocation());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001559 }
Greg Clayton6beaaa62011-01-17 03:46:26 +00001560 FieldDecl *field = FieldDecl::Create (*ast,
Greg Clayton8cf05932010-07-22 18:30:50 +00001561 record_decl,
1562 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00001563 SourceLocation(),
Greg Clayton8cf05932010-07-22 18:30:50 +00001564 name ? &identifier_table->get(name) : NULL, // Identifier
1565 QualType::getFromOpaquePtr(field_type), // Field type
1566 NULL, // DeclaratorInfo *
1567 bit_width, // BitWidth
1568 false); // Mutable
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001569
Greg Clayton8cf05932010-07-22 18:30:50 +00001570 field->setAccess (ConvertAccessTypeToAccessSpecifier (access));
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001571
1572 if (field)
1573 {
1574 record_decl->addDecl(field);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001575 }
1576 }
Greg Clayton9e409562010-07-28 02:04:09 +00001577 else
1578 {
Sean Callanan78e37602011-01-27 04:42:51 +00001579 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(clang_type);
Greg Clayton9e409562010-07-28 02:04:09 +00001580 if (objc_class_type)
1581 {
Greg Clayton0fffff52010-09-24 05:15:53 +00001582 bool is_synthesized = false;
Greg Clayton6beaaa62011-01-17 03:46:26 +00001583 ClangASTContext::AddObjCClassIVar (ast,
Sean Callanan6e6a7c72010-09-16 20:01:08 +00001584 record_clang_type,
Greg Clayton9e409562010-07-28 02:04:09 +00001585 name,
1586 field_type,
1587 access,
1588 bitfield_bit_size,
Greg Clayton0fffff52010-09-24 05:15:53 +00001589 is_synthesized);
Greg Clayton9e409562010-07-28 02:04:09 +00001590 }
1591 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001592 }
1593 return false;
1594}
1595
1596bool
1597ClangASTContext::FieldIsBitfield (FieldDecl* field, uint32_t& bitfield_bit_size)
1598{
1599 return FieldIsBitfield(getASTContext(), field, bitfield_bit_size);
1600}
1601
1602bool
1603ClangASTContext::FieldIsBitfield
1604(
Greg Clayton6beaaa62011-01-17 03:46:26 +00001605 ASTContext *ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001606 FieldDecl* field,
1607 uint32_t& bitfield_bit_size
1608)
1609{
Greg Clayton6beaaa62011-01-17 03:46:26 +00001610 if (ast == NULL || field == NULL)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001611 return false;
1612
1613 if (field->isBitField())
1614 {
1615 Expr* bit_width_expr = field->getBitWidth();
1616 if (bit_width_expr)
1617 {
1618 llvm::APSInt bit_width_apsint;
Greg Clayton6beaaa62011-01-17 03:46:26 +00001619 if (bit_width_expr->isIntegerConstantExpr(bit_width_apsint, *ast))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001620 {
1621 bitfield_bit_size = bit_width_apsint.getLimitedValue(UINT32_MAX);
1622 return true;
1623 }
1624 }
1625 }
1626 return false;
1627}
1628
1629bool
1630ClangASTContext::RecordHasFields (const RecordDecl *record_decl)
1631{
1632 if (record_decl == NULL)
1633 return false;
1634
1635 if (!record_decl->field_empty())
1636 return true;
1637
1638 // No fields, lets check this is a CXX record and check the base classes
1639 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
1640 if (cxx_record_decl)
1641 {
1642 CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
1643 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
1644 base_class != base_class_end;
1645 ++base_class)
1646 {
1647 const CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
1648 if (RecordHasFields(base_class_decl))
1649 return true;
1650 }
1651 }
1652 return false;
1653}
1654
1655void
Greg Clayton6beaaa62011-01-17 03:46:26 +00001656ClangASTContext::SetDefaultAccessForRecordFields (clang_type_t clang_type, int default_accessibility, int *assigned_accessibilities, size_t num_assigned_accessibilities)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001657{
Greg Clayton6beaaa62011-01-17 03:46:26 +00001658 if (clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001659 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001660 QualType qual_type(QualType::getFromOpaquePtr(clang_type));
1661
Sean Callanan78e37602011-01-27 04:42:51 +00001662 const RecordType *record_type = dyn_cast<RecordType>(qual_type.getTypePtr());
Greg Clayton6beaaa62011-01-17 03:46:26 +00001663 if (record_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001664 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001665 RecordDecl *record_decl = record_type->getDecl();
1666 if (record_decl)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001667 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001668 uint32_t field_idx;
1669 RecordDecl::field_iterator field, field_end;
1670 for (field = record_decl->field_begin(), field_end = record_decl->field_end(), field_idx = 0;
1671 field != field_end;
1672 ++field, ++field_idx)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001673 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001674 // If no accessibility was assigned, assign the correct one
1675 if (field_idx < num_assigned_accessibilities && assigned_accessibilities[field_idx] == clang::AS_none)
1676 field->setAccess ((AccessSpecifier)default_accessibility);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001677 }
1678 }
1679 }
1680 }
1681}
1682
1683#pragma mark C++ Base Classes
1684
1685CXXBaseSpecifier *
Greg Clayton1be10fc2010-09-29 01:12:09 +00001686ClangASTContext::CreateBaseClassSpecifier (clang_type_t base_class_type, AccessType access, bool is_virtual, bool base_of_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001687{
1688 if (base_class_type)
Greg Claytone6371122010-07-30 20:30:44 +00001689 return new CXXBaseSpecifier (SourceRange(),
1690 is_virtual,
1691 base_of_class,
1692 ConvertAccessTypeToAccessSpecifier (access),
Sean Callanan2c777c42011-01-18 23:32:05 +00001693 getASTContext()->CreateTypeSourceInfo (QualType::getFromOpaquePtr(base_class_type)),
1694 SourceLocation());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001695 return NULL;
1696}
1697
Greg Clayton0b42ac32010-07-02 01:29:13 +00001698void
1699ClangASTContext::DeleteBaseClassSpecifiers (CXXBaseSpecifier **base_classes, unsigned num_base_classes)
1700{
1701 for (unsigned i=0; i<num_base_classes; ++i)
1702 {
1703 delete base_classes[i];
1704 base_classes[i] = NULL;
1705 }
1706}
1707
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001708bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00001709ClangASTContext::SetBaseClassesForClassType (clang_type_t class_clang_type, CXXBaseSpecifier const * const *base_classes, unsigned num_base_classes)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001710{
1711 if (class_clang_type)
1712 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001713 CXXRecordDecl *cxx_record_decl = QualType::getFromOpaquePtr(class_clang_type)->getAsCXXRecordDecl();
1714 if (cxx_record_decl)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001715 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001716 cxx_record_decl->setBases(base_classes, num_base_classes);
1717 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001718 }
1719 }
1720 return false;
1721}
Greg Clayton8cf05932010-07-22 18:30:50 +00001722#pragma mark Objective C Classes
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001723
Greg Clayton1be10fc2010-09-29 01:12:09 +00001724clang_type_t
Greg Clayton8cf05932010-07-22 18:30:50 +00001725ClangASTContext::CreateObjCClass
1726(
1727 const char *name,
1728 DeclContext *decl_ctx,
1729 bool isForwardDecl,
1730 bool isInternal
1731)
1732{
Greg Clayton6beaaa62011-01-17 03:46:26 +00001733 ASTContext *ast = getASTContext();
1734 assert (ast != NULL);
Greg Clayton8cf05932010-07-22 18:30:50 +00001735 assert (name && name[0]);
1736 if (decl_ctx == NULL)
Greg Clayton6beaaa62011-01-17 03:46:26 +00001737 decl_ctx = ast->getTranslationUnitDecl();
Greg Clayton8cf05932010-07-22 18:30:50 +00001738
1739 // NOTE: Eventually CXXRecordDecl will be merged back into RecordDecl and
1740 // we will need to update this code. I was told to currently always use
1741 // the CXXRecordDecl class since we often don't know from debug information
1742 // if something is struct or a class, so we default to always use the more
1743 // complete definition just in case.
Greg Clayton6beaaa62011-01-17 03:46:26 +00001744 ObjCInterfaceDecl *decl = ObjCInterfaceDecl::Create (*ast,
Greg Clayton8cf05932010-07-22 18:30:50 +00001745 decl_ctx,
1746 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00001747 &ast->Idents.get(name),
Greg Clayton8cf05932010-07-22 18:30:50 +00001748 SourceLocation(),
1749 isForwardDecl,
1750 isInternal);
Greg Clayton9e409562010-07-28 02:04:09 +00001751
Greg Clayton6beaaa62011-01-17 03:46:26 +00001752 return ast->getObjCInterfaceType(decl).getAsOpaquePtr();
Greg Clayton8cf05932010-07-22 18:30:50 +00001753}
1754
1755bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00001756ClangASTContext::SetObjCSuperClass (clang_type_t class_opaque_type, clang_type_t super_opaque_type)
Greg Clayton8cf05932010-07-22 18:30:50 +00001757{
1758 if (class_opaque_type && super_opaque_type)
1759 {
1760 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type));
1761 QualType super_qual_type(QualType::getFromOpaquePtr(super_opaque_type));
Sean Callanan78e37602011-01-27 04:42:51 +00001762 const clang::Type *class_type = class_qual_type.getTypePtr();
1763 const clang::Type *super_type = super_qual_type.getTypePtr();
Greg Clayton8cf05932010-07-22 18:30:50 +00001764 if (class_type && super_type)
1765 {
Sean Callanan78e37602011-01-27 04:42:51 +00001766 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type);
1767 const ObjCObjectType *objc_super_type = dyn_cast<ObjCObjectType>(super_type);
Greg Clayton8cf05932010-07-22 18:30:50 +00001768 if (objc_class_type && objc_super_type)
1769 {
1770 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
1771 ObjCInterfaceDecl *super_interface_decl = objc_super_type->getInterface();
1772 if (class_interface_decl && super_interface_decl)
1773 {
1774 class_interface_decl->setSuperClass(super_interface_decl);
1775 return true;
1776 }
1777 }
1778 }
1779 }
1780 return false;
1781}
1782
1783
1784bool
1785ClangASTContext::AddObjCClassIVar
1786(
Greg Clayton6beaaa62011-01-17 03:46:26 +00001787 ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001788 clang_type_t class_opaque_type,
Greg Clayton8cf05932010-07-22 18:30:50 +00001789 const char *name,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001790 clang_type_t ivar_opaque_type,
Greg Clayton8cf05932010-07-22 18:30:50 +00001791 AccessType access,
1792 uint32_t bitfield_bit_size,
Greg Clayton0fffff52010-09-24 05:15:53 +00001793 bool is_synthesized
Greg Clayton8cf05932010-07-22 18:30:50 +00001794)
1795{
1796 if (class_opaque_type == NULL || ivar_opaque_type == NULL)
1797 return false;
1798
Greg Clayton6beaaa62011-01-17 03:46:26 +00001799 IdentifierTable *identifier_table = &ast->Idents;
Greg Clayton8cf05932010-07-22 18:30:50 +00001800
Greg Clayton6beaaa62011-01-17 03:46:26 +00001801 assert (ast != NULL);
Greg Clayton8cf05932010-07-22 18:30:50 +00001802 assert (identifier_table != NULL);
1803
1804 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type));
1805
Sean Callanan78e37602011-01-27 04:42:51 +00001806 const clang::Type *class_type = class_qual_type.getTypePtr();
Greg Clayton8cf05932010-07-22 18:30:50 +00001807 if (class_type)
1808 {
Sean Callanan78e37602011-01-27 04:42:51 +00001809 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type);
Greg Clayton8cf05932010-07-22 18:30:50 +00001810
1811 if (objc_class_type)
1812 {
1813 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
1814
1815 if (class_interface_decl)
1816 {
1817 clang::Expr *bit_width = NULL;
1818 if (bitfield_bit_size != 0)
1819 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001820 APInt bitfield_bit_size_apint(ast->getTypeSize(ast->IntTy), bitfield_bit_size);
1821 bit_width = new (*ast)IntegerLiteral (*ast, bitfield_bit_size_apint, ast->IntTy, SourceLocation());
Greg Clayton8cf05932010-07-22 18:30:50 +00001822 }
1823
Greg Clayton6beaaa62011-01-17 03:46:26 +00001824 ObjCIvarDecl *field = ObjCIvarDecl::Create (*ast,
Greg Clayton9e409562010-07-28 02:04:09 +00001825 class_interface_decl,
1826 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00001827 SourceLocation(),
Greg Clayton9e409562010-07-28 02:04:09 +00001828 &identifier_table->get(name), // Identifier
1829 QualType::getFromOpaquePtr(ivar_opaque_type), // Field type
1830 NULL, // TypeSourceInfo *
1831 ConvertAccessTypeToObjCIvarAccessControl (access),
1832 bit_width,
Greg Clayton0fffff52010-09-24 05:15:53 +00001833 is_synthesized);
Greg Clayton9e409562010-07-28 02:04:09 +00001834
1835 if (field)
1836 {
1837 class_interface_decl->addDecl(field);
1838 return true;
1839 }
Greg Clayton8cf05932010-07-22 18:30:50 +00001840 }
1841 }
1842 }
1843 return false;
1844}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001845
Greg Clayton9e409562010-07-28 02:04:09 +00001846
1847bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00001848ClangASTContext::ObjCTypeHasIVars (clang_type_t class_opaque_type, bool check_superclass)
Greg Clayton9e409562010-07-28 02:04:09 +00001849{
1850 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type));
1851
Sean Callanan78e37602011-01-27 04:42:51 +00001852 const clang::Type *class_type = class_qual_type.getTypePtr();
Greg Clayton9e409562010-07-28 02:04:09 +00001853 if (class_type)
1854 {
Sean Callanan78e37602011-01-27 04:42:51 +00001855 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type);
Greg Clayton9e409562010-07-28 02:04:09 +00001856
1857 if (objc_class_type)
1858 return ObjCDeclHasIVars (objc_class_type->getInterface(), check_superclass);
1859 }
1860 return false;
1861}
1862
1863bool
1864ClangASTContext::ObjCDeclHasIVars (ObjCInterfaceDecl *class_interface_decl, bool check_superclass)
1865{
1866 while (class_interface_decl)
1867 {
1868 if (class_interface_decl->ivar_size() > 0)
1869 return true;
1870
1871 if (check_superclass)
1872 class_interface_decl = class_interface_decl->getSuperClass();
1873 else
1874 break;
1875 }
1876 return false;
1877}
Greg Clayton0fffff52010-09-24 05:15:53 +00001878
Greg Clayton1be10fc2010-09-29 01:12:09 +00001879ObjCMethodDecl *
Greg Clayton0fffff52010-09-24 05:15:53 +00001880ClangASTContext::AddMethodToObjCObjectType
1881(
Greg Clayton6beaaa62011-01-17 03:46:26 +00001882 ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00001883 clang_type_t class_opaque_type,
Greg Clayton0fffff52010-09-24 05:15:53 +00001884 const char *name, // the full symbol name as seen in the symbol table ("-[NString stringWithCString:]")
Greg Clayton1be10fc2010-09-29 01:12:09 +00001885 clang_type_t method_opaque_type,
Greg Clayton0fffff52010-09-24 05:15:53 +00001886 lldb::AccessType access
1887)
1888{
1889 if (class_opaque_type == NULL || method_opaque_type == NULL)
1890 return NULL;
1891
Greg Clayton6beaaa62011-01-17 03:46:26 +00001892 IdentifierTable *identifier_table = &ast->Idents;
Greg Clayton0fffff52010-09-24 05:15:53 +00001893
Greg Clayton6beaaa62011-01-17 03:46:26 +00001894 assert (ast != NULL);
Greg Clayton0fffff52010-09-24 05:15:53 +00001895 assert (identifier_table != NULL);
1896
1897 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type));
1898
Sean Callanan78e37602011-01-27 04:42:51 +00001899 const clang::Type *class_type = class_qual_type.getTypePtr();
Greg Clayton0fffff52010-09-24 05:15:53 +00001900 if (class_type == NULL)
1901 return NULL;
1902
Sean Callanan78e37602011-01-27 04:42:51 +00001903 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type);
Greg Clayton0fffff52010-09-24 05:15:53 +00001904
1905 if (objc_class_type == NULL)
1906 return NULL;
1907
1908 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
1909
1910 if (class_interface_decl == NULL)
1911 return NULL;
Greg Clayton9e409562010-07-28 02:04:09 +00001912
Greg Clayton0fffff52010-09-24 05:15:53 +00001913 const char *selector_start = ::strchr (name, ' ');
1914 if (selector_start == NULL)
1915 return NULL;
1916
1917 selector_start++;
1918 if (!(::isalpha (selector_start[0]) || selector_start[0] == '_'))
1919 return NULL;
1920 llvm::SmallVector<IdentifierInfo *, 12> selector_idents;
1921
Greg Clayton450e3f32010-10-12 02:24:53 +00001922 size_t len = 0;
Greg Clayton0fffff52010-09-24 05:15:53 +00001923 const char *start;
Greg Clayton450e3f32010-10-12 02:24:53 +00001924 //printf ("name = '%s'\n", name);
1925
1926 unsigned num_selectors_with_args = 0;
1927 for (start = selector_start;
Greg Clayton0fffff52010-09-24 05:15:53 +00001928 start && *start != '\0' && *start != ']';
Greg Clayton450e3f32010-10-12 02:24:53 +00001929 start += len)
Greg Clayton0fffff52010-09-24 05:15:53 +00001930 {
Greg Clayton450e3f32010-10-12 02:24:53 +00001931 len = ::strcspn(start, ":]");
Greg Clayton90f90cd2010-10-27 04:01:14 +00001932 bool has_arg = (start[len] == ':');
1933 if (has_arg)
Greg Clayton450e3f32010-10-12 02:24:53 +00001934 ++num_selectors_with_args;
Greg Clayton0fffff52010-09-24 05:15:53 +00001935 selector_idents.push_back (&identifier_table->get (StringRef (start, len)));
Greg Clayton90f90cd2010-10-27 04:01:14 +00001936 if (has_arg)
1937 len += 1;
Greg Clayton0fffff52010-09-24 05:15:53 +00001938 }
1939
1940
1941 if (selector_idents.size() == 0)
1942 return 0;
1943
Greg Clayton6beaaa62011-01-17 03:46:26 +00001944 clang::Selector method_selector = ast->Selectors.getSelector (num_selectors_with_args ? selector_idents.size() : 0,
Greg Clayton0fffff52010-09-24 05:15:53 +00001945 selector_idents.data());
1946
1947 QualType method_qual_type (QualType::getFromOpaquePtr (method_opaque_type));
1948
1949 // Populate the method decl with parameter decls
Sean Callanan78e37602011-01-27 04:42:51 +00001950 const clang::Type *method_type(method_qual_type.getTypePtr());
Greg Clayton0fffff52010-09-24 05:15:53 +00001951
1952 if (method_type == NULL)
1953 return NULL;
1954
Sean Callanan78e37602011-01-27 04:42:51 +00001955 const FunctionProtoType *method_function_prototype (dyn_cast<FunctionProtoType>(method_type));
Greg Clayton0fffff52010-09-24 05:15:53 +00001956
1957 if (!method_function_prototype)
1958 return NULL;
1959
1960
1961 bool is_variadic = false;
1962 bool is_synthesized = false;
1963 bool is_defined = false;
1964 ObjCMethodDecl::ImplementationControl imp_control = ObjCMethodDecl::None;
1965
1966 const unsigned num_args = method_function_prototype->getNumArgs();
1967
Greg Clayton6beaaa62011-01-17 03:46:26 +00001968 ObjCMethodDecl *objc_method_decl = ObjCMethodDecl::Create (*ast,
Greg Clayton0fffff52010-09-24 05:15:53 +00001969 SourceLocation(), // beginLoc,
1970 SourceLocation(), // endLoc,
1971 method_selector,
1972 method_function_prototype->getResultType(),
1973 NULL, // TypeSourceInfo *ResultTInfo,
1974 GetDeclContextForType (class_opaque_type),
1975 name[0] == '-',
1976 is_variadic,
1977 is_synthesized,
1978 is_defined,
1979 imp_control,
1980 num_args);
1981
1982
1983 if (objc_method_decl == NULL)
1984 return NULL;
1985
1986 if (num_args > 0)
1987 {
1988 llvm::SmallVector<ParmVarDecl *, 12> params;
1989
1990 for (int param_index = 0; param_index < num_args; ++param_index)
1991 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00001992 params.push_back (ParmVarDecl::Create (*ast,
Greg Clayton0fffff52010-09-24 05:15:53 +00001993 objc_method_decl,
1994 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00001995 SourceLocation(),
Greg Clayton0fffff52010-09-24 05:15:53 +00001996 NULL, // anonymous
1997 method_function_prototype->getArgType(param_index),
1998 NULL,
1999 SC_Auto,
2000 SC_Auto,
2001 NULL));
2002 }
2003
Greg Clayton6beaaa62011-01-17 03:46:26 +00002004 objc_method_decl->setMethodParams(*ast, params.data(), params.size(), num_args);
Greg Clayton0fffff52010-09-24 05:15:53 +00002005 }
2006
2007 class_interface_decl->addDecl (objc_method_decl);
2008
2009
2010 return objc_method_decl;
2011}
2012
2013
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002014uint32_t
Greg Clayton73b472d2010-10-27 03:32:59 +00002015ClangASTContext::GetTypeInfo
2016(
2017 clang_type_t clang_type,
Greg Clayton6beaaa62011-01-17 03:46:26 +00002018 clang::ASTContext *ast,
Greg Clayton73b472d2010-10-27 03:32:59 +00002019 clang_type_t *pointee_or_element_clang_type
2020)
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002021{
2022 if (clang_type == NULL)
Greg Clayton73b472d2010-10-27 03:32:59 +00002023 return 0;
2024
2025 if (pointee_or_element_clang_type)
2026 *pointee_or_element_clang_type = NULL;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002027
2028 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
2029
2030 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
2031 switch (type_class)
2032 {
Sean Callanana2424172010-10-25 00:29:48 +00002033 case clang::Type::Builtin:
2034 switch (cast<clang::BuiltinType>(qual_type)->getKind())
2035 {
Sean Callanana2424172010-10-25 00:29:48 +00002036 case clang::BuiltinType::ObjCId:
2037 case clang::BuiltinType::ObjCClass:
Greg Clayton6beaaa62011-01-17 03:46:26 +00002038 if (ast && pointee_or_element_clang_type)
2039 *pointee_or_element_clang_type = ast->ObjCBuiltinClassTy.getAsOpaquePtr();
Sean Callanana2424172010-10-25 00:29:48 +00002040 return eTypeIsBuiltIn | eTypeIsPointer | eTypeHasValue;
Greg Clayton73b472d2010-10-27 03:32:59 +00002041
2042 default:
2043 break;
Sean Callanana2424172010-10-25 00:29:48 +00002044 }
2045 return eTypeIsBuiltIn | eTypeHasValue;
Greg Clayton73b472d2010-10-27 03:32:59 +00002046
2047 case clang::Type::BlockPointer:
2048 if (pointee_or_element_clang_type)
2049 *pointee_or_element_clang_type = qual_type->getPointeeType().getAsOpaquePtr();
2050 return eTypeIsPointer | eTypeHasChildren | eTypeIsBlock;
2051
Greg Clayton49462ea2011-01-15 02:52:14 +00002052 case clang::Type::Complex: return eTypeIsBuiltIn | eTypeHasValue;
Greg Clayton73b472d2010-10-27 03:32:59 +00002053
2054 case clang::Type::ConstantArray:
2055 case clang::Type::DependentSizedArray:
2056 case clang::Type::IncompleteArray:
2057 case clang::Type::VariableArray:
2058 if (pointee_or_element_clang_type)
2059 *pointee_or_element_clang_type = cast<ArrayType>(qual_type.getTypePtr())->getElementType().getAsOpaquePtr();
2060 return eTypeHasChildren | eTypeIsArray;
2061
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002062 case clang::Type::DependentName: return 0;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002063 case clang::Type::DependentSizedExtVector: return eTypeHasChildren | eTypeIsVector;
2064 case clang::Type::DependentTemplateSpecialization: return eTypeIsTemplate;
2065 case clang::Type::Decltype: return 0;
Greg Clayton73b472d2010-10-27 03:32:59 +00002066
2067 case clang::Type::Enum:
2068 if (pointee_or_element_clang_type)
2069 *pointee_or_element_clang_type = cast<EnumType>(qual_type)->getDecl()->getIntegerType().getAsOpaquePtr();
2070 return eTypeIsEnumeration | eTypeHasValue;
2071
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002072 case clang::Type::Elaborated: return 0;
2073 case clang::Type::ExtVector: return eTypeHasChildren | eTypeIsVector;
2074 case clang::Type::FunctionProto: return eTypeIsFuncPrototype | eTypeHasValue;
2075 case clang::Type::FunctionNoProto: return eTypeIsFuncPrototype | eTypeHasValue;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002076 case clang::Type::InjectedClassName: return 0;
Greg Clayton73b472d2010-10-27 03:32:59 +00002077
2078 case clang::Type::LValueReference:
2079 case clang::Type::RValueReference:
2080 if (pointee_or_element_clang_type)
2081 *pointee_or_element_clang_type = cast<ReferenceType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr();
2082 return eTypeHasChildren | eTypeIsReference | eTypeHasValue;
2083
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002084 case clang::Type::MemberPointer: return eTypeIsPointer | eTypeIsMember | eTypeHasValue;
Greg Clayton73b472d2010-10-27 03:32:59 +00002085
2086 case clang::Type::ObjCObjectPointer:
2087 if (pointee_or_element_clang_type)
2088 *pointee_or_element_clang_type = qual_type->getPointeeType().getAsOpaquePtr();
2089 return eTypeHasChildren | eTypeIsObjC | eTypeIsClass | eTypeIsPointer | eTypeHasValue;
2090
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002091 case clang::Type::ObjCObject: return eTypeHasChildren | eTypeIsObjC | eTypeIsClass;
2092 case clang::Type::ObjCInterface: return eTypeHasChildren | eTypeIsObjC | eTypeIsClass;
Greg Clayton73b472d2010-10-27 03:32:59 +00002093
2094 case clang::Type::Pointer:
2095 if (pointee_or_element_clang_type)
2096 *pointee_or_element_clang_type = qual_type->getPointeeType().getAsOpaquePtr();
2097 return eTypeHasChildren | eTypeIsPointer | eTypeHasValue;
2098
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002099 case clang::Type::Record:
2100 if (qual_type->getAsCXXRecordDecl())
2101 return eTypeHasChildren | eTypeIsClass | eTypeIsCPlusPlus;
2102 else
2103 return eTypeHasChildren | eTypeIsStructUnion;
2104 break;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002105 case clang::Type::SubstTemplateTypeParm: return eTypeIsTemplate;
2106 case clang::Type::TemplateTypeParm: return eTypeIsTemplate;
2107 case clang::Type::TemplateSpecialization: return eTypeIsTemplate;
Greg Clayton73b472d2010-10-27 03:32:59 +00002108
2109 case clang::Type::Typedef:
Sean Callanan48114472010-12-13 01:26:27 +00002110 return eTypeIsTypedef | ClangASTContext::GetTypeInfo (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00002111 ast,
Greg Clayton73b472d2010-10-27 03:32:59 +00002112 pointee_or_element_clang_type);
2113
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002114 case clang::Type::TypeOfExpr: return 0;
2115 case clang::Type::TypeOf: return 0;
2116 case clang::Type::UnresolvedUsing: return 0;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002117 case clang::Type::Vector: return eTypeHasChildren | eTypeIsVector;
2118 default: return 0;
2119 }
2120 return 0;
2121}
2122
Greg Clayton9e409562010-07-28 02:04:09 +00002123
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002124#pragma mark Aggregate Types
2125
2126bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00002127ClangASTContext::IsAggregateType (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002128{
2129 if (clang_type == NULL)
2130 return false;
2131
2132 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
2133
Greg Clayton737b9322010-09-13 03:32:57 +00002134 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
2135 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002136 {
Greg Claytone1a916a2010-07-21 22:12:05 +00002137 case clang::Type::IncompleteArray:
2138 case clang::Type::VariableArray:
2139 case clang::Type::ConstantArray:
2140 case clang::Type::ExtVector:
2141 case clang::Type::Vector:
2142 case clang::Type::Record:
Greg Clayton9e409562010-07-28 02:04:09 +00002143 case clang::Type::ObjCObject:
2144 case clang::Type::ObjCInterface:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002145 return true;
2146
Greg Claytone1a916a2010-07-21 22:12:05 +00002147 case clang::Type::Typedef:
Sean Callanan48114472010-12-13 01:26:27 +00002148 return ClangASTContext::IsAggregateType (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002149
2150 default:
2151 break;
2152 }
2153 // The clang type does have a value
2154 return false;
2155}
2156
2157uint32_t
Greg Clayton6beaaa62011-01-17 03:46:26 +00002158ClangASTContext::GetNumChildren (clang::ASTContext *ast, clang_type_t clang_type, bool omit_empty_base_classes)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002159{
Greg Clayton6beaaa62011-01-17 03:46:26 +00002160 if (clang_type == NULL)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002161 return 0;
2162
2163 uint32_t num_children = 0;
Greg Clayton6beaaa62011-01-17 03:46:26 +00002164 QualType qual_type(QualType::getFromOpaquePtr(clang_type));
Greg Clayton9e409562010-07-28 02:04:09 +00002165 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
2166 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002167 {
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002168 case clang::Type::Builtin:
2169 switch (cast<clang::BuiltinType>(qual_type)->getKind())
2170 {
Greg Clayton73b472d2010-10-27 03:32:59 +00002171 case clang::BuiltinType::ObjCId: // child is Class
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002172 case clang::BuiltinType::ObjCClass: // child is Class
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002173 num_children = 1;
Greg Clayton73b472d2010-10-27 03:32:59 +00002174 break;
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002175
2176 default:
2177 break;
2178 }
2179 break;
Greg Clayton54979cd2010-12-15 05:08:08 +00002180
Greg Clayton49462ea2011-01-15 02:52:14 +00002181 case clang::Type::Complex: return 0;
Greg Clayton54979cd2010-12-15 05:08:08 +00002182
Greg Claytone1a916a2010-07-21 22:12:05 +00002183 case clang::Type::Record:
Greg Claytonc432c192011-01-20 04:18:48 +00002184 if (GetCompleteQualType (ast, qual_type))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002185 {
2186 const RecordType *record_type = cast<RecordType>(qual_type.getTypePtr());
2187 const RecordDecl *record_decl = record_type->getDecl();
2188 assert(record_decl);
2189 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
2190 if (cxx_record_decl)
2191 {
2192 if (omit_empty_base_classes)
2193 {
2194 // Check each base classes to see if it or any of its
2195 // base classes contain any fields. This can help
2196 // limit the noise in variable views by not having to
2197 // show base classes that contain no members.
2198 CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
2199 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
2200 base_class != base_class_end;
2201 ++base_class)
2202 {
2203 const CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
2204
2205 // Skip empty base classes
2206 if (RecordHasFields(base_class_decl) == false)
2207 continue;
2208
2209 num_children++;
2210 }
2211 }
2212 else
2213 {
2214 // Include all base classes
2215 num_children += cxx_record_decl->getNumBases();
2216 }
2217
2218 }
2219 RecordDecl::field_iterator field, field_end;
2220 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field)
2221 ++num_children;
2222 }
2223 break;
2224
Greg Clayton9e409562010-07-28 02:04:09 +00002225 case clang::Type::ObjCObject:
2226 case clang::Type::ObjCInterface:
Greg Claytonc432c192011-01-20 04:18:48 +00002227 if (GetCompleteQualType (ast, qual_type))
Greg Clayton9e409562010-07-28 02:04:09 +00002228 {
Sean Callanan78e37602011-01-27 04:42:51 +00002229 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr());
Greg Clayton9e409562010-07-28 02:04:09 +00002230 assert (objc_class_type);
2231 if (objc_class_type)
2232 {
2233 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
2234
2235 if (class_interface_decl)
2236 {
2237
2238 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
2239 if (superclass_interface_decl)
2240 {
2241 if (omit_empty_base_classes)
2242 {
2243 if (ClangASTContext::ObjCDeclHasIVars (superclass_interface_decl, true))
2244 ++num_children;
2245 }
2246 else
2247 ++num_children;
2248 }
2249
2250 num_children += class_interface_decl->ivar_size();
2251 }
2252 }
2253 }
2254 break;
2255
2256 case clang::Type::ObjCObjectPointer:
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002257 {
Sean Callanan78e37602011-01-27 04:42:51 +00002258 const ObjCObjectPointerType *pointer_type = cast<ObjCObjectPointerType>(qual_type.getTypePtr());
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002259 QualType pointee_type = pointer_type->getPointeeType();
Greg Clayton6beaaa62011-01-17 03:46:26 +00002260 uint32_t num_pointee_children = ClangASTContext::GetNumChildren (ast,
2261 pointee_type.getAsOpaquePtr(),
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002262 omit_empty_base_classes);
2263 // If this type points to a simple type, then it has 1 child
2264 if (num_pointee_children == 0)
2265 num_children = 1;
2266 else
2267 num_children = num_pointee_children;
2268 }
2269 break;
Greg Clayton9e409562010-07-28 02:04:09 +00002270
Greg Claytone1a916a2010-07-21 22:12:05 +00002271 case clang::Type::ConstantArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002272 num_children = cast<ConstantArrayType>(qual_type.getTypePtr())->getSize().getLimitedValue();
2273 break;
2274
Greg Claytone1a916a2010-07-21 22:12:05 +00002275 case clang::Type::Pointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002276 {
Sean Callanan78e37602011-01-27 04:42:51 +00002277 const PointerType *pointer_type = cast<PointerType>(qual_type.getTypePtr());
Greg Clayton54979cd2010-12-15 05:08:08 +00002278 QualType pointee_type (pointer_type->getPointeeType());
Greg Clayton6beaaa62011-01-17 03:46:26 +00002279 uint32_t num_pointee_children = ClangASTContext::GetNumChildren (ast,
2280 pointee_type.getAsOpaquePtr(),
Greg Clayton9e409562010-07-28 02:04:09 +00002281 omit_empty_base_classes);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002282 if (num_pointee_children == 0)
Greg Clayton54979cd2010-12-15 05:08:08 +00002283 {
2284 // We have a pointer to a pointee type that claims it has no children.
2285 // We will want to look at
2286 num_children = ClangASTContext::GetNumPointeeChildren (pointee_type.getAsOpaquePtr());
2287 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002288 else
2289 num_children = num_pointee_children;
2290 }
2291 break;
2292
Greg Clayton73b472d2010-10-27 03:32:59 +00002293 case clang::Type::LValueReference:
2294 case clang::Type::RValueReference:
2295 {
Sean Callanan78e37602011-01-27 04:42:51 +00002296 const ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr());
Greg Clayton73b472d2010-10-27 03:32:59 +00002297 QualType pointee_type = reference_type->getPointeeType();
Greg Clayton6beaaa62011-01-17 03:46:26 +00002298 uint32_t num_pointee_children = ClangASTContext::GetNumChildren (ast,
2299 pointee_type.getAsOpaquePtr(),
Greg Clayton73b472d2010-10-27 03:32:59 +00002300 omit_empty_base_classes);
2301 // If this type points to a simple type, then it has 1 child
2302 if (num_pointee_children == 0)
2303 num_children = 1;
2304 else
2305 num_children = num_pointee_children;
2306 }
2307 break;
2308
2309
Greg Claytone1a916a2010-07-21 22:12:05 +00002310 case clang::Type::Typedef:
Greg Clayton6beaaa62011-01-17 03:46:26 +00002311 num_children = ClangASTContext::GetNumChildren (ast,
2312 cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
2313 omit_empty_base_classes);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002314 break;
2315
2316 default:
2317 break;
2318 }
2319 return num_children;
2320}
2321
Greg Clayton54979cd2010-12-15 05:08:08 +00002322// If a pointer to a pointee type (the clang_type arg) says that it has no
2323// children, then we either need to trust it, or override it and return a
2324// different result. For example, an "int *" has one child that is an integer,
2325// but a function pointer doesn't have any children. Likewise if a Record type
2326// claims it has no children, then there really is nothing to show.
2327uint32_t
2328ClangASTContext::GetNumPointeeChildren (clang_type_t clang_type)
2329{
2330 if (clang_type == NULL)
2331 return 0;
2332
2333 QualType qual_type(QualType::getFromOpaquePtr(clang_type));
2334 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
2335 switch (type_class)
2336 {
Greg Clayton97a43712011-01-08 22:26:47 +00002337 case clang::Type::Builtin:
2338 switch (cast<clang::BuiltinType>(qual_type)->getKind())
2339 {
Greg Clayton7260f622011-04-18 08:33:37 +00002340 case clang::BuiltinType::UnknownAny:
Greg Clayton97a43712011-01-08 22:26:47 +00002341 case clang::BuiltinType::Void:
2342 case clang::BuiltinType::NullPtr:
2343 return 0;
2344 case clang::BuiltinType::Bool:
2345 case clang::BuiltinType::Char_U:
2346 case clang::BuiltinType::UChar:
Sean Callanan2c777c42011-01-18 23:32:05 +00002347 case clang::BuiltinType::WChar_U:
Greg Clayton97a43712011-01-08 22:26:47 +00002348 case clang::BuiltinType::Char16:
2349 case clang::BuiltinType::Char32:
2350 case clang::BuiltinType::UShort:
2351 case clang::BuiltinType::UInt:
2352 case clang::BuiltinType::ULong:
2353 case clang::BuiltinType::ULongLong:
2354 case clang::BuiltinType::UInt128:
2355 case clang::BuiltinType::Char_S:
2356 case clang::BuiltinType::SChar:
Sean Callanan2c777c42011-01-18 23:32:05 +00002357 case clang::BuiltinType::WChar_S:
Greg Clayton97a43712011-01-08 22:26:47 +00002358 case clang::BuiltinType::Short:
2359 case clang::BuiltinType::Int:
2360 case clang::BuiltinType::Long:
2361 case clang::BuiltinType::LongLong:
2362 case clang::BuiltinType::Int128:
2363 case clang::BuiltinType::Float:
2364 case clang::BuiltinType::Double:
2365 case clang::BuiltinType::LongDouble:
2366 case clang::BuiltinType::Dependent:
2367 case clang::BuiltinType::Overload:
Greg Clayton97a43712011-01-08 22:26:47 +00002368 case clang::BuiltinType::ObjCId:
2369 case clang::BuiltinType::ObjCClass:
2370 case clang::BuiltinType::ObjCSel:
Sean Callanand12cf8bb2011-05-15 22:34:38 +00002371 case clang::BuiltinType::BoundMember:
Greg Clayton97a43712011-01-08 22:26:47 +00002372 return 1;
2373 }
2374 break;
2375
Greg Clayton49462ea2011-01-15 02:52:14 +00002376 case clang::Type::Complex: return 1;
Greg Clayton54979cd2010-12-15 05:08:08 +00002377 case clang::Type::Pointer: return 1;
2378 case clang::Type::BlockPointer: return 0; // If block pointers don't have debug info, then no children for them
2379 case clang::Type::LValueReference: return 1;
2380 case clang::Type::RValueReference: return 1;
2381 case clang::Type::MemberPointer: return 0;
2382 case clang::Type::ConstantArray: return 0;
2383 case clang::Type::IncompleteArray: return 0;
2384 case clang::Type::VariableArray: return 0;
2385 case clang::Type::DependentSizedArray: return 0;
2386 case clang::Type::DependentSizedExtVector: return 0;
2387 case clang::Type::Vector: return 0;
2388 case clang::Type::ExtVector: return 0;
2389 case clang::Type::FunctionProto: return 0; // When we function pointers, they have no children...
2390 case clang::Type::FunctionNoProto: return 0; // When we function pointers, they have no children...
2391 case clang::Type::UnresolvedUsing: return 0;
2392 case clang::Type::Paren: return 0;
2393 case clang::Type::Typedef: return ClangASTContext::GetNumPointeeChildren (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
2394 case clang::Type::TypeOfExpr: return 0;
2395 case clang::Type::TypeOf: return 0;
2396 case clang::Type::Decltype: return 0;
2397 case clang::Type::Record: return 0;
2398 case clang::Type::Enum: return 1;
2399 case clang::Type::Elaborated: return 1;
2400 case clang::Type::TemplateTypeParm: return 1;
2401 case clang::Type::SubstTemplateTypeParm: return 1;
2402 case clang::Type::TemplateSpecialization: return 1;
2403 case clang::Type::InjectedClassName: return 0;
2404 case clang::Type::DependentName: return 1;
2405 case clang::Type::DependentTemplateSpecialization: return 1;
2406 case clang::Type::ObjCObject: return 0;
2407 case clang::Type::ObjCInterface: return 0;
2408 case clang::Type::ObjCObjectPointer: return 1;
2409 default:
2410 break;
2411 }
2412 return 0;
2413}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002414
Greg Clayton1be10fc2010-09-29 01:12:09 +00002415clang_type_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002416ClangASTContext::GetChildClangTypeAtIndex
2417(
2418 const char *parent_name,
Greg Clayton1be10fc2010-09-29 01:12:09 +00002419 clang_type_t parent_clang_type,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002420 uint32_t idx,
2421 bool transparent_pointers,
2422 bool omit_empty_base_classes,
2423 std::string& child_name,
2424 uint32_t &child_byte_size,
2425 int32_t &child_byte_offset,
2426 uint32_t &child_bitfield_bit_size,
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002427 uint32_t &child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002428 bool &child_is_base_class,
2429 bool &child_is_deref_of_parent
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002430)
2431{
2432 if (parent_clang_type)
2433
2434 return GetChildClangTypeAtIndex (getASTContext(),
2435 parent_name,
2436 parent_clang_type,
2437 idx,
2438 transparent_pointers,
2439 omit_empty_base_classes,
2440 child_name,
2441 child_byte_size,
2442 child_byte_offset,
2443 child_bitfield_bit_size,
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002444 child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002445 child_is_base_class,
2446 child_is_deref_of_parent);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002447 return NULL;
2448}
2449
Greg Clayton1be10fc2010-09-29 01:12:09 +00002450clang_type_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002451ClangASTContext::GetChildClangTypeAtIndex
2452(
Greg Clayton6beaaa62011-01-17 03:46:26 +00002453 ASTContext *ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002454 const char *parent_name,
Greg Clayton1be10fc2010-09-29 01:12:09 +00002455 clang_type_t parent_clang_type,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002456 uint32_t idx,
2457 bool transparent_pointers,
2458 bool omit_empty_base_classes,
2459 std::string& child_name,
2460 uint32_t &child_byte_size,
2461 int32_t &child_byte_offset,
2462 uint32_t &child_bitfield_bit_size,
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002463 uint32_t &child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002464 bool &child_is_base_class,
2465 bool &child_is_deref_of_parent
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002466)
2467{
2468 if (parent_clang_type == NULL)
2469 return NULL;
2470
Greg Clayton6beaaa62011-01-17 03:46:26 +00002471 if (idx < ClangASTContext::GetNumChildren (ast, parent_clang_type, omit_empty_base_classes))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002472 {
2473 uint32_t bit_offset;
2474 child_bitfield_bit_size = 0;
2475 child_bitfield_bit_offset = 0;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002476 child_is_base_class = false;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002477 QualType parent_qual_type(QualType::getFromOpaquePtr(parent_clang_type));
Greg Clayton737b9322010-09-13 03:32:57 +00002478 const clang::Type::TypeClass parent_type_class = parent_qual_type->getTypeClass();
2479 switch (parent_type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002480 {
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002481 case clang::Type::Builtin:
2482 switch (cast<clang::BuiltinType>(parent_qual_type)->getKind())
2483 {
2484 case clang::BuiltinType::ObjCId:
2485 case clang::BuiltinType::ObjCClass:
Sean Callanana2424172010-10-25 00:29:48 +00002486 child_name = "isa";
Greg Clayton6beaaa62011-01-17 03:46:26 +00002487 child_byte_size = ast->getTypeSize(ast->ObjCBuiltinClassTy) / CHAR_BIT;
2488 return ast->ObjCBuiltinClassTy.getAsOpaquePtr();
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002489
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002490 default:
2491 break;
2492 }
2493 break;
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002494
Greg Claytone1a916a2010-07-21 22:12:05 +00002495 case clang::Type::Record:
Greg Claytonc432c192011-01-20 04:18:48 +00002496 if (GetCompleteQualType (ast, parent_qual_type))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002497 {
2498 const RecordType *record_type = cast<RecordType>(parent_qual_type.getTypePtr());
2499 const RecordDecl *record_decl = record_type->getDecl();
2500 assert(record_decl);
Greg Clayton6beaaa62011-01-17 03:46:26 +00002501 const ASTRecordLayout &record_layout = ast->getASTRecordLayout(record_decl);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002502 uint32_t child_idx = 0;
2503
2504 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
2505 if (cxx_record_decl)
2506 {
2507 // We might have base classes to print out first
2508 CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
2509 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
2510 base_class != base_class_end;
2511 ++base_class)
2512 {
2513 const CXXRecordDecl *base_class_decl = NULL;
2514
2515 // Skip empty base classes
2516 if (omit_empty_base_classes)
2517 {
2518 base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
2519 if (RecordHasFields(base_class_decl) == false)
2520 continue;
2521 }
2522
2523 if (idx == child_idx)
2524 {
2525 if (base_class_decl == NULL)
2526 base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
2527
2528
2529 if (base_class->isVirtual())
Greg Clayton6ed95942011-01-22 07:12:45 +00002530 bit_offset = record_layout.getVBaseClassOffset(base_class_decl).getQuantity() * 8;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002531 else
Greg Clayton6ed95942011-01-22 07:12:45 +00002532 bit_offset = record_layout.getBaseClassOffset(base_class_decl).getQuantity() * 8;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002533
2534 // Base classes should be a multiple of 8 bits in size
2535 assert (bit_offset % 8 == 0);
2536 child_byte_offset = bit_offset/8;
2537 std::string base_class_type_name(base_class->getType().getAsString());
2538
2539 child_name.assign(base_class_type_name.c_str());
2540
Greg Clayton6beaaa62011-01-17 03:46:26 +00002541 uint64_t clang_type_info_bit_size = ast->getTypeSize(base_class->getType());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002542
Jim Inghamf46b3382011-04-15 23:42:06 +00002543 // Base classes bit sizes should be a multiple of 8 bits in size
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002544 assert (clang_type_info_bit_size % 8 == 0);
2545 child_byte_size = clang_type_info_bit_size / 8;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002546 child_is_base_class = true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002547 return base_class->getType().getAsOpaquePtr();
2548 }
2549 // We don't increment the child index in the for loop since we might
2550 // be skipping empty base classes
2551 ++child_idx;
2552 }
2553 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002554 // Make sure index is in range...
2555 uint32_t field_idx = 0;
2556 RecordDecl::field_iterator field, field_end;
2557 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field, ++field_idx, ++child_idx)
2558 {
2559 if (idx == child_idx)
2560 {
2561 // Print the member type if requested
2562 // Print the member name and equal sign
2563 child_name.assign(field->getNameAsString().c_str());
2564
2565 // Figure out the type byte size (field_type_info.first) and
2566 // alignment (field_type_info.second) from the AST context.
Greg Clayton6beaaa62011-01-17 03:46:26 +00002567 std::pair<uint64_t, unsigned> field_type_info = ast->getTypeInfo(field->getType());
Greg Claytonc982c762010-07-09 20:39:50 +00002568 assert(field_idx < record_layout.getFieldCount());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002569
2570 child_byte_size = field_type_info.first / 8;
2571
2572 // Figure out the field offset within the current struct/union/class type
2573 bit_offset = record_layout.getFieldOffset (field_idx);
2574 child_byte_offset = bit_offset / 8;
Greg Clayton6beaaa62011-01-17 03:46:26 +00002575 if (ClangASTContext::FieldIsBitfield (ast, *field, child_bitfield_bit_size))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002576 child_bitfield_bit_offset = bit_offset % 8;
2577
2578 return field->getType().getAsOpaquePtr();
2579 }
2580 }
2581 }
2582 break;
2583
Greg Clayton9e409562010-07-28 02:04:09 +00002584 case clang::Type::ObjCObject:
2585 case clang::Type::ObjCInterface:
Greg Claytonc432c192011-01-20 04:18:48 +00002586 if (GetCompleteQualType (ast, parent_qual_type))
Greg Clayton9e409562010-07-28 02:04:09 +00002587 {
Sean Callanan78e37602011-01-27 04:42:51 +00002588 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(parent_qual_type.getTypePtr());
Greg Clayton9e409562010-07-28 02:04:09 +00002589 assert (objc_class_type);
2590 if (objc_class_type)
2591 {
2592 uint32_t child_idx = 0;
2593 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
2594
2595 if (class_interface_decl)
2596 {
2597
Greg Clayton6beaaa62011-01-17 03:46:26 +00002598 const ASTRecordLayout &interface_layout = ast->getASTObjCInterfaceLayout(class_interface_decl);
Greg Clayton9e409562010-07-28 02:04:09 +00002599 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
2600 if (superclass_interface_decl)
2601 {
2602 if (omit_empty_base_classes)
2603 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00002604 if (ClangASTContext::GetNumChildren(ast, ast->getObjCInterfaceType(superclass_interface_decl).getAsOpaquePtr(), omit_empty_base_classes) > 0)
Greg Clayton9e409562010-07-28 02:04:09 +00002605 {
2606 if (idx == 0)
2607 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00002608 QualType ivar_qual_type(ast->getObjCInterfaceType(superclass_interface_decl));
Greg Clayton9e409562010-07-28 02:04:09 +00002609
2610
2611 child_name.assign(superclass_interface_decl->getNameAsString().c_str());
2612
Greg Clayton6beaaa62011-01-17 03:46:26 +00002613 std::pair<uint64_t, unsigned> ivar_type_info = ast->getTypeInfo(ivar_qual_type.getTypePtr());
Greg Clayton9e409562010-07-28 02:04:09 +00002614
2615 child_byte_size = ivar_type_info.first / 8;
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002616 child_byte_offset = 0;
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002617 child_is_base_class = true;
Greg Clayton9e409562010-07-28 02:04:09 +00002618
2619 return ivar_qual_type.getAsOpaquePtr();
2620 }
2621
2622 ++child_idx;
2623 }
2624 }
2625 else
2626 ++child_idx;
2627 }
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002628
2629 const uint32_t superclass_idx = child_idx;
Greg Clayton9e409562010-07-28 02:04:09 +00002630
2631 if (idx < (child_idx + class_interface_decl->ivar_size()))
2632 {
2633 ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
2634
2635 for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos)
2636 {
2637 if (child_idx == idx)
2638 {
2639 const ObjCIvarDecl* ivar_decl = *ivar_pos;
2640
2641 QualType ivar_qual_type(ivar_decl->getType());
2642
2643 child_name.assign(ivar_decl->getNameAsString().c_str());
2644
Greg Clayton6beaaa62011-01-17 03:46:26 +00002645 std::pair<uint64_t, unsigned> ivar_type_info = ast->getTypeInfo(ivar_qual_type.getTypePtr());
Greg Clayton9e409562010-07-28 02:04:09 +00002646
2647 child_byte_size = ivar_type_info.first / 8;
2648
2649 // Figure out the field offset within the current struct/union/class type
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002650 bit_offset = interface_layout.getFieldOffset (child_idx - superclass_idx);
Greg Clayton9e409562010-07-28 02:04:09 +00002651 child_byte_offset = bit_offset / 8;
2652
2653 return ivar_qual_type.getAsOpaquePtr();
2654 }
2655 ++child_idx;
2656 }
2657 }
2658 }
2659 }
2660 }
2661 break;
2662
2663 case clang::Type::ObjCObjectPointer:
2664 {
Sean Callanan78e37602011-01-27 04:42:51 +00002665 const ObjCObjectPointerType *pointer_type = cast<ObjCObjectPointerType>(parent_qual_type.getTypePtr());
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002666 QualType pointee_type = pointer_type->getPointeeType();
2667
2668 if (transparent_pointers && ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
2669 {
Greg Claytone221f822011-01-21 01:59:00 +00002670 child_is_deref_of_parent = false;
2671 bool tmp_child_is_deref_of_parent = false;
Greg Clayton6beaaa62011-01-17 03:46:26 +00002672 return GetChildClangTypeAtIndex (ast,
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002673 parent_name,
2674 pointer_type->getPointeeType().getAsOpaquePtr(),
2675 idx,
2676 transparent_pointers,
2677 omit_empty_base_classes,
2678 child_name,
2679 child_byte_size,
2680 child_byte_offset,
2681 child_bitfield_bit_size,
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002682 child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002683 child_is_base_class,
2684 tmp_child_is_deref_of_parent);
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002685 }
2686 else
2687 {
Greg Claytone221f822011-01-21 01:59:00 +00002688 child_is_deref_of_parent = true;
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002689 if (parent_name)
2690 {
2691 child_name.assign(1, '*');
2692 child_name += parent_name;
2693 }
2694
2695 // We have a pointer to an simple type
2696 if (idx == 0)
2697 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00002698 std::pair<uint64_t, unsigned> clang_type_info = ast->getTypeInfo(pointee_type);
Greg Claytonb0b9fe62010-08-03 00:35:52 +00002699 assert(clang_type_info.first % 8 == 0);
2700 child_byte_size = clang_type_info.first / 8;
2701 child_byte_offset = 0;
2702 return pointee_type.getAsOpaquePtr();
2703 }
2704 }
Greg Clayton9e409562010-07-28 02:04:09 +00002705 }
2706 break;
2707
Greg Claytone1a916a2010-07-21 22:12:05 +00002708 case clang::Type::ConstantArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002709 {
2710 const ConstantArrayType *array = cast<ConstantArrayType>(parent_qual_type.getTypePtr());
2711 const uint64_t element_count = array->getSize().getLimitedValue();
2712
2713 if (idx < element_count)
2714 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00002715 if (GetCompleteQualType (ast, array->getElementType()))
2716 {
2717 std::pair<uint64_t, unsigned> field_type_info = ast->getTypeInfo(array->getElementType());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002718
Greg Clayton6beaaa62011-01-17 03:46:26 +00002719 char element_name[64];
2720 ::snprintf (element_name, sizeof (element_name), "[%u]", idx);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002721
Greg Clayton6beaaa62011-01-17 03:46:26 +00002722 child_name.assign(element_name);
2723 assert(field_type_info.first % 8 == 0);
2724 child_byte_size = field_type_info.first / 8;
2725 child_byte_offset = idx * child_byte_size;
2726 return array->getElementType().getAsOpaquePtr();
2727 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002728 }
2729 }
2730 break;
2731
Greg Claytone1a916a2010-07-21 22:12:05 +00002732 case clang::Type::Pointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002733 {
Sean Callanan78e37602011-01-27 04:42:51 +00002734 const PointerType *pointer_type = cast<PointerType>(parent_qual_type.getTypePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002735 QualType pointee_type = pointer_type->getPointeeType();
Greg Clayton97a43712011-01-08 22:26:47 +00002736
2737 // Don't dereference "void *" pointers
2738 if (pointee_type->isVoidType())
2739 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002740
2741 if (transparent_pointers && ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
2742 {
Greg Claytone221f822011-01-21 01:59:00 +00002743 child_is_deref_of_parent = false;
2744 bool tmp_child_is_deref_of_parent = false;
Greg Clayton6beaaa62011-01-17 03:46:26 +00002745 return GetChildClangTypeAtIndex (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002746 parent_name,
2747 pointer_type->getPointeeType().getAsOpaquePtr(),
2748 idx,
2749 transparent_pointers,
2750 omit_empty_base_classes,
2751 child_name,
2752 child_byte_size,
2753 child_byte_offset,
2754 child_bitfield_bit_size,
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002755 child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002756 child_is_base_class,
2757 tmp_child_is_deref_of_parent);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002758 }
2759 else
2760 {
Greg Claytone221f822011-01-21 01:59:00 +00002761 child_is_deref_of_parent = true;
2762
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002763 if (parent_name)
2764 {
2765 child_name.assign(1, '*');
2766 child_name += parent_name;
2767 }
2768
2769 // We have a pointer to an simple type
2770 if (idx == 0)
2771 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00002772 std::pair<uint64_t, unsigned> clang_type_info = ast->getTypeInfo(pointee_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002773 assert(clang_type_info.first % 8 == 0);
2774 child_byte_size = clang_type_info.first / 8;
2775 child_byte_offset = 0;
2776 return pointee_type.getAsOpaquePtr();
2777 }
2778 }
2779 }
2780 break;
2781
Greg Clayton73b472d2010-10-27 03:32:59 +00002782 case clang::Type::LValueReference:
2783 case clang::Type::RValueReference:
2784 {
Sean Callanan78e37602011-01-27 04:42:51 +00002785 const ReferenceType *reference_type = cast<ReferenceType>(parent_qual_type.getTypePtr());
Greg Clayton73b472d2010-10-27 03:32:59 +00002786 QualType pointee_type(reference_type->getPointeeType());
2787 clang_type_t pointee_clang_type = pointee_type.getAsOpaquePtr();
2788 if (transparent_pointers && ClangASTContext::IsAggregateType (pointee_clang_type))
2789 {
Greg Claytone221f822011-01-21 01:59:00 +00002790 child_is_deref_of_parent = false;
2791 bool tmp_child_is_deref_of_parent = false;
Greg Clayton6beaaa62011-01-17 03:46:26 +00002792 return GetChildClangTypeAtIndex (ast,
Greg Clayton73b472d2010-10-27 03:32:59 +00002793 parent_name,
2794 pointee_clang_type,
2795 idx,
2796 transparent_pointers,
2797 omit_empty_base_classes,
2798 child_name,
2799 child_byte_size,
2800 child_byte_offset,
2801 child_bitfield_bit_size,
2802 child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002803 child_is_base_class,
2804 tmp_child_is_deref_of_parent);
Greg Clayton73b472d2010-10-27 03:32:59 +00002805 }
2806 else
2807 {
2808 if (parent_name)
2809 {
2810 child_name.assign(1, '&');
2811 child_name += parent_name;
2812 }
2813
2814 // We have a pointer to an simple type
2815 if (idx == 0)
2816 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00002817 std::pair<uint64_t, unsigned> clang_type_info = ast->getTypeInfo(pointee_type);
Greg Clayton73b472d2010-10-27 03:32:59 +00002818 assert(clang_type_info.first % 8 == 0);
2819 child_byte_size = clang_type_info.first / 8;
2820 child_byte_offset = 0;
2821 return pointee_type.getAsOpaquePtr();
2822 }
2823 }
2824 }
2825 break;
2826
Greg Claytone1a916a2010-07-21 22:12:05 +00002827 case clang::Type::Typedef:
Greg Clayton6beaaa62011-01-17 03:46:26 +00002828 return GetChildClangTypeAtIndex (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002829 parent_name,
Sean Callanan48114472010-12-13 01:26:27 +00002830 cast<TypedefType>(parent_qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002831 idx,
2832 transparent_pointers,
2833 omit_empty_base_classes,
2834 child_name,
2835 child_byte_size,
2836 child_byte_offset,
2837 child_bitfield_bit_size,
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002838 child_bitfield_bit_offset,
Greg Claytone221f822011-01-21 01:59:00 +00002839 child_is_base_class,
2840 child_is_deref_of_parent);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002841 break;
2842
2843 default:
2844 break;
2845 }
2846 }
Greg Clayton19503a22010-07-23 15:37:46 +00002847 return NULL;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002848}
2849
2850static inline bool
2851BaseSpecifierIsEmpty (const CXXBaseSpecifier *b)
2852{
Greg Clayton6beaaa62011-01-17 03:46:26 +00002853 return ClangASTContext::RecordHasFields(b->getType()->getAsCXXRecordDecl()) == false;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002854}
2855
2856static uint32_t
2857GetNumBaseClasses (const CXXRecordDecl *cxx_record_decl, bool omit_empty_base_classes)
2858{
2859 uint32_t num_bases = 0;
2860 if (cxx_record_decl)
2861 {
2862 if (omit_empty_base_classes)
2863 {
2864 CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
2865 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
2866 base_class != base_class_end;
2867 ++base_class)
2868 {
2869 // Skip empty base classes
2870 if (omit_empty_base_classes)
2871 {
2872 if (BaseSpecifierIsEmpty (base_class))
2873 continue;
2874 }
2875 ++num_bases;
2876 }
2877 }
2878 else
2879 num_bases = cxx_record_decl->getNumBases();
2880 }
2881 return num_bases;
2882}
2883
2884
2885static uint32_t
2886GetIndexForRecordBase
2887(
2888 const RecordDecl *record_decl,
2889 const CXXBaseSpecifier *base_spec,
2890 bool omit_empty_base_classes
2891)
2892{
2893 uint32_t child_idx = 0;
2894
2895 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
2896
2897// const char *super_name = record_decl->getNameAsCString();
2898// const char *base_name = base_spec->getType()->getAs<RecordType>()->getDecl()->getNameAsCString();
2899// printf ("GetIndexForRecordChild (%s, %s)\n", super_name, base_name);
2900//
2901 if (cxx_record_decl)
2902 {
2903 CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
2904 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
2905 base_class != base_class_end;
2906 ++base_class)
2907 {
2908 if (omit_empty_base_classes)
2909 {
2910 if (BaseSpecifierIsEmpty (base_class))
2911 continue;
2912 }
2913
2914// printf ("GetIndexForRecordChild (%s, %s) base[%u] = %s\n", super_name, base_name,
2915// child_idx,
2916// base_class->getType()->getAs<RecordType>()->getDecl()->getNameAsCString());
2917//
2918//
2919 if (base_class == base_spec)
2920 return child_idx;
2921 ++child_idx;
2922 }
2923 }
2924
2925 return UINT32_MAX;
2926}
2927
2928
2929static uint32_t
2930GetIndexForRecordChild
2931(
2932 const RecordDecl *record_decl,
2933 NamedDecl *canonical_decl,
2934 bool omit_empty_base_classes
2935)
2936{
2937 uint32_t child_idx = GetNumBaseClasses (dyn_cast<CXXRecordDecl>(record_decl), omit_empty_base_classes);
2938
2939// const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
2940//
2941//// printf ("GetIndexForRecordChild (%s, %s)\n", record_decl->getNameAsCString(), canonical_decl->getNameAsCString());
2942// if (cxx_record_decl)
2943// {
2944// CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
2945// for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
2946// base_class != base_class_end;
2947// ++base_class)
2948// {
2949// if (omit_empty_base_classes)
2950// {
2951// if (BaseSpecifierIsEmpty (base_class))
2952// continue;
2953// }
2954//
2955//// printf ("GetIndexForRecordChild (%s, %s) base[%u] = %s\n",
2956//// record_decl->getNameAsCString(),
2957//// canonical_decl->getNameAsCString(),
2958//// child_idx,
2959//// base_class->getType()->getAs<RecordType>()->getDecl()->getNameAsCString());
2960//
2961//
2962// CXXRecordDecl *curr_base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
2963// if (curr_base_class_decl == canonical_decl)
2964// {
2965// return child_idx;
2966// }
2967// ++child_idx;
2968// }
2969// }
2970//
2971// const uint32_t num_bases = child_idx;
2972 RecordDecl::field_iterator field, field_end;
2973 for (field = record_decl->field_begin(), field_end = record_decl->field_end();
2974 field != field_end;
2975 ++field, ++child_idx)
2976 {
2977// printf ("GetIndexForRecordChild (%s, %s) field[%u] = %s\n",
2978// record_decl->getNameAsCString(),
2979// canonical_decl->getNameAsCString(),
2980// child_idx - num_bases,
2981// field->getNameAsCString());
2982
2983 if (field->getCanonicalDecl() == canonical_decl)
2984 return child_idx;
2985 }
2986
2987 return UINT32_MAX;
2988}
2989
2990// Look for a child member (doesn't include base classes, but it does include
2991// their members) in the type hierarchy. Returns an index path into "clang_type"
2992// on how to reach the appropriate member.
2993//
2994// class A
2995// {
2996// public:
2997// int m_a;
2998// int m_b;
2999// };
3000//
3001// class B
3002// {
3003// };
3004//
3005// class C :
3006// public B,
3007// public A
3008// {
3009// };
3010//
3011// If we have a clang type that describes "class C", and we wanted to looked
3012// "m_b" in it:
3013//
3014// With omit_empty_base_classes == false we would get an integer array back with:
3015// { 1, 1 }
3016// The first index 1 is the child index for "class A" within class C
3017// The second index 1 is the child index for "m_b" within class A
3018//
3019// With omit_empty_base_classes == true we would get an integer array back with:
3020// { 0, 1 }
3021// The first index 0 is the child index for "class A" within class C (since class B doesn't have any members it doesn't count)
3022// The second index 1 is the child index for "m_b" within class A
3023
3024size_t
3025ClangASTContext::GetIndexOfChildMemberWithName
3026(
Greg Clayton6beaaa62011-01-17 03:46:26 +00003027 ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00003028 clang_type_t clang_type,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003029 const char *name,
3030 bool omit_empty_base_classes,
3031 std::vector<uint32_t>& child_indexes
3032)
3033{
3034 if (clang_type && name && name[0])
3035 {
3036 QualType qual_type(QualType::getFromOpaquePtr(clang_type));
Greg Clayton737b9322010-09-13 03:32:57 +00003037 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
3038 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003039 {
Greg Claytone1a916a2010-07-21 22:12:05 +00003040 case clang::Type::Record:
Greg Claytonc432c192011-01-20 04:18:48 +00003041 if (GetCompleteQualType (ast, qual_type))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003042 {
3043 const RecordType *record_type = cast<RecordType>(qual_type.getTypePtr());
3044 const RecordDecl *record_decl = record_type->getDecl();
3045
3046 assert(record_decl);
3047 uint32_t child_idx = 0;
3048
3049 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
3050
3051 // Try and find a field that matches NAME
3052 RecordDecl::field_iterator field, field_end;
3053 StringRef name_sref(name);
3054 for (field = record_decl->field_begin(), field_end = record_decl->field_end();
3055 field != field_end;
3056 ++field, ++child_idx)
3057 {
3058 if (field->getName().equals (name_sref))
3059 {
3060 // We have to add on the number of base classes to this index!
3061 child_indexes.push_back (child_idx + GetNumBaseClasses (cxx_record_decl, omit_empty_base_classes));
3062 return child_indexes.size();
3063 }
3064 }
3065
3066 if (cxx_record_decl)
3067 {
3068 const RecordDecl *parent_record_decl = cxx_record_decl;
3069
3070 //printf ("parent = %s\n", parent_record_decl->getNameAsCString());
3071
3072 //const Decl *root_cdecl = cxx_record_decl->getCanonicalDecl();
3073 // Didn't find things easily, lets let clang do its thang...
Greg Clayton6beaaa62011-01-17 03:46:26 +00003074 IdentifierInfo & ident_ref = ast->Idents.get(name, name + strlen (name));
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003075 DeclarationName decl_name(&ident_ref);
3076
3077 CXXBasePaths paths;
3078 if (cxx_record_decl->lookupInBases(CXXRecordDecl::FindOrdinaryMember,
3079 decl_name.getAsOpaquePtr(),
3080 paths))
3081 {
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003082 CXXBasePaths::const_paths_iterator path, path_end = paths.end();
3083 for (path = paths.begin(); path != path_end; ++path)
3084 {
3085 const size_t num_path_elements = path->size();
3086 for (size_t e=0; e<num_path_elements; ++e)
3087 {
3088 CXXBasePathElement elem = (*path)[e];
3089
3090 child_idx = GetIndexForRecordBase (parent_record_decl, elem.Base, omit_empty_base_classes);
3091 if (child_idx == UINT32_MAX)
3092 {
3093 child_indexes.clear();
3094 return 0;
3095 }
3096 else
3097 {
3098 child_indexes.push_back (child_idx);
3099 parent_record_decl = cast<RecordDecl>(elem.Base->getType()->getAs<RecordType>()->getDecl());
3100 }
3101 }
3102 DeclContext::lookup_iterator named_decl_pos;
3103 for (named_decl_pos = path->Decls.first;
3104 named_decl_pos != path->Decls.second && parent_record_decl;
3105 ++named_decl_pos)
3106 {
3107 //printf ("path[%zu] = %s\n", child_indexes.size(), (*named_decl_pos)->getNameAsCString());
3108
3109 child_idx = GetIndexForRecordChild (parent_record_decl, *named_decl_pos, omit_empty_base_classes);
3110 if (child_idx == UINT32_MAX)
3111 {
3112 child_indexes.clear();
3113 return 0;
3114 }
3115 else
3116 {
3117 child_indexes.push_back (child_idx);
3118 }
3119 }
3120 }
3121 return child_indexes.size();
3122 }
3123 }
3124
3125 }
3126 break;
3127
Greg Clayton9e409562010-07-28 02:04:09 +00003128 case clang::Type::ObjCObject:
3129 case clang::Type::ObjCInterface:
Greg Claytonc432c192011-01-20 04:18:48 +00003130 if (GetCompleteQualType (ast, qual_type))
Greg Clayton9e409562010-07-28 02:04:09 +00003131 {
3132 StringRef name_sref(name);
Sean Callanan78e37602011-01-27 04:42:51 +00003133 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr());
Greg Clayton9e409562010-07-28 02:04:09 +00003134 assert (objc_class_type);
3135 if (objc_class_type)
3136 {
3137 uint32_t child_idx = 0;
3138 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
3139
3140 if (class_interface_decl)
3141 {
3142 ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
3143 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
3144
Greg Clayton6ba78152010-09-18 02:11:07 +00003145 for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos, ++child_idx)
Greg Clayton9e409562010-07-28 02:04:09 +00003146 {
3147 const ObjCIvarDecl* ivar_decl = *ivar_pos;
3148
3149 if (ivar_decl->getName().equals (name_sref))
3150 {
3151 if ((!omit_empty_base_classes && superclass_interface_decl) ||
3152 ( omit_empty_base_classes && ObjCDeclHasIVars (superclass_interface_decl, true)))
3153 ++child_idx;
3154
3155 child_indexes.push_back (child_idx);
3156 return child_indexes.size();
3157 }
3158 }
3159
3160 if (superclass_interface_decl)
3161 {
3162 // The super class index is always zero for ObjC classes,
3163 // so we push it onto the child indexes in case we find
3164 // an ivar in our superclass...
3165 child_indexes.push_back (0);
3166
Greg Clayton6beaaa62011-01-17 03:46:26 +00003167 if (GetIndexOfChildMemberWithName (ast,
3168 ast->getObjCInterfaceType(superclass_interface_decl).getAsOpaquePtr(),
Greg Clayton9e409562010-07-28 02:04:09 +00003169 name,
3170 omit_empty_base_classes,
3171 child_indexes))
3172 {
3173 // We did find an ivar in a superclass so just
3174 // return the results!
3175 return child_indexes.size();
3176 }
3177
3178 // We didn't find an ivar matching "name" in our
3179 // superclass, pop the superclass zero index that
3180 // we pushed on above.
3181 child_indexes.pop_back();
3182 }
3183 }
3184 }
3185 }
3186 break;
3187
3188 case clang::Type::ObjCObjectPointer:
3189 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003190 return GetIndexOfChildMemberWithName (ast,
Greg Clayton9e409562010-07-28 02:04:09 +00003191 cast<ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr(),
3192 name,
3193 omit_empty_base_classes,
3194 child_indexes);
3195 }
3196 break;
3197
3198
Greg Claytone1a916a2010-07-21 22:12:05 +00003199 case clang::Type::ConstantArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003200 {
3201// const ConstantArrayType *array = cast<ConstantArrayType>(parent_qual_type.getTypePtr());
3202// const uint64_t element_count = array->getSize().getLimitedValue();
3203//
3204// if (idx < element_count)
3205// {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003206// std::pair<uint64_t, unsigned> field_type_info = ast->getTypeInfo(array->getElementType());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003207//
3208// char element_name[32];
3209// ::snprintf (element_name, sizeof (element_name), "%s[%u]", parent_name ? parent_name : "", idx);
3210//
3211// child_name.assign(element_name);
3212// assert(field_type_info.first % 8 == 0);
3213// child_byte_size = field_type_info.first / 8;
3214// child_byte_offset = idx * child_byte_size;
3215// return array->getElementType().getAsOpaquePtr();
3216// }
3217 }
3218 break;
3219
Greg Claytone1a916a2010-07-21 22:12:05 +00003220// case clang::Type::MemberPointerType:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003221// {
3222// MemberPointerType *mem_ptr_type = cast<MemberPointerType>(qual_type.getTypePtr());
3223// QualType pointee_type = mem_ptr_type->getPointeeType();
3224//
3225// if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
3226// {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003227// return GetIndexOfChildWithName (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003228// mem_ptr_type->getPointeeType().getAsOpaquePtr(),
3229// name);
3230// }
3231// }
3232// break;
3233//
Greg Claytone1a916a2010-07-21 22:12:05 +00003234 case clang::Type::LValueReference:
3235 case clang::Type::RValueReference:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003236 {
Sean Callanan78e37602011-01-27 04:42:51 +00003237 const ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003238 QualType pointee_type = reference_type->getPointeeType();
3239
3240 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
3241 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003242 return GetIndexOfChildMemberWithName (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003243 reference_type->getPointeeType().getAsOpaquePtr(),
3244 name,
3245 omit_empty_base_classes,
3246 child_indexes);
3247 }
3248 }
3249 break;
3250
Greg Claytone1a916a2010-07-21 22:12:05 +00003251 case clang::Type::Pointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003252 {
Sean Callanan78e37602011-01-27 04:42:51 +00003253 const PointerType *pointer_type = cast<PointerType>(qual_type.getTypePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003254 QualType pointee_type = pointer_type->getPointeeType();
3255
3256 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
3257 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003258 return GetIndexOfChildMemberWithName (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003259 pointer_type->getPointeeType().getAsOpaquePtr(),
3260 name,
3261 omit_empty_base_classes,
3262 child_indexes);
3263 }
3264 else
3265 {
3266// if (parent_name)
3267// {
3268// child_name.assign(1, '*');
3269// child_name += parent_name;
3270// }
3271//
3272// // We have a pointer to an simple type
3273// if (idx == 0)
3274// {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003275// std::pair<uint64_t, unsigned> clang_type_info = ast->getTypeInfo(pointee_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003276// assert(clang_type_info.first % 8 == 0);
3277// child_byte_size = clang_type_info.first / 8;
3278// child_byte_offset = 0;
3279// return pointee_type.getAsOpaquePtr();
3280// }
3281 }
3282 }
3283 break;
3284
Greg Claytone1a916a2010-07-21 22:12:05 +00003285 case clang::Type::Typedef:
Greg Clayton6beaaa62011-01-17 03:46:26 +00003286 return GetIndexOfChildMemberWithName (ast,
Sean Callanan48114472010-12-13 01:26:27 +00003287 cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003288 name,
3289 omit_empty_base_classes,
3290 child_indexes);
3291
3292 default:
3293 break;
3294 }
3295 }
3296 return 0;
3297}
3298
3299
3300// Get the index of the child of "clang_type" whose name matches. This function
3301// doesn't descend into the children, but only looks one level deep and name
3302// matches can include base class names.
3303
3304uint32_t
3305ClangASTContext::GetIndexOfChildWithName
3306(
Greg Clayton6beaaa62011-01-17 03:46:26 +00003307 ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00003308 clang_type_t clang_type,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003309 const char *name,
3310 bool omit_empty_base_classes
3311)
3312{
3313 if (clang_type && name && name[0])
3314 {
3315 QualType qual_type(QualType::getFromOpaquePtr(clang_type));
Greg Clayton9e409562010-07-28 02:04:09 +00003316
Greg Clayton737b9322010-09-13 03:32:57 +00003317 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
Greg Clayton9e409562010-07-28 02:04:09 +00003318
Greg Clayton737b9322010-09-13 03:32:57 +00003319 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003320 {
Greg Claytone1a916a2010-07-21 22:12:05 +00003321 case clang::Type::Record:
Greg Claytonc432c192011-01-20 04:18:48 +00003322 if (GetCompleteQualType (ast, qual_type))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003323 {
3324 const RecordType *record_type = cast<RecordType>(qual_type.getTypePtr());
3325 const RecordDecl *record_decl = record_type->getDecl();
3326
3327 assert(record_decl);
3328 uint32_t child_idx = 0;
3329
3330 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
3331
3332 if (cxx_record_decl)
3333 {
3334 CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
3335 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
3336 base_class != base_class_end;
3337 ++base_class)
3338 {
3339 // Skip empty base classes
3340 CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
3341 if (omit_empty_base_classes && RecordHasFields(base_class_decl) == false)
3342 continue;
3343
3344 if (base_class->getType().getAsString().compare (name) == 0)
3345 return child_idx;
3346 ++child_idx;
3347 }
3348 }
3349
3350 // Try and find a field that matches NAME
3351 RecordDecl::field_iterator field, field_end;
3352 StringRef name_sref(name);
3353 for (field = record_decl->field_begin(), field_end = record_decl->field_end();
3354 field != field_end;
3355 ++field, ++child_idx)
3356 {
3357 if (field->getName().equals (name_sref))
3358 return child_idx;
3359 }
3360
3361 }
3362 break;
3363
Greg Clayton9e409562010-07-28 02:04:09 +00003364 case clang::Type::ObjCObject:
3365 case clang::Type::ObjCInterface:
Greg Claytonc432c192011-01-20 04:18:48 +00003366 if (GetCompleteQualType (ast, qual_type))
Greg Clayton9e409562010-07-28 02:04:09 +00003367 {
3368 StringRef name_sref(name);
Sean Callanan78e37602011-01-27 04:42:51 +00003369 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr());
Greg Clayton9e409562010-07-28 02:04:09 +00003370 assert (objc_class_type);
3371 if (objc_class_type)
3372 {
3373 uint32_t child_idx = 0;
3374 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
3375
3376 if (class_interface_decl)
3377 {
3378 ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
3379 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
3380
3381 for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos)
3382 {
3383 const ObjCIvarDecl* ivar_decl = *ivar_pos;
3384
3385 if (ivar_decl->getName().equals (name_sref))
3386 {
3387 if ((!omit_empty_base_classes && superclass_interface_decl) ||
3388 ( omit_empty_base_classes && ObjCDeclHasIVars (superclass_interface_decl, true)))
3389 ++child_idx;
3390
3391 return child_idx;
3392 }
3393 }
3394
3395 if (superclass_interface_decl)
3396 {
3397 if (superclass_interface_decl->getName().equals (name_sref))
3398 return 0;
3399 }
3400 }
3401 }
3402 }
3403 break;
3404
3405 case clang::Type::ObjCObjectPointer:
3406 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003407 return GetIndexOfChildWithName (ast,
Greg Clayton9e409562010-07-28 02:04:09 +00003408 cast<ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr(),
3409 name,
3410 omit_empty_base_classes);
3411 }
3412 break;
3413
Greg Claytone1a916a2010-07-21 22:12:05 +00003414 case clang::Type::ConstantArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003415 {
3416// const ConstantArrayType *array = cast<ConstantArrayType>(parent_qual_type.getTypePtr());
3417// const uint64_t element_count = array->getSize().getLimitedValue();
3418//
3419// if (idx < element_count)
3420// {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003421// std::pair<uint64_t, unsigned> field_type_info = ast->getTypeInfo(array->getElementType());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003422//
3423// char element_name[32];
3424// ::snprintf (element_name, sizeof (element_name), "%s[%u]", parent_name ? parent_name : "", idx);
3425//
3426// child_name.assign(element_name);
3427// assert(field_type_info.first % 8 == 0);
3428// child_byte_size = field_type_info.first / 8;
3429// child_byte_offset = idx * child_byte_size;
3430// return array->getElementType().getAsOpaquePtr();
3431// }
3432 }
3433 break;
3434
Greg Claytone1a916a2010-07-21 22:12:05 +00003435// case clang::Type::MemberPointerType:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003436// {
3437// MemberPointerType *mem_ptr_type = cast<MemberPointerType>(qual_type.getTypePtr());
3438// QualType pointee_type = mem_ptr_type->getPointeeType();
3439//
3440// if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
3441// {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003442// return GetIndexOfChildWithName (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003443// mem_ptr_type->getPointeeType().getAsOpaquePtr(),
3444// name);
3445// }
3446// }
3447// break;
3448//
Greg Claytone1a916a2010-07-21 22:12:05 +00003449 case clang::Type::LValueReference:
3450 case clang::Type::RValueReference:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003451 {
Sean Callanan78e37602011-01-27 04:42:51 +00003452 const ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003453 QualType pointee_type = reference_type->getPointeeType();
3454
3455 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
3456 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003457 return GetIndexOfChildWithName (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003458 reference_type->getPointeeType().getAsOpaquePtr(),
3459 name,
3460 omit_empty_base_classes);
3461 }
3462 }
3463 break;
3464
Greg Claytone1a916a2010-07-21 22:12:05 +00003465 case clang::Type::Pointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003466 {
Sean Callanan78e37602011-01-27 04:42:51 +00003467 const PointerType *pointer_type = cast<PointerType>(qual_type.getTypePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003468 QualType pointee_type = pointer_type->getPointeeType();
3469
3470 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
3471 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003472 return GetIndexOfChildWithName (ast,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003473 pointer_type->getPointeeType().getAsOpaquePtr(),
3474 name,
3475 omit_empty_base_classes);
3476 }
3477 else
3478 {
3479// if (parent_name)
3480// {
3481// child_name.assign(1, '*');
3482// child_name += parent_name;
3483// }
3484//
3485// // We have a pointer to an simple type
3486// if (idx == 0)
3487// {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003488// std::pair<uint64_t, unsigned> clang_type_info = ast->getTypeInfo(pointee_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003489// assert(clang_type_info.first % 8 == 0);
3490// child_byte_size = clang_type_info.first / 8;
3491// child_byte_offset = 0;
3492// return pointee_type.getAsOpaquePtr();
3493// }
3494 }
3495 }
3496 break;
3497
Greg Claytone1a916a2010-07-21 22:12:05 +00003498 case clang::Type::Typedef:
Greg Clayton6beaaa62011-01-17 03:46:26 +00003499 return GetIndexOfChildWithName (ast,
Sean Callanan48114472010-12-13 01:26:27 +00003500 cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003501 name,
3502 omit_empty_base_classes);
3503
3504 default:
3505 break;
3506 }
3507 }
3508 return UINT32_MAX;
3509}
3510
3511#pragma mark TagType
3512
3513bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00003514ClangASTContext::SetTagTypeKind (clang_type_t tag_clang_type, int kind)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003515{
3516 if (tag_clang_type)
3517 {
3518 QualType tag_qual_type(QualType::getFromOpaquePtr(tag_clang_type));
Sean Callanan78e37602011-01-27 04:42:51 +00003519 const clang::Type *clang_type = tag_qual_type.getTypePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003520 if (clang_type)
3521 {
Sean Callanan78e37602011-01-27 04:42:51 +00003522 const TagType *tag_type = dyn_cast<TagType>(clang_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003523 if (tag_type)
3524 {
3525 TagDecl *tag_decl = dyn_cast<TagDecl>(tag_type->getDecl());
3526 if (tag_decl)
3527 {
3528 tag_decl->setTagKind ((TagDecl::TagKind)kind);
3529 return true;
3530 }
3531 }
3532 }
3533 }
3534 return false;
3535}
3536
3537
3538#pragma mark DeclContext Functions
3539
3540DeclContext *
Greg Clayton1be10fc2010-09-29 01:12:09 +00003541ClangASTContext::GetDeclContextForType (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003542{
3543 if (clang_type == NULL)
3544 return NULL;
3545
3546 QualType qual_type(QualType::getFromOpaquePtr(clang_type));
Greg Clayton737b9322010-09-13 03:32:57 +00003547 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
3548 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003549 {
Greg Clayton9e409562010-07-28 02:04:09 +00003550 case clang::Type::FunctionNoProto: break;
3551 case clang::Type::FunctionProto: break;
3552 case clang::Type::IncompleteArray: break;
3553 case clang::Type::VariableArray: break;
3554 case clang::Type::ConstantArray: break;
Sean Callananfb0b7582011-03-15 00:17:19 +00003555 case clang::Type::DependentSizedArray: break;
Greg Clayton9e409562010-07-28 02:04:09 +00003556 case clang::Type::ExtVector: break;
Sean Callananfb0b7582011-03-15 00:17:19 +00003557 case clang::Type::DependentSizedExtVector: break;
Greg Clayton9e409562010-07-28 02:04:09 +00003558 case clang::Type::Vector: break;
3559 case clang::Type::Builtin: break;
3560 case clang::Type::BlockPointer: break;
3561 case clang::Type::Pointer: break;
3562 case clang::Type::LValueReference: break;
3563 case clang::Type::RValueReference: break;
3564 case clang::Type::MemberPointer: break;
3565 case clang::Type::Complex: break;
3566 case clang::Type::ObjCObject: break;
3567 case clang::Type::ObjCInterface: return cast<ObjCObjectType>(qual_type.getTypePtr())->getInterface();
3568 case clang::Type::ObjCObjectPointer: return ClangASTContext::GetDeclContextForType (cast<ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr());
3569 case clang::Type::Record: return cast<RecordType>(qual_type)->getDecl();
3570 case clang::Type::Enum: return cast<EnumType>(qual_type)->getDecl();
Sean Callanan48114472010-12-13 01:26:27 +00003571 case clang::Type::Typedef: return ClangASTContext::GetDeclContextForType (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003572
Greg Clayton9e409562010-07-28 02:04:09 +00003573 case clang::Type::TypeOfExpr: break;
3574 case clang::Type::TypeOf: break;
3575 case clang::Type::Decltype: break;
3576 //case clang::Type::QualifiedName: break;
3577 case clang::Type::TemplateSpecialization: break;
Sean Callananfb0b7582011-03-15 00:17:19 +00003578 case clang::Type::DependentTemplateSpecialization: break;
3579 case clang::Type::TemplateTypeParm: break;
3580 case clang::Type::SubstTemplateTypeParm: break;
3581 case clang::Type::SubstTemplateTypeParmPack:break;
3582 case clang::Type::PackExpansion: break;
3583 case clang::Type::UnresolvedUsing: break;
3584 case clang::Type::Paren: break;
3585 case clang::Type::Elaborated: break;
3586 case clang::Type::Attributed: break;
3587 case clang::Type::Auto: break;
3588 case clang::Type::InjectedClassName: break;
3589 case clang::Type::DependentName: break;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003590 }
3591 // No DeclContext in this type...
3592 return NULL;
3593}
3594
3595#pragma mark Namespace Declarations
3596
3597NamespaceDecl *
3598ClangASTContext::GetUniqueNamespaceDeclaration (const char *name, const Declaration &decl, DeclContext *decl_ctx)
3599{
3600 // TODO: Do something intelligent with the Declaration object passed in
3601 // like maybe filling in the SourceLocation with it...
3602 if (name)
3603 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003604 ASTContext *ast = getASTContext();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003605 if (decl_ctx == NULL)
Greg Clayton6beaaa62011-01-17 03:46:26 +00003606 decl_ctx = ast->getTranslationUnitDecl();
Sean Callananfb0b7582011-03-15 00:17:19 +00003607 return NamespaceDecl::Create(*ast, decl_ctx, SourceLocation(), SourceLocation(), &ast->Idents.get(name));
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003608 }
3609 return NULL;
3610}
3611
3612
3613#pragma mark Function Types
3614
3615FunctionDecl *
Greg Clayton1be10fc2010-09-29 01:12:09 +00003616ClangASTContext::CreateFunctionDeclaration (const char *name, clang_type_t function_clang_type, int storage, bool is_inline)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003617{
3618 if (name)
3619 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003620 ASTContext *ast = getASTContext();
3621 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003622
3623 if (name && name[0])
3624 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003625 return FunctionDecl::Create(*ast,
3626 ast->getTranslationUnitDecl(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003627 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00003628 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00003629 DeclarationName (&ast->Idents.get(name)),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003630 QualType::getFromOpaquePtr(function_clang_type),
3631 NULL,
3632 (FunctionDecl::StorageClass)storage,
3633 (FunctionDecl::StorageClass)storage,
3634 is_inline);
3635 }
3636 else
3637 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003638 return FunctionDecl::Create(*ast,
3639 ast->getTranslationUnitDecl(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003640 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00003641 SourceLocation(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003642 DeclarationName (),
3643 QualType::getFromOpaquePtr(function_clang_type),
3644 NULL,
3645 (FunctionDecl::StorageClass)storage,
3646 (FunctionDecl::StorageClass)storage,
3647 is_inline);
3648 }
3649 }
3650 return NULL;
3651}
3652
Greg Clayton1be10fc2010-09-29 01:12:09 +00003653clang_type_t
Greg Clayton6beaaa62011-01-17 03:46:26 +00003654ClangASTContext::CreateFunctionType (ASTContext *ast,
Greg Clayton1be10fc2010-09-29 01:12:09 +00003655 clang_type_t result_type,
3656 clang_type_t *args,
Sean Callananc81256a2010-09-16 20:40:25 +00003657 unsigned num_args,
3658 bool is_variadic,
3659 unsigned type_quals)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003660{
Greg Clayton6beaaa62011-01-17 03:46:26 +00003661 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003662 std::vector<QualType> qual_type_args;
3663 for (unsigned i=0; i<num_args; ++i)
3664 qual_type_args.push_back (QualType::getFromOpaquePtr(args[i]));
3665
3666 // TODO: Detect calling convention in DWARF?
Sean Callanan2c777c42011-01-18 23:32:05 +00003667 FunctionProtoType::ExtProtoInfo proto_info;
3668 proto_info.Variadic = is_variadic;
Sean Callananfb0b7582011-03-15 00:17:19 +00003669 proto_info.ExceptionSpecType = EST_None;
Sean Callanan2c777c42011-01-18 23:32:05 +00003670 proto_info.TypeQuals = type_quals;
Sean Callananfb0b7582011-03-15 00:17:19 +00003671 proto_info.RefQualifier = RQ_None;
Sean Callanan2c777c42011-01-18 23:32:05 +00003672 proto_info.NumExceptions = 0;
3673 proto_info.Exceptions = NULL;
3674
Greg Clayton6beaaa62011-01-17 03:46:26 +00003675 return ast->getFunctionType(QualType::getFromOpaquePtr(result_type),
Greg Clayton471b31c2010-07-20 22:52:08 +00003676 qual_type_args.empty() ? NULL : &qual_type_args.front(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003677 qual_type_args.size(),
Sean Callanan2c777c42011-01-18 23:32:05 +00003678 proto_info).getAsOpaquePtr(); // NoReturn);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003679}
3680
3681ParmVarDecl *
Greg Clayton1be10fc2010-09-29 01:12:09 +00003682ClangASTContext::CreateParameterDeclaration (const char *name, clang_type_t param_type, int storage)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003683{
Greg Clayton6beaaa62011-01-17 03:46:26 +00003684 ASTContext *ast = getASTContext();
3685 assert (ast != NULL);
3686 return ParmVarDecl::Create(*ast,
3687 ast->getTranslationUnitDecl(),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003688 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00003689 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00003690 name && name[0] ? &ast->Idents.get(name) : NULL,
Sean Callananc81256a2010-09-16 20:40:25 +00003691 QualType::getFromOpaquePtr(param_type),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003692 NULL,
3693 (VarDecl::StorageClass)storage,
3694 (VarDecl::StorageClass)storage,
3695 0);
3696}
3697
3698void
3699ClangASTContext::SetFunctionParameters (FunctionDecl *function_decl, ParmVarDecl **params, unsigned num_params)
3700{
3701 if (function_decl)
3702 function_decl->setParams (params, num_params);
3703}
3704
3705
3706#pragma mark Array Types
3707
Greg Clayton1be10fc2010-09-29 01:12:09 +00003708clang_type_t
3709ClangASTContext::CreateArrayType (clang_type_t element_type, size_t element_count, uint32_t bit_stride)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003710{
3711 if (element_type)
3712 {
Greg Clayton6beaaa62011-01-17 03:46:26 +00003713 ASTContext *ast = getASTContext();
3714 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003715 llvm::APInt ap_element_count (64, element_count);
Greg Clayton6beaaa62011-01-17 03:46:26 +00003716 return ast->getConstantArrayType(QualType::getFromOpaquePtr(element_type),
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003717 ap_element_count,
3718 ArrayType::Normal,
3719 0).getAsOpaquePtr(); // ElemQuals
3720 }
3721 return NULL;
3722}
3723
3724
3725#pragma mark TagDecl
3726
3727bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00003728ClangASTContext::StartTagDeclarationDefinition (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003729{
3730 if (clang_type)
3731 {
3732 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
Sean Callanan78e37602011-01-27 04:42:51 +00003733 const clang::Type *t = qual_type.getTypePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003734 if (t)
3735 {
Sean Callanan78e37602011-01-27 04:42:51 +00003736 const TagType *tag_type = dyn_cast<TagType>(t);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003737 if (tag_type)
3738 {
3739 TagDecl *tag_decl = tag_type->getDecl();
3740 if (tag_decl)
3741 {
3742 tag_decl->startDefinition();
3743 return true;
3744 }
3745 }
3746 }
3747 }
3748 return false;
3749}
3750
3751bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00003752ClangASTContext::CompleteTagDeclarationDefinition (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003753{
3754 if (clang_type)
3755 {
3756 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
Greg Clayton14372242010-09-29 03:44:17 +00003757
3758 CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
3759
3760 if (cxx_record_decl)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003761 {
Greg Clayton14372242010-09-29 03:44:17 +00003762 cxx_record_decl->completeDefinition();
3763
3764 return true;
3765 }
3766
Sean Callanan78e37602011-01-27 04:42:51 +00003767 const ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type);
Sean Callanana2424172010-10-25 00:29:48 +00003768
3769 if (objc_class_type)
3770 {
3771 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
3772
3773 class_interface_decl->setForwardDecl(false);
3774 }
3775
Greg Clayton14372242010-09-29 03:44:17 +00003776 const EnumType *enum_type = dyn_cast<EnumType>(qual_type.getTypePtr());
3777
3778 if (enum_type)
3779 {
3780 EnumDecl *enum_decl = enum_type->getDecl();
3781
3782 if (enum_decl)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003783 {
Greg Clayton14372242010-09-29 03:44:17 +00003784 /// TODO This really needs to be fixed.
3785
3786 unsigned NumPositiveBits = 1;
3787 unsigned NumNegativeBits = 0;
3788
Greg Clayton6beaaa62011-01-17 03:46:26 +00003789 ASTContext *ast = getASTContext();
Greg Claytone02b8502010-10-12 04:29:14 +00003790
3791 QualType promotion_qual_type;
3792 // If the enum integer type is less than an integer in bit width,
3793 // then we must promote it to an integer size.
Greg Clayton6beaaa62011-01-17 03:46:26 +00003794 if (ast->getTypeSize(enum_decl->getIntegerType()) < ast->getTypeSize(ast->IntTy))
Greg Claytone02b8502010-10-12 04:29:14 +00003795 {
3796 if (enum_decl->getIntegerType()->isSignedIntegerType())
Greg Clayton6beaaa62011-01-17 03:46:26 +00003797 promotion_qual_type = ast->IntTy;
Greg Claytone02b8502010-10-12 04:29:14 +00003798 else
Greg Clayton6beaaa62011-01-17 03:46:26 +00003799 promotion_qual_type = ast->UnsignedIntTy;
Greg Claytone02b8502010-10-12 04:29:14 +00003800 }
3801 else
3802 promotion_qual_type = enum_decl->getIntegerType();
3803
3804 enum_decl->completeDefinition(enum_decl->getIntegerType(), promotion_qual_type, NumPositiveBits, NumNegativeBits);
Greg Clayton14372242010-09-29 03:44:17 +00003805 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003806 }
3807 }
3808 }
3809 return false;
3810}
3811
3812
3813#pragma mark Enumeration Types
3814
Greg Clayton1be10fc2010-09-29 01:12:09 +00003815clang_type_t
Greg Claytonca512b32011-01-14 04:54:56 +00003816ClangASTContext::CreateEnumerationType
3817(
3818 const char *name,
3819 DeclContext *decl_ctx,
3820 const Declaration &decl,
3821 clang_type_t integer_qual_type
3822)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003823{
3824 // TODO: Do something intelligent with the Declaration object passed in
3825 // like maybe filling in the SourceLocation with it...
Greg Clayton6beaaa62011-01-17 03:46:26 +00003826 ASTContext *ast = getASTContext();
3827 assert (ast != NULL);
Greg Claytone02b8502010-10-12 04:29:14 +00003828
3829 // TODO: ask about these...
3830// const bool IsScoped = false;
3831// const bool IsFixed = false;
3832
Greg Clayton6beaaa62011-01-17 03:46:26 +00003833 EnumDecl *enum_decl = EnumDecl::Create (*ast,
Greg Claytonca512b32011-01-14 04:54:56 +00003834 decl_ctx,
Greg Claytone02b8502010-10-12 04:29:14 +00003835 SourceLocation(),
Greg Claytone02b8502010-10-12 04:29:14 +00003836 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00003837 name && name[0] ? &ast->Idents.get(name) : NULL,
Sean Callanan48114472010-12-13 01:26:27 +00003838 NULL,
3839 false, // IsScoped
3840 false, // IsScopedUsingClassTag
3841 false); // IsFixed
Sean Callanan2652ad22011-01-18 01:03:44 +00003842
3843
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003844 if (enum_decl)
Greg Clayton83ff3892010-09-12 23:17:56 +00003845 {
3846 // TODO: check if we should be setting the promotion type too?
3847 enum_decl->setIntegerType(QualType::getFromOpaquePtr (integer_qual_type));
Sean Callanan2652ad22011-01-18 01:03:44 +00003848
3849 enum_decl->setAccess(AS_public); // TODO respect what's in the debug info
3850
Greg Clayton6beaaa62011-01-17 03:46:26 +00003851 return ast->getTagDeclType(enum_decl).getAsOpaquePtr();
Greg Clayton83ff3892010-09-12 23:17:56 +00003852 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003853 return NULL;
3854}
3855
Greg Clayton1be10fc2010-09-29 01:12:09 +00003856clang_type_t
3857ClangASTContext::GetEnumerationIntegerType (clang_type_t enum_clang_type)
3858{
3859 QualType enum_qual_type (QualType::getFromOpaquePtr(enum_clang_type));
3860
Sean Callanan78e37602011-01-27 04:42:51 +00003861 const clang::Type *clang_type = enum_qual_type.getTypePtr();
Greg Clayton1be10fc2010-09-29 01:12:09 +00003862 if (clang_type)
3863 {
3864 const EnumType *enum_type = dyn_cast<EnumType>(clang_type);
3865 if (enum_type)
3866 {
3867 EnumDecl *enum_decl = enum_type->getDecl();
3868 if (enum_decl)
3869 return enum_decl->getIntegerType().getAsOpaquePtr();
3870 }
3871 }
3872 return NULL;
3873}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003874bool
3875ClangASTContext::AddEnumerationValueToEnumerationType
3876(
Greg Clayton1be10fc2010-09-29 01:12:09 +00003877 clang_type_t enum_clang_type,
3878 clang_type_t enumerator_clang_type,
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003879 const Declaration &decl,
3880 const char *name,
3881 int64_t enum_value,
3882 uint32_t enum_value_bit_size
3883)
3884{
3885 if (enum_clang_type && enumerator_clang_type && name)
3886 {
3887 // TODO: Do something intelligent with the Declaration object passed in
3888 // like maybe filling in the SourceLocation with it...
Greg Clayton6beaaa62011-01-17 03:46:26 +00003889 ASTContext *ast = getASTContext();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003890 IdentifierTable *identifier_table = getIdentifierTable();
3891
Greg Clayton6beaaa62011-01-17 03:46:26 +00003892 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003893 assert (identifier_table != NULL);
3894 QualType enum_qual_type (QualType::getFromOpaquePtr(enum_clang_type));
3895
Sean Callanan78e37602011-01-27 04:42:51 +00003896 const clang::Type *clang_type = enum_qual_type.getTypePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003897 if (clang_type)
3898 {
3899 const EnumType *enum_type = dyn_cast<EnumType>(clang_type);
3900
3901 if (enum_type)
3902 {
3903 llvm::APSInt enum_llvm_apsint(enum_value_bit_size, false);
3904 enum_llvm_apsint = enum_value;
3905 EnumConstantDecl *enumerator_decl =
Greg Clayton6beaaa62011-01-17 03:46:26 +00003906 EnumConstantDecl::Create (*ast,
3907 enum_type->getDecl(),
3908 SourceLocation(),
3909 name ? &identifier_table->get(name) : NULL, // Identifier
3910 QualType::getFromOpaquePtr(enumerator_clang_type),
3911 NULL,
3912 enum_llvm_apsint);
3913
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003914 if (enumerator_decl)
3915 {
3916 enum_type->getDecl()->addDecl(enumerator_decl);
3917 return true;
3918 }
3919 }
3920 }
3921 }
3922 return false;
3923}
3924
3925#pragma mark Pointers & References
3926
Greg Clayton1be10fc2010-09-29 01:12:09 +00003927clang_type_t
3928ClangASTContext::CreatePointerType (clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003929{
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003930 return CreatePointerType (getASTContext(), clang_type);
3931}
3932
3933clang_type_t
3934ClangASTContext::CreatePointerType (clang::ASTContext *ast, clang_type_t clang_type)
3935{
3936 if (ast && clang_type)
Greg Clayton5fb47cd2010-07-29 20:06:32 +00003937 {
3938 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
3939
Greg Clayton737b9322010-09-13 03:32:57 +00003940 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
3941 switch (type_class)
Greg Clayton5fb47cd2010-07-29 20:06:32 +00003942 {
3943 case clang::Type::ObjCObject:
3944 case clang::Type::ObjCInterface:
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003945 return ast->getObjCObjectPointerType(qual_type).getAsOpaquePtr();
Greg Clayton5fb47cd2010-07-29 20:06:32 +00003946
Greg Clayton5fb47cd2010-07-29 20:06:32 +00003947 default:
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003948 return ast->getPointerType(qual_type).getAsOpaquePtr();
Greg Clayton5fb47cd2010-07-29 20:06:32 +00003949 }
3950 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003951 return NULL;
3952}
3953
Greg Clayton1be10fc2010-09-29 01:12:09 +00003954clang_type_t
Sean Callanan92adcac2011-01-13 08:53:35 +00003955ClangASTContext::CreateLValueReferenceType (clang::ASTContext *ast,
3956 clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003957{
3958 if (clang_type)
Sean Callanan92adcac2011-01-13 08:53:35 +00003959 return ast->getLValueReferenceType (QualType::getFromOpaquePtr(clang_type)).getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003960 return NULL;
3961}
3962
Greg Clayton1be10fc2010-09-29 01:12:09 +00003963clang_type_t
Sean Callanan92adcac2011-01-13 08:53:35 +00003964ClangASTContext::CreateRValueReferenceType (clang::ASTContext *ast,
3965 clang_type_t clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003966{
3967 if (clang_type)
Sean Callanan92adcac2011-01-13 08:53:35 +00003968 return ast->getRValueReferenceType (QualType::getFromOpaquePtr(clang_type)).getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003969 return NULL;
3970}
3971
Greg Clayton1be10fc2010-09-29 01:12:09 +00003972clang_type_t
3973ClangASTContext::CreateMemberPointerType (clang_type_t clang_pointee_type, clang_type_t clang_class_type)
Greg Clayton9b81a312010-06-12 01:20:30 +00003974{
3975 if (clang_pointee_type && clang_pointee_type)
3976 return getASTContext()->getMemberPointerType(QualType::getFromOpaquePtr(clang_pointee_type),
3977 QualType::getFromOpaquePtr(clang_class_type).getTypePtr()).getAsOpaquePtr();
3978 return NULL;
3979}
3980
Greg Clayton1a65ae12011-01-25 23:55:37 +00003981uint32_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003982ClangASTContext::GetPointerBitSize ()
3983{
Greg Clayton6beaaa62011-01-17 03:46:26 +00003984 ASTContext *ast = getASTContext();
3985 return ast->getTypeSize(ast->VoidPtrTy);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00003986}
3987
3988bool
Greg Clayton007d5be2011-05-30 00:49:24 +00003989ClangASTContext::IsPossibleCPlusPlusDynamicType (clang::ASTContext *ast, clang_type_t clang_type, clang_type_t *dynamic_pointee_type)
3990{
3991 QualType pointee_qual_type;
3992 if (clang_type)
3993 {
3994 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
3995 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
3996 bool success = false;
3997 switch (type_class)
3998 {
3999 case clang::Type::Pointer:
4000 pointee_qual_type = cast<PointerType>(qual_type)->getPointeeType();
4001 success = true;
4002 break;
4003
4004 case clang::Type::LValueReference:
4005 case clang::Type::RValueReference:
4006 pointee_qual_type = cast<ReferenceType>(qual_type)->getPointeeType();
4007 success = true;
4008 break;
4009
4010 case clang::Type::Typedef:
4011 return ClangASTContext::IsPossibleCPlusPlusDynamicType (ast, cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), dynamic_pointee_type);
4012
4013 default:
4014 break;
4015 }
4016
4017 if (success)
4018 {
4019 // Check to make sure what we are pointing too is a possible dynamic C++ type
4020 // We currently accept any "void *" (in case we have a class that has been
4021 // watered down to an opaque pointer) and virtual C++ classes.
4022 const clang::Type::TypeClass pointee_type_class = pointee_qual_type->getTypeClass();
4023 switch (pointee_type_class)
4024 {
4025 case clang::Type::Builtin:
4026 switch (cast<clang::BuiltinType>(pointee_qual_type)->getKind())
4027 {
4028 case clang::BuiltinType::UnknownAny:
4029 case clang::BuiltinType::Void:
4030 if (dynamic_pointee_type)
4031 *dynamic_pointee_type = pointee_qual_type.getAsOpaquePtr();
4032 return true;
4033
4034 case clang::BuiltinType::NullPtr:
4035 case clang::BuiltinType::Bool:
4036 case clang::BuiltinType::Char_U:
4037 case clang::BuiltinType::UChar:
4038 case clang::BuiltinType::WChar_U:
4039 case clang::BuiltinType::Char16:
4040 case clang::BuiltinType::Char32:
4041 case clang::BuiltinType::UShort:
4042 case clang::BuiltinType::UInt:
4043 case clang::BuiltinType::ULong:
4044 case clang::BuiltinType::ULongLong:
4045 case clang::BuiltinType::UInt128:
4046 case clang::BuiltinType::Char_S:
4047 case clang::BuiltinType::SChar:
4048 case clang::BuiltinType::WChar_S:
4049 case clang::BuiltinType::Short:
4050 case clang::BuiltinType::Int:
4051 case clang::BuiltinType::Long:
4052 case clang::BuiltinType::LongLong:
4053 case clang::BuiltinType::Int128:
4054 case clang::BuiltinType::Float:
4055 case clang::BuiltinType::Double:
4056 case clang::BuiltinType::LongDouble:
4057 case clang::BuiltinType::Dependent:
4058 case clang::BuiltinType::Overload:
4059 case clang::BuiltinType::ObjCId:
4060 case clang::BuiltinType::ObjCClass:
4061 case clang::BuiltinType::ObjCSel:
4062 case clang::BuiltinType::BoundMember:
4063 break;
4064 }
4065 break;
4066 case clang::Type::Record:
4067 {
4068 CXXRecordDecl *cxx_record_decl = pointee_qual_type->getAsCXXRecordDecl();
4069 if (cxx_record_decl)
4070 {
4071 if (GetCompleteQualType (ast, pointee_qual_type))
4072 {
4073 success = cxx_record_decl->isPolymorphic() || cxx_record_decl->isAbstract();
4074 }
4075 else
4076 {
4077 // We failed to get the complete type, so we have to
4078 // treat this as a void * which we might possibly be
4079 // able to complete
4080 success = true;
4081 }
4082 if (success)
4083 {
4084 if (dynamic_pointee_type)
4085 *dynamic_pointee_type = pointee_qual_type.getAsOpaquePtr();
4086 return true;
4087 }
4088 }
4089 }
4090 break;
4091
4092 default:
4093 break;
4094 }
4095 }
4096 }
4097 if (dynamic_pointee_type)
4098 *dynamic_pointee_type = NULL;
4099 return false;
4100}
4101
4102
4103bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004104ClangASTContext::IsPointerOrReferenceType (clang_type_t clang_type, clang_type_t*target_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004105{
4106 if (clang_type == NULL)
4107 return false;
4108
4109 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
Greg Clayton737b9322010-09-13 03:32:57 +00004110 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
4111 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004112 {
Sean Callanana2424172010-10-25 00:29:48 +00004113 case clang::Type::Builtin:
4114 switch (cast<clang::BuiltinType>(qual_type)->getKind())
4115 {
4116 default:
4117 break;
4118 case clang::BuiltinType::ObjCId:
4119 case clang::BuiltinType::ObjCClass:
Sean Callanana2424172010-10-25 00:29:48 +00004120 return true;
4121 }
4122 return false;
Greg Claytone1a916a2010-07-21 22:12:05 +00004123 case clang::Type::ObjCObjectPointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004124 if (target_type)
4125 *target_type = cast<ObjCObjectPointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4126 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004127 case clang::Type::BlockPointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004128 if (target_type)
4129 *target_type = cast<BlockPointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4130 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004131 case clang::Type::Pointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004132 if (target_type)
4133 *target_type = cast<PointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4134 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004135 case clang::Type::MemberPointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004136 if (target_type)
4137 *target_type = cast<MemberPointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4138 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004139 case clang::Type::LValueReference:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004140 if (target_type)
4141 *target_type = cast<LValueReferenceType>(qual_type)->desugar().getAsOpaquePtr();
4142 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004143 case clang::Type::RValueReference:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004144 if (target_type)
4145 *target_type = cast<LValueReferenceType>(qual_type)->desugar().getAsOpaquePtr();
4146 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004147 case clang::Type::Typedef:
Sean Callanan48114472010-12-13 01:26:27 +00004148 return ClangASTContext::IsPointerOrReferenceType (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004149 default:
4150 break;
4151 }
4152 return false;
4153}
4154
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004155bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004156ClangASTContext::IsIntegerType (clang_type_t clang_type, bool &is_signed)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004157{
4158 if (!clang_type)
4159 return false;
4160
4161 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4162 const BuiltinType *builtin_type = dyn_cast<BuiltinType>(qual_type->getCanonicalTypeInternal());
4163
4164 if (builtin_type)
4165 {
4166 if (builtin_type->isInteger())
4167 is_signed = builtin_type->isSignedInteger();
4168
4169 return true;
4170 }
4171
4172 return false;
4173}
4174
4175bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004176ClangASTContext::IsPointerType (clang_type_t clang_type, clang_type_t*target_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004177{
4178 if (clang_type)
4179 {
4180 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
Greg Clayton737b9322010-09-13 03:32:57 +00004181 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
4182 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004183 {
Sean Callanana2424172010-10-25 00:29:48 +00004184 case clang::Type::Builtin:
4185 switch (cast<clang::BuiltinType>(qual_type)->getKind())
4186 {
4187 default:
4188 break;
4189 case clang::BuiltinType::ObjCId:
4190 case clang::BuiltinType::ObjCClass:
Sean Callanana2424172010-10-25 00:29:48 +00004191 return true;
4192 }
4193 return false;
Greg Claytone1a916a2010-07-21 22:12:05 +00004194 case clang::Type::ObjCObjectPointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004195 if (target_type)
4196 *target_type = cast<ObjCObjectPointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4197 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004198 case clang::Type::BlockPointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004199 if (target_type)
4200 *target_type = cast<BlockPointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4201 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004202 case clang::Type::Pointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004203 if (target_type)
4204 *target_type = cast<PointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4205 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004206 case clang::Type::MemberPointer:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004207 if (target_type)
4208 *target_type = cast<MemberPointerType>(qual_type)->getPointeeType().getAsOpaquePtr();
4209 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004210 case clang::Type::Typedef:
Sean Callanan48114472010-12-13 01:26:27 +00004211 return ClangASTContext::IsPointerOrReferenceType (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), target_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004212 default:
4213 break;
4214 }
4215 }
4216 return false;
4217}
4218
4219bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004220ClangASTContext::IsFloatingPointType (clang_type_t clang_type, uint32_t &count, bool &is_complex)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004221{
4222 if (clang_type)
4223 {
4224 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4225
4226 if (const BuiltinType *BT = dyn_cast<BuiltinType>(qual_type->getCanonicalTypeInternal()))
4227 {
4228 clang::BuiltinType::Kind kind = BT->getKind();
4229 if (kind >= BuiltinType::Float && kind <= BuiltinType::LongDouble)
4230 {
4231 count = 1;
4232 is_complex = false;
4233 return true;
4234 }
4235 }
4236 else if (const ComplexType *CT = dyn_cast<ComplexType>(qual_type->getCanonicalTypeInternal()))
4237 {
4238 if (IsFloatingPointType(CT->getElementType().getAsOpaquePtr(), count, is_complex))
4239 {
4240 count = 2;
4241 is_complex = true;
4242 return true;
4243 }
4244 }
4245 else if (const VectorType *VT = dyn_cast<VectorType>(qual_type->getCanonicalTypeInternal()))
4246 {
4247 if (IsFloatingPointType(VT->getElementType().getAsOpaquePtr(), count, is_complex))
4248 {
4249 count = VT->getNumElements();
4250 is_complex = false;
4251 return true;
4252 }
4253 }
4254 }
4255 return false;
4256}
4257
Greg Clayton8f92f0a2010-10-14 22:52:14 +00004258
4259bool
4260ClangASTContext::GetCXXClassName (clang_type_t clang_type, std::string &class_name)
4261{
4262 if (clang_type)
4263 {
4264 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4265
4266 CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
4267 if (cxx_record_decl)
4268 {
4269 class_name.assign (cxx_record_decl->getIdentifier()->getNameStart());
4270 return true;
4271 }
4272 }
4273 class_name.clear();
4274 return false;
4275}
4276
4277
Greg Clayton0fffff52010-09-24 05:15:53 +00004278bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004279ClangASTContext::IsCXXClassType (clang_type_t clang_type)
Greg Clayton0fffff52010-09-24 05:15:53 +00004280{
4281 if (clang_type)
4282 {
4283 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4284 if (qual_type->getAsCXXRecordDecl() != NULL)
4285 return true;
4286 }
4287 return false;
4288}
4289
4290bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004291ClangASTContext::IsObjCClassType (clang_type_t clang_type)
Greg Clayton0fffff52010-09-24 05:15:53 +00004292{
4293 if (clang_type)
4294 {
4295 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4296 if (qual_type->isObjCObjectOrInterfaceType())
4297 return true;
4298 }
4299 return false;
4300}
4301
4302
Greg Clayton73b472d2010-10-27 03:32:59 +00004303bool
4304ClangASTContext::IsCharType (clang_type_t clang_type)
4305{
4306 if (clang_type)
4307 return QualType::getFromOpaquePtr(clang_type)->isCharType();
4308 return false;
4309}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004310
4311bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004312ClangASTContext::IsCStringType (clang_type_t clang_type, uint32_t &length)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004313{
Greg Clayton73b472d2010-10-27 03:32:59 +00004314 clang_type_t pointee_or_element_clang_type = NULL;
4315 Flags type_flags (ClangASTContext::GetTypeInfo (clang_type, NULL, &pointee_or_element_clang_type));
4316
4317 if (pointee_or_element_clang_type == NULL)
4318 return false;
4319
4320 if (type_flags.AnySet (eTypeIsArray | eTypeIsPointer))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004321 {
Greg Clayton73b472d2010-10-27 03:32:59 +00004322 QualType pointee_or_element_qual_type (QualType::getFromOpaquePtr (pointee_or_element_clang_type));
4323
4324 if (pointee_or_element_qual_type.getUnqualifiedType()->isCharType())
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004325 {
Greg Clayton73b472d2010-10-27 03:32:59 +00004326 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4327 if (type_flags.Test (eTypeIsArray))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004328 {
Greg Clayton73b472d2010-10-27 03:32:59 +00004329 // We know the size of the array and it could be a C string
4330 // since it is an array of characters
4331 length = cast<ConstantArrayType>(qual_type.getTypePtr())->getSize().getLimitedValue();
4332 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004333 }
Greg Clayton73b472d2010-10-27 03:32:59 +00004334 else
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004335 {
Greg Clayton73b472d2010-10-27 03:32:59 +00004336 length = 0;
4337 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004338 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004339
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004340 }
4341 }
4342 return false;
4343}
4344
4345bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004346ClangASTContext::IsFunctionPointerType (clang_type_t clang_type)
Greg Clayton737b9322010-09-13 03:32:57 +00004347{
4348 if (clang_type)
4349 {
4350 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4351
4352 if (qual_type->isFunctionPointerType())
4353 return true;
4354
4355 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
4356 switch (type_class)
4357 {
Sean Callananfb0b7582011-03-15 00:17:19 +00004358 default:
4359 break;
Greg Clayton737b9322010-09-13 03:32:57 +00004360 case clang::Type::Typedef:
Sean Callanan48114472010-12-13 01:26:27 +00004361 return ClangASTContext::IsFunctionPointerType (cast<TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
Greg Clayton737b9322010-09-13 03:32:57 +00004362
4363 case clang::Type::LValueReference:
4364 case clang::Type::RValueReference:
4365 {
Sean Callanan78e37602011-01-27 04:42:51 +00004366 const ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr());
Greg Clayton737b9322010-09-13 03:32:57 +00004367 if (reference_type)
4368 return ClangASTContext::IsFunctionPointerType (reference_type->getPointeeType().getAsOpaquePtr());
4369 }
4370 break;
4371 }
4372 }
4373 return false;
4374}
4375
Greg Clayton73b472d2010-10-27 03:32:59 +00004376size_t
4377ClangASTContext::GetArraySize (clang_type_t clang_type)
4378{
4379 if (clang_type)
4380 {
Sean Callanan78e37602011-01-27 04:42:51 +00004381 const ConstantArrayType *array = cast<ConstantArrayType>(QualType::getFromOpaquePtr(clang_type).getTypePtr());
Greg Clayton73b472d2010-10-27 03:32:59 +00004382 if (array)
4383 return array->getSize().getLimitedValue();
4384 }
4385 return 0;
4386}
Greg Clayton737b9322010-09-13 03:32:57 +00004387
4388bool
Greg Clayton1be10fc2010-09-29 01:12:09 +00004389ClangASTContext::IsArrayType (clang_type_t clang_type, clang_type_t*member_type, uint64_t *size)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004390{
4391 if (!clang_type)
4392 return false;
4393
4394 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4395
Greg Clayton737b9322010-09-13 03:32:57 +00004396 const clang::Type::TypeClass type_class = qual_type->getTypeClass();
4397 switch (type_class)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004398 {
Sean Callananfb0b7582011-03-15 00:17:19 +00004399 default:
4400 break;
Greg Claytone1a916a2010-07-21 22:12:05 +00004401 case clang::Type::ConstantArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004402 if (member_type)
4403 *member_type = cast<ConstantArrayType>(qual_type)->getElementType().getAsOpaquePtr();
4404 if (size)
Greg Claytonac4827f2011-04-01 18:14:08 +00004405 *size = cast<ConstantArrayType>(qual_type)->getSize().getLimitedValue(ULLONG_MAX);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004406 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004407 case clang::Type::IncompleteArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004408 if (member_type)
4409 *member_type = cast<IncompleteArrayType>(qual_type)->getElementType().getAsOpaquePtr();
4410 if (size)
4411 *size = 0;
4412 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004413 case clang::Type::VariableArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004414 if (member_type)
4415 *member_type = cast<VariableArrayType>(qual_type)->getElementType().getAsOpaquePtr();
4416 if (size)
4417 *size = 0;
Greg Clayton03dbf2e2011-02-02 00:52:14 +00004418 return true;
Greg Claytone1a916a2010-07-21 22:12:05 +00004419 case clang::Type::DependentSizedArray:
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004420 if (member_type)
4421 *member_type = cast<DependentSizedArrayType>(qual_type)->getElementType().getAsOpaquePtr();
4422 if (size)
4423 *size = 0;
4424 return true;
4425 }
4426 return false;
4427}
4428
4429
4430#pragma mark Typedefs
4431
Greg Clayton1be10fc2010-09-29 01:12:09 +00004432clang_type_t
4433ClangASTContext::CreateTypedefType (const char *name, clang_type_t clang_type, DeclContext *decl_ctx)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004434{
4435 if (clang_type)
4436 {
4437 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
Greg Clayton6beaaa62011-01-17 03:46:26 +00004438 ASTContext *ast = getASTContext();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004439 IdentifierTable *identifier_table = getIdentifierTable();
Greg Clayton6beaaa62011-01-17 03:46:26 +00004440 assert (ast != NULL);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004441 assert (identifier_table != NULL);
4442 if (decl_ctx == NULL)
Greg Clayton6beaaa62011-01-17 03:46:26 +00004443 decl_ctx = ast->getTranslationUnitDecl();
4444 TypedefDecl *decl = TypedefDecl::Create (*ast,
4445 decl_ctx,
4446 SourceLocation(),
Sean Callananfb0b7582011-03-15 00:17:19 +00004447 SourceLocation(),
Greg Clayton6beaaa62011-01-17 03:46:26 +00004448 name ? &identifier_table->get(name) : NULL, // Identifier
4449 ast->CreateTypeSourceInfo(qual_type));
Sean Callanan2652ad22011-01-18 01:03:44 +00004450
4451 decl->setAccess(AS_public); // TODO respect proper access specifier
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004452
4453 // Get a uniqued QualType for the typedef decl type
Greg Clayton6beaaa62011-01-17 03:46:26 +00004454 return ast->getTypedefType (decl).getAsOpaquePtr();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004455 }
4456 return NULL;
4457}
4458
4459
4460std::string
Greg Clayton1be10fc2010-09-29 01:12:09 +00004461ClangASTContext::GetTypeName (clang_type_t opaque_qual_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004462{
4463 std::string return_name;
4464
Greg Clayton1be10fc2010-09-29 01:12:09 +00004465 QualType qual_type(QualType::getFromOpaquePtr(opaque_qual_type));
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004466
Greg Clayton1be10fc2010-09-29 01:12:09 +00004467 const TypedefType *typedef_type = qual_type->getAs<TypedefType>();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004468 if (typedef_type)
4469 {
Sean Callanand12cf8bb2011-05-15 22:34:38 +00004470 const TypedefNameDecl *typedef_decl = typedef_type->getDecl();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004471 return_name = typedef_decl->getQualifiedNameAsString();
4472 }
4473 else
4474 {
4475 return_name = qual_type.getAsString();
4476 }
4477
4478 return return_name;
4479}
4480
4481// Disable this for now since I can't seem to get a nicely formatted float
4482// out of the APFloat class without just getting the float, double or quad
4483// and then using a formatted print on it which defeats the purpose. We ideally
4484// would like to get perfect string values for any kind of float semantics
4485// so we can support remote targets. The code below also requires a patch to
4486// llvm::APInt.
4487//bool
Greg Clayton6beaaa62011-01-17 03:46:26 +00004488//ClangASTContext::ConvertFloatValueToString (ASTContext *ast, clang_type_t clang_type, const uint8_t* bytes, size_t byte_size, int apint_byte_order, std::string &float_str)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004489//{
4490// uint32_t count = 0;
4491// bool is_complex = false;
4492// if (ClangASTContext::IsFloatingPointType (clang_type, count, is_complex))
4493// {
4494// unsigned num_bytes_per_float = byte_size / count;
4495// unsigned num_bits_per_float = num_bytes_per_float * 8;
4496//
4497// float_str.clear();
4498// uint32_t i;
4499// for (i=0; i<count; i++)
4500// {
4501// APInt ap_int(num_bits_per_float, bytes + i * num_bytes_per_float, (APInt::ByteOrder)apint_byte_order);
4502// bool is_ieee = false;
4503// APFloat ap_float(ap_int, is_ieee);
4504// char s[1024];
4505// unsigned int hex_digits = 0;
4506// bool upper_case = false;
4507//
4508// if (ap_float.convertToHexString(s, hex_digits, upper_case, APFloat::rmNearestTiesToEven) > 0)
4509// {
4510// if (i > 0)
4511// float_str.append(", ");
4512// float_str.append(s);
4513// if (i == 1 && is_complex)
4514// float_str.append(1, 'i');
4515// }
4516// }
4517// return !float_str.empty();
4518// }
4519// return false;
4520//}
4521
4522size_t
Greg Clayton6beaaa62011-01-17 03:46:26 +00004523ClangASTContext::ConvertStringToFloatValue (ASTContext *ast, clang_type_t clang_type, const char *s, uint8_t *dst, size_t dst_size)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004524{
4525 if (clang_type)
4526 {
4527 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4528 uint32_t count = 0;
4529 bool is_complex = false;
4530 if (ClangASTContext::IsFloatingPointType (clang_type, count, is_complex))
4531 {
4532 // TODO: handle complex and vector types
4533 if (count != 1)
4534 return false;
4535
4536 StringRef s_sref(s);
Greg Clayton6beaaa62011-01-17 03:46:26 +00004537 APFloat ap_float(ast->getFloatTypeSemantics(qual_type), s_sref);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004538
Greg Clayton6beaaa62011-01-17 03:46:26 +00004539 const uint64_t bit_size = ast->getTypeSize (qual_type);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00004540 const uint64_t byte_size = bit_size / 8;
4541 if (dst_size >= byte_size)
4542 {
4543 if (bit_size == sizeof(float)*8)
4544 {
4545 float float32 = ap_float.convertToFloat();
4546 ::memcpy (dst, &float32, byte_size);
4547 return byte_size;
4548 }
4549 else if (bit_size >= 64)
4550 {
4551 llvm::APInt ap_int(ap_float.bitcastToAPInt());
4552 ::memcpy (dst, ap_int.getRawData(), byte_size);
4553 return byte_size;
4554 }
4555 }
4556 }
4557 }
4558 return 0;
4559}
Sean Callanan6fe64b52010-09-17 02:24:29 +00004560
4561unsigned
Greg Clayton1be10fc2010-09-29 01:12:09 +00004562ClangASTContext::GetTypeQualifiers(clang_type_t clang_type)
Sean Callanan6fe64b52010-09-17 02:24:29 +00004563{
4564 assert (clang_type);
4565
4566 QualType qual_type (QualType::getFromOpaquePtr(clang_type));
4567
4568 return qual_type.getQualifiers().getCVRQualifiers();
4569}
Greg Clayton6beaaa62011-01-17 03:46:26 +00004570
4571bool
4572ClangASTContext::GetCompleteType (clang::ASTContext *ast, lldb::clang_type_t clang_type)
4573{
4574 if (clang_type == NULL)
4575 return false;
4576
Greg Claytonc432c192011-01-20 04:18:48 +00004577 return GetCompleteQualType (ast, clang::QualType::getFromOpaquePtr(clang_type));
Greg Clayton6beaaa62011-01-17 03:46:26 +00004578}
4579
4580
4581bool
4582ClangASTContext::GetCompleteType (clang_type_t clang_type)
4583{
4584 return ClangASTContext::GetCompleteType (getASTContext(), clang_type);
4585}
4586