diff --git a/core/meta/inc/TClass.h b/core/meta/inc/TClass.h
index d434ed68a3d0deeb82ab2471f243535ddf8cb32c..e6512c63004e244538b1d9d8182cac23c216ee97 100644
--- a/core/meta/inc/TClass.h
+++ b/core/meta/inc/TClass.h
@@ -258,6 +258,9 @@ private:
 protected:
    TVirtualStreamerInfo     *FindStreamerInfo(TObjArray* arr, UInt_t checksum) const;
    static THashTable        *GetClassTypedefHash();
+   void                      GetMissingDictionariesForBaseClasses(TCollection& result, bool recurse);
+   void                      GetMissingDictionariesForMembers(TCollection& result, bool recurse);
+   void                      GetMissingDictionariesWithRecursionCheck(TCollection& result, bool recurse);
 
 public:
    TClass();
@@ -372,7 +375,7 @@ public:
    TVirtualStreamerInfo     *FindStreamerInfoAbstractEmulated(UInt_t checksum) const;
    const type_info   *GetTypeInfo() const { return fTypeInfo; };
    Bool_t             HasDictionary();
-   void               GetMissingDictionaries(TObjArray& result, bool recurse = false);
+   void               GetMissingDictionaries(THashTable& result, bool recurse = false);
    void               IgnoreTObjectStreamer(Bool_t ignore=kTRUE);
    Bool_t             InheritsFrom(const char *cl) const;
    Bool_t             InheritsFrom(const TClass *cl) const;
diff --git a/core/meta/inc/TInterpreter.h b/core/meta/inc/TInterpreter.h
index a2db7281c5ba1b827487dd9ad15688e46e434b4b..d313526da482bd98b02bbfcbbda793bdb56ce737 100644
--- a/core/meta/inc/TInterpreter.h
+++ b/core/meta/inc/TInterpreter.h
@@ -120,8 +120,6 @@ public:
    virtual const char *GetIncludePath() = 0;
    virtual const char *GetSTLIncludePath() const { return ""; }
    virtual TObjArray  *GetRootMapFiles() const = 0;
-   virtual Bool_t   HasDictionary(TClass* cl) = 0;
-   virtual void     GetMissingDictionaries(TClass* cl, TObjArray& result, bool recurse = false) = 0;
    virtual void     Initialize() = 0;
    virtual void     InspectMembers(TMemberInspector&, const void* obj, const TClass* cl, Bool_t isTransient) = 0;
    virtual Bool_t   IsLoaded(const char *filename) const = 0;
diff --git a/core/meta/src/TClass.cxx b/core/meta/src/TClass.cxx
index 36903902b3c30cfa60f691c49f4d70be042f5473..275a851ce37e76cff6cd5f9907393c737c4f2589 100644
--- a/core/meta/src/TClass.cxx
+++ b/core/meta/src/TClass.cxx
@@ -3369,20 +3369,137 @@ void TClass::GetMenuItems(TList *list)
    }
 }
 
