[cfe-commits] r155961 - in /cfe/trunk: include/clang/Sema/Sema.h lib/Sema/SemaDeclObjC.cpp

Douglas Gregor dgregor at apple.com
Tue May 1 16:37:00 PDT 2012


Author: dgregor
Date: Tue May  1 18:37:00 2012
New Revision: 155961

URL: http://llvm.org/viewvc/llvm-project?rev=155961&view=rev
Log:
Eliminate Sema::CompareMethodParamsInBaseAndSuper() entirely, by
folding its one check into the normal path for checking overridden
Objective-C methods. Good for another 3.6% speedup on the test case in
<rdar://problem/11004361>.

Modified:
    cfe/trunk/include/clang/Sema/Sema.h
    cfe/trunk/lib/Sema/SemaDeclObjC.cpp

Modified: cfe/trunk/include/clang/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=155961&r1=155960&r2=155961&view=diff
==============================================================================
--- cfe/trunk/include/clang/Sema/Sema.h (original)
+++ cfe/trunk/include/clang/Sema/Sema.h Tue May  1 18:37:00 2012
@@ -2130,15 +2130,12 @@
   void CheckCategoryVsClassMethodMatches(ObjCCategoryImplDecl *CatIMP);
 
   /// \brief Add the given method to the list of globally-known methods.
-  ///
-  /// \returns true if this is the first method in the list with the given
-  /// selector.
-  bool addMethodToGlobalList(ObjCMethodList *List, ObjCMethodDecl *Method);
+  void addMethodToGlobalList(ObjCMethodList *List, ObjCMethodDecl *Method);
   
 private:
   /// AddMethodToGlobalPool - Add an instance or factory method to the global
   /// pool. See descriptoin of AddInstanceMethodToGlobalPool.
-  bool AddMethodToGlobalPool(ObjCMethodDecl *Method, bool impl, bool instance);
+  void AddMethodToGlobalPool(ObjCMethodDecl *Method, bool impl, bool instance);
 
   /// LookupMethodInGlobalPool - Returns the instance or factory method and
   /// optionally warns if there are multiple signatures.
@@ -2151,17 +2148,13 @@
   /// unit are added to a global pool. This allows us to efficiently associate
   /// a selector with a method declaraation for purposes of typechecking
   /// messages sent to "id" (where the class of the object is unknown).
-  ///
-  /// Returns true if the method was added, false if a method was already there.
-  bool AddInstanceMethodToGlobalPool(ObjCMethodDecl *Method, bool impl=false) {
-    return AddMethodToGlobalPool(Method, impl, /*instance*/true);
+  void AddInstanceMethodToGlobalPool(ObjCMethodDecl *Method, bool impl=false) {
+    AddMethodToGlobalPool(Method, impl, /*instance*/true);
   }
 
   /// AddFactoryMethodToGlobalPool - Same as above, but for factory methods.
-  ///
-  /// Returns true if the method was added, false if a method was already there.
-  bool AddFactoryMethodToGlobalPool(ObjCMethodDecl *Method, bool impl=false) {
-    return AddMethodToGlobalPool(Method, impl, /*instance*/false);
+  void AddFactoryMethodToGlobalPool(ObjCMethodDecl *Method, bool impl=false) {
+    AddMethodToGlobalPool(Method, impl, /*instance*/false);
   }
 
   /// AddAnyMethodToGlobalPool - Add any method, instance or factory to global
@@ -5832,9 +5825,6 @@
                                 const IdentifierInfo *Name);
   void ComparePropertiesInBaseAndSuper(ObjCInterfaceDecl *IDecl);
 
-  void CompareMethodParamsInBaseAndSuper(Decl *IDecl,
-                                         ObjCMethodDecl *MethodDecl,
-                                         bool IsInstance);
 
   void CompareProperties(Decl *CDecl, Decl *MergeProtocols);
 

Modified: cfe/trunk/lib/Sema/SemaDeclObjC.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclObjC.cpp?rev=155961&r1=155960&r2=155961&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclObjC.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclObjC.cpp Tue May  1 18:37:00 2012
@@ -1970,12 +1970,12 @@
   return true;
 }
 
-bool Sema::addMethodToGlobalList(ObjCMethodList *List, ObjCMethodDecl *Method) {
+void Sema::addMethodToGlobalList(ObjCMethodList *List, ObjCMethodDecl *Method) {
   // If the list is empty, make it a singleton list.
   if (List->Method == 0) {
     List->Method = Method;
     List->Next = 0;
-    return true;
+    return;
   }
   
   // We've seen a method with this name, see if we have already seen this type
@@ -2004,14 +2004,13 @@
         List->Method = Method;
     }
     
-    return false;
+    return;
   }
   
   // We have a new signature for an existing method - add it.
   // This is extremely rare. Only 1% of Cocoa selectors are "overloaded".
   ObjCMethodList *Mem = BumpAlloc.Allocate<ObjCMethodList>();
   Previous->Next = new (Mem) ObjCMethodList(Method, 0);
-  return false;
 }
 
 /// \brief Read the contents of the method pool for a given selector from
@@ -2021,11 +2020,11 @@
   ExternalSource->ReadMethodPool(Sel);
 }
 
