Clearing can happen at a time when various state objects are incoherent
and not ready for a draw. Some of the validation functions don't handle
this well, so only flush the framebuffer state. This has the advantage
of also not doing extra work.
This works around some crashes that can happen when clearing.
Signed-off-by: Ilia Mirkin <imirkin@alum.mit.edu>
Reviewed-by: Tobias Klausmann <tobias.johannes.klausmann@mni.thm.de>
(cherry picked from commit
aba3392541f38f82e3ebde251fdcca78e90adbf3)
struct pipe_framebuffer_state *fb = &nv30->framebuffer;
uint32_t colr = 0, zeta = 0, mode = 0;
- if (!nv30_state_validate(nv30, TRUE))
+ if (!nv30_state_validate(nv30, NV30_NEW_FRAMEBUFFER | NV30_NEW_SCISSOR, TRUE))
return;
if (buffers & PIPE_CLEAR_COLOR && fb->nr_cbufs) {
nv30_render_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info);
boolean
-nv30_state_validate(struct nv30_context *nv30, boolean hwtnl);
+nv30_state_validate(struct nv30_context *nv30, uint32_t mask, boolean hwtnl);
void
nv30_state_release(struct nv30_context *nv30);
NOUVEAU_BO_LOW | NOUVEAU_BO_RD, 0, NV30_3D_VTXBUF_DMA1);
}
- if (!nv30_state_validate(nv30, FALSE))
+ if (!nv30_state_validate(nv30, ~0, FALSE))
return;
BEGIN_NV04(push, NV30_3D(VERTEX_BEGIN_END), 1);
NOUVEAU_BO_LOW | NOUVEAU_BO_RD, 0, NV30_3D_VTXBUF_DMA1);
}
- if (!nv30_state_validate(nv30, FALSE))
+ if (!nv30_state_validate(nv30, ~0, FALSE))
return;
BEGIN_NV04(push, NV30_3D(VERTEX_BEGIN_END), 1);
}
boolean
-nv30_state_validate(struct nv30_context *nv30, boolean hwtnl)
+nv30_state_validate(struct nv30_context *nv30, uint32_t mask, boolean hwtnl)
{
struct nouveau_screen *screen = &nv30->screen->base;
struct nouveau_pushbuf *push = nv30->base.pushbuf;
else
validate = swtnl_validate_list;
- if (nv30->dirty) {
+ mask &= nv30->dirty;
+
+ if (mask) {
while (validate->func) {
- if (nv30->dirty & validate->mask)
+ if (mask & validate->mask)
validate->func(nv30);
validate++;
}
- nv30->dirty = 0;
+ nv30->dirty &= ~mask;
}
nouveau_pushbuf_bufctx(push, bctx);
if (nv30->vbo_user && !(nv30->dirty & (NV30_NEW_VERTEX | NV30_NEW_ARRAYS)))
nv30_update_user_vbufs(nv30);
- nv30_state_validate(nv30, TRUE);
+ nv30_state_validate(nv30, ~0, TRUE);
if (nv30->draw_flags) {
nv30_render_vbo(pipe, info);
return;