Patch #3345 2012-10-06 15:35

koonschi

Added code completion of declarations in for/if/while heads
Download
3345-Added_code_com.patch (9.3 KB)
Category
Application::Refinement
Status
Accepted
Close date
2012-12-21 07:41
Assigned to
ollydbg
Index: plugins/codecompletion/parser/parserthread.cpp
===================================================================
--- plugins/codecompletion/parser/parserthread.cpp    (revision 8431)
+++ plugins/codecompletion/parser/parserthread.cpp    (working copy)
@@ -666,7 +666,8 @@
                 if (!m_Options.useBuffer || m_Options.bufferSkipBlocks)
                     SkipToOneOfChars(ParserConsts::semicolonclbrace, true, true);
                 else
-                    m_Tokenizer.GetToken(); // skip arguments
+                    HandleConditionalArguments();
+
                 m_Str.Clear();
             }
             else
@@ -682,7 +683,8 @@
                 if (!m_Options.useBuffer || m_Options.bufferSkipBlocks)
                     SkipToOneOfChars(ParserConsts::semicolonclbrace, true, true);
                 else
-                    m_Tokenizer.GetToken(); // skip arguments
+                    HandleForLoopArguments();
+
                 m_Str.Clear();
             }
             else
@@ -727,7 +729,8 @@
                 if (!m_Options.useBuffer || m_Options.bufferSkipBlocks)
                     SkipToOneOfChars(ParserConsts::semicolonclbrace, true, true);
                 else
-                    m_Tokenizer.GetToken(); // skip arguments
+                    HandleConditionalArguments();
+
                 m_Str.Clear();
             }
             else if (token == ParserConsts::kw_const)
@@ -2070,6 +2073,188 @@
     }
 }
 
+void ParserThread::HandleConditionalArguments()
+{
+    // if these aren't empty at this point, we have a syntax error
+    if (!m_Str.empty())
+        return;
+
+    if (!m_PointerOrRef.empty())
+        return;
+
+    if (!m_TemplateArgument.empty())
+        return;
+
+    // conditional arguments can look like this:
+    // (int i = 12)
+    // (Foo *bar = getFooBar())
+    // (var <= 12 && (getType() != 23))
+    wxString args = m_Tokenizer.GetToken();
+
+    // remove braces
+    if (args.StartsWith(_T("(")))
+        args = args.Mid(1, args.length() - 1);
+
+    if (args.EndsWith(_T(")")))
+        args = args.Mid(0, args.length() - 1);
+
+    // parse small tokens inside for loop head
+    TokenTree tree;
+    wxString fileName = m_Tokenizer.GetFilename();
+    Tokenizer smallTokenizer(&tree);
+
+    smallTokenizer.InitFromBuffer(args, fileName, m_Tokenizer.GetLineNumber());
+
+    while (IS_ALIVE)
+    {
+        wxString token = smallTokenizer.GetToken();
+        if (token.empty())
+            break;
+
+        wxString peek = smallTokenizer.PeekToken();
+
+        if (peek.empty())
+        {
+            if (!m_Str.empty())
+            {
+                // remove template argument if there is one
+                wxString varType, templateArgs;
+                RemoveTemplateArgs(m_Str, varType, templateArgs);
+
+                m_Str = varType;
+                m_TemplateArgument = templateArgs;
+
+                Token *newToken = DoAddToken(tkVariable, token, smallTokenizer.GetLineNumber());
+                if (newToken && !m_TemplateArgument.IsEmpty())
+                {
+                    ResolveTemplateArgs(newToken);
+                }
+                else
+                {
+                    TRACE(_T("HandleConditionalArguments() : Unable to create/add new token: ") + token);
+                }
+            }
+
+            break;
+        }
+        else
+        {
+            if (token == ParserConsts::ref_chr || token == ParserConsts::ptr_chr)
+            {
+                m_PointerOrRef << token;
+            }
+            else
+            {
+                if (!m_Str.empty())
+                    m_Str << _T(" ");
+
+                m_Str << token;
+            }
+        }
+    }
+
+    m_Str.clear();
+    m_PointerOrRef.clear();
+    m_TemplateArgument.clear();
+}
+
+void ParserThread::HandleForLoopArguments()
+{
+    // if these aren't empty at this point, we have a syntax error
+    if (!m_Str.empty())
+        return;
+
+    if (!m_PointerOrRef.empty())
+        return;
+
+    if (!m_TemplateArgument.empty())
+        return;
+
+    // for loop heads look like this:
+    // ([init1 [, init2 ...] ] ; [cond1 [, cond2 ..]]; [mod1 [, mod2 ..]])
+    wxString args = m_Tokenizer.GetToken();
+
+    // remove braces
+    if (args.StartsWith(_T("(")))
+        args = args.Mid(1, args.length() - 1);
+    if (args.EndsWith(_T(")")))
+        args = args.Mid(0, args.length() - 1);
+
+    // parse small tokens inside for loop head
+    TokenTree tree;
+    wxString fileName = m_Tokenizer.GetFilename();
+    Tokenizer smallTokenizer(&tree);
+
+    smallTokenizer.InitFromBuffer(args, fileName, m_Tokenizer.GetLineNumber());
+
+    while (IS_ALIVE)
+    {
+        wxString token = smallTokenizer.GetToken();
+        if (token.empty())
+            break;
+
+        wxString peek = smallTokenizer.PeekToken();
+
+        bool createNewToken = false;
+        bool finished = false;
+
+        if (peek == ParserConsts::comma)
+        {
+
download for full patch...
koonschi 2012-10-06 15:40

Added some whitespaces to meet the coding conventions

koonschi 2012-10-07 10:36

Templated declarations are now recognized correctly

koonschi 2012-10-07 10:45

Removed tabs and replaced them with whitespaces

koonschi 2012-10-09 09:59

Comments corrected

ollydbg 2012-10-10 09:50

Looks good to me, but I need more time to test it.

mortenmacfly 2012-12-16 14:48

...just for the record, testing, too (for some weeks now) - no issues so far.

ollydbg 2012-12-21 07:41

Applied in the trunk rev 8700. Thanks.