private void Initialise()
        {
            try
            {
                m_tlsServerListener = new TcpListener(m_localSIPEndPoint.GetIPEndPoint());
                m_tlsServerListener.Server.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);

                m_tlsServerListener.Start(MAX_TLS_CONNECTIONS);

                if (m_localSIPEndPoint.Port == 0)
                {
                    m_localSIPEndPoint = new SIPEndPoint(SIPProtocolsEnum.tls, (IPEndPoint)m_tlsServerListener.Server.LocalEndPoint);
                }

                LocalTCPSockets.Add(((IPEndPoint)m_tlsServerListener.Server.LocalEndPoint).ToString());

                ThreadPool.QueueUserWorkItem(delegate { AcceptConnections(ACCEPT_THREAD_NAME + m_localSIPEndPoint.Port); });
                ThreadPool.QueueUserWorkItem(delegate { PruneConnections(PRUNE_THREAD_NAME + m_localSIPEndPoint.Port); });

                logger.LogDebug("SIP TLS Channel listener created " + m_localSIPEndPoint.GetIPEndPoint() + ".");
            }
            catch (Exception excp)
            {
                logger.LogError("Exception SIPTLSChannel Initialise. " + excp);
                throw;
            }
        }
Example #2
0
            new Dictionary <string, DateTime>();    // Tracks sockets that have had a connection failure on them to avoid endless re-connect attmepts.

        public SIPTCPChannel(IPEndPoint endPoint)
        {
            m_localSIPEndPoint = new SIPEndPoint(SIPProtocolsEnum.tcp, endPoint);
            LocalTCPSockets.Add(endPoint.ToString());
            m_isReliable = true;
            Initialise();
        }
Example #3
0
        /// <summary>
        /// Initialises the SIP channel's socket listener.
        /// </summary>
        private void Initialise()
        {
            try
            {
                IPEndPoint listenEndPoint = m_localSIPEndPoint.GetIPEndPoint();

                m_tcpServerListener = new TcpListener(listenEndPoint);
                m_tcpServerListener.Server.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
                m_tcpServerListener.Server.LingerState = new LingerOption(true, 0);
                m_tcpServerListener.Start(MAX_TCP_CONNECTIONS);

                if (m_localSIPEndPoint.Port == 0)
                {
                    m_localSIPEndPoint = new SIPEndPoint(SIPProtocolsEnum.tcp, listenEndPoint);
                }

                LocalTCPSockets.Add(listenEndPoint.ToString());

                ThreadPool.QueueUserWorkItem(delegate { AcceptConnections(); });
                ThreadPool.QueueUserWorkItem(delegate { PruneConnections(m_pruneThreadName + m_localSIPEndPoint.Port); });

                logger.LogDebug("SIP TCP Channel listener created " + m_localSIPEndPoint.GetIPEndPoint() + ".");
            }
            catch (Exception excp)
            {
                logger.LogError("Exception SIPTCPChannel Initialise. " + excp.Message);
                throw excp;
            }
        }
Example #4
0
        /// <summary>
        /// Attempts to send data to the remote end point over a reliable connection. If an existing
        /// connection exists it will be used otherwise an attempt will be made to establish a new connection.
        /// </summary>
        /// <param name="dstEndPoint">The remote end point to send the reliable data to.</param>
        /// <param name="buffer">The data to send.</param>
        /// <param name="serverCertificateName">Optional. Only relevant for SSL streams. The common name
        /// that is expected for the remote SSL server.</param>
        public override async Task <SocketError> SendAsync(IPEndPoint dstEndPoint, byte[] buffer, string serverCertificateName)
        {
            try
            {
                if (buffer == null || buffer.Length == 0)
                {
                    throw new ApplicationException("An empty buffer was specified to Send in SIPTCPChannel.");
                }
                else if (DisableLocalTCPSocketsCheck == false && LocalTCPSockets.Contains(dstEndPoint.ToString()))
                {
                    logger.LogWarning($"SIPTCPChannel blocked Send to {dstEndPoint} as it was identified as a locally hosted TCP socket.\r\n" + Encoding.UTF8.GetString(buffer));
                    throw new ApplicationException("A Send call was blocked in SIPTCPChannel due to the destination being another local TCP socket.");
                }
                else if (m_connectionFailures.ContainsKey(dstEndPoint.ToString()))
                {
                    throw new ApplicationException($"SIP TCP channel connect attempt to {dstEndPoint} failed.");
                }
                else
                {
                    SIPStreamConnection sipStreamConn = null;

                    // Lookup a client socket that is connected to the destination. If it does not exist attempt to connect a new one.
                    if (m_connectedSockets.ContainsKey(dstEndPoint.ToString()))
                    {
                        sipStreamConn = m_connectedSockets[dstEndPoint.ToString()];
                        SendOnConnected(sipStreamConn, buffer);
                        return(SocketError.Success);
                    }
                    else
                    {
                        await ConnectClientAsync(dstEndPoint, buffer, serverCertificateName);

                        return(SocketError.Success);
                    }
                }
            }
            catch (SocketException sockExcp)
            {
                return(sockExcp.SocketErrorCode);
            }
            catch (ApplicationException)
            {
                throw;
            }
            catch (Exception excp)
            {
                logger.LogError("Exception (" + excp.GetType().ToString() + ") SIPTCPChannel Send (sendto=>" + dstEndPoint + "). " + excp.Message);
                throw;
            }
        }
