Files
cdev-1.7.2n/extensions/cdevGenericServer/lib/cdevSocketStream.cc
2022-12-13 12:44:04 +01:00

178 lines
4.6 KiB
C++
Executable File

#include "cdevSocketStream.h"
// *****************************************************************************
// * cdevSocketStream::cdevSocketStream :
// * Constructor for the cdevSocketStream class. Only serves to initialize
// * the readRetryCount variable.
// *****************************************************************************
cdevSocketStream::cdevSocketStream ( void )
{
}
// *****************************************************************************
// * cdevSocketStream::send :
// * Send an n byte message to the connected socket.
// *****************************************************************************
ssize_t cdevSocketStream::send(const void *buf, size_t n, int flags) const
{
int retval;
if((retval = ::send(getHandle(), (const char *) buf, n, flags))<=0)
{
int errCode = GetSocketErrno();
if(errCode==EAGAIN || errCode==EWOULDBLOCK) retval = 0;
}
return retval;
}
// *****************************************************************************
// * cdevSocketStream::send_n :
// * This method will transmit an n byte message to a connected socket,
// * waiting until all data has been transmitted or an error occurs.
// *****************************************************************************
ssize_t cdevSocketStream::send_n(const void *buf, size_t n, int flags) const
{
ssize_t amntsent = 0;
int result = 0;
while(amntsent<(ssize_t)n && result>=0)
{
if((result = ::send(getHandle(), (const char *)buf+amntsent, n-amntsent, flags))<=0)
{
int errCode = GetSocketErrno();
if(errCode==EAGAIN || errCode==EWOULDBLOCK) result = 0;
else result = -1;
}
else amntsent+=result;
}
return (amntsent>=(ssize_t)n)?amntsent:-1;
}
// *****************************************************************************
// * cdevSocketStream::recv :
// * Recv an n byte message from the connected socket.
// *****************************************************************************
ssize_t cdevSocketStream::recv(void *buf, size_t n, int flags)
{
int retval = 0;
if((retval = ::recv(getHandle(), (char *)buf, n, flags))<=0)
{
int errCode = GetSocketErrno();
if(errCode==EAGAIN || errCode==EWOULDBLOCK) retval = 0;
}
return retval;
}
// *****************************************************************************
// * cdevSocketStream::recv_n :
// * This method will receive an n byte message from a connected socket,
// * waiting until all data has been received or an error occurs.
// *****************************************************************************
ssize_t cdevSocketStream::recv_n(void *buf, size_t n, int flags)
{
ssize_t amntrecv = 0;
int result = 0;
while(amntrecv < (ssize_t)n)
{
if((result = ::recv(getHandle(), (char *)buf+amntrecv, n-amntrecv, flags)) < 0)
{
return -1;
}
else if (result == 0)
break;
else amntrecv+=result;
}
return amntrecv;
}
// *****************************************************************************
// * cdevSocketStream::closeReader :
// * Shut down just the reading end of a cdevSocket.
// *****************************************************************************
int cdevSocketStream::closeReader(void)
{
return ::shutdown(getHandle(), 0);
}
// *****************************************************************************
// * cdevSocketStream::closeWriter :
// * Shut down just the writing end of a cdevSocket.
// *****************************************************************************
int cdevSocketStream::closeWriter(void)
{
return ::shutdown(getHandle(), 1);
}
int cdevSocketStream::getBlockingSemantics ( void ) const
{
return O_NONBLOCK;
}
int cdevSocketStream::getRcvLowWaterMark ( void ) const
{
return 0;
}
int cdevSocketStream::getRcvBufferSize ( void ) const
{
return 56000;
}
int cdevSocketStream::getSndLowWaterMark ( void ) const
{
return 16000;
}
int cdevSocketStream::getSndBufferSize ( void ) const
{
return 56000;
}
int cdevSocketStream::configureHandle ( void )
{
int retval = 0;
int parm = 1;
if(getBlockingSemantics()==O_NONBLOCK && setFlags(O_NONBLOCK)==-1)
{
retval = -1;
}
setOption(IPPROTO_TCP, TCP_NODELAY, &parm, sizeof(parm));
if((parm = getRcvBufferSize())>0)
{
setOption(SOL_SOCKET, SO_RCVBUF, &parm, sizeof(parm));
}
#ifndef __linux
if((parm = getRcvLowWaterMark())>0)
{
setOption(SOL_SOCKET, SO_RCVLOWAT, &parm, sizeof(parm));
}
#endif
if((parm = getSndBufferSize())>0)
{
setOption(SOL_SOCKET, SO_SNDBUF, &parm, sizeof(parm));
}
#ifndef __linux
if((parm = getSndLowWaterMark())>0)
{
setOption(SOL_SOCKET, SO_SNDLOWAT, &parm, sizeof(parm));
}
#endif
return retval;
}