/*********************************************************************/
/* */
/* AgentService Framework */
/* www.agentservice.it */
/* */
/* Copyright (C) 2007 l.i.d.o. - DIST, University of Genoa, Italy */
/* GNU Lesser General Public License */
/* */
/* This library is free software; you can redistribute it and/or */
/* modify it under the terms of the GNU Lesser General Public */
/* License as published by the Free Software Foundation, */
/* version 2.1 of the License. */
/* */
/* This library 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 */
/* Lesser General Public License for more details. */
/* */
/* You should have received a copy of the GNU Lesser General Public */
/* License along with this library; if not, write to the */
/* Free Software Foundation, Inc., 59 Temple Place - Suite 330, */
/* Boston, MA 02111-1307, USA. */
/* */
/*********************************************************************/
using System;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using AgentService.Interop;
using AgentService.Platform;
namespace AgentService.Interop.Implementation
{
///
/// Class PlatformChannel. Defualt implementation
/// of the IPlatformChannel interface.
///
public class PlatformChannel : IPlatformChannel
{
///
/// paltform public key.
///
private byte[] key;
///
/// Gets the platform public key.
///
public byte[] PlatformPublicKey
{
get
{
return this.key;
}
}
///
/// TCP address of the platform instance
/// to which the client is connected.
///
private TCPAddress address;
///
/// Gets the address of the platform instance
/// to which the clieny is connected.
///
public TCPAddress PlatformAddress
{
get
{
return this.address;
}
}
///
/// client credentials.
///
private PlatformClientInfo client;
///
/// Gets the client credentials, used by the
/// channel to connect to the platform.
///
public PlatformClientInfo Client
{
get
{
return this.client;
}
}
///
/// channel state.
///
private ChannelState state;
///
/// Gets the channel state.
///
public AgentService.Interop.ChannelState State
{
get
{
return state;
}
}
///
/// reference to the platform controller.
///
private IPlatformController controller;
///
/// Gets the interface used to access the platform.
/// This value is not null only when the connection
/// with the platform is active.
///
public IPlatformController Controller
{
get
{
return this.controller;
}
}
///
/// Fires evry time an error on the platform channel occurs.
///
public event AgentService.Interop.PlatformChannelDelegate ChannelError;
///
/// autoclose flag;
///
private bool bAutoClose;
///
/// Gets, sets the channel closure
/// strategy, if true the channel
/// authomatically closes on every
/// type of error.
///
public bool AutoCloseOnError
{
get
{
return this.bAutoClose;
}
set
{
this.bAutoClose = value;
if ((this.bAutoClose == true) && ((this.state & ChannelState.Error) > 0))
{
this.Close(true);
}
}
}
///
/// Reference to the platform binder that manages this channel.
///
private PlatformBinder binder;
///
/// thread used to connect to the platform instance.
///
private Thread connectorThread;
///
/// Constructs a PlatformChannel instance.
///
/// reference to the platform binder that created the channel
/// user credentials used by the channel
/// tcp address of the platform instance
/// public key of the platform instance
public PlatformChannel(PlatformBinder binder, User user, TCPAddress address, byte[] publicKey)
{
this.bAutoClose = false;
this.binder = binder;
this.key = publicKey;
// provide a dummy address
// when the platform is connected
// provide the correct one.
TCPAddress thisAddress = null;
this.client = new PlatformClientInfo(user,thisAddress);
this.connectorThread = new Thread(new ThreadStart(this.DoActivation));
this.connectorThread.Start();
}
///
/// Reconnects to the platform instance.
///
public void Reconnect()
{
// TODO: provide channel reconnection.
}
///
/// Close the communication channel.
///
public void Close()
{
this.Close(true);
}
///
/// Closes the connection and eventually signals
/// to the binder the event of the channel closure.
///
///
internal void Close(bool bNotifyBinder)
{
// TODO: provide channel closure.
if (this.state != ChannelState.Disconnected)
{
if (bNotifyBinder == true)
this.binder.SignalClose(this);
}
}
///
/// method used to connect the platform instance.
///
private void DoActivation()
{
this.state = ChannelState.Connecting;
Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
IPEndPoint remotePoint = new IPEndPoint(this.address.Address, this.address.Port);
try
{
socket.Connect(remotePoint);
this.state = ChannelState.Authenticating;
}
catch(SocketException sex)
{
this.state = ChannelState.Disconnected;
}
}
}
}