diff --git a/src/ca/access.c b/src/ca/access.c index 83ce26240..370c615cf 100644 --- a/src/ca/access.c +++ b/src/ca/access.c @@ -99,6 +99,9 @@ /************************************************************************/ /* * $Log$ + * Revision 1.91 1997/04/10 19:26:01 jhill + * asynch connect, faster connect, ... + * * Revision 1.90 1997/01/22 21:06:30 jhill * use genLocalExcepWFL for generateLocalExceptionWithFileAndLine * @@ -204,10 +207,12 @@ static char *sccsId = "@(#) $Id$"; #define CAC_VERSION_GLOBAL #include "iocinf.h" -#include "net_convert.h" -#include "epicsPrint.h" #include "sigPipeIgnore.h" +#ifdef vxWorks +#include "dbEvent.h" +#endif + /****************************************************************/ /* Macros for syncing message insertion into send buffer */ @@ -261,10 +266,10 @@ unsigned cmmd ); #ifdef vxWorks LOCAL void ca_event_handler( -miu monix, +void *usrArg, struct dbAddr *paddr, int hold, -void *pfl +db_field_log *pfl ); LOCAL void ca_put_notify_action(PUTNOTIFY *ppn); #endif @@ -2206,7 +2211,7 @@ long mask ca_event_handler, monix, mask, - monix+1); + (struct event_block *)(monix+1)); if(status == ERROR){ UNLOCK; return ECA_DBLCLFAIL; @@ -2225,7 +2230,7 @@ long mask * return warning msg if they have made the queue to full * to force the first (untriggered) event. */ - if(db_post_single_event(monix+1)==ERROR){ + if(db_post_single_event((struct event_block *)(monix+1))==ERROR){ UNLOCK; return ECA_OVEVFAIL; } @@ -2328,12 +2333,13 @@ int ca_request_event(evid monix) */ #ifdef vxWorks LOCAL void ca_event_handler( -miu monix, +void *usrArg, struct dbAddr *paddr, int hold, -void *pfl +db_field_log *pfl ) { + miu monix = (miu) usrArg; register int status; register int count; register chtype type = monix->type; @@ -2519,7 +2525,7 @@ int epicsShareAPI ca_clear_event (evid monix) */ LOCK; ellDelete(&chix->eventq, &pMon->node); - status = db_cancel_event(pMon + 1); + status = db_cancel_event((struct event_block *)(pMon + 1)); ellAdd(&dbfree_ev_list, &pMon->node); UNLOCK; @@ -2629,7 +2635,7 @@ int epicsShareAPI ca_clear_channel (chid chix) * clear out the events for this channel */ while ( (monix = (miu) ellGet(&pChan->eventq)) ) { - status = db_cancel_event(monix + 1); + status = db_cancel_event((struct event_block *)(monix + 1)); assert (status == OK); ellAdd(&dbfree_ev_list, &monix->node); } @@ -2746,12 +2752,12 @@ void clearChannelResources(unsigned id) status = bucketRemoveItemUnsignedId ( ca_static->ca_pSlowBucket, &chix->cid); assert (status == S_bucket_success); + removeFromChanList(chix); free (chix); if (piiu!=piiuCast && ellCount(&piiu->chidlist.count)==0){ TAG_CONN_DOWN(piiu); } - removeFromChanList(chix); - + UNLOCK; } @@ -2773,6 +2779,17 @@ int epicsShareAPI ca_pend (ca_real timeout, int early) INITCHK; + /* + * select() under WIN32 gives us grief + * if we delay with out interest in at + * least one fd + */ + if (!ca_static->ca_piiuCast) { + create_udp_fd(); + if(!ca_static->ca_piiuCast){ + return ECA_NOCAST; + } + } if(EVENTLOCKTEST){ return ECA_EVDISALLOW; @@ -3263,7 +3280,7 @@ void noop_msg(struct ioc_in_use *piiu) hdr.m_available = htons(0); hdr.m_postsize = 0; - cac_push_msg_no_block(piiu, &hdr, NULL); + status = cac_push_msg_no_block(piiu, &hdr, NULL); if (status == ECA_NORMAL) { piiu->send_needed = TRUE; } diff --git a/src/ca/bsd_depen.c b/src/ca/bsd_depen.c index 06731389f..c80ffd595 100644 --- a/src/ca/bsd_depen.c +++ b/src/ca/bsd_depen.c @@ -52,6 +52,7 @@ int cac_select_io(struct timeval *ptimeout, int flags) unsigned long freespace; SOCKET maxfd; caFDInfo *pfdi; + int ioPending; LOCK; pfdi = (caFDInfo *) ellGet(&ca_static->fdInfoFreeList); @@ -70,6 +71,7 @@ int cac_select_io(struct timeval *ptimeout, int flags) FD_ZERO (&pfdi->writeMask); maxfd = 0; + ioPending = FALSE; for( piiu = (IIU *) iiuList.node.next; piiu; piiu = (IIU *) piiu->node.next) { @@ -115,6 +117,7 @@ int cac_select_io(struct timeval *ptimeout, int flags) maxfd = max (maxfd,piiu->sock_chan); FD_SET (piiu->sock_chan, &pfdi->readMask); piiu->recvPending = TRUE; + ioPending = TRUE; } else { piiu->recvPending = FALSE; @@ -127,6 +130,7 @@ int cac_select_io(struct timeval *ptimeout, int flags) if (flags&CA_DO_SENDS) { if (piiu->state==iiu_connecting) { FD_SET (piiu->sock_chan, &pfdi->writeMask); + ioPending = TRUE; } else { if (cacRingBufferReadSize(&piiu->send, FALSE)>0) { @@ -138,21 +142,37 @@ int cac_select_io(struct timeval *ptimeout, int flags) } UNLOCK; -# if defined(__hpux) + /* + * win32 requires this (others will + * run faster with this installed) + */ + if ( !ioPending && + ptimeout->tv_sec==0 && + ptimeout->tv_usec==0 ) { + status = 0; + } + else { +# if defined(__hpux) +# define HPCAST (int *) +# else +# define HPCAST +# endif status = select( maxfd+1, - (int *)&pfdi->readMask, - (int *)&pfdi->writeMask, - (int *)NULL, + HPCAST &pfdi->readMask, + HPCAST &pfdi->writeMask, + HPCAST NULL, &autoTimeOut); -# else - status = select( - maxfd+1, - &pfdi->readMask, - &pfdi->writeMask, - NULL, - &autoTimeOut); -# endif + if (status<0) { + int errnoCpy = SOCKERRNO; + + if (errnoCpy!=EINTR) { + ca_printf ( + "CAC: unexpected select fail: %s\n", + strerror(SOCKERRNO)); + } + } + } /* * get a new time stamp if we have been waiting @@ -162,21 +182,6 @@ int cac_select_io(struct timeval *ptimeout, int flags) cac_gettimeval (&ca_static->currentTime); } - if (status<0) { - if (SOCKERRNO == EINTR) { - } - else if (SOCKERRNO == EWOULDBLOCK) { - ca_printf("CAC: blocked at select ?\n"); - } - else if (SOCKERRNO == ESRCH) { - } - else { - ca_printf ( - "CAC: unexpected select fail: %s\n", - strerror(SOCKERRNO)); - } - } - LOCK; if (status>0) { for ( piiu = (IIU *) iiuList.node.next; diff --git a/src/ca/ca.def b/src/ca/ca.def index 2f0dafa97..f544dd0c7 100644 --- a/src/ca/ca.def +++ b/src/ca/ca.def @@ -45,15 +45,15 @@ caFetchPortConfig caAddConfiguredAddr caDiscoverInterfaces ca_printf -ca_message_text +ca_message_text ca_message cac_gettimeval -dbr_value_size -dbr_value_offset -dbf_text -dbf_text_invalid -dbf_text_dim -dbr_text -dbr_text_invalid -dbr_text_dim -dbr_size +dbr_value_size +dbr_value_offset +dbf_text +dbf_text_invalid +dbf_text_dim +dbr_text +dbr_text_invalid +dbr_text_dim +dbr_size diff --git a/src/ca/cadef.h b/src/ca/cadef.h index 6e799b972..b40caa72b 100644 --- a/src/ca/cadef.h +++ b/src/ca/cadef.h @@ -249,7 +249,7 @@ struct pending_event{ #else /*CAC_ANSI_FUNC_PROTO*/ void (*usr_func)(); #endif /*CAC_ANSI_FUNC_PROTO*/ - void *usr_arg; + const void *usr_arg; chid chan; chtype type; /* requested type for local CA */ unsigned long count; /* requested count for local CA */ diff --git a/src/ca/catime.c b/src/ca/catime.c index a6e2c8c00..984046e13 100644 --- a/src/ca/catime.c +++ b/src/ca/catime.c @@ -147,7 +147,7 @@ int catime (char *channelName, enum appendNumberFlag appNF) printf ("free test\n"); timeIt (test_free, itemList, 100u); - printf ("waiting for the server to reply..."); + printf ("waiting for the server to reply to free requests..."); fflush (stdout); ca_pend_event(1.0); printf ("hopefully done\n"); diff --git a/src/ca/iocinf.c b/src/ca/iocinf.c index aaf96006b..993e8f54d 100644 --- a/src/ca/iocinf.c +++ b/src/ca/iocinf.c @@ -47,6 +47,9 @@ /* address in use so that test works on UNIX */ /* kernels that support multicast */ /* $Log$ + * Revision 1.68 1997/04/10 19:26:14 jhill + * asynch connect, faster connect, ... + * * Revision 1.67 1997/01/08 22:48:42 jhill * improved message * @@ -584,6 +587,8 @@ LOCAL void cac_connect_iiu (struct ioc_in_use *piiu) * attempt to connect to a CA server */ while (1) { + int errnoCpy; + status = connect( piiu->sock_chan, &pNode->destAddr.sa, @@ -592,7 +597,19 @@ LOCAL void cac_connect_iiu (struct ioc_in_use *piiu) break; } - if (SOCKERRNO==EINPROGRESS) { + errnoCpy = SOCKERRNO; + if (errnoCpy==EISCONN) { + /* + * called connect after we are already connected + * (this appears to be how they provide + * connect completion notification) + */ + break; + } + else if ( + errnoCpy==EINPROGRESS || + errnoCpy==EWOULDBLOCK /* for WINSOCK */ + ) { /* * The socket is non-blocking and a * connection attempt has been initiated, @@ -600,32 +617,27 @@ LOCAL void cac_connect_iiu (struct ioc_in_use *piiu) */ return; } - else if (SOCKERRNO==EISCONN) { - /* - * called connect after we are already connected - * (this appears to be how they provide connect completion - * notification) - */ - break; + else if ( + errnoCpy==EALREADY || + errnoCpy==EINVAL /* for early WINSOCK */ + ) { + ca_printf( + "CAC: duplicate connect err %d=\"%s\"\n", + errnoCpy, strerror(errnoCpy)); + return; } - else if (SOCKERRNO==EALREADY) { - /* - * The socket is non-blocking and - * we have issued a duplicate connect - * request. - */ - ca_printf("CAC: duplicate call to connect()???\n"); - return; - } - else if (SOCKERRNO==EINTR) { + else if(errnoCpy==EINTR) { /* * restart the system call if interrupted */ continue; } else { - ca_printf("CAC: Unable to connect port %d on \"%s\" because \"%s\"\n", - pNode->destAddr.in.sin_port, piiu->host_name_str, strerror(SOCKERRNO)); + ca_printf( + "CAC: Unable to connect port %d on \"%s\" because %d=\"%s\"\n", + ntohs(pNode->destAddr.in.sin_port), + piiu->host_name_str, errnoCpy, + strerror(errnoCpy)); TAG_CONN_DOWN(piiu); return; } diff --git a/src/ca/iocinf.h b/src/ca/iocinf.h index 2989f9afa..92b694691 100644 --- a/src/ca/iocinf.h +++ b/src/ca/iocinf.h @@ -32,6 +32,9 @@ /************************************************************************/ /* $Log$ + * Revision 1.60 1997/04/10 19:26:24 jhill + * asynch connect, faster connect, ... + * * Revision 1.59 1997/01/22 21:10:26 jhill * smaller external sym name for VAXC * @@ -130,8 +133,6 @@ HDRVERSIONID(iocinfh, "$Id$") #include #include -#include "shareLib.h" - /* * OS dependent includes */ @@ -141,13 +142,26 @@ HDRVERSIONID(iocinfh, "$Id$") /* * EPICS includes */ +#if defined(epicsExportSharedSymbols) +#error suspect that libCom was not imported +#endif + #include "epicsAssert.h" -#include "cadef.h" #include "bucketLib.h" #include "ellLib.h" #include "envDefs.h" #include "epicsPrint.h" +#if defined(epicsExportSharedSymbols) +#error suspect that libCom was not imported +#endif + +/* + * this is defined only after we import from libCom above + */ +#define epicsExportSharedSymbols +#include "cadef.h" + /* * CA private includes */ diff --git a/src/ca/net_convert.h b/src/ca/net_convert.h index 8f3d2bc78..4ea4098d5 100644 --- a/src/ca/net_convert.h +++ b/src/ca/net_convert.h @@ -85,7 +85,7 @@ typedef void CACVRTFUNC(void *pSrc, void *pDest, int hton, unsigned long count); #ifdef CONVERSION_REQUIRED /* cvrt is (array of) (pointer to) (function returning) int */ -extern CACVRTFUNC *cac_dbr_cvrt[]; +extern CACVRTFUNC *cac_dbr_cvrt[LAST_BUFFER_TYPE+1]; #endif @@ -100,11 +100,15 @@ extern CACVRTFUNC *cac_dbr_cvrt[]; #ifdef CA_LITTLE_ENDIAN # ifndef ntohs # define ntohs(SHORT)\ - ( ((SHORT) & 0x00ff) << 8 | ((SHORT) & 0xff00) >> 8 ) + ( (dbr_short_t)\ + (((SHORT) & (dbr_short_t) 0x00ff) << 8 |\ + ((SHORT) & (dbr_short_t) 0xff00) >> 8) ) # endif # ifndef htons # define htons(SHORT)\ - ( ((SHORT) & 0x00ff) << 8 | ((SHORT) & 0xff00) >> 8 ) + ( (dbr_short_t)\ + (((SHORT) & (dbr_short_t) 0x00ff) << 8 |\ + ((SHORT) & (dbr_short_t) 0xff00) >> 8) ) # endif #else # ifndef ntohs @@ -120,19 +124,19 @@ extern CACVRTFUNC *cac_dbr_cvrt[]; # ifndef ntohl # define ntohl(LONG)\ (\ - ((LONG) & 0xff000000) >> 24 |\ - ((LONG) & 0x000000ff) << 24 |\ - ((LONG) & 0x0000ff00) << 8 |\ - ((LONG) & 0x00ff0000) >> 8\ + ((LONG) & (dbr_long_t) 0xff000000) >> 24 |\ + ((LONG) & (dbr_long_t) 0x000000ff) << 24 |\ + ((LONG) & (dbr_long_t) 0x0000ff00) << 8 |\ + ((LONG) & (dbr_long_t) 0x00ff0000) >> 8\ ) # endif # ifndef htonl # define htonl(LONG)\ - (\ - ((LONG) & 0x000000ff) << 24 |\ - ((LONG) & 0xff000000) >> 24 |\ - ((LONG) & 0x00ff0000) >> 8 |\ - ((LONG) & 0x0000ff00) << 8\ + ( (dbr_long_t) \ + (((LONG) & (dbr_long_t) 0x000000ff) << 24 |\ + ((LONG) & (dbr_long_t) 0xff000000) >> 24 |\ + ((LONG) & (dbr_long_t) 0x00ff0000) >> 8 |\ + ((LONG) & (dbr_long_t) 0x0000ff00) << 8 )\ ) # endif # else diff --git a/src/ca/repeater.c b/src/ca/repeater.c index b1a6bc8ed..f8af13138 100644 --- a/src/ca/repeater.c +++ b/src/ca/repeater.c @@ -63,6 +63,9 @@ * datagram socket (and watching for ECONNREFUSED) * * $Log$ + * Revision 1.38 1996/11/02 00:51:04 jhill + * many pc port, const in API, and other changes + * * Revision 1.37 1996/09/04 20:02:32 jhill * fixed gcc warning * @@ -298,7 +301,8 @@ LOCAL void verifyClients() else { if (SOCKERRNO!=EADDRINUSE) { ca_printf( - "CA Repeater: bind test err was \"%s\"\n", strerror(SOCKERRNO)); + "CA Repeater: bind test err was %d=\"%s\"\n", + SOCKERRNO, strerror(SOCKERRNO)); } } } diff --git a/src/ca/vxWorks_depen.c b/src/ca/vxWorks_depen.c index 8b8467695..b7a1901b7 100644 --- a/src/ca/vxWorks_depen.c +++ b/src/ca/vxWorks_depen.c @@ -29,6 +29,9 @@ * Modification Log: * ----------------- * $Log$ + * Revision 1.28 1997/04/10 19:26:19 jhill + * asynch connect, faster connect, ... + * * Revision 1.27 1996/11/02 00:51:10 jhill * many pc port, const in API, and other changes * @@ -59,6 +62,7 @@ #include "callback.h" #include "iocinf.h" #include "remLib.h" +#include "dbEvent.h" LOCAL void ca_repeater_task(); LOCAL void ca_task_exit_tcb(WIND_TCB *ptcb); @@ -67,6 +71,7 @@ LOCAL int cac_os_depen_exit_tid (struct ca_static *pcas, int tid); LOCAL int cac_add_task_variable (struct ca_static *ca_temp); LOCAL void deleteCallBack(CALLBACK *pcb); LOCAL void ca_check_for_fp(); +LOCAL int event_import(int tid); /* * order of ops is important here @@ -391,7 +396,7 @@ int cac_os_depen_init(struct ca_static *pcas) assert(evuser); status = db_add_extra_labor_event( - evuser, + (struct event_user *)evuser, ca_extra_event_labor, pcas); assert(status==0); @@ -401,9 +406,9 @@ int cac_os_depen_init(struct ca_static *pcas) taskName(VXTHISTASKID), sizeof(name) - strlen(name) - 1); status = db_start_events( - evuser, + (struct event_user *)evuser, name, - ca_import, + event_import, taskIdSelf(), -1); /* higher priority */ assert(status == OK); @@ -473,7 +478,7 @@ LOCAL int cac_os_depen_exit_tid (struct ca_static *pcas, int tid) * can finish */ UNLOCK; - status = db_cancel_event(monix + 1); + status = db_cancel_event((struct event_block *)(monix+1)); LOCK; assert(status == OK); free(monix); @@ -630,6 +635,22 @@ unsigned size) return; } +/* + * event_import() + */ +LOCAL int event_import(int tid) +{ + int status; + + status = ca_import(tid); + if (status==ECA_NORMAL) { + return OK; + } + else { + return ERROR; + } +} + /* * CA_IMPORT() diff --git a/src/include/cadef.h b/src/include/cadef.h index 6e799b972..b40caa72b 100644 --- a/src/include/cadef.h +++ b/src/include/cadef.h @@ -249,7 +249,7 @@ struct pending_event{ #else /*CAC_ANSI_FUNC_PROTO*/ void (*usr_func)(); #endif /*CAC_ANSI_FUNC_PROTO*/ - void *usr_arg; + const void *usr_arg; chid chan; chtype type; /* requested type for local CA */ unsigned long count; /* requested count for local CA */