/** Perform the delayed (thread safe) insertion into the game list */ static void NetworkGameListHandleDelayedInsert() { _network_game_list_mutex->BeginCritical(); while (_network_game_delayed_insertion_list != NULL) { NetworkGameList *ins_item = _network_game_delayed_insertion_list; _network_game_delayed_insertion_list = ins_item->next; NetworkGameList *item = NetworkGameListAddItem(ins_item->address); if (item != NULL) { if (StrEmpty(item->info.server_name)) { ClearGRFConfigList(&item->info.grfconfig); memset(&item->info, 0, sizeof(item->info)); strecpy(item->info.server_name, ins_item->info.server_name, lastof(item->info.server_name)); strecpy(item->info.hostname, ins_item->info.hostname, lastof(item->info.hostname)); item->online = false; } item->manually |= ins_item->manually; if (item->manually) NetworkRebuildHostList(); UpdateNetworkGameWindow(false); } free(ins_item); } _network_game_list_mutex->EndCritical(); }
DEF_UDP_RECEIVE_COMMAND(Client, PACKET_UDP_SERVER_RESPONSE) { NetworkGameList *item; /* Just a fail-safe.. should never happen */ if (_network_udp_server) return; DEBUG(net, 4, "[udp] server response from %s", client_addr->GetAddressAsString()); /* Find next item */ item = NetworkGameListAddItem(*client_addr); this->Recv_NetworkGameInfo(p, &item->info); item->info.compatible = true; { /* Checks whether there needs to be a request for names of GRFs and makes * the request if necessary. GRFs that need to be requested are the GRFs * that do not exist on the clients system and we do not have the name * resolved of, i.e. the name is still UNKNOWN_GRF_NAME_PLACEHOLDER. * The in_request array and in_request_count are used so there is no need * to do a second loop over the GRF list, which can be relatively expensive * due to the string comparisons. */ const GRFConfig *in_request[NETWORK_MAX_GRF_COUNT]; const GRFConfig *c; uint in_request_count = 0; for (c = item->info.grfconfig; c != NULL; c = c->next) { if (c->status == GCS_NOT_FOUND) item->info.compatible = false; if (c->status != GCS_NOT_FOUND || strcmp(c->name, UNKNOWN_GRF_NAME_PLACEHOLDER) != 0) continue; in_request[in_request_count] = c; in_request_count++; } if (in_request_count > 0) { /* There are 'unknown' GRFs, now send a request for them */ uint i; Packet packet(PACKET_UDP_CLIENT_GET_NEWGRFS); packet.Send_uint8(in_request_count); for (i = 0; i < in_request_count; i++) { this->Send_GRFIdentifier(&packet, in_request[i]); } this->SendPacket(&packet, &item->address); } } if (item->info.hostname[0] == '\0') { snprintf(item->info.hostname, sizeof(item->info.hostname), "%s", client_addr->GetHostname()); } if (client_addr->GetAddress()->ss_family == AF_INET6) { strecat(item->info.server_name, " (IPv6)", lastof(item->info.server_name)); } /* Check if we are allowed on this server based on the revision-match */ item->info.version_compatible = IsNetworkCompatibleVersion(item->info.server_revision); item->info.compatible &= item->info.version_compatible; // Already contains match for GRFs item->online = true; UpdateNetworkGameWindow(false); }