boost::to_lower(net);
if (net == "ipv4") return NET_IPV4;
if (net == "ipv6") return NET_IPV6;
- if (net == "tor") return NET_TOR;
+ if (net == "tor" || net == "onion") return NET_TOR;
if (net == "i2p") return NET_I2P;
return NET_UNROUTABLE;
}
printf("SOCKS4 connecting %s\n", addrDest.ToString().c_str());
if (!addrDest.IsIPv4())
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Proxy destination is not IPv4");
}
char pszSocks4IP[] = "\4\1\0\0\0\0\0\0user";
socklen_t len = sizeof(addr);
if (!addrDest.GetSockAddr((struct sockaddr*)&addr, &len) || addr.sin_family != AF_INET)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Cannot get proxy destination address");
}
memcpy(pszSocks4IP + 2, &addr.sin_port, 2);
int ret = send(hSocket, pszSocks4, nSize, MSG_NOSIGNAL);
if (ret != nSize)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error sending to proxy");
}
char pchRet[8];
if (recv(hSocket, pchRet, 8, 0) != 8)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error reading proxy response");
}
if (pchRet[1] != 0x5a)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
if (pchRet[1] != 0x5b)
printf("ERROR: Proxy returned error %d\n", pchRet[1]);
return false;
printf("SOCKS5 connecting %s\n", strDest.c_str());
if (strDest.size() > 255)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Hostname too long");
}
char pszSocks5Init[] = "\5\1\0";
ssize_t ret = send(hSocket, pszSocks5Init, nSize, MSG_NOSIGNAL);
if (ret != nSize)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error sending to proxy");
}
char pchRet1[2];
if (recv(hSocket, pchRet1, 2, 0) != 2)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error reading proxy response");
}
if (pchRet1[0] != 0x05 || pchRet1[1] != 0x00)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Proxy failed to initialize");
}
string strSocks5("\5\1");
ret = send(hSocket, strSocks5.c_str(), strSocks5.size(), MSG_NOSIGNAL);
if (ret != (ssize_t)strSocks5.size())
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error sending to proxy");
}
char pchRet2[4];
if (recv(hSocket, pchRet2, 4, 0) != 4)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error reading proxy response");
}
if (pchRet2[0] != 0x05)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Proxy failed to accept request");
}
if (pchRet2[1] != 0x00)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
switch (pchRet2[1])
{
case 0x01: return error("Proxy error: general failure");
}
if (pchRet2[2] != 0x00)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error: malformed proxy response");
}
char pchRet3[256];
{
ret = recv(hSocket, pchRet3, 1, 0) != 1;
if (ret) {
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error reading from proxy");
}
int nRecv = pchRet3[0];
ret = recv(hSocket, pchRet3, nRecv, 0) != nRecv;
break;
}
- default: closesocket(hSocket); return error("Error: malformed proxy response");
+ default: CloseSocket(hSocket); return error("Error: malformed proxy response");
}
if (ret)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error reading from proxy");
}
if (recv(hSocket, pchRet3, 2, 0) != 2)
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return error("Error reading from proxy");
}
printf("SOCKS5 connected %s\n", strDest.c_str());
if (fcntl(hSocket, F_SETFL, fFlags | O_NONBLOCK) == -1)
#endif
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
if (connect(hSocket, (struct sockaddr*)&sockaddr, len) == SOCKET_ERROR)
{
+ int nErr = WSAGetLastError();
// WSAEINVAL is here because some legacy version of winsock uses it
- if (WSAGetLastError() == WSAEINPROGRESS || WSAGetLastError() == WSAEWOULDBLOCK || WSAGetLastError() == WSAEINVAL)
+ if (nErr == WSAEINPROGRESS || nErr == WSAEWOULDBLOCK || nErr == WSAEINVAL)
{
struct timeval timeout;
timeout.tv_sec = nTimeout / 1000;
if (nRet == 0)
{
printf("connection timeout\n");
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
if (nRet == SOCKET_ERROR)
{
printf("select() for connection failed: %i\n",WSAGetLastError());
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
socklen_t nRetSize = sizeof(nRet);
#endif
{
printf("getsockopt() for connection failed: %i\n",WSAGetLastError());
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
if (nRet != 0)
{
printf("connect() failed after select(): %s\n",strerror(nRet));
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
}
#endif
{
printf("connect() failed: %i\n",WSAGetLastError());
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
}
if (fcntl(hSocket, F_SETFL, fFlags & ~O_NONBLOCK) == SOCKET_ERROR)
#endif
{
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
return false;
break;
default:
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
}
switch(nameproxy.second) {
default:
case 4:
- closesocket(hSocket);
+ CloseSocket(hSocket);
return false;
case 5:
if (!Socks5(strDest, port, hSocket))
{
port = portIn;
}
+
+bool CloseSocket(SOCKET& hSocket)
+{
+ if (hSocket == INVALID_SOCKET)
+ return false;
+#ifdef WIN32
+ int ret = closesocket(hSocket);
+#else
+ int ret = close(hSocket);
+#endif
+ hSocket = INVALID_SOCKET;
+ return ret != SOCKET_ERROR;
+}
\ No newline at end of file