nak: Plumb tessellation parameters through ShaderStageInfo

Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/30283>
This commit is contained in:
Faith Ekstrand 2024-07-18 23:15:43 -05:00
parent c4c9bfdebd
commit d96fe18547
4 changed files with 77 additions and 39 deletions

View file

@ -353,40 +353,12 @@ pub extern "C" fn nak_compile_shader(
},
}
}
ShaderStageInfo::Tessellation => {
let nir_ts_info = unsafe { &nir.info.__bindgen_anon_1.tess };
ShaderStageInfo::Tessellation(ts_info) => {
nak_shader_info__bindgen_ty_1 {
ts: nak_shader_info__bindgen_ty_1__bindgen_ty_3 {
domain: match nir_ts_info._primitive_mode {
TESS_PRIMITIVE_TRIANGLES => NAK_TS_DOMAIN_TRIANGLE,
TESS_PRIMITIVE_QUADS => NAK_TS_DOMAIN_QUAD,
TESS_PRIMITIVE_ISOLINES => NAK_TS_DOMAIN_ISOLINE,
_ => panic!("Invalid tess_primitive_mode"),
},
spacing: match nir_ts_info.spacing() {
TESS_SPACING_EQUAL => NAK_TS_SPACING_INTEGER,
TESS_SPACING_FRACTIONAL_ODD => {
NAK_TS_SPACING_FRACT_ODD
}
TESS_SPACING_FRACTIONAL_EVEN => {
NAK_TS_SPACING_FRACT_EVEN
}
_ => panic!("Invalid gl_tess_spacing"),
},
prims: if nir_ts_info.point_mode() {
NAK_TS_PRIMS_POINTS
} else if nir_ts_info._primitive_mode
== TESS_PRIMITIVE_ISOLINES
{
NAK_TS_PRIMS_LINES
} else if nir_ts_info.ccw() {
NAK_TS_PRIMS_TRIANGLES_CCW
} else {
NAK_TS_PRIMS_TRIANGLES_CW
},
domain: ts_info.domain as u8,
spacing: ts_info.spacing as u8,
prims: ts_info.primitives as u8,
_pad: Default::default(),
},
}
@ -397,7 +369,7 @@ pub extern "C" fn nak_compile_shader(
},
vtg: match &s.info.stage {
ShaderStageInfo::Geometry(_)
| ShaderStageInfo::Tessellation
| ShaderStageInfo::Tessellation(_)
| ShaderStageInfo::Vertex => {
let writes_layer =
nir.info.outputs_written & (1 << VARYING_SLOT_LAYER) != 0;

View file

@ -69,7 +69,40 @@ fn init_info_from_nir(nir: &nir_shader) -> ShaderInfo {
threads_per_patch: info_tess.tcs_vertices_out,
})
}
MESA_SHADER_TESS_EVAL => ShaderStageInfo::Tessellation,
MESA_SHADER_TESS_EVAL => {
let info_tess = unsafe { &nir.info.__bindgen_anon_1.tess };
ShaderStageInfo::Tessellation(TessellationShaderInfo {
domain: match info_tess._primitive_mode {
TESS_PRIMITIVE_TRIANGLES => {
TessellationDomain::Triangle
}
TESS_PRIMITIVE_QUADS => TessellationDomain::Quad,
TESS_PRIMITIVE_ISOLINES => TessellationDomain::Isoline,
_ => panic!("Invalid tess_primitive_mode"),
},
spacing: match info_tess.spacing() {
TESS_SPACING_EQUAL => TessellationSpacing::Integer,
TESS_SPACING_FRACTIONAL_ODD => {
TessellationSpacing::FractionalOdd
}
TESS_SPACING_FRACTIONAL_EVEN => {
TessellationSpacing::FractionalEven
}
_ => panic!("Invalid gl_tess_spacing"),
},
primitives: if info_tess.point_mode() {
TessellationPrimitives::Points
} else if info_tess._primitive_mode
== TESS_PRIMITIVE_ISOLINES
{
TessellationPrimitives::Lines
} else if info_tess.ccw() {
TessellationPrimitives::TrianglesCCW
} else {
TessellationPrimitives::TrianglesCW
},
})
}
_ => panic!("Unknown shader stage"),
},
io: match nir.info.stage() {
@ -2002,7 +2035,7 @@ impl<'a> ShaderFromNir<'a> {
(range.end / 4).try_into().unwrap(),
);
}
ShaderStageInfo::Tessellation => (),
ShaderStageInfo::Tessellation(_) => (),
_ => panic!("Patch I/O not supported"),
}
} else {
@ -2531,7 +2564,7 @@ impl<'a> ShaderFromNir<'a> {
// weird. It's treated as a per-vertex output which is indexed
// by LANEID.
match &self.info.stage {
ShaderStageInfo::Tessellation => (),
ShaderStageInfo::Tessellation(_) => (),
_ => panic!(
"load_tess_coord is only available in tessellation \
shaders"
@ -3450,7 +3483,7 @@ impl<'a> ShaderFromNir<'a> {
// Tessellation evaluation shaders MUST claim to read gl_TessCoord or
// the hardware will throw an SPH error.
if matches!(self.info.stage, ShaderStageInfo::Tessellation) {
if matches!(self.info.stage, ShaderStageInfo::Tessellation(_)) {
match &mut self.info.io {
ShaderIoInfo::Vtg(io) => {
let tc = NAK_ATTR_TESS_COORD;

View file

@ -5,6 +5,7 @@ extern crate bitview;
extern crate nak_ir_proc;
use bitview::BitMutView;
use nak_bindings::*;
pub use crate::builder::{Builder, InstrBuilder, SSABuilder, SSAInstrBuilder};
use crate::cfg::CFG;
@ -6268,6 +6269,38 @@ pub struct TessellationInitShaderInfo {
pub threads_per_patch: u8,
}
#[repr(u8)]
#[derive(Clone, Copy, Debug)]
pub enum TessellationDomain {
Isoline = NAK_TS_DOMAIN_ISOLINE,
Triangle = NAK_TS_DOMAIN_TRIANGLE,
Quad = NAK_TS_DOMAIN_QUAD,
}
#[repr(u8)]
#[derive(Clone, Copy, Debug)]
pub enum TessellationSpacing {
Integer = NAK_TS_SPACING_INTEGER,
FractionalOdd = NAK_TS_SPACING_FRACT_ODD,
FractionalEven = NAK_TS_SPACING_FRACT_EVEN,
}
#[repr(u8)]
#[derive(Clone, Copy, Debug)]
pub enum TessellationPrimitives {
Points = NAK_TS_PRIMS_POINTS,
Lines = NAK_TS_PRIMS_LINES,
TrianglesCW = NAK_TS_PRIMS_TRIANGLES_CW,
TrianglesCCW = NAK_TS_PRIMS_TRIANGLES_CCW,
}
#[derive(Debug)]
pub struct TessellationShaderInfo {
pub domain: TessellationDomain,
pub spacing: TessellationSpacing,
pub primitives: TessellationPrimitives,
}
#[derive(Debug)]
pub enum ShaderStageInfo {
Compute(ComputeShaderInfo),
@ -6275,7 +6308,7 @@ pub enum ShaderStageInfo {
Fragment,
Geometry(GeometryShaderInfo),
TessellationInit(TessellationInitShaderInfo),
Tessellation,
Tessellation(TessellationShaderInfo),
}
#[derive(Debug, Default)]

View file

@ -37,7 +37,7 @@ impl From<&ShaderStageInfo> for ShaderType {
ShaderStageInfo::TessellationInit(_) => {
ShaderType::TessellationInit
}
ShaderStageInfo::Tessellation => ShaderType::Tessellation,
ShaderStageInfo::Tessellation(_) => ShaderType::Tessellation,
_ => panic!("Invalid ShaderStageInfo {:?}", value),
}
}