Major upgrade
This commit is contained in:
@@ -0,0 +1,218 @@
|
||||
// **********************************************************************************************************
|
||||
// BitFieldGeneric.cs
|
||||
// 5/18/2022
|
||||
// NGI - Next Generation Interceptor
|
||||
//
|
||||
// Contract No. HQ0856-21-C-0003/1022000209
|
||||
//
|
||||
// THIS DOCUMENT DOES NOT CONTAIN TECHNOLOGY OR TECHNICAL DATA CONTROLLED UNDER EITHER THE U.S.
|
||||
// INTERNATIONAL TRAFFIC IN ARMS REGULATIONS OR THE U.S. EXPORT ADMINISTRATION REGULATIONS.
|
||||
//
|
||||
// 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)
|
||||
// **********************************************************************************************************
|
||||
using System;
|
||||
|
||||
namespace Raytheon.Common.Coe
|
||||
{
|
||||
// This is a generic class used to apply a bitfield to
|
||||
// a value to get the desired value
|
||||
class BitFieldGeneric<T> where T : IConvertible
|
||||
{
|
||||
protected long m_Value; // This is the value being operated on
|
||||
protected ulong m_Mask;
|
||||
|
||||
public char ToChar()
|
||||
{
|
||||
return (char)m_Value;
|
||||
}
|
||||
|
||||
public sbyte ToSByte()
|
||||
{
|
||||
return (sbyte)m_Value;
|
||||
}
|
||||
|
||||
public short ToShort()
|
||||
{
|
||||
return (short)m_Value;
|
||||
}
|
||||
|
||||
public int ToInt()
|
||||
{
|
||||
return (int)m_Value;
|
||||
}
|
||||
|
||||
public long ToLong()
|
||||
{
|
||||
return (long)m_Value;
|
||||
}
|
||||
|
||||
public ushort ToUShort()
|
||||
{
|
||||
return (ushort)m_Value;
|
||||
}
|
||||
|
||||
public uint ToUInt()
|
||||
{
|
||||
return (uint)m_Value;
|
||||
}
|
||||
|
||||
public ulong ToULong()
|
||||
{
|
||||
return (ulong)m_Value;
|
||||
}
|
||||
|
||||
public BitFieldGeneric(T value, ulong bitMask)
|
||||
{
|
||||
m_Mask = bitMask;
|
||||
try
|
||||
{
|
||||
m_Value = ApplyBitMask((ulong)value.ToInt64(null), bitMask);
|
||||
}
|
||||
catch
|
||||
{
|
||||
m_Value = ApplyBitMask(value.ToUInt64(null), bitMask);
|
||||
}
|
||||
}
|
||||
|
||||
public BitFieldGeneric(string value, ulong bitMask)
|
||||
{
|
||||
m_Mask = bitMask;
|
||||
|
||||
if(string.IsNullOrEmpty(value))
|
||||
{
|
||||
value = "0";
|
||||
}
|
||||
|
||||
if (Parse.Try(value, out m_Value) == true)
|
||||
{
|
||||
m_Value = PrepareWithBitMask(m_Value, bitMask);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("Unable to parse value = " + value);
|
||||
}
|
||||
}
|
||||
|
||||
// count the number of 1 bits in a ulong
|
||||
int BitCount(ulong x)
|
||||
{
|
||||
int n = 0;
|
||||
if (x > 0) do ++n; while ((x &= x - 1) > 1);
|
||||
return n;
|
||||
}
|
||||
|
||||
// Check to see if the MSB is set after accounting for
|
||||
// the mask. If it is, then the number should be converted
|
||||
// to display a negative number
|
||||
public void ToSigned()
|
||||
{
|
||||
if (m_Mask > 0)
|
||||
{
|
||||
// See if the sign bit is set
|
||||
int numbits = BitCount(m_Mask);
|
||||
if (m_Value > (Math.Pow(2, numbits - 1)))
|
||||
{
|
||||
// If it is, take the two's complement
|
||||
m_Value = (~m_Value) + 1;
|
||||
|
||||
// Mask off the leading F's from the conversion
|
||||
ulong mask = 1;
|
||||
for (int i = 0; i < numbits - 1; i++)
|
||||
{
|
||||
mask = (mask << 1) + 1;
|
||||
}
|
||||
|
||||
m_Value = (long)(((ulong)m_Value) & mask);
|
||||
|
||||
// Add the negative sign
|
||||
m_Value = -m_Value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return m_Value.ToString();
|
||||
}
|
||||
|
||||
public void BitOR(T value)
|
||||
{
|
||||
long orValue = value.ToInt64(null);
|
||||
m_Value |= orValue;
|
||||
}
|
||||
|
||||
private long PrepareWithBitMask(long val, ulong bitMask)
|
||||
{
|
||||
ulong value = (ulong)val;
|
||||
ulong mask = bitMask;
|
||||
|
||||
if (bitMask != 0)
|
||||
{
|
||||
if ((mask & 1) != 1)
|
||||
{
|
||||
while (((mask >> 1) & 1) != 1) //shift mask to LSB
|
||||
{
|
||||
mask >>= 1;
|
||||
}
|
||||
|
||||
mask >>= 1; // one last shift not done by loop
|
||||
}
|
||||
|
||||
value &= mask; // ensure value is contained in the same # of bits as the mask
|
||||
|
||||
// Shift the value back to its proper spot in the memory
|
||||
while (mask != bitMask)
|
||||
{
|
||||
value <<= 1;
|
||||
mask <<= 1;
|
||||
}
|
||||
}
|
||||
return (long)value;
|
||||
}
|
||||
|
||||
private long ApplyBitMask(ulong val, ulong bitMask)
|
||||
{
|
||||
ulong value = val;
|
||||
|
||||
if (bitMask != 0) // Apply the bit field
|
||||
{
|
||||
value &= bitMask;
|
||||
|
||||
// Shift until the bitmask resides in the LSB
|
||||
if ((bitMask & 1) != 1)
|
||||
{
|
||||
while (((bitMask >> 1) & 1) != 1)
|
||||
{
|
||||
value >>= 1;
|
||||
bitMask >>= 1;
|
||||
}
|
||||
|
||||
// We need one more shift after leaving the while loop
|
||||
value >>= 1;
|
||||
}
|
||||
}
|
||||
return (long)value;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,525 @@
|
||||
// **********************************************************************************************************
|
||||
// BytePackingXml.cs
|
||||
// 5/18/2022
|
||||
// NGI - Next Generation Interceptor
|
||||
//
|
||||
// Contract No. HQ0856-21-C-0003/1022000209
|
||||
//
|
||||
// THIS DOCUMENT DOES NOT CONTAIN TECHNOLOGY OR TECHNICAL DATA CONTROLLED UNDER EITHER THE U.S.
|
||||
// INTERNATIONAL TRAFFIC IN ARMS REGULATIONS OR THE U.S. EXPORT ADMINISTRATION REGULATIONS.
|
||||
//
|
||||
// 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)
|
||||
// **********************************************************************************************************
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq.Expressions;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Xml;
|
||||
using System.Xml.XPath;
|
||||
|
||||
namespace Raytheon.Common.Coe
|
||||
{
|
||||
// Takes an XML ICD and adds in nodes to represent the byte packing
|
||||
// The padding added will be displayed in the tool as arrays of characters
|
||||
internal class BytePackingXml : XmlDocument
|
||||
{
|
||||
private readonly int m_Packing = 0;
|
||||
private readonly Dictionary<string, double> m_ConstMap;
|
||||
private readonly Dictionary<string, int> m_SizeMap;
|
||||
private readonly Dictionary<string, int> m_PadMap;
|
||||
|
||||
public BytePackingXml(string icdStr) : base()
|
||||
{
|
||||
// Create the dictionaries
|
||||
m_ConstMap = new Dictionary<string, double>();
|
||||
m_PadMap = new Dictionary<string, int>();
|
||||
m_SizeMap = new Dictionary<string, int>();
|
||||
|
||||
// Create an XML document from the string
|
||||
LoadXml(icdStr);
|
||||
|
||||
XPathNavigator node = CreateNavigator();
|
||||
//Get the type of packing
|
||||
XPathNodeIterator nodeset = node.Select("/interface/packing");
|
||||
if (nodeset.MoveNext() == true)
|
||||
{
|
||||
if (!Parse.Try(nodeset.Current.Value.Trim(), out m_Packing))
|
||||
{
|
||||
switch (nodeset.Current.Value.Trim())
|
||||
{
|
||||
case "char":
|
||||
case "1":
|
||||
m_Packing = 1;
|
||||
break;
|
||||
case "short":
|
||||
case "2":
|
||||
m_Packing = 2;
|
||||
break;
|
||||
case "long":
|
||||
case "4":
|
||||
m_Packing = 4;
|
||||
break;
|
||||
case "double":
|
||||
case "8":
|
||||
default:
|
||||
m_Packing = 8;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Handle all of the constants
|
||||
nodeset = node.Select("/interface/constant|/interface/namespace/constant");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
ProcessConstantNode(nodeset.Current);
|
||||
}
|
||||
|
||||
nodeset = node.Select("/interface/typedef|/interface/namespace/typedef");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
ProcessTypedefNode(nodeset.Current);
|
||||
}
|
||||
|
||||
nodeset = node.Select("/interface/enum|/interface/namespace/enum");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
ProcessEnumerationNode(nodeset.Current);
|
||||
}
|
||||
|
||||
nodeset = node.Select("/interface/structure|/interface/message|/interface/namespace/structure|/interface/namespace/message");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
ProcessStructureNode(nodeset.Current);
|
||||
}
|
||||
|
||||
NormalizeIcdLabels();
|
||||
}
|
||||
|
||||
// This function takes all of the messages in the ICD
|
||||
// and converts the labels into decimal, so when we do
|
||||
// a string lookup, they will all be in the same known format
|
||||
private void NormalizeIcdLabels()
|
||||
{
|
||||
XPathNavigator navigator = CreateNavigator();
|
||||
XPathNodeIterator nodeset;
|
||||
|
||||
nodeset = navigator.Select("/interface/message/label|/interface/namespace/message/label");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
try
|
||||
{
|
||||
double dLabel = GetConstFromString(nodeset.Current.Value);
|
||||
nodeset.Current.SetValue(((int)dLabel).ToString());
|
||||
}
|
||||
catch
|
||||
{
|
||||
throw new Exception("Message Label, " + nodeset.Current.Value + ", can not be converted to an integer");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void ProcessConstantNode(XPathNavigator node)
|
||||
{
|
||||
string name = "";
|
||||
string constStr = "";
|
||||
double constNum = 0;
|
||||
|
||||
if (node.MoveToChild("name", ""))
|
||||
{
|
||||
name = node.Value.Trim();
|
||||
node.MoveToParent();
|
||||
}
|
||||
if (node.MoveToChild("value", ""))
|
||||
{
|
||||
constStr = node.Value.Trim();
|
||||
if ((constStr.Length != 0) && (constStr[0] != '\"'))
|
||||
{
|
||||
constNum = GetConstFromString(constStr);
|
||||
}
|
||||
else
|
||||
{
|
||||
constNum = 0;
|
||||
}
|
||||
node.MoveToParent();
|
||||
}
|
||||
|
||||
// Verify the correctnes of the <constant> tag
|
||||
if ((name != "") && (constStr != ""))
|
||||
{
|
||||
AddItemToMap(m_ConstMap, name, constNum);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception(
|
||||
"ERROR: Constant Definition Incorrect - <name>:" + name +
|
||||
" <value>:" + constStr);
|
||||
}
|
||||
}
|
||||
|
||||
private void ProcessTypedefNode(XPathNavigator node)
|
||||
{
|
||||
string name = "";
|
||||
string type = "";
|
||||
int typeSize = 0; // Size of the item
|
||||
int typePad = 0; //Size of the largest item to pad to
|
||||
|
||||
if (node.MoveToChild("name", ""))
|
||||
{
|
||||
name = node.Value.Trim();
|
||||
node.MoveToParent();
|
||||
}
|
||||
if (node.MoveToChild("value", ""))
|
||||
{
|
||||
type = node.Value.Trim();
|
||||
GetSizeFromType(type, out typeSize, out typePad);
|
||||
node.MoveToParent();
|
||||
}
|
||||
|
||||
// Verify the correctnes of the <typedef> tag
|
||||
if ((name != "") && (type != ""))
|
||||
{
|
||||
AddItemToMap(m_PadMap, name, typePad);
|
||||
AddItemToMap(m_SizeMap, name, typeSize);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception(
|
||||
"ERROR: Typedef Definition Incorrect - <name>:" + name +
|
||||
" <value>:" + type);
|
||||
}
|
||||
}
|
||||
|
||||
private void ProcessEnumerationNode(XPathNavigator node)
|
||||
{
|
||||
string name;
|
||||
double constNum = 0;
|
||||
var constStr = string.Empty;
|
||||
|
||||
if (node.MoveToChild("name", ""))
|
||||
{
|
||||
name = node.Value.Trim();
|
||||
AddItemToMap(m_PadMap, name, 4);
|
||||
AddItemToMap(m_SizeMap, name, 4);
|
||||
node.MoveToParent();
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("ERROR: Enumeration Definition Incorrect. No <name> tag present.");
|
||||
}
|
||||
|
||||
XPathNodeIterator nodeSet = node.Select("item|enum_item");
|
||||
while (nodeSet.MoveNext())
|
||||
{
|
||||
name = string.Empty;
|
||||
|
||||
if ((nodeSet.Current.MoveToChild("name", "")) ||
|
||||
(nodeSet.Current.MoveToChild("item_name", "")))
|
||||
{
|
||||
name = nodeSet.Current.Value.Trim();
|
||||
nodeSet.Current.MoveToParent();
|
||||
}
|
||||
if (nodeSet.Current.MoveToChild("value", ""))
|
||||
{
|
||||
constStr = nodeSet.Current.Value.Trim();
|
||||
constNum = GetConstFromString(constStr);
|
||||
nodeSet.Current.MoveToParent();
|
||||
}
|
||||
|
||||
// Verify the correctnes of the <enum><item> tag
|
||||
if ((name != "") && (constStr != ""))
|
||||
{
|
||||
AddItemToMap(m_ConstMap, name, constNum);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception($"ERROR: Enumeration Item Definition Incorrect - <name>: {name} <value>: {constStr}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void ProcessStructureNode(XPathNavigator node)
|
||||
{
|
||||
string name;
|
||||
|
||||
if (node.MoveToChild("name", ""))
|
||||
{
|
||||
name = node.Value.Trim();
|
||||
node.MoveToParent();
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("ERROR: Stucture/Message Definition Incorrect. No <name> tag present.");
|
||||
}
|
||||
|
||||
int maxSize = 0;
|
||||
int padCount = 0;
|
||||
uint bitCount = 0; // Used to see how many bits have been processed.
|
||||
int lastItemSize = 0;
|
||||
|
||||
var nodeSet = node.Select("item|struct_item|msg_item");
|
||||
while (nodeSet.MoveNext())
|
||||
{
|
||||
GetItemSize(nodeSet.Current, out int padSize, out int itemSize, out int reps, out uint bits);
|
||||
if ((lastItemSize != itemSize) || ((bitCount + bits) > (uint)(itemSize * 8)))
|
||||
{
|
||||
bitCount = 0; // Size changed or bit rollover
|
||||
}
|
||||
|
||||
if (bitCount == 0)
|
||||
{
|
||||
padCount += AddPadding(node, nodeSet.Current, padSize, padCount);
|
||||
|
||||
// Set maxSize
|
||||
if (padSize > maxSize)
|
||||
{
|
||||
maxSize = padSize;
|
||||
}
|
||||
|
||||
// Keep up with the pad count
|
||||
padCount += (itemSize * reps);
|
||||
}
|
||||
|
||||
lastItemSize = itemSize;
|
||||
bitCount += bits;
|
||||
}
|
||||
|
||||
if (maxSize != 0)
|
||||
{
|
||||
// Add final padding
|
||||
padCount += AddPadding(node, null, maxSize, padCount);
|
||||
}
|
||||
|
||||
AddItemToMap(m_PadMap, name, maxSize);
|
||||
AddItemToMap(m_SizeMap, name, padCount);
|
||||
}
|
||||
|
||||
private void GetItemSize(XPathNavigator node, out int padSize, out int itemSize, out int reps, out uint bits)
|
||||
{
|
||||
string name = "";
|
||||
|
||||
if ((node.MoveToChild("name", "")) ||
|
||||
(node.MoveToChild("item_name", "")))
|
||||
{
|
||||
name = node.Value.Trim();
|
||||
node.MoveToParent();
|
||||
}
|
||||
|
||||
itemSize = -1;
|
||||
padSize = -1;
|
||||
reps = 1;
|
||||
bits = 0;
|
||||
|
||||
var nodeSet = node.Select("type");
|
||||
while (nodeSet.MoveNext())
|
||||
{
|
||||
GetSizeFromType(nodeSet.Current.Value.Trim(), out padSize, out itemSize);
|
||||
}
|
||||
|
||||
nodeSet = node.Select("bits");
|
||||
if (nodeSet.MoveNext())
|
||||
{
|
||||
bits = (uint)GetConstFromString(nodeSet.Current.Value.Trim());
|
||||
}
|
||||
|
||||
nodeSet = node.Select("arrayLength|imageWidth|imageHeight");
|
||||
while (nodeSet.MoveNext())
|
||||
{
|
||||
try
|
||||
{
|
||||
reps *= (int)GetConstFromString(nodeSet.Current.Value.Trim());
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new Exception
|
||||
(e.Message + " item name = \"" + name + "\", tag = <" +
|
||||
nodeSet.Current.Name + ">.");
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
if ((itemSize == -1) || (padSize == -1))
|
||||
{
|
||||
throw new Exception
|
||||
("ERROR: Item named " + name + "does not contain a <type> tag.");
|
||||
}
|
||||
|
||||
if (bits == 0)
|
||||
bits = (uint)padSize * 8;
|
||||
}
|
||||
|
||||
private double GetConstFromString(string constStr)
|
||||
{
|
||||
// remove namespace
|
||||
constStr = Regex.Replace(constStr, @"[^:]+::([^:]+)", "$1");
|
||||
if ((constStr.Length > 0) && (constStr[0] == '\''))
|
||||
{
|
||||
byte charData = (byte)constStr[1];
|
||||
constStr = charData.ToString();
|
||||
}
|
||||
|
||||
if (Parse.Try(constStr, out double data) == false)
|
||||
{
|
||||
if (Parse.Try(constStr, out int iData) == false)
|
||||
{
|
||||
try
|
||||
{
|
||||
data = m_ConstMap[constStr];
|
||||
}
|
||||
catch
|
||||
{
|
||||
throw new Exception("ERROR: ConstantValue - \"" + constStr + "\" does not resolve to a number.");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
data = (double)iData;
|
||||
}
|
||||
}
|
||||
return data;
|
||||
}
|
||||
|
||||
private void AddItemToMap(Dictionary<string, int> map, string name, int value)
|
||||
{
|
||||
if (map.ContainsKey(name))
|
||||
{
|
||||
throw new Exception("ERROR: Element " + name + " is defined multiple times.");
|
||||
}
|
||||
else
|
||||
{
|
||||
map.Add(name, value);
|
||||
}
|
||||
}
|
||||
|
||||
private void AddItemToMap(Dictionary<string, double> map, string name, double value)
|
||||
{
|
||||
if (map.ContainsKey(name))
|
||||
{
|
||||
throw new Exception("ERROR: Element " + name + " is defined multiple times.");
|
||||
}
|
||||
else
|
||||
{
|
||||
map.Add(name, value);
|
||||
}
|
||||
}
|
||||
|
||||
private void GetSizeFromType(string type, out int typePad, out int typeSize)
|
||||
{
|
||||
// Remove all whitespace
|
||||
type = type.Replace(" ", "");
|
||||
// remove namespace
|
||||
type = Regex.Replace(type, @"[^:]+::([^:]+)", "$1");
|
||||
|
||||
switch (type)
|
||||
{
|
||||
case "uint8_t":
|
||||
type = "char";
|
||||
break;
|
||||
case "uint16_t":
|
||||
case "int16_t":
|
||||
type = "short";
|
||||
break;
|
||||
case "uint32_t":
|
||||
case "int32_t":
|
||||
type = "int";
|
||||
break;
|
||||
case "uint64_t":
|
||||
case "int64_t":
|
||||
type = "double";
|
||||
break;
|
||||
}
|
||||
|
||||
if ((type == "char"))
|
||||
{
|
||||
typePad = 1;
|
||||
typeSize = 1;
|
||||
}
|
||||
else if ((type == "short"))
|
||||
{
|
||||
typePad = 2;
|
||||
typeSize = 2;
|
||||
}
|
||||
else if ((Regex.IsMatch(type, @"unsigned", RegexOptions.IgnoreCase)) || (type == "int") || (type == "float") ||
|
||||
(type == "boolean") || (type == "address"))
|
||||
{
|
||||
typePad = 4;
|
||||
typeSize = 4;
|
||||
}
|
||||
else if ((type == "double"))
|
||||
{
|
||||
typePad = 8;
|
||||
typeSize = 8;
|
||||
}
|
||||
else // The type is complex and has already been defined
|
||||
{
|
||||
try
|
||||
{
|
||||
typePad = m_PadMap[type];
|
||||
typeSize = m_SizeMap[type];
|
||||
}
|
||||
catch
|
||||
{
|
||||
throw new Exception("ERROR: <type> - " + type + " used without being defined.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private int AddPadding(XPathNavigator ParentElement, XPathNavigator CurrentElement, int padSize, int padCount)
|
||||
{
|
||||
int padAdd = 0;
|
||||
int padTo = padSize;
|
||||
|
||||
if (m_Packing < padSize)
|
||||
{
|
||||
padTo = m_Packing;
|
||||
}
|
||||
|
||||
if (m_Packing > 0 && padTo != 0 && (padCount % padTo != 0))
|
||||
{
|
||||
padAdd = padTo - (padCount % padTo);
|
||||
InsertPaddingNode(ParentElement, CurrentElement, padAdd);
|
||||
}
|
||||
|
||||
return padAdd;
|
||||
}
|
||||
|
||||
private void InsertPaddingNode(XPathNavigator ParentElement, XPathNavigator CurrentElement, int padAdd)
|
||||
{
|
||||
string pad = "<item>" +
|
||||
"<name>" + Message.PADDING_ITEM_NAME + "</name>" +
|
||||
"<type>char</type>" +
|
||||
"<arrayLength>" + padAdd + "</arrayLength>" +
|
||||
"<instruType>S</instruType>" +
|
||||
"</item>";
|
||||
if (CurrentElement != null)
|
||||
{
|
||||
CurrentElement.InsertBefore(pad);
|
||||
}
|
||||
else // End padding
|
||||
{
|
||||
ParentElement.AppendChild(pad);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,604 @@
|
||||
// **********************************************************************************************************
|
||||
// MessageData.cs
|
||||
// 5/18/2022
|
||||
// NGI - Next Generation Interceptor
|
||||
//
|
||||
// Contract No. HQ0856-21-C-0003/1022000209
|
||||
//
|
||||
// THIS DOCUMENT DOES NOT CONTAIN TECHNOLOGY OR TECHNICAL DATA CONTROLLED UNDER EITHER THE U.S.
|
||||
// INTERNATIONAL TRAFFIC IN ARMS REGULATIONS OR THE U.S. EXPORT ADMINISTRATION REGULATIONS.
|
||||
//
|
||||
// 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)
|
||||
// **********************************************************************************************************
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
|
||||
namespace Raytheon.Common.Coe
|
||||
{
|
||||
public class MessageData : ICloneable
|
||||
{
|
||||
public string FieldName;
|
||||
public string FieldType;
|
||||
public string FieldValue;
|
||||
public string FieldArrayValue;
|
||||
public string FieldDefaultValue;
|
||||
public string FieldMaxValue;
|
||||
public string FieldMinValue;
|
||||
public string FieldBitValue;
|
||||
public string FieldInstruType;
|
||||
public string Variable;
|
||||
public string MaxOffset;
|
||||
public string MinOffset;
|
||||
public string VerifyType;
|
||||
public bool isSelected;
|
||||
public bool isArray;
|
||||
public bool isStructure;
|
||||
public bool isArrayOfStructures;
|
||||
public bool isEnum;
|
||||
public bool usesRegister;
|
||||
public bool isValid;
|
||||
public bool useRange;
|
||||
public int arrayLength;
|
||||
public uint imageWidth;
|
||||
public uint imageHeight;
|
||||
public uint imagePixelSize;
|
||||
public ulong bitMask;
|
||||
public bool expanded;
|
||||
public int depth;
|
||||
public byte[] imageBuffer;
|
||||
public uint imageBufferSize;
|
||||
public MessageData[] MessageArray;
|
||||
|
||||
public delegate coe.Status ReadImageDelegate
|
||||
(
|
||||
string filename,
|
||||
uint columns,
|
||||
uint rows,
|
||||
uint pixel_size,
|
||||
byte[] buffer
|
||||
);
|
||||
|
||||
private MessageXmlDocument m_Icd;
|
||||
|
||||
internal int m_BitCounter = 0; // used to calculate the bit mask
|
||||
|
||||
internal static Dictionary<string, ReadImageDelegate> m_ReadFunctions = null;
|
||||
|
||||
public bool LogData { get; set; }
|
||||
|
||||
private MessageData() { }
|
||||
private MessageData(MessageXmlDocument Icd)
|
||||
{
|
||||
FieldName = null;
|
||||
FieldType = null;
|
||||
FieldValue = null;
|
||||
FieldArrayValue = null;
|
||||
FieldDefaultValue = null;
|
||||
FieldMaxValue = null;
|
||||
FieldMinValue = null;
|
||||
FieldBitValue = null;
|
||||
Variable = null;
|
||||
MaxOffset = null;
|
||||
MinOffset = null;
|
||||
VerifyType = null;
|
||||
isSelected = false;
|
||||
isArray = false;
|
||||
isStructure = false;
|
||||
isArrayOfStructures = false;
|
||||
usesRegister = false;
|
||||
useRange = false;
|
||||
arrayLength = 0;
|
||||
imageWidth = 0;
|
||||
imageHeight = 0;
|
||||
imagePixelSize = 0;
|
||||
bitMask = 0;
|
||||
expanded = false;
|
||||
depth = 0;
|
||||
imageBufferSize = 0;
|
||||
imageBuffer = null;
|
||||
|
||||
m_Icd = Icd;
|
||||
}
|
||||
|
||||
public MessageData(string fieldname,
|
||||
string fieldtype,
|
||||
string fieldvalue,
|
||||
string fielddefaultvalue,
|
||||
MessageXmlDocument Icd,
|
||||
bool logData = true) :
|
||||
this(Icd)
|
||||
{
|
||||
FieldName = fieldname;
|
||||
FieldType = fieldtype;
|
||||
FieldValue = fieldvalue;
|
||||
|
||||
LogData = logData;
|
||||
|
||||
SetInstruType(null);
|
||||
SetDefaultValue(fielddefaultvalue);
|
||||
|
||||
}
|
||||
|
||||
public MessageData(string fieldname,
|
||||
string fieldtype,
|
||||
string fieldvalue,
|
||||
string fielddefaultvalue,
|
||||
string fieldmaxvalue,
|
||||
string fieldminvalue,
|
||||
MessageXmlDocument Icd) :
|
||||
this(fieldname, fieldtype, fieldvalue, fielddefaultvalue, Icd)
|
||||
{
|
||||
SetMaxValue(fieldmaxvalue);
|
||||
SetMinValue(fieldminvalue);
|
||||
}
|
||||
|
||||
public string FormattedValue
|
||||
{
|
||||
get { return FormatValue(FieldValue); }
|
||||
}
|
||||
public string FormattedMinValue
|
||||
{
|
||||
get { return FormatValue(FieldMinValue); }
|
||||
}
|
||||
public string FormattedMaxValue
|
||||
{
|
||||
get { return FormatValue(FieldMaxValue); }
|
||||
}
|
||||
|
||||
public static string ImageFileReadTypes
|
||||
{
|
||||
get
|
||||
{
|
||||
string fileTypes = "";
|
||||
if (m_ReadFunctions == null) return null;
|
||||
foreach (string type in m_ReadFunctions.Keys)
|
||||
{
|
||||
if (fileTypes != "")
|
||||
fileTypes += "|";
|
||||
|
||||
fileTypes += type.ToUpper() + " files (*." + type.ToLower() + ")|*." + type.ToLower();
|
||||
}
|
||||
|
||||
return fileTypes;
|
||||
}
|
||||
}
|
||||
|
||||
public void AddReadExtension(string extension, ReadImageDelegate readFunc)
|
||||
{
|
||||
if (m_ReadFunctions == null)
|
||||
m_ReadFunctions = new Dictionary<string, ReadImageDelegate>();
|
||||
|
||||
if (m_ReadFunctions.ContainsKey(extension))
|
||||
m_ReadFunctions[extension] = readFunc;
|
||||
else
|
||||
m_ReadFunctions.Add(extension, readFunc);
|
||||
}
|
||||
|
||||
public void UpdateImage()
|
||||
{
|
||||
if (FieldInstruType == "P")
|
||||
{
|
||||
if (File.Exists(FieldValue))
|
||||
{
|
||||
string extension = FieldValue.Substring(FieldValue.LastIndexOf(".") + 1);
|
||||
m_ReadFunctions[extension](FieldValue,
|
||||
imageWidth,
|
||||
imageHeight,
|
||||
imagePixelSize,
|
||||
imageBuffer);
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO add error message
|
||||
//MessageBox.Show("Unable to open file " + FieldValue +
|
||||
// " to populate " + FieldName,
|
||||
// "File Read Error",
|
||||
// MessageBoxButtons.OK,
|
||||
// MessageBoxIcon.Error);
|
||||
FieldValue = "";
|
||||
for (int i = 0; i < imageBuffer.Length; i++)
|
||||
{
|
||||
imageBuffer[i] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public void SetDefaultValue(string fieldDefaultValue)
|
||||
{
|
||||
// Initialize uninitialized value
|
||||
if (fieldDefaultValue == null)
|
||||
{
|
||||
fieldDefaultValue = "";
|
||||
}
|
||||
|
||||
if ((FieldType == "char") && (fieldDefaultValue.Contains("\"")))
|
||||
{
|
||||
FieldInstruType = "S";
|
||||
}
|
||||
|
||||
FieldDefaultValue = RemoveCharFromString(fieldDefaultValue, '\"');
|
||||
}
|
||||
|
||||
public void SetMaxValue(string fieldmaxvalue)
|
||||
{
|
||||
if (fieldmaxvalue == null) return; /* Bad argument */
|
||||
|
||||
if ((FieldType == "char") && (fieldmaxvalue.Contains("\"")))
|
||||
{
|
||||
FieldInstruType = "S";
|
||||
}
|
||||
|
||||
FieldMaxValue = RemoveCharFromString(fieldmaxvalue, '\"');
|
||||
}
|
||||
|
||||
public void SetMinValue(string fieldminvalue)
|
||||
{
|
||||
if (fieldminvalue == null) return; /* Bad argument */
|
||||
|
||||
if ((FieldType == "char") && (fieldminvalue.Contains("\"")))
|
||||
{
|
||||
FieldInstruType = "S";
|
||||
}
|
||||
|
||||
FieldMinValue = RemoveCharFromString(fieldminvalue, '\"');
|
||||
}
|
||||
|
||||
public void SetBitValue(int bits)
|
||||
{
|
||||
int size = (int)Message.GetTypeSize(FieldType, isEnum, LogData);
|
||||
|
||||
// Determine the bitMask
|
||||
if (bits == 0)
|
||||
{
|
||||
m_BitCounter = 0;
|
||||
FieldBitValue = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
FieldBitValue = bits.ToString();
|
||||
|
||||
// If bits overflow across the type boundary, then
|
||||
// they start at the next boundary.
|
||||
//
|
||||
// MSDN :
|
||||
// "Note that nYear is 8 bits long and would overflow
|
||||
// the word boundary of the declared type, unsigned short.
|
||||
// Therefore, it is begun at the beginning of a
|
||||
// new unsigned short."
|
||||
if (m_BitCounter + bits > size * 8)
|
||||
{
|
||||
m_BitCounter = 0;
|
||||
}
|
||||
|
||||
// 2^bits-1 will give a bit mask with bit# of 1's
|
||||
// ex: bits = 5, bitMask = 11111
|
||||
bitMask = (ulong)Math.Pow(2, (double)bits) - 1;
|
||||
|
||||
// We must slide the bitMask left to put it in place
|
||||
bitMask <<= m_BitCounter;
|
||||
m_BitCounter += bits;
|
||||
|
||||
// If we have used all the bits in the type that was defined, then
|
||||
// restart the counter
|
||||
if (m_BitCounter == size * 8)
|
||||
m_BitCounter = 0;
|
||||
}
|
||||
|
||||
if (bitMask == 0xffffff)
|
||||
{
|
||||
bitMask = 0;
|
||||
}
|
||||
}
|
||||
|
||||
public void SetArraySize(int size)
|
||||
{
|
||||
char result;
|
||||
|
||||
arrayLength = size; // Save the size
|
||||
|
||||
if (!isArray && !isStructure)
|
||||
{
|
||||
// Don't handle strings as arrays
|
||||
if ((FieldInstruType != "S") && (FieldInstruType != "P"))
|
||||
{
|
||||
isArray = true;
|
||||
|
||||
MessageArray = new MessageData[size];
|
||||
// If the field type is char or unsigned char and the default value
|
||||
// exists and is a string then write one char of the string to
|
||||
// each element of the array
|
||||
if ((FieldType == "char" || FieldType == "unsigned char") &&
|
||||
FieldDefaultValue != null &&
|
||||
!Parse.Try(FieldDefaultValue, out result))
|
||||
{
|
||||
for (uint index = 0; index < size; index++)
|
||||
{
|
||||
//Only the elements that are required to spell out the string should
|
||||
//receive default values.
|
||||
if (index < FieldDefaultValue.Length)
|
||||
{
|
||||
MessageArray[index] = new MessageData(FieldName + "[" + index + "]",
|
||||
FieldType, FieldValue, FieldDefaultValue[(int)index].ToString(),
|
||||
FieldMaxValue, FieldMinValue, m_Icd);
|
||||
MessageArray[index].FieldInstruType = FieldInstruType;
|
||||
}
|
||||
else
|
||||
{
|
||||
MessageArray[index] = new MessageData(FieldName + "[" + index + "]",
|
||||
FieldType, FieldValue, "0",
|
||||
FieldMaxValue, FieldMinValue, m_Icd);
|
||||
MessageArray[index].FieldInstruType = FieldInstruType;
|
||||
}
|
||||
MessageArray[index].depth = depth + 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (uint index = 0; index < size; index++)
|
||||
{
|
||||
MessageArray[index] = new MessageData(FieldName + "[" + index + "]",
|
||||
FieldType, FieldValue, FieldDefaultValue, FieldMaxValue,
|
||||
FieldMinValue, m_Icd);
|
||||
MessageArray[index].FieldInstruType = FieldInstruType;
|
||||
MessageArray[index].depth = depth + 1;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void SetStructureSize(int size)
|
||||
{
|
||||
if (!isArray && !isStructure)
|
||||
{
|
||||
isStructure = true;
|
||||
MessageArray = new MessageData[size];
|
||||
for (uint index = 0; index < size; index++)
|
||||
{
|
||||
MessageArray[index] = new MessageData(FieldName + ".", null, null, null, m_Icd);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
internal void SetInstruType(string Type)
|
||||
{
|
||||
if (Type != null)
|
||||
{
|
||||
FieldInstruType = Type;
|
||||
|
||||
// Ensure 'S' is used properly
|
||||
if ((Type == "S") && (FieldType != "char"))
|
||||
{
|
||||
return; /* << EXIT >> */
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if ((FieldType != null) &&
|
||||
((FieldType.Trim() == "float") || (FieldType.Trim() == "double")))
|
||||
{
|
||||
FieldInstruType = "F";
|
||||
}
|
||||
else
|
||||
{
|
||||
FieldInstruType = "I";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
internal void SetPixelSize()
|
||||
{
|
||||
// Only do this if the user did not define a size
|
||||
if (imagePixelSize == 0)
|
||||
{
|
||||
switch (FieldType)
|
||||
{
|
||||
case "char":
|
||||
case "unsigned char":
|
||||
case "unsignedchar":
|
||||
imagePixelSize = 1;
|
||||
break;
|
||||
|
||||
case "short":
|
||||
case "unsigned short":
|
||||
case "unsignedshort":
|
||||
imagePixelSize = 2;
|
||||
break;
|
||||
|
||||
case "int":
|
||||
case "unsigned int":
|
||||
case "unsignedint":
|
||||
case "unsigned":
|
||||
case "boolean":
|
||||
case "address":
|
||||
case "float":
|
||||
imagePixelSize = 4;
|
||||
break;
|
||||
|
||||
case "double":
|
||||
case "long long":
|
||||
case "longlong":
|
||||
case "unsigned long long":
|
||||
case "unsignedlonglong":
|
||||
imagePixelSize = 8;
|
||||
break;
|
||||
|
||||
default:
|
||||
if (isEnum)
|
||||
{
|
||||
imagePixelSize = 4;
|
||||
}
|
||||
else // Error case
|
||||
{
|
||||
imagePixelSize = 1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private string FormatValue(string Value)
|
||||
{
|
||||
if ((Value == null) || (Value == ""))
|
||||
{
|
||||
return "";
|
||||
}
|
||||
else // Value exists
|
||||
{
|
||||
if (isEnum == false)
|
||||
{
|
||||
if (FieldInstruType == "I")
|
||||
{
|
||||
// This is being represented as a decimal
|
||||
if (Parse.Try(Value, out long dec) == true)
|
||||
{
|
||||
return dec.ToString();
|
||||
}
|
||||
}
|
||||
else if (FieldInstruType == "F")
|
||||
{
|
||||
// This is being represented as floating point
|
||||
if (Parse.Try(Value, out double flt) == true)
|
||||
{
|
||||
return flt.ToString();
|
||||
}
|
||||
}
|
||||
else if ((FieldInstruType == "X") ||
|
||||
(FieldInstruType == "B") ||
|
||||
(FieldInstruType == "T"))
|
||||
{
|
||||
// This is being represented as a hexadecimal value
|
||||
if (Parse.Try(Value, out long hex) == true)
|
||||
{
|
||||
return "0x" + hex.ToString("X");
|
||||
}
|
||||
}
|
||||
else if (FieldInstruType == "N")
|
||||
{
|
||||
// This is being represented as a binary number
|
||||
if (Parse.Try(Value, out long bin) == true)
|
||||
{
|
||||
return Convert.ToString(bin, 2) + "b";
|
||||
}
|
||||
}
|
||||
// else InstruType == 'S' or 'P' or anything else return the value
|
||||
}
|
||||
else // This value is an enumeration
|
||||
{
|
||||
Dictionary<string, string> enums = m_Icd.GetEnumerations(FieldType);
|
||||
if (enums.ContainsValue(Value) == true)
|
||||
{
|
||||
foreach (KeyValuePair<string, string> pair in enums)
|
||||
{
|
||||
if (pair.Value.Trim() == Value.Trim())
|
||||
{
|
||||
return pair.Key;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Value; // If nothing above applies, simply return the value string
|
||||
}
|
||||
|
||||
private String RemoveCharFromString(String str, char c)
|
||||
{
|
||||
if (str == null) return null; // Handle null case
|
||||
|
||||
int index = str.IndexOf(c);
|
||||
while (index != -1)
|
||||
{
|
||||
str = str.Remove(index, 1);
|
||||
index = str.IndexOf(c);
|
||||
}
|
||||
|
||||
return str;
|
||||
}
|
||||
|
||||
#region ICloneable Members
|
||||
|
||||
public object Clone()
|
||||
{
|
||||
MessageData clone = new MessageData();
|
||||
|
||||
clone.FieldName = FieldName;
|
||||
clone.FieldType = FieldType;
|
||||
clone.FieldValue = FieldValue;
|
||||
clone.FieldArrayValue = FieldArrayValue;
|
||||
clone.FieldDefaultValue = FieldDefaultValue;
|
||||
clone.FieldMaxValue = FieldMaxValue;
|
||||
clone.FieldMinValue = FieldMinValue;
|
||||
clone.FieldBitValue = FieldBitValue;
|
||||
clone.FieldInstruType = FieldInstruType;
|
||||
clone.Variable = Variable;
|
||||
clone.MaxOffset = MaxOffset;
|
||||
clone.MinOffset = MinOffset;
|
||||
clone.VerifyType = VerifyType;
|
||||
clone.isSelected = isSelected;
|
||||
clone.isArray = isArray;
|
||||
clone.isStructure = isStructure;
|
||||
clone.isArrayOfStructures = isArrayOfStructures;
|
||||
clone.isEnum = isEnum;
|
||||
clone.usesRegister = usesRegister;
|
||||
clone.isValid = isValid;
|
||||
clone.useRange = useRange;
|
||||
clone.arrayLength = arrayLength;
|
||||
clone.bitMask = bitMask;
|
||||
clone.expanded = expanded;
|
||||
clone.depth = depth;
|
||||
clone.m_Icd = m_Icd;
|
||||
clone.imageWidth = imageWidth;
|
||||
clone.imageHeight = imageHeight;
|
||||
clone.imagePixelSize = imagePixelSize;
|
||||
clone.imageBufferSize = imageBufferSize;
|
||||
if (imageBufferSize > 0)
|
||||
{
|
||||
clone.imageBuffer = new byte[imageBufferSize];
|
||||
imageBuffer.CopyTo(clone.imageBuffer, 0);
|
||||
}
|
||||
|
||||
if (MessageArray == null)
|
||||
{
|
||||
clone.MessageArray = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
clone.MessageArray = new MessageData[MessageArray.Length];
|
||||
for (int i = 0; i < MessageArray.Length; i++)
|
||||
{
|
||||
clone.MessageArray[i] = (MessageData)MessageArray[i].Clone();
|
||||
}
|
||||
}
|
||||
|
||||
return clone;
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,449 @@
|
||||
// **********************************************************************************************************
|
||||
// MessageXmlDocument.cs
|
||||
// 5/18/2022
|
||||
// NGI - Next Generation Interceptor
|
||||
//
|
||||
// Contract No. HQ0856-21-C-0003/1022000209
|
||||
//
|
||||
// THIS DOCUMENT DOES NOT CONTAIN TECHNOLOGY OR TECHNICAL DATA CONTROLLED UNDER EITHER THE U.S.
|
||||
// INTERNATIONAL TRAFFIC IN ARMS REGULATIONS OR THE U.S. EXPORT ADMINISTRATION REGULATIONS.
|
||||
//
|
||||
// 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)
|
||||
// **********************************************************************************************************
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Threading;
|
||||
using System.Xml;
|
||||
using System.Xml.XPath;
|
||||
using NLog;
|
||||
|
||||
namespace Raytheon.Common.Coe
|
||||
{
|
||||
public class MessageXmlDocument : XmlDocument
|
||||
{
|
||||
private readonly ILogger _logger;
|
||||
private readonly string _XmlFileName;
|
||||
private string BuiltXML = "<?xml version=\"1.0\" encoding=\"UTF-8\"?><?xml-stylesheet type=\"text/xsl\" ?><interface>";
|
||||
|
||||
private uint m_MaxMsgSize = 0;
|
||||
private readonly List<string> m_IncludeList;
|
||||
|
||||
public bool LogData { get; set; }
|
||||
|
||||
private MessageXmlDocument() : base()
|
||||
{
|
||||
LogData = true;
|
||||
}
|
||||
|
||||
public MessageXmlDocument(string Pathname, bool logData = true) :
|
||||
base()
|
||||
{
|
||||
LogData = logData;
|
||||
|
||||
_logger = LogManager.GetCurrentClassLogger();
|
||||
_XmlFileName = Pathname;
|
||||
|
||||
m_IncludeList = new List<string>();
|
||||
RecurseProcessing(Pathname);
|
||||
|
||||
BuiltXML = string.Concat(BuiltXML, "</interface>");
|
||||
BytePackingXml addPacking = new BytePackingXml(BuiltXML);
|
||||
LoadXml(addPacking.OuterXml);
|
||||
}
|
||||
|
||||
public Dictionary<string, string> GetEnumerations(string Type)
|
||||
{
|
||||
Dictionary<string, string> enumList = new Dictionary<string, string>();
|
||||
|
||||
// Get XML nodes to parse the XML ICD document
|
||||
XPathNavigator Node = CreateNavigator();
|
||||
XPathNodeIterator Nodeset = Node.Select("interface/enum/name");
|
||||
|
||||
while (Nodeset.MoveNext())
|
||||
{
|
||||
// Find the enumeration with the name of the type
|
||||
if (Nodeset.Current.Value.Trim().Equals(Type.Trim()))
|
||||
{
|
||||
// Find all the enumeration items
|
||||
XPathNavigator enumNode = Nodeset.Current.Clone();
|
||||
while (enumNode.MoveToNext())
|
||||
{
|
||||
if (enumNode.Name.Trim().Equals("item") ||
|
||||
enumNode.Name.Trim().Equals("enum_item"))
|
||||
{
|
||||
string name = null;
|
||||
string value = null;
|
||||
|
||||
// Find all name nodes
|
||||
XPathNavigator childNode = enumNode.Clone();
|
||||
childNode.MoveToFirstChild();
|
||||
do
|
||||
{
|
||||
if (childNode.Name.Trim().Equals("name"))
|
||||
{
|
||||
name = childNode.Value.Trim();
|
||||
}
|
||||
else if (childNode.Name.Trim().Equals("item_name"))
|
||||
{
|
||||
name = childNode.Value.Trim();
|
||||
}
|
||||
|
||||
if (childNode.Name.Trim().Equals("value"))
|
||||
{
|
||||
value = childNode.Value.Trim();
|
||||
}
|
||||
|
||||
// Once we find the name & value, add it to the list
|
||||
if ((name != null) && (value != null))
|
||||
{
|
||||
enumList.Add(name, value);
|
||||
break;
|
||||
}
|
||||
} while (childNode.MoveToNext());
|
||||
}
|
||||
}
|
||||
|
||||
break; // We found the enumeration we wanted
|
||||
}
|
||||
}
|
||||
|
||||
return enumList;
|
||||
}
|
||||
|
||||
private void RecurseProcessing(string pathName)
|
||||
{
|
||||
string directory;
|
||||
string IncludePathname;
|
||||
XPathNodeIterator nodeset;
|
||||
|
||||
// Only process each file once
|
||||
pathName = pathName.Replace('/', '\\');
|
||||
if (m_IncludeList.Contains(pathName))
|
||||
{
|
||||
return; // This file has already been processed
|
||||
}
|
||||
else
|
||||
{
|
||||
m_IncludeList.Add(pathName);
|
||||
}
|
||||
|
||||
if (LogData)
|
||||
_logger.Info($"Loading File: {pathName}");
|
||||
XPathDocument document = new XPathDocument(pathName);
|
||||
XPathNavigator navigator = document.CreateNavigator();
|
||||
|
||||
// Verify this is a COE XML ICD
|
||||
nodeset = navigator.Select("/interface");
|
||||
if (nodeset.Count == 0)
|
||||
{
|
||||
// This is not an XML ICD
|
||||
throw new Exception($"Invalid COE XML Format. Unable to process {pathName}" +
|
||||
"\nEnsure this is a properly formatted ICD.");
|
||||
}
|
||||
|
||||
nodeset = navigator.Select("/interface/include/file");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
try
|
||||
{
|
||||
directory = DirectoryOf(pathName);
|
||||
}
|
||||
catch
|
||||
{
|
||||
directory = ".\\";
|
||||
}
|
||||
|
||||
IncludePathname = nodeset.Current.Value.Trim();
|
||||
if ((!IncludePathname.StartsWith("\\")) && (!IncludePathname.Contains(":")))
|
||||
{
|
||||
while (IncludePathname.StartsWith("."))
|
||||
{
|
||||
if ((IncludePathname.StartsWith("..\\")) || (IncludePathname.StartsWith("../")))
|
||||
{
|
||||
directory = DirectoryOf(directory);
|
||||
IncludePathname = IncludePathname.Remove(0, 3);
|
||||
}
|
||||
else if ((IncludePathname.StartsWith(".\\")) || (IncludePathname.StartsWith("./")))
|
||||
{
|
||||
IncludePathname = IncludePathname.Remove(0, 2);
|
||||
}
|
||||
}
|
||||
IncludePathname = string.Concat(directory, "\\", IncludePathname);
|
||||
}
|
||||
|
||||
if (Regex.IsMatch(IncludePathname, @"\.xml", RegexOptions.IgnoreCase))
|
||||
RecurseProcessing(IncludePathname);
|
||||
}
|
||||
|
||||
nodeset = navigator.Select("/interface/packing|/interface/typedef|/interface/namespace/typedef|" +
|
||||
"/interface/constant|/interface/namespace/constant|interface/enum|interface/namespace/enum|" +
|
||||
"/interface/structure|/interface/namespace/structure|/interface/message|/interface/namespace/message");
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
string item = nodeset.Current.OuterXml;
|
||||
int index;
|
||||
while ((index = item.IndexOf("<description>")) != -1)
|
||||
{
|
||||
item = item.Remove(index, item.IndexOf("</description>") + 14 - index);
|
||||
}
|
||||
while ((index = item.IndexOf("<!--")) != -1)
|
||||
{
|
||||
item = item.Remove(index, item.IndexOf("-->") + 3 - index);
|
||||
}
|
||||
while (item.IndexOf("> ") != -1)
|
||||
{
|
||||
item = item.Replace("> ", ">");
|
||||
}
|
||||
while (item.IndexOf(" <") != -1)
|
||||
{
|
||||
item = item.Replace(" <", "<");
|
||||
}
|
||||
//_logger.Log(LogLevel.Trace, $"Loading Node :\n{item}");
|
||||
Thread.Sleep(1);
|
||||
BuiltXML = string.Concat(BuiltXML, item);
|
||||
}
|
||||
}
|
||||
|
||||
private string DirectoryOf(string Pathname)
|
||||
{
|
||||
return Pathname.Remove(Pathname.LastIndexOf("\\"));
|
||||
}
|
||||
|
||||
//
|
||||
// From the XML document, the definition of a single message can be identified
|
||||
// from the Message Name and returned as an XML string.
|
||||
//
|
||||
public string XmlFileName
|
||||
{
|
||||
get
|
||||
{
|
||||
return _XmlFileName;
|
||||
}
|
||||
}
|
||||
|
||||
public string GetMessage(string messageName)
|
||||
{
|
||||
string message;
|
||||
|
||||
messageName = messageName.Trim();
|
||||
|
||||
if (LogData)
|
||||
_logger.Info($"Searching for message : {messageName}");
|
||||
try
|
||||
{
|
||||
message = SelectSingleNode($"/interface/message[name='{messageName}']").OuterXml;
|
||||
message = TranslateValue(message);
|
||||
|
||||
string labelStr = Regex.Replace(message, @".+<label>([\d]+)[^\d]+", "$1", RegexOptions.IgnoreCase);
|
||||
|
||||
int label = 0;
|
||||
|
||||
Parse.Try(labelStr, out label);
|
||||
|
||||
if (LogData)
|
||||
_logger.Trace($"Found by name: {Regex.Replace(message, @"<label>[\d]+", $"<label>0x{label.ToString("X8")}")}");
|
||||
}
|
||||
catch
|
||||
{
|
||||
message = null;
|
||||
throw new Exception("Message not found");
|
||||
}
|
||||
return message;
|
||||
}
|
||||
|
||||
//
|
||||
// From the XML document, the definition of a single message can be identified
|
||||
// from the Message Label and returned as an XML string.
|
||||
//
|
||||
public string GetMessageFromLabel(string messageLabel)
|
||||
{
|
||||
string message;
|
||||
|
||||
int label = 0;
|
||||
|
||||
if (Parse.Try(messageLabel, out label) == true)
|
||||
{
|
||||
if (LogData)
|
||||
_logger.Debug($"Searching for message: 0x{label.ToString("X8")}");
|
||||
|
||||
// Search by message label
|
||||
message = SelectSingleNode($"/interface/message[label='{label.ToString()}']").OuterXml;
|
||||
message = TranslateValue(message);
|
||||
|
||||
if (LogData)
|
||||
_logger.Debug($"Found by label: {Regex.Replace(message, @"<label>[\d]+", $"<label>0x{label.ToString("X8")}")}");
|
||||
}
|
||||
else
|
||||
{
|
||||
if (LogData)
|
||||
_logger.Debug($"Searching for message: {messageLabel}");
|
||||
|
||||
// Search by instruLabel
|
||||
message = SelectSingleNode($"/interface/message[instruLabel='{messageLabel}']").OuterXml;
|
||||
message = TranslateValue(message);
|
||||
|
||||
string labelStr = Regex.Replace(message, @".+<label>([\d]+)[^\d]+", "$1", RegexOptions.IgnoreCase);
|
||||
|
||||
Parse.Try(labelStr, out label);
|
||||
|
||||
if (LogData)
|
||||
_logger.Debug($"Found by name: {Regex.Replace(message, @"<label>[\d]+", $"<label>0x{label.ToString("X8")}")}");
|
||||
}
|
||||
|
||||
return message;
|
||||
}
|
||||
|
||||
//
|
||||
// From the XML document, the definition of a single message can be identified
|
||||
// from the Message InstruLabel and returned as an XML string.
|
||||
//
|
||||
public string GetMessageFromInstruLabel(string messageInstruLabel)
|
||||
{
|
||||
string message;
|
||||
|
||||
messageInstruLabel = messageInstruLabel.Trim();
|
||||
if (LogData)
|
||||
_logger.Debug($"Searching for message: {messageInstruLabel}");
|
||||
try
|
||||
{
|
||||
message = SelectSingleNode($"/interface/message[instruLabel='{messageInstruLabel}']").OuterXml;
|
||||
message = TranslateValue(message);
|
||||
|
||||
if (LogData)
|
||||
_logger.Debug($"Found by instrument label: {message}");
|
||||
}
|
||||
catch
|
||||
{
|
||||
message = null;
|
||||
throw new Exception("Message not found");
|
||||
}
|
||||
return message;
|
||||
}
|
||||
|
||||
public uint GetLargestMessageSize()
|
||||
{
|
||||
lock (this)
|
||||
{
|
||||
// return the max message size if we have already calculated it
|
||||
if (m_MaxMsgSize != 0)
|
||||
{
|
||||
return m_MaxMsgSize;
|
||||
}
|
||||
else
|
||||
{
|
||||
DateTime t1 = DateTime.Now;
|
||||
|
||||
XPathNavigator navigator = CreateNavigator();
|
||||
XPathNodeIterator nodeset = navigator.Select("/interface/message/name");
|
||||
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
Message msg = new Message(nodeset.Current.Value.Trim(), this);
|
||||
uint msgSize = msg.GetMessageSize();
|
||||
if (msgSize > m_MaxMsgSize)
|
||||
{
|
||||
m_MaxMsgSize = msgSize;
|
||||
}
|
||||
}
|
||||
|
||||
DateTime t2 = DateTime.Now;
|
||||
TimeSpan duration = t2 - t1;
|
||||
Debug.WriteLine("Max Msg Size Algorithm Time = " + duration);
|
||||
}
|
||||
}
|
||||
|
||||
return m_MaxMsgSize;
|
||||
}
|
||||
|
||||
public uint GetMessageSize(string MsgName)
|
||||
{
|
||||
uint msg_size = 0;
|
||||
|
||||
lock (this)
|
||||
{
|
||||
XPathNavigator navigator = CreateNavigator();
|
||||
XPathNodeIterator nodeset = navigator.Select("/interface/message/name");
|
||||
|
||||
while (nodeset.MoveNext())
|
||||
{
|
||||
if (MsgName == nodeset.Current.Value.Trim())
|
||||
{
|
||||
Message msg = new Message(nodeset.Current.Value.Trim(), this);
|
||||
msg_size = msg.GetMessageSize();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return msg_size;
|
||||
}
|
||||
|
||||
//
|
||||
// Since the XML message definitions contain the definitions of all the enumerations and constants,
|
||||
// this object is the only one containing the knowledge to interpret strings using enumerations and/or
|
||||
// constants. This method will substitute enumerations and constants with their respective base values
|
||||
// in a specified string.
|
||||
//
|
||||
public string TranslateValue(string Value)
|
||||
{
|
||||
XPathNavigator navigator = CreateNavigator();
|
||||
XPathNavigator position;
|
||||
string NewValue = Value;
|
||||
|
||||
//
|
||||
// Substitute enumeration
|
||||
//
|
||||
try
|
||||
{
|
||||
position = navigator.SelectSingleNode("/interface/enum/item[name='" + NewValue + "']");
|
||||
if (position == null)
|
||||
{
|
||||
position = navigator.SelectSingleNode("/interface/enum/item[item_name='" + NewValue + "']");
|
||||
}
|
||||
if (position != null)
|
||||
{
|
||||
position.MoveToChild("value", "");
|
||||
NewValue = position.Value;
|
||||
}
|
||||
|
||||
//
|
||||
// Substitute constants
|
||||
//
|
||||
position = navigator.SelectSingleNode("/interface/constant[name='" + NewValue + "']");
|
||||
if (position != null)
|
||||
{
|
||||
NewValue = position.Value;
|
||||
_logger.Debug("Translating field value : " + Value + " -> " + NewValue);
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
_logger.Error(e.Message);
|
||||
}
|
||||
|
||||
return NewValue;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,129 @@
|
||||
// **********************************************************************************************************
|
||||
// OeMessage.cs
|
||||
// 5/18/2022
|
||||
// NGI - Next Generation Interceptor
|
||||
//
|
||||
// Contract No. HQ0856-21-C-0003/1022000209
|
||||
//
|
||||
// THIS DOCUMENT DOES NOT CONTAIN TECHNOLOGY OR TECHNICAL DATA CONTROLLED UNDER EITHER THE U.S.
|
||||
// INTERNATIONAL TRAFFIC IN ARMS REGULATIONS OR THE U.S. EXPORT ADMINISTRATION REGULATIONS.
|
||||
//
|
||||
// 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)
|
||||
// **********************************************************************************************************
|
||||
|
||||
using System;
|
||||
|
||||
namespace Raytheon.Common.Coe
|
||||
{
|
||||
public class OeMessage : coeMessage
|
||||
{
|
||||
public Message XmlMessage
|
||||
{
|
||||
get { return m_Msg; }
|
||||
set
|
||||
{
|
||||
m_Msg = value;
|
||||
Label = value.Label;
|
||||
Size = value.GetMessageSize();
|
||||
}
|
||||
}
|
||||
|
||||
public new string Label
|
||||
{
|
||||
get { return base.Label.ToString(); }
|
||||
set
|
||||
{
|
||||
if (Parse.Try(value, out uint label) == true)
|
||||
{
|
||||
base.Label = label;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("OeMessage: Label does not parse to an Unsigned Integer");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public new string Domain
|
||||
{
|
||||
get { return base.Domain.ToString(); }
|
||||
set
|
||||
{
|
||||
if (Parse.Try(value, out uint domain) == true)
|
||||
{
|
||||
base.Domain = domain;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("OeMessage: Domain does not parse to an Unsigned Integer");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public OeMessage() : base(0) { m_Msg = null; }
|
||||
public OeMessage(int size) : base(size) { m_Msg = null; }
|
||||
public OeMessage(Message msg)
|
||||
: base(0)
|
||||
{
|
||||
XmlMessage = msg;
|
||||
}
|
||||
public OeMessage(Message msg, int msgSize) : base(msgSize)
|
||||
{
|
||||
XmlMessage = msg;
|
||||
}
|
||||
|
||||
override public void Serialize()
|
||||
{
|
||||
if (m_Msg != null)
|
||||
{
|
||||
byte[] serializedBuffer = m_Msg.serialize();
|
||||
if (serializedBuffer.Length > BufferSize)
|
||||
{
|
||||
BufferSize = serializedBuffer.Length;
|
||||
}
|
||||
Size = (uint)serializedBuffer.Length;
|
||||
copyToMessageBuffer(serializedBuffer);
|
||||
Domain = m_Msg.Domain;
|
||||
}
|
||||
}
|
||||
|
||||
override public void Deserialize()
|
||||
{
|
||||
if (m_Msg != null)
|
||||
{
|
||||
// Get sending time and pass it to the XmlMessage object;
|
||||
GetSendTime(out ulong sendSec, out uint sendSecFrac);
|
||||
m_Msg.SendSecond = sendSec;
|
||||
m_Msg.SendSecondFraction = sendSecFrac;
|
||||
m_Msg.Domain = Domain;
|
||||
byte[] receiveBuffer = copyFromMessageBuffer();
|
||||
if (receiveBuffer != null)
|
||||
{
|
||||
m_Msg.deserialize(receiveBuffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Message m_Msg = null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,377 @@
|
||||
// **********************************************************************************************************
|
||||
// Parse.cs
|
||||
// 5/18/2022
|
||||
// NGI - Next Generation Interceptor
|
||||
//
|
||||
// Contract No. HQ0856-21-C-0003/1022000209
|
||||
//
|
||||
// THIS DOCUMENT DOES NOT CONTAIN TECHNOLOGY OR TECHNICAL DATA CONTROLLED UNDER EITHER THE U.S.
|
||||
// INTERNATIONAL TRAFFIC IN ARMS REGULATIONS OR THE U.S. EXPORT ADMINISTRATION REGULATIONS.
|
||||
//
|
||||
// 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)
|
||||
// **********************************************************************************************************
|
||||
using System;
|
||||
|
||||
namespace Raytheon.Common.Coe
|
||||
{
|
||||
public class Parse
|
||||
{
|
||||
public static bool Try(string value, out byte result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = byte.TryParse(value, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = byte.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToByte(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out decimal result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = decimal.TryParse(value, System.Globalization.NumberStyles.Any, null, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = int.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out int hexResult);
|
||||
if (passed)
|
||||
{
|
||||
result = hexResult;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out short result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = short.TryParse(value, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = short.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToInt16(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out ushort result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = ushort.TryParse(value, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = ushort.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToUInt16(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out int result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = int.TryParse(value, System.Globalization.NumberStyles.Any, null, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = int.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToInt32(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out uint result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = uint.TryParse(value, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = uint.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToUInt32(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out long result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null || value == "")
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = long.TryParse(value, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = long.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToInt64(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out ulong result)
|
||||
{
|
||||
result = 0;
|
||||
if (value == null)
|
||||
return false; // Handle bad argument
|
||||
|
||||
bool passed = ulong.TryParse(value, out result);
|
||||
if (passed == false)
|
||||
{
|
||||
if (value.StartsWith("0x") == true)
|
||||
{
|
||||
value = value.Substring(2, value.Length - 2);
|
||||
passed = ulong.TryParse(value, System.Globalization.NumberStyles.HexNumber, null, out result);
|
||||
}
|
||||
else if (value.EndsWith("b") == true)
|
||||
{
|
||||
value = value.TrimEnd("b".ToCharArray());
|
||||
try
|
||||
{
|
||||
result = Convert.ToUInt64(value, 2);
|
||||
passed = true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
passed = true; // Handle Boolean TYPES
|
||||
if (value.Trim().ToUpper().Equals("TRUE"))
|
||||
result = 1;
|
||||
else if (value.Trim().ToUpper().Equals("FALSE"))
|
||||
result = 0;
|
||||
else
|
||||
passed = false;
|
||||
}
|
||||
}
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
public static bool Try(string value, out char result)
|
||||
{
|
||||
return char.TryParse(value, out result);
|
||||
}
|
||||
|
||||
public static bool Try(string value, out float result)
|
||||
{
|
||||
if (value.EndsWith("f") == true)
|
||||
value = value.TrimEnd("f".ToCharArray());
|
||||
|
||||
return float.TryParse(value, System.Globalization.NumberStyles.Any, null, out result);
|
||||
}
|
||||
|
||||
public static bool Try(string value, out double result)
|
||||
{
|
||||
if (value.EndsWith("f") == true)
|
||||
value = value.TrimEnd("f".ToCharArray());
|
||||
|
||||
return double.TryParse(value, System.Globalization.NumberStyles.Any, null, out result);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user