-bool Sema::AddMethodToGlobalPool(ObjCMethodDecl *Method, bool impl,
+void Sema::AddMethodToGlobalPool(ObjCMethodDecl *Method, bool impl,
                                  bool instance) {
   // Ignore methods of invalid containers.
   if (cast<Decl>(Method->getDeclContext())->isInvalidDecl())
-    return false;
+    return;
 
   if (ExternalSource)
     ReadMethodPool(Method->getSelector());
@@ -2038,7 +2037,7 @@
   Method->setDefined(impl);
   
   ObjCMethodList &Entry = instance ? Pos->second.first : Pos->second.second;
-  return addMethodToGlobalList(&Entry, Method);
+  addMethodToGlobalList(&Entry, Method);
 }
 
 /// Determines if this is an "acceptable" loose mismatch in the global
@@ -2141,43 +2140,6 @@
   return 0;
 }
 
-/// CompareMethodParamsInBaseAndSuper - This routine compares methods with
-/// identical selector names in current and its super classes and issues
-/// a warning if any of their argument types are incompatible.
-void Sema::CompareMethodParamsInBaseAndSuper(Decl *ClassDecl,
-                                             ObjCMethodDecl *Method,
-                                             bool IsInstance)  {
-  ObjCInterfaceDecl *ID = dyn_cast<ObjCInterfaceDecl>(ClassDecl);
-  if (ID == 0) return;
-
-  while (ObjCInterfaceDecl *SD = ID->getSuperClass()) {
-    ObjCMethodDecl *SuperMethodDecl =
-        SD->lookupMethod(Method->getSelector(), IsInstance);
-    if (SuperMethodDecl == 0) {
-      ID = SD;
-      continue;
-    }
-    ObjCMethodDecl::param_iterator ParamI = Method->param_begin(),
-      E = Method->param_end();
-    ObjCMethodDecl::param_iterator PrevI = SuperMethodDecl->param_begin();
-    for (; ParamI != E; ++ParamI, ++PrevI) {
-      // Number of parameters are the same and is guaranteed by selector match.
-      assert(PrevI != SuperMethodDecl->param_end() && "Param mismatch");
-      QualType T1 = Context.getCanonicalType((*ParamI)->getType());
-      QualType T2 = Context.getCanonicalType((*PrevI)->getType());
-      // If type of argument of method in this class does not match its
-      // respective argument type in the super class method, issue warning;
-      if (!Context.typesAreCompatible(T1, T2)) {
-        Diag((*ParamI)->getLocation(), diag::ext_typecheck_base_super)
-          << T1 << T2;
-        Diag(SuperMethodDecl->getLocation(), diag::note_previous_declaration);
-        return;
-      }
-    }
-    ID = SD;
-  }
-}
-
 /// DiagnoseDuplicateIvars - 
 /// Check for duplicate ivars in the entire class at the start of 
 /// @implementation. This becomes necesssary because class extension can
@@ -2273,11 +2235,7 @@
         }
         InsMap[Method->getSelector()] = Method;
         /// The following allows us to typecheck messages to "id".
-        if (!AddInstanceMethodToGlobalPool(Method)) {
-          // verify that the instance method conforms to the same definition of
-          // parent methods if it shadows one.
-          CompareMethodParamsInBaseAndSuper(ClassDecl, Method, true);
-        }
+        AddInstanceMethodToGlobalPool(Method);
       }
     } else {
       /// Check for class method of the same name with incompatible types
@@ -2300,12 +2258,7 @@
           Diag(PrevMethod->getLocation(), diag::note_previous_declaration);
         }
         ClsMap[Method->getSelector()] = Method;
-        /// The following allows us to typecheck messages to "Class".
-        if (!AddFactoryMethodToGlobalPool(Method)) {
-          // verify that the class method conforms to the same definition of
-          // parent methods if it shadows one.
-          CompareMethodParamsInBaseAndSuper(ClassDecl, Method, false);
-        }
+        AddFactoryMethodToGlobalPool(Method);
       }
     }
   }
@@ -2892,6 +2845,27 @@
         isa<ObjCImplementationDecl>(ObjCMethod->getDeclContext()))
       CheckConflictingOverridingMethod(ObjCMethod, overridden,
               isa<ObjCProtocolDecl>(overridden->getDeclContext()));
+    
+    if (CurrentClass && overridden->getDeclContext() != CurrentClass &&
+        isa<ObjCInterfaceDecl>(overridden->getDeclContext())) {
+      ObjCMethodDecl::param_iterator ParamI = ObjCMethod->param_begin(),
+                                          E = ObjCMethod->param_end();
+      ObjCMethodDecl::param_iterator PrevI = overridden->param_begin();
+      for (; ParamI != E; ++ParamI, ++PrevI) {
+        // Number of parameters are the same and is guaranteed by selector match.
+        assert(PrevI != overridden->param_end() && "Param mismatch");
+        QualType T1 = Context.getCanonicalType((*ParamI)->getType());
+        QualType T2 = Context.getCanonicalType((*PrevI)->getType());
+        // If type of argument of method in this class does not match its
+        // respective argument type in the super class method, issue warning;
+        if (!Context.typesAreCompatible(T1, T2)) {
+          Diag((*ParamI)->getLocation(), diag::ext_typecheck_base_super)
+            << T1 << T2;
+          Diag(overridden->getLocation(), diag::note_previous_declaration);
+          break;
+        }
+      }
+    }
   }
   
   bool ARCError = false;





More information about the cfe-commits mailing list