diff options
| author | bitflash-maintainer <noreply@bitflash.invalid> | 2026-08-08 02:29:26 +0000 |
|---|---|---|
| committer | bitflash-maintainer <noreply@bitflash.invalid> | 2026-08-19 22:48:26 +0000 |
| commit | 541223daa6e6510daf3bdfdcb4dd4f6b0e38d877 (patch) | |
| tree | ec09f2f0bf24cc737bf978b4152df8a5a2e7fc07 /src/btfrv.cpp | |
| parent | 68de575503c5df5e944278cecd3129cd10f2546e (diff) | |
pool: sync-gate job creation, retry failed payouts; widen nostr relay set
- RebuildJob: no jobs with zero peers or a tip older than 30min;
mining unsynced produced orphaned blocks and payouts that can
never be paid (observed in production: 8 orphan 'found blocks')
- payout exec: on SendMoney failure requeue with 60s backoff, up to
30 attempts, instead of silently forfeiting the payment
- nostr: add oxtr.dev, nos.social, fmt.wiz.biz, current.fyi, nostr.bg
(12 relays total) for announcement redundancy
(cherry picked from commit f1986cd7e4a6f69469a2256eb96ff03f3f146792)
Diffstat (limited to 'src/btfrv.cpp')
| -rw-r--r-- | src/btfrv.cpp | 41 |
1 files changed, 26 insertions, 15 deletions
diff --git a/src/btfrv.cpp b/src/btfrv.cpp index 6ac3280..905717f 100644 --- a/src/btfrv.cpp +++ b/src/btfrv.cpp | |||
| @@ -94,31 +94,42 @@ static SOCKET ConnectTo(const char* host, unsigned short port) | |||
| 94 | { | 94 | { |
| 95 | struct addrinfo hints, *res = NULL; | 95 | struct addrinfo hints, *res = NULL; |
| 96 | memset(&hints, 0, sizeof(hints)); | 96 | memset(&hints, 0, sizeof(hints)); |
| 97 | hints.ai_family = AF_INET; | 97 | hints.ai_family = AF_UNSPEC; // IPv4 or IPv6 (some relays are v6-only) |
| 98 | hints.ai_socktype = SOCK_STREAM; | 98 | hints.ai_socktype = SOCK_STREAM; |
| 99 | char portstr[16]; sprintf(portstr, "%u", (unsigned)port); | 99 | char portstr[16]; sprintf(portstr, "%u", (unsigned)port); |
| 100 | if (getaddrinfo(host, portstr, &hints, &res) != 0 || !res) return INVALID_SOCKET; | 100 | if (getaddrinfo(host, portstr, &hints, &res) != 0 || !res) return INVALID_SOCKET; |
| 101 | SOCKET s = BtfSocketTag(socket(res->ai_family, res->ai_socktype, res->ai_protocol), SOCK_RV_DIAL); | ||
| 102 | if (s == INVALID_SOCKET) { freeaddrinfo(res); return INVALID_SOCKET; } | ||
| 103 | 101 | ||
| 104 | // Apply a short timeout only for the connect() and initial handshake so an | 102 | // Try each resolved address until one connects. |
| 105 | // unresponsive relay doesn't block the thread. Once the tunnel is live the | 103 | SOCKET s = INVALID_SOCKET; |
| 106 | // timeout is cleared -- a forwarding pipe must block indefinitely on recv(). | 104 | for (struct addrinfo* rp = res; rp != NULL; rp = rp->ai_next) |
| 105 | { | ||
| 106 | s = BtfSocketTag(socket(rp->ai_family, rp->ai_socktype, rp->ai_protocol), SOCK_RV_DIAL); | ||
| 107 | if (s == INVALID_SOCKET) | ||
| 108 | continue; | ||
| 109 | |||
| 110 | // Apply a short timeout only for the connect() and initial handshake so an | ||
| 111 | // unresponsive relay doesn't block the thread. Once the tunnel is live the | ||
| 112 | // timeout is cleared -- a forwarding pipe must block indefinitely on recv(). | ||
| 107 | #ifdef _WIN32 | 113 | #ifdef _WIN32 |
| 108 | DWORD tvShort = 10000; | 114 | DWORD tvShort = 10000; |
| 109 | setsockopt(s, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tvShort, sizeof(tvShort)); | 115 | setsockopt(s, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tvShort, sizeof(tvShort)); |
| 110 | setsockopt(s, SOL_SOCKET, SO_SNDTIMEO, (const char*)&tvShort, sizeof(tvShort)); | 116 | setsockopt(s, SOL_SOCKET, SO_SNDTIMEO, (const char*)&tvShort, sizeof(tvShort)); |
| 111 | #else | 117 | #else |
| 112 | struct timeval tvShort; tvShort.tv_sec = 10; tvShort.tv_usec = 0; | 118 | struct timeval tvShort; tvShort.tv_sec = 10; tvShort.tv_usec = 0; |
| 113 | setsockopt(s, SOL_SOCKET, SO_RCVTIMEO, &tvShort, sizeof(tvShort)); | 119 | setsockopt(s, SOL_SOCKET, SO_RCVTIMEO, (char*)&tvShort, sizeof(tvShort)); |
| 114 | setsockopt(s, SOL_SOCKET, SO_SNDTIMEO, &tvShort, sizeof(tvShort)); | 120 | setsockopt(s, SOL_SOCKET, SO_SNDTIMEO, (char*)&tvShort, sizeof(tvShort)); |
| 115 | #endif | 121 | #endif |
| 116 | 122 | ||
| 117 | if (connect(s, res->ai_addr, (int)res->ai_addrlen) != 0) | 123 | if (connect(s, rp->ai_addr, (int)rp->ai_addrlen) != 0) |
| 118 | { | 124 | { |
| 119 | CLOSESOCK(s); freeaddrinfo(res); return INVALID_SOCKET; | 125 | CLOSESOCK(s); |
| 126 | s = INVALID_SOCKET; | ||
| 127 | continue; | ||
| 128 | } | ||
| 129 | break; | ||
| 120 | } | 130 | } |
| 121 | freeaddrinfo(res); | 131 | freeaddrinfo(res); |
| 132 | if (s == INVALID_SOCKET) return INVALID_SOCKET; | ||
| 122 | 133 | ||
| 123 | // Clear the timeout -- the socket is now a live tunnel and must not | 134 | // Clear the timeout -- the socket is now a live tunnel and must not |
| 124 | // time out when idle. recv() will block until data arrives or peer closes. | 135 | // time out when idle. recv() will block until data arrives or peer closes. |