-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
4300015
commit b49b860
Showing
9 changed files
with
612 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
|
||
Microsoft Visual Studio Solution File, Format Version 12.00 | ||
# Visual Studio Version 16 | ||
VisualStudioVersion = 16.0.31624.102 | ||
MinimumVisualStudioVersion = 10.0.40219.1 | ||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "BSABR", "BSABR\BSABR.csproj", "{7B474A17-7931-4385-A6C3-0045B17FD9EC}" | ||
EndProject | ||
Global | ||
GlobalSection(SolutionConfigurationPlatforms) = preSolution | ||
Debug|Any CPU = Debug|Any CPU | ||
Release|Any CPU = Release|Any CPU | ||
EndGlobalSection | ||
GlobalSection(ProjectConfigurationPlatforms) = postSolution | ||
{7B474A17-7931-4385-A6C3-0045B17FD9EC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | ||
{7B474A17-7931-4385-A6C3-0045B17FD9EC}.Debug|Any CPU.Build.0 = Debug|Any CPU | ||
{7B474A17-7931-4385-A6C3-0045B17FD9EC}.Release|Any CPU.ActiveCfg = Release|Any CPU | ||
{7B474A17-7931-4385-A6C3-0045B17FD9EC}.Release|Any CPU.Build.0 = Release|Any CPU | ||
EndGlobalSection | ||
GlobalSection(SolutionProperties) = preSolution | ||
HideSolutionNode = FALSE | ||
EndGlobalSection | ||
GlobalSection(ExtensibilityGlobals) = postSolution | ||
SolutionGuid = {E5B22D7B-0383-41CE-B986-DDC48207B64B} | ||
EndGlobalSection | ||
EndGlobal |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
<?xml version="1.0" encoding="utf-8" ?> | ||
<configuration> | ||
<startup> | ||
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7.2" /> | ||
</startup> | ||
</configuration> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
// Copyright © 2021 Matt Sullivan | ||
|
||
using System.Linq; | ||
|
||
namespace Bsabr | ||
{ | ||
/// <summary> | ||
/// Extracts string arguments for B-SABR into a more easy to use object. | ||
/// </summary> | ||
class ArgParser | ||
{ | ||
private readonly string[] _args; | ||
|
||
/// <summary> | ||
/// Initializes a new instance of the <see cref="ArgParser"/> class. | ||
/// </summary> | ||
/// <param name="args">The arguments to extract.</param> | ||
private ArgParser(string[] args) | ||
{ | ||
_args = args; | ||
} | ||
|
||
/// <summary> | ||
/// Gets a new instance of the <see cref="ArgParser"/> class. | ||
/// </summary> | ||
/// <param name="args">The arguments that the ArgParser should process.</param> | ||
/// <returns>An <see cref="ArgParser"/> for the specified <paramref name="args"/>.</returns> | ||
public static ArgParser InitializeNew(string[] args) | ||
{ | ||
return new ArgParser(args); | ||
} | ||
|
||
/// <summary> | ||
/// Gets the options that this <see cref="ArgParser"/>'s arguments specified. | ||
/// </summary> | ||
/// <returns>The options that were represented by the arguments.</returns> | ||
internal Options GetOptions() | ||
{ | ||
// help will have been requested if the first of the arguments match a normal help string | ||
var helpRequested = _args.FirstOrDefault() == "/?" || _args.FirstOrDefault() == "/help"; | ||
|
||
// studio file name will be the first argument (as long as that wasn't the help arg) | ||
var studioFileName = helpRequested ? null : _args.FirstOrDefault(); | ||
|
||
// whether or not the caller is requesting build output to be saved to a file | ||
var outFileSpecified = _args.Any(a => a == "/out"); | ||
|
||
// output filename will be the first argument after the "/out" filename | ||
var outFileName = outFileSpecified ? _args.SkipWhile(a => a != "/out").Skip(1).FirstOrDefault() : null; | ||
|
||
// studio arguments will be all of the arguments after the first argument | ||
var studioArgs = helpRequested ? null : string.Join(" ", _args.Skip(1)); | ||
|
||
return new Options(studioFileName, outFileName, outFileSpecified, studioArgs, helpRequested); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,155 @@ | ||
// Copyright © 2021 Matt Sullivan | ||
|
||
using System; | ||
using System.IO; | ||
using System.Text; | ||
|
||
namespace Bsabr | ||
{ | ||
/// <summary> | ||
/// Validates options for the process instance. | ||
/// </summary> | ||
class ArgValidator | ||
{ | ||
private readonly Options _options; | ||
private readonly string _errorMessage; | ||
|
||
/// <summary> | ||
/// Initializes a new instance of the <see cref="ArgValidator"/> class. | ||
/// </summary> | ||
/// <param name="options">The <see cref="Options"/> to validate.</param> | ||
public ArgValidator(Options options) | ||
{ | ||
_options = options; | ||
|
||
if (!_options.HelpRequested) | ||
{ | ||
_errorMessage = GetErrorMessage(); | ||
} | ||
} | ||
|
||
/// <summary> | ||
/// Summary of what is wrong with the options. | ||
/// </summary> | ||
public string ErrorMessage => _errorMessage; | ||
|
||
/// <summary> | ||
/// Indicates whether or not the options for this <see cref="ArgValidator"/> are valid. | ||
/// </summary> | ||
public bool OptionsAreValid => _errorMessage == null; | ||
|
||
/// <summary> | ||
/// Determines whether an <see cref="Options"/> is suitable for the program to execute. | ||
/// </summary> | ||
/// <param name="options">The configuration to validate.</param> | ||
/// <returns>An error message, if an error occurred. <c>null</c> otherwise.</returns> | ||
private string GetErrorMessage() | ||
{ | ||
var errorBuilder = new StringBuilder(); | ||
|
||
var studioExecutableErrorMessage = GetStudioExecutableErrorString(); | ||
|
||
if (studioExecutableErrorMessage != null) | ||
{ | ||
errorBuilder.AppendLine($"\t- {studioExecutableErrorMessage}"); | ||
} | ||
|
||
var outFileNameErrorMessage = GetOutFileNameErrorString(); | ||
|
||
if (outFileNameErrorMessage != null) | ||
{ | ||
errorBuilder.AppendLine($"\t- {outFileNameErrorMessage}"); | ||
} | ||
|
||
if (errorBuilder.Length > 0) | ||
{ | ||
return $"The following error(s) occurred: \n{errorBuilder}"; | ||
} | ||
|
||
return null; | ||
} | ||
|
||
/// <summary> | ||
/// Gets an error string based on the specified output filename. | ||
/// </summary> | ||
/// <returns>An error message if the argument is invalid, <c>null</c> otherwise.</returns> | ||
private string GetOutFileNameErrorString() | ||
{ | ||
if (_options.OutFileName == null) | ||
{ | ||
if (_options.OutFileSpecified) | ||
{ | ||
return "The \"/out\" argument should be followed by a valid file path."; | ||
} | ||
|
||
return null; | ||
} | ||
|
||
try | ||
{ | ||
var attributes = File.GetAttributes(_options.OutFileName); | ||
} | ||
catch (ArgumentException) | ||
{ | ||
return "Invalid output file path. Path is empty, contains only white spaces, or contains invalid characters."; | ||
} | ||
catch (PathTooLongException) | ||
{ | ||
return "Output file path is too long. File paths should be less than 260 characters."; | ||
} | ||
catch (NotSupportedException) | ||
{ | ||
return "Output file path is in an invalid format."; | ||
} | ||
catch (FileNotFoundException) | ||
{ | ||
// Not a problem in this scenario as we will be creating the file | ||
} | ||
catch (DirectoryNotFoundException) | ||
{ | ||
return "Output file path represents a directory and is invalid, such as being on an unmapped drive, or the directory cannot be found."; | ||
} | ||
catch (IOException) | ||
{ | ||
return "Output file path is to a file that is in use by another process."; | ||
} | ||
catch (UnauthorizedAccessException) | ||
{ | ||
return "You do not have permission to access the file specified as the output file path argument."; | ||
} | ||
|
||
return null; | ||
} | ||
|
||
/// <summary> | ||
/// Gets an error string based on the specified path to AtmelStudio.exe. | ||
/// </summary> | ||
/// <returns>An error message if the argument is invalid, <c>null</c> otherwise.</returns> | ||
private string GetStudioExecutableErrorString() | ||
{ | ||
bool fileExists = File.Exists(_options.StudioExecutable); | ||
|
||
if (!fileExists) | ||
{ | ||
// see if it exists on the path somewhere | ||
foreach (var evt in Enum.GetValues(typeof(EnvironmentVariableTarget))) | ||
{ | ||
var paths = Environment.GetEnvironmentVariable("PATH", (EnvironmentVariableTarget)evt).Split(';'); | ||
|
||
foreach (var path in paths) | ||
{ | ||
if (File.Exists(_options.StudioExecutable)) | ||
{ | ||
fileExists = true; | ||
break; | ||
} | ||
} | ||
} | ||
|
||
return "The specified Atmel Studio/Microchip Studio executable does not exist. Make sure you have entered the path correctly and that you have permission to access the executable."; | ||
} | ||
|
||
return null; | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,86 @@ | ||
<?xml version="1.0" encoding="utf-8"?> | ||
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> | ||
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" /> | ||
<PropertyGroup> | ||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> | ||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform> | ||
<ProjectGuid>{7B474A17-7931-4385-A6C3-0045B17FD9EC}</ProjectGuid> | ||
<OutputType>Exe</OutputType> | ||
<RootNamespace>Bsabr</RootNamespace> | ||
<AssemblyName>bsabr</AssemblyName> | ||
<TargetFrameworkVersion>v4.7.2</TargetFrameworkVersion> | ||
<FileAlignment>512</FileAlignment> | ||
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects> | ||
<Deterministic>true</Deterministic> | ||
<PublishUrl>publish\</PublishUrl> | ||
<Install>true</Install> | ||
<InstallFrom>Disk</InstallFrom> | ||
<UpdateEnabled>false</UpdateEnabled> | ||
<UpdateMode>Foreground</UpdateMode> | ||
<UpdateInterval>7</UpdateInterval> | ||
<UpdateIntervalUnits>Days</UpdateIntervalUnits> | ||
<UpdatePeriodically>false</UpdatePeriodically> | ||
<UpdateRequired>false</UpdateRequired> | ||
<MapFileExtensions>true</MapFileExtensions> | ||
<ApplicationRevision>0</ApplicationRevision> | ||
<ApplicationVersion>1.0.0.%2a</ApplicationVersion> | ||
<IsWebBootstrapper>false</IsWebBootstrapper> | ||
<UseApplicationTrust>false</UseApplicationTrust> | ||
<BootstrapperEnabled>true</BootstrapperEnabled> | ||
</PropertyGroup> | ||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' "> | ||
<PlatformTarget>AnyCPU</PlatformTarget> | ||
<DebugSymbols>true</DebugSymbols> | ||
<DebugType>full</DebugType> | ||
<Optimize>false</Optimize> | ||
<OutputPath>bin\Debug\</OutputPath> | ||
<DefineConstants>DEBUG;TRACE</DefineConstants> | ||
<ErrorReport>prompt</ErrorReport> | ||
<WarningLevel>4</WarningLevel> | ||
<Prefer32Bit>false</Prefer32Bit> | ||
</PropertyGroup> | ||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' "> | ||
<PlatformTarget>AnyCPU</PlatformTarget> | ||
<DebugType>pdbonly</DebugType> | ||
<Optimize>true</Optimize> | ||
<OutputPath>bin\Release\</OutputPath> | ||
<DefineConstants>TRACE</DefineConstants> | ||
<ErrorReport>prompt</ErrorReport> | ||
<WarningLevel>4</WarningLevel> | ||
<Prefer32Bit>false</Prefer32Bit> | ||
</PropertyGroup> | ||
<ItemGroup> | ||
<Reference Include="System" /> | ||
<Reference Include="System.Core" /> | ||
<Reference Include="System.Management" /> | ||
<Reference Include="System.Xml.Linq" /> | ||
<Reference Include="System.Data.DataSetExtensions" /> | ||
<Reference Include="Microsoft.CSharp" /> | ||
<Reference Include="System.Data" /> | ||
<Reference Include="System.Net.Http" /> | ||
<Reference Include="System.Xml" /> | ||
</ItemGroup> | ||
<ItemGroup> | ||
<Compile Include="ArgParser.cs" /> | ||
<Compile Include="ArgValidator.cs" /> | ||
<Compile Include="Options.cs" /> | ||
<Compile Include="Program.cs" /> | ||
<Compile Include="Properties\AssemblyInfo.cs" /> | ||
</ItemGroup> | ||
<ItemGroup> | ||
<None Include="App.config" /> | ||
</ItemGroup> | ||
<ItemGroup> | ||
<BootstrapperPackage Include=".NETFramework,Version=v4.7.2"> | ||
<Visible>False</Visible> | ||
<ProductName>Microsoft .NET Framework 4.7.2 %28x86 and x64%29</ProductName> | ||
<Install>true</Install> | ||
</BootstrapperPackage> | ||
<BootstrapperPackage Include="Microsoft.Net.Framework.3.5.SP1"> | ||
<Visible>False</Visible> | ||
<ProductName>.NET Framework 3.5 SP1</ProductName> | ||
<Install>false</Install> | ||
</BootstrapperPackage> | ||
</ItemGroup> | ||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" /> | ||
</Project> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
// Copyright © 2021 Matt Sullivan | ||
|
||
namespace Bsabr | ||
{ | ||
/// <summary> | ||
/// Represents the command line options selected when the process was started. | ||
/// </summary> | ||
class Options | ||
{ | ||
/// <summary> | ||
/// Initializes a new instance of the <see cref="Options"/> class. | ||
/// </summary> | ||
/// <param name="studioExecutable">Path to the Atmel Studio/Microchip Studio executable.</param> | ||
/// <param name="outFileName">The name of the output file requested in the process arguments. <c>null</c> if no /out argument was supplied.</param> | ||
/// <param name="studioArgs">The arguments that should be passed to Atmel Studio/Microchip Studio.</param> | ||
/// <param name="helpRequested">Indicates whether or not a help argument was passed in at process start.</param> | ||
public Options(string studioExecutable, string outFileName, bool outFileSpecified, string studioArgs, bool helpRequested) | ||
{ | ||
StudioExecutable = studioExecutable; | ||
OutFileName = outFileName; | ||
OutFileSpecified = outFileSpecified; | ||
StudioArgs = studioArgs; | ||
HelpRequested = helpRequested; | ||
} | ||
|
||
/// <summary> | ||
/// The name of the output file requested in the process arguments. Is <c>null</c> when no /out argument was supplied. | ||
/// </summary> | ||
public string OutFileName { get; } | ||
|
||
/// <summary> | ||
/// Whether or not the user specified the "/out" argument for AtmelStudio.exe. | ||
/// </summary> | ||
public bool OutFileSpecified { get; } | ||
|
||
/// <summary> | ||
/// Path to the Atmel Studio/Microchip Studio executable. | ||
/// </summary> | ||
public string StudioExecutable { get; } | ||
|
||
/// <summary> | ||
/// The arguments that should be passed to Atmel Studio/Microchip Studio. | ||
/// </summary> | ||
public string StudioArgs { get; } | ||
|
||
/// <summary> | ||
/// Indicates whether or not a help argument was passed in at process start. | ||
/// </summary> | ||
public bool HelpRequested { get; } | ||
} | ||
} |
Oops, something went wrong.