From 4a46694f01117921e9153fdb74c173cb6f314bda Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=B8nstantine=20Kovalensky?= <45331093+kovalensky@users.noreply.github.com> Date: Thu, 2 Nov 2023 23:05:28 +0400 Subject: [PATCH] Announce IPv4 && IPv6 of peers! (#1017) --- bt/announce.php | 44 ++++++++++++++++++++++++++++++++----------- install/sql/mysql.sql | 4 ++-- 2 files changed, 35 insertions(+), 13 deletions(-) diff --git a/bt/announce.php b/bt/announce.php index a38755a6b..902eab511 100644 --- a/bt/announce.php +++ b/bt/announce.php @@ -121,8 +121,13 @@ if (!\TorrentPier\Helpers\IPHelper::isValid($ip)) { // Convert IP to long format $ip_sql = \TorrentPier\Helpers\IPHelper::ip2long($ip); +// Detect IP version +$ipv4 = $ipv6 = null; +$ip_version = \TorrentPier\Helpers\IPHelper::isValidv6($ip) ? 'ipv6' : 'ip'; +($ip_version === 'ipv6') ? ($ipv6 = $ip_sql) : ($ipv4 = $ip_sql); + // Peer unique id -$peer_hash = hash('xxh128', $passkey . $info_hash_hex); +$peer_hash = hash('xxh128', $passkey . $info_hash_hex . $port); // Events $stopped = ($event === 'stopped'); @@ -140,11 +145,12 @@ if ($stopped && $lp_info) { // Drop fast announce if ($lp_info && (!isset($event) || !$stopped)) { - if ($lp_cached_peers = CACHE('tr_cache')->get(PEERS_LIST_PREFIX . $lp_info['topic_id'])) { - drop_fast_announce($lp_info, $lp_cached_peers); // Use cache but with new calculated interval and seed, peer count set + if ($lp_info['ip_ver4'] === $ipv4 || $lp_info['ip_ver6'] === $ipv6) { + if ($lp_cached_peers = CACHE('tr_cache')->get(PEERS_LIST_PREFIX . $lp_info['topic_id'])) { + drop_fast_announce($lp_info, $lp_cached_peers); // Use cache but with new calculated interval and seed, peer count set + } } } - // Get last peer info from DB if (!CACHE('tr_cache')->used && !$lp_info) { $lp_info = DB()->fetch_row(" @@ -245,7 +251,7 @@ if ($lp_info) { WHERE topic_id = $topic_id AND user_id = $user_id AND seeder = $seeder - AND ip != '$ip_sql'"; + AND $ip_version != '$ip_sql'"; if (!$seeder && $bb_cfg['tracker']['leech_expire_factor']) { $sql .= " AND update_time > " . (TIMENOW - 60 * $bb_cfg['tracker']['leech_expire_factor']); @@ -301,6 +307,7 @@ if (isset($hybrid_tor_update) || !isset($is_hybrid)) { // Update statistics only if ($lp_info) { $sql = "UPDATE " . BB_BT_TRACKER . " SET update_time = $update_time"; + $sql .= ", $ip_version = '$ip_sql'"; $sql .= ", seeder = $seeder"; $sql .= ($releaser != $lp_info['releaser']) ? ", releaser = $releaser" : ''; @@ -328,7 +335,8 @@ if (isset($hybrid_tor_update) || !isset($is_hybrid)) { // Update statistics only } if (!$lp_info || !$peer_info_updated) { - $columns = 'peer_hash, topic_id, user_id, ip, port, seeder, releaser, tor_type, uploaded, downloaded, remain, speed_up, speed_down, up_add, down_add, update_time, complete, peer_id'; + + $columns = "peer_hash, topic_id, user_id, $ip_version, port, seeder, releaser, tor_type, uploaded, downloaded, remain, speed_up, speed_down, up_add, down_add, update_time, complete, peer_id"; $values = "'$peer_hash', $topic_id, $user_id, '$ip_sql', $port, $seeder, $releaser, $tor_type, $uploaded, $downloaded, $left, $speed_up, $speed_down, $up_add, $down_add, $update_time, $complete, '$peer_id_sql'"; DB()->query("REPLACE INTO " . BB_BT_TRACKER . " ($columns) VALUES ($values)"); @@ -351,6 +359,8 @@ $lp_info = [ 'user_id' => (int)$user_id, 'tor_type' => (int)$tor_type, 'complete' => (int)$complete, + 'ip_ver4' => $lp_info['ip_ver4'] ?? $ipv4, + 'ip_ver6' => $lp_info['ip_ver6'] ?? $ipv6, ]; $lp_info_cached = CACHE('tr_cache')->set(PEER_HASH_PREFIX . $peer_hash, $lp_info, PEER_HASH_EXPIRE); @@ -364,7 +374,7 @@ if (!$output) { $compact_mode = ($bb_cfg['tracker']['compact_mode'] || !empty($compact)); $rowset = DB()->fetch_rowset(" - SELECT ip, port + SELECT ip, ipv6, port FROM " . BB_BT_TRACKER . " WHERE topic_id = $topic_id ORDER BY seeder ASC, RAND() @@ -381,15 +391,27 @@ if (!$output) { $peers6 = ''; foreach ($rowset as $peer) { - $peer_ip = \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ip']); - $peer_ip_endian = inet_pton($peer_ip) . pack('n', $peer['port']); - \TorrentPier\Helpers\IPHelper::isValidv6($peer_ip) ? ($peers6 .= $peer_ip_endian) : ($peers .= $peer_ip_endian); + if (!empty($peer['ip'])){ + $peer_ipv4 = \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ip']); + $peers .= inet_pton($peer_ipv4) . pack('n', $peer['port']); + } + if (!empty($peer['ipv6'])){ + $peer_ipv6 = \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ipv6']); + $peers6 .= inet_pton($peer_ipv6) . pack('n', $peer['port']); + } } } else { $peers = []; foreach ($rowset as $peer) { - $peers[] = ['ip' => \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ip']), 'port' => (int)$peer['port']]; + if (!empty($peer['ip'])){ + $peer_ipv4 = \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ip']); + $peers[] = ['ip' => \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ip']), 'port' => (int)$peer['port']]; + } + if (!empty($peer['ipv6'])){ + $peer_ipv6 = \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ipv6']); + $peers[] = ['ip' => \TorrentPier\Helpers\IPHelper::long2ip_extended($peer['ipv6']), 'port' => (int)$peer['port']]; + } } } diff --git a/install/sql/mysql.sql b/install/sql/mysql.sql index f912da240..309ead97a 100644 --- a/install/sql/mysql.sql +++ b/install/sql/mysql.sql @@ -358,8 +358,8 @@ CREATE TABLE IF NOT EXISTS `bb_bt_tracker` `topic_id` MEDIUMINT(8) UNSIGNED NOT NULL DEFAULT '0', `peer_id` VARCHAR(20) NOT NULL DEFAULT '0', `user_id` MEDIUMINT(9) NOT NULL DEFAULT '0', - `ip` VARCHAR(42) NOT NULL DEFAULT '0', - `ipv6` VARCHAR(32) DEFAULT NULL, + `ip` VARCHAR(42) DEFAULT NULL, + `ipv6` VARCHAR(42) DEFAULT NULL, `port` SMALLINT(5) UNSIGNED NOT NULL DEFAULT '0', `client` VARCHAR(51) NOT NULL DEFAULT 'Unknown', `seeder` TINYINT(1) NOT NULL DEFAULT '0',