summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers
diff options
context:
space:
mode:
authorChia-I Wu <[email protected]>2014-11-10 13:44:45 +0800
committerChia-I Wu <[email protected]>2014-11-10 15:46:31 +0800
commitd388d8576f004cbc6e659ab7e7b0e9af938f7068 (patch)
tree44ee37594b717eaa6fa83b88d5c7353ad71e75de /src/gallium/drivers
parent55d70e0669fd363c434ad781fe66d60095585062 (diff)
ilo: derive fb blending caps at bind time
Derive whether a RT supports blending, logicop, and the like when set_framebuffer_state() is called. This enables us to simplify gen6_BLEND_STATE(). Signed-off-by: Chia-I Wu <[email protected]>
Diffstat (limited to 'src/gallium/drivers')
-rw-r--r--src/gallium/drivers/ilo/ilo_builder_3d_bottom.h91
-rw-r--r--src/gallium/drivers/ilo/ilo_state.h7
-rw-r--r--src/gallium/drivers/ilo/ilo_state_3d_bottom.c81
3 files changed, 101 insertions, 78 deletions
diff --git a/src/gallium/drivers/ilo/ilo_builder_3d_bottom.h b/src/gallium/drivers/ilo/ilo_builder_3d_bottom.h
index 456a494d12b..2397a2c7943 100644
--- a/src/gallium/drivers/ilo/ilo_builder_3d_bottom.h
+++ b/src/gallium/drivers/ilo/ilo_builder_3d_bottom.h
@@ -1224,72 +1224,36 @@ gen6_BLEND_STATE(struct ilo_builder *builder,
ILO_BUILDER_ITEM_BLEND, state_align, state_len, &dw);
for (i = 0; i < num_targets; i++) {
- const unsigned idx = (blend->independent_blend_enable) ? i : 0;
- const struct ilo_blend_cso *cso = &blend->cso[idx];
- const int num_samples = fb->num_samples;
- const struct util_format_description *format_desc =
- (idx < fb->state.nr_cbufs && fb->state.cbufs[idx]) ?
- util_format_description(fb->state.cbufs[idx]->format) : NULL;
- bool rt_is_unorm, rt_is_pure_integer, rt_dst_alpha_forced_one;
-
- rt_is_unorm = true;
- rt_is_pure_integer = false;
- rt_dst_alpha_forced_one = false;
-
- if (format_desc) {
- int ch;
-
- switch (format_desc->format) {
- case PIPE_FORMAT_B8G8R8X8_UNORM:
- /* force alpha to one when the HW format has alpha */
- assert(ilo_translate_render_format(builder->dev,
- PIPE_FORMAT_B8G8R8X8_UNORM) ==
- GEN6_FORMAT_B8G8R8A8_UNORM);
- rt_dst_alpha_forced_one = true;
- break;
- default:
- break;
- }
+ const struct ilo_blend_cso *cso =
+ &blend->cso[(blend->independent_blend_enable) ? i : 0];
- for (ch = 0; ch < 4; ch++) {
- if (format_desc->channel[ch].type == UTIL_FORMAT_TYPE_VOID)
- continue;
+ dw[0] = cso->payload[0];
+ dw[1] = cso->payload[1];
- if (format_desc->channel[ch].pure_integer) {
- rt_is_unorm = false;
- rt_is_pure_integer = true;
- break;
- }
+ if (i < fb->state.nr_cbufs && fb->state.cbufs[i]) {
+ const struct ilo_fb_blend_caps *caps = &fb->blend_caps[i];
- if (!format_desc->channel[ch].normalized ||
- format_desc->channel[ch].type != UTIL_FORMAT_TYPE_UNSIGNED)
- rt_is_unorm = false;
+ if (caps->can_blend) {
+ if (caps->dst_alpha_forced_one)
+ dw[0] |= cso->dw_blend_dst_alpha_forced_one;
+ else
+ dw[0] |= cso->dw_blend;
}
- }
- dw[0] = cso->payload[0];
- dw[1] = cso->payload[1];
-
- if (!rt_is_pure_integer) {
- if (rt_dst_alpha_forced_one)
- dw[0] |= cso->dw_blend_dst_alpha_forced_one;
- else
- dw[0] |= cso->dw_blend;
+ if (caps->can_logicop)
+ dw[1] |= cso->dw_logicop;
+
+ if (caps->can_alpha_test)
+ dw[1] |= dsa->dw_alpha;
+ } else {
+ dw[1] |= GEN6_BLEND_DW1_WRITE_DISABLE_A |
+ GEN6_BLEND_DW1_WRITE_DISABLE_R |
+ GEN6_BLEND_DW1_WRITE_DISABLE_G |
+ GEN6_BLEND_DW1_WRITE_DISABLE_B |
+ dsa->dw_alpha;
}
/*
- * From the Sandy Bridge PRM, volume 2 part 1, page 365:
- *
- * "Logic Ops are only supported on *_UNORM surfaces (excluding
- * _SRGB variants), otherwise Logic Ops must be DISABLED."
- *
- * Since logicop is ignored for non-UNORM color buffers, no special care
- * is needed.
- */
- if (rt_is_unorm)
- dw[1] |= cso->dw_logicop;
-
- /*
* From the Sandy Bridge PRM, volume 2 part 1, page 356:
*
* "When NumSamples = 1, AlphaToCoverage and AlphaToCoverage
@@ -1298,18 +1262,9 @@ gen6_BLEND_STATE(struct ilo_builder *builder,
* There is no such limitation on GEN7, or for AlphaToOne. But GL
* requires that anyway.
*/
- if (num_samples > 1)
+ if (fb->num_samples > 1)
dw[1] |= cso->dw_alpha_mod;
- /*
- * From the Sandy Bridge PRM, volume 2 part 1, page 382:
- *
- * "Alpha Test can only be enabled if Pixel Shader outputs a float
- * alpha value."
- */
- if (!rt_is_pure_integer)
- dw[1] |= dsa->dw_alpha;
-
dw += 2;
}
diff --git a/src/gallium/drivers/ilo/ilo_state.h b/src/gallium/drivers/ilo/ilo_state.h
index 6f544e1f788..afe27847a93 100644
--- a/src/gallium/drivers/ilo/ilo_state.h
+++ b/src/gallium/drivers/ilo/ilo_state.h
@@ -347,6 +347,13 @@ struct ilo_fb_state {
struct ilo_view_surface null_rt;
struct ilo_zs_surface null_zs;
+ struct ilo_fb_blend_caps {
+ bool can_logicop;
+ bool can_blend;
+ bool can_alpha_test;
+ bool dst_alpha_forced_one;
+ } blend_caps[PIPE_MAX_COLOR_BUFS];
+
unsigned num_samples;
};
diff --git a/src/gallium/drivers/ilo/ilo_state_3d_bottom.c b/src/gallium/drivers/ilo/ilo_state_3d_bottom.c
index a390124c2e9..822f8a46f68 100644
--- a/src/gallium/drivers/ilo/ilo_state_3d_bottom.c
+++ b/src/gallium/drivers/ilo/ilo_state_3d_bottom.c
@@ -1540,13 +1540,70 @@ ilo_gpe_set_scissor_null(const struct ilo_dev_info *dev,
}
}
+static void
+fb_set_blend_caps(const struct ilo_dev_info *dev,
+ enum pipe_format format,
+ struct ilo_fb_blend_caps *caps)
+{
+ const struct util_format_description *desc =
+ util_format_description(format);
+ const int ch = util_format_get_first_non_void_channel(format);
+
+ memset(caps, 0, sizeof(*caps));
+
+ if (format == PIPE_FORMAT_NONE || desc->is_mixed)
+ return;
+
+ /*
+ * From the Sandy Bridge PRM, volume 2 part 1, page 365:
+ *
+ * "Logic Ops are only supported on *_UNORM surfaces (excluding _SRGB
+ * variants), otherwise Logic Ops must be DISABLED."
+ */
+ caps->can_logicop = (ch >= 0 && desc->channel[ch].normalized &&
+ desc->channel[ch].type == UTIL_FORMAT_TYPE_UNSIGNED &&
+ desc->colorspace == UTIL_FORMAT_COLORSPACE_RGB);
+
+ /* no blending for pure integer formats */
+ caps->can_blend = !util_format_is_pure_integer(format);
+
+ /*
+ * From the Sandy Bridge PRM, volume 2 part 1, page 382:
+ *
+ * "Alpha Test can only be enabled if Pixel Shader outputs a float
+ * alpha value."
+ */
+ caps->can_alpha_test = !util_format_is_pure_integer(format);
+
+ caps->dst_alpha_forced_one =
+ (ilo_translate_render_format(dev, format) !=
+ ilo_translate_color_format(dev, format));
+
+ /* sanity check */
+ if (caps->dst_alpha_forced_one) {
+ enum pipe_format render_format;
+
+ switch (format) {
+ case PIPE_FORMAT_B8G8R8X8_UNORM:
+ render_format = PIPE_FORMAT_B8G8R8A8_UNORM;
+ break;
+ default:
+ render_format = PIPE_FORMAT_NONE;
+ break;
+ }
+
+ assert(ilo_translate_render_format(dev, format) ==
+ ilo_translate_color_format(dev, render_format));
+ }
+}
+
void
ilo_gpe_set_fb(const struct ilo_dev_info *dev,
const struct pipe_framebuffer_state *state,
struct ilo_fb_state *fb)
{
- const struct pipe_surface *first;
- unsigned first_idx;
+ const struct pipe_surface *first_surf = NULL;
+ int i;
ILO_DEV_ASSERT(dev, 6, 7.5);
@@ -1557,17 +1614,21 @@ ilo_gpe_set_fb(const struct ilo_dev_info *dev,
(state->height) ? state->height : 1,
1, 0, &fb->null_rt);
- first = NULL;
- for (first_idx = 0; first_idx < state->nr_cbufs; first_idx++) {
- if (state->cbufs[first_idx]) {
- first = state->cbufs[first_idx];
- break;
+ for (i = 0; i < state->nr_cbufs; i++) {
+ if (state->cbufs[i]) {
+ fb_set_blend_caps(dev, state->cbufs[i]->format, &fb->blend_caps[i]);
+
+ if (!first_surf)
+ first_surf = state->cbufs[i];
+ } else {
+ fb_set_blend_caps(dev, PIPE_FORMAT_NONE, &fb->blend_caps[i]);
}
}
- if (!first)
- first = state->zsbuf;
- fb->num_samples = (first) ? first->texture->nr_samples : 1;
+ if (!first_surf && state->zsbuf)
+ first_surf = state->zsbuf;
+
+ fb->num_samples = (first_surf) ? first_surf->texture->nr_samples : 1;
if (!fb->num_samples)
fb->num_samples = 1;