gallium: Add pipe cap for masked clears and support stencil masking

Add a new PIPE_CAP_CLEAR_MASKED capability that allows drivers to
handle buffer clears with color and stencil masks directly, instead
of falling back to drawing a quad in Mesa.

This patch introduces several changes:

1. Add the new pipe cap PIPE_CAP_CLEAR_MASKED to pipe_defines.h and
   document it in the Gallium screen documentation.

2. Add color_clear_mask and stencil_clear_mask parameters to the
   pipe_context::clear() hook:
   - color_clear_mask (uint32_t): contains 4 color mask bits per draw buffer
     (max 8 buffers = 32 bits)
   - stencil_clear_mask (uint8_t): contains the stencil write mask (8 bits)

3. Update the state tracker to use the masked clear path when the
   driver supports it:
   - Pass ctx->Color.ColorMask for color buffer clears
   - Pass ctx->Stencil.WriteMask for stencil clears
   - Allow both color and stencil clears to avoid the quad path when
     masks are present and the driver advertises support

4. Update all existing driver clear() hooks to accept the new
   color_clear_mask and stencil_clear_mask parameter.

This optimization allows drivers that can efficiently handle masked
clears in hardware to do so, improving performance for applications
that frequently clear buffers with masks enabled.

Signed-off-by: Christian Gmeiner <cgmeiner@igalia.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/31512>
This commit is contained in:
Christian Gmeiner 2025-07-09 15:40:38 +02:00 committed by Marge Bot
parent 3361ca86cf
commit 9c972a61d5
45 changed files with 109 additions and 27 deletions

View file

@ -674,6 +674,7 @@ Capability about the features and limits of the driver/GPU.
dilation.
* ``pipe_caps.conservative_raster_dilate_granularity``: The conservative rasterization
dilation granularity for values relative to the minimum dilation.
* ``pipe_caps.clear_masked``: Whether ``clear`` can accept a color_clear_mask for all color buffers and stencil_clear_mask.
.. _pipe_shader_caps:

View file

