31 #include "TClingUtils.h"
34 #include "cling/Interpreter/Interpreter.h"
35 #include "cling/Interpreter/LookupHelper.h"
36 #include "cling/Utils/AST.h"
38 #include "clang/AST/ASTContext.h"
39 #include "clang/AST/Decl.h"
40 #include "clang/AST/DeclCXX.h"
41 #include "clang/AST/DeclTemplate.h"
42 #include "clang/AST/GlobalDecl.h"
43 #include "clang/AST/PrettyPrinter.h"
44 #include "clang/AST/RecordLayout.h"
45 #include "clang/AST/Type.h"
46 #include "clang/Basic/Specifiers.h"
47 #include "clang/Frontend/CompilerInstance.h"
48 #include "clang/Sema/Sema.h"
50 #include "llvm/ExecutionEngine/GenericValue.h"
51 #include "llvm/Support/Casting.h"
52 #include "llvm/Support/raw_ostream.h"
57 using namespace clang;
60 static std::string FullyQualifiedName(
const Decl *decl) {
63 if (
const NamedDecl* ND = llvm::dyn_cast<NamedDecl>(decl)) {
64 PrintingPolicy Policy(decl->getASTContext().getPrintingPolicy());
65 llvm::raw_string_ostream stream(buf);
66 ND->getNameForDiagnostic(stream, Policy,
true);
71 TClingClassInfo::TClingClassInfo(cling::Interpreter *interp, Bool_t all)
72 : TClingDeclInfo(nullptr), fInterp(interp), fFirstTime(true), fDescend(false), fIterAll(all),
73 fIsIter(true), fType(0), fOffsetCache(0)
75 TranslationUnitDecl *TU =
76 interp->getCI()->getASTContext().getTranslationUnitDecl();
82 TClingClassInfo::TClingClassInfo(cling::Interpreter *interp,
const char *name)
83 : TClingDeclInfo(nullptr), fInterp(interp), fFirstTime(true), fDescend(false), fIterAll(kTRUE), fIsIter(false),
84 fType(0), fTitle(
""), fOffsetCache(0)
86 const cling::LookupHelper& lh = fInterp->getLookupHelper();
88 const Decl *decl = lh.findScope(name,
89 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
90 : cling::LookupHelper::NoDiagnostics,
93 std::string buf = TClassEdit::InsertStd(name);
95 decl = lh.findScope(buf,
96 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
97 : cling::LookupHelper::NoDiagnostics,
102 const TagType *tagtype =type->getAs<TagType>();
104 decl = tagtype->getDecl();
109 if (decl && decl->isInvalidDecl()) {
110 Error(
"TClingClassInfo",
"Found an invalid decl for %s.",name);
116 TClingClassInfo::TClingClassInfo(cling::Interpreter *interp,
118 : TClingDeclInfo(nullptr), fInterp(interp), fFirstTime(true), fDescend(false), fIterAll(kTRUE),
119 fIsIter(false), fType(0), fTitle(
""), fOffsetCache(0)
124 TClingClassInfo::TClingClassInfo(cling::Interpreter *interp,
126 : TClingDeclInfo(nullptr), fInterp(interp), fFirstTime(true), fDescend(false), fIterAll(kTRUE),
127 fIsIter(false), fType(0), fTitle(
""), fOffsetCache(0)
132 void TClingClassInfo::AddBaseOffsetValue(
const clang::Decl* decl, ptrdiff_t offset)
137 OffsetPtrFunc_t executableFunc = 0;
138 fOffsetCache[decl] = std::make_pair(offset, executableFunc);
141 long TClingClassInfo::ClassProperty()
const
147 const RecordDecl *RD = llvm::dyn_cast<RecordDecl>(GetDecl());
158 const CXXRecordDecl *CRD =
159 llvm::dyn_cast<CXXRecordDecl>(GetDecl());
160 property |= kClassIsValid;
161 if (CRD->isAbstract()) {
162 property |= kClassIsAbstract;
164 if (CRD->hasUserDeclaredConstructor()) {
165 property |= kClassHasExplicitCtor;
168 !CRD->hasUserDeclaredConstructor() &&
169 !CRD->hasTrivialDefaultConstructor()
171 property |= kClassHasImplicitCtor;
174 CRD->hasUserProvidedDefaultConstructor() ||
175 !CRD->hasTrivialDefaultConstructor()
177 property |= kClassHasDefaultCtor;
179 if (CRD->hasUserDeclaredDestructor()) {
180 property |= kClassHasExplicitDtor;
182 else if (!CRD->hasTrivialDestructor()) {
183 property |= kClassHasImplicitDtor;
185 if (CRD->hasUserDeclaredCopyAssignment()) {
186 property |= kClassHasAssignOpr;
188 if (CRD->isPolymorphic()) {
189 property |= kClassHasVirtual;
194 void TClingClassInfo::Delete(
void *arena,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
199 Error(
"TClingClassInfo::Delete()",
"Called while invalid!");
203 Error(
"TClingClassInfo::Delete()",
"Class is not loaded: %s",
204 FullyQualifiedName(GetDecl()).c_str());
207 TClingCallFunc cf(fInterp,normCtxt);
208 cf.ExecDestructor(
this, arena, 0,
true);
211 void TClingClassInfo::DeleteArray(
void *arena,
bool dtorOnly,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
224 Error(
"DeleteArray",
"Placement delete of an array is unsupported!\n");
227 TClingCallFunc cf(fInterp,normCtxt);
228 cf.ExecDestructor(
this, arena, 1,
true);
231 void TClingClassInfo::Destruct(
void *arena,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
238 TClingCallFunc cf(fInterp,normCtxt);
239 cf.ExecDestructor(
this, arena, 0,
false);
242 const FunctionTemplateDecl *TClingClassInfo::GetFunctionTemplate(
const char *fname)
const
251 const TypedefType *TT = llvm::dyn_cast<TypedefType>(fType);
253 llvm::StringRef tname(TT->getDecl()->getName());
254 if (tname.equals(fname)) {
255 const NamedDecl *ndecl = llvm::dyn_cast<NamedDecl>(GetDecl());
256 if (ndecl && !ndecl->getName().equals(fname)) {
258 return GetFunctionTemplate(ndecl->getName().str().c_str());
263 const cling::LookupHelper &lh = fInterp->getLookupHelper();
264 const FunctionTemplateDecl *fd
265 = lh.findFunctionTemplate(GetDecl(), fname,
266 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
267 : cling::LookupHelper::NoDiagnostics,
false);
268 if (fd)
return fd->getCanonicalDecl();
272 const clang::ValueDecl *TClingClassInfo::GetDataMember(
const char *name)
const
277 const cling::LookupHelper &lh = fInterp->getLookupHelper();
279 = lh.findDataMember(GetDecl(), name,
280 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
281 : cling::LookupHelper::NoDiagnostics);
282 if (vd)
return llvm::dyn_cast<ValueDecl>(vd->getCanonicalDecl());
286 TClingMethodInfo TClingClassInfo::GetMethod(
const char *fname)
const
291 TClingMethodInfo tmi(fInterp);
295 R__LOCKGUARD(gInterpreterMutex);
298 const TypedefType *TT = llvm::dyn_cast<TypedefType>(fType);
300 llvm::StringRef tname(TT->getDecl()->getName());
301 if (tname.equals(fname)) {
302 const NamedDecl *ndecl = llvm::dyn_cast<NamedDecl>(GetDecl());
303 if (ndecl && !ndecl->getName().equals(fname)) {
305 return GetMethod(ndecl->getName().str().c_str());
310 const cling::LookupHelper &lh = fInterp->getLookupHelper();
311 const FunctionDecl *fd
312 = lh.findAnyFunction(GetDecl(), fname,
313 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
314 : cling::LookupHelper::NoDiagnostics,
318 TClingMethodInfo tmi(fInterp);
321 TClingMethodInfo tmi(fInterp);
326 TClingMethodInfo TClingClassInfo::GetMethod(
const char *fname,
327 const char *proto,
long *poffset, EFunctionMatchMode mode ,
328 EInheritanceMode imode )
const
330 return GetMethod(fname,proto,
false,poffset,mode,imode);
333 TClingMethodInfo TClingClassInfo::GetMethod(
const char *fname,
334 const char *proto,
bool objectIsConst,
335 long *poffset, EFunctionMatchMode mode ,
336 EInheritanceMode imode )
const
342 TClingMethodInfo tmi(fInterp);
346 R__LOCKGUARD(gInterpreterMutex);
349 const TypedefType *TT = llvm::dyn_cast<TypedefType>(fType);
351 llvm::StringRef tname(TT->getDecl()->getName());
352 if (tname.equals(fname)) {
353 const NamedDecl *ndecl = llvm::dyn_cast<NamedDecl>(GetDecl());
354 if (ndecl && !ndecl->getName().equals(fname)) {
356 return GetMethod(ndecl->getName().str().c_str(),proto,
357 objectIsConst,poffset,
364 const cling::LookupHelper& lh = fInterp->getLookupHelper();
365 const FunctionDecl *fd;
366 if (mode == kConversionMatch) {
367 fd = lh.findFunctionProto(GetDecl(), fname, proto,
368 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
369 : cling::LookupHelper::NoDiagnostics,
371 }
else if (mode == kExactMatch) {
372 fd = lh.matchFunctionProto(GetDecl(), fname, proto,
373 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
374 : cling::LookupHelper::NoDiagnostics,
377 Error(
"TClingClassInfo::GetMethod",
378 "The MatchMode %d is not supported.", mode);
379 TClingMethodInfo tmi(fInterp);
384 TClingMethodInfo tmi(fInterp);
387 if (imode == TClingClassInfo::kInThisScope) {
396 const clang::DeclContext* ourDC = llvm::dyn_cast<clang::DeclContext>(GetDecl());
397 if (!fd->getDeclContext()->Equals(ourDC)
398 && !(fd->getDeclContext()->isTransparentContext()
399 && fd->getDeclContext()->getParent()->Equals(ourDC)))
400 return TClingMethodInfo(fInterp);
403 if (poffset) *poffset = 0;
407 if (
const CXXMethodDecl *md =
408 llvm::dyn_cast<CXXMethodDecl>(fd)) {
410 *poffset = GetOffset(md);
414 TClingMethodInfo tmi(fInterp);
419 TClingMethodInfo TClingClassInfo::GetMethod(
const char *fname,
420 const llvm::SmallVectorImpl<clang::QualType> &proto,
421 long *poffset, EFunctionMatchMode mode ,
422 EInheritanceMode imode )
const
424 return GetMethod(fname,proto,
false,poffset,mode,imode);
427 TClingMethodInfo TClingClassInfo::GetMethod(
const char *fname,
428 const llvm::SmallVectorImpl<clang::QualType> &proto,
bool objectIsConst,
429 long *poffset, EFunctionMatchMode mode ,
430 EInheritanceMode imode )
const
436 TClingMethodInfo tmi(fInterp);
440 R__LOCKGUARD(gInterpreterMutex);
443 const TypedefType *TT = llvm::dyn_cast<TypedefType>(fType);
445 llvm::StringRef tname(TT->getDecl()->getName());
446 if (tname.equals(fname)) {
447 const NamedDecl *ndecl = llvm::dyn_cast<NamedDecl>(GetDecl());
448 if (ndecl && !ndecl->getName().equals(fname)) {
450 return GetMethod(ndecl->getName().str().c_str(),proto,objectIsConst,poffset,
457 const cling::LookupHelper& lh = fInterp->getLookupHelper();
458 const FunctionDecl *fd;
459 if (mode == kConversionMatch) {
460 fd = lh.findFunctionProto(GetDecl(), fname, proto,
461 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
462 : cling::LookupHelper::NoDiagnostics,
464 }
else if (mode == kExactMatch) {
465 fd = lh.matchFunctionProto(GetDecl(), fname, proto,
466 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
467 : cling::LookupHelper::NoDiagnostics,
470 Error(
"TClingClassInfo::GetMethod",
471 "The MatchMode %d is not supported.", mode);
472 TClingMethodInfo tmi(fInterp);
477 TClingMethodInfo tmi(fInterp);
482 if (
const CXXMethodDecl *md =
483 llvm::dyn_cast<CXXMethodDecl>(fd)) {
485 *poffset = GetOffset(md);
488 TClingMethodInfo tmi(fInterp);
493 TClingMethodInfo TClingClassInfo::GetMethodWithArgs(
const char *fname,
494 const char *arglist,
long *poffset, EFunctionMatchMode mode ,
495 EInheritanceMode imode )
const
497 return GetMethodWithArgs(fname,arglist,
false,poffset,mode,imode);
500 TClingMethodInfo TClingClassInfo::GetMethodWithArgs(
const char *fname,
501 const char *arglist,
bool objectIsConst,
502 long *poffset, EFunctionMatchMode ,
503 EInheritanceMode )
const
506 R__LOCKGUARD(gInterpreterMutex);
509 const TypedefType *TT = llvm::dyn_cast<TypedefType>(fType);
511 llvm::StringRef tname(TT->getDecl()->getName());
512 if (tname.equals(fname)) {
513 const NamedDecl *ndecl = llvm::dyn_cast<NamedDecl>(GetDecl());
514 if (ndecl && !ndecl->getName().equals(fname)) {
516 return GetMethod(ndecl->getName().str().c_str(),arglist,
517 objectIsConst,poffset
528 TClingMethodInfo tmi(fInterp);
531 if (!strcmp(arglist,
")")) {
535 const cling::LookupHelper &lh = fInterp->getLookupHelper();
536 const FunctionDecl *fd
537 = lh.findFunctionArgs(GetDecl(), fname, arglist,
538 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
539 : cling::LookupHelper::NoDiagnostics,
543 TClingMethodInfo tmi(fInterp);
548 if (
const CXXMethodDecl *md =
549 llvm::dyn_cast<CXXMethodDecl>(fd)) {
551 *poffset = GetOffset(md);
554 TClingMethodInfo tmi(fInterp);
559 int TClingClassInfo::GetMethodNArg(
const char *method,
const char *proto,
560 Bool_t objectIsConst,
561 EFunctionMatchMode mode )
const
568 R__LOCKGUARD(gInterpreterMutex);
570 TClingMethodInfo mi = GetMethod(method, proto, objectIsConst, 0, mode);
573 unsigned num_params = mi.GetMethodDecl()->getNumParams();
574 clang_val =
static_cast<int>(num_params);
579 long TClingClassInfo::GetOffset(
const CXXMethodDecl* md)
const
582 R__LOCKGUARD(gInterpreterMutex);
585 const CXXRecordDecl* definer = md->getParent();
586 const CXXRecordDecl* accessor =
587 llvm::cast<CXXRecordDecl>(GetDecl());
588 if (definer != accessor) {
592 TClingBaseClassInfo bi(fInterp, const_cast<TClingClassInfo*>(
this));
594 TClingClassInfo* bci = bi.GetBase();
595 if (bci->GetDecl() == definer) {
598 offset = bi.Offset();
606 ptrdiff_t TClingClassInfo::GetBaseOffset(TClingClassInfo* base,
void* address,
bool isDerivedObject)
610 R__READ_LOCKGUARD(ROOT::gCoreMutex);
613 auto iter = fOffsetCache.find(base->GetDecl());
614 if (iter != fOffsetCache.end()) {
615 std::pair<ptrdiff_t, OffsetPtrFunc_t> offsetCache = (*iter).second;
616 if (OffsetPtrFunc_t executableFunc = offsetCache.second) {
618 return (*executableFunc)(address, isDerivedObject);
621 Error(
"TClingBaseClassInfo::Offset",
"The address of the object for virtual base offset calculation is not valid.");
626 return offsetCache.first;
632 R__WRITE_LOCKGUARD(ROOT::gCoreMutex);
633 TClingBaseClassInfo binfo(fInterp,
this, base);
634 return binfo.Offset(address, isDerivedObject);
637 std::vector<std::string> TClingClassInfo::GetUsingNamespaces()
640 std::vector<std::string> res;
642 R__LOCKGUARD(gInterpreterMutex);
644 cling::Interpreter::PushTransactionRAII RAII(fInterp);
645 const auto DC = dyn_cast<DeclContext>(fDecl);
649 clang::PrintingPolicy policy(fDecl->getASTContext().getPrintingPolicy());
650 for (
auto UD : DC->using_directives()) {
651 NamespaceDecl *NS = UD->getNominatedNamespace();
654 llvm::raw_string_ostream stream(nsName);
656 NS->getNameForDiagnostic(stream, policy,
true);
659 res.push_back(nsName);
666 bool TClingClassInfo::HasDefaultConstructor()
const
679 const CXXRecordDecl* CRD = llvm::dyn_cast<CXXRecordDecl>(GetDecl());
684 using namespace TMetaUtils;
685 const RConstructorType ioctortype(
"",*fInterp);
686 return EIOCtorCategory::kAbsent != CheckConstructor(CRD,ioctortype,*fInterp);
689 bool TClingClassInfo::HasMethod(
const char *name)
const
691 R__LOCKGUARD(gInterpreterMutex);
692 if (IsLoaded() && !llvm::isa<EnumDecl>(GetDecl())) {
693 return fInterp->getLookupHelper()
694 .hasFunction(GetDecl(), name,
695 gDebug > 5 ? cling::LookupHelper::WithDiagnostics
696 : cling::LookupHelper::NoDiagnostics);
701 void TClingClassInfo::Init(
const char *name)
706 fIter = DeclContext::decl_iterator();
710 const cling::LookupHelper& lh = fInterp->getLookupHelper();
711 SetDecl(lh.findScope(name, gDebug > 5 ? cling::LookupHelper::WithDiagnostics
712 : cling::LookupHelper::NoDiagnostics,
715 std::string buf = TClassEdit::InsertStd(name);
717 SetDecl(lh.findScope(buf, gDebug > 5 ? cling::LookupHelper::WithDiagnostics
718 : cling::LookupHelper::NoDiagnostics,
722 if (!GetDecl() && fType) {
723 const TagType *tagtype =fType->getAs<TagType>();
725 SetDecl(tagtype->getDecl());
730 void TClingClassInfo::Init(
const Decl* decl)
735 fIter = DeclContext::decl_iterator();
741 void TClingClassInfo::Init(
int tagnum)
743 Fatal(
"TClingClassInfo::Init(tagnum)",
"Should no longer be called");
747 void TClingClassInfo::Init(
const Type &tag)
751 R__LOCKGUARD(gInterpreterMutex);
753 const TagType *tagtype = fType->getAs<TagType>();
755 SetDecl(tagtype->getDecl());
761 QualType qType(fType,0);
762 static PrintingPolicy printPol(fInterp->getCI()->getLangOpts());
763 printPol.SuppressScope =
false;
764 Error(
"TClingClassInfo::Init(const Type&)",
765 "The given type %s does not point to a Decl",
766 qType.getAsString(printPol).c_str());
770 bool TClingClassInfo::IsBase(
const char *name)
const
775 TClingClassInfo base(fInterp, name);
776 if (!base.IsValid()) {
780 R__LOCKGUARD(gInterpreterMutex);
782 const CXXRecordDecl *CRD =
783 llvm::dyn_cast<CXXRecordDecl>(GetDecl());
789 const CXXRecordDecl *baseCRD =
790 llvm::dyn_cast<CXXRecordDecl>(base.GetDecl());
791 return CRD->isDerivedFrom(baseCRD);
794 bool TClingClassInfo::IsEnum(cling::Interpreter *interp,
const char *name)
797 TClingClassInfo info(interp, name);
798 if (info.IsValid() && (info.Property() & kIsEnum)) {
804 bool TClingClassInfo::IsScopedEnum()
const
806 if (
auto *ED = llvm::dyn_cast<clang::EnumDecl>(GetDecl()))
807 return ED->isScoped();
811 EDataType TClingClassInfo::GetUnderlyingType()
const
814 return kNumDataTypes;
816 return kNumDataTypes;
818 if (
auto ED = llvm::dyn_cast<EnumDecl>(GetDecl())) {
819 R__LOCKGUARD(gInterpreterMutex);
820 auto Ty = ED->getIntegerType().getTypePtrOrNull();
821 if (
auto BTy = llvm::dyn_cast<BuiltinType>(Ty)) {
822 switch (BTy->getKind()) {
823 case BuiltinType::Bool:
826 case BuiltinType::Char_U:
827 case BuiltinType::UChar:
830 case BuiltinType::Char_S:
831 case BuiltinType::SChar:
834 case BuiltinType::UShort:
836 case BuiltinType::Short:
838 case BuiltinType::UInt:
840 case BuiltinType::Int:
842 case BuiltinType::ULong:
844 case BuiltinType::Long:
846 case BuiltinType::ULongLong:
848 case BuiltinType::LongLong:
851 return kNumDataTypes;
855 return kNumDataTypes;
859 bool TClingClassInfo::IsLoaded()
const
868 if (GetDecl() == 0) {
872 R__LOCKGUARD(gInterpreterMutex);
874 const CXXRecordDecl *CRD = llvm::dyn_cast<CXXRecordDecl>(GetDecl());
876 if (!CRD->hasDefinition()) {
880 const TagDecl *TD = llvm::dyn_cast<TagDecl>(GetDecl());
881 if (TD && TD->getDefinition() == 0) {
889 bool TClingClassInfo::IsValidMethod(
const char *method,
const char *proto,
890 Bool_t objectIsConst,
892 EFunctionMatchMode mode )
const
901 TClingMethodInfo mi = GetMethod(method, proto, offset, mode);
905 int TClingClassInfo::InternalNext()
907 R__LOCKGUARD(gInterpreterMutex);
909 fDeclFileName.clear();
912 cling::Interpreter::PushTransactionRAII RAII(fInterp);
915 const clang::DeclContext *DC = cast<DeclContext>(GetDecl());
917 fIter = DC->decls_begin();
919 fIter = DC->noload_decls_begin();
926 if (
const NamedDecl* ND =
927 llvm::dyn_cast<NamedDecl>(GetDecl())) {
928 PrintingPolicy Policy(GetDecl()->getASTContext().
929 getPrintingPolicy());
930 llvm::raw_string_ostream stream(buf);
931 ND->getNameForDiagnostic(stream, Policy,
false);
933 Error(
"TClingClassInfo::InternalNext",
934 "Next called but iteration not prepared for %s!", buf.c_str());
936 Error(
"TClingClassInfo::InternalNext",
937 "Next called but iteration not prepared!");
964 fIterStack.push_back(fIter);
965 DeclContext *DC = llvm::cast<DeclContext>(*fIter);
967 fIter = DC->decls_begin();
969 fIter = DC->noload_decls_begin();
972 while (!*fIter && fIterStack.size()) {
976 fIter = fIterStack.back();
977 fIterStack.pop_back();
989 Decl::Kind DK = fIter->getKind();
990 if ((DK == Decl::Namespace) || (DK == Decl::Enum) ||
991 (DK == Decl::CXXRecord) ||
992 (DK == Decl::ClassTemplateSpecialization)) {
993 const TagDecl *TD = llvm::dyn_cast<TagDecl>(*fIter);
994 if (TD && !TD->isCompleteDefinition()) {
998 if (DK == Decl::Namespace) {
1000 if (!fIter->isCanonicalDecl()) {
1006 if (DK != Decl::Enum) {
1008 DeclContext *DC = llvm::cast<DeclContext>(*fIter);
1009 if ((fIterAll && *DC->decls_begin())
1010 || (!fIterAll && *DC->noload_decls_begin())) {
1020 if (GetDecl()->isInvalidDecl()) {
1021 Warning(
"TClingClassInfo::Next()",
"Reached an invalid decl.");
1023 if (
const RecordDecl *RD =
1024 llvm::dyn_cast<RecordDecl>(GetDecl())) {
1025 fType = RD->getASTContext().getRecordType(RD).getTypePtr();
1033 int TClingClassInfo::Next()
1035 return InternalNext();
1038 void *TClingClassInfo::New(
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
1043 Error(
"TClingClassInfo::New()",
"Called while invalid!");
1047 Error(
"TClingClassInfo::New()",
"Class is not loaded: %s",
1048 FullyQualifiedName(GetDecl()).c_str());
1052 R__LOCKGUARD(gInterpreterMutex);
1053 const CXXRecordDecl* RD = dyn_cast<CXXRecordDecl>(GetDecl());
1055 Error(
"TClingClassInfo::New()",
"This is a namespace!: %s",
1056 FullyQualifiedName(GetDecl()).c_str());
1059 if (!HasDefaultConstructor()) {
1067 TClingCallFunc cf(fInterp,normCtxt);
1068 obj = cf.ExecDefaultConstructor(
this, 0, 0);
1070 Error(
"TClingClassInfo::New()",
"Call of default constructor "
1071 "failed to return an object for class: %s",
1072 FullyQualifiedName(GetDecl()).c_str());
1078 void *TClingClassInfo::New(
int n,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
1084 Error(
"TClingClassInfo::New(n)",
"Called while invalid!");
1088 Error(
"TClingClassInfo::New(n)",
"Class is not loaded: %s",
1089 FullyQualifiedName(GetDecl()).c_str());
1094 R__LOCKGUARD(gInterpreterMutex);
1096 const CXXRecordDecl* RD = dyn_cast<CXXRecordDecl>(GetDecl());
1098 Error(
"TClingClassInfo::New(n)",
"This is a namespace!: %s",
1099 FullyQualifiedName(GetDecl()).c_str());
1102 if (!HasDefaultConstructor()) {
1111 TClingCallFunc cf(fInterp,normCtxt);
1112 obj = cf.ExecDefaultConstructor(
this, 0,
1115 Error(
"TClingClassInfo::New(n)",
"Call of default constructor "
1116 "failed to return an array of class: %s",
1117 FullyQualifiedName(GetDecl()).c_str());
1123 void *TClingClassInfo::New(
int n,
void *arena,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
1130 Error(
"TClingClassInfo::New(n, arena)",
"Called while invalid!");
1134 Error(
"TClingClassInfo::New(n, arena)",
"Class is not loaded: %s",
1135 FullyQualifiedName(GetDecl()).c_str());
1139 R__LOCKGUARD(gInterpreterMutex);
1141 const CXXRecordDecl* RD = dyn_cast<CXXRecordDecl>(GetDecl());
1143 Error(
"TClingClassInfo::New(n, arena)",
"This is a namespace!: %s",
1144 FullyQualifiedName(GetDecl()).c_str());
1147 if (!HasDefaultConstructor()) {
1156 TClingCallFunc cf(fInterp,normCtxt);
1158 obj = cf.ExecDefaultConstructor(
this, arena,
1163 void *TClingClassInfo::New(
void *arena,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
1169 Error(
"TClingClassInfo::New(arena)",
"Called while invalid!");
1173 Error(
"TClingClassInfo::New(arena)",
"Class is not loaded: %s",
1174 FullyQualifiedName(GetDecl()).c_str());
1178 R__LOCKGUARD(gInterpreterMutex);
1180 const CXXRecordDecl* RD = dyn_cast<CXXRecordDecl>(GetDecl());
1182 Error(
"TClingClassInfo::New(arena)",
"This is a namespace!: %s",
1183 FullyQualifiedName(GetDecl()).c_str());
1186 if (!HasDefaultConstructor()) {
1195 TClingCallFunc cf(fInterp,normCtxt);
1197 obj = cf.ExecDefaultConstructor(
this, arena, 0);
1201 long TClingClassInfo::Property()
const
1207 R__LOCKGUARD(gInterpreterMutex);
1210 property |= kIsCPPCompiled;
1213 cling::Interpreter::PushTransactionRAII RAII(fInterp);
1215 const clang::DeclContext *ctxt = GetDecl()->getDeclContext();
1216 clang::NamespaceDecl *std_ns =fInterp->getSema().getStdNamespace();
1217 while (! ctxt->isTranslationUnit()) {
1218 if (ctxt->Equals(std_ns)) {
1219 property |= kIsDefinedInStd;
1222 ctxt = ctxt->getParent();
1224 Decl::Kind DK = GetDecl()->getKind();
1225 if ((DK == Decl::Namespace) || (DK == Decl::TranslationUnit)) {
1226 property |= kIsNamespace;
1230 const TagDecl *TD = llvm::dyn_cast<TagDecl>(GetDecl());
1235 property |= kIsEnum;
1239 const CXXRecordDecl *CRD =
1240 llvm::dyn_cast<CXXRecordDecl>(GetDecl());
1241 if (CRD->isClass()) {
1242 property |= kIsClass;
1244 else if (CRD->isStruct()) {
1245 property |= kIsStruct;
1247 else if (CRD->isUnion()) {
1248 property |= kIsUnion;
1250 if (CRD->hasDefinition() && CRD->isAbstract()) {
1251 property |= kIsAbstract;
1256 int TClingClassInfo::RootFlag()
const
1265 int TClingClassInfo::Size()
const
1275 R__LOCKGUARD(gInterpreterMutex);
1277 Decl::Kind DK = GetDecl()->getKind();
1278 if (DK == Decl::Namespace) {
1282 else if (DK == Decl::Enum) {
1286 const RecordDecl *RD = llvm::dyn_cast<RecordDecl>(GetDecl());
1291 if (!RD->getDefinition()) {
1295 ASTContext &Context = GetDecl()->getASTContext();
1296 cling::Interpreter::PushTransactionRAII RAII(fInterp);
1297 const ASTRecordLayout &Layout = Context.getASTRecordLayout(RD);
1298 int64_t size = Layout.getSize().getQuantity();
1299 int clang_size =
static_cast<int>(size);
1303 long TClingClassInfo::Tagnum()
const
1308 return reinterpret_cast<long>(GetDecl());
1311 const char *TClingClassInfo::FileName()
1316 if (fDeclFileName.empty())
1317 fDeclFileName = ROOT::TMetaUtils::GetFileName(*GetDecl(), *fInterp);
1318 return fDeclFileName.c_str();
1321 void TClingClassInfo::FullName(std::string &output,
const ROOT::TMetaUtils::TNormalizedCtxt &normCtxt)
const
1329 QualType type(fType, 0);
1330 ROOT::TMetaUtils::GetNormalizedName(output, type, *fInterp, normCtxt);
1333 if (
const NamedDecl* ND =
1334 llvm::dyn_cast<NamedDecl>(GetDecl())) {
1335 PrintingPolicy Policy(GetDecl()->getASTContext().
1336 getPrintingPolicy());
1337 llvm::raw_string_ostream stream(output);
1338 ND->getNameForDiagnostic(stream, Policy,
true);
1343 const char *TClingClassInfo::Title()
1354 R__LOCKGUARD(gInterpreterMutex);
1356 if (
const TagDecl *TD = llvm::dyn_cast<TagDecl>(GetDecl())) {
1357 if ( (TD = ROOT::TMetaUtils::GetAnnotatedRedeclarable(TD)) ) {
1358 if (AnnotateAttr *A = TD->getAttr<AnnotateAttr>()) {
1359 std::string attr = A->getAnnotation().str();
1360 if (attr.find(TMetaUtils::propNames::separator) != std::string::npos) {
1361 if (TMetaUtils::ExtractAttrPropertyFromName(*TD,TMetaUtils::propNames::comment,attr)) {
1363 return fTitle.c_str();
1367 return fTitle.c_str();
1375 const CXXRecordDecl *CRD =
1376 llvm::dyn_cast<CXXRecordDecl>(GetDecl());
1377 if (CRD && !CRD->isFromASTFile()) {
1378 fTitle = ROOT::TMetaUtils::GetClassComment(*CRD,0,*fInterp).str();
1380 return fTitle.c_str();
1383 const char *TClingClassInfo::TmpltName()
const
1389 R__LOCKGUARD(gInterpreterMutex);
1392 TTHREAD_TLS_DECL( std::string, buf);
1394 if (
const NamedDecl* ND = llvm::dyn_cast<NamedDecl>(GetDecl())) {
1396 buf = ND->getNameAsString();