/// <summary>
        /// Perform a bulk update of a collection of <see cref="Completion"/> instances to match the values
        /// contained in a pair of source collections.
        /// </summary>
        /// <remarks>The <see cref="Completion"/> instances in <paramref name="sourceCompletions"/> and
        /// <paramref name="secondSourceCompletions"/> are merged and sorted using
        /// <see cref="CompletionDisplayTextComparer.Default"/>.
        ///
        /// <list type="bullet">
        ///     <item>Any items present in <paramref name="result"/> but not present in the merged collection are
        /// removed from <paramref name="result"/>.</item>
        ///     <item>Any items not already present in <paramref name="result"/> are inserted at the correct
        /// location.</item>
        /// </list>
        ///
        /// <note type="caller">The <paramref name="result"/> collection is assumed to already be sorted
        /// according to <see cref="CompletionDisplayTextComparer.Default"/> before this method is called.</note>
        /// </remarks>
        /// <param name="result">The collection holding the merged result.</param>
        /// <param name="sourceCompletions">The collection of <see cref="Completion"/> instances from the first
        /// source.</param>
        /// <param name="secondSourceCompletions">The collection of <see cref="Completion"/> instances from the
        /// second source.</param>
        private static void UpdateCompletionList(BulkObservableCollection <Completion> result,
                                                 IEnumerable <Completion> sourceCompletions, IEnumerable <Completion> secondSourceCompletions)
        {
            try
            {
                result.BeginBulkOperation();

                // SortedSet<Completion> provides for immediate sorting, and also allows Contains() to be used
                // below instead of a manual call to CompletionDisplayTextComparer.Compare().
                SortedSet <Completion> filteredCompletions = new SortedSet <Completion>(CompletionDisplayTextComparer.Default);
                filteredCompletions.UnionWith(sourceCompletions);
                filteredCompletions.UnionWith(secondSourceCompletions);

                int j = 0;

                foreach (Completion completion in filteredCompletions)
                {
                    while (j < result.Count && !filteredCompletions.Contains(result[j]))
                    {
                        result.RemoveAt(j);
                    }

                    if (j == result.Count || completion != result[j])
                    {
                        result.Insert(j, completion);
                        j++;
                    }
                }
            }
            finally
            {
                result.EndBulkOperation();
            }
        }
Beispiel #2
0
        private void Update()
        {
            if (debuggerService.State != DebuggerState.Running)
            {
                var frames = debuggerService.Machine.GetStackFrames();

                stackFrames.BeginBulkOperation();
                try
                {
                    stackFrames.Clear();

                    for (int i = 0; i < frames.Length; i++)
                    {
                        var  frame         = frames[i];
                        uint jumpToAddress = 0;
                        if (i == 0)
                        {
                            jumpToAddress = (uint)debuggerService.Machine.PC;
                        }
                        else
                        {
                            jumpToAddress = frames[i - 1].ReturnAddress;
                        }

                        stackFrames.Add(new StackFrameViewModel(frame, routineService.RoutineTable, jumpToAddress));
                    }
                }
                finally
                {
                    stackFrames.EndBulkOperation();
                }
            }
        }
Beispiel #3
0
        private void UpdateAnalyzers()
        {
            if (_analyzerItems == null)
            {
                // The set of AnalyzerItems hasn't been realized yet. Just signal that HasItems
                // may have changed.

                NotifyPropertyChanged(nameof(HasItems));
                return;
            }

            var project = _analyzersFolder.Workspace.CurrentSolution.GetProject(
                _analyzersFolder.ProjectId
                );

            if (project != null && project.AnalyzerReferences != _analyzerReferences)
            {
                _analyzerReferences = project.AnalyzerReferences;

                _analyzerItems.BeginBulkOperation();

                var itemsToRemove = _analyzerItems
                                    .Where(item => !_analyzerReferences.Contains(item.AnalyzerReference))
                                    .ToArray();

                var referencesToAdd = GetFilteredAnalyzers(_analyzerReferences, project)
                                      .Where(r => !_analyzerItems.Any(item => item.AnalyzerReference == r))
                                      .ToArray();

                foreach (var item in itemsToRemove)
                {
                    _analyzerItems.Remove(item);
                }

                foreach (var reference in referencesToAdd)
                {
                    _analyzerItems.Add(
                        new AnalyzerItem(
                            _analyzersFolder,
                            reference,
                            _commandHandler.AnalyzerContextMenuController
                            )
                        );
                }

                var sorted = _analyzerItems
                             .OrderBy(item => item.AnalyzerReference.Display)
                             .ToArray();
                for (var i = 0; i < sorted.Length; i++)
                {
                    _analyzerItems.Move(_analyzerItems.IndexOf(sorted[i]), i);
                }

                _analyzerItems.EndBulkOperation();

                NotifyPropertyChanged(nameof(HasItems));
            }
        }
