Hacker News new | past | comments | ask | show | jobs | submit login
Dramatically reduced power usage in Firefox 70 on macOS with Core Animation (mozillagfx.wordpress.com)
526 points by muizelaar 21 days ago | hide | past | web | favorite | 78 comments

This is quite dramatic, in that I can actually feel my Macbook not heating up as much, nor can I hear the fans anymore.

We do quite a lot of work on a trading website that has heavy use of Canvas and CSS animations, and the latter really kills performance. Two runs on our production website from Intel Power Gadget, pre and post upgrade, show decreased temperature, a lot fewer power spikes, less DRAM wattage, lower GFX clocks, and about 40% less power overall:

Before: https://i.imgur.com/WkdWaHx.jpg

After: https://i.imgur.com/3ojMyjT.jpg

Thank you for sharing these stats. They really seem significant!

Bitmex looks very interesting, any fun stories to share?

Given the extensive market manipulation and liquidation of margin traders in cryptocurrency, probably nothing that can be shared publicly.

I've been nagging on HN's comment sections every few months about this issue whenever a FF related submission made the frontpage... Now I can finally ditch chrome and start spreading the news so the guys in my office can do it too :D

Even better is the news that it's going to improve even further, and the plans to include a Metal backend to WebRender...

> I've been nagging on HN's comment sections every few months about this issue whenever a FF related submission made the frontpage...

Same here, until one of the people responsible for the patches replied to tell me that he fixed it. I've been running nightly builds of Firefox ever since.

Firefox with NoScript runs fast and cool. I love it.


Hey, could you please stop posting unsubstantive comments here? and especially not personal swipes? We're trying for a bit better than internet default and need everyone to pitch in in order to keep the site interesting for all of us.


This will bring me back as well

Amazing work by my colleagues! I hope we'll not regress this with WebRender ;)

Celebration aside, one particular note (that was known, but still) makes me sad:

> It’s worth noting that the ability to assign an IOSurface to the CALayer contents property is not properly documented. Nevertheless, all major browsers on macOS now make use of this API.

So we end up in a situation where using the most efficient way to display contents now relies on undocumented/private APIs. At any point Apple can break them, or punish us for using them.

It's "documented" as in "tweeted out by an Apple engineer": https://twitter.com/bciechanowski/status/874345241666437120?...

One thing that is not documented is that the IOSurface must have been created with the 'BGRA' pixel format, or it will silently render as black instead.

I hope that 'bgra' was at least a typo of 'rgba'

BGRA is a "weird" convention in the graphics world that goes back to at least OS/2 bitmaps, when there was no wrong answer, and has stuck since then. Since early GPUs targeted Windows (where BGRA is the native format for GDI/D2D), it makes sense that it made it this far :)

Do you have an FB number for improving the documentation here?

CALayer accepts a number of different data types for its contents property, IOSurface being one of them.

Another tip: CAShapeLayer draws on the GPU so simple shapes/strokes can be insanely faster drawn that way vs CoreGraphics.

It's not a private API, the docs are just out of date. You can technically set any object as the contents of a CALayer (the property's type is `id` or `Any`), it's just that most objects won't do anything productive.

The docs call out using images specifically because that's the 99% use-case; they need to be updated saying that `IOSurfaceRef`s can be used as layer content as well.

`IOSurfaceRef` itself was actually private at one point, IIRC, but isn't anymore.

> So we end up in a situation where using the most efficient way to display contents now relies on undocumented/private APIs. At any point Apple can break them, or punish us for using them.

Unless Apple wants to break all browsers, that is. At least Chrome and now Firefox use it.

They can make other browsers subtly slower, just open your imagination.

What I want is an https://arewesafariyet.com that tracks Firefox's macOS energy usage against Safari's so that I can figure out when to switch. As far as I can tell, they still have a long way to go to match Safari in battery life and it would be nice if they had an explicit tracker set up as a way of prioritizing fixing that.

I think they would need to fully adopt CALayers to get all of the way down to Safari's power usage.

