diff options
author | schmidt <douglascraigschmidt@users.noreply.github.com> | 1999-06-14 02:17:02 +0000 |
---|---|---|
committer | schmidt <douglascraigschmidt@users.noreply.github.com> | 1999-06-14 02:17:02 +0000 |
commit | b4a501994dd71bacf8c727a8a11e8c57a023e1fc (patch) | |
tree | cd090e6574f0f1d2f35adc0dd6d719c5c0d9b90e /ace | |
parent | a43d81d54a95a6fd5359d4733b7e3c1e4f02bd6b (diff) | |
download | ATCD-b4a501994dd71bacf8c727a8a11e8c57a023e1fc.tar.gz |
*** empty log message ***
Diffstat (limited to 'ace')
-rw-r--r-- | ace/OS.h | 267 | ||||
-rw-r--r-- | ace/OS.i | 506 | ||||
-rw-r--r-- | ace/SOCK_Acceptor.cpp | 260 | ||||
-rw-r--r-- | ace/SOCK_Acceptor.h | 34 | ||||
-rw-r--r-- | ace/SOCK_Connector.cpp | 255 | ||||
-rw-r--r-- | ace/SOCK_Connector.h | 68 | ||||
-rw-r--r-- | ace/SOCK_Connector.i | 18 |
7 files changed, 1167 insertions, 241 deletions
@@ -3126,6 +3126,8 @@ struct iovec { size_t iov_len; // byte count to read/write char *iov_base; // data to be read/written + + operator WSABUF &(void) { return *((WSABUF *) this); } }; struct msghdr @@ -4692,7 +4694,7 @@ extern "C" { typedef int (*ACE_COMPARE_FUNC)(const void *, const void *); } -class ACE_Errno_Guard +class ACE_Export ACE_Errno_Guard { // = TITLE // Provides a wrapper to improve performance when thread-specific @@ -4716,39 +4718,224 @@ class ACE_Errno_Guard // avoids an unnecessary second access to thread-specific storage // by caching a pointer to the value of errno in TSS. public: - ACE_Errno_Guard (int &e, int error): -#if defined (ACE_MT_SAFE) - ep_ (&e), -#endif /* ACE_MT_SAFE */ - error_ (error) { } + // = Initialization and termination methods. + ACE_Errno_Guard (int &errno_ref, + int error); + // Stash the value of <error> into <error_> and initialize the + // <errno_ptr_> to the address of <errno_ref>. - ACE_Errno_Guard (int &e): -#if defined (ACE_MT_SAFE) - ep_ (&e), -#endif /* ACE_MT_SAFE */ - error_ (e) { } + ACE_Errno_Guard (int &errno_ref); + // Stash the value of <errno> into <error_> and initialize the + // <errno_ptr_> to the address of <errno_ref>. + + ~ACE_Errno_Guard (void); + // Reset the value of <errno> to <error>. - ~ACE_Errno_Guard (void) - { -#if defined (ACE_MT_SAFE) - *ep_ = error_; -#else - errno = error_; -#endif /* ACE_MT_SAFE */ - } + int operator= (int error); + // Assign <error> to <error_>. - int operator= (int error) - { - return this->error_ = error; - } + int operator== (int error); + // Compare <error> with <error_> for equality. + + int operator!= (int error); + // Compare <error> with <error_> for inequality. private: #if defined (ACE_MT_SAFE) - int *ep_; + int *errno_ptr_; #endif /* ACE_MT_SAFE */ int error_; }; +// @@ We might want a smarter way to do this... +#if !defined (SERVICETYPE) +typedef u_long ACE_SERVICE_TYPE; +#else +typedef SERVICETYPE ACE_SERVICE_TYPE; +#endif /* SERVICETYPE */ + +class ACE_Export ACE_Flow_Spec +#if defined (ACE_HAS_WINSOCK2) + : public FLOWSPEC +#endif /* ACE_HAS_WINSOCK2 */ +{ + // = TITLE + // Wrapper class that defines the flow spec QoS information, which + // is used by RSVP. +public: + // = Get/set the token rate in bytes/sec. + u_long token_rate (void); + void token_rate (u_long tr); + + // = Get/set the token bucket size in bytes. + u_long token_bucket_size (void); + void token_bucket_size (u_long tbs); + + // = Get/set the PeakBandwidth in bytes/sec. + u_long peak_bandwidth (void); + void peak_bandwidth (u_long pb); + + // = Get/set the latency in microseconds. + u_long latency (void); + void latency (u_long l); + + // = Get/set the delay variation in microseconds. + u_long delay_variation (void); + void delay_variation (u_long dv); + + // = Get/set the service type. + ACE_SERVICE_TYPE service_type (void); + void service_type (ACE_SERVICE_TYPE st); + + // = Get/set the maximum SDU size in bytes. + u_long max_sdu_size (void); + void max_sdu_size (u_long mss); + + // = Get/set the minimum policed size in bytes. + u_long minimum_policed_size (void); + void minimum_policed_size (u_long mps); +}; + +class ACE_Export ACE_QoS +#if defined (ACE_HAS_WINSOCK2) + : public QOS +#endif /* ACE_HAS_WINSOCK2 */ +{ + // = TITLE + // Wrapper class that holds the sender and receiver flow spec + // information, which is used by RSVP. +public: + // = Get/set the flow spec for data sending. + ACE_Flow_Spec sending_flowspec (void); + void sending_flowspec (const ACE_Flow_Spec &fs); + + // = Get/set the flow spec for data receiving. + ACE_Flow_Spec receiving_flowspec (void); + void receiving_flowspec (const ACE_Flow_Spec &fs); + + // = Get/set the provider specific information. + iovec provider_specific (void); + void provider_specific (const iovec &ps); +}; + +class ACE_Export ACE_Connect_QoS_Params +{ + // = TITLE + // Wrapper class that simplifies the information passed to the QoS + // enabled <ACE_OS::connect> and <ACE_OS::join_leaf> methods. +public: + ACE_Connect_QoS_Params (iovec *caller_data = 0, + iovec *callee_data = 0, + ACE_QoS *socket_qos = 0, + ACE_QoS *group_socket_qos = 0, + u_long flags = 0); + // Initialize the data members. The <caller_data> is a pointer to + // the user data that is to be transferred to the peer during + // connection establishment. The <callee_data> is a pointer to the + // user data that is to be transferred back from the peer during + // connection establishment. The_<socket_qos> is a pointer to the + // flow speicfications for the socket, one for each direction. The + // <group_socket_qos> is a pointer to the flow speicfications for + // the socket group, if applicable. The_<flags> indicate if we're a + // sender, receiver, or both. + + // = Get/set caller data. + iovec *caller_data (void); + void caller_data (iovec *); + + // = Get/set callee data. + iovec *callee_data (void); + void callee_data (iovec *); + + // = Get/set socket qos. + ACE_QoS *socket_qos (void); + void socket_qos (ACE_QoS *); + + // = Get/set group socket qos. + ACE_QoS *group_socket_qos (void); + void group_socket_qos (ACE_QoS *); + + // = Get/set flags. + u_long flags (void); + void flags (u_long); + +private: + iovec *caller_data_; + // A pointer to the user data that is to be transferred to the peer + // during connection establishment. + + iovec *callee_data_; + // A pointer to the user data that is to be transferred back from + // the peer during connection establishment. + + ACE_QoS *socket_qos_; + // A pointer to the flow speicfications for the socket, one for each + // direction. + + ACE_QoS *group_socket_qos_; + // A pointer to the flow speicfications for the socket group, if + // applicable. + + u_long flags_; + // Flags that indicate if we're a sender, receiver, or both. +}; + +// Callback function that's used by the QoS-enabled <ACE_OS::accept> +// method. +typedef int (*ACE_QOS_CONDITION_FUNC) (iovec *caller_id, + iovec *caller_data, + ACE_QoS *socket_qos, + ACE_QoS *group_socket_qos, + iovec *callee_id, + iovec *callee_data, + u_long *g, /* unused */ + u_long callbackdata); + +// Callback function that's used by the QoS-enabled <ACE_OS::ioctl> +// method. +typedef void (*ACE_OVERLAPPED_COMPLETION_FUNC) (u_long error, + u_long bytes_transferred, + ACE_OVERLAPPED *overlapped, + u_long flags); +class ACE_Export ACE_Accept_QoS_Params +{ + // = TITLE + // Wrapper class that simplifies the information passed to the QoS + // enabled <ACE_OS::accept> method. +public: + ACE_Accept_QoS_Params (ACE_QOS_CONDITION_FUNC qos_condition_callback = 0, + u_long callback_data = 0); + // Initialize the data members. The <qos_condition_callback> is the + // address of an optional, application-supplied condition function + // that will make an accept/reject decision based on the caller + // information pass in as parameters, and optionally create or join + // a socket group by assinging an appropriate value to the result + // parameter <g> of this function. The <callback_data> data is + // passed back to the application as a condition function parameter, + // i.e., it is an Asynchronous Completion Token (ACT). + + // = Get/set QoS condition callback. + ACE_QOS_CONDITION_FUNC qos_condition_callback (void); + void qos_condition_callback (ACE_QOS_CONDITION_FUNC qcc); + + // = Get/Set callback data. + u_long callback_data (void); + void callback_data (u_long cd); + +private: + ACE_QOS_CONDITION_FUNC qos_condition_callback_; + // This is the address of an optional, application-supplied + // condition function that will make an accept/reject decision based + // on the caller information pass in as parameters, and optionally + // create or join a socket group by assinging an appropriate value + // to the result parameter <g> of this function. + + u_long callback_data_; + // This data is passed back to the application as a condition + // function parameter, i.e., it is an Asynchronous Completion Token + // (ACT). +}; + class ACE_Export ACE_OS { // = TITLE @@ -5260,6 +5447,16 @@ public: static int ioctl (ACE_HANDLE handle, int cmd, void * = 0); + static int ioctl (ACE_HANDLE socket, + u_long io_control_code, + void *in_buffer_p, + u_long in_buffer, + void *out_buffer_p, + u_long out_buffer, + u_long *bytes_returned, + ACE_OVERLAPPED *overlapped, + ACE_OVERLAPPED_COMPLETION_FUNC func); + // QoS-enabled <ioctl>. static int isastream (ACE_HANDLE handle); static int isatty (ACE_HANDLE handle); static off_t lseek (ACE_HANDLE handle, @@ -5488,12 +5685,25 @@ public: static ACE_HANDLE accept (ACE_HANDLE handle, struct sockaddr *addr, int *addrlen); + // BSD-style <accept> (no QoS). + static ACE_HANDLE accept (ACE_HANDLE handle, + struct sockaddr *addr, + int *addrlen, + ACE_Accept_QoS_Params qos_params); + // QoS-enabled <accept>. static int bind (ACE_HANDLE s, struct sockaddr *name, int namelen); static int connect (ACE_HANDLE handle, struct sockaddr *addr, int addrlen); + // BSD-style <connect> (no QoS). + static int connect (ACE_HANDLE handle, + const sockaddr *addr, + int addrlen, + ACE_Connect_QoS_Params qos_params); + // QoS-enabled <connect>. + static int closesocket (ACE_HANDLE s); static struct hostent *gethostbyaddr (const char *addr, int length, @@ -5539,7 +5749,6 @@ public: static char *inet_ntoa (const struct in_addr addr); static int inet_aton (const char *strptr, struct in_addr *addr); - static const char *inet_ntop (int family, const void *addrptr, char *strptr, @@ -5547,8 +5756,11 @@ public: static int inet_pton (int family, const char *strptr, void *addrptr); - - + static ACE_HANDLE join_leaf (ACE_HANDLE socket, + const sockaddr *name, + int namelen, + ACE_Connect_QoS_Params qos_params); + // Joins a leaf node into a QoS-enabled multi-point session. static int listen (ACE_HANDLE handle, int backlog); static int recv (ACE_HANDLE handle, @@ -5579,6 +5791,7 @@ public: int optname, const char *optval, int optlen); + // QoS-enabled <ioctl> wrapper. static int shutdown (ACE_HANDLE handle, int how); static ACE_HANDLE socket (int domain, @@ -697,8 +697,6 @@ ACE_OS::umask (mode_t cmask) #else /* ACE_WIN32 */ -// This is for Win32 exclusively! - // Adapt the Win32 System Calls (which return BOOLEAN values of TRUE // and FALSE) into int values expected by the ACE_OSCALL macros. # define ACE_ADAPT_RETVAL(OP,RESULT) ((RESULT = (OP)) == FALSE ? -1 : 0) @@ -4141,48 +4139,430 @@ ACE_OS::event_reset (ACE_event_t *event) # endif /* ACE_MT_SAFE && ACE_MT_SAFE != 0 */ #endif /* ACE_LACKS_NETDB_REENTRANT_FUNCTIONS */ +ACE_INLINE u_long +ACE_Flow_Spec::token_rate (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->TokenRate; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::token_rate (u_long tr) +{ +#if defined (ACE_HAS_WINSOCK2) + this->TokenRate = tr; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE u_long +ACE_Flow_Spec::token_bucket_size (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->TokenBucketSize; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::token_bucket_size (u_long tbs) +{ +#if defined (ACE_HAS_WINSOCK2) + this->TokenBucketSize = tbs; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE u_long +ACE_Flow_Spec::peak_bandwidth (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->PeakBandwidth; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::peak_bandwidth (u_long pb) +{ +#if defined (ACE_HAS_WINSOCK2) + this->PeakBandwidth = pb; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE u_long +ACE_Flow_Spec::latency (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->Latency; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::latency (u_long l) +{ +#if defined (ACE_HAS_WINSOCK2) + this->Latency = l; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE u_long +ACE_Flow_Spec::delay_variation (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->DelayVariation; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} +ACE_INLINE void +ACE_Flow_Spec::delay_variation (u_long dv) +{ +#if defined (ACE_HAS_WINSOCK2) + this->DelayVariation = dv; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE ACE_SERVICE_TYPE +ACE_Flow_Spec::service_type (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->ServiceType; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::service_type (ACE_SERVICE_TYPE st) +{ +#if defined (ACE_HAS_WINSOCK2) + this->ServiceType = st; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE u_long +ACE_Flow_Spec::max_sdu_size (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->MaxSduSize; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::max_sdu_size (u_long mss) +{ +#if defined (ACE_HAS_WINSOCK2) + this->MaxSduSize = mss; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE u_long +ACE_Flow_Spec::minimum_policed_size (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return this->MinimumPolicedSize; +#else + ACE_NOTSUP_RETURN (0); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_Flow_Spec::minimum_policed_size (u_long mps) +{ +#if defined (ACE_HAS_WINSOCK2) + this->MinimumPolicedSize = mps; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE ACE_Flow_Spec +ACE_QoS::sending_flowspec (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return (ACE_Flow_Spec &) this->SendingFlowspec; +#else + ACE_NOTSUP_RETURN (ACE_Flow_Spec ()); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_QoS::sending_flowspec (const ACE_Flow_Spec &fs) +{ +#if defined (ACE_HAS_WINSOCK2) + this->SendingFlowspec = (FLOWSPEC) fs; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE ACE_Flow_Spec +ACE_QoS::receiving_flowspec (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return (ACE_Flow_Spec &) this->ReceivingFlowspec; +#else + ACE_NOTSUP_RETURN (ACE_Flow_Spec ()); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_QoS::receiving_flowspec (const ACE_Flow_Spec &fs) +{ +#if defined (ACE_HAS_WINSOCK2) + this->ReceivingFlowspec = (FLOWSPEC) fs; +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE iovec +ACE_QoS::provider_specific (void) +{ +#if defined (ACE_HAS_WINSOCK2) + return (iovec &) this->ProviderSpecific; +#else + ACE_NOTSUP_RETURN (iovec ()); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE void +ACE_QoS::provider_specific (const iovec &ps) +{ +#if defined (ACE_HAS_WINSOCK2) + this->ProviderSpecific = (WSABUF) ((iovec &) ps); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE +ACE_Connect_QoS_Params::ACE_Connect_QoS_Params (iovec *caller_data, + iovec *callee_data, + ACE_QoS *socket_qos, + ACE_QoS *group_socket_qos, + u_long flags) + : caller_data_ (caller_data), + callee_data_ (callee_data), + socket_qos_ (socket_qos), + group_socket_qos_ (group_socket_qos), + flags_ (flags) +{ +} + +ACE_INLINE iovec * +ACE_Connect_QoS_Params::caller_data (void) +{ + return this->caller_data_; +} + +ACE_INLINE void +ACE_Connect_QoS_Params::caller_data (iovec *cd) +{ + this->caller_data_ = cd; +} + +ACE_INLINE iovec * +ACE_Connect_QoS_Params::callee_data (void) +{ + return this->callee_data_; +} + +ACE_INLINE void +ACE_Connect_QoS_Params::callee_data (iovec *cd) +{ + this->callee_data_ = cd; +} + +ACE_INLINE ACE_QoS * +ACE_Connect_QoS_Params::socket_qos (void) +{ + return this->socket_qos_; +} + +ACE_INLINE void +ACE_Connect_QoS_Params::socket_qos (ACE_QoS *sq) +{ + this->socket_qos_ = sq; +} + +ACE_INLINE ACE_QoS * +ACE_Connect_QoS_Params::group_socket_qos (void) +{ + return this->group_socket_qos_; +} + +ACE_INLINE void +ACE_Connect_QoS_Params::group_socket_qos (ACE_QoS *gsq) +{ + this->group_socket_qos_ = gsq; +} + +ACE_INLINE u_long +ACE_Connect_QoS_Params::flags (void) +{ + return this->flags_; +} + +ACE_INLINE void +ACE_Connect_QoS_Params::flags (u_long f) +{ + this->flags_ = f; +} + +ACE_INLINE +ACE_Accept_QoS_Params::ACE_Accept_QoS_Params (ACE_QOS_CONDITION_FUNC qos_condition_callback, + u_long callback_data) + : qos_condition_callback_ (qos_condition_callback), + callback_data_ (callback_data) +{ +} + +ACE_INLINE ACE_QOS_CONDITION_FUNC +ACE_Accept_QoS_Params::qos_condition_callback (void) +{ + return this->qos_condition_callback_; +} + +ACE_INLINE void +ACE_Accept_QoS_Params::qos_condition_callback (ACE_QOS_CONDITION_FUNC qcc) +{ + this->qos_condition_callback_ = qcc; +} + +ACE_INLINE u_long +ACE_Accept_QoS_Params::callback_data (void) +{ + return this->callback_data_; +} + +ACE_INLINE void +ACE_Accept_QoS_Params::callback_data (u_long cd) +{ + this->callback_data_ = cd; +} ACE_INLINE ACE_HANDLE -ACE_OS::accept (ACE_HANDLE handle, struct sockaddr *addr, +ACE_OS::accept (ACE_HANDLE handle, + struct sockaddr *addr, int *addrlen) { ACE_TRACE ("ACE_OS::accept"); #if defined (ACE_PSOS) # if !defined (ACE_PSOS_DIAB_PPC) -ACE_SOCKCALL_RETURN (::accept ((ACE_SOCKET) handle, (struct sockaddr_in *) addr, - (ACE_SOCKET_LEN *) addrlen), - ACE_HANDLE, ACE_INVALID_HANDLE); + ACE_SOCKCALL_RETURN (::accept ((ACE_SOCKET) handle, + (struct sockaddr_in *) addr, + (ACE_SOCKET_LEN *) addrlen), + ACE_HANDLE, + ACE_INVALID_HANDLE); # else -ACE_SOCKCALL_RETURN (::accept ((ACE_SOCKET) handle, (struct sockaddr *) addr, - (ACE_SOCKET_LEN *) addrlen), - ACE_HANDLE, ACE_INVALID_HANDLE); +ACE_SOCKCALL_RETURN (::accept ((ACE_SOCKET) handle, + (struct sockaddr *) addr, + (ACE_SOCKET_LEN *) addrlen), + ACE_HANDLE, + ACE_INVALID_HANDLE); # endif /* defined ACE_PSOS_DIAB_PPC */ #else - // On a non-blocking socket with no connections to accept, this system - // call will return EWOULDBLOCK or EAGAIN, depending on the platform. - // UNIX 98 allows either errno, and they may be the same numeric value. - // So to make life easier for upper ACE layers as well as application - // programmers, always change EAGAIN to EWOULDBLOCK. Rather than hack the - // ACE_OSCALL_RETURN macro, it's handled explicitly here. If the ACE_OSCALL - // macro ever changes, this function needs to be reviewed. - // On Win32, the regular macros can be used, as this is not an issue. + // On a non-blocking socket with no connections to accept, this + // system call will return EWOULDBLOCK or EAGAIN, depending on the + // platform. UNIX 98 allows either errno, and they may be the same + // numeric value. So to make life easier for upper ACE layers as + // well as application programmers, always change EAGAIN to + // EWOULDBLOCK. Rather than hack the ACE_OSCALL_RETURN macro, it's + // handled explicitly here. If the ACE_OSCALL macro ever changes, + // this function needs to be reviewed. On Win32, the regular macros + // can be used, as this is not an issue. # if defined (ACE_WIN32) - ACE_SOCKCALL_RETURN (::accept ((ACE_SOCKET) handle, addr, (ACE_SOCKET_LEN *) addrlen), - ACE_HANDLE, ACE_INVALID_HANDLE); + ACE_SOCKCALL_RETURN (::accept ((ACE_SOCKET) handle, + addr, + (ACE_SOCKET_LEN *) addrlen), + ACE_HANDLE, + ACE_INVALID_HANDLE); # else - - ACE_HANDLE ace_result_; - ace_result_ = ::accept ((ACE_SOCKET) handle, addr, - (ACE_SOCKET_LEN *) addrlen) ; + ACE_HANDLE ace_result = ::accept ((ACE_SOCKET) handle, + addr, + (ACE_SOCKET_LEN *) addrlen) ; if (ace_result_ == ACE_INVALID_HANDLE && errno == EAGAIN) errno = EWOULDBLOCK; - return ace_result_; + return ace_result; # endif /* defined (ACE_WIN32) */ #endif /* defined (ACE_PSOS) */ } +ACE_INLINE ACE_HANDLE +ACE_OS::accept (ACE_HANDLE handle, + struct sockaddr *addr, + int *addrlen, + ACE_Accept_QoS_Params qos_params) +{ +#if defined (ACE_HAS_WINSOCK2) + ACE_SOCKCALL_RETURN (::WSAAccept ((ACE_SOCKET) handle, + addr, + (ACE_SOCKET_LEN *) addrlen, + (LPCONDITIONPROC) qos_params.qos_condition_callback (), + qos_params.callback_data ()), + ACE_HANDLE, + ACE_INVALID_HANDLE); +#else + ACE_UNUSED_ARG (qos_params); + return ACE_OS::accept (handle, + addr, + addrlen); +#endif /* ACE_HAS_WINSOCK2 */ +} + +ACE_INLINE ACE_HANDLE +ACE_OS::join_leaf (ACE_HANDLE socket, + const sockaddr *name, + int namelen, + ACE_Connect_QoS_Params qos_params) +{ +#if defined (ACE_HAS_WINSOCK2) + ACE_SOCKCALL_RETURN (::WSAJoinLeaf ((ACE_SOCKET) socket, + name, + namelen, + (WSABUF *) qos_params.caller_data (), + (WSABUF *) qos_params.callee_data (), + (QOS *) qos_params.socket_qos (), + (QOS *) qos_params.group_socket_qos (), + qos_params.flags ()), + ACE_HANDLE, + ACE_INVALID_HANDLE); +#else + ACE_NOTSUP_RETURN (ACE_INVALID_HANDLE); +#endif /* ACE_HAS_WINSOCK2 */ +} + +int +ACE_OS::ioctl (ACE_HANDLE socket, + u_long io_control_code, + void *in_buffer_p, + u_long in_buffer, + void *out_buffer_p, + u_long out_buffer, + u_long *bytes_returned, + ACE_OVERLAPPED *overlapped, + ACE_OVERLAPPED_COMPLETION_FUNC func) +{ +#if defined (ACE_HAS_WINSOCK2) + ACE_SOCKCALL_RETURN (::WSAIoctl ((ACE_SOCKET) socket, + io_control_code, + in_buffer_p, + in_buffer, + out_buffer_p, + out_buffer, + bytes_returned, + (WSAOVERLAPPED *) overlapped, + (LPWSAOVERLAPPED_COMPLETION_ROUTINE) func), + int, + SOCKET_ERROR); +#else + ACE_NOTSUP_RETURN (ACE_INVALID_HANDLE); +#endif /* ACE_HAS_WINSOCK2 */ +} + ACE_INLINE int ACE_OS::bind (ACE_HANDLE handle, struct sockaddr *addr, int addrlen) { @@ -4197,7 +4577,9 @@ ACE_OS::bind (ACE_HANDLE handle, struct sockaddr *addr, int addrlen) } ACE_INLINE int -ACE_OS::connect (ACE_HANDLE handle, struct sockaddr *addr, int addrlen) +ACE_OS::connect (ACE_HANDLE handle, + struct sockaddr *addr, + int addrlen) { ACE_TRACE ("ACE_OS::connect"); #if defined (ACE_PSOS) && !defined (ACE_PSOS_DIAB_PPC) @@ -4209,6 +4591,30 @@ ACE_OS::connect (ACE_HANDLE handle, struct sockaddr *addr, int addrlen) #endif /* defined (ACE_PSOS) && !defined (ACE_PSOS_DIAB_PPC) */ } +ACE_INLINE int +ACE_OS::connect (ACE_HANDLE handle, + const sockaddr *addr, + int addrlen, + ACE_Connect_QoS_Params qos_params) +{ + ACE_TRACE ("ACE_OS::connect"); +#if defined (ACE_HAS_WINSOCK2) + ACE_SOCKCALL_RETURN (::WSAConnect ((ACE_SOCKET) handle, + (const sockaddr *) addr, + (ACE_SOCKET_LEN) addrlen, + (WSABUF *) qos_params.caller_data (), + (WSABUF *) qos_params.callee_data (), + (QOS *) qos_params.socket_qos (), + (QOS *) qos_params.group_socket_qos ()), + int, -1); +#else + ACE_UNUSED_ARG (qos_params); + return ACE_OS::connect (handle, + addr, + addrlen); +#endif /* ACE_HAS_WINSOCK2 */ +} + #if !defined (VXWORKS) ACE_INLINE struct hostent * ACE_OS::gethostbyname (const char *name) @@ -10950,3 +11356,53 @@ ACE_OS_CString::wchar_rep (void) { return this->rep_; } + +ACE_INLINE +ACE_Errno_Guard::ACE_Errno_Guard (int &errno_ref, + int error) + : +#if defined (ACE_MT_SAFE) + errno_ptr_ (&errno_ref), +#endif /* ACE_MT_SAFE */ + error_ (error) +{ +} + +ACE_INLINE +ACE_Errno_Guard::ACE_Errno_Guard (int &errno_ref) + : +#if defined (ACE_MT_SAFE) + errno_ptr_ (&errno_ref), +#endif /* ACE_MT_SAFE */ + error_ (errno_ref) +{ +} + +ACE_INLINE +ACE_Errno_Guard::~ACE_Errno_Guard (void) +{ +#if defined (ACE_MT_SAFE) + *errno_ptr_ = this->error_; +#else + errno = this->error_; +#endif /* ACE_MT_SAFE */ +} + +ACE_INLINE int +ACE_Errno_Guard::operator= (int error) +{ + return this->error_ = error; +} + +ACE_INLINE int +ACE_Errno_Guard::operator== (int error) +{ + return this->error_ == error; +} + +ACE_INLINE int +ACE_Errno_Guard::operator!= (int error) +{ + return this->error_ != error; +} + diff --git a/ace/SOCK_Acceptor.cpp b/ace/SOCK_Acceptor.cpp index 62f12886438..b6c2599de7e 100644 --- a/ace/SOCK_Acceptor.cpp +++ b/ace/SOCK_Acceptor.cpp @@ -21,6 +21,75 @@ ACE_SOCK_Acceptor::ACE_SOCK_Acceptor (void) ACE_TRACE ("ACE_SOCK_Acceptor::ACE_SOCK_Acceptor"); } +// Performs the timed accept operation. + +int +ACE_SOCK_Acceptor::shared_accept_start (ACE_Time_Value *timeout, + int restart, + int &in_blocking_mode) const +{ + ACE_TRACE ("ACE_SOCK_Acceptor::shared_accept_start"); + + ACE_HANDLE handle = this->get_handle (); + + // Handle the case where we're doing a timed <accept>. + if (timeout != 0) + { + if (ACE::handle_timed_accept (handle, + timeout, + restart) == -1) + return -1; + else + { + in_blocking_mode = ACE_BIT_DISABLED (ACE::get_flags (handle), + ACE_NONBLOCK); + // Set the handle into non-blocking mode if it's not already + // in it. + if (in_blocking_mode + && ACE::set_flags (handle, + ACE_NONBLOCK) == -1) + return -1; + } + } + + return 0; +} + +int +ACE_SOCK_Acceptor::shared_accept_finish (ACE_SOCK_Stream new_stream, + int in_blocking_mode, + int reset_new_handle) const +{ + ACE_TRACE ("ACE_SOCK_Acceptor::shared_accept_finish ()"); + + ACE_HANDLE new_handle = new_stream.get_handle (); + + // Check to see if we were originally in blocking mode, and if so, + // set the <new_stream>'s handle and <this> handle to be in blocking + // mode. + if (in_blocking_mode) + { + // Save/restore errno. + ACE_Errno_Guard error (errno); + // Only disable ACE_NONBLOCK if we weren't in + // non-blocking mode originally. + ACE::clr_flags (this->get_handle (), + ACE_NONBLOCK); + ACE::clr_flags (new_handle, + ACE_NONBLOCK); + } + +#if defined (ACE_HAS_WINSOCK2) && (ACE_HAS_WINSOCK2 != 0) + if (reset_new_handle) + // Reset the event association inherited by the new handle. + ::WSAEventSelect ((SOCKET) new_handle, 0, 0); +#else + ACE_UNUSED_ARG (reset_new_handle); +#endif /* ACE_WIN32 */ + + return new_handle == ACE_INVALID_HANDLE ? -1 : 0; +} + // General purpose routine for accepting new connections. int @@ -32,13 +101,89 @@ ACE_SOCK_Acceptor::accept (ACE_SOCK_Stream &new_stream, { ACE_TRACE ("ACE_SOCK_Acceptor::accept"); - ACE_HANDLE new_handle = - this->shared_accept (remote_addr, - timeout, - restart, - reset_new_handle); - new_stream.set_handle (new_handle); - return new_handle == ACE_INVALID_HANDLE ? -1 : 0; + int in_blocking_mode = 0; + if (this->shared_accept_start (timeout, + restart, + in_blocking_mode) == -1) + return -1; + else + { + sockaddr *addr = 0; + int len = 0; + + if (remote_addr != 0) + { + len = remote_addr->get_size (); + addr = (sockaddr *) remote_addr->get_addr (); + } + + do + new_stream.set_handle (ACE_OS::accept (this->get_handle (), + addr, + &len)); + while (new_stream.get_handle () == ACE_INVALID_HANDLE + && restart != 0 + && errno == EINTR + && timeout == 0); + + // Reset the size of the addr, which is only necessary for UNIX + // domain sockets. + if (new_stream.get_handle () != ACE_INVALID_HANDLE + && remote_addr != 0) + remote_addr->set_size (len); + } + + return this->shared_accept_finish (new_stream, + in_blocking_mode, + reset_new_handle); +} + +int +ACE_SOCK_Acceptor::accept (ACE_SOCK_Stream &new_stream, + ACE_Accept_QoS_Params qos_params, + ACE_Addr *remote_addr, + ACE_Time_Value *timeout, + int restart, + int reset_new_handle) const +{ + ACE_TRACE ("ACE_SOCK_Acceptor::accept"); + + int in_blocking_mode = 0; + if (this->shared_accept_start (timeout, + restart, + in_blocking_mode) == -1) + return -1; + else + { + sockaddr *addr = 0; + int len = 0; + + if (remote_addr != 0) + { + len = remote_addr->get_size (); + addr = (sockaddr *) remote_addr->get_addr (); + } + + do + new_stream.set_handle (ACE_OS::accept (this->get_handle (), + addr, + &len, + qos_params)); + while (new_stream.get_handle () == ACE_INVALID_HANDLE + && restart != 0 + && errno == EINTR + && timeout == 0); + + // Reset the size of the addr, which is only necessary for UNIX + // domain sockets. + if (new_stream.get_handle () != ACE_INVALID_HANDLE + && remote_addr != 0) + remote_addr->set_size (len); + } + + return this->shared_accept_finish (new_stream, + in_blocking_mode, + reset_new_handle); } // General purpose routine for performing server ACE_SOCK creation. @@ -50,9 +195,14 @@ ACE_SOCK_Acceptor::ACE_SOCK_Acceptor (const ACE_Addr &local_sap, int protocol) { ACE_TRACE ("ACE_SOCK_Acceptor::ACE_SOCK_Acceptor"); - if (this->open (local_sap, reuse_addr, protocol_family, - backlog, protocol) == -1) - ACE_ERROR ((LM_ERROR, ASYS_TEXT ("%p\n"), ASYS_TEXT ("ACE_SOCK_Acceptor"))); + if (this->open (local_sap, + reuse_addr, + protocol_family, + backlog, + protocol) == -1) + ACE_ERROR ((LM_ERROR, + ASYS_TEXT ("%p\n"), + ASYS_TEXT ("ACE_SOCK_Acceptor"))); } void @@ -73,8 +223,10 @@ ACE_SOCK_Acceptor::open (const ACE_Addr &local_sap, ACE_TRACE ("ACE_SOCK_Acceptor::open"); int error = 0; - if (ACE_SOCK::open (SOCK_STREAM, protocol_family, - protocol, reuse_addr) == -1) + if (ACE_SOCK::open (SOCK_STREAM, + protocol_family, + protocol, + reuse_addr) == -1) error = 1; else if (protocol_family == PF_INET) @@ -101,92 +253,20 @@ ACE_SOCK_Acceptor::open (const ACE_Addr &local_sap, else { if (ACE_OS::bind (this->get_handle (), - ACE_reinterpret_cast(sockaddr *, &local_inet_addr), + ACE_reinterpret_cast (sockaddr *, + &local_inet_addr), sizeof local_inet_addr) == -1) error = 1; } } - else if (ACE_OS::bind (this->get_handle (), (sockaddr *) local_sap.get_addr (), + else if (ACE_OS::bind (this->get_handle (), + (sockaddr *) local_sap.get_addr (), local_sap.get_size ()) == -1) error = 1; - if (error || ACE_OS::listen (this->get_handle (), backlog) == -1) + if (error || ACE_OS::listen (this->get_handle (), + backlog) == -1) this->close (); return error ? -1 : 0; } - -// Performs the timed accept operation. - -ACE_HANDLE -ACE_SOCK_Acceptor::shared_accept (ACE_Addr *remote_addr, - ACE_Time_Value *timeout, - int restart, - int reset_new_handle) const -{ - ACE_TRACE ("ACE_SOCK_Acceptor::shared_accept"); - ACE_UNUSED_ARG (reset_new_handle); - - sockaddr *addr = 0; - int *len_ptr = 0; - int len; - ACE_HANDLE new_handle; - ACE_HANDLE handle = this->get_handle (); - - if (remote_addr != 0) - { - len = remote_addr->get_size (); - len_ptr = &len; - addr = (sockaddr *) remote_addr->get_addr (); - } - - // Handle the case where we're doing a timed <accept>. - if (timeout != 0) - { - if (ACE::handle_timed_accept (handle, timeout, restart) == -1) - return ACE_INVALID_HANDLE; - else - { - int val = ACE::get_flags (handle); - - // Set the handle into non-blocking mode if it's not already - // in it. - if (ACE_BIT_DISABLED (val, ACE_NONBLOCK) - && ACE::set_flags (handle, ACE_NONBLOCK) == -1) - return ACE_INVALID_HANDLE; - - new_handle = ACE_OS::accept (handle, addr, len_ptr); - - if (ACE_BIT_DISABLED (val, ACE_NONBLOCK)) - { - // Save/restore errno. - ACE_Errno_Guard error (errno); - // Only disable ACE_NONBLOCK if we weren't in - // non-blocking mode originally. - ACE::clr_flags (handle, ACE_NONBLOCK); - ACE::clr_flags (new_handle, ACE_NONBLOCK); - } - } - } - else - { - // Perform a blocking accept. - - do - new_handle = ACE_OS::accept (handle, addr, len_ptr); - while (new_handle == ACE_INVALID_HANDLE && restart && errno == EINTR); - } - -#if defined (ACE_HAS_WINSOCK2) && (ACE_HAS_WINSOCK2 != 0) - if (reset_new_handle) - // Reset the event association inherited by the new handle. - ::WSAEventSelect ((SOCKET) new_handle, NULL, 0); -#endif /* ACE_WIN32 */ - - // Reset the size of the addr (really only necessary for the - // UNIX domain sockets). - if (new_handle != ACE_INVALID_HANDLE && remote_addr != 0) - remote_addr->set_size (*len_ptr); - - return new_handle; -} diff --git a/ace/SOCK_Acceptor.h b/ace/SOCK_Acceptor.h index 5f68e60030f..b7aa9f0b545 100644 --- a/ace/SOCK_Acceptor.h +++ b/ace/SOCK_Acceptor.h @@ -28,8 +28,7 @@ class ACE_Export ACE_SOCK_Acceptor : public ACE_SOCK { // = TITLE - // Defines the format and interface for an <ACE_Stream> - // acceptor. + // Defines a factory that creates new <ACE_Stream>s passively. public: // = Initialization methods. ACE_SOCK_Acceptor (void); @@ -52,15 +51,26 @@ public: int protocol = 0); // Initiate a passive mode socket. - // = Passive connection acceptance method. + // = Passive connection <accept> methods. int accept (ACE_SOCK_Stream &new_stream, ACE_Addr *remote_addr = 0, ACE_Time_Value *timeout = 0, int restart = 1, int reset_new_handle = 0) const; - // Accept a new data transfer connection. A <timeout> of 0 means - // block forever, a <timeout> of {0, 0} means poll. <restart> == 1 - // means "restart if interrupted." + // Accept a new <ACE_SOCK_Stream> connection. A <timeout> of 0 + // means block forever, a <timeout> of {0, 0} means poll. <restart> + // == 1 means "restart if interrupted," i.e., if errno == EINTR. + + int accept (ACE_SOCK_Stream &new_stream, + ACE_Accept_QoS_Params qos_params, + ACE_Addr *remote_addr = 0, + ACE_Time_Value *timeout = 0, + int restart = 1, + int reset_new_handle = 0) const; + // Accept a new <ACE_SOCK_Stream> connection using the RVSP QoS + // information in <qos_params>. A <timeout> of 0 means block + // forever, a <timeout> of {0, 0} means poll. <restart> == 1 means + // "restart if interrupted," i.e., if errno == EINTR. // = Meta-type info typedef ACE_INET_Addr PEER_ADDR; @@ -73,6 +83,18 @@ public: // Declare the dynamic allocation hooks. protected: + int shared_accept_start (ACE_Time_Value *timeout, + int restart, + int &in_blocking_mode) const; + // Perform operations that must occur before <ACE_OS::accept> is + // called. + + int shared_accept_finish (ACE_SOCK_Stream new_stream, + int in_blocking_mode, + int reset_new_handle) const; + // Perform operations that must occur after <ACE_OS::accept> is + // called. + ACE_HANDLE shared_accept (ACE_Addr *remote_addr, ACE_Time_Value *, int restart, diff --git a/ace/SOCK_Connector.cpp b/ace/SOCK_Connector.cpp index 6a1edc9028d..9938d839f4a 100644 --- a/ace/SOCK_Connector.cpp +++ b/ace/SOCK_Connector.cpp @@ -20,22 +20,15 @@ ACE_SOCK_Connector::dump (void) const ACE_TRACE ("ACE_SOCK_Connector::dump"); } -// Actively connect and produce a new ACE_SOCK_Stream if things go well... - -int -ACE_SOCK_Connector::connect (ACE_SOCK_Stream &new_stream, - const ACE_Addr &remote_sap, - ACE_Time_Value *timeout, - const ACE_Addr &local_sap, - int reuse_addr, - int /* flags */, - int /* perms */, - int protocol_family, - int protocol) +int +ACE_SOCK_Connector::shared_connect_start (ACE_SOCK_Stream &new_stream, + ACE_Time_Value *timeout, + const ACE_Addr &local_sap, + int reuse_addr, + int protocol_family, + int protocol) { - ACE_TRACE ("ACE_SOCK_Connector::connect"); - int result = 0; - + ACE_TRACE ("ACE_SOCK_Connector::shared_connect_start"); // Only open a new socket if we don't already have a valid handle. if (new_stream.get_handle () == ACE_INVALID_HANDLE && new_stream.open (SOCK_STREAM, @@ -43,65 +36,126 @@ ACE_SOCK_Connector::connect (ACE_SOCK_Stream &new_stream, protocol, reuse_addr) == -1) return -1; - - sockaddr *raddr = (sockaddr *) remote_sap.get_addr (); - size_t rsize = remote_sap.get_size (); - - if (local_sap != ACE_Addr::sap_any) + else if (local_sap != ACE_Addr::sap_any) { sockaddr *laddr = (sockaddr *) local_sap.get_addr (); size_t size = local_sap.get_size (); - result = ACE_OS::bind (new_stream.get_handle (), - laddr, - size); - - if (result == -1) + if (ACE_OS::bind (new_stream.get_handle (), + laddr, + size) == -1) { + // Save/restore errno. + ACE_Errno_Guard error (errno); new_stream.close (); return -1; } } // Enable non-blocking, if required. - if (timeout != 0) + if (timeout != 0 && new_stream.enable (ACE_NONBLOCK) == -1) + return -1; + else + return 0; +} + +int +ACE_SOCK_Connector::shared_connect_finish (ACE_SOCK_Stream &new_stream, + ACE_Time_Value *timeout, + int result) +{ + ACE_TRACE ("ACE_SOCK_Connector::shared_connect_finish"); + // Save/restore errno. + ACE_Errno_Guard error (errno); + + if (result == -1 && timeout != 0) { - if (new_stream.enable (ACE_NONBLOCK) == -1) - result = -1; - - if (ACE_OS::connect (new_stream.get_handle (), raddr, rsize) == -1) + // Check whether the connection is in progress. + if (error == EINPROGRESS || error == EWOULDBLOCK) { - result = -1; - - // Check whether the connection is in progress. - if (errno == EINPROGRESS || errno == EWOULDBLOCK) - { - // This expression checks if we were polling. - if (timeout->sec () == 0 && timeout->usec () == 0) - errno = EWOULDBLOCK; - // Wait synchronously - else if (this->complete (new_stream, 0, timeout) != -1) - return 0; - } + // This expression checks if we were polling. + if (timeout->sec () == 0 && timeout->usec () == 0) + error = EWOULDBLOCK; + // Wait synchronously using timeout. + else if (this->complete (new_stream, + 0, + timeout) == -1) + error = errno; + else + return 0; } } - // Do a blocking connect. - else if (ACE_OS::connect (new_stream.get_handle (), raddr, rsize) == -1) - result = -1; // EISCONN is treated specially since this routine may be used to // check if we are already connected. - if (result != -1 || errno == EISCONN) + if (result != -1 || error == EISCONN) // Start out with non-blocking disabled on the <new_stream>. new_stream.disable (ACE_NONBLOCK); - else if (!(errno == EWOULDBLOCK || errno == ETIMEDOUT)) - { - // Save/restore errno. - ACE_Errno_Guard error (errno); - new_stream.close (); - } - + else if (!(error == EWOULDBLOCK || error == ETIMEDOUT)) + new_stream.close (); + return result; } +// Actively connect and produce a new ACE_SOCK_Stream if things go well... + +int +ACE_SOCK_Connector::connect (ACE_SOCK_Stream &new_stream, + const ACE_Addr &remote_sap, + ACE_Time_Value *timeout, + const ACE_Addr &local_sap, + int reuse_addr, + int /* flags */, + int /* perms */, + int protocol_family, + int protocol) +{ + ACE_TRACE ("ACE_SOCK_Connector::connect"); + if (this->shared_connect_start (new_stream, + timeout, + local_sap, + reuse_addr, + protocol_family, + protocol) == -1) + return -1; + + int result = ACE_OS::connect (new_stream.get_handle (), + (sockaddr *) remote_sap.get_addr (), + remote_sap.get_size ()); + + return this->shared_connect_finish (new_stream, + timeout, + result); +} + +int +ACE_SOCK_Connector::connect (ACE_SOCK_Stream &new_stream, + const ACE_Addr &remote_sap, + ACE_Connect_QoS_Params qos_params, + ACE_Time_Value *timeout, + const ACE_Addr &local_sap, + int reuse_addr, + int /* flags */, + int /* perms */, + int protocol_family, + int protocol) +{ + ACE_TRACE ("ACE_SOCK_Connector::connect"); + if (this->shared_connect_start (new_stream, + timeout, + local_sap, + reuse_addr, + protocol_family, + protocol) == -1) + return -1; + + int result = ACE_OS::connect (new_stream.get_handle (), + (sockaddr *) remote_sap.get_addr (), + remote_sap.get_size (), + qos_params); + + return this->shared_connect_finish (new_stream, + timeout, + result); +} // Try to complete a non-blocking connection. @@ -118,8 +172,9 @@ ACE_SOCK_Connector::complete (ACE_SOCK_Stream &new_stream, ACE_Time_Value time (0, ACE_NON_BLOCKING_BUG_DELAY); ACE_OS::sleep (time); #endif /* ACE_HAS_BROKEN_NON_BLOCKING_CONNECTS */ - ACE_HANDLE h = ACE::handle_timed_complete (new_stream.get_handle (), tv); - + ACE_HANDLE h = ACE::handle_timed_complete (new_stream.get_handle (), + tv); + // We failed to get connected. if (h == ACE_INVALID_HANDLE) { // Save/restore errno. @@ -127,28 +182,82 @@ ACE_SOCK_Connector::complete (ACE_SOCK_Stream &new_stream, new_stream.close (); return -1; } - else // We've successfully connected! + else if (remote_sap != 0) { - if (remote_sap != 0) + int len = remote_sap->get_size (); + sockaddr *addr = (sockaddr *) remote_sap->get_addr (); + + if (ACE_OS::getpeername (h, + addr, + &len) == -1) { - int len; - - len = remote_sap->get_size (); - sockaddr *addr = (sockaddr *) remote_sap->get_addr (); - - if (ACE_OS::getpeername (h, addr, &len) == -1) - { - // Save/restore errno. - ACE_Errno_Guard error (errno); - new_stream.close (); - return -1; - } + // Save/restore errno. + ACE_Errno_Guard error (errno); + new_stream.close (); + return -1; } - - // Start out with non-blocking disabled on the <new_stream>. - new_stream.disable (ACE_NONBLOCK); - return 0; } + + // Start out with non-blocking disabled on the <new_stream>. + new_stream.disable (ACE_NONBLOCK); + return 0; } +ACE_SOCK_Connector::ACE_SOCK_Connector (ACE_SOCK_Stream &new_stream, + const ACE_Addr &remote_sap, + ACE_Time_Value *timeout, + const ACE_Addr &local_sap, + int reuse_addr, + int flags, + int perms, + int protocol_family, + int protocol) +{ + ACE_TRACE ("ACE_SOCK_Connector::ACE_SOCK_Connector"); + + if (this->connect (new_stream, + remote_sap, + timeout, + local_sap, + reuse_addr, + flags, + perms, + protocol_family, + protocol) == -1 + && timeout != 0 + && !(errno == EWOULDBLOCK || errno == ETIME)) + ACE_ERROR ((LM_ERROR, + ASYS_TEXT ("%p\n"), + ASYS_TEXT ("ACE_SOCK_Connector::ACE_SOCK_Connector"))); +} + +ACE_SOCK_Connector::ACE_SOCK_Connector (ACE_SOCK_Stream &new_stream, + const ACE_Addr &remote_sap, + ACE_Connect_QoS_Params qos_params, + ACE_Time_Value *timeout, + const ACE_Addr &local_sap, + int reuse_addr, + int flags, + int perms, + int protocol_family, + int protocol) +{ + ACE_TRACE ("ACE_SOCK_Connector::ACE_SOCK_Connector"); + + if (this->connect (new_stream, + remote_sap, + qos_params, + timeout, + local_sap, + reuse_addr, + flags, + perms, + protocol_family, + protocol) == -1 + && timeout != 0 + && !(errno == EWOULDBLOCK || errno == ETIME)) + ACE_ERROR ((LM_ERROR, + ASYS_TEXT ("%p\n"), + ASYS_TEXT ("ACE_SOCK_Connector::ACE_SOCK_Connector"))); +} diff --git a/ace/SOCK_Connector.h b/ace/SOCK_Connector.h index 57d52903f52..e6abeb6a0e9 100644 --- a/ace/SOCK_Connector.h +++ b/ace/SOCK_Connector.h @@ -61,8 +61,30 @@ public: // the OS do the binding. If <reuse_addr> == 1 then the // <local_addr> is reused, even if it hasn't been cleanedup yet. - ~ACE_SOCK_Connector (void); - // Default dtor. + ACE_SOCK_Connector (ACE_SOCK_Stream &new_stream, + const ACE_Addr &remote_sap, + ACE_Connect_QoS_Params qos_params, + ACE_Time_Value *timeout = 0, + const ACE_Addr &local_sap = ACE_Addr::sap_any, + int reuse_addr = 0, + int flags = 0, + int perms = 0, + int protocol_family = PF_INET, + int protocol = 0); + // Actively connect and produce a <new_stream> if things go well. + // The <remote_sap> is the address that we are trying to connect + // with. The <qos_params> contains QoS parameters that are passed + // to RSVP. The <timeout> is the amount of time to wait to connect. + // If it's 0 then we block indefinitely. If *timeout == {0, 0} then + // the connection is done using non-blocking mode. In this case, if + // the connection can't be made immediately the value of -1 is + // returned with <errno == EWOULDBLOCK>. If *timeout > {0, 0} then + // this is the amount of time to wait before timing out. If the + // time expires before the connection is made <errno == ETIME>. The + // <local_sap> is the value of local address to bind to. If it's + // the default value of <ACE_Addr::sap_any> then the user is letting + // the OS do the binding. If <reuse_addr> == 1 then the + // <local_addr> is reused, even if it hasn't been cleanedup yet. int connect (ACE_SOCK_Stream &new_stream, const ACE_Addr &remote_sap, @@ -87,6 +109,34 @@ public: // the OS do the binding. If <reuse_addr> == 1 then the // <local_addr> is reused, even if it hasn't been cleanedup yet. + int connect (ACE_SOCK_Stream &new_stream, + const ACE_Addr &remote_sap, + ACE_Connect_QoS_Params qos_params, + ACE_Time_Value *timeout = 0, + const ACE_Addr &local_sap = ACE_Addr::sap_any, + int reuse_addr = 0, + int flags = 0, + int perms = 0, + int protocol_family = PF_INET, + int protocol = 0); + // Actively connect and produce a <new_stream> if things go well. + // The <remote_sap> is the address that we are trying to connect + // with. The <qos_params> contains QoS parameters that are passed + // to RSVP. The <timeout> is the amount of time to wait to connect. + // If it's 0 then we block indefinitely. If *timeout == {0, 0} then + // the connection is done using non-blocking mode. In this case, if + // the connection can't be made immediately the value of -1 is + // returned with <errno == EWOULDBLOCK>. If *timeout > {0, 0} then + // this is the amount of time to wait before timing out. If the + // time expires before the connection is made <errno == ETIME>. The + // <local_sap> is the value of local address to bind to. If it's + // the default value of <ACE_Addr::sap_any> then the user is letting + // the OS do the binding. If <reuse_addr> == 1 then the + // <local_addr> is reused, even if it hasn't been cleanedup yet. + + ~ACE_SOCK_Connector (void); + // Default dtor. + // = Completion routine. int complete (ACE_SOCK_Stream &new_stream, ACE_Addr *remote_sap = 0, @@ -108,6 +158,20 @@ public: ACE_ALLOC_HOOK_DECLARE; // Declare the dynamic allocation hooks. + +protected: + int shared_connect_start (ACE_SOCK_Stream &new_stream, + ACE_Time_Value *timeout, + const ACE_Addr &local_sap, + int reuse_addr, + int protocol_family, + int protocol); + // Perform operations that must be called before <ACE_OS::connect>. + + int shared_connect_finish (ACE_SOCK_Stream &new_stream, + ACE_Time_Value *timeout, + int result); + // Perform operations that must be called after <ACE_OS::connect>. }; #if !defined (ACE_LACKS_INLINE_FUNCTIONS) diff --git a/ace/SOCK_Connector.i b/ace/SOCK_Connector.i index ebce17c7f53..c4801c01cf0 100644 --- a/ace/SOCK_Connector.i +++ b/ace/SOCK_Connector.i @@ -12,24 +12,6 @@ ACE_SOCK_Connector::~ACE_SOCK_Connector (void) ACE_TRACE ("ACE_SOCK_Connector::~ACE_SOCK_Connector"); } -ASYS_INLINE -ACE_SOCK_Connector::ACE_SOCK_Connector (ACE_SOCK_Stream &new_stream, - const ACE_Addr &remote_sap, - ACE_Time_Value *timeout, - const ACE_Addr &local_sap, - int reuse_addr, - int flags, - int perms, - int protocol_family, - int protocol) -{ - ACE_TRACE ("ACE_SOCK_Connector::ACE_SOCK_Connector"); - if (this->connect (new_stream, remote_sap, timeout, local_sap, - reuse_addr, flags, perms, protocol_family, protocol) == -1 - && timeout != 0 && !(errno == EWOULDBLOCK || errno == ETIME)) - ACE_ERROR ((LM_ERROR, ASYS_TEXT ("%p\n"), ASYS_TEXT ("ACE_SOCK_Connector::ACE_SOCK_Connector"))); -} - // Do-nothing constructor... ASYS_INLINE |