Beispiel #4
0
        //private void MemoryChanged(object sender, MemoryEventArgs e)
        //{
        //    // Replace affected lines
        //    int firstLineIndex = e.Address / 16;
        //    int lastLineIndex = (e.Address + e.Length) / 16;

        //    var reader = e.Memory.CreateReader(firstLineIndex * 16);

        //    for (int i = firstLineIndex; i <= lastLineIndex; i++)
        //    {
        //        var address = reader.Address;
        //        var count = Math.Min(8, reader.RemainingBytes);
        //        var values = reader.NextWords(count);

        //        lines[i] = new MemoryLineViewModel(address, values);
        //    }

        //    // TODO: Highlight modified memory
        //}

        private void StoryService_StoryOpened(object sender, StoryOpenedEventArgs e)
        {
            var reader = new MemoryReader(e.Story.Memory, 0);

            lines.BeginBulkOperation();
            try
            {
                while (reader.RemainingBytes > 0)
                {
                    var address = reader.Address;

                    ushort[] values;

                    if (reader.RemainingBytes >= 16 || reader.RemainingBytes % 2 == 0)
                    {
                        var count = Math.Min(8, reader.RemainingBytes / 2);
                        values = reader.NextWords(count);
                    }
                    else
                    {
                        // if the last line is an odd number of bytes...

                        // TODO: memory view always shows even number of bytes
                        // (padding with zeroes if necessry). Need to fix it to show odd
                        // number of bytes if that's the case.
                        var valueList = new List <ushort>();
                        while (reader.RemainingBytes > 0)
                        {
                            if (reader.RemainingBytes > 2)
                            {
                                valueList.Add(reader.NextWord());
                            }
                            else
                            {
                                valueList.Add((ushort)(reader.NextByte() << 8));
                            }
                        }

                        values = valueList.ToArray();
                    }

                    lines.Add(new MemoryLineViewModel(address, values));
                }
            }
            finally
            {
                lines.EndBulkOperation();
            }

            PropertyChanged("HasStory");
        }
Beispiel #5
0
        private void StoryService_StoryOpened(object sender, StoryOpenedEventArgs e)
        {
            objects.BeginBulkOperation();
            try
            {
                foreach (var obj in e.Story.ObjectTable)
                {
                    objects.Add(new ObjectViewModel(obj));
                }
            }
            finally
            {
                objects.EndBulkOperation();
            }

            PropertyChanged("HasStory");
        }
