2
0
Daniele Bartolini 9 жил өмнө
parent
commit
d662f31362
1 өөрчлөгдсөн 54 нэмэгдсэн , 149 устгасан
  1. 54 149
      src/core/network/socket.h

+ 54 - 149
src/core/network/socket.h

@@ -17,6 +17,9 @@
 	#include <sys/socket.h>
 	#include <unistd.h>     // close
 	typedef int SOCKET;
+	#define INVALID_SOCKET (-1)
+	#define SOCKET_ERROR (-1)
+	#define closesocket close
 #elif CROWN_PLATFORM_WINDOWS
 	#include <winsock2.h>
 	#pragma comment(lib, "Ws2_32.lib")
@@ -24,12 +27,20 @@
 
 namespace crown
 {
+inline int last_error()
+{
+#ifdef CROWN_PLATFORM_LINUX
+	return errno;
+#elif CROWN_PLATFORM_WINDOWS
+	return WSAGetLastError();
+#endif
+}
+
 struct ConnectResult
 {
 	enum
 	{
 		SUCCESS,
-		BAD_SOCKET,
 		REFUSED,
 		TIMEOUT,
 		UNKNOWN
@@ -41,7 +52,6 @@ struct BindResult
 	enum
 	{
 		SUCCESS,
-		BAD_SOCKET,
 		ADDRESS_IN_USE,
 		UNKNOWN
 	} error;
@@ -52,7 +62,6 @@ struct AcceptResult
 	enum
 	{
 		SUCCESS,
-		BAD_SOCKET,
 		NO_CONNECTION,
 		UNKNOWN
 	} error;
@@ -64,7 +73,6 @@ struct ReadResult
 	{
 		SUCCESS,
 		WOULDBLOCK,
-		BAD_SOCKET,
 		REMOTE_CLOSED,
 		TIMEOUT,
 		UNKNOWN
@@ -78,7 +86,6 @@ struct WriteResult
 	{
 		SUCCESS,
 		WOULDBLOCK,
-		BAD_SOCKET,
 		REMOTE_CLOSED,
 		TIMEOUT,
 		UNKNOWN
@@ -94,39 +101,23 @@ struct TCPSocket
 	SOCKET _socket;
 
 	TCPSocket()
-#if CROWN_PLATFORM_POSIX
-		: _socket(0)
-#elif CROWN_PLATFORM_WINDOWS
 		: _socket(INVALID_SOCKET)
-#endif
 	{
 	}
 
 	void open()
 	{
 		_socket = ::socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
-#if CROWN_PLATFORM_POSIX
-		CE_ASSERT(_socket >= 0, "socket: errno = %d", errno);
-#elif CROWN_PLATFORM_WINDOWS
-		CE_ASSERT(_socket >= 0, "socket: WSAGetLastError = %d", WSAGetLastError());
-#endif
+		CE_ASSERT(_socket >= 0, "socket: last_error() = %d", last_error());
 	}
 
 	void close()
 	{
-#if CROWN_PLATFORM_POSIX
-		if (_socket != 0)
-		{
-			::close(_socket);
-			_socket = 0;
-		}
-#elif CROWN_PLATFORM_WINDOWS
 		if (_socket != INVALID_SOCKET)
 		{
 			::closesocket(_socket);
 			_socket = INVALID_SOCKET;
 		}
-#endif
 	}
 
 	/// Connects to the @a ip address and @a port and returns the result.
@@ -145,24 +136,16 @@ struct TCPSocket
 		ConnectResult cr;
 		cr.error = ConnectResult::SUCCESS;
 
-		if (err == 0)
-			return cr;
-#if CROWN_PLATFORM_POSIX
-		if (errno == ECONNREFUSED)
-			cr.error = ConnectResult::REFUSED;
-		else if (errno == ETIMEDOUT)
-			cr.error = ConnectResult::TIMEOUT;
-		else
-			cr.error = ConnectResult::UNKNOWN;
-#elif CROWN_PLATFORM_WINDOWS
-		int wsaerr = WSAGetLastError();
-		if (wsaerr == WSAECONNREFUSED)
-			cr.error = ConnectResult::REFUSED;
-		else if (wsaerr == WSAETIMEDOUT)
-			cr.error = ConnectResult::TIMEOUT;
-		else
-			cr.error = ConnectResult::UNKNOWN;
-#endif
+		if (err == SOCKET_ERROR)
+		{
+			if (last_error() == ECONNREFUSED)
+				cr.error = ConnectResult::REFUSED;
+			else if (last_error() == ETIMEDOUT)
+				cr.error = ConnectResult::TIMEOUT;
+			else
+				cr.error = ConnectResult::UNKNOWN;
+		}
+
 		return cr;
 	}
 
@@ -183,22 +166,14 @@ struct TCPSocket
 		BindResult br;
 		br.error = BindResult::SUCCESS;
 
-		if (err == 0)
-			return br;
-#if CROWN_PLATFORM_POSIX
-		if (errno == EBADF)
-			br.error = BindResult::BAD_SOCKET;
-		else if (errno == EADDRINUSE)
-			br.error = BindResult::ADDRESS_IN_USE;
-		else
-			br.error = BindResult::UNKNOWN;
-#elif CROWN_PLATFORM_WINDOWS
-		int wsaerr = WSAGetLastError();
-		if (wsaerr == WSAEADDRINUSE)
-			br.error = BindResult::ADDRESS_IN_USE;
-		else
-			br.error = BindResult::UNKNOWN;
-#endif
+		if (err == SOCKET_ERROR)
+		{
+			if (last_error() == EADDRINUSE)
+				br.error = BindResult::ADDRESS_IN_USE;
+			else
+				br.error = BindResult::UNKNOWN;
+		}
+
 		return br;
 	}
 
@@ -206,11 +181,7 @@ struct TCPSocket
 	void listen(u32 max)
 	{
 		int err = ::listen(_socket, max);
-#if CROWN_PLATFORM_POSIX
-		CE_ASSERT(err == 0, "listen: errno = %d", errno);
-#elif CROWN_PLATFORM_WINDOWS
-		CE_ASSERT(err == 0, "listen: WSAGetLastError = %d", WSAGetLastError());
-#endif
+		CE_ASSERT(err == 0, "listen: last_error() = %d", last_error());
 		CE_UNUSED(err);
 	}
 
@@ -221,28 +192,18 @@ struct TCPSocket
 		AcceptResult ar;
 		ar.error = AcceptResult::SUCCESS;
 
-#if CROWN_PLATFORM_POSIX
-		if (err >= 0)
-			c._socket = err;
-		else if (err == -1 && errno == EBADF)
-			ar.error = AcceptResult::BAD_SOCKET;
-		else if (err == -1 && (errno == EAGAIN || errno == EWOULDBLOCK))
-			ar.error = AcceptResult::NO_CONNECTION;
+		if (err == INVALID_SOCKET)
+		{
+			if (last_error() == EWOULDBLOCK)
+				ar.error = AcceptResult::NO_CONNECTION;
+			else
+				ar.error = AcceptResult::UNKNOWN;
+		}
 		else
-			ar.error = AcceptResult::UNKNOWN;
-#elif CROWN_PLATFORM_WINDOWS
-		if (err != INVALID_SOCKET)
 		{
 			c._socket = err;
-			return ar;
 		}
 
-		int wsaerr = WSAGetLastError();
-		if (wsaerr == WSAEWOULDBLOCK)
-			ar.error = AcceptResult::NO_CONNECTION;
-		else
-			ar.error = AcceptResult::UNKNOWN;
-#endif
 		return ar;
 	}
 
@@ -270,40 +231,17 @@ struct TCPSocket
 
 		while (to_read > 0)
 		{
-#if CROWN_PLATFORM_POSIX
-			ssize_t bytes_read = ::recv(_socket
-				, (char*)data + rr.bytes_read
-				, to_read
-				, 0
-				);
-
-			if (bytes_read == -1)
-			{
-				if (errno == EAGAIN || errno == EWOULDBLOCK)
-					rr.error = ReadResult::WOULDBLOCK;
-				else if (errno == ETIMEDOUT)
-					rr.error = ReadResult::TIMEOUT;
-				else
-					rr.error = ReadResult::UNKNOWN;
-				return rr;
-			}
-			else if (bytes_read == 0)
-			{
-				rr.error = ReadResult::REMOTE_CLOSED;
-				return rr;
-			}
-#elif CROWN_PLATFORM_WINDOWS
 			int bytes_read = ::recv(_socket
 				, (char*)data + rr.bytes_read
-				, (int)to_read
+				, to_read
 				, 0
 				);
 
 			if (bytes_read == SOCKET_ERROR)
 			{
-				if (WSAGetLastError() == WSAEWOULDBLOCK)
+				if (last_error() == EWOULDBLOCK)
 					rr.error = ReadResult::WOULDBLOCK;
-				else if (WSAGetLastError() == WSAETIMEDOUT)
+				else if (last_error() == ETIMEDOUT)
 					rr.error = ReadResult::TIMEOUT;
 				else
 					rr.error = ReadResult::UNKNOWN;
@@ -314,7 +252,7 @@ struct TCPSocket
 				rr.error = ReadResult::REMOTE_CLOSED;
 				return rr;
 			}
-#endif
+
 			to_read -= bytes_read;
 			rr.bytes_read += bytes_read;
 		}
@@ -342,44 +280,21 @@ struct TCPSocket
 		wr.error = WriteResult::SUCCESS;
 		wr.bytes_wrote = 0;
 
-		u32 to_send = size;
+		u32 to_write = size;
 
-		while (to_send > 0)
+		while (to_write > 0)
 		{
-#if CROWN_PLATFORM_POSIX
-			ssize_t bytes_wrote = ::send(_socket
-				, (char*)data + wr.bytes_wrote
-				, to_send
-				, 0
-				);
-
-			if (bytes_wrote == -1)
-			{
-				if (errno == EAGAIN || errno == EWOULDBLOCK)
-					wr.error = WriteResult::WOULDBLOCK;
-				else if (errno == ETIMEDOUT)
-					wr.error = WriteResult::TIMEOUT;
-				else
-					wr.error = WriteResult::UNKNOWN;
-				return wr;
-			}
-			else if (bytes_wrote == 0)
-			{
-				wr.error = WriteResult::REMOTE_CLOSED;
-				return wr;
-			}
-#elif CROWN_PLATFORM_WINDOWS
 			int bytes_wrote = ::send(_socket
 				, (char*)data + wr.bytes_wrote
-				, (int)to_send
+				, to_write
 				, 0
 				);
 
 			if (bytes_wrote == SOCKET_ERROR)
 			{
-				if (WSAGetLastError() == WSAEWOULDBLOCK)
+				if (last_error() == EWOULDBLOCK)
 					wr.error = WriteResult::WOULDBLOCK;
-				else if (WSAGetLastError() == WSAETIMEDOUT)
+				else if (last_error() == ETIMEDOUT)
 					wr.error = WriteResult::TIMEOUT;
 				else
 					wr.error = WriteResult::UNKNOWN;
@@ -390,8 +305,8 @@ struct TCPSocket
 				wr.error = WriteResult::REMOTE_CLOSED;
 				return wr;
 			}
-#endif
-			to_send -= bytes_wrote;
+
+			to_write -= bytes_wrote;
 			wr.bytes_wrote += bytes_wrote;
 		}
 		return wr;
@@ -428,11 +343,7 @@ struct TCPSocket
 	{
 		int optval = (int)reuse;
 		int err = setsockopt(_socket, SOL_SOCKET, SO_REUSEADDR, (const char*)&optval, sizeof(optval));
-#if CROWN_PLATFORM_POSIX
-		CE_ASSERT(err == 0, "setsockopt: errno = %d", errno);
-#elif CROWN_PLATFORM_WINDOWS
-		CE_ASSERT(err == 0, "setsockopt: WSAGetLastError = %d", WSAGetLastError());
-#endif
+		CE_ASSERT(err == 0, "setsockopt: last_error() = %d", last_error());
 		CE_UNUSED(err);
 	}
 
@@ -442,17 +353,11 @@ struct TCPSocket
 		struct timeval timeout;
 		timeout.tv_sec = seconds;
 		timeout.tv_usec = 0;
-#if CROWN_PLATFORM_POSIX
-		int err = setsockopt(_socket, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeout, sizeof(timeout));
-		CE_ASSERT(err == 0, "setsockopt: errno: %d", errno);
-		err = setsockopt(_socket, SOL_SOCKET, SO_SNDTIMEO, (char*)&timeout, sizeof(timeout));
-		CE_ASSERT(err == 0, "setsockopt: errno: %d", errno);
-#elif CROWN_PLATFORM_WINDOWS
+
 		int err = setsockopt(_socket, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeout, sizeof(timeout));
-		CE_ASSERT(err == 0, "setsockopt: WSAGetLastError: %d", WSAGetLastError());
+		CE_ASSERT(err == 0, "setsockopt: last_error(): %d", last_error());
 		err = setsockopt(_socket, SOL_SOCKET, SO_SNDTIMEO, (char*)&timeout, sizeof(timeout));
-		CE_ASSERT(err == 0, "setsockopt: WSAGetLastError: %d", WSAGetLastError());
-#endif
+		CE_ASSERT(err == 0, "setsockopt: last_error(): %d", last_error());
 		CE_UNUSED(err);
 	}
 };