Flutter Impeller
code_gen_template.h
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include <string_view>
6 
7 namespace impeller {
8 namespace compiler {
9 
10 constexpr std::string_view kReflectionHeaderTemplate =
11  R"~~(// THIS FILE IS GENERATED BY impellerc.
12 // DO NOT EDIT OR CHECK THIS INTO SOURCE CONTROL
13 
14 #pragma once
15 
16 {# Note: The nogncheck decorations are only to make GN not mad at the template#}
17 {# this file is generated from. There are no GN rule violations in the generated#}
18 {# file itself and the no-check declarations will be stripped in generated files.#}
19 #include "impeller/core/buffer_view.h" {# // nogncheck #}
20 
21 #include "impeller/core/sampler.h" {# // nogncheck #}
22 
23 #include "impeller/core/shader_types.h" {# // nogncheck #}
24 
25 #include "impeller/core/resource_binder.h" {# // nogncheck #}
26 
27 #include "impeller/core/texture.h" {# // nogncheck #}
28 
29 
30 namespace impeller {
31 
32 struct {{camel_case(shader_name)}}{{camel_case(shader_stage)}}Shader {
33  // ===========================================================================
34  // Stage Info ================================================================
35  // ===========================================================================
36  static constexpr std::string_view kLabel = "{{camel_case(shader_name)}}";
37  static constexpr std::string_view kEntrypointName = "{{entrypoint}}";
38  static constexpr ShaderStage kShaderStage = {{to_shader_stage(shader_stage)}};
39  // The generator used to prepare these bindings. Metal generators may be used
40  // by GLES backends but GLES generators are unsuitable for the metal backend.
41  static constexpr std::string_view kGeneratorName = "{{get_generator_name()}}";
42 {% if length(struct_definitions) > 0 %}
43  // ===========================================================================
44  // Struct Definitions ========================================================
45  // ===========================================================================
46 {% for def in struct_definitions %}
47 
48 {% if last(def.members).array_elements == 0 %}
49  template <size_t FlexCount>
50 {% endif %}
51  struct {{def.name}} {
52 {% for member in def.members %}
53 {{" "}}{% if member.element_padding > 0 %}Padded<{{member.type}}, {{member.element_padding}}>{% else %}{{member.type}}{% endif %}{{" " + member.name}}{% if member.array_elements != "std::nullopt" %}[{% if member.array_elements == 0 %}FlexCount{% else %}{{member.array_elements}}{% endif %}]{% endif %}; // (offset {{member.offset}}, size {{member.byte_length}})
54 {% endfor %}
55  }; // struct {{def.name}} (size {{def.byte_length}})
56 {% endfor %}
57 {% endif %}
58 {% if length(buffers) > 0 %}
59 
60  // ===========================================================================
61  // Stage Uniform & Storage Buffers ===========================================
62  // ===========================================================================
63 {% for buffer in buffers %}
64 
65  static constexpr auto kResource{{camel_case(buffer.name)}} = ShaderUniformSlot { // {{buffer.name}}
66  "{{buffer.name}}", // name
67  {{buffer.ext_res_0}}u, // ext_res_0
68  {{buffer.set}}u, // set
69  {{buffer.binding}}u, // binding
70  };
71  static ShaderMetadata kMetadata{{camel_case(buffer.name)}};
72 {% endfor %}
73 {% endif %}
74 
75  // ===========================================================================
76  // Stage Inputs ==============================================================
77  // ===========================================================================
78 {% if length(stage_inputs) > 0 %}
79 {% for stage_input in stage_inputs %}
80 
81  static constexpr auto kInput{{camel_case(stage_input.name)}} = ShaderStageIOSlot { // {{stage_input.name}}
82  "{{stage_input.name}}", // name
83  {{stage_input.location}}u, // attribute location
84  {{stage_input.descriptor_set}}u, // attribute set
85  {{stage_input.binding}}u, // attribute binding
86  {{stage_input.type.type_name}}, // type
87  {{stage_input.type.bit_width}}u, // bit width of type
88  {{stage_input.type.vec_size}}u, // vec size
89  {{stage_input.type.columns}}u, // number of columns
90  {{stage_input.offset}}u, // offset for interleaved layout
91  };
92 {% endfor %}
93 {% endif %}
94 
95  static constexpr std::array<const ShaderStageIOSlot*, {{length(stage_inputs)}}> kAllShaderStageInputs = {
96 {% for stage_input in stage_inputs %}
97  &kInput{{camel_case(stage_input.name)}}, // {{stage_input.name}}
98 {% endfor %}
99  };
100 
101 {% if shader_stage == "vertex" %}
102  static constexpr auto kInterleavedLayout = ShaderStageBufferLayout {
103 {% if length(stage_inputs) > 0 %}
104  sizeof(PerVertexData), // stride for interleaved layout
105 {% else %}
106  0u,
107 {% endif %}
108  0u, // attribute binding
109  };
110  static constexpr std::array<const ShaderStageBufferLayout*, 1> kInterleavedBufferLayout = {
111  &kInterleavedLayout
112  };
113 {% endif %}
114 
115 {% if length(sampled_images) > 0 %}
116  // ===========================================================================
117  // Sampled Images ============================================================
118  // ===========================================================================
119 {% for sampled_image in sampled_images %}
120 
121  static constexpr auto kResource{{camel_case(sampled_image.name)}} = SampledImageSlot { // {{sampled_image.name}}
122  "{{sampled_image.name}}", // name
123  {{sampled_image.ext_res_0}}u, // ext_res_0
124  {{sampled_image.set}}u, // set
125  {{sampled_image.binding}}u, // binding
126  };
127  static ShaderMetadata kMetadata{{camel_case(sampled_image.name)}};
128 {% endfor %}
129 {% endif %}
130  // ===========================================================================
131  // Stage Outputs =============================================================
132  // ===========================================================================
133 {% if length(stage_outputs) > 0 %}
134 {% for stage_output in stage_outputs %}
135  static constexpr auto kOutput{{camel_case(stage_output.name)}} = ShaderStageIOSlot { // {{stage_output.name}}
136  "{{stage_output.name}}", // name
137  {{stage_output.location}}u, // attribute location
138  {{stage_output.descriptor_set}}u, // attribute set
139  {{stage_output.binding}}u, // attribute binding
140  {{stage_output.type.type_name}}, // type
141  {{stage_output.type.bit_width}}u, // bit width of type
142  {{stage_output.type.vec_size}}u, // vec size
143  {{stage_output.type.columns}}u // number of columns
144  };
145 {% endfor %}
146  static constexpr std::array<const ShaderStageIOSlot*, {{length(stage_outputs)}}> kAllShaderStageOutputs = {
147 {% for stage_output in stage_outputs %}
148  &kOutput{{camel_case(stage_output.name)}}, // {{stage_output.name}}
149 {% endfor %}
150  };
151 {% endif %}
152 
153  // ===========================================================================
154  // Resource Binding Utilities ================================================
155  // ===========================================================================
156 
157 {% for proto in bind_prototypes %}
158  /// {{proto.docstring}}
159  static {{proto.return_type}} Bind{{proto.name}}({% for arg in proto.args %}
160 {{arg.type_name}} {{arg.argument_name}}{% if not loop.is_last %}, {% endif %}
161 {% endfor %}) {
162  return {{ proto.args.0.argument_name }}.BindResource({% for arg in proto.args %}
163  {% if loop.is_first %}
164 {{to_shader_stage(shader_stage)}}, {{ proto.descriptor_type }}, kResource{{ proto.name }}, kMetadata{{ proto.name }}, {% else %}
165 std::move({{ arg.argument_name }}){% if not loop.is_last %}, {% endif %}
166  {% endif %}
167  {% endfor %});
168  }
169 
170 {% endfor %}
171 
172  // ===========================================================================
173  // Metadata for Vulkan =======================================================
174  // ===========================================================================
175  static constexpr std::array<DescriptorSetLayout,{{length(buffers)+length(sampled_images)+length(subpass_inputs)}}> kDescriptorSetLayouts{
176 {% for subpass_input in subpass_inputs %}
177  DescriptorSetLayout{
178  {{subpass_input.binding}}, // binding = {{subpass_input.binding}}
179  {{subpass_input.descriptor_type}}, // descriptor_type = {{subpass_input.descriptor_type}}
180  {{to_shader_stage(shader_stage)}}, // shader_stage = {{to_shader_stage(shader_stage)}}
181  },
182 {% endfor %}
183 {% for buffer in buffers %}
184  DescriptorSetLayout{
185  {{buffer.binding}}, // binding = {{buffer.binding}}
186  {{buffer.descriptor_type}}, // descriptor_type = {{buffer.descriptor_type}}
187  {{to_shader_stage(shader_stage)}}, // shader_stage = {{to_shader_stage(shader_stage)}}
188  },
189 {% endfor %}
190 {% for sampled_image in sampled_images %}
191  DescriptorSetLayout{
192  {{sampled_image.binding}}, // binding = {{sampled_image.binding}}
193  {{sampled_image.descriptor_type}}, // descriptor_type = {{sampled_image.descriptor_type}}
194  {{to_shader_stage(shader_stage)}}, // shader_stage = {{to_shader_stage(shader_stage)}}
195  },
196 {% endfor %}
197  };
198 
199 }; // struct {{camel_case(shader_name)}}{{camel_case(shader_stage)}}Shader
200 
201 } // namespace impeller
202 )~~";
203 
204 constexpr std::string_view kReflectionCCTemplate =
205  R"~~(// THIS FILE IS GENERATED BY impellerc.
206 // DO NOT EDIT OR CHECK THIS INTO SOURCE CONTROL
207 
208 #include "{{header_file_name}}"
209 
210 #include <type_traits>
211 
212 namespace impeller {
213 
214 using Shader = {{camel_case(shader_name)}}{{camel_case(shader_stage)}}Shader;
215 
216 {% for def in struct_definitions %}
217 // Sanity checks for {{def.name}}
218 {% if last(def.members).array_elements == 0 %}
219 static_assert(std::is_standard_layout_v<Shader::{{def.name}}<0>>);
220 {% for member in def.members %}
221 static_assert(offsetof(Shader::{{def.name}}<0>, {{member.name}}) == {{member.offset}});
222 {% endfor %}
223 {% else %}
224 static_assert(std::is_standard_layout_v<Shader::{{def.name}}>);
225 static_assert(sizeof(Shader::{{def.name}}) == {{def.byte_length}});
226 {% for member in def.members %}
227 static_assert(offsetof(Shader::{{def.name}}, {{member.name}}) == {{member.offset}});
228 {% endfor %}
229 {% endif %}
230 {% endfor %}
231 
232 {% for buffer in buffers %}
233 ShaderMetadata Shader::kMetadata{{camel_case(buffer.name)}} = {
234  "{{buffer.name}}", // name
235  std::vector<ShaderStructMemberMetadata> {
236  {% for member in buffer.type.members %}
237  ShaderStructMemberMetadata {
238  {{ member.base_type }}, // type
239  "{{ member.name }}", // name
240  {{ member.offset }}, // offset
241  {{ member.size }}, // size
242  {{ member.byte_length }}, // byte_length
243  {{ member.array_elements }}, // array_elements
244  },
245  {% endfor %}
246  } // members
247 };
248 {% endfor %}
249 
250 {% for sampled_image in sampled_images %}
251 ShaderMetadata Shader::kMetadata{{camel_case(sampled_image.name)}} = {
252  "{{sampled_image.name}}", // name
253  std::vector<ShaderStructMemberMetadata> {}, // 0 members
254 };
255 {% endfor %}
256 
257 } // namespace impeller
258 )~~";
259 
260 } // namespace compiler
261 } // namespace impeller
impeller::compiler::kReflectionCCTemplate
constexpr std::string_view kReflectionCCTemplate
Definition: code_gen_template.h:204
impeller::compiler::kReflectionHeaderTemplate
constexpr std::string_view kReflectionHeaderTemplate
Definition: code_gen_template.h:10
impeller
Definition: aiks_blur_unittests.cc:20