1 Upon reception of an event that lowered the number of active back buffers,
2 the code would immediately try to free all back buffers with an id equal to or
3 higher than the new number of active back buffers.
5 However, that could lead to an active or to-be-active back buffer being freed,
6 since the old number of back buffers was used when obtaining an idle back
9 This lead to crashes when lowering the number of active back buffers by
10 transitioning from page-flipping to non-page-flipping presents.
12 Fix this by computing the number of active back buffers only when trying to
13 obtain a new back buffer.
15 Fixes: 15e208c4cc ("loader/dri3: Don't accidently free buffer holding new back content")
16 Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=104214
17 Cc: "17.3" <mesa-stable@lists.freedesktop.org>
18 Tested-by: Andriy.Khulap <andriy.khulap@globallogic.com>
19 Tested-by: Vadym Shovkoplias <vadym.shovkoplias@globallogic.com>
20 Reviewed-by: Michel Dänzer <michel.daenzer@amd.com>
21 Signed-off-by: Thomas Hellstrom <thellstrom@vmware.com>
23 src/loader/loader_dri3_helper.c | 6 +++---
24 1 file changed, 3 insertions(+), 3 deletions(-)
26 diff --git a/src/loader/loader_dri3_helper.c b/src/loader/loader_dri3_helper.c
27 index cc890bc..8f8efcb 100644
28 --- a/src/loader/loader_dri3_helper.c
29 +++ b/src/loader/loader_dri3_helper.c
30 @@ -205,7 +205,6 @@ void
31 loader_dri3_set_swap_interval(struct loader_dri3_drawable *draw, int interval)
33 draw->swap_interval = interval;
34 - dri3_update_num_back(draw);
37 /** dri3_free_render_buffer
38 @@ -377,7 +376,6 @@ dri3_handle_present_event(struct loader_dri3_drawable *draw,
39 draw->flipping = false;
42 - dri3_update_num_back(draw);
44 if (draw->vtable->show_fps)
45 draw->vtable->show_fps(draw, ce->ust);
46 @@ -402,7 +400,8 @@ dri3_handle_present_event(struct loader_dri3_drawable *draw,
49 if (buf && draw->num_back <= b && b < LOADER_DRI3_MAX_BACK &&
50 - draw->cur_blit_source != b) {
51 + draw->cur_blit_source != b &&
53 dri3_free_render_buffer(draw, buf);
54 draw->buffers[b] = NULL;
56 @@ -537,6 +536,7 @@ dri3_find_back(struct loader_dri3_drawable *draw)
57 /* Check whether we need to reuse the current back buffer as new back.
58 * In that case, wait until it's not busy anymore.
60 + dri3_update_num_back(draw);
61 num_to_consider = draw->num_back;
62 if (!loader_dri3_have_image_blit(draw) && draw->cur_blit_source != -1) {