From 3047681d4107d843be8d6943bc943a3d21307280 Mon Sep 17 00:00:00 2001 From: Andrew Johnson Date: Wed, 15 Jan 2025 15:29:50 -0600 Subject: [PATCH] Add a class method to cac for creating sockets When EPICS_CAC_AVOID_LOW_FDS exists in the environment, all client socket fds are renumbered to above FD_SETSIZE, allowing the client library to play nice with applications like the CA gateway which use select() for their own sockets. --- modules/ca/src/client/ca_client_context.cpp | 2 +- modules/ca/src/client/cac.cpp | 15 +++++++++++++++ modules/ca/src/client/cac.h | 2 ++ modules/ca/src/client/tcpiiu.cpp | 2 +- modules/ca/src/client/udpiiu.cpp | 4 ++-- 5 files changed, 21 insertions(+), 4 deletions(-) diff --git a/modules/ca/src/client/ca_client_context.cpp b/modules/ca/src/client/ca_client_context.cpp index 1e830fd080..e9155119c2 100644 --- a/modules/ca/src/client/ca_client_context.cpp +++ b/modules/ca/src/client/ca_client_context.cpp @@ -87,7 +87,7 @@ ca_client_context::ca_client_context ( bool enablePreemptiveCallback ) : } } - this->sock = epicsSocketCreate ( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); + this->sock = cac::SocketCreate ( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); if ( this->sock == INVALID_SOCKET ) { char sockErrBuf[64]; epicsSocketConvertErrnoToString ( sockErrBuf, sizeof ( sockErrBuf ) ); diff --git a/modules/ca/src/client/cac.cpp b/modules/ca/src/client/cac.cpp index fd641ad214..c47cc83495 100644 --- a/modules/ca/src/client/cac.cpp +++ b/modules/ca/src/client/cac.cpp @@ -385,6 +385,21 @@ unsigned cac::highestPriorityLevelBelow ( unsigned priority ) return belowPriority; } +SOCKET cac::SocketCreate ( + int domain, + int type, + int protocol ) +{ + SOCKET sock = epicsSocketCreate ( domain, type, protocol ); +#ifdef HAS_SOCK_RENUMBER + static bool renumber = getenv ( "EPICS_CAC_AVOID_LOW_FDS" ); + if ( renumber ) { + sock = epicsSocketRenumber ( sock ); + } +#endif + return sock; +} + // // set the push pending flag on all virtual circuits // diff --git a/modules/ca/src/client/cac.h b/modules/ca/src/client/cac.h index 79dcbaa9be..795052b55d 100644 --- a/modules/ca/src/client/cac.h +++ b/modules/ca/src/client/cac.h @@ -204,6 +204,8 @@ class cac : const char * pLocalHostName (); + static SOCKET SocketCreate ( int domain, int type, int protocol ); + private: epicsSingleton < localHostName > :: reference _refLocalHostName; chronIntIdResTable < nciu > chanTable; diff --git a/modules/ca/src/client/tcpiiu.cpp b/modules/ca/src/client/tcpiiu.cpp index 30f6fad174..9d4472f485 100644 --- a/modules/ca/src/client/tcpiiu.cpp +++ b/modules/ca/src/client/tcpiiu.cpp @@ -717,7 +717,7 @@ tcpiiu::tcpiiu ( if(!pCurData) throw std::bad_alloc(); - this->sock = epicsSocketCreate ( AF_INET, SOCK_STREAM, IPPROTO_TCP ); + this->sock = cac::SocketCreate ( AF_INET, SOCK_STREAM, IPPROTO_TCP ); if ( this->sock == INVALID_SOCKET ) { freeListFree(this->cacRef.tcpSmallRecvBufFreeList, this->pCurData); char sockErrBuf[64]; diff --git a/modules/ca/src/client/udpiiu.cpp b/modules/ca/src/client/udpiiu.cpp index d36e2c5b48..9d6e436973 100644 --- a/modules/ca/src/client/udpiiu.cpp +++ b/modules/ca/src/client/udpiiu.cpp @@ -168,7 +168,7 @@ udpiiu::udpiiu ( envGetInetPortConfigParam ( &EPICS_CA_REPEATER_PORT, static_cast (CA_REPEATER_PORT) ); - this->sock = epicsSocketCreate ( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); + this->sock = cac::SocketCreate ( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); if ( this->sock == INVALID_SOCKET ) { char sockErrBuf[64]; epicsSocketConvertErrnoToString ( @@ -594,7 +594,7 @@ void epicsStdCall caStartRepeaterIfNotInstalled ( unsigned repeaterPort ) return; } - tmpSock = epicsSocketCreate ( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); + tmpSock = cac::SocketCreate ( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); if ( tmpSock != INVALID_SOCKET ) { ca_uint16_t port = static_cast < ca_uint16_t > ( repeaterPort ); memset ( (char *) &bd, 0, sizeof ( bd ) );