Skip to content

Commit

Permalink
Merge branch 'develop' into 'master'
Browse files Browse the repository at this point in the history
Develop

See merge request company-projects/Meadow!52
  • Loading branch information
zone117x committed Oct 10, 2018
2 parents d09862f + c6cd398 commit 4da446f
Show file tree
Hide file tree
Showing 13 changed files with 194 additions and 64 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -661,6 +661,7 @@ private string GetExceptionMessage(ExecutionTraceException traceException)
{
message.AppendLine(GetCallStackString(traceException.TraceIndex.Value));
}

return message.ToString().TrimEnd();
}

Expand Down
20 changes: 12 additions & 8 deletions src/Meadow.DebugExampleTests/.vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,17 @@
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
"name": ".NET Core Launch (console)",
"type": "coreclr",
"request": "launch",
//"preLaunchTask": "build",
"program": "${workspaceFolder}/bin/Debug/netcoreapp2.1/Meadow.DebugExampleTests.dll",
"args": [],
"cwd": "${workspaceFolder}",
"stopAtEntry": false,
"console": "internalConsole"
},
{
"type": "solidityMeadow",
"request": "launch",
Expand All @@ -13,7 +24,6 @@
"type": "solidityMeadow",
"request": "launch",
"name": "Solidity Meadow",
"program": "${workspaceFolder}/test.sol",
"stopOnEntry": false,
"logFile": "./debugger_trace.txt",
"testAssembly": "./bin/Debug/netcoreapp2.1/Meadow.DebugExampleTests.dll",
Expand All @@ -38,11 +48,5 @@
"VSTEST_HOST_DEBUG": "1"
}
}
],
"compounds": [
{
"name": "Both Meadow",
"configurations": [ "Solidity Meadow", "Unit Tests" ]
}
]
]
}
17 changes: 17 additions & 0 deletions src/Meadow.DebugExampleTests/.vscode/tasks.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"label": "build",
"command": "dotnet build",
"type": "shell",
"group": "build",
"presentation": {
"reveal": "silent"
},
"problemMatcher": "$msCompile"
}
]
}
53 changes: 34 additions & 19 deletions src/Meadow.UnitTestTemplate/Debugging.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,16 @@ namespace Meadow.UnitTestTemplate
public class Debugging : IDisposable
{

public static bool IsSolidityDebuggerAttached { get; set; }

public static string SolidityDebugSessionID => Environment.GetEnvironmentVariable("DEBUG_SESSION_ID");

public static bool HasSolidityDebugAttachRequest => !string.IsNullOrWhiteSpace(SolidityDebugSessionID);


public static void Launch()
{
var debugSessionID = Environment.GetEnvironmentVariable("DEBUG_SESSION_ID");
if (string.IsNullOrWhiteSpace(debugSessionID))
if (!HasSolidityDebugAttachRequest)
{
MSTestRunner.RunAllTests(Assembly.GetExecutingAssembly());
}
Expand All @@ -32,31 +38,40 @@ public static void Launch()
Debugger.Launch();
}

using (var debuggingInstance = new Debugging(debugSessionID))
{
debuggingInstance.InitializeDebugConnection();
debuggingInstance.SetupRpcDebuggingHook();

var cancelToken = new CancellationTokenSource();

debuggingInstance.OnDebuggerDisconnect += () =>
{
// If the C# debugger is not attached, we don't care about running the rest of the tests
// so exit program
if (!Debugger.IsAttached)
{
cancelToken.Cancel();
Environment.Exit(0);
}
};

var cancelToken = new CancellationTokenSource();

using (AttachSolidityDebugger(cancelToken))
{
// Run all tests (blocking)
MSTestRunner.RunAllTests(Assembly.GetExecutingAssembly(), cancelToken.Token);
Console.WriteLine("Tests completed");
}
}
}

public static IDisposable AttachSolidityDebugger(CancellationTokenSource cancelToken)
{
var debuggingInstance = new Debugging(SolidityDebugSessionID);

debuggingInstance.InitializeDebugConnection();
IsSolidityDebuggerAttached = true;
debuggingInstance.SetupRpcDebuggingHook();

debuggingInstance.OnDebuggerDisconnect += () =>
{
// If the C# debugger is not attached, we don't care about running the rest of the tests
// so exit program
if (!Debugger.IsAttached)
{
cancelToken.Cancel();
Environment.Exit(0);
}
};

return debuggingInstance;
}

