summaryrefslogtreecommitdiffstats
path: root/data/mnet/Common/socket
diff options
context:
space:
mode:
Diffstat (limited to 'data/mnet/Common/socket')
-rw-r--r--data/mnet/Common/socket/Makefile47
-rw-r--r--data/mnet/Common/socket/include/CallBackSSL.h35
-rw-r--r--data/mnet/Common/socket/src/GenClientSocket.cpp236
-rw-r--r--data/mnet/Common/socket/src/GenSecServerSocket.cpp110
-rw-r--r--data/mnet/Common/socket/src/GenServerSocket.cpp210
-rw-r--r--data/mnet/Common/socket/src/GenSocket.cpp403
-rw-r--r--data/mnet/Common/socket/src/GenSocketSSL.cpp167
-rw-r--r--data/mnet/Common/socket/src/Makefile61
-rw-r--r--data/mnet/Common/socket/src_ssl/GenSocketSSL_lib.cpp968
-rw-r--r--data/mnet/Common/socket/src_ssl/Makefile61
-rw-r--r--data/mnet/Common/socket/src_ssl/ssl_intf.cpp235
-rw-r--r--data/mnet/Common/socket/src_stub/GenSocketSSL_stub.cpp95
-rw-r--r--data/mnet/Common/socket/src_stub/Makefile61
-rw-r--r--data/mnet/Common/socket/src_stub/ssl_intf.cpp23
14 files changed, 2712 insertions, 0 deletions
diff --git a/data/mnet/Common/socket/Makefile b/data/mnet/Common/socket/Makefile
new file mode 100644
index 0000000..2466a80
--- /dev/null
+++ b/data/mnet/Common/socket/Makefile
@@ -0,0 +1,47 @@
+##########################################################
+#
+# (c) Copyright Cisco 2000
+# All Rights Reserved
+#
+# Use Examples:
+#
+# Case 1:
+# make all VOB=GP10 -
+# Places .out in VOB/bin directory
+#
+# Case 2:
+# make all VOB=GP10 APPDIR=Host\<Application Name>\<Source Directory> -
+# Places .o file(s) in VOB\$(APPDIR)\bin directory.
+#
+# <Application Name> = Name of Application directory
+# <Source Directory> = application sub directory where the calling
+# Makefile resides.
+#
+# Example: make all VOB=GP10 APPDIR=Host\vxTemplate\src
+#
+# (OPTIONAL) Append REPLACE - Replaces the List of directories
+# to be used in the SUBDIRS variable
+#
+# Example: make all VOB=GP10 APPDIR=Host\vxTemplate\src REPLACE="src_api src_debug"
+#
+# Note: This make file must reference a VOB that
+# has a defs.mk in the top level directory.
+#
+##########################################################
+
+SUBDIRS = src
+
+# TOP_OF_VOB must be defined before including l3defs.mk
+TOP_OF_VOB = ..
+
+VOBDIR = $(TOP_OF_VOB)/../$(VOB)
+
+# Allows a sub-set of the source code directories to be used
+
+ifneq ($(REPLACE),)
+ SUBDIRS = $(REPLACE)
+endif
+
+include $(VOBDIR)\l3defs.mk
+
+
diff --git a/data/mnet/Common/socket/include/CallBackSSL.h b/data/mnet/Common/socket/include/CallBackSSL.h
new file mode 100644
index 0000000..3d7b316
--- /dev/null
+++ b/data/mnet/Common/socket/include/CallBackSSL.h
@@ -0,0 +1,35 @@
+#ifndef __CALLBACKSSL_H__
+#define __CALLBACKSSL_H__
+
+//*******************************************************************
+//
+// (c) Copyright CISCO Systems Inc. 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 1.0
+// File : CallBackSSL.h
+// Author(s) : Igal Gutkin
+// Create Date : 5/22/01
+// Description : declaration of the service function required by the
+// SSL library
+//
+// *******************************************************************
+
+int verify_callback (int ok , X509_STORE_CTX *ctx);
+
+#if defined (_OPEN_SSL_LIB_)
+
+ int password_cb (char *buf, int num ,int rwflag, void *userdata);
+
+#elif defined (_RSA_SSL_LIB_)
+
+ int password_cb (char *buf, int num ,int rwflag);
+
+#endif
+
+
+#endif //__CALLBACKSSL_H__ \ No newline at end of file
diff --git a/data/mnet/Common/socket/src/GenClientSocket.cpp b/data/mnet/Common/socket/src/GenClientSocket.cpp
new file mode 100644
index 0000000..95fcc8a
--- /dev/null
+++ b/data/mnet/Common/socket/src/GenClientSocket.cpp
@@ -0,0 +1,236 @@
+// *******************************************************************
+//
+// (c) Copyright CISCO Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 1.0
+// Status : Under development
+// File : GenClientSocket.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 06/20/00
+// Description : implementation of the GenClientSocket class
+//
+// *******************************************************************
+
+
+#include "socket\GenClientSocket.h"
+
+//////////////////////////////////////////////////////////////////////
+// Static data members
+//////////////////////////////////////////////////////////////////////
+SSL_CTX *GenClientSocket::pCtx_ = NULL;
+
+
+//////////////////////////////////////////////////////////////////////
+// Construction/Destruction
+//////////////////////////////////////////////////////////////////////
+
+GenClientSocket::GenClientSocket()
+ : GenSocketSSL ()
+{
+ reset ();
+}
+
+
+GenClientSocket::GenClientSocket (int sndSize, int rcvSize)
+ : GenSocketSSL ()
+{
+ reset ();
+
+ sndBuffLen_ = sndSize;
+ rcvBuffLen_ = rcvSize;
+}
+
+
+GenClientSocket::GenClientSocket (bool bEnableSSL, bool bEnableEncryption)
+ : GenSocketSSL (bEnableSSL, bEnableEncryption)
+{
+ reset ();
+}
+
+
+GenClientSocket::GenClientSocket (int sndSize, int rcvSize, bool bEnableSSL, bool bEnableEncryption)
+ : GenSocketSSL (bEnableSSL, bEnableEncryption)
+{
+ reset ();
+
+ sndBuffLen_ = sndSize;
+ rcvBuffLen_ = rcvSize;
+}
+
+
+//////////////////////////////////////////////////////////////////////
+// Primary behaviour methods
+//////////////////////////////////////////////////////////////////////
+
+bool GenClientSocket::connectServer (ubyte4 ipAddr, ubyte2 tcpPort)
+{
+ bool retVal = false;
+
+ struct sockaddr_in remAddr;
+
+ AM_FUNC ("GenClientSocket::connectServer", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isConnected() != SOCKET_CONNECTED)
+ {
+ if (create ()) // Create a socket
+ {
+ srvPort_ = tcpPort;
+ srvAddr_ = ipAddr ;
+
+ memset (&remAddr, 0, sizeof(remAddr));
+
+ remAddr.sin_family = AF_INET ;
+ remAddr.sin_addr.s_addr = srvAddr_ ;
+ remAddr.sin_port = htons(srvPort_);
+
+ if ((connect (getSocket(), (struct sockaddr *)&remAddr, sizeof(remAddr))
+ != SOC_STATUS_ERROR) )
+ {
+ if (isEnableSSL())
+ {
+ if (connectSsl ())
+ {
+ retVal = true;
+ AM_TRACE (("SSL Client is connected to %s\n",
+ getIp (srvAddr_) ));
+ }
+ else
+ {
+ AM_WARNING (("SSL Client is unable to connect to %s\n",
+ getIp (srvAddr_) ));
+ }
+ }
+ else
+ {
+ retVal = true;
+ AM_TRACE (("TCP Client is connected to: %s,%u\n",
+ getIp(srvAddr_), srvPort_ ));
+ }
+ }
+ else
+ {
+ AM_WARNING (("Socket %u error (%s) on connecting to TCP Server %s\n",
+ getSocket(), strerror(ERROR_NUM), getIp(srvAddr_)));
+ }
+
+ if (!retVal)
+ { // release the socket if not connected
+ releaseSocket (true);
+ }
+ }
+ }
+ else
+ {
+ AM_TRACE (("Invalid attempt to reinitialize an active IP connection.\n"));
+ retVal = true;
+ }
+
+ AM_RETURN (retVal);
+}
+
+
+bool GenClientSocket::reconnect()
+{
+ bool retVal = false;
+
+ AM_FUNC ("GenClientSocket::reconnect", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ releaseSocket (true);
+
+ retVal = connectServer (srvAddr_, srvPort_);
+
+ AM_RETURN (retVal);
+}
+
+
+bool GenClientSocket::create ()
+{
+ bool retVal = false;
+ int buffSize = 4 ;
+
+ AM_FUNC ("GenClientSocket::create", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (GenSocket::create())
+ {
+ if (rcvBuffLen_ > 0)
+ if (setsockopt (getSocket() , SOL_SOCKET, SO_RCVBUF,
+ (char *)&rcvBuffLen_, buffSize ) == SOC_STATUS_ERROR)
+ {
+ AM_TRACE (("Unable to set SO_RCVBUF socket option\n"));
+ }
+
+ if (rcvBuffLen_ > 0)
+ if (setsockopt (getSocket() , SOL_SOCKET, SO_SNDBUF,
+ (char *)&sndBuffLen_, buffSize ) == SOC_STATUS_ERROR)
+ {
+ AM_TRACE (("Unable to set SO_SNDBUF socket option\n"));
+ }
+
+ if (setLinger_)
+ setsockopt (getSocket() , SOL_SOCKET, SO_LINGER,
+ (char *)&lingerVal_, sizeof(linger) );
+
+ retVal = true;
+ }
+
+ AM_RETURN (retVal);
+}
+
+
+bool GenClientSocket::isContext ()
+{
+ return (pCtx_ != NULL);
+}
+
+
+bool GenClientSocket::initSslContext (LPSTR lpPswd)
+{
+ return (isSupportSSL() ? GenSocketSSL::initSslContext (pCtx_, false, lpPswd)
+ : true );
+}
+
+
+SSL_CTX *GenClientSocket::getContext ()
+{
+ return (pCtx_);
+}
+
+
+void GenClientSocket::printInfo()
+{
+ GenSocketSSL::printInfo();
+
+ if (isConnected())
+ {
+ printf ("Client Socket Info: socket %u is connected to IP (%s,%d).\n",
+ getSocket(), getIp(srvAddr_), srvPort_);
+ }
+ else
+ {
+ printf ("Client Socket Info: socket is not connected to the server.\n");
+ }
+}
+
+
+//////////////////////////////////////////////////////////////////////
+// service methods
+//////////////////////////////////////////////////////////////////////
+
+
+void GenClientSocket::reset()
+{
+ srvPort_ = 0 ;
+ srvAddr_ = 0 ;
+ sndBuffLen_ = -1;
+ rcvBuffLen_ = -1;
+ setLinger_ = false;
+}
+
diff --git a/data/mnet/Common/socket/src/GenSecServerSocket.cpp b/data/mnet/Common/socket/src/GenSecServerSocket.cpp
new file mode 100644
index 0000000..36d468b
--- /dev/null
+++ b/data/mnet/Common/socket/src/GenSecServerSocket.cpp
@@ -0,0 +1,110 @@
+// *******************************************************************
+//
+// (c) Copyright CISCO Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 1.0
+// Status : Under development
+// File : GenSecServerSocket.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 06/20/00
+// Description : implementation of the GenSecServerSocket (secondary
+// server socket) class
+//
+// *******************************************************************
+
+#include "socket\GenSecServerSocket.h"
+
+//////////////////////////////////////////////////////////////////////
+// Constructors/Destructor
+//////////////////////////////////////////////////////////////////////
+
+/*
+ This class should be used ONLY to create "secondary" socket objects:
+ Those sockets are created when a server socket accepts a connection
+ fromt the client and assigns a new "secondary" socket to handle it.
+ Socket parameter should be a valid socket.
+*/
+
+GenSecServerSocket::GenSecServerSocket (OS_SPECIFIC_SOCKET_HANDLE socket)
+ : GenServerSocket ()
+{
+ reset (socket);
+}
+
+
+GenSecServerSocket::GenSecServerSocket (OS_SPECIFIC_SOCKET_HANDLE socket ,
+ bool enableSSL,
+ bool enableEncryption)
+ : GenServerSocket (enableSSL, enableEncryption)
+{
+ AM_FUNC ("GenSecServerSocket::GenSecServerSocket(SSL)", SOC_LAYER_ID);
+ AM_ENTER();
+
+ reset (socket);
+
+ if (isEnableSSL())
+ {
+ // blocking call to SSL API. USE only for dynamic object creation!!!
+ // 1. All the necessary validity checks are performed inside "acceptSsl"
+ // 2. will release a socket on error !!!
+ if (acceptSsl () == false)
+ {
+ AM_WARNING (("Server is unable to establish SSL connection with the client on %s\n",
+ getIp(getRemoteHostAddress()) ));
+ releaseSocket (true);
+ }
+ }
+
+ if (bMoreInfo_)
+ printInfo ();
+
+ AM_LEAVE();
+}
+
+
+GenSecServerSocket::~GenSecServerSocket()
+{
+ AM_FUNC ("GenSecServerSocket::~GenSecServerSocket", SOC_LAYER_ID);
+ AM_ENTER();
+
+ if (isValid())
+ {
+ AM_TRACE (("Disconnecting socket (%u) from the client IP(%s) \n",
+ getSocket(), getIp(getRemoteHostAddress()) ));
+ }
+
+ AM_LEAVE();
+}
+
+
+void GenSecServerSocket::reset (OS_SPECIFIC_SOCKET_HANDLE socket)
+{
+ AM_FUNC ("GenSecServerSocket::reset", SOC_LAYER_ID);
+ AM_ENTER();
+
+ if (setSocket (socket))
+ {
+ //Optional timer to keep alive the connection
+ char optVal = 1 ;
+ int rcvBuffLen = SOC_RCV_BUFF_LEN,
+ sndBuffLen = SOC_SND_BUFF_LEN;
+ // hard socket close mode
+ struct linger lingerVal = {1,0};
+
+ setsockopt (getSocket(), SOL_SOCKET, SO_KEEPALIVE, &optVal , sizeof(optVal) );
+ setsockopt (getSocket(), SOL_SOCKET, SO_RCVBUF , (char *)&rcvBuffLen, sizeof(rcvBuffLen));
+ setsockopt (getSocket(), SOL_SOCKET, SO_SNDBUF , (char *)&sndBuffLen, sizeof(sndBuffLen));
+ setsockopt (getSocket(), SOL_SOCKET, SO_LINGER , (char *)&lingerVal , sizeof(linger ));
+
+ AM_TRACE (("Open new socket %d to IP (%s)\n",
+ getSocket(), getIp(getRemoteHostAddress()) ));
+ }
+
+ AM_LEAVE();
+}
+
diff --git a/data/mnet/Common/socket/src/GenServerSocket.cpp b/data/mnet/Common/socket/src/GenServerSocket.cpp
new file mode 100644
index 0000000..d44a08e
--- /dev/null
+++ b/data/mnet/Common/socket/src/GenServerSocket.cpp
@@ -0,0 +1,210 @@
+// *******************************************************************
+//
+// (c) Copyright Cisco Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 2.0
+// Status : Under development
+// File : GenServerSocket.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 06/20/00
+// Description : implementation of the GenServerSocket class.
+//
+// *******************************************************************
+
+#include "socket\GenServerSocket.h"
+
+//////////////////////////////////////////////////////////////////////
+// Static data members
+//////////////////////////////////////////////////////////////////////
+SSL_CTX *GenServerSocket::pCtx_ = NULL;
+
+
+//////////////////////////////////////////////////////////////////////
+// Constructors/Destructor
+//////////////////////////////////////////////////////////////////////
+GenServerSocket::GenServerSocket (bool bEnableSSL, bool bEnableEncryption)
+ : GenSocketSSL (bEnableSSL, bEnableEncryption), port_(0)
+{
+ ;
+}
+
+
+GenServerSocket::~GenServerSocket()
+{
+ AM_FUNC ("GenServerSocket::~GenServerSocket", SOC_LAYER_ID);
+ AM_ENTER();
+
+ if (isValid())
+ {
+ AM_DEBUG (("Closing server socket (%d) on IP (%s,%u)\n",
+ getSocket(), getIp(getLocalHostAddress()), port_));
+ }
+
+ // should clean server SSL context once per host
+
+ AM_LEAVE();
+}
+
+
+///////////////////////////////////////////////////////////
+// primary methods
+///////////////////////////////////////////////////////////
+
+bool GenServerSocket::open (ubyte2 Port)
+{
+ AM_FUNC ("GenServerSocket::open", SOC_LAYER_ID);
+ AM_ENTER ();
+ bool retVal = true;
+
+ // hard socket close mode
+ struct linger lingerVal = {1,0};
+
+ if ((retVal = !isValid()) == false)
+ {
+ AM_WARNING (("GenServerSocket::open - Attempt to reopen socket (%d).\n",
+ getSocket() ));
+ }
+
+ // create socket
+ if (retVal)
+ retVal = create ();
+
+ // bind socket
+ if (retVal)
+ retVal = bind2Address (Port);
+
+ // wait for client connection requests
+ if (retVal)
+ {
+ if (listen (getSocket(), kTCP_LISTEN_BACKLOG) == 0)
+ {
+ int rcvBuffLen = SOC_MRCV_BUFF_LEN,
+ sndBuffLen = SOC_MSND_BUFF_LEN;
+
+ setPort (Port);
+
+ setsockopt (getSocket(), SOL_SOCKET, SO_RCVBUF, (char *)&rcvBuffLen, sizeof(rcvBuffLen));
+ setsockopt (getSocket(), SOL_SOCKET, SO_SNDBUF, (char *)&sndBuffLen, sizeof(sndBuffLen));
+ setsockopt (getSocket(), SOL_SOCKET, SO_LINGER, (char *)&lingerVal , sizeof(linger ));
+
+ if (!isEnableSSL () || initSsl ())
+ { // initiate SSL session on a valid socket
+ AM_TRACE (("Open main server socket (%d) on IP (%s,%u)\n",
+ getSocket(), getIp(getLocalHostAddress()), port_));
+ }
+ else
+ {
+ AM_TRACE (("Unable to initiate SSL session on a server socket\n"));
+ retVal = false;
+ }
+
+#ifdef _AM_DEBUG_
+ printInfo ();
+#endif // _AM_DEBUG_
+ }
+ else
+ {
+ AM_ERROR (("%s: %sd\n", "listen", strerror(ERROR_NUM)));
+ retVal = false;
+ }
+ }
+
+ AM_RETURN (retVal);
+}
+
+
+SSL_CTX *GenServerSocket::getContext ()
+{
+ return (pCtx_);
+}
+
+
+bool GenServerSocket::isContext ()
+{
+ return (pCtx_ != NULL);
+}
+
+
+bool GenServerSocket::initSslContext (LPSTR lpPswd)
+{
+ return (isSupportSSL() ? GenSocketSSL::initSslContext (pCtx_, false, lpPswd)
+ : true );
+}
+
+
+///////////////////////////////////////////////////////////
+// service methods
+///////////////////////////////////////////////////////////
+
+bool GenServerSocket::bind2Address (ubyte2 Port)
+{
+ AM_FUNC("GenServerSocket::bind2Address", SOC_LAYER_ID);
+ AM_ENTER();
+
+ struct sockaddr_in LocalAddr;
+ bool retVal = false;
+ u_long ulHostAddress;
+
+ if (!isValid())
+ AM_RETURN (false);
+
+ /* ask the system to allocate a port and bind to INADDR_ANY */
+ memset(&LocalAddr, 0x00, sizeof(LocalAddr));
+
+ if ((ulHostAddress = getLocalHostAddress()) == 0)
+ AM_RETURN (false);
+
+ /* get system to allocate a port number by binding a host address */
+ LocalAddr.sin_family = AF_INET;
+
+ /* allows connection on any local interface. Replace it with ulHostAddress
+ for multihomed machine compatibility */
+ LocalAddr.sin_addr.s_addr = htonl(INADDR_ANY);
+ LocalAddr.sin_port = htons(Port);
+
+ if (bind (getSocket(), (struct sockaddr *)&LocalAddr, sizeof(LocalAddr)) != 0)
+ {
+ AM_ERROR (("Unable to bind a socket to [%s:%u]\nAnother application using it\n",
+ getIp(getLocalHostAddress()),Port ));
+ }
+ else
+ retVal = true;
+
+ AM_RETURN (retVal);
+}
+
+
+bool GenServerSocket::acceptConnection (OS_SPECIFIC_SOCKET_HANDLE& accSoc)
+{
+ bool retVal = false;
+ char ClientAddr[MAX_PATH];
+ int iAddrLen;
+
+ AM_FUNC("GenServerSocket::acceptConnection", SOC_LAYER_ID);
+ AM_ENTER();
+
+ iAddrLen = sizeof(ClientAddr);
+ memset(&ClientAddr, 0x00, iAddrLen);
+
+ if ((accSoc = accept (getSocket(), (sockaddr FAR *)&ClientAddr, &iAddrLen))
+ != INVALID_SOCKET)
+ {
+ // Perform
+ retVal = true;
+ }
+ else
+ {
+ if (isValid())
+ {
+ AM_WARNING (("GenServerSocket::acceptConnection: %s\n", strerror(ERROR_NUM) ));
+ }
+ }
+
+ AM_RETURN (retVal);
+}
+
diff --git a/data/mnet/Common/socket/src/GenSocket.cpp b/data/mnet/Common/socket/src/GenSocket.cpp
new file mode 100644
index 0000000..33b7920
--- /dev/null
+++ b/data/mnet/Common/socket/src/GenSocket.cpp
@@ -0,0 +1,403 @@
+// *******************************************************************
+//
+// (c) Copyright Cisco Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 2.0
+// Status : Under development
+// File : GenSocket.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 06/20/00
+// Description : implementation of the GenSocket class.
+//
+// *******************************************************************
+
+#include "socdefs.h"
+#include "socket\GenSocket.h"
+
+
+
+//////////////////////////////////////////////////////////////////////
+// static data members
+//////////////////////////////////////////////////////////////////////
+IpAddrPool_t GenSocket::szIpAddr_;
+
+const struct timeval GenSocket::timeOut_ = {0, 0};
+
+bool GenSocket::bMoreInfo_ =
+#ifdef _AM_DEBUG_
+ true ;
+#else
+ false;
+#endif // _AM_DEBUG_
+
+//////////////////////////////////////////////////////////////////////
+// Construction/Destruction
+//////////////////////////////////////////////////////////////////////
+
+GenSocket::GenSocket()
+ : sock_ (INVALID_SOCKET)
+{
+ ;
+}
+
+
+GenSocket::~GenSocket()
+{
+ cleanup ();
+}
+
+
+
+//////////////////////////////////////////////////////////////////////
+// static methods
+//////////////////////////////////////////////////////////////////////
+
+// Retrives local host IP address
+ubyte4 GenSocket::getLocalHostAddress()
+{
+ ubyte4 ulHostAddr = 0;
+ sbyte szHostName[MAX_PATH];
+
+ AM_FUNC ("GenSocket::getLocalHostAddress", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ // get local host name
+ if (gethostname (szHostName, sizeof(szHostName)) != SOC_STATUS_ERROR)
+ {
+ ulHostAddr = getHostAddress (szHostName);
+ }
+ else
+ {
+ AM_ERROR(("%s: %s\n", "GenSocket::getLocalHostAddress", strerror(ERROR_NUM) ));
+ }
+
+ AM_LEAVE();
+ return (ulHostAddr);
+}
+
+
+// Converts IP from HEX to dotted form
+const LPSTR GenSocket::getIp (ubyte4 ipAddr)
+{
+ memset (szIpAddr_, 0, sizeof szIpAddr_);
+
+ sprintf (szIpAddr_, "%d.%d.%d.%d", IP_BYTES (ipAddr));
+
+ return (szIpAddr_);
+}
+
+
+
+//////////////////////////////////////////////////////////////////////
+// service methods
+//////////////////////////////////////////////////////////////////////
+
+SocketState_t GenSocket::isConnected ()
+{
+ SocketState_t retVal = SOCKET_NOT_CONNECTED;
+ fd_set readFds ;
+ int tempVal ;
+ char tempBuff [32];
+
+ AM_FUNC ("GenSocket::isConnected", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isValid())
+ {
+ FD_ZERO (&readFds);
+ FD_SET (getSocket(), &readFds);
+
+ /*
+ Readability means that queued data is available for reading such
+ that a call to recv, WSARecv, WSARecvFrom, or recvfrom is
+ guaranteed not to block.
+ For connection-oriented sockets, readability can also indicate that
+ a request to close the socket has been received from the peer. If
+ the virtual circuit was closed gracefully, and all data was received,
+ then a recv will return immediately with zero bytes read. If the
+ virtual circuit was reset, then a recv will complete immediately with
+ an error code such as WSAECONNRESET. The presence of out-of-band data
+ will be checked if the socket option SO_OOBINLINE has been enabled.
+
+ 1. select returns -1, no connection
+ +2. select returns 0, socket isn't ready to read - connection is OK
+ 3. select returns > 0, socket is ready to read - check it with recv
+ 1. recv return 0 OR
+ recv return SOCKET_ERROR and errno != WSAEMSGSIZE
+ socket is closed.
+ 2. recv return SOCKET_ERROR and errno == WSAEMSGSIZE OR
+ recv return > 1, there is a data on the socket
+ If the data is unexpected, reset the socket to avoid
+ potential security violation in the child class.
+ */
+ tempVal = select (1, &readFds, NULL, NULL, (struct timeval *)&timeOut_);
+
+
+ switch (tempVal)
+ {
+ case SOC_STATUS_ERROR:
+ retVal = SOCKET_NOT_CONNECTED;
+ break;
+
+ case 0:
+ retVal = SOCKET_CONNECTED;
+ break;
+
+ default:
+ tempVal = recv (getSocket(), tempBuff, sizeof (tempBuff), MSG_PEEK);
+
+ retVal = (!tempVal || (tempVal == SOC_STATUS_ERROR && ERROR_NUM != WSAEMSGSIZE))
+ ? SOCKET_NOT_CONNECTED
+ : SOCKET_CONNECTED_READABLE;
+ break;
+ }
+ }
+
+ // AM_DEBUG (("Socket %u is %s connected.\n", getSocket(), retVal ? "" : " not"));
+
+ AM_LEAVE();
+ return (retVal);
+}
+
+
+bool GenSocket::create()
+{
+ bool retVal = false;
+ OS_SPECIFIC_SOCKET_HANDLE newSocket;
+
+ AM_FUNC ("GenSocket::create", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (!isValid ())
+ {
+ if ((newSocket = socket(AF_INET, SOCK_STREAM, 0)) != INVALID_SOCKET)
+ {
+ retVal = setSocket (newSocket);
+ AM_DEBUG (("Open new socket %u\n", getSocket()));
+ }
+ else
+ {
+ AM_ERROR(("GenSocket::create: %s\n", strerror(ERROR_NUM) ));
+ }
+ }
+ else
+ {
+ retVal = true;
+ AM_WARNING (("Attempt to reinitialize socket.\n"));
+ }
+
+ AM_LEAVE();
+ return (retVal);
+}
+
+
+// Returns a host address by the host name
+ubyte4 GenSocket::getHostAddress (LPSTR HostName)
+{
+ ubyte4 ipAddr;
+
+#ifdef _WINDOWS_
+ struct hostent *pHostAddr;
+ pHostAddr = gethostbyname (HostName);
+ ipAddr = (pHostAddr) ? (*((ubyte4 *)pHostAddr->h_addr)) : 0;
+#else
+ ipAddr = hostGetByName (HostName);
+#endif
+
+ return (ipAddr);
+}
+
+
+// Returns remote (peer) host address
+ubyte4 GenSocket::getRemoteHostAddress ()
+{
+ sockaddr_in ClientAddr ;
+ ubyte4 remIpAddr = 0;
+ int iAddrLen = sizeof(ClientAddr);
+
+ AM_FUNC ("GenSocket::getRemoteHostAddress", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isValid ())
+ {
+ if (SOC_STATUS_OK == getpeername (getSocket(), (struct sockaddr *)&ClientAddr, &iAddrLen))
+ remIpAddr = ClientAddr.sin_addr.s_addr;
+ else
+ {
+ remIpAddr = 0;
+
+ AM_TRACE (("getpeername() error %s on socket %d\n",
+ strerror(ERROR_NUM), getSocket() ));
+ }
+ }
+
+ AM_LEAVE();
+ return (remIpAddr);
+}
+
+
+bool GenSocket::setSocket (OS_SPECIFIC_SOCKET_HANDLE Socket)
+{
+ bool retVal = false;
+
+ if (!isValid() && Socket != INVALID_SOCKET && Socket)
+ {
+ sock_ = Socket;
+ retVal = true ;
+ }
+
+ return (retVal);
+}
+
+
+int GenSocket::tcpReceive (sbyte *pBuf, int BufSize)
+{
+ int MsgLen = SOC_STATUS_ERROR;
+
+ AM_FUNC ("GenSocket::tcpReceive", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isValid())
+ {
+ MsgLen = recv (getSocket(), pBuf, BufSize, 0);
+
+ switch (MsgLen)
+ {
+ case 0:
+ AM_TRACE (("GenSocket::tcpReceive: Client closed connection on socket (%d)\n",
+ getSocket()));
+ break;
+
+ case SOC_STATUS_ERROR:
+ AM_TRACE (("GenSocket::tcpReceive: recv error %s on socket (%d)\n",
+ strerror(ERROR_NUM), getSocket() ));
+ break;
+
+ default:
+ AM_DEBUG (("GenSocket::tcpReceive: message received - total length (%d)\n", MsgLen));
+ AM_HEXDUMP ((ubyte *)pBuf, MsgLen);
+ break;
+ }
+ }
+
+ AM_LEAVE();
+ return (MsgLen);
+}
+
+
+int GenSocket::tcpSend (sbyte* pBuff, int inDataLen)
+{
+ AM_FUNC ("GenSocket::tcpSend", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ int retVal = SOCKET_STATUS_FATAL_SOC_ERR;
+ int sentDataLen, socError;
+
+
+ if (isValid ())
+ {
+ sentDataLen = send (getSocket(), pBuff, inDataLen, 0);
+
+ if (sentDataLen != SOC_STATUS_ERROR)
+ {
+ /* Checks that ALL the data is sent.
+ If blocking mode is used all the data is sent.
+ For non-blocking mode it could be less. */
+ retVal = SOCKET_STATUS_OK;
+
+ AM_DEBUG (("tcpSend: Sent %d bytes to socket %d\n", sentDataLen,
+ getSocket()));
+ }
+ else
+ {
+ socError = ERROR_NUM;
+
+ switch (socError)
+ {
+ case WSAENOBUFS:
+ retVal = SOCKET_STATUS_TEMP_SOC_ERR;
+ break;
+
+ case WSAEMSGSIZE:
+ retVal = SOCKET_STATUS_MSG_TOO_LONG;
+ AM_TRACE (("tcpSend: Data length %u exciding maximum allowed by the network.\n",
+ inDataLen));
+ break;
+
+ default:
+ retVal = SOCKET_STATUS_FATAL_SOC_ERR; // fatal error, the connection is broken
+ }
+ }
+ }
+ else
+ {
+ AM_TRACE (("Socket is not connected. Send has failed.\n"));
+ }
+
+ AM_LEAVE();
+ return (retVal);
+}
+
+
+void GenSocket::releaseSocket (bool grace)
+{
+ AM_FUNC ("GenSocket::releaseSocket", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isValid())
+ {
+ if (grace)
+ {
+ // Optional "grace" closing of the socket will wait
+ // till all pending data is sent
+ shutdown (getSocket(), SD_BOTH);
+ }
+
+ AM_DEBUG (("Closing socket %u\n", getSocket()));
+
+ SysCloseSocket (getSocket());
+ // Put optional diagnostics here
+
+ resetSocket ();
+ }
+
+ AM_LEAVE();
+}
+
+
+void GenSocket::cleanup()
+{
+ releaseSocket (true);
+}
+
+
+void GenSocket::printInfo()
+{
+ if (isValid())
+ {
+ sbyte4 rcvBuffLen = 0,
+ sndBuffLen = 0;
+ int buffSize = 4;
+
+ printf ("Socket Info: socket %d.\n", getSocket());
+
+ if (bMoreInfo_)
+ {
+ getsockopt (getSocket(), SOL_SOCKET, SO_RCVBUF, (char *)&rcvBuffLen , &buffSize);
+ getsockopt (getSocket(), SOL_SOCKET, SO_SNDBUF, (char *)&sndBuffLen , &buffSize);
+
+ printf ("Socket receive buffer is %ld Byte, send buffer is %ld Byte\n",
+ rcvBuffLen, sndBuffLen );
+ }
+ }
+ else
+ {
+ printf ("Socket is not initialized\n");
+ }
+}
+
diff --git a/data/mnet/Common/socket/src/GenSocketSSL.cpp b/data/mnet/Common/socket/src/GenSocketSSL.cpp
new file mode 100644
index 0000000..d7da39d
--- /dev/null
+++ b/data/mnet/Common/socket/src/GenSocketSSL.cpp
@@ -0,0 +1,167 @@
+// *******************************************************************
+//
+// (c) Copyright CISCO Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 1.0
+// File : GenSocketSSL.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 05/17/01
+// Description : platform independent implementation of the GenSocketSSL class.
+//
+// *******************************************************************
+
+#include "socket\GenSocketSSL.h"
+
+
+//////////////////////////////////////////////////////////////////////
+// Static data members
+//////////////////////////////////////////////////////////////////////
+
+bool GenSocketSSL::bInitLib_ = false ;
+SslError_t GenSocketSSL::errorCode_= SSL_NO_ERROR;
+int GenSocketSSL::count_ = 0 ;
+char GenSocketSSL::szPswd_ [SSL_MAX_PASSWORD_LENGTH+2];
+
+LPCSTR GenSocketSSL::cipherSuite_ [] =
+{
+ "eNULL:DES-CBC3-SHA:RC4-SHA",
+ "DES-CBC3-SHA" ,
+ "eNULL"
+};
+
+// Full pathname storege of the SSL files
+char GenSocketSSL::szKeyFile_ [MAX_PATH]; // private key
+char GenSocketSSL::szCertFile_[MAX_PATH]; // certificate
+char GenSocketSSL::szCaFile_ [MAX_PATH]; // trusted CA List
+
+//////////////////////////////////////////////////////////////////////
+// Construction/Destruction
+//////////////////////////////////////////////////////////////////////
+
+
+//////////////////////////////////////////////////////////////////////
+// Primary methods
+//////////////////////////////////////////////////////////////////////
+
+int GenSocketSSL::tcpReceive (sbyte *pBuf, int BufSize)
+{
+ return ((bEnableSsl_ ? readSsl (pBuf, BufSize)
+ : GenSocket::tcpReceive (pBuf, BufSize)));
+}
+
+
+int GenSocketSSL::tcpSend (sbyte *pBuf, int BufSize)
+{
+ return ((bEnableSsl_ ? writeSsl (pBuf, BufSize)
+ : GenSocket::tcpSend (pBuf, BufSize)));
+}
+
+
+void GenSocketSSL::releaseSocket (bool grace)
+{
+ AM_FUNC ("GenSocketSSL::releaseSocket", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ cleanSsl ();
+ // Context is not deleted upon release of the single socket
+ // High level application should take case
+
+ // for SSL socket: forcibly false so that shutdown is not called
+ // GenSocket::releaseSocket ((bEnableSsl_? false : grace));
+ GenSocket::releaseSocket (grace);
+
+ AM_LEAVE ();
+}
+
+
+void GenSocketSSL::printInfo ()
+{
+ GenSocket::printInfo ();
+
+ if (isSSL())
+ {
+ if (bEnableSsl_)
+ {
+ printf ("SSL is enabled on the socket, encryption is %s.\n",
+ (bEnableEncryption_ ? "enabled" : "disabled") );
+
+ if (bMoreInfo_)
+ {
+ printf ("SSL info: Context %p, BIO %p, connection %p\n",
+ getContext(), pSbio_, pSsl_);
+
+ if (pSsl_)
+ printSession ();
+ else
+ printf ("SSL Connection is not initialized.\n");
+ }
+ }
+ else
+ printf ("SSL is disabled on the socket.\n");
+ }
+}
+
+
+void GenSocketSSL::classPrintInfo ()
+{
+ printf ("SSL Socket class info:\n");
+ printf (" SSL is%s supported.\n", (isSSL()) ? "" : " not");
+
+ if (isSSL())
+ {
+ printf (" Total number of active SSL-enabled sockets = %u\n", count_);
+
+ if (errorCode_ != SSL_NO_ERROR)
+ printf ("Last SSL error recorded %d\n", errorCode_);
+
+#ifdef _AM_DEBUG_
+ if (bMoreInfo_)
+ printf (" Password \"%s\"\n",
+ (szPswd_ && strlen(szPswd_) <= SSL_MAX_PASSWORD_LENGTH)
+ ? szPswd_ : "INVALID");
+#endif // _AM_DEBUG_
+ }
+}
+
+
+// Set password only when it's NOT set and a new password is of valid length
+bool GenSocketSSL::setPassword (LPCSTR lpPswd)
+{
+ int length = (lpPswd) ? strlen (lpPswd) : 0;
+ bool retVal = false;
+
+ if (!isPswdSet() && length > 0 && length <= SSL_MAX_PASSWORD_LENGTH)
+ {
+ strcpy (szPswd_, lpPswd);
+ retVal = true;
+ }
+
+ return (retVal);
+}
+
+
+void GenSocketSSL::resetPassword ()
+{
+ memset (szPswd_, 0, sizeof(szPswd_)) ;
+}
+
+
+//////////////////////////////////////////////////////////////////////
+// Service methods
+//////////////////////////////////////////////////////////////////////
+
+
+//////////////////////////////////////////////////////////////////////
+// Shell Interface
+//////////////////////////////////////////////////////////////////////
+
+void SocDataPrint ()
+{
+ GenSocketSSL::classPrintInfo();
+}
+
diff --git a/data/mnet/Common/socket/src/Makefile b/data/mnet/Common/socket/src/Makefile
new file mode 100644
index 0000000..7dab74a
--- /dev/null
+++ b/data/mnet/Common/socket/src/Makefile
@@ -0,0 +1,61 @@
+##########################################################
+#
+# (c) Copyright Cisco 2000
+# All Rights Reserved
+#
+# Use Examples:
+#
+# Case 1:
+# make all VOB=GP10 -
+# Places .out in VOB/bin directory
+#
+# Case 2:
+# make all VOB=GP10 APPDIR=Host\<Application Name>\<Source Directory> -
+# Places .o file(s) in VOB\$(APPDIR)\bin directory.
+#
+# <Application Name> = Name of Application directory
+# <Source Directory> = application sub directory where the calling
+# Makefile resides.
+#
+# Example: make all VOB=GP10 APPDIR=Host\vxTemplate\src
+#
+#
+# Note: This make file must reference a VOB that
+# has a defs.mk in the top level directory.
+#
+##########################################################
+
+# TOP_OF_VOB must be defined before including l3defs.mk
+TOP_OF_VOB = ..\..
+
+# Name of this App's Directory
+THIS_APP_DIR = socket
+
+VOB2DIR = $(TOP_OF_VOB)\..\$(VOB)
+BINDIR = ..\bin
+
+ifeq ($(APPDIR),)
+ MY_OUTPUT = $(VOB2DIR)\bin\soc.out
+else
+ MY_OUTPUT = $(OBJDIR)\soc_com.out
+endif
+
+include $(VOB2DIR)\l3defs.mk
+
+
+all: $(MY_OUTPUT)
+
+$(MY_OUTPUT): $(MODULE_OBJS)
+ $(LD) -r -o $@.tmp $(MODULE_OBJS)
+ $(NM) $@.tmp | munch > _ctdt.c
+ $(CC) -traditional $(CC_ARCH_SPEC) -c _ctdt.c
+ $(LD) -r -o $@ _ctdt.o $@.tmp
+ $(RM)$(subst /,$(DIRCHAR), _ctdt.c _ctdt.o $@.tmp)
+
+cleanall:
+ @for %f in ($(notdir $(MODULE_OBJS))) do \
+ $(RM) ..\bin\%f
+
+ $(RM) $(MY_OUTPUT)
+
+
diff --git a/data/mnet/Common/socket/src_ssl/GenSocketSSL_lib.cpp b/data/mnet/Common/socket/src_ssl/GenSocketSSL_lib.cpp
new file mode 100644
index 0000000..e29a333
--- /dev/null
+++ b/data/mnet/Common/socket/src_ssl/GenSocketSSL_lib.cpp
@@ -0,0 +1,968 @@
+// *******************************************************************
+//
+// (c) Copyright Cisco Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 2.0
+// Status : Under development
+// File : GenSocketSSL_lib.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 06/20/00
+// Description : Implementation GenSocketSSL class methods
+//
+//
+// *******************************************************************
+
+#include "socket\GenSocketSSL.h"
+#include "CallBackSSL.h"
+
+// maximum depth of the certificates chain to explore
+#define MAX_ALLOWED_CERTIFICATE_DEPTH 10
+
+// the length of the generated RSA key
+#define RSA_KEY_LENGTH 1024
+
+
+// Base names fot the SSL files
+#define SSL_KEY_FILE "key.pem"
+#define SSL_CERT_FILE "cert.pem"
+#define SSL_CA_FILE "ca.pem"
+
+
+//////////////////////////////////////////////////////////////////////
+// Static data
+//////////////////////////////////////////////////////////////////////
+
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ #include "Os\JCMutex.h"
+ static JCMutex socMutex;
+#endif
+
+
+///////////////////////////////////////////////////////////
+// Constructors\destractor
+///////////////////////////////////////////////////////////
+
+
+///////////////////////////////////////////////////////////
+// SSL library setup functions
+///////////////////////////////////////////////////////////
+void GenSocketSSL::initSslLib ()
+{
+ AM_FUNC ("GenSocketSSL::initSslLib", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ // Global system initialization one-per-application
+ if (isSupportSSL() && !bInitLib_)
+ {
+ char rand_seed [] = "this is to make him think that there is some randomness";
+ //int randStat;
+ LPSTR pRoot = NULL;
+ size_t length = 0 ;
+
+ SSL_library_init ();
+
+ RAND_seed ((unsigned char *)rand_seed, sizeof(rand_seed));
+
+ //randStat = RAND_status ();
+
+ // Construct full pathname for the SSL required files
+ pRoot = getenv ("MNET_BASE");
+
+ if (!pRoot || !*pRoot || (strlen (pRoot) > MAX_PATH - 10))
+ {
+ pRoot = DEF_ROOT_DIR;
+ AM_WARNING (("MNET root directory \"MNET_BASE\" is not specified or too long. Use default value.\n"));
+ }
+
+ if (pRoot)
+ length = strlen(pRoot);
+
+ sprintf (szKeyFile_ , "%s%c%s", pRoot, ((length) ? DIR_DELIMITER : '\0'), SSL_KEY_FILE );
+ sprintf (szCertFile_, "%s%c%s", pRoot, ((length) ? DIR_DELIMITER : '\0'), SSL_CERT_FILE);
+ sprintf (szCaFile_ , "%s%c%s", pRoot, ((length) ? DIR_DELIMITER : '\0'), SSL_CA_FILE );
+
+ bInitLib_ = true;
+ }
+
+ AM_LEAVE();
+}
+
+
+///////////////////////////////////////////////////////////
+// SSL context setup functions (one per server\client)
+///////////////////////////////////////////////////////////
+bool GenSocketSSL::initSslContext (SSL_CTX *& pCtx, bool bServer, LPSTR lpPswd)
+{
+ AM_FUNC ("GenSocketSSL::initSslContext", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (pCtx)
+ { // already initialized
+ AM_RETURN (true);
+ }
+
+ if (!isSupportSSL())
+ {
+ AM_RETURN (true);
+ }
+
+ bool retVal = true;
+ int IDContext = 1 ;
+ int iRetVal ;
+ SSL_METHOD *meth ;
+
+ initSslLib ();
+
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ socMutex.take();
+#endif
+
+ if (lpPswd)
+ setPassword (lpPswd);
+
+ // Check that the password is set and of correct value
+ if (!isPswdSet())
+ {
+ setError (SSL_BAD_PASSWORD);
+ AM_WARNING (("initSslContext: bad or missing SSL password\n"));
+ retVal = false;
+ }
+
+ if (retVal)
+ {
+ //meth = (bServer) ? SSLv3_server_method () : SSLv3_client_method ();
+ meth = SSLv3_method ();
+
+ pCtx = SSL_CTX_new (meth);
+ SSL_CTX_set_verify_depth (pCtx, MAX_ALLOWED_CERTIFICATE_DEPTH);
+
+ /* Load the keys and certificates */
+ if (!(SSL_CTX_use_certificate_file (pCtx, (LPSTR)szCertFile_, SSL_FILETYPE_PEM)))
+ {
+ setError (SSL_BAD_USER_CERT);
+ AM_ERROR (("Unable to read certificate file %s\n", szCertFile_));
+ retVal = false;
+ }
+ }
+
+ if (retVal)
+ {
+ SSL_CTX_set_default_passwd_cb (pCtx,
+#ifdef _RSA_SSL_LIB_
+ (FUNCPTR)
+#endif // _RSA_SSL_LIB_
+ password_cb);
+
+ /* load the private key from the file */
+ if (SSL_CTX_use_PrivateKey_file (pCtx, (LPSTR)szKeyFile_, SSL_FILETYPE_PEM))
+ {
+ /* check that the certificate and private key match */
+ if (!SSL_CTX_check_private_key (pCtx))
+ {
+ setError (SSL_BAD_KEY);
+ AM_ERROR (("Private key does not match the user certificate\n"));
+ retVal = false;
+ }
+ }
+ else
+ {
+ setError (SSL_BAD_KEY);
+ AM_ERROR (("Unable to read SSL key file %s\n", szKeyFile_));
+ retVal = false;
+ }
+ }
+
+ if (retVal)
+ {
+ /* Load the CAs we trust*/
+ if (!(SSL_CTX_load_verify_locations (pCtx, (LPSTR)szCaFile_, 0)))
+ {
+ setError (SSL_BAD_CA_ERROR);
+ AM_ERROR (("Unable to read CA list from %s file\n", szCaFile_));
+ retVal = false;
+ }
+ }
+
+ if (retVal)
+ {
+#ifdef _OPEN_SSL_LIB_
+ // very useful
+ SSL_CTX_set_mode (pCtx, SSL_MODE_AUTO_RETRY);
+#endif _OPEN_SSL_LIB_
+
+ if (!(iRetVal = SSL_CTX_set_cipher_list (pCtx,(LPSTR)cipherSuite_[ALLSUITES])) )
+ {
+ setError (SSL_GENERIC_ERROR);
+ AM_ERROR (("Cipher setting failed for the context\n"));
+ retVal = false;
+ }
+ }
+
+#ifdef __SSL_USE_TEMP_KEY__
+ if (retVal && bServer)
+ {
+ // generate context key
+ pRsa_ = RSA_generate_key (RSA_KEY_LENGTH, RSA_F4, NULL, NULL);
+
+ if (pRsa_)
+ {
+ if (!SSL_CTX_set_tmp_rsa (pCtx, pRsa_))
+ {
+ AM_TRACE (("Unable to set temporary key\n"));
+ retVal = false;
+ }
+ }
+ else
+ {
+ AM_TRACE (("Unable to generate temporary key\n"));
+ retVal = false;
+ }
+
+ if (!retVal)
+ {
+ setError (SSL_GEN_ERROR);
+ retVal = false;
+ }
+ }
+#endif // __SSL_USE_TEMP_KEY__
+
+ if (retVal)
+ {
+ SSL_CTX_set_session_id_context (pCtx, (const unsigned char*)&IDContext,
+ sizeof(IDContext) );
+ retVal = true;
+
+ AM_TRACE (("SSL context is initialized\n"));
+ }
+
+ if (!retVal)
+ cleanSslContext (pCtx);
+
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ socMutex.give();
+#endif
+
+ AM_RETURN (retVal);
+}
+
+
+void GenSocketSSL::cleanSslContext (SSL_CTX *& pCtx)
+{
+ AM_FUNC ("GenSocketSSL::cleanSslContext", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isSupportSSL())
+ {
+ if (pCtx)
+ {
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ socMutex.take();
+#endif
+ SSL_CTX_free (pCtx);
+ pCtx = NULL;
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ socMutex.give();
+#endif
+ }
+
+#ifdef __SSL_USE_TEMP_KEY__
+ if (pRsa_)
+ RSA_free (pRsa_);
+#endif // __SSL_USE_TEMP_KEY__
+ }
+}
+
+
+///////////////////////////////////////////////////////////
+// SSL connection setup functions
+///////////////////////////////////////////////////////////
+
+bool GenSocketSSL::initSsl ()
+{
+ bool retVal = false;
+
+ AM_FUNC ("GenSocketSSL::initSsl", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (!isEnableSSL())
+ {
+ retVal = true;
+ }
+ else if (isValid() && isContext())
+ { // Start it for a valid socket under initialized context
+ if (!pSbio_)
+ { // create new socket wrapper
+ AM_DEBUG (("Creating BIO for a socket\n"));
+ pSbio_ = BIO_new_socket (getSocket(), BIO_NOCLOSE);
+ }
+
+ if (pSbio_ && !pSsl_)
+ {
+ AM_DEBUG (("Creating new SSL connection\n"));
+
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ socMutex.take();
+#endif
+ if ((pSsl_ = SSL_new(getContext())) != NULL)
+ {
+ AM_DEBUG (("Set SSL session\n"));
+
+ if (SSL_set_session (pSsl_, NULL))
+ {
+ SSL_set_bio (pSsl_, pSbio_, pSbio_);
+ ++count_;
+ }
+ else
+ {
+ AM_TRACE (("Unable to set SSL session\n"));
+ cleanSsl ();
+ }
+ }
+
+#if defined(__VXWORKS__) && defined (__USE_SSL_LOCK__)
+ socMutex.give();
+#endif
+
+ }
+
+ if (pSsl_ && pSbio_)
+ retVal = true;
+ else
+ {
+ cleanSsl ();
+ AM_WARNING (("Unable to create SSL session\n"));
+ }
+ }
+ else
+ AM_WARNING (("Unable to start SSL handshake.\n"));
+
+ AM_RETURN (retVal);
+}
+
+
+void GenSocketSSL::cleanSsl ()
+{
+ AM_FUNC ("GenSocketSSL::cleanSsl", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isEnableSSL())
+ {
+ if (pSsl_)
+ {
+ SSL_shutdown (pSsl_);
+ SSL_clear (pSsl_);
+ SSL_free (pSsl_);
+ pSsl_ = NULL;
+ pSbio_ = NULL; // Released by the SSL_free() ???
+ --count_;
+ }
+
+ if (!pSbio_)
+ {
+ BIO_free (pSbio_);
+ pSbio_ = NULL;
+ }
+ }
+}
+
+
+
+///////////////////////////////////////////////////////////
+// SSL connect function
+///////////////////////////////////////////////////////////
+
+// SSL Client
+bool GenSocketSSL::connectSsl ()
+{
+ AM_FUNC ("GenSocketSSL::connectSsl", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ bool retVal = false;
+ int stat ;
+ CipherSuite_t suiteType = (bEnableEncryption_ ? DESCBC3SHA : NOSSL);
+
+ if (isEnableSSL())
+ {
+ if (initSsl ())
+ {
+#ifdef _RSA_SSL_LIB_
+ // RSA lib requires to set state explicitly
+ SSL_set_connect_state (pSsl_);
+#endif // _RSA_SSL_LIB_
+
+ if (!SSL_set_cipher_list(pSsl_,(LPSTR)cipherSuite_[suiteType]) )
+ {
+ AM_ERROR (("Set cipher list for socket connection failed\n"));
+ AM_RETURN (retVal);
+ }
+
+ /* Check peer certificate against the local list here.
+ The chain length is automatically checked by SSL when we
+ set the verify depth in the ctx.
+ Check is stoped when trusted certificate is found or
+ when reachingthe maximum specified chain depth. */
+ SSL_CTX_set_verify (getContext() ,
+ SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
+#ifdef _RSA_SSL_LIB_
+ (FUNCPTR)
+#endif // _RSA_SSL_LIB_
+ verify_callback );
+
+ //This is where the handshake really occurs
+ if ((stat = SSL_connect(pSsl_)) > 0)
+ { // normal case
+ // sometimes certificate verificxation error does not prevent TSL session establishment
+ if (verifyCert (SSL_get_verify_result(pSsl_)) == false)
+ {
+ AM_ERROR (("Server [%s] certificate verification has failed\n Cause: %s\n",
+ getIp(getRemoteHostAddress()),
+ getCertError(SSL_get_verify_result(pSsl_)) ));
+ setError (SSL_BAD_PEER_CERT);
+ }
+ else
+ {
+ // connection is extablished, peer's certificate is verified
+ AM_TRACE (("SSL Connection is established to [%s] using ciphering %s\n",
+ getIp(getRemoteHostAddress()) ,
+ SSL_CIPHER_get_name(SSL_get_current_cipher(pSsl_)) ));
+ retVal = true;
+ }
+ }
+ else if (stat == 0)
+ {
+ AM_ERROR (("Server on [%s] closed connection on the socket %d\n",
+ getIp(getRemoteHostAddress()), getSocket() ));
+ }
+ else
+ { // (stat < 0)
+ // connection error. Can't continue anyway
+ switch (SSL_get_error(pSsl_,stat))
+ {
+ case SSL_ERROR_NONE:
+ AM_TRACE (("SSL connection is established on socket %u\n", getSocket() ));
+ retVal = true;
+ break;
+
+ case SSL_ERROR_ZERO_RETURN:
+ // peer shutdown connection
+ AM_ERROR (("Server on [%s] closed connection on the socket %d\n",
+ getIp(getRemoteHostAddress()), getSocket() ));
+ break;
+
+ case SSL_ERROR_WANT_READ:
+ AM_ERROR (("connectSsl: Data needs to be read, problem due to renegotiation\n"));
+ break;
+
+ case SSL_ERROR_WANT_WRITE:
+ AM_ERROR (("connectSsl: Data needs to be written, problem due to renegotiation\n"));
+ break;
+
+ case SSL_ERROR_WANT_X509_LOOKUP:
+ AM_TRACE (("connectSsl: The operation did not complete because an \
+application callback set by SSL_CTX_set_client_cert_cb() \
+has askedto be called again. The TLS/SSL I/O function \
+should becalled again later\n"));
+ break;
+
+ case SSL_ERROR_SYSCALL:
+ AM_TRACE (("SSL system call error on SSL_connect\n"));
+ break;
+
+ case SSL_ERROR_SSL:
+ // General error
+ // check if the peer's certificate is OK
+ // print verification error
+ if (verifyCert(SSL_get_verify_result(pSsl_)) == false)
+ {
+ AM_ERROR (("Server [%s] certificate verification has failed\n Cause: %s\n",
+ getIp(getRemoteHostAddress()),
+ getCertError(SSL_get_verify_result(pSsl_)) ));
+ setError (SSL_BAD_PEER_CERT);
+ }
+ else
+ {
+ AM_TRACE (("General SSL error during on SSL connect\n"));
+ }
+ break;
+
+ default:
+ AM_TRACE (("Unspecified SSL connect error %d\n", stat));
+ break;
+ }
+ }
+ }
+ }
+ else
+ { // SSL is disabled or not supported
+ retVal = true;
+ }
+
+ AM_RETURN (retVal);
+}
+
+
+// SSL server
+bool GenSocketSSL::acceptSsl ()
+{
+ int stat;
+ bool retVal = false;
+
+ AM_FUNC ("GenSocketSSL::acceptSsl", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (!isEnableSSL())
+ {
+ retVal = true;
+ }
+ else if (initSsl ())
+ {
+#ifdef _RSA_SSL_LIB_
+ // SSL_set_accept_state (pSsl_);
+#endif // _RSA_SSL_LIB_
+
+ // accept state is the default one
+
+ /* Check peer certificate against the local list here.
+ The chain length is automatically checked by SSL when we
+ set the verify depth in the ctx.
+ Check is stoped when trusted certificate is found or
+ when reachingthe maximum specified chain depth. */
+ SSL_CTX_set_verify (getContext(), SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
+#ifdef _RSA_SSL_LIB_
+ (FUNCPTR)
+#endif // _RSA_SSL_LIB_
+ verify_callback);
+
+ //This is where the handshake really occurs
+ if ((stat = SSL_accept(pSsl_)) > 0)
+ {
+ if (verifyCert(SSL_get_verify_result(pSsl_)) == false)
+ {
+ AM_ERROR (("Client [%s] certificate verification has failed.\nCause: %s\n",
+ getIp (getRemoteHostAddress()),
+ getCertError (SSL_get_verify_result(pSsl_)) ));
+ setError (SSL_BAD_PEER_CERT);
+ }
+ else
+ {
+ // connection is extablished, peer's certificate is OK
+ AM_TRACE (("SSL Connection is accepted from [%s] using ciphering %s\n",
+ getIp(getRemoteHostAddress()) ,
+ SSL_CIPHER_get_name(SSL_get_current_cipher(pSsl_)) ));
+ retVal = true;
+ }
+ }
+ else if (stat == 0)
+ {
+ AM_ERROR (("Client on [%s] closed connection on the socket %d\n",
+ getIp(getRemoteHostAddress()), getSocket() ));
+ }
+ else if (stat < 0)
+ {
+ switch (SSL_get_error (pSsl_, stat) )
+ {
+ case SSL_ERROR_NONE:
+ AM_TRACE (("SSL connection is accepted on socket %u\n", getSocket() ));
+ retVal = true;
+ break;
+
+ case SSL_ERROR_ZERO_RETURN:
+ AM_ERROR (("Client on [%s] closed connection on the socket %d\n",
+ getIp(getRemoteHostAddress()), getSocket() ));
+ break;
+ break;
+
+ case SSL_ERROR_WANT_READ:
+ AM_ERROR (("acceptSsl: Data needs to be read, problem due to renegotiation\n"));
+ break;
+
+ case SSL_ERROR_WANT_WRITE:
+ AM_ERROR (("acceptSsl: Data needs to be written, problem due to renegotiation\n"));
+ break;
+
+ case SSL_ERROR_WANT_X509_LOOKUP:
+ AM_ERROR (("acceptSsl: The operation did not complete because an \
+application callback set by SSL_CTX_set_client_cert_cb() \
+has asked to be called again. The TLS/SSL I/O function \
+should be called again later\n"));
+ break;
+
+ case SSL_ERROR_SYSCALL:
+ AM_ERROR (("SSL system call error in SSL_accept\n"));
+ break;
+
+ case SSL_ERROR_SSL:
+ // General error
+ // check if the peer's certificate is OK
+ // print verification error
+ if (verifyCert(SSL_get_verify_result(pSsl_)) == false)
+ {
+ AM_ERROR (("Client [%s] certificate verification has failed.\nCause: %s\n",
+ getIp (getRemoteHostAddress()) ,
+ getCertError (SSL_get_verify_result(pSsl_)) ));
+ setError (SSL_BAD_PEER_CERT );
+ }
+ else
+ AM_ERROR (("General SSL error on SSL accept connection\n"));
+ break;
+
+ default:
+ AM_ERROR (("Unspecified SSL accept error %d\n", stat));
+ }
+ }
+ }
+
+ AM_RETURN (retVal);
+}
+
+
+///////////////////////////////////////////////////////////
+// SSL read\write functions
+///////////////////////////////////////////////////////////
+
+int GenSocketSSL::readSsl (sbyte *pBuf, int BufSize)
+{
+ AM_FUNC ("GenSocketSSL::readSsl", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ int msgLen = SOC_STATUS_ERROR;
+ int errCode;
+
+ if (isInitSSL ())
+ {
+ msgLen = SSL_read (pSsl_, pBuf, BufSize);
+
+ if (msgLen <= 0 && (errCode = SSL_get_error(pSsl_,msgLen)) != SSL_ERROR_NONE )
+ {
+ msgLen = SOC_STATUS_ERROR;
+
+ switch (errCode)
+ {
+ case SSL_ERROR_NONE:
+ AM_DEBUG (("readSsl: message received - total length (%d)\n", msgLen));
+ msgLen = SOC_STATUS_OK;
+ break;
+
+ case SSL_ERROR_ZERO_RETURN:
+ AM_TRACE (("readSsl: Client closed connection on socket (%d)\n",
+ getSocket() ));
+ break;
+
+ case SSL_ERROR_SYSCALL:
+ AM_ERROR (("readSsl: Problem in SSL_read,system call error\n"));
+ break;
+
+ case SSL_ERROR_SSL:
+ AM_ERROR (("readSsl: general SSL library error\n"));
+ break;
+
+ case SSL_ERROR_WANT_X509_LOOKUP:
+ AM_ERROR(("readSsl: The operation did not complete because an \
+application callback set by SSL_CTX_set_client_cert_cb() \
+has asked to be called again. The TLS/SSL I/O function \
+should be called again later\n"));
+ break;
+
+ case SSL_ERROR_WANT_READ:
+ AM_ERROR(("readSsl: Data needs to be read, problem due to renegotiation\n"));
+ break;
+
+ default:
+ AM_ERROR (("readSsl: recv error %d on socket (%d)\n",
+ errCode, getSocket() ));
+ }
+ }
+ else
+ {
+ AM_DEBUG (("readSsl: received message [length=%d] on the socket %u\n",
+ msgLen, getSocket() ));
+ AM_HEXDUMP ((ubyte *)pBuf, msgLen);
+ }
+ }
+ else
+ AM_ERROR (("Attempt to read read from uninitialised SSL socket %u\n",
+ getSocket() ));
+
+ AM_RETURN (msgLen);
+}
+
+
+int GenSocketSSL::writeSsl (sbyte *pBuf, int BufSize)
+{
+ AM_FUNC ("GenSocketSSL::writeSsl", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ int msgLen = SOCKET_STATUS_FATAL_SOC_ERR;
+ int errCode;
+
+ if (isInitSSL ())
+ {
+ msgLen = SSL_write (pSsl_, pBuf, BufSize);
+
+ if (msgLen <= 0 && (errCode = SSL_get_error(pSsl_,msgLen)) != SSL_ERROR_NONE)
+ {
+ msgLen = SOCKET_STATUS_FATAL_SOC_ERR;
+
+ switch (errCode)
+ {
+ case SSL_ERROR_NONE:
+ AM_DEBUG (("writeSsl: Sent %d bytes to socket %d\n", msgLen, getSocket() ));
+ msgLen = SOCKET_STATUS_OK;
+ break;
+
+ case SSL_ERROR_ZERO_RETURN:
+ AM_ERROR (("writeSsl: Peer closed connection on socket (%d)\n",
+ getSocket()));
+ break;
+
+ case SSL_ERROR_SYSCALL:
+ AM_ERROR (("writeSsl: System call error\n"));
+ ERR_print_errors_fp (stdout);
+ break;
+
+ case SSL_ERROR_SSL:
+ AM_ERROR (("writeSsl: general SSL library error\n"));
+ break;
+
+ case SSL_ERROR_WANT_X509_LOOKUP:
+ AM_ERROR (("writeSsl: The operation did not complete because an \
+application callback set by SSL_CTX_set_client_cert_cb() \
+has asked to be called again. The TLS/SSL I/O function \
+should be called again later\n"));
+ break;
+
+ case SSL_ERROR_WANT_WRITE:
+ AM_ERROR(("writeSsl: Data needs to be written, problem due to renegotiation\n"));
+ break;
+
+ default:
+ AM_TRACE (("writeSsl: error %d on socket (%d)\n",
+ errCode, getSocket() ));
+ break;
+ }
+ }
+ else
+ {
+ AM_DEBUG (("writeSsl: Sent %d bytes to socket %u\n", msgLen, getSocket() ));
+ msgLen = SOCKET_STATUS_OK;
+ }
+ }
+ else
+ AM_ERROR (("Attempt to read read from uninitialised SSL socket %u\n",
+ getSocket() ));
+
+ if (msgLen == SOCKET_STATUS_FATAL_SOC_ERR)
+ releaseSocket(true);
+
+ AM_RETURN (msgLen);
+}
+
+
+// Define here certificate verification policy
+bool GenSocketSSL::verifyCert (long code)
+{
+ bool retVal = false;
+
+ switch (code)
+ {
+ // no error
+ case X509_V_OK :
+ // minor verification errors
+ case X509_V_ERR_CERT_NOT_YET_VALID :
+ case X509_V_ERR_CERT_HAS_EXPIRED :
+ case X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD:
+ case X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD :
+ case X509_V_ERR_ERROR_IN_CRL_LAST_UPDATE_FIELD:
+ case X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD:
+ retVal = true;
+ break;
+
+#ifdef _OPEN_SSL_LIB_
+
+ // minor verification errors
+ case X509_V_ERR_INVALID_PURPOSE :
+ case X509_V_ERR_SUBJECT_ISSUER_MISMATCH :
+ case X509_V_ERR_AKID_SKID_MISMATCH :
+ case X509_V_ERR_AKID_ISSUER_SERIAL_MISMATCH:
+ case X509_V_ERR_KEYUSAGE_NO_CERTSIGN :
+ retVal = true;
+ break;
+
+ // The following errors considered as critical and will cause a link termination
+ case X509_V_ERR_PATH_LENGTH_EXCEEDED :
+ case X509_V_ERR_INVALID_CA :
+ case X509_V_ERR_CERT_UNTRUSTED :
+ break;
+
+#endif // _OPEN_SSL_LIB_
+
+ case X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT :
+ case X509_V_ERR_CERT_REVOKED :
+ case X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE :
+ case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT :
+ case X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN :
+ case X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE :
+ case X509_V_ERR_UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY:
+ case X509_V_ERR_CERT_SIGNATURE_FAILURE :
+ case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY :
+ default :
+ break;
+ }
+
+ return (retVal);
+}
+
+// Define here certificate verification policy
+LPSTR GenSocketSSL::getCertError (long code)
+{
+
+ static LPSTR verificationErrorList [] =
+ {
+ "Certificate is OK" , // no error
+ "Minor certificate verification error" , // OPENSSL specific errors
+ "Unspecified verification error" ,
+
+ "Certificate is not valid yet" ,
+ "Certificate has expired" ,
+ "Certificate \"Not before\" field is not valid",
+ "Certificate \"Not After\" field is not valid" ,
+ "Certificate Last CRL update field is wrong" ,
+ "Certificate CRL next update field is wrong" ,
+ "Certificate the basic Constraints pathlength parameter has been exceeded",
+ "Certificate purpose invalid" ,
+ "The certificate is untrusted" ,
+ "Invalid CA detected" ,
+ "Certificate is self signed and cannot be found in the list of trusted certificates",
+ "The certificate has been revoked" ,
+ "No signatures could be verified because the chain contains only one certificate\n\
+and it is not self signed" ,
+ "Certificate: Unable to get issuer certificate",
+ "The certificate chain could be built up using the untrusted\n \
+certificates but the root could not be found locally",
+ "Unable to decrypt certificate\'s signature ",
+ "Unable to decode issuer public key ",
+ "Invalid signature found ",
+ "Unable to get issuer certificate locally ",
+ };
+
+ LPSTR retVal = NULL;
+
+ switch (code)
+ {
+ case X509_V_OK:
+ // no error
+ retVal = verificationErrorList[CertNoError];
+ break;
+
+ case X509_V_ERR_CERT_NOT_YET_VALID:
+ retVal = verificationErrorList[CertNotYetValid];
+ break;
+
+ case X509_V_ERR_CERT_HAS_EXPIRED:
+ retVal = verificationErrorList[CertExpired];
+ break;
+
+ case X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD:
+ retVal = verificationErrorList[CertNotBeforeError];
+ break;
+
+ case X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD:
+ retVal = verificationErrorList[CertNotAfterError];
+ break;
+
+ case X509_V_ERR_ERROR_IN_CRL_LAST_UPDATE_FIELD:
+ retVal = verificationErrorList[CertCrlLastUpdateError];
+ break;
+
+ case X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD:
+ retVal = verificationErrorList[CertCrlNextUpdateError];
+ break;
+
+#ifdef _OPEN_SSL_LIB_
+
+ case X509_V_ERR_PATH_LENGTH_EXCEEDED:
+ retVal = verificationErrorList[CertPathLengthExceed];
+ break;
+
+ case X509_V_ERR_INVALID_PURPOSE:
+ retVal = verificationErrorList[CertInvalidPurpose];
+ break;
+
+ case X509_V_ERR_CERT_UNTRUSTED:
+ retVal = verificationErrorList[CertUntrusted];
+ break;
+
+ case X509_V_ERR_SUBJECT_ISSUER_MISMATCH :
+ case X509_V_ERR_AKID_SKID_MISMATCH :
+ case X509_V_ERR_AKID_ISSUER_SERIAL_MISMATCH:
+ case X509_V_ERR_KEYUSAGE_NO_CERTSIGN :
+ // minor verification errors
+ retVal = verificationErrorList[CertMiscError];
+ break;
+
+// The following errors considered as critical and will cause a link termination
+
+ case X509_V_ERR_INVALID_CA:
+ retVal = verificationErrorList[CertInvalidCA];
+ break;
+
+#endif // _OPEN_SSL_LIB_
+
+ case X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT:
+ retVal = verificationErrorList[CertZeroSelfSigned];
+ break;
+
+ case X509_V_ERR_CERT_REVOKED:
+ retVal = verificationErrorList[CertRevoked];
+ break;
+
+ case X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE:
+ retVal = verificationErrorList[CertOneNotSelfSigned];
+ break;
+
+ case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT:
+ retVal = verificationErrorList[CertNoIssuer];
+ break;
+
+ case X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN:
+ retVal = verificationErrorList[CertUntrustedNoRoot];
+ break;
+
+ case X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE:
+ retVal = verificationErrorList[CertUnableDecryptSignature];
+ break;
+
+ case X509_V_ERR_UNABLE_TO_DECODE_ISSUER_PUBLIC_KEY:
+ retVal = verificationErrorList[CertUnableDecodeIssuerKey];
+ break;
+
+ case X509_V_ERR_CERT_SIGNATURE_FAILURE:
+ retVal = verificationErrorList[CertInvalidSignature];
+ break;
+
+ case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY:
+ retVal = verificationErrorList[CertNoIssuerCert];
+ break;
+
+ default:
+ retVal = verificationErrorList[CertUnspecifiedError];
+ break;
+ }
+
+ return (retVal);
+}
+
+
+void GenSocketSSL::printSession ()
+{
+ SSL_SESSION *pSession = SSL_get_session(pSsl_);
+
+ if (pSession)
+ SSL_SESSION_print_fp (stderr, pSession);
+}
+
diff --git a/data/mnet/Common/socket/src_ssl/Makefile b/data/mnet/Common/socket/src_ssl/Makefile
new file mode 100644
index 0000000..f1122b9
--- /dev/null
+++ b/data/mnet/Common/socket/src_ssl/Makefile
@@ -0,0 +1,61 @@
+##########################################################
+#
+# (c) Copyright Cisco 2000
+# All Rights Reserved
+#
+# Use Examples:
+#
+# Case 1:
+# make all VOB=GP10 -
+# Places .out in VOB/bin directory
+#
+# Case 2:
+# make all VOB=GP10 APPDIR=Host\<Application Name>\<Source Directory> -
+# Places .o file(s) in VOB\$(APPDIR)\bin directory.
+#
+# <Application Name> = Name of Application directory
+# <Source Directory> = application sub directory where the calling
+# Makefile resides.
+#
+# Example: make all VOB=GP10 APPDIR=Host\vxTemplate\src
+#
+#
+# Note: This make file must reference a VOB that
+# has a defs.mk in the top level directory.
+#
+##########################################################
+
+# TOP_OF_VOB must be defined before including l3defs.mk
+TOP_OF_VOB = ..\..
+
+# Name of this App's Directory
+THIS_APP_DIR = socket
+
+VOB2DIR = $(TOP_OF_VOB)\..\$(VOB)
+BINDIR = ..\bin
+
+ifeq ($(APPDIR),)
+ MY_OUTPUT = $(VOB2DIR)\bin\soc_ssl_lib.out
+else
+ MY_OUTPUT = $(OBJDIR)\soc_ssl_cmn.out
+endif
+
+include $(VOB2DIR)\l3defs.mk
+
+
+all: $(MY_OUTPUT)
+
+$(MY_OUTPUT): $(MODULE_OBJS)
+ $(LD) -r -o $@.tmp $(MODULE_OBJS)
+ $(NM) $@.tmp | munch > _ctdt.c
+ $(CC) -traditional $(CC_ARCH_SPEC) -c _ctdt.c
+ $(LD) -r -o $@ _ctdt.o $@.tmp
+ $(RM)$(subst /,$(DIRCHAR), _ctdt.c _ctdt.o $@.tmp)
+
+cleanall:
+ @for %f in ($(notdir $(MODULE_OBJS))) do \
+ $(RM) ..\bin\%f
+
+ $(RM) $(MY_OUTPUT)
+
+
diff --git a/data/mnet/Common/socket/src_ssl/ssl_intf.cpp b/data/mnet/Common/socket/src_ssl/ssl_intf.cpp
new file mode 100644
index 0000000..f969a8e
--- /dev/null
+++ b/data/mnet/Common/socket/src_ssl/ssl_intf.cpp
@@ -0,0 +1,235 @@
+// *******************************************************************
+//
+// (c) Copyright Cisco Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 2.0
+// Status : Under development
+// File : ssl_intf.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 06/20/00
+// Description : Implementation of the service functions required by
+// SSL library
+//
+// *******************************************************************
+
+#include "socket\GenSocketSSL.h"
+#include "CallBackSSL.h"
+
+
+// Global variables
+// random key data
+#define PASSWORD_KEY {0xA5,0x30,0x1F,0x3C,0x8D,0x1B,0x39,0xE5}
+
+////////////////////////////////////////////////////////////////
+// Open SSL support functions
+////////////////////////////////////////////////////////////////
+
+#ifdef _OPEN_SSL_LIB_
+// OpenSSL library does not have it
+int isSSL ()
+{
+ return (1);
+}
+#endif // _OPEN_SSL_LIB_
+
+
+// callback functions used by SSL library
+// note OpenSSL allows passing a void user data pointer,and can do a per session check
+// may need to modify RSA source to do that
+// We will use one password for all the sockets on the host
+int password_cb (char *buf, int bufSize, int rwflag
+#ifdef _OPEN_SSL_LIB_
+ , void *pData
+#endif // _OPEN_SSL_LIB_
+ )
+{
+ AM_FUNC ("password_cb", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ int length = 0;
+ LPCSTR pPasswd = GenSocketSSL::getPassword();
+
+ if (pPasswd && (length = strlen(pPasswd)) <= bufSize)
+ strcpy (buf, pPasswd);
+
+ AM_RETURN (length);
+}
+
+
+int verify_callback (int ok, X509_STORE_CTX *pStoreCtx)
+{
+ AM_FUNC ("verify_callback", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ char *s, buf[256] = "";
+
+ // read subject line from the certificate
+ s = X509_NAME_oneline (X509_get_subject_name(pStoreCtx->current_cert), buf, 256);
+
+ if (s == NULL)
+ {
+ if (ok)
+ {
+ AM_TRACE (("Certificate depth=%d %s\n",pStoreCtx->error_depth, buf));
+ }
+ else
+ {
+ AM_WARNING (("Certificate depth=%d error=%d %s\n",
+ pStoreCtx->error_depth, pStoreCtx->error,buf));
+ }
+ }
+
+ if (!ok)
+ { // Certificate got a problem, parse it and decide whether to continue
+ ok = GenSocketSSL::verifyCert (pStoreCtx->error);
+ }
+
+ AM_RETURN (ok);
+}
+
+
+// Encrypt and save password to the specified file
+bool encryptPassword (const char *pwd, const char *filename)
+{
+ int stat ;
+ unsigned idx ;
+ const unsigned blockNum = SSL_MAX_PASSWORD_LENGTH/LENGTH_OF_CBLOCK;
+ des_cblock out [blockNum];
+ des_key_schedule ks ;
+ FILE *fd = NULL;
+ bool retVal = false;
+
+ AM_FUNC ("SocLib: encryptPassword", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isSSL ())
+ {
+ const unsigned char key_data [] = PASSWORD_KEY;
+
+ // Always encode SSL_MAX_PASSWORD_LENGTH bytes
+ if (strlen (pwd) > SSL_MAX_PASSWORD_LENGTH)
+ {
+ AM_WARNING (("SocLib: Provided password is longer than allowed.\n Use first %u characters\n",
+ SSL_MAX_PASSWORD_LENGTH ));
+ }
+
+ if (fd = fopen (filename, "wb"))
+ {
+ memset (out, 0, sizeof(out));
+
+ for (idx = 0; idx < blockNum; idx++)
+ {
+ if ((stat = des_key_sched ((C_Block *)(key_data),ks)) != 0)
+ {
+ AM_TRACE (("SocLib: Key error %d\n", stat));
+ AM_RETURN (retVal);
+ }
+
+ des_ecb_encrypt ((C_Block *)(pwd+idx*LENGTH_OF_CBLOCK), // source
+ (C_Block *)out[idx] , // dest
+ ks, DES_ENCRYPT );
+ }
+
+ unsigned temp = 0;
+
+ if ((temp = fwrite (out, SSL_MAX_PASSWORD_LENGTH, 1, fd)) == 1)
+ {
+ retVal = true;
+ }
+ else
+ {
+ AM_TRACE (("SocLib: Unable to save password file %s\n", filename));
+ }
+
+ fclose (fd);
+ }
+ else
+ {
+ AM_TRACE (("SocLib: Unable to open password file %s\n", filename));
+ }
+ }
+
+ AM_RETURN (retVal);
+}
+
+
+bool decryptPassword (char *pwdout, const char *filename)
+{
+ int stat ,
+ idx ;
+ const unsigned blockNum= SSL_MAX_PASSWORD_LENGTH/LENGTH_OF_CBLOCK;
+ des_cblock in [blockNum];
+ des_key_schedule ks ;
+ FILE *fd = NULL ;
+ bool retVal = false;
+ char passwd [SSL_MAX_PASSWORD_LENGTH+2];
+
+ AM_FUNC ("decryptPassword", SOC_LAYER_ID);
+ AM_ENTER ();
+
+ if (isSSL ())
+ {
+ const unsigned char key_data [] = PASSWORD_KEY;
+
+ if (fd = fopen (filename, "rb"))
+ {
+ memset (passwd, 0, (SSL_MAX_PASSWORD_LENGTH+2));
+
+ // Always encode SSL_MAX_PASSWORD_LENGTH bytes
+ if (fread (in, SSL_MAX_PASSWORD_LENGTH, 1, fd) == 1)
+ {
+ for (idx = 0; idx < blockNum; idx++)
+ { // decrypt it
+ if ((stat = des_key_sched((C_Block *)(key_data), ks)) != 0)
+ {
+ AM_TRACE (("SocLib: Key error %d\n", stat));
+ AM_RETURN (retVal);
+ }
+
+ des_ecb_encrypt ((des_cblock *)in[idx], // source
+ (des_cblock *)(passwd + idx * LENGTH_OF_CBLOCK), // dest
+ ks, DES_DECRYPT );
+ }
+
+ // verify decrypted password
+ if ((stat = strlen (passwd)) != 0 && stat <= SSL_MAX_PASSWORD_LENGTH)
+ {
+ for (idx = 0; idx < stat; idx++)
+ {
+ if (!isprint(passwd[idx]))
+ break;
+ }
+
+ if (idx == stat)
+ { // Password is OK
+ strcpy (pwdout, passwd);
+ retVal = true;
+ }
+ }
+
+ fclose (fd);
+
+ if (!retVal)
+ {
+ AM_TRACE (("Password verification failed\n"));
+ }
+ }
+ else
+ {
+ AM_TRACE (("Invalid password file\n"));
+ }
+ }
+ else
+ {
+ AM_TRACE (("Unable to open password file %s.\n", filename));
+ }
+ }
+
+ AM_RETURN (retVal);
+}
+
diff --git a/data/mnet/Common/socket/src_stub/GenSocketSSL_stub.cpp b/data/mnet/Common/socket/src_stub/GenSocketSSL_stub.cpp
new file mode 100644
index 0000000..4c1c819
--- /dev/null
+++ b/data/mnet/Common/socket/src_stub/GenSocketSSL_stub.cpp
@@ -0,0 +1,95 @@
+// *******************************************************************
+//
+// (c) Copyright CISCO Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 1.0
+// File : GenSocketSSL.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 05/17/01
+// Description : stub implementation of the GenSocketSSL class methods
+//
+// *******************************************************************
+
+#include "socket\GenSocketSSL.h"
+
+//////////////////////////////////////////////////////////////////////
+// function stubs
+//////////////////////////////////////////////////////////////////////
+
+
+bool GenSocketSSL::initSslContext (SSL_CTX *& pCtx, bool bServer, LPSTR lpPswd)
+{
+ return (false);
+}
+
+
+void GenSocketSSL::cleanSslContext (SSL_CTX *& pCtx)
+{
+ return ;
+}
+
+
+bool GenSocketSSL::initSsl ()
+{
+ return (false);
+}
+
+void GenSocketSSL::cleanSsl ()
+{
+ pSsl_ = NULL;
+ pSbio_ = NULL;
+}
+
+
+bool GenSocketSSL::acceptSsl ()
+{
+ return (false);
+}
+
+
+bool GenSocketSSL::connectSsl ()
+{
+ return (false);
+}
+
+
+void GenSocketSSL::initSslLib ()
+{
+ return ;
+}
+
+
+int GenSocketSSL::readSsl (sbyte *pBuf, int BufSize)
+{
+ return (SOC_STATUS_ERROR);
+}
+
+
+int GenSocketSSL::writeSsl (sbyte *pBuf, int BufSize)
+{
+ return (SOC_STATUS_ERROR);
+}
+
+
+void GenSocketSSL::printSession ()
+{
+ ;
+}
+
+
+bool encryptPassword (const char *pwd, const char *filename)
+{
+ return (false);
+}
+
+
+bool decryptPassword (char *pwdout, const char *filename)
+{
+ return (false);
+}
+
diff --git a/data/mnet/Common/socket/src_stub/Makefile b/data/mnet/Common/socket/src_stub/Makefile
new file mode 100644
index 0000000..038097c
--- /dev/null
+++ b/data/mnet/Common/socket/src_stub/Makefile
@@ -0,0 +1,61 @@
+##########################################################
+#
+# (c) Copyright Cisco 2000
+# All Rights Reserved
+#
+# Use Examples:
+#
+# Case 1:
+# make all VOB=GP10 -
+# Places .out in VOB/bin directory
+#
+# Case 2:
+# make all VOB=GP10 APPDIR=Host\<Application Name>\<Source Directory> -
+# Places .o file(s) in VOB\$(APPDIR)\bin directory.
+#
+# <Application Name> = Name of Application directory
+# <Source Directory> = application sub directory where the calling
+# Makefile resides.
+#
+# Example: make all VOB=GP10 APPDIR=Host\vxTemplate\src
+#
+#
+# Note: This make file must reference a VOB that
+# has a defs.mk in the top level directory.
+#
+##########################################################
+
+# TOP_OF_VOB must be defined before including l3defs.mk
+TOP_OF_VOB = ..\..
+
+# Name of this App's Directory
+THIS_APP_DIR = socket
+
+VOB2DIR = $(TOP_OF_VOB)\..\$(VOB)
+BINDIR = ..\bin
+
+ifeq ($(APPDIR),)
+ MY_OUTPUT = $(VOB2DIR)\bin\soc_ssl.out
+else
+ MY_OUTPUT = $(OBJDIR)\soc_ssl_cmn.out
+endif
+
+include $(VOB2DIR)\l3defs.mk
+
+
+all: $(MY_OUTPUT)
+
+$(MY_OUTPUT): $(MODULE_OBJS)
+ $(LD) -r -o $@.tmp $(MODULE_OBJS)
+ $(NM) $@.tmp | munch > _ctdt.c
+ $(CC) -traditional $(CC_ARCH_SPEC) -c _ctdt.c
+ $(LD) -r -o $@ _ctdt.o $@.tmp
+ $(RM)$(subst /,$(DIRCHAR), _ctdt.c _ctdt.o $@.tmp)
+
+cleanall:
+ @for %f in ($(notdir $(MODULE_OBJS))) do \
+ $(RM) ..\bin\%f
+
+ $(RM) $(MY_OUTPUT)
+
+
diff --git a/data/mnet/Common/socket/src_stub/ssl_intf.cpp b/data/mnet/Common/socket/src_stub/ssl_intf.cpp
new file mode 100644
index 0000000..260cdae
--- /dev/null
+++ b/data/mnet/Common/socket/src_stub/ssl_intf.cpp
@@ -0,0 +1,23 @@
+// *******************************************************************
+//
+// (c) Copyright CISCO Systems, Inc 2000
+// All Rights Reserved
+//
+// *******************************************************************
+
+// *******************************************************************
+//
+// Version : 1.0
+// File : ssl_intf.cpp
+// Author(s) : Igal Gutkin
+// Create Date : 05/17/01
+// Description : SSL library interface module stub
+//
+// *******************************************************************
+
+#include "socket\SslIntf.h"
+
+int isSSL ()
+{
+ return (0);
+}