|
|
|
|
@ -68,6 +68,7 @@ struct DB_SYNC_INSTANCE {
|
|
|
|
|
int peer_count, peer_capacity; |
|
|
|
|
db_sync_insert_cb on_insert; |
|
|
|
|
void* on_insert_arg; |
|
|
|
|
uint8_t sync_gated; /* 1 = не запускать авто-синхронизацию (ждём member_sync/pubkeys) */ |
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
struct db_sync_done_cbk_entry { |
|
|
|
|
@ -1297,6 +1298,7 @@ static void db_sync_on_conn_up(struct ETCP_CONN* conn, void* arg)
|
|
|
|
|
struct SI_PEER* p = si_peer_add(si, pid); |
|
|
|
|
if (!p) continue; |
|
|
|
|
if (p->sync_state != 0) continue; |
|
|
|
|
if (si->sync_gated) continue; |
|
|
|
|
if (!conn->initialized || !conn->links_up) continue; |
|
|
|
|
{ uint8_t ek[32]; if (db_get_ed25519_pubkey(db, pid, ek) != 0) continue; } |
|
|
|
|
p->sync_state = 1; |
|
|
|
|
@ -1447,6 +1449,35 @@ void db_sync_peer_set_state(struct DB_SYNC_INSTANCE* si, uint64_t node_id, uint8
|
|
|
|
|
if (p) p->sync_state = state; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// Гейт авто-синхронизации: пока gated — инстанс не запускает sync автоматически
|
|
|
|
|
// (ждёт member_sync/pubkeys). При снятии гейта запускает sync к пирам в sync_state==0.
|
|
|
|
|
void db_sync_instance_set_gated(struct DB_SYNC_INSTANCE* si, int gated) |
|
|
|
|
{ |
|
|
|
|
if (!si || !si->enabled) return; |
|
|
|
|
gated = gated ? 1 : 0; |
|
|
|
|
if (si->sync_gated == (uint8_t)gated) return; |
|
|
|
|
si->sync_gated = (uint8_t)gated; |
|
|
|
|
if (!gated) { |
|
|
|
|
struct DB_SYNC* db = si->db_sync; |
|
|
|
|
int launched = 0; |
|
|
|
|
for (int i = 0; i < si->peer_count; i++) { |
|
|
|
|
struct SI_PEER* p = &si->peers[i]; |
|
|
|
|
if (p->sync_state != 0) continue; |
|
|
|
|
uint8_t ek[32]; |
|
|
|
|
if (db_get_ed25519_pubkey(db, p->node_id, ek) != 0) continue; |
|
|
|
|
p->sync_state = 1; p->sync_start_tb = get_time_tb(); |
|
|
|
|
db_sync_initiate_sync(si, p->node_id); |
|
|
|
|
launched++; |
|
|
|
|
} |
|
|
|
|
if (launched == 0) db_sync_resume_peer_check(db); |
|
|
|
|
DEBUG_INFO(DEBUG_CATEGORY_CHAT_SYNC, "sync [%s] → un-gated: launched sync for %d peers (mc=%u)", |
|
|
|
|
SI_SHRT(si), launched, db_count(si)); |
|
|
|
|
} else { |
|
|
|
|
DEBUG_INFO(DEBUG_CATEGORY_CHAT_SYNC, "sync [%s] → gated: auto-sync suspended (mc=%u)", |
|
|
|
|
SI_SHRT(si), db_count(si)); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
// Принудительно перезапускает синхронизацию с указанным пиром (для тестов)
|
|
|
|
|
void db_sync_reinitiate(struct DB_SYNC_INSTANCE* si, uint64_t node_id) |
|
|
|
|
{ |
|
|
|
|
@ -1517,6 +1548,7 @@ static void db_sync_peer_check_cb(void* arg)
|
|
|
|
|
for (int i = 0; i < db->instance_count; i++) { |
|
|
|
|
struct DB_SYNC_INSTANCE* si = &db->instances[i]; |
|
|
|
|
if (!si->enabled) continue; |
|
|
|
|
if (si->sync_gated) continue; |
|
|
|
|
|
|
|
|
|
int peers_found = 0; |
|
|
|
|
struct ll_entry* e = g->senders_list->head; |
|
|
|
|
@ -1776,7 +1808,7 @@ struct DB_SYNC_INSTANCE* db_sync_instance_add(struct UTUN_INSTANCE* inst, const
|
|
|
|
|
peers_found++; |
|
|
|
|
struct SI_PEER* p = si_peer_add(si, pid); |
|
|
|
|
if (!p) { DEBUG_ERROR(DEBUG_CATEGORY_CHAT_SYNC, "si_peer_add failed for %N in %s", (unsigned long long)pid, SI_TBL(si)); continue; } |
|
|
|
|
if (p->sync_state == 0 && auto_sync) { p->sync_state = 1; db_sync_initiate_sync(si, pid); peers_synced++; } |
|
|
|
|
if (p->sync_state == 0 && auto_sync && !si->sync_gated) { p->sync_state = 1; db_sync_initiate_sync(si, pid); peers_synced++; } |
|
|
|
|
} |
|
|
|
|
entry = entry->next; |
|
|
|
|
} |
|
|
|
|
|