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