Added patch to avoid race-conditions of async WSARecv() operations with write watches.

This commit is contained in:
Sebastian Lackner 2014-11-22 01:52:41 +01:00
parent cc1292a1ac
commit 50b6b69053
5 changed files with 84 additions and 1 deletions

View File

@ -39,8 +39,9 @@ Wine. All those differences are also documented on the
Included bug fixes and improvements
===================================
**Bugfixes and features included in the next upcoming release [2]:**
**Bugfixes and features included in the next upcoming release [3]:**
* Avoid race-conditions of async WSARecv() operations with write watches.
* Implement exclusive mode in PulseAudio backend ([Wine Bug #37042](https://bugs.winehq.org/show_bug.cgi?id=37042))
* Take abs() of vertex z coordinate as FFP fog coordinate

1
debian/changelog vendored
View File

@ -4,6 +4,7 @@ wine-compholio (1.7.32) UNRELEASED; urgency=low
* Added patch for pulseaudio exclusive mode support.
* Added patch to take abs() of vertex z coordinate as FFP fog coordinate.
* Added patch to ensure ShowWindow avoids interthread no-op messages.
* Added patch to avoid race-conditions of async WSARecv() operations with write watches.
* Removed patch to close server fd is there is no space in thread inflight fd list (accepted upstream).
* Removed patch to fix bugs in StrStr functions (accepted upstream).
* Removed patches to avoid sending messages in FindWindowExW (accepted upstream).

View File

@ -118,6 +118,7 @@ PATCHLIST := \
wpcap-Dynamic_Linking.ok \
ws2_32-Connect_Time.ok \
ws2_32-TransmitFile.ok \
ws2_32-WriteWatches.ok \
wtsapi32-EnumerateProcesses.ok
.PHONY: install
@ -1870,6 +1871,18 @@ ws2_32-TransmitFile.ok:
echo '+ { "Erich E. Hoover", "ws2_32: Add support for TF_DISCONNECT and TF_REUSE_SOCKET to TransmitFile.", 1 },'; \
) > ws2_32-TransmitFile.ok
# Patchset ws2_32-WriteWatches
# |
# | Modified files:
# | * dlls/ws2_32/socket.c
# |
.INTERMEDIATE: ws2_32-WriteWatches.ok
ws2_32-WriteWatches.ok:
$(call APPLY_FILE,ws2_32-WriteWatches/0001-ws2_32-Avoid-race-conditions-of-async-WSARecv-operat.patch)
@( \
echo '+ { "Sebastian Lackner", "ws2_32: Avoid race-conditions of async WSARecv() operations with write watches.", 1 },'; \
) > ws2_32-WriteWatches.ok
# Patchset wtsapi32-EnumerateProcesses
# |
# | This patchset fixes the following Wine bugs:

View File

@ -0,0 +1,67 @@
From dc07ceb5dff69b2a306278d5d3254c18c98205df Mon Sep 17 00:00:00 2001
From: Sebastian Lackner <sebastian@fds-team.de>
Date: Fri, 21 Nov 2014 12:22:46 +0100
Subject: ws2_32: Avoid race-conditions of async WSARecv() operations with
write watches.
Under specific circumstances Silverlight resets the write watch while the async
WSARecv() operation is still pending:
23723.867:003a:Call ws2_32.WSARecv(00000400,018eac80,00000001,0815df24,0815df28,0196132c,00000000) ret=7a3a8197
[...]
23723.868:003a:Call KERNEL32.IsBadWritePtr(028f3368,00015554) ret=205465c4
23723.868:003a:Ret KERNEL32.IsBadWritePtr() retval=00000000 ret=205465c4
[...]
23723.868:003a:Ret ws2_32.WSARecv() retval=ffffffff ret=7a3a8197
23723.868:003a:Call KERNEL32.GetLastError() ret=792be2fd
23723.868:003a:Ret KERNEL32.GetLastError() retval=00000102 ret=79259875
[...]
23723.874:003d:Call KERNEL32.ResetWriteWatch(028d1000,0009ce00) ret=792ca021
23723.875:003d:Ret KERNEL32.ResetWriteWatch() retval=00000000 ret=792ca021
[...]
23723.966:003a:Call ntdll.wine_server_handle_to_fd(00000400,00000001,0815de9c,00000000) ret=2053ec7c
23723.966:003a:Ret ntdll.wine_server_handle_to_fd() retval=00000000 ret=2053ec7c
23723.966:003a:Call ntdll.wine_server_release_fd(00000400,00000081) ret=2053eca4
23723.966:003a:Ret ntdll.wine_server_release_fd() retval=00000000 ret=2053eca4
23723.966:003a:warn:winsock:wsaErrStatus errno 14, (Bad address).
This seems to work fine on Windows, most likely because the kernel handles write
watches directly, without involving usermode. To workaround this issue we repeat
recvmsg(...) when it looks like it might have failed because of write watches.
Based on the Linux kernel code it seems to be save to assume, that on EFAULT
no actually important data was lost:
http://lxr.free-electrons.com/source/net/ipv4/tcp.c#L1940
Based on the code it looks like we could savely remove the write-watch check
at the beginning of WS2_recv_base, which might make the application think
that data is immediately available.
---
dlls/ws2_32/socket.c | 11 ++++++++++-
1 file changed, 10 insertions(+), 1 deletion(-)
diff --git a/dlls/ws2_32/socket.c b/dlls/ws2_32/socket.c
index b3db306..ef86b28 100644
--- a/dlls/ws2_32/socket.c
+++ b/dlls/ws2_32/socket.c
@@ -1930,7 +1930,16 @@ static int WS2_recv( int fd, struct ws2_async *wsa )
while ((n = recvmsg(fd, &hdr, wsa->flags)) == -1)
{
- if (errno != EINTR)
+ if (errno == EFAULT)
+ {
+ unsigned int i;
+ for (i = wsa->first_iovec; i < wsa->n_iovecs; i++)
+ {
+ if (IsBadWritePtr( wsa->iovec[i].iov_base, wsa->iovec[i].iov_len ))
+ return -1;
+ }
+ }
+ else if (errno != EINTR)
return -1;
}
--
2.1.3

View File

@ -0,0 +1 @@
Fixes: Avoid race-conditions of async WSARecv() operations with write watches.