Пример #1
0
 internal void RemoveNode(LibraryNode node)
 {
     lock (_updates) {
         _updates.Add(new KeyValuePair <UpdateType, LibraryNode>(UpdateType.Remove, node));
     }
     ApplyUpdates(false);
 }
Пример #2
0
 public Library(Guid libraryGuid)
 {
     _guid      = libraryGuid;
     _root      = new LibraryNode(null, String.Empty, String.Empty, LibraryNodeType.Package);
     _updates   = new List <KeyValuePair <UpdateType, LibraryNode> >();
     _searching = new SemaphoreSlim(1);
 }
Пример #3
0
 internal async void AddNode(LibraryNode node)
 {
     lock (_updates) {
         _updates.Add(new KeyValuePair <UpdateType, LibraryNode>(UpdateType.Add, node));
     }
     ApplyUpdates(false);
 }
Пример #4
0
        protected CommonLibraryNode(LibraryNode parent, IScopeNode scope, string namePrefix, IVsHierarchy hierarchy, uint itemId) :
            base(parent, GetLibraryNodeName(scope, namePrefix), namePrefix + scope.Name, scope.NodeType)
        {
            _ownerHierarchy = hierarchy;
            _fileId         = itemId;

            // Now check if we have all the information to navigate to the source location.
            if ((null != _ownerHierarchy) && (VSConstants.VSITEMID_NIL != _fileId))
            {
                if ((SourceLocation.Invalid != scope.Start) && (SourceLocation.Invalid != scope.End))
                {
                    _sourceSpan             = new TextSpan();
                    _sourceSpan.iStartIndex = scope.Start.Column - 1;
                    if (scope.Start.Line > 0)
                    {
                        _sourceSpan.iStartLine = scope.Start.Line - 1;
                    }
                    _sourceSpan.iEndIndex = scope.End.Column;
                    if (scope.End.Line > 0)
                    {
                        _sourceSpan.iEndLine = scope.End.Line - 1;
                    }
                    CanGoToSource = true;
                }
            }
            _scope = scope;
        }
Пример #5
0
 internal void RemoveNode(LibraryNode node)
 {
     lock (this) {
         _root = _root.Clone();
         _root.RemoveNode(node);
         _updateCount++;
     }
 }
Пример #6
0
 internal void RemoveNode(LibraryNode node)
 {
     lock (syncLock)
     {
         this.root = this.root.Clone();
         this.root.RemoveNode(node);
         this.updateCount++;
     }
 }
Пример #7
0
 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++;
     }
 }
Пример #8
0
        /// <summary>
        /// Called by derived class when a file has been parsed.  The caller should
        /// provide the LibraryTask received from the OnNewFile call and an IScopeNode
        /// which represents the contents of the library.
        ///
        /// It is safe to call this method from any thread.
        /// </summary>
        protected void FileParsed(LibraryTask task)
        {
            try
            {
                var project = task.ModuleID.Hierarchy.GetProject()?.GetCommonProject();
                if (project == null)
                {
                    return;
                }

                HierarchyNode fileNode = fileNode = project.NodeFromItemId(task.ModuleID.ItemID);
                HierarchyInfo parent;
                if (fileNode == null || !_hierarchies.TryGetValue(task.ModuleID.Hierarchy, out parent))
                {
                    return;
                }

                LibraryNode module = CreateFileLibraryNode(
                    parent.ProjectLibraryNode,
                    fileNode,
                    System.IO.Path.GetFileName(task.FileName),
                    task.FileName
                    );

                // TODO: Creating the module tree should be done lazily as needed
                // Currently we replace the entire tree and rely upon the libraries
                // update count to invalidate the whole thing.  We could do this
                // finer grained and only update the changed nodes.  But then we
                // need to make sure we're not mutating lists which are handed out.

                if (null != task.ModuleID)
                {
                    LibraryNode previousItem = null;
                    lock (_files)
                    {
                        if (_files.TryGetValue(task.ModuleID, out previousItem))
                        {
                            _files.Remove(task.ModuleID);
                            parent.ProjectLibraryNode.RemoveNode(previousItem);
                        }
                    }
                }
                parent.ProjectLibraryNode.AddNode(module);
                _library.Update();
                if (null != task.ModuleID)
                {
                    lock (_files)
                    {
                        _files.Add(task.ModuleID, module);
                    }
                }
            }
            catch (COMException)
            {
                // we're shutting down and can't get the project
            }
        }
Пример #9
0
        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();
                }
            }
        }
        /// <summary>
        /// Does a delete w/o checking if it's a non-meber item, for handling the
        /// transition from member item to non-member item.
        /// </summary>
        private void OnDeleteFile(IVsHierarchy hierarchy, HierarchyEventArgs args)
        {
            ModuleId    id   = new ModuleId(hierarchy, args.ItemID);
            LibraryNode node = null;

            lock (_files) {
                if (_files.TryGetValue(id, out node))
                {
                    _files.Remove(id);
                }
            }
            if (null != node)
            {
                _library.RemoveNode(node);
            }
        }
Пример #11
0
 /// <summary>
 /// Does a delete w/o checking if it's a non-meber item, for handling the
 /// transition from member item to non-member item.
 /// </summary>
 private void OnDeleteFile(IVsHierarchy hierarchy, HierarchyEventArgs args)
 {
     var id = new ModuleId(hierarchy, args.ItemID);
     LibraryNode node = null;
     lock (this._files)
     {
         if (this._files.TryGetValue(id, out node))
         {
             this._files.Remove(id);
             if (this._hierarchies.TryGetValue(hierarchy, out var parent))
             {
                 parent.ProjectLibraryNode.RemoveNode(node);
             }
         }
     }
     if (null != node)
     {
         this._library.RemoveNode(node);
     }
 }
Пример #12
0
        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);
            }
        }
Пример #13
0
 public virtual LibraryNode CreateFileLibraryNode(LibraryNode parent, HierarchyNode hierarchy, string name, string filename, LibraryNodeType libraryNodeType)
 {
     return(new LibraryNode(null, name, filename, libraryNodeType));
 }
Пример #14
0
 protected abstract LibraryNode CreateLibraryNode(LibraryNode parent, IScopeNode subItem, string namePrefix, IVsHierarchy hierarchy, uint itemid);
Пример #15
0
 public Library(Guid libraryGuid)
 {
     this._guid = libraryGuid;
     this._root = new LibraryNode(null, string.Empty, string.Empty, LibraryNodeType.Package);
 }
Пример #16
0
        private static SimpleObjectList <LibraryNode> SearchNodes(VSOBSEARCHCRITERIA2 srch, SimpleObjectList <LibraryNode> list, LibraryNode curNode)
        {
            foreach (var child in curNode.Children)
            {
                if (child.Name.IndexOf(srch.szName, StringComparison.OrdinalIgnoreCase) != -1)
                {
                    list.Children.Add(child.Clone(child.Name));
                }

                SearchNodes(srch, list, child);
            }
            return(list);
        }
Пример #17
0
        public int GetList2(uint ListType, uint flags, VSOBSEARCHCRITERIA2[] pobSrch, out IVsSimpleObjectList2 ppIVsSimpleObjectList2)
        {
            if ((flags & (uint)_LIB_LISTFLAGS.LLF_RESOURCEVIEW) != 0)
            {
                ppIVsSimpleObjectList2 = null;
                return(VSConstants.E_NOTIMPL);
            }

            ICustomSearchListProvider listProvider;

            if (pobSrch != null &&
                pobSrch.Length > 0)
            {
                if ((listProvider = pobSrch[0].pIVsNavInfo as ICustomSearchListProvider) != null)
                {
                    switch ((_LIB_LISTTYPE)ListType)
                    {
                    case _LIB_LISTTYPE.LLT_NAMESPACES:
                        ppIVsSimpleObjectList2 = listProvider.GetSearchList();
                        break;

                    default:
                        ppIVsSimpleObjectList2 = null;
                        return(VSConstants.E_FAIL);
                    }
                }
                else
                {
                    if (pobSrch[0].eSrchType == VSOBSEARCHTYPE.SO_ENTIREWORD && ListType == (uint)_LIB_LISTTYPE.LLT_MEMBERS)
                    {
                        string srchText = pobSrch[0].szName;
                        int    colonIndex;
                        if ((colonIndex = srchText.LastIndexOf(':')) != -1)
                        {
                            string filename = srchText.Substring(0, srchText.LastIndexOf(':'));
                            foreach (ProjectLibraryNode project in _root.Children)
                            {
                                foreach (var item in project.Children)
                                {
                                    if (item.FullName == filename)
                                    {
                                        ppIVsSimpleObjectList2 = item.DoSearch(pobSrch[0]);
                                        if (ppIVsSimpleObjectList2 != null)
                                        {
                                            return(VSConstants.S_OK);
                                        }
                                    }
                                }
                            }
                        }

                        ppIVsSimpleObjectList2 = null;
                        return(VSConstants.E_FAIL);
                    }
                    else if (pobSrch[0].eSrchType == VSOBSEARCHTYPE.SO_SUBSTRING && ListType == (uint)_LIB_LISTTYPE.LLT_NAMESPACES)
                    {
                        var lib = new LibraryNode(null, "Search results " + pobSrch[0].szName, "Search results " + pobSrch[0].szName, LibraryNodeType.Package);
                        foreach (var item in SearchNodes(pobSrch[0], new SimpleObjectList <LibraryNode>(), _root).Children)
                        {
                            lib.Children.Add(item);
                        }
                        ppIVsSimpleObjectList2 = lib;
                        return(VSConstants.S_OK);
                    }
                    else if ((pobSrch[0].grfOptions & (uint)_VSOBSEARCHOPTIONS.VSOBSO_LOOKINREFS) != 0 &&
                             ListType == (uint)_LIB_LISTTYPE.LLT_HIERARCHY)
                    {
                        LibraryNode node = pobSrch[0].pIVsNavInfo as LibraryNode;
                        if (node != null)
                        {
                            var refs = node.FindReferences();
                            if (refs != null)
                            {
                                ppIVsSimpleObjectList2 = refs;
                                return(VSConstants.S_OK);
                            }
                        }
                    }
                    ppIVsSimpleObjectList2 = null;
                    return(VSConstants.E_FAIL);
                }
            }
            else
            {
                ppIVsSimpleObjectList2 = _root as IVsSimpleObjectList2;
            }
            return(VSConstants.S_OK);
        }
Пример #18
0
 protected CommonLibraryNode(LibraryNode parent, string name, string fullName, IVsHierarchy hierarchy, uint itemId, LibraryNodeType type, IList <LibraryNode> children = null) :
     base(parent, name, fullName, type, children: children)
 {
     _ownerHierarchy = hierarchy;
     _fileId         = itemId;
 }
Пример #19
0
 public Library(Guid libraryGuid)
 {
     _guid = libraryGuid;
     _root = new LibraryNode(null, String.Empty, String.Empty, LibraryNodeType.Package);
 }
Пример #20
0
 public NodeFileLibraryNode(LibraryNode parent, HierarchyNode hierarchy, string name, string filename, LibraryNodeType libraryNodeType)
     : base(parent, name, filename, libraryNodeType)
 {
 }