Example #5
0
        public SIPTLSChannel(X509Certificate2 serverCertificate, IPEndPoint endPoint)
        {
            if (serverCertificate == null)
            {
                throw new ArgumentNullException("serverCertificate", "An X509 certificate must be supplied for a SIP TLS channel.");
            }

            if (endPoint == null)
            {
                throw new ArgumentNullException("endPoint", "An IP end point must be supplied for a SIP TLS channel.");
            }

            m_localSIPEndPoint = new SIPEndPoint(SIPProtocolsEnum.tls, endPoint);
            LocalTCPSockets.Add(endPoint.ToString());
            m_isReliable = true;
            m_isTLS      = true;
            //m_certificatePath = certificateFileName;
            ///base.Name = "s" + Crypto.GetRandomInt(4);
            m_serverCertificate = serverCertificate;
            Initialise();
        }
Example #6
0
        public override void Send(IPEndPoint dstEndPoint, byte[] buffer, string serverCertificateName)
        {
            try
            {
                if (buffer == null)
                {
                    throw new ApplicationException("An empty buffer was specified to Send in SIPTLSChannel.");
                }
                else if (LocalTCPSockets.Contains(dstEndPoint.ToString()))
                {
                    logger.Error("SIPTLSChannel blocked Send to " + dstEndPoint.ToString() + " as it was identified as a locally hosted TCP socket.\r\n" + Encoding.UTF8.GetString(buffer));
                    throw new ApplicationException("A Send call was made in SIPTLSChannel to send to another local TCP socket.");
                }
                else
                {
                    bool sent = false;
                    bool existingConnection = false;

                    // Lookup a client socket that is connected to the destination.
                    //m_sipConn(buffer, buffer.Length, destinationEndPoint);
                    if (m_connectedSockets.ContainsKey(dstEndPoint.ToString()))
                    {
                        existingConnection = true;
                        SIPConnection sipTLSClient = m_connectedSockets[dstEndPoint.ToString()];

                        try
                        {
                            if (sipTLSClient.SIPStream != null && sipTLSClient.SIPStream.CanWrite)
                            {
                                sipTLSClient.SIPStream.BeginWrite(buffer, 0, buffer.Length, new AsyncCallback(EndSend), sipTLSClient);
                                sent = true;
                                sipTLSClient.LastTransmission = DateTime.Now;
                            }
                            else
                            {
                                logger.Warn("A SIPTLSChannel write operation to " + dstEndPoint + " was dropped as the stream was null or could not be written to.");
                            }
                        }
                        catch (SocketException)
                        {
                            logger.Warn("Could not send to TLS socket " + dstEndPoint + ", closing and removing.");
                            sipTLSClient.SIPStream.Close();
                            m_connectedSockets.Remove(dstEndPoint.ToString());
                        }
                    }

                    if (!sent && !existingConnection)
                    {
                        if (serverCertificateName.IsNullOrBlank())
                        {
                            throw new ApplicationException("The SIP TLS Channel must be provided with the name of the expected server certificate, please use alternative method.");
                        }

                        if (!m_connectingSockets.Contains(dstEndPoint.ToString()))
                        {
                            logger.Debug("Attempting to establish TLS connection to " + dstEndPoint + ".");
                            TcpClient tcpClient = new TcpClient();
                            tcpClient.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
                            tcpClient.Client.Bind(m_localSIPEndPoint.GetIPEndPoint());

                            m_connectingSockets.Add(dstEndPoint.ToString());
                            tcpClient.BeginConnect(dstEndPoint.Address, dstEndPoint.Port, EndConnect, new object[] { tcpClient, dstEndPoint, buffer, serverCertificateName });
                        }
                        else
                        {
                            logger.Warn("Could not send SIP packet to TLS " + dstEndPoint + " and another connection was already in progress so dropping message.");
                        }
                    }
                }
            }
            catch (Exception excp)
            {
                logger.Error("Exception (" + excp.GetType().ToString() + ") SIPTLSChannel Send (sendto=>" + dstEndPoint + "). " + excp);
                throw excp;
            }
        }
