From d64f99adf3fbd2a1a37fb4f81eaeb9f208a14b0a Mon Sep 17 00:00:00 2001
From: BlueSkeye_cp <7a9a8e0be1356805ba39aaefd2f72a2ce9bd2015XwR8pJkz>
Date: Thu, 20 Sep 2012 09:41:02 +0000
Subject: [PATCH] Add Bochs debugging support to Visual Studio Cosmos project
(UI). A new pane and associated launch type is added in the Cosmos project
properties pane.
---
.../Cosmos.Build.Common/BuildProperties.cs | 9 +-
.../Build/Cosmos.Build.Common/CosmosPaths.cs | 27 ++++-
.../Build/Cosmos.Build.MSBuild/IL2CPUTask.cs | 19 ++-
.../Debug/Cosmos.Debug.Common/BochsSupport.cs | 89 ++++++++++++++
.../Cosmos.Debug.Common.csproj | 1 +
.../AD7.Impl/AD7Process.cs | 13 ++-
.../Cosmos.Debug.VSDebugEngine.csproj | 4 -
.../Cosmos.Debug.VSDebugEngine/Host/Bochs.cs | 109 +++++++-----------
.../ResourceStrings.Designer.cs | 11 +-
.../ResourceStrings.resx | 7 +-
.../Cosmos.VS.Package/CosmosPage.Designer.cs | 35 +++++-
source2/VSIP/Cosmos.VS.Package/CosmosPage.cs | 44 ++++++-
.../VSIP/Cosmos.VS.Package/ProfilePresets.cs | 3 +
.../Projects/Cosmos/Cosmos.vstemplate | 1 +
.../Proj/CosmosProj.vstemplate | 4 +-
.../Cosmos.VS.Wizards.csproj | 1 +
source2/VSIP/Cosmos.VS.Wizards/Cosmos.bxrc | 44 +++++++
.../GenerateCosmosProjectWizard.cs | 30 ++++-
18 files changed, 355 insertions(+), 96 deletions(-)
create mode 100644 source2/Debug/Cosmos.Debug.Common/BochsSupport.cs
create mode 100644 source2/VSIP/Cosmos.VS.Wizards/Cosmos.bxrc
diff --git a/source2/Build/Cosmos.Build.Common/BuildProperties.cs b/source2/Build/Cosmos.Build.Common/BuildProperties.cs
index e94083e80..216d9a020 100644
--- a/source2/Build/Cosmos.Build.Common/BuildProperties.cs
+++ b/source2/Build/Cosmos.Build.Common/BuildProperties.cs
@@ -64,7 +64,7 @@ namespace Cosmos.Build.Common {
Launch = LaunchType.None;
} else if (aName == "Bochs") {
- Description = "Use Bochs emulatior to deploy and debug.";
+ Description = "Use Bochs emulator to deploy and debug.";
Deployment = DeploymentType.ISO;
Launch = LaunchType.Bochs;
}
@@ -202,5 +202,12 @@ namespace Cosmos.Build.Common {
get { return GetProperty(StartCosmosGDBString, false); }
set { SetProperty(StartCosmosGDBString, value); }
}
+
+ public const string EnableBochsDebugString = "EnableBochsDebug";
+ public Boolean EnableBochsDebug
+ {
+ get { return GetProperty(EnableBochsDebugString, false); }
+ set { SetProperty(EnableBochsDebugString, value); }
+ }
}
}
\ No newline at end of file
diff --git a/source2/Build/Cosmos.Build.Common/CosmosPaths.cs b/source2/Build/Cosmos.Build.Common/CosmosPaths.cs
index 6e4d5a30c..1a1562c21 100644
--- a/source2/Build/Cosmos.Build.Common/CosmosPaths.cs
+++ b/source2/Build/Cosmos.Build.Common/CosmosPaths.cs
@@ -25,11 +25,17 @@ namespace Cosmos.Build.Common {
}
static CosmosPaths() {
- using (var xReg = Registry.LocalMachine.OpenSubKey(@"Software\Cosmos", false)) {
- if (xReg == null) {
- throw new Exception(@"HKEY_LOCAL_MACHINE\SOFTWARE\Cosmos was not found.");
+ using (RegistryKey baseKey = RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry32))
+ {
+ using (var xReg = baseKey.OpenSubKey(@"Software\Cosmos", false)) {
+ if (xReg == null) {
+ throw new Exception(@"HKEY_LOCAL_MACHINE\SOFTWARE\Cosmos was not found.");
+ }
+ UserKit = (string)xReg.GetValue("UserKit");
+ if (null == UserKit) {
+ throw new Exception(@"HKEY_LOCAL_MACHINE\SOFTWARE\Cosmos\@UserKit was not found.");
+ }
}
- UserKit = (string)xReg.GetValue("UserKit");
}
Build = CheckPath(UserKit, @"Build");
Vsip = CheckPath(UserKit, @"Build\VSIP");
@@ -41,9 +47,20 @@ namespace Cosmos.Build.Common {
using (var xReg = Registry.CurrentUser.OpenSubKey(@"Software\Cosmos", false)) {
if (xReg != null) {
DevKit = (string)xReg.GetValue("DevKit");
- DebugStubSrc = CheckPath(DevKit, @"source2\Compiler\Cosmos.Compiler.DebugStub");
+ if (null == DevKit) {
+ throw new Exception(@"HKEY_LOCAL_MACHINE\SOFTWARE\Cosmos\@DevKit was not found.");
+ }
+ try { DebugStubSrc = CheckPath(DevKit, @"source2\Compiler\Cosmos.Compiler.DebugStub"); }
+ // Not finding this one is not an issue. We will fallback to already retrieved stun from UserKit
+ catch { }
}
}
}
+
+ /// This method is intentionally empty. It's sole purpose is to be able to trigger
+ /// class initialization in a controlled manner so as to intercept initializer thrown
+ /// exceptions.
+ public static void Initialize() {
+ }
}
}
\ No newline at end of file
diff --git a/source2/Build/Cosmos.Build.MSBuild/IL2CPUTask.cs b/source2/Build/Cosmos.Build.MSBuild/IL2CPUTask.cs
index 0f0fc38ce..f9162a473 100644
--- a/source2/Build/Cosmos.Build.MSBuild/IL2CPUTask.cs
+++ b/source2/Build/Cosmos.Build.MSBuild/IL2CPUTask.cs
@@ -85,10 +85,28 @@ namespace Cosmos.Build.MSBuild {
}
return null;
}
+
+ private bool EnsureCosmosPathsInitialization() {
+ try {
+ CosmosPaths.Initialize();
+ return true;
+ } catch (Exception e)
+ {
+ StringBuilder builder = new StringBuilder();
+ builder.Append("Error while initializing Cosmos paths");
+ for (Exception scannedException = e; null != scannedException; scannedException = scannedException.InnerException)
+ {
+ builder.Append(" | " + scannedException.Message);
+ }
+ LogError(builder.ToString());
+ return false;
+ }
+ }
protected bool Initialize() {
// Add UserKit dirs for asms to load from.
mSearchDirs.Add(Path.GetDirectoryName(typeof(IL2CPU).Assembly.Location));
+ if (!EnsureCosmosPathsInitialization()) { return false; }
mSearchDirs.Add(CosmosPaths.UserKit);
mSearchDirs.Add(CosmosPaths.Kernel);
AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(CurrentDomain_AssemblyResolve);
@@ -135,7 +153,6 @@ namespace Cosmos.Build.MSBuild {
}
public bool Execute() {
- //System.Diagnostics.Debugger.Launch();
try {
LogMessage("Executing IL2CPU on assembly");
if (!Initialize()) {
diff --git a/source2/Debug/Cosmos.Debug.Common/BochsSupport.cs b/source2/Debug/Cosmos.Debug.Common/BochsSupport.cs
new file mode 100644
index 000000000..b478f69aa
--- /dev/null
+++ b/source2/Debug/Cosmos.Debug.Common/BochsSupport.cs
@@ -0,0 +1,89 @@
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Text;
+
+using Microsoft.Win32;
+
+namespace Cosmos.Debug.Common
+{
+ /// An helper class that is used from both Cosmos.VS.Package and Cosmos.VS.DebugEngine for
+ /// Bochs emulator support.
+ public static class BochsSupport
+ {
+ static BochsSupport()
+ {
+ FindBochsExe();
+ }
+
+ /// Get a flag that tell whether Bochs is enabled on this system.
+ public static bool BochsEnabled
+ {
+ get { return (null != BochsExe); }
+ }
+
+ /// Get a descriptor for the Bochs emulator with debugger support program. The return value
+ /// is a null reference if Bochs is not installed.
+ public static FileInfo BochsDebugExe
+ {
+ get;
+ private set;
+ }
+
+ /// Get a descriptor for the Bochs emulator program. The return value is a null reference if
+ /// Bochs is not installed.
+ public static FileInfo BochsExe
+ {
+ get;
+ private set;
+ }
+
+ /// Retrieve installation path for Bochs and initialize the property.
+ /// Search is performed using the registry and rely on the shell command defined for the
+ /// BochsConfigFile.
+ private static void FindBochsExe()
+ {
+ try
+ {
+ using (var runCommandRegistryKey = Registry.ClassesRoot.OpenSubKey(@"BochsConfigFile\shell\Run\command", false))
+ {
+ if (null == runCommandRegistryKey) { return; }
+ string commandLine = (string)runCommandRegistryKey.GetValue(null, null);
+ if (null != commandLine) { commandLine = commandLine.Trim(); }
+ if (string.IsNullOrEmpty(commandLine)) { return; }
+ // Now perform some parsing on command line to discover full exe path.
+ string candidateFilePath;
+ int commandLineLength = commandLine.Length;
+ if ('"' == commandLine[0])
+ {
+ // Seek for a non escaped double quote.
+ int lastDoubleQuoteIndex = 1;
+ for (; lastDoubleQuoteIndex < commandLineLength; lastDoubleQuoteIndex++)
+ {
+ if ('"' != commandLine[lastDoubleQuoteIndex]) { continue; }
+ if ('\\' != commandLine[lastDoubleQuoteIndex - 1]) { break; }
+ }
+ if (lastDoubleQuoteIndex >= commandLineLength) { return; }
+ candidateFilePath = commandLine.Substring(1, lastDoubleQuoteIndex - 1);
+ }
+ else
+ {
+ // Seek for first separator character.
+ int firstSeparatorIndex = 0;
+ for (; firstSeparatorIndex < commandLineLength; firstSeparatorIndex++)
+ {
+ if (char.IsSeparator(commandLine[firstSeparatorIndex])) { break; }
+ }
+ if (firstSeparatorIndex >= commandLineLength) { return; }
+ candidateFilePath = commandLine.Substring(0, firstSeparatorIndex);
+ }
+ if (!File.Exists(candidateFilePath)) { return; }
+ BochsExe = new FileInfo(candidateFilePath);
+ BochsDebugExe = new FileInfo(Path.Combine(BochsExe.Directory.FullName, "bochsdbg.exe"));
+ return;
+ }
+ }
+ catch { return; }
+ }
+ }
+}
diff --git a/source2/Debug/Cosmos.Debug.Common/Cosmos.Debug.Common.csproj b/source2/Debug/Cosmos.Debug.Common/Cosmos.Debug.Common.csproj
index eee5b7e58..ef59a5729 100644
--- a/source2/Debug/Cosmos.Debug.Common/Cosmos.Debug.Common.csproj
+++ b/source2/Debug/Cosmos.Debug.Common/Cosmos.Debug.Common.csproj
@@ -96,6 +96,7 @@
+
diff --git a/source2/Debug/Cosmos.Debug.VSDebugEngine/AD7.Impl/AD7Process.cs b/source2/Debug/Cosmos.Debug.VSDebugEngine/AD7.Impl/AD7Process.cs
index 61307f284..23b772b43 100644
--- a/source2/Debug/Cosmos.Debug.VSDebugEngine/AD7.Impl/AD7Process.cs
+++ b/source2/Debug/Cosmos.Debug.VSDebugEngine/AD7.Impl/AD7Process.cs
@@ -104,7 +104,12 @@ namespace Cosmos.Debug.VSDebugEngine {
mDbgConnector = null;
string xPort = mDebugInfo[BuildProperties.VisualStudioDebugPortString];
- var xParts = xPort.Split(' ');
+ var xParts = (null == xPort) ? null : xPort.Split(' ');
+ if ((null == xParts) || (2 > xParts.Length)) {
+ throw new Exception(string.Format(
+ "The '{0}' Cosmos project file property is either ill-formed or missing.",
+ BuildProperties.VisualStudioDebugPortString));
+ }
string xPortType = xParts[0].ToLower();
string xPortParam = xParts[1].ToLower();
@@ -168,6 +173,9 @@ namespace Cosmos.Debug.VSDebugEngine {
mHost = new Host.Slave(mDebugInfo, xUseGDB);
break;
case LaunchType.Bochs:
+ // The project has been created on another machine or Bochs has been uninstalled since the project has
+ // been created.
+ if (!BochsSupport.BochsEnabled) { throw new Exception(ResourceStrings.BochsIsNotInstalled); }
string bochsConfigurationFileName = mDebugInfo[BuildProperties.BochsEmulatorConfigurationFileString];
if (string.IsNullOrEmpty(bochsConfigurationFileName)) {
bochsConfigurationFileName = BuildProperties.BochsDefaultConfigurationFileName;
@@ -181,6 +189,9 @@ namespace Cosmos.Debug.VSDebugEngine {
// TODO : What if the configuration file doesn't exist ? This will throw a FileNotFoundException in
// the Bochs class constructor. Is this appropriate behavior ?
mHost = new Host.Bochs(mDebugInfo, xUseGDB, bochsConfigurationFile);
+ ((Host.Bochs)mHost).FixBochsConfiguration(new KeyValuePair[]
+ { new KeyValuePair("IsoFileName", mISO) }
+ );
break;
default:
throw new Exception("Invalid Launch value: '" + mLaunch + "'.");
diff --git a/source2/Debug/Cosmos.Debug.VSDebugEngine/Cosmos.Debug.VSDebugEngine.csproj b/source2/Debug/Cosmos.Debug.VSDebugEngine/Cosmos.Debug.VSDebugEngine.csproj
index d355efd91..2f3e323f8 100644
--- a/source2/Debug/Cosmos.Debug.VSDebugEngine/Cosmos.Debug.VSDebugEngine.csproj
+++ b/source2/Debug/Cosmos.Debug.VSDebugEngine/Cosmos.Debug.VSDebugEngine.csproj
@@ -181,8 +181,4 @@
-->
-
-
-
-
\ No newline at end of file
diff --git a/source2/Debug/Cosmos.Debug.VSDebugEngine/Host/Bochs.cs b/source2/Debug/Cosmos.Debug.VSDebugEngine/Host/Bochs.cs
index 6baa159cb..7dd745984 100644
--- a/source2/Debug/Cosmos.Debug.VSDebugEngine/Host/Bochs.cs
+++ b/source2/Debug/Cosmos.Debug.VSDebugEngine/Host/Bochs.cs
@@ -1,9 +1,4 @@
-// DO NOT remove this line. Consider commenting it out. When the symbol is enabled the Bochs debug
-// enbabled version will be launched instead of the regular one. The debug enabled version breaks
-// in Bochs internal debugger as soon as the emulator starts. You must use the 'c' (continue) command
-// in the Bochs console for the emulation to proceed.
-// #define USE_BOCHSDBG
-using System;
+using System;
using System.Collections.Specialized;
using System.Collections.Generic;
using System.Diagnostics;
@@ -13,26 +8,19 @@ using System.Text;
using Microsoft.Win32;
+using Cosmos.Build.Common;
+using Cosmos.Debug.Common;
+
namespace Cosmos.Debug.VSDebugEngine.Host
{
/// This class handles interactions with the Bochs emulation environment.
public class Bochs : Base
{
- /// The Bochs runtime.
- private static FileInfo _bochsExe;
-#if USE_BOCHSDBG
- /// The Bochs runtime with internal debugger enabled.
- private static FileInfo _bochsDebugExe;
-#endif
/// The emulator process once started.
private static Process _bochsProcess;
/// The configuration file to be used when launching the Bochs virtual machine.
private FileInfo _bochsConfigurationFile;
-
- static Bochs()
- {
- FindBochsExe();
- }
+ private bool _useDebugVersion;
/// Instanciation occurs when debugging engine is invoked to launch the process in suspended
/// mode. Bochs process will eventually be launched later when debugging engine is instructed to
@@ -43,53 +31,32 @@ namespace Cosmos.Debug.VSDebugEngine.Host
if (null == configurationFile) { throw new ArgumentNullException("configurationFile"); }
if (!configurationFile.Exists) { throw new FileNotFoundException("Configuration file doesn't exist."); }
_bochsConfigurationFile = configurationFile;
+ bool parseSucceeded = bool.TryParse(aParams[BuildProperties.EnableBochsDebugString], out _useDebugVersion);
+ return;
}
- /// Get a flag that tell whether Bochs is enabled on this system.
- public bool BochsEnabled
+ /// Fix the content of the configuration file, replacing each of the symbolic variable occurence
+ /// with its associated value.
+ /// A set of key/value pairs where the key is the name of a variable. The value is
+ /// used for variable replacement. Variables are case sensistive.
+ internal void FixBochsConfiguration(KeyValuePair[] symbols)
{
- get { return (null != _bochsExe); }
- }
+ if ((null == symbols) || (0 == symbols.Length)) { return; }
+ string content;
+ using (StreamReader reader = new StreamReader(File.Open(_bochsConfigurationFile.FullName, FileMode.Open, FileAccess.Read)))
+ {
+ content = reader.ReadToEnd();
+ }
+ foreach (KeyValuePair pair in symbols)
+ {
+ string variableName = string.Format("$({0})", pair.Key);
- /// Retrieve installation path for Bochs and initialize the field.
- /// Search is performed using the registry and rely on the shell command defined for the
- /// BochsConfigFile.
- private static void FindBochsExe()
- {
- using (var runCommandRegistryKey = Registry.ClassesRoot.OpenSubKey(@"BochsConfigFile\shell\Run\command", false)) {
- if (null == runCommandRegistryKey) { return; }
- string commandLine = (string)runCommandRegistryKey.GetValue(null, null);
- if (null != commandLine) { commandLine = commandLine.Trim(); }
- if (string.IsNullOrEmpty(commandLine)) { return; }
- // Now perform some parsing on command line to discover full exe path.
- string candidateFilePath;
- int commandLineLength = commandLine.Length;
- if ('"' == commandLine[0]) {
- // Seek for a non escaped double quote.
- int lastDoubleQuoteIndex = 1;
- for (; lastDoubleQuoteIndex < commandLineLength; lastDoubleQuoteIndex++) {
- if ('"' != commandLine[lastDoubleQuoteIndex]) { continue; }
- if ('\\' != commandLine[lastDoubleQuoteIndex - 1]) { break; }
- }
- if (lastDoubleQuoteIndex >= commandLineLength) { return; }
- candidateFilePath = commandLine.Substring(1, lastDoubleQuoteIndex - 1);
+ content.Replace(variableName, pair.Value);
}
- else {
- // Seek for first separator character.
- int firstSeparatorIndex = 0;
- for(; firstSeparatorIndex < commandLineLength; firstSeparatorIndex++) {
- if (char.IsSeparator(commandLine[firstSeparatorIndex])) { break; }
- }
- if (firstSeparatorIndex >= commandLineLength) { return; }
- candidateFilePath = commandLine.Substring(0, firstSeparatorIndex);
+ using (StreamWriter writer = new StreamWriter(File.Open(_bochsConfigurationFile.FullName, FileMode.Create, FileAccess.Write)))
+ {
+ writer.Write(content);
}
- if (!File.Exists(candidateFilePath)) { return; }
- _bochsExe = new FileInfo(candidateFilePath);
-#if USE_BOCHSDBG
- _bochsDebugExe = new FileInfo(Path.Combine(_bochsExe.Directory.FullName, "bochsdbg.exe"));
-#endif
- return;
- }
}
/// Initialize and start the Bochs process.
@@ -97,37 +64,39 @@ namespace Cosmos.Debug.VSDebugEngine.Host
{
_bochsProcess = new Process();
ProcessStartInfo _bochsStartInfo = _bochsProcess.StartInfo;
-#if USE_BOCHSDBG
- _bochsStartInfo.FileName = _bochsDebugExe.FullName;
-#else
- _bochsStartInfo.FileName = _bochsExe.FullName;
-#endif
+ _bochsStartInfo.FileName = (_useDebugVersion && BochsSupport.BochsDebugExe.Exists)
+ ? BochsSupport.BochsDebugExe.FullName
+ : BochsSupport.BochsExe.FullName;
// Start Bochs without displaying the configuration interface (-q) and using the specified
// configuration file (-f). The user is intended to edit the configuration file coming with
// the Cosmos project whenever she wants to modify the environment.
_bochsStartInfo.Arguments = string.Format("-q -f \"{0}\"", _bochsConfigurationFile.FullName);
_bochsStartInfo.WorkingDirectory = _bochsConfigurationFile.Directory.FullName;
+ _bochsStartInfo.UseShellExecute = false;
// Register for process completion event so that we can funnel it to any code that
// subscribed to this event in our base class.
_bochsProcess.EnableRaisingEvents = true;
- _bochsProcess.Exited += delegate(object sender, EventArgs e)
- {
- if (null != OnShutDown) { OnShutDown(sender, e); }
- };
+ _bochsProcess.Exited += ExitCallback;
_bochsProcess.Start();
return;
}
+ private void ExitCallback(object sender, EventArgs e)
+ {
+ if (null != OnShutDown) { try { OnShutDown(sender, e); } catch { } }
+ }
+
public override void Stop()
{
- // TODO BlueSkeye : How are we supposed to stop the bochs process ?
- CleanUp();
+ if (null != _bochsProcess) { try { _bochsProcess.Kill(); } catch { } }
+ CleanUp();
}
private void CleanUp()
{
- // TODO BlueSkeye : What kind of garbage may Bochs have left for us to clean ?
+ _bochsProcess.Exited -= ExitCallback;
+ // TODO BlueSkeye : What kind of garbage may Bochs have left for us to clean ?
}
}
}
diff --git a/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.Designer.cs b/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.Designer.cs
index b41565ee2..1c8842a1f 100644
--- a/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.Designer.cs
+++ b/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.Designer.cs
@@ -1,7 +1,7 @@
//------------------------------------------------------------------------------
//
// This code was generated by a tool.
-// Runtime Version:4.0.30319.1
+// Runtime Version:4.0.30319.276
//
// Changes to this file may cause incorrect behavior and will be lost if
// the code is regenerated.
@@ -60,6 +60,15 @@ namespace Cosmos.Debug.VSDebugEngine {
}
}
+ ///
+ /// Looks up a localized string similar to The Bochs emulator doesn't seem to be installed on this machine..
+ ///
+ internal static string BochsIsNotInstalled {
+ get {
+ return ResourceManager.GetString("BochsIsNotInstalled", resourceCulture);
+ }
+ }
+
///
/// Looks up a localized string similar to Cosmos Debug Engine.
///
diff --git a/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.resx b/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.resx
index 2be69097e..bdc3272ef 100644
--- a/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.resx
+++ b/source2/Debug/Cosmos.Debug.VSDebugEngine/ResourceStrings.resx
@@ -112,11 +112,14 @@
2.0
- System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+ System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
- System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+ The Bochs emulator doesn't seem to be installed on this machine.
+
Cosmos Debug Engine
diff --git a/source2/VSIP/Cosmos.VS.Package/CosmosPage.Designer.cs b/source2/VSIP/Cosmos.VS.Package/CosmosPage.Designer.cs
index 6111591ec..23ab5d67f 100644
--- a/source2/VSIP/Cosmos.VS.Package/CosmosPage.Designer.cs
+++ b/source2/VSIP/Cosmos.VS.Package/CosmosPage.Designer.cs
@@ -68,6 +68,8 @@
this.lboxDeployment = new System.Windows.Forms.ListBox();
this.tabLaunch = new System.Windows.Forms.TabPage();
this.lboxLaunch = new System.Windows.Forms.ListBox();
+ this.tabBochs = new System.Windows.Forms.TabPage();
+ this.checkEnableBochsDebug = new System.Windows.Forms.CheckBox();
this.tabVMware = new System.Windows.Forms.TabPage();
this.checkEnableGDB = new System.Windows.Forms.CheckBox();
this.checkStartCosmosGDB = new System.Windows.Forms.CheckBox();
@@ -99,6 +101,7 @@
this.tabUSB.SuspendLayout();
this.tabISO.SuspendLayout();
this.tabSlave.SuspendLayout();
+ this.tabBochs.SuspendLayout();
this.SuspendLayout();
//
// panel1
@@ -138,6 +141,7 @@
this.TabControl1.Controls.Add(this.tabDeployment);
this.TabControl1.Controls.Add(this.tabLaunch);
this.TabControl1.Controls.Add(this.tabVMware);
+ this.TabControl1.Controls.Add(this.tabBochs);
this.TabControl1.Controls.Add(this.tabPXE);
this.TabControl1.Controls.Add(this.tabUSB);
this.TabControl1.Controls.Add(this.tabISO);
@@ -546,6 +550,27 @@
this.lboxLaunch.Sorted = true;
this.lboxLaunch.TabIndex = 3;
//
+ // tabBochs
+ //
+ this.tabBochs.Controls.Add(this.checkEnableBochsDebug);
+ this.tabBochs.Location = new System.Drawing.Point(4, 22);
+ this.tabBochs.Name = "tabBochs";
+ this.tabBochs.Padding = new System.Windows.Forms.Padding(3);
+ this.tabBochs.Size = new System.Drawing.Size(627, 387);
+ this.tabBochs.TabIndex = 5;
+ this.tabBochs.Text = "Bochs";
+ this.tabBochs.UseVisualStyleBackColor = true;
+ //
+ // checkEnableBochsDebug
+ //
+ this.checkEnableBochsDebug.Font = new System.Drawing.Font("Segoe UI", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(0)));
+ this.checkEnableBochsDebug.Location = new System.Drawing.Point(9, 12);
+ this.checkEnableBochsDebug.Name = "checkEnableBochsDebug";
+ this.checkEnableBochsDebug.Size = new System.Drawing.Size(218, 20);
+ this.checkEnableBochsDebug.TabIndex = 25;
+ this.checkEnableBochsDebug.Text = "Enable Bochs Debugger";
+ this.checkEnableBochsDebug.UseVisualStyleBackColor = true;
+ //
// tabVMware
//
this.tabVMware.Controls.Add(this.checkEnableGDB);
@@ -609,7 +634,7 @@
this.tabPXE.Name = "tabPXE";
this.tabPXE.Padding = new System.Windows.Forms.Padding(3);
this.tabPXE.Size = new System.Drawing.Size(627, 387);
- this.tabPXE.TabIndex = 5;
+ this.tabPXE.TabIndex = 6;
this.tabPXE.Text = "PXE";
this.tabPXE.UseVisualStyleBackColor = true;
//
@@ -636,7 +661,7 @@
this.tabUSB.Name = "tabUSB";
this.tabUSB.Padding = new System.Windows.Forms.Padding(3);
this.tabUSB.Size = new System.Drawing.Size(627, 387);
- this.tabUSB.TabIndex = 6;
+ this.tabUSB.TabIndex = 7;
this.tabUSB.Text = "USB";
this.tabUSB.UseVisualStyleBackColor = true;
//
@@ -656,7 +681,7 @@
this.tabISO.Name = "tabISO";
this.tabISO.Padding = new System.Windows.Forms.Padding(3);
this.tabISO.Size = new System.Drawing.Size(627, 387);
- this.tabISO.TabIndex = 7;
+ this.tabISO.TabIndex = 8;
this.tabISO.Text = "ISO";
this.tabISO.UseVisualStyleBackColor = true;
//
@@ -733,6 +758,8 @@
this.panlDebugSettings.PerformLayout();
this.tabDeployment.ResumeLayout(false);
this.tabLaunch.ResumeLayout(false);
+ this.tabBochs.ResumeLayout(false);
+ this.tabBochs.PerformLayout();
this.tabVMware.ResumeLayout(false);
this.tabVMware.PerformLayout();
this.tabPXE.ResumeLayout(false);
@@ -779,6 +806,8 @@
private System.Windows.Forms.Label label5;
private System.Windows.Forms.Label label9;
private System.Windows.Forms.CheckBox checkIgnoreDebugStubAttribute;
+ private System.Windows.Forms.TabPage tabBochs;
+ private System.Windows.Forms.CheckBox checkEnableBochsDebug;
private System.Windows.Forms.TabPage tabVMware;
private System.Windows.Forms.CheckBox checkEnableGDB;
private System.Windows.Forms.CheckBox checkStartCosmosGDB;
diff --git a/source2/VSIP/Cosmos.VS.Package/CosmosPage.cs b/source2/VSIP/Cosmos.VS.Package/CosmosPage.cs
index 339dcfeb3..b8cbace92 100644
--- a/source2/VSIP/Cosmos.VS.Package/CosmosPage.cs
+++ b/source2/VSIP/Cosmos.VS.Package/CosmosPage.cs
@@ -45,8 +45,11 @@ namespace Cosmos.VS.Package {
}
protected ProfilePresets mPresets = new ProfilePresets();
- protected int mVMwareDebugPipe;
+ /// The index in the combo for the pipe name used by both
+ /// Bochs and VMware environment to communicate with Vsiual Studio debugger.
+ protected int mVMwareAndBochsDebugPipe;
+ protected bool mShowTabBochs;
protected bool mShowTabDebug;
protected bool mShowTabDeployment;
protected bool mShowTabLaunch;
@@ -81,6 +84,7 @@ namespace Cosmos.VS.Package {
RemoveTab(tabUSB);
RemoveTab(tabISO);
RemoveTab(tabSlave);
+ RemoveTab(tabBochs);
if (mShowTabDebug) {
TabControl1.TabPages.Add(tabDebug);
@@ -108,6 +112,9 @@ namespace Cosmos.VS.Package {
if (mShowTabSlave) {
TabControl1.TabPages.Add(tabSlave);
}
+ if (mShowTabBochs) {
+ TabControl1.TabPages.Add(tabBochs);
+ }
if (TabControl1.TabPages.Contains(xTab)) {
TabControl1.SelectedTab = xTab;
@@ -133,11 +140,18 @@ namespace Cosmos.VS.Package {
chckEnableDebugStub.Checked = true;
cmboCosmosDebugPort.Enabled = false;
cmboVisualStudioDebugPort.Enabled = false;
- cmboVisualStudioDebugPort.SelectedIndex = mVMwareDebugPipe;
+ cmboVisualStudioDebugPort.SelectedIndex = mVMwareAndBochsDebugPipe;
} else if (mProps.Profile == "PXE") {
chckEnableDebugStub.Checked = false;
+ } else if (mProps.Profile == "Bochs") {
+ mShowTabBochs = true;
+ chckEnableDebugStub.Checked = true;
+ cmboCosmosDebugPort.Enabled = false;
+ cmboVisualStudioDebugPort.Enabled = false;
+ cmboVisualStudioDebugPort.SelectedIndex = mVMwareAndBochsDebugPipe;
+
}
}
@@ -173,6 +187,7 @@ namespace Cosmos.VS.Package {
checkUseInternalAssembler.Checked = mProps.UseInternalAssembler;
checkEnableGDB.Checked = mProps.EnableGDB;
checkStartCosmosGDB.Checked = mProps.StartCosmosGDB;
+ checkEnableBochsDebug.Checked = mProps.EnableBochsDebug;
// Locked to COM1 for now.
cmboCosmosDebugPort.SelectedIndex = 0;
@@ -199,6 +214,7 @@ namespace Cosmos.VS.Package {
//
mShowTabVMware = mProps.Launch == LaunchType.VMware;
mShowTabSlave = mProps.Launch == LaunchType.Slave;
+ mShowTabBochs = (LaunchType.Bochs == mProps.Launch);
//
UpdateTabs();
}
@@ -274,6 +290,18 @@ namespace Cosmos.VS.Package {
if (xValue != mProps.Launch) {
mProps.Launch = xValue;
IsDirty = true;
+ // Bochs requires an ISO. Force Deployment property.
+ if (LaunchType.Bochs == xValue) {
+ if (DeploymentType.ISO != mProps.Deployment) {
+ foreach (EnumValue scannedValue in lboxDeployment.Items)
+ {
+ if (DeploymentType.ISO == (DeploymentType)scannedValue.Value) {
+ lboxDeployment.SelectedItem = scannedValue;
+ break;
+ }
+ }
+ }
+ }
}
};
#endregion
@@ -400,6 +428,16 @@ namespace Cosmos.VS.Package {
IsDirty = true;
}
};
+
+ checkEnableBochsDebug.CheckedChanged += delegate(Object sender, EventArgs e)
+ {
+ bool x = checkEnableBochsDebug.Checked;
+ if (x != mProps.EnableBochsDebug)
+ {
+ mProps.EnableBochsDebug = x;
+ IsDirty = true;
+ }
+ };
}
void butnProfileRename_Click(object sender, EventArgs e) {
@@ -532,7 +570,7 @@ namespace Cosmos.VS.Package {
cmboVisualStudioDebugPort.Items.Clear();
FillComPorts(cmboVisualStudioDebugPort.Items);
- mVMwareDebugPipe = cmboVisualStudioDebugPort.Items.Add(@"Pipe: Cosmos\Serial");
+ mVMwareAndBochsDebugPipe = cmboVisualStudioDebugPort.Items.Add(@"Pipe: Cosmos\Serial");
comboDebugMode.Items.AddRange(EnumValue.GetEnumValues(typeof(Cosmos.Build.Common.DebugMode), false));
comboTraceMode.Items.AddRange(EnumValue.GetEnumValues(typeof(TraceAssemblies), false));
diff --git a/source2/VSIP/Cosmos.VS.Package/ProfilePresets.cs b/source2/VSIP/Cosmos.VS.Package/ProfilePresets.cs
index ee3382f1d..a79b51bf3 100644
--- a/source2/VSIP/Cosmos.VS.Package/ProfilePresets.cs
+++ b/source2/VSIP/Cosmos.VS.Package/ProfilePresets.cs
@@ -3,6 +3,8 @@ using System.Collections.Generic;
using System.Linq;
using System.Text;
+using Cosmos.Debug.Common;
+
namespace Cosmos.VS.Package {
public class ProfilePresets : Dictionary {
public ProfilePresets() {
@@ -10,6 +12,7 @@ namespace Cosmos.VS.Package {
Add("USB", "USB Bootable Drive");
Add("PXE", "PXE Network Boot");
Add("VMware", "VMware");
+ if (BochsSupport.BochsEnabled) { Add("Bochs", "Bochs"); }
}
}
}
diff --git a/source2/VSIP/Cosmos.VS.Package/Templates/Projects/Cosmos/Cosmos.vstemplate b/source2/VSIP/Cosmos.VS.Package/Templates/Projects/Cosmos/Cosmos.vstemplate
index 8a6543416..dc8cade7d 100644
--- a/source2/VSIP/Cosmos.VS.Package/Templates/Projects/Cosmos/Cosmos.vstemplate
+++ b/source2/VSIP/Cosmos.VS.Package/Templates/Projects/Cosmos/Cosmos.vstemplate
@@ -10,6 +10,7 @@
+ Cosmos.bxrc
\ No newline at end of file
diff --git a/source2/VSIP/Cosmos.VS.Package/Templates/Projects/CosmosProject (C#)/Proj/CosmosProj.vstemplate b/source2/VSIP/Cosmos.VS.Package/Templates/Projects/CosmosProject (C#)/Proj/CosmosProj.vstemplate
index 8d3b8f2f5..812256e3d 100644
--- a/source2/VSIP/Cosmos.VS.Package/Templates/Projects/CosmosProject (C#)/Proj/CosmosProj.vstemplate
+++ b/source2/VSIP/Cosmos.VS.Package/Templates/Projects/CosmosProject (C#)/Proj/CosmosProj.vstemplate
@@ -12,7 +12,9 @@
true-->
-
+
+ Cosmos.bxrc
+
Cosmos.VS.Package, Version=1.0.0.0, Culture=neutral, PublicKeyToken=f4d94ac959d59ec3
diff --git a/source2/VSIP/Cosmos.VS.Wizards/Cosmos.VS.Wizards.csproj b/source2/VSIP/Cosmos.VS.Wizards/Cosmos.VS.Wizards.csproj
index 100ae18ee..16ff23aa1 100644
--- a/source2/VSIP/Cosmos.VS.Wizards/Cosmos.VS.Wizards.csproj
+++ b/source2/VSIP/Cosmos.VS.Wizards/Cosmos.VS.Wizards.csproj
@@ -64,6 +64,7 @@
+
diff --git a/source2/VSIP/Cosmos.VS.Wizards/Cosmos.bxrc b/source2/VSIP/Cosmos.VS.Wizards/Cosmos.bxrc
new file mode 100644
index 000000000..fcdecc6b4
--- /dev/null
+++ b/source2/VSIP/Cosmos.VS.Wizards/Cosmos.bxrc
@@ -0,0 +1,44 @@
+# configuration file generated by Bochs
+plugin_ctrl: unmapped=1, biosdev=1, speaker=1, extfpuirq=1, parallel=1, serial=1, gameport=1
+config_interface: win32config
+display_library: win32
+memory: host=256, guest=256
+romimage: file="C:\Program Files (x86)\Bochs-2.6/BIOS-bochs-latest"
+vgaromimage: file="C:\Program Files (x86)\Bochs-2.6/VGABIOS-lgpl-latest"
+boot: cdrom
+floppy_bootsig_check: disabled=0
+# no floppya
+# no floppyb
+ata0: enabled=1, ioaddr1=0x1f0, ioaddr2=0x3f0, irq=14
+ata0-master: type=cdrom, path=".\$CosmosProjectName$.iso", status=inserted, biosdetect=auto, model="Generic 1234"
+ata1: enabled=1, ioaddr1=0x170, ioaddr2=0x370, irq=15
+ata2: enabled=0
+ata3: enabled=0
+pci: enabled=1, chipset=i440fx
+vga: extension=vbe, update_freq=5
+cpu: count=1, ips=4000000, model=bx_generic, reset_on_triple_fault=1, cpuid_limit_winnt=0, ignore_bad_msrs=1, mwait_is_nop=0
+cpuid: family=6, model=0x03, stepping=3, mmx=1, apic=xapic, sse=sse2, sse4a=0, sep=1, aes=0, xsave=0, xsaveopt=0, movbe=0, adx=0, smep=0, x86_64=1, 1g_pages=0, pcid=0, fsgsbase=0, mwait=1
+cpuid: vendor_string="GenuineIntel"
+cpuid: brand_string=" Intel(R) Pentium(R) 4 CPU "
+
+print_timestamps: enabled=0
+port_e9_hack: enabled=0
+private_colormap: enabled=0
+clock: sync=none, time0=local, rtc_sync=0
+# no cmosimage
+# no loader
+log: -
+logprefix: %t%e%d
+panic: action=ask
+error: action=report
+info: action=report
+debug: action=ignore
+keyboard: type=mf, serial_delay=250, paste_delay=100000, keymap=
+user_shortcut: keys=none
+mouse: enabled=0, type=ps2, toggle=ctrl+mbutton
+parport1: enabled=1, file=""
+parport2: enabled=0
+com1: enabled=1, mode=pipe-client, dev=\\.\pipe\Cosmos\Serial
+com2: enabled=0
+com3: enabled=0
+com4: enabled=0
diff --git a/source2/VSIP/Cosmos.VS.Wizards/GenerateCosmosProjectWizard.cs b/source2/VSIP/Cosmos.VS.Wizards/GenerateCosmosProjectWizard.cs
index e5b1e3827..01663afcb 100644
--- a/source2/VSIP/Cosmos.VS.Wizards/GenerateCosmosProjectWizard.cs
+++ b/source2/VSIP/Cosmos.VS.Wizards/GenerateCosmosProjectWizard.cs
@@ -8,14 +8,18 @@ using EnvDTE;
namespace Cosmos.VS.Package.Templates {
public class GenerateCosmosProjectWizard : IWizard {
+ private const string BochsConfigurationFileName = "Cosmos.bxrc";
+
public void BeforeOpeningFile(EnvDTE.ProjectItem projectItem) {
}
- private static string GetTemplateString() {
+ private static string GetTemplate(string templateName)
+ {
var xAsm = typeof(GenerateCosmosProjectWizard).Assembly;
- using (var xStream = xAsm.GetManifestResourceStream(typeof(Cosmos.VS.Wizards.ResHelper), "CosmosProject.Cosmos")) {
+ using (var xStream = xAsm.GetManifestResourceStream(typeof(Cosmos.VS.Wizards.ResHelper), templateName))
+ {
if (xStream == null) {
- MessageBox.Show("Could not find template manifest stream!");
+ MessageBox.Show("Could not find template manifest stream : " + templateName);
return null;
}
using (var xReader = new StreamReader(xStream)) {
@@ -24,10 +28,18 @@ namespace Cosmos.VS.Package.Templates {
}
}
+ private static string GetBochsConfigurationFileTemplate() {
+ return GetTemplate(BochsConfigurationFileName);
+ }
+
+ private static string GetProjectFileTemplate() {
+ return GetTemplate("CosmosProject.Cosmos");
+ }
+
public void ProjectFinishedGenerating(EnvDTE.Project project) {
// add Cosmos template to solution
// read embedded template file
- var xInputString = GetTemplateString();
+ var xInputString = GetProjectFileTemplate();
if (xInputString == null) {
return;
}
@@ -60,6 +72,16 @@ namespace Cosmos.VS.Package.Templates {
}
}
+ // Copy Bochs configuration file.
+ xInputString = GetBochsConfigurationFileTemplate();
+ if (xInputString == null) {
+ return;
+ }
+ xInputString = xInputString.Replace("$CosmosProjectName$", project.Name + "Boot");
+ xFilename = Path.GetDirectoryName(project.FullName);
+ xFilename = Path.Combine(xFilename, BochsConfigurationFileName);
+ File.WriteAllText(xFilename, xInputString);
+
// set Cosmos Boot as startup project
project.DTE.Windows.Item(EnvDTE.Constants.vsWindowKindSolutionExplorer).Activate();
EnvDTE.UIHierarchy hierarchy = project.DTE.ActiveWindow.Object as EnvDTE.UIHierarchy;