mirror of
https://github.com/AlexMacocian/MTSC.git
synced 2026-07-24 03:56:32 +00:00
143 lines
6.3 KiB
C#
143 lines
6.3 KiB
C#
using System;
|
|
using System.IO;
|
|
using System.Security.Cryptography;
|
|
using System.Xml;
|
|
|
|
namespace MTSC
|
|
{
|
|
static class HelperFunctions
|
|
{
|
|
#region XML
|
|
|
|
public static void FromXmlString(this RSA rsa, string xmlString)
|
|
{
|
|
RSAParameters parameters = new RSAParameters();
|
|
|
|
XmlDocument xmlDoc = new XmlDocument();
|
|
xmlDoc.LoadXml(xmlString);
|
|
|
|
if (xmlDoc.DocumentElement.Name.Equals("RSAKeyValue"))
|
|
{
|
|
foreach (XmlNode node in xmlDoc.DocumentElement.ChildNodes)
|
|
{
|
|
switch (node.Name)
|
|
{
|
|
case "Modulus": parameters.Modulus = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "Exponent": parameters.Exponent = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "P": parameters.P = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "Q": parameters.Q = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "DP": parameters.DP = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "DQ": parameters.DQ = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "InverseQ": parameters.InverseQ = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
case "D": parameters.D = (string.IsNullOrEmpty(node.InnerText) ? null : Convert.FromBase64String(node.InnerText)); break;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
throw new Exception("Invalid XML RSA key.");
|
|
}
|
|
|
|
rsa.ImportParameters(parameters);
|
|
}
|
|
|
|
public static string ToXmlString(this RSA rsa, bool includePrivateParameters)
|
|
{
|
|
RSAParameters parameters = rsa.ExportParameters(includePrivateParameters);
|
|
|
|
return string.Format("<RSAKeyValue><Modulus>{0}</Modulus><Exponent>{1}</Exponent><P>{2}</P><Q>{3}</Q><DP>{4}</DP><DQ>{5}</DQ><InverseQ>{6}</InverseQ><D>{7}</D></RSAKeyValue>",
|
|
parameters.Modulus != null ? Convert.ToBase64String(parameters.Modulus) : null,
|
|
parameters.Exponent != null ? Convert.ToBase64String(parameters.Exponent) : null,
|
|
parameters.P != null ? Convert.ToBase64String(parameters.P) : null,
|
|
parameters.Q != null ? Convert.ToBase64String(parameters.Q) : null,
|
|
parameters.DP != null ? Convert.ToBase64String(parameters.DP) : null,
|
|
parameters.DQ != null ? Convert.ToBase64String(parameters.DQ) : null,
|
|
parameters.InverseQ != null ? Convert.ToBase64String(parameters.InverseQ) : null,
|
|
parameters.D != null ? Convert.ToBase64String(parameters.D) : null);
|
|
}
|
|
/// <summary>
|
|
/// Returns true if <paramref name="path"/> starts with the path <paramref name="baseDirPath"/>.
|
|
/// The comparison is case-insensitive, handles / and \ slashes as folder separators and
|
|
/// only matches if the base dir folder name is matched exactly ("c:\foobar\file.txt" is not a sub path of "c:\foo").
|
|
/// </summary>
|
|
public static bool IsSubPathOf(this string path, string baseDirPath)
|
|
{
|
|
string normalizedPath = Path.GetFullPath(path.Replace('/', '\\')
|
|
.WithEnding("\\"));
|
|
|
|
string normalizedBaseDirPath = Path.GetFullPath(baseDirPath.Replace('/', '\\')
|
|
.WithEnding("\\"));
|
|
|
|
return normalizedPath.StartsWith(normalizedBaseDirPath, StringComparison.OrdinalIgnoreCase);
|
|
}
|
|
/// <summary>
|
|
/// Returns <paramref name="str"/> with the minimal concatenation of <paramref name="ending"/> (starting from end) that
|
|
/// results in satisfying .EndsWith(ending).
|
|
/// </summary>
|
|
/// <example>"hel".WithEnding("llo") returns "hello", which is the result of "hel" + "lo".</example>
|
|
public static string WithEnding(this string str, string ending)
|
|
{
|
|
if (str == null)
|
|
return ending;
|
|
|
|
string result = str;
|
|
|
|
// Right() is 1-indexed, so include these cases
|
|
// * Append no characters
|
|
// * Append up to N characters, where N is ending length
|
|
for (int i = 0; i <= ending.Length; i++)
|
|
{
|
|
string tmp = result + ending.Right(i);
|
|
if (tmp.EndsWith(ending))
|
|
return tmp;
|
|
}
|
|
|
|
return result;
|
|
}
|
|
/// <summary>Gets the rightmost <paramref name="length" /> characters from a string.</summary>
|
|
/// <param name="value">The string to retrieve the substring from.</param>
|
|
/// <param name="length">The number of characters to retrieve.</param>
|
|
/// <returns>The substring.</returns>
|
|
public static string Right(this string value, int length)
|
|
{
|
|
if (value == null)
|
|
{
|
|
throw new ArgumentNullException("value");
|
|
}
|
|
if (length < 0)
|
|
{
|
|
throw new ArgumentOutOfRangeException("length", length, "Length is less than zero");
|
|
}
|
|
|
|
return (length < value.Length) ? value.Substring(value.Length - length) : value;
|
|
}
|
|
#endregion
|
|
|
|
public static byte[] ReadRemainingBytes(this MemoryStream ms)
|
|
{
|
|
byte[] buffer = new byte[ms.Length - ms.Position];
|
|
ms.Read(buffer, 0, buffer.Length);
|
|
return buffer;
|
|
}
|
|
|
|
public static byte[] TrimTrailingNullBytes(this byte[] bytes)
|
|
{
|
|
int trimSize = 0;
|
|
for(int i = bytes.Length - 1; i >= 0; i--)
|
|
{
|
|
if(bytes[i] == 0)
|
|
{
|
|
trimSize++;
|
|
}
|
|
else
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
byte[] newBytes = new byte[bytes.Length - trimSize];
|
|
Array.Copy(bytes, 0, newBytes, 0, newBytes.Length);
|
|
return newBytes;
|
|
}
|
|
}
|
|
}
|