Example #7
0
        public override void Send(IPEndPoint dstEndPoint, byte[] buffer)
        {
            try
            {
                if (buffer == null)
                {
                    throw new ApplicationException("An empty buffer was specified to Send in SIPTCPChannel.");
                }
                else if (LocalTCPSockets.Contains(dstEndPoint.ToString()))
                {
                    logger.Error("SIPTCPChannel blocked Send to " + dstEndPoint.ToString() + " as it was identified as a locally hosted TCP socket.\r\n" + Encoding.UTF8.GetString(buffer));
                    throw new ApplicationException("A Send call was made in SIPTCPChannel to send to another local TCP socket.");
                }
                else
                {
                    bool sent = false;

                    // Lookup a client socket that is connected to the destination.
                    //m_sipConn(buffer, buffer.Length, destinationEndPoint);
                    if (m_connectedSockets.ContainsKey(dstEndPoint.ToString()))
                    {
                        SIPConnection sipTCPClient = m_connectedSockets[dstEndPoint.ToString()];

                        try
                        {
                            lock (m_writeLock)
                            {
                                //logger.Warn("TCP channel BeginWrite from " + SIPChannelEndPoint.ToString() + " to " + sipTCPClient.RemoteEndPoint + ": " + Encoding.ASCII.GetString(buffer, 0, 32) + ".");
                                sipTCPClient.SIPStream.BeginWrite(buffer, 0, buffer.Length, new AsyncCallback(EndSend), sipTCPClient);
                                //logger.Warn("TCP channel BeginWrite complete from " + SIPChannelEndPoint.ToString() + " to " + sipTCPClient.RemoteEndPoint + ".");
                                //sipTCPClient.SIPStream.Flush();
                                sent = true;
                                sipTCPClient.LastTransmission = DateTime.Now;
                            }
                        }
                        catch (SocketException)
                        {
                            logger.Warn("Could not send to TCP socket " + dstEndPoint + ", closing and removing.");
                            sipTCPClient.SIPStream.Close();
                            m_connectedSockets.Remove(dstEndPoint.ToString());
                        }
                    }

                    if (!sent)
                    {
                        if (m_connectionFailures.ContainsKey(dstEndPoint.ToString()) && m_connectionFailures[dstEndPoint.ToString()] < DateTime.Now.AddSeconds(FAILED_CONNECTION_DONTUSE_INTERVAL * -1))
                        {
                            m_connectionFailures.Remove(dstEndPoint.ToString());
                        }

                        if (m_connectionFailures.ContainsKey(dstEndPoint.ToString()))
                        {
                            throw new ApplicationException("TCP connection attempt to " + dstEndPoint.ToString() + " was not attempted, too many failures.");
                        }
                        else if (!m_connectingSockets.Contains(dstEndPoint.ToString()))
                        {
                            logger.Debug("Attempting to establish TCP connection to " + dstEndPoint + ".");

                            TcpClient tcpClient = new TcpClient();
                            tcpClient.Client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
                            tcpClient.Client.Bind(m_localSIPEndPoint.GetIPEndPoint());

                            m_connectingSockets.Add(dstEndPoint.ToString());
                            tcpClient.BeginConnect(dstEndPoint.Address, dstEndPoint.Port, EndConnect, new object[] { tcpClient, dstEndPoint, buffer });
                        }
                        else
                        {
                            //logger.Warn("Could not send SIP packet to TCP " + dstEndPoint + " and another connection was already in progress so dropping message.");
                        }
                    }
                }
            }
            catch (ApplicationException appExcp)
            {
                logger.Warn("ApplicationException SIPTCPChannel Send (sendto=>" + dstEndPoint + "). " + appExcp.Message);
                throw;
            }
            catch (Exception excp)
            {
                logger.Error("Exception (" + excp.GetType().ToString() + ") SIPTCPChannel Send (sendto=>" + dstEndPoint + "). " + excp.Message);
                throw;
            }
        }