-
Notifications
You must be signed in to change notification settings - Fork 294
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #723 from DebugOk/WizMerge-22/01
Finally, a big merge
- Loading branch information
Showing
4,016 changed files
with
520,492 additions
and
488,439 deletions.
The diff you're trying to view is too large. We only load the first 3000 changed files.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -14,7 +14,7 @@ jobs: | |
|
||
steps: | ||
- name: Install dependencies | ||
run: sudo apt-get install -y python3-paramiko | ||
run: sudo apt-get install -y python3-paramiko python3-lxml | ||
|
||
- uses: actions/[email protected] | ||
with: | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,187 @@ | ||
#nullable enable | ||
using System; | ||
using System.Collections.Generic; | ||
using System.Linq; | ||
using BenchmarkDotNet.Attributes; | ||
using Content.IntegrationTests; | ||
using Content.IntegrationTests.Pair; | ||
using Content.Server.Warps; | ||
using Robust.Server.GameObjects; | ||
using Robust.Shared; | ||
using Robust.Shared.Analyzers; | ||
using Robust.Shared.Enums; | ||
using Robust.Shared.GameObjects; | ||
using Robust.Shared.GameStates; | ||
using Robust.Shared.Map; | ||
using Robust.Shared.Network; | ||
using Robust.Shared.Player; | ||
using Robust.Shared.Random; | ||
|
||
namespace Content.Benchmarks; | ||
|
||
// This benchmark probably benefits from some accidental cache locality. I,e. the order in which entities in a pvs | ||
// chunk are sent to players matches the order in which the entities were spawned. | ||
// | ||
// in a real mid-late game round, this is probably no longer the case. | ||
// One way to somewhat offset this is to update the NetEntity assignment to assign random (but still unique) NetEntity uids to entities. | ||
// This makes the benchmark run noticeably slower. | ||
|
||
[Virtual] | ||
public class PvsBenchmark | ||
{ | ||
public const string Map = "Maps/box.yml"; | ||
|
||
[Params(1, 8, 80)] | ||
public int PlayerCount { get; set; } | ||
|
||
private TestPair _pair = default!; | ||
private IEntityManager _entMan = default!; | ||
private MapId _mapId = new(10); | ||
private ICommonSession[] _players = default!; | ||
private EntityCoordinates[] _spawns = default!; | ||
public int _cycleOffset = 0; | ||
private SharedTransformSystem _sys = default!; | ||
private EntityCoordinates[] _locations = default!; | ||
|
||
[GlobalSetup] | ||
public void Setup() | ||
{ | ||
#if !DEBUG | ||
ProgramShared.PathOffset = "../../../../"; | ||
#endif | ||
PoolManager.Startup(null); | ||
|
||
_pair = PoolManager.GetServerClient().GetAwaiter().GetResult(); | ||
_entMan = _pair.Server.ResolveDependency<IEntityManager>(); | ||
_pair.Server.CfgMan.SetCVar(CVars.NetPVS, true); | ||
_pair.Server.CfgMan.SetCVar(CVars.ThreadParallelCount, 0); | ||
_pair.Server.CfgMan.SetCVar(CVars.NetPvsAsync, false); | ||
_sys = _entMan.System<SharedTransformSystem>(); | ||
|
||
// Spawn the map | ||
_pair.Server.ResolveDependency<IRobustRandom>().SetSeed(42); | ||
_pair.Server.WaitPost(() => | ||
{ | ||
var success = _entMan.System<MapLoaderSystem>().TryLoad(_mapId, Map, out _); | ||
if (!success) | ||
throw new Exception("Map load failed"); | ||
_pair.Server.MapMan.DoMapInitialize(_mapId); | ||
}).Wait(); | ||
|
||
// Get list of ghost warp positions | ||
_spawns = _entMan.AllComponentsList<WarpPointComponent>() | ||
.OrderBy(x => x.Component.Location) | ||
.Select(x => _entMan.GetComponent<TransformComponent>(x.Uid).Coordinates) | ||
.ToArray(); | ||
|
||
Array.Resize(ref _players, PlayerCount); | ||
|
||
// Spawn "Players". | ||
_pair.Server.WaitPost(() => | ||
{ | ||
for (var i = 0; i < PlayerCount; i++) | ||
{ | ||
var pos = _spawns[i % _spawns.Length]; | ||
var uid =_entMan.SpawnEntity("MobHuman", pos); | ||
_pair.Server.ConsoleHost.ExecuteCommand($"setoutfit {_entMan.GetNetEntity(uid)} CaptainGear"); | ||
_players[i] = new DummySession{AttachedEntity = uid}; | ||
} | ||
}).Wait(); | ||
|
||
// Repeatedly move players around so that they "explore" the map and see lots of entities. | ||
// This will populate their PVS data with out-of-view entities. | ||
var rng = new Random(42); | ||
ShufflePlayers(rng, 100); | ||
|
||
_pair.Server.PvsTick(_players); | ||
_pair.Server.PvsTick(_players); | ||
|
||
var ents = _players.Select(x => x.AttachedEntity!.Value).ToArray(); | ||
_locations = ents.Select(x => _entMan.GetComponent<TransformComponent>(x).Coordinates).ToArray(); | ||
} | ||
|
||
private void ShufflePlayers(Random rng, int count) | ||
{ | ||
while (count > 0) | ||
{ | ||
ShufflePlayers(rng); | ||
count--; | ||
} | ||
} | ||
|
||
private void ShufflePlayers(Random rng) | ||
{ | ||
_pair.Server.PvsTick(_players); | ||
|
||
var ents = _players.Select(x => x.AttachedEntity!.Value).ToArray(); | ||
var locations = ents.Select(x => _entMan.GetComponent<TransformComponent>(x).Coordinates).ToArray(); | ||
|
||
// Shuffle locations | ||
var n = locations.Length; | ||
while (n > 1) | ||
{ | ||
n -= 1; | ||
var k = rng.Next(n + 1); | ||
(locations[k], locations[n]) = (locations[n], locations[k]); | ||
} | ||
|
||
_pair.Server.WaitPost(() => | ||
{ | ||
for (var i = 0; i < PlayerCount; i++) | ||
{ | ||
_sys.SetCoordinates(ents[i], locations[i]); | ||
} | ||
}).Wait(); | ||
|
||
_pair.Server.PvsTick(_players); | ||
} | ||
|
||
/// <summary> | ||
/// Basic benchmark for PVS in a static situation where nothing moves or gets dirtied.. | ||
/// This effectively provides a lower bound on "real" pvs tick time, as it is missing: | ||
/// - PVS chunks getting dirtied and needing to be rebuilt | ||
/// - Fetching component states for dirty components | ||
/// - Compressing & sending network messages | ||
/// - Sending PVS leave messages | ||
/// </summary> | ||
[Benchmark] | ||
public void StaticTick() | ||
{ | ||
_pair.Server.PvsTick(_players); | ||
} | ||
|
||
/// <summary> | ||
/// Basic benchmark for PVS in a situation where players are teleporting all over the place. This isn't very | ||
/// realistic, but unlike <see cref="StaticTick"/> this will actually also measure the speed of processing dirty | ||
/// chunks and sending PVS leave messages. | ||
/// </summary> | ||
[Benchmark] | ||
public void CycleTick() | ||
{ | ||
_cycleOffset = (_cycleOffset + 1) % _players.Length; | ||
_pair.Server.WaitPost(() => | ||
{ | ||
for (var i = 0; i < PlayerCount; i++) | ||
{ | ||
_sys.SetCoordinates(_players[i].AttachedEntity!.Value, _locations[(i + _cycleOffset) % _players.Length]); | ||
} | ||
}).Wait(); | ||
_pair.Server.PvsTick(_players); | ||
} | ||
|
||
private sealed class DummySession : ICommonSession | ||
{ | ||
public SessionStatus Status => SessionStatus.InGame; | ||
public EntityUid? AttachedEntity {get; set; } | ||
public NetUserId UserId => default; | ||
public string Name => string.Empty; | ||
public short Ping => default; | ||
public INetChannel Channel { get; set; } = default!; | ||
public LoginType AuthType => default; | ||
public HashSet<EntityUid> ViewSubscriptions { get; } = new(); | ||
public DateTime ConnectedTime { get; set; } | ||
public SessionState State => default!; | ||
public SessionData Data => default!; | ||
public bool ClientSide { get; set; } | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.