>This proposal is a bit hacky. The more pure solution would be to teach the compositor to create CoreAnimation layers for Gecko layers, so that for example the throbber animation gets one CoreAnimation layer that contains all the animation frames in a film strip, plus an offset and clip that only shows the current frame. (That's how the Gecko layers are set up for the throbber animation.) Such a solution would be preferable but it would require much more work in the compositor. The tiling solution that I'm proposing in this bug is easier to implement and a bit more generic, because it treats CompositorOGL compositing as a black box that just produces a framebuffer filled with pixels, along with an invalid region.


If I am following this correctly, when dealing with a small on-screen animation, they are moving from having to repaint the whole window to only repainting a largish chunk of the window.

Adopting CALayers at a deeper level in Gekko would allow them to only update the animation itself.

Doing so would require a good deal of additional work.

There's work going on to adopt Core Animation more deeply in WebRender. Patches in review right now, in fact.

That's great news.

I can see where it would make more sense to do the deeper integration work "where the puck is going" so to speak.

I appreciate the work you and your comrades are doing.

Mind linking the patchset?

In addition to battery life, I'd also like things like native PiP mode (if possible) and native, fullscreen video playback. Better rendering gets closer to letting Firefox replace Safari for me, but the other features are important to me, too.

Native PiP is coming in Firefox 71 (already available for testing on Beta releases), though Windows-only at first. You can track macOS progress by following: https://bugzilla.mozilla.org/show_bug.cgi?id=1532675

Picture-in-picture is possible, but it relies on SPI on macOS (for which headers happen to be in the WebKit repository, so there are third-party applications that use it already).

Native PiP and fullscreen video playback are both available in developer edition on Windows for me and the former has been around for at least a month. I've had fullscreen video playback for years so I'm not sure what the deal is with that one... Hopefully mac users get both.

I went back to Safari after bouncing between Chrome and FFX and I’m so happy there. It’s quite a bit faster and uses far less resources.

Activity Monitor does decent tracking of power consumption. If you can remember to switch browsers at regular intervals, you should be able to get meaningful measurements.

I think maybe Mozilla developers should not waste their time to support poorly documented proprietary platform with very low market share.

Do you understand the difference between relative and absolute?

Do you think 100million is nothing?

Is there a version of this for chrome?

If you mean is there something that compares Firefox battery drain to Chrome battery drain, then I don't care because Chrome is also garbage about energy efficiency. If you mean is there something that compares Chrome battery drain to Safari battery drain, no I don't think so.

Microsoft has been working real hard to bring the original Edge's battery efficiency to Chrome.

Isn't Edge using Chromium in the first place?

Right, they’re working to bring the old non-Chromium Edge’s efficiency to Chromium for the new Edge.

This is very good news!

Firefox has been my daily driver for well over a year now and I've been extremely happy with it. The gripe I've had has been the heat/power consumption.

Props to the dev team!

This is great to see! One gripe I still have with Firefox is how poorly it handles video playback (controls and energy consumption) compared to Safari. This makes me want to use Firefox more often, but Safari will still remain my daily driver because of native full screen video and PiP mode.

You can enable PiP mode on Firefox - in `about:config` look at the `picture-in-picture` options.

Just downloaded a clean install of Firefox 70 but even scrolling a simple site like Hacker News feels very laggy compared to Chrome.

Not sure whats going on. 2018 Retina MBP with dedicated GPU running Catalina.

I'm not a normal Firefox user — I usually use Chrome and Safari side-by-side. So I decided to give FF another try with this release, and I agree that the scrolling performance is noticeably worse in FF than Safari and Chrome on the same page. I know the link here is about power usage, not performance, but it makes things feel much less nice.

Firefox touchpad scrolling feels worse than other browsers by default because of the terrible default inertia and acceleration values. If you're not opposed to some tweaking, you can get them to feel much more like Safari. Further reading: https://www.reddit.com/r/firefox/comments/63cd0m/how_to_get_...

WOW this explains so much about why my experience with Firefox has felt like garbage.

Why are the defaults set this way???

Are you scrolling with a touchpad? Most of those settings don't impact touchpad scrolling. Is there a particular setting which makes the difference?

Did you try them? Several of the settings labeled "mousewheel" also affect touchpads. I don't have a touchpad on hand to check but I remember general.smoothScroll.mouseWheel.durationMaxMS making a difference as well.

I assume these are the default values that were selected a while ago, and it would be considered breakage to change them now?

Just if someone wonders: "Tagesschau" is a german television news service, probably the most famous in Germany.

Cool! I've been curious about Firefox's progress over the last few years, but this is what pushed me to download a modern version. Good work, Firefox team!

So OpenGL wasn't allowing partial viewport "dirtying" on macOS. Does that mean Firefox on Linux has an opportunity for a similar gain?

In theory, yes, via the XPRESENT extension and similar mechanisms on Wayland. I don't know how well the drivers and window server optimize it though. (I plan to investigate this at some point.)

Most Wayland compositors track damage obsessively. If you turn on the paint debug overlay in Weston or something wlroots-based and start typing in e.g. gnome-terminal (with blinking cursor turned off), you'll see that only a single character is painted at a time.

Here's a good post: https://emersion.fr/blog/2019/intro-to-damage-tracking/

To do this with EGL, you need to eglSwapBuffersWithDamage(KHR|EXT) instead of just eglSwapBuffers: https://gitlab.freedesktop.org/wayland/weston/blob/23d01c67a... (isn't it nice to have a GL API that's not terrible? :D)

I think I know how to do it, going to try soon. Bugzilled: https://bugzilla.mozilla.org/show_bug.cgi?id=1590586

Firefox on Linux, we remember, is the browser that has software ffmpeg video decode. If you're looking for battery life, you better find some script that can pipe YouTube to VLC and an ad-blocker that allows you to block all videos, all of them.

And, well, then you are probably still using X server with various terrible extensions that are either polluting the graphics card with constantly composing windows as fast as it will go or, not entirely unlikely, doing CPU blits of window buffers. Just to produce an artifact-riddled not-Vsynced mess.

Anyone has insights how power usage compares to safari? I’m team safari for the past years because it’s just so much easier on the battery than anything else

Safari is unfortunately still consuming far, far less power on my Mid 2012 MBP and my 2017 MBP - though there is a significant improvement. Others have posted exact statistics.

I thought it would've been informative to show Safari in the charts.

Does this help with streaming? In particular I have always had issues with twitch and firefox.

Stream video playback would probably invalidate most of the framebuffer anyway, so I'm not sure how much it would help. It's possible it will make a difference but probably not much. There are other things they could do along these lines that would definitely help, though.

Open the About Firefox menu item and there's a button there to update.

Good changes, although I find it amusing/discouraging that the "high complexity" graphics use case is a word processor.

Can't wait to compare this to Safari, which I don't like but is dramatically gentler on my macbook's battery.

> The crucial limitation here is that flushBuffer gives you no way to indicate which parts of the OpenGL context have changed. This is a limitation which does not exist on Windows


The state of OpenGL on OSX is terrible.

Core Animation Layers do allow you to mark a layer or only a portion of a layer as needing an update.


Taking advantage of this would require deeper changes in Gekko than this initial change.


Perhaps WebRender will do a better job of leveraging the possibilities of the native platform APIs for the various lesser used platforms?

In any event, it's a huge amount of work to land a change which makes such a huge difference in battery life, and that work is appreciated.

I think the author is incorrect: flushBuffer is ~20 years old. The "corresponding API" in Windows is not OpenGL, and Apple also has analogous modern APIs which handle dirty regions efficiently.

Deprecated, I thought. Just there for legacy support

Ah, you are right, since Mojave.

Yay for proprietary APIs.

I wonder what that means for WebGL support on Mac. Though I guess it can run through an intermediate layer similar to ANGLE on Windows.

> The crucial limitation here is that flushBuffer gives you no way to indicate which parts of the OpenGL context have changed.

Partial window updates have been available in Windows since long ago (in non-accelerated GDI). Why don't others just copy Windows API instead of inventing their own poor API?

Maybe there is no partial updates because an application can write directly to GPU textures and GPU will redraw entire screen anyway?

Also I am not sure that browser needs OpenGL, because you cannot render text efficiently on GPU anyway and the main content of web pages is text.

> Whenever a layer is mutated in any way, the window manager will redraw an area that includes the bounds of that layer, rather than the bounds of the entire window.

Then the problem still isn't solved because a layer can be much larger than changed pixels.

Of course Apple has a partial window update API which is the primary drawing mechanism. flushBuffer maps to OpenGL, and Windows has its own version of this too (Wingdi::SwapBuffers).

I agree that browsers using OpenGL is...a design you could reach when measuring for graphics throughput at the expense of all else.

Wonderful, can't wait to test it out. This is one of the main reasons I still use Chrome. I can't watch videos on my laptop without hearing my fans go crazy when using FF

Using Linux, I can't watch youtube or use Google Hangouts for too long before the fans start going. Google refuses to add GPU support for Linux/Chrome. It's annoying.

I don't know any details, but Chrome canary on MacOS has a "metal" flag.

"Vulkan" flag on Android too.

(Post mentioned they plan on implementing metal backend)

Isn’t it worrisome the dependence on OpenGL when it’s been deprecated by Apple in favor of Metal?

Are there any plans to move of off this API?

Really exciting. This was the one thing keeping me from using Firefox on my personal laptop.

How long till we get video acceleration?

How does it compare to Chrome?

Seems like a wash to me on a non-retina mac. It was fine before and seems fine now. Does anybody know if this should theoretically help non-retina mac users?

It won't hurt, but the article pointed out the main performance fail was coming from all the increased strain that retina displays were causing on memory and cache. Since retina displays have 4x as many pixels, Firefox was doing 4x as much work for its inefficient compositing engine doing large full-scene copies on every frame, and this was pushing the limits of what typical integrated graphics was able to smoothly pump through bandwidth-wise.

Yes, it will help, but the memory bandwidth savings decrease quadratically as DPI decreases, which is why you aren't seeing much of an impact.

Guidelines | FAQ | Support | API | Security | Lists | Bookmarklet | Legal | Apply to YC | Contact