216 lines
7.2 KiB
C#
216 lines
7.2 KiB
C#
// **********************************************************************************************************
|
||
// BITCommand.cs
|
||
// 8/31/2023
|
||
// NGI - Next Generation Interceptor
|
||
//
|
||
// Contract No. HQ0856-21-C-0003/1022000209
|
||
//
|
||
// DISTRIBUTION STATEMENT F: FURTHER DISSEMINATION ONLY AS DIRECTED BY
|
||
// MISSILE DEFENSE AGENCY, MDA/GMY NEXT GENERATION INTERCEPTOR PROJECT
|
||
// OFFICE (DATE OF DETERMINATION 14 JUNE 2021) OR HIGHER DOD AUTHORITY.
|
||
// OTHER REQUESTS FOR THIS DOCUMENT SHALL BE REFERRED TO: MISSILE DEFENSE
|
||
// AGENCY, CONTRACTS DIRECTORATE, ATTN: GMY‐K, BLDG. 5222 MARTIN ROAD,
|
||
// REDSTONE ARSENAL, AL 35898.
|
||
//
|
||
// WARNING: THIS DOCUMENT CONTAINS TECHNICAL DATA WHOSE EXPORT IS
|
||
// RESTRICTED BY THE ARMS EXPORT CONTROL ACT (TITLE 22, U.S.C.,
|
||
// SECTION 2751, ET SEQ.) OR THE EXPORT ADMINISTRATION ACT OF 1979
|
||
// (TITLE 50 U.S.C. APP. 2401 ET SEQ.), AS AMENDED. VIOLATIONS OF
|
||
// THESE EXPORT LAWS ARE SUBJECT TO SEVERE CRIMINAL PENALTIES.
|
||
// DISSEMINATE IN ACCORDANCE WITH PROVISIONS OF DOD DIRECTIVE 5230.25.
|
||
//
|
||
// RAYTHEON PROPRIETARY: THIS DOCUMENT CONTAINS DATA OR INFORMATION
|
||
// PROPRIETARY TO RAYTHEON COMPANY AND IS RESTRICTED TO USE ONLY BY
|
||
// PERSONS AUTHORIZED BY RAYTHEON COMPANY IN WRITING TO USE IT.
|
||
// DISCLOSURE TO UNAUTHORIZED PERSONS WOULD LIKELY CAUSE SUBSTANTIAL
|
||
// COMPETITIVE HARM TO RAYTHEON COMPANY'S BUSINESS POSITION. NEITHER
|
||
// SAID DOCUMENT NOR ITS CONTENTS SHALL BE FURNISHED OR DISCLOSED TO
|
||
// OR COPIED OR USED BY PERSONS OUTSIDE RAYTHEON COMPANY WITHOUT THE
|
||
// EXPRESS WRITTEN APPROVAL OF RAYTHEON COMPANY.
|
||
//
|
||
// UNPUBLISHED WORK - COPYRIGHT RAYTHEON COMPANY.
|
||
//
|
||
// DESTRUCTION NOTICE - FOR CLASSIFIED DOCUMENTS FOLLOW THE PROCEDURES IN
|
||
// DOD 5220.22-M, NATIONAL INDUSTRIAL SECURITY PROGRAM OPERATING MANUAL,
|
||
// FEBRUARY 2006, INCORPORATING CHANGE 1, MARCH 28, 2013, CHAPTER 5,
|
||
// SECTION 7, OR DODM 5200.01-VOLUME 3, DOD INFORMATION SECURITY PROGRAM:
|
||
// PROTECTION OF CLASSIFIED INFORMATION, ENCLOSURE 3, SECTION 17. FOR
|
||
// CONTROLLED UNCLASSIFIED INFORMATION FOLLOW THE PROCEDURES IN DODM
|
||
// 5200.01-VOLUME 4, INFORMATION SECURITY PROGRAM: CONTROLLED UNCLASSIFIED
|
||
// INFORMATION.
|
||
//
|
||
// CONTROLLED BY: MISSILE DEFENSE AGENCY
|
||
// CONTROLLED BY: GROUND-BASED MIDCOURSE DEFENSE PROGRAM OFFICE
|
||
// CUI CATEGORY: CTI
|
||
// DISTRIBUTION/DISSEMINATION CONTROL: F
|
||
// POC: Alex Kravchenko (1118268)
|
||
// **********************************************************************************************************
|
||
// Ignore Spelling: Deserialized
|
||
|
||
using System;
|
||
using System.Collections.Generic;
|
||
using System.Linq;
|
||
using System.Xml.Serialization;
|
||
|
||
namespace BitGenSoftMeasurementManagerLib
|
||
{
|
||
|
||
[XmlType(TypeName = "ResponseMessageType")]
|
||
public enum ResponseMessageType
|
||
{
|
||
U, // Unknown or Undefined
|
||
R, // Required
|
||
E, // Error
|
||
P // Parametric
|
||
}
|
||
|
||
[XmlType(TypeName = "ParamType")]
|
||
public enum ParameterType
|
||
{
|
||
U, // Unknown or Undefined will default to string
|
||
N, // Numeric
|
||
S, // String
|
||
A, // Array
|
||
P // p-data array
|
||
}
|
||
|
||
|
||
[XmlType(TypeName = "BITResponseMsg")]
|
||
public class BITResponseMsg
|
||
{
|
||
[XmlAttribute("type")]
|
||
public ResponseMessageType ResponseType { get; set; }
|
||
|
||
[XmlText]
|
||
public string Name { get; set; }
|
||
}
|
||
|
||
[XmlType("Value")]
|
||
public class BITParameter
|
||
{
|
||
[XmlAttribute(AttributeName = "name")]
|
||
public string Key { get; set; }
|
||
|
||
[XmlAttribute(AttributeName = "type")]
|
||
public ParameterType ParameterType { get; set; }
|
||
|
||
[XmlAttribute(AttributeName = "delim")]
|
||
public string Delim { get; set; }
|
||
|
||
[XmlText]
|
||
public string Value { get; set; }
|
||
}
|
||
|
||
[Serializable]
|
||
public class BITCommand
|
||
{
|
||
[XmlElement(ElementName = "Command")]
|
||
public string Command { get; set; }
|
||
|
||
[XmlElement(ElementName = "CommandTimeout")]
|
||
public uint CommandTimeout { get; set; }
|
||
|
||
[XmlArray("CommandParameters")]
|
||
[XmlArrayItem("Value", Type = typeof(BITParameter))]
|
||
public List<BITParameter> CommandParameters { get; set; } = new List<BITParameter>();
|
||
|
||
[XmlArray("CommandResponses")]
|
||
[XmlArrayItem("BITResponseMsg", Type = typeof(BITResponseMsg))]
|
||
public List<BITResponseMsg> CommandResponses { get; set; } = new List<BITResponseMsg>();
|
||
|
||
[XmlElement(ElementName = "ParametricResponse")]
|
||
public string ParametricResponse { get; set; }
|
||
|
||
[XmlElement(ElementName = "ParametricTimeout")]
|
||
public uint ParametricTimeout { get; set; }
|
||
|
||
[XmlArray("ResponseParameters")]
|
||
[XmlArrayItem("Value", Type = typeof(BITParameter))]
|
||
public List<BITParameter> ResponseParameters { get; set; } = new List<BITParameter>();
|
||
|
||
/// <summary>
|
||
/// converts one hex parameter string into parameter array
|
||
/// </summary>
|
||
public void UnfoldHexParameters()
|
||
{
|
||
if (!CommandParameters.Any(p => p.ParameterType == ParameterType.P))
|
||
return;
|
||
|
||
var paramList = CommandParameters.Where(p => p.ParameterType == ParameterType.P).ToList();
|
||
List<BITParameter> removeList = new List<BITParameter>();
|
||
foreach (BITParameter param in paramList)
|
||
{
|
||
AddPDataArrayValues(param.Key, param.Value, param.Delim);
|
||
removeList.Add(param);
|
||
}
|
||
CommandParameters.RemoveAll(c => removeList.Contains(c));
|
||
}
|
||
|
||
/// <summary>
|
||
/// takes a hex string and breaks it up into individual characters
|
||
/// then inserts them as parameters
|
||
/// </summary>
|
||
/// <param name="key"></param>
|
||
/// <param name="value"></param>
|
||
/// <param name="delim"></param>
|
||
private void AddPDataArrayValues(string key, string value, string delim)
|
||
{
|
||
var parms = BreakByPages(value, delim);
|
||
|
||
int index = 0;
|
||
foreach (var item in parms)
|
||
{
|
||
string itemKey = $"{key}[{index++}]";
|
||
string itemValue = item;
|
||
CommandParameters.Add(new BITParameter { Key = itemKey, Value = itemValue } );
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// takes a large hex string and breaks it in multiple pages based on the known header
|
||
/// adjusts the size of the page to be divisible by 4 bytes
|
||
/// and also adds a 12 byte footer of zero values to the end of the page
|
||
/// </summary>
|
||
/// <param name="hexStr"></param>
|
||
/// <param name="header"></param>
|
||
/// <returns></returns>
|
||
private static IEnumerable<string> BreakByPages(string hexStr, string header)
|
||
{
|
||
const int footerSize = 12;
|
||
string[] pages = hexStr.Split(new[] { header }, StringSplitOptions.RemoveEmptyEntries);
|
||
|
||
foreach (string page in pages)
|
||
{
|
||
string completePage = header + page;
|
||
int pageSize = (completePage.Length + 7) & ~7;
|
||
string paddedPage = completePage.PadRight(pageSize + (footerSize * 2), '0');
|
||
IEnumerable<string> hexChars = BreakIntoHexCharacters(paddedPage);
|
||
foreach (string hexChar in hexChars)
|
||
{
|
||
yield return hexChar;
|
||
}
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// takes a large string of hex characters and breaks it into individual hex values
|
||
/// then yields these values to the calling code
|
||
/// </summary>
|
||
/// <param name="hexString"></param>
|
||
/// <returns></returns>
|
||
public static IEnumerable<string> BreakIntoHexCharacters(string hexString)
|
||
{
|
||
int characterSize = 2;
|
||
int length = hexString.Length;
|
||
for (int i = 0; i < length; i += characterSize)
|
||
{
|
||
if (i + characterSize > length)
|
||
{
|
||
hexString = hexString.PadRight(i + characterSize, '0');
|
||
}
|
||
yield return "0x" + hexString.Substring(i, characterSize);
|
||
}
|
||
}
|
||
}
|
||
}
|