ArcCW icon indicating copy to clipboard operation
ArcCW copied to clipboard

Ping/Latency substantially affects client or and server performance.

Open SemixOfficial opened this issue 3 years ago • 13 comments

Hello, so few hours ago I was just messing around with some things and I noticed that physical bullets are not lag compensated, being a total nerd I have decided to lag compensate them myself and rewrite ArcCW physbullet code to make projectiles fully lag compensated and supported, whilst doing so I have ran into a very interesting issue however, I have noticed that regardless of what I did player's latency to the server has a huge impact on framerate and because I couldn't find and fix this issue myself I have decided to submit a issue here on the github, running a powerful Ryzen 5 5600X CPU and RTX 2060 Super OC GPU I can usually stay on stable 143 fps (limited by RTSS) regardless of what I do or where I play, yet with ArcCW weapon a round trip time of 400ms results in massive loads and as shown in the video below, I struggle to get stable or even decent frametimes, and on round trip time of 800ms the game becomes completely unplayable as the client experiences massive rubber banding and stutter, sure no one is going to play or have nice time playing with round trip time of 400ms or even 200ms but it still shows that somewhere in ArcCW a bit of code has a lot of performance issues as latency increases.

I feel like this is a really big issue and whilst I don't know whether it's the server or client that is experiencing massive loads as latency goes up due to testing on a local server I still believe that this is an issue that needs a lot of attention and has to be fixed as quickly as possible as it can very negatively affect people with weaker PC setups or high latency.

Here is the link to my video showcasing the issue: https://youtu.be/CQCtdfqYGs8

SemixOfficial avatar Mar 19 '21 13:03 SemixOfficial

Recently some changes have been pushed that resolved some of ArcCW's prediction issues. Let us know if that has remedied your problem.

TheOnly8Z avatar May 05 '21 15:05 TheOnly8Z

Hello, after nearly one year I have made another investigation into this problem and I have managed to pin-point the smaller portion of this problem to come from SWEP:GetViewModelPosition located here.

This function unfortunately suffers from multitude of issues, the excessive lag being the main one, so let's begin with it.

GetViewModelPosition is a predicted hook which means that in the client realm this hook will be called multiple times in order to smooth out the experience as the client simulates multiple times at different intervals, interpolating the results, as the client's latency to the server increases and predicted hooks need to be called more often, GetViewModelPosition alone isn't all that expensive, during my testing, with zero latency it had a stable average runtime of 240uS, generating about 3.9 kilobytes of garbage every call, the problem comes when your latency starts increasing, with round trip time of 200msec this becomes rather unstable runtime of anywhere between 1500-2700uS, generating 50.7kb of garbage every call, so on top of low frame rate due to to the cost of calling the function so many times, the amount of garbage generated will trigger a full garbage collection cycle almost every 0.2-0.4 seconds, this makes the game completely unplayable at any latency that's above 100-150 milliseconds, which is a large issue in my opinion, now do keep in mind that I am on a local server with no clutter or other addons that could in any noticeable way affect my test results, anyways here are some interesting screenshots to take a look at.

RTSS Frametime Graph (ArcCW, Zero latency) gmod_j1gb6lv3pX

RTSS Frametime Graph (ArcCW, 200msec latency) gmod_FFNtMnzPl0

RTSS Frametime Graph (Customisable Weaponry 2.0, 200msec latency) image

RTSS Frametime Graph (Customisable Weaponry 2.0, 1000msec latency) image

FProfiler test results (Focused on GetViewModelPosition only) gmod_svafAT1A8h

Frametime Instabilities at 200msec (ArcCW) image

All of the tests were done on a local P2P server with 7empty slots (8 in total) using arccw_ak47 from Counter-Strike+ pack with no attachments and all ArcCW settings set to default values, the only modified settings were:

Server settings: sv_cheats 1;net_fakelag 100;sv_maxrate 0 Client settings: cl_SetupAllBones 0;cl_threaded_bone_setup 1;mat_queue_mode 2;gmod_mcore_test 1;cl_predictionlist 1;net_graph 4

To conclude this, I have tried fixing this issue myself but after few hours of testing I came to the conclusion that not being one of the developers I don't understand majority of the code for stuff like GetBuff or why such system exists, I have vague idea as to what most of it does but when it comes to fixing issues having vague idea about something is usually not the best approach, therefore I am leaving this issue to the original developers here on GitHub to hopefully fix up the code as they know their weapon pack the best. (obviously)

That being said GetViewModelPosition is not the only issue, compared to other weapon packs like M9K, CW 2.0, FA:S, ArcCW seems to have a lot of problems with prediction and or predicted hooks, I understand that this weapon pack is lot larger and has many more features than the above mentioned ones, and I have nothing but respect for the developers who put their time and hard work into this, but I do believe that some bits of the code need to be re-worked.

SemixOfficial avatar Mar 23 '22 17:03 SemixOfficial

Development efforts are being nowadays being pushed towards ARC-9, so if you would like to do profiling and stuff for that, that would help

Fesiug avatar Mar 24 '22 12:03 Fesiug

Thanks for your updated report. I'll look into it and see if optimization is possible.

WRT ARC-9 development, it's likely that similar issues persist since many of the functions/code is reused, esp. if it is related to GetBuff.

TheOnly8Z avatar Mar 24 '22 15:03 TheOnly8Z

