mirror of
https://github.com/RetroShare/RetroShare.git
synced 2024-12-29 01:16:20 -05:00
Port pqissl to dual stack IPv6+IPv4
Changed unix_connect signature to be more comfortable for dual stack usage Remove dead code in pqissl::pqissl(...) Adapt p3I2pBob::connectI2P() to new unix_connect Adapt extaddrfinder to new unix_connect Add sockaddr_storage_ipv4_to_ipv6 to convert from flat IPv4 to IPv4 mapped as IPv6
This commit is contained in:
parent
2170313e42
commit
b3c7d195c8
@ -3,7 +3,8 @@
|
|||||||
*
|
*
|
||||||
* 3P/PQI network interface for RetroShare.
|
* 3P/PQI network interface for RetroShare.
|
||||||
*
|
*
|
||||||
* Copyright 2007-2011 by Robert Fernie.
|
* Copyright (C) 2007-2011 Robert Fernie.
|
||||||
|
* Copyright (C) 2015-2018 Gioacchino Mazzurco <gio@eigenlab.org>
|
||||||
*
|
*
|
||||||
* This library is free software; you can redistribute it and/or
|
* This library is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Library General Public
|
* modify it under the terms of the GNU Library General Public
|
||||||
|
@ -438,43 +438,17 @@ int unix_fcntl_nonblock(int fd)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int unix_connect(int fd, const struct sockaddr *serv_addr, socklen_t socklen)
|
int unix_connect(int fd, const sockaddr_storage &serv_addr)
|
||||||
{
|
{
|
||||||
#ifdef NET_DEBUG
|
#ifdef NET_DEBUG
|
||||||
std::cerr << "unix_connect()";
|
std::cerr << __PRETTY_FUNCTION__ << std::endl;
|
||||||
std::cerr << std::endl;
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
const struct sockaddr_storage *ss_addr = (struct sockaddr_storage *) serv_addr;
|
int ret = connect( fd, (const struct sockaddr *) &serv_addr,
|
||||||
socklen_t len = socklen;
|
sizeof(struct sockaddr_in6) );
|
||||||
|
|
||||||
switch (ss_addr->ss_family)
|
|
||||||
{
|
|
||||||
case AF_INET:
|
|
||||||
len = sizeof(struct sockaddr_in);
|
|
||||||
break;
|
|
||||||
case AF_INET6:
|
|
||||||
len = sizeof(struct sockaddr_in6);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (len > socklen)
|
|
||||||
{
|
|
||||||
std::cerr << "unix_connect() ERROR len > socklen";
|
|
||||||
std::cerr << std::endl;
|
|
||||||
|
|
||||||
len = socklen;
|
|
||||||
//return EINVAL;
|
|
||||||
}
|
|
||||||
|
|
||||||
int ret = connect(fd, serv_addr, len);
|
|
||||||
|
|
||||||
/******************* WINDOWS SPECIFIC PART ******************/
|
/******************* WINDOWS SPECIFIC PART ******************/
|
||||||
#ifdef WINDOWS_SYS // WINDOWS
|
#ifdef WINDOWS_SYS // WINDOWS
|
||||||
|
|
||||||
#ifdef NET_DEBUG
|
|
||||||
std::cerr << "unix_connect()" << std::endl;
|
|
||||||
#endif
|
|
||||||
if (ret != 0)
|
if (ret != 0)
|
||||||
{
|
{
|
||||||
errno = WinToUnixError(WSAGetLastError());
|
errno = WinToUnixError(WSAGetLastError());
|
||||||
|
@ -103,7 +103,7 @@ bool getLocalAddresses(std::vector<sockaddr_storage> & addrs);
|
|||||||
int unix_close(int sockfd);
|
int unix_close(int sockfd);
|
||||||
int unix_socket(int domain, int type, int protocol);
|
int unix_socket(int domain, int type, int protocol);
|
||||||
int unix_fcntl_nonblock(int sockfd);
|
int unix_fcntl_nonblock(int sockfd);
|
||||||
int unix_connect(int sockfd, const struct sockaddr *serv_addr, socklen_t addrlen);
|
int unix_connect(int sockfd, const sockaddr_storage& serv_addr);
|
||||||
int unix_getsockopt_error(int sockfd, int *err);
|
int unix_getsockopt_error(int sockfd, int *err);
|
||||||
|
|
||||||
#ifdef WINDOWS_SYS // WINDOWS
|
#ifdef WINDOWS_SYS // WINDOWS
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
* 3P/PQI network interface for RetroShare.
|
* 3P/PQI network interface for RetroShare.
|
||||||
*
|
*
|
||||||
* Copyright 2004-2006 by Robert Fernie.
|
* Copyright 2004-2006 by Robert Fernie.
|
||||||
|
* Copyright (C) 2015-2018 Gioacchino Mazzurco <gio@eigenlab.org>
|
||||||
*
|
*
|
||||||
* This library is free software; you can redistribute it and/or
|
* This library is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Library General Public
|
* modify it under the terms of the GNU Library General Public
|
||||||
@ -96,44 +97,14 @@ static const int PQISSL_SSL_CONNECT_TIMEOUT = 30;
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
pqissl::pqissl(pqissllistener *l, PQInterface *parent, p3LinkMgr *lm)
|
pqissl::pqissl(pqissllistener *l, PQInterface *parent, p3LinkMgr *lm) :
|
||||||
:NetBinInterface(parent, parent->PeerId()),
|
NetBinInterface(parent, parent->PeerId()),
|
||||||
mLinkMgr(lm), pqil(l),
|
mLinkMgr(lm), pqil(l), mSslMtx("pqissl"), active(false), certvalid(false),
|
||||||
mSslMtx("pqissl"),
|
waiting(WAITING_NOT), sslmode(PQISSL_ACTIVE), ssl_connection(NULL),
|
||||||
active(false), certvalid(false), waiting(WAITING_NOT),
|
sockfd(-1), readpkt(NULL), pktlen(0), total_len(0), attempt_ts(0),
|
||||||
sslmode(PQISSL_ACTIVE), ssl_connection(NULL), sockfd(-1),
|
n_read_zero(0), mReadZeroTS(0), ssl_connect_timeout(0), mConnectDelay(0),
|
||||||
readpkt(NULL), pktlen(0), total_len(0),
|
mConnectTS(0), mConnectTimeout(0), mTimeoutTS(0)
|
||||||
attempt_ts(0),
|
{ sockaddr_storage_clear(remote_addr); }
|
||||||
n_read_zero(0), mReadZeroTS(0), ssl_connect_timeout(0),
|
|
||||||
mConnectDelay(0), mConnectTS(0),
|
|
||||||
mConnectTimeout(0), mTimeoutTS(0)
|
|
||||||
{
|
|
||||||
RsStackMutex stack(mSslMtx); /**** LOCKED MUTEX ****/
|
|
||||||
|
|
||||||
/* set address to zero */
|
|
||||||
sockaddr_storage_clear(remote_addr);
|
|
||||||
|
|
||||||
#ifdef PQISSL_LOG_DEBUG
|
|
||||||
rslog(RSL_DEBUG_BASIC, pqisslzone, "pqissl for PeerId: " + PeerId());
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if 0
|
|
||||||
if (!(AuthSSL::getAuthSSL()->isAuthenticated(PeerId())))
|
|
||||||
{
|
|
||||||
rslog(RSL_ALERT, pqisslzone,
|
|
||||||
"pqissl::Warning Certificate Not Approved!");
|
|
||||||
|
|
||||||
rslog(RSL_ALERT, pqisslzone,
|
|
||||||
"\t pqissl will not initialise....");
|
|
||||||
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
rslog(RSL_DEBUG_BASIC, pqisslzone,
|
|
||||||
"pqissl::Warning SSL Certificate Approval Not CHECKED??");
|
|
||||||
#endif
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
pqissl::~pqissl()
|
pqissl::~pqissl()
|
||||||
{
|
{
|
||||||
@ -151,11 +122,8 @@ pqissl::pqissl(pqissllistener *l, PQInterface *parent, p3LinkMgr *lm)
|
|||||||
|
|
||||||
int pqissl::connect(const struct sockaddr_storage &raddr)
|
int pqissl::connect(const struct sockaddr_storage &raddr)
|
||||||
{
|
{
|
||||||
RsStackMutex stack(mSslMtx); /**** LOCKED MUTEX ****/
|
RS_STACK_MUTEX(mSslMtx);
|
||||||
|
|
||||||
// reset failures
|
|
||||||
remote_addr = raddr;
|
remote_addr = raddr;
|
||||||
|
|
||||||
return ConnectAttempt();
|
return ConnectAttempt();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -636,7 +604,7 @@ int pqissl::Initiate_Connection()
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
// open socket connection to addr.
|
// open socket connection to addr.
|
||||||
int osock = unix_socket(PF_INET, SOCK_STREAM, 0);
|
int osock = unix_socket(PF_INET6, SOCK_STREAM, 0);
|
||||||
|
|
||||||
#ifdef PQISSL_LOG_DEBUG
|
#ifdef PQISSL_LOG_DEBUG
|
||||||
{
|
{
|
||||||
@ -736,10 +704,26 @@ int pqissl::Initiate_Connection()
|
|||||||
#endif
|
#endif
|
||||||
#endif // WINDOWS_SYS
|
#endif // WINDOWS_SYS
|
||||||
|
|
||||||
|
/* Systems that supports dual stack sockets defines IPV6_V6ONLY and some set
|
||||||
|
* it to 1 by default. This enable dual stack socket on such systems.
|
||||||
|
* Systems which don't support dual stack (only Windows older then XP SP3)
|
||||||
|
* will support IPv6 only and not IPv4 */
|
||||||
|
#ifdef IPV6_V6ONLY
|
||||||
|
int no = 0;
|
||||||
|
err = setsockopt(sockfd, IPPROTO_IPV6, IPV6_V6ONLY, (void *)&no, sizeof(no));
|
||||||
|
#ifdef PQISSL_DEBUG
|
||||||
|
if (err) std::cerr << __PRETTY_FUNCTION__
|
||||||
|
<< " Error setting IPv6 socket dual stack" << std::endl;
|
||||||
|
else std::cerr << __PRETTY_FUNCTION__
|
||||||
|
<< " Setting IPv6 socket dual stack" << std::endl;
|
||||||
|
#endif // PQISSL_DEBUG
|
||||||
|
#endif // IPV6_V6ONLY
|
||||||
|
|
||||||
mTimeoutTS = time(NULL) + mConnectTimeout;
|
mTimeoutTS = time(NULL) + mConnectTimeout;
|
||||||
//std::cerr << "Setting Connect Timeout " << mConnectTimeout << " Seconds into Future " << std::endl;
|
//std::cerr << "Setting Connect Timeout " << mConnectTimeout << " Seconds into Future " << std::endl;
|
||||||
|
|
||||||
if (0 != (err = unix_connect(osock, (struct sockaddr *) &addr, sizeof(addr))))
|
sockaddr_storage_ipv4_to_ipv6(addr);
|
||||||
|
if (0 != (err = unix_connect(osock, addr)))
|
||||||
{
|
{
|
||||||
std::string out;
|
std::string out;
|
||||||
rs_sprintf(out, "pqissl::Initiate_Connection() connect returns:%d -> errno: %d error: %s\n", err, errno, socket_errorType(errno).c_str());
|
rs_sprintf(out, "pqissl::Initiate_Connection() connect returns:%d -> errno: %d error: %s\n", err, errno, socket_errorType(errno).c_str());
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
* 3P/PQI network interface for RetroShare.
|
* 3P/PQI network interface for RetroShare.
|
||||||
*
|
*
|
||||||
* Copyright 2004-2006 by Robert Fernie.
|
* Copyright 2004-2006 by Robert Fernie.
|
||||||
|
* Copyright (C) 2015-2018 Gioacchino Mazzurco <gio@eigenlab.org>
|
||||||
*
|
*
|
||||||
* This library is free software; you can redistribute it and/or
|
* This library is free software; you can redistribute it and/or
|
||||||
* modify it under the terms of the GNU Library General Public
|
* modify it under the terms of the GNU Library General Public
|
||||||
@ -114,7 +115,7 @@ virtual bool cansend(uint32_t usec);
|
|||||||
|
|
||||||
virtual int close(); /* BinInterface version of reset() */
|
virtual int close(); /* BinInterface version of reset() */
|
||||||
virtual RsFileHash gethash(); /* not used here */
|
virtual RsFileHash gethash(); /* not used here */
|
||||||
virtual bool bandwidthLimited() { return true ; } // replace by !sameLAN to avoid bandwidth limiting on LAN
|
virtual bool bandwidthLimited() { return true ; }
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
@ -890,7 +890,7 @@ bool p3I2pBob::connectI2P()
|
|||||||
}
|
}
|
||||||
|
|
||||||
// create socket
|
// create socket
|
||||||
mSocket = unix_socket(AF_INET, SOCK_STREAM, 0);
|
mSocket = unix_socket(PF_INET, SOCK_STREAM, 0);
|
||||||
if (mSocket < 0)
|
if (mSocket < 0)
|
||||||
{
|
{
|
||||||
rslog(RsLog::Warning, &i2pBobLogInfo, "connectI2P_locked Failed to open socket! Socket Error: " + socket_errorType(errno));
|
rslog(RsLog::Warning, &i2pBobLogInfo, "connectI2P_locked Failed to open socket! Socket Error: " + socket_errorType(errno));
|
||||||
@ -898,7 +898,7 @@ bool p3I2pBob::connectI2P()
|
|||||||
}
|
}
|
||||||
|
|
||||||
// connect
|
// connect
|
||||||
int err = unix_connect(mSocket, (struct sockaddr *)&mI2PProxyAddr, sizeof(mI2PProxyAddr));
|
int err = unix_connect(mSocket, mI2PProxyAddr);
|
||||||
if (err != 0) {
|
if (err != 0) {
|
||||||
rslog(RsLog::Warning, &i2pBobLogInfo, "connectI2P_locked Failed to connect to BOB! Socket Error: " + socket_errorType(errno));
|
rslog(RsLog::Warning, &i2pBobLogInfo, "connectI2P_locked Failed to connect to BOB! Socket Error: " + socket_errorType(errno));
|
||||||
return false;
|
return false;
|
||||||
|
@ -94,7 +94,10 @@ static void getPage(const std::string& server_name,std::string& page)
|
|||||||
#endif
|
#endif
|
||||||
std::cerr << "ExtAddrFinder: resolved hostname " << server_name << " to " << rs_inet_ntoa(in) << std::endl;
|
std::cerr << "ExtAddrFinder: resolved hostname " << server_name << " to " << rs_inet_ntoa(in) << std::endl;
|
||||||
|
|
||||||
if(unix_connect(sockfd,(struct sockaddr *)&serveur, sizeof(serveur)) == -1)
|
sockaddr_storage server;
|
||||||
|
sockaddr_storage_setipv4(server, &serveur);
|
||||||
|
sockaddr_storage_setport(server, 80);
|
||||||
|
if(unix_connect(sockfd, server) == -1)
|
||||||
{
|
{
|
||||||
std::cerr << "ExtAddrFinder: Connection error to " << server_name << std::endl ;
|
std::cerr << "ExtAddrFinder: Connection error to " << server_name << std::endl ;
|
||||||
unix_close(sockfd);
|
unix_close(sockfd);
|
||||||
|
@ -106,6 +106,7 @@ bool sockaddr_storage_setipv6(struct sockaddr_storage &addr, const sockaddr_in6
|
|||||||
bool sockaddr_storage_ipv4_aton(struct sockaddr_storage &addr, const char *name);
|
bool sockaddr_storage_ipv4_aton(struct sockaddr_storage &addr, const char *name);
|
||||||
bool sockaddr_storage_ipv4_setport(struct sockaddr_storage &addr, const uint16_t port);
|
bool sockaddr_storage_ipv4_setport(struct sockaddr_storage &addr, const uint16_t port);
|
||||||
|
|
||||||
|
bool sockaddr_storage_ipv4_to_ipv6(sockaddr_storage &addr);
|
||||||
|
|
||||||
// comparisons.
|
// comparisons.
|
||||||
bool operator<(const struct sockaddr_storage &a, const struct sockaddr_storage &b);
|
bool operator<(const struct sockaddr_storage &a, const struct sockaddr_storage &b);
|
||||||
|
@ -265,6 +265,33 @@ bool sockaddr_storage_ipv4_aton(struct sockaddr_storage &addr, const char *name)
|
|||||||
return (1 == inet_aton(name, &(ipv4_ptr->sin_addr)));
|
return (1 == inet_aton(name, &(ipv4_ptr->sin_addr)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool sockaddr_storage_ipv4_to_ipv6(sockaddr_storage &addr)
|
||||||
|
{
|
||||||
|
#ifdef SS_DEBUG
|
||||||
|
std::cerr << __PRETTY_FUNCTION__ << std::endl;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if ( addr.ss_family == AF_INET6 ) return true;
|
||||||
|
|
||||||
|
if ( addr.ss_family == AF_INET )
|
||||||
|
{
|
||||||
|
sockaddr_in & addr_ipv4 = (sockaddr_in &) addr;
|
||||||
|
sockaddr_in6 & addr_ipv6 = (sockaddr_in6 &) addr;
|
||||||
|
|
||||||
|
u_int32_t ip = addr_ipv4.sin_addr.s_addr;
|
||||||
|
u_int16_t port = addr_ipv4.sin_port;
|
||||||
|
|
||||||
|
sockaddr_storage_clear(addr);
|
||||||
|
addr_ipv6.sin6_family = AF_INET6;
|
||||||
|
addr_ipv6.sin6_port = port;
|
||||||
|
addr_ipv6.sin6_addr.s6_addr32[3] = ip;
|
||||||
|
addr_ipv6.sin6_addr.s6_addr16[5] = (u_int16_t) 0xffff;
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/******************************** Comparisions **********************************/
|
/******************************** Comparisions **********************************/
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user