intel/fs: Perform 64-bit SHUFFLE lowering in the lower_regioning pass.
Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/14273>
This commit is contained in:
committed by
Marge Bot
parent
d2d72fccf1
commit
9449b71bdd
@@ -606,7 +606,8 @@ fs_generator::generate_shuffle(fs_inst *inst,
|
||||
/* Ivy bridge has some strange behavior that makes this a real pain to
|
||||
* implement for 64-bit values so we just don't bother.
|
||||
*/
|
||||
assert(devinfo->verx10 >= 75 || type_sz(src.type) <= 4);
|
||||
assert((devinfo->verx10 >= 75 && devinfo->has_64bit_float) ||
|
||||
type_sz(src.type) <= 4);
|
||||
|
||||
/* Because we're using the address register, we're limited to 8-wide
|
||||
* execution on gfx7. On gfx8, we're limited to 16-wide by the address
|
||||
@@ -632,15 +633,7 @@ fs_generator::generate_shuffle(fs_inst *inst,
|
||||
const unsigned i = idx.file == BRW_IMMEDIATE_VALUE ? idx.ud : 0;
|
||||
struct brw_reg group_src = stride(suboffset(src, i), 0, 1, 0);
|
||||
struct brw_reg group_dst = suboffset(dst, group << (dst.hstride - 1));
|
||||
if (type_sz(src.type) > 4 && !devinfo->has_64bit_float) {
|
||||
brw_MOV(p, subscript(group_dst, BRW_REGISTER_TYPE_UD, 0),
|
||||
subscript(group_src, BRW_REGISTER_TYPE_UD, 0));
|
||||
brw_set_default_swsb(p, tgl_swsb_null());
|
||||
brw_MOV(p, subscript(group_dst, BRW_REGISTER_TYPE_UD, 1),
|
||||
subscript(group_src, BRW_REGISTER_TYPE_UD, 1));
|
||||
} else {
|
||||
brw_MOV(p, group_dst, group_src);
|
||||
}
|
||||
brw_MOV(p, group_dst, group_src);
|
||||
} else {
|
||||
/* We use VxH indirect addressing, clobbering a0.0 through a0.7. */
|
||||
struct brw_reg addr = vec8(brw_address_reg(0));
|
||||
@@ -712,40 +705,8 @@ fs_generator::generate_shuffle(fs_inst *inst,
|
||||
|
||||
/* Add on the register start offset */
|
||||
brw_ADD(p, addr, addr, brw_imm_uw(src_start_offset));
|
||||
|
||||
if (type_sz(src.type) > 4 &&
|
||||
((devinfo->verx10 == 70) ||
|
||||
devinfo->platform == INTEL_PLATFORM_CHV || intel_device_info_is_9lp(devinfo) ||
|
||||
!devinfo->has_64bit_float)) {
|
||||
/* IVB has an issue (which we found empirically) where it reads
|
||||
* two address register components per channel for indirectly
|
||||
* addressed 64-bit sources.
|
||||
*
|
||||
* From the Cherryview PRM Vol 7. "Register Region Restrictions":
|
||||
*
|
||||
* "When source or destination datatype is 64b or operation is
|
||||
* integer DWord multiply, indirect addressing must not be
|
||||
* used."
|
||||
*
|
||||
* To work around both of these, we do two integer MOVs insead of
|
||||
* one 64-bit MOV. Because no double value should ever cross a
|
||||
* register boundary, it's safe to use the immediate offset in the
|
||||
* indirect here to handle adding 4 bytes to the offset and avoid
|
||||
* the extra ADD to the register file.
|
||||
*/
|
||||
struct brw_reg gdst = suboffset(dst, group);
|
||||
struct brw_reg dst_d = retype(spread(gdst, 2),
|
||||
BRW_REGISTER_TYPE_D);
|
||||
assert(dst.hstride == 1);
|
||||
brw_MOV(p, dst_d,
|
||||
retype(brw_VxH_indirect(0, 0), BRW_REGISTER_TYPE_D));
|
||||
brw_set_default_swsb(p, tgl_swsb_null());
|
||||
brw_MOV(p, byte_offset(dst_d, 4),
|
||||
retype(brw_VxH_indirect(0, 4), BRW_REGISTER_TYPE_D));
|
||||
} else {
|
||||
brw_MOV(p, suboffset(dst, group << (dst.hstride - 1)),
|
||||
retype(brw_VxH_indirect(0, 0), src.type));
|
||||
}
|
||||
brw_MOV(p, suboffset(dst, group << (dst.hstride - 1)),
|
||||
retype(brw_VxH_indirect(0, 0), src.type));
|
||||
}
|
||||
|
||||
brw_set_default_swsb(p, tgl_swsb_null());
|
||||
|
||||
Reference in New Issue
Block a user