mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-02-05 06:10:28 +01:00
intel/elk: Fix optimize_extract_to_float for i2f of unsigned extract
Fixes fs-uint-to-float-of-extract-int8.shader_test and fs-uint-to-float-of-extract-int16.shader_test added by piglit!883. v2: Expand the comment explaining the potential problem. Suggested by Caio. Fixes:e6022281f2("intel/elk: Rename files to use elk prefix") Reviewed-by: Caio Oliveira <caio.oliveira@intel.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/27891> (cherry picked from commit0fa17962d6)
This commit is contained in:
parent
55ad51ff40
commit
e0899ef81a
2 changed files with 39 additions and 6 deletions
|
|
@ -64,7 +64,7 @@
|
|||
"description": "intel/elk: Fix optimize_extract_to_float for i2f of unsigned extract",
|
||||
"nominated": true,
|
||||
"nomination_type": 1,
|
||||
"resolution": 0,
|
||||
"resolution": 1,
|
||||
"main_sha": null,
|
||||
"because_sha": "e6022281f273287499e9012f9a7c3dd87a733e5b",
|
||||
"notes": null
|
||||
|
|
|
|||
|
|
@ -479,6 +479,9 @@ optimize_extract_to_float(nir_to_elk_state &ntb, nir_alu_instr *instr,
|
|||
const intel_device_info *devinfo = ntb.devinfo;
|
||||
const fs_builder &bld = ntb.bld;
|
||||
|
||||
/* No fast path for f16 or f64. */
|
||||
assert(instr->op == nir_op_i2f32 || instr->op == nir_op_u2f32);
|
||||
|
||||
if (!instr->src[0].src.ssa->parent_instr)
|
||||
return false;
|
||||
|
||||
|
|
@ -488,16 +491,46 @@ optimize_extract_to_float(nir_to_elk_state &ntb, nir_alu_instr *instr,
|
|||
nir_alu_instr *src0 =
|
||||
nir_instr_as_alu(instr->src[0].src.ssa->parent_instr);
|
||||
|
||||
if (src0->op != nir_op_extract_u8 && src0->op != nir_op_extract_u16 &&
|
||||
src0->op != nir_op_extract_i8 && src0->op != nir_op_extract_i16)
|
||||
unsigned bytes;
|
||||
bool is_signed;
|
||||
|
||||
switch (src0->op) {
|
||||
case nir_op_extract_u8:
|
||||
case nir_op_extract_u16:
|
||||
bytes = src0->op == nir_op_extract_u8 ? 1 : 2;
|
||||
|
||||
/* i2f(extract_u8(a, b)) and u2f(extract_u8(a, b)) produce the same
|
||||
* result. Ditto for extract_u16.
|
||||
*/
|
||||
is_signed = false;
|
||||
break;
|
||||
|
||||
case nir_op_extract_i8:
|
||||
case nir_op_extract_i16:
|
||||
bytes = src0->op == nir_op_extract_i8 ? 1 : 2;
|
||||
|
||||
/* The fast path can't handle u2f(extract_i8(a, b)) because the implicit
|
||||
* sign extension of the extract_i8 is lost. For example,
|
||||
* u2f(extract_i8(0x0000ff00, 1)) should produce 4294967295.0, but a
|
||||
* fast path could either give 255.0 (by implementing the fast path as
|
||||
* u2f(extract_u8(x))) or -1.0 (by implementing the fast path as
|
||||
* i2f(extract_i8(x))). At one point in time, we incorrectly implemented
|
||||
* the former.
|
||||
*/
|
||||
if (instr->op != nir_op_i2f32)
|
||||
return false;
|
||||
|
||||
is_signed = true;
|
||||
break;
|
||||
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
|
||||
unsigned element = nir_src_as_uint(src0->src[1].src);
|
||||
|
||||
/* Element type to extract.*/
|
||||
const elk_reg_type type = elk_int_type(
|
||||
src0->op == nir_op_extract_u16 || src0->op == nir_op_extract_i16 ? 2 : 1,
|
||||
src0->op == nir_op_extract_i16 || src0->op == nir_op_extract_i8);
|
||||
const elk_reg_type type = elk_int_type(bytes, is_signed);
|
||||
|
||||
elk_fs_reg op0 = get_nir_src(ntb, src0->src[0].src);
|
||||
op0.type = elk_type_for_nir_type(devinfo,
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue