]> granicus.if.org Git - clang/commitdiff
objective-C++: Delayed parsing of most common
authorFariborz Jahanian <fjahanian@apple.com>
Fri, 10 Aug 2012 15:54:40 +0000 (15:54 +0000)
committerFariborz Jahanian <fjahanian@apple.com>
Fri, 10 Aug 2012 15:54:40 +0000 (15:54 +0000)
member functions defined inside an objc class
implementation. wip.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@161667 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Parse/ParseDecl.cpp
lib/Parse/Parser.cpp
test/SemaObjCXX/delay-parsing-cplusfuncs.mm [new file with mode: 0644]

index 9f8f3cec2889aa2e07236214b8b9b6f13290cd78..b830d9ccfd9f81f2b6dc67ba4cd4abf310182ebc 100644 (file)
@@ -1340,12 +1340,7 @@ Parser::DeclGroupPtrTy Parser::ParseDeclGroup(ParsingDeclSpec &DS,
       // Look at the next token to make sure that this isn't a function
       // declaration.  We have to check this because __attribute__ might be the
       // start of a function definition in GCC-extended K&R C.
-      // FIXME. Delayed parsing not done for c/c++ functions nested in namespace
-      !isDeclarationAfterDeclarator() && 
-      (!CurParsedObjCImpl || Tok.isNot(tok::l_brace) || 
-       (getLangOpts().CPlusPlus && 
-        (D.getCXXScopeSpec().isSet() || 
-         !Actions.CurContext->isTranslationUnit())))) {
+      !isDeclarationAfterDeclarator()) {
 
     if (isStartOfFunctionDefinition(D)) {
       if (DS.getStorageClassSpec() == DeclSpec::SCS_typedef) {
@@ -1401,14 +1396,6 @@ Parser::DeclGroupPtrTy Parser::ParseDeclGroup(ParsingDeclSpec &DS,
     DeclsInGroup.push_back(FirstDecl);
 
   bool ExpectSemi = Context != Declarator::ForContext;
-
-  if (CurParsedObjCImpl && D.isFunctionDeclarator() &&
-      Tok.is(tok::l_brace)) {
-    // Consume the tokens and store them for later parsing.
-    StashAwayMethodOrFunctionBodyTokens(FirstDecl);
-    CurParsedObjCImpl->HasCFunction = true;
-    ExpectSemi = false;
-  }
   
   // If we don't have a comma, it is either the end of the list (a ';') or an
   // error, bail out.
index 7314228b9f9ba9367f980aa1947dd195d64ddde9..3531deba4f91d383312512966137df3c7ca69be8 100644 (file)
@@ -1025,7 +1025,26 @@ Decl *Parser::ParseFunctionDefinition(ParsingDeclarator &D,
     }
     return DP;
   }
-
+  else if (CurParsedObjCImpl && Tok.is(tok::l_brace) && 
+      !TemplateInfo.TemplateParams &&
+      Actions.CurContext->isTranslationUnit()) {
+    MultiTemplateParamsArg TemplateParameterLists(Actions, 0, 0);
+    ParseScope BodyScope(this, Scope::FnScope|Scope::DeclScope);
+    Scope *ParentScope = getCurScope()->getParent();
+    
+    D.setFunctionDefinitionKind(FDK_Definition);
+    Decl *FuncDecl = Actions.HandleDeclarator(ParentScope, D,
+                                        move(TemplateParameterLists));
+    D.complete(FuncDecl);
+    D.getMutableDeclSpec().abort();
+    if (FuncDecl) {
+      // Consume the tokens and store them for later parsing.
+      StashAwayMethodOrFunctionBodyTokens(FuncDecl);
+      CurParsedObjCImpl->HasCFunction = true;
+      return FuncDecl;
+    }
+  }
+      
   // Enter a scope for the function body.
   ParseScope BodyScope(this, Scope::FnScope|Scope::DeclScope);
 
diff --git a/test/SemaObjCXX/delay-parsing-cplusfuncs.mm b/test/SemaObjCXX/delay-parsing-cplusfuncs.mm
new file mode 100644 (file)
index 0000000..feae744
--- /dev/null
@@ -0,0 +1,38 @@
+// RUN: %clang_cc1 -x objective-c++ -fsyntax-only -Werror -verify -Wno-objc-root-class %s
+// rdar://10387088
+
+@interface MyClass
+- (void)someMethod;
+@end
+
+struct S {
+  int bar(MyClass * myObject);
+
+  int gorfbar(MyClass * myObject);
+
+};
+
+@implementation MyClass
+- (void)someMethod {
+    [self privateMethod];  // clang already does not warn here
+}
+
+int S::bar(MyClass * myObject) {
+    [myObject privateMethod]; 
+    return gorfbar(myObject);
+}
+- (void)privateMethod { }
+
+int S::gorfbar(MyClass * myObject) {
+    [myObject privateMethod]; 
+    [myObject privateMethod1]; 
+    return getMe + bar(myObject);
+}
+
+- (void)privateMethod1 {
+  getMe = getMe+1;
+}
+
+static int getMe;
+
+@end