Opened 8 years ago
Last modified 2 years ago
#3752 new enhancement
Improve multiplayer game responsiveness
Reported by: | fcxSanya | Owned by: | wraitii |
---|---|---|---|
Priority: | Should Have | Milestone: | Backlog |
Component: | Network | Keywords: | beta |
Cc: | Krinkle | Patch: | Phab:D3275 |
Description (last modified by )
In r8400 multiplayer turn length was increased to mask the effects of latency. Consequently multiplayer has longer delay before player orders are performed after being issued (see for example start of the match here: https://youtu.be/Dl85JBt6zGM?t=57s). According to Georg (aka leper):
the current plan is to make the turn length shorter and allow scheduling commands for not only the next turn but also N+2, N+3 and such (or some computations start on the next turn, but the result will only be used some turns later)
(the corresponding IRC log is here: http://irclogs.wildfiregames.com/2016-01-22-QuakeNet-%230ad-dev.log also there are relevant discussions in the earlier logs)
#69 also proposed to dynamically adjust the turn length, but according to Georg:
the main issue with dynamic turn lengths is lots of pointless complexitiy
Change History (18)
comment:1 by , 8 years ago
Type: | defect → enhancement |
---|
comment:5 by , 8 years ago
causative mentioned that some things in the simulation occur only once per turn (instead of being executed periodically every N simulation milliseconds).
For example if a unit is blocked by an obstruction, it will not try a new path until the next turn. Thus shorter turn lengths will yield much less annoying pathfinding behavior.
So either all these simulation components need to be readjusted to check for simulation time instead of turn number, or we could execute multiple turns inside the network latency timeframe (and execute these turns without waiting for the ack of a client to avoid simulation pauses).
comment:6 by , 7 years ago
According to Philip (see irclogs yesterday), this behavior is already implemented with COMMAND_DELAY
, so we should check whether COMMAND_DELAY = 3
and DEFAULT_TURN_LENGTH_MP = 150
works f.e. (and doesn't respond to lag before 450ms rtt).
comment:7 by , 7 years ago
Keywords: | beta added |
---|
comment:8 by , 7 years ago
Owner: | set to |
---|---|
Status: | new → assigned |
comment:9 by , 7 years ago
Currently, with increased COMMAND_DELAY
an assertion fails:
NetServerTurnManager.cpp(49): Assertion failed: "turn == m_ClientsReady[client] + 1"
comment:10 by , 6 years ago
Description: | modified (diff) |
---|---|
Priority: | Should Have → Must Have |
If I had written the ticket today:
Title: TurnManager should handle observer timeouts and lag more fault-tolerantly
Description:
Observers are often frowned upon because of the possibility of them delaying the game by
(1) network timeouts
(2) bad network latency
(3) rejoins
(4) insufficient simulation performance
The root for all four problems is the server-turnmanager waiting for the affected observer to compute the next turn before progressing with the simulation.
The severity of networking problems can be reduced by improving the UI (making the network warnings "kick" buttons) and improving the simulation performance.
But the task of this ticket is to establish "graceful degradation", meaning to teach the NetServerTurnManager to progress the simulation in spite of one observerclient being affected by one of these four conditions.
The NetServerTurnManager can handle the four cases equally.
In CNetServerWorker::StartGame
we find
m_ServerTurnManager->InitialiseClient(session->GetHostID(), 0); TODO: only for non-observers
But because rejoin syncs might never finish and because we don't want observers commenting on different times of the game, the NetServerTurnManager
may not entirely disregard observers being too slow with the simulation / rejoin sync and have to wait for them to catch up only for a certain amount of time, for instance 8 simulation turns or a dynamically adjusted amount of time.
comment:11 by , 6 years ago
Might be stupid but can't they just get the computed state from say the host ?
comment:12 by , 5 years ago
Cc: | added |
---|
comment:13 by , 3 years ago
Owner: | changed from | to
---|---|
Patch: | → Phab:D3275 |
Status: | assigned → new |
The key here is indeed the command delay, as command_delay * turn_length = max lag before things freeze.
Decreasing turn lengths certainly could work, but it has diminishing returns, and the current value of 200ms in SP seems 'fine enough' in general.
I think it would be interesting to also reduce the COMMAND_DELAY dynamically, though possibly harder. However, if we were to go with Phab:D3275, it'd probably be necessary: with a delay of 4, we can't really have 'low lag' unless we use <125ms turns, which seems low. In SP, we effectively have a COMMAND_DELAY of 1, and 200ms turns.
(having turn lengths be too low means the ratio of "time spent computing turns" vs "time spent computing graphics" might become too unfavourable, resulting in really low FPS overall, not just 'spiky' fps).
comment:14 by , 3 years ago
Milestone: | Backlog → Alpha 24 |
---|
Bumping to A24 though it's probably a bit late in the release cycle... This is at least an A25 RB imo.
comment:15 by , 3 years ago
Milestone: | Alpha 24 → Alpha 25 |
---|---|
Priority: | Must Have → Release Blocker |
comment:17 by , 3 years ago
Milestone: | Alpha 25 → Alpha 26 |
---|---|
Priority: | Release Blocker → Should Have |
comment:18 by , 2 years ago
Milestone: | Alpha 26 → Backlog |
---|
This seems to be a must-have:
Motivation:
As observed in #69 and #3264, if the round trip time of a client exceeds the current turn length, the simulation is paused, waiting for the ack of that client.
While the simulation is paused, the units stay in their position while remaining in the walk animation (moonwalking).
Adapting the turn length eliminates those simulation pauses by increasing the turn length.
If the simulation is never paused waiting for the lagger, the ingame and realtime progress with the same speed (thus not losing lifetime to network lag anymore).
Since performance improvements in the engine can't fix network induced lag, these optimizations should be done in other tickets.
Existing implementation: (As of r18264) changing the rate manually is implemented, but it's not done automatically.
Explanation: The host can call
Engine.SetTurnLength(foo);
from the JS command-line interface (F9 key). It will directly changem_TurnLength
of theNetServerTurnManager
. Then the new turn length is broadcasted to the clients when sending theEndCommandBatchMessage
fromCheckClientsReady()
in theNetServerTurnManager
. On receive, the clients adopt that turn length inFinishedAllCommands()
of the client'sNetTurnManager
.To finish the implementation:
EndCommandBatchMessage
from the server is likely sufficient.EndCommandBatchMessage
: It is used for both directions (server->client, client->server) but with different connotations: