public override List<FilePositionSpan> Search(SearchContentsData searchContentsData) { if (searchContentsData.ParsedSearchString.MainEntry.Text.Length > ByteLength) return NoSpans; var algo = searchContentsData.GetSearchAlgorithms(searchContentsData.ParsedSearchString.MainEntry).AsciiStringSearchAlgo; // TODO(rpaquay): We are limited to 2GB for now. var result = algo.SearchAll(Pointer, (int)ByteLength); if (searchContentsData.ParsedSearchString.EntriesBeforeMainEntry.Count == 0 && searchContentsData.ParsedSearchString.EntriesAfterMainEntry.Count == 0) { return result.ToList(); } return FilterOnOtherEntries(searchContentsData, result).ToList(); }
private static FileSearchResult MatchFileContents(FileData fileData, SearchContentsData searchContentsData, TaskResultCounter taskResultCounter) { var spans = fileData.Contents.Search(searchContentsData); if (spans.Count == 0) { return(null); } taskResultCounter.Add(spans.Count); return(new FileSearchResult { FileName = fileData.FileName, Spans = spans }); }
private IEnumerable<FilePositionSpan> FilterOnOtherEntries(SearchContentsData searchContentsData, IEnumerable<FilePositionSpan> matches) { FindEntryFunction findEntry = (position, length, entry) => { var algo = searchContentsData.GetSearchAlgorithms(searchContentsData.ParsedSearchString.MainEntry).UTF16StringSearchAlgo; // TODO(rpaquay): Do we need to take into account sizeof(char) == 2? var start = Pointers.AddPtr(this.Pointer, position); var result = algo.Search(start, length); if (result == IntPtr.Zero) return -1; return position + Pointers.Offset32(start, result); }; GetLineExtentFunction getLineExtent = position => { int lineStart; int lineLength; NativeMethods.UTF16_GetLineExtentFromPosition(Pointer, (int)CharacterCount, position, out lineStart, out lineLength); return new FilePositionSpan { Position = lineStart, Length = lineLength }; }; return new TextSourceTextSearch(getLineExtent, findEntry).FilterOnOtherEntries(searchContentsData.ParsedSearchString, matches); }
public SearchFileContentsResult SearchFileContents(SearchParams searchParams) { var parsedSearchString = _searchStringParser.Parse(searchParams.SearchString ?? ""); // Don't search empty or very small strings -- no significant results. if (string.IsNullOrWhiteSpace(parsedSearchString.MainEntry.Text) || (parsedSearchString.MainEntry.Text.Length < MinimumSearchPatternLength)) { return(SearchFileContentsResult.Empty); } using (var searchContentsData = new SearchContentsData(parsedSearchString, CreateSearchAlgorithms(parsedSearchString, searchParams.MatchCase))) { // taskCancellation is used to make sure we cancel previous tasks as // fast as possible to avoid using too many CPU resources if the caller // keeps asking us to search for things. Note that this assumes the // caller is only interested in the result of the *last* query, while // the previous queries will throw an OperationCanceled exception. _taskCancellation.CancelAll(); var cancellationToken = _taskCancellation.GetNewToken(); return(DoSearchFileContents(searchContentsData, searchParams.MaxResults, cancellationToken)); } }
private SearchFileContentsResult DoSearchFileContents(SearchContentsData searchContentsData, int maxResults, CancellationToken cancellationToken) { var taskResults = new TaskResultCounter(maxResults); var searchedFileCount = 0; var matches = _currentFileDatabase.FilesWithContents .AsParallel() .WithExecutionMode(ParallelExecutionMode.ForceParallelism) .WithCancellation(cancellationToken) .Where(x => !taskResults.Done) .Select(item => { Interlocked.Increment(ref searchedFileCount); return(MatchFileContents(item, searchContentsData, taskResults)); }) .Where(r => r != null) .ToList(); return(new SearchFileContentsResult { Entries = matches, SearchedFileCount = searchedFileCount, TotalFileCount = _currentFileDatabase.FilesWithContents.Count, HitCount = taskResults.Count, }); }
public override List<FilePositionSpan> Search(SearchContentsData searchContentsData) { if (ReferenceEquals(this, _empty)) return NoSpans; // TODO(rpaquay): Maybe we will need this someday. For now, we use this class only for empty file content placeholder. throw new NotImplementedException(); #if false Logger.Log("Searching file contents"); List<FilePositionSpan> result = null; var index = 0; while (true) { var newIndex = _text.IndexOf(searchContentsData.Text, index, StringComparison.Ordinal); if (newIndex < 0) break; if (result == null) { result = new List<FilePositionSpan>(); } result.Add(newIndex); index = newIndex + searchContentsData.Text.Length; } return result ?? NoPositions; #endif }
public virtual List<FilePositionSpan> Search(SearchContentsData searchContentsData) { return NoSpans; }