Dear Sir: connect() in RTSPClient::openConnectionFromURL() is blocking. A practical application may not accept such a behavior. The following functions provide connect() with timeout setting on Windows(maybe work on Linux). Not very elegant but work. Please take them into consideration.
Boolean makeSocketBlocking(int sock) { #if defined(__WIN32__) || defined(_WIN32) || defined(IMN_PIM) unsigned long arg = 0; return ioctlsocket(sock, FIONBIO, &arg) == 0; #elif defined(VXWORKS) int arg = 1; return ioctl(sock, FIONBIO, (int)&arg) == 0; #else int curFlags = fcntl(sock, F_GETFL, 0); return fcntl(sock, F_SETFL, curFlags|O_NONBLOCK) >= 0; #endif } int connect(SOCKET sock, const sockaddr *name, int namelen, int timeout) { if(!makeSocketNonBlocking(sock)) { fprintf("[connect()] fail to set socket non-blocking\n"); return -1; } struct timeval tv; tv.tv_sec = timeout; tv.tv_usec = 0; fd_set rfds, wfds; FD_ZERO(&rfds); int ret = connect(sock, name, namelen); do { if(ret == SOCKET_ERROR) { #if defined(__WIN32__) || defined(_WIN32) || defined(IMN_PIM) if(WSAGetLastError() != WSAEWOULDBLOCK) { fprintf(stderr, "[connect()] WSAGetLastError() %d\n", WSAGetLastError()); ret = -1; break; } else // need select #endif { FD_SET(sock, &rfds); wfds = rfds; ret = select(sock + 1, &rfds, &wfds, 0, &tv); if(ret == 0) { fprintf(stderr, "[connect()] timeout in %ds\n", timeout); ret = -1; break; } if(FD_ISSET(sock, &rfds) || FD_ISSET(sock, &wfds)) { int error; int size = sizeof(error); if(getsockopt(sock, SOL_SOCKET, SO_ERROR, (char*)&error, &size) != 0 || error != 0) { fprintf(stderr, "[connect()] getsockopt() error %d\n", error); ret = -1; break; } } else { fprintf(stderr, "[connect()] unknown error\n"); ret = -1; break; } } ret = 0; } else ret = 0; } while(false); if(!makeSocketBlocking(sock)) { fprintf("[connect()] fail to set socket blocking\n"); ret = -1; } return ret; }
_______________________________________________ live-devel mailing list live-devel@lists.live555.com http://lists.live555.com/mailman/listinfo/live-devel