Cosmos.VS.Windows improvements.

This commit is contained in:
José Pedro 2018-02-18 18:07:42 +00:00
parent bcb047523e
commit cd32f8f27c
No known key found for this signature in database
GPG key ID: B8247B9301707B83
10 changed files with 211 additions and 237 deletions

View file

@ -53,6 +53,7 @@
<ItemGroup>
<PackageReference Include="Microsoft.VisualStudio.ImageCatalog" Version="15.5.27130" />
<PackageReference Include="Microsoft.VisualStudio.Imaging" Version="15.5.27130" />
<PackageReference Include="Microsoft.VisualStudio.Imaging.Interop.14.0.DesignTime" Version="14.3.25408" />
<PackageReference Include="Microsoft.VisualStudio.SDK.EmbedInteropTypes" Version="15.0.16" />
<PackageReference Include="Microsoft.VisualStudio.Shell.15.0" Version="15.4.27004" />
<PackageReference Include="Microsoft.VisualStudio.Shell.Interop.10.0" Version="10.0.30320" />

View file

@ -75,7 +75,7 @@ namespace Cosmos.VS.Windows
private void ShowWindowRegisters(object aCommand, EventArgs e)
{
ShowWindow(typeof(RegistersTW));
ShowWindow(typeof(RegistersToolWindow));
}
private void ShowWindowStack(object aCommand, EventArgs e)

View file

@ -19,7 +19,7 @@ namespace Cosmos.VS.Windows
[PackageRegistration(UseManagedResourcesOnly = true)]
[ProvideMenuResource("Menus.ctmenu", 1)]
[ProvideToolWindow(typeof(AssemblyToolWindow))]
[ProvideToolWindow(typeof(RegistersTW))]
[ProvideToolWindow(typeof(RegistersToolWindow))]
[ProvideToolWindow(typeof(StackTW))]
[ProvideToolWindow(typeof(InternalTW))]
[ProvideToolWindow(typeof(ConsoleTW))]
@ -113,7 +113,7 @@ namespace Cosmos.VS.Windows
break;
case Debugger2Windows.Registers:
UpdateWindow(typeof(RegistersTW), null, xMsg);
UpdateWindow(typeof(RegistersToolWindow), null, xMsg);
break;
case Debugger2Windows.Quit:
@ -218,7 +218,7 @@ namespace Cosmos.VS.Windows
byte[] aData = cWindow.UserControl.GetCurrentState();
StateStorer.StoreState("StackTW", aData == null ? null : (byte[])aData.Clone());
cWindow = FindWindow(typeof(RegistersTW));
cWindow = FindWindow(typeof(RegistersToolWindow));
aData = cWindow.UserControl.GetCurrentState();
StateStorer.StoreState("RegistersTW", aData == null ? null : (byte[])aData.Clone());
}
@ -229,7 +229,7 @@ namespace Cosmos.VS.Windows
byte[] aData = StateStorer.RetrieveState(StateStorer.CurrLineId, "StackTW");
cWindow.UserControl.SetCurrentState(aData == null ? null : (byte[])aData.Clone());
cWindow = FindWindow(typeof(RegistersTW));
cWindow = FindWindow(typeof(RegistersToolWindow));
aData = StateStorer.RetrieveState(StateStorer.CurrLineId, "RegistersTW");
cWindow.UserControl.SetCurrentState(aData == null ? null : (byte[])aData.Clone());
}

View file