+//______________________________________________________________________________
 Bool_t TClass::HasDictionary()
 {
    // Check whether a class has a dictionary or not.
 
-   return gInterpreter->HasDictionary(this);
+   if (gClassTable->GetDict(fName)) return true;
+
+   return false;
+}
+
+//______________________________________________________________________________
+void TClass::GetMissingDictionariesForBaseClasses(TCollection& result, bool recurse)
+{
+   // Verify the base classes always.
+
+   TList* lb = GetListOfBases();
+   if (!lb) return;
+   TIter nextBase(lb);
+   TBaseClass* base = 0;
+   while ((base = (TBaseClass*)nextBase())) {
+      TClass* baseCl = base->Class();
+      if (baseCl) {
+            baseCl->GetMissingDictionariesWithRecursionCheck(result, recurse);
+      }
+   }
+}
+
+//______________________________________________________________________________
+void TClass::GetMissingDictionariesForMembers(TCollection& result, bool recurse)
+{
+   // Verify the Data Members.
+
+   TListOfDataMembers* ldm = (TListOfDataMembers*)GetListOfDataMembers();
+   if (!ldm) return ;
+   TIter nextMemb(ldm);
+   TDataMember * dm = 0;
+   while ((dm = (TDataMember*)nextMemb())) {
+      // If it is a built-in data type.
+      TClass* dmTClass = 0;
+      if (dm->GetDataType()) {
+         dmTClass = dm->GetDataType()->Class();
+         // Otherwise get the string representing the type.
+      } else if (dm->GetTypeName()) {
+            dmTClass = TClass::GetClass(dm->GetTypeName());
+      }
+      if (dmTClass) {
+            dmTClass->GetMissingDictionariesWithRecursionCheck(result, recurse);
+      }
+   }
+}
+
+//______________________________________________________________________________
+void TClass::GetMissingDictionariesWithRecursionCheck(TCollection& result, bool recurse)
+{
+   // From the second level of recursion onwards it is different state check.
+
+   if (result.FindObject(this)) return;
+
+   static TClassRef sCIString("string");
+   if (this == sCIString) return;
+
+   if (strncmp(fName, "pair<", 5) == 0) return;
+
+   if (!HasDictionary()) {
+      result.Add(this);
+   }
+   //Check whether a custom streamer
+   if (!TestBit(TClass::kHasCustomStreamerMember)) {
+      if (GetCollectionProxy()) {
+         // We need to look at the collection's content
+         // The collection has different kind of elements the check would be required.
+         TClass* t = 0;
+         if ((t = GetCollectionProxy()->GetValueClass())) {
+            if (!t->HasDictionary()) {
+               if (recurse) {
+                  t->GetMissingDictionariesWithRecursionCheck(result, recurse);
+               } else {
+                  result.Add(this);
+               }
+            }
+         }
+      } else {
+         if (recurse) {
+            GetMissingDictionariesForMembers(result, recurse);
+         }
+         GetMissingDictionariesForBaseClasses(result, recurse);
+      }
+   }
 }
 
-void TClass::GetMissingDictionaries(TObjArray& result, bool recurse)
+//______________________________________________________________________________
+void TClass::GetMissingDictionaries(THashTable& result, bool recurse)
 {
-   // Get the classes that have a missing dictionary.
-   // Recurse over the data members using the flag recurse.
-   // By default is is not recursing on the data members.
+   // Get the classes that have a missing dictionary starting from this one.
+   // With recurse = false the classes checked for missing dictionaries are:
+   //                      the class itself, all base classes, direct data members,
+   //                      and for collection proxies the container's
+   //                      elements without iterating over the element's data members;
+   // With recurse = true the classes checked for missing dictionaries are:
+   //                      the class itself, all base classes, recursing on the data members,
+   //                      and for the collection proxies recursiong on the elements of the
+   //                      collection and iterating over the element's data members.
+
+   // Top level recursion it different from the following levels of recursion.
+
+   if (result.FindObject(this)) return;
 
-   gInterpreter->GetMissingDictionaries(this, result, recurse);
+   static TClassRef sCIString("string");
+   if (this == sCIString) return;
+
+   if (strncmp(fName, "pair<", 5) == 0) return;
+
+   if (!HasDictionary()) {
+      result.Add(this);
+   }
+   //Check whether a custom streamer
+   if (!TestBit(TClass::kHasCustomStreamerMember)) {
+      if (GetCollectionProxy()) {
+         // We need to look at the collection's content
+         // The collection has different kind of elements the check would be required.
+         TClass* t = 0;
+         if ((t = GetCollectionProxy()->GetValueClass())) {
+            if (!t->HasDictionary()) {
+               t->GetMissingDictionariesWithRecursionCheck(result, recurse);
+            }
+         }
+      } else {
+         GetMissingDictionariesForMembers(result, recurse);
+         GetMissingDictionariesForBaseClasses(result, recurse);
+      }
+   }
 }
 
 //______________________________________________________________________________
diff --git a/core/meta/src/TCling.cxx b/core/meta/src/TCling.cxx
index 192fb1cb0f0ca4c9b6b1f0e6e8df49d18d5c854c..6d09670e5f0444b07d55d0fc3c44cabb1f1b871a 100644
--- a/core/meta/src/TCling.cxx
+++ b/core/meta/src/TCling.cxx
@@ -3409,154 +3409,6 @@ void TCling::GetInterpreterTypeName(const char* name, std::string &output, Bool_
    return;
 }
 
