I2P Address: [http://git.idk.i2p]

Skip to content
Snippets Groups Projects
Commit dc04b7cf authored by mpc's avatar mpc Committed by zzz
Browse files

Some winsock improvements

parent 77a8a46d
No related branches found
No related tags found
No related merge requests found
...@@ -3,7 +3,7 @@ ...@@ -3,7 +3,7 @@
# #
# #
# Your operating system # Your operating environment
# #
OS = CYGWIN OS = CYGWIN
......
...@@ -44,6 +44,7 @@ ...@@ -44,6 +44,7 @@
#define NO_GETHOSTBYNAME2 #define NO_GETHOSTBYNAME2
#define NO_INET_ATON /* implies NO_INET_PTON */ #define NO_INET_ATON /* implies NO_INET_PTON */
#define NO_INET_NTOP #define NO_INET_NTOP
#define NO_SSIZE_T
#define NO_STRL #define NO_STRL
#define NO_Z_FORMAT #define NO_Z_FORMAT
#define WINSOCK #define WINSOCK
...@@ -103,6 +104,7 @@ ...@@ -103,6 +104,7 @@
#endif #endif
#ifdef WINSOCK #ifdef WINSOCK
#include <windows.h> #include <windows.h>
#include <winsock2.h>
#else #else
#include <unistd.h> #include <unistd.h>
#endif #endif
...@@ -112,10 +114,12 @@ ...@@ -112,10 +114,12 @@
*/ */
#ifdef WINSOCK #ifdef WINSOCK
typedef SOCKET socket_t; typedef SOCKET socket_t;
typedef signed long ssize_t;
#else #else
typedef int socket_t; typedef int socket_t;
#endif #endif
#ifdef NO_SSIZE_T
typedef signed long ssize_t;
#endif
/* /*
* Prints out the file name, line number, and function name before log message * Prints out the file name, line number, and function name before log message
......
...@@ -86,7 +86,7 @@ extern samerr_t sam_connect(const char *samhost, uint16_t samport, ...@@ -86,7 +86,7 @@ extern samerr_t sam_connect(const char *samhost, uint16_t samport,
const char *destname, sam_conn_t style, uint_t tunneldepth); const char *destname, sam_conn_t style, uint_t tunneldepth);
extern void sam_naming_lookup(const char *name); extern void sam_naming_lookup(const char *name);
extern bool sam_read_buffer(void); extern bool sam_read_buffer(void);
extern char *sam_strerror(samerr_t code); extern const char *sam_strerror(samerr_t code);
/* SAM controls - callbacks */ /* SAM controls - callbacks */
extern void (*sam_diedback)(void); extern void (*sam_diedback)(void);
extern void (*sam_logback)(char *str); extern void (*sam_logback)(char *str);
......
...@@ -41,6 +41,11 @@ static samerr_t sam_session_create(const char *destname, sam_conn_t style, ...@@ -41,6 +41,11 @@ static samerr_t sam_session_create(const char *destname, sam_conn_t style,
uint_t tunneldepth); uint_t tunneldepth);
static bool sam_socket_connect(const char *host, uint16_t port); static bool sam_socket_connect(const char *host, uint16_t port);
static bool sam_socket_resolve(const char *hostname, char *ipaddr); static bool sam_socket_resolve(const char *hostname, char *ipaddr);
#ifdef WINSOCK
static samerr_t sam_winsock_cleanup(void);
static samerr_t sam_winsock_startup(void);
static const char *sam_winsock_strerror(int code);
#endif
static ssize_t sam_write(const void *buf, size_t n); static ssize_t sam_write(const void *buf, size_t n);
/* /*
...@@ -83,6 +88,8 @@ bool sam_close(void) ...@@ -83,6 +88,8 @@ bool sam_close(void)
if (closesocket(samd) == 0) { if (closesocket(samd) == 0) {
samd_connected = false; samd_connected = false;
return true; return true;
if (sam_winsock_cleanup() != SAM_OK)
return false;
#else #else
if (close(samd) == 0) { if (close(samd) == 0) {
samd_connected = false; samd_connected = false;
...@@ -132,23 +139,9 @@ samerr_t sam_connect(const char *samhost, uint16_t samport, ...@@ -132,23 +139,9 @@ samerr_t sam_connect(const char *samhost, uint16_t samport,
} }
#ifdef WINSOCK #ifdef WINSOCK
/* rc = sam_winsock_startup();
* Is Windows retarded or what? if (rc != SAM_OK)
*/ return rc;
WORD wVersionRequested;
WSADATA wsaData;
int err;
wVersionRequested = MAKEWORD(1, 1);
err = WSAStartup(wVersionRequested, &wsaData);
if (err != 0) {
SAMLOGS("WSAStartup() failed");
return SAM_SOCKET_ERROR;
}
if (LOBYTE(wsaData.wVersion) != 1 || HIBYTE(wsaData.wVersion) != 1 ) {
SAMLOGS("Bad WinSock version");
return SAM_SOCKET_ERROR;
}
#endif #endif
if (!sam_socket_connect(samhost, samport)) { if (!sam_socket_connect(samhost, samport)) {
...@@ -953,7 +946,7 @@ samerr_t sam_stream_send(sam_sid_t stream_id, const void *data, size_t size) ...@@ -953,7 +946,7 @@ samerr_t sam_stream_send(sam_sid_t stream_id, const void *data, size_t size)
* *
* Returns: error string * Returns: error string
*/ */
char *sam_strerror(samerr_t code) const char *sam_strerror(samerr_t code)
{ {
switch (code) { switch (code) {
case SAM_OK: /* Operation completed succesfully */ case SAM_OK: /* Operation completed succesfully */
...@@ -994,6 +987,177 @@ char *sam_strerror(samerr_t code) ...@@ -994,6 +987,177 @@ char *sam_strerror(samerr_t code)
} }
} }
#ifdef WINSOCK
/*
* Unloads the Winsock network subsystem
*
* Returns: SAM error code
*/
samerr_t sam_winsock_cleanup(void)
{
if (WSACleanup() == SOCKET_ERROR) {
SAMLOG("WSACleanup() failed (%s)",
sam_winsock_strerror(WSAGetLastError()));
return SAM_SOCKET_ERROR;
}
return SAM_OK;
}
/*
* Loads the Winsock network sucksystem
*
* Returns: SAM error code
*/
samerr_t sam_winsock_startup(void)
{
/*
* Is Windows retarded or what?
*/
WORD wVersionRequested;
WSADATA wsaData;
int rc;
wVersionRequested = MAKEWORD(2, 2);
rc = WSAStartup(wVersionRequested, &wsaData);
if (rc != 0) {
SAMLOG("WSAStartup() failed (%s)", sam_winsock_strerror(rc));
return SAM_SOCKET_ERROR;
}
if (LOBYTE(wsaData.wVersion) != 2 || HIBYTE(wsaData.wVersion) != 2) {
SAMLOGS("Bad Winsock version");
sam_winsock_cleanup();
return SAM_SOCKET_ERROR;
}
return SAM_OK;
}
/*
* Apparently Winsock does not have a strerror() equivalent for its functions
*
* code - code from WSAGetLastError()
*
* Returns: error string (from http://msdn.microsoft.com/library/default.asp?
* url=/library/en-us/winsock/winsock/windows_sockets_error_codes_2.asp)
*/
const char *sam_winsock_strerror(int code)
{
switch (code) {
case WSAEINTR:
return "Interrupted function call";
case WSAEACCES: // yes, that is the correct spelling
return "Permission denied";
case WSAEFAULT:
return "Bad address";
case WSAEINVAL:
return "Invalid argument";
case WSAEMFILE:
return "Too many open files";
case WSAEWOULDBLOCK:
return "Resource temporarily unavailable";
case WSAEINPROGRESS:
return "Operation now in progress";
case WSAEALREADY:
return "Operation already in progress";
case WSAENOTSOCK:
return "Socket operations on nonsocket";
case WSAEDESTADDRREQ:
return "Destination address required";
case WSAEMSGSIZE:
return "Message too long";
case WSAEPROTOTYPE:
return "Protocol wrong type for socket";
case WSAENOPROTOOPT:
return "Bad protocol option";
case WSAEPROTONOSUPPORT:
return "Protocol not supported";
case WSAESOCKTNOSUPPORT:
return "Socket type not supported";
case WSAEOPNOTSUPP:
return "Operation not supported";
case WSAEPFNOSUPPORT:
return "Protocol family not supported";
case WSAEAFNOSUPPORT:
return "Address family not supported by protocol family";
case WSAEADDRINUSE:
return "Address already in use";
case WSAEADDRNOTAVAIL:
return "Cannot assign requested address";
case WSAENETDOWN:
return "Network is down";
case WSAENETUNREACH:
return "Network is unreachable";
case WSAENETRESET:
return "Network dropped connection on reset";
case WSAECONNABORTED:
return "Software caused connection abort";
case WSAECONNRESET:
return "Connection reset by peer";
case WSAENOBUFS:
return "No buffer space available";
case WSAEISCONN:
return "Socket is already connected";
case WSAENOTCONN:
return "Socket is not connected";
case WSAESHUTDOWN:
return "Cannot send after socket shutdown";
case WSAETIMEDOUT:
return "Connection timed out";
case WSAECONNREFUSED:
return "Connection refused";
case WSAEHOSTDOWN:
return "Host is down";
case WSAEHOSTUNREACH:
return "No route to host";
case WSAEPROCLIM:
return "Too many processes";
case WSASYSNOTREADY:
return "Network subsystem is unavailable";
case WSAVERNOTSUPPORTED:
return "Winsock.dll version out of range";
case WSANOTINITIALISED:
return "Successful WSAStartup not yet performed";
case WSAEDISCON:
return "Graceful shutdown in progress";
case WSATYPE_NOT_FOUND:
return "Class type not found";
case WSAHOST_NOT_FOUND:
return "Host not found";
case WSATRY_AGAIN:
return "Nonauthoritative host not found";
case WSANO_RECOVERY:
return "This is a nonrecoverable error";
case WSANO_DATA:
return "Valid name, no data record of requested type";
/* None of this shit compiles under Mingw - who knows why...
case WSA_INVALID_HANDLE:
return "Specified event object handle is invalid";
case WSA_INVALID_PARAMETER:
return "One or more parameters are invalid";
case WSA_IO_INCOMPLETE:
return "Overlapped I/O event object not in signaled state";
case WSA_IO_PENDING:
return "Overlapped operations will complete later";
case WSA_NOT_ENOUGH_MEMORY:
return "Insufficient memory available";
case WSA_OPERATION_ABORTED:
return "Overlapped operation aborted";
case WSAINVALIDPROCTABLE:
return "Invalid procedure table from service provider";
case WSAINVALIDPROVIDER:
return "Invalid service provider version number";
case WSAPROVIDERFAILEDINIT:
return "Unable to initialize a service provider";
*/
case WSASYSCALLFAILURE:
return "System call failure";
default:
return "Unknown error";
}
}
#endif
/* /*
* Sends `n' bytes to the SAM host * Sends `n' bytes to the SAM host
* *
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment