mirror of
https://github.com/gfx-rs/wgpu.git
synced 2026-04-22 03:02:01 -04:00
[glsl-out] Reworked the backend
The backend now works in a similar way to the msl backend Should require less loops, allocations and backtracking Overall just better to work with it Added a build script which reads a file with the glsl keywords and generates a slice to be used in the Namer Added a way to build a call graph
This commit is contained in:
committed by
Dzmitry Malyshau
parent
23b1e4dd76
commit
dd5021234d
@@ -8,6 +8,7 @@ homepage = "https://github.com/gfx-rs/naga"
|
||||
repository = "https://github.com/gfx-rs/naga"
|
||||
keywords = ["shader", "SPIR-V"]
|
||||
license = "MIT OR Apache-2.0"
|
||||
build = "build.rs"
|
||||
|
||||
[dependencies]
|
||||
bitflags = "1"
|
||||
@@ -24,7 +25,7 @@ petgraph = { version ="0.5", optional = true }
|
||||
default = []
|
||||
glsl-in = ["pomelo"]
|
||||
glsl-validate = []
|
||||
glsl-out = []
|
||||
glsl-out = ["petgraph"]
|
||||
msl-out = []
|
||||
serialize = ["serde"]
|
||||
deserialize = ["serde"]
|
||||
|
||||
26
build.rs
Normal file
26
build.rs
Normal file
@@ -0,0 +1,26 @@
|
||||
use std::{
|
||||
env,
|
||||
fs::{read_to_string, OpenOptions},
|
||||
io::{Result, Write},
|
||||
};
|
||||
|
||||
fn main() -> Result<()> {
|
||||
println!("cargo:rerun-if-changed=glsl-keywords.txt");
|
||||
|
||||
let keywords = read_to_string("glsl-keywords.txt")?.replace('\n', " ");
|
||||
let mut out = OpenOptions::new()
|
||||
.write(true)
|
||||
.truncate(true)
|
||||
.create(true)
|
||||
.open(format!("{}/glsl_keywords.rs", env::var("OUT_DIR").unwrap()))?;
|
||||
|
||||
writeln!(&mut out, "const RESERVED_KEYWORDS: &[&str] = &[")?;
|
||||
|
||||
for keyword in keywords.split(' ') {
|
||||
writeln!(&mut out, "\"{}\",", keyword)?;
|
||||
}
|
||||
|
||||
writeln!(&mut out, "];")?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
@@ -216,14 +216,17 @@ fn main() {
|
||||
),
|
||||
};
|
||||
|
||||
let mut file = fs::OpenOptions::new()
|
||||
let file = fs::OpenOptions::new()
|
||||
.write(true)
|
||||
.truncate(true)
|
||||
.create(true)
|
||||
.open(&args[2])
|
||||
.unwrap();
|
||||
|
||||
glsl::write(&module, &mut file, options)
|
||||
let mut writer = glsl::Writer::new(file, &module, &options).unwrap();
|
||||
|
||||
writer
|
||||
.write()
|
||||
.map_err(|e| {
|
||||
fs::remove_file(&args[2]).unwrap();
|
||||
e
|
||||
|
||||
20
glsl-keywords.txt
Normal file
20
glsl-keywords.txt
Normal file
@@ -0,0 +1,20 @@
|
||||
attribute const uniform varying buffer shared coherent volatile restrict readonly writeonly
|
||||
atomic_uint layout centroid flat smooth noperspective patch sample break continue do for while
|
||||
switch case default if else subroutine in out inout float double int void bool true false invariant
|
||||
precise discard return mat2 mat3 mat4 dmat2 dmat3 dmat4 mat2x2 mat2x3 mat2x4 dmat2x2 dmat2x3 dmat2x4
|
||||
mat3x2 mat3x3 mat3x4 dmat3x2 dmat3x3 dmat3x4 mat4x2 mat4x3 mat4x4 dmat4x2 dmat4x3 dmat4x4 vec2 vec3
|
||||
vec4 ivec2 ivec3 ivec4 bvec2 bvec3 bvec4 dvec2 dvec3 dvec4 uint uvec2 uvec3 uvec4 lowp mediump highp
|
||||
precision sampler1D sampler2D sampler3D samplerCube sampler1DShadow sampler2DShadow
|
||||
samplerCubeShadow sampler1DArray sampler2DArray sampler1DArrayShadow sampler2DArrayShadow
|
||||
isampler1D isampler2D isampler3D isamplerCube isampler1DArray isampler2DArray usampler1D usampler2D
|
||||
usampler3D usamplerCube usampler1DArray usampler2DArray sampler2DRect sampler2DRectShadow isampler2D
|
||||
Rect usampler2DRect samplerBuffer isamplerBuffer usamplerBuffer sampler2DMS isampler2DMS
|
||||
usampler2DMS sampler2DMSArray isampler2DMSArray usampler2DMSArray samplerCubeArray
|
||||
samplerCubeArrayShadow isamplerCubeArray usamplerCubeArray image1D iimage1D uimage1D image2D
|
||||
iimage2D uimage2D image3D iimage3D uimage3D image2DRect iimage2DRect uimage2DRect imageCube
|
||||
iimageCube uimageCube imageBuffer iimageBuffer uimageBuffer image1DArray iimage1DArray uimage1DArray
|
||||
image2DArray iimage2DArray uimage2DArray imageCubeArray iimageCubeArray uimageCubeArray image2DMS
|
||||
iimage2DMS uimage2DMS image2DMSArray iimage2DMSArray uimage2DMSArraystruct common partition active
|
||||
asm class union enum typedef template this resource goto inline noinline public static extern
|
||||
external interface long short half fixed unsigned superp input output hvec2 hvec3 hvec4 fvec2 fvec3
|
||||
fvec4 sampler3DRect filter sizeof cast namespace using main
|
||||
2641
src/back/glsl.rs
2641
src/back/glsl.rs
File diff suppressed because it is too large
Load Diff
74
src/proc/call_graph.rs
Normal file
74
src/proc/call_graph.rs
Normal file
@@ -0,0 +1,74 @@
|
||||
use crate::{
|
||||
arena::{Arena, Handle},
|
||||
proc::{Interface, Visitor},
|
||||
Function,
|
||||
};
|
||||
use petgraph::{
|
||||
graph::{DefaultIx, NodeIndex},
|
||||
Graph,
|
||||
};
|
||||
|
||||
pub type CallGraph = Graph<Handle<Function>, ()>;
|
||||
|
||||
pub struct CallGraphBuilder<'a> {
|
||||
pub functions: &'a Arena<Function>,
|
||||
}
|
||||
|
||||
impl<'a> CallGraphBuilder<'a> {
|
||||
pub fn process(&self, func: &Function) -> CallGraph {
|
||||
let mut graph = Graph::new();
|
||||
let mut children = Vec::new();
|
||||
|
||||
let visitor = CallGraphVisitor {
|
||||
children: &mut children,
|
||||
};
|
||||
|
||||
let mut interface = Interface {
|
||||
expressions: &func.expressions,
|
||||
local_variables: &func.local_variables,
|
||||
visitor,
|
||||
};
|
||||
|
||||
interface.traverse(&func.body);
|
||||
|
||||
for handle in children {
|
||||
let id = graph.add_node(handle);
|
||||
self.collect(handle, id, &mut graph);
|
||||
}
|
||||
|
||||
graph
|
||||
}
|
||||
|
||||
fn collect(&self, handle: Handle<Function>, id: NodeIndex<DefaultIx>, graph: &mut CallGraph) {
|
||||
let mut children = Vec::new();
|
||||
let visitor = CallGraphVisitor {
|
||||
children: &mut children,
|
||||
};
|
||||
let func = &self.functions[handle];
|
||||
|
||||
let mut interface = Interface {
|
||||
expressions: &func.expressions,
|
||||
local_variables: &func.local_variables,
|
||||
visitor,
|
||||
};
|
||||
|
||||
interface.traverse(&func.body);
|
||||
|
||||
for handle in children {
|
||||
let child_id = graph.add_node(handle);
|
||||
graph.add_edge(id, child_id, ());
|
||||
|
||||
self.collect(handle, child_id, graph);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct CallGraphVisitor<'a> {
|
||||
children: &'a mut Vec<Handle<Function>>,
|
||||
}
|
||||
|
||||
impl<'a> Visitor for CallGraphVisitor<'a> {
|
||||
fn visit_fun(&mut self, func: Handle<Function>) {
|
||||
self.children.push(func)
|
||||
}
|
||||
}
|
||||
@@ -1,10 +1,14 @@
|
||||
//! Module processing functionality.
|
||||
|
||||
#[cfg(feature = "petgraph")]
|
||||
mod call_graph;
|
||||
mod interface;
|
||||
mod namer;
|
||||
mod typifier;
|
||||
mod validator;
|
||||
|
||||
#[cfg(feature = "petgraph")]
|
||||
pub use call_graph::{CallGraph, CallGraphBuilder};
|
||||
pub use interface::{Interface, Visitor};
|
||||
pub use namer::{EntryPointIndex, NameKey, Namer};
|
||||
pub use typifier::{check_constant_type, ResolveContext, ResolveError, Typifier};
|
||||
|
||||
Reference in New Issue
Block a user