1 // Copyright © 2023 Collabora, Ltd. 2 // SPDX-License-Identifier: MIT 3 4 use crate::{ 5 api::{GetDebugFlags, DEBUG}, 6 ir::*, 7 }; 8 try_combine_outs(emit: &mut Instr, cut: &Instr) -> bool9fn try_combine_outs(emit: &mut Instr, cut: &Instr) -> bool { 10 let Op::Out(emit) = &mut emit.op else { 11 return false; 12 }; 13 14 let Op::Out(cut) = &cut.op else { 15 return false; 16 }; 17 18 if emit.out_type != OutType::Emit || cut.out_type != OutType::Cut { 19 return false; 20 } 21 22 let Some(handle) = emit.dst.as_ssa() else { 23 return false; 24 }; 25 26 if cut.handle.as_ssa() != Some(handle) { 27 return false; 28 } 29 30 if emit.stream != cut.stream { 31 return false; 32 } 33 34 emit.dst = cut.dst; 35 emit.out_type = OutType::EmitThenCut; 36 37 true 38 } 39 40 impl Shader<'_> { opt_out(&mut self)41 pub fn opt_out(&mut self) { 42 if !matches!(self.info.stage, ShaderStageInfo::Geometry(_)) { 43 return; 44 } 45 46 for f in &mut self.functions { 47 for b in &mut f.blocks { 48 let mut instrs: Vec<Box<Instr>> = Vec::new(); 49 for instr in b.instrs.drain(..) { 50 if let Some(prev) = instrs.last_mut() { 51 if try_combine_outs(prev, &instr) { 52 if DEBUG.annotate() { 53 instrs.push(Instr::new_boxed(OpAnnotate { 54 annotation: "combined by opt_out".into(), 55 })); 56 } 57 continue; 58 } 59 } 60 instrs.push(instr); 61 } 62 b.instrs = instrs; 63 } 64 } 65 } 66 } 67