rsrv: ignore CA client version older than v4.4
RSRV ignore search and version messages from CA minor versions older than 4.
This commit is contained in:
@@ -28,7 +28,8 @@
|
||||
#define CA_VERSION_STRING( MINOR_REVISION ) \
|
||||
( capStrOfX ( CA_MAJOR_PROTOCOL_REVISION ) "." capStrOfX ( MINOR_REVISION ) )
|
||||
#define CA_UKN_MINOR_VERSION 0u /* unknown minor version */
|
||||
#if CA_MAJOR_PROTOCOL_REVISION == 4u
|
||||
#define CA_MINIMUM_SUPPORTED_VERSION 4u
|
||||
# define CA_VSUPPORTED(MINOR) ((MINOR)>=CA_MINIMUM_SUPPORTED_VERSION)
|
||||
# define CA_V41(MINOR) ((MINOR)>=1u)
|
||||
# define CA_V42(MINOR) ((MINOR)>=2u)
|
||||
# define CA_V43(MINOR) ((MINOR)>=3u)
|
||||
@@ -42,35 +43,6 @@
|
||||
# define CA_V411(MINOR) ((MINOR)>=11u) /* sequence numbers in UDP version command */
|
||||
# define CA_V412(MINOR) ((MINOR)>=12u) /* TCP-based search requests */
|
||||
# define CA_V413(MINOR) ((MINOR)>=13u) /* Allow zero length in requests. */
|
||||
#elif CA_MAJOR_PROTOCOL_REVISION > 4u
|
||||
# define CA_V41(MINOR) ( 1u )
|
||||
# define CA_V42(MINOR) ( 1u )
|
||||
# define CA_V43(MINOR) ( 1u )
|
||||
# define CA_V44(MINOR) ( 1u )
|
||||
# define CA_V45(MINOR) ( 1u )
|
||||
# define CA_V46(MINOR) ( 1u )
|
||||
# define CA_V47(MINOR) ( 1u )
|
||||
# define CA_V48(MINOR) ( 1u )
|
||||
# define CA_V49(MINOR) ( 1u )
|
||||
# define CA_V410(MINOR) ( 1u )
|
||||
# define CA_V411(MINOR) ( 1u )
|
||||
# define CA_V412(MINOR) ( 1u )
|
||||
# define CA_V413(MINOR) ( 1u )
|
||||
#else
|
||||
# define CA_V41(MINOR) ( 0u )
|
||||
# define CA_V42(MINOR) ( 0u )
|
||||
# define CA_V43(MINOR) ( 0u )
|
||||
# define CA_V44(MINOR) ( 0u )
|
||||
# define CA_V45(MINOR) ( 0u )
|
||||
# define CA_V46(MINOR) ( 0u )
|
||||
# define CA_V47(MINOR) ( 0u )
|
||||
# define CA_V48(MINOR) ( 0u )
|
||||
# define CA_V49(MINOR) ( 0u )
|
||||
# define CA_V410(MINOR) ( 0u )
|
||||
# define CA_V411(MINOR) ( 0u )
|
||||
# define CA_V412(MINOR) ( 0u )
|
||||
# define CA_V413(MINOR) ( 0u )
|
||||
#endif
|
||||
|
||||
/*
|
||||
* These port numbers are only used if the CA repeater and
|
||||
|
||||
@@ -360,6 +360,13 @@ static int tcp_version_action ( caHdrLargeArray *mp, void *pPayload,
|
||||
unsigned epicsPriorityNew;
|
||||
unsigned epicsPrioritySelf;
|
||||
|
||||
client->minor_version_number = mp->m_count;
|
||||
|
||||
if (!CA_VSUPPORTED(mp->m_count)) {
|
||||
DLOG ( 2, ( "CAS: Ignore version from unsupported client %u\n", mp->m_count ) );
|
||||
return RSRV_ERROR;
|
||||
}
|
||||
|
||||
if ( mp->m_dataType > CA_PROTO_PRIORITY_MAX ) {
|
||||
return RSRV_ERROR;
|
||||
}
|
||||
@@ -2197,8 +2204,14 @@ static void search_fail_reply ( caHdrLargeArray *mp, void *pPayload, struct clie
|
||||
*/
|
||||
static int udp_version_action ( caHdrLargeArray *mp, void *pPayload, struct client *client )
|
||||
{
|
||||
client->minor_version_number = mp->m_count;
|
||||
|
||||
if (!CA_VSUPPORTED(mp->m_count)) {
|
||||
DLOG ( 2, ( "CAS: Ignore version from unsupported client %u\n", mp->m_count ) );
|
||||
return RSRV_ERROR;
|
||||
}
|
||||
|
||||
if ( mp->m_count != 0 ) {
|
||||
client->minor_version_number = mp->m_count;
|
||||
if ( CA_V411 ( mp->m_count ) ) {
|
||||
client->seqNoOfReq = mp->m_cid;
|
||||
}
|
||||
@@ -2248,6 +2261,11 @@ static int search_reply_udp ( caHdrLargeArray *mp, void *pPayload, struct client
|
||||
size_t spaceNeeded;
|
||||
size_t reasonableMonitorSpace = 10;
|
||||
|
||||
if (!CA_VSUPPORTED(mp->m_count)) {
|
||||
DLOG ( 2, ( "CAS: Ignore search from unsupported client %u\n", mp->m_count ) );
|
||||
return RSRV_ERROR;
|
||||
}
|
||||
|
||||
/*
|
||||
* check the sanity of the message
|
||||
*/
|
||||
@@ -2359,6 +2377,11 @@ static int search_reply_tcp (
|
||||
size_t spaceNeeded;
|
||||
size_t reasonableMonitorSpace = 10;
|
||||
|
||||
if (!CA_VSUPPORTED(mp->m_count)) {
|
||||
DLOG ( 2, ( "CAS: Ignore search from unsupported client %u\n", mp->m_count ) );
|
||||
return RSRV_ERROR;
|
||||
}
|
||||
|
||||
/*
|
||||
* check the sanity of the message
|
||||
*/
|
||||
@@ -2542,15 +2565,37 @@ int camessage ( struct client *client )
|
||||
pBody = ( void * ) ( mp + 1 );
|
||||
}
|
||||
|
||||
/* ignore deprecated clients, but let newer clients identify themselves. */
|
||||
if (msg.m_cmmd!=CA_PROTO_VERSION && !CA_VSUPPORTED(client->minor_version_number)) {
|
||||
if (client->proto==IPPROTO_TCP) {
|
||||
/* log and error for too old clients, but keep the connection open to avoid a
|
||||
* re-connect loop.
|
||||
*/
|
||||
send_err ( &msg, ECA_DEFUNCT, client,
|
||||
"CAS: Client version %u too old", client->minor_version_number );
|
||||
log_header ( "CAS: Client version too old",
|
||||
client, &msg, 0, nmsg );
|
||||
client->recvBytesToDrain = msgsize - bytes_left;
|
||||
client->recv.stk = client->recv.cnt;
|
||||
status = RSRV_OK;
|
||||
} else {
|
||||
/* silently ignore UDP from old clients */
|
||||
status = RSRV_ERROR;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* disconnect clients that dont send 8 byte
|
||||
* aligned payloads
|
||||
*/
|
||||
if ( msgsize & 0x7 ) {
|
||||
send_err ( &msg, ECA_INTERNAL, client,
|
||||
"CAS: Missaligned protocol rejected" );
|
||||
log_header ( "CAS: Missaligned protocol rejected",
|
||||
client, &msg, 0, nmsg );
|
||||
if (client->proto==IPPROTO_TCP) {
|
||||
send_err ( &msg, ECA_INTERNAL, client,
|
||||
"CAS: Missaligned protocol rejected" );
|
||||
log_header ( "CAS: Missaligned protocol rejected",
|
||||
client, &msg, 0, nmsg );
|
||||
}
|
||||
status = RSRV_ERROR;
|
||||
break;
|
||||
}
|
||||
@@ -2564,11 +2609,13 @@ int camessage ( struct client *client )
|
||||
if ( msgsize > client->recv.maxstk ) {
|
||||
casExpandRecvBuffer ( client, msgsize );
|
||||
if ( msgsize > client->recv.maxstk ) {
|
||||
send_err ( &msg, ECA_TOLARGE, client,
|
||||
"CAS: Server unable to load large request message. Max bytes=%lu",
|
||||
rsrvSizeofLargeBufTCP );
|
||||
log_header ( "CAS: server unable to load large request message",
|
||||
client, &msg, 0, nmsg );
|
||||
if (client->proto==IPPROTO_TCP) {
|
||||
send_err ( &msg, ECA_TOLARGE, client,
|
||||
"CAS: Server unable to load large request message. Max bytes=%lu",
|
||||
rsrvSizeofLargeBufTCP );
|
||||
log_header ( "CAS: server unable to load large request message",
|
||||
client, &msg, 0, nmsg );
|
||||
}
|
||||
assert ( client->recv.cnt <= client->recv.maxstk );
|
||||
assert ( msgsize >= bytes_left );
|
||||
client->recvBytesToDrain = msgsize - bytes_left;
|
||||
|
||||
@@ -197,7 +197,7 @@ void cast_server(void *pParm)
|
||||
client->recv.stk = 0ul;
|
||||
epicsTimeGetCurrent(&client->time_at_last_recv);
|
||||
|
||||
client->minor_version_number = 0;
|
||||
client->minor_version_number = CA_UKN_MINOR_VERSION;
|
||||
client->seqNoOfReq = 0;
|
||||
|
||||
/*
|
||||
|
||||
Reference in New Issue
Block a user