@SemixOfficial I made a preliminary optimization to reduce GetBuff calls on non-changing values in the optimization branch. Please try it out and see if it is an improvement.

https://github.com/HaodongMo/ArcCW/tree/optimization

TheOnly8Z avatar Mar 24 '22 15:03 TheOnly8Z

Development efforts are being nowadays being pushed towards ARC-9, so if you would like to do profiling and stuff for that, that would help

I have just yesterday written some basic parts of my own weapon pack, I would be happy to join ARC-9 development team if possible.

SemixOfficial avatar Mar 24 '22 18:03 SemixOfficial

@SemixOfficial I made a preliminary optimization to reduce GetBuff calls on non-changing values in the optimization branch. Please try it out and see if it is an improvement.

https://github.com/HaodongMo/ArcCW/tree/optimization

I have just done some tests on the optimization branch I'm glad I can say that over the previous results I have noticed significant improvement, first let's look and compare the RTSS frametime graphs.

Here's RTSS Frametime Graph with no latency from yesterday. gmod_j1gb6lv3pX

And here's RTSS Frametime Graph with no latency from today on the optimization branch. gmod_zl0OkG2Tsq This is really good to see as holding ArcCW weapon no longer causes micro-stutter and no longer triggers garbage collection cycles, now let's look at the results with 200msec latency.

Here's RTSS Frametime Graph with 200msec from yesterday. gmod_FFNtMnzPl0

And here's RTSS Frametime Graph with 200msec latency from today on the optimization branch. gmod_pNFC5V6tVF

The improvement is still significant, and given the fact that the frametime graph is almost stable on 200msec latency I deem the runtime optimization to be good enough for now, at 200msec latency users might have larger concerns than ~0.01ms frametime instabilities, what needs to be focused on now is the garbage collection, even with 100ms latency, GetViewModelPosition still seems to be triggering manual garbage collection, as can be seen here with the sudden spike image and here image

SemixOfficial avatar Mar 24 '22 18:03 SemixOfficial

The improvement is still significant, and given the fact that the frametime graph is almost stable on 200msec latency I deem the runtime optimization to be good enough for now, at 200msec latency users might have larger concerns than ~0.01ms frametime instabilities, what needs to be focused on now is the garbage collection, even with 100ms latency, GetViewModelPosition still seems to be triggering manual garbage collection, as can be seen here with the sudden spike image and here image

Can you show the code you use to calculate the render time and garbage size?

TheOnly8Z avatar Mar 25 '22 00:03 TheOnly8Z

I create two trash/placeholder variables in the file's scope like so image then in PreDrawiewModel I assign them values, one being SysTime() used for render time, and the second being amount of allocated dynamic lua memory image then in PostDrawViewModel I simply print the difference between the current values and the values before. image (Note that the SysTime delta is multiplied by 1,000,000 because one second has 1,000,000 microseconds (uS)

Do note that this is not perfect way to measure the total cost of GetViewModelPosition, as we are measuring it per call and not per frame, but I see that as tolerable, because we only need to know how much the function takes per call to see if we are optimizing it or making improvements, since the final result will be your average cost per call times the amount of times the function has been called, the most reliable way to measure the total cost of GetViewModelPosition I can think of would be to create two variables in global scope, print and reset their values in FrameUpdatePreEntityThink, then for every timeGetViewModelPosition is called measure the time and garbage, add it to the placeholder variables and see the results on next frame, this should tell us the total cost of GetViewModelPosition as it would include additional prediction calls from the engine, but again, It's not really necessary info.

Edit: Fixed a typo

SemixOfficial avatar Mar 25 '22 00:03 SemixOfficial

@SemixOfficial I've pushed changes to the branch that should noticeably decrease garbage generation. Let me know how it goes.

TheOnly8Z avatar Mar 25 '22 04:03 TheOnly8Z

I have tested the latest changes, in the optimization branch, the improvements are good, although the weapons still trigger garbage collection occasionally on higher latency, they don't trigger full cycle, but only smaller steps, which are tolerable and don't lag the game for full second or so, there is a large problem that I have noticed tho, that being view model bob, sway and iron sights not working at all now and view model appears in weird position, this is most likely caused by swapping most of add, substract, multiply and other operations from regular arithmetic to function calls like VMPos:Add(), etc.... as these functions modify the Vector or Angle itself rather than creating a new copy or changing just the localized reference.

Here are some in-game screenshots: gmod_rtxR443zik gmod_ldhTRPZP5P

as far as today's profiling results go, GetViewModelPosition still appears to be amongst one of the largest bottlenecks, but table.Add and GetBuff_Override functions seem to be catching up, both spotting awful cost of 3500-4000uS per frame.

anyways, the important part is that the weapon pack is very usable now even with high latency, which is what matters the most, therefore I deem the issue fixed and will probably close this ticket, further improvements could still be made but with development efforts being pushed towards ARC-9 It doesn't make a whole lot of sense to rewrite every single expensive bit of ArcCW.

SemixOfficial avatar Mar 25 '22 19:03 SemixOfficial

Thanks for pointing that out - I fixed the holosight issue.

TheOnly8Z avatar Mar 25 '22 20:03 TheOnly8Z

Performance branch has been merged recently, should we close this?

Fesiug avatar Apr 10 '22 22:04 Fesiug