|
| 1 | +// build-pass |
| 2 | +// compile-flags: -C llvm-args=--disassemble |
| 3 | +// normalize-stderr-test "OpSource .*\n" -> "" |
| 4 | +// normalize-stderr-test "OpLine .*\n" -> "" |
| 5 | +// normalize-stderr-test "%\d+ = OpString .*\n" -> "" |
| 6 | +// normalize-stderr-test "; .*\n" -> "" |
| 7 | +// normalize-stderr-test "OpCapability VulkanMemoryModel\n" -> "" |
| 8 | +// normalize-stderr-test "OpMemoryModel Logical Vulkan" -> "OpMemoryModel Logical Simple" |
| 9 | +// ignore-spv1.0 |
| 10 | +// ignore-spv1.1 |
| 11 | +// ignore-spv1.2 |
| 12 | +// ignore-spv1.3 |
| 13 | +// ignore-vulkan1.0 |
| 14 | +// ignore-vulkan1.1 |
| 15 | + |
| 16 | +use core::arch::asm; |
| 17 | +use spirv_std::glam::*; |
| 18 | +use spirv_std::spirv; |
| 19 | + |
| 20 | +#[inline] |
| 21 | +pub fn main(frag_coord: Vec4, viewport_size: &Vec2, output: &mut Vec4) { |
| 22 | + *output = Vec4::from((frag_coord.xy() / *viewport_size, 0., 1.)); |
| 23 | +} |
| 24 | + |
| 25 | +pub fn entry() { |
| 26 | + unsafe { |
| 27 | + let mut frag_coord = Vec4::default(); |
| 28 | + asm! { |
| 29 | + "%frag_coord = OpVariable typeof{frag_coord} Input", |
| 30 | + "OpDecorate %frag_coord BuiltIn FragCoord", |
| 31 | + "OpName %frag_coord \"frag_coord\"", |
| 32 | + "%tmp = OpLoad typeof*{frag_coord} %frag_coord", |
| 33 | + "OpStore {frag_coord} %tmp", |
| 34 | + frag_coord = in(reg) &mut frag_coord, |
| 35 | + }; |
| 36 | + |
| 37 | + #[derive(Copy, Clone, Default)] |
| 38 | + struct ViewportBuffer(Vec2); |
| 39 | + let mut viewport_size = &ViewportBuffer::default(); |
| 40 | + asm! { |
| 41 | + "OpDecorate typeof*{viewport_size} Block", |
| 42 | + "%viewport_size = OpVariable typeof{viewport_size} Input", |
| 43 | + "OpDecorate %viewport_size DescriptorSet 0", |
| 44 | + "OpDecorate %viewport_size Binding 0", |
| 45 | + "OpDecorate %viewport_size NonWritable", |
| 46 | + "OpName %viewport_size \"viewport_size\"", |
| 47 | + "%tmp = OpLoad typeof*{viewport_size} %viewport_size", |
| 48 | + "OpStore {viewport_size} %tmp", |
| 49 | + viewport_size = in(reg) &mut viewport_size, |
| 50 | + }; |
| 51 | + |
| 52 | + let mut output = Vec4::default(); |
| 53 | + main(frag_coord, &viewport_size.0, &mut output); |
| 54 | + asm! { |
| 55 | + "%output = OpVariable typeof{output} Output", |
| 56 | + "OpName %output \"output\"", |
| 57 | + "OpDecorate %output Location 0", |
| 58 | + "%tmp = OpLoad _ {output}", |
| 59 | + "OpStore %output %tmp", |
| 60 | + output = in(reg) &output, |
| 61 | + }; |
| 62 | + } |
| 63 | +} |
| 64 | + |
| 65 | +/// we don't support `global_asm!` yet |
| 66 | +pub fn non_global_asm() { |
| 67 | + unsafe { |
| 68 | + asm! { |
| 69 | + "OpEntryPoint Fragment {entry} \"main\"", |
| 70 | + "OpExecutionMode {entry} OriginUpperLeft", |
| 71 | + entry = in(reg) entry, |
| 72 | + } |
| 73 | + } |
| 74 | +} |
0 commit comments