Beispiel #6
0
        private void Update()
        {
            if (debuggerService.State != DebuggerState.Running)
            {
                var frames = debuggerService.Machine.GetStackFrames();

                stackFrames.BeginBulkOperation();
                try
                {
                    stackFrames.Clear();

                    foreach (var frame in frames)
                    {
                        stackFrames.Add(new StackFrameViewModel(frame, routineService.RoutineTable));
                    }
                }
                finally
                {
                    stackFrames.EndBulkOperation();
                }
            }
        }
        /// <summary>
        /// Perform a bulk update of a collection of <see cref="Completion"/> instances to match the values
        /// contained in a pair of source collections.
        /// </summary>
        /// <remarks>The <see cref="Completion"/> instances in <paramref name="sourceCompletions"/> and
        /// <paramref name="secondSourceCompletions"/> are merged and sorted using
        /// <see cref="CompletionDisplayTextComparer.Default"/>.
        ///
        /// <list type="bullet">
        ///     <item>Any items present in <paramref name="result"/> but not present in the merged collection are
        /// removed from <paramref name="result"/>.</item>
        ///     <item>Any items not already present in <paramref name="result"/> are inserted at the correct
        /// location.</item>
        /// </list>
        ///
        /// <note type="caller">The <paramref name="result"/> collection is assumed to already be sorted
        /// according to <see cref="CompletionDisplayTextComparer.Default"/> before this method is called.</note>
        /// </remarks>
        /// <param name="result">The collection holding the merged result.</param>
        /// <param name="sourceCompletions">The collection of <see cref="Completion"/> instances from the first
        /// source.</param>
        /// <param name="secondSourceCompletions">The collection of <see cref="Completion"/> instances from the
        /// second source.</param>
        private static void UpdateCompletionList(BulkObservableCollection<Completion> result,
          IEnumerable<Completion> sourceCompletions, IEnumerable<Completion> secondSourceCompletions)
        {
            try
            {
                result.BeginBulkOperation();

                // SortedSet<Completion> provides for immediate sorting, and also allows Contains() to be used
                // below instead of a manual call to CompletionDisplayTextComparer.Compare().
                SortedSet<Completion> filteredCompletions = new SortedSet<Completion>(CompletionDisplayTextComparer.Default);
                filteredCompletions.UnionWith(sourceCompletions);
                filteredCompletions.UnionWith(secondSourceCompletions);

                int j = 0;

                foreach(Completion completion in filteredCompletions)
                {
                    while(j < result.Count && !filteredCompletions.Contains(result[j]))
                        result.RemoveAt(j);

                    if(j == result.Count || completion != result[j])
                    {
                        result.Insert(j, completion);
                        j++;
                    }
                }
            }
            finally
            {
                result.EndBulkOperation();
            }
        }
        private void DebuggerService_MachineCreated(object sender, MachineCreatedEventArgs e)
        {
            var reader = new MemoryReader(storyService.Story.Memory, 0);

            DisassemblyLineViewModel ipLine;

            lines.BeginBulkOperation();
            try
            {
                var routineTable = routineService.RoutineTable;

                for (int rIndex = 0; rIndex < routineTable.Count; rIndex++)
                {
                    var routine = routineTable[rIndex];

                    if (rIndex > 0)
                    {
                        var lastRoutine = routineTable[rIndex - 1];
                        if (lastRoutine.Address + lastRoutine.Length < routine.Address)
                        {
                            var addressGapLine = new DisassemblyAddressGapLineViewModel(lastRoutine, routine)
                            {
                                ShowBlankBefore = true
                            };

                            lines.Add(addressGapLine);
                        }
                    }

                    var routineHeaderLine = new DisassemblyRoutineHeaderLineViewModel(routine)
                    {
                        ShowBlankBefore = rIndex > 0,
                        ShowBlankAfter  = true
                    };

                    routineAddressAndIndexList.Add(new AddressAndIndex(routineHeaderLine.Address, lines.Count));
                    lines.Add(routineHeaderLine);
                    addressToLineMap.Add(routine.Address, routineHeaderLine);

                    var instructions = routine.Instructions;
                    var lastIndex    = instructions.Length - 1;
                    for (int i = 0; i <= lastIndex; i++)
                    {
                        var instruction     = instructions[i];
                        var instructionLine = new DisassemblyInstructionLineViewModel(instruction, i == lastIndex);

                        if (breakpointService.Exists(instruction.Address))
                        {
                            instructionLine.HasBreakpoint = true;
                        }

                        lines.Add(instructionLine);
                        addressToLineMap.Add(instruction.Address, instructionLine);
                    }
                }

                ipLine       = GetLineByAddress(debuggerService.Machine.PC);
                ipLine.HasIP = true;
            }
            finally
            {
                lines.EndBulkOperation();
            }

            BringLineIntoView(ipLine);

            routineService.RoutineTable.RoutineAdded += RoutineTable_RoutineAdded;
        }