CommandManager.cs
Go to the documentation of this file.
//
// CommandManager.cs
//
// Author:
// Di MERCURIO Sébastien <dimercur@insa-toulouse.fr>
//
// Copyright (c) 2018 INSA - DGEI
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.
using System.Threading;
namespace monitor
{
public class CommandManager
{
public delegate void CommandReceivedEvent(string msg, byte[] buffer);
public CommandReceivedEvent commandReceivedEvent = null;
private System.Timers.Timer waitTimer = new System.Timers.Timer();
private ManualResetEvent waitEvent = new ManualResetEvent(false);
private bool waitForAcknowledge = false;
private string messageReceived = null;
private bool isBusy = false;
public enum CommandManagerStatus
{
AnswerReceived,
Timeout,
Busy
};
public CommandManager(CommandReceivedEvent callback)
{
Client.readEvent += this.OnMessageReception;
this.commandReceivedEvent += callback;
waitTimer.Elapsed += OnMessageTimeout;
}
~CommandManager()
{
Client.Close();
}
public bool Open(string hostname)
{
return this.Open(hostname, Client.defaultPort);
}
public bool Open(string hostname, int port)
{
return Client.Open(hostname, port);
}
public void Close()
{
Client.Close();
}
private void OnMessageReception(string message, byte[] buffer)
{
waitTimer.Stop(); // Stop timeout stopwatch
this.messageReceived = message;
isBusy = false;
// if SendCommand wait for an acknowledge, release semaphore waitEvent
// so that SendCommand will be able to read received answer
// Received answer will not be sent to upper level
if (waitForAcknowledge)
{
waitForAcknowledge = false;
waitEvent.Set(); // Envoi de l'evenement
}
else
// if sendCommand doesn't wait for an acknowledge, message received
// is for upper level, so call callback
{
waitForAcknowledge = false;
this.commandReceivedEvent?.Invoke(message, buffer);
}
}
private void OnMessageTimeout(object sender, System.Timers.ElapsedEventArgs e)
{
messageReceived = null;
// set buffer and message as null to indicate that no message was received
// and call to OnMessagereception is due to timeout
OnMessageReception(messageReceived, null);
}
public CommandManagerStatus SendCommand(string cmd, out string answer, double timeout)
{
CommandManagerStatus status = CommandManagerStatus.AnswerReceived;
answer = null;
if (isBusy) status = CommandManagerStatus.Busy;
else
{
isBusy = true;
// Send command to server
Client.Write(cmd);
if (timeout > 0) // Command request an acknowledge
{
waitForAcknowledge = true; // Flag used in OnMessageReception callback to avoid
// sending acknowledge message to upper level
waitTimer.Interval = timeout;
waitTimer.Start(); // Start timeout timer
waitEvent.WaitOne(); // Stop current thread, waiting for waitEvent semaphore
// produced in OnMessageReception when either a message is received
// or a timeout occur
waitEvent.Reset(); // reset semaphore for next message
if (this.messageReceived == null) // timeout: server connection error
{
status = CommandManagerStatus.Timeout;
}
}
else isBusy = false;
// return received answer, null in case of timeout
answer = this.messageReceived;
this.messageReceived = null;
}
return status;
}
}
}
monitor.CommandManager.OnMessageTimeout
void OnMessageTimeout(object sender, System.Timers.ElapsedEventArgs e)
Callback called by stopwatch on timeout
Definition: CommandManager.cs:156
monitor.Client.defaultPort
const int defaultPort
Default server port number
Definition: Client.cs:41
monitor.CommandManager.Open
bool Open(string hostname)
Open the specified hostname server, using default port number.
Definition: CommandManager.cs:96
monitor.Client.Write
static void Write(string mes)
Write a string to server
Definition: Client.cs:219
monitor.CommandManager
Command Manager. Use for timeout managment during reception of data Used as intermediate layer betwee...
Definition: CommandManager.cs:31
System
monitor.CommandManager.CommandReceivedEvent
delegate void CommandReceivedEvent(string msg, byte[] buffer)
Callback for sending received data to upper level
monitor.CommandManager.SendCommand
CommandManagerStatus SendCommand(string cmd, out string answer, double timeout)
Sends a command to TCP server
Definition: CommandManager.cs:171
monitor.CommandManager.isBusy
bool isBusy
flag indicating command manager is currently busy waiting an acknowledge
Definition: CommandManager.cs:58
monitor.CommandManager.OnMessageReception
void OnMessageReception(string message, byte[] buffer)
Callback called by Client class after reception of new message
Definition: CommandManager.cs:125
monitor.CommandManager.commandReceivedEvent
CommandReceivedEvent commandReceivedEvent
Definition: CommandManager.cs:37
monitor.CommandManager.waitTimer
System.Timers.Timer waitTimer
Timer for managing timeout
Definition: CommandManager.cs:42
monitor.CommandManager.waitEvent
ManualResetEvent waitEvent
Definition: CommandManager.cs:43
monitor
Definition: Client.cs:26
monitor.Client.Open
static bool Open(string host)
Open connection to server "host", on default port number.
Definition: Client.cs:89
monitor.Client
Static class for TCP client
Definition: Client.cs:31
monitor.Client.Close
static void Close()
Close connection to server
Definition: Client.cs:141
monitor.CommandManager.CommandManagerStatus
CommandManagerStatus
Available status when sending command
Definition: CommandManager.cs:63
monitor.Client.readEvent
static ReadEvent readEvent
Definition: Client.cs:82
monitor.CommandManager.Open
bool Open(string hostname, int port)
Open connection to server "host", with port number "port"
Definition: CommandManager.cs:107
monitor.CommandManager.messageReceived
string messageReceived
received message
Definition: CommandManager.cs:53
monitor.CommandManager.CommandManager
CommandManager(CommandReceivedEvent callback)
Initializes a new instance of the T:monitor.CommandManager class.
Definition: CommandManager.cs:74
monitor.CommandManager.~CommandManager
~CommandManager()
Releases unmanaged resources and performs other cleanup operations before the T:monitor.CommandManager is reclaimed by garbage collection.
Definition: CommandManager.cs:86
monitor.CommandManager.waitForAcknowledge
bool waitForAcknowledge
Flag to tell rogram to wait for an acknowledge from server
Definition: CommandManager.cs:48
monitor.CommandManager.Close
void Close()
Close connection to server
Definition: CommandManager.cs:115