@ -1,28 +1,19 @@
using System;
using System.Runtime.InteropServices;
using Microsoft.VisualStudio.Imaging;
using Microsoft.VisualStudio.Shell;
namespace Cosmos.VS.Windows.ToolWindows
{
[Guid("f019fb29-c2c2-4d27-9abf-739533c939be")]
[Guid(ToolWindowGuid)]
internal class AssemblyToolWindow : ToolWindowPane2
{
public const string ToolWindowGuid = "f019fb29-c2c2-4d27-9abf-739533c939be";
public AssemblyToolWindow()
{
//ToolBar = new CommandID(GuidList.guidAsmToolbarCmdSet, (int)PkgCmdIDList.AsmToolbar);
BitmapImageMoniker = KnownMonikers.DisassemblyWindow;
Caption = "Cosmos Assembly";
// Set the image that will appear on the tab of the window frame
// when docked with an other window.
// The resource ID correspond to the one defined in the resx file
// while the Index is the offset in the bitmap strip. Each image in
// the strip being 16x16.
BitmapResourceID = 301;
BitmapIndex = 1;
// This is the user control hosted by the tool window; Note that, even if this class implements IDisposable,
// we are not calling Dispose on this object. This is because ToolWindowPane calls Dispose on
// the object returned by the Content property.
Content = new AssemblyUC();
}
}

View file

@ -5,7 +5,6 @@
xmlns:imaging="clr-namespace:Microsoft.VisualStudio.Imaging;assembly=Microsoft.VisualStudio.Imaging"
xmlns:imagecatalog="clr-namespace:Microsoft.VisualStudio.Imaging;assembly=Microsoft.VisualStudio.ImageCatalog"
xmlns:platformui="clr-namespace:Microsoft.VisualStudio.PlatformUI;assembly=Microsoft.VisualStudio.Shell.15.0"
x:Name="CosmosAssemblyUserControl"
Background="{DynamicResource {x:Static platformui:EnvironmentColors.ToolWindowBackgroundBrushKey}}"
Foreground="{DynamicResource {x:Static platformui:EnvironmentColors.ToolWindowTextBrushKey}}">
<DockPanel>

View file

@ -0,0 +1,54 @@
<local:DebuggerUC x:Class="Cosmos.VS.Windows.RegistersControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d"
xmlns:local="clr-namespace:Cosmos.VS.Windows"
xmlns:platformui="clr-namespace:Microsoft.VisualStudio.PlatformUI;assembly=Microsoft.VisualStudio.Shell.15.0"
Background="{DynamicResource {x:Static platformui:EnvironmentColors.ToolWindowBackgroundBrushKey}}"
Foreground="{DynamicResource {x:Static platformui:EnvironmentColors.ToolWindowTextBrushKey}}"
FontFamily="Consolas"
d:DataContext="{d:DesignInstance {x:Type local:RegistersViewModel}, IsDesignTimeCreatable=True}">
<StackPanel Orientation="Vertical"
Margin="8">
<StackPanel Orientation="Horizontal">
<StackPanel>
<TextBlock Text="{Binding EAX, StringFormat='EAX = {0}'}" />
<TextBlock Text="{Binding EBX, StringFormat='EBX = {0}'}" />
<TextBlock Text="{Binding ECX, StringFormat='ECX = {0}'}" />
<TextBlock Text="{Binding EDX, StringFormat='EDX = {0}'}" />
</StackPanel>
<StackPanel Margin="12,0,0,0">
<TextBlock Text="{Binding AX, StringFormat='AX = {0}'}" />
<TextBlock Text="{Binding BX, StringFormat='BX = {0}'}" />
<TextBlock Text="{Binding CX, StringFormat='CX = {0}'}" />
<TextBlock Text="{Binding DX, StringFormat='DX = {0}'}" />
</StackPanel>
<StackPanel Margin="12,0,0,0">
<TextBlock Text="{Binding AH, StringFormat='AH = {0}'}" />
<TextBlock Text="{Binding BH, StringFormat='BH = {0}'}" />
<TextBlock Text="{Binding CH, StringFormat='CH = {0}'}" />
<TextBlock Text="{Binding DH, StringFormat='DH = {0}'}" />
</StackPanel>
<StackPanel Margin="12,0,0,0">
<TextBlock Text="{Binding AL, StringFormat='AL = {0}'}" />
<TextBlock Text="{Binding BL, StringFormat='BL = {0}'}" />
<TextBlock Text="{Binding CL, StringFormat='CL = {0}'}" />
<TextBlock Text="{Binding DL, StringFormat='DL = {0}'}" />
</StackPanel>
</StackPanel>
<StackPanel Orientation="Horizontal" Margin="0,12,0,0">
<StackPanel>
<TextBlock Text="{Binding ESP, StringFormat='ESP = {0}'}" />
<TextBlock Text="{Binding EBP, StringFormat='EBP = {0}'}" />
<TextBlock Text="{Binding ESI, StringFormat='ESI = {0}'}" />
<TextBlock Text="{Binding EDI, StringFormat='EDI = {0}'}" />
</StackPanel>
<StackPanel Margin="12,0,0,0">
<TextBlock Text="{Binding EIP, StringFormat='EIP = {0}'}" />
<TextBlock Text="{Binding Flags, StringFormat='Flags = {0}'}" />
</StackPanel>
</StackPanel>
</StackPanel>
</local:DebuggerUC>

View file

@ -0,0 +1,126 @@
using System;
using System.ComponentModel;
using System.Windows;
using System.Windows.Threading;
namespace Cosmos.VS.Windows
{
public partial class RegistersControl : DebuggerUC
{
private RegistersViewModel mViewModel;
public RegistersControl()
{
InitializeComponent();
DataContext = mViewModel = new RegistersViewModel();
}
protected override void DoUpdate(string aTag)
{
Application.Current.Dispatcher.Invoke(
() =>
{
if (mData != null)
{
mViewModel.UpdateData(mData);
}
}, DispatcherPriority.Normal);
}
}
internal class RegistersViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
//Push All
// Temp = (ESP);
// Push(EAX); 28
// Push(ECX); 24
// Push(EDX); 20
// Push(EBX); 16
// Push(Temp); 12 // Have to get from another source, ESP is already in DS when we pushall
// Push(EBP); 8
// Push(ESI); 4
// Push(EDI); 0
// We get them from bottom up, so we receive them in reverse order as shown above. That is 0-3 is EDI.
//
// Additional ones sent manually (at end, not from stack)
// ESP 32
// EIP 36
//
//TODO: Flags
private byte[] mData;
private object mSyncObject = new object();
public void UpdateData(byte[] data)
{
lock (mSyncObject)
{
mData = data;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(String.Empty));
}
}
public string EAX => GetRegisterValue(28).ToHexString();
public string AX => EAX.Substring(4, 4);
public string AH => EAX.Substring(4, 2);
public string AL => EAX.Substring(6, 2);
public string EBX => GetRegisterValue(16).ToHexString();
public string BX => EBX.Substring(4, 4);
public string BH => EBX.Substring(4, 2);
public string BL => EBX.Substring(6, 2);
public string ECX => GetRegisterValue(24).ToHexString();
public string CX => ECX.Substring(4, 4);
public string CH => ECX.Substring(4, 2);
public string CL => ECX.Substring(6, 2);
public string EDX => GetRegisterValue(20).ToHexString();
public string DX => EDX.Substring(4, 4);
public string DH => EDX.Substring(4, 2);
public string DL => EDX.Substring(6, 2);
public string ESI => GetRegisterValue(8).ToHexString();
public string EDI => GetRegisterValue(4).ToHexString();
public string EBP => GetRegisterValue(0).ToHexString();
public string ESP => GetRegisterValue(32).ToHexString();
public string EIP => GetRegisterValue(36).ToHexString();
public string Flags => ((uint?)null).ToHexString();
private uint? GetRegisterValue(int offset)
{
lock (mSyncObject)
{
if (mData == null)
{
return null;
}
#if DEBUG
if (offset >= mData.Length)
{
throw new ArgumentOutOfRangeException(nameof(offset));
}
#endif
return BitConverter.ToUInt32(mData, offset);
}
}
}
internal static class ExtensionMethods
{
public static string ToHexString(this uint? value)
{
if (value.HasValue)
{
return value.Value.ToString("X8");
}
return "--------";
}
}
}

