mirror of
https://github.com/SChernykh/p2pool.git
synced 2024-11-16 15:57:39 +00:00
Added UPnP port forwarding
This commit is contained in:
parent
79ad29e99a
commit
19cc044cab
12 changed files with 95 additions and 15 deletions
6
.github/workflows/test-sync.yml
vendored
6
.github/workflows/test-sync.yml
vendored
|
@ -24,7 +24,7 @@ jobs:
|
|||
run: |
|
||||
mkdir build
|
||||
cd build
|
||||
cmake .. -DDEV_TEST_SYNC=ON -DCMAKE_C_COMPILER=gcc-12 -DCMAKE_CXX_COMPILER=g++-12
|
||||
cmake .. -DWITH_UPNP=OFF -DDEV_TEST_SYNC=ON -DCMAKE_C_COMPILER=gcc-12 -DCMAKE_CXX_COMPILER=g++-12
|
||||
make -j$(nproc)
|
||||
|
||||
- name: Run p2pool
|
||||
|
@ -60,7 +60,7 @@ jobs:
|
|||
run: |
|
||||
mkdir build
|
||||
cd build
|
||||
cmake .. -DDEV_TEST_SYNC=ON
|
||||
cmake .. -DWITH_UPNP=OFF -DDEV_TEST_SYNC=ON
|
||||
make -j3
|
||||
|
||||
- name: Run p2pool
|
||||
|
@ -96,7 +96,7 @@ jobs:
|
|||
run: |
|
||||
mkdir build
|
||||
cd build
|
||||
cmake .. -G "Visual Studio 17 2022" -DDEV_TEST_SYNC=ON
|
||||
cmake .. -G "Visual Studio 17 2022" -DWITH_UPNP=OFF -DDEV_TEST_SYNC=ON
|
||||
& "C:\\Program Files\\Microsoft Visual Studio\\2022\\Enterprise\\Msbuild\\Current\\Bin\\amd64\\msbuild" /m /p:Configuration=Debug p2pool.vcxproj
|
||||
|
||||
- name: Run p2pool
|
||||
|
|
|
@ -24,8 +24,9 @@
|
|||
--no-autodiff Disable automatic difficulty adjustment for miners connected to stratum (WARNING: incompatible with Nicehash and MRR)
|
||||
--rpc-login Specify username[:password] required for Monero RPC server
|
||||
--socks5 Specify IP:port of a SOCKS5 proxy to use for outgoing connections
|
||||
--no-dns disable DNS queries, use only IP addresses to connect to peers (seed node DNS will be unavailable too)
|
||||
--p2p-external-port port number that your router uses for mapping to your local p2p port. Use it if you are behind a NAT and still want to accept incoming connections
|
||||
--no-dns Disable DNS queries, use only IP addresses to connect to peers (seed node DNS will be unavailable too)
|
||||
--p2p-external-port Port number that your router uses for mapping to your local p2p port. Use it if you are behind a NAT and still want to accept incoming connections
|
||||
--no-upnp Disable UPnP port forwarding
|
||||
```
|
||||
|
||||
### Example command line
|
||||
|
|
|
@ -49,8 +49,11 @@ void p2pool_usage()
|
|||
"--no-autodiff Disable automatic difficulty adjustment for miners connected to stratum (WARNING: incompatible with Nicehash and MRR)\n"
|
||||
"--rpc-login Specify username[:password] required for Monero RPC server\n"
|
||||
"--socks5 Specify IP:port of a SOCKS5 proxy to use for outgoing connections\n"
|
||||
"--no-dns disable DNS queries, use only IP addresses to connect to peers (seed node DNS will be unavailable too)\n"
|
||||
"--p2p-external-port port number that your router uses for mapping to your local p2p port. Use it if you are behind a NAT and still want to accept incoming connections\n"
|
||||
"--no-dns Disable DNS queries, use only IP addresses to connect to peers (seed node DNS will be unavailable too)\n"
|
||||
"--p2p-external-port Port number that your router uses for mapping to your local p2p port. Use it if you are behind a NAT and still want to accept incoming connections\n"
|
||||
#ifdef WITH_UPNP
|
||||
"--no-upnp Disable UPnP port forwarding\n"
|
||||
#endif
|
||||
"--help Show this help message\n\n"
|
||||
"Example command line:\n\n"
|
||||
"%s --host 127.0.0.1 --rpc-port 18081 --zmq-port 18083 --wallet YOUR_WALLET_ADDRESS --stratum 0.0.0.0:%d --p2p 0.0.0.0:%d\n\n",
|
||||
|
|
|
@ -134,7 +134,7 @@ P2PServer::P2PServer(p2pool* pool)
|
|||
}
|
||||
|
||||
load_peer_list();
|
||||
start_listening(params.m_p2pAddresses);
|
||||
start_listening(params.m_p2pAddresses, params.m_upnp);
|
||||
}
|
||||
|
||||
P2PServer::~P2PServer()
|
||||
|
@ -989,7 +989,7 @@ void P2PServer::show_peers() const
|
|||
LOGINFO(0, "Total: " << n << " peers");
|
||||
}
|
||||
|
||||
int P2PServer::listen_port() const
|
||||
int P2PServer::external_listen_port() const
|
||||
{
|
||||
const Params& params = m_pool->params();
|
||||
return params.m_p2pExternalPort ? params.m_p2pExternalPort : m_listenPort;
|
||||
|
@ -1848,7 +1848,7 @@ void P2PServer::P2PClient::on_after_handshake(uint8_t* &p)
|
|||
LOGINFO(5, "sending LISTEN_PORT to " << static_cast<char*>(m_addrString));
|
||||
*(p++) = static_cast<uint8_t>(MessageId::LISTEN_PORT);
|
||||
|
||||
const int32_t port = m_owner->listen_port();
|
||||
const int32_t port = m_owner->external_listen_port();
|
||||
memcpy(p, &port, sizeof(port));
|
||||
p += sizeof(port);
|
||||
|
||||
|
|
|
@ -155,7 +155,7 @@ public:
|
|||
void show_peers_async();
|
||||
size_t peer_list_size() const { MutexLock lock(m_peerListLock); return m_peerList.size(); }
|
||||
|
||||
int listen_port() const override;
|
||||
int external_listen_port() const override;
|
||||
|
||||
uint32_t max_outgoing_peers() const { return m_maxOutgoingPeers; }
|
||||
uint32_t max_incoming_peers() const { return m_maxIncomingPeers; }
|
||||
|
|
|
@ -151,6 +151,11 @@ Params::Params(int argc, char* argv[])
|
|||
ok = true;
|
||||
}
|
||||
|
||||
if (strcmp(argv[i], "--no-upnp") == 0) {
|
||||
m_upnp = false;
|
||||
ok = true;
|
||||
}
|
||||
|
||||
if (!ok) {
|
||||
fprintf(stderr, "Unknown command line parameter %s\n\n", argv[i]);
|
||||
p2pool_usage();
|
||||
|
|
|
@ -53,6 +53,7 @@ struct Params
|
|||
std::string m_socks5Proxy;
|
||||
bool m_dns = true;
|
||||
uint32_t m_p2pExternalPort = 0;
|
||||
bool m_upnp = true;
|
||||
};
|
||||
|
||||
} // namespace p2pool
|
||||
|
|
|
@ -82,7 +82,7 @@ StratumServer::StratumServer(p2pool* pool)
|
|||
uv_async_init_checked(&m_loop, &m_showWorkersAsync, on_show_workers);
|
||||
m_showWorkersAsync.data = this;
|
||||
|
||||
start_listening(pool->params().m_stratumAddresses);
|
||||
start_listening(pool->params().m_stratumAddresses, pool->params().m_upnp);
|
||||
}
|
||||
|
||||
StratumServer::~StratumServer()
|
||||
|
|
|
@ -42,7 +42,7 @@ public:
|
|||
|
||||
uv_loop_t* get_loop() { return &m_loop; }
|
||||
|
||||
virtual int listen_port() const { return m_listenPort; }
|
||||
virtual int external_listen_port() const { return m_listenPort; }
|
||||
|
||||
bool connect_to_peer(bool is_v6, const raw_ip& ip, int port);
|
||||
virtual void on_connect_failed(bool /*is_v6*/, const raw_ip& /*ip*/, int /*port*/) {}
|
||||
|
@ -158,7 +158,7 @@ private:
|
|||
uv_thread_t m_loopThread;
|
||||
|
||||
protected:
|
||||
void start_listening(const std::string& listen_addresses);
|
||||
void start_listening(const std::string& listen_addresses, bool upnp);
|
||||
|
||||
std::string m_socks5Proxy;
|
||||
bool m_socks5ProxyV6;
|
||||
|
|
|
@ -128,7 +128,7 @@ void TCPServer<READ_BUF_SIZE, WRITE_BUF_SIZE>::parse_address_list(const std::str
|
|||
}
|
||||
|
||||
template<size_t READ_BUF_SIZE, size_t WRITE_BUF_SIZE>
|
||||
void TCPServer<READ_BUF_SIZE, WRITE_BUF_SIZE>::start_listening(const std::string& listen_addresses)
|
||||
void TCPServer<READ_BUF_SIZE, WRITE_BUF_SIZE>::start_listening(const std::string& listen_addresses, bool upnp)
|
||||
{
|
||||
if (listen_addresses.empty()) {
|
||||
LOGERR(1, "listen address not set");
|
||||
|
@ -206,6 +206,14 @@ void TCPServer<READ_BUF_SIZE, WRITE_BUF_SIZE>::start_listening(const std::string
|
|||
LOGINFO(1, "listening on " << log::Gray() << address);
|
||||
});
|
||||
|
||||
#ifdef WITH_UPNP
|
||||
if (upnp) {
|
||||
add_portmapping(external_listen_port(), m_listenPort);
|
||||
}
|
||||
#else
|
||||
(void)upnp;
|
||||
#endif
|
||||
|
||||
const int err = uv_thread_create(&m_loopThread, loop, this);
|
||||
if (err) {
|
||||
LOGERR(1, "failed to start event loop thread, error " << uv_err_name(err));
|
||||
|
|
58
src/util.cpp
58
src/util.cpp
|
@ -25,6 +25,11 @@
|
|||
#include <sched.h>
|
||||
#endif
|
||||
|
||||
#ifdef WITH_UPNP
|
||||
#include "miniupnpc.h"
|
||||
#include "upnpcommands.h"
|
||||
#endif
|
||||
|
||||
static constexpr char log_category_prefix[] = "Util ";
|
||||
|
||||
namespace p2pool {
|
||||
|
@ -560,4 +565,57 @@ UV_LoopUserData* GetLoopUserData(uv_loop_t* loop, bool create)
|
|||
return data;
|
||||
}
|
||||
|
||||
#ifdef WITH_UPNP
|
||||
static struct UPnP_Discover
|
||||
{
|
||||
UPnP_Discover() { devlist = upnpDiscover(1000, nullptr, nullptr, UPNP_LOCAL_PORT_ANY, 0, 2, &error); }
|
||||
~UPnP_Discover() { freeUPNPDevlist(devlist); }
|
||||
|
||||
int error;
|
||||
UPNPDev* devlist;
|
||||
} upnp_discover;
|
||||
|
||||
void add_portmapping(int external_port, int internal_port)
|
||||
{
|
||||
LOGINFO(1, "UPnP: trying to map WAN:" << external_port << " to LAN:" << internal_port);
|
||||
|
||||
if (!upnp_discover.devlist) {
|
||||
LOGWARN(1, "upnpDiscover: no UPnP IGD devices found, error " << upnp_discover.error);
|
||||
return;
|
||||
}
|
||||
|
||||
UPNPUrls urls;
|
||||
IGDdatas data;
|
||||
char local_addr[64] = {};
|
||||
|
||||
int result = UPNP_GetValidIGD(upnp_discover.devlist, &urls, &data, local_addr, sizeof(local_addr));
|
||||
if (result != 1) {
|
||||
LOGWARN(1, "UPNP_GetValidIGD returned " << result << ", no valid UPnP IGD devices found");
|
||||
return;
|
||||
}
|
||||
|
||||
LOGINFO(1, "UPnP: LAN IP address " << log::Gray() << static_cast<const char*>(local_addr));
|
||||
|
||||
char ext_addr[64] = {};
|
||||
result = UPNP_GetExternalIPAddress(urls.controlURL, data.first.servicetype, ext_addr);
|
||||
if ((result != UPNPCOMMAND_SUCCESS) || !ext_addr[0]) {
|
||||
LOGWARN(1, "UPNP_GetExternalIPAddress: failed to query external IP address, error " << result);
|
||||
}
|
||||
else {
|
||||
LOGINFO(1, "UPnP: WAN IP address " << log::Gray() << static_cast<const char*>(ext_addr));
|
||||
}
|
||||
|
||||
const std::string eport = std::to_string(external_port);
|
||||
const std::string iport = std::to_string(internal_port);
|
||||
|
||||
result = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype, eport.c_str(), iport.c_str(), local_addr, "P2Pool", "TCP", nullptr, nullptr);
|
||||
if (result) {
|
||||
LOGWARN(1, "UPNP_AddPortMapping returned error " << result);
|
||||
}
|
||||
else {
|
||||
LOGINFO(1, "UPnP: Mapped " << log::Gray() << static_cast<const char*>(ext_addr) << ':' << external_port << log::NoColor() << " to " << log::Gray() << static_cast<const char*>(local_addr) << ':' << internal_port);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace p2pool
|
||||
|
|
|
@ -246,6 +246,10 @@ FORCEINLINE uint64_t bsr(uint64_t x)
|
|||
bool str_to_ip(bool is_v6, const char* ip, raw_ip& result);
|
||||
bool is_localhost(const std::string& host);
|
||||
|
||||
#ifdef WITH_UPNP
|
||||
void add_portmapping(int external_port, int internal_port);
|
||||
#endif
|
||||
|
||||
} // namespace p2pool
|
||||
|
||||
void memory_tracking_start();
|
||||
|
|
Loading…
Reference in a new issue