r337607 - [AST] Various micro-optimizations in CXXInheritance

Benjamin Kramer via cfe-commits cfe-commits at lists.llvm.org
Fri Jul 20 13:13:08 PDT 2018


Author: d0k
Date: Fri Jul 20 13:13:08 2018
New Revision: 337607

URL: http://llvm.org/viewvc/llvm-project?rev=337607&view=rev
Log:
[AST] Various micro-optimizations in CXXInheritance

1. Pack std::pair<bool, unsigned> in CXXBasePaths::ClassSubobjects.
2. Use a SmallPtrSet instead of a SmallDenseSet for CXXBasePaths::VisitedDependentRecords.
3. Reorder some members of CXXBasePaths to save 8 bytes.
4. Use a SmallSetVector instead of a SetVector in CXXBasePaths::ComputeDeclsFound to avoid some allocations.

This speeds up an -fsyntax-only on all of Boost by approx 0.15%,
mainly by speeding up CXXBasePaths::lookupInBases by
approx 10%. No functional changes.

Patch by Bruno Ricci!

Differential Revision: https://reviews.llvm.org/D49302

Modified:
    cfe/trunk/include/clang/AST/CXXInheritance.h
    cfe/trunk/lib/AST/CXXInheritance.cpp

Modified: cfe/trunk/include/clang/AST/CXXInheritance.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/CXXInheritance.h?rev=337607&r1=337606&r2=337607&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/CXXInheritance.h (original)
+++ cfe/trunk/include/clang/AST/CXXInheritance.h Fri Jul 20 13:13:08 2018
@@ -125,18 +125,36 @@ class CXXBasePaths {
   /// Paths - The actual set of paths that can be taken from the
   /// derived class to the same base class.
   std::list<CXXBasePath> Paths;
-  
+
   /// ClassSubobjects - Records the class subobjects for each class
-  /// type that we've seen. The first element in the pair says
+  /// type that we've seen. The first element IsVirtBase says
   /// whether we found a path to a virtual base for that class type,
-  /// while the element contains the number of non-virtual base
+  /// while NumberOfNonVirtBases contains the number of non-virtual base
   /// class subobjects for that class type. The key of the map is
   /// the cv-unqualified canonical type of the base class subobject.
-  llvm::SmallDenseMap<QualType, std::pair<bool, unsigned>, 8> ClassSubobjects;
+  struct IsVirtBaseAndNumberNonVirtBases {
+    unsigned IsVirtBase : 1;
+    unsigned NumberOfNonVirtBases : 31;
+  };
+  llvm::SmallDenseMap<QualType, IsVirtBaseAndNumberNonVirtBases, 8>
+      ClassSubobjects;
 
   /// VisitedDependentRecords - Records the dependent records that have been
   /// already visited.
-  llvm::SmallDenseSet<const CXXRecordDecl *, 4> VisitedDependentRecords;
+  llvm::SmallPtrSet<const CXXRecordDecl *, 4> VisitedDependentRecords;
+
+  /// DetectedVirtual - The base class that is virtual.
+  const RecordType *DetectedVirtual = nullptr;
+
+  /// ScratchPath - A BasePath that is used by Sema::lookupInBases
+  /// to help build the set of paths.
+  CXXBasePath ScratchPath;
+
+  /// Array of the declarations that have been found. This
+  /// array is constructed only if needed, e.g., to iterate over the
+  /// results within LookupResult.
+  std::unique_ptr<NamedDecl *[]> DeclsFound;
+  unsigned NumDeclsFound = 0;
 
   /// FindAmbiguities - Whether Sema::IsDerivedFrom should try find
   /// ambiguous paths while it is looking for a path from a derived
@@ -152,20 +170,7 @@ class CXXBasePaths {
   /// if it finds a path that goes across a virtual base. The virtual class
   /// is also recorded.
   bool DetectVirtual;
-  
-  /// ScratchPath - A BasePath that is used by Sema::lookupInBases
-  /// to help build the set of paths.
-  CXXBasePath ScratchPath;
 
-  /// DetectedVirtual - The base class that is virtual.
-  const RecordType *DetectedVirtual = nullptr;
-  
-  /// Array of the declarations that have been found. This
-  /// array is constructed only if needed, e.g., to iterate over the
-  /// results within LookupResult.
-  std::unique_ptr<NamedDecl *[]> DeclsFound;
-  unsigned NumDeclsFound = 0;
-  
   void ComputeDeclsFound();
 
   bool lookupInBases(ASTContext &Context, const CXXRecordDecl *Record,

Modified: cfe/trunk/lib/AST/CXXInheritance.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/CXXInheritance.cpp?rev=337607&r1=337606&r2=337607&view=diff
==============================================================================
--- cfe/trunk/lib/AST/CXXInheritance.cpp (original)
+++ cfe/trunk/lib/AST/CXXInheritance.cpp Fri Jul 20 13:13:08 2018
@@ -40,7 +40,7 @@ void CXXBasePaths::ComputeDeclsFound() {
   assert(NumDeclsFound == 0 && !DeclsFound &&
          "Already computed the set of declarations");
 
-  llvm::SetVector<NamedDecl *, SmallVector<NamedDecl *, 8>> Decls;
+  llvm::SmallSetVector<NamedDecl *, 8> Decls;
   for (paths_iterator Path = begin(), PathEnd = end(); Path != PathEnd; ++Path)
     Decls.insert(Path->Decls.front());
 
@@ -63,8 +63,8 @@ CXXBasePaths::decl_range CXXBasePaths::f
 /// an unqualified, canonical class type.
 bool CXXBasePaths::isAmbiguous(CanQualType BaseType) {
   BaseType = BaseType.getUnqualifiedType();
-  std::pair<bool, unsigned>& Subobjects = ClassSubobjects[BaseType];
-  return Subobjects.second + (Subobjects.first? 1 : 0) > 1;
+  IsVirtBaseAndNumberNonVirtBases Subobjects = ClassSubobjects[BaseType];
+  return Subobjects.NumberOfNonVirtBases + (Subobjects.IsVirtBase ? 1 : 0) > 1;
 }
 
 /// clear - Clear out all prior path information.
@@ -217,21 +217,21 @@ bool CXXBasePaths::lookupInBases(ASTCont
     
     // Determine whether we need to visit this base class at all,
     // updating the count of subobjects appropriately.
-    std::pair<bool, unsigned>& Subobjects = ClassSubobjects[BaseType];
+    IsVirtBaseAndNumberNonVirtBases &Subobjects = ClassSubobjects[BaseType];
     bool VisitBase = true;
     bool SetVirtual = false;
     if (BaseSpec.isVirtual()) {
-      VisitBase = !Subobjects.first;
-      Subobjects.first = true;
+      VisitBase = !Subobjects.IsVirtBase;
+      Subobjects.IsVirtBase = true;
       if (isDetectingVirtual() && DetectedVirtual == nullptr) {
         // If this is the first virtual we find, remember it. If it turns out
         // there is no base path here, we'll reset it later.
         DetectedVirtual = BaseType->getAs<RecordType>();
         SetVirtual = true;
       }
-    } else
-      ++Subobjects.second;
-    
+    } else {
+      ++Subobjects.NumberOfNonVirtBases;
+    }
     if (isRecordingPaths()) {
       // Add this base specifier to the current path.
       CXXBasePathElement Element;
@@ -240,7 +240,7 @@ bool CXXBasePaths::lookupInBases(ASTCont
       if (BaseSpec.isVirtual())
         Element.SubobjectNumber = 0;
       else
-        Element.SubobjectNumber = Subobjects.second;
+        Element.SubobjectNumber = Subobjects.NumberOfNonVirtBases;
       ScratchPath.push_back(Element);
 
       // Calculate the "top-down" access to this base class.




More information about the cfe-commits mailing list