ilo: offset to layers only when necessary
GEN6 has several requirements regarding the LOD/Depth/Width/Height of the render targets and the depth buffer. We used to offset to the layers in question unconditionally to meet the requirements. With this commit, offseting is done only when the requirements are not met.
This commit is contained in:
parent
0a2a221d01
commit
011fde4bf2
|
@ -723,13 +723,27 @@ gen6_pipeline_wm_depth(struct ilo_3d_pipeline *p,
|
|||
/* 3DSTATE_DEPTH_BUFFER and 3DSTATE_CLEAR_PARAMS */
|
||||
if (DIRTY(FB) || session->batch_bo_changed) {
|
||||
const struct ilo_zs_surface *zs;
|
||||
struct ilo_zs_surface layer;
|
||||
|
||||
if (ilo->fb.state.zsbuf) {
|
||||
const struct ilo_surface_cso *surface =
|
||||
(const struct ilo_surface_cso *) ilo->fb.state.zsbuf;
|
||||
|
||||
assert(!surface->is_rt);
|
||||
zs = &surface->u.zs;
|
||||
if (ilo->fb.offset_to_layers) {
|
||||
assert(surface->base.u.tex.first_layer ==
|
||||
surface->base.u.tex.last_layer);
|
||||
|
||||
ilo_gpe_init_zs_surface(ilo->dev,
|
||||
ilo_texture(surface->base.texture),
|
||||
surface->base.format, surface->base.u.tex.level,
|
||||
surface->base.u.tex.first_layer, 1, true, &layer);
|
||||
|
||||
zs = &layer;
|
||||
}
|
||||
else {
|
||||
assert(!surface->is_rt);
|
||||
zs = &surface->u.zs;
|
||||
}
|
||||
}
|
||||
else {
|
||||
zs = &ilo->fb.null_zs;
|
||||
|
@ -875,9 +889,27 @@ gen6_pipeline_state_surfaces_rt(struct ilo_3d_pipeline *p,
|
|||
const struct ilo_surface_cso *surface =
|
||||
(const struct ilo_surface_cso *) fb->state.cbufs[i];
|
||||
|
||||
assert(surface && surface->is_rt);
|
||||
surface_state[i] =
|
||||
gen6_emit_SURFACE_STATE(p->dev, &surface->u.rt, true, p->cp);
|
||||
if (fb->offset_to_layers) {
|
||||
struct ilo_view_surface layer;
|
||||
|
||||
assert(surface->base.u.tex.first_layer ==
|
||||
surface->base.u.tex.last_layer);
|
||||
|
||||
ilo_gpe_init_view_surface_for_texture(ilo->dev,
|
||||
ilo_texture(surface->base.texture),
|
||||
surface->base.format,
|
||||
surface->base.u.tex.level, 1,
|
||||
surface->base.u.tex.first_layer, 1,
|
||||
true, true, &layer);
|
||||
|
||||
surface_state[i] =
|
||||
gen6_emit_SURFACE_STATE(p->dev, &layer, true, p->cp);
|
||||
}
|
||||
else {
|
||||
assert(surface && surface->is_rt);
|
||||
surface_state[i] =
|
||||
gen6_emit_SURFACE_STATE(p->dev, &surface->u.rt, true, p->cp);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -257,7 +257,9 @@ struct ilo_fb_state {
|
|||
struct pipe_framebuffer_state state;
|
||||
|
||||
struct ilo_zs_surface null_zs;
|
||||
|
||||
unsigned num_samples;
|
||||
bool offset_to_layers;
|
||||
};
|
||||
|
||||
struct ilo_global_binding {
|
||||
|
@ -525,4 +527,9 @@ ilo_gpe_init_fs_cso(const struct ilo_dev_info *dev,
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
ilo_gpe_init_fb(const struct ilo_dev_info *dev,
|
||||
const struct pipe_framebuffer_state *state,
|
||||
struct ilo_fb_state *fb);
|
||||
|
||||
#endif /* ILO_GPE_H */
|
||||
|
|
|
@ -26,6 +26,7 @@
|
|||
*/
|
||||
|
||||
#include "util/u_dual_blend.h"
|
||||
#include "util/u_framebuffer.h"
|
||||
#include "util/u_half.h"
|
||||
#include "brw_defines.h"
|
||||
#include "intel_reg.h"
|
||||
|
@ -2454,6 +2455,94 @@ ilo_gpe_init_sampler_cso(const struct ilo_dev_info *dev,
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
ilo_gpe_init_fb(const struct ilo_dev_info *dev,
|
||||
const struct pipe_framebuffer_state *state,
|
||||
struct ilo_fb_state *fb)
|
||||
{
|
||||
const struct pipe_surface *first;
|
||||
unsigned num_surfaces;
|
||||
|
||||
ILO_GPE_VALID_GEN(dev, 6, 7.5);
|
||||
|
||||
util_copy_framebuffer_state(&fb->state, state);
|
||||
|
||||
first = (state->nr_cbufs) ? state->cbufs[0] :
|
||||
(state->zsbuf) ? state->zsbuf :
|
||||
NULL;
|
||||
num_surfaces = state->nr_cbufs + !!state->zsbuf;
|
||||
|
||||
fb->num_samples = (first) ? first->texture->nr_samples : 1;
|
||||
if (!fb->num_samples)
|
||||
fb->num_samples = 1;
|
||||
|
||||
fb->offset_to_layers = false;
|
||||
|
||||
if (num_surfaces > 1) {
|
||||
const unsigned first_depth =
|
||||
(first->texture->target == PIPE_TEXTURE_3D) ?
|
||||
first->texture->depth0 :
|
||||
first->u.tex.last_layer - first->u.tex.first_layer + 1;
|
||||
bool has_3d_target = (first->texture->target == PIPE_TEXTURE_3D);
|
||||
unsigned i;
|
||||
|
||||
for (i = 1; i < num_surfaces; i++) {
|
||||
const struct pipe_surface *surf =
|
||||
(i < state->nr_cbufs) ? state->cbufs[i] : state->zsbuf;
|
||||
const unsigned depth =
|
||||
(surf->texture->target == PIPE_TEXTURE_3D) ?
|
||||
surf->texture->depth0 :
|
||||
surf->u.tex.last_layer - surf->u.tex.first_layer + 1;
|
||||
|
||||
has_3d_target |= (surf->texture->target == PIPE_TEXTURE_3D);
|
||||
|
||||
/*
|
||||
* From the Sandy Bridge PRM, volume 4 part 1, page 79:
|
||||
*
|
||||
* "The LOD of a render target must be the same as the LOD of the
|
||||
* other render target(s) and of the depth buffer (defined in
|
||||
* 3DSTATE_DEPTH_BUFFER)."
|
||||
*
|
||||
* From the Sandy Bridge PRM, volume 4 part 1, page 81:
|
||||
*
|
||||
* "The Depth of a render target must be the same as the Depth of
|
||||
* the other render target(s) and of the depth buffer (defined
|
||||
* in 3DSTATE_DEPTH_BUFFER)."
|
||||
*/
|
||||
if (surf->u.tex.level != first->u.tex.level ||
|
||||
depth != first_depth) {
|
||||
fb->offset_to_layers = true;
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* From the Sandy Bridge PRM, volume 4 part 1, page 77:
|
||||
*
|
||||
* "The Height of a render target must be the same as the Height
|
||||
* of the other render targets and the depth buffer (defined in
|
||||
* 3DSTATE_DEPTH_BUFFER), unless Surface Type is SURFTYPE_1D or
|
||||
* SURFTYPE_2D with Depth = 0 (non-array) and LOD = 0 (non-mip
|
||||
* mapped)."
|
||||
*
|
||||
* From the Sandy Bridge PRM, volume 4 part 1, page 78:
|
||||
*
|
||||
* "The Width of a render target must be the same as the Width of
|
||||
* the other render target(s) and the depth buffer (defined in
|
||||
* 3DSTATE_DEPTH_BUFFER), unless Surface Type is SURFTYPE_1D or
|
||||
* SURFTYPE_2D with Depth = 0 (non-array) and LOD = 0 (non-mip
|
||||
* mapped)."
|
||||
*/
|
||||
if (surf->texture->width0 != first->texture->width0 ||
|
||||
surf->texture->height0 != first->texture->height0) {
|
||||
if (has_3d_target || first->u.tex.level || first_depth > 1) {
|
||||
fb->offset_to_layers = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
ilo_gpe_gen6_estimate_command_size(const struct ilo_dev_info *dev,
|
||||
enum ilo_gpe_gen6_command cmd,
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
* Chia-I Wu <olv@lunarg.com>
|
||||
*/
|
||||
|
||||
#include "util/u_framebuffer.h"
|
||||
#include "util/u_helpers.h"
|
||||
#include "util/u_upload_mgr.h"
|
||||
|
||||
|
@ -645,17 +644,7 @@ ilo_set_framebuffer_state(struct pipe_context *pipe,
|
|||
{
|
||||
struct ilo_context *ilo = ilo_context(pipe);
|
||||
|
||||
util_copy_framebuffer_state(&ilo->fb.state, state);
|
||||
|
||||
if (state->nr_cbufs)
|
||||
ilo->fb.num_samples = state->cbufs[0]->texture->nr_samples;
|
||||
else if (state->zsbuf)
|
||||
ilo->fb.num_samples = state->zsbuf->texture->nr_samples;
|
||||
else
|
||||
ilo->fb.num_samples = 1;
|
||||
|
||||
if (!ilo->fb.num_samples)
|
||||
ilo->fb.num_samples = 1;
|
||||
ilo_gpe_init_fb(ilo->dev, state, &ilo->fb);
|
||||
|
||||
ilo->dirty |= ILO_DIRTY_FB;
|
||||
}
|
||||
|
@ -943,7 +932,7 @@ ilo_create_sampler_view(struct pipe_context *pipe,
|
|||
templ->u.tex.last_level - templ->u.tex.first_level + 1,
|
||||
templ->u.tex.first_layer,
|
||||
templ->u.tex.last_layer - templ->u.tex.first_layer + 1,
|
||||
false, true, &view->surface);
|
||||
false, false, &view->surface);
|
||||
}
|
||||
|
||||
return &view->base;
|
||||
|
@ -991,7 +980,7 @@ ilo_create_surface(struct pipe_context *pipe,
|
|||
templ->format, templ->u.tex.level, 1,
|
||||
templ->u.tex.first_layer,
|
||||
templ->u.tex.last_layer - templ->u.tex.first_layer + 1,
|
||||
true, true, &surf->u.rt);
|
||||
true, false, &surf->u.rt);
|
||||
}
|
||||
else {
|
||||
assert(res->target != PIPE_BUFFER);
|
||||
|
@ -1000,7 +989,7 @@ ilo_create_surface(struct pipe_context *pipe,
|
|||
templ->format, templ->u.tex.level,
|
||||
templ->u.tex.first_layer,
|
||||
templ->u.tex.last_layer - templ->u.tex.first_layer + 1,
|
||||
true, &surf->u.zs);
|
||||
false, &surf->u.zs);
|
||||
}
|
||||
|
||||
return &surf->base;
|
||||
|
|
Loading…
Reference in New Issue