No longer hide the compiler detail.
The partial desugaring (part of normalization) now strips a typedef even when it original from std and points to compiler details (__gnu_cxx, etc.). The cost of this convenience was the fact the same entity could have different 'name' and thus different class even-though they were supposed to be strictly equivalent. i.e. depending on the way to get to the class it could be name vector<int*>::iterator or __gnu_cxx::iterator<int*> or std::iterator<int*>. This different from the case where we have a strictly bidirectional equivalent between the class and its unique typedef (yes, we are talking about you std::string). This also different from the case where there is a semantic difference between the two possible name. I.e. where an opaque typedef is used. For example, vector<Double32_t> and vector<double> and where the 'way' to get to the type[name] is relevant.
This commit is contained in:
parent
3115300308
commit
45895aec23
@ -602,31 +602,6 @@ namespace utils {
|
||||
return false;
|
||||
}
|
||||
|
||||
static bool IsCompilerDetails(const TagType *tagTy)
|
||||
{
|
||||
// Return true if the TagType is a 'details' of the std implementation.
|
||||
// (For now it means declared in __gnu_cxx or starting with underscore).
|
||||
|
||||
const TagDecl *decl = tagTy->getDecl();
|
||||
assert(decl);
|
||||
IdentifierInfo *info = decl->getDeclName().getAsIdentifierInfo();
|
||||
if (info && info->getNameStart()[0] == '_') {
|
||||
// We have a name starting by _, this is reserve for compiler
|
||||
// implementation, so let's not desugar to it.
|
||||
return true;
|
||||
}
|
||||
// And let's check if it is in one of the know compiler implementation
|
||||
// namespace.
|
||||
const NamedDecl *outer =dyn_cast_or_null<NamedDecl>(decl->getDeclContext());
|
||||
while (outer && outer->getName().size() ) {
|
||||
if (outer->getName().compare("__gnu_cxx") == 0) {
|
||||
return true;
|
||||
}
|
||||
outer = dyn_cast_or_null<NamedDecl>(outer->getDeclContext());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
unsigned int
|
||||
Transform::Config::DropDefaultArg(clang::TemplateDecl &Template) const
|
||||
{
|
||||
@ -658,41 +633,7 @@ namespace utils {
|
||||
{
|
||||
// Return true, if we should keep this typedef rather than desugaring it.
|
||||
|
||||
if ( 0 != TypesToSkip.count(QT.getTypePtr()) )
|
||||
return true;
|
||||
|
||||
const TypedefType* typedeftype =
|
||||
dyn_cast_or_null<TypedefType>(QT.getTypePtr());
|
||||
const TypedefNameDecl* decl = typedeftype ? typedeftype->getDecl() : 0;
|
||||
if (decl) {
|
||||
const NamedDecl* outer
|
||||
= dyn_cast_or_null<NamedDecl>(decl->getDeclContext());
|
||||
// We want to keep the typedef that are defined within std and
|
||||
// are pointing to something also declared in std (usually an
|
||||
// implementation details like std::basic_string or __gnu_cxx::iterator.
|
||||
|
||||
while ( outer && outer->getName().size() ) {
|
||||
// NOTE: Net is being cast too widely, replace by a lookup.
|
||||
// or by using Sema::getStdNamespace
|
||||
if (outer->getDeclContext()->isTranslationUnit()
|
||||
&& outer->getName().compare("std") == 0) {
|
||||
// And now let's check that the target is also within std.
|
||||
const Type *underlyingType
|
||||
= decl->getUnderlyingType().getSplitDesugaredType().Ty;
|
||||
const ElaboratedType *elTy = dyn_cast<ElaboratedType>(underlyingType);
|
||||
if (elTy) {
|
||||
underlyingType = elTy->getNamedType().getTypePtr();
|
||||
}
|
||||
const TagType *tagTy = underlyingType->getAs<TagType>();
|
||||
if (tagTy) {
|
||||
bool details = IsCompilerDetails(tagTy);
|
||||
if (details) return true;
|
||||
}
|
||||
}
|
||||
outer = dyn_cast_or_null<NamedDecl>(outer->getDeclContext());
|
||||
}
|
||||
}
|
||||
return false;
|
||||
return 0 != TypesToSkip.count(QT.getTypePtr());
|
||||
}
|
||||
|
||||
static bool SingleStepPartiallyDesugarTypeImpl(QualType& QT)
|
||||
|
@ -36,7 +36,7 @@ template <typename T, typename U> class C {};
|
||||
typedef C<A<B<Double32_t, Int_t> >, Double32_t > CTD;
|
||||
typedef C<A<B<const Double32_t, const Int_t> >, Double32_t > CTDConst;
|
||||
|
||||
template <typename key, typename value, typename compare_operation = std::less<key>, typename alloc = std::allocator<std::pair<const key, value> > > class cmap { key fKey; const value fValue; alloc fAlloc; };
|
||||
template <typename key, typename value, typename compare_operation = std::less<key>, typename alloc = std::allocator<std::pair<const key, value> > > class cmap { key fKey; const value fValue; alloc fAlloc; public: cmap() : fValue(0) {} };
|
||||
// : public std::map<key, value, compare_operation, alloc> {
|
||||
|
||||
template <typename key, typename value = const key> class mypair { public: key fKey; value fValue; };
|
||||
@ -108,10 +108,10 @@ public:
|
||||
Embedded_objects::EmbeddedClasses::Embedded5 m_emb5;
|
||||
Embedded_objects::EmbeddedTypedef::Embedded6 m_emb6;
|
||||
typedef std::vector<int> vecint;
|
||||
vecint::iterator m_iter;
|
||||
vecint* m_iter;
|
||||
const Eenum m_enum;
|
||||
typedef vector<int> vecint2;
|
||||
vecint2::iterator m_iter2;
|
||||
vecint2* m_iter2;
|
||||
};
|
||||
|
||||
namespace NS1 {
|
||||
@ -141,7 +141,6 @@ transConfig.m_toSkip.insert(lookup.findType("string", diags).getTypePtr());
|
||||
transConfig.m_toSkip.insert(lookup.findType("std::string", diags).getTypePtr());
|
||||
|
||||
const clang::Type* t = 0;
|
||||
const clang::TypedefType *td = 0;
|
||||
clang::QualType QT;
|
||||
using namespace cling::utils;
|
||||
|
||||
@ -318,19 +317,6 @@ QT = clang::QualType(t, 0);
|
||||
Transform::GetPartiallyDesugaredType(Ctx, QT, transConfig).getAsString().c_str()
|
||||
// CHECK: ({{const char [*]|const_pointer}}) "Details::Impl"
|
||||
|
||||
lookup.findScope("vector<Details::Impl>::iterator", diags, &t);
|
||||
QT = clang::QualType(t, 0);
|
||||
Transform::GetPartiallyDesugaredType(Ctx, QT, transConfig).getAsString().c_str()
|
||||
// CHECK: ({{const char [*]|const_pointer}}) "std::vector<Details::Impl>::iterator"
|
||||
|
||||
lookup.findScope("vector<Details::Impl>::const_iterator", diags, &t);
|
||||
QT = clang::QualType(t, 0);
|
||||
td = QT->getAs<clang::TypedefType>();
|
||||
clang::TypedefNameDecl *tdDecl = td->getDecl();
|
||||
QT = Ctx.getTypedefType(tdDecl);
|
||||
Transform::GetPartiallyDesugaredType(Ctx, QT, transConfig, true).getAsString().c_str()
|
||||
// CHECK: ({{const char [*]|const_pointer}}) "std::vector<Details::Impl, std::allocator<Details::Impl> >::const_iterator"
|
||||
|
||||
const clang::Decl*decl=lookup.findScope("Embedded_objects", diags,&t);
|
||||
if (decl) {
|
||||
const clang::CXXRecordDecl *cxxdecl
|
||||
@ -356,9 +342,9 @@ if (decl) {
|
||||
// CHECK: Embedded_objects::EmbeddedClasses::Embedded4
|
||||
// CHECK: Embedded_objects::EmbeddedClasses::Embedded5
|
||||
// CHECK: Embedded_objects::EmbeddedClasses::Embedded6
|
||||
// CHECK: std::vector<int>::iterator
|
||||
// CHECK: std::vector<int> *
|
||||
// CHECK: const Embedded_objects::Eenum
|
||||
// CHECK: std::vector<int>::iterator
|
||||
// CHECK: std::vector<int> *
|
||||
|
||||
// In the partial desugaring add support for the case where we have a type
|
||||
// that point to an already completely desugared template instantiation in
|
||||
|
Loading…
x
Reference in New Issue
Block a user