Bug 92309

Summary: Box drawn around cursor in multiple 3D games
Product: Mesa Reporter: Bryant <bryant.mairs>
Component: Drivers/Gallium/radeonsiAssignee: Default DRI bug account <dri-devel>
Status: RESOLVED FIXED QA Contact: Default DRI bug account <dri-devel>
Severity: normal    
Priority: medium CC: kamil.paral
Version: git   
Hardware: x86-64 (AMD64)   
OS: Linux (All)   
Whiteboard:
i915 platform: i915 features:
Attachments: Natural Selection 2 cursor corruption
Legend of Grimrock cursor corruption
Kingdom Rush cursor corruption

Description Bryant 2015-10-06 02:16:00 UTC
When playing Legend of Grimrock or Natural Selection 2 on the radeonsi drivers on Cape Verde there is a box drawn around the cursor. This does not occur in other games such as Risk of Rain, Starbound, and Left 4 Dead 2.

This is when running Mesa 11.1.0-devel on Fedora 22, git 9932142.
Comment 1 Bryant 2015-10-06 02:16:40 UTC
Created attachment 118696 [details]
Natural Selection 2 cursor corruption
Comment 2 Michel Dänzer 2015-10-06 02:21:56 UTC
Reminds me of bug 91641, which turned out to be a game bug.
Comment 3 Bryant 2015-10-06 02:48:36 UTC
Indeed looks to be a game specific bug: http://www.grimrock.net/forum/viewtopic.php?f=12&t=4583

Should I just close this with a NOTOURBUG or what's the procedure?
Comment 5 Bryant 2015-10-06 02:56:00 UTC
There are 10 people who reported it for Grimrock and 3 in Natural Selection 2, all but 1 who are running AMD drivers open and closed.

I'd like to use apitrace to look at the texture used for the cursor to confirm it's a game bug for both of these games, but I can't get apitrace to work with Steam games for me and the internet is being little help.
Comment 6 Bryant 2015-10-21 06:04:44 UTC
This is also happening on an HD5770 card (Juniper XT) I have with the R600 driver.
Comment 7 Kamil Páral 2015-10-25 10:19:21 UTC
I see the same problem with Natural Selection 2, Legend of Grimrock, Kingdom Rush and some other games I already forgot. It's not rare. Attaching screenshots.

I managed to capture apitrace for all three games (my first time working with apitrace), the problem is that if I replay them, the cursor is not shown in the replay. Also when I inspect it using qapitrace, the cursor is now visible in the thumbnails/screenshots. So I don't know if the traces will be even useful. The traces are 20MB, 20MB and 70MB, I can temporarily host them somewhere if needed.

I experimented with some other games (where I see no cursor corruption), and in some games the cursor is recorded and replayed, in some games it is not. Does anybody know what the reason is and how to make sure the cursor is included?

My system:
01:00.0 VGA compatible controller [0300]: Advanced Micro Devices, Inc. [AMD/ATI] Curacao PRO [Radeon R7 370 / R9 270/370 OEM] [1002:6811]
kernel-4.2.3-300.fc23.x86_64
mesa-dri-drivers-11.0.3-1.20151012.fc23.x86_64
xorg-x11-server-Xorg-1.18.0-0.5.20150907.fc23.x86_64
xorg-x11-drv-ati-7.6.0-0.4.20150729git5510cd6.fc23.x86_64
Fedora 23

(In reply to acutiator from comment #5)
> I can't get apitrace to
> work with Steam games for me and the internet is being little help.

This worked for me:
https://github.com/apitrace/apitrace/wiki/Steam
Comment 8 Kamil Páral 2015-10-25 10:20:37 UTC
Created attachment 119183 [details]
Legend of Grimrock cursor corruption
Comment 9 Kamil Páral 2015-10-25 10:21:45 UTC
Created attachment 119184 [details]
Kingdom Rush cursor corruption

The cursor is in upper left corner, the corruption is a bit harder to see (similar colors).
Comment 10 Michel Dänzer 2015-10-27 06:23:53 UTC
Presumably the cursor isn't captured by apitrace because it's not rendered using OpenGL but uses the Xcursor* APIs. The artifacts are most likely due to the cursor image not using proper pre-mulitplied alpha data as expected by those APIs, which apparently happens to "work" to some degree with other drivers / hardware.
Comment 11 Kamil Páral 2015-10-27 08:37:07 UTC
Thanks, Michel, that sounds plausible. In that case it seems we can close this bug and the only thing to do here is to ask the developers to fix their games.
Comment 12 Bryant 2015-12-01 15:10:30 UTC
I'd like to start contacting these game developers to tell them about the issue, but I'd like to be quite specific about what they need to do to fix it. Can anyone provide some more insight on this so I know what to tell them?
Comment 13 Kamil Páral 2015-12-01 15:36:23 UTC
acutiator, thanks in advanced for the effort. I have zero knowledge about all of this, but this wikipedia article seems to be comprehensible:
https://en.wikipedia.org/wiki/Alpha_compositing

The important part:
~~~~~~~
If an alpha channel is used in an image, it is common to also multiply the color by the alpha value, to save on additional multiplications during compositing. This is usually referred to as premultiplied alpha.

Assuming that the pixel color is expressed using straight (non-premultiplied) RGBA tuples, a pixel value of (0.0, 0.5, 0.0, 0.5) implies a pixel that has 50% of the maximum green intensity and 50% opacity. If the color were fully green, its RGBA would be (0, 1, 0, 0.5).

However, if this pixel uses premultiplied alpha, all of the RGB values (0, 1, 0) are multiplied by 0.5 and then the alpha is appended to the end to yield (0, 0.5, 0, 0.5). In this case, the 0.5 value for the G channel actually indicates 100% green intensity (with 50% opacity). For this reason, knowing whether a file uses premultiplied or straight alpha is essential to correctly process or composite it.
~~~~~~~

I've also found the following howtos when searching for this:
http://www.gamedev.net/topic/623481-how-to-create-pre-multiplied-alpha-for-use-with-opengl/
http://blog.qythyx.com/2014/01/premultiplied-alpha.html

Hope that helps a bit. You might wait a while whether someone more knowledgeable gives you a better advice.
Comment 14 Michel Dänzer 2015-12-02 02:45:39 UTC
Kamil is spot on.

In particular, this means that the only way to encode a fully transparent pixel with premultiplied alpha is using (0, 0, 0, 0). Which is obviously not the case for the cursors on the attached screenshots, so those cursors don't use valid premultiplied alpha encoding.
Comment 15 Bryant 2015-12-02 04:48:21 UTC
Based on what you said, I would think that it should be possible to detect when an invalid pre-multiplied alpha bitmap is in use. Is that true in all circumstances or is there more nuance to that? If it is true, I would think it'd be worth correcting for this error on the library side, though the problem is actually in the games.
Comment 16 Alex Deucher 2015-12-02 15:27:52 UTC
(In reply to acutiator from comment #15)
> Based on what you said, I would think that it should be possible to detect
> when an invalid pre-multiplied alpha bitmap is in use. Is that true in all
> circumstances or is there more nuance to that? If it is true, I would think
> it'd be worth correcting for this error on the library side, though the
> problem is actually in the games.

How would the xserver know what the game intends in the cursor image?
Comment 17 Bryant 2015-12-02 15:42:11 UTC
> How would the xserver know what the game intends in the cursor image?

This is what I'm asking you, actually. I don't know if it's possible. I'm asking if it is. From what I understand based on the comments by Michel and Kamil it sounds like it should be possible. So I wanted to clarify on whether or not it is. The comment about a (0,0,0,0) pixel being a clear indicator that something is wrong is what triggered my question. If it can be clearly detected that it's a premultiplied alpha, even when the program doesn't indicate this, I would think that should be implemented. Now the question is if that can be easily detected without human intervention. But based on your question to me it doesn't sound like it is. Is that correct?
Comment 18 Alex Deucher 2015-12-02 16:17:26 UTC
(In reply to acutiator from comment #17)
> This is what I'm asking you, actually. I don't know if it's possible. I'm
> asking if it is. From what I understand based on the comments by Michel and
> Kamil it sounds like it should be possible. So I wanted to clarify on
> whether or not it is. The comment about a (0,0,0,0) pixel being a clear
> indicator that something is wrong is what triggered my question. If it can
> be clearly detected that it's a premultiplied alpha, even when the program
> doesn't indicate this, I would think that should be implemented. Now the
> question is if that can be easily detected without human intervention. But
> based on your question to me it doesn't sound like it is. Is that correct?

Correct.  I don't think it's possible.  We just get the raw image.  How do you determine the indent of a specific pixel based on the pixel value?  Did the provider intend it to be clear or did they indent it to be some specific color?
Comment 19 Kamil Páral 2015-12-02 17:16:35 UTC
I believe you can automatically detect invalid input in some cases. If you receive an image in which R or G or B value is higher than A value, for any available pixel, you can be certain that the image does not have premultiplied alpha but straight alpha (this situation can never happen with premultiplied alpha, by definition). You can then assume a developer mistake and "fix" the image automatically. It might even resolve most of the usual cursor-related mistakes (we can clearly see colored boxes, while it's expected to be transparent, so those images have RGB>A for some pixels).

However, this has downsides as well. It does not cover all cases (for images where all RGB are lower or equal to their respective A, you can't decide whether it is premultiplied or straight). The automatic detection and conversion might involve some performance hit. And it might not be a good API design, because trying to be overly helpful often leads to lowered predictability and more difficult debugging. But that would be someone else's call.

I might also be talking utter nonsense because I have no expertise in graphics.
Comment 20 Adam Jackson 2016-07-15 14:03:44 UTC
commit 401a8d6e1379133863e3271374dc21850d0d3cab
Author: Michel Dänzer <michel.daenzer@amd.com>
Date:   Tue Jun 28 17:22:47 2016 +0900

    dix: Work around non-premultiplied ARGB cursor data
Comment 21 Kamil Páral 2016-07-15 14:09:56 UTC
Thanks, Michel and Adam.

Use of freedesktop.org services, including Bugzilla, is subject to our Code of Conduct. How we collect and use information is described in our Privacy Policy.