readonly string _debugSessionID;
readonly NamedPipeServerStream _pipeServer;
readonly MeadowSolidityDebugAdapter _debugAdapter;
Expand Down
36 changes: 26 additions & 10 deletions src/Meadow.UnitTestTemplate/Global.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
using System.Runtime.CompilerServices;
using System.Runtime.Loader;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

[assembly: Parallelize(Workers = 0, Scope = ExecutionScope.MethodLevel)]
Expand Down Expand Up @@ -116,24 +117,41 @@ public static class Global
//static readonly Dictionary<string, string[]> AppConfigValues = new Dictionary<string, string[]>();
static (string Key, string Value)[] appConfigValues;

static Action _debuggerCleanup;

static Global()
{
if (!Debugging.IsSolidityDebuggerAttached && Debugging.HasSolidityDebugAttachRequest)
{
var cancelToken = new CancellationTokenSource();
var debuggerDisposal = Debugging.AttachSolidityDebugger(cancelToken);
_debuggerCleanup = () =>
{
_debuggerCleanup = null;
if (!cancelToken.IsCancellationRequested)
{
cancelToken.Cancel();
debuggerDisposal.Dispose();
}
};
}


// Hook onto events for after tests have ran so we can call
// cleanup which does report generation.
// Its unclear which of these may or may not work in any given
// execution context and operating system, so hook to both.
// HOWEVER, neither seem to be called while running
// tests through test panels or `dotnet test`
AppDomain.CurrentDomain.ProcessExit += CurrentDomain_ProcessExit;
AssemblyLoadContext.Default.Unloading += Default_Unloading;
AppDomain.CurrentDomain.ProcessExit += (s, e) => OnProcessExit();
AssemblyLoadContext.Default.Unloading += (s) => OnProcessExit();

// Initialize our test variables.
TestServicesPool = new AsyncObjectPool<TestServices>(CreateTestServicesInstance);
CoverageMaps = new ConcurrentBag<(CompoundCoverageMap Coverage, SolcBytecodeInfo Contract)[]>();
UnitTestResults = new ConcurrentBag<UnitTestResult>();


var thisAsm = Assembly.GetExecutingAssembly().GetName().Name;
var unitTestAssembly = AppDomain.CurrentDomain
.GetAssemblies()
Expand All @@ -145,20 +163,18 @@ static Global()

ParseAppConfigSettings(unitTestAssembly);

}
//var dtest = Environment.GetEnvironmentVariable("MEADOW_SOLIDITY_DEBUG_SESSION");
//var debugSessionID = Environment.GetEnvironmentVariable("DEBUG_SESSION_ID");

private static void Default_Unloading(AssemblyLoadContext obj)
{
// Perform report generation on progrma exit.
// (The cleanup method handles itself when being called multiple times).
Cleanup().GetAwaiter().GetResult();
//File.AppendAllLines("/Users/matthewlittle/Desktop/log.txt", new[] { "ENV TEST: " + debugSessionID });
}

private static void CurrentDomain_ProcessExit(object sender, EventArgs e)
static void OnProcessExit()
{
// Perform report generation on progrma exit.
// (The cleanup method handles itself when being called multiple times).
Cleanup().GetAwaiter().GetResult();
_debuggerCleanup?.Invoke();
}

