diff --git a/src/ca/access.c b/src/ca/access.c index aacc3502f..4e28f6758 100644 --- a/src/ca/access.c +++ b/src/ca/access.c @@ -556,6 +556,13 @@ int ca_task_initialize() /* init sync group facility */ ca_sg_init(); + /* + * init broadcasted serch counters + */ + ca_static->ca_conn_n_tries = 0; + ca_static->ca_conn_next_retry = CA_CURRENT_TIME; + ca_static->ca_conn_retry_delay = CA_RECAST_DELAY; + ellInit(&ca_static->ca_iiuList); ellInit(&ca_static->ca_ioeventlist); ellInit(&ca_static->ca_free_event_list); @@ -1457,9 +1464,12 @@ int ca_build_and_connect chix->piiu = piiuCast; ellAdd(&piiuCast->chidlist, &chix->node); - piiuCast->nconn_tries = 0; - piiuCast->next_retry = CA_CURRENT_TIME; - piiuCast->retry_delay = CA_RECAST_DELAY; + /* + * reset broadcasted search counters + */ + ca_static->ca_conn_n_tries = 0; + ca_static->ca_conn_next_retry = CA_CURRENT_TIME; + ca_static->ca_conn_retry_delay = CA_RECAST_DELAY; UNLOCK; @@ -2315,11 +2325,22 @@ chid chan; void (*pfunc)(); #endif /*__STDC__*/ { + struct access_rights_handler_args args; + INITCHK; LOOSECHIXCHK(chan); chan->access_rights_func = pfunc; + /* + * make certain that it runs at least once + */ + if(chan->state == cs_conn){ + args.chid = chan; + args.ar = chan->ar; + (*chan->access_rights_func)(args); + } + return ECA_NORMAL; } @@ -3297,20 +3318,20 @@ int lineno; "CA.Client.Diagnostic..............................................\n"); ca_printf( -" Message: [%s]\n", ca_message_text[CA_EXTRACT_MSG_NO(ca_status)]); +" Message: \"%s\"\n", ca_message_text[CA_EXTRACT_MSG_NO(ca_status)]); if(message) ca_printf( -" Severity: [%s] Context: [%s]\n", +" Severity: \"%s\" Context: \"%s\"\n", severity[CA_EXTRACT_SEVERITY(ca_status)], message); else ca_printf( -" Severity: [%s]\n", severity[CA_EXTRACT_SEVERITY(ca_status)]); +" Severity: %s\n", severity[CA_EXTRACT_SEVERITY(ca_status)]); if(pfilenm){ ca_printf( -" Source File: [%s] Line Number: [%d]\n", +" Source File: %s Line Number: %d\n", pfilenm, lineno); } diff --git a/src/ca/acctst.c b/src/ca/acctst.c index 3eaedb54f..92889af27 100644 --- a/src/ca/acctst.c +++ b/src/ca/acctst.c @@ -29,6 +29,7 @@ void null_event(struct event_handler_args args); void write_event(struct event_handler_args args); void conn(struct connection_handler_args args); void conn_cb(struct event_handler_args args); +void accessSecurity_cb(struct access_rights_handler_args args); #else /*__STDC__*/ int doacctst(); void test_sync_groups(); @@ -37,6 +38,7 @@ void null_event(); void write_event(); void conn(); void conn_cb(); +void accessSecurity_cb(); #endif /*__STDC__*/ @@ -122,10 +124,10 @@ char *pname; for (i = 0; i < 10; i++) { status = ca_array_build(pname, /* channel ASCII name */ - DBR_GR_FLOAT, /* fetch external type */ - NUM, /* array element cnt */ + TYPENOTCONN,/* fetch external type*/ + 0, /* array element cnt */ &chix3, /* ptr to chid */ - ptr /* pointer to recv buf */ + NULL /* pointer to recv buf */ ); SEVCHK(status, NULL); @@ -179,13 +181,17 @@ char *pname; status = ca_array_build( pname, /* channel ASCII name */ - DBR_GR_FLOAT, /* fetch external type */ - NUM, /* array element cnt */ + TYPENOTCONN, /* fetch external type */ + 0, /* array element cnt */ &chix3, /* ptr to chid */ - ptr /* pointer to recv buf */ + NULL /* pointer to recv buf */ ); SEVCHK(status, NULL); + status = ca_replace_access_rights_event(chix3, accessSecurity_cb); + /* + * verify clear before connect + */ SEVCHK(ca_build_and_connect( pname, TYPENOTCONN, @@ -194,6 +200,17 @@ char *pname; NULL, CONN_ROUTINE, NULL), NULL); + SEVCHK(ca_clear_channel(chix4), NULL); + SEVCHK(ca_build_and_connect( + pname, + TYPENOTCONN, + 0, + &chix4, + NULL, + CONN_ROUTINE, + NULL), NULL); + status = ca_replace_access_rights_event(chix4, accessSecurity_cb); + SEVCHK(status, NULL); SEVCHK(ca_build_and_connect( pname, TYPENOTCONN, @@ -202,6 +219,8 @@ char *pname; NULL, CONN_ROUTINE, NULL), NULL); + status = ca_replace_access_rights_event(chix2, accessSecurity_cb); + SEVCHK(status, NULL); SEVCHK(ca_build_and_connect( pname, TYPENOTCONN, @@ -210,10 +229,8 @@ char *pname; NULL, CONN_ROUTINE, NULL), NULL); -#if 0 - status = ca_replace_access_rights_event(chix1, ar_event); - SEVCHK(status,NULL); -#endif + status = ca_replace_access_rights_event(chix1, accessSecurity_cb); + SEVCHK(status, NULL); status = ca_pend_io(1000.0); SEVCHK(status, NULL); @@ -641,3 +658,23 @@ CA_SYNC_GID gid; SEVCHK(status, NULL); } } + + +/* + * accessSecurity_cb() + */ +#ifdef __STDC__ +void accessSecurity_cb(struct access_rights_handler_args args) +#else /*__STDC__*/ +void accessSecurity_cb(args) +struct access_rights_handler_args args; +#endif /*__STDC__*/ +{ + + printf( "%s on %s has %s/%s access\n", + ca_name(args.chid), + ca_host_name(args.chid), + ca_read_access(args.chid)?"read":"noread", + ca_write_access(args.chid)?"write":"nowrite"); +} + diff --git a/src/ca/conn.c b/src/ca/conn.c index 6031d70ec..96e72cf20 100644 --- a/src/ca/conn.c +++ b/src/ca/conn.c @@ -24,6 +24,7 @@ /* (now handled by the send needed flag) */ /* .10 102093 joh improved broadcast schedualing for */ /* reconnects */ +/* .11 042994 joh removed client side heart beat */ /* */ /*_begin */ /************************************************************************/ @@ -38,7 +39,7 @@ /************************************************************************/ /*_end */ -static char *sccsId = "$Id$\t$Date$"; +static char *sccsId = "$Id$"; #include "iocinf.h" @@ -61,63 +62,30 @@ int silent; struct ioc_in_use *piiu; chid chix; unsigned int retry_cnt = 0; - unsigned int keepalive_cnt = 0; unsigned int retry_cnt_no_handler = 0; ca_time current; current = time(NULL); - /* - * issue connection heartbeat - */ - LOCK; - for( piiu = (struct ioc_in_use *) iiuList.node.next; - piiu; - piiu = (struct ioc_in_use *) piiu->node.next){ - - if(piiu == piiuCast || !piiu->conn_up){ - continue; - } - - if(piiu->next_retry == CA_CURRENT_TIME){ - piiu->next_retry = current + CA_RETRY_PERIOD; - continue; - } - - if(piiu->next_retry > current) - continue; - - /* - * periodic keepalive on unused channels - */ - - /* - * reset of delay to the next keepalive - * occurs when the message is sent - */ - noop_msg(piiu); - keepalive_cnt++; - } - UNLOCK; - if(!piiuCast){ return; } - if(piiuCast->next_retry == CA_CURRENT_TIME){ - piiuCast->next_retry = current + piiuCast->retry_delay; + if(ca_static->ca_conn_next_retry == CA_CURRENT_TIME){ + ca_static->ca_conn_next_retry = + current + ca_static->ca_conn_retry_delay; } - if(piiuCast->next_retry > current) + if(ca_static->ca_conn_next_retry > current) return; - if(piiuCast->nconn_tries++ > MAXCONNTRIES) + if(ca_static->ca_conn_n_tries++ > MAXCONNTRIES) return; - if(piiuCast->retry_delayretry_delay += piiuCast->retry_delay; + if(ca_static->ca_conn_retry_delayca_conn_retry_delay += ca_static->ca_conn_retry_delay; } - piiuCast->next_retry = current + piiuCast->retry_delay; + ca_static->ca_conn_next_retry = current + ca_static->ca_conn_retry_delay; LOCK; for( chix = (chid) piiuCast->chidlist.node.next; @@ -313,20 +281,25 @@ struct in_addr *pnet_addr; next = currentTime + delay; - if(piiuCast->next_retry>next){ - piiuCast->next_retry = next; + if(ca_static->ca_conn_next_retry>next){ + ca_static->ca_conn_next_retry = next; } - piiuCast->retry_delay = CA_RECAST_DELAY; - piiuCast->nconn_tries = 0; + ca_static->ca_conn_retry_delay = CA_RECAST_DELAY; + ca_static->ca_conn_n_tries = 0; } -#ifdef DEBUG - ca_printf("CAC: ", - piiuCast->retry_delay); -#ifdef UNIX - fflush(stdout); -#endif -#endif +# ifdef DEBUG + + ca_printf( + "CAC: ", + ca_static->ca_conn_retry_delay); + +# ifdef UNIX + fflush(stdout); +# endif + +# endif + UNLOCK; } diff --git a/src/ca/if_depen.c b/src/ca/if_depen.c index 526fba8e2..76b182cb8 100644 --- a/src/ca/if_depen.c +++ b/src/ca/if_depen.c @@ -77,7 +77,7 @@ struct sockaddr_in *plcladdr; ifconf.ifc_req = ifreq; status = socket_ioctl(s, SIOCGIFCONF, (int)&ifconf); if (status < 0 || ifconf.ifc_len == 0) { - ca_printf("CAC: ioctl failed %d\n", MYERRNO); + ca_printf("CAC: ioctl failed %s\n", strerror(MYERRNO)); ifconf.ifc_len = 0; } diff --git a/src/ca/iocinf.c b/src/ca/iocinf.c index e8d4e0635..4cdedbe57 100644 --- a/src/ca/iocinf.c +++ b/src/ca/iocinf.c @@ -209,8 +209,6 @@ int net_proto; return ECA_ALLOCMEM; } - piiu->send_retry_count = SEND_RETRY_COUNT_INIT; - piiu->active = FALSE; piiu->pcas = ca_static; @@ -219,13 +217,6 @@ int net_proto; piiu->sock_proto = net_proto; - /* - * reset the delay to the next retry or keepalive - */ - piiu->next_retry = CA_CURRENT_TIME; - piiu->retry_delay = CA_RECAST_DELAY; - piiu->nconn_tries = 0; - /* * set the minor version ukn until the server * updates the client @@ -382,7 +373,7 @@ int net_proto; &pNode->destAddr.sockAddr, sizeof(pNode->destAddr.sockAddr)); if(status < 0){ - ca_printf("CAC: no conn errno %d\n", MYERRNO); + ca_printf("CAC: no conn err=\"%s\"\n", strerror(MYERRNO)); status = socket_close(sock); if(status<0){ SEVCHK(ECA_INTERNAL,NULL); @@ -445,7 +436,8 @@ int net_proto; sizeof(true)); if(status<0){ free(piiu); - ca_printf("CAC: sso (errno=%d)\n",MYERRNO); + ca_printf("CAC: sso (err=\"%s\")\n", + strerror(MYERRNO)); status = socket_close(sock); if(status < 0){ SEVCHK(ECA_INTERNAL,NULL); @@ -466,7 +458,7 @@ int net_proto; (struct sockaddr *) &saddr, sizeof(saddr)); if(status<0){ - ca_printf("CAC: bind (errno=%d)\n",MYERRNO); + ca_printf("CAC: bind (err=%s)\n",strerror(MYERRNO)); ca_signal(ECA_INTERNAL,"bind failed"); } @@ -645,8 +637,8 @@ struct ioc_in_use *piiu; MYERRNO != ENOBUFS && MYERRNO != EINTR){ ca_printf( - "CAC: error on socket send() %d\n", - MYERRNO); + "CAC: error on socket send() %s\n", + strerror(MYERRNO)); } piiu->conn_up = FALSE; @@ -714,13 +706,6 @@ struct ioc_in_use *piiu; if(status>=0){ assert(status<=sendCnt); - /* - * reset the delay to the next keepalive - */ - if(status){ - piiu->next_retry = time(NULL) + CA_RETRY_PERIOD; - } - CAC_RING_BUFFER_READ_ADVANCE(&piiu->send, status); sendCnt = cacRingBufferReadSize(&piiu->send, FALSE); @@ -743,8 +728,8 @@ struct ioc_in_use *piiu; MYERRNO != ECONNRESET && MYERRNO != ETIMEDOUT){ ca_printf( - "CAC: error on socket send() %d\n", - MYERRNO); + "CAC: error on socket send() %s\n", + strerror(MYERRNO)); } piiu->conn_up = FALSE; @@ -906,8 +891,8 @@ int flags; char text[255]; sprintf( text, - "CAC: unexpected select fail: %d", - MYERRNO); + "CAC: unexpected select fail: %s", + strerror(MYERRNO)); SEVCHK(ECA_INTERNAL,text); } } @@ -1020,8 +1005,9 @@ struct ioc_in_use *piiu; if( MYERRNO != EPIPE && MYERRNO != ECONNRESET && MYERRNO != ETIMEDOUT){ - ca_printf( "CAC: unexpected recv error (errno=%d)\n", - MYERRNO); + ca_printf( + "CAC: unexpected recv error (err=%s)\n", + strerror(MYERRNO)); } piiu->conn_up = FALSE; UNLOCK; @@ -1040,11 +1026,10 @@ struct ioc_in_use *piiu; CAC_RING_BUFFER_WRITE_ADVANCE(&piiu->recv, status); /* - * reset the delay to the next keepalive + * Record the time whenever we receive a message + * from this IOC */ - if(piiu != piiuCast){ - piiu->next_retry = time(NULL) + CA_RETRY_PERIOD; - } + piiu->timeAtLastRecv = time(NULL); UNLOCK; return; @@ -1153,7 +1138,7 @@ struct ioc_in_use *piiu; UNLOCK; return; } - ca_printf("Unexpected UDP failure %d\n", MYERRNO); + ca_printf("Unexpected UDP failure %s\n", strerror(MYERRNO)); piiu->conn_up = FALSE; } else if(status > 0){ diff --git a/src/ca/iocinf.h b/src/ca/iocinf.h index eaef093d8..4f3071d34 100644 --- a/src/ca/iocinf.h +++ b/src/ca/iocinf.h @@ -297,6 +297,7 @@ typedef struct ioc_in_use{ void *pCurData; unsigned long curDataMax; unsigned long curDataBytes; + ca_time timeAtLastRecv; #ifdef __STDC__ void (*sendBytes)(struct ioc_in_use *); void (*recvBytes)(struct ioc_in_use *); @@ -311,10 +312,6 @@ typedef struct ioc_in_use{ short conn_up; /* boolean: T-conn /F-disconn */ short send_needed; /* CA needs a send */ char host_name_str[32]; - unsigned nconn_tries; - unsigned send_retry_count; - ca_time next_retry; - ca_time retry_delay; #ifdef VMS /* for qio ASTs */ unsigned long putConvertBufSize; @@ -354,13 +351,18 @@ struct ca_static{ unsigned short ca_post_msg_active; short ca_repeater_contacted; unsigned short ca_send_msg_active; +#if 0 struct in_addr ca_castaddr; +#endif char ca_sprintf_buf[256]; BUCKET *ca_pBucket; unsigned long ca_nextBucketId; bhe *ca_beaconHash[BHT_INET_ADDR_MASK+1]; char *ca_pUserName; char *ca_pHostName; + unsigned ca_conn_n_tries; + ca_time ca_conn_next_retry; + ca_time ca_conn_retry_delay; #if defined(UNIX) || defined(vxWorks) fd_set ca_readch; fd_set ca_writech; diff --git a/src/ca/iocmsg.h b/src/ca/iocmsg.h index 3cbbc82aa..285eeb452 100644 --- a/src/ca/iocmsg.h +++ b/src/ca/iocmsg.h @@ -19,13 +19,14 @@ #define __IOCMSG__ -static char *iocmsghSccsId = "$Id$ CA version 4.1"; +static char *iocmsghSccsId = "$Id$ CA version 4.2"; /* TCP/UDP port number (bumped each protocol change) */ #define CA_PROTOCOL_VERSION 4 -#define CA_MINOR_VERSION 1 +#define CA_MINOR_VERSION 2 #define CA_UKN_MINOR_VERSION 0 /* unknown minor version */ -#define CA_V41(MAJOR,MINOR) ( ((MAJOR)==4&&(MINOR)>0) || (MAJOR)>4 ) +#define CA_V41(MAJOR,MINOR) ( ((MAJOR)==4&&(MINOR)>=1) || (MAJOR)>4 ) +#define CA_V42(MAJOR,MINOR) ( ((MAJOR)==4&&(MINOR)>=2) || (MAJOR)>4 ) #define CA_PORT_BASE IPPORT_USERRESERVED + 56 #define CA_SERVER_PORT (CA_PORT_BASE+CA_PROTOCOL_VERSION*2) #define CA_CLIENT_PORT (CA_PORT_BASE+CA_PROTOCOL_VERSION*2+1) diff --git a/src/ca/posix_depen.c b/src/ca/posix_depen.c index 34ec8f90e..1e91e691c 100644 --- a/src/ca/posix_depen.c +++ b/src/ca/posix_depen.c @@ -34,13 +34,13 @@ /* * ANSI includes */ -#include "assert.h" -#include "string.h" -#include "stdlib.h" +#include +#include +#include -#include "unistd.h" -#include "pwd.h" -#include "sys/param.h" +#include +#include +#include #include "iocinf.h" diff --git a/src/ca/repeater.c b/src/ca/repeater.c index 71f7694ff..a842816eb 100644 --- a/src/ca/repeater.c +++ b/src/ca/repeater.c @@ -60,7 +60,7 @@ * */ -static char *sccsId = "$Id$\t$Date$"; +static char *sccsId = "$Id$"; #include "iocinf.h" @@ -125,8 +125,8 @@ int ca_repeater() status = bind(sock, (struct sockaddr *)&bd, sizeof(bd)); if(status<0){ if(MYERRNO != EADDRINUSE){ - ca_printf("CA Repeater: unexpected bind fail %d\n", - MYERRNO); + ca_printf("CA Repeater: unexpected bind fail %s\n", + strerror(MYERRNO)); } socket_close(sock); exit(0); @@ -178,8 +178,8 @@ int ca_repeater() (struct sockaddr *)&pclient->from, sizeof pclient->from); if(status < 0){ - ca_printf("CA Repeater: fanout err %d\n", - MYERRNO); + ca_printf("CA Repeater: fanout err %s\n", + strerror(MYERRNO)); } #ifdef DEBUG ca_printf("Sent\n"); @@ -228,13 +228,13 @@ int ca_repeater() (struct sockaddr *)&from, /* back to sender */ sizeof from); if(status != sizeof confirm){ - ca_printf("CA Repeater: confirm err %d\n", - MYERRNO); + ca_printf("CA Repeater: confirm err %s\n", + strerror(MYERRNO)); } } else{ - ca_printf("CA Repeater: recv err %d\n", - MYERRNO); + ca_printf("CA Repeater: recv err %s\n", + strerror(MYERRNO)); } /* remove any dead wood prior to pending */ @@ -278,8 +278,8 @@ int sock; if(MYERRNO == EADDRINUSE) present = TRUE; else{ - ca_printf("CA Repeater: client cleanup err %d\n", - MYERRNO); + ca_printf("CA Repeater: client cleanup err %s\n", + strerror(MYERRNO)); } } diff --git a/src/ca/service.c b/src/ca/service.c index ae18db309..2e4d27387 100644 --- a/src/ca/service.c +++ b/src/ca/service.c @@ -77,7 +77,7 @@ static char *sccsId = "$Id$"; LOCAL void reconnect_channel( IIU *piiu, -struct in_addr *pnet_addr +chid chan ); LOCAL int cacMsg( @@ -85,10 +85,16 @@ struct ioc_in_use *piiu, struct in_addr *pnet_addr ); +LOCAL void perform_claim_channel( +IIU *piiu, +struct in_addr *pnet_addr +); + #else -LOCAL void reconnect_channel(); LOCAL int cacMsg(); +LOCAL void perform_claim_channel(); +LOCAL void reconnect_channel(); #endif @@ -152,14 +158,15 @@ unsigned long blockSize; piiu->curMsg.m_type = ntohs(piiu->curMsg.m_type); piiu->curMsg.m_count = ntohs(piiu->curMsg.m_count); #if 0 -printf("%s Cmd=%3d Type=%3d Count=%4d Size=%4d Avail=%8x Cid=%6d\n", - piiu->host_name_str, - piiu->curMsg.m_cmmd, - piiu->curMsg.m_type, - piiu->curMsg.m_count, - piiu->curMsg.m_postsize, - piiu->curMsg.m_available, - piiu->curMsg.m_cid); + ca_printf("%s Cmd=%3d Type=%3d Count=%4d Size=%4d", + piiu->host_name_str, + piiu->curMsg.m_cmmd, + piiu->curMsg.m_type, + piiu->curMsg.m_count, + piiu->curMsg.m_postsize); + ca_printf(" Avail=%8x Cid=%6d\n", + piiu->curMsg.m_available, + piiu->curMsg.m_cid); #endif } @@ -507,7 +514,7 @@ struct in_addr *pnet_addr; } case IOC_SEARCH: case IOC_BUILD: - reconnect_channel(piiu, pnet_addr); + perform_claim_channel(piiu, pnet_addr); break; case IOC_READ_SYNC: @@ -671,6 +678,17 @@ struct in_addr *pnet_addr; } break; } + case IOC_CLAIM_CIU: + { + chid chan; + + LOCK; + chan = bucketLookupItem(pBucket, piiu->curMsg.m_cid); + UNLOCK; + assert(chan); + reconnect_channel(piiu, chan); + break; + } default: ca_printf("CAC: post_msg(): Corrupt cmd in msg %x\n", piiu->curMsg.m_cmmd); @@ -684,29 +702,27 @@ struct in_addr *pnet_addr; /* * - * reconnect_channel() + * perform_claim_channel() * */ #ifdef __STDC__ -LOCAL void reconnect_channel( +LOCAL void perform_claim_channel( IIU *piiu, struct in_addr *pnet_addr ) #else -LOCAL void reconnect_channel(piiu,pnet_addr) +LOCAL void perform_claim_channel(piiu,pnet_addr) IIU *piiu; struct in_addr *pnet_addr; #endif { + int v42; char rej[64]; chid chan; - evid pevent; int status; - enum channel_state prev_cs; IIU *allocpiiu; IIU *chpiiu; unsigned short *pMinorVersion; - int v41; /* * ignore broadcast replies for deleted channels @@ -723,7 +739,6 @@ struct in_addr *pnet_addr; } chpiiu = chan->piiu; - if(!chpiiu){ ca_printf("cast reply to local channel??\n"); UNLOCK; @@ -741,18 +756,13 @@ struct in_addr *pnet_addr; /* * Ignore duplicate search replies */ - if (chan->state == cs_conn) { + if (chpiiu != piiuCast) { caAddrNode *pNode; pNode = (caAddrNode *) chpiiu->destAddr.node.next; assert(pNode); - if (pNode->destAddr.inetAddr.sin_addr.s_addr == + if (pNode->destAddr.inetAddr.sin_addr.s_addr != pnet_addr->s_addr) { - ca_printf(" "); -# ifdef UNIX - fflush(stdout); -# endif - } else { caHostFromInetAddr(pnet_addr,rej,sizeof(rej)); sprintf( @@ -777,23 +787,6 @@ struct in_addr *pnet_addr; return; } - /* Update rmt chid fields from extmsg fields */ - chan->type = piiu->curMsg.m_type; - chan->count = piiu->curMsg.m_count; - chan->id.sid = piiu->curMsg.m_cid; - - /* - * Assume that we have access once connected briefly - * until the server is able to tell us the correct - * state for backwards compatibility. - * - * Their access rights call back does not get - * called for the first time until the information - * arrives however. - */ - chan->ar.read_access = TRUE; - chan->ar.write_access = TRUE; - /* * Starting with CA V4.1 the minor version number * is appended to the end of each search reply. @@ -807,32 +800,80 @@ struct in_addr *pnet_addr; allocpiiu->minor_version_number = CA_UKN_MINOR_VERSION; } + ellDelete(&chpiiu->chidlist, &chan->node); + chan->piiu = allocpiiu; + ellAdd(&allocpiiu->chidlist, &chan->node); + + /* + * If this is the first channel to be + * added to this IIU then communicate + * the client's name to the server. + * (CA V4.1 or higher) + */ + if(ellCount(&allocpiiu->chidlist)==1){ + issue_identify_client(allocpiiu); + issue_client_host_name(allocpiiu); + } + + /* + * claim the resource in the IOC + * over TCP so problems with duplicate UDP port + * after reboot go away + */ + chan->id.sid = piiu->curMsg.m_cid; + issue_claim_channel(allocpiiu, chan); + + /* + * Assume that we have access once connected briefly + * until the server is able to tell us the correct + * state for backwards compatibility. + * + * Their access rights call back does not get + * called for the first time until the information + * arrives however. + */ + chan->ar.read_access = TRUE; + chan->ar.write_access = TRUE; + + UNLOCK; + + v42 = CA_V42( + CA_PROTOCOL_VERSION, + allocpiiu->minor_version_number); + if(!v42){ + reconnect_channel(piiu, chan); + } +} + + +/* + * reconnect_channel() + */ +#ifdef __STDC__ +LOCAL void reconnect_channel( +IIU *piiu, +chid chan +) +#else +LOCAL void reconnect_channel(piiu,chan) +IIU *piiu; +chid chan; +#endif +{ + evid pevent; + enum channel_state prev_cs; + int v41; + + LOCK; + v41 = CA_V41( CA_PROTOCOL_VERSION, - allocpiiu->minor_version_number); + ((IIU *)chan->piiu)->minor_version_number); - if(chpiiu != allocpiiu){ + /* Update rmt chid fields from extmsg fields */ + chan->type = piiu->curMsg.m_type; + chan->count = piiu->curMsg.m_count; - /* - * The address changed (or was found for the first time) - */ - if(chpiiu != piiuCast) - ca_signal(ECA_NEWADDR, (char *)(chan+1)); - ellDelete(&chpiiu->chidlist, &chan->node); - chan->piiu = chpiiu = allocpiiu; - ellAdd(&chpiiu->chidlist, &chan->node); - - /* - * If this is the first channel to be - * added to this IIU then communicate - * the client's name to the server. - * (CA V4.1 or higher) - */ - if(ellCount(&chpiiu->chidlist)==1){ - issue_identify_client(chpiiu); - issue_client_host_name(chpiiu); - } - } /* * set state to cs_conn before caling @@ -842,13 +883,6 @@ struct in_addr *pnet_addr; prev_cs = chan->state; chan->state = cs_conn; - /* - * claim the resource in the IOC - * over TCP so problems with duplicate UDP port - * after reboot go away - */ - issue_claim_channel(chpiiu, chan); - /* * NOTE: monitor and callback reissue must occur prior to calling * their connection routine otherwise they could be requested twice. @@ -876,6 +910,20 @@ struct in_addr *pnet_addr; UNLOCK; + /* + * if less than v4.1 then the server will never + * send access rights and we know that there + * will always be access and call their call back + * here + */ + if (chan->access_rights_func && !v41) { + struct access_rights_handler_args args; + + args.chid = chan; + args.ar = chan->ar; + (*chan->access_rights_func) (args); + } + if(chan->connection_func){ struct connection_handler_args args; @@ -890,19 +938,6 @@ struct in_addr *pnet_addr; CLRPENDRECV(TRUE); } - /* - * if less than v4.1 then the server will never - * send access rights so we know that there - * will always be access and call their call back - * here - */ - if (chan->access_rights_func && !v41) { - struct access_rights_handler_args args; - - args.chid = chan; - args.ar = chan->ar; - (*chan->access_rights_func) (args); - } UNLOCK; } diff --git a/src/ca/vms_depen.c b/src/ca/vms_depen.c index efada2262..ce4ecd460 100644 --- a/src/ca/vms_depen.c +++ b/src/ca/vms_depen.c @@ -34,12 +34,16 @@ /* * ANSI includes */ -#include "assert.h" -#include "string.h" -#include "stdLib.h" +#include +#include +#include -#include "stsdef.h" -#include "ssdef.h" +/* + * VMS includes + */ +#include +#include +#include #include "iocinf.h" @@ -60,21 +64,26 @@ char *localUserName() short item_code; void *pBuf; void *pRetSize; - unsigned long end_of_list; - }item_list; + }item_list[3]; int length; char pName[8]; /* the size of VMS account names */ short nameLength; char *psrc; char *pdest; int status; + int jobType; + int jobTypeSize; char *pTmp; - item_list.buffer_length = sizeof(pName); - item_list.item_code = JPI$ACCOUNT; /* fetch the account name */ - item_list.pBuf = pName; - item_list.pRetSize = &nameLength; - item_list.end_of_list = NULL; + item_list[0].buffer_length = sizeof(pName); + item_list[0].item_code = JPI$_ACCOUNT; /* fetch the account name */ + item_list[0].pBuf = pName; + item_list[0].pRetSize = &nameLength; + item_list[1].buffer_length = sizeof(jobtype); + item_list[1].item_code = JPI$_JOBTYPE; /* fetch the account name */ + item_list[1].pBuf = &jobType; + item_list[1].pRetSize = &jobTypeSize; + item_list[2].buffer_length = 0; status = sys$getjpiw( NULL, @@ -90,7 +99,7 @@ char *localUserName() psrc = pName; length = 0; - while(psrc<&pName[sizeof(pName)] && *psrc != ' '){ + while(psrc<&pName[nameLength] && !isspace(*psrc)){ length++; psrc++; } @@ -102,6 +111,14 @@ char *localUserName() strncpy(pTmp, pName, length); pTmp[length] = '\0'; + /* + * test for remote login + */ + if(jobTypeSize == sizeof(jobtype)){ + if(jobType != JPI$K_LOCAL){ + } + } + return pTmp; } diff --git a/src/ca/vxWorks_depen.c b/src/ca/vxWorks_depen.c index 8982d1dce..ad7ab6ab1 100644 --- a/src/ca/vxWorks_depen.c +++ b/src/ca/vxWorks_depen.c @@ -111,6 +111,16 @@ int tid; return status; } + /* + * just return success if they have already done + * a ca import for this task + */ + pcas = (struct ca_static *) + taskVarGet(taskIdSelf(), (int *)&ca_static); + if (pcas != (struct ca_static *) ERROR){ + return ECA_NORMAL; + } + ptviu = calloc(1, sizeof(*ptviu)); if(!ptviu){ return ECA_ALLOCMEM; diff --git a/src/db/dbEvent.c b/src/db/dbEvent.c index bf4f4a5cb..6f733f32a 100644 --- a/src/db/dbEvent.c +++ b/src/db/dbEvent.c @@ -133,9 +133,9 @@ FASTUNLOCK(&(RECPTR)->mlok); int db_event_list(char *name) { struct db_addr addr; - int status; - struct event_block *pevent; - register struct dbCommon *precord; + int status; + struct event_block *pevent; + struct dbCommon *precord; status = db_name_to_addr(name, &addr); if(status==ERROR) @@ -179,7 +179,7 @@ int db_event_list(char *name) */ struct event_user *db_init_events(void) { - register struct event_user *evuser; + struct event_user *evuser; evuser = (struct event_user *) calloc(1, sizeof(*evuser)); if(!evuser) @@ -263,9 +263,9 @@ unsigned int select, struct event_block *pevent /* ptr to event blk (not required) */ ) { - register struct dbCommon *precord; - register struct event_que *ev_que; - register struct event_que *tmp_que; + struct dbCommon *precord; + struct event_que *ev_que; + struct event_que *tmp_que; /* (MDA) in LANL stuff, this used to taskSuspend if invalid address in new code, the mechanism to help do this checking has been removed @@ -329,12 +329,70 @@ struct event_block *pevent /* ptr to event blk (not required) */ pevent->valque = FALSE; LOCKREC(precord); - ellAdd((ELLLIST*)&precord->mlis, (ELLNODE*)pevent); + ellAdd(&precord->mlis, &pevent->node); UNLOCKREC(precord); return OK; } + +/* + * db_event_enable() + */ +int db_event_enable(struct event_block *pevent) +{ + struct dbCommon *precord; + int status; + + precord = (struct dbCommon *) pevent->paddr->precord; + + LOCKREC(precord); + /* + * dont let a misplaced event corrupt the queue + */ + status = ellFind(&precord->mlis, &pevent->node); + if(status == ERROR){ + ellAdd(&precord->mlis, &pevent->node); + } + UNLOCKREC(precord); + + if(status != ERROR){ + return ERROR; + } + else{ + return OK; + } +} + + +/* + * db_event_disable() + */ +int db_event_disable(struct event_block *pevent) +{ + struct dbCommon *precord; + int status; + + precord = (struct dbCommon *) pevent->paddr->precord; + + LOCKREC(precord); + /* + * dont let a misplaced event corrupt the queue + */ + status = ellFind(&precord->mlis, &pevent->node); + if(status == OK){ + ellDelete(&precord->mlis, &pevent->node); + } + UNLOCKREC(precord); + + if(status != OK){ + return ERROR; + } + else{ + return OK; + } +} + /* * DB_CANCEL_EVENT() @@ -364,8 +422,6 @@ int db_cancel_event(struct event_block *pevent) if(status!=ERROR) ellDelete((ELLLIST*)&precord->mlis, (ELLNODE*)pevent); UNLOCKREC(precord); - if(status == ERROR) - return ERROR; /* * Flush the event que so we know event block not left in use. This @@ -510,10 +566,10 @@ int db_post_extra_labor(struct event_user *evuser) */ int db_post_single_event(struct event_block *pevent) { - register struct event_que *ev_que = pevent->ev_que; - int success = FALSE; - struct dbCommon *precord; - register unsigned int putix; + struct event_que *ev_que = pevent->ev_que; + int success = FALSE; + struct dbCommon *precord; + unsigned int putix; precord = (struct dbCommon *) pevent->paddr->precord; @@ -572,9 +628,9 @@ union native_value *pvalue, unsigned int select ) { - register struct event_block *event; - register struct event_que *ev_que; - register unsigned int putix; + struct event_block *event; + struct event_que *ev_que; + unsigned int putix; if (precord->mlis.count == 0) return OK; /* no monitors set */ @@ -825,10 +881,10 @@ int init_func_arg */ LOCAL int event_read(struct event_que *ev_que) { - register struct event_block *event; - register unsigned int getix; - register unsigned int nextgetix; - db_field_log *pfl; + struct event_block *event; + unsigned int getix; + unsigned int nextgetix; + db_field_log *pfl; /* diff --git a/src/rsrv/camessage.c b/src/rsrv/camessage.c index 303c5cac7..cccfac78b 100644 --- a/src/rsrv/camessage.c +++ b/src/rsrv/camessage.c @@ -52,6 +52,9 @@ static char *sccsId = "$Id$"; #include +#include +#include +#include #include #include @@ -61,14 +64,13 @@ static char *sccsId = "$Id$"; #include #include #include -#include -#include #include #include -#include +#include #include +#include static struct extmsg nill_msg; @@ -105,7 +107,8 @@ LOCAL void send_err( struct extmsg *curp, int status, struct client *client, -char *footnote +char *footnote, + ... ); LOCAL void log_header( @@ -118,11 +121,16 @@ struct extmsg *mp, struct client *client ); -LOCAL void logBadId( -struct client *client, -struct extmsg *mp +LOCAL void logBadIdWithFileAndLineno( +struct client *client, +struct extmsg *mp, +char *pFileName, +unsigned lineno ); +#define logBadId(CLIENT, MP)\ +logBadIdWithFileAndLineno(CLIENT, MP, __FILE__, __LINE__) + LOCAL struct channel_in_use *MPTOPCIU( struct extmsg *mp ); @@ -169,6 +177,10 @@ struct client *client, struct event_ext *pevext ); +LOCAL void access_rights_reply( +struct channel_in_use *pciu +); + LOCAL unsigned long bucketID; @@ -430,7 +442,7 @@ struct client *client asDbGetAsl(&pciu->addr), client->pUserName, client->pHostName); - if(status){ + if(status != 0 && status != S_asLib_asNotActive){ UNLOCK_CLIENT(prsrv_cast_client); free_client(client); exit(0); @@ -489,7 +501,7 @@ struct client *client asDbGetAsl(&pciu->addr), client->pUserName, client->pHostName); - if(status){ + if(status != 0 && status != S_asLib_asNotActive){ UNLOCK_CLIENT(prsrv_cast_client); free_client(client); exit(0); @@ -509,6 +521,7 @@ struct extmsg *mp, struct client *client ) { + int v42; int status; struct channel_in_use *pciu; @@ -534,6 +547,16 @@ struct client *client exit(0); } + /* + * remove channel in use block from + * the UDP client where it could time + * out and place it on the client + * who is claiming it + */ + ellDelete( + &prsrv_cast_client->addrq, + &pciu->node); + UNLOCK_CLIENT(prsrv_cast_client); /* * Any other client attachment is a severe error @@ -554,31 +577,28 @@ struct client *client /* * set up access security for this channel */ - status = asChangeClient( - pciu->asClientPVT, + status = asAddClient( + &pciu->asClientPVT, + asDbGetMemberPvt(&pciu->addr), asDbGetAsl(&pciu->addr), client->pUserName, client->pHostName); - if(status){ - UNLOCK_CLIENT(prsrv_cast_client); + if(status != 0 && status != S_asLib_asNotActive){ + LOCK_CLIENT(client); + send_err(mp, ECA_ALLOCMEM, client, "No room for security table"); + UNLOCK_CLIENT(client); free_client(client); exit(0); } /* - * remove channel in use block from - * the UDP client where it could time - * out and place it on the client - * who is claiming it + * store ptr to channel in use block + * in access security private */ - ellDelete( - &prsrv_cast_client->addrq, - &pciu->node); - UNLOCK_CLIENT(prsrv_cast_client); - - pciu->client = client; + asPutClientPvt(pciu->asClientPVT, pciu); LOCK_CLIENT(client); + pciu->client = client; ellAdd(&client->addrq, &pciu->node); UNLOCK_CLIENT(client); @@ -590,13 +610,42 @@ struct client *client */ pciu->client->minor_version_number = mp->m_available; + v42 = CA_V42( + CA_PROTOCOL_VERSION, + client->minor_version_number); + /* * register for asynch updates of access rights changes * (only after the lock is released, we are added to * the correct client, and the clients version is * known) */ - asRegisterClientCallback(pciu->asClientPVT, casAccessRightsCB); + status = asRegisterClientCallback(pciu->asClientPVT, casAccessRightsCB); + if(status == S_asLib_asNotActive){ + /* + * force the initial update + */ + access_rights_reply(pciu); + } + else{ + assert(status==0); + } + + if(v42){ + struct extmsg *claim_reply; + + LOCK_CLIENT(client); + claim_reply = (struct extmsg *) ALLOC_MSG(client, 0); + assert (claim_reply); + + *claim_reply = nill_msg; + claim_reply->m_cmmd = IOC_CLAIM_CIU; + claim_reply->m_type = pciu->addr.field_type; + claim_reply->m_count = pciu->addr.no_elements; + claim_reply->m_cid = pciu->cid; + END_MSG(client); + UNLOCK_CLIENT(client); + } } @@ -960,15 +1009,6 @@ struct client *client ellAdd( &pciu->eventq, &pevext->node); UNLOCK_CLIENT(client); - /* - * dont set up the event if no read access - */ - if(!asCheckGet(pciu->asClientPVT)){ - pevext->pdbev = NULL; - no_read_access_event(client, pevext); - return; - } - pevext->pdbev = (struct event_block *)(pevext+1); status = db_add_event( @@ -1018,6 +1058,13 @@ struct client *client db_post_single_event(pevext->pdbev); + /* + * disable future labor if no read access + */ + if(!asCheckGet(pciu->asClientPVT)){ + db_event_disable(pevext->pdbev); + } + return; } @@ -1086,14 +1133,6 @@ struct client *client free(pciu->pPutNotify); } - /* - * remove from access control list - */ - status = asRemoveClient(&pciu->asClientPVT); - if(status){ - taskSuspend(0); - } - /* * send delete confirmed message */ @@ -1109,6 +1148,15 @@ struct client *client ellDelete(&client->addrq, &pciu->node); UNLOCK_CLIENT(client); + /* + * remove from access control list + */ + status = asRemoveClient(&pciu->asClientPVT); + assert(status == 0 || status == S_asLib_asNotActive); + if(status != 0 && status != S_asLib_asNotActive){ + errMessage(status, RECORD_NAME(&pciu->addr)); + } + FASTLOCK(&rsrv_free_addrq_lck); status = bucketRemoveItem(pCaBucket, pciu->sid, pciu); if(status != BUCKET_SUCCESS){ @@ -1314,7 +1362,7 @@ db_field_log *pfl * operation directly to the * event/put/get callback. * - * Fetched value is zerod in case they + * Fetched value is set to zero in case they * use it even when the status indicates * failure. * @@ -1425,8 +1473,10 @@ struct event_ext *pevext * The m_cid field in the protocol * header is abused to carry the status */ - bzero((char *)(reply+1), pevext->size); + *reply = pevext->msg; + reply->m_postsize = pevext->size; reply->m_cid = ECA_NORDACCESS; + bzero((char *)(reply+1), pevext->size); END_MSG(client); } } @@ -1519,41 +1569,21 @@ struct client *client pchannel->client = client; pchannel->cid = mp->m_cid; - /* - * set up access security for this channel - * - * done here rather than at channel claim so - * that search reply will fail if there - * isnt enough memory. - */ - status = asAddClient( - &pchannel->asClientPVT, - asDbGetMemberPvt(&pchannel->addr), - asDbGetAsl(&pchannel->addr), - "", - ""); - if(status){ - LOCK_CLIENT(client); - send_err(mp, ECA_ALLOCMEM, client, "No room for security table"); - UNLOCK_CLIENT(client); - FASTLOCK(&rsrv_free_addrq_lck); - ellAdd(&rsrv_free_addrq, &pchannel->node); - FASTUNLOCK(&rsrv_free_addrq_lck); - return; - } - asPutClientPvt(pchannel->asClientPVT, pchannel); - /* * Existing build() interface to the client does not provide mechanism * to inform them that the channel connected but the value * couldnt be fetched so search/get combined op * to no read access channel not allowed. */ +#if 0 if (mp->m_cmmd == IOC_BUILD && !asCheckGet(pchannel->asClientPVT)) { +#else + if (mp->m_cmmd == IOC_BUILD) { +printf("Build access security bypassed\n"); +#endif LOCK_CLIENT(client); send_err(mp, ECA_NORDACCESS, client, RECORD_NAME(&tmp_addr)); UNLOCK_CLIENT(client); - asRemoveClient(&pchannel->asClientPVT); FASTLOCK(&rsrv_free_addrq_lck); ellAdd(&rsrv_free_addrq, &pchannel->node); FASTUNLOCK(&rsrv_free_addrq_lck); @@ -1573,7 +1603,6 @@ struct client *client LOCK_CLIENT(client); send_err(mp, ECA_ALLOCMEM, client, "No room for hash table"); UNLOCK_CLIENT(client); - asRemoveClient(&pchannel->asClientPVT); FASTLOCK(&rsrv_free_addrq_lck); ellAdd(&rsrv_free_addrq, &pchannel->node); FASTUNLOCK(&rsrv_free_addrq_lck); @@ -1607,7 +1636,6 @@ struct client *client /* tell them that their request is to large */ send_err(mp, ECA_TOLARGE, client, RECORD_NAME(&tmp_addr)); UNLOCK_CLIENT(client); - asRemoveClient(&pchannel->asClientPVT); FASTLOCK(&rsrv_free_addrq_lck); bucketRemoveItem( pCaBucket, @@ -1716,32 +1744,52 @@ LOCAL void send_err( struct extmsg *curp, int status, struct client *client, -char *footnote +char *pformat, + ... ) { + va_list args; struct channel_in_use *pciu; int size; struct extmsg *reply; + char *pMsgString; + va_start(args, pformat); /* - * force string post size to be the true size rounded to even - * boundary + * allocate plenty of space for a sprintf() buffer */ - size = strlen(footnote)+1; - size += sizeof(*curp); - - reply = (struct extmsg *) ALLOC_MSG(client, size); + reply = (struct extmsg *) ALLOC_MSG(client, 512); if (!reply){ - printf( "caserver: Unable to deliver err msg [%s]\n", - ca_message(status)); + int logMsgArgs[6]; + int i; + + for(i=0; i< NELEMENTS(logMsgArgs); i++){ + logMsgArgs[i] = va_arg(args, int); + } + + logMsg( "caserver: Unable to deliver err msg [%s]\n", + (int) ca_message(status), + NULL, + NULL, + NULL, + NULL, + NULL); + logMsg( + pformat, + logMsgArgs[0], + logMsgArgs[1], + logMsgArgs[2], + logMsgArgs[3], + logMsgArgs[4], + logMsgArgs[5]); + return; } reply[0] = nill_msg; reply[0].m_cmmd = IOC_ERROR; reply[0].m_available = status; - reply[0].m_postsize = size; switch (curp->m_cmmd) { case IOC_EVENT_ADD: @@ -1774,25 +1822,49 @@ char *footnote reply->m_cid = NULL; break; } - reply[1] = *curp; - strcpy((char *)(reply + 2), footnote); + /* + * copy back the request protocol + */ + reply[1] = *curp; + + /* + * add their context string into the protocol + */ + pMsgString = (char *) (reply+2); + status = vsprintf(pMsgString, pformat, args); + + /* + * force string post size to be the true size rounded to even + * boundary + */ + size = strlen(pMsgString)+1; + size += sizeof(*curp); + reply->m_postsize = size; END_MSG(client); } /* - * logBadId() + * logBadIdWithFileAndLineno() */ -LOCAL void logBadId( -struct client *client, -struct extmsg *mp +LOCAL void logBadIdWithFileAndLineno( +struct client *client, +struct extmsg *mp, +char *pFileName, +unsigned lineno ) { log_header(mp,0); LOCK_CLIENT(client); - send_err(mp, ECA_INTERNAL, client, "ID lookup failed"); + send_err( + mp, + ECA_INTERNAL, + client, + "Bad Resource ID at %s.%d", + pFileName, + lineno); UNLOCK_CLIENT(client); } @@ -1893,49 +1965,27 @@ LOCAL void casAccessRightsCB(ASCLIENTPVT ascpvt, asClientStatus type) { struct client *pclient; struct channel_in_use *pciu; - struct extmsg *reply; struct event_ext *pevext; int status; - unsigned ar; - int v41; pciu = asGetClientPvt(ascpvt); - if(!pciu){ - printf("casAccessRightsCB() without channel pointer ??\n"); - return; - } + assert(pciu); + pclient = pciu->client; assert(pclient); - v41 = CA_V41(CA_PROTOCOL_VERSION,pclient->minor_version_number); + + if(pclient == prsrv_cast_client){ + return; + } + switch(type) { case asClientCOAR: - /* - * noop if this is an old client - */ - if(!v41){ - break; - } - ar = 0; /* none */ - if(asCheckGet(ascpvt)){ - ar |= CA_ACCESS_RIGHT_READ; - } - if(asCheckPut(ascpvt)){ - ar |= CA_ACCESS_RIGHT_WRITE; - } + access_rights_reply(pciu); LOCK_CLIENT(pclient); - reply = (struct extmsg *)ALLOC_MSG(pclient, 0); - assert(reply); - - *reply = nill_msg; - reply->m_cmmd = IOC_ACCESS_RIGHTS; - reply->m_cid = pciu->cid; - reply->m_available = ar; - - END_MSG(pclient); /* * Update all event call backs @@ -1943,34 +1993,16 @@ LOCAL void casAccessRightsCB(ASCLIENTPVT ascpvt, asClientStatus type) for (pevext = (struct event_ext *) ellFirst(&pciu->eventq); pevext; pevext = (struct event_ext *) ellNext(&pevext->node)){ + int readAccess; - if(pevext->pdbev && !(ar&CA_ACCESS_RIGHT_READ)){ - status = db_cancel_event(pevext->pdbev); - assert(status == OK); - pevext->pdbev = NULL; + readAccess = asCheckGet(pciu->asClientPVT); + + if(pevext->pdbev && !readAccess){ + db_post_single_event(pevext->pdbev); + db_event_disable(pevext->pdbev); } - else if(!pevext->pdbev && ar&CA_ACCESS_RIGHT_READ){ - pevext->pdbev = - (struct event_block *)(pevext+1); - - status = db_add_event( - pclient->evuser, - &pciu->addr, - read_reply, - pevext, - pevext->mask, - pevext->pdbev); - if (status == ERROR) { - pevext->pdbev = NULL; - send_err( - &pevext->msg, - ECA_ADDFAIL, - pclient, - RECORD_NAME(&pciu->addr)); - } - } - - if(pevext->pdbev){ + else if(pevext->pdbev && readAccess){ + db_event_enable(pevext->pdbev); db_post_single_event(pevext->pdbev); } } @@ -1984,3 +2016,45 @@ LOCAL void casAccessRightsCB(ASCLIENTPVT ascpvt, asClientStatus type) } } + +/* + * access_rights_reply() + */ +LOCAL void access_rights_reply(struct channel_in_use *pciu) +{ + struct client *pclient; + struct extmsg *reply; + unsigned ar; + int v41; + + pclient = pciu->client; + + assert(pclient != prsrv_cast_client); + + /* + * noop if this is an old client + */ + v41 = CA_V41(CA_PROTOCOL_VERSION,pclient->minor_version_number); + if(!v41){ + return; + } + + ar = 0; /* none */ + if(asCheckGet(pciu->asClientPVT)){ + ar |= CA_ACCESS_RIGHT_READ; + } + if(asCheckPut(pciu->asClientPVT)){ + ar |= CA_ACCESS_RIGHT_WRITE; + } + + LOCK_CLIENT(pclient); + reply = (struct extmsg *)ALLOC_MSG(pclient, 0); + assert(reply); + + *reply = nill_msg; + reply->m_cmmd = IOC_ACCESS_RIGHTS; + reply->m_cid = pciu->cid; + reply->m_available = ar; + END_MSG(pclient); + UNLOCK_CLIENT(pclient); +} diff --git a/src/rsrv/caservertask.c b/src/rsrv/caservertask.c index 721256037..1b93fc0e9 100644 --- a/src/rsrv/caservertask.c +++ b/src/rsrv/caservertask.c @@ -328,14 +328,9 @@ LOCAL int terminate_one_client(struct client *client) NULL); } status = asRemoveClient(&pciu->asClientPVT); - if(status){ - logMsg( "%s Bad client PVD during client shutdown", - (int)__FILE__, - NULL, - NULL, - NULL, - NULL, - NULL); + if(status!=0 && status != S_asLib_asNotActive){ + printf("And the status is %x \n", status); + errPrintf(status, __FILE__, __LINE__, "asRemoveClient"); } /* diff --git a/src/rsrv/cast_server.c b/src/rsrv/cast_server.c index a931f37df..ed5a9edee 100644 --- a/src/rsrv/cast_server.c +++ b/src/rsrv/cast_server.c @@ -58,6 +58,9 @@ static char *sccsId = "$Id$"; +#include +#include + #include #include #include @@ -67,7 +70,6 @@ static char *sccsId = "$Id$"; #include #include #include -#include #include #include #include @@ -341,17 +343,6 @@ clean_addrq(struct client *pclient) int status; ellDelete(&pclient->addrq, &pciu->node); - status = asRemoveClient(&pciu->asClientPVT); - if(status){ - logMsg( - "%s Bad client PVD at close", - (int)__FILE__, - NULL, - NULL, - NULL, - NULL, - NULL); - } FASTLOCK(&rsrv_free_addrq_lck); s = bucketRemoveItem(pCaBucket, pciu->sid, pciu); if(s != BUCKET_SUCCESS){ diff --git a/src/rsrv/online_notify.c b/src/rsrv/online_notify.c index ba6866b16..1112f8c4e 100644 --- a/src/rsrv/online_notify.c +++ b/src/rsrv/online_notify.c @@ -38,6 +38,7 @@ static char *sccsId = "$Id$\t$Date$"; /* * ansi includes */ +#include #include /*