use fnv::FnvHashMap as HashMap;
use crate::{
constant::ConstantValue,
entry_point::EntryPoint,
error::Result,
inspect::{FnInspector, Inspector},
parse::{Instr, SpirvBinary},
reflect::{reflect, FunctionInspector, ReflectIntermediate},
var::SpecId,
};
#[derive(Default, Clone)]
pub struct ReflectConfig {
pub(crate) spv: Option<SpirvBinary>,
pub(crate) ref_all_rscs: bool,
pub(crate) combine_img_samplers: bool,
pub(crate) gen_unique_names: bool,
pub(crate) spec_values: HashMap<SpecId, ConstantValue>,
}
impl ReflectConfig {
pub fn new() -> Self {
Default::default()
}
pub fn spv<Spv: Into<SpirvBinary>>(&mut self, x: Spv) -> &mut Self {
self.spv = Some(x.into());
self
}
pub fn ref_all_rscs(&mut self, x: bool) -> &mut Self {
self.ref_all_rscs = x;
self
}
pub fn combine_img_samplers(&mut self, x: bool) -> &mut Self {
self.combine_img_samplers = x;
self
}
pub fn gen_unique_names(&mut self, x: bool) -> &mut Self {
self.gen_unique_names = x;
self
}
pub fn specialize(&mut self, spec_id: SpecId, value: ConstantValue) -> &mut Self {
self.spec_values.insert(spec_id, value);
self
}
pub fn reflect(&mut self) -> Result<Vec<EntryPoint>> {
let spv = self.spv.take().unwrap_or_default();
let mut itm = ReflectIntermediate::new(self)?;
let inspector = FunctionInspector::new();
reflect(&mut itm, &mut spv.instrs()?, inspector)
}
pub fn reflect_inspect<I: Inspector>(&mut self, inspector: &mut I) -> Result<Vec<EntryPoint>> {
let spv = self.spv.take().unwrap_or_default();
let mut itm = ReflectIntermediate::new(self)?;
let mut func_inspector = FunctionInspector::new();
reflect(
&mut itm,
&mut spv.instrs()?,
func_inspector.chain(inspector),
)
}
pub fn reflect_inspect_by<F: FnMut(&mut ReflectIntermediate<'_>, &Instr)>(
&mut self,
inspector: F,
) -> Result<Vec<EntryPoint>> {
let mut inspector = FnInspector::<F>(inspector);
self.reflect_inspect(&mut inspector)
}
}