Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Change: use TCP for everything except for master-server and initial server scan #9130

Merged
merged 1 commit into from
Apr 30, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 7 additions & 3 deletions os/emscripten/pre.js
Original file line number Diff line number Diff line change
Expand Up @@ -65,10 +65,14 @@ Module.preRun.push(function() {
}

window.openttd_server_list = function() {
add_server = Module.cwrap("em_openttd_add_server", null, ["string", "number"]);
add_server = Module.cwrap("em_openttd_add_server", null, ["string"]);

/* Add servers that support WebSocket here. Example:
* add_server("localhost", 3979); */
/* Add servers that support WebSocket here. Examples:
* add_server("localhost");
* add_server("localhost:3979");
* add_server("127.0.0.1:3979");
* add_server("[::1]:3979");
*/
}

var leftButtonDown = false;
Expand Down
1 change: 1 addition & 0 deletions src/lang/english.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2217,6 +2217,7 @@ STR_NETWORK_ERROR_TIMEOUT_COMPUTER :{WHITE}Your com
STR_NETWORK_ERROR_TIMEOUT_MAP :{WHITE}Your computer took too long to download the map
STR_NETWORK_ERROR_TIMEOUT_JOIN :{WHITE}Your computer took too long to join the server
STR_NETWORK_ERROR_INVALID_CLIENT_NAME :{WHITE}Your player name is not valid
STR_NETWORK_ERROR_SERVER_TOO_OLD :{WHITE}The queried server is too old for this client

############ Leave those lines in this order!!
STR_NETWORK_ERROR_CLIENT_GENERAL :general error
Expand Down
44 changes: 32 additions & 12 deletions src/network/network.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -602,8 +602,11 @@ static void NetworkInitialize(bool close_admins = true)

/** Non blocking connection create to query servers */
class TCPQueryConnecter : TCPConnecter {
private:
bool request_company_info;

public:
TCPQueryConnecter(const NetworkAddress &address) : TCPConnecter(address) {}
TCPQueryConnecter(const NetworkAddress &address, bool request_company_info) : TCPConnecter(address), request_company_info(request_company_info) {}

void OnFailure() override
{
Expand All @@ -613,36 +616,53 @@ class TCPQueryConnecter : TCPConnecter {
void OnConnect(SOCKET s) override
{
_networking = true;
new ClientNetworkGameSocketHandler(s);
MyClient::SendInformationQuery();
new ClientNetworkGameSocketHandler(s, address);
MyClient::SendInformationQuery(request_company_info);
}
};

/**
* Query a server to fetch his game-info.
* @param address the address to query.
* @param request_company_info Whether to request company info too.
*/
void NetworkTCPQueryServer(NetworkAddress address)
void NetworkTCPQueryServer(NetworkAddress address, bool request_company_info)
{
if (!_network_available) return;

NetworkDisconnect();
NetworkInitialize();

new TCPQueryConnecter(address);
new TCPQueryConnecter(address, request_company_info);
}

/**
* Validates an address entered as a string and adds the server to
* the list. If you use this function, the games will be marked
* as manually added.
* @param connection_string The IP:port to add to the list.
* @param connection_string The IP:port of the server to add.
* @return The entry on the game list.
*/
void NetworkAddServer(const char *connection_string)
NetworkGameList *NetworkAddServer(const std::string &connection_string)
{
if (StrEmpty(connection_string)) return;
if (connection_string.empty()) return nullptr;

NetworkAddress address = ParseConnectionString(connection_string, NETWORK_DEFAULT_PORT);

/* Ensure the item already exists in the list */
NetworkGameList *item = NetworkGameListAddItem(address);
if (StrEmpty(item->info.server_name)) {
ClearGRFConfigList(&item->info.grfconfig);
address.GetAddressAsString(item->info.server_name, lastof(item->info.server_name));
item->manually = true;

NetworkRebuildHostList();
UpdateNetworkGameWindow();
}

NetworkTCPQueryServer(address);

NetworkUDPQueryServer(ParseConnectionString(connection_string, NETWORK_DEFAULT_PORT), true);
return item;
}

/**
Expand Down Expand Up @@ -687,7 +707,7 @@ class TCPClientConnecter : TCPConnecter {
void OnConnect(SOCKET s) override
{
_networking = true;
new ClientNetworkGameSocketHandler(s);
new ClientNetworkGameSocketHandler(s, this->address);
IConsoleCmdExec("exec scripts/on_client.scr 0");
NetworkClient_Connected();
}
Expand Down Expand Up @@ -1132,9 +1152,9 @@ void NetworkShutDown()
#ifdef __EMSCRIPTEN__
extern "C" {

void CDECL em_openttd_add_server(const char *host, int port)
void CDECL em_openttd_add_server(const char *connection_string)
{
NetworkUDPQueryServer(NetworkAddress(host, port), true);
NetworkAddServer(connection_string);
}

}
Expand Down
35 changes: 27 additions & 8 deletions src/network/network_client.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ void ClientNetworkEmergencySave()
* Create a new socket for the client side of the game connection.
* @param s The socket to connect with.
*/
ClientNetworkGameSocketHandler::ClientNetworkGameSocketHandler(SOCKET s) : NetworkGameSocketHandler(s), savegame(nullptr), status(STATUS_INACTIVE)
ClientNetworkGameSocketHandler::ClientNetworkGameSocketHandler(SOCKET s, NetworkAddress address) : NetworkGameSocketHandler(s), address(address), savegame(nullptr), status(STATUS_INACTIVE)
{
assert(ClientNetworkGameSocketHandler::my_client == nullptr);
ClientNetworkGameSocketHandler::my_client = this;
Expand Down Expand Up @@ -345,14 +345,18 @@ static_assert(NETWORK_SERVER_ID_LENGTH == 16 * 2 + 1);
/**
* Query the server for server information.
*/
NetworkRecvStatus ClientNetworkGameSocketHandler::SendInformationQuery()
NetworkRecvStatus ClientNetworkGameSocketHandler::SendInformationQuery(bool request_company_info)
{
my_client->status = STATUS_COMPANY_INFO;
_network_join_status = NETWORK_JOIN_STATUS_GETTING_COMPANY_INFO;
SetWindowDirty(WC_NETWORK_STATUS_WINDOW, WN_NETWORK_STATUS_WINDOW_JOIN);

my_client->status = STATUS_GAME_INFO;
my_client->SendPacket(new Packet(PACKET_CLIENT_GAME_INFO));
my_client->SendPacket(new Packet(PACKET_CLIENT_COMPANY_INFO));

if (request_company_info) {
my_client->status = STATUS_COMPANY_INFO;
_network_join_status = NETWORK_JOIN_STATUS_GETTING_COMPANY_INFO;
SetWindowDirty(WC_NETWORK_STATUS_WINDOW, WN_NETWORK_STATUS_WINDOW_JOIN);

my_client->SendPacket(new Packet(PACKET_CLIENT_COMPANY_INFO));
}

return NETWORK_RECV_STATUS_OKAY;
}
Expand Down Expand Up @@ -577,9 +581,13 @@ NetworkRecvStatus ClientNetworkGameSocketHandler::Receive_SERVER_BANNED(Packet *

NetworkRecvStatus ClientNetworkGameSocketHandler::Receive_SERVER_GAME_INFO(Packet *p)
{
if (this->status != STATUS_COMPANY_INFO && this->status != STATUS_INACTIVE) return NETWORK_RECV_STATUS_MALFORMED_PACKET;
if (this->status != STATUS_COMPANY_INFO && this->status != STATUS_GAME_INFO) return NETWORK_RECV_STATUS_MALFORMED_PACKET;

NetworkGameList *item = GetLobbyGameInfo();
if (item == nullptr) {
/* This is not the lobby, so add it to the game list. */
item = NetworkGameListAddItem(this->address);
}

/* Clear any existing GRFConfig chain. */
ClearGRFConfigList(&item->info.grfconfig);
Expand All @@ -590,6 +598,8 @@ NetworkRecvStatus ClientNetworkGameSocketHandler::Receive_SERVER_GAME_INFO(Packe
/* Ensure we consider the server online. */
item->online = true;

/* It could be either window, but only one is open, so redraw both. */
SetWindowDirty(WC_NETWORK_WINDOW, WN_NETWORK_WINDOW_GAME);
SetWindowDirty(WC_NETWORK_WINDOW, WN_NETWORK_WINDOW_LOBBY);

/* We will receive company info next, so keep connection open. */
Expand Down Expand Up @@ -727,6 +737,15 @@ NetworkRecvStatus ClientNetworkGameSocketHandler::Receive_SERVER_ERROR(Packet *p

NetworkErrorCode error = (NetworkErrorCode)p->Recv_uint8();

/* If we query a server that is 1.11.1 or older, we get an
* NETWORK_ERROR_NOT_EXPECTED on requesting the game info. Show a special
* error popup in that case.
*/
if (error == NETWORK_ERROR_NOT_EXPECTED && (this->status == STATUS_GAME_INFO || this->status == STATUS_COMPANY_INFO)) {
ShowErrorMessage(STR_NETWORK_ERROR_SERVER_TOO_OLD, INVALID_STRING_ID, WL_CRITICAL);
return NETWORK_RECV_STATUS_CLOSE_QUERY;
}

StringID err = STR_NETWORK_ERROR_LOSTCONNECTION;
if (error < (ptrdiff_t)lengthof(network_error_strings)) err = network_error_strings[error];
/* In case of kicking a client, we assume there is a kick message in the packet if we can read one byte */
Expand Down
6 changes: 4 additions & 2 deletions src/network/network_client.h
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,14 @@
/** Class for handling the client side of the game connection. */
class ClientNetworkGameSocketHandler : public ZeroedMemoryAllocator, public NetworkGameSocketHandler {
private:
NetworkAddress address; ///< Address we are connected to.
struct PacketReader *savegame; ///< Packet reader for reading the savegame.
byte token; ///< The token we need to send back to the server to prove we're the right client.

/** Status of the connection with the server. */
enum ServerStatus {
STATUS_INACTIVE, ///< The client is not connected nor active.
STATUS_GAME_INFO, ///< We are trying to get the game information.
STATUS_COMPANY_INFO, ///< We are trying to get company information.
STATUS_JOIN, ///< We are trying to join a server.
STATUS_NEWGRFS_CHECK, ///< Last action was checking NewGRFs.
Expand Down Expand Up @@ -74,13 +76,13 @@ class ClientNetworkGameSocketHandler : public ZeroedMemoryAllocator, public Netw
static NetworkRecvStatus SendMapOk();
void CheckConnection();
public:
ClientNetworkGameSocketHandler(SOCKET s);
ClientNetworkGameSocketHandler(SOCKET s, NetworkAddress address);
~ClientNetworkGameSocketHandler();

NetworkRecvStatus CloseConnection(NetworkRecvStatus status) override;
void ClientError(NetworkRecvStatus res);

static NetworkRecvStatus SendInformationQuery();
static NetworkRecvStatus SendInformationQuery(bool request_company_info);

static NetworkRecvStatus SendJoin();
static NetworkRecvStatus SendCommand(const CommandPacket *cp);
Expand Down
10 changes: 0 additions & 10 deletions src/network/network_gamelist.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -69,15 +69,6 @@ static void NetworkGameListHandleDelayedInsert()
*/
NetworkGameList *NetworkGameListAddItem(NetworkAddress address)
{
const char *hostname = address.GetHostname();

/* Do not query the 'any' address. */
if (StrEmpty(hostname) ||
strcmp(hostname, "0.0.0.0") == 0 ||
strcmp(hostname, "::") == 0) {
return nullptr;
}

NetworkGameList *item, *prev_item;

prev_item = nullptr;
Expand All @@ -95,7 +86,6 @@ NetworkGameList *NetworkGameListAddItem(NetworkAddress address)
} else {
prev_item->next = item;
}
DEBUG(net, 4, "[gamelist] added server to list");

UpdateNetworkGameWindow();

Expand Down
11 changes: 5 additions & 6 deletions src/network/network_gui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -472,9 +472,8 @@ class NetworkGameWindow : public Window {
EM_ASM(if (window["openttd_server_list"]) openttd_server_list());
#endif

this->last_joined = NetworkGameListAddItem(ParseConnectionString(_settings_client.network.last_joined, NETWORK_DEFAULT_PORT));
this->last_joined = NetworkAddServer(_settings_client.network.last_joined);
this->server = this->last_joined;
if (this->last_joined != nullptr) NetworkUDPQueryServer(this->last_joined->address);

this->requery_timer.SetInterval(MILLISECONDS_PER_TICK);

Expand Down Expand Up @@ -750,7 +749,7 @@ class NetworkGameWindow : public Window {
break;

case WID_NG_REFRESH: // Refresh
if (this->server != nullptr) NetworkUDPQueryServer(this->server->address);
if (this->server != nullptr) NetworkTCPQueryServer(this->server->address);
break;

case WID_NG_NEWGRF: // NewGRF Settings
Expand Down Expand Up @@ -971,7 +970,7 @@ void ShowNetworkGameWindow()
first = false;
/* Add all servers from the config file to our list. */
for (const auto &iter : _network_host_list) {
NetworkAddServer(iter.c_str());
NetworkAddServer(iter);
}
}

Expand Down Expand Up @@ -1485,7 +1484,7 @@ struct NetworkLobbyWindow : public Window {
/* Clear the information so removed companies don't remain */
for (auto &company : this->company_info) company = {};

NetworkTCPQueryServer(this->server->address);
NetworkTCPQueryServer(this->server->address, true);
break;
}
}
Expand Down Expand Up @@ -1555,7 +1554,7 @@ static void ShowNetworkLobbyWindow(NetworkGameList *ngl)

strecpy(_settings_client.network.last_joined, ngl->address.GetAddressAsString(false).c_str(), lastof(_settings_client.network.last_joined));

NetworkTCPQueryServer(ngl->address);
NetworkTCPQueryServer(ngl->address, true);

new NetworkLobbyWindow(&_network_lobby_window_desc, ngl);
}
Expand Down
4 changes: 2 additions & 2 deletions src/network/network_internal.h
Original file line number Diff line number Diff line change
Expand Up @@ -87,10 +87,10 @@ extern uint8 _network_reconnect;

extern CompanyMask _network_company_passworded;

void NetworkTCPQueryServer(NetworkAddress address);
void NetworkTCPQueryServer(NetworkAddress address, bool request_company_info = false);

void GetBindAddresses(NetworkAddressList *addresses, uint16 port);
void NetworkAddServer(const char *b);
struct NetworkGameList *NetworkAddServer(const std::string &connection_string);
void NetworkRebuildHostList();
void UpdateNetworkGameWindow();

Expand Down