Module: Mesa
Branch: main
Commit: 7b6103ccc85908fd4ffffd542d33afb255b5eecf
URL:    
http://cgit.freedesktop.org/mesa/mesa/commit/?id=7b6103ccc85908fd4ffffd542d33afb255b5eecf

Author: Faith Ekstrand <faith.ekstr...@collabora.com>
Date:   Thu Nov 23 21:42:57 2023 -0600

nak: Add a builder helper for OpPrmt

The builder also has some extra smarts in it for avoiding the PRMT when
the operation happens to exactly select one of the two sources.

Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/26348>

---

 src/nouveau/compiler/nak_builder.rs  | 26 ++++++++++++++++++++++++++
 src/nouveau/compiler/nak_from_nir.rs |  7 +------
 2 files changed, 27 insertions(+), 6 deletions(-)

diff --git a/src/nouveau/compiler/nak_builder.rs 
b/src/nouveau/compiler/nak_builder.rs
index 31cb220b6c8..f8090243acd 100644
--- a/src/nouveau/compiler/nak_builder.rs
+++ b/src/nouveau/compiler/nak_builder.rs
@@ -49,6 +49,26 @@ pub trait Builder {
         }
     }
 
+    fn prmt_to(&mut self, dst: Dst, x: Src, y: Src, sel: [u8;4]) {
+        if sel == [0, 1, 2, 3] {
+            self.copy_to(dst, x);
+        } else if sel == [4, 5, 6, 7] {
+            self.copy_to(dst, y);
+        } else {
+            let mut sel_u32 = 0;
+            for i in 0..4 {
+                assert!(sel[i] < 16);
+                sel_u32 |= u32::from(sel[i]) << (i * 4);
+            }
+
+            self.push_op(OpPrmt {
+                dst: dst,
+                srcs: [x, y],
+                selection: sel_u32.into(),
+            });
+        }
+    }
+
     fn copy_to(&mut self, dst: Dst, src: Src) {
         self.push_op(OpCopy { dst: dst, src: src });
     }
@@ -206,6 +226,12 @@ pub trait SSABuilder: Builder {
         dst
     }
 
+    fn prmt(&mut self, x: Src, y: Src, sel: [u8;4]) -> SSARef {
+        let dst = self.alloc_ssa(RegFile::GPR, 1);
+        self.prmt_to(dst.into(), x, y, sel);
+        dst
+    }
+
     fn sel(&mut self, cond: Src, x: Src, y: Src) -> SSARef {
         assert!(cond.src_ref.is_predicate());
         assert!(x.is_predicate() == y.is_predicate());
diff --git a/src/nouveau/compiler/nak_from_nir.rs 
b/src/nouveau/compiler/nak_from_nir.rs
index 7e7653dad56..40e87c63dcf 100644
--- a/src/nouveau/compiler/nak_from_nir.rs
+++ b/src/nouveau/compiler/nak_from_nir.rs
@@ -811,12 +811,7 @@ impl<'a> ShaderFromNir<'a> {
                     high: false,
                 });
 
-                b.push_op(OpPrmt {
-                    dst: dst.into(),
-                    srcs: [low.into(), high.into()],
-                    selection: 0x5410.into(),
-                });
-                dst
+                b.prmt(low.into(), high.into(), [0, 1, 4, 5])
             }
             nir_op_u2f32 => {
                 assert!(alu.def.bit_size() == 32);

Reply via email to