]> granicus.if.org Git - clang/commitdiff
When in code-completion, skip obj-c method bodies for speed up.
authorArgyrios Kyrtzidis <akyrtzi@gmail.com>
Mon, 3 Jan 2011 22:33:06 +0000 (22:33 +0000)
committerArgyrios Kyrtzidis <akyrtzi@gmail.com>
Mon, 3 Jan 2011 22:33:06 +0000 (22:33 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@122781 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/Parse/Parser.h
lib/Parse/ParseObjc.cpp
lib/Parse/ParseStmt.cpp
lib/Sema/SemaDecl.cpp
test/Index/complete-synthesized.m

index f523bed9761a16b0e851560115945cbabea50110..80e4626536b90d9feb5fb99ca2751aa3add7046e 100644 (file)
@@ -1262,6 +1262,12 @@ private:
   Decl *ParseFunctionStatementBody(Decl *Decl);
   Decl *ParseFunctionTryBlock(Decl *Decl);
 
+  /// \brief When in code-completion, skip parsing of the function/method body
+  /// unless the body contains the code-completion point.
+  ///
+  /// \returns true if the function body was skipped.
+  bool MaybeSkipFunctionBodyForCodeCompletion();
+
   bool ParseImplicitInt(DeclSpec &DS, CXXScopeSpec *SS,
                         const ParsedTemplateInfo &TemplateInfo,
                         AccessSpecifier AS);
index c48f6803b01ce3007da5686303b0c31f04e33d22..25829e8975fb7bb7c2e8af1652b48374ad836e54 100644 (file)
@@ -1718,6 +1718,9 @@ Decl *Parser::ParseObjCMethodDefinition() {
   // specified Declarator for the method.
   Actions.ActOnStartOfObjCMethodDef(getCurScope(), MDecl);
 
+  if (MaybeSkipFunctionBodyForCodeCompletion())
+    return Actions.ActOnFinishFunctionBody(MDecl, 0);
+
   StmtResult FnBody(ParseCompoundStatementBody());
 
   // If the function body could not be parsed, make a bogus compoundstmt.
index d25cc110a8a8c3f31921b6316abeeffa2c796798..28b140e731bb986cb0d77fe5227685f51d7ea515 100644 (file)
@@ -1466,18 +1466,8 @@ Decl *Parser::ParseFunctionStatementBody(Decl *Decl) {
   assert(Tok.is(tok::l_brace));
   SourceLocation LBraceLoc = Tok.getLocation();
 
-  // When in code-completion, skip parsing for all function bodies unless
-  // the body contains the code-completion point.
-  if (PP.isCodeCompletionEnabled()) {
-    TentativeParsingAction PA(*this);
-    ConsumeBrace();
-    if (SkipUntil(tok::r_brace, /*StopAtSemi=*/false, /*DontConsume=*/false,
-                  /*StopAtCodeCompletion=*/true)) {
-      PA.Commit();
-      return Actions.ActOnFinishFunctionBody(Decl, 0);
-    }
-    PA.Revert();
-  }
+  if (MaybeSkipFunctionBodyForCodeCompletion())
+    return Actions.ActOnFinishFunctionBody(Decl, 0);
 
   PrettyDeclStackTraceEntry CrashInfo(Actions, Decl, LBraceLoc,
                                       "parsing function body");
@@ -1511,6 +1501,9 @@ Decl *Parser::ParseFunctionTryBlock(Decl *Decl) {
   if (Tok.is(tok::colon))
     ParseConstructorInitializer(Decl);
 
+  if (MaybeSkipFunctionBodyForCodeCompletion())
+    return Actions.ActOnFinishFunctionBody(Decl, 0);
+
   SourceLocation LBraceLoc = Tok.getLocation();
   StmtResult FnBody(ParseCXXTryBlockCommon(TryLoc));
   // If we failed to parse the try-catch, we just give the function an empty
@@ -1522,6 +1515,26 @@ Decl *Parser::ParseFunctionTryBlock(Decl *Decl) {
   return Actions.ActOnFinishFunctionBody(Decl, FnBody.take());
 }
 
+bool Parser::MaybeSkipFunctionBodyForCodeCompletion() {
+  assert(Tok.is(tok::l_brace));
+
+  if (!PP.isCodeCompletionEnabled())
+    return false;
+
+  // We're in code-completion mode. Skip parsing for all function bodies unless
+  // the body contains the code-completion point.
+  TentativeParsingAction PA(*this);
+  ConsumeBrace();
+  if (SkipUntil(tok::r_brace, /*StopAtSemi=*/false, /*DontConsume=*/false,
+                /*StopAtCodeCompletion=*/true)) {
+    PA.Commit();
+    return true;
+  }
+
+  PA.Revert();
+  return false;
+}
+
 /// ParseCXXTryBlock - Parse a C++ try-block.
 ///
 ///       try-block:
index dc851a3e8365aa6bb26fa9595bf76a58406e6367..1c03f7d7f77ae17f158c1f63c4ad315200174a9b 100644 (file)
@@ -5415,7 +5415,8 @@ Decl *Sema::ActOnFinishFunctionBody(Decl *dcl, Stmt *Body,
   } else if (ObjCMethodDecl *MD = dyn_cast_or_null<ObjCMethodDecl>(dcl)) {
     assert(MD == getCurMethodDecl() && "Method parsing confused");
     MD->setBody(Body);
-    MD->setEndLoc(Body->getLocEnd());
+    if (Body)
+      MD->setEndLoc(Body->getLocEnd());
     if (!MD->isInvalidDecl()) {
       DiagnoseUnusedParameters(MD->param_begin(), MD->param_end());
       DiagnoseSizeOfParametersAndReturnValue(MD->param_begin(), MD->param_end(),
index a97eeab8cbd02d4ec2c6c2a5e713d367108e9493..2c26d36a34459205516b3883ce26d2c5eece5624 100644 (file)
@@ -51,6 +51,6 @@
 // RUN: c-index-test -code-completion-at=%s:34:2 -Xclang -fobjc-nonfragile-abi2 %s | FileCheck -check-prefix=CHECK-CC3 %s
 // CHECK-CC3: NotImplemented:{TypedText _Bool} (50)
 // CHECK-CC3: ObjCIvarDecl:{ResultType float}{TypedText _prop2} (35)
-// CHECK-CC3: ObjCIvarDecl:{ResultType double}{TypedText prop4}
+// CHECK-CC3: ObjCPropertyDecl:{ResultType double}{TypedText prop4}
 // CHECK-CC3-NOT: ObjCPropertyDecl:{ResultType double}{TypedText prop4} (35)
 // CHECK-CC1: restrict