static void r600_texture_state_cb(struct r600_screen *rscreen, struct r600_resource_texture *rtexture, unsigned cb, unsigned level) { struct radeon_state *rstate; struct r600_resource *rbuffer; unsigned pitch, slice; unsigned color_info; unsigned format, swap, ntype; const struct util_format_description *desc; rstate = &rtexture->cb[cb][level]; radeon_state_init(rstate, rscreen->rw, R600_STATE_CB0 + cb, 0, 0); rbuffer = &rtexture->resource; /* set states (most default value are 0 and struct already * initialized to 0, thus avoid resetting them) */ pitch = (rtexture->pitch[level] / rtexture->bpt) / 8 - 1; slice = (rtexture->pitch[level] / rtexture->bpt) * rtexture->height[level] / 64 - 1; ntype = 0; desc = util_format_description(rbuffer->base.b.format); if (desc->colorspace == UTIL_FORMAT_COLORSPACE_SRGB) ntype = V_0280A0_NUMBER_SRGB; format = r600_translate_colorformat(rtexture->resource.base.b.format); swap = r600_translate_colorswap(rtexture->resource.base.b.format); if (desc->colorspace == UTIL_FORMAT_COLORSPACE_ZS) { rstate->bo[0] = radeon_bo_incref(rscreen->rw, rtexture->uncompressed); rstate->bo[1] = radeon_bo_incref(rscreen->rw, rtexture->uncompressed); rstate->bo[2] = radeon_bo_incref(rscreen->rw, rtexture->uncompressed); rstate->placement[0] = RADEON_GEM_DOMAIN_GTT; rstate->placement[2] = RADEON_GEM_DOMAIN_GTT; rstate->placement[4] = RADEON_GEM_DOMAIN_GTT; rstate->nbo = 3; color_info = 0; } else { rstate->bo[0] = radeon_bo_incref(rscreen->rw, rbuffer->bo); rstate->bo[1] = radeon_bo_incref(rscreen->rw, rbuffer->bo); rstate->bo[2] = radeon_bo_incref(rscreen->rw, rbuffer->bo); rstate->placement[0] = RADEON_GEM_DOMAIN_GTT; rstate->placement[2] = RADEON_GEM_DOMAIN_GTT; rstate->placement[4] = RADEON_GEM_DOMAIN_GTT; rstate->nbo = 3; color_info = S_0280A0_SOURCE_FORMAT(1); } color_info |= S_0280A0_FORMAT(format) | S_0280A0_COMP_SWAP(swap) | S_0280A0_BLEND_CLAMP(1) | S_0280A0_NUMBER_TYPE(ntype); rstate->states[R600_CB0__CB_COLOR0_BASE] = rtexture->offset[level] >> 8; rstate->states[R600_CB0__CB_COLOR0_INFO] = color_info; rstate->states[R600_CB0__CB_COLOR0_SIZE] = S_028060_PITCH_TILE_MAX(pitch) | S_028060_SLICE_TILE_MAX(slice); radeon_state_pm4(rstate); }
static void vi_get_fast_clear_parameters(enum pipe_format surface_format, const union pipe_color_union *color, uint32_t* reset_value, bool* clear_words_needed) { bool values[4] = {}; int i; bool main_value = false; bool extra_value = false; int extra_channel; const struct util_format_description *desc = util_format_description(surface_format); *clear_words_needed = true; *reset_value = 0x20202020U; /* If we want to clear without needing a fast clear eliminate step, we * can set each channel to 0 or 1 (or 0/max for integer formats). We * have two sets of flags, one for the last or first channel(extra) and * one for the other channels(main). */ if (surface_format == PIPE_FORMAT_R11G11B10_FLOAT || surface_format == PIPE_FORMAT_B5G6R5_UNORM || surface_format == PIPE_FORMAT_B5G6R5_SRGB) { extra_channel = -1; } else if (desc->layout == UTIL_FORMAT_LAYOUT_PLAIN) { if(r600_translate_colorswap(surface_format) <= 1) extra_channel = desc->nr_channels - 1; else extra_channel = 0; } else return; for (i = 0; i < 4; ++i) { int index = desc->swizzle[i] - UTIL_FORMAT_SWIZZLE_X; if (desc->swizzle[i] < UTIL_FORMAT_SWIZZLE_X || desc->swizzle[i] > UTIL_FORMAT_SWIZZLE_W) continue; if (util_format_is_pure_sint(surface_format)) { values[i] = color->i[i] != 0; if (color->i[i] != 0 && color->i[i] != INT32_MAX) return; } else if (util_format_is_pure_uint(surface_format)) { values[i] = color->ui[i] != 0U; if (color->ui[i] != 0U && color->ui[i] != UINT32_MAX) return; } else { values[i] = color->f[i] != 0.0F; if (color->f[i] != 0.0F && color->f[i] != 1.0F) return; } if (index == extra_channel) extra_value = values[i]; else main_value = values[i]; } for (int i = 0; i < 4; ++i) if (values[i] != main_value && desc->swizzle[i] - UTIL_FORMAT_SWIZZLE_X != extra_channel && desc->swizzle[i] >= UTIL_FORMAT_SWIZZLE_X && desc->swizzle[i] <= UTIL_FORMAT_SWIZZLE_W) return; *clear_words_needed = false; if (main_value) *reset_value |= 0x80808080U; if (extra_value) *reset_value |= 0x40404040U; }