[prev in list] [next in list] [prev in thread] [next in thread]
List: kde-core-devel
Subject: [patch] KExtendedSocket and SO_REUSEADDR
From: Malte Starostik <malte () kde ! org>
Date: 2002-12-31 13:39:24
[Download RAW message or body]
[Attachment #2 (multipart/mixed)]
Hi,
as mentioned earlier, KExtendedSocket set SO_REUSEADDR too late, effectively
making it useless.
This one fixes it for me makes it possible to call setAddressReusable() before
calling listen(), the only problem I see is that the return value doesn't
represent success of setsockopt() anymore.
Okay to apply to both HEAD and bru^Hanch?
-Malte
PS: Happy New Year everyone!
["kextsock.diff" (text/x-diff)]
Index: kextsock.cpp
===================================================================
RCS file: /home/kde/kdelibs/kdecore/kextsock.cpp,v
retrieving revision 1.45
diff -u -3 -d -p -r1.45 kextsock.cpp
--- kextsock.cpp 29 Dec 2002 13:30:37 -0000 1.45
+++ kextsock.cpp 31 Dec 2002 13:38:38 -0000
@@ -108,6 +108,7 @@ public:
QSocketNotifier *qsnIn, *qsnOut;
int inMaxSize, outMaxSize;
bool emitRead, emitWrite;
+ bool addressReusable;
KExtendedSocketLookup *dns, *dnsLocal;
@@ -116,7 +117,7 @@ public:
host(QString::null), service(QString::null), localhost(QString::null), localservice(QString::null),
resolution(0), bindres(0), current(0), local(0), peer(0),
qsnIn(0), qsnOut(0), inMaxSize(-1), outMaxSize(-1), emitRead(false), emitWrite(false),
- dns(0), dnsLocal(0)
+ addressReusable(false), dns(0), dnsLocal(0)
{
timeout.tv_sec = timeout.tv_usec = 0;
}
@@ -724,15 +725,14 @@ bool KExtendedSocket::blockingMode()
bool KExtendedSocket::setAddressReusable(bool enable)
{
cleanError();
+ d->addressReusable = enable;
if (d->status < created)
- return false;
+ return true;
if (sockfd == -1)
- return false; // error!
-
- int on = (int)enable; // just to be on the safe side
+ return true;
- if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, (char*)&on, sizeof(on)) == -1)
+ if (!setAddressReusable(sockfd, enable))
{
setError(IO_UnspecifiedError, errno);
return false;
@@ -740,6 +740,18 @@ bool KExtendedSocket::setAddressReusable
return true;
}
+bool KExtendedSocket::setAddressReusable(int fd, bool enable)
+{
+ if (fd == -1)
+ return false;
+
+ int on = (int)enable; // just to be on the safe side
+
+ if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (char*)&on, sizeof(on)) == -1)
+ return false;
+ return true;
+}
+
/*
* Retrieves the reusability flag for this socket
*/
@@ -747,10 +759,10 @@ bool KExtendedSocket::addressReusable()
{
cleanError();
if (d->status < created)
- return false;
+ return d->addressReusable;
if (sockfd == -1)
- return false;
+ return d->addressReusable;
int on;
socklen_t onsiz = sizeof(on);
@@ -1067,6 +1079,8 @@ int KExtendedSocket::listen(int N)
continue;
}
+ if (d->addressReusable)
+ setAddressReusable(sockfd, true);
if (KSocks::self()->bind(sockfd, p->ai_addr, p->ai_addrlen) == -1)
{
kdDebug(170) << "Failed to bind: " << perror << endl;
@@ -1243,6 +1257,8 @@ int KExtendedSocket::connect()
setError(IO_ConnectError, errno);
if (sockfd == -1)
continue; // cannot create this socket
+ if (d->addressReusable)
+ setAddressReusable(sockfd, true);
if (KSocks::self()->bind(sockfd, q->ai_addr, q->ai_addrlen) == -1)
{
kdDebug(170) << "Bind failed: " << perror << endl;
@@ -2039,6 +2055,8 @@ void KExtendedSocket::connectionEvent()
errcode = errno;
if (sockfd == -1)
continue; // cannot create this socket
+ if (d->addressReusable)
+ setAddressReusable(sockfd, true);
if (KSocks::self()->bind(sockfd, q->ai_addr, q->ai_addrlen) == -1)
{
::close(sockfd);
Index: kextsock.h
===================================================================
RCS file: /home/kde/kdelibs/kdecore/kextsock.h,v
retrieving revision 1.30
diff -u -3 -d -p -r1.30 kextsock.h
--- kextsock.h 3 Oct 2002 13:44:52 -0000 1.30
+++ kextsock.h 31 Dec 2002 13:38:39 -0000
@@ -372,7 +372,8 @@ public:
* This function returns true if the value was set correctly. That is NOT
* the result of the set.
* @param enable if true, set address reusable
- * @return true on success, false if this is not possible in this state
+ * @return true on success, false on failure. If the socket was not yet created,
+ * the value is only remembered. In this case the return value is always true.
*/
bool setAddressReusable(bool enable);
@@ -914,6 +915,17 @@ public:
* @return the text for the given error code
*/
static QString strError(int code, int syserr);
+
+ /**
+ * Sets/unsets address reusing flag for this socket.
+ *
+ * This function returns true if the value was set correctly. That is NOT
+ * the result of the set.
+ * @param fd the file descriptor
+ * @param enable if true, set address reusable
+ * @return true on success, false on failure.
+ */
+ static bool setAddressReusable(int fd, bool enable);
protected:
virtual void virtual_hook( int id, void* data );
[Attachment #6 (application/pgp-signature)]
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic