Jump to content
Dante Unbound: Share Bug Reports and Feedback Here! ×

Max Framerate


[DE]Glen

Recommended Posts

I've had a small hobby project that I've been working on now and then over the last few weeks. I was trying to improve part of the engine that has largely been unchanged for 15 years and some people thought I was crazy for even caring about it. Lucky for me they put up with my obsessions around here and the results of my work is coming soon to a build near you.

TLDR: the FPS counter in game is now more accurate and if you use the Max Framerate setting instead of Vertical Sync you may notice a smoother experience when you're running fast enough to hit the cap.

Let me start by explaining why I even care about this, and to do that I need to tell you about my craptop. My play time is split between my high-end PC and super low-end laptops that don't even have a discrete graphics processors. I've been living in this dual universe for about 5 years now and has been extremely helpful for testing graphics scaling options and has motivated plenty of optimizations.

IMG_0565_800.JPG.16a27b448b8362ab9778dcc520d47d93.JPG
My Original 2013 MacBook Air (Bootcamp)

One of the features that came to Warframe last year was Dynamic Resolution and it's made it possible for me to enjoy over 30 FPS in places that would have been crushed without it. However, if you remember when we launched this feature, it was a bit of a mess: despite all our testing ahead of time we found that it malfunctioned on a lot of people's PCs and made the game blurry for no good reason. 

It turns out that there's a key element of the system's graphics driver that we couldn't seem to depend on: GPU time measurements were often unreliable and inaccurate especially when running Windowed or Borderless fullscreen. For Dynamic Resolution to work we need to be able to measure these times on the GPU and use that information to scale the detail to just high enough to match the speed of your CPU -- if those numbers were wrong we might be tricked into making your game blurry.

In our struggle to find a solution to this problem we found several other game developers with the same issue including one that claimed to be working with the major graphics card vendors to solve it. I was, however, bound and determined to get Dynamic Resolution to work properly with my laptop and continued to poke at it.

Disclaimer: this worked for me, on the Intel IGPs I've tested, with Windows 7 and Windows 10 and may not work for you (but please let me know if it does!)

You might have guessed by now that my trick to get accurate GPU time measurements was to disable Vertical Sync. If you're running Windowed or Borderless Fullscreen this probably won't cause any visible tearing (or at least none that I've noticed) because the Desktop Window Manager (DWM) will composite the game window and present it to your display on a Vertical Sync anyway.

This brings me back to where we started; Max Framerate. If you want to run without Vertical Sync you should set a limit because the faster you run the hotter your system will get; not only can this make your PC's fans annoyingly loud or even damage systems with improper cooling, it is especially important if you're playing on a laptop because running hot can trigger thermal throttling limits and that slow your system down again. 

In my case, I set my Max Framerate to my desktop Refresh Rate and have enjoyed the performance boost from Dynamic Resolution for almost a year now. However, as we continued to squeeze out more and more performance I found myself inching closer to that 60 FPS cap I had set and that's when I found a whole new set of problems.

On my PC I play with a mouse and keyboard but on my laptop I play with a controller because I find it more comfortable when I have my feet up in my recliner. One of the things that's easier to appreciate when you're playing with a controller is the consistency of your framerate: if the frame-rate isn't smooth and steady it's harder to aim because your crosshairs jump unpredictably. Paradoxically I found the closer I got to 60 FPS the less consistent my aim became!

As I dug deeper I found these inconsistencies showed up even on my high-end PC; here's a graph of Frame Time taken on my i7-5960X / GTX 1080 Ti standing in the orbiter:

507526001_0-RoundedSleep.png.7f6e2e27c3ded9ee993d967ae10f1229.png

Frame Time is the reciprocal of Frame Rate and a time-spike is often referred to a micro-stutter or dropped frames. In that image those spikes of 10ms or more. If you want to hit 60 FPS that gives you only 16.7ms per frame and so a sudden jump by 10ms is a big deal; if you're trying to cap for a 144 Hz monitor your budget is just under 7ms which is even more sensitive to that size of a jump.

The first thing I did was improved the accuracy of some of the arithmetic used to enforce the limit; this helped but there was still a lot of variance (note that because the really big spikes are gone the graph automatically zoomed in closer).

140740722_1-TruncatedSleep.png.5e699449d912823b935e9f99f52f381a.png

As I dug deeper I found a fatal flaw in the original code: it naively expected a simple Windows API to be much more accurate than it was in practice. When we needed to wait for our cap we would ask the operating system to put us to sleep and wake us up after a few milliseconds, however, because of the way Windows schedules threads, instead of waking us up promptly it would often wait for our next scheduling quantum instead. Since a scheduling quantum might be 10-15ms that would often overshoot our requested delay by a wide margin!

It took a few experiments but I found a more sophisticated way to work with Windows to get woken up at the right time; it looks a lot better but it's still not quite perfect:

628989883_3-TransientTimerQueue.png.2dda1137fa7c87f94ec92773883cef48.png

You can't tell from the graph because there's no scale marked but in this case the oscillation is usually about 1ms here! That's good, but not great -- remember that if you want to sync to a 144 Hz monitor your target frame time is about 7ms so a variance of one or two is still a substantial amount.

After a few more failed experiments I made some more progress: the variance in this final version is only around 20 to 30 microseconds!

86591993_5-PersistentTQwithSub-MSSpin.png.b8adb9cdd0aebf188a19d5a4e7ecd2b3.png

After all this I was pretty excited but there was one last thing that bothered me: the graph was telling me that I was within spitting distance of a perfectly smooth 144 FPS but the in-game FPS display was showing me a few frames less! 

1258692689_142FPS.png.04be3d6b0d0c7ac0bd6dfedf4115414b.png

Again, I went digging and found some code written many years ago that was just a little bit off. We smooth the FPS display value slightly (we take the harmonic mean of the last 64 frames to make it a bit easier to read) but this code was not as precise as it should be -- it was skewing the number slightly lower! One last easy fix and my pride was satisfied:

1051386289_144FPS.png.da44379e3c9e314335e75b6c99a12ddc.png

So I now get much more consistent frame-rate when I'm using the Max Framerate instead of Vertical Sync, and the FPS counter in game is more accurate no matter what you use! 

Bonus Notes:

  • 32-bit Warframe does not benefit because the timers are much less accurate
  • The consoles were fine (they use Auto Vertical Sync and Dynamic Resolution)
  • Dynamic Resolution is off by default on PC (we will revisit after Windows XP is retired and are able to optimize for more modern operating systems)
  • Also coming in this build: NTSC 59.59 Hz frame cap option

I'm super excited to see this change go out today. If you're like me and are using Max Framerate I'd love to hear if you noticed an improvement with this!


 

Link to comment
Share on other sites

You are a savant. I have always wondered why my fps was inconsistent with what it should be, and looking at GPU activity graphs just confused me even more with inconsistent data. I'm excited to see how these changes show up now on my pc and laptop, and if they really are hitting max fps. (My PC always showed 138 fps on 144 setting dispute GPU not even close to maxing even when looking at hwmonitor. 😃 Keep up the good work! Go steal candy from Steve, you've earned it!

Link to comment
Share on other sites

Very thoroughly well done, and a good read as well for those of us who like technical stuff! Super excited to see these optimizations hit PC soon.

Because I use G-Sync I've always opted for the Max Framerate setting with a refresh rate that's slightly higher, like 150-160Hz capped at 144 FPS to hit that sweet zone for G-Sync, but have noticed some abnormalities with it (some of which you addressed in the post).

I'll keep an eye out when this deploys to see if I notice any improvements or otherwise.
Very cool stuff indeed.

Edit:

Already noticing huge stability improvements and a smoother flow of frames to my 160Hz monitor. In the Orbiter and in-mission. Fantastic! I thought my game was smooth before this update but damn, this hotfix has made it even better.

Link to comment
Share on other sites

1 minute ago, Zyneris said:

Sounds good! Was actually very interesting to read through this 🙂 .

Also....

Assuming you're actually talking about XP, it retired in 2014. 

That being said, I'm wondering it's just a typo and you meant Win7 which is scheduled for retirement next year.

I think he's talking about DE retiring their support for Windows XP and 32-bit devices, which will be pretty soon.

Link to comment
Share on other sites

1 minute ago, Zyneris said:

Sounds good! Was actually very interesting to read through this 🙂 .

Also....

Assuming you're actually talking about XP, it retired in 2014. 

That being said, I'm wondering it's just a typo and you meant Win7 which is scheduled for retirement next year.

They still are phasing out XP support on Warframe. Really this is x32 in general, but XP was mostly x32 and I'd say the majority of x32 players are XP... And yes there are people who use XP still; it was the best OS MS ever made and the last to allow 16bit support dispite even windows 10 being able to run 16bit programs, but blocking it normally.

Link to comment
Share on other sites

9 minutes ago, Zyneris said:

Sounds good! Was actually very interesting to read through this 🙂 .

Also....

Assuming you're actually talking about XP, it retired in 2014. 

That being said, I'm wondering it's just a typo and you meant Win7 which is scheduled for retirement next year.

As others have mentioned, Glen is talking about DE's official support for Windows XP in warframe, not Microsoft's support of the operating system.  Windows 7 is "retiring" soon according to Microsoft, but game companies will most likely not stop support for it any time soon given that a  LOT of people are still using it.  Not supporting Windows 7 is basically cutting yourself off from 1/2 to 1/4 of your potential customers (depends on the region and kind of game),  while Windows XP has only a couple of percent of people that are still using it.

Link to comment
Share on other sites

While we talking about Dynamic resolution, do you guys thinking about expanding that setting as chance to go above 100% (SuperSampling AA) ??

Ive try Nvidia DSR 4.00x which is equivalent of 4K resolution, but UI is just terrible at that scale even on Custom setting

Link to comment
Share on other sites

29 minutes ago, [DE]Glen said:

I'm super excited to see this change go out today. If you're like me and are using Max Framerate I'd love to hear if you noticed an improvement with this!

 

 

Do you mean this is already out or a game hotfix or update is coming later today?

Link to comment
Share on other sites

31 minutes ago, [DE]Glen said:

It turns out that there's a key element of the system's graphics driver that we couldn't seem to depend on: GPU time measurements were often unreliable and inaccurate especially when running Windowed or Borderless fullscreen.

Hi @[DE]Glen ! Thanks for the update. I'm a bit puzzled with regards to this part of your post, which may explain something I reported before. Is the dynamic resolution setting a feature that is exclusive to windowed or borderless? The feature never worked for me when on fullscreen mode. I asked if that was the expected behavior in that thread and sadly I never got a response.

Here's the thread:

I'm on:

W10 Pro x64

Intel Core i7-4790K @4.6 (All cores)

GTX 1070 (Latest drivers as of the time of this post)

Thank you very much for the clarification.

Link to comment
Share on other sites

Honestly I'm just floored at the fact that you got Warframe running on a Macbook Air.

That said, as an electrical engineer who designs graphics processor cards, this is some very interesting and very cool information about the software/API side of graphics processing and framerates.

Link to comment
Share on other sites

17 minutes ago, Jarriaga said:

Is the dynamic resolution setting a feature that is exclusive to windowed or borderless? The feature never worked for me when on fullscreen mode. I asked if that was the expected behavior in that thread and sadly I never got a response.

Dynamic Resolution works in all three modes; you can test in fullscreen (like I just did) by setting a user ratio of 50% and you can see everything get just a bit blurry. However, like I said, depending on the drivers and the DWM we may not get accurate GPU timings back so the Auto Dynamic Resolution setting doesn't always work properly and it's beyond our control.

The other reason the auto setting may not appear to work is if you're not actually GPU bound; if you're hitting hitting your sync or your CPU is slower and there's no reason to reduce the resolution you won't notice any difference.

And, like I also said, we'd like to revisit that after we retire support for Windows XP (because there are DWM optimizations we can't make while we continue older operating systems).

 

Link to comment
Share on other sites

3 minutes ago, [DE]Glen said:

Dynamic Resolution works in all three modes; you can test in fullscreen (like I just did) by setting a user ratio of 50% and you can see everything get just a bit blurry. However, like I said, depending on the drivers and the DWM we may not get accurate GPU timings back so the Auto Dynamic Resolution setting doesn't always work properly and it's beyond our control.

The other reason the auto setting may not appear to work is if you're not actually GPU bound; if you're hitting hitting your sync or your CPU is slower and there's no reason to reduce the resolution you won't notice any difference.

And, like I also said, we'd like to revisit that after we retire support for Windows XP (because there are DWM optimizations we can't make while we continue older operating systems).

 

Thank you!

Link to comment
Share on other sites

Im running a Asus G74sx with a 3gb gtx 560m.... Im running everything on minimum and struggle to keep 30fps (I now have it limited to 30fps so as to not overwork this laptop, also have it on a cooling pad. Heat not an issue really)

What in the world am i doing wrong?

Link to comment
Share on other sites

Oh hey, I can set 100hz frame cap now instead of forcing in Riva Turner.  Would still be better as a slider but least it supports more common settings.

Not like running borderless windowed and letting desktop manager force V-Sync was critical input delay but always nice when options get fleshed out.

What's the deal with 72hz anyways? That's such a weird number.

My Predator x34 thanks you. 21:9  4Life.

EDIT:  Oh, I made a disgruntle post a while back about not saturating any of my CPU cores or using full GPU when other players are around and sitting at 85 FPS for no reason but holding 100 FPS firm on a 2070 when Solo in Fortuna. The last patch or two seems to have fixed that. I'm 100 FPS all day now. So thanks also to whoever fixed that.

Link to comment
Share on other sites

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...