├── Example ├── ASM1.txt ├── HDA.txt ├── HLDMM.txt └── SDA1.txt ├── ICD └── SAPIENT_Interface_Control_Document_v5.0.pdf ├── LICENSE.txt ├── README.md ├── SAPIENT Test Harness Build Note.pdf ├── SapientAsmSimulator ├── SapientAsmSimulatorV3.sln └── SapientAsmSimulatorV3 │ ├── AlertGenerator.cs │ ├── AsmMainProcess.cs │ ├── CSVDetection.cs │ ├── CSVFileParser.cs │ ├── ClientForm.Designer.cs │ ├── ClientForm.cs │ ├── ClientForm.resx │ ├── DetectionGenerator.cs │ ├── HeartbeatGenerator.cs │ ├── IGUIInterface.cs │ ├── ISender.cs │ ├── MessageSender.cs │ ├── Program.cs │ ├── Properties │ ├── AssemblyInfo.cs │ ├── Settings.Designer.cs │ └── Settings.settings │ ├── RegistrationGenerator.cs │ ├── RoutePlanGenerator.cs │ ├── SapientAsmSimulatorV3.csproj │ ├── SapientServices.dll │ ├── ScriptForm.Designer.cs │ ├── ScriptForm.cs │ ├── ScriptForm.resx │ ├── TaskAckGenerator.cs │ ├── TaskMessage.cs │ ├── XmlGenerators.cs │ ├── app.config │ └── log4net.dll ├── SapientDataAgent ├── SapientDataAgentV3.sln └── SapientDataAgentV3 │ ├── GUIProtocol.cs │ ├── HldmmDataAgentClientProtocol.cs │ ├── HldmmDataAgentTaskingProtocol.cs │ ├── IConnectionMonitor.cs │ ├── LocationOffsetForm.Designer.cs │ ├── LocationOffsetForm.cs │ ├── LocationOffsetForm.resx │ ├── MessageParserTest.cs │ ├── Mono.Security.dll │ ├── NETGeographic.dll │ ├── Npgsql.dll │ ├── ObjectiveInformation.cs │ ├── PresetHeartbeat.cs │ ├── Program.cs │ ├── Properties │ ├── AssemblyInfo.cs │ ├── Resources.Designer.cs │ ├── Resources.resx │ ├── Settings.Designer.cs │ └── Settings.settings │ ├── Resources │ ├── greenLight.png │ ├── redLight.png │ └── yellowLight.png │ ├── SapientConnectionMonitor.cs │ ├── SapientDataAgent.csproj │ ├── SapientDataAgentClientProtocol.cs │ ├── SapientDataAgentTaskingProtocol.cs │ ├── SapientDatabase.dll │ ├── SapientMessageMonitor.cs │ ├── SapientMessageParser.cs │ ├── SapientMessageValidator.cs │ ├── SapientProtocol.cs │ ├── SapientServices.dll │ ├── ServerForm.Designer.cs │ ├── ServerForm.cs │ ├── ServerForm.resx │ ├── StatusIndicator.Designer.cs │ ├── StatusIndicator.cs │ ├── StatusIndicator.resx │ ├── TaskPermissions.cs │ ├── TextForm.Designer.cs │ ├── TextForm.cs │ ├── TextForm.resx │ ├── app.config │ └── log4net.dll ├── SapientDatabase ├── Database.cs ├── DatabaseCreator.cs ├── DatabaseTables │ ├── AlertConstants.cs │ ├── AlertQueries.cs │ ├── AlertTableCreator.cs │ ├── DatabaseUtil.cs │ ├── DetectionConstants.cs │ ├── DetectionQueries.cs │ ├── DetectionTableCreator.cs │ ├── ObjectiveConstants.cs │ ├── ObjectiveQueries.cs │ ├── ObjectiveTableCreator.cs │ ├── RegistrationQueries.cs │ ├── RoutePlanConstants.cs │ ├── RoutePlanQueries.cs │ ├── RoutePlanTableCreator.cs │ ├── SensorLocationOffsetConstants.cs │ ├── SensorLocationOffsetTableCreator.cs │ ├── StatusReportConstants.cs │ ├── StatusReportInsertQueries.cs │ ├── StatusReportTableCreator.cs │ ├── TaskAckQueries.cs │ ├── TaskConstants.cs │ ├── TaskQueries.cs │ └── TaskingTablesCreator.cs ├── MiddlewareLogDatabase.cs ├── Mono.Security.dll ├── Npgsql.dll ├── Properties │ └── AssemblyInfo.cs ├── SapientDatabase.csproj ├── SapientDatabase.csproj.user └── log4net.dll ├── SapientHldmmSimulator ├── SapientHldmmSimulatorV3.sln └── SapientHldmmSimulatorV3 │ ├── AlertGenerator.cs │ ├── CSVFileParser.cs │ ├── DetectionGenerator.cs │ ├── HeartbeatGenerator.cs │ ├── LookAtTaskGenerator.cs │ ├── MessageSender.cs │ ├── ObjectiveGenerator.cs │ ├── PTZForm.Designer.cs │ ├── PTZForm.cs │ ├── PTZForm.resx │ ├── Program.cs │ ├── Properties │ ├── AssemblyInfo.cs │ ├── Settings.Designer.cs │ └── Settings.settings │ ├── RegionTaskGenerator.cs │ ├── SapientHldmmSimulatorV3.csproj │ ├── SapientServices.dll │ ├── ScriptForm.Designer.cs │ ├── ScriptForm.cs │ ├── ScriptForm.resx │ ├── TaskACKParser.cs │ ├── TaskForm.Designer.cs │ ├── TaskForm.cs │ ├── TaskForm.resx │ ├── TaskGenerator.cs │ ├── XYZLookAtTaskGenerator.cs │ ├── XmlGenerators.cs │ ├── app.config │ └── log4net.dll ├── SapientServices ├── Data │ ├── Alert.cs │ ├── AlertResponse.cs │ ├── Approval.cs │ ├── ConfigXMLParser.cs │ ├── DetectionReport.cs │ ├── Error.cs │ ├── Objective.cs │ ├── RoutePlan.cs │ ├── SensorRegistration.cs │ ├── SensorRegistrationACK.cs │ ├── SensorTask.cs │ ├── SensorTaskACK.cs │ ├── StatusReport.cs │ ├── Validation │ │ ├── AlertValidation.cs │ │ ├── ApprovalValidation.cs │ │ ├── DetectionValidation.cs │ │ ├── SensorRegistrationValidation.cs │ │ ├── SensorTaskValidation.cs │ │ └── StatusReportValidation.cs │ └── location.cs ├── Histogram.cs ├── ICommsConnection.cs ├── IConnection.cs ├── Properties │ └── AssemblyInfo.cs ├── SapientClient.cs ├── SapientCommsCommon.cs ├── SapientLogger.cs ├── SapientMessageType.cs ├── SapientServer.cs ├── SapientServerClientHandler.cs ├── SapientServices.csproj ├── SapientServices.sln ├── SocketCommsCommon.cs ├── log4net.dll └── readme.txt └── XSD ├── Approval.xsd ├── RoutePlan.xsd ├── SapientICDv3.xsd ├── SensorRegistrationACK.xsd ├── SensorTaskACK.xsd ├── alert.xsd ├── alertResponse.xsd ├── detectionV3.xsd ├── error.xsd ├── heartbeatV3.xsd ├── locationV3.xsd ├── objective.xsd ├── registrationV3.xsd └── taskV3.xsd /Example/ASM1.txt: -------------------------------------------------------------------------------- 1 | 2022-01-20 10:02:43,072 [1] INFO SapientASMsimulator.Program 2 | 3 | 2022-01-20 10:02:43,088 [1] INFO SapientASMsimulator.Program SapientASMsimulator - Version 2.7.4.0 4 | 2022-01-20 10:02:50,414 [127.0.0.1:14001 Client Receive Thread] INFO SapientServices.Communication.SapientClient Connected To Server 5 | 2022-01-20 10:03:08,894 [1] INFO SapientASMsimulator.RegistrationGenerator Send Registration Succeeded 6 | 2022-01-20 10:03:09,222 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess SensorRegistrationACK Received 7 | 2022-01-20 10:03:09,222 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess ASM ID: 1 Latency(ms): 328.0809 8 | 2022-01-20 10:03:14,502 [6] INFO SapientASMsimulator.HeartbeatGenerator Sent StatusReport:0 9 | 2022-01-20 10:03:31,764 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess Task Message Received 10 | 2022-01-20 10:03:31,764 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.TaskMessage Task Message Received 11 | 2022-01-20 10:03:31,795 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.RegistrationGenerator Send Registration Succeeded 12 | 2022-01-20 10:03:31,795 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.TaskAckGenerator Send SensorTaskACK 1 Succeeded 13 | 2022-01-20 10:03:31,842 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess SensorRegistrationACK Received 14 | 2022-01-20 10:03:31,842 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess ASM ID: 1 Latency(ms): 62.4562 15 | 2022-01-20 10:04:17,222 [7] INFO SapientASMsimulator.AlertGenerator Send Alert:0 16 | 2022-01-20 10:04:30,156 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess AlertResponse Message Received 17 | 2022-01-20 10:04:30,156 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess AlertResponse alertID:0 18 | 2022-01-20 10:04:30,156 [127.0.0.1:14001 Client Receive Thread] INFO SapientASMsimulator.ASMMainProcess 19 | 20 | 2022-01-20T10:04:30.109783Z 21 | 1 22 | 0 23 | Acknowledge 24 | Reason 25 | -------------------------------------------------------------------------------- /Example/HLDMM.txt: -------------------------------------------------------------------------------- 1 | 2022-01-20 10:02:46,321 [1] INFO SapientHldmmSimulator.Program 2 | 3 | 2022-01-20 10:02:46,337 [1] INFO SapientHldmmSimulator.Program SapientHldmmSimulator - Version 2.7.4.0 4 | 2022-01-20 10:02:46,477 [1] INFO SapientHldmmSimulator.TaskForm Port: 12002 5 | 2022-01-20 10:02:48,524 [127.0.0.1:12002 Client Receive Thread] INFO SapientServices.Communication.SapientClient Connected To Server 6 | 2022-01-20 10:03:31,623 [6] INFO SapientHldmmSimulator.TaskGenerator Sent Command:1 to SensorID:1 7 | 2022-01-20 10:03:31,873 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskACKParser SensorTaskACK at:239 8 | 2022-01-20 10:03:31,873 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskACKParser 1:SensorTaskACK Task ID: 1:Accepted: 9 | 2022-01-20 10:03:58,960 [8] INFO SapientHldmmSimulator.TaskGenerator Sent Command:2 to SensorID:10 10 | 2022-01-20 10:03:58,992 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskACKParser SensorTaskACK at:213 11 | 2022-01-20 10:03:58,992 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskACKParser 1:SensorTaskACK Task ID: 2:Rejected:No ASM with this ID 12 | 2022-01-20 10:04:17,487 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskForm Alert Message Received 13 | 2022-01-20 10:04:17,503 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskForm Alert alertID: 0 from sensor: 1 14 | 2022-01-20 10:04:17,503 [127.0.0.1:12002 Client Receive Thread] INFO SapientHldmmSimulator.TaskForm 15 | 16 | 2022-01-20T10:04:17.2065798Z 17 | 1 18 | 0 19 | Information 20 | Active 21 | Text description of alert 22 | 23 | 565618 24 | 5777612 25 | 26 | 27 | 28 | 2022-01-20 10:04:30,109 [1] INFO SapientHldmmSimulator.TaskForm Send Alert Response Succeeded 29 | -------------------------------------------------------------------------------- /ICD/SAPIENT_Interface_Control_Document_v5.0.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/ICD/SAPIENT_Interface_Control_Document_v5.0.pdf -------------------------------------------------------------------------------- /LICENSE.txt: -------------------------------------------------------------------------------- 1 | Crown owned Copyright 2021 2 | 3 | Except where noted otherwise, the SAPIENT Middleware and Test 4 | Harness software is licensed under the Apache License, Version 2.0 5 | (the "License"); you may not use this file except in compliance with 6 | the License. You may obtain a copy of the License at 7 | 8 | http://www.apache.org/licenses/LICENSE-2.0 9 | 10 | Unless required by applicable law or agreed to in writing, software 11 | distributed under the License is distributed on an "AS IS" BASIS, 12 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | See the License for the specific language governing permissions and 14 | limitations under the License. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # SAPIENT Middleware and Test Harness 2 | This software in this repository is now obsolete. 3 | 4 | The current version of the SAPIENT Test Harness software (compatible with [BSI Flex 335 v2](https://knowledge.bsigroup.com/products/bsi-flex-335-v2-0-2023-sapient-network-of-autonomous-sensors-and-effectors-interface-control-document-specification-specification?version=standard)) can be found [here](https://github.com/dstl/BSI-Flex-335-v2-Test-Harness). The test harness software is intended to be used during development and testing of a SAPIENT component to test compliance with the SAPIENT standard (BSI Flex 335). 5 | 6 | A separate [SAPIENT Middleware](https://github.com/dstl/Apex-SAPIENT-Middleware) software package has also been released. This is non-mandatory component of a SAPIENT system, designed to be used in an operational SAPIENT system as a message routing and database application. 7 | -------------------------------------------------------------------------------- /SAPIENT Test Harness Build Note.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SAPIENT Test Harness Build Note.pdf -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 11.00 3 | # Visual Studio 2010 4 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SapientAsmSimulatorV3", "SapientAsmSimulatorV3\SapientAsmSimulatorV3.csproj", "{D7AB8356-90FF-4AB4-88BC-D980B65BC671}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|Any CPU = Debug|Any CPU 9 | Debug|Mixed Platforms = Debug|Mixed Platforms 10 | Debug|x86 = Debug|x86 11 | Release|Any CPU = Release|Any CPU 12 | Release|Mixed Platforms = Release|Mixed Platforms 13 | Release|x86 = Release|x86 14 | EndGlobalSection 15 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 16 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|Any CPU.ActiveCfg = Debug|x86 17 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|Mixed Platforms.ActiveCfg = Debug|x86 18 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|Mixed Platforms.Build.0 = Debug|x86 19 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|x86.ActiveCfg = Debug|x86 20 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|x86.Build.0 = Debug|x86 21 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|Any CPU.ActiveCfg = Release|x86 22 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|Mixed Platforms.ActiveCfg = Release|x86 23 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|Mixed Platforms.Build.0 = Release|x86 24 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|x86.ActiveCfg = Release|x86 25 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|x86.Build.0 = Release|x86 26 | EndGlobalSection 27 | GlobalSection(SolutionProperties) = preSolution 28 | HideSolutionNode = FALSE 29 | EndGlobalSection 30 | EndGlobal 31 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/AlertGenerator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: AlertGenerator.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientASMsimulator 8 | { 9 | using System; 10 | using System.Threading; 11 | using log4net; 12 | using SapientServices; 13 | using SapientServices.Communication; 14 | using SapientServices.Data; 15 | 16 | /// 17 | /// Generate Alert messages 18 | /// 19 | public class AlertGenerator : XmlGenerators 20 | { 21 | /// 22 | /// Log4net logger 23 | /// 24 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 25 | 26 | /// 27 | /// Gets the Alert Identifier to use in generated alert message 28 | /// 29 | public int AlertID { get; private set; } 30 | 31 | /// 32 | /// Gets or sets an Image URL to provide with the detection message 33 | /// 34 | public static string ImageURL { get; set; } 35 | 36 | /// 37 | /// Send an Alert message 38 | /// 39 | /// connection to use to send message 40 | /// file data logger 41 | public void GenerateAlert(object comms_connection, SapientLogger logger) 42 | { 43 | IConnection messenger = (IConnection)comms_connection; 44 | do 45 | { 46 | Alert alert = GenerateAlert(this.AlertID); 47 | string xmlstring = ConfigXMLParser.Serialize(alert); 48 | bool retval = MessageSender.Send(messenger, xmlstring, logger); 49 | 50 | this.MessageCount++; 51 | 52 | if (retval) 53 | { 54 | Log.InfoFormat("Send Alert:{0}", this.AlertID); 55 | } 56 | else 57 | { 58 | Log.ErrorFormat("Send Alert Failed:{0}", this.AlertID); 59 | } 60 | 61 | this.AlertID++; 62 | if (this.LoopMessages) 63 | { 64 | Thread.Sleep(this.LoopTime); 65 | } 66 | } while (this.LoopMessages); 67 | } 68 | 69 | /// 70 | /// Generate example alert 71 | /// 72 | /// alert identifier to use 73 | /// alert message object 74 | private static Alert GenerateAlert(int alertId) 75 | { 76 | double sensorX = Properties.Settings.Default.startLongitude; 77 | double sensorY = Properties.Settings.Default.startLatitude; 78 | 79 | if (sensorY > 90) 80 | { 81 | sensorY += 100; 82 | } 83 | else 84 | { 85 | sensorY = 0.001; 86 | } 87 | 88 | Alert alert = new Alert 89 | { 90 | alertID = alertId, 91 | alertType = "Information", 92 | sourceID = ASMId, 93 | status = "Active", 94 | description = "Text description of alert", 95 | timestamp = DateTime.UtcNow, 96 | location = new location { X = sensorX, Y = sensorY } 97 | }; 98 | 99 | if(!string.IsNullOrEmpty(ImageURL)) 100 | { 101 | alert.associatedFile = new[] 102 | { 103 | new AlertAssociatedFile 104 | { 105 | type = "image", 106 | url = ImageURL, 107 | }, 108 | }; 109 | } 110 | 111 | return alert; 112 | } 113 | } 114 | } 115 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/CSVDetection.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: CSVDetection.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientASMsimulator 8 | { 9 | using System; 10 | using System.IO; 11 | using log4net; 12 | using ScriptReader; 13 | class CSVDetection 14 | { 15 | /// 16 | /// Log4net logger 17 | /// 18 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 19 | 20 | private string directory; 21 | 22 | /// 23 | /// used for passing filename from single file click to process thread 24 | /// 25 | private string currentFilename; 26 | 27 | ////private ISender messenger; 28 | 29 | ////private Dictionary expectedErrors; 30 | 31 | /// private List xmlList = new List(); 32 | 33 | private string output; 34 | 35 | public void LoadData(string filename) 36 | { 37 | CSVFileParser parser = new CSVFileParser(filename); 38 | directory = Path.GetDirectoryName(filename); 39 | output += "Directory:" + directory + "\r\n"; 40 | 41 | parser.Open(); 42 | 43 | while (parser.Parse()) 44 | { 45 | string[] linedata; 46 | 47 | // Parse a line of data 48 | parser.ParseLineString(out linedata); 49 | if (linedata[0] != "") 50 | { 51 | ////this.listBox1.Items.Add(linedata[0]); 52 | ////xmlList.Add(directory + "\\" + linedata[0]); 53 | } 54 | } 55 | ////this.listBox1.Items.Add("END"); 56 | ////this.listBox1.SelectedIndex = 0; 57 | parser.Close(); 58 | } 59 | 60 | 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/CSVFileParser.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: CSVFileParser.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace ScriptReader 8 | { 9 | using System; 10 | using System.IO; 11 | using log4net; 12 | 13 | /// 14 | /// Read a CSV File in and parse it 15 | /// 16 | public class CSVFileParser 17 | { 18 | /// 19 | /// Log4net logger 20 | /// 21 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 22 | 23 | /// 24 | /// CSV filename to read 25 | /// 26 | private string fileName; 27 | 28 | /// 29 | /// file stream reader 30 | /// 31 | private StreamReader sr = null; 32 | 33 | /// 34 | /// last line of text read from CSV file 35 | /// 36 | private string lineOfText = null; 37 | 38 | /// 39 | /// Initializes a new instance of the CSVFileParser class. 40 | /// 41 | /// script filename 42 | public CSVFileParser(string filename) 43 | { 44 | this.fileName = filename; 45 | } 46 | 47 | /// 48 | /// Open CSV file 49 | /// 50 | public void Open() 51 | { 52 | try 53 | { 54 | Log.InfoFormat("Opening CSV File:{0}", this.fileName); 55 | this.sr = new StreamReader(new FileStream(this.fileName, FileMode.Open, FileAccess.Read)); 56 | } 57 | catch (FileNotFoundException) 58 | { 59 | Log.ErrorFormat("File Not Found: {0}", this.fileName); 60 | } 61 | catch (Exception ex) 62 | { 63 | Log.Error("Error Reading Script File:", ex); 64 | } 65 | } 66 | 67 | /// 68 | /// Close CSV file 69 | /// 70 | public void Close() 71 | { 72 | if (this.sr != null) 73 | { 74 | this.sr.Dispose(); 75 | } 76 | } 77 | 78 | /// 79 | /// Parse CSV file 80 | /// 81 | /// flag whether text successfully read 82 | public bool Parse() 83 | { 84 | bool textRead = false; 85 | try 86 | { 87 | if (this.sr.Peek() >= 0) 88 | { 89 | this.lineOfText = this.sr.ReadLine(); 90 | textRead = true; 91 | } 92 | } 93 | catch (Exception ex) 94 | { 95 | Log.Error("Error Parsing Script File:", ex); 96 | } 97 | 98 | return textRead; 99 | } 100 | 101 | /// 102 | /// Split CSV file line into a list of strings 103 | /// 104 | /// list of strings 105 | public void ParseLineString(out string[] result) 106 | { 107 | result = null; 108 | char[] charSeparators = new char[] { ',' }; 109 | if (this.lineOfText != null) 110 | { 111 | result = this.lineOfText.Split(charSeparators, StringSplitOptions.None); 112 | } 113 | } 114 | 115 | /// 116 | /// Show list of strings from a line of the CSV file 117 | /// 118 | /// 119 | ////public void Show(string[] sArray) 120 | ////{ 121 | //// for (int i = 0; i < sArray.Length; i++) 122 | //// { 123 | //// Console.Write(": " + sArray[i]); 124 | //// } 125 | //// Console.Write("\n"); 126 | ////} 127 | } 128 | } 129 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/IGUIInterface.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: IGUIInterface.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientASMsimulator 8 | { 9 | /// 10 | /// Interface to user interface 11 | /// 12 | public interface IGUIInterface 13 | { 14 | /// 15 | /// method to Update Output Window that can be called from outside the UI thread 16 | /// 17 | /// message to update with 18 | void UpdateOutputWindow(string message); 19 | 20 | /// 21 | /// Update ASM ID text 22 | /// 23 | /// ASM ID text 24 | void UpdateASMText(string text); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/ISender.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: ISender.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientServices 8 | { 9 | /// 10 | /// Interface for sending messages 11 | /// 12 | public interface ISender 13 | { 14 | /// 15 | /// Method to read and send xml from file. 16 | /// 17 | /// Path to XML file to be loaded. 18 | void ReadAndSendFile(string input_filename); 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/MessageSender.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: MessageSender.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientASMsimulator 8 | { 9 | using System; 10 | using System.Threading; 11 | using SapientServices; 12 | using SapientServices.Communication; 13 | 14 | /// 15 | /// Send Message 16 | /// 17 | public class MessageSender 18 | { 19 | /// 20 | /// Gets or sets a value indicating whether to fragment data to test communication resilience 21 | /// 22 | public static bool FragmentData { get; set; } 23 | 24 | /// 25 | /// Gets or sets a value indicating whether to put a delay between data fragments 26 | /// 27 | public static int PacketDelay { get; set; } 28 | 29 | /// 30 | /// Send Data over Sapient connection 31 | /// 32 | /// connection object 33 | /// message string to send 34 | /// file data logger 35 | /// true if successful 36 | public static bool Send(IConnection messenger, string message, SapientLogger logger) 37 | { 38 | // add nulkl termination 39 | if (Properties.Settings.Default.sendNullTermination) 40 | { 41 | message += '\0'; 42 | } 43 | 44 | byte[] record_bytes = System.Text.Encoding.UTF8.GetBytes(message); 45 | 46 | bool retval = false; 47 | 48 | // fragment packet to test handling of partial messages 49 | if (FragmentData && (record_bytes.Length > 1500)) 50 | { 51 | retval = messenger.SendMessage(record_bytes, 1500); 52 | 53 | if (retval) 54 | { 55 | Thread.Sleep(PacketDelay); 56 | byte[] remainingBytes = new byte[record_bytes.Length - 1500]; 57 | Array.Copy(record_bytes, 1500, remainingBytes, 0, record_bytes.Length - 1500); 58 | retval = messenger.SendMessage(remainingBytes, remainingBytes.Length); 59 | } 60 | } 61 | else 62 | { 63 | retval = messenger.SendMessage(record_bytes, record_bytes.Length); 64 | } 65 | 66 | if (logger != null && Properties.Settings.Default.Log) 67 | { 68 | logger.Log(message); 69 | } 70 | 71 | return retval; 72 | } 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/Program.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: Program.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | using System; 8 | using System.Windows.Forms; 9 | using log4net; 10 | 11 | [assembly: log4net.Config.XmlConfigurator(Watch = true)] 12 | 13 | namespace SapientASMsimulator 14 | { 15 | /// 16 | /// Main Program Class 17 | /// 18 | public static class Program 19 | { 20 | /// 21 | /// Log4net logger 22 | /// 23 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 24 | 25 | /// 26 | /// The main entry point for the application. 27 | /// 28 | /// command line argument - optionally specify fixed sensor identifier 29 | [STAThread] 30 | public static void Main(string[] args) 31 | { 32 | const int ExeName = 0; 33 | const int ExeVersion = 2; 34 | 35 | // Output the assembly name and version number for configuration purposes 36 | string[] assemblyDetails = System.Reflection.Assembly.GetExecutingAssembly().FullName.Split(',', '='); 37 | 38 | Log.Info(Environment.NewLine); 39 | Log.Info(assemblyDetails[ExeName] + " - Version " + assemblyDetails[ExeVersion]); 40 | 41 | if (args.Length > 0) 42 | { 43 | ASMMainProcess.AsmId = int.Parse(args[0]); 44 | } 45 | 46 | Application.EnableVisualStyles(); 47 | Application.SetCompatibleTextRenderingDefault(false); 48 | Application.Run(new ClientForm()); 49 | } 50 | } 51 | } -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // Crown-Owned Copyright (c) 6 | // General Information about an assembly is controlled through the following 7 | // set of attributes. Change these attribute values to modify the information 8 | // associated with an assembly. 9 | [assembly: AssemblyTitle("Sapient ASM Simulator")] 10 | [assembly: AssemblyDescription("")] 11 | [assembly: AssemblyConfiguration("")] 12 | [assembly: AssemblyCompany("QinetiQ")] 13 | [assembly: AssemblyProduct("Sapient")] 14 | [assembly: AssemblyCopyright("© Crown-Owned Copyright 2016-21")] 15 | [assembly: AssemblyTrademark("")] 16 | [assembly: AssemblyCulture("")] 17 | 18 | // Setting ComVisible to false makes the types in this assembly not visible 19 | // to COM components. If you need to access a type in this assembly from 20 | // COM, set the ComVisible attribute to true on that type. 21 | [assembly: ComVisible(false)] 22 | 23 | // The following GUID is for the ID of the typelib if this project is exposed to COM 24 | [assembly: Guid("3f6d53e1-e6bd-42eb-b0bc-3a91a73c5ebd")] 25 | 26 | // Version information for an assembly consists of the following four values: 27 | // 28 | // Major Version 29 | // Minor Version 30 | // Build Number 31 | // Revision 32 | // 33 | // You can specify all the values or you can default the Build and Revision Numbers 34 | // by using the '*' as shown below: 35 | // [assembly: AssemblyVersion("1.0.*")] 36 | [assembly: AssemblyVersion("2.7.4.0")] 37 | [assembly: AssemblyFileVersion("2.7.4.0")] 38 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/Properties/Settings.settings: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 127.0.0.1 7 | 8 | 9 | 14000 10 | 11 | 12 | ../Log/Log 13 | 14 | 15 | True 16 | 17 | 18 | ASM_sendlog 19 | 20 | 21 | 3600 22 | 23 | 24 | 0 25 | 26 | 27 | 1 28 | 29 | 30 | 5777512 31 | 32 | 33 | 565618 34 | 35 | 36 | 5777550 37 | 38 | 39 | RangeBearing 40 | 41 | 42 | True 43 | 44 | 45 | 0 46 | 47 | 48 | True 49 | 50 | 51 | image 52 | 53 | 54 | ship 55 | 56 | 57 | 8 58 | 59 | 60 | sensorType 61 | 62 | 63 | C:\StarTeam\00010855-Sapient\root\06_Test\Test ConfigurationV3\XML\ExpectedSystemResponseASM.txt 64 | 65 | 66 | C:\StarTeam\00010855-Sapient\root\06_Test\Test ConfigurationV3\XML 67 | 68 | 69 | Static 70 | 71 | 72 | 30U 73 | 74 | 75 | Steerable 76 | 77 | 78 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/RoutePlanGenerator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: RoutePlanGenerator.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | using System; 8 | using System.Collections.Generic; 9 | using System.Threading; 10 | using log4net; 11 | using SapientServices; 12 | using SapientServices.Communication; 13 | using SapientServices.Data; 14 | 15 | namespace SapientASMsimulator 16 | { 17 | /// 18 | /// Generate Route Plan Messages 19 | /// 20 | public class RoutePlanGenerator : XmlGenerators 21 | { 22 | #region Properties 23 | 24 | public bool ChangeRoutePlanID { get; set; } 25 | 26 | #endregion 27 | 28 | /// 29 | /// log4net logger 30 | /// 31 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 32 | 33 | #region Data Members 34 | 35 | private double maxLoopLatitude = Properties.Settings.Default.maxLatitude; 36 | 37 | private double longitude = start_longitude; 38 | private double latitude = start_latitude; 39 | 40 | /// 41 | /// message identifier 42 | /// 43 | private int messageId = 1; 44 | 45 | #endregion 46 | /// 47 | /// send out route plan messages, will loop until latitude is greater than 52.69 48 | /// there is a wait of 100ms between each send 49 | /// 50 | /// IConnection messenger object used to send messages over 51 | public void GenerateRoutePlans(object comms_connection, SapientLogger logger) 52 | { 53 | var messenger = (IConnection)comms_connection; 54 | 55 | var routePlan = new RoutePlan(); 56 | 57 | routePlan.sensorID = ASMId; 58 | routePlan.taskID = 1; 59 | routePlan.taskIDSpecified = true; 60 | 61 | do 62 | { 63 | routePlan.objectiveID = this.messageId; 64 | routePlan.objectiveIDSpecified = true; 65 | routePlan.timestamp = DateTime.UtcNow; 66 | routePlan.eta = routePlan.timestamp.AddSeconds(60); 67 | routePlan.etaSpecified = true; 68 | routePlan.routeName = string.Format("Route for ASM {0}", routePlan.sensorID); 69 | routePlan.routeDescription = string.Format("Route Plan for sensor {0} going to location {1} {2}", routePlan.sensorID, longitude, latitude); 70 | 71 | locationList routePlan1 = new locationList(); 72 | List locList = new List(); 73 | 74 | double xDelta = 1; 75 | double yDelta = 1; 76 | 77 | if (isUTM) 78 | { 79 | xDelta = 1.0; 80 | yDelta = 1.0; 81 | } 82 | else 83 | { 84 | xDelta = 0.00001; 85 | yDelta = 0.00001; 86 | } 87 | 88 | double waypointSeparation = xDelta * 10; 89 | 90 | 91 | for (int i = 0; i < 4; i++) 92 | { 93 | location loc = new location 94 | { 95 | X = longitude + xDelta * i * waypointSeparation, 96 | Y = latitude + yDelta * i * waypointSeparation 97 | }; 98 | 99 | locList.Add(loc); 100 | } 101 | 102 | routePlan1.location = locList.ToArray(); 103 | routePlan.locationList = routePlan1; 104 | 105 | if (latitude < maxLoopLatitude) 106 | { 107 | latitude += yDelta; 108 | longitude += xDelta; 109 | messageId++; 110 | } 111 | else 112 | { 113 | latitude = start_latitude; 114 | longitude = start_longitude; 115 | 116 | if (ChangeRoutePlanID) 117 | { 118 | messageId++; 119 | } 120 | } 121 | 122 | var xmlstring = ConfigXMLParser.Serialize(routePlan); 123 | 124 | bool retval = MessageSender.Send(messenger, xmlstring, logger); 125 | 126 | if (retval) 127 | { 128 | MessageCount++; 129 | } 130 | else 131 | { 132 | Log.ErrorFormat("Send Route Plan Failed {0}", MessageCount); 133 | } 134 | 135 | if (LoopMessages) 136 | { 137 | Thread.Sleep(LoopTime); 138 | } 139 | 140 | } while (LoopMessages); 141 | } 142 | } 143 | } 144 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/SapientAsmSimulatorV3.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | Debug 5 | x86 6 | 8.0.30703 7 | 2.0 8 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671} 9 | Exe 10 | Properties 11 | SapientASMsimulator 12 | SapientASMsimulator 13 | v4.8 14 | 15 | 16 | 512 17 | 18 | 19 | x86 20 | true 21 | full 22 | false 23 | bin\Debug\ 24 | DEBUG;TRACE 25 | prompt 26 | 4 27 | false 28 | 29 | 30 | x86 31 | pdbonly 32 | true 33 | bin\Release\ 34 | TRACE 35 | prompt 36 | 4 37 | false 38 | 39 | 40 | 41 | .\log4net.dll 42 | 43 | 44 | .\SapientServices.dll 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | True 69 | True 70 | Settings.settings 71 | 72 | 73 | 74 | 75 | Form 76 | 77 | 78 | ScriptForm.cs 79 | 80 | 81 | 82 | 83 | 84 | Form 85 | 86 | 87 | ClientForm.cs 88 | 89 | 90 | 91 | 92 | 93 | Designer 94 | 95 | 96 | SettingsSingleFileGenerator 97 | Settings.Designer.cs 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | ClientForm.cs 106 | Designer 107 | 108 | 109 | ScriptForm.cs 110 | 111 | 112 | 113 | 120 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/SapientServices.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientAsmSimulator/SapientAsmSimulatorV3/SapientServices.dll -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/TaskAckGenerator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: TaskAckGenerator.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientASMsimulator 8 | { 9 | using System; 10 | using System.IO; 11 | using log4net; 12 | using SapientServices; 13 | using SapientServices.Communication; 14 | using SapientServices.Data; 15 | 16 | /// 17 | /// Generate Task Acknowledgement messages 18 | /// 19 | public class TaskAckGenerator 20 | { 21 | /// 22 | /// Log4net logger 23 | /// 24 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 25 | 26 | /// 27 | /// sends out the task ACK message 28 | /// 29 | /// object used to send messages over 30 | /// main form 31 | /// task object 32 | /// file data logger 33 | public static void GenerateTaskAck(IConnection messenger, IGUIInterface form, SensorTask task, SapientLogger logger) 34 | { 35 | string xmlstring = GenerateXml(task); 36 | bool retval = MessageSender.Send(messenger, xmlstring, logger); 37 | 38 | if (retval) 39 | { 40 | form.UpdateOutputWindow("SensorTaskACK Sent"); 41 | Log.InfoFormat("Send SensorTaskACK {0} Succeeded", task.taskID); 42 | } 43 | else 44 | { 45 | form.UpdateOutputWindow("SensorTaskACK Send failed"); 46 | Log.ErrorFormat("Send SensorTaskACK {0} Failed", task.taskID); 47 | } 48 | } 49 | 50 | /// 51 | /// Generate XML message string 52 | /// 53 | /// Source Sensor Task Object 54 | /// XML string 55 | private static string GenerateXml(SensorTask task) 56 | { 57 | SensorTaskACK sensor_task_ack = new SensorTaskACK 58 | { 59 | sensorID = task.sensorID, 60 | taskID = task.taskID, 61 | timestamp = DateTime.UtcNow, 62 | status = "Accepted", 63 | }; 64 | 65 | sensor_task_ack.associatedFile = new[] 66 | { 67 | new SensorTaskACKAssociatedFile { type = "image", url = "filenameYYMMDD_HHMMSS.jpg" }, 68 | }; 69 | 70 | string xmlstring = ConfigXMLParser.Serialize(sensor_task_ack); 71 | File.WriteAllLines(@".\SensorTaskACK1.xml", new[] { xmlstring }); 72 | return xmlstring; 73 | } 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/XmlGenerators.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: XmlGenerators.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientASMsimulator 8 | { 9 | using log4net; 10 | 11 | /// 12 | /// Base class for XML generation 13 | /// 14 | public class XmlGenerators 15 | { 16 | /// 17 | /// Default Longitude or X coordinate to use in detection and sensor location 18 | /// 19 | protected static double start_longitude = Properties.Settings.Default.startLongitude; 20 | 21 | /// 22 | /// Default Latitude or Y coordinate to use in detection and sensor location 23 | /// 24 | protected static double start_latitude = Properties.Settings.Default.startLatitude; 25 | 26 | /// 27 | /// determine whether using UTM or GPS coordinates 28 | /// 29 | protected static bool isUTM = (start_longitude > 180) || (start_longitude < -180) || (start_latitude > 90) || (start_latitude < -90); 30 | 31 | /// 32 | /// Gets or sets the Sensor ID to use in SAPIENT messages 33 | /// 34 | public static int ASMId { get; set; } 35 | 36 | /// 37 | /// Gets or sets the Message count for each message type 38 | /// 39 | public long MessageCount { get; protected set; } 40 | 41 | /// 42 | /// Gets or sets a value indicating whether to send messages periodically 43 | /// 44 | public bool LoopMessages { get; set; } 45 | 46 | /// 47 | /// Gets or sets the period between sending messages 48 | /// 49 | public int LoopTime { get; set; } 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /SapientAsmSimulator/SapientAsmSimulatorV3/log4net.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientAsmSimulator/SapientAsmSimulatorV3/log4net.dll -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio Version 16 4 | VisualStudioVersion = 16.0.29411.108 5 | MinimumVisualStudioVersion = 10.0.40219.1 6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SapientDataAgent", "SapientDataAgentV3\SapientDataAgent.csproj", "{865D13B1-5CA3-470A-B5D6-89351CCA56EF}" 7 | EndProject 8 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SapientServices", "..\..\Inter Process Communications\SapientComms\SapientServicesV3\SapientServices.csproj", "{9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}" 9 | EndProject 10 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SapientDatabase", "..\SapientDatabase\SapientDatabase.csproj", "{F6812F94-A231-4B1C-BB27-2E10402F593B}" 11 | EndProject 12 | Global 13 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 14 | Debug|Any CPU = Debug|Any CPU 15 | Debug|Mixed Platforms = Debug|Mixed Platforms 16 | Debug|x86 = Debug|x86 17 | Release|Any CPU = Release|Any CPU 18 | Release|Mixed Platforms = Release|Mixed Platforms 19 | Release|x86 = Release|x86 20 | EndGlobalSection 21 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 22 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Debug|Any CPU.ActiveCfg = Debug|x86 23 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Debug|Mixed Platforms.ActiveCfg = Debug|x86 24 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Debug|Mixed Platforms.Build.0 = Debug|x86 25 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Debug|x86.ActiveCfg = Debug|x86 26 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Debug|x86.Build.0 = Debug|x86 27 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Release|Any CPU.ActiveCfg = Release|x86 28 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Release|Any CPU.Build.0 = Release|x86 29 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Release|Mixed Platforms.ActiveCfg = Release|x86 30 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Release|Mixed Platforms.Build.0 = Release|x86 31 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Release|x86.ActiveCfg = Release|x86 32 | {865D13B1-5CA3-470A-B5D6-89351CCA56EF}.Release|x86.Build.0 = Release|x86 33 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 34 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|Any CPU.Build.0 = Debug|Any CPU 35 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU 36 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU 37 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|x86.ActiveCfg = Debug|Any CPU 38 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|x86.Build.0 = Debug|Any CPU 39 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|Any CPU.ActiveCfg = Release|Any CPU 40 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|Any CPU.Build.0 = Release|Any CPU 41 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU 42 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|Mixed Platforms.Build.0 = Release|Any CPU 43 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|x86.ActiveCfg = Release|Any CPU 44 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|x86.Build.0 = Release|Any CPU 45 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 46 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Debug|Any CPU.Build.0 = Debug|Any CPU 47 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU 48 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU 49 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Debug|x86.ActiveCfg = Debug|Any CPU 50 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Debug|x86.Build.0 = Debug|Any CPU 51 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Release|Any CPU.ActiveCfg = Release|Any CPU 52 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Release|Any CPU.Build.0 = Release|Any CPU 53 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU 54 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Release|Mixed Platforms.Build.0 = Release|Any CPU 55 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Release|x86.ActiveCfg = Release|Any CPU 56 | {F6812F94-A231-4B1C-BB27-2E10402F593B}.Release|x86.Build.0 = Release|Any CPU 57 | EndGlobalSection 58 | GlobalSection(SolutionProperties) = preSolution 59 | HideSolutionNode = FALSE 60 | EndGlobalSection 61 | GlobalSection(ExtensibilityGlobals) = postSolution 62 | SolutionGuid = {3D7155E5-4B06-4CD8-A91B-75F3342AED4C} 63 | EndGlobalSection 64 | EndGlobal 65 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/IConnectionMonitor.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: IConnectionMonitor.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | /// 9 | /// Interface Class for capturing Data Agent Connection status. 10 | /// 11 | public interface IConnectionMonitor 12 | { 13 | /// 14 | /// Set Task Manager connected tick box. 15 | /// 16 | /// whether connected. 17 | void SetTaskManagerConnected(bool connected); 18 | 19 | /// 20 | /// Set client connected indicator. 21 | /// 22 | /// whether connected. 23 | void SetClientConnectedStatus(bool connected); 24 | 25 | /// 26 | /// Set Number of Clients. 27 | /// 28 | /// Number of Clients. 29 | void SetNumClients(int numClients); 30 | 31 | /// 32 | /// Set Number of GUI Clients Connected. 33 | /// 34 | /// Number of GUI Clients. 35 | void SetNumGuiClients(int numClients); 36 | 37 | /// 38 | /// Hide indications for GUI connections. 39 | /// 40 | void DisableGUIConnectionReporting(); 41 | 42 | /// 43 | /// Set window title text. 44 | /// 45 | /// text string. 46 | void SetWindowText(string text); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/MessageParserTest.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: MessageParserTest.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | using System; 9 | using SapientDatabase; 10 | 11 | /// 12 | /// Unit test class to wrap message parser. 13 | public class MessageParserTest 14 | { 15 | private SapientMessageParser messageParser; 16 | 17 | private string msg = @" 18 | 2019-05-29T07:41:59.106Z 19 | 501 20 | 677 21 | 1 22 | 0 23 | 24 | 1000 25 | 133.384 26 | 1000 27 | 28 | 29 | 30 | 31 | 32 | "; 33 | 34 | /// 35 | /// Initializes a new instance of the class. 36 | /// 37 | public MessageParserTest() 38 | { 39 | messageParser = new SapientMessageParser(new SapientDataAgentClientProtocol(Properties.Settings.Default.ForwardAlerts, 0), true); 40 | Program.previouslyConnectedASMs.AddOrUpdate(501, DateTime.Now, (key, previousValue) => DateTime.Now); 41 | } 42 | 43 | /// 44 | /// Unit test. 45 | /// 46 | /// Database Object. 47 | public void Test(Database database) 48 | { 49 | int loop = 0; 50 | for (loop = 0; loop < 100000; loop++) 51 | { 52 | string msgwithterm = msg + "\0" + msg + "\0" + msg + "\0" + msg + "\0" + msg + "\0" + msg + "\0" + msg + "\0"; 53 | GC.Collect(); 54 | messageParser.BuildAndNotify(msgwithterm, database, 1); 55 | } 56 | } 57 | } 58 | } 59 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Mono.Security.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/Mono.Security.dll -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/NETGeographic.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/NETGeographic.dll -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Npgsql.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/Npgsql.dll -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/ObjectiveInformation.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: ObjectiveInformation.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | using System; 9 | using System.Collections.Concurrent; 10 | using System.Linq; 11 | using System.Timers; 12 | using log4net; 13 | using SapientDatabase; 14 | using SapientServices.Data; 15 | 16 | /// 17 | /// Class to handle the objective information store 18 | /// 19 | public static class ObjectiveInformation 20 | { 21 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 22 | 23 | // concurrent dictionary to handle reading and writing to objective list 24 | private static ConcurrentDictionary dictObjectiveInternalInfo = new ConcurrentDictionary(); 25 | 26 | // timer for printing objective list info every 30 seconds 27 | private static System.Timers.Timer printListTimer = new System.Timers.Timer(TimeSpan.FromMinutes(0.5).TotalMilliseconds); 28 | 29 | /// 30 | /// Initializes static members of the class. 31 | /// Sets the parameters for the list all timer 32 | /// 33 | static ObjectiveInformation() 34 | { 35 | printListTimer.AutoReset = true; 36 | printListTimer.Elapsed += new System.Timers.ElapsedEventHandler(ListAll); 37 | } 38 | 39 | /// 40 | /// Add objectives to the objective dictionary and starts the list all timer 41 | /// 42 | /// objective message object 43 | public static void AddObjective(Objective objective) 44 | { 45 | dictObjectiveInternalInfo.TryAdd(objective, "No acknowledgement"); 46 | printListTimer.Start(); 47 | } 48 | 49 | /// 50 | /// Update objective status based on sensorTask Acknowledgement 51 | /// 52 | /// objective ID 53 | /// sensor ID 54 | /// status text 55 | /// database object 56 | public static void ApproveObjective(int objectiveID, int sensorID, string status, Database database) 57 | { 58 | try 59 | { 60 | dictObjectiveInternalInfo[dictObjectiveInternalInfo.Where(e => e.Key.objectiveID == objectiveID && e.Key.sensorID == sensorID).Single().Key] = status; 61 | } 62 | catch 63 | { 64 | Log.Debug($@"Acknowledgement Task ID: {objectiveID} does not belong to an objective"); 65 | } 66 | 67 | try 68 | { 69 | database.DbApproval(objectiveID, sensorID, status); 70 | } 71 | catch (Exception e) 72 | { 73 | Log.Error("Error writing approval status to DB: " + e.Message); 74 | } 75 | } 76 | 77 | /// 78 | /// Remove old objectives from the objective list and pause timer if empty 79 | /// 80 | private static void RemoveOldObjectives() 81 | { 82 | string valueout; 83 | 84 | foreach (var key in (dictObjectiveInternalInfo.Where(e => e.Key.timestamp < (DateTime.UtcNow.AddHours(-1))).Select(f => f.Key))) 85 | { 86 | dictObjectiveInternalInfo.TryRemove(key, out valueout); 87 | } 88 | 89 | if (dictObjectiveInternalInfo.Count == 0) 90 | { 91 | printListTimer.Stop(); 92 | } 93 | } 94 | 95 | /// 96 | /// purge old objectives and print pertinent information 97 | /// 98 | /// not used 99 | /// not used 100 | public static void ListAll(object sender, ElapsedEventArgs e) 101 | { 102 | if (dictObjectiveInternalInfo.Count > 0) 103 | { 104 | RemoveOldObjectives(); 105 | foreach (var pair in (dictObjectiveInternalInfo.OrderByDescending(a => a.Key.timestamp).GroupBy(b => b.Key.sensorID).Select(c => c.First()))) 106 | { 107 | Log.Info($@"SensorID: {pair.Key.sensorID}, ObjectiveID: {pair.Key.objectiveID}, Objective Information: {pair.Key.description}, Objective timestamp: {pair.Key.timestamp}, Objective Status: {pair.Value}"); 108 | } 109 | } 110 | } 111 | } 112 | } 113 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/PresetHeartbeat.cs: -------------------------------------------------------------------------------- 1 | // ----------------------------------------------------------------------- 2 | // 3 | // TODO: Update copyright text. 4 | // Crown-Owned Copyright (c) 5 | // 6 | // ----------------------------------------------------------------------- 7 | 8 | namespace SapientMiddleware 9 | { 10 | using System; 11 | using System.Collections.Generic; 12 | using System.IO; 13 | using System.Linq; 14 | using System.Text; 15 | using SapientServices; 16 | 17 | /// 18 | /// TODO: Update summary. 19 | /// 20 | public class PresetHeartbeat 21 | { 22 | private StatusReport statusReport; 23 | 24 | private SensorRegistration registration; 25 | 26 | public PresetHeartbeat() 27 | { 28 | statusReport = new StatusReport(); 29 | registration = new SensorRegistration(); 30 | } 31 | 32 | public void LoadRegistration(string fileName) 33 | { 34 | try 35 | { 36 | Console.WriteLine("Opening Reg File:" + fileName + "\n"); 37 | StreamReader sr = new StreamReader(new FileStream(fileName, FileMode.Open, FileAccess.Read)); 38 | string message = sr.ReadToEnd(); 39 | } 40 | catch ( FileNotFoundException ) 41 | { 42 | Console.WriteLine("File Not Found: " + fileName); 43 | } 44 | catch ( Exception ex ) 45 | { 46 | Console.WriteLine(ex.ToString()); 47 | } 48 | } 49 | 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // Crown-Owned Copyright (c) 6 | // General Information about an assembly is controlled through the following 7 | // set of attributes. Change these attribute values to modify the information 8 | // associated with an assembly. 9 | [assembly: AssemblyTitle("Sapient Data Agent")] 10 | [assembly: AssemblyDescription("")] 11 | [assembly: AssemblyConfiguration("")] 12 | [assembly: AssemblyCompany("QinetiQ")] 13 | [assembly: AssemblyProduct("Sapient")] 14 | [assembly: AssemblyCopyright("© Crown-Owned Copyright 2021")] 15 | [assembly: AssemblyTrademark("")] 16 | [assembly: AssemblyCulture("")] 17 | 18 | // Setting ComVisible to false makes the types in this assembly not visible 19 | // to COM components. If you need to access a type in this assembly from 20 | // COM, set the ComVisible attribute to true on that type. 21 | [assembly: ComVisible(false)] 22 | 23 | // The following GUID is for the ID of the typelib if this project is exposed to COM 24 | [assembly: Guid("639d9393-b53e-4776-805b-c5748b7e67c1")] 25 | 26 | // Version information for an assembly consists of the following four values: 27 | // 28 | // Major Version 29 | // Minor Version 30 | // Build Number 31 | // Revision 32 | // 33 | // You can specify all the values or you can default the Build and Revision Numbers 34 | // by using the '*' as shown below: 35 | // [assembly: AssemblyVersion("1.0.*")] 36 | [assembly: AssemblyVersion("2.7.4.0")] 37 | [assembly: AssemblyFileVersion("2.7.4.0")] 38 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Properties/Resources.Designer.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | namespace SapientMiddleware.Properties { 12 | using System; 13 | 14 | 15 | /// 16 | /// A strongly-typed resource class, for looking up localized strings, etc. 17 | /// 18 | // This class was auto-generated by the StronglyTypedResourceBuilder 19 | // class via a tool like ResGen or Visual Studio. 20 | // To add or remove a member, edit your .ResX file then rerun ResGen 21 | // with the /str option, or rebuild your VS project. 22 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "16.0.0.0")] 23 | [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] 24 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] 25 | internal class Resources { 26 | 27 | private static global::System.Resources.ResourceManager resourceMan; 28 | 29 | private static global::System.Globalization.CultureInfo resourceCulture; 30 | 31 | [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")] 32 | internal Resources() { 33 | } 34 | 35 | /// 36 | /// Returns the cached ResourceManager instance used by this class. 37 | /// 38 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] 39 | internal static global::System.Resources.ResourceManager ResourceManager { 40 | get { 41 | if (object.ReferenceEquals(resourceMan, null)) { 42 | global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("SapientMiddleware.Properties.Resources", typeof(Resources).Assembly); 43 | resourceMan = temp; 44 | } 45 | return resourceMan; 46 | } 47 | } 48 | 49 | /// 50 | /// Overrides the current thread's CurrentUICulture property for all 51 | /// resource lookups using this strongly typed resource class. 52 | /// 53 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] 54 | internal static global::System.Globalization.CultureInfo Culture { 55 | get { 56 | return resourceCulture; 57 | } 58 | set { 59 | resourceCulture = value; 60 | } 61 | } 62 | 63 | /// 64 | /// Looks up a localized resource of type System.Drawing.Bitmap. 65 | /// 66 | internal static System.Drawing.Bitmap greenLight { 67 | get { 68 | object obj = ResourceManager.GetObject("greenLight", resourceCulture); 69 | return ((System.Drawing.Bitmap)(obj)); 70 | } 71 | } 72 | 73 | /// 74 | /// Looks up a localized resource of type System.Drawing.Bitmap. 75 | /// 76 | internal static System.Drawing.Bitmap redLight { 77 | get { 78 | object obj = ResourceManager.GetObject("redLight", resourceCulture); 79 | return ((System.Drawing.Bitmap)(obj)); 80 | } 81 | } 82 | 83 | /// 84 | /// Looks up a localized resource of type System.Drawing.Bitmap. 85 | /// 86 | internal static System.Drawing.Bitmap yellowLight { 87 | get { 88 | object obj = ResourceManager.GetObject("yellowLight", resourceCulture); 89 | return ((System.Drawing.Bitmap)(obj)); 90 | } 91 | } 92 | } 93 | } 94 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Resources/greenLight.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/Resources/greenLight.png -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Resources/redLight.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/Resources/redLight.png -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/Resources/yellowLight.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/Resources/yellowLight.png -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/SapientConnectionMonitor.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: SapientConnectionMonitor.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | using log4net; 9 | 10 | /// 11 | /// Class for capturing Data Agent Connection status. 12 | /// 13 | public class SapientConnectionMonitor : IConnectionMonitor 14 | { 15 | /// 16 | /// Log4net logger. 17 | /// 18 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 19 | 20 | /// 21 | /// Set Task Manager connected tick box. 22 | /// 23 | /// whether connected. 24 | public void SetTaskManagerConnected(bool connected) 25 | { 26 | if (connected) 27 | { 28 | Log.Warn("Tasking Connection Connected"); 29 | } 30 | else 31 | { 32 | Log.Warn("Tasking Connection Disconnected"); 33 | } 34 | } 35 | 36 | /// 37 | /// Set client connected indicator. 38 | /// 39 | /// whether connected. 40 | public void SetClientConnectedStatus(bool connected) 41 | { 42 | if (connected) 43 | { 44 | Log.Warn("Client Connection Connected"); 45 | } 46 | else 47 | { 48 | Log.Warn("Client Connection Disconnected"); 49 | } 50 | } 51 | 52 | /// 53 | /// Set Number of Clients. 54 | /// 55 | /// Number of Clients. 56 | public void SetNumClients(int numClients) 57 | { 58 | Log.WarnFormat("{0} Client(s) Connected", numClients); 59 | } 60 | 61 | /// 62 | /// Set Number of GUI Clients Connected. 63 | /// 64 | /// Number of GUI Clients. 65 | public void SetNumGuiClients(int numClients) 66 | { 67 | Log.WarnFormat("{0} GUI Client(s) Connected", numClients); 68 | } 69 | 70 | /// 71 | /// Disable logging of GUI connections - nothing to do at the moment. 72 | /// 73 | public void DisableGUIConnectionReporting() 74 | { 75 | // Do nothing at the moment. 76 | } 77 | 78 | /// 79 | /// Set window title text. 80 | /// 81 | /// text string. 82 | public void SetWindowText(string text) 83 | { 84 | Log.Warn(text); 85 | } 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/SapientDatabase.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/SapientDatabase.dll -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/SapientServices.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/SapientServices.dll -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/StatusIndicator.Designer.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: StatusIndicator.Designer.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | partial class StatusIndicator 9 | { 10 | /// 11 | /// Required designer variable. 12 | /// 13 | private System.ComponentModel.IContainer components = null; 14 | 15 | /// 16 | /// Clean up any resources being used. 17 | /// 18 | /// true if managed resources should be disposed; otherwise, false. 19 | protected override void Dispose(bool disposing) 20 | { 21 | if (disposing && (components != null)) 22 | { 23 | components.Dispose(); 24 | } 25 | base.Dispose(disposing); 26 | } 27 | 28 | #region Component Designer generated code 29 | 30 | /// 31 | /// Required method for Designer support - do not modify 32 | /// the contents of this method with the code editor. 33 | /// 34 | private void InitializeComponent() 35 | { 36 | this.SuspendLayout(); 37 | // 38 | // StatusIndicator 39 | // 40 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); 41 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; 42 | this.Name = "StatusIndicator"; 43 | this.Size = new System.Drawing.Size(36, 36); 44 | this.ResumeLayout(false); 45 | 46 | } 47 | 48 | #endregion 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/StatusIndicator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: StatusIndicator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | using System; 9 | using System.Collections.Generic; 10 | using System.ComponentModel; 11 | using System.Data; 12 | using System.Drawing; 13 | using System.Linq; 14 | using System.Text; 15 | using System.Windows.Forms; 16 | 17 | /// 18 | /// User control to provide a red/green indicator. 19 | /// 20 | public partial class StatusIndicator : UserControl 21 | { 22 | /// 23 | /// Current indicator state 24 | /// 25 | private bool currentState = false; 26 | 27 | private bool warning = false; 28 | 29 | /// 30 | /// Initializes a new instance of the class. 31 | /// 32 | public StatusIndicator() 33 | { 34 | InitializeComponent(); 35 | } 36 | 37 | /// 38 | /// Set Indicator state. 39 | /// 40 | /// indicator state. 41 | public void SetStatus(bool state) 42 | { 43 | if ((currentState != state) || warning) 44 | { 45 | currentState = state; 46 | warning = false; 47 | 48 | if (state) 49 | { 50 | this.BackgroundImage = Properties.Resources.greenLight; 51 | } 52 | else 53 | { 54 | this.BackgroundImage = Properties.Resources.redLight; 55 | } 56 | } 57 | } 58 | 59 | /// 60 | /// Set Indicator to warning - yellow. 61 | /// 62 | public void SetStatusWarning() 63 | { 64 | this.BackgroundImage = Properties.Resources.yellowLight; 65 | warning = true; 66 | } 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/TaskPermissions.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: TaskPermissions.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | using System.Collections.Generic; 9 | using log4net; 10 | 11 | /// 12 | /// Holds the identities of sensors for which the GUI has taken control. 13 | /// 14 | public class TaskPermissions 15 | { 16 | /// 17 | /// Log4net logger 18 | /// 19 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 20 | 21 | /// 22 | /// Contains the ids of any sensors that the GUI has taken control of. Once released by the GUI, the id is removed from this set. 23 | /// 24 | private ISet controlledIds; 25 | 26 | /// 27 | /// Used to protect access to controlledIds. 28 | /// 29 | private object locker = new object(); 30 | 31 | /// 32 | /// Creates a new instance. 33 | /// 34 | public TaskPermissions() 35 | { 36 | controlledIds = new SortedSet(); 37 | } 38 | 39 | /// 40 | /// Checks if the HLDMM currently has control of this ASM. 41 | /// 42 | /// The identifier of the ASM. 43 | /// True if the HLDMM has control of the ASM and should forward these messages, false if it should reject them. 44 | public bool HldmmHasControl(int asmId) 45 | { 46 | bool hasControl = true; 47 | lock (locker) 48 | { 49 | // HLDMM has control is the ASM ID is NOT in the set. 50 | hasControl = !controlledIds.Contains(asmId); 51 | } 52 | 53 | return hasControl; 54 | } 55 | 56 | /// 57 | /// Checks if the GuiProtocol class should forward sensor task messages with this id. 58 | /// 59 | /// The identifier for the ASM. 60 | /// True if the GuiProtocol class should forward, false if it should reject it. 61 | public bool GuiProtocolShouldForward(int asmId) 62 | { 63 | bool shouldForward = true; 64 | lock (locker) 65 | { 66 | // sensor task messages should only be forwarded if the GUI has taken control, which means the ASM ID 67 | // be in the set. 68 | shouldForward = controlledIds.Contains(asmId); 69 | } 70 | 71 | return shouldForward; 72 | } 73 | 74 | /// 75 | /// Records that the GUI has taken control of the given sensor. 76 | /// 77 | /// The identifier of the sensor. 78 | public void TakeControl(int asmId) 79 | { 80 | lock (locker) 81 | { 82 | if(controlledIds.Add(asmId)) 83 | { 84 | Log.Info($"GUI taking control of sensor {asmId}."); 85 | } 86 | } 87 | } 88 | 89 | /// 90 | /// Records that the GUI has released control of the given sensor. 91 | /// 92 | /// The identifier of the sensor. 93 | public void ReleaseControl(int asmId) 94 | { 95 | lock (locker) 96 | { 97 | if(controlledIds.Remove(asmId)) 98 | { 99 | Log.Info($"GUI releasing control of sensor {asmId}."); 100 | } 101 | } 102 | } 103 | } 104 | } 105 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/TextForm.Designer.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: TextForm.Designer.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | public partial class TextForm 9 | { 10 | /// 11 | /// Required designer variable. 12 | /// 13 | private System.ComponentModel.IContainer components = null; 14 | 15 | /// 16 | /// Clean up any resources being used. 17 | /// 18 | /// true if managed resources should be disposed; otherwise, false. 19 | protected override void Dispose(bool disposing) 20 | { 21 | if (disposing && (components != null)) 22 | { 23 | components.Dispose(); 24 | } 25 | 26 | base.Dispose(disposing); 27 | } 28 | 29 | #region Windows Form Designer generated code 30 | 31 | /// 32 | /// Required method for Designer support - do not modify 33 | /// the contents of this method with the code editor. 34 | /// 35 | private void InitializeComponent() 36 | { 37 | this.textBox1 = new System.Windows.Forms.TextBox(); 38 | this.SuspendLayout(); 39 | // 40 | // textBox1 41 | // 42 | this.textBox1.Dock = System.Windows.Forms.DockStyle.Fill; 43 | this.textBox1.Location = new System.Drawing.Point(0, 0); 44 | this.textBox1.Multiline = true; 45 | this.textBox1.Name = "textBox1"; 46 | this.textBox1.ReadOnly = true; 47 | this.textBox1.ScrollBars = System.Windows.Forms.ScrollBars.Vertical; 48 | this.textBox1.Size = new System.Drawing.Size(284, 451); 49 | this.textBox1.TabIndex = 0; 50 | // 51 | // TextForm 52 | // 53 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); 54 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; 55 | this.ClientSize = new System.Drawing.Size(284, 451); 56 | this.Controls.Add(this.textBox1); 57 | this.Name = "TextForm"; 58 | this.Text = "TextForm"; 59 | this.ResumeLayout(false); 60 | this.PerformLayout(); 61 | 62 | } 63 | 64 | #endregion 65 | 66 | private System.Windows.Forms.TextBox textBox1; 67 | } 68 | } -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/TextForm.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: TextForm.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientMiddleware 7 | { 8 | using System; 9 | using System.Windows.Forms; 10 | 11 | /// 12 | /// Class for form displaying text information. 13 | /// 14 | public partial class TextForm : Form 15 | { 16 | /// 17 | /// Initializes a new instance of the class. 18 | /// 19 | public TextForm() 20 | { 21 | InitializeComponent(); 22 | } 23 | 24 | /// 25 | /// Delegate for AddText method. 26 | /// 27 | /// text string to add to form. 28 | private delegate void AddTextDelegate(string text); 29 | 30 | /// 31 | /// Set form to show only specified text. 32 | /// 33 | /// text string. 34 | public void SetText(string text) 35 | { 36 | this.textBox1.Text = text; 37 | } 38 | 39 | /// 40 | /// Add text to form. 41 | /// 42 | /// text string to add to form. 43 | public void AddText(string text) 44 | { 45 | if (this.InvokeRequired) 46 | { 47 | // Create a delegate to self 48 | AddTextDelegate doAddText = 49 | new AddTextDelegate(this.AddText); 50 | 51 | // "Recurse once, onto another thread" 52 | this.Invoke(doAddText, new object[] { text }); 53 | } 54 | else 55 | { 56 | if (this.textBox1.Text != string.Empty) 57 | { 58 | this.textBox1.AppendText(Environment.NewLine); 59 | } 60 | 61 | this.textBox1.AppendText(text); 62 | } 63 | } 64 | 65 | /// 66 | /// Clearr all text from form. 67 | /// 68 | public void Clear() 69 | { 70 | this.textBox1.Clear(); 71 | } 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /SapientDataAgent/SapientDataAgentV3/log4net.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDataAgent/SapientDataAgentV3/log4net.dll -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/AlertConstants.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: AlertConstants.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | 6 | namespace SapientDatabase.DatabaseTables 7 | { 8 | /// 9 | /// The names of alert tables and sequences. 10 | /// 11 | public static class AlertConstants 12 | { 13 | /// 14 | /// Primary ASM Alert Table 15 | /// 16 | public static class Alert 17 | { 18 | public const string Table = "alert_v3"; 19 | public const string Seq = "alert_id_seq"; 20 | public const string Pkey = "alert_pkey"; 21 | } 22 | 23 | /// 24 | /// ASM Alert Associated Detection Table 25 | /// 26 | public static class AlertAssocDetection 27 | { 28 | public const string Table = "alert_assoc_detection_v3"; 29 | public const string KeyIdSeq = Alert.Seq; 30 | public const string Pkey = "alert_assoc_detection_pkey"; 31 | } 32 | 33 | /// 34 | /// ASM Alert Associated File Table 35 | /// 36 | public static class AlertAssocFile 37 | { 38 | public const string Table = "alert_assoc_file_v3"; 39 | public const string KeyIdSeq = Alert.Seq; 40 | public const string Pkey = "alert_assoc_file_pkey"; 41 | } 42 | 43 | /// 44 | /// ASM Alert Cartesian Location Table 45 | /// 46 | public static class AlertLocation 47 | { 48 | public const string Table = "alert_location_v3"; 49 | public const string KeyIdSeq = Alert.Seq; 50 | public const string Pkey = "alert_location_pkey"; 51 | } 52 | 53 | /// 54 | /// ASM Alert Spherical Location Table 55 | /// 56 | public static class AlertRangeBearing 57 | { 58 | public const string Table = "alert_range_bearing_v3"; 59 | public const string Seq = Alert.Seq; 60 | public const string Pkey = "alert_range_bearing_pkey"; 61 | } 62 | 63 | /// 64 | /// Primary HLDMM Alert Table 65 | /// 66 | public static class HLAlert 67 | { 68 | public const string Table = "hl_alert_v3"; 69 | public const string Seq = "hl_alert_id_seq"; 70 | public const string Pkey = "hl_alert_pkey"; 71 | } 72 | 73 | /// 74 | /// HLDMM Alert Associated Detection Table 75 | /// 76 | public static class HLAlertAssocDetection 77 | { 78 | public const string Table = "hl_alert_assoc_detection_v3"; 79 | public const string KeyIdSeq = HLAlert.Seq; 80 | public const string Pkey = "hl_alert_assoc_detection_pkey"; 81 | } 82 | 83 | /// 84 | /// HLDMM Alert Associated File Table 85 | /// 86 | public static class HLAlertAssocFile 87 | { 88 | public const string Table = "hl_alert_assoc_file_v3"; 89 | public const string KeyIdSeq = HLAlert.Seq; 90 | public const string Pkey = "hl_alert_assoc_file_pkey"; 91 | } 92 | 93 | /// 94 | /// HLDMM Alert Cartesian Location Table 95 | /// 96 | public static class HLAlertLocation 97 | { 98 | public const string Table = "hl_alert_location_v3"; 99 | public const string KeyIdSeq = HLAlert.Seq; 100 | public const string Pkey = "hl_alert_location_pkey"; 101 | } 102 | 103 | /// 104 | /// HLDMM Alert Spherical Location Table 105 | /// 106 | public static class HLAlertRangeBearing 107 | { 108 | public const string Table = "hl_alert_range_bearing_v3"; 109 | public const string Seq = HLAlert.Seq; 110 | public const string Pkey = "hl_alert_range_bearing_pkey"; 111 | } 112 | } 113 | } 114 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/ObjectiveConstants.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: ObjectiveConstants.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | /// 8 | /// The names of objective tables and sequences. 9 | /// 10 | public static class ObjectiveConstants 11 | { 12 | public static class Objective 13 | { 14 | public const string Table = "hl_objective_v3"; 15 | public const string Pkey = "hl_objective_pkey"; 16 | } 17 | 18 | public static class Approval 19 | { 20 | public const string Table = "hl_task_approval_v3"; 21 | public const string Pkey = "hl_task_approval_pkey"; 22 | } 23 | } 24 | } -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/ObjectiveTableCreator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: ObjectiveTableCreator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | using log4net; 8 | using Npgsql; 9 | 10 | /// 11 | /// Helper functions for creating the objective tables and sequences. 12 | /// 13 | public static class ObjectiveTableCreator 14 | { 15 | /// 16 | /// Creates all the objective sequences, indices and tables. 17 | /// 18 | /// The database connection. 19 | /// The message logger. 20 | public static void Create(NpgsqlConnection connection, ILog logger) 21 | { 22 | using (var command = new NpgsqlCommand { Connection = connection }) 23 | { 24 | CreateObjectiveTable(ObjectiveConstants.Objective.Table, ObjectiveConstants.Objective.Pkey, command, logger); 25 | CreateApprovalTable(ObjectiveConstants.Approval.Table, ObjectiveConstants.Approval.Pkey, command, logger); 26 | } 27 | } 28 | 29 | /// 30 | /// Creates the Objective table. 31 | /// 32 | /// The table name. 33 | /// The table primary key constraint. 34 | /// The database command to use. 35 | /// The message logger. 36 | private static void CreateObjectiveTable(string tableName, string tablePkey, NpgsqlCommand command, ILog logger) 37 | { 38 | command.CommandText = @"CREATE TABLE IF NOT EXISTS " + tableName + @" ( 39 | objective_time timestamp without time zone NOT NULL, 40 | update_time timestamp without time zone NOT NULL, 41 | source_id bigint NOT NULL, 42 | objective_id bigint NOT NULL, 43 | sensor_id bigint NOT NULL, 44 | type text, 45 | status text, 46 | description text, 47 | x double precision NOT NULL, 48 | y double precision NOT NULL, 49 | z double precision, 50 | priority text, 51 | ranking double precision, 52 | information text, 53 | object_id bigint, 54 | region_id integer, 55 | key_id bigserial, 56 | CONSTRAINT " + tablePkey + @" PRIMARY KEY (key_id));"; 57 | command.ExecuteNonQuery(); 58 | 59 | logger.Info("Created table " + tableName); 60 | } 61 | 62 | /// 63 | /// Creates the Approval table. 64 | /// 65 | /// The table name. 66 | /// The table primary key constraint. 67 | /// The database command to use. 68 | /// The message logger. 69 | private static void CreateApprovalTable(string tableName, string tablePkey, NpgsqlCommand command, ILog logger) 70 | { 71 | command.CommandText = @"CREATE TABLE IF NOT EXISTS " + tableName + @" ( 72 | update_time timestamp without time zone NOT NULL, 73 | sensor_id bigint NOT NULL, 74 | objective_id bigint NOT NULL, 75 | approval_status text, 76 | key_id bigserial, 77 | CONSTRAINT " + tablePkey + @" PRIMARY KEY (key_id));"; 78 | command.ExecuteNonQuery(); 79 | 80 | logger.Info("Created table " + tableName); 81 | } 82 | } 83 | } 84 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/RoutePlanConstants.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: RoutePlanConstants.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | /// 8 | /// The names of route plan tables and sequences. 9 | /// 10 | internal static class RoutePlanConstants 11 | { 12 | public const string Table = "route_plan_v3"; 13 | public const string Seq = "route_plan_id_seq"; 14 | public const string Pkey = "route_plan_pkey"; 15 | public const string CommonKeyName = "route_plan_id"; 16 | } 17 | 18 | /// 19 | /// The names of route plan field of view table and sequences. 20 | /// 21 | internal static class RoutePlanRangeBearingConstants 22 | { 23 | public const string Table = "route_plan_fov_range_bearing_v3"; 24 | public const string IdSeq = RoutePlanConstants.Seq; 25 | public const string Pkey = "route_plan_range_bearing_pkey"; 26 | public const string CommonKeyName = RoutePlanConstants.CommonKeyName; 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/RoutePlanTableCreator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: RoutePlanTableCreator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | using log4net; 8 | using Npgsql; 9 | 10 | /// 11 | /// Helper functions for creating the RoutePlan tables and sequences. 12 | /// 13 | public static class RoutePlanTableCreator 14 | { 15 | /// 16 | /// Creates all the Route Plan sequences, indices and tables. 17 | /// 18 | /// The database connection. 19 | /// The message logger. 20 | public static void Create(NpgsqlConnection connection, ILog logger) 21 | { 22 | using (var command = new NpgsqlCommand { Connection = connection }) 23 | { 24 | DatabaseUtil.CreateSequence(RoutePlanConstants.Seq, command, logger); 25 | 26 | CreateRoutePlanTable( 27 | RoutePlanConstants.Table, 28 | RoutePlanConstants.Seq, 29 | RoutePlanConstants.Pkey, 30 | command, 31 | logger); 32 | 33 | StatusReportTableCreator.CreateRangeBearingTable( 34 | RoutePlanRangeBearingConstants.Table, 35 | RoutePlanRangeBearingConstants.IdSeq, 36 | RoutePlanRangeBearingConstants.Pkey, 37 | RoutePlanRangeBearingConstants.CommonKeyName, 38 | command, 39 | logger); 40 | 41 | CreateIndices(command, logger); 42 | } 43 | } 44 | 45 | /// 46 | /// Creates the Route Plan table. 47 | /// 48 | /// The table name. 49 | /// The sequence for the primary key. 50 | /// The table primary key constraint. 51 | /// The database command to use. 52 | /// The message logger. 53 | private static void CreateRoutePlanTable(string tableName, string idSeq, string tablePkey, NpgsqlCommand command, ILog logger) 54 | { 55 | command.CommandText = string.Format($@"CREATE TABLE IF NOT EXISTS {tableName} ( 56 | source_id bigint NOT NULL, 57 | message_time timestamp without time zone NOT NULL, 58 | update_time timestamp without time zone NOT NULL, 59 | sensor_id bigint NOT NULL, 60 | task_id bigint NOT NULL, 61 | objective_id bigint NOT NULL, 62 | route_name text, 63 | description text, 64 | location path NOT NULL, 65 | eta timestamp without time zone, 66 | route_status text, 67 | xy_fov polygon, 68 | key_id bigint DEFAULT nextval('{idSeq}') NOT NULL, 69 | CONSTRAINT {tablePkey} PRIMARY KEY (key_id));"); 70 | command.ExecuteNonQuery(); 71 | 72 | logger.Info("Created table " + tableName); 73 | } 74 | 75 | /// 76 | /// Creates indices for sensor report tables. 77 | /// 78 | /// The database command to use. 79 | /// The message logger. 80 | private static void CreateIndices(NpgsqlCommand command, ILog logger) 81 | { 82 | try 83 | { 84 | command.CommandText = @" 85 | CREATE INDEX route_plan_source_id 86 | ON route_plan_v3 USING btree (source_id); 87 | 88 | CREATE INDEX route_plan_range_bearing_source_id 89 | ON route_plan_fov_range_bearing_v3 USING btree (source_id);"; 90 | command.ExecuteNonQuery(); 91 | 92 | command.CommandText = @" 93 | CREATE INDEX route_plan_time_id 94 | ON route_plan_v3 USING btree (update_time); 95 | 96 | CREATE INDEX route_plan_range_bearing_time_id 97 | ON route_plan_fov_range_bearing_v3 USING btree (update_time);"; 98 | 99 | logger.Info("Created route_plan indices in db."); 100 | } 101 | catch (NpgsqlException e) 102 | { 103 | logger.Error("Can't create route_plan indices in db.", e); 104 | } 105 | } 106 | } 107 | } 108 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/SensorLocationOffsetConstants.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: SensorLocationOffsetConstants.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | /// 8 | /// The names of sensor location offset tables and sequences. 9 | /// 10 | public class SensorLocationOffsetConstants 11 | { 12 | public const string Table = "sensor_location_offset"; 13 | public const string Pkey = "sensor_location_offset_pkey"; 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/SensorLocationOffsetTableCreator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: SensorLocationOffsetTableCreator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | using log4net; 8 | using Npgsql; 9 | 10 | /// 11 | /// creator of sensor location offset table 12 | /// 13 | public class SensorLocationOffsetTableCreator 14 | { 15 | public static void Create(NpgsqlConnection connection, ILog logger) 16 | { 17 | using (var command = new NpgsqlCommand { Connection = connection }) 18 | { 19 | CreateLocationOffsetTable(SensorLocationOffsetConstants.Table, SensorLocationOffsetConstants.Pkey, command, logger); 20 | } 21 | } 22 | 23 | /// 24 | /// Creates the sensor location offset table. 25 | /// 26 | /// The table name. 27 | /// The table primary key constraint. 28 | /// The database command to use. 29 | /// The message logger. 30 | private static void CreateLocationOffsetTable(string tableName, string tablePkey, NpgsqlCommand command, ILog logger) 31 | { 32 | command.CommandText = @"CREATE TABLE IF NOT EXISTS " + tableName + @" ( 33 | update_time timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP, 34 | sensor_id bigint NOT NULL UNIQUE, 35 | x_offset double precision NOT NULL, 36 | y_offset double precision NOT NULL, 37 | z_offset double precision NOT NULL, 38 | az_offset double precision NOT NULL, 39 | ele_offset double precision NOT NULL, 40 | key_id bigserial, 41 | CONSTRAINT " + tablePkey + @" PRIMARY KEY (key_id));"; 42 | command.ExecuteNonQuery(); 43 | 44 | logger.Info("Created table " + tableName); 45 | } 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/StatusReportConstants.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: StatusReportConstants.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | /// 8 | /// The names of status report tables and sequences. 9 | /// 10 | internal static class StatusReportConstants 11 | { 12 | public const string Table = "status_report_v3"; 13 | public const string Seq = "status_id_seq"; 14 | public const string Pkey = "status_report_pkey"; 15 | public const string CommonKeyName = "status_id"; 16 | 17 | } 18 | 19 | /// 20 | /// The names of status report messages table and sequences. 21 | /// 22 | internal static class StatusReportMessagesConstants 23 | { 24 | public const string Table = "status_report_messages_v3"; 25 | public const string IdSeq = StatusReportConstants.Seq; 26 | public const string Pkey = "status_report_messages_pkey"; 27 | public const string CommonKeyName = StatusReportConstants.CommonKeyName; 28 | } 29 | 30 | /// 31 | /// The names of status report field of view table and sequences. 32 | /// 33 | internal static class StatusReportRangeBearingConstants 34 | { 35 | public const string Table = "status_report_range_bearing_v3"; 36 | public const string IdSeq = StatusReportConstants.Seq; 37 | public const string Pkey = "status_report_range_bearing_pkey"; 38 | public const string CommonKeyName = StatusReportConstants.CommonKeyName; 39 | } 40 | 41 | /// 42 | /// The names of status report region table and sequences. 43 | /// 44 | internal static class StatusReportRegionConstants 45 | { 46 | public const string Table = "status_report_region_v3"; 47 | public const string IdSeq = StatusReportConstants.Seq; 48 | public const string Pkey = "status_report_region_pkey"; 49 | public const string CommonKeyName = StatusReportConstants.CommonKeyName; 50 | } 51 | 52 | /// 53 | /// The names of High Level status report region table and sequences. 54 | /// 55 | internal static class HLStatusReportRegionConstants 56 | { 57 | public const string Table = "hl_status_report_region_v3"; 58 | public const string Pkey = "hl_status_report_region_pkey"; 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /SapientDatabase/DatabaseTables/TaskConstants.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: TaskConstants.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | // $NoKeywords$ 5 | namespace SapientDatabase.DatabaseTables 6 | { 7 | /// 8 | /// The names of tasking tables and sequences. 9 | /// 10 | public static class TaskConstants 11 | { 12 | public static class Objective 13 | { 14 | public const string Table = "hl_objective_v3"; 15 | public const string Pkey = "hl_objective_pkey"; 16 | } 17 | 18 | public static class SensorTask 19 | { 20 | public const string Table = "sensor_task_v3"; 21 | public const string Seq = "sensor_task_id_seq"; 22 | public const string Pkey = "sensor_task_pkey"; 23 | } 24 | 25 | public static class HLTask 26 | { 27 | public const string Table = "hl_task_v3"; 28 | public const string Seq = "hl_task_id_seq"; 29 | public const string Pkey = "hl_task_pkey"; 30 | } 31 | 32 | public static class SensorTaskAck 33 | { 34 | public const string Table = "sensor_taskack_v3"; 35 | public const string Seq = "sensor_taskack_v3_key_id_seq"; 36 | public const string Pkey = "sensor_taskack_pkey"; 37 | } 38 | 39 | public static class HLTaskAck 40 | { 41 | public const string Table = "hl_taskack_v3"; 42 | public const string Seq = "hl_taskack_v3_key_id_seq"; 43 | public const string Pkey = "hl_taskack_pkey"; 44 | } 45 | 46 | public static class GUITaskAck 47 | { 48 | public const string Table = "gui_taskack_v3"; 49 | public const string Seq = "gui_taskack_v3_key_id_seq"; 50 | public const string Pkey = "gui_taskack_pkey"; 51 | } 52 | 53 | public static class SensorTaskRegion 54 | { 55 | public const string Table = "sensor_task_region_v3"; 56 | public const string Seq = "sensor_task_region_v3_key_id_seq"; 57 | public const string Pkey = "sensor_task_region_v3_pkey"; 58 | public const string TaskKeyIdSeq = SensorTask.Seq; 59 | } 60 | 61 | public static class HLTaskRegion 62 | { 63 | public const string Table = "hl_task_region_v3"; 64 | public const string Seq = "hl_task_region_v3_key_id_seq"; 65 | public const string Pkey = "hl_task_region_v3_pkey"; 66 | } 67 | 68 | public static class HLTaskApproval 69 | { 70 | public const string Table = "hl_task_approval_v3"; 71 | public const string Pkey = "hl_task_approval_pkey"; 72 | public const string Accepted = "Accepted"; 73 | public const string Rejected = "Rejected"; 74 | } 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /SapientDatabase/Mono.Security.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDatabase/Mono.Security.dll -------------------------------------------------------------------------------- /SapientDatabase/Npgsql.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDatabase/Npgsql.dll -------------------------------------------------------------------------------- /SapientDatabase/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // Crown-Owned Copyright (c) 6 | // General Information about an assembly is controlled through the following 7 | // set of attributes. Change these attribute values to modify the information 8 | // associated with an assembly. 9 | [assembly: AssemblyTitle("SapientDatabase")] 10 | [assembly: AssemblyDescription("")] 11 | [assembly: AssemblyConfiguration("")] 12 | [assembly: AssemblyCompany("")] 13 | [assembly: AssemblyProduct("SapientDatabase")] 14 | [assembly: AssemblyCopyright("Crown-Owned Copyright © 2021")] 15 | [assembly: AssemblyTrademark("")] 16 | [assembly: AssemblyCulture("")] 17 | 18 | // Setting ComVisible to false makes the types in this assembly not visible 19 | // to COM components. If you need to access a type in this assembly from 20 | // COM, set the ComVisible attribute to true on that type. 21 | [assembly: ComVisible(false)] 22 | 23 | // The following GUID is for the ID of the typelib if this project is exposed to COM 24 | [assembly: Guid("f6812f94-a231-4b1c-bb27-2e10402f593b")] 25 | 26 | // Version information for an assembly consists of the following four values: 27 | // 28 | // Major Version 29 | // Minor Version 30 | // Build Number 31 | // Revision 32 | // 33 | // You can specify all the values or you can default the Build and Revision Numbers 34 | // by using the '*' as shown below: 35 | // [assembly: AssemblyVersion("1.0.*")] 36 | [assembly: AssemblyVersion("2.7.4.0")] 37 | [assembly: AssemblyFileVersion("2.7.4.0")] 38 | -------------------------------------------------------------------------------- /SapientDatabase/SapientDatabase.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | Debug 6 | AnyCPU 7 | {F6812F94-A231-4B1C-BB27-2E10402F593B} 8 | Library 9 | Properties 10 | SapientDatabase 11 | SapientDatabase 12 | v4.8 13 | 512 14 | 15 | 16 | 17 | true 18 | full 19 | false 20 | bin\Debug\ 21 | DEBUG;TRACE 22 | prompt 23 | 4 24 | 25 | 26 | pdbonly 27 | true 28 | bin\Release\ 29 | TRACE 30 | prompt 31 | 4 32 | 33 | 34 | 35 | .\log4net.dll 36 | 37 | 38 | .\Mono.Security.dll 39 | 40 | 41 | .\Npgsql.dll 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | {9d6bd18a-2abb-4ef8-9e54-cc11a9b78d6e} 84 | SapientServices 85 | 86 | 87 | 88 | 95 | -------------------------------------------------------------------------------- /SapientDatabase/SapientDatabase.csproj.user: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 1 5 | 6 | -------------------------------------------------------------------------------- /SapientDatabase/log4net.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientDatabase/log4net.dll -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 11.00 3 | # Visual Studio 2010 4 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SapientHldmmSimulatorV3", "SapientHldmmSimulatorV3\SapientHldmmSimulatorV3.csproj", "{D7AB8356-90FF-4AB4-88BC-D980B65BC671}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|Any CPU = Debug|Any CPU 9 | Debug|Mixed Platforms = Debug|Mixed Platforms 10 | Debug|x86 = Debug|x86 11 | Release|Any CPU = Release|Any CPU 12 | Release|Mixed Platforms = Release|Mixed Platforms 13 | Release|x86 = Release|x86 14 | EndGlobalSection 15 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 16 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|Any CPU.ActiveCfg = Debug|x86 17 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|Mixed Platforms.ActiveCfg = Debug|x86 18 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|Mixed Platforms.Build.0 = Debug|x86 19 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|x86.ActiveCfg = Debug|x86 20 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Debug|x86.Build.0 = Debug|x86 21 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|Any CPU.ActiveCfg = Release|x86 22 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|Mixed Platforms.ActiveCfg = Release|x86 23 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|Mixed Platforms.Build.0 = Release|x86 24 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|x86.ActiveCfg = Release|x86 25 | {D7AB8356-90FF-4AB4-88BC-D980B65BC671}.Release|x86.Build.0 = Release|x86 26 | EndGlobalSection 27 | GlobalSection(SolutionProperties) = preSolution 28 | HideSolutionNode = FALSE 29 | EndGlobalSection 30 | EndGlobal 31 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/AlertGenerator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: AlertGenerator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | namespace SapientHldmmSimulator 6 | { 7 | using System; 8 | using System.Threading; 9 | using log4net; 10 | using SapientServices.Communication; 11 | using SapientServices.Data; 12 | 13 | /// 14 | /// Generate Alert messages 15 | /// 16 | public class AlertGenerator : XmlGenerators 17 | { 18 | /// 19 | /// log4net logger 20 | /// 21 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 22 | 23 | #region Properties 24 | 25 | /// 26 | /// Gets the Alert ID field to use in alert message 27 | /// 28 | public int AlertID { get; private set; } 29 | 30 | /// 31 | /// Gets or sets an Image URL to provide with the detection message 32 | /// 33 | public static string ImageURL { get; set; } 34 | 35 | #endregion 36 | 37 | /// 38 | /// Send an Alert message 39 | /// 40 | /// connection to use to send message 41 | public void GenerateAlert(object comms_connection) 42 | { 43 | IConnection messenger = (IConnection)comms_connection; 44 | do 45 | { 46 | Alert alert = GenerateAlert(this.AlertID); 47 | string xmlstring = ConfigXMLParser.Serialize(alert); 48 | bool retval = MessageSender.Send(messenger, xmlstring); 49 | 50 | if (retval) 51 | { 52 | this.MessageCount++; 53 | 54 | Log.InfoFormat("Send Alert: {0}", this.AlertID); 55 | } 56 | else 57 | { 58 | Log.ErrorFormat("Send Alert Failed: {0}", this.AlertID); 59 | } 60 | 61 | this.AlertID++; 62 | 63 | if (this.LoopMessages) 64 | { 65 | Thread.Sleep(this.LoopTime); 66 | } 67 | } while (this.LoopMessages); 68 | } 69 | 70 | /// 71 | /// Generate example alert 72 | /// 73 | /// alert ID field value 74 | /// Populated Alert object 75 | public static Alert GenerateAlert(int alertId) 76 | { 77 | double sensorX = Properties.Settings.Default.startLongitude; 78 | double sensorY = Properties.Settings.Default.startLatitude; 79 | 80 | if (sensorY > 90) 81 | { 82 | sensorY += 100; 83 | } 84 | else 85 | { 86 | sensorY = 0.001; 87 | } 88 | 89 | Alert alert = new Alert 90 | { 91 | alertID = alertId, 92 | alertType = "Information", 93 | sourceID = ASMId, 94 | status = "Active", 95 | description = "Text description of alert", 96 | timestamp = DateTime.UtcNow, 97 | location = new location { X = sensorX, Y = sensorY }, 98 | regionID = 1, 99 | debugText = "debug" 100 | }; 101 | 102 | alert.priority = "High"; 103 | alert.ranking = 0.9; 104 | alert.rankingSpecified = true; 105 | 106 | alert.associatedDetection = new[] 107 | { 108 | new AlertAssociatedDetection 109 | { 110 | sourceID = 0, 111 | objectID = 123, 112 | timestampSpecified = true, 113 | timestamp = alert.timestamp, 114 | location = new location { X = sensorX + 0.001, Y = sensorY }, 115 | description = "location description" 116 | } 117 | }; 118 | 119 | if (!string.IsNullOrEmpty(ImageURL)) 120 | { 121 | alert.associatedFile = new[] 122 | { 123 | new AlertAssociatedFile 124 | { 125 | type = "image", 126 | url = ImageURL, 127 | }, 128 | }; 129 | } 130 | 131 | return alert; 132 | } 133 | } 134 | } 135 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/CSVFileParser.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: CSVFileParser.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | namespace ScriptReader 6 | { 7 | using System; 8 | using System.IO; 9 | using log4net; 10 | 11 | /// 12 | /// Read a CSV File in and parse it 13 | /// 14 | public class CSVFileParser 15 | { 16 | /// 17 | /// Log4net logger 18 | /// 19 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 20 | 21 | /// 22 | /// CSV filename to read 23 | /// 24 | private string fileName; 25 | 26 | /// 27 | /// file stream reader 28 | /// 29 | private StreamReader sr = null; 30 | 31 | /// 32 | /// last line of text read from CSV file 33 | /// 34 | private string lineOfText = null; 35 | 36 | /// 37 | /// Initializes a new instance of the CSVFileParser class. 38 | /// 39 | /// script filename 40 | public CSVFileParser(string filename) 41 | { 42 | this.fileName = filename; 43 | } 44 | 45 | /// 46 | /// Open CSV file 47 | /// 48 | public void Open() 49 | { 50 | try 51 | { 52 | Log.InfoFormat("Opening CSV File:{0}", this.fileName); 53 | this.sr = new StreamReader(new FileStream(this.fileName, FileMode.Open, FileAccess.Read)); 54 | } 55 | catch (FileNotFoundException) 56 | { 57 | Log.ErrorFormat("File Not Found: {0}", this.fileName); 58 | } 59 | catch (Exception ex) 60 | { 61 | Log.Error("Error Reading Script File:", ex); 62 | } 63 | } 64 | 65 | /// 66 | /// Close CSV file 67 | /// 68 | public void Close() 69 | { 70 | if (this.sr != null) 71 | { 72 | this.sr.Dispose(); 73 | } 74 | } 75 | 76 | /// 77 | /// Parse CSV file 78 | /// 79 | /// flag whether text successfully read 80 | public bool Parse() 81 | { 82 | bool textRead = false; 83 | try 84 | { 85 | if (this.sr.Peek() >= 0) 86 | { 87 | this.lineOfText = this.sr.ReadLine(); 88 | textRead = true; 89 | } 90 | } 91 | catch (Exception ex) 92 | { 93 | Log.Error("Error Parsing Script File:", ex); 94 | } 95 | 96 | return textRead; 97 | } 98 | 99 | /// 100 | /// Split CSV file line into a list of strings 101 | /// 102 | /// list of strings 103 | public void ParseLineString(out string[] result) 104 | { 105 | result = null; 106 | char[] charSeparators = new char[] { ',' }; 107 | if (this.lineOfText != null) 108 | { 109 | result = this.lineOfText.Split(charSeparators, StringSplitOptions.None); 110 | } 111 | } 112 | 113 | /// 114 | /// Show list of strings from a line of the CSV file 115 | /// 116 | /// 117 | ////public void Show(string[] sArray) 118 | ////{ 119 | //// for (int i = 0; i < sArray.Length; i++) 120 | //// { 121 | //// Console.Write(": " + sArray[i]); 122 | //// } 123 | //// Console.Write("\n"); 124 | ////} 125 | } 126 | } 127 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/HeartbeatGenerator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: HeartbeatGenerator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | namespace SapientHldmmSimulator 6 | { 7 | using System; 8 | using System.Threading; 9 | using log4net; 10 | using SapientServices.Communication; 11 | using SapientServices.Data; 12 | 13 | /// 14 | /// Generate SAPIENT heartbeat (status report messages) 15 | /// 16 | public class HeartbeatGenerator 17 | { 18 | public int ASMId { get; set; } 19 | 20 | public int HeartbeatTime { get; set; } 21 | 22 | public bool LoopHeatbeat { get; set; } 23 | 24 | public int Azimuth { get; set; } 25 | 26 | private int heartbeat_id = 1; 27 | 28 | /// 29 | /// log4net logger 30 | /// 31 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 32 | 33 | /// 34 | /// Constructor 35 | /// 36 | public HeartbeatGenerator() 37 | { 38 | 39 | } 40 | 41 | /// 42 | /// sends out health messages, will loop until manually told not too 43 | /// 44 | /// IConnection messenger object used to send messages over 45 | public void GenerateHLStatus(object comms_connection) 46 | { 47 | do 48 | { 49 | const double sensorX = -2.313; 50 | const double sensorY = 52.101; 51 | const double obsX = 0.0001; 52 | const double obsY = 0.0001; 53 | const double fieldOfViewX = 0.001; 54 | 55 | var messenger = (IConnection)comms_connection; 56 | 57 | locationList sensorStatusRegion1 = new locationList 58 | { 59 | location = new[] 60 | { 61 | new location {X = sensorX + fieldOfViewX - obsX, Y = sensorY}, 62 | new location {X = sensorX + fieldOfViewX, Y = sensorY + obsY}, 63 | new location {X = sensorX + fieldOfViewX, Y = sensorY}, 64 | new location {X = sensorX + fieldOfViewX - obsX, Y = sensorY} 65 | } 66 | }; 67 | 68 | locationList sensorStatusRegion2 = new locationList 69 | { 70 | location = new[] 71 | { 72 | new location {X = sensorX + fieldOfViewX - obsX, Y = sensorY}, 73 | new location {X = sensorX + fieldOfViewX, Y = sensorY - obsY}, 74 | new location {X = sensorX + fieldOfViewX, Y = sensorY}, 75 | new location {X = sensorX + fieldOfViewX - obsX, Y = sensorY} 76 | } 77 | }; 78 | 79 | StatusReportStatusRegion statusRegion1 = new StatusReportStatusRegion 80 | { 81 | type = "Area Of Interest", 82 | regionID = 1, 83 | regionName = "region 1", 84 | regionStatus = "Unchanged", 85 | description = "Description:a region in area 1", 86 | locationList = sensorStatusRegion1 87 | }; 88 | 89 | StatusReportStatusRegion statusRegion2 = new StatusReportStatusRegion 90 | { 91 | type = "Area Of Interest", 92 | regionID = 2, 93 | regionName = "region 2", 94 | regionStatus = "Unchanged", 95 | description = "Description:a region in area 2", 96 | locationList = sensorStatusRegion2 97 | }; 98 | 99 | StatusReport status = new StatusReport 100 | { 101 | timestamp = DateTime.UtcNow, 102 | sourceID = ASMId, 103 | reportID = heartbeat_id++, 104 | system = "OK", 105 | info = "Unchanged", 106 | activeTaskID = 0, 107 | statusRegion = new StatusReportStatusRegion[] { statusRegion1, statusRegion2 } 108 | }; 109 | 110 | if (heartbeat_id > 2) 111 | { 112 | status.sensorLocation = null; 113 | } 114 | 115 | var xmlstring = ConfigXMLParser.Serialize(status); 116 | var record_bytes = System.Text.Encoding.UTF8.GetBytes(xmlstring); 117 | if (messenger.SendMessage(record_bytes, record_bytes.Length)) 118 | { 119 | Log.InfoFormat("Sent StatusReport: {0}", status.reportID); 120 | } 121 | else 122 | { 123 | Log.InfoFormat("Sent StatusReport Failed: {0}", status.reportID); 124 | } 125 | 126 | if (LoopHeatbeat) Thread.Sleep(HeartbeatTime); 127 | } while (LoopHeatbeat); 128 | } 129 | } 130 | } 131 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/MessageSender.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: MessageSender.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | using System; 6 | using System.Threading; 7 | using SapientServices.Communication; 8 | 9 | namespace SapientHldmmSimulator 10 | { 11 | /// 12 | /// Send Message 13 | /// 14 | public class MessageSender 15 | { 16 | public static bool FragmentData { get; set; } 17 | 18 | public static int PacketDelay { get; set; } 19 | 20 | public static bool Send(IConnection messenger, string message) 21 | { 22 | byte[] record_bytes = System.Text.Encoding.UTF8.GetBytes(message); 23 | 24 | bool retval = false; 25 | 26 | // fragment packet to test handling of partial messages 27 | if (FragmentData && (record_bytes.Length > 1500)) 28 | { 29 | retval = messenger.SendMessage(record_bytes, 1500); 30 | 31 | if (retval) 32 | { 33 | Thread.Sleep(PacketDelay); 34 | byte[] remainingBytes = new byte[record_bytes.Length - 1500]; 35 | Array.Copy(record_bytes, 1500, remainingBytes, 0, record_bytes.Length - 1500); 36 | retval = messenger.SendMessage(remainingBytes, remainingBytes.Length); 37 | } 38 | } 39 | else 40 | { 41 | retval = messenger.SendMessage(record_bytes, record_bytes.Length); 42 | } 43 | 44 | return retval; 45 | } 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/ObjectiveGenerator.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: ObjectiveGenerator.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | namespace SapientHldmmSimulator 6 | { 7 | using System; 8 | using System.Threading; 9 | using log4net; 10 | using SapientServices.Communication; 11 | using SapientServices.Data; 12 | 13 | /// 14 | /// Generate Objective Messages 15 | /// 16 | public class ObjectiveGenerator : XmlGenerators 17 | { 18 | #region Properties 19 | 20 | public bool ChangeObjectiveID { get; set; } 21 | 22 | #endregion 23 | 24 | /// 25 | /// log4net logger 26 | /// 27 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 28 | 29 | #region Data Members 30 | 31 | private double maxLoopLatitude = Properties.Settings.Default.maxLatitude; 32 | 33 | private double longitude = start_longitude; 34 | private double latitude = start_latitude; 35 | 36 | /// 37 | /// message identifier 38 | /// 39 | private int messageId = 1; 40 | 41 | #endregion 42 | 43 | /// 44 | /// send out objective messages, will loop until latitude is greater than 52.69 45 | /// there is a wait of 100ms between each send 46 | /// 47 | /// IConnection messenger object used to send messages over 48 | public void GenerateObjectives(object comms_connection, int sensorID) 49 | { 50 | var messenger = (IConnection)comms_connection; 51 | 52 | var objective = new Objective(); 53 | 54 | objective.sourceID = 0; 55 | objective.sensorID = sensorID; 56 | objective.location = new location { X = longitude, Y = latitude }; 57 | 58 | do 59 | { 60 | objective.objectiveID = this.messageId; 61 | objective.objectID = this.messageId; 62 | objective.objectIDSpecified = true; 63 | objective.regionID = 1; 64 | objective.status = "Proposed"; 65 | objective.regionIDSpecified = true; 66 | objective.timestamp = DateTime.UtcNow; 67 | objective.description = string.Format("Objective for sensor {0} go to location {1} {2}", objective.sensorID, longitude, latitude); 68 | objective.information = string.Format("Objective {0} Information", this.messageId); 69 | { 70 | objective.location = new location { X = longitude, Y = latitude }; 71 | 72 | if (isUTM) 73 | { 74 | longitude += 1.0; 75 | latitude += 1.0; 76 | } 77 | else 78 | { 79 | longitude += 0.00001; 80 | latitude += 0.00001; 81 | } 82 | } 83 | 84 | if (latitude > maxLoopLatitude) 85 | { 86 | latitude = start_latitude; 87 | longitude = start_longitude; 88 | messageId++; 89 | } 90 | else if (ChangeObjectiveID) 91 | { 92 | messageId++; 93 | } 94 | 95 | var xmlstring = ConfigXMLParser.Serialize(objective); 96 | 97 | bool retval = MessageSender.Send(messenger, xmlstring); 98 | 99 | if (retval) 100 | { 101 | MessageCount++; 102 | } 103 | else 104 | { 105 | Log.ErrorFormat("Send Objective Failed {0}", MessageCount); 106 | } 107 | 108 | if (LoopMessages) 109 | { 110 | Thread.Sleep(LoopTime); 111 | } 112 | 113 | } while (LoopMessages); 114 | } 115 | } 116 | } 117 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/PTZForm.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: PTZForm.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | using System; 6 | using System.Windows.Forms; 7 | 8 | namespace SapientHldmmSimulator 9 | { 10 | /// 11 | /// form for entry of Pan/Tilt/Zoom or Azimuth/Range/Zoom command parameters 12 | /// 13 | public partial class PTZForm : Form 14 | { 15 | public static double Az; 16 | public static double Elevation; 17 | public static double Zoom; 18 | public static bool PTZ; 19 | 20 | private static readonly Random random = new Random(); 21 | 22 | /// 23 | /// constructor for PTZ Form 24 | /// 25 | public PTZForm(bool showPTZcontrols) 26 | { 27 | InitializeComponent(); 28 | Azimuth_txt.Text = Az.ToString("F2"); 29 | Elevation_txt.Text = Elevation.ToString("F2"); 30 | Zoom_txt.Text = Zoom.ToString("F2"); 31 | SendAsPTZ.Checked = PTZ; 32 | if (showPTZcontrols == false) 33 | { 34 | Azimuth_txt.Hide(); 35 | Elevation_txt.Hide(); 36 | Zoom_txt.Hide(); 37 | SendAsPTZ.Hide(); 38 | button2.Hide(); 39 | label1.Hide(); 40 | label2.Hide(); 41 | label4.Hide(); 42 | command.Items.RemoveAt(0); // remove lookAt 43 | } 44 | else 45 | { 46 | command.Items.Clear(); 47 | command.Items.Add("lookAt"); 48 | command.Items.Add("region"); 49 | } 50 | } 51 | 52 | /// 53 | /// method to randomize azimuth and range 54 | /// 55 | public static void Randomize() 56 | { 57 | Az = (random.NextDouble() * 360.0); 58 | Zoom = (6.0 + random.NextDouble() * (100.0 - 6.0)); 59 | } 60 | 61 | /// 62 | /// click event on Randomize button 63 | /// 64 | /// sender button 65 | /// click event 66 | private void RandomizeClick(object sender, EventArgs e) 67 | { 68 | Randomize(); 69 | Azimuth_txt.Text = Az.ToString("F2"); 70 | Elevation_txt.Text = Elevation.ToString("F2"); 71 | } 72 | 73 | /// 74 | /// click event on OK button 75 | /// 76 | /// OK button 77 | /// click event 78 | private void OnOk(object sender, EventArgs e) 79 | { 80 | Az = double.Parse(Azimuth_txt.Text); 81 | Elevation = double.Parse(Elevation_txt.Text); 82 | Zoom = double.Parse(Zoom_txt.Text); 83 | PTZ = SendAsPTZ.Checked; 84 | } 85 | } 86 | } 87 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/Program.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: Program.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | using System; 6 | using System.Windows.Forms; 7 | using log4net; 8 | 9 | [assembly: log4net.Config.XmlConfigurator(Watch = true)] 10 | 11 | namespace SapientHldmmSimulator 12 | { 13 | class Program 14 | { 15 | /// 16 | /// log4net logger 17 | /// 18 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 19 | 20 | [STAThread] 21 | static void Main() 22 | { 23 | const int ExeName = 0; 24 | const int ExeVersion = 2; 25 | 26 | // Output the assembly name and version number for configuration purposes 27 | string[] assemblyDetails = System.Reflection.Assembly.GetExecutingAssembly().FullName.Split(',', '='); 28 | 29 | Log.Info(Environment.NewLine); 30 | Log.Info(assemblyDetails[ExeName] + " - Version " + assemblyDetails[ExeVersion]); 31 | 32 | Application.EnableVisualStyles(); 33 | Application.SetCompatibleTextRenderingDefault(false); 34 | Application.Run(new TaskForm()); 35 | } 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // Crown-Owned Copyright (c) 6 | // General Information about an assembly is controlled through the following 7 | // set of attributes. Change these attribute values to modify the information 8 | // associated with an assembly. 9 | [assembly: AssemblyTitle("Sapient HLDMM Simulator")] 10 | [assembly: AssemblyDescription("")] 11 | [assembly: AssemblyConfiguration("")] 12 | [assembly: AssemblyCompany("QinetiQ")] 13 | [assembly: AssemblyProduct("Sapient")] 14 | [assembly: AssemblyCopyright("© Crown-Owned Copyright 2021")] 15 | [assembly: AssemblyTrademark("")] 16 | [assembly: AssemblyCulture("")] 17 | 18 | // Setting ComVisible to false makes the types in this assembly not visible 19 | // to COM components. If you need to access a type in this assembly from 20 | // COM, set the ComVisible attribute to true on that type. 21 | [assembly: ComVisible(false)] 22 | 23 | // The following GUID is for the ID of the typelib if this project is exposed to COM 24 | [assembly: Guid("3f6d53e1-e6bd-42eb-b0bc-3a91a73c5ebd")] 25 | 26 | // Version information for an assembly consists of the following four values: 27 | // 28 | // Major Version 29 | // Minor Version 30 | // Build Number 31 | // Revision 32 | // 33 | // You can specify all the values or you can default the Build and Revision Numbers 34 | // by using the '*' as shown below: 35 | // [assembly: AssemblyVersion("1.0.*")] 36 | [assembly: AssemblyVersion("2.7.4.0")] 37 | [assembly: AssemblyFileVersion("2.7.4.0")] 38 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/Properties/Settings.settings: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 127.0.0.1 7 | 8 | 9 | 12002 10 | 11 | 12 | ..\Log\Log-HLDMM 13 | 14 | 15 | True 16 | 17 | 18 | HLDMMsim_sendlog 19 | 20 | 21 | 3600 22 | 23 | 24 | 1000 25 | 26 | 27 | 52.101 28 | 29 | 30 | -2.315 31 | 32 | 33 | 52.103 34 | 35 | 36 | True 37 | 38 | 39 | C:\StarTeam\00010855-Sapient\root\06_Test\Test ConfigurationV3\XML\ExpectedSystemResponseHLDMM.txt 40 | 41 | 42 | C:\StarTeam\00010855-Sapient\root\06_Test\Test ConfigurationV3\XML 43 | 44 | 45 | False 46 | 47 | 48 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/SapientServices.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientHldmmSimulator/SapientHldmmSimulatorV3/SapientServices.dll -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/TaskACKParser.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: TaskACKParser.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | namespace SapientHldmmSimulator 6 | { 7 | using log4net; 8 | using SapientServices.Data; 9 | using System; 10 | 11 | /// 12 | /// Parser for Task Acknowledgement messages 13 | /// 14 | public class TaskACKParser 15 | { 16 | /// 17 | /// log4net logger 18 | /// 19 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 20 | 21 | public static void ParseTaskACK(string message, TaskForm form) 22 | { 23 | int messageCount = 0; 24 | int offset = 0; 25 | const int closeTagLength = 16; 26 | 27 | do 28 | { 29 | int index = message.IndexOf("", offset); 30 | 31 | if (index > 0) 32 | { 33 | Log.InfoFormat("SensorTaskACK at:{0}", index); 34 | 35 | if (index + closeTagLength > message.Length) 36 | { 37 | Log.ErrorFormat("ParseTaskACK Error offset {0} length {1}", index + closeTagLength, message.Length); 38 | 39 | // error so exit loop 40 | offset = message.Length; 41 | } 42 | else 43 | { 44 | string singleMessage = message.Substring(offset, index - offset + closeTagLength); 45 | { 46 | var id = (SensorTaskACK)ConfigXMLParser.Deserialize(typeof(SensorTaskACK), singleMessage); 47 | messageCount++; 48 | 49 | // Added to pass SAPIENT_Test_Harness_Build_Note-O 50 | form.UpdateOutputWindow("SensorTaskACK: " + message + "\n"); 51 | form.UpdateOutputWindow("Latency(ms): " + (DateTime.UtcNow - id.timestamp).TotalMilliseconds); 52 | Log.InfoFormat("{0}:SensorTaskACK Task ID: {1}:{2}:{3}", messageCount, id.taskID, id.status, id.reason); 53 | } 54 | 55 | // iterate on to next message 56 | offset += (index + closeTagLength); 57 | 58 | while ((offset < message.Length) && ((message[offset] == 0) || (message[offset] == ' ') || (message[offset] == '\r') || (message[offset] == '\n'))) 59 | { 60 | offset++; 61 | } 62 | } 63 | } 64 | else 65 | { 66 | // not found so exit loop 67 | offset = message.Length; 68 | } 69 | } while (offset < message.Length); 70 | } 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/XmlGenerators.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: XmlGenerators.cs$ 3 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 4 | 5 | namespace SapientHldmmSimulator 6 | { 7 | using log4net; 8 | 9 | /// 10 | /// Base class for XML generation 11 | /// 12 | public class XmlGenerators 13 | { 14 | #region data members 15 | 16 | /// 17 | /// log4net logger 18 | /// 19 | private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); 20 | 21 | protected static double start_longitude = Properties.Settings.Default.startLongitude; 22 | protected static double start_latitude = Properties.Settings.Default.startLatitude; 23 | protected static bool isUTM = ((start_longitude > 180) || (start_longitude < -180) || (start_latitude > 90) || (start_latitude < -90)); 24 | 25 | #endregion 26 | 27 | #region Properties 28 | 29 | public static int ASMId { get; set; } 30 | 31 | public long MessageCount { get; protected set; } 32 | 33 | public bool LoopMessages { get; set; } 34 | 35 | public int LoopTime { get; set; } 36 | 37 | #endregion 38 | 39 | #region public methods 40 | 41 | #endregion 42 | 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/app.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 |
6 | 7 |
8 | 9 | 10 | 11 | 12 | 127.0.0.1 13 | 14 | 15 | 12002 16 | 17 | 18 | ..\Log\Log-HLDMM 19 | 20 | 21 | True 22 | 23 | 24 | HLDMMsim_sendlog 25 | 26 | 27 | 3600 28 | 29 | 30 | 1000 31 | 32 | 33 | 52.101 34 | 35 | 36 | -2.315 37 | 38 | 39 | 52.103 40 | 41 | 42 | True 43 | 44 | 45 | C:\StarTeam\00010855-Sapient\root\06_Test\Test ConfigurationV3\XML\ExpectedSystemResponseHLDMM.txt 46 | 47 | 48 | C:\StarTeam\00010855-Sapient\root\06_Test\Test ConfigurationV3\XML 49 | 50 | 51 | False 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | -------------------------------------------------------------------------------- /SapientHldmmSimulator/SapientHldmmSimulatorV3/log4net.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientHldmmSimulator/SapientHldmmSimulatorV3/log4net.dll -------------------------------------------------------------------------------- /SapientServices/Data/AlertResponse.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | // 12 | // This source code was auto-generated by xsd, Version=4.0.30319.1. 13 | // 14 | namespace SapientServices.Data 15 | { 16 | /// 17 | [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")] 18 | [System.SerializableAttribute()] 19 | [System.Diagnostics.DebuggerStepThroughAttribute()] 20 | [System.ComponentModel.DesignerCategoryAttribute("code")] 21 | [System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true)] 22 | [System.Xml.Serialization.XmlRootAttribute(Namespace = "", IsNullable = false)] 23 | public partial class AlertResponse 24 | { 25 | private System.DateTime timestampField; 26 | 27 | private int sourceIDField; 28 | 29 | private int alertIDField; 30 | 31 | private string statusField; 32 | 33 | private string reasonField; 34 | 35 | /// 36 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 37 | public System.DateTime timestamp 38 | { 39 | get 40 | { 41 | return this.timestampField; 42 | } 43 | set 44 | { 45 | this.timestampField = value; 46 | } 47 | } 48 | 49 | /// 50 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 51 | public int sourceID 52 | { 53 | get 54 | { 55 | return this.sourceIDField; 56 | } 57 | set 58 | { 59 | this.sourceIDField = value; 60 | } 61 | } 62 | 63 | /// 64 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 65 | public int alertID 66 | { 67 | get 68 | { 69 | return this.alertIDField; 70 | } 71 | set 72 | { 73 | this.alertIDField = value; 74 | } 75 | } 76 | 77 | /// 78 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 79 | public string status 80 | { 81 | get 82 | { 83 | return this.statusField; 84 | } 85 | set 86 | { 87 | this.statusField = value; 88 | } 89 | } 90 | 91 | /// 92 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 93 | public string reason 94 | { 95 | get 96 | { 97 | return this.reasonField; 98 | } 99 | set 100 | { 101 | this.reasonField = value; 102 | } 103 | } 104 | } 105 | } 106 | -------------------------------------------------------------------------------- /SapientServices/Data/Approval.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | // 12 | // This source code was auto-generated by xsd, Version=4.0.30319.1. 13 | // 14 | namespace SapientServices.Data 15 | { 16 | /// 17 | [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")] 18 | [System.SerializableAttribute()] 19 | [System.Diagnostics.DebuggerStepThroughAttribute()] 20 | [System.ComponentModel.DesignerCategoryAttribute("code")] 21 | [System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)] 22 | [System.Xml.Serialization.XmlRootAttribute(Namespace="", IsNullable=false)] 23 | public partial class Approval { 24 | 25 | private System.DateTime timestampField; 26 | 27 | private int sensorIDField; 28 | 29 | private int taskIDField; 30 | 31 | private int objectiveIDField; 32 | 33 | private string statusField; 34 | 35 | private string informationField; 36 | 37 | /// 38 | [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)] 39 | public System.DateTime timestamp { 40 | get { 41 | return this.timestampField; 42 | } 43 | set { 44 | this.timestampField = value; 45 | } 46 | } 47 | 48 | /// 49 | [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)] 50 | public int sensorID { 51 | get { 52 | return this.sensorIDField; 53 | } 54 | set { 55 | this.sensorIDField = value; 56 | } 57 | } 58 | 59 | /// 60 | [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)] 61 | public int taskID { 62 | get { 63 | return this.taskIDField; 64 | } 65 | set { 66 | this.taskIDField = value; 67 | } 68 | } 69 | 70 | /// 71 | [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)] 72 | public int objectiveID { 73 | get { 74 | return this.objectiveIDField; 75 | } 76 | set { 77 | this.objectiveIDField = value; 78 | } 79 | } 80 | 81 | /// 82 | [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)] 83 | public string status { 84 | get { 85 | return this.statusField; 86 | } 87 | set { 88 | this.statusField = value; 89 | } 90 | } 91 | 92 | /// 93 | [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)] 94 | public string information { 95 | get { 96 | return this.informationField; 97 | } 98 | set { 99 | this.informationField = value; 100 | } 101 | } 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /SapientServices/Data/Error.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | // 12 | // This source code was auto-generated by xsd, Version=4.0.30319.1. 13 | // 14 | namespace SapientServices.Data 15 | { 16 | /// 17 | [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")] 18 | [System.SerializableAttribute()] 19 | [System.Diagnostics.DebuggerStepThroughAttribute()] 20 | [System.ComponentModel.DesignerCategoryAttribute("code")] 21 | [System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true)] 22 | [System.Xml.Serialization.XmlRootAttribute(Namespace = "", IsNullable = false)] 23 | public partial class Error 24 | { 25 | private System.DateTime timestampField; 26 | 27 | private string packetField; 28 | 29 | private string errorMessageField; 30 | 31 | /// 32 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 33 | public System.DateTime timestamp 34 | { 35 | get 36 | { 37 | return this.timestampField; 38 | } 39 | set 40 | { 41 | this.timestampField = value; 42 | } 43 | } 44 | 45 | /// 46 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 47 | public string packet 48 | { 49 | get 50 | { 51 | return this.packetField; 52 | } 53 | set 54 | { 55 | this.packetField = value; 56 | } 57 | } 58 | 59 | /// 60 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 61 | public string errorMessage 62 | { 63 | get 64 | { 65 | return this.errorMessageField; 66 | } 67 | set 68 | { 69 | this.errorMessageField = value; 70 | } 71 | } 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /SapientServices/Data/SensorRegistrationACK.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | // 12 | // This source code was auto-generated by xsd, Version=4.0.30319.1. 13 | // 14 | namespace SapientServices.Data 15 | { 16 | /// 17 | [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")] 18 | [System.SerializableAttribute()] 19 | [System.Diagnostics.DebuggerStepThroughAttribute()] 20 | [System.ComponentModel.DesignerCategoryAttribute("code")] 21 | [System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true)] 22 | [System.Xml.Serialization.XmlRootAttribute(Namespace = "", IsNullable = false)] 23 | public partial class SensorRegistrationACK 24 | { 25 | private int sensorIDField; 26 | 27 | /// 28 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 29 | public int sensorID 30 | { 31 | get 32 | { 33 | return this.sensorIDField; 34 | } 35 | set 36 | { 37 | this.sensorIDField = value; 38 | } 39 | } 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /SapientServices/Data/SensorTaskACK.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | // 12 | // This source code was auto-generated by xsd, Version=4.0.30319.1. 13 | // 14 | namespace SapientServices.Data 15 | { 16 | /// 17 | [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")] 18 | [System.SerializableAttribute()] 19 | [System.Diagnostics.DebuggerStepThroughAttribute()] 20 | [System.ComponentModel.DesignerCategoryAttribute("code")] 21 | [System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true)] 22 | [System.Xml.Serialization.XmlRootAttribute(Namespace = "", IsNullable = false)] 23 | public partial class SensorTaskACK 24 | { 25 | private System.DateTime timestampField; 26 | 27 | private int sensorIDField; 28 | 29 | private int taskIDField; 30 | 31 | private string statusField; 32 | 33 | private string reasonField; 34 | 35 | private SensorTaskACKAssociatedFile[] associatedFileField; 36 | 37 | /// 38 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 39 | public System.DateTime timestamp 40 | { 41 | get 42 | { 43 | return this.timestampField; 44 | } 45 | set 46 | { 47 | this.timestampField = value; 48 | } 49 | } 50 | 51 | /// 52 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 53 | public int sensorID 54 | { 55 | get 56 | { 57 | return this.sensorIDField; 58 | } 59 | set 60 | { 61 | this.sensorIDField = value; 62 | } 63 | } 64 | 65 | /// 66 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 67 | public int taskID 68 | { 69 | get 70 | { 71 | return this.taskIDField; 72 | } 73 | set 74 | { 75 | this.taskIDField = value; 76 | } 77 | } 78 | 79 | /// 80 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 81 | public string status 82 | { 83 | get 84 | { 85 | return this.statusField; 86 | } 87 | set 88 | { 89 | this.statusField = value; 90 | } 91 | } 92 | 93 | /// 94 | [System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 95 | public string reason 96 | { 97 | get 98 | { 99 | return this.reasonField; 100 | } 101 | set 102 | { 103 | this.reasonField = value; 104 | } 105 | } 106 | 107 | /// 108 | [System.Xml.Serialization.XmlElementAttribute("associatedFile", Form = System.Xml.Schema.XmlSchemaForm.Unqualified)] 109 | public SensorTaskACKAssociatedFile[] associatedFile 110 | { 111 | get 112 | { 113 | return this.associatedFileField; 114 | } 115 | set 116 | { 117 | this.associatedFileField = value; 118 | } 119 | } 120 | } 121 | 122 | /// 123 | [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")] 124 | [System.SerializableAttribute()] 125 | [System.Diagnostics.DebuggerStepThroughAttribute()] 126 | [System.ComponentModel.DesignerCategoryAttribute("code")] 127 | [System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true)] 128 | public partial class SensorTaskACKAssociatedFile 129 | { 130 | 131 | private string typeField; 132 | 133 | private string urlField; 134 | 135 | /// 136 | [System.Xml.Serialization.XmlAttributeAttribute()] 137 | public string type 138 | { 139 | get 140 | { 141 | return this.typeField; 142 | } 143 | set 144 | { 145 | this.typeField = value; 146 | } 147 | } 148 | 149 | /// 150 | [System.Xml.Serialization.XmlAttributeAttribute()] 151 | public string url 152 | { 153 | get 154 | { 155 | return this.urlField; 156 | } 157 | set 158 | { 159 | this.urlField = value; 160 | } 161 | } 162 | } 163 | } 164 | -------------------------------------------------------------------------------- /SapientServices/Data/Validation/AlertValidation.cs: -------------------------------------------------------------------------------- 1 | namespace SapientServices.Data.Validation 2 | { 3 | public class AlertValidation 4 | { 5 | /// 6 | /// validate a Deserialized Alert Message 7 | /// 8 | /// the Alert Message 9 | /// empty string or validation error message 10 | public static string ValidateAlert(Alert alert) 11 | { 12 | string retval = string.Empty; 13 | if (string.IsNullOrEmpty(alert.status) == false) 14 | { 15 | if (!ValidAlertStatus(alert.status)) 16 | { 17 | retval = "Alert Invalid status"; 18 | } 19 | } 20 | 21 | if (alert.location != null && alert.rangeBearing != null) 22 | { 23 | retval = "Alert Invalid has both location and rangeBearing"; 24 | } 25 | 26 | return retval; 27 | } 28 | 29 | /// 30 | /// validate a Deserialized Alert Response Message 31 | /// 32 | /// the Alert Response Message 33 | /// empty string or validation error message 34 | public static string ValidateAlertResponse(AlertResponse response) 35 | { 36 | string retval = string.Empty; 37 | if (!ValidAlertStatus(response.status)) 38 | { 39 | retval = "AlertResponse Invalid status"; 40 | } 41 | 42 | return retval; 43 | } 44 | 45 | /// 46 | /// Whether this is a valid request command 47 | /// 48 | /// request string to validate 49 | /// true if valid 50 | private static bool ValidAlertStatus(string tag) 51 | { 52 | var retval = false; 53 | switch (tag) 54 | { 55 | case "Active": 56 | case "Acknowledge": 57 | case "Reject": 58 | case "Ignore": 59 | case "Clear": 60 | retval = true; 61 | break; 62 | } 63 | 64 | return retval; 65 | } 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /SapientServices/Data/Validation/ApprovalValidation.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Text; 5 | using System.Threading.Tasks; 6 | 7 | namespace SapientServices.Data.Validation 8 | { 9 | public class ApprovalValidation 10 | { 11 | 12 | /// 13 | /// validate a Deserialized Approval Message 14 | /// 15 | /// the Approval Message 16 | /// empty string or validation error message 17 | public static string ValidateApproval(Approval approval) 18 | { 19 | string retval = string.Empty; 20 | if (!ValidApprovalStatus(approval.status)) 21 | { 22 | retval = "Approval Invalid Status"; 23 | } 24 | 25 | return retval; 26 | } 27 | 28 | /// 29 | /// Whether this is a valid request command 30 | /// 31 | /// request string to validate 32 | /// true if valid 33 | private static bool ValidApprovalStatus(string tag) 34 | { 35 | var retval = false; 36 | switch (tag) 37 | { 38 | case "Accepted": 39 | case "Approved": 40 | case "Rejected": 41 | case "Complete": 42 | retval = true; 43 | break; 44 | } 45 | 46 | return retval; 47 | } 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /SapientServices/Data/Validation/DetectionValidation.cs: -------------------------------------------------------------------------------- 1 | namespace SapientServices.Data.Validation 2 | { 3 | public class DetectionValidation 4 | { 5 | /// 6 | /// validate a Deserialized Detection Report Message 7 | /// 8 | /// the Detection Report Message 9 | /// empty string or validation error message 10 | public static string ValidateDetection(DetectionReport detection_report) 11 | { 12 | // if detection is not lost then it needs either a location or a range-bearing 13 | if (detection_report.location == null && detection_report.rangeBearing == null) 14 | { 15 | return "DetectionReport Invalid has neither location nor rangeBearing"; 16 | } 17 | 18 | return ValidatePredictedLocation(detection_report); 19 | } 20 | 21 | /// 22 | /// validate Predicted Location element of detection message 23 | /// 24 | /// the Detection Report Message 25 | /// empty string or validation error message 26 | private static string ValidatePredictedLocation(DetectionReport detection_report) 27 | { 28 | // if predictedLocation is present then it needs either a location or a range-bearing 29 | if (detection_report.predictedLocation != null) 30 | { 31 | if (detection_report.predictedLocation.location == null && detection_report.predictedLocation.rangeBearing == null) 32 | { 33 | return "DetectionReport Invalid predicted Location has neither Location nor rangeBearing"; 34 | } 35 | 36 | if (detection_report.predictedLocation.location != null && detection_report.predictedLocation.rangeBearing != null) 37 | { 38 | return "DetectionReport Invalid predictedLocation has both location and rangeBearing"; 39 | } 40 | } 41 | 42 | return string.Empty; 43 | } 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /SapientServices/Histogram.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: Histogram.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientServices 8 | { 9 | /// 10 | /// class to provide a simple histogram of network timing 11 | /// 12 | public class Histogram 13 | { 14 | /// 15 | /// Histogram array 16 | /// 17 | public int[] histo = new int[10]; 18 | 19 | /// 20 | /// Initialize histogram 21 | /// 22 | public void Initialise() 23 | { 24 | int index; 25 | for (index = 0; index < 10; index++) 26 | { 27 | this.histo[index] = 0; 28 | } 29 | } 30 | 31 | /// 32 | /// Add a data point to the histogram 33 | /// 34 | /// data point to add to histogram 35 | public void Add(double value) 36 | { 37 | if ((value >= 0) && (value <= 10.0)) 38 | { 39 | this.histo[0]++; 40 | } 41 | else if ((value > 10.0) && (value <= 20.0)) 42 | { 43 | this.histo[1]++; 44 | } 45 | else if ((value > 20.0) && (value <= 50.0)) 46 | { 47 | this.histo[2]++; 48 | } 49 | else if ((value > 50.0) && (value <= 100.0)) 50 | { 51 | this.histo[3]++; 52 | } 53 | else if ((value > 100.0) && (value <= 200.0)) 54 | { 55 | this.histo[4]++; 56 | } 57 | else if ((value > 200.0) && (value <= 500.0)) 58 | { 59 | this.histo[5]++; 60 | } 61 | else if ((value > 500.0) && (value <= 1000.0)) 62 | { 63 | this.histo[6]++; 64 | } 65 | else if (value > 1000.0) 66 | { 67 | this.histo[7]++; 68 | } 69 | else if (value < 0) 70 | { 71 | this.histo[8]++; 72 | } 73 | } 74 | 75 | /// 76 | /// return the histogram as a text string 77 | /// 78 | /// text string 79 | public string Print() 80 | { 81 | return string.Format("{0}, {1}, {2}, {3}, {4}, {5}, {6}, {7}, -{8} ", histo[0], histo[1], histo[2], histo[3], histo[4], histo[5], histo[6], histo[7], histo[8]); 82 | } 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /SapientServices/ICommsConnection.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: ICommsConnection.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientServices.Communication 8 | { 9 | /// 10 | /// interface definition for Communications Connection 11 | /// 12 | public interface ICommsConnection 13 | { 14 | /// 15 | /// interface method to Start Communications Connection 16 | /// 17 | /// maximum packet size in bytes 18 | /// whether a send only connection 19 | void Start(uint maximumPacketSize, bool sendOnly); 20 | 21 | /// 22 | /// interface method to Start Communications Connection 23 | /// 24 | void Start(); 25 | 26 | /// 27 | /// interface method to Shutdown Communications Connection 28 | /// 29 | void Shutdown(); 30 | 31 | /// 32 | /// interface method to Set Data Received Callback for Communications Connection 33 | /// 34 | /// callback method 35 | void SetDataReceivedCallback(SapientCommsCommon.DataReceivedCallback callback); 36 | 37 | /// 38 | /// interface method to Set Connected Callback for Communications Connection 39 | /// 40 | /// callback method 41 | void SetConnectedCallback(SapientCommsCommon.StatusCallback statuscallback); 42 | 43 | /// 44 | /// Poll Communications connection status 45 | /// 46 | /// true for connected 47 | bool IsConnected(); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /SapientServices/IConnection.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: IConnection.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientServices.Communication 8 | { 9 | /// 10 | /// Interface for Sending Data over a communications connection 11 | /// 12 | public interface IConnection 13 | { 14 | /// 15 | /// Gets a Connection unique identifier 16 | /// 17 | uint ConnectionID { get; } 18 | 19 | /// 20 | /// interface method to Send Message 21 | /// 22 | /// message to send 23 | /// size in bytes 24 | /// whether successful 25 | bool SendMessage(byte[] msg, int msg_size); 26 | 27 | /// 28 | /// interface method to Set No Delay 29 | /// 30 | /// set connection to no delay 31 | void SetNoDelay(bool no_delay); 32 | 33 | /// 34 | /// set whether to end subsequent messages with null termination 35 | /// 36 | /// whether to include null termination on sent messages 37 | void SetSendNullTermination(bool useNullTermination); 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /SapientServices/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // Crown-Owned Copyright (c) 6 | // General Information about an assembly is controlled through the following 7 | // set of attributes. Change these attribute values to modify the information 8 | // associated with an assembly. 9 | [assembly: AssemblyTitle("Sapient Services")] 10 | [assembly: AssemblyDescription("")] 11 | [assembly: AssemblyConfiguration("")] 12 | [assembly: AssemblyCompany("QinetiQ")] 13 | [assembly: AssemblyProduct("Sapient")] 14 | [assembly: AssemblyCopyright("© Crown-Owned Copyright 2021")] 15 | [assembly: AssemblyTrademark("")] 16 | [assembly: AssemblyCulture("")] 17 | 18 | // Setting ComVisible to false makes the types in this assembly not visible 19 | // to COM components. If you need to access a type in this assembly from 20 | // COM, set the ComVisible attribute to true on that type. 21 | [assembly: ComVisible(false)] 22 | 23 | // The following GUID is for the ID of the typelib if this project is exposed to COM 24 | [assembly: Guid("e28628fc-5db8-435a-bb15-aefedc03bd4c")] 25 | 26 | // Version information for an assembly consists of the following four values: 27 | // 28 | // Major Version 29 | // Minor Version 30 | // Build Number 31 | // Revision 32 | // 33 | // You can specify all the values or you can default the Build and Revision Numbers 34 | // by using the '*' as shown below: 35 | // [assembly: AssemblyVersion("1.0.*")] 36 | [assembly: AssemblyVersion("2.7.4.0")] 37 | [assembly: AssemblyFileVersion("2.7.4.0")] 38 | -------------------------------------------------------------------------------- /SapientServices/SapientCommsCommon.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: SapientCommsCommon.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientServices.Communication 8 | { 9 | /// 10 | /// delegates class for Sapient Communications 11 | /// 12 | public class SapientCommsCommon 13 | { 14 | /// 15 | /// delegate for Data Received Callback 16 | /// 17 | /// message data 18 | /// message size in bytes 19 | /// connection object 20 | public delegate void DataReceivedCallback(ref byte[] msgBuffer, int size, IConnection client); 21 | 22 | /// 23 | /// delegate for Status Callback 24 | /// 25 | /// status message 26 | /// connection object 27 | public delegate void StatusCallback(string statusMsg, IConnection client); 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /SapientServices/SapientMessageType.cs: -------------------------------------------------------------------------------- 1 | // Project: $Project: 00010855-Sapient$ 2 | // File: $Workfile: SapientMessageType.cs$ 3 | // 4 | // Crown-Owned Copyright (c) supplied by QinetiQ. See Release/Supply Conditions 5 | // 6 | 7 | namespace SapientServices 8 | { 9 | public enum SapientMessageType 10 | { 11 | Detection = 0, 12 | Status = 1, 13 | Alert = 2, 14 | Task = 3, 15 | TaskACK = 4, 16 | AlertResponse = 5, 17 | Registration = 6, 18 | IdError = 7, 19 | InternalError = 8, 20 | InvalidTasking = 9, 21 | Unknown = 10, 22 | InvalidClient = 11, 23 | RegistrationACK = 12, 24 | Error = 13, 25 | ResponseIdError = 14, 26 | Unsupported = 15, 27 | Reserved = 16, 28 | Objective = 17, 29 | RoutePlan = 18, 30 | Approval = 19, 31 | SensorTaskDropped = 20, 32 | SensorTaskTakeControl = 21, 33 | SensorTaskReleaseControl = 22 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /SapientServices/SapientServices.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | Debug 5 | AnyCPU 6 | 8.0.30703 7 | 2.0 8 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E} 9 | Library 10 | Properties 11 | SapientServices 12 | SapientServices 13 | v4.8 14 | 512 15 | 16 | 17 | 18 | true 19 | full 20 | false 21 | bin\Debug\ 22 | DEBUG;TRACE 23 | prompt 24 | 4 25 | false 26 | 27 | 28 | pdbonly 29 | true 30 | bin\Release\ 31 | TRACE 32 | prompt 33 | 4 34 | false 35 | 36 | 37 | 38 | .\log4net.dll 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 89 | -------------------------------------------------------------------------------- /SapientServices/SapientServices.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 11.00 3 | # Visual Studio 2010 4 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SapientServices", "SapientServices.csproj", "{9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|Any CPU = Debug|Any CPU 9 | Release|Any CPU = Release|Any CPU 10 | EndGlobalSection 11 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 12 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 13 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Debug|Any CPU.Build.0 = Debug|Any CPU 14 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|Any CPU.ActiveCfg = Release|Any CPU 15 | {9D6BD18A-2ABB-4EF8-9E54-CC11A9B78D6E}.Release|Any CPU.Build.0 = Release|Any CPU 16 | EndGlobalSection 17 | GlobalSection(SolutionProperties) = preSolution 18 | HideSolutionNode = FALSE 19 | EndGlobalSection 20 | EndGlobal 21 | -------------------------------------------------------------------------------- /SapientServices/log4net.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dstl/SAPIENT-Middleware-and-Test-Harness/efff60a7f5d3ee3c60ef1800324f21f7ea02a7ce/SapientServices/log4net.dll -------------------------------------------------------------------------------- /SapientServices/readme.txt: -------------------------------------------------------------------------------- 1 | Readme File for Sapient Comms Library 2 | ===================================== 3 | 4 | This is a c# / .NET 4 library for wrapping 5 | the client server interactions on the Sapient system 6 | 7 | 30/07/14 -rejigged to make it easier to replay to messages by including SendMesage in IConnection interface 8 | 31/07/14 - bug fix in reported size of received messages 9 | 21/09/15 - final fields for SAPIENT Phase 2 10 | 13/06/16 - additional HL alert fields for SAPIENT Phase 4 11 | 01/09/16 - v2.3.3 - added 'Follow Track' request 12 | 26/09/16 - v2.3.4 - added start/Stop/Play Video request 13 | 11/06/17 - v2.3.5 - added additional database and ground truth table for SAPIENT cUAS 14 | 27/06/17 - v2.3.5.1 - bug fix in ground truth table - detection_id 15 | 27/11/17 - v2.3.6 - Fixed Regions and Add/Delete Regions from Map parsed via HDA, Added Region trigger builder 16 | 05/03/19 - v2.3.7 - bug fix in dbAlert - allow alert messages when not connected to database 17 | 08/03/19 - v2.3.8 - more friendly error reporting of database and client socket errors 18 | 12/01/20 - v2.5.1 - rebuilt for DSTL SAPIENT Workshop release 19 | 03/05/20 - v2.6.1 - refactored Middleware code and added automated testing to test harness 20 | 31/07/20 - v2.6.4 - Zodiac Pre-Alpha Virtual Integration 21 | 31/03/21 - v2.7.4 - Zodiac Pre-Alpha Demonstration 22 | -------------------------------------------------------------------------------- /XSD/Approval.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /XSD/RoutePlan.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /XSD/SapientICDv3.xsd: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /XSD/SensorRegistrationACK.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /XSD/SensorTaskACK.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /XSD/alert.xsd: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | -------------------------------------------------------------------------------- /XSD/alertResponse.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /XSD/detectionV3.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | -------------------------------------------------------------------------------- /XSD/error.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /XSD/heartbeatV3.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | -------------------------------------------------------------------------------- /XSD/locationV3.xsd: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | -------------------------------------------------------------------------------- /XSD/objective.xsd: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | --------------------------------------------------------------------------------