-//______________________________________________________________________________
-Bool_t TCling::HasDictionary(TClass* cl)
-{
-   // Check whether a class has a dictionary or not.
-
-   // Get the Decl and Type for the class.
-   TClingClassInfo* cli = (TClingClassInfo*)cl->GetClassInfo();
-   if (!cli) return false;
-   const clang::Decl* D = cli->GetDecl();
-   const clang::Type* T = cli->GetType();
-
-   // Convert to RecordDecl.
-   if (llvm::isa<clang::RecordDecl>(D)) {
-
-      // Get the name of the class
-      std::string buf;
-      ROOT::TMetaUtils::GetNormalizedName(buf, QualType(T, 0), *fInterpreter, *fNormalizedCtxt);
-      const char* name = buf.c_str();
-
-      // Check for the dictionary of the curent class.
-      if (gClassTable->GetDict(name))
-         return true;
-   }
-   return false;
-}
-
-//______________________________________________________________________________
-bool TCling::InsertMissingDictionaryDecl(const clang::Decl* D, std::set<std::string> &netD, clang::QualType qType, bool recurse)
-{
-
-   // Utility function to insert a type pointer to a decl that does not have a dictionary
-   // In the set of pointer for the classes without dictionaries.
-
-   // Get the name of the class.
-
-   // If we deal with a std::string we do not need to recurse and we do not need to get the normalized name
-   // because we want to now if it is a std string or not.
-   if (strcmp(qType.getAsString().c_str(), "std::string")==0) return false;
-   std::string buf;
-   ROOT::TMetaUtils::GetNormalizedName(buf, qType, *fInterpreter, *fNormalizedCtxt);
-   const char* name = buf.c_str();
-
-   // Check whether the type pointer is not already in the set.
-   std::set<std::string>::iterator it = netD.find(name);
-   if (it != netD.end()) return false;
-
-   // Check for the dictionary of the curent class.
-   if (TClass* t = TClass::GetClass(name)) {
-   //Check whether a custom streamer
-      if (t->TestBit(TClass::kHasCustomStreamerMember)) return false;
-      // Deal with proxies.
-      if (t->GetCollectionProxy()) {
-         // We need to make sure the collection proxy is not emulated
-         if ((t->GetCollectionProxy()->GetProperties() & TVirtualCollectionProxy::kIsEmulated) != 0) {
-            // oups we are missing the dictionary for the collection.
-            netD.insert(name);
-            return false;
-         } else {
-            // We need to *not* look at t but instead at its content
-            // The collection has different kind of elements the check would be required.
-            if ((t = t->GetCollectionProxy()->GetValueClass())) {
-               if (TClingClassInfo* ti = (TClingClassInfo*)t->GetClassInfo()) {
-                  if(const clang::Type* elemType = ti->GetType()) {
-                     // Get the name of the class.
-                     std::string elemBuf;
-                     ROOT::TMetaUtils::GetNormalizedName(elemBuf, QualType(elemType, 0), *fInterpreter, *fNormalizedCtxt);
-                     const char* elemName = elemBuf.c_str();
-                     if (!gClassTable->GetDict(elemName)) {
-                        std::set<std::string>::iterator it = netD.find(elemName);
-                        if (it != netD.end()) return false;
-                        netD.insert(elemName);
-                     }
-                  }
-               }
-            }
-            return true;
-         }
-      }
-   }
-   if (!gClassTable->GetDict(name)) {
-         netD.insert(name);
-   }
-
-   return true;
-}
-//______________________________________________________________________________
-void TCling::GetMissingDictionariesForDecl(const clang::Decl* D, std::set<std::string> &netD, clang::QualType qType, bool recurse)
-{
-   // Utility function to get the missing dictionaries for a record decl.
-   // Checks all the data members and if the recurse flag is true it recurses over contents of the data members.
-
-   // Insert this Type pointer in the set if it is not already there and it does not have a dictionary.
-   if (!InsertMissingDictionaryDecl(D, netD, qType, recurse)) return;
-
-   // Verify the Data members.
-   if (const clang::CXXRecordDecl* RD = llvm::dyn_cast<clang::CXXRecordDecl>(D)) {
-      for (clang::RecordDecl::field_iterator iField = RD->field_begin(),
-           eField = RD->field_end(); iField != eField; ++iField) {
-
-         clang::QualType fieldQualType = (*iField)->getType();
-         if (!fieldQualType.isNull()) {
-            // Check if not NullType.
-            //if (const clang::TypedefType* TD = dyn_cast<clang::TypedefType>(fieldQualType.getTypePtr())) {
-            if (const clang::Type* fieldType = ROOT::TMetaUtils::GetUnderlyingType(fieldQualType)) {
-               clang::Decl* FD = fieldType->getAsCXXRecordDecl();
-               if (FD) {
-                  if(recurse) {
-                     GetMissingDictionariesForDecl(FD, netD, QualType(fieldType, 0), recurse);
-                  } else {
-                     InsertMissingDictionaryDecl(FD, netD, QualType(fieldType, 0), recurse);
-                  }
-               }
-            }
-         }
-      }
-   }
-}
-
-//______________________________________________________________________________
-void TCling::GetMissingDictionaries(TClass* cl, TObjArray& result, bool recurse /*recurse*/)
-{
-   // Get the missing dictionaries for a given TClass cl.
-
-   // Get the Decl and Type for the class.
-   TClingClassInfo* cli = (TClingClassInfo*)cl->GetClassInfo();
-   if (!cli){
-      return;
-   }
-   const clang::Decl* D = cli->GetDecl();
-   const clang::Type* T = cli->GetType();
-
-   // Set containing all the decls of the classes that do not have a dictionary.
-   std::set<std::string> netD;
-   clang::QualType qType = QualType(T, 0);
-   GetMissingDictionariesForDecl(D, netD, qType, recurse);
-
-   // Convert set<std::string> to TObjArray.
-   for (std::set<std::string>::const_iterator I = netD.begin(),
-        E = netD.end(); I != E; ++I) {
-
-      if (TClass* clMissingDict = TClass::GetClass((*I).c_str())) {
-         result.Add(clMissingDict);
-      } else {
-         Error("TCling::GetMissingDictionaries", "The class %s missing dictionary was not found.", (*I).c_str());
-      }
-   }
-}
-
 //______________________________________________________________________________
 void TCling::Execute(const char* function, const char* params, int* error)
 {
diff --git a/core/meta/src/TCling.h b/core/meta/src/TCling.h
index 692f06328bdefbae77f09a60a143f0c6de13e14e..ea861b01d7f2e13cca6775e1d20e28b461abdc83 100644
--- a/core/meta/src/TCling.h
+++ b/core/meta/src/TCling.h
@@ -170,8 +170,6 @@ public: // Public Interface
    const char* GetIncludePath();
    virtual const char* GetSTLIncludePath() const;
    TObjArray*  GetRootMapFiles() const { return fRootmapFiles; }
-   Bool_t  HasDictionary(TClass* cl);
-   void    GetMissingDictionaries(TClass* cl, TObjArray& result, bool recurse);
    unsigned long long GetInterpreterStateMarker() const { return fTransactionCount;}
    virtual void Initialize();
    void    InspectMembers(TMemberInspector&, const void* obj, const TClass* cl, Bool_t isTransient);
@@ -503,8 +501,6 @@ private: // Private Utility Functions
 
    bool LoadPCM(TString pcmFileName, const char** headers,
                 void (*triggerFunc)()) const;
-   void GetMissingDictionariesForDecl(const clang::Decl* D, std::set<std::string> &netD, clang::QualType qType, bool recurse);
-   bool InsertMissingDictionaryDecl(const clang::Decl* D, std::set<std::string> &netD, clang::QualType qType, bool recurse);
    void InitRootmapFile(const char *name);
    int  ReadRootmapFile(const char *rootmapfile);
    Bool_t HandleNewTransaction(const cling::Transaction &T);
diff --git a/core/metautils/src/TClassEdit.cxx b/core/metautils/src/TClassEdit.cxx
index f61cf0a23324bf929fa413b0c42695e5e17b5231..966a2960bcec41b322e6ad13c9969ac342951fa2 100644
--- a/core/metautils/src/TClassEdit.cxx
+++ b/core/metautils/src/TClassEdit.cxx
@@ -336,7 +336,12 @@ void TClassEdit::TSplitType::ShortType(std::string &answ, int mode)
          answ += '>';
       }
    }
-   if (fNestedLocation) answ += fElements[fNestedLocation];
+   if (fNestedLocation) {
+      // Treat X pf A<B>::X
+      fElements[fNestedLocation] = TClassEdit::ShortType(fElements[fNestedLocation].c_str(),mode);
+      answ += fElements[fNestedLocation];
+   }
+   // tail is not a type name, just [2], &, * etc.
    if (tailLoc) answ += fElements[tailLoc];
 }