The open source OpenXR runtime
1// Copyright 2019-2023, Collabora, Ltd.
2// SPDX-License-Identifier: BSL-1.0
3/*!
4 * @file
5 * @brief Shader loading code.
6 * @author Lubosz Sarnecki <lubosz.sarnecki@collabora.com>
7 * @author Jakob Bornecrantz <jakob@collabora.com>
8 * @ingroup comp_render
9 */
10
11#include "vk/vk_mini_helpers.h"
12
13#include "render/render_interface.h"
14
15
16/*
17 *
18 * Shader headers.
19 *
20 */
21
22#if defined(__GNUC__)
23#pragma GCC diagnostic push
24#pragma GCC diagnostic ignored "-Wpragmas"
25#pragma GCC diagnostic ignored "-Wnewline-eof"
26#endif
27
28#include "shaders/blit.comp.h"
29#include "shaders/clear.comp.h"
30#include "shaders/layer.comp.h"
31#include "shaders/distortion.comp.h"
32#include "shaders/layer_cylinder.frag.h"
33#include "shaders/layer_cylinder.vert.h"
34#include "shaders/layer_equirect2.frag.h"
35#include "shaders/layer_equirect2.vert.h"
36#include "shaders/layer_projection.vert.h"
37#include "shaders/layer_projection.vert.h"
38#include "shaders/layer_quad.vert.h"
39#include "shaders/layer_shared.frag.h"
40#include "shaders/mesh.frag.h"
41#include "shaders/mesh.vert.h"
42
43#if defined(__GNUC__)
44#pragma GCC diagnostic pop
45#endif
46
47
48/*
49 *
50 * Helpers
51 *
52 */
53
54#define LOAD(SHADER) \
55 do { \
56 const uint32_t *code = shaders_##SHADER; \
57 size_t size = sizeof(shaders_##SHADER); \
58 VkResult ret = shader_load(vk, /* vk_bundle */ \
59 code, /* code */ \
60 size, /* size */ \
61 &s->SHADER); /* out */ \
62 if (ret != VK_SUCCESS) { \
63 VK_ERROR(vk, "Failed to load shader '" #SHADER "'"); \
64 render_shaders_fini(s, vk); \
65 return false; \
66 } \
67 VK_NAME_SHADER_MODULE(vk, s->SHADER, #SHADER); \
68 } while (false)
69
70
71/*
72 *
73 * Functions.
74 *
75 */
76
77XRT_CHECK_RESULT static VkResult
78shader_load(struct vk_bundle *vk, const uint32_t *code, size_t size, VkShaderModule *out_module)
79{
80 VkResult ret;
81
82 VkShaderModuleCreateInfo info = {
83 .sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO,
84 .codeSize = size,
85 .pCode = code,
86 };
87
88 VkShaderModule module;
89 ret = vk->vkCreateShaderModule( //
90 vk->device, //
91 &info, //
92 NULL, //
93 &module); //
94 VK_CHK_AND_RET(ret, "vkCreateShaderModule");
95
96 *out_module = module;
97
98 return VK_SUCCESS;
99}
100
101bool
102render_shaders_load(struct render_shaders *s, struct vk_bundle *vk)
103{
104 LOAD(blit_comp);
105
106 LOAD(clear_comp);
107
108 LOAD(layer_comp);
109
110 LOAD(distortion_comp);
111
112 LOAD(mesh_vert);
113 LOAD(mesh_frag);
114
115 LOAD(layer_cylinder_frag);
116 LOAD(layer_cylinder_vert);
117 LOAD(layer_equirect2_frag);
118 LOAD(layer_equirect2_vert);
119 LOAD(layer_projection_vert);
120 LOAD(layer_quad_vert);
121 LOAD(layer_shared_frag);
122
123 VK_DEBUG(vk, "Shaders loaded!");
124
125 return true;
126}
127
128void
129render_shaders_fini(struct render_shaders *s, struct vk_bundle *vk)
130{
131 D(ShaderModule, s->blit_comp);
132 D(ShaderModule, s->clear_comp);
133 D(ShaderModule, s->distortion_comp);
134 D(ShaderModule, s->layer_comp);
135 D(ShaderModule, s->mesh_vert);
136 D(ShaderModule, s->mesh_frag);
137
138 D(ShaderModule, s->layer_cylinder_frag);
139 D(ShaderModule, s->layer_cylinder_vert);
140 D(ShaderModule, s->layer_equirect2_frag);
141 D(ShaderModule, s->layer_equirect2_vert);
142 D(ShaderModule, s->layer_projection_vert);
143 D(ShaderModule, s->layer_quad_vert);
144 D(ShaderModule, s->layer_shared_frag);
145
146 VK_DEBUG(vk, "Shaders destroyed!");
147}