@@ -1753,3 +1753,149 @@ fn memory_decorations_require_storage_address_space() {
17531753 }
17541754 ) ) ;
17551755}
1756+
1757+ /// Naga validation should permit multiple entry points to have the same name,
1758+ /// as long as they are for distinct stages.
1759+ ///
1760+ /// WGSL does not permit conflicting names; this is a case where Naga IR is
1761+ /// looser than WGSL.
1762+ #[ test]
1763+ fn entry_points_distinguished_by_stage ( ) {
1764+ let mut test_spans = TestSpanGenerator :: default ( ) ;
1765+ let mut module = Module :: default ( ) ;
1766+
1767+ let ty_vec4f = module. types . insert (
1768+ ir:: Type {
1769+ name : Some ( "vec4f" . to_string ( ) ) ,
1770+ inner : ir:: TypeInner :: Vector {
1771+ size : ir:: VectorSize :: Quad ,
1772+ scalar : ir:: Scalar :: F32 ,
1773+ } ,
1774+ } ,
1775+ test_spans. next ( ) ,
1776+ ) ;
1777+
1778+ let vertex_function = ir:: Function {
1779+ name : Some ( "non_unique_name" . into ( ) ) ,
1780+ result : Some ( ir:: FunctionResult {
1781+ ty : ty_vec4f,
1782+ binding : Some ( ir:: Binding :: BuiltIn ( ir:: BuiltIn :: Position {
1783+ invariant : false ,
1784+ } ) ) ,
1785+ } ) ,
1786+ ..ir:: Function :: default ( )
1787+ } ;
1788+ module. entry_points . push ( ir:: EntryPoint {
1789+ name : "non_unique_name" . into ( ) ,
1790+ stage : ir:: ShaderStage :: Vertex ,
1791+ early_depth_test : None ,
1792+ workgroup_size : [ 0 , 0 , 0 ] ,
1793+ workgroup_size_overrides : None ,
1794+ function : vertex_function,
1795+ mesh_info : None ,
1796+ task_payload : None ,
1797+ incoming_ray_payload : None ,
1798+ } ) ;
1799+
1800+ module. entry_points . push ( ir:: EntryPoint {
1801+ name : "non_unique_name" . into ( ) ,
1802+ stage : ir:: ShaderStage :: Compute ,
1803+ early_depth_test : None ,
1804+ workgroup_size : [ 1 , 1 , 1 ] ,
1805+ workgroup_size_overrides : None ,
1806+ function : ir:: Function :: default ( ) ,
1807+ mesh_info : None ,
1808+ task_payload : None ,
1809+ incoming_ray_payload : None ,
1810+ } ) ;
1811+
1812+ valid:: Validator :: new (
1813+ valid:: ValidationFlags :: default ( ) ,
1814+ valid:: Capabilities :: default ( ) ,
1815+ )
1816+ . validate ( & module)
1817+ . expect ( "module should be valid" ) ;
1818+ }
1819+
1820+ /// Naga validation should not allow a `Module` to have multiple entry points
1821+ /// with the same name and the same stage.
1822+ #[ test]
1823+ fn entry_points_share_name ( ) {
1824+ let mut module = Module :: default ( ) ;
1825+
1826+ module. entry_points . push ( ir:: EntryPoint {
1827+ name : "non_unique_name" . into ( ) ,
1828+ stage : ir:: ShaderStage :: Compute ,
1829+ early_depth_test : None ,
1830+ workgroup_size : [ 1 , 1 , 1 ] ,
1831+ workgroup_size_overrides : None ,
1832+ function : ir:: Function :: default ( ) ,
1833+ mesh_info : None ,
1834+ task_payload : None ,
1835+ incoming_ray_payload : None ,
1836+ } ) ;
1837+
1838+ module. entry_points . push ( ir:: EntryPoint {
1839+ name : "non_unique_name" . into ( ) ,
1840+ stage : ir:: ShaderStage :: Compute ,
1841+ early_depth_test : None ,
1842+ workgroup_size : [ 1 , 1 , 1 ] ,
1843+ workgroup_size_overrides : None ,
1844+ function : ir:: Function :: default ( ) ,
1845+ mesh_info : None ,
1846+ task_payload : None ,
1847+ incoming_ray_payload : None ,
1848+ } ) ;
1849+
1850+ let err = valid:: Validator :: new (
1851+ valid:: ValidationFlags :: default ( ) ,
1852+ valid:: Capabilities :: default ( ) ,
1853+ )
1854+ . validate ( & module)
1855+ . expect_err ( "module should be invalid" ) ;
1856+
1857+ assert ! ( matches!(
1858+ err. into_inner( ) ,
1859+ valid:: ValidationError :: EntryPoint {
1860+ source: valid:: EntryPointError :: Conflict ,
1861+ ..
1862+ }
1863+ ) ) ;
1864+ }
1865+
1866+ /// Naga validation should permit a `Module` to have multiple non-entry-point
1867+ /// functions with the same name.
1868+ ///
1869+ /// WGSL does not allow this, but Naga IR does: it always refers to functions by
1870+ /// handle, so the names aren't actually needed to interpret the module's
1871+ /// contents.
1872+ #[ test]
1873+ fn functions_share_name ( ) {
1874+ let mut test_spans = TestSpanGenerator :: default ( ) ;
1875+ let mut module = Module :: default ( ) ;
1876+
1877+ module. functions . append (
1878+ ir:: Function {
1879+ name : Some ( "non_unique_name" . into ( ) ) ,
1880+ result : None ,
1881+ ..ir:: Function :: default ( )
1882+ } ,
1883+ test_spans. next ( ) ,
1884+ ) ;
1885+
1886+ module. functions . append (
1887+ ir:: Function {
1888+ name : Some ( "non_unique_name" . into ( ) ) ,
1889+ result : None ,
1890+ ..ir:: Function :: default ( )
1891+ } ,
1892+ test_spans. next ( ) ,
1893+ ) ;
1894+
1895+ valid:: Validator :: new (
1896+ valid:: ValidationFlags :: default ( ) ,
1897+ valid:: Capabilities :: default ( ) ,
1898+ )
1899+ . validate ( & module)
1900+ . expect ( "module should be valid" ) ;
1901+ }
0 commit comments