Changing the socket address causes some applications to attempt to bind the same port twice. These applications enumerate all adapters on the local machine and bind to their unique addresses so they can receive UDP broadcast messages on every connected network.
By default, binding to 0.0.0.0:<port> will only bind to the primary adapter of the machine using Windows. --- dlls/ws2_32/socket.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=50579
Your paranoid android.
=== debian9 (32 bit Chinese:China report) ===
ws2_32: sock.c:3040: Test failed: Test[1]: expected 2, got 0 sock.c:3040: Test failed: Test[2]: expected 2, got 0 sock.c:3040: Test failed: Test[1]: expected 2, got 0 sock.c:3040: Test failed: Test[2]: expected 2, got 0
On Fri, Apr 5, 2019 at 9:27 PM Michel van Langen michelvanlangen@gmail.com wrote:
Changing the socket address causes some applications to attempt to bind the same port twice. These applications enumerate all adapters on the local machine and bind to their unique addresses so they can receive UDP broadcast messages on every connected network.
By default, binding to 0.0.0.0:<port> will only bind to the primary adapter of the machine using Windows.
This won't work, it needs to bind to INADDR_ANY for broadcast packets to work properly. All of the applications that I have encountered work just fine with this (they bind to the same port as many times as you have local adapters). Is the application you encountered not using SO_REUSEADDR?
Best, Erich
The application I am trying to work iterates over all available network addresses and attempts to bind to a port on said address. The line I changed rewrites the address to INADDR_ANY and therefore results in a double bind. Because of this behaviour the applications never expects to have to use SO_REUSEADDR.
I've read deeper into the code of socket.c and found that the function interface_bind actually sets SO_REUSEADDR on the socket. While setsockopt call is successful, the SO_REUSEADDR is never actually set when the address of the socket is INADDR_ANY.
I've tried some small modifications to socket.c to mitigate this, but I haven't yet found an elegant solution. And of course, breaking the ability to receive broadcast packets is a no-no.
On 06/04/2019 20:16, Erich E. Hoover wrote:
On Fri, Apr 5, 2019 at 9:27 PM Michel van Langen michelvanlangen@gmail.com wrote:
Changing the socket address causes some applications to attempt to bind the same port twice. These applications enumerate all adapters on the local machine and bind to their unique addresses so they can receive UDP broadcast messages on every connected network.
By default, binding to 0.0.0.0:<port> will only bind to the primary adapter of the machine using Windows.
This won't work, it needs to bind to INADDR_ANY for broadcast packets to work properly. All of the applications that I have encountered work just fine with this (they bind to the same port as many times as you have local adapters). Is the application you encountered not using SO_REUSEADDR?
Best, Erich
On Sat, Apr 6, 2019 at 5:09 PM Michelle van Langen michelvanlangen@gmail.com wrote:
The application I am trying to work iterates over all available network addresses and attempts to bind to a port on said address. The line I changed rewrites the address to INADDR_ANY and therefore results in a double bind. Because of this behaviour the applications never expects to have to use SO_REUSEADDR.
The way Wine does this (it uses SO_REUSEADDR automatically) both binds should succeed just fine.
I've read deeper into the code of socket.c and found that the function interface_bind actually sets SO_REUSEADDR on the socket. While setsockopt call is successful, the SO_REUSEADDR is never actually set when the address of the socket is INADDR_ANY.
Yes, I thought that maybe you had another (non-Wine) application conflicting with the behavior of the Wine application because the non-Wine app was missing SO_REUSEADDR.
I've tried some small modifications to socket.c to mitigate this, but I haven't yet found an elegant solution. And of course, breaking the ability to receive broadcast packets is a no-no.
What exactly is the problem the application is encountering? Is it possibly checking the bind in some way that's not getsockname (that case is already covered)?
Best, Erich
It turns out that I have overlooked something. It turns out that the file descriptor is the same for both binds, which is obviously never going to work. I am now going to figure out how that happens.
Best,
Michelle
On 07/04/2019 19:44, Erich E. Hoover wrote:
On Sat, Apr 6, 2019 at 5:09 PM Michelle van Langen michelvanlangen@gmail.com wrote:
The application I am trying to work iterates over all available network addresses and attempts to bind to a port on said address. The line I changed rewrites the address to INADDR_ANY and therefore results in a double bind. Because of this behaviour the applications never expects to have to use SO_REUSEADDR.
The way Wine does this (it uses SO_REUSEADDR automatically) both binds should succeed just fine.
I've read deeper into the code of socket.c and found that the function interface_bind actually sets SO_REUSEADDR on the socket. While setsockopt call is successful, the SO_REUSEADDR is never actually set when the address of the socket is INADDR_ANY.
Yes, I thought that maybe you had another (non-Wine) application conflicting with the behavior of the Wine application because the non-Wine app was missing SO_REUSEADDR.
I've tried some small modifications to socket.c to mitigate this, but I haven't yet found an elegant solution. And of course, breaking the ability to receive broadcast packets is a no-no.
What exactly is the problem the application is encountering? Is it possibly checking the bind in some way that's not getsockname (that case is already covered)?
Best, Erich