mirror of
https://github.com/X11Libre/xserver.git
synced 2026-11-15 05:23:40 +00:00
dri2: Use booleans for (fake) front buffer tracking in do_get_buffers
This works as intended — the (fake) front buffer needs to be added
only if the client didn't request it in the first place — even if the
client requests the same attachment multiple times. This ensures we
never try to access more than (count + 1) entries of the buffers array.
Fixes: ff6c7764c2 ("DRI2: Implement protocol for DRI2GetBuffersWithFormat")
Signed-off-by: Michel Dänzer <mdaenzer@redhat.com>
Part-of: <https://gitlab.freedesktop.org/xorg/xserver/-/merge_requests/2228>
This commit is contained in:
parent
4f3b7f7a64
commit
dce46884f9
1 changed files with 18 additions and 19 deletions
|
|
@ -564,9 +564,10 @@ do_get_buffers(DrawablePtr pDraw, int *width, int *height,
|
||||||
DRI2DrawablePtr pPriv = DRI2GetDrawable(pDraw);
|
DRI2DrawablePtr pPriv = DRI2GetDrawable(pDraw);
|
||||||
DRI2ScreenPtr ds;
|
DRI2ScreenPtr ds;
|
||||||
DRI2BufferPtr *buffers;
|
DRI2BufferPtr *buffers;
|
||||||
int need_real_front = 0;
|
Bool need_real_front = FALSE;
|
||||||
int need_fake_front = 0;
|
Bool have_real_front = FALSE;
|
||||||
int have_fake_front = 0;
|
Bool need_fake_front = FALSE;
|
||||||
|
Bool have_fake_front = FALSE;
|
||||||
int front_format = 0;
|
int front_format = 0;
|
||||||
int dimensions_match;
|
int dimensions_match;
|
||||||
int buffers_changed = 0;
|
int buffers_changed = 0;
|
||||||
|
|
@ -599,34 +600,32 @@ do_get_buffers(DrawablePtr pDraw, int *width, int *height,
|
||||||
if (buffers[i] == NULL)
|
if (buffers[i] == NULL)
|
||||||
goto err_out;
|
goto err_out;
|
||||||
|
|
||||||
/* If the drawable is a window and the front-buffer is requested,
|
/* In certain cases the (fake) front buffer is always needed, so return
|
||||||
* silently add the fake front-buffer to the list of requested
|
* it even if the client failed to request it.
|
||||||
* attachments. The counting logic in the loop accounts for the case
|
* The logic in & after the loop accounts for the case where the client
|
||||||
* where the client requests both the fake and real front-buffer.
|
* does request the (fake) front buffer, to avoid returning it multiple
|
||||||
|
* times.
|
||||||
*/
|
*/
|
||||||
if (attachment == DRI2BufferBackLeft) {
|
if (attachment == DRI2BufferBackLeft) {
|
||||||
need_real_front++;
|
need_real_front = TRUE;
|
||||||
front_format = format;
|
front_format = format;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (attachment == DRI2BufferFrontLeft) {
|
if (attachment == DRI2BufferFrontLeft) {
|
||||||
need_real_front--;
|
have_real_front = TRUE;
|
||||||
front_format = format;
|
front_format = format;
|
||||||
|
|
||||||
if (pDraw->type == DRAWABLE_WINDOW) {
|
if (pDraw->type == DRAWABLE_WINDOW)
|
||||||
need_fake_front++;
|
need_fake_front = TRUE;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pDraw->type == DRAWABLE_WINDOW) {
|
if (pDraw->type == DRAWABLE_WINDOW) {
|
||||||
if (attachment == DRI2BufferFakeFrontLeft) {
|
if (attachment == DRI2BufferFakeFrontLeft)
|
||||||
need_fake_front--;
|
have_fake_front = TRUE;
|
||||||
have_fake_front = 1;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (need_real_front > 0) {
|
if (need_real_front && !have_real_front) {
|
||||||
if (allocate_or_reuse_buffer(pDraw, ds, pPriv, DRI2BufferFrontLeft,
|
if (allocate_or_reuse_buffer(pDraw, ds, pPriv, DRI2BufferFrontLeft,
|
||||||
front_format, dimensions_match,
|
front_format, dimensions_match,
|
||||||
&buffers[i]))
|
&buffers[i]))
|
||||||
|
|
@ -637,7 +636,7 @@ do_get_buffers(DrawablePtr pDraw, int *width, int *height,
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (need_fake_front > 0) {
|
if (need_fake_front && !have_fake_front) {
|
||||||
if (allocate_or_reuse_buffer(pDraw, ds, pPriv, DRI2BufferFakeFrontLeft,
|
if (allocate_or_reuse_buffer(pDraw, ds, pPriv, DRI2BufferFakeFrontLeft,
|
||||||
front_format, dimensions_match,
|
front_format, dimensions_match,
|
||||||
&buffers[i]))
|
&buffers[i]))
|
||||||
|
|
@ -647,7 +646,7 @@ do_get_buffers(DrawablePtr pDraw, int *width, int *height,
|
||||||
goto err_out;
|
goto err_out;
|
||||||
|
|
||||||
i++;
|
i++;
|
||||||
have_fake_front = 1;
|
have_fake_front = TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
*out_count = i;
|
*out_count = i;
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue