From abe2cc196abe26a1c309d66c97c6466dc17fffb3 Mon Sep 17 00:00:00 2001 From: Nekotekina Date: Mon, 23 Dec 2019 22:36:04 +0300 Subject: [PATCH] sys_net: fixup for race condition Don't reset is_connecting without checking correctness. Also cleanup dead WIN32 code. --- rpcs3/Emu/Cell/lv2/sys_net.cpp | 33 ++++++--------------------------- rpcs3/Emu/Cell/lv2/sys_net.h | 2 -- 2 files changed, 6 insertions(+), 29 deletions(-) diff --git a/rpcs3/Emu/Cell/lv2/sys_net.cpp b/rpcs3/Emu/Cell/lv2/sys_net.cpp index 64e486b8d1..f994b6d48e 100644 --- a/rpcs3/Emu/Cell/lv2/sys_net.cpp +++ b/rpcs3/Emu/Cell/lv2/sys_net.cpp @@ -81,7 +81,7 @@ void fmt_class_string::format(std::string& out, u64 arg) #ifdef _WIN32 // Workaround function for WSAPoll not reporting failed connections -void windows_poll(pollfd* fds, unsigned long nfds, int timeout, bool *connecting) +void windows_poll(pollfd* fds, unsigned long nfds, int timeout, bool* connecting) { int r = ::WSAPoll(fds, nfds, timeout); for (unsigned long i = 0; i < nfds; i++) @@ -92,7 +92,7 @@ void windows_poll(pollfd* fds, unsigned long nfds, int timeout, bool *connecting { int error = 0; socklen_t intlen = sizeof(error); - if (getsockopt(fds[i].fd, SOL_SOCKET, SO_ERROR, (char*)&error, &intlen) == -1 || error != 0) + if (getsockopt(fds[i].fd, SOL_SOCKET, SO_ERROR, reinterpret_cast(&error), &intlen) == -1 || error != 0) { // Connection silently failed connecting[i] = false; @@ -217,6 +217,7 @@ struct network_thread ::pollfd fds[lv2_socket::id_count]{}; #ifdef _WIN32 bool connecting[lv2_socket::id_count]{}; + bool was_connecting[lv2_socket::id_count]{}; #endif while (thread_ctrl::state() != thread_state::aborting) @@ -237,7 +238,8 @@ struct network_thread lv2_socket& sock = *socklist[i]; #ifdef _WIN32 - sock.is_connecting = connecting[i]; + if (was_connecting[i] && !connecting[i]) + sock.is_connecting = false; #endif if (fds[i].revents & (POLLIN | POLLHUP) && socklist[i]->events.test_and_reset(lv2_socket::poll::read)) @@ -302,6 +304,7 @@ struct network_thread 0; fds[i].revents = 0; #ifdef _WIN32 + was_connecting[i] = socklist[i]->is_connecting; connecting[i] = socklist[i]->is_connecting; #endif } @@ -349,9 +352,6 @@ error_code sys_net_bnet_accept(ppu_thread& ppu, s32 s, vm::ptr //if (!(sock.events & lv2_socket::poll::read)) { -#ifdef _WIN32 - sock.ev_set &= ~FD_ACCEPT; -#endif native_socket = ::accept(sock.socket, reinterpret_cast(&native_addr), &native_addrlen); if (native_socket != -1) @@ -373,9 +373,6 @@ error_code sys_net_bnet_accept(ppu_thread& ppu, s32 s, vm::ptr { if (events & lv2_socket::poll::read) { -#ifdef _WIN32 - sock.ev_set &= ~FD_ACCEPT; -#endif native_socket = ::accept(sock.socket, reinterpret_cast(&native_addr), &native_addrlen); if (native_socket != -1 || (result = get_last_error(!sock.so_nbio))) @@ -574,9 +571,6 @@ error_code sys_net_bnet_connect(ppu_thread& ppu, s32 s, vm::ptr(&native_error), &size) != 0 || size != sizeof(int)) @@ -605,9 +599,6 @@ error_code sys_net_bnet_connect(ppu_thread& ppu, s32 s, vm::ptr(&native_error), &size) != 0 || size != sizeof(int)) @@ -1028,9 +1019,6 @@ error_code sys_net_bnet_recvfrom(ppu_thread& ppu, s32 s, vm::ptr buf, u32 //if (!(sock.events & lv2_socket::poll::read)) { -#ifdef _WIN32 - if (!(native_flags & MSG_PEEK)) sock.ev_set &= ~FD_READ; -#endif native_result = ::recvfrom(sock.socket, reinterpret_cast(buf.get_ptr()), len, native_flags, reinterpret_cast(&native_addr), &native_addrlen); if (native_result >= 0) @@ -1052,9 +1040,6 @@ error_code sys_net_bnet_recvfrom(ppu_thread& ppu, s32 s, vm::ptr buf, u32 { if (events & lv2_socket::poll::read) { -#ifdef _WIN32 - if (!(native_flags & MSG_PEEK)) sock.ev_set &= ~FD_READ; -#endif native_result = ::recvfrom(sock.socket, reinterpret_cast(buf.get_ptr()), len, native_flags, reinterpret_cast(&native_addr), &native_addrlen); if (native_result >= 0 || (result = get_last_error(!sock.so_nbio && (flags & SYS_NET_MSG_DONTWAIT) == 0))) @@ -1204,9 +1189,6 @@ error_code sys_net_bnet_sendto(ppu_thread& ppu, s32 s, vm::cptr buf, u32 l //if (!(sock.events & lv2_socket::poll::write)) { -#ifdef _WIN32 - sock.ev_set &= ~FD_WRITE; -#endif native_result = ::sendto(sock.socket, reinterpret_cast(buf.get_ptr()), len, native_flags, addr ? reinterpret_cast(&name) : nullptr, addr ? namelen : 0); if (native_result >= 0) @@ -1228,9 +1210,6 @@ error_code sys_net_bnet_sendto(ppu_thread& ppu, s32 s, vm::cptr buf, u32 l { if (events & lv2_socket::poll::write) { -#ifdef _WIN32 - sock.ev_set &= ~FD_WRITE; -#endif native_result = ::sendto(sock.socket, reinterpret_cast(buf.get_ptr()), len, native_flags, addr ? reinterpret_cast(&name) : nullptr, addr ? namelen : 0); if (native_result >= 0 || (result = get_last_error(!sock.so_nbio && (flags & SYS_NET_MSG_DONTWAIT) == 0))) diff --git a/rpcs3/Emu/Cell/lv2/sys_net.h b/rpcs3/Emu/Cell/lv2/sys_net.h index a3c922e50b..7f3f0adfcc 100644 --- a/rpcs3/Emu/Cell/lv2/sys_net.h +++ b/rpcs3/Emu/Cell/lv2/sys_net.h @@ -334,8 +334,6 @@ struct lv2_socket final shared_mutex mutex; #ifdef _WIN32 - // Remember events (WSAEnumNetworkEvents) - u32 ev_set = 0; // Tracks connect for WSAPoll workaround bool is_connecting = false; #endif