ClangASTContext.cpp revision 839fde455820d7758685f5eb2257a83e96ca68d2
1//===-- 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 10#include "lldb/Symbol/ClangASTContext.h" 11 12// C Includes 13// C++ Includes 14#include <string> 15 16// Other libraries and framework includes 17#define NDEBUG 18#include "clang/AST/ASTContext.h" 19#include "clang/AST/ASTImporter.h" 20#include "clang/AST/CXXInheritance.h" 21#include "clang/AST/DeclObjC.h" 22#include "clang/AST/RecordLayout.h" 23#include "clang/AST/Type.h" 24#include "clang/Basic/Builtins.h" 25#include "clang/Basic/FileManager.h" 26#include "clang/Basic/SourceManager.h" 27#include "clang/Basic/TargetInfo.h" 28#include "clang/Basic/TargetOptions.h" 29#include "clang/Frontend/FrontendOptions.h" 30#include "clang/Frontend/LangStandard.h" 31#undef NDEBUG 32 33#include "lldb/Core/dwarf.h" 34#include "lldb/Core/Flags.h" 35#include "lldb/Core/Log.h" 36 37#include <stdio.h> 38 39using namespace lldb; 40using namespace lldb_private; 41using namespace llvm; 42using namespace clang; 43 44static AccessSpecifier 45ConvertAccessTypeToAccessSpecifier (AccessType access) 46{ 47 switch (access) 48 { 49 default: break; 50 case eAccessNone: return AS_none; 51 case eAccessPublic: return AS_public; 52 case eAccessPrivate: return AS_private; 53 case eAccessProtected: return AS_protected; 54 } 55 return AS_none; 56} 57 58static ObjCIvarDecl::AccessControl 59ConvertAccessTypeToObjCIvarAccessControl (AccessType access) 60{ 61 switch (access) 62 { 63 default: break; 64 case eAccessNone: return ObjCIvarDecl::None; 65 case eAccessPublic: return ObjCIvarDecl::Public; 66 case eAccessPrivate: return ObjCIvarDecl::Private; 67 case eAccessProtected: return ObjCIvarDecl::Protected; 68 case eAccessPackage: return ObjCIvarDecl::Package; 69 } 70 return ObjCIvarDecl::None; 71} 72 73 74static void 75ParseLangArgs 76( 77 LangOptions &Opts, 78 InputKind IK 79) 80{ 81 // FIXME: Cleanup per-file based stuff. 82 83 // Set some properties which depend soley on the input kind; it would be nice 84 // to move these to the language standard, and have the driver resolve the 85 // input kind + language standard. 86 if (IK == IK_Asm) { 87 Opts.AsmPreprocessor = 1; 88 } else if (IK == IK_ObjC || 89 IK == IK_ObjCXX || 90 IK == IK_PreprocessedObjC || 91 IK == IK_PreprocessedObjCXX) { 92 Opts.ObjC1 = Opts.ObjC2 = 1; 93 } 94 95 LangStandard::Kind LangStd = LangStandard::lang_unspecified; 96 97 if (LangStd == LangStandard::lang_unspecified) { 98 // Based on the base language, pick one. 99 switch (IK) { 100 case IK_None: 101 case IK_AST: 102 assert(0 && "Invalid input kind!"); 103 case IK_OpenCL: 104 LangStd = LangStandard::lang_opencl; 105 break; 106 case IK_Asm: 107 case IK_C: 108 case IK_PreprocessedC: 109 case IK_ObjC: 110 case IK_PreprocessedObjC: 111 LangStd = LangStandard::lang_gnu99; 112 break; 113 case IK_CXX: 114 case IK_PreprocessedCXX: 115 case IK_ObjCXX: 116 case IK_PreprocessedObjCXX: 117 LangStd = LangStandard::lang_gnucxx98; 118 break; 119 } 120 } 121 122 const LangStandard &Std = LangStandard::getLangStandardForKind(LangStd); 123 Opts.BCPLComment = Std.hasBCPLComments(); 124 Opts.C99 = Std.isC99(); 125 Opts.CPlusPlus = Std.isCPlusPlus(); 126 Opts.CPlusPlus0x = Std.isCPlusPlus0x(); 127 Opts.Digraphs = Std.hasDigraphs(); 128 Opts.GNUMode = Std.isGNUMode(); 129 Opts.GNUInline = !Std.isC99(); 130 Opts.HexFloats = Std.hasHexFloats(); 131 Opts.ImplicitInt = Std.hasImplicitInt(); 132 133 // OpenCL has some additional defaults. 134 if (LangStd == LangStandard::lang_opencl) { 135 Opts.OpenCL = 1; 136 Opts.AltiVec = 1; 137 Opts.CXXOperatorNames = 1; 138 Opts.LaxVectorConversions = 1; 139 } 140 141 // OpenCL and C++ both have bool, true, false keywords. 142 Opts.Bool = Opts.OpenCL || Opts.CPlusPlus; 143 144// if (Opts.CPlusPlus) 145// Opts.CXXOperatorNames = !Args.hasArg(OPT_fno_operator_names); 146// 147// if (Args.hasArg(OPT_fobjc_gc_only)) 148// Opts.setGCMode(LangOptions::GCOnly); 149// else if (Args.hasArg(OPT_fobjc_gc)) 150// Opts.setGCMode(LangOptions::HybridGC); 151// 152// if (Args.hasArg(OPT_print_ivar_layout)) 153// Opts.ObjCGCBitmapPrint = 1; 154// 155// if (Args.hasArg(OPT_faltivec)) 156// Opts.AltiVec = 1; 157// 158// if (Args.hasArg(OPT_pthread)) 159// Opts.POSIXThreads = 1; 160// 161// llvm::StringRef Vis = getLastArgValue(Args, OPT_fvisibility, 162// "default"); 163// if (Vis == "default") 164 Opts.setVisibilityMode(LangOptions::Default); 165// else if (Vis == "hidden") 166// Opts.setVisibilityMode(LangOptions::Hidden); 167// else if (Vis == "protected") 168// Opts.setVisibilityMode(LangOptions::Protected); 169// else 170// Diags.Report(diag::err_drv_invalid_value) 171// << Args.getLastArg(OPT_fvisibility)->getAsString(Args) << Vis; 172 173// Opts.OverflowChecking = Args.hasArg(OPT_ftrapv); 174 175 // Mimicing gcc's behavior, trigraphs are only enabled if -trigraphs 176 // is specified, or -std is set to a conforming mode. 177 Opts.Trigraphs = !Opts.GNUMode; 178// if (Args.hasArg(OPT_trigraphs)) 179// Opts.Trigraphs = 1; 180// 181// Opts.DollarIdents = Args.hasFlag(OPT_fdollars_in_identifiers, 182// OPT_fno_dollars_in_identifiers, 183// !Opts.AsmPreprocessor); 184// Opts.PascalStrings = Args.hasArg(OPT_fpascal_strings); 185// Opts.Microsoft = Args.hasArg(OPT_fms_extensions); 186// Opts.WritableStrings = Args.hasArg(OPT_fwritable_strings); 187// if (Args.hasArg(OPT_fno_lax_vector_conversions)) 188// Opts.LaxVectorConversions = 0; 189// Opts.Exceptions = Args.hasArg(OPT_fexceptions); 190// Opts.RTTI = !Args.hasArg(OPT_fno_rtti); 191// Opts.Blocks = Args.hasArg(OPT_fblocks); 192// Opts.CharIsSigned = !Args.hasArg(OPT_fno_signed_char); 193// Opts.ShortWChar = Args.hasArg(OPT_fshort_wchar); 194// Opts.Freestanding = Args.hasArg(OPT_ffreestanding); 195// Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding; 196// Opts.AssumeSaneOperatorNew = !Args.hasArg(OPT_fno_assume_sane_operator_new); 197// Opts.HeinousExtensions = Args.hasArg(OPT_fheinous_gnu_extensions); 198// Opts.AccessControl = Args.hasArg(OPT_faccess_control); 199// Opts.ElideConstructors = !Args.hasArg(OPT_fno_elide_constructors); 200// Opts.MathErrno = !Args.hasArg(OPT_fno_math_errno); 201// Opts.InstantiationDepth = getLastArgIntValue(Args, OPT_ftemplate_depth, 99, 202// Diags); 203// Opts.NeXTRuntime = !Args.hasArg(OPT_fgnu_runtime); 204// Opts.ObjCConstantStringClass = getLastArgValue(Args, 205// OPT_fconstant_string_class); 206// Opts.ObjCNonFragileABI = Args.hasArg(OPT_fobjc_nonfragile_abi); 207// Opts.CatchUndefined = Args.hasArg(OPT_fcatch_undefined_behavior); 208// Opts.EmitAllDecls = Args.hasArg(OPT_femit_all_decls); 209// Opts.PICLevel = getLastArgIntValue(Args, OPT_pic_level, 0, Diags); 210// Opts.Static = Args.hasArg(OPT_static_define); 211 Opts.OptimizeSize = 0; 212 213 // FIXME: Eliminate this dependency. 214// unsigned Opt = 215// Args.hasArg(OPT_Os) ? 2 : getLastArgIntValue(Args, OPT_O, 0, Diags); 216// Opts.Optimize = Opt != 0; 217 unsigned Opt = 0; 218 219 // This is the __NO_INLINE__ define, which just depends on things like the 220 // optimization level and -fno-inline, not actually whether the backend has 221 // inlining enabled. 222 // 223 // FIXME: This is affected by other options (-fno-inline). 224 Opts.NoInline = !Opt; 225 226// unsigned SSP = getLastArgIntValue(Args, OPT_stack_protector, 0, Diags); 227// switch (SSP) { 228// default: 229// Diags.Report(diag::err_drv_invalid_value) 230// << Args.getLastArg(OPT_stack_protector)->getAsString(Args) << SSP; 231// break; 232// case 0: Opts.setStackProtectorMode(LangOptions::SSPOff); break; 233// case 1: Opts.setStackProtectorMode(LangOptions::SSPOn); break; 234// case 2: Opts.setStackProtectorMode(LangOptions::SSPReq); break; 235// } 236} 237 238 239ClangASTContext::ClangASTContext(const char *target_triple) : 240 m_target_triple(), 241 m_ast_context_ap(), 242 m_language_options_ap(), 243 m_source_manager_ap(), 244 m_diagnostic_ap(), 245 m_target_options_ap(), 246 m_target_info_ap(), 247 m_identifier_table_ap(), 248 m_selector_table_ap(), 249 m_builtins_ap() 250{ 251 if (target_triple && target_triple[0]) 252 m_target_triple.assign (target_triple); 253} 254 255//---------------------------------------------------------------------- 256// Destructor 257//---------------------------------------------------------------------- 258ClangASTContext::~ClangASTContext() 259{ 260 m_builtins_ap.reset(); 261 m_selector_table_ap.reset(); 262 m_identifier_table_ap.reset(); 263 m_target_info_ap.reset(); 264 m_target_options_ap.reset(); 265 m_diagnostic_ap.reset(); 266 m_source_manager_ap.reset(); 267 m_language_options_ap.reset(); 268 m_ast_context_ap.reset(); 269} 270 271 272void 273ClangASTContext::Clear() 274{ 275 m_ast_context_ap.reset(); 276 m_language_options_ap.reset(); 277 m_source_manager_ap.reset(); 278 m_diagnostic_ap.reset(); 279 m_target_options_ap.reset(); 280 m_target_info_ap.reset(); 281 m_identifier_table_ap.reset(); 282 m_selector_table_ap.reset(); 283 m_builtins_ap.reset(); 284} 285 286const char * 287ClangASTContext::GetTargetTriple () 288{ 289 return m_target_triple.c_str(); 290} 291 292void 293ClangASTContext::SetTargetTriple (const char *target_triple) 294{ 295 Clear(); 296 m_target_triple.assign(target_triple); 297} 298 299 300ASTContext * 301ClangASTContext::getASTContext() 302{ 303 if (m_ast_context_ap.get() == NULL) 304 { 305 m_ast_context_ap.reset( 306 new ASTContext( 307 *getLanguageOptions(), 308 *getSourceManager(), 309 *getTargetInfo(), 310 *getIdentifierTable(), 311 *getSelectorTable(), 312 *getBuiltinContext(), 313 0)); 314 } 315 return m_ast_context_ap.get(); 316} 317 318Builtin::Context * 319ClangASTContext::getBuiltinContext() 320{ 321 if (m_builtins_ap.get() == NULL) 322 m_builtins_ap.reset (new Builtin::Context(*getTargetInfo())); 323 return m_builtins_ap.get(); 324} 325 326IdentifierTable * 327ClangASTContext::getIdentifierTable() 328{ 329 if (m_identifier_table_ap.get() == NULL) 330 m_identifier_table_ap.reset(new IdentifierTable (*ClangASTContext::getLanguageOptions(), NULL)); 331 return m_identifier_table_ap.get(); 332} 333 334LangOptions * 335ClangASTContext::getLanguageOptions() 336{ 337 if (m_language_options_ap.get() == NULL) 338 { 339 m_language_options_ap.reset(new LangOptions()); 340 ParseLangArgs(*m_language_options_ap, IK_ObjCXX); 341// InitializeLangOptions(*m_language_options_ap, IK_ObjCXX); 342 } 343 return m_language_options_ap.get(); 344} 345 346SelectorTable * 347ClangASTContext::getSelectorTable() 348{ 349 if (m_selector_table_ap.get() == NULL) 350 m_selector_table_ap.reset (new SelectorTable()); 351 return m_selector_table_ap.get(); 352} 353 354clang::SourceManager * 355ClangASTContext::getSourceManager() 356{ 357 if (m_source_manager_ap.get() == NULL) 358 m_source_manager_ap.reset(new clang::SourceManager(*getDiagnostic())); 359 return m_source_manager_ap.get(); 360} 361 362Diagnostic * 363ClangASTContext::getDiagnostic() 364{ 365 if (m_diagnostic_ap.get() == NULL) 366 m_diagnostic_ap.reset(new Diagnostic()); 367 return m_diagnostic_ap.get(); 368} 369 370TargetOptions * 371ClangASTContext::getTargetOptions() 372{ 373 if (m_target_options_ap.get() == NULL && !m_target_triple.empty()) 374 { 375 m_target_options_ap.reset (new TargetOptions()); 376 if (m_target_options_ap.get()) 377 m_target_options_ap->Triple = m_target_triple; 378 } 379 return m_target_options_ap.get(); 380} 381 382 383TargetInfo * 384ClangASTContext::getTargetInfo() 385{ 386 // target_triple should be something like "x86_64-apple-darwin10" 387 if (m_target_info_ap.get() == NULL && !m_target_triple.empty()) 388 m_target_info_ap.reset (TargetInfo::CreateTargetInfo(*getDiagnostic(), *getTargetOptions())); 389 return m_target_info_ap.get(); 390} 391 392#pragma mark Basic Types 393 394static inline bool 395QualTypeMatchesBitSize(const uint64_t bit_size, ASTContext *ast_context, QualType qual_type) 396{ 397 uint64_t qual_type_bit_size = ast_context->getTypeSize(qual_type); 398 if (qual_type_bit_size == bit_size) 399 return true; 400 return false; 401} 402 403clang_type_t 404ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (Encoding encoding, uint32_t bit_size) 405{ 406 ASTContext *ast_context = getASTContext(); 407 408 assert (ast_context != NULL); 409 410 return GetBuiltinTypeForEncodingAndBitSize (ast_context, encoding, bit_size); 411} 412 413clang_type_t 414ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (ASTContext *ast_context, Encoding encoding, uint32_t bit_size) 415{ 416 if (!ast_context) 417 return NULL; 418 419 switch (encoding) 420 { 421 case eEncodingInvalid: 422 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->VoidPtrTy)) 423 return ast_context->VoidPtrTy.getAsOpaquePtr(); 424 break; 425 426 case eEncodingUint: 427 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedCharTy)) 428 return ast_context->UnsignedCharTy.getAsOpaquePtr(); 429 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedShortTy)) 430 return ast_context->UnsignedShortTy.getAsOpaquePtr(); 431 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedIntTy)) 432 return ast_context->UnsignedIntTy.getAsOpaquePtr(); 433 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedLongTy)) 434 return ast_context->UnsignedLongTy.getAsOpaquePtr(); 435 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedLongLongTy)) 436 return ast_context->UnsignedLongLongTy.getAsOpaquePtr(); 437 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedInt128Ty)) 438 return ast_context->UnsignedInt128Ty.getAsOpaquePtr(); 439 break; 440 441 case eEncodingSint: 442 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->CharTy)) 443 return ast_context->CharTy.getAsOpaquePtr(); 444 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->ShortTy)) 445 return ast_context->ShortTy.getAsOpaquePtr(); 446 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->IntTy)) 447 return ast_context->IntTy.getAsOpaquePtr(); 448 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongTy)) 449 return ast_context->LongTy.getAsOpaquePtr(); 450 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongLongTy)) 451 return ast_context->LongLongTy.getAsOpaquePtr(); 452 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->Int128Ty)) 453 return ast_context->Int128Ty.getAsOpaquePtr(); 454 break; 455 456 case eEncodingIEEE754: 457 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->FloatTy)) 458 return ast_context->FloatTy.getAsOpaquePtr(); 459 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->DoubleTy)) 460 return ast_context->DoubleTy.getAsOpaquePtr(); 461 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongDoubleTy)) 462 return ast_context->LongDoubleTy.getAsOpaquePtr(); 463 break; 464 465 case eEncodingVector: 466 default: 467 break; 468 } 469 470 return NULL; 471} 472 473clang_type_t 474ClangASTContext::GetBuiltinTypeForDWARFEncodingAndBitSize (const char *type_name, uint32_t dw_ate, uint32_t bit_size) 475{ 476 ASTContext *ast_context = getASTContext(); 477 478 #define streq(a,b) strcmp(a,b) == 0 479 assert (ast_context != NULL); 480 if (ast_context) 481 { 482 switch (dw_ate) 483 { 484 default: 485 break; 486 487 case DW_ATE_address: 488 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->VoidPtrTy)) 489 return ast_context->VoidPtrTy.getAsOpaquePtr(); 490 break; 491 492 case DW_ATE_boolean: 493 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->BoolTy)) 494 return ast_context->BoolTy.getAsOpaquePtr(); 495 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedCharTy)) 496 return ast_context->UnsignedCharTy.getAsOpaquePtr(); 497 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedShortTy)) 498 return ast_context->UnsignedShortTy.getAsOpaquePtr(); 499 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedIntTy)) 500 return ast_context->UnsignedIntTy.getAsOpaquePtr(); 501 break; 502 503 case DW_ATE_complex_float: 504 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->FloatComplexTy)) 505 return ast_context->FloatComplexTy.getAsOpaquePtr(); 506 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->DoubleComplexTy)) 507 return ast_context->DoubleComplexTy.getAsOpaquePtr(); 508 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongDoubleComplexTy)) 509 return ast_context->LongDoubleComplexTy.getAsOpaquePtr(); 510 break; 511 512 case DW_ATE_float: 513 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->FloatTy)) 514 return ast_context->FloatTy.getAsOpaquePtr(); 515 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->DoubleTy)) 516 return ast_context->DoubleTy.getAsOpaquePtr(); 517 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongDoubleTy)) 518 return ast_context->LongDoubleTy.getAsOpaquePtr(); 519 break; 520 521 case DW_ATE_signed: 522 if (type_name) 523 { 524 if (streq(type_name, "int") || 525 streq(type_name, "signed int")) 526 { 527 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->IntTy)) 528 return ast_context->IntTy.getAsOpaquePtr(); 529 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->Int128Ty)) 530 return ast_context->Int128Ty.getAsOpaquePtr(); 531 } 532 533 if (streq(type_name, "long int") || 534 streq(type_name, "long long int") || 535 streq(type_name, "signed long long")) 536 { 537 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongTy)) 538 return ast_context->LongTy.getAsOpaquePtr(); 539 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongLongTy)) 540 return ast_context->LongLongTy.getAsOpaquePtr(); 541 } 542 543 if (streq(type_name, "short") || 544 streq(type_name, "short int") || 545 streq(type_name, "signed short") || 546 streq(type_name, "short signed int")) 547 { 548 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->ShortTy)) 549 return ast_context->ShortTy.getAsOpaquePtr(); 550 } 551 552 if (streq(type_name, "char") || 553 streq(type_name, "signed char")) 554 { 555 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->CharTy)) 556 return ast_context->CharTy.getAsOpaquePtr(); 557 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->SignedCharTy)) 558 return ast_context->SignedCharTy.getAsOpaquePtr(); 559 } 560 561 if (streq(type_name, "wchar_t")) 562 { 563 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->WCharTy)) 564 return ast_context->WCharTy.getAsOpaquePtr(); 565 } 566 567 } 568 // We weren't able to match up a type name, just search by size 569 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->CharTy)) 570 return ast_context->CharTy.getAsOpaquePtr(); 571 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->ShortTy)) 572 return ast_context->ShortTy.getAsOpaquePtr(); 573 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->IntTy)) 574 return ast_context->IntTy.getAsOpaquePtr(); 575 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongTy)) 576 return ast_context->LongTy.getAsOpaquePtr(); 577 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->LongLongTy)) 578 return ast_context->LongLongTy.getAsOpaquePtr(); 579 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->Int128Ty)) 580 return ast_context->Int128Ty.getAsOpaquePtr(); 581 break; 582 583 case DW_ATE_signed_char: 584 if (type_name) 585 { 586 if (streq(type_name, "signed char")) 587 { 588 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->SignedCharTy)) 589 return ast_context->SignedCharTy.getAsOpaquePtr(); 590 } 591 } 592 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->CharTy)) 593 return ast_context->CharTy.getAsOpaquePtr(); 594 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->SignedCharTy)) 595 return ast_context->SignedCharTy.getAsOpaquePtr(); 596 break; 597 598 case DW_ATE_unsigned: 599 if (type_name) 600 { 601 if (streq(type_name, "unsigned int")) 602 { 603 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedIntTy)) 604 return ast_context->UnsignedIntTy.getAsOpaquePtr(); 605 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedInt128Ty)) 606 return ast_context->UnsignedInt128Ty.getAsOpaquePtr(); 607 } 608 609 if (streq(type_name, "unsigned int") || 610 streq(type_name, "long unsigned int") || 611 streq(type_name, "unsigned long long")) 612 { 613 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedLongTy)) 614 return ast_context->UnsignedLongTy.getAsOpaquePtr(); 615 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedLongLongTy)) 616 return ast_context->UnsignedLongLongTy.getAsOpaquePtr(); 617 } 618 619 if (streq(type_name, "unsigned short") || 620 streq(type_name, "short unsigned int")) 621 { 622 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedShortTy)) 623 return ast_context->UnsignedShortTy.getAsOpaquePtr(); 624 } 625 if (streq(type_name, "unsigned char")) 626 { 627 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedCharTy)) 628 return ast_context->UnsignedCharTy.getAsOpaquePtr(); 629 } 630 631 } 632 // We weren't able to match up a type name, just search by size 633 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedCharTy)) 634 return ast_context->UnsignedCharTy.getAsOpaquePtr(); 635 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedShortTy)) 636 return ast_context->UnsignedShortTy.getAsOpaquePtr(); 637 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedIntTy)) 638 return ast_context->UnsignedIntTy.getAsOpaquePtr(); 639 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedLongTy)) 640 return ast_context->UnsignedLongTy.getAsOpaquePtr(); 641 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedLongLongTy)) 642 return ast_context->UnsignedLongLongTy.getAsOpaquePtr(); 643 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedInt128Ty)) 644 return ast_context->UnsignedInt128Ty.getAsOpaquePtr(); 645 break; 646 647 case DW_ATE_unsigned_char: 648 if (QualTypeMatchesBitSize (bit_size, ast_context, ast_context->UnsignedCharTy)) 649 return ast_context->UnsignedCharTy.getAsOpaquePtr(); 650 break; 651 652 case DW_ATE_imaginary_float: 653 break; 654 } 655 } 656 // This assert should fire for anything that we don't catch above so we know 657 // to fix any issues we run into. 658 assert (!"error: ClangASTContext::GetClangTypeForDWARFEncodingAndSize() contains an unhandled encoding. Fix this ASAP!"); 659 return NULL; 660} 661 662clang_type_t 663ClangASTContext::GetBuiltInType_void(ASTContext *ast_context) 664{ 665 return ast_context->VoidTy.getAsOpaquePtr(); 666} 667 668clang_type_t 669ClangASTContext::GetBuiltInType_objc_id() 670{ 671 return getASTContext()->ObjCBuiltinIdTy.getAsOpaquePtr(); 672} 673 674clang_type_t 675ClangASTContext::GetBuiltInType_objc_Class() 676{ 677 return getASTContext()->ObjCBuiltinClassTy.getAsOpaquePtr(); 678} 679 680clang_type_t 681ClangASTContext::GetBuiltInType_objc_selector() 682{ 683 return getASTContext()->ObjCBuiltinSelTy.getAsOpaquePtr(); 684} 685 686clang_type_t 687ClangASTContext::GetCStringType (bool is_const) 688{ 689 QualType char_type(getASTContext()->CharTy); 690 691 if (is_const) 692 char_type.addConst(); 693 694 return getASTContext()->getPointerType(char_type).getAsOpaquePtr(); 695} 696 697clang_type_t 698ClangASTContext::GetVoidPtrType (bool is_const) 699{ 700 return GetVoidPtrType(getASTContext(), is_const); 701} 702 703clang_type_t 704ClangASTContext::GetVoidPtrType (ASTContext *ast_context, bool is_const) 705{ 706 QualType void_ptr_type(ast_context->VoidPtrTy); 707 708 if (is_const) 709 void_ptr_type.addConst(); 710 711 return void_ptr_type.getAsOpaquePtr(); 712} 713 714class NullDiagnosticClient : public DiagnosticClient 715{ 716public: 717 NullDiagnosticClient () 718 { 719 m_log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS); 720 } 721 722 void HandleDiagnostic (Diagnostic::Level DiagLevel, const DiagnosticInfo &info) 723 { 724 if (m_log) 725 { 726 llvm::SmallVectorImpl<char> diag_str(10); 727 info.FormatDiagnostic(diag_str); 728 diag_str.push_back('\0'); 729 m_log->Printf("Compiler diagnostic: %s\n", diag_str.data()); 730 } 731 } 732private: 733 Log *m_log; 734}; 735 736clang_type_t 737ClangASTContext::CopyType (ASTContext *dest_context, 738 ASTContext *source_context, 739 clang_type_t clang_type) 740{ 741 NullDiagnosticClient *null_client = new NullDiagnosticClient; 742 Diagnostic diagnostics(null_client); 743 FileManager file_manager; 744 ASTImporter importer(diagnostics, 745 *dest_context, file_manager, 746 *source_context, file_manager); 747 QualType ret = importer.Import(QualType::getFromOpaquePtr(clang_type)); 748 return ret.getAsOpaquePtr(); 749} 750 751bool 752ClangASTContext::AreTypesSame(ASTContext *ast_context, 753 clang_type_t type1, 754 clang_type_t type2) 755{ 756 return ast_context->hasSameType(QualType::getFromOpaquePtr(type1), 757 QualType::getFromOpaquePtr(type2)); 758} 759 760#pragma mark CVR modifiers 761 762clang_type_t 763ClangASTContext::AddConstModifier (clang_type_t clang_type) 764{ 765 if (clang_type) 766 { 767 QualType result(QualType::getFromOpaquePtr(clang_type)); 768 result.addConst(); 769 return result.getAsOpaquePtr(); 770 } 771 return NULL; 772} 773 774clang_type_t 775ClangASTContext::AddRestrictModifier (clang_type_t clang_type) 776{ 777 if (clang_type) 778 { 779 QualType result(QualType::getFromOpaquePtr(clang_type)); 780 result.getQualifiers().setRestrict (true); 781 return result.getAsOpaquePtr(); 782 } 783 return NULL; 784} 785 786clang_type_t 787ClangASTContext::AddVolatileModifier (clang_type_t clang_type) 788{ 789 if (clang_type) 790 { 791 QualType result(QualType::getFromOpaquePtr(clang_type)); 792 result.getQualifiers().setVolatile (true); 793 return result.getAsOpaquePtr(); 794 } 795 return NULL; 796} 797 798#pragma mark Structure, Unions, Classes 799 800clang_type_t 801ClangASTContext::CreateRecordType (const char *name, int kind, DeclContext *decl_ctx, LanguageType language) 802{ 803 ASTContext *ast_context = getASTContext(); 804 assert (ast_context != NULL); 805 806 if (decl_ctx == NULL) 807 decl_ctx = ast_context->getTranslationUnitDecl(); 808 809 810 if (language == eLanguageTypeObjC) 811 { 812 bool isForwardDecl = true; 813 bool isInternal = false; 814 return CreateObjCClass (name, decl_ctx, isForwardDecl, isInternal); 815 } 816 817 // NOTE: Eventually CXXRecordDecl will be merged back into RecordDecl and 818 // we will need to update this code. I was told to currently always use 819 // the CXXRecordDecl class since we often don't know from debug information 820 // if something is struct or a class, so we default to always use the more 821 // complete definition just in case. 822 CXXRecordDecl *decl = CXXRecordDecl::Create(*ast_context, 823 (TagDecl::TagKind)kind, 824 decl_ctx, 825 SourceLocation(), 826 name && name[0] ? &ast_context->Idents.get(name) : NULL); 827 828 return ast_context->getTagDeclType(decl).getAsOpaquePtr(); 829} 830 831static bool 832IsOperator (const char *name, OverloadedOperatorKind &op_kind) 833{ 834 if (name == NULL || name[0] == '\0') 835 return false; 836 837 if (::strstr(name, "operator ") != name) 838 return false; 839 840 const char *post_op_name = name + 9; 841 842 // This is an operator, set the overloaded operator kind to invalid 843 // in case this is a conversion operator... 844 op_kind = NUM_OVERLOADED_OPERATORS; 845 846 switch (post_op_name[0]) 847 { 848 case 'n': 849 if (strcmp (post_op_name, "new") == 0) 850 op_kind = OO_New; 851 else if (strcmp (post_op_name, "new[]") == 0) 852 op_kind = OO_Array_New; 853 break; 854 855 case 'd': 856 if (strcmp (post_op_name, "delete") == 0) 857 op_kind = OO_Delete; 858 else if (strcmp (post_op_name, "delete[]") == 0) 859 op_kind = OO_Array_Delete; 860 break; 861 862 case '+': 863 if (post_op_name[1] == '\0') 864 op_kind = OO_Plus; 865 else if (post_op_name[2] == '\0') 866 { 867 if (post_op_name[1] == '=') 868 op_kind = OO_PlusEqual; 869 else if (post_op_name[1] == '+') 870 op_kind = OO_PlusPlus; 871 } 872 break; 873 874 case '-': 875 if (post_op_name[1] == '\0') 876 op_kind = OO_Minus; 877 else if (post_op_name[2] == '\0') 878 { 879 switch (post_op_name[1]) 880 { 881 case '=': op_kind = OO_MinusEqual; break; 882 case '-': op_kind = OO_MinusMinus; break; 883 case '>': op_kind = OO_Arrow; break; 884 } 885 } 886 else if (post_op_name[3] == '\0') 887 { 888 if (post_op_name[2] == '*') 889 op_kind = OO_ArrowStar; break; 890 } 891 break; 892 893 case '*': 894 if (post_op_name[1] == '\0') 895 op_kind = OO_Star; 896 else if (post_op_name[1] == '=' && post_op_name[2] == '\0') 897 op_kind = OO_StarEqual; 898 break; 899 900 case '/': 901 if (post_op_name[1] == '\0') 902 op_kind = OO_Slash; 903 else if (post_op_name[1] == '=' && post_op_name[2] == '\0') 904 op_kind = OO_SlashEqual; 905 break; 906 907 case '%': 908 if (post_op_name[1] == '\0') 909 op_kind = OO_Percent; 910 else if (post_op_name[1] == '=' && post_op_name[2] == '\0') 911 op_kind = OO_PercentEqual; 912 break; 913 914 915 case '^': 916 if (post_op_name[1] == '\0') 917 op_kind = OO_Caret; 918 else if (post_op_name[1] == '=' && post_op_name[2] == '\0') 919 op_kind = OO_CaretEqual; 920 break; 921 922 case '&': 923 if (post_op_name[1] == '\0') 924 op_kind = OO_Amp; 925 else if (post_op_name[2] == '\0') 926 { 927 switch (post_op_name[1]) 928 { 929 case '=': op_kind = OO_AmpEqual; break; 930 case '&': op_kind = OO_AmpAmp; break; 931 } 932 } 933 break; 934 935 case '|': 936 if (post_op_name[1] == '\0') 937 op_kind = OO_Pipe; 938 else if (post_op_name[2] == '\0') 939 { 940 switch (post_op_name[1]) 941 { 942 case '=': op_kind = OO_PipeEqual; break; 943 case '|': op_kind = OO_PipePipe; break; 944 } 945 } 946 break; 947 948 case '~': 949 if (post_op_name[1] == '\0') 950 op_kind = OO_Tilde; 951 break; 952 953 case '!': 954 if (post_op_name[1] == '\0') 955 op_kind = OO_Exclaim; 956 else if (post_op_name[1] == '=' && post_op_name[2] == '\0') 957 op_kind = OO_ExclaimEqual; 958 break; 959 960 case '=': 961 if (post_op_name[1] == '\0') 962 op_kind = OO_Equal; 963 else if (post_op_name[1] == '=' && post_op_name[2] == '\0') 964 op_kind = OO_EqualEqual; 965 break; 966 967 case '<': 968 if (post_op_name[1] == '\0') 969 op_kind = OO_Less; 970 else if (post_op_name[2] == '\0') 971 { 972 switch (post_op_name[1]) 973 { 974 case '<': op_kind = OO_LessLess; break; 975 case '=': op_kind = OO_LessEqual; break; 976 } 977 } 978 else if (post_op_name[3] == '\0') 979 { 980 if (post_op_name[2] == '=') 981 op_kind = OO_LessLessEqual; 982 } 983 break; 984 985 case '>': 986 if (post_op_name[1] == '\0') 987 op_kind = OO_Greater; 988 else if (post_op_name[2] == '\0') 989 { 990 switch (post_op_name[1]) 991 { 992 case '>': op_kind = OO_GreaterGreater; break; 993 case '=': op_kind = OO_GreaterEqual; break; 994 } 995 } 996 else if (post_op_name[1] == '>' && 997 post_op_name[2] == '=' && 998 post_op_name[3] == '\0') 999 { 1000 op_kind = OO_GreaterGreaterEqual; 1001 } 1002 break; 1003 1004 case ',': 1005 if (post_op_name[1] == '\0') 1006 op_kind = OO_Comma; 1007 break; 1008 1009 case '(': 1010 if (post_op_name[1] == ')' && post_op_name[2] == '\0') 1011 op_kind = OO_Call; 1012 break; 1013 1014 case '[': 1015 if (post_op_name[1] == ']' && post_op_name[2] == '\0') 1016 op_kind = OO_Subscript; 1017 break; 1018 } 1019 1020 return true; 1021} 1022CXXMethodDecl * 1023ClangASTContext::AddMethodToCXXRecordType 1024( 1025 ASTContext *ast_context, 1026 clang_type_t record_opaque_type, 1027 const char *name, 1028 clang_type_t method_opaque_type, 1029 lldb::AccessType access, 1030 bool is_virtual, 1031 bool is_static, 1032 bool is_inline, 1033 bool is_explicit 1034) 1035{ 1036 if (!record_opaque_type || !method_opaque_type || !name) 1037 return NULL; 1038 1039 assert(ast_context); 1040 1041 IdentifierTable *identifier_table = &ast_context->Idents; 1042 1043 assert(identifier_table); 1044 1045 QualType record_qual_type(QualType::getFromOpaquePtr(record_opaque_type)); 1046 1047 clang::Type *clang_type(record_qual_type.getTypePtr()); 1048 1049 if (clang_type == NULL) 1050 return NULL; 1051 1052 RecordType *record_clang_type(dyn_cast<RecordType>(clang_type)); 1053 1054 if (record_clang_type == NULL) 1055 return NULL; 1056 1057 RecordDecl *record_decl = record_clang_type->getDecl(); 1058 1059 if (record_decl == NULL) 1060 return NULL; 1061 1062 CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 1063 1064 if (cxx_record_decl == NULL) 1065 return NULL; 1066 1067 QualType method_qual_type (QualType::getFromOpaquePtr (method_opaque_type)); 1068 1069 CXXMethodDecl *cxx_method_decl = NULL; 1070 1071 DeclarationName decl_name (&identifier_table->get(name)); 1072 1073 const bool is_implicitly_declared = false; 1074 1075 clang::FunctionType *function_Type = dyn_cast<FunctionType>(method_qual_type.getTypePtr()); 1076 1077 if (function_Type == NULL) 1078 return NULL; 1079 1080 FunctionProtoType *method_function_prototype (dyn_cast<FunctionProtoType>(function_Type)); 1081 1082 if (!method_function_prototype) 1083 return NULL; 1084 1085 unsigned int num_params = method_function_prototype->getNumArgs(); 1086 1087 if (name[0] == '~') 1088 { 1089 cxx_method_decl = CXXDestructorDecl::Create (*ast_context, 1090 cxx_record_decl, 1091 DeclarationNameInfo (ast_context->DeclarationNames.getCXXDestructorName (ast_context->getCanonicalType (record_qual_type)), SourceLocation()), 1092 method_qual_type, 1093 is_inline, 1094 is_implicitly_declared); 1095 } 1096 else if (decl_name == record_decl->getDeclName()) 1097 { 1098 cxx_method_decl = CXXConstructorDecl::Create (*ast_context, 1099 cxx_record_decl, 1100 DeclarationNameInfo (ast_context->DeclarationNames.getCXXConstructorName (ast_context->getCanonicalType (record_qual_type)), SourceLocation()), 1101 method_qual_type, 1102 NULL, // TypeSourceInfo * 1103 is_explicit, 1104 is_inline, 1105 is_implicitly_declared); 1106 } 1107 else 1108 { 1109 1110 OverloadedOperatorKind op_kind = NUM_OVERLOADED_OPERATORS; 1111 if (IsOperator (name, op_kind)) 1112 { 1113 if (op_kind != NUM_OVERLOADED_OPERATORS) 1114 { 1115 cxx_method_decl = CXXMethodDecl::Create (*ast_context, 1116 cxx_record_decl, 1117 DeclarationNameInfo (ast_context->DeclarationNames.getCXXOperatorName (op_kind), SourceLocation()), 1118 method_qual_type, 1119 NULL, // TypeSourceInfo * 1120 is_static, 1121 SC_None, 1122 is_inline); 1123 } 1124 else if (num_params == 0) 1125 { 1126 // Conversion operators don't take params... 1127 cxx_method_decl = CXXConversionDecl::Create (*ast_context, 1128 cxx_record_decl, 1129 DeclarationNameInfo (ast_context->DeclarationNames.getCXXConversionFunctionName (ast_context->getCanonicalType (function_Type->getResultType())), SourceLocation()), 1130 method_qual_type, 1131 NULL, // TypeSourceInfo * 1132 is_inline, 1133 is_explicit); 1134 } 1135 } 1136 1137 if (cxx_method_decl == NULL) 1138 { 1139 cxx_method_decl = CXXMethodDecl::Create (*ast_context, 1140 cxx_record_decl, 1141 DeclarationNameInfo (decl_name, SourceLocation()), 1142 method_qual_type, 1143 NULL, // TypeSourceInfo * 1144 is_static, 1145 SC_None, 1146 is_inline); 1147 } 1148 } 1149 1150 AccessSpecifier access_specifier = ConvertAccessTypeToAccessSpecifier (access); 1151 1152 cxx_method_decl->setAccess (access_specifier); 1153 cxx_method_decl->setVirtualAsWritten (is_virtual); 1154 1155 // Populate the method decl with parameter decls 1156 1157 ParmVarDecl *params[num_params]; 1158 1159 for (int param_index = 0; 1160 param_index < num_params; 1161 ++param_index) 1162 { 1163 params[param_index] = ParmVarDecl::Create (*ast_context, 1164 cxx_method_decl, 1165 SourceLocation(), 1166 NULL, // anonymous 1167 method_function_prototype->getArgType(param_index), 1168 NULL, 1169 SC_None, 1170 SC_None, 1171 NULL); 1172 } 1173 1174 cxx_method_decl->setParams (params, num_params); 1175 1176 cxx_record_decl->addDecl (cxx_method_decl); 1177 1178 return cxx_method_decl; 1179} 1180 1181bool 1182ClangASTContext::AddFieldToRecordType 1183( 1184 ASTContext *ast_context, 1185 clang_type_t record_clang_type, 1186 const char *name, 1187 clang_type_t field_type, 1188 AccessType access, 1189 uint32_t bitfield_bit_size 1190) 1191{ 1192 if (record_clang_type == NULL || field_type == NULL) 1193 return false; 1194 1195 IdentifierTable *identifier_table = &ast_context->Idents; 1196 1197 assert (ast_context != NULL); 1198 assert (identifier_table != NULL); 1199 1200 QualType record_qual_type(QualType::getFromOpaquePtr(record_clang_type)); 1201 1202 clang::Type *clang_type = record_qual_type.getTypePtr(); 1203 if (clang_type) 1204 { 1205 const RecordType *record_type = dyn_cast<RecordType>(clang_type); 1206 1207 if (record_type) 1208 { 1209 RecordDecl *record_decl = record_type->getDecl(); 1210 1211 clang::Expr *bit_width = NULL; 1212 if (bitfield_bit_size != 0) 1213 { 1214 APInt bitfield_bit_size_apint(ast_context->getTypeSize(ast_context->IntTy), bitfield_bit_size); 1215 bit_width = new (*ast_context)IntegerLiteral (*ast_context, bitfield_bit_size_apint, ast_context->IntTy, SourceLocation()); 1216 } 1217 FieldDecl *field = FieldDecl::Create (*ast_context, 1218 record_decl, 1219 SourceLocation(), 1220 name ? &identifier_table->get(name) : NULL, // Identifier 1221 QualType::getFromOpaquePtr(field_type), // Field type 1222 NULL, // DeclaratorInfo * 1223 bit_width, // BitWidth 1224 false); // Mutable 1225 1226 field->setAccess (ConvertAccessTypeToAccessSpecifier (access)); 1227 1228 if (field) 1229 { 1230 record_decl->addDecl(field); 1231 } 1232 } 1233 else 1234 { 1235 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(clang_type); 1236 if (objc_class_type) 1237 { 1238 bool is_synthesized = false; 1239 ClangASTContext::AddObjCClassIVar (ast_context, 1240 record_clang_type, 1241 name, 1242 field_type, 1243 access, 1244 bitfield_bit_size, 1245 is_synthesized); 1246 } 1247 } 1248 } 1249 return false; 1250} 1251 1252bool 1253ClangASTContext::FieldIsBitfield (FieldDecl* field, uint32_t& bitfield_bit_size) 1254{ 1255 return FieldIsBitfield(getASTContext(), field, bitfield_bit_size); 1256} 1257 1258bool 1259ClangASTContext::FieldIsBitfield 1260( 1261 ASTContext *ast_context, 1262 FieldDecl* field, 1263 uint32_t& bitfield_bit_size 1264) 1265{ 1266 if (ast_context == NULL || field == NULL) 1267 return false; 1268 1269 if (field->isBitField()) 1270 { 1271 Expr* bit_width_expr = field->getBitWidth(); 1272 if (bit_width_expr) 1273 { 1274 llvm::APSInt bit_width_apsint; 1275 if (bit_width_expr->isIntegerConstantExpr(bit_width_apsint, *ast_context)) 1276 { 1277 bitfield_bit_size = bit_width_apsint.getLimitedValue(UINT32_MAX); 1278 return true; 1279 } 1280 } 1281 } 1282 return false; 1283} 1284 1285bool 1286ClangASTContext::RecordHasFields (const RecordDecl *record_decl) 1287{ 1288 if (record_decl == NULL) 1289 return false; 1290 1291 if (!record_decl->field_empty()) 1292 return true; 1293 1294 // No fields, lets check this is a CXX record and check the base classes 1295 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 1296 if (cxx_record_decl) 1297 { 1298 CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 1299 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 1300 base_class != base_class_end; 1301 ++base_class) 1302 { 1303 const CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl()); 1304 if (RecordHasFields(base_class_decl)) 1305 return true; 1306 } 1307 } 1308 return false; 1309} 1310 1311void 1312ClangASTContext::SetDefaultAccessForRecordFields (clang_type_t clang_qual_type, int default_accessibility, int *assigned_accessibilities, size_t num_assigned_accessibilities) 1313{ 1314 if (clang_qual_type) 1315 { 1316 QualType qual_type(QualType::getFromOpaquePtr(clang_qual_type)); 1317 clang::Type *clang_type = qual_type.getTypePtr(); 1318 if (clang_type) 1319 { 1320 RecordType *record_type = dyn_cast<RecordType>(clang_type); 1321 if (record_type) 1322 { 1323 RecordDecl *record_decl = record_type->getDecl(); 1324 if (record_decl) 1325 { 1326 uint32_t field_idx; 1327 RecordDecl::field_iterator field, field_end; 1328 for (field = record_decl->field_begin(), field_end = record_decl->field_end(), field_idx = 0; 1329 field != field_end; 1330 ++field, ++field_idx) 1331 { 1332 // If no accessibility was assigned, assign the correct one 1333 if (field_idx < num_assigned_accessibilities && assigned_accessibilities[field_idx] == clang::AS_none) 1334 field->setAccess ((AccessSpecifier)default_accessibility); 1335 } 1336 } 1337 } 1338 } 1339 } 1340} 1341 1342#pragma mark C++ Base Classes 1343 1344CXXBaseSpecifier * 1345ClangASTContext::CreateBaseClassSpecifier (clang_type_t base_class_type, AccessType access, bool is_virtual, bool base_of_class) 1346{ 1347 if (base_class_type) 1348 return new CXXBaseSpecifier (SourceRange(), 1349 is_virtual, 1350 base_of_class, 1351 ConvertAccessTypeToAccessSpecifier (access), 1352 getASTContext()->CreateTypeSourceInfo (QualType::getFromOpaquePtr(base_class_type))); 1353 return NULL; 1354} 1355 1356void 1357ClangASTContext::DeleteBaseClassSpecifiers (CXXBaseSpecifier **base_classes, unsigned num_base_classes) 1358{ 1359 for (unsigned i=0; i<num_base_classes; ++i) 1360 { 1361 delete base_classes[i]; 1362 base_classes[i] = NULL; 1363 } 1364} 1365 1366bool 1367ClangASTContext::SetBaseClassesForClassType (clang_type_t class_clang_type, CXXBaseSpecifier const * const *base_classes, unsigned num_base_classes) 1368{ 1369 if (class_clang_type) 1370 { 1371 clang::Type *clang_type = QualType::getFromOpaquePtr(class_clang_type).getTypePtr(); 1372 if (clang_type) 1373 { 1374 RecordType *record_type = dyn_cast<RecordType>(clang_type); 1375 if (record_type) 1376 { 1377 CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_type->getDecl()); 1378 if (cxx_record_decl) 1379 { 1380 cxx_record_decl->setBases(base_classes, num_base_classes); 1381 return true; 1382 } 1383 } 1384 } 1385 } 1386 return false; 1387} 1388#pragma mark Objective C Classes 1389 1390clang_type_t 1391ClangASTContext::CreateObjCClass 1392( 1393 const char *name, 1394 DeclContext *decl_ctx, 1395 bool isForwardDecl, 1396 bool isInternal 1397) 1398{ 1399 ASTContext *ast_context = getASTContext(); 1400 assert (ast_context != NULL); 1401 assert (name && name[0]); 1402 if (decl_ctx == NULL) 1403 decl_ctx = ast_context->getTranslationUnitDecl(); 1404 1405 // NOTE: Eventually CXXRecordDecl will be merged back into RecordDecl and 1406 // we will need to update this code. I was told to currently always use 1407 // the CXXRecordDecl class since we often don't know from debug information 1408 // if something is struct or a class, so we default to always use the more 1409 // complete definition just in case. 1410 ObjCInterfaceDecl *decl = ObjCInterfaceDecl::Create (*ast_context, 1411 decl_ctx, 1412 SourceLocation(), 1413 &ast_context->Idents.get(name), 1414 SourceLocation(), 1415 isForwardDecl, 1416 isInternal); 1417 1418 return ast_context->getObjCInterfaceType(decl).getAsOpaquePtr(); 1419} 1420 1421bool 1422ClangASTContext::SetObjCSuperClass (clang_type_t class_opaque_type, clang_type_t super_opaque_type) 1423{ 1424 if (class_opaque_type && super_opaque_type) 1425 { 1426 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type)); 1427 QualType super_qual_type(QualType::getFromOpaquePtr(super_opaque_type)); 1428 clang::Type *class_type = class_qual_type.getTypePtr(); 1429 clang::Type *super_type = super_qual_type.getTypePtr(); 1430 if (class_type && super_type) 1431 { 1432 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type); 1433 ObjCObjectType *objc_super_type = dyn_cast<ObjCObjectType>(super_type); 1434 if (objc_class_type && objc_super_type) 1435 { 1436 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 1437 ObjCInterfaceDecl *super_interface_decl = objc_super_type->getInterface(); 1438 if (class_interface_decl && super_interface_decl) 1439 { 1440 class_interface_decl->setSuperClass(super_interface_decl); 1441 return true; 1442 } 1443 } 1444 } 1445 } 1446 return false; 1447} 1448 1449 1450bool 1451ClangASTContext::AddObjCClassIVar 1452( 1453 ASTContext *ast_context, 1454 clang_type_t class_opaque_type, 1455 const char *name, 1456 clang_type_t ivar_opaque_type, 1457 AccessType access, 1458 uint32_t bitfield_bit_size, 1459 bool is_synthesized 1460) 1461{ 1462 if (class_opaque_type == NULL || ivar_opaque_type == NULL) 1463 return false; 1464 1465 IdentifierTable *identifier_table = &ast_context->Idents; 1466 1467 assert (ast_context != NULL); 1468 assert (identifier_table != NULL); 1469 1470 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type)); 1471 1472 clang::Type *class_type = class_qual_type.getTypePtr(); 1473 if (class_type) 1474 { 1475 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type); 1476 1477 if (objc_class_type) 1478 { 1479 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 1480 1481 if (class_interface_decl) 1482 { 1483 clang::Expr *bit_width = NULL; 1484 if (bitfield_bit_size != 0) 1485 { 1486 APInt bitfield_bit_size_apint(ast_context->getTypeSize(ast_context->IntTy), bitfield_bit_size); 1487 bit_width = new (*ast_context)IntegerLiteral (*ast_context, bitfield_bit_size_apint, ast_context->IntTy, SourceLocation()); 1488 } 1489 1490 ObjCIvarDecl *field = ObjCIvarDecl::Create (*ast_context, 1491 class_interface_decl, 1492 SourceLocation(), 1493 &identifier_table->get(name), // Identifier 1494 QualType::getFromOpaquePtr(ivar_opaque_type), // Field type 1495 NULL, // TypeSourceInfo * 1496 ConvertAccessTypeToObjCIvarAccessControl (access), 1497 bit_width, 1498 is_synthesized); 1499 1500 if (field) 1501 { 1502 class_interface_decl->addDecl(field); 1503 return true; 1504 } 1505 } 1506 } 1507 } 1508 return false; 1509} 1510 1511 1512bool 1513ClangASTContext::ObjCTypeHasIVars (clang_type_t class_opaque_type, bool check_superclass) 1514{ 1515 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type)); 1516 1517 clang::Type *class_type = class_qual_type.getTypePtr(); 1518 if (class_type) 1519 { 1520 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type); 1521 1522 if (objc_class_type) 1523 return ObjCDeclHasIVars (objc_class_type->getInterface(), check_superclass); 1524 } 1525 return false; 1526} 1527 1528bool 1529ClangASTContext::ObjCDeclHasIVars (ObjCInterfaceDecl *class_interface_decl, bool check_superclass) 1530{ 1531 while (class_interface_decl) 1532 { 1533 if (class_interface_decl->ivar_size() > 0) 1534 return true; 1535 1536 if (check_superclass) 1537 class_interface_decl = class_interface_decl->getSuperClass(); 1538 else 1539 break; 1540 } 1541 return false; 1542} 1543 1544ObjCMethodDecl * 1545ClangASTContext::AddMethodToObjCObjectType 1546( 1547 ASTContext *ast_context, 1548 clang_type_t class_opaque_type, 1549 const char *name, // the full symbol name as seen in the symbol table ("-[NString stringWithCString:]") 1550 clang_type_t method_opaque_type, 1551 lldb::AccessType access 1552) 1553{ 1554 if (class_opaque_type == NULL || method_opaque_type == NULL) 1555 return NULL; 1556 1557 IdentifierTable *identifier_table = &ast_context->Idents; 1558 1559 assert (ast_context != NULL); 1560 assert (identifier_table != NULL); 1561 1562 QualType class_qual_type(QualType::getFromOpaquePtr(class_opaque_type)); 1563 1564 clang::Type *class_type = class_qual_type.getTypePtr(); 1565 if (class_type == NULL) 1566 return NULL; 1567 1568 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(class_type); 1569 1570 if (objc_class_type == NULL) 1571 return NULL; 1572 1573 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 1574 1575 if (class_interface_decl == NULL) 1576 return NULL; 1577 1578 const char *selector_start = ::strchr (name, ' '); 1579 if (selector_start == NULL) 1580 return NULL; 1581 1582 selector_start++; 1583 if (!(::isalpha (selector_start[0]) || selector_start[0] == '_')) 1584 return NULL; 1585 llvm::SmallVector<IdentifierInfo *, 12> selector_idents; 1586 1587 size_t len = 0; 1588 const char *start; 1589 //printf ("name = '%s'\n", name); 1590 1591 unsigned num_selectors_with_args = 0; 1592 for (start = selector_start; 1593 start && *start != '\0' && *start != ']'; 1594 start += len) 1595 { 1596 len = ::strcspn(start, ":]"); 1597 bool has_arg = (start[len] == ':'); 1598 if (has_arg) 1599 ++num_selectors_with_args; 1600 selector_idents.push_back (&identifier_table->get (StringRef (start, len))); 1601 if (has_arg) 1602 len += 1; 1603 } 1604 1605 1606 if (selector_idents.size() == 0) 1607 return 0; 1608 1609 clang::Selector method_selector = ast_context->Selectors.getSelector (num_selectors_with_args ? selector_idents.size() : 0, 1610 selector_idents.data()); 1611 1612 QualType method_qual_type (QualType::getFromOpaquePtr (method_opaque_type)); 1613 1614 // Populate the method decl with parameter decls 1615 clang::Type *method_type(method_qual_type.getTypePtr()); 1616 1617 if (method_type == NULL) 1618 return NULL; 1619 1620 FunctionProtoType *method_function_prototype (dyn_cast<FunctionProtoType>(method_type)); 1621 1622 if (!method_function_prototype) 1623 return NULL; 1624 1625 1626 bool is_variadic = false; 1627 bool is_synthesized = false; 1628 bool is_defined = false; 1629 ObjCMethodDecl::ImplementationControl imp_control = ObjCMethodDecl::None; 1630 1631 const unsigned num_args = method_function_prototype->getNumArgs(); 1632 1633 ObjCMethodDecl *objc_method_decl = ObjCMethodDecl::Create (*ast_context, 1634 SourceLocation(), // beginLoc, 1635 SourceLocation(), // endLoc, 1636 method_selector, 1637 method_function_prototype->getResultType(), 1638 NULL, // TypeSourceInfo *ResultTInfo, 1639 GetDeclContextForType (class_opaque_type), 1640 name[0] == '-', 1641 is_variadic, 1642 is_synthesized, 1643 is_defined, 1644 imp_control, 1645 num_args); 1646 1647 1648 if (objc_method_decl == NULL) 1649 return NULL; 1650 1651 if (num_args > 0) 1652 { 1653 llvm::SmallVector<ParmVarDecl *, 12> params; 1654 1655 for (int param_index = 0; param_index < num_args; ++param_index) 1656 { 1657 params.push_back (ParmVarDecl::Create (*ast_context, 1658 objc_method_decl, 1659 SourceLocation(), 1660 NULL, // anonymous 1661 method_function_prototype->getArgType(param_index), 1662 NULL, 1663 SC_Auto, 1664 SC_Auto, 1665 NULL)); 1666 } 1667 1668 objc_method_decl->setMethodParams(*ast_context, params.data(), params.size(), num_args); 1669 } 1670 1671 class_interface_decl->addDecl (objc_method_decl); 1672 1673 1674 return objc_method_decl; 1675} 1676 1677 1678uint32_t 1679ClangASTContext::GetTypeInfo 1680( 1681 clang_type_t clang_type, 1682 clang::ASTContext *ast_context, 1683 clang_type_t *pointee_or_element_clang_type 1684) 1685{ 1686 if (clang_type == NULL) 1687 return 0; 1688 1689 if (pointee_or_element_clang_type) 1690 *pointee_or_element_clang_type = NULL; 1691 1692 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 1693 1694 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 1695 switch (type_class) 1696 { 1697 case clang::Type::Builtin: 1698 switch (cast<clang::BuiltinType>(qual_type)->getKind()) 1699 { 1700 case clang::BuiltinType::ObjCId: 1701 case clang::BuiltinType::ObjCClass: 1702 if (ast_context && pointee_or_element_clang_type) 1703 *pointee_or_element_clang_type = ast_context->ObjCBuiltinClassTy.getAsOpaquePtr(); 1704 return eTypeIsBuiltIn | eTypeIsPointer | eTypeHasValue; 1705 1706 default: 1707 break; 1708 } 1709 return eTypeIsBuiltIn | eTypeHasValue; 1710 1711 case clang::Type::BlockPointer: 1712 if (pointee_or_element_clang_type) 1713 *pointee_or_element_clang_type = qual_type->getPointeeType().getAsOpaquePtr(); 1714 return eTypeIsPointer | eTypeHasChildren | eTypeIsBlock; 1715 1716 case clang::Type::Complex: return eTypeHasChildren | eTypeIsBuiltIn | eTypeHasValue; 1717 1718 case clang::Type::ConstantArray: 1719 case clang::Type::DependentSizedArray: 1720 case clang::Type::IncompleteArray: 1721 case clang::Type::VariableArray: 1722 if (pointee_or_element_clang_type) 1723 *pointee_or_element_clang_type = cast<ArrayType>(qual_type.getTypePtr())->getElementType().getAsOpaquePtr(); 1724 return eTypeHasChildren | eTypeIsArray; 1725 1726 case clang::Type::DependentName: return 0; 1727 case clang::Type::DependentSizedExtVector: return eTypeHasChildren | eTypeIsVector; 1728 case clang::Type::DependentTemplateSpecialization: return eTypeIsTemplate; 1729 case clang::Type::Decltype: return 0; 1730 1731 case clang::Type::Enum: 1732 if (pointee_or_element_clang_type) 1733 *pointee_or_element_clang_type = cast<EnumType>(qual_type)->getDecl()->getIntegerType().getAsOpaquePtr(); 1734 return eTypeIsEnumeration | eTypeHasValue; 1735 1736 case clang::Type::Elaborated: return 0; 1737 case clang::Type::ExtVector: return eTypeHasChildren | eTypeIsVector; 1738 case clang::Type::FunctionProto: return eTypeIsFuncPrototype | eTypeHasValue; 1739 case clang::Type::FunctionNoProto: return eTypeIsFuncPrototype | eTypeHasValue; 1740 case clang::Type::InjectedClassName: return 0; 1741 1742 case clang::Type::LValueReference: 1743 case clang::Type::RValueReference: 1744 if (pointee_or_element_clang_type) 1745 *pointee_or_element_clang_type = cast<ReferenceType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr(); 1746 return eTypeHasChildren | eTypeIsReference | eTypeHasValue; 1747 1748 case clang::Type::MemberPointer: return eTypeIsPointer | eTypeIsMember | eTypeHasValue; 1749 1750 case clang::Type::ObjCObjectPointer: 1751 if (pointee_or_element_clang_type) 1752 *pointee_or_element_clang_type = qual_type->getPointeeType().getAsOpaquePtr(); 1753 return eTypeHasChildren | eTypeIsObjC | eTypeIsClass | eTypeIsPointer | eTypeHasValue; 1754 1755 case clang::Type::ObjCObject: return eTypeHasChildren | eTypeIsObjC | eTypeIsClass; 1756 case clang::Type::ObjCInterface: return eTypeHasChildren | eTypeIsObjC | eTypeIsClass; 1757 1758 case clang::Type::Pointer: 1759 if (pointee_or_element_clang_type) 1760 *pointee_or_element_clang_type = qual_type->getPointeeType().getAsOpaquePtr(); 1761 return eTypeHasChildren | eTypeIsPointer | eTypeHasValue; 1762 1763 case clang::Type::Record: 1764 if (qual_type->getAsCXXRecordDecl()) 1765 return eTypeHasChildren | eTypeIsClass | eTypeIsCPlusPlus; 1766 else 1767 return eTypeHasChildren | eTypeIsStructUnion; 1768 break; 1769 case clang::Type::SubstTemplateTypeParm: return eTypeIsTemplate; 1770 case clang::Type::TemplateTypeParm: return eTypeIsTemplate; 1771 case clang::Type::TemplateSpecialization: return eTypeIsTemplate; 1772 1773 case clang::Type::Typedef: 1774 return eTypeIsTypedef | ClangASTContext::GetTypeInfo (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr(), 1775 ast_context, 1776 pointee_or_element_clang_type); 1777 1778 case clang::Type::TypeOfExpr: return 0; 1779 case clang::Type::TypeOf: return 0; 1780 case clang::Type::UnresolvedUsing: return 0; 1781 case clang::Type::Vector: return eTypeHasChildren | eTypeIsVector; 1782 default: return 0; 1783 } 1784 return 0; 1785} 1786 1787 1788#pragma mark Aggregate Types 1789 1790bool 1791ClangASTContext::IsAggregateType (clang_type_t clang_type) 1792{ 1793 if (clang_type == NULL) 1794 return false; 1795 1796 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 1797 1798 if (qual_type->isAggregateType ()) 1799 return true; 1800 1801 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 1802 switch (type_class) 1803 { 1804 case clang::Type::IncompleteArray: 1805 case clang::Type::VariableArray: 1806 case clang::Type::ConstantArray: 1807 case clang::Type::ExtVector: 1808 case clang::Type::Vector: 1809 case clang::Type::Record: 1810 case clang::Type::ObjCObject: 1811 case clang::Type::ObjCInterface: 1812 return true; 1813 1814 case clang::Type::Typedef: 1815 return ClangASTContext::IsAggregateType (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr()); 1816 1817 default: 1818 break; 1819 } 1820 // The clang type does have a value 1821 return false; 1822} 1823 1824uint32_t 1825ClangASTContext::GetNumChildren (clang_type_t clang_qual_type, bool omit_empty_base_classes) 1826{ 1827 if (clang_qual_type == NULL) 1828 return 0; 1829 1830 uint32_t num_children = 0; 1831 QualType qual_type(QualType::getFromOpaquePtr(clang_qual_type)); 1832 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 1833 switch (type_class) 1834 { 1835 case clang::Type::Builtin: 1836 switch (cast<clang::BuiltinType>(qual_type)->getKind()) 1837 { 1838 case clang::BuiltinType::ObjCId: // child is Class 1839 case clang::BuiltinType::ObjCClass: // child is Class 1840 num_children = 1; 1841 break; 1842 1843 default: 1844 break; 1845 } 1846 break; 1847 1848 case clang::Type::Record: 1849 { 1850 const RecordType *record_type = cast<RecordType>(qual_type.getTypePtr()); 1851 const RecordDecl *record_decl = record_type->getDecl(); 1852 assert(record_decl); 1853 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 1854 if (cxx_record_decl) 1855 { 1856 if (omit_empty_base_classes) 1857 { 1858 // Check each base classes to see if it or any of its 1859 // base classes contain any fields. This can help 1860 // limit the noise in variable views by not having to 1861 // show base classes that contain no members. 1862 CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 1863 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 1864 base_class != base_class_end; 1865 ++base_class) 1866 { 1867 const CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl()); 1868 1869 // Skip empty base classes 1870 if (RecordHasFields(base_class_decl) == false) 1871 continue; 1872 1873 num_children++; 1874 } 1875 } 1876 else 1877 { 1878 // Include all base classes 1879 num_children += cxx_record_decl->getNumBases(); 1880 } 1881 1882 } 1883 RecordDecl::field_iterator field, field_end; 1884 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field) 1885 ++num_children; 1886 } 1887 break; 1888 1889 case clang::Type::ObjCObject: 1890 case clang::Type::ObjCInterface: 1891 { 1892 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr()); 1893 assert (objc_class_type); 1894 if (objc_class_type) 1895 { 1896 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 1897 1898 if (class_interface_decl) 1899 { 1900 1901 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass(); 1902 if (superclass_interface_decl) 1903 { 1904 if (omit_empty_base_classes) 1905 { 1906 if (ClangASTContext::ObjCDeclHasIVars (superclass_interface_decl, true)) 1907 ++num_children; 1908 } 1909 else 1910 ++num_children; 1911 } 1912 1913 num_children += class_interface_decl->ivar_size(); 1914 } 1915 } 1916 } 1917 break; 1918 1919 case clang::Type::ObjCObjectPointer: 1920 { 1921 ObjCObjectPointerType *pointer_type = cast<ObjCObjectPointerType>(qual_type.getTypePtr()); 1922 QualType pointee_type = pointer_type->getPointeeType(); 1923 uint32_t num_pointee_children = ClangASTContext::GetNumChildren (pointee_type.getAsOpaquePtr(), 1924 omit_empty_base_classes); 1925 // If this type points to a simple type, then it has 1 child 1926 if (num_pointee_children == 0) 1927 num_children = 1; 1928 else 1929 num_children = num_pointee_children; 1930 } 1931 break; 1932 1933 case clang::Type::ConstantArray: 1934 num_children = cast<ConstantArrayType>(qual_type.getTypePtr())->getSize().getLimitedValue(); 1935 break; 1936 1937 case clang::Type::Pointer: 1938 { 1939 PointerType *pointer_type = cast<PointerType>(qual_type.getTypePtr()); 1940 QualType pointee_type = pointer_type->getPointeeType(); 1941 uint32_t num_pointee_children = ClangASTContext::GetNumChildren (pointee_type.getAsOpaquePtr(), 1942 omit_empty_base_classes); 1943 // If this type points to a simple type, then it has 1 child 1944 if (num_pointee_children == 0) 1945 num_children = 1; 1946 else 1947 num_children = num_pointee_children; 1948 } 1949 break; 1950 1951 case clang::Type::LValueReference: 1952 case clang::Type::RValueReference: 1953 { 1954 ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr()); 1955 QualType pointee_type = reference_type->getPointeeType(); 1956 uint32_t num_pointee_children = ClangASTContext::GetNumChildren (pointee_type.getAsOpaquePtr(), 1957 omit_empty_base_classes); 1958 // If this type points to a simple type, then it has 1 child 1959 if (num_pointee_children == 0) 1960 num_children = 1; 1961 else 1962 num_children = num_pointee_children; 1963 } 1964 break; 1965 1966 1967 case clang::Type::Typedef: 1968 num_children = ClangASTContext::GetNumChildren (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr(), omit_empty_base_classes); 1969 break; 1970 1971 default: 1972 break; 1973 } 1974 return num_children; 1975} 1976 1977 1978clang_type_t 1979ClangASTContext::GetChildClangTypeAtIndex 1980( 1981 const char *parent_name, 1982 clang_type_t parent_clang_type, 1983 uint32_t idx, 1984 bool transparent_pointers, 1985 bool omit_empty_base_classes, 1986 std::string& child_name, 1987 uint32_t &child_byte_size, 1988 int32_t &child_byte_offset, 1989 uint32_t &child_bitfield_bit_size, 1990 uint32_t &child_bitfield_bit_offset, 1991 bool &child_is_base_class 1992) 1993{ 1994 if (parent_clang_type) 1995 1996 return GetChildClangTypeAtIndex (getASTContext(), 1997 parent_name, 1998 parent_clang_type, 1999 idx, 2000 transparent_pointers, 2001 omit_empty_base_classes, 2002 child_name, 2003 child_byte_size, 2004 child_byte_offset, 2005 child_bitfield_bit_size, 2006 child_bitfield_bit_offset, 2007 child_is_base_class); 2008 return NULL; 2009} 2010 2011clang_type_t 2012ClangASTContext::GetChildClangTypeAtIndex 2013( 2014 ASTContext *ast_context, 2015 const char *parent_name, 2016 clang_type_t parent_clang_type, 2017 uint32_t idx, 2018 bool transparent_pointers, 2019 bool omit_empty_base_classes, 2020 std::string& child_name, 2021 uint32_t &child_byte_size, 2022 int32_t &child_byte_offset, 2023 uint32_t &child_bitfield_bit_size, 2024 uint32_t &child_bitfield_bit_offset, 2025 bool &child_is_base_class 2026) 2027{ 2028 if (parent_clang_type == NULL) 2029 return NULL; 2030 2031 if (idx < ClangASTContext::GetNumChildren (parent_clang_type, omit_empty_base_classes)) 2032 { 2033 uint32_t bit_offset; 2034 child_bitfield_bit_size = 0; 2035 child_bitfield_bit_offset = 0; 2036 child_is_base_class = false; 2037 QualType parent_qual_type(QualType::getFromOpaquePtr(parent_clang_type)); 2038 const clang::Type::TypeClass parent_type_class = parent_qual_type->getTypeClass(); 2039 switch (parent_type_class) 2040 { 2041 case clang::Type::Builtin: 2042 switch (cast<clang::BuiltinType>(parent_qual_type)->getKind()) 2043 { 2044 case clang::BuiltinType::ObjCId: 2045 case clang::BuiltinType::ObjCClass: 2046 child_name = "isa"; 2047 child_byte_size = ast_context->getTypeSize(ast_context->ObjCBuiltinClassTy) / CHAR_BIT; 2048 return ast_context->ObjCBuiltinClassTy.getAsOpaquePtr(); 2049 2050 default: 2051 break; 2052 } 2053 break; 2054 2055 2056 case clang::Type::Record: 2057 { 2058 const RecordType *record_type = cast<RecordType>(parent_qual_type.getTypePtr()); 2059 const RecordDecl *record_decl = record_type->getDecl(); 2060 assert(record_decl); 2061 const ASTRecordLayout &record_layout = ast_context->getASTRecordLayout(record_decl); 2062 uint32_t child_idx = 0; 2063 2064 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 2065 if (cxx_record_decl) 2066 { 2067 // We might have base classes to print out first 2068 CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 2069 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 2070 base_class != base_class_end; 2071 ++base_class) 2072 { 2073 const CXXRecordDecl *base_class_decl = NULL; 2074 2075 // Skip empty base classes 2076 if (omit_empty_base_classes) 2077 { 2078 base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl()); 2079 if (RecordHasFields(base_class_decl) == false) 2080 continue; 2081 } 2082 2083 if (idx == child_idx) 2084 { 2085 if (base_class_decl == NULL) 2086 base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl()); 2087 2088 2089 if (base_class->isVirtual()) 2090 bit_offset = record_layout.getVBaseClassOffset(base_class_decl); 2091 else 2092 bit_offset = record_layout.getBaseClassOffset(base_class_decl); 2093 2094 // Base classes should be a multiple of 8 bits in size 2095 assert (bit_offset % 8 == 0); 2096 child_byte_offset = bit_offset/8; 2097 std::string base_class_type_name(base_class->getType().getAsString()); 2098 2099 child_name.assign(base_class_type_name.c_str()); 2100 2101 uint64_t clang_type_info_bit_size = ast_context->getTypeSize(base_class->getType()); 2102 2103 // Base classes biut sizes should be a multiple of 8 bits in size 2104 assert (clang_type_info_bit_size % 8 == 0); 2105 child_byte_size = clang_type_info_bit_size / 8; 2106 child_is_base_class = true; 2107 return base_class->getType().getAsOpaquePtr(); 2108 } 2109 // We don't increment the child index in the for loop since we might 2110 // be skipping empty base classes 2111 ++child_idx; 2112 } 2113 } 2114 // Make sure index is in range... 2115 uint32_t field_idx = 0; 2116 RecordDecl::field_iterator field, field_end; 2117 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field, ++field_idx, ++child_idx) 2118 { 2119 if (idx == child_idx) 2120 { 2121 // Print the member type if requested 2122 // Print the member name and equal sign 2123 child_name.assign(field->getNameAsString().c_str()); 2124 2125 // Figure out the type byte size (field_type_info.first) and 2126 // alignment (field_type_info.second) from the AST context. 2127 std::pair<uint64_t, unsigned> field_type_info = ast_context->getTypeInfo(field->getType()); 2128 assert(field_idx < record_layout.getFieldCount()); 2129 2130 child_byte_size = field_type_info.first / 8; 2131 2132 // Figure out the field offset within the current struct/union/class type 2133 bit_offset = record_layout.getFieldOffset (field_idx); 2134 child_byte_offset = bit_offset / 8; 2135 if (ClangASTContext::FieldIsBitfield (ast_context, *field, child_bitfield_bit_size)) 2136 child_bitfield_bit_offset = bit_offset % 8; 2137 2138 return field->getType().getAsOpaquePtr(); 2139 } 2140 } 2141 } 2142 break; 2143 2144 case clang::Type::ObjCObject: 2145 case clang::Type::ObjCInterface: 2146 { 2147 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(parent_qual_type.getTypePtr()); 2148 assert (objc_class_type); 2149 if (objc_class_type) 2150 { 2151 uint32_t child_idx = 0; 2152 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 2153 2154 if (class_interface_decl) 2155 { 2156 2157 const ASTRecordLayout &interface_layout = ast_context->getASTObjCInterfaceLayout(class_interface_decl); 2158 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass(); 2159 if (superclass_interface_decl) 2160 { 2161 if (omit_empty_base_classes) 2162 { 2163 if (ClangASTContext::GetNumChildren(ast_context->getObjCInterfaceType(superclass_interface_decl).getAsOpaquePtr(), omit_empty_base_classes) > 0) 2164 { 2165 if (idx == 0) 2166 { 2167 QualType ivar_qual_type(ast_context->getObjCInterfaceType(superclass_interface_decl)); 2168 2169 2170 child_name.assign(superclass_interface_decl->getNameAsString().c_str()); 2171 2172 std::pair<uint64_t, unsigned> ivar_type_info = ast_context->getTypeInfo(ivar_qual_type.getTypePtr()); 2173 2174 child_byte_size = ivar_type_info.first / 8; 2175 child_byte_offset = 0; 2176 child_is_base_class = true; 2177 2178 return ivar_qual_type.getAsOpaquePtr(); 2179 } 2180 2181 ++child_idx; 2182 } 2183 } 2184 else 2185 ++child_idx; 2186 } 2187 2188 const uint32_t superclass_idx = child_idx; 2189 2190 if (idx < (child_idx + class_interface_decl->ivar_size())) 2191 { 2192 ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end(); 2193 2194 for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos) 2195 { 2196 if (child_idx == idx) 2197 { 2198 const ObjCIvarDecl* ivar_decl = *ivar_pos; 2199 2200 QualType ivar_qual_type(ivar_decl->getType()); 2201 2202 child_name.assign(ivar_decl->getNameAsString().c_str()); 2203 2204 std::pair<uint64_t, unsigned> ivar_type_info = ast_context->getTypeInfo(ivar_qual_type.getTypePtr()); 2205 2206 child_byte_size = ivar_type_info.first / 8; 2207 2208 // Figure out the field offset within the current struct/union/class type 2209 bit_offset = interface_layout.getFieldOffset (child_idx - superclass_idx); 2210 child_byte_offset = bit_offset / 8; 2211 2212 return ivar_qual_type.getAsOpaquePtr(); 2213 } 2214 ++child_idx; 2215 } 2216 } 2217 } 2218 } 2219 } 2220 break; 2221 2222 case clang::Type::ObjCObjectPointer: 2223 { 2224 ObjCObjectPointerType *pointer_type = cast<ObjCObjectPointerType>(parent_qual_type.getTypePtr()); 2225 QualType pointee_type = pointer_type->getPointeeType(); 2226 2227 if (transparent_pointers && ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2228 { 2229 return GetChildClangTypeAtIndex (ast_context, 2230 parent_name, 2231 pointer_type->getPointeeType().getAsOpaquePtr(), 2232 idx, 2233 transparent_pointers, 2234 omit_empty_base_classes, 2235 child_name, 2236 child_byte_size, 2237 child_byte_offset, 2238 child_bitfield_bit_size, 2239 child_bitfield_bit_offset, 2240 child_is_base_class); 2241 } 2242 else 2243 { 2244 if (parent_name) 2245 { 2246 child_name.assign(1, '*'); 2247 child_name += parent_name; 2248 } 2249 2250 // We have a pointer to an simple type 2251 if (idx == 0) 2252 { 2253 std::pair<uint64_t, unsigned> clang_type_info = ast_context->getTypeInfo(pointee_type); 2254 assert(clang_type_info.first % 8 == 0); 2255 child_byte_size = clang_type_info.first / 8; 2256 child_byte_offset = 0; 2257 return pointee_type.getAsOpaquePtr(); 2258 } 2259 } 2260 } 2261 break; 2262 2263 case clang::Type::ConstantArray: 2264 { 2265 const ConstantArrayType *array = cast<ConstantArrayType>(parent_qual_type.getTypePtr()); 2266 const uint64_t element_count = array->getSize().getLimitedValue(); 2267 2268 if (idx < element_count) 2269 { 2270 std::pair<uint64_t, unsigned> field_type_info = ast_context->getTypeInfo(array->getElementType()); 2271 2272 char element_name[64]; 2273 ::snprintf (element_name, sizeof (element_name), "[%u]", idx); 2274 2275 child_name.assign(element_name); 2276 assert(field_type_info.first % 8 == 0); 2277 child_byte_size = field_type_info.first / 8; 2278 child_byte_offset = idx * child_byte_size; 2279 return array->getElementType().getAsOpaquePtr(); 2280 } 2281 } 2282 break; 2283 2284 case clang::Type::Pointer: 2285 { 2286 PointerType *pointer_type = cast<PointerType>(parent_qual_type.getTypePtr()); 2287 QualType pointee_type = pointer_type->getPointeeType(); 2288 2289 if (transparent_pointers && ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2290 { 2291 return GetChildClangTypeAtIndex (ast_context, 2292 parent_name, 2293 pointer_type->getPointeeType().getAsOpaquePtr(), 2294 idx, 2295 transparent_pointers, 2296 omit_empty_base_classes, 2297 child_name, 2298 child_byte_size, 2299 child_byte_offset, 2300 child_bitfield_bit_size, 2301 child_bitfield_bit_offset, 2302 child_is_base_class); 2303 } 2304 else 2305 { 2306 if (parent_name) 2307 { 2308 child_name.assign(1, '*'); 2309 child_name += parent_name; 2310 } 2311 2312 // We have a pointer to an simple type 2313 if (idx == 0) 2314 { 2315 std::pair<uint64_t, unsigned> clang_type_info = ast_context->getTypeInfo(pointee_type); 2316 assert(clang_type_info.first % 8 == 0); 2317 child_byte_size = clang_type_info.first / 8; 2318 child_byte_offset = 0; 2319 return pointee_type.getAsOpaquePtr(); 2320 } 2321 } 2322 } 2323 break; 2324 2325 case clang::Type::LValueReference: 2326 case clang::Type::RValueReference: 2327 { 2328 ReferenceType *reference_type = cast<ReferenceType>(parent_qual_type.getTypePtr()); 2329 QualType pointee_type(reference_type->getPointeeType()); 2330 clang_type_t pointee_clang_type = pointee_type.getAsOpaquePtr(); 2331 if (transparent_pointers && ClangASTContext::IsAggregateType (pointee_clang_type)) 2332 { 2333 return GetChildClangTypeAtIndex (ast_context, 2334 parent_name, 2335 pointee_clang_type, 2336 idx, 2337 transparent_pointers, 2338 omit_empty_base_classes, 2339 child_name, 2340 child_byte_size, 2341 child_byte_offset, 2342 child_bitfield_bit_size, 2343 child_bitfield_bit_offset, 2344 child_is_base_class); 2345 } 2346 else 2347 { 2348 if (parent_name) 2349 { 2350 child_name.assign(1, '&'); 2351 child_name += parent_name; 2352 } 2353 2354 // We have a pointer to an simple type 2355 if (idx == 0) 2356 { 2357 std::pair<uint64_t, unsigned> clang_type_info = ast_context->getTypeInfo(pointee_type); 2358 assert(clang_type_info.first % 8 == 0); 2359 child_byte_size = clang_type_info.first / 8; 2360 child_byte_offset = 0; 2361 return pointee_type.getAsOpaquePtr(); 2362 } 2363 } 2364 } 2365 break; 2366 2367 case clang::Type::Typedef: 2368 return GetChildClangTypeAtIndex (ast_context, 2369 parent_name, 2370 cast<TypedefType>(parent_qual_type)->LookThroughTypedefs().getAsOpaquePtr(), 2371 idx, 2372 transparent_pointers, 2373 omit_empty_base_classes, 2374 child_name, 2375 child_byte_size, 2376 child_byte_offset, 2377 child_bitfield_bit_size, 2378 child_bitfield_bit_offset, 2379 child_is_base_class); 2380 break; 2381 2382 default: 2383 break; 2384 } 2385 } 2386 return NULL; 2387} 2388 2389static inline bool 2390BaseSpecifierIsEmpty (const CXXBaseSpecifier *b) 2391{ 2392 return ClangASTContext::RecordHasFields(cast<CXXRecordDecl>(b->getType()->getAs<RecordType>()->getDecl())) == false; 2393} 2394 2395static uint32_t 2396GetNumBaseClasses (const CXXRecordDecl *cxx_record_decl, bool omit_empty_base_classes) 2397{ 2398 uint32_t num_bases = 0; 2399 if (cxx_record_decl) 2400 { 2401 if (omit_empty_base_classes) 2402 { 2403 CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 2404 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 2405 base_class != base_class_end; 2406 ++base_class) 2407 { 2408 // Skip empty base classes 2409 if (omit_empty_base_classes) 2410 { 2411 if (BaseSpecifierIsEmpty (base_class)) 2412 continue; 2413 } 2414 ++num_bases; 2415 } 2416 } 2417 else 2418 num_bases = cxx_record_decl->getNumBases(); 2419 } 2420 return num_bases; 2421} 2422 2423 2424static uint32_t 2425GetIndexForRecordBase 2426( 2427 const RecordDecl *record_decl, 2428 const CXXBaseSpecifier *base_spec, 2429 bool omit_empty_base_classes 2430) 2431{ 2432 uint32_t child_idx = 0; 2433 2434 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 2435 2436// const char *super_name = record_decl->getNameAsCString(); 2437// const char *base_name = base_spec->getType()->getAs<RecordType>()->getDecl()->getNameAsCString(); 2438// printf ("GetIndexForRecordChild (%s, %s)\n", super_name, base_name); 2439// 2440 if (cxx_record_decl) 2441 { 2442 CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 2443 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 2444 base_class != base_class_end; 2445 ++base_class) 2446 { 2447 if (omit_empty_base_classes) 2448 { 2449 if (BaseSpecifierIsEmpty (base_class)) 2450 continue; 2451 } 2452 2453// printf ("GetIndexForRecordChild (%s, %s) base[%u] = %s\n", super_name, base_name, 2454// child_idx, 2455// base_class->getType()->getAs<RecordType>()->getDecl()->getNameAsCString()); 2456// 2457// 2458 if (base_class == base_spec) 2459 return child_idx; 2460 ++child_idx; 2461 } 2462 } 2463 2464 return UINT32_MAX; 2465} 2466 2467 2468static uint32_t 2469GetIndexForRecordChild 2470( 2471 const RecordDecl *record_decl, 2472 NamedDecl *canonical_decl, 2473 bool omit_empty_base_classes 2474) 2475{ 2476 uint32_t child_idx = GetNumBaseClasses (dyn_cast<CXXRecordDecl>(record_decl), omit_empty_base_classes); 2477 2478// const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 2479// 2480//// printf ("GetIndexForRecordChild (%s, %s)\n", record_decl->getNameAsCString(), canonical_decl->getNameAsCString()); 2481// if (cxx_record_decl) 2482// { 2483// CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 2484// for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 2485// base_class != base_class_end; 2486// ++base_class) 2487// { 2488// if (omit_empty_base_classes) 2489// { 2490// if (BaseSpecifierIsEmpty (base_class)) 2491// continue; 2492// } 2493// 2494//// printf ("GetIndexForRecordChild (%s, %s) base[%u] = %s\n", 2495//// record_decl->getNameAsCString(), 2496//// canonical_decl->getNameAsCString(), 2497//// child_idx, 2498//// base_class->getType()->getAs<RecordType>()->getDecl()->getNameAsCString()); 2499// 2500// 2501// CXXRecordDecl *curr_base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl()); 2502// if (curr_base_class_decl == canonical_decl) 2503// { 2504// return child_idx; 2505// } 2506// ++child_idx; 2507// } 2508// } 2509// 2510// const uint32_t num_bases = child_idx; 2511 RecordDecl::field_iterator field, field_end; 2512 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); 2513 field != field_end; 2514 ++field, ++child_idx) 2515 { 2516// printf ("GetIndexForRecordChild (%s, %s) field[%u] = %s\n", 2517// record_decl->getNameAsCString(), 2518// canonical_decl->getNameAsCString(), 2519// child_idx - num_bases, 2520// field->getNameAsCString()); 2521 2522 if (field->getCanonicalDecl() == canonical_decl) 2523 return child_idx; 2524 } 2525 2526 return UINT32_MAX; 2527} 2528 2529// Look for a child member (doesn't include base classes, but it does include 2530// their members) in the type hierarchy. Returns an index path into "clang_type" 2531// on how to reach the appropriate member. 2532// 2533// class A 2534// { 2535// public: 2536// int m_a; 2537// int m_b; 2538// }; 2539// 2540// class B 2541// { 2542// }; 2543// 2544// class C : 2545// public B, 2546// public A 2547// { 2548// }; 2549// 2550// If we have a clang type that describes "class C", and we wanted to looked 2551// "m_b" in it: 2552// 2553// With omit_empty_base_classes == false we would get an integer array back with: 2554// { 1, 1 } 2555// The first index 1 is the child index for "class A" within class C 2556// The second index 1 is the child index for "m_b" within class A 2557// 2558// With omit_empty_base_classes == true we would get an integer array back with: 2559// { 0, 1 } 2560// 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) 2561// The second index 1 is the child index for "m_b" within class A 2562 2563size_t 2564ClangASTContext::GetIndexOfChildMemberWithName 2565( 2566 ASTContext *ast_context, 2567 clang_type_t clang_type, 2568 const char *name, 2569 bool omit_empty_base_classes, 2570 std::vector<uint32_t>& child_indexes 2571) 2572{ 2573 if (clang_type && name && name[0]) 2574 { 2575 QualType qual_type(QualType::getFromOpaquePtr(clang_type)); 2576 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 2577 switch (type_class) 2578 { 2579 case clang::Type::Record: 2580 { 2581 const RecordType *record_type = cast<RecordType>(qual_type.getTypePtr()); 2582 const RecordDecl *record_decl = record_type->getDecl(); 2583 2584 assert(record_decl); 2585 uint32_t child_idx = 0; 2586 2587 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 2588 2589 // Try and find a field that matches NAME 2590 RecordDecl::field_iterator field, field_end; 2591 StringRef name_sref(name); 2592 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); 2593 field != field_end; 2594 ++field, ++child_idx) 2595 { 2596 if (field->getName().equals (name_sref)) 2597 { 2598 // We have to add on the number of base classes to this index! 2599 child_indexes.push_back (child_idx + GetNumBaseClasses (cxx_record_decl, omit_empty_base_classes)); 2600 return child_indexes.size(); 2601 } 2602 } 2603 2604 if (cxx_record_decl) 2605 { 2606 const RecordDecl *parent_record_decl = cxx_record_decl; 2607 2608 //printf ("parent = %s\n", parent_record_decl->getNameAsCString()); 2609 2610 //const Decl *root_cdecl = cxx_record_decl->getCanonicalDecl(); 2611 // Didn't find things easily, lets let clang do its thang... 2612 IdentifierInfo & ident_ref = ast_context->Idents.get(name, name + strlen (name)); 2613 DeclarationName decl_name(&ident_ref); 2614 2615 CXXBasePaths paths; 2616 if (cxx_record_decl->lookupInBases(CXXRecordDecl::FindOrdinaryMember, 2617 decl_name.getAsOpaquePtr(), 2618 paths)) 2619 { 2620 CXXBasePaths::const_paths_iterator path, path_end = paths.end(); 2621 for (path = paths.begin(); path != path_end; ++path) 2622 { 2623 const size_t num_path_elements = path->size(); 2624 for (size_t e=0; e<num_path_elements; ++e) 2625 { 2626 CXXBasePathElement elem = (*path)[e]; 2627 2628 child_idx = GetIndexForRecordBase (parent_record_decl, elem.Base, omit_empty_base_classes); 2629 if (child_idx == UINT32_MAX) 2630 { 2631 child_indexes.clear(); 2632 return 0; 2633 } 2634 else 2635 { 2636 child_indexes.push_back (child_idx); 2637 parent_record_decl = cast<RecordDecl>(elem.Base->getType()->getAs<RecordType>()->getDecl()); 2638 } 2639 } 2640 DeclContext::lookup_iterator named_decl_pos; 2641 for (named_decl_pos = path->Decls.first; 2642 named_decl_pos != path->Decls.second && parent_record_decl; 2643 ++named_decl_pos) 2644 { 2645 //printf ("path[%zu] = %s\n", child_indexes.size(), (*named_decl_pos)->getNameAsCString()); 2646 2647 child_idx = GetIndexForRecordChild (parent_record_decl, *named_decl_pos, omit_empty_base_classes); 2648 if (child_idx == UINT32_MAX) 2649 { 2650 child_indexes.clear(); 2651 return 0; 2652 } 2653 else 2654 { 2655 child_indexes.push_back (child_idx); 2656 } 2657 } 2658 } 2659 return child_indexes.size(); 2660 } 2661 } 2662 2663 } 2664 break; 2665 2666 case clang::Type::ObjCObject: 2667 case clang::Type::ObjCInterface: 2668 { 2669 StringRef name_sref(name); 2670 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr()); 2671 assert (objc_class_type); 2672 if (objc_class_type) 2673 { 2674 uint32_t child_idx = 0; 2675 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 2676 2677 if (class_interface_decl) 2678 { 2679 ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end(); 2680 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass(); 2681 2682 for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos, ++child_idx) 2683 { 2684 const ObjCIvarDecl* ivar_decl = *ivar_pos; 2685 2686 if (ivar_decl->getName().equals (name_sref)) 2687 { 2688 if ((!omit_empty_base_classes && superclass_interface_decl) || 2689 ( omit_empty_base_classes && ObjCDeclHasIVars (superclass_interface_decl, true))) 2690 ++child_idx; 2691 2692 child_indexes.push_back (child_idx); 2693 return child_indexes.size(); 2694 } 2695 } 2696 2697 if (superclass_interface_decl) 2698 { 2699 // The super class index is always zero for ObjC classes, 2700 // so we push it onto the child indexes in case we find 2701 // an ivar in our superclass... 2702 child_indexes.push_back (0); 2703 2704 if (GetIndexOfChildMemberWithName (ast_context, 2705 ast_context->getObjCInterfaceType(superclass_interface_decl).getAsOpaquePtr(), 2706 name, 2707 omit_empty_base_classes, 2708 child_indexes)) 2709 { 2710 // We did find an ivar in a superclass so just 2711 // return the results! 2712 return child_indexes.size(); 2713 } 2714 2715 // We didn't find an ivar matching "name" in our 2716 // superclass, pop the superclass zero index that 2717 // we pushed on above. 2718 child_indexes.pop_back(); 2719 } 2720 } 2721 } 2722 } 2723 break; 2724 2725 case clang::Type::ObjCObjectPointer: 2726 { 2727 return GetIndexOfChildMemberWithName (ast_context, 2728 cast<ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr(), 2729 name, 2730 omit_empty_base_classes, 2731 child_indexes); 2732 } 2733 break; 2734 2735 2736 case clang::Type::ConstantArray: 2737 { 2738// const ConstantArrayType *array = cast<ConstantArrayType>(parent_qual_type.getTypePtr()); 2739// const uint64_t element_count = array->getSize().getLimitedValue(); 2740// 2741// if (idx < element_count) 2742// { 2743// std::pair<uint64_t, unsigned> field_type_info = ast_context->getTypeInfo(array->getElementType()); 2744// 2745// char element_name[32]; 2746// ::snprintf (element_name, sizeof (element_name), "%s[%u]", parent_name ? parent_name : "", idx); 2747// 2748// child_name.assign(element_name); 2749// assert(field_type_info.first % 8 == 0); 2750// child_byte_size = field_type_info.first / 8; 2751// child_byte_offset = idx * child_byte_size; 2752// return array->getElementType().getAsOpaquePtr(); 2753// } 2754 } 2755 break; 2756 2757// case clang::Type::MemberPointerType: 2758// { 2759// MemberPointerType *mem_ptr_type = cast<MemberPointerType>(qual_type.getTypePtr()); 2760// QualType pointee_type = mem_ptr_type->getPointeeType(); 2761// 2762// if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2763// { 2764// return GetIndexOfChildWithName (ast_context, 2765// mem_ptr_type->getPointeeType().getAsOpaquePtr(), 2766// name); 2767// } 2768// } 2769// break; 2770// 2771 case clang::Type::LValueReference: 2772 case clang::Type::RValueReference: 2773 { 2774 ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr()); 2775 QualType pointee_type = reference_type->getPointeeType(); 2776 2777 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2778 { 2779 return GetIndexOfChildMemberWithName (ast_context, 2780 reference_type->getPointeeType().getAsOpaquePtr(), 2781 name, 2782 omit_empty_base_classes, 2783 child_indexes); 2784 } 2785 } 2786 break; 2787 2788 case clang::Type::Pointer: 2789 { 2790 PointerType *pointer_type = cast<PointerType>(qual_type.getTypePtr()); 2791 QualType pointee_type = pointer_type->getPointeeType(); 2792 2793 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2794 { 2795 return GetIndexOfChildMemberWithName (ast_context, 2796 pointer_type->getPointeeType().getAsOpaquePtr(), 2797 name, 2798 omit_empty_base_classes, 2799 child_indexes); 2800 } 2801 else 2802 { 2803// if (parent_name) 2804// { 2805// child_name.assign(1, '*'); 2806// child_name += parent_name; 2807// } 2808// 2809// // We have a pointer to an simple type 2810// if (idx == 0) 2811// { 2812// std::pair<uint64_t, unsigned> clang_type_info = ast_context->getTypeInfo(pointee_type); 2813// assert(clang_type_info.first % 8 == 0); 2814// child_byte_size = clang_type_info.first / 8; 2815// child_byte_offset = 0; 2816// return pointee_type.getAsOpaquePtr(); 2817// } 2818 } 2819 } 2820 break; 2821 2822 case clang::Type::Typedef: 2823 return GetIndexOfChildMemberWithName (ast_context, 2824 cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr(), 2825 name, 2826 omit_empty_base_classes, 2827 child_indexes); 2828 2829 default: 2830 break; 2831 } 2832 } 2833 return 0; 2834} 2835 2836 2837// Get the index of the child of "clang_type" whose name matches. This function 2838// doesn't descend into the children, but only looks one level deep and name 2839// matches can include base class names. 2840 2841uint32_t 2842ClangASTContext::GetIndexOfChildWithName 2843( 2844 ASTContext *ast_context, 2845 clang_type_t clang_type, 2846 const char *name, 2847 bool omit_empty_base_classes 2848) 2849{ 2850 if (clang_type && name && name[0]) 2851 { 2852 QualType qual_type(QualType::getFromOpaquePtr(clang_type)); 2853 2854 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 2855 2856 switch (type_class) 2857 { 2858 case clang::Type::Record: 2859 { 2860 const RecordType *record_type = cast<RecordType>(qual_type.getTypePtr()); 2861 const RecordDecl *record_decl = record_type->getDecl(); 2862 2863 assert(record_decl); 2864 uint32_t child_idx = 0; 2865 2866 const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl); 2867 2868 if (cxx_record_decl) 2869 { 2870 CXXRecordDecl::base_class_const_iterator base_class, base_class_end; 2871 for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end(); 2872 base_class != base_class_end; 2873 ++base_class) 2874 { 2875 // Skip empty base classes 2876 CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl()); 2877 if (omit_empty_base_classes && RecordHasFields(base_class_decl) == false) 2878 continue; 2879 2880 if (base_class->getType().getAsString().compare (name) == 0) 2881 return child_idx; 2882 ++child_idx; 2883 } 2884 } 2885 2886 // Try and find a field that matches NAME 2887 RecordDecl::field_iterator field, field_end; 2888 StringRef name_sref(name); 2889 for (field = record_decl->field_begin(), field_end = record_decl->field_end(); 2890 field != field_end; 2891 ++field, ++child_idx) 2892 { 2893 if (field->getName().equals (name_sref)) 2894 return child_idx; 2895 } 2896 2897 } 2898 break; 2899 2900 case clang::Type::ObjCObject: 2901 case clang::Type::ObjCInterface: 2902 { 2903 StringRef name_sref(name); 2904 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type.getTypePtr()); 2905 assert (objc_class_type); 2906 if (objc_class_type) 2907 { 2908 uint32_t child_idx = 0; 2909 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 2910 2911 if (class_interface_decl) 2912 { 2913 ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end(); 2914 ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass(); 2915 2916 for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos) 2917 { 2918 const ObjCIvarDecl* ivar_decl = *ivar_pos; 2919 2920 if (ivar_decl->getName().equals (name_sref)) 2921 { 2922 if ((!omit_empty_base_classes && superclass_interface_decl) || 2923 ( omit_empty_base_classes && ObjCDeclHasIVars (superclass_interface_decl, true))) 2924 ++child_idx; 2925 2926 return child_idx; 2927 } 2928 } 2929 2930 if (superclass_interface_decl) 2931 { 2932 if (superclass_interface_decl->getName().equals (name_sref)) 2933 return 0; 2934 } 2935 } 2936 } 2937 } 2938 break; 2939 2940 case clang::Type::ObjCObjectPointer: 2941 { 2942 return GetIndexOfChildWithName (ast_context, 2943 cast<ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr(), 2944 name, 2945 omit_empty_base_classes); 2946 } 2947 break; 2948 2949 case clang::Type::ConstantArray: 2950 { 2951// const ConstantArrayType *array = cast<ConstantArrayType>(parent_qual_type.getTypePtr()); 2952// const uint64_t element_count = array->getSize().getLimitedValue(); 2953// 2954// if (idx < element_count) 2955// { 2956// std::pair<uint64_t, unsigned> field_type_info = ast_context->getTypeInfo(array->getElementType()); 2957// 2958// char element_name[32]; 2959// ::snprintf (element_name, sizeof (element_name), "%s[%u]", parent_name ? parent_name : "", idx); 2960// 2961// child_name.assign(element_name); 2962// assert(field_type_info.first % 8 == 0); 2963// child_byte_size = field_type_info.first / 8; 2964// child_byte_offset = idx * child_byte_size; 2965// return array->getElementType().getAsOpaquePtr(); 2966// } 2967 } 2968 break; 2969 2970// case clang::Type::MemberPointerType: 2971// { 2972// MemberPointerType *mem_ptr_type = cast<MemberPointerType>(qual_type.getTypePtr()); 2973// QualType pointee_type = mem_ptr_type->getPointeeType(); 2974// 2975// if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2976// { 2977// return GetIndexOfChildWithName (ast_context, 2978// mem_ptr_type->getPointeeType().getAsOpaquePtr(), 2979// name); 2980// } 2981// } 2982// break; 2983// 2984 case clang::Type::LValueReference: 2985 case clang::Type::RValueReference: 2986 { 2987 ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr()); 2988 QualType pointee_type = reference_type->getPointeeType(); 2989 2990 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 2991 { 2992 return GetIndexOfChildWithName (ast_context, 2993 reference_type->getPointeeType().getAsOpaquePtr(), 2994 name, 2995 omit_empty_base_classes); 2996 } 2997 } 2998 break; 2999 3000 case clang::Type::Pointer: 3001 { 3002 PointerType *pointer_type = cast<PointerType>(qual_type.getTypePtr()); 3003 QualType pointee_type = pointer_type->getPointeeType(); 3004 3005 if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr())) 3006 { 3007 return GetIndexOfChildWithName (ast_context, 3008 pointer_type->getPointeeType().getAsOpaquePtr(), 3009 name, 3010 omit_empty_base_classes); 3011 } 3012 else 3013 { 3014// if (parent_name) 3015// { 3016// child_name.assign(1, '*'); 3017// child_name += parent_name; 3018// } 3019// 3020// // We have a pointer to an simple type 3021// if (idx == 0) 3022// { 3023// std::pair<uint64_t, unsigned> clang_type_info = ast_context->getTypeInfo(pointee_type); 3024// assert(clang_type_info.first % 8 == 0); 3025// child_byte_size = clang_type_info.first / 8; 3026// child_byte_offset = 0; 3027// return pointee_type.getAsOpaquePtr(); 3028// } 3029 } 3030 } 3031 break; 3032 3033 case clang::Type::Typedef: 3034 return GetIndexOfChildWithName (ast_context, 3035 cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr(), 3036 name, 3037 omit_empty_base_classes); 3038 3039 default: 3040 break; 3041 } 3042 } 3043 return UINT32_MAX; 3044} 3045 3046#pragma mark TagType 3047 3048bool 3049ClangASTContext::SetTagTypeKind (clang_type_t tag_clang_type, int kind) 3050{ 3051 if (tag_clang_type) 3052 { 3053 QualType tag_qual_type(QualType::getFromOpaquePtr(tag_clang_type)); 3054 clang::Type *clang_type = tag_qual_type.getTypePtr(); 3055 if (clang_type) 3056 { 3057 TagType *tag_type = dyn_cast<TagType>(clang_type); 3058 if (tag_type) 3059 { 3060 TagDecl *tag_decl = dyn_cast<TagDecl>(tag_type->getDecl()); 3061 if (tag_decl) 3062 { 3063 tag_decl->setTagKind ((TagDecl::TagKind)kind); 3064 return true; 3065 } 3066 } 3067 } 3068 } 3069 return false; 3070} 3071 3072 3073#pragma mark DeclContext Functions 3074 3075DeclContext * 3076ClangASTContext::GetDeclContextForType (clang_type_t clang_type) 3077{ 3078 if (clang_type == NULL) 3079 return NULL; 3080 3081 QualType qual_type(QualType::getFromOpaquePtr(clang_type)); 3082 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 3083 switch (type_class) 3084 { 3085 case clang::Type::FunctionNoProto: break; 3086 case clang::Type::FunctionProto: break; 3087 case clang::Type::IncompleteArray: break; 3088 case clang::Type::VariableArray: break; 3089 case clang::Type::ConstantArray: break; 3090 case clang::Type::ExtVector: break; 3091 case clang::Type::Vector: break; 3092 case clang::Type::Builtin: break; 3093 case clang::Type::BlockPointer: break; 3094 case clang::Type::Pointer: break; 3095 case clang::Type::LValueReference: break; 3096 case clang::Type::RValueReference: break; 3097 case clang::Type::MemberPointer: break; 3098 case clang::Type::Complex: break; 3099 case clang::Type::ObjCObject: break; 3100 case clang::Type::ObjCInterface: return cast<ObjCObjectType>(qual_type.getTypePtr())->getInterface(); 3101 case clang::Type::ObjCObjectPointer: return ClangASTContext::GetDeclContextForType (cast<ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType().getAsOpaquePtr()); 3102 case clang::Type::Record: return cast<RecordType>(qual_type)->getDecl(); 3103 case clang::Type::Enum: return cast<EnumType>(qual_type)->getDecl(); 3104 case clang::Type::Typedef: return ClangASTContext::GetDeclContextForType (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr()); 3105 3106 case clang::Type::TypeOfExpr: break; 3107 case clang::Type::TypeOf: break; 3108 case clang::Type::Decltype: break; 3109 //case clang::Type::QualifiedName: break; 3110 case clang::Type::TemplateSpecialization: break; 3111 } 3112 // No DeclContext in this type... 3113 return NULL; 3114} 3115 3116#pragma mark Namespace Declarations 3117 3118NamespaceDecl * 3119ClangASTContext::GetUniqueNamespaceDeclaration (const char *name, const Declaration &decl, DeclContext *decl_ctx) 3120{ 3121 // TODO: Do something intelligent with the Declaration object passed in 3122 // like maybe filling in the SourceLocation with it... 3123 if (name) 3124 { 3125 ASTContext *ast_context = getASTContext(); 3126 if (decl_ctx == NULL) 3127 decl_ctx = ast_context->getTranslationUnitDecl(); 3128 return NamespaceDecl::Create(*ast_context, decl_ctx, SourceLocation(), &ast_context->Idents.get(name)); 3129 } 3130 return NULL; 3131} 3132 3133 3134#pragma mark Function Types 3135 3136FunctionDecl * 3137ClangASTContext::CreateFunctionDeclaration (const char *name, clang_type_t function_clang_type, int storage, bool is_inline) 3138{ 3139 if (name) 3140 { 3141 ASTContext *ast_context = getASTContext(); 3142 assert (ast_context != NULL); 3143 3144 if (name && name[0]) 3145 { 3146 return FunctionDecl::Create(*ast_context, 3147 ast_context->getTranslationUnitDecl(), 3148 SourceLocation(), 3149 DeclarationName (&ast_context->Idents.get(name)), 3150 QualType::getFromOpaquePtr(function_clang_type), 3151 NULL, 3152 (FunctionDecl::StorageClass)storage, 3153 (FunctionDecl::StorageClass)storage, 3154 is_inline); 3155 } 3156 else 3157 { 3158 return FunctionDecl::Create(*ast_context, 3159 ast_context->getTranslationUnitDecl(), 3160 SourceLocation(), 3161 DeclarationName (), 3162 QualType::getFromOpaquePtr(function_clang_type), 3163 NULL, 3164 (FunctionDecl::StorageClass)storage, 3165 (FunctionDecl::StorageClass)storage, 3166 is_inline); 3167 } 3168 } 3169 return NULL; 3170} 3171 3172clang_type_t 3173ClangASTContext::CreateFunctionType (ASTContext *ast_context, 3174 clang_type_t result_type, 3175 clang_type_t *args, 3176 unsigned num_args, 3177 bool is_variadic, 3178 unsigned type_quals) 3179{ 3180 assert (ast_context != NULL); 3181 std::vector<QualType> qual_type_args; 3182 for (unsigned i=0; i<num_args; ++i) 3183 qual_type_args.push_back (QualType::getFromOpaquePtr(args[i])); 3184 3185 // TODO: Detect calling convention in DWARF? 3186 return ast_context->getFunctionType(QualType::getFromOpaquePtr(result_type), 3187 qual_type_args.empty() ? NULL : &qual_type_args.front(), 3188 qual_type_args.size(), 3189 is_variadic, 3190 type_quals, 3191 false, // hasExceptionSpec 3192 false, // hasAnyExceptionSpec, 3193 0, // NumExs 3194 0, // const QualType *ExArray 3195 FunctionType::ExtInfo ()).getAsOpaquePtr(); // NoReturn); 3196} 3197 3198ParmVarDecl * 3199ClangASTContext::CreateParameterDeclaration (const char *name, clang_type_t param_type, int storage) 3200{ 3201 ASTContext *ast_context = getASTContext(); 3202 assert (ast_context != NULL); 3203 return ParmVarDecl::Create(*ast_context, 3204 ast_context->getTranslationUnitDecl(), 3205 SourceLocation(), 3206 name && name[0] ? &ast_context->Idents.get(name) : NULL, 3207 QualType::getFromOpaquePtr(param_type), 3208 NULL, 3209 (VarDecl::StorageClass)storage, 3210 (VarDecl::StorageClass)storage, 3211 0); 3212} 3213 3214void 3215ClangASTContext::SetFunctionParameters (FunctionDecl *function_decl, ParmVarDecl **params, unsigned num_params) 3216{ 3217 if (function_decl) 3218 function_decl->setParams (params, num_params); 3219} 3220 3221 3222#pragma mark Array Types 3223 3224clang_type_t 3225ClangASTContext::CreateArrayType (clang_type_t element_type, size_t element_count, uint32_t bit_stride) 3226{ 3227 if (element_type) 3228 { 3229 ASTContext *ast_context = getASTContext(); 3230 assert (ast_context != NULL); 3231 llvm::APInt ap_element_count (64, element_count); 3232 return ast_context->getConstantArrayType(QualType::getFromOpaquePtr(element_type), 3233 ap_element_count, 3234 ArrayType::Normal, 3235 0).getAsOpaquePtr(); // ElemQuals 3236 } 3237 return NULL; 3238} 3239 3240 3241#pragma mark TagDecl 3242 3243bool 3244ClangASTContext::StartTagDeclarationDefinition (clang_type_t clang_type) 3245{ 3246 if (clang_type) 3247 { 3248 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3249 clang::Type *t = qual_type.getTypePtr(); 3250 if (t) 3251 { 3252 TagType *tag_type = dyn_cast<TagType>(t); 3253 if (tag_type) 3254 { 3255 TagDecl *tag_decl = tag_type->getDecl(); 3256 if (tag_decl) 3257 { 3258 tag_decl->startDefinition(); 3259 return true; 3260 } 3261 } 3262 } 3263 } 3264 return false; 3265} 3266 3267bool 3268ClangASTContext::CompleteTagDeclarationDefinition (clang_type_t clang_type) 3269{ 3270 if (clang_type) 3271 { 3272 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3273 3274 CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl(); 3275 3276 if (cxx_record_decl) 3277 { 3278 cxx_record_decl->completeDefinition(); 3279 3280 return true; 3281 } 3282 3283 ObjCObjectType *objc_class_type = dyn_cast<ObjCObjectType>(qual_type); 3284 3285 if (objc_class_type) 3286 { 3287 ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); 3288 3289 class_interface_decl->setForwardDecl(false); 3290 } 3291 3292 const EnumType *enum_type = dyn_cast<EnumType>(qual_type.getTypePtr()); 3293 3294 if (enum_type) 3295 { 3296 EnumDecl *enum_decl = enum_type->getDecl(); 3297 3298 if (enum_decl) 3299 { 3300 /// TODO This really needs to be fixed. 3301 3302 unsigned NumPositiveBits = 1; 3303 unsigned NumNegativeBits = 0; 3304 3305 ASTContext *ast_context = getASTContext(); 3306 3307 QualType promotion_qual_type; 3308 // If the enum integer type is less than an integer in bit width, 3309 // then we must promote it to an integer size. 3310 if (ast_context->getTypeSize(enum_decl->getIntegerType()) < ast_context->getTypeSize(ast_context->IntTy)) 3311 { 3312 if (enum_decl->getIntegerType()->isSignedIntegerType()) 3313 promotion_qual_type = ast_context->IntTy; 3314 else 3315 promotion_qual_type = ast_context->UnsignedIntTy; 3316 } 3317 else 3318 promotion_qual_type = enum_decl->getIntegerType(); 3319 3320 enum_decl->completeDefinition(enum_decl->getIntegerType(), promotion_qual_type, NumPositiveBits, NumNegativeBits); 3321 return true; 3322 } 3323 } 3324 } 3325 return false; 3326} 3327 3328 3329#pragma mark Enumeration Types 3330 3331clang_type_t 3332ClangASTContext::CreateEnumerationType (const Declaration &decl, const char *name, clang_type_t integer_qual_type) 3333{ 3334 // TODO: Do something intelligent with the Declaration object passed in 3335 // like maybe filling in the SourceLocation with it... 3336 ASTContext *ast_context = getASTContext(); 3337 assert (ast_context != NULL); 3338 3339 // TODO: ask about these... 3340// const bool IsScoped = false; 3341// const bool IsFixed = false; 3342 3343 EnumDecl *enum_decl = EnumDecl::Create (*ast_context, 3344 ast_context->getTranslationUnitDecl(), 3345 SourceLocation(), 3346 name && name[0] ? &ast_context->Idents.get(name) : NULL, 3347 SourceLocation(), 3348 NULL); //IsScoped, IsFixed); 3349 if (enum_decl) 3350 { 3351 // TODO: check if we should be setting the promotion type too? 3352 enum_decl->setIntegerType(QualType::getFromOpaquePtr (integer_qual_type)); 3353 return ast_context->getTagDeclType(enum_decl).getAsOpaquePtr(); 3354 } 3355 return NULL; 3356} 3357 3358clang_type_t 3359ClangASTContext::GetEnumerationIntegerType (clang_type_t enum_clang_type) 3360{ 3361 QualType enum_qual_type (QualType::getFromOpaquePtr(enum_clang_type)); 3362 3363 clang::Type *clang_type = enum_qual_type.getTypePtr(); 3364 if (clang_type) 3365 { 3366 const EnumType *enum_type = dyn_cast<EnumType>(clang_type); 3367 if (enum_type) 3368 { 3369 EnumDecl *enum_decl = enum_type->getDecl(); 3370 if (enum_decl) 3371 return enum_decl->getIntegerType().getAsOpaquePtr(); 3372 } 3373 } 3374 return NULL; 3375} 3376bool 3377ClangASTContext::AddEnumerationValueToEnumerationType 3378( 3379 clang_type_t enum_clang_type, 3380 clang_type_t enumerator_clang_type, 3381 const Declaration &decl, 3382 const char *name, 3383 int64_t enum_value, 3384 uint32_t enum_value_bit_size 3385) 3386{ 3387 if (enum_clang_type && enumerator_clang_type && name) 3388 { 3389 // TODO: Do something intelligent with the Declaration object passed in 3390 // like maybe filling in the SourceLocation with it... 3391 ASTContext *ast_context = getASTContext(); 3392 IdentifierTable *identifier_table = getIdentifierTable(); 3393 3394 assert (ast_context != NULL); 3395 assert (identifier_table != NULL); 3396 QualType enum_qual_type (QualType::getFromOpaquePtr(enum_clang_type)); 3397 3398 clang::Type *clang_type = enum_qual_type.getTypePtr(); 3399 if (clang_type) 3400 { 3401 const EnumType *enum_type = dyn_cast<EnumType>(clang_type); 3402 3403 if (enum_type) 3404 { 3405 llvm::APSInt enum_llvm_apsint(enum_value_bit_size, false); 3406 enum_llvm_apsint = enum_value; 3407 EnumConstantDecl *enumerator_decl = 3408 EnumConstantDecl::Create(*ast_context, 3409 enum_type->getDecl(), 3410 SourceLocation(), 3411 name ? &identifier_table->get(name) : NULL, // Identifier 3412 QualType::getFromOpaquePtr(enumerator_clang_type), 3413 NULL, 3414 enum_llvm_apsint); 3415 3416 if (enumerator_decl) 3417 { 3418 enum_type->getDecl()->addDecl(enumerator_decl); 3419 return true; 3420 } 3421 } 3422 } 3423 } 3424 return false; 3425} 3426 3427#pragma mark Pointers & References 3428 3429clang_type_t 3430ClangASTContext::CreatePointerType (clang_type_t clang_type) 3431{ 3432 if (clang_type) 3433 { 3434 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3435 3436 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 3437 switch (type_class) 3438 { 3439 case clang::Type::ObjCObject: 3440 case clang::Type::ObjCInterface: 3441 return getASTContext()->getObjCObjectPointerType(qual_type).getAsOpaquePtr(); 3442 3443 default: 3444 return getASTContext()->getPointerType(qual_type).getAsOpaquePtr(); 3445 } 3446 } 3447 return NULL; 3448} 3449 3450clang_type_t 3451ClangASTContext::CreateLValueReferenceType (clang_type_t clang_type) 3452{ 3453 if (clang_type) 3454 return getASTContext()->getLValueReferenceType (QualType::getFromOpaquePtr(clang_type)).getAsOpaquePtr(); 3455 return NULL; 3456} 3457 3458clang_type_t 3459ClangASTContext::CreateRValueReferenceType (clang_type_t clang_type) 3460{ 3461 if (clang_type) 3462 return getASTContext()->getRValueReferenceType (QualType::getFromOpaquePtr(clang_type)).getAsOpaquePtr(); 3463 return NULL; 3464} 3465 3466clang_type_t 3467ClangASTContext::CreateMemberPointerType (clang_type_t clang_pointee_type, clang_type_t clang_class_type) 3468{ 3469 if (clang_pointee_type && clang_pointee_type) 3470 return getASTContext()->getMemberPointerType(QualType::getFromOpaquePtr(clang_pointee_type), 3471 QualType::getFromOpaquePtr(clang_class_type).getTypePtr()).getAsOpaquePtr(); 3472 return NULL; 3473} 3474 3475size_t 3476ClangASTContext::GetPointerBitSize () 3477{ 3478 ASTContext *ast_context = getASTContext(); 3479 return ast_context->getTypeSize(ast_context->VoidPtrTy); 3480} 3481 3482bool 3483ClangASTContext::IsPointerOrReferenceType (clang_type_t clang_type, clang_type_t*target_type) 3484{ 3485 if (clang_type == NULL) 3486 return false; 3487 3488 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3489 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 3490 switch (type_class) 3491 { 3492 case clang::Type::Builtin: 3493 switch (cast<clang::BuiltinType>(qual_type)->getKind()) 3494 { 3495 default: 3496 break; 3497 case clang::BuiltinType::ObjCId: 3498 case clang::BuiltinType::ObjCClass: 3499 return true; 3500 } 3501 return false; 3502 case clang::Type::ObjCObjectPointer: 3503 if (target_type) 3504 *target_type = cast<ObjCObjectPointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3505 return true; 3506 case clang::Type::BlockPointer: 3507 if (target_type) 3508 *target_type = cast<BlockPointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3509 return true; 3510 case clang::Type::Pointer: 3511 if (target_type) 3512 *target_type = cast<PointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3513 return true; 3514 case clang::Type::MemberPointer: 3515 if (target_type) 3516 *target_type = cast<MemberPointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3517 return true; 3518 case clang::Type::LValueReference: 3519 if (target_type) 3520 *target_type = cast<LValueReferenceType>(qual_type)->desugar().getAsOpaquePtr(); 3521 return true; 3522 case clang::Type::RValueReference: 3523 if (target_type) 3524 *target_type = cast<LValueReferenceType>(qual_type)->desugar().getAsOpaquePtr(); 3525 return true; 3526 case clang::Type::Typedef: 3527 return ClangASTContext::IsPointerOrReferenceType (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr()); 3528 default: 3529 break; 3530 } 3531 return false; 3532} 3533 3534bool 3535ClangASTContext::IsIntegerType (clang_type_t clang_type, bool &is_signed) 3536{ 3537 if (!clang_type) 3538 return false; 3539 3540 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3541 const BuiltinType *builtin_type = dyn_cast<BuiltinType>(qual_type->getCanonicalTypeInternal()); 3542 3543 if (builtin_type) 3544 { 3545 if (builtin_type->isInteger()) 3546 is_signed = builtin_type->isSignedInteger(); 3547 3548 return true; 3549 } 3550 3551 return false; 3552} 3553 3554bool 3555ClangASTContext::IsPointerType (clang_type_t clang_type, clang_type_t*target_type) 3556{ 3557 if (clang_type) 3558 { 3559 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3560 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 3561 switch (type_class) 3562 { 3563 case clang::Type::Builtin: 3564 switch (cast<clang::BuiltinType>(qual_type)->getKind()) 3565 { 3566 default: 3567 break; 3568 case clang::BuiltinType::ObjCId: 3569 case clang::BuiltinType::ObjCClass: 3570 return true; 3571 } 3572 return false; 3573 case clang::Type::ObjCObjectPointer: 3574 if (target_type) 3575 *target_type = cast<ObjCObjectPointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3576 return true; 3577 case clang::Type::BlockPointer: 3578 if (target_type) 3579 *target_type = cast<BlockPointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3580 return true; 3581 case clang::Type::Pointer: 3582 if (target_type) 3583 *target_type = cast<PointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3584 return true; 3585 case clang::Type::MemberPointer: 3586 if (target_type) 3587 *target_type = cast<MemberPointerType>(qual_type)->getPointeeType().getAsOpaquePtr(); 3588 return true; 3589 case clang::Type::Typedef: 3590 return ClangASTContext::IsPointerOrReferenceType (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr(), target_type); 3591 default: 3592 break; 3593 } 3594 } 3595 return false; 3596} 3597 3598bool 3599ClangASTContext::IsFloatingPointType (clang_type_t clang_type, uint32_t &count, bool &is_complex) 3600{ 3601 if (clang_type) 3602 { 3603 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3604 3605 if (const BuiltinType *BT = dyn_cast<BuiltinType>(qual_type->getCanonicalTypeInternal())) 3606 { 3607 clang::BuiltinType::Kind kind = BT->getKind(); 3608 if (kind >= BuiltinType::Float && kind <= BuiltinType::LongDouble) 3609 { 3610 count = 1; 3611 is_complex = false; 3612 return true; 3613 } 3614 } 3615 else if (const ComplexType *CT = dyn_cast<ComplexType>(qual_type->getCanonicalTypeInternal())) 3616 { 3617 if (IsFloatingPointType(CT->getElementType().getAsOpaquePtr(), count, is_complex)) 3618 { 3619 count = 2; 3620 is_complex = true; 3621 return true; 3622 } 3623 } 3624 else if (const VectorType *VT = dyn_cast<VectorType>(qual_type->getCanonicalTypeInternal())) 3625 { 3626 if (IsFloatingPointType(VT->getElementType().getAsOpaquePtr(), count, is_complex)) 3627 { 3628 count = VT->getNumElements(); 3629 is_complex = false; 3630 return true; 3631 } 3632 } 3633 } 3634 return false; 3635} 3636 3637 3638bool 3639ClangASTContext::GetCXXClassName (clang_type_t clang_type, std::string &class_name) 3640{ 3641 if (clang_type) 3642 { 3643 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3644 3645 CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl(); 3646 if (cxx_record_decl) 3647 { 3648 class_name.assign (cxx_record_decl->getIdentifier()->getNameStart()); 3649 return true; 3650 } 3651 } 3652 class_name.clear(); 3653 return false; 3654} 3655 3656 3657bool 3658ClangASTContext::IsCXXClassType (clang_type_t clang_type) 3659{ 3660 if (clang_type) 3661 { 3662 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3663 if (qual_type->getAsCXXRecordDecl() != NULL) 3664 return true; 3665 } 3666 return false; 3667} 3668 3669bool 3670ClangASTContext::IsObjCClassType (clang_type_t clang_type) 3671{ 3672 if (clang_type) 3673 { 3674 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3675 if (qual_type->isObjCObjectOrInterfaceType()) 3676 return true; 3677 } 3678 return false; 3679} 3680 3681 3682bool 3683ClangASTContext::IsCharType (clang_type_t clang_type) 3684{ 3685 if (clang_type) 3686 return QualType::getFromOpaquePtr(clang_type)->isCharType(); 3687 return false; 3688} 3689 3690bool 3691ClangASTContext::IsCStringType (clang_type_t clang_type, uint32_t &length) 3692{ 3693 clang_type_t pointee_or_element_clang_type = NULL; 3694 Flags type_flags (ClangASTContext::GetTypeInfo (clang_type, NULL, &pointee_or_element_clang_type)); 3695 3696 if (pointee_or_element_clang_type == NULL) 3697 return false; 3698 3699 if (type_flags.AnySet (eTypeIsArray | eTypeIsPointer)) 3700 { 3701 QualType pointee_or_element_qual_type (QualType::getFromOpaquePtr (pointee_or_element_clang_type)); 3702 3703 if (pointee_or_element_qual_type.getUnqualifiedType()->isCharType()) 3704 { 3705 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3706 if (type_flags.Test (eTypeIsArray)) 3707 { 3708 // We know the size of the array and it could be a C string 3709 // since it is an array of characters 3710 length = cast<ConstantArrayType>(qual_type.getTypePtr())->getSize().getLimitedValue(); 3711 return true; 3712 } 3713 else 3714 { 3715 length = 0; 3716 return true; 3717 } 3718 3719 } 3720 } 3721 return false; 3722} 3723 3724bool 3725ClangASTContext::IsFunctionPointerType (clang_type_t clang_type) 3726{ 3727 if (clang_type) 3728 { 3729 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3730 3731 if (qual_type->isFunctionPointerType()) 3732 return true; 3733 3734 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 3735 switch (type_class) 3736 { 3737 case clang::Type::Typedef: 3738 return ClangASTContext::IsFunctionPointerType (cast<TypedefType>(qual_type)->LookThroughTypedefs().getAsOpaquePtr()); 3739 3740 case clang::Type::LValueReference: 3741 case clang::Type::RValueReference: 3742 { 3743 ReferenceType *reference_type = cast<ReferenceType>(qual_type.getTypePtr()); 3744 if (reference_type) 3745 return ClangASTContext::IsFunctionPointerType (reference_type->getPointeeType().getAsOpaquePtr()); 3746 } 3747 break; 3748 } 3749 } 3750 return false; 3751} 3752 3753size_t 3754ClangASTContext::GetArraySize (clang_type_t clang_type) 3755{ 3756 if (clang_type) 3757 { 3758 ConstantArrayType *array = cast<ConstantArrayType>(QualType::getFromOpaquePtr(clang_type).getTypePtr()); 3759 if (array) 3760 return array->getSize().getLimitedValue(); 3761 } 3762 return 0; 3763} 3764 3765bool 3766ClangASTContext::IsArrayType (clang_type_t clang_type, clang_type_t*member_type, uint64_t *size) 3767{ 3768 if (!clang_type) 3769 return false; 3770 3771 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3772 3773 const clang::Type::TypeClass type_class = qual_type->getTypeClass(); 3774 switch (type_class) 3775 { 3776 case clang::Type::ConstantArray: 3777 if (member_type) 3778 *member_type = cast<ConstantArrayType>(qual_type)->getElementType().getAsOpaquePtr(); 3779 if (size) 3780 *size = cast<ConstantArrayType>(qual_type)->getSize().getLimitedValue(ULONG_LONG_MAX); 3781 return true; 3782 case clang::Type::IncompleteArray: 3783 if (member_type) 3784 *member_type = cast<IncompleteArrayType>(qual_type)->getElementType().getAsOpaquePtr(); 3785 if (size) 3786 *size = 0; 3787 return true; 3788 case clang::Type::VariableArray: 3789 if (member_type) 3790 *member_type = cast<VariableArrayType>(qual_type)->getElementType().getAsOpaquePtr(); 3791 if (size) 3792 *size = 0; 3793 case clang::Type::DependentSizedArray: 3794 if (member_type) 3795 *member_type = cast<DependentSizedArrayType>(qual_type)->getElementType().getAsOpaquePtr(); 3796 if (size) 3797 *size = 0; 3798 return true; 3799 } 3800 return false; 3801} 3802 3803 3804#pragma mark Typedefs 3805 3806clang_type_t 3807ClangASTContext::CreateTypedefType (const char *name, clang_type_t clang_type, DeclContext *decl_ctx) 3808{ 3809 if (clang_type) 3810 { 3811 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3812 ASTContext *ast_context = getASTContext(); 3813 IdentifierTable *identifier_table = getIdentifierTable(); 3814 assert (ast_context != NULL); 3815 assert (identifier_table != NULL); 3816 if (decl_ctx == NULL) 3817 decl_ctx = ast_context->getTranslationUnitDecl(); 3818 TypedefDecl *decl = TypedefDecl::Create(*ast_context, 3819 decl_ctx, 3820 SourceLocation(), 3821 name ? &identifier_table->get(name) : NULL, // Identifier 3822 ast_context->CreateTypeSourceInfo(qual_type)); 3823 3824 // Get a uniqued QualType for the typedef decl type 3825 return ast_context->getTypedefType (decl).getAsOpaquePtr(); 3826 } 3827 return NULL; 3828} 3829 3830 3831std::string 3832ClangASTContext::GetTypeName (clang_type_t opaque_qual_type) 3833{ 3834 std::string return_name; 3835 3836 QualType qual_type(QualType::getFromOpaquePtr(opaque_qual_type)); 3837 3838 const TypedefType *typedef_type = qual_type->getAs<TypedefType>(); 3839 if (typedef_type) 3840 { 3841 const TypedefDecl *typedef_decl = typedef_type->getDecl(); 3842 return_name = typedef_decl->getQualifiedNameAsString(); 3843 } 3844 else 3845 { 3846 return_name = qual_type.getAsString(); 3847 } 3848 3849 return return_name; 3850} 3851 3852// Disable this for now since I can't seem to get a nicely formatted float 3853// out of the APFloat class without just getting the float, double or quad 3854// and then using a formatted print on it which defeats the purpose. We ideally 3855// would like to get perfect string values for any kind of float semantics 3856// so we can support remote targets. The code below also requires a patch to 3857// llvm::APInt. 3858//bool 3859//ClangASTContext::ConvertFloatValueToString (ASTContext *ast_context, clang_type_t clang_type, const uint8_t* bytes, size_t byte_size, int apint_byte_order, std::string &float_str) 3860//{ 3861// uint32_t count = 0; 3862// bool is_complex = false; 3863// if (ClangASTContext::IsFloatingPointType (clang_type, count, is_complex)) 3864// { 3865// unsigned num_bytes_per_float = byte_size / count; 3866// unsigned num_bits_per_float = num_bytes_per_float * 8; 3867// 3868// float_str.clear(); 3869// uint32_t i; 3870// for (i=0; i<count; i++) 3871// { 3872// APInt ap_int(num_bits_per_float, bytes + i * num_bytes_per_float, (APInt::ByteOrder)apint_byte_order); 3873// bool is_ieee = false; 3874// APFloat ap_float(ap_int, is_ieee); 3875// char s[1024]; 3876// unsigned int hex_digits = 0; 3877// bool upper_case = false; 3878// 3879// if (ap_float.convertToHexString(s, hex_digits, upper_case, APFloat::rmNearestTiesToEven) > 0) 3880// { 3881// if (i > 0) 3882// float_str.append(", "); 3883// float_str.append(s); 3884// if (i == 1 && is_complex) 3885// float_str.append(1, 'i'); 3886// } 3887// } 3888// return !float_str.empty(); 3889// } 3890// return false; 3891//} 3892 3893size_t 3894ClangASTContext::ConvertStringToFloatValue (ASTContext *ast_context, clang_type_t clang_type, const char *s, uint8_t *dst, size_t dst_size) 3895{ 3896 if (clang_type) 3897 { 3898 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3899 uint32_t count = 0; 3900 bool is_complex = false; 3901 if (ClangASTContext::IsFloatingPointType (clang_type, count, is_complex)) 3902 { 3903 // TODO: handle complex and vector types 3904 if (count != 1) 3905 return false; 3906 3907 StringRef s_sref(s); 3908 APFloat ap_float(ast_context->getFloatTypeSemantics(qual_type), s_sref); 3909 3910 const uint64_t bit_size = ast_context->getTypeSize (qual_type); 3911 const uint64_t byte_size = bit_size / 8; 3912 if (dst_size >= byte_size) 3913 { 3914 if (bit_size == sizeof(float)*8) 3915 { 3916 float float32 = ap_float.convertToFloat(); 3917 ::memcpy (dst, &float32, byte_size); 3918 return byte_size; 3919 } 3920 else if (bit_size >= 64) 3921 { 3922 llvm::APInt ap_int(ap_float.bitcastToAPInt()); 3923 ::memcpy (dst, ap_int.getRawData(), byte_size); 3924 return byte_size; 3925 } 3926 } 3927 } 3928 } 3929 return 0; 3930} 3931 3932unsigned 3933ClangASTContext::GetTypeQualifiers(clang_type_t clang_type) 3934{ 3935 assert (clang_type); 3936 3937 QualType qual_type (QualType::getFromOpaquePtr(clang_type)); 3938 3939 return qual_type.getQualifiers().getCVRQualifiers(); 3940} 3941