internal void AddNode(LibraryNode node) { lock (this) { // re-create root node here because we may have handed out the node before and don't want to mutate it's list. _root = _root.Clone(); _root.AddNode(node); _updateCount++; } }
private LibraryNode ParseEnum() { int enumStartLine = start.line; int enumStartCol = start.col; string ename = ExpectID(); LibraryNode enode = new LibraryNode(ename, LibraryNode.LibraryNodeType.Classes, moduleId); enode.StartLine = enumStartLine; enode.StartCol = enumStartCol; if (ename == "CHAIN_ACTIONID") { Console.WriteLine("asd"); } Expect('{'); while (_token != '}' && _token > 0) { int memberStartLine = start.line; int memberStartCol = start.col; int memberEndLine = end.line; int memberEndCol = end.col; string mname = ExpectID(); LibraryNode mnode = new LibraryNode(mname, LibraryNode.LibraryNodeType.Members, moduleId); mnode.StartLine = memberStartLine; mnode.StartCol = memberStartCol; if (_token == '=') { Lex(); memberEndLine = end.line; memberEndCol = end.col; string type = ExpectScalar(); } mnode.EndLine = memberEndLine; mnode.EndCol = memberEndCol; if (_token == ',') { Lex(); } //if (_token != '}') //{ //Expect(','); //} enode.AddNode(mnode); } enode.EndLine = end.line; enode.EndCol = end.col; Expect('}'); return(enode); }
private LibraryNode ParseFunction(bool isconstructor) { int funcStartLine = start.line; int funcStartCol = start.col; string fname = isconstructor ? "constructor" : ExpectID(); LibraryNode fnode = new LibraryNode(fname, LibraryNode.LibraryNodeType.Members, moduleId); fnode.StartLine = funcStartLine; fnode.StartCol = funcStartCol; if (_token == (int)Token.DOUBLE_COLON) { Expect((int)Token.DOUBLE_COLON); fnode.NodeType = LibraryNode.LibraryNodeType.Classes; fnode.AddNode(ParseFunction(false)); } else { Expect('('); while (_token != ')' && _token > 0) { /*string vname = ExpectID(); // ignoring function params for now - josh * if (_token != ')') * Expect(',');*/ Lex(); } Expect(')'); if (_token == ':') { Lex(); Expect('('); while (_token != ')' && _token > 0) { /*string vname = ExpectID(); // ignoring function params for now - josh * if (_token != ')') * Expect(',');*/ Lex(); } Expect(')'); } if (_token != '{') { SkipToEndOfTheLine(); } lastclosingbrace = MatchBraces('{', '}'); } fnode.EndLine = lastclosingbrace.line; fnode.EndCol = lastclosingbrace.col; return(fnode); }
void ShowInFindResultWindow(FileModel fileModel, NSpan span, Location[] locations) { Microsoft.VisualStudio.Shell.ThreadHelper.ThrowIfNotOnUIThread(); CheckDisposed(); if (locations.Length == 0) { return; } if (locations.Length == 1) { GoToLocation(fileModel, locations[0]); return; } var findSvc = (IVsFindSymbol)fileModel.Server.ServiceProvider.GetService(typeof(SVsObjectSearch)); Debug.Assert(findSvc != null); var caption = _wpfTextView.TextBuffer.CurrentSnapshot.GetText(VsUtils.Convert(span)); var libSearchResults = new LibraryNode("<Nitra>", LibraryNode.LibraryNodeType.References, LibraryNode.LibraryNodeCapabilities.None, null); foreach (var location in locations) { var inner = new GotoInfoLibraryNode(location, caption, fileModel.Server); libSearchResults.AddNode(inner); } var package = NitraCommonVsPackage.Instance; package.SetFindResult(libSearchResults); var criteria = new[] { new VSOBSEARCHCRITERIA2 { eSrchType = VSOBSEARCHTYPE.SO_ENTIREWORD, grfOptions = (uint)_VSOBSEARCHOPTIONS.VSOBSO_CASESENSITIVE, szName = "<dummy>", dwCustom = Library.FindAllReferencesMagicNum, } }; var scope = Library.MagicGuid; var hr = findSvc.DoSearch(ref scope, criteria); }
/// <summary> /// Реализация Find All References поиска всех вхождений (в перспективе включая поиск и по не-Nemerle проектам) /// с заполнением окошка "Find Symbol Results" студии /// </summary> /// <remarks> /// Вызываем Source.Goto, и подготавливаем результаты поиска /// Потом передаём уже готовые результаты поиска в _library через метод NemerleLibraryManager /// Затем вызываем IVsObjectSearch.Find - интерфейс отвечающий за поиски, который найдёт и вызовет _library.GetList2(), /// IVsObjectSearch в свою очередь должен поискать и в остальных проектах (пока не реализовано, т.к. нет чёткого понятия какими должны быть VSOBSEARCHCRITERIA), /// и вывести все результаты поиска в окошке Find Symbol Results (уже выводит) /// /// Обсуждения в форумах по теме: /// http://social.msdn.microsoft.com/Forums/en-US/vsx/thread/951158dd-fc98-4325-b07d-bab65b372603/ /// http://social.msdn.microsoft.com/Forums/en-US/vsx/thread/793f916d-80a6-4944-b058-7166d48d3a32 /// http://social.msdn.microsoft.com/Forums/en-US/vsx/thread/3d85e968-f735-420c-b9c8-d57ed7839d36 /// /// Возможно для поиска по всему проекту IVsObjectSearch.Find придётся заменить на IVsFindSymbol.DoSearch /// http://msdn.microsoft.com/en-us/library/microsoft.visualstudio.shell.interop.ivsfindsymbol.dosearch.aspx /// есть какая-то инфа про глюки в методе Find /// http://social.msdn.microsoft.com/Forums/en-US/vsx/thread/08b71611-2c94-40e7-a79e-3be843c974ea/ /// </remarks> private void FindReferences() { int line, col; // Get the caret position ErrorHandler.ThrowOnFailure(this.TextView.GetCaretPos(out line, out col)); var findSvc = (IVsFindSymbol)Source.Service.GetService(typeof(SVsObjectSearch)); //IVsNavInfo navInfo; if (findSvc != null) { string caption; var infos = Source.GetGotoInfo(TextView, false, line, col, out caption); if ((infos != null) && (infos.Length > 0)) { var criteria = new[] { new VSOBSEARCHCRITERIA2 { eSrchType = VSOBSEARCHTYPE.SO_ENTIREWORD, grfOptions = (uint)_VSOBSEARCHOPTIONS.VSOBSO_CASESENSITIVE, szName = "<dummy>", dwCustom = Library.FindAllReferencesMagicNum, } }; var inlm = Source.Service.GetService(typeof(INemerleLibraryManager)); if (inlm != null) { var nlm = (NemerleLibraryManager)inlm; var libSearchResults = new LibraryNode("<dummy2>", LibraryNode.LibraryNodeType.References, LibraryNode.LibraryNodeCapabilities.None, null); foreach (var i in infos) { var inner = new GotoInfoLibraryNode((NemerleLanguageService)Source.LanguageService, i, caption); libSearchResults.AddNode(inner); } nlm.OnFindAllReferencesDone(libSearchResults); var scope = NemerleLibraryManager.LibraryGuid; var hr = findSvc.DoSearch(ref scope, criteria); } } } }
private void RemoveGlobalNode(ref LibraryNode node) { foreach (LibraryNode child in node.Children) { if (child.NodeType == LibraryNode.LibraryNodeType.Package) { LibraryNode globalnode = new LibraryNode(child); node.RemoveNode(child); foreach (LibraryNode gchild in globalnode.Children) { node.AddNode(gchild); } break; } } }
void ShowInFindResultWindow(FileModel fileModel, NSpan span, Location[] locations) { CheckDisposed(); if (locations.Length == 1) { GoToLocation(fileModel, locations[0]); return; } var findSvc = (IVsObjectSearch)fileModel.Server.ServiceProvider.GetService(typeof(SVsObjectSearch)); Debug.Assert(findSvc != null); var caption = _wpfTextView.TextBuffer.CurrentSnapshot.GetText(VsUtils.Convert(span)); var libSearchResults = new LibraryNode("<Nitra>", LibraryNode.LibraryNodeType.References, LibraryNode.LibraryNodeCapabilities.None, null); foreach (var location in locations) { var inner = new GotoInfoLibraryNode(location, caption, fileModel.Server); libSearchResults.AddNode(inner); } var package = NitraCommonVsPackage.Instance; package.SetFindResult(libSearchResults); var criteria = new[] { new VSOBSEARCHCRITERIA { eSrchType = VSOBSEARCHTYPE.SO_ENTIREWORD, grfOptions = (uint)_VSOBSEARCHOPTIONS.VSOBSO_CASESENSITIVE, szName = "<dummy>", dwCustom = Library.FindAllReferencesMagicNum, } }; IVsObjectList results; var hr = findSvc.Find((uint)__VSOBSEARCHFLAGS.VSOSF_EXPANDREFS, criteria, out results); }
private void ApplyUpdates(bool assumeLockHeld) { if (!assumeLockHeld) { if (!_searching.Wait(0)) { // Didn't get the lock immediately, which means we are // currently searching. Once the search is done, updates // will be applied. return; } } try { lock (_updates) { if (_updates.Count == 0) { return; } // re-create root node here because we may have handed out // the node before and don't want to mutate it's list. _root = _root.Clone(); _updateCount += 1; foreach (var kv in _updates) { switch (kv.Key) { case UpdateType.Add: _root.AddNode(kv.Value); break; case UpdateType.Remove: _root.RemoveNode(kv.Value); break; default: Debug.Fail("Unsupported update type " + kv.Key.ToString()); break; } } _updates.Clear(); } } finally { if (!assumeLockHeld) { _searching.Release(); } } }
private void MergeFileNode(LibraryNode node, ref LibraryNode result) { for (int i = 0; i < node.Children.Count; i++) { bool found = false; LibraryNode nodechild = node.Children[i]; for (int j = 0; j < result.Children.Count; j++) { LibraryNode resultchild = result.Children[j]; if (nodechild.Name == resultchild.Name) { found = true; MergeFileNode(nodechild, ref resultchild); } } if (!found) { result.AddNode(nodechild); } } }
private void CreateModuleTree(LibraryNode root, LibraryNode current, IScopeNode scope, string namePrefix, ModuleId moduleId) { if ((null == root) || (null == scope) || (null == scope.NestedScopes)) { return; } foreach (IScopeNode subItem in scope.NestedScopes) { LibraryNode newNode = CreateLibraryNode(subItem, namePrefix, moduleId.Hierarchy, moduleId.ItemID); string newNamePrefix = namePrefix; // The classes are always added to the root node, the functions to the // current node. if ((newNode.NodeType & LibraryNode.LibraryNodeType.Members) != LibraryNode.LibraryNodeType.None) { current.AddNode(newNode); } else if ((newNode.NodeType & LibraryNode.LibraryNodeType.Classes) != LibraryNode.LibraryNodeType.None) { // Classes are always added to the root. root.AddNode(newNode); newNamePrefix = newNode.Name + "."; } // Now use recursion to get the other types. CreateModuleTree(root, newNode, subItem, newNamePrefix, moduleId); } }
private void CreateModuleTree(LibraryNode current, IScopeNode scope, string namePrefix, ModuleId moduleId) { if ((null == scope) || (null == scope.NestedScopes)) { return; } foreach (IScopeNode subItem in scope.NestedScopes) { LibraryNode newNode = CreateLibraryNode(current, subItem, namePrefix, moduleId.Hierarchy, moduleId.ItemID); string newNamePrefix = namePrefix; current.AddNode(newNode); if ((newNode.NodeType & LibraryNodeType.Classes) != LibraryNodeType.None) { newNamePrefix = namePrefix + newNode.Name + "."; } // Now use recursion to get the other types. CreateModuleTree(newNode, subItem, newNamePrefix, moduleId); } }
public LibraryNode Parse(LibraryTask task) { this.filename = task.FileName; this.moduleId = task.ModuleID; LibraryNode filenode = new LibraryNode(System.IO.Path.GetFileName(filename), LibraryNode.LibraryNodeType.PhysicalContainer, moduleId); LibraryNode globalnode = new LibraryNode("(Global Scope)", LibraryNode.LibraryNodeType.Package, moduleId); start = new SourceLocation(0, 0); end = new SourceLocation(0, 0); globalnode.StartLine = start.line; globalnode.StartCol = start.col; filenode.AddNode(globalnode); try { if (task.Text == null) { lexer.SetSource(File.ReadAllText(filename), 0); } else { lexer.SetSource(task.Text, 0); } Lex(); while (_token > 0 && !lexer.IsEob()) { try { switch (_token) { case (int)Token.FUNCTION: Lex(); if (_token == '(') // ignoring function literals for now - josh { MatchBraces('{', '}'); } else { LibraryNode fnode = ParseFunction(false); if (fnode.NodeType == LibraryNode.LibraryNodeType.Members) { globalnode.AddNode(fnode); } else { filenode.AddNode(fnode); } } break; case (int)Token.DOUBLE_COLON: Lex(); continue; case (int)Token.IDENTIFIER: LibraryNode inode = ParseClassOrTable(true); if (inode != null) { globalnode.AddNode(inode); } /* * else * { * SkipToEndOfTheLine(); * } */ break; case (int)Token.CLASS: Lex(); filenode.AddNode(ParseClassOrTable(false)); break; case (int)Token.ENUM: Lex(); LibraryNode enode = ParseEnum(); globalnode.AddNode(enode); break; case (int)Token.LINE_COMMENT: Lex(); break; default: SkipToEndOfTheLine(); break; } } catch (Exception e) { if (parselogging) { logger.Log(filename + ": " + e.Message); } Lex(); } } } catch (Exception e) { if (parselogging) { logger.Log("cannot read " + filename + ": " + e.Message); } } if (filenode.Children[0].Children.Count == 0) { filenode.RemoveNode(filenode.Children[0]); } globalnode.EndLine = end.line; globalnode.EndCol = end.col; return(filenode); }
private SourceLocation MatchClassBraces(LibraryNode parent) { if (_token == (int)Token.ATTR_OPEN) { Lex(); } Expect('{'); int bracecount = 1; SourceLocation closingbrace = new SourceLocation(); while (bracecount != 0 && _token > 0) { if (_token == '{') { bracecount++; } if (_token == '}') { bracecount--; } if (bracecount == 0) { closingbrace = end; } switch (_token) { case (int)Token.IDENTIFIER: string symname = ExpectID(); if (_token == '=') { Lex(); if (_token == '{') { LibraryNode sn = new LibraryNode(symname, LibraryNode.LibraryNodeType.Classes, moduleId); sn.StartLine = start.line; sn.StartCol = start.col; SourceLocation endbrace = MatchClassBraces(sn); sn.EndLine = endbrace.line; sn.EndCol = endbrace.col; parent.AddNode(sn); } else { Lex(); } } break; case (int)Token.FUNCTION: Lex(); if (_token == '(') // ignoring function literals for now - josh { MatchBraces('{', '}'); } else { parent.AddNode(ParseFunction(false)); } break; case (int)Token.CONSTRUCTOR: Lex(); parent.AddNode(ParseFunction(true)); break; case (int)Token.ENUM: Lex(); parent.AddNode(ParseEnum()); break; default: Lex(); break; } } return(closingbrace); }
private LibraryNode ParseClassOrTable(bool istable) { if (_token == (int)Token.DOUBLE_COLON) { Lex(); } int classStartLine = start.line; int classStartCol = start.col; string cname = ExpectID(); LibraryNode ret = new LibraryNode(cname, LibraryNode.LibraryNodeType.Classes, moduleId); ret.StartLine = classStartLine; ret.StartCol = classStartCol; LibraryNode scope = ret; while (_token == '.' && _token > 0) { Lex(); int subclassStartLine = start.line; int subclassStartCol = start.col; cname = ExpectID(); LibraryNode ns = new LibraryNode(cname, LibraryNode.LibraryNodeType.Classes, moduleId); ns.StartLine = subclassStartLine; ns.StartCol = subclassStartCol; ns.EndLine = end.line; ns.EndCol = end.col; scope.AddNode(ns); scope = ns; } if (_token == '(') { MatchBraces('(', ')'); return(null); } if (_token == '[') { MatchBraces('[', ']'); if (_token == (int)Token.NEWSLOT) { Lex(); if (_token == '{' || _token == (int)Token.CLASS) { MatchBraces('{', '}'); } } return(null); } bool assignmentflag = true; if (istable) { if (_token == (int)Token.NEWSLOT || _token == '=') { Lex(); if (_token == '[') { lastclosingbrace = MatchArrayBraces(); ret.EndLine = lastclosingbrace.line; ret.EndCol = lastclosingbrace.col; return(ret); } if (_token == (int)Token.CLASS) { Lex(); if (_token == (int)Token.EXTENDS) { Lex(); //lex extends while (_token == (int)Token.IDENTIFIER || _token == '.') { Lex(); //lexes the base class } } lastclosingbrace = MatchClassBraces(scope); ret.EndLine = lastclosingbrace.line; ret.EndCol = lastclosingbrace.col; return(ret); } if (_token == (int)Token.FUNCTION) { Lex(); if (_token == '(') // ignoring function literals for now - josh { MatchBraces('{', '}'); } return(null); } if (_token != '{') { return(null); } } else { assignmentflag = false; } } else { if (_token == (int)Token.EXTENDS) { while (_token != '{' && _token > 0) { Lex(); } // ignoring base classes for now - josh /* * Lex(); * if (_token == (int)Token.DOUBLE_COLON) Lex(); * string basename = ExpectID(); * while (_token == '.') * { * Lex(); * basename = ExpectID(); * } */ } } if (!assignmentflag) { return(null); } lastclosingbrace = MatchClassBraces(scope); if (_token == ',') { Lex(); } ret.EndLine = lastclosingbrace.line; ret.EndCol = lastclosingbrace.col; return(ret); }