View file

@ -0,0 +1,20 @@
using System;
using System.Runtime.InteropServices;
using Microsoft.VisualStudio.Imaging;
using Microsoft.VisualStudio.Shell;
namespace Cosmos.VS.Windows.ToolWindows
{
[Guid(ToolWindowGuid)]
internal class RegistersToolWindow : ToolWindowPane2
{
public const string ToolWindowGuid = "ce2a2d0f-0f1b-4a1f-a9ac-5a5f2a5e2c25";
public RegistersToolWindow()
{
BitmapImageMoniker = KnownMonikers.RegistersWindow;
Caption = "Cosmos Registers";
Content = new RegistersControl();
}
}
}

View file

@ -1,85 +0,0 @@
<local:DebuggerUC x:Class="Cosmos.VS.Windows.RegistersUC"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:Cosmos.VS.Windows"
mc:Ignorable="d"
x:Name="CosmosRegistersUserControl"
Background="WhiteSmoke" xmlns:my="clr-namespace:Cosmos.VS.Windows">
<StackPanel Orientation="Vertical" Margin="5">
<StackPanel Orientation="Horizontal" Margin="0,0,0,0">
<StackPanel Margin="0,0,0,0">
<TextBlock Text="EAX" FontFamily="Consolas" />
<TextBlock Text="EBX" FontFamily="Consolas" />
<TextBlock Text="ECX" FontFamily="Consolas" />
<TextBlock Text="EDX" FontFamily="Consolas" />
</StackPanel>
<StackPanel Margin="5,0,0,0">
<my:DataBytesUC x:Name="dataEAX" />
<my:DataBytesUC x:Name="dataEBX" />
<my:DataBytesUC x:Name="dataECX" />
<my:DataBytesUC x:Name="dataEDX" />
</StackPanel>
<StackPanel Margin="15,0,0,0">
<TextBlock Text="AX" FontFamily="Consolas" />
<TextBlock Text="BX" FontFamily="Consolas" />
<TextBlock Text="CX" FontFamily="Consolas" />
<TextBlock Text="DX" FontFamily="Consolas" />
</StackPanel>
<StackPanel Margin="5,0,0,0">
<my:DataBytesUC Prefix="" Digits="4" x:Name="dataAX" />
<my:DataBytesUC Prefix="" Digits="4" x:Name="dataBX" />
<my:DataBytesUC Prefix="" Digits="4" x:Name="dataCX" />
<my:DataBytesUC Prefix="" Digits="4" x:Name="dataDX" />
</StackPanel>
<StackPanel Margin="15,0,0,0">
<TextBlock Text="AH" FontFamily="Consolas" />
<TextBlock Text="BH" FontFamily="Consolas" />
<TextBlock Text="CH" FontFamily="Consolas" />
<TextBlock Text="DH" FontFamily="Consolas" />
</StackPanel>
<StackPanel Margin="5,0,0,0">
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataAH" />
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataBH" />
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataCH" />
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataDH" />
</StackPanel>
<StackPanel Margin="15,0,0,0">
<TextBlock Text="AL" FontFamily="Consolas" />
<TextBlock Text="BL" FontFamily="Consolas" />
<TextBlock Text="CL" FontFamily="Consolas" />
<TextBlock Text="DL" FontFamily="Consolas" />
</StackPanel>
<StackPanel Margin="5,0,0,0">
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataAL" />
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataBL" />
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataCL" />
<my:DataBytesUC Prefix="" Digits="2" x:Name="dataDL" />
</StackPanel>
</StackPanel>
<StackPanel Orientation="Horizontal" Margin="0,15,0,0">
<StackPanel Margin="0,0,0,0">
<TextBlock Text="ESP" FontFamily="Consolas" />
<TextBlock Text="EBP" FontFamily="Consolas" />
<TextBlock Text="ESI" FontFamily="Consolas" />
<TextBlock Text="EDI" FontFamily="Consolas" />
</StackPanel>
<StackPanel Margin="5,0,0,0">
<my:DataBytesUC x:Name="dataESP" />
<my:DataBytesUC x:Name="dataEBP" />
<my:DataBytesUC x:Name="dataESI" />
<my:DataBytesUC x:Name="dataEDI" />
</StackPanel>
<StackPanel Margin="15,0,0,0">
<TextBlock Text="EIP" FontFamily="Consolas" />
<TextBlock Text="Flags" FontFamily="Consolas" />
</StackPanel>
<StackPanel Margin="5,0,0,0">
<my:DataBytesUC x:Name="dataEIP" />
<my:DataBytesUC x:Name="dataFlags" />
</StackPanel>
</StackPanel>
</StackPanel>
</local:DebuggerUC>

