| Summary: | port allocation/deallocation needs to be made thread-safe | ||||||||
|---|---|---|---|---|---|---|---|---|---|
| Product: | [Fedora] Fedora | Reporter: | Stefan Berger <stefanb> | ||||||
| Component: | libnl | Assignee: | Dan Williams <dcbw> | ||||||
| Status: | CLOSED ERRATA | QA Contact: | Fedora Extras Quality Assurance <extras-qa> | ||||||
| Severity: | urgent | Docs Contact: | |||||||
| Priority: | high | ||||||||
| Version: | 14 | CC: | dcbw, nhorman, tgraf | ||||||
| Target Milestone: | --- | ||||||||
| Target Release: | --- | ||||||||
| Hardware: | Unspecified | ||||||||
| OS: | Linux | ||||||||
| Whiteboard: | |||||||||
| Fixed In Version: | libnl-1.1-14.fc14 | Doc Type: | Bug Fix | ||||||
| Doc Text: | Story Points: | --- | |||||||
| Clone Of: | |||||||||
| : | 677724 (view as bug list) | Environment: | |||||||
| Last Closed: | 2011-04-12 21:24:14 UTC | Type: | --- | ||||||
| Regression: | --- | Mount Type: | --- | ||||||
| Documentation: | --- | CRM: | |||||||
| Verified Versions: | Category: | --- | |||||||
| oVirt Team: | --- | RHEL 7.3 requirements from Atomic Host: | |||||||
| Cloudforms Team: | --- | Target Upstream Version: | |||||||
| Attachments: |
|
||||||||
Created attachment 478874 [details]
make libnl thread safe and fix a port allocation bug
Here's the fix that I built libnl with. I did not link with -lpthread, so you may want to add this.
Index: libnl-1.1/lib/socket.c
===================================================================
--- libnl-1.1/lib.orig/socket.c
+++ libnl-1.1/lib/socket.c
@@ -89,6 +89,8 @@
* @{
*/
+#include <pthread.h>
+
#include <netlink-local.h>
#include <netlink/netlink.h>
#include <netlink/utils.h>
@@ -117,12 +119,15 @@ static void __init init_default_cb(void)
}
static uint32_t used_ports_map[32];
+static pthread_mutex_t port_map_mutex = PTHREAD_MUTEX_INITIALIZER;
static uint32_t generate_local_port(void)
{
int i, n;
uint32_t pid = getpid() & 0x3FFFFF;
+ pthread_mutex_lock(&port_map_mutex);
+
for (i = 0; i < 32; i++) {
if (used_ports_map[i] == 0xFFFFFFFF)
continue;
@@ -136,11 +141,15 @@ static uint32_t generate_local_port(void
/* PID_MAX_LIMIT is currently at 2^22, leaving 10 bit
* to, i.e. 1024 unique ports per application. */
- return pid + (n << 22);
+ pthread_mutex_unlock(&port_map_mutex);
+
+ return pid + (n << 22);
}
}
+ pthread_mutex_unlock(&port_map_mutex);
+
/* Out of sockets in our own PID namespace, what to do? FIXME */
return UINT_MAX;
}
@@ -153,7 +162,10 @@ static void release_local_port(uint32_t
return;
nr = port >> 22;
- used_ports_map[nr / 32] &= ~((nr % 32) + 1);
+
+ pthread_mutex_lock(&port_map_mutex);
+ used_ports_map[nr / 32] &= ~(1 << (nr & 0x1f));
+ pthread_mutex_unlock(&port_map_mutex);
}
/**
Created attachment 480973 [details]
patch against libnl-1.1-12
I added a hunk so that the final library also gets linked with -lpthread. This is necessary due to the mutex being used to protect the global used_ports_map.
Thomas, what do you think? What sort of solution would you apply upstream? I can ship this patch in the mean time. libnl-1.1-14.fc15 has been submitted as an update for Fedora 15. https://admin.fedoraproject.org/updates/libnl-1.1-14.fc15 libnl-1.1-14.fc14 has been submitted as an update for Fedora 14. https://admin.fedoraproject.org/updates/libnl-1.1-14.fc14 libnl-1.1-14.fc13 has been submitted as an update for Fedora 13. https://admin.fedoraproject.org/updates/libnl-1.1-14.fc13 I can't think of any better alternatives. I will merge this upstream. libnl-1.1-14.fc14 has been pushed to the Fedora 14 stable repository. If problems still persist, please make note of it in this bug report. libnl-1.1-14.fc13 has been pushed to the Fedora 13 stable repository. If problems still persist, please make note of it in this bug report. libnl-1.1-14.fc15 has been pushed to the Fedora 15 stable repository. If problems still persist, please make note of it in this bug report. |
Description of problem: The port allocation/deallocation in socket.c needs to be made thread-safe. Too many different callers hidden in libraries (netcf) may call this code at the same time and corrupt the port allocation. Concrete problem may arise in libvirt. Since I am a nice guy I provide you a patch, which I haven't tested, though: Index: lib/socket.c =================================================================== --- lib.orig/socket.c +++ lib/socket.c @@ -89,6 +89,8 @@ * @{ */ +#include <pthread.h> + #include <netlink-local.h> #include <netlink/netlink.h> #include <netlink/utils.h> @@ -117,12 +119,15 @@ static void __init init_default_cb(void) } static uint32_t used_ports_map[32]; +static pthread_mutex_t port_map_mutex = PTHREAD_MUTEX_INITIALIZER; static uint32_t generate_local_port(void) { int i, n; uint32_t pid = getpid() & 0x3FFFFF; + pthread_mutex_lock(&port_map_mutex); + for (i = 0; i < 32; i++) { if (used_ports_map[i] == 0xFFFFFFFF) continue; @@ -141,6 +146,8 @@ static uint32_t generate_local_port(void } } + pthread_mutex_unlock(&port_map_mutex); + /* Out of sockets in our own PID namespace, what to do? FIXME */ return UINT_MAX; } @@ -152,8 +159,12 @@ static void release_local_port(uint32_t if (port == UINT_MAX) return; + nr = port >> 22; - used_ports_map[nr / 32] &= ~((nr % 32) + 1); + + pthread_mutex_lock(&port_map_mutex); + used_ports_map[nr / 32] &= ~(1 << (nr & 0x1f)); + pthread_mutex_unlock(&port_map_mutex); } /** Now need to link against -lpthread as well. Version-Release number of selected component (if applicable): libnl-1.1-12.fc14.x86_64 libnl-debuginfo-1.1-12.fc14.x86_64 libnl-devel-1.1-12.fc14.x86_64