@ -1601,7 +1601,9 @@ dd_context_flush_resource(struct pipe_context *_pipe,
}
static void
dd_context_clear(struct pipe_context *_pipe, unsigned buffers, const struct pipe_scissor_state *scissor_state,
dd_context_clear(struct pipe_context *_pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil)
{
@ -1611,6 +1613,8 @@ dd_context_clear(struct pipe_context *_pipe, unsigned buffers, const struct pipe
record->call.type = CALL_CLEAR;
record->call.info.clear.buffers = buffers;
record->call.info.clear.color_clear_mask = color_clear_mask;
record->call.info.clear.stencil_clear_mask = stencil_clear_mask;
if (scissor_state)
record->call.info.clear.scissor_state = *scissor_state;
record->call.info.clear.color = *color;
@ -1618,7 +1622,7 @@ dd_context_clear(struct pipe_context *_pipe, unsigned buffers, const struct pipe
record->call.info.clear.stencil = stencil;
dd_before_draw(dctx, record);
pipe->clear(pipe, buffers, scissor_state, color, depth, stencil);
pipe->clear(pipe, buffers, color_clear_mask, stencil_clear_mask, scissor_state, color, depth, stencil);
dd_after_draw(dctx, record);
}

View file

@ -106,6 +106,8 @@ struct call_image_copy_buffer
struct call_clear
{
unsigned buffers;
uint32_t color_clear_mask;
uint8_t stencil_clear_mask;
struct pipe_scissor_state scissor_state;
union pipe_color_union color;
double depth;

View file

@ -277,7 +277,9 @@ static void noop_texture_subdata(struct pipe_context *pipe,
/*
* clear/copy
*/
static void noop_clear(struct pipe_context *ctx, unsigned buffers, const struct pipe_scissor_state *scissor_state,
static void noop_clear(struct pipe_context *ctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
}

View file

@ -1411,6 +1411,8 @@ trace_context_flush_resource(struct pipe_context *_pipe,
static void
trace_context_clear(struct pipe_context *_pipe,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth,
@ -1423,6 +1425,8 @@ trace_context_clear(struct pipe_context *_pipe,
trace_dump_arg(ptr, pipe);
trace_dump_arg(uint, buffers);
trace_dump_arg(uint, color_clear_mask);
trace_dump_arg(uint, stencil_clear_mask);
trace_dump_arg_begin("scissor_state");
trace_dump_scissor_state(scissor_state);
trace_dump_arg_end();
@ -1433,7 +1437,7 @@ trace_context_clear(struct pipe_context *_pipe,
trace_dump_arg(float, depth);
trace_dump_arg(uint, stencil);
pipe->clear(pipe, buffers, scissor_state, color, depth, stencil);
pipe->clear(pipe, buffers, color_clear_mask, stencil_clear_mask, scissor_state, color, depth, stencil);
trace_dump_call_end();
}

View file

@ -129,7 +129,7 @@ pp_jimenezmlaa_run(struct pp_queue_t *ppq, struct pipe_resource *in,
pp_filter_set_fb(p);
pp_filter_misc_state(p);
cso_set_depth_stencil_alpha(p->cso, &mstencil);
p->pipe->clear(p->pipe, PIPE_CLEAR_STENCIL | PIPE_CLEAR_COLOR0, NULL,
p->pipe->clear(p->pipe, PIPE_CLEAR_STENCIL | PIPE_CLEAR_COLOR0, 0xf, 0xff, NULL,
&p->clear_color, 0, 0);
{

View file

@ -306,5 +306,5 @@ void
pp_filter_set_clear_fb(struct pp_program *p)
{
cso_set_framebuffer(p->cso, &p->framebuffer);
p->pipe->clear(p->pipe, PIPE_CLEAR_COLOR0, NULL, &p->clear_color, 0, 0);
p->pipe->clear(p->pipe, PIPE_CLEAR_COLOR0, 0xf, 0, NULL, &p->clear_color, 0, 0);
}

View file

@ -181,7 +181,7 @@ util_set_common_states_and_clear(struct cso_context *cso, struct pipe_context *c
util_set_rasterizer_normal(cso);
util_set_max_viewport(cso, cb);
ctx->clear(ctx, PIPE_CLEAR_COLOR0, NULL, (void*)clear_color, 0, 0);
ctx->clear(ctx, PIPE_CLEAR_COLOR0, 0xf, 0xff, NULL, (void*)clear_color, 0, 0);
}
static void

View file

@ -4825,6 +4825,8 @@ struct tc_clear {
bool scissor_state_set;
uint8_t stencil;
uint16_t buffers;
uint32_t color_clear_mask;
uint8_t stencil_clear_mask;
float depth;
struct pipe_scissor_state scissor_state;
union pipe_color_union color;
@ -4835,12 +4837,14 @@ tc_call_clear(struct pipe_context *pipe, void *call)
{
struct tc_clear *p = to_call(call, tc_clear);
pipe->clear(pipe, p->buffers, p->scissor_state_set ? &p->scissor_state : NULL, &p->color, p->depth, p->stencil);
pipe->clear(pipe, p->buffers, p->color_clear_mask, p->stencil_clear_mask, p->scissor_state_set ? &p->scissor_state : NULL, &p->color, p->depth, p->stencil);
return call_size(tc_clear);
}
static void
tc_clear(struct pipe_context *_pipe, unsigned buffers, const struct pipe_scissor_state *scissor_state,
tc_clear(struct pipe_context *_pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil)
{
@ -4848,6 +4852,8 @@ tc_clear(struct pipe_context *_pipe, unsigned buffers, const struct pipe_scissor
struct tc_clear *p = tc_add_call(tc, TC_CALL_clear, tc_clear);
p->buffers = buffers;
p->color_clear_mask = color_clear_mask;
p->stencil_clear_mask = stencil_clear_mask;
tc->seen_fb_state = true;
if (scissor_state) {
p->scissor_state = *scissor_state;

View file

@ -1073,6 +1073,7 @@ agx_transfer_unmap(struct pipe_context *pctx, struct pipe_transfer *transfer)
*/
static void
agx_clear(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{

View file

@ -613,6 +613,8 @@ clear_depth_stencil(struct crocus_context *ice,
static void
crocus_clear(struct pipe_context *ctx,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *p_color,
double depth,

View file

@ -2081,6 +2081,7 @@ d3d12_clear_depth_stencil(struct pipe_context *pctx,
static void
d3d12_clear(struct pipe_context *pctx,
unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)

View file

@ -479,7 +479,9 @@ etna_blit_clear_zs_blt(struct pipe_context *pctx, struct pipe_surface *dst,
}
static void
etna_clear_blt(struct pipe_context *pctx, unsigned buffers, const struct pipe_scissor_state *scissor_state,
etna_clear_blt(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
struct etna_context *ctx = etna_context(pctx);

View file

@ -476,7 +476,9 @@ etna_blit_clear_zs_rs(struct pipe_context *pctx, struct pipe_surface *dst,
}
static void
etna_clear_rs(struct pipe_context *pctx, unsigned buffers, const struct pipe_scissor_state *scissor_state,
etna_clear_rs(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
struct etna_context *ctx = etna_context(pctx);

View file

@ -461,6 +461,7 @@ batch_clear_tracking(struct fd_batch *batch, unsigned buffers) assert_dt
static void
fd_clear(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil) in_dt

View file

@ -218,6 +218,7 @@ i915_clear_emit(struct pipe_context *pipe, unsigned buffers,
*/
void
i915_clear_blitter(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil)
@ -251,6 +252,7 @@ i915_clear_blitter(struct pipe_context *pipe, unsigned buffers,
void
i915_clear_render(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil)

View file

@ -406,10 +406,12 @@ void i915_emit_hardware_state(struct i915_context *i915);
* i915_clear.c:
*/
void i915_clear_blitter(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil);
void i915_clear_render(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil);

View file

@ -818,6 +818,8 @@ clear_depth_stencil(struct iris_context *ice,
static void
iris_clear(struct pipe_context *ctx,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *p_color,
double depth,

View file

@ -148,7 +148,9 @@ lima_update_job_wb(struct lima_context *ctx, unsigned buffers)
}
static void
lima_clear(struct pipe_context *pctx, unsigned buffers, const struct pipe_scissor_state *scissor_state,
lima_clear(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
struct lima_context *ctx = lima_context(pctx);

View file

@ -48,6 +48,8 @@
void
llvmpipe_clear(struct pipe_context *pipe,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth,

View file

@ -37,6 +37,7 @@ struct pipe_context;
extern void
llvmpipe_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil);

View file

@ -51,7 +51,9 @@ pack_zeta(enum pipe_format format, double depth, unsigned stencil)
}
static void
nv30_clear(struct pipe_context *pipe, unsigned buffers, const struct pipe_scissor_state *scissor_state,
nv30_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
struct nv30_context *nv30 = nv30_context(pipe);

View file

@ -312,6 +312,7 @@ bool nv50_state_validate_3d(struct nv50_context *, uint32_t);
/* nv50_surface.c */
extern void nv50_clear(struct pipe_context *, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil);

View file

@ -454,7 +454,9 @@ nv50_clear_depth_stencil(struct pipe_context *pipe,
}
void
nv50_clear(struct pipe_context *pipe, unsigned buffers, const struct pipe_scissor_state *scissor_state,
nv50_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)
{

View file

@ -378,6 +378,7 @@ bool nvc0_state_validate_3d(struct nvc0_context *, uint32_t);
/* nvc0_surface.c */
extern void nvc0_clear(struct pipe_context *, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil);

View file

@ -693,6 +693,7 @@ nvc0_clear_depth_stencil(struct pipe_context *pipe,
void
nvc0_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)

View file

@ -40,6 +40,7 @@
static void
panfrost_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil)

View file

@ -195,6 +195,8 @@ DEBUG_GET_ONCE_BOOL_OPTION(hyperz, "RADEON_HYPERZ", false)
/* Clear currently bound buffers. */
static void r300_clear(struct pipe_context* pipe,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth,

View file

@ -585,6 +585,7 @@ evergreen_do_fast_color_clear(struct r600_context *rctx,
}
static void r600_clear(struct pipe_context *ctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)

View file

@ -1116,6 +1116,7 @@ static void si_fb_clear_via_compute(struct si_context *sctx, unsigned *buffers,
}
static void gfx6_clear(struct pipe_context *ctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
@ -1235,6 +1236,7 @@ static void gfx6_clear(struct pipe_context *ctx, unsigned buffers,
}
static void gfx12_clear(struct pipe_context *ctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
@ -1309,7 +1311,7 @@ static bool si_try_normal_clear(struct si_context *sctx, struct pipe_surface *ds
fb.height = surf_height;
ctx->set_framebuffer_state(ctx, &fb);
ctx->clear(ctx, buffers, NULL, color, depth, stencil);
ctx->clear(ctx, buffers, 0xf, 0, NULL, color, depth, stencil);
ctx->set_framebuffer_state(ctx, &saved_fb);
util_copy_framebuffer_state(&saved_fb, NULL);

View file

@ -540,7 +540,7 @@ void si_test_blit_perf(struct si_screen *sscreen)
switch (method) {
case METHOD_DEFAULT:
if (test_flavor == TEST_FB_CLEAR) {
ctx->clear(ctx, PIPE_CLEAR_COLOR, NULL, clear_color, 0, 0);
ctx->clear(ctx, PIPE_CLEAR_COLOR, 0xf, 0, NULL, clear_color, 0, 0);
si_set_barrier_flags(sctx, SI_BARRIER_SYNC_AND_INV_CB | SI_BARRIER_INV_L2);
} else {
ctx->clear_render_target(ctx, &surf_templ, clear_color,

View file

@ -48,6 +48,7 @@
*/
void
softpipe_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)

View file

@ -32,10 +32,13 @@
#ifndef SP_CLEAR_H
#define SP_CLEAR_H
#include <stdint.h>
struct pipe_context;
extern void
softpipe_clear(struct pipe_context *pipe, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil);

View file

@ -229,6 +229,8 @@ try_clear(struct svga_context *svga,
static void
svga_clear(struct pipe_context *pipe,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)

View file

@ -713,13 +713,15 @@ tegra_blit(struct pipe_context *pcontext, const struct pipe_blit_info *pinfo)
}
static void
tegra_clear(struct pipe_context *pcontext, unsigned buffers, const struct pipe_scissor_state *scissor_state,
tegra_clear(struct pipe_context *pcontext, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth,
unsigned stencil)
{
struct tegra_context *context = to_tegra_context(pcontext);
context->gpu->clear(context->gpu, buffers, NULL, color, depth, stencil);
context->gpu->clear(context->gpu, buffers, color_clear_mask, stencil_clear_mask, NULL, color, depth, stencil);
}
static void

View file

@ -1804,7 +1804,9 @@ v3d_tlb_clear(struct v3d_job *job, unsigned buffers,
}
static void
v3d_clear(struct pipe_context *pctx, unsigned buffers, const struct pipe_scissor_state *scissor_state,
v3d_clear(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
struct v3d_context *v3d = v3d_context(pctx);

View file

@ -541,7 +541,9 @@ pack_rgba(enum pipe_format format, const float *rgba)
}
static void
vc4_clear(struct pipe_context *pctx, unsigned buffers, const struct pipe_scissor_state *scissor_state,
vc4_clear(struct pipe_context *pctx, unsigned buffers,
uint32_t color_clear_mask, uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color, double depth, unsigned stencil)
{
struct vc4_context *vc4 = vc4_context(pctx);

View file

@ -894,6 +894,8 @@ static void virgl_bind_fs_state(struct pipe_context *ctx,
static void virgl_clear(struct pipe_context *ctx,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth, unsigned stencil)

View file

@ -148,6 +148,8 @@ get_clear_data(struct zink_context *ctx, struct zink_framebuffer_clear *fb_clear
void
zink_clear(struct pipe_context *pctx,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *pcolor,
double depth, unsigned stencil)
@ -243,7 +245,7 @@ zink_clear(struct pipe_context *pctx,
}
}
if (void_clears)
pctx->clear(pctx, void_clears, NULL, &color, 0, 0);
pctx->clear(pctx, void_clears, 0xffffffff, 0, NULL, &color, 0, 0);
}
if (buffers & PIPE_CLEAR_COLOR) {
@ -378,6 +380,7 @@ out:
clear_bits |= zsclear->zs.bits;
}
zink_clear(&ctx->base, clear_bits,
0xffffffff, 0xff,
clear->has_scissor ? &clear->scissor : NULL,
&clear->color,
zsclear ? zsclear->zs.depth : 0,
@ -387,6 +390,7 @@ out:
for (int j = !zink_fb_clear_first_needs_explicit(zs_clear); j < zink_fb_clear_count(zs_clear); j++) {
struct zink_framebuffer_clear_data *clear = zink_fb_clear_element(zs_clear, j);
zink_clear(&ctx->base, clear->zs.bits,
0xffffffff, 0xff,
clear->has_scissor ? &clear->scissor : NULL,
NULL,
clear->zs.depth,
@ -581,7 +585,7 @@ zink_clear_render_target(struct pipe_context *pctx, struct pipe_surface *dst,
struct pipe_scissor_state scissor = {dstx, dsty, dstx + width, dsty + height};
zink_blit_barriers(ctx, NULL, zink_resource(pres), false);
ctx->blitting = true;
pctx->clear(pctx, PIPE_CLEAR_COLOR0, &scissor, color, 0, 0);
pctx->clear(pctx, PIPE_CLEAR_COLOR0, 0xf, 0, &scissor, color, 0, 0);
util_blitter_restore_fb_state(ctx->blitter);
ctx->blitting = false;
if (!render_condition_enabled && render_condition_active)
@ -618,7 +622,7 @@ zink_clear_depth_stencil(struct pipe_context *pctx, struct pipe_surface *dst,
}
}
struct pipe_scissor_state scissor = {dstx, dsty, dstx + width, dsty + height};
pctx->clear(pctx, clear_flags, &scissor, NULL, depth, stencil);
pctx->clear(pctx, clear_flags, 0, 0xff, &scissor, NULL, depth, stencil);
if (!cur_attachment && !blitting) {
util_blitter_restore_fb_state(ctx->blitter);
ctx->blitting = false;

View file

@ -31,6 +31,8 @@
void
zink_clear(struct pipe_context *pctx,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *pcolor,
double depth, unsigned stencil);

View file

@ -3466,7 +3466,7 @@ zink_batch_rp(struct zink_context *ctx)
union pipe_color_union color;
color.f[0] = color.f[1] = color.f[2] = 0;
color.f[3] = 1.0;
ctx->base.clear(&ctx->base, ctx->void_clears, NULL, &color, 0, 0);
ctx->base.clear(&ctx->base, ctx->void_clears, 0xffffffff, 0xff, NULL, &color, 0, 0);
ctx->void_clears = 0;
}
if (!ctx->blitting) {

View file

@ -1475,6 +1475,7 @@ static void render_clear_fast(struct rendering_state *state)
col_val.ui[i] = color_value.color.uint32[i];
state->pctx->clear(state->pctx, buffers,
0xffffffff, 0xff,
NULL, &col_val,
dclear_val, sclear_val);
return;

View file

@ -712,6 +712,8 @@ struct pipe_context {
* The entire buffers are cleared (no scissor, no colormask, etc).
*
* \param buffers bitfield of PIPE_CLEAR_* values.
* \param color_clear_mask 4 color_mask bits per draw buffer, max 8 draw buffers. 4*8 = 32 bits
* \param stencil_clear_mask the stencil mask
* \param scissor_state the scissored region to clear
* \param color pointer to a union of fiu array for each of r, g, b, a.
* \param depth depth clear value in [0,1].
@ -719,6 +721,8 @@ struct pipe_context {
*/
void (*clear)(struct pipe_context *pipe,
unsigned buffers,
uint32_t color_clear_mask,
uint8_t stencil_clear_mask,
const struct pipe_scissor_state *scissor_state,
const union pipe_color_union *color,
double depth,

View file

@ -927,6 +927,7 @@ struct pipe_caps {
bool shareable_shaders;
bool copy_between_compressed_and_plain_formats;
bool clear_scissored;
bool clear_masked;
bool draw_parameters;
bool shader_pack_half_float;
bool multi_draw_indirect;

View file

@ -392,6 +392,8 @@ st_Clear(struct gl_context *ctx, GLbitfield mask)
= ctx->DrawBuffer->Attachment[BUFFER_DEPTH].Renderbuffer;
struct gl_renderbuffer *stencilRb
= ctx->DrawBuffer->Attachment[BUFFER_STENCIL].Renderbuffer;
uint32_t color_clear_mask = ctx->Color.ColorMask;
uint8_t stencil_clear_mask = ctx->Stencil.WriteMask[0] & 0xff;
GLbitfield quad_buffers = 0x0;
GLbitfield clear_buffers = 0x0;
bool have_scissor_buffers = false;
@ -429,7 +431,7 @@ st_Clear(struct gl_context *ctx, GLbitfield mask)
bool scissor = is_scissor_enabled(ctx, rb);
if ((scissor && !st->can_scissor_clear) ||
is_window_rectangle_enabled(ctx) ||
((colormask & surf_colormask) != surf_colormask))
(((colormask & surf_colormask) != surf_colormask) && !st->pipe->screen->caps.clear_masked))
quad_buffers |= PIPE_CLEAR_COLOR0 << i;
else
clear_buffers |= PIPE_CLEAR_COLOR0 << i;
@ -454,7 +456,7 @@ st_Clear(struct gl_context *ctx, GLbitfield mask)
bool scissor = is_scissor_enabled(ctx, stencilRb);
if ((scissor && !st->can_scissor_clear) ||
is_window_rectangle_enabled(ctx) ||
is_stencil_masked(ctx, stencilRb))
(is_stencil_masked(ctx, stencilRb) && !st->pipe->screen->caps.clear_masked))
quad_buffers |= PIPE_CLEAR_STENCIL;
else
clear_buffers |= PIPE_CLEAR_STENCIL;
@ -508,7 +510,9 @@ st_Clear(struct gl_context *ctx, GLbitfield mask)
/* We can't translate the clear color to the colorbuffer format,
* because different colorbuffers may have different formats.
*/
st->pipe->clear(st->pipe, clear_buffers, have_scissor_buffers ? &scissor_state : NULL,
st->pipe->clear(st->pipe, clear_buffers,
color_clear_mask, stencil_clear_mask,
have_scissor_buffers ? &scissor_state : NULL,
(union pipe_color_union*)&ctx->Color.ClearColor,
ctx->Depth.Clear, ctx->Stencil.Clear);
}