background-content: Fix pipeline cache size

The cache had the size 9, which was "big enough" in the past, but when
more ways pipelines could be constructed, the size was not enough. The
need to increase the cache size was hard to spot though, since adding
pipeline flag didn't give any hints about the cache being directly tied
to these flag values.

So, when enough flag bits were set when attempting to retrieve and put a
pipeline in the cache, it'd instead overwrite some arbitrary stack
memory, which would sooner or later result in a memory corruption
induced crash. Valgrind could not detect this particular memory
corruption, as it messed up stack memory, not e.g. freed heap memory, so
it instead got confused and thought plain stack values were unreadable.

Fix these two issues by making the cache size the combination of all
pipeline flags + 1, so that we can safely put any flag combination in
the cache.

Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1747>
This commit is contained in:
Jonas Ådahl 2021-02-24 16:39:42 +01:00 committed by Marge Bot
parent bec456ba0a
commit 3bbfaa03b3

View File

@ -218,6 +218,11 @@ typedef enum
PIPELINE_BLEND = (1 << 1), PIPELINE_BLEND = (1 << 1),
PIPELINE_GRADIENT = (1 << 2), PIPELINE_GRADIENT = (1 << 2),
PIPELINE_ROUNDED_CLIP = (1 << 3), PIPELINE_ROUNDED_CLIP = (1 << 3),
PIPELINE_ALL = (PIPELINE_VIGNETTE |
PIPELINE_BLEND |
PIPELINE_GRADIENT |
PIPELINE_ROUNDED_CLIP)
} PipelineFlags; } PipelineFlags;
struct _MetaBackgroundContent struct _MetaBackgroundContent
@ -324,9 +329,11 @@ on_background_changed (MetaBackground *background,
static CoglPipeline * static CoglPipeline *
make_pipeline (PipelineFlags pipeline_flags) make_pipeline (PipelineFlags pipeline_flags)
{ {
static CoglPipeline *templates[9]; static CoglPipeline *templates[PIPELINE_ALL + 1];
CoglPipeline **templatep; CoglPipeline **templatep;
g_assert (pipeline_flags < G_N_ELEMENTS (templates));
templatep = &templates[pipeline_flags]; templatep = &templates[pipeline_flags];
if (*templatep == NULL) if (*templatep == NULL)
{ {