View file

@ -1,132 +0,0 @@
using System;
using System.Runtime.InteropServices;
using System.Windows.Threading;
namespace Cosmos.VS.Windows
{
[Guid("CE2A2D0F-0F1B-4A1F-A9AC-5A5F2A5E2C25")]
public class RegistersTW : ToolWindowPane2
{
public RegistersTW()
{
Caption = "Cosmos x86 Registers";
BitmapResourceID = 301;
BitmapIndex = 1;
Content = new RegistersUC();
}
}
public partial class RegistersUC : DebuggerUC
{
public RegistersUC()
{
InitializeComponent();
}
protected UInt32 mCurrEBP = 0x0;
public UInt32 CurrentEBP
{
get
{
return mCurrEBP;
}
}
protected void UpdateRegisters(byte[] aData, int aOffset, DataBytesUC a32, DataBytesUC a16, DataBytesUC a8Hi, DataBytesUC a8Lo)
{
a8Lo.Value = aData[aOffset];
a8Hi.Value = aData[aOffset + 1];
a16.Value = a8Hi.Value << 8 | a8Lo.Value;
UpdateRegister32(aData, aOffset, a32);
}
protected void UpdateRegister32(byte[] aData, int aOffset, DataBytesUC a32)
{
UInt32 x32 = (UInt32)
(aData[aOffset + 3] << 24 |
aData[aOffset + 2] << 16 |
aData[aOffset + 1] << 8 |
aData[aOffset]);
a32.Value = x32;
if (a32 == dataEBP)
{
mCurrEBP = x32;
}
}
protected override void DoUpdate(string aTag)
{
//Push All
// Temp = (ESP);
// Push(EAX); 28
// Push(ECX); 24
// Push(EDX); 20
// Push(EBX); 16
// Push(Temp); 12 // Have to get from another source, ESP is already in DS when we pushall
// Push(EBP); 8
// Push(ESI); 4
// Push(EDI); 0
// We get them from bottom up, so we receive them in reverse order as shown above. That is 0-3 is EDI.
//
// Additional ones sent manually (at end, not from stack)
// ESP 32
// EIP 36
//
System.Windows.Application.Current.Dispatcher.Invoke(DispatcherPriority.Normal,
(Action)delegate()
{
if (mData == null)
{
dataEAX.Value = null;
dataAX.Value = null;
dataAH.Value = null;
dataAL.Value = null;
dataEBX.Value = null;
dataBX.Value = null;
dataBH.Value = null;
dataBL.Value = null;
dataECX.Value = null;
dataCX.Value = null;
dataCH.Value = null;
dataCL.Value = null;
dataEDX.Value = null;
dataDX.Value = null;
dataDH.Value = null;
dataDL.Value = null;
dataEBP.Value = null;
mCurrEBP = 0x0;
dataESI.Value = null;
dataEDI.Value = null;
dataESP.Value = null;
dataEIP.Value = null;
}
else
{
try
{
UpdateRegisters(mData, 28, dataEAX, dataAX, dataAH, dataAL);
UpdateRegisters(mData, 16, dataEBX, dataBX, dataBH, dataBL);
UpdateRegisters(mData, 24, dataECX, dataCX, dataCH, dataCL);
UpdateRegisters(mData, 20, dataEDX, dataDX, dataDH, dataDL);
UpdateRegister32(mData, 8, dataEBP);
UpdateRegister32(mData, 4, dataESI);
UpdateRegister32(mData, 0, dataEDI);
UpdateRegister32(mData, 32, dataESP);
UpdateRegister32(mData, 36, dataEIP);
}
catch
{
}
}
}
);
//TODO: Flags
}
}
}