static void ParseAppConfigSettings(Assembly callingAssembly)
Expand Down
15 changes: 6 additions & 9 deletions src/Meadow.VSCode.Debugger/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,8 @@
"activationEvents": [
"onDebug",
"onDebugInitialConfigurations",
"onCommand:extension.meadow.vscode.debugger.getDebuggerPath"
"onCommand:extension.meadow.vscode.debugger.getDebuggerPath",
"workspaceContains:**/*.sol"
],
"contributes": {
"languages": [
Expand All @@ -83,6 +84,10 @@
}
],
"debuggers": [
{
"type": "coreclr",
"label": "Meadow C# Unit Test Hook"
},
{
"type": "solidityMeadow",
"label": "Solidity Debug",
Expand All @@ -98,15 +103,7 @@
}
},
"launch": {
"required": [
"program"
],
"properties": {
"program": {
"type": "string",
"description": "Absolute path to a text file.",
"default": "${workspaceFolder}"
},
"stopOnEntry": {
"type": "boolean",
"description": "Automatically stop after launch.",
Expand Down
71 changes: 71 additions & 0 deletions src/Meadow.VSCode.Debugger/src/clrDebugConfigProvider.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
import * as vscode from 'vscode';
import { DEBUG_SESSION_ID, SOLIDITY_MEADOW_TYPE } from './constants';
import * as uuid from 'uuid/v1';
import { Logger } from './logger';
import * as common from './common';

export class ClrDebugConfigProvider implements vscode.DebugConfigurationProvider {

private _context: vscode.ExtensionContext;

constructor(context: vscode.ExtensionContext) {
this._context = context;
}

/**
* Provides initial [debug configuration](#DebugConfiguration). If more than one debug configuration provider is
* registered for the same type, debug configurations are concatenated in arbitrary order.
*
* @param folder The workspace folder for which the configurations are used or undefined for a folderless setup.
* @param token A cancellation token.
* @return An array of [debug configurations](#DebugConfiguration).
*/
provideDebugConfigurations?(folder: vscode.WorkspaceFolder | undefined, token?: vscode.CancellationToken): vscode.ProviderResult<vscode.DebugConfiguration[]> {
// We have nothing to add here. Implemented to just fulfill the interface.
return [];
}

/**
* Resolves a [debug configuration](#DebugConfiguration) by filling in missing values or by adding/changing/removing attributes.
* If more than one debug configuration provider is registered for the same type, the resolveDebugConfiguration calls are chained
* in arbitrary order and the initial debug configuration is piped through the chain.
* Returning the value 'undefined' prevents the debug session from starting.
*
* @param folder The workspace folder from which the configuration originates from or undefined for a folderless setup.
* @param debugConfiguration The [debug configuration](#DebugConfiguration) to resolve.
* @param token A cancellation token.
* @return The resolved debug configuration or undefined.
*/
resolveDebugConfiguration?(folder: vscode.WorkspaceFolder | undefined, debugConfiguration: vscode.DebugConfiguration, token?: vscode.CancellationToken): vscode.ProviderResult<vscode.DebugConfiguration> {

// Check if the solidity debugger has already been launched and set the session ID
if (debugConfiguration.env && debugConfiguration.env[DEBUG_SESSION_ID]) {
return debugConfiguration;
}

let config : any = debugConfiguration;
if (!config.env) {
config.env = {};
}

let debugSessionID = uuid();
config.env[DEBUG_SESSION_ID] = debugSessionID;

let workspaceFolder = common.getWorkspaceFolder();

let unitTestRunnerDebugConfig: vscode.DebugConfiguration = {
name: "Solidity Debugger",
type: SOLIDITY_MEADOW_TYPE,
request: "launch",
cwd: workspaceFolder.uri.fsPath,
[DEBUG_SESSION_ID]: debugSessionID
};

Logger.log(`Launching dotnet debugger for: ${JSON.stringify(unitTestRunnerDebugConfig)}`);

vscode.debug.startDebugging(workspaceFolder, unitTestRunnerDebugConfig);

return config;
}

}
2 changes: 2 additions & 0 deletions src/Meadow.VSCode.Debugger/src/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ import * as vscode from 'vscode';

export const SOLIDITY_MEADOW_TYPE: string = 'solidityMeadow';

export const DEBUG_SESSION_ID: string = 'DEBUG_SESSION_ID';

export interface ISolidityMeadowDebugConfig extends vscode.DebugConfiguration {
readonly stopOnEntry?: boolean;
readonly debugAdapterFile?: string;
Expand Down
4 changes: 2 additions & 2 deletions src/Meadow.VSCode.Debugger/src/debugAdapterExecutable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import * as fs from 'fs';
import * as path from 'path';
import { IDebugAdapterExecutable, ISolidityMeadowDebugConfig } from './constants';
import { Logger } from './logger';
import { SOLIDITY_MEADOW_TYPE } from './constants';
import { DEBUG_SESSION_ID, SOLIDITY_MEADOW_TYPE } from './constants';

export async function resolveMeadowDebugAdapter(context: vscode.ExtensionContext, debugSessionID: string, debugConfig?: ISolidityMeadowDebugConfig): Promise<IDebugAdapterExecutable> {

Expand Down Expand Up @@ -44,7 +44,7 @@ export async function resolveMeadowDebugAdapter(context: vscode.ExtensionContext
type: "executable",
command: "dotnet",
args: args,
env: { "DEBUG_SESSION_ID": debugSessionID }
env: { [DEBUG_SESSION_ID]: debugSessionID }
};

Logger.log(`Launching debug adapter with: ${JSON.stringify(launchInfo)}`);
Expand Down

0 comments on commit 4da446f

Please sign in to comment.