2 * Copyright © 2015 Canonical Ltd.
4 * This program is free software: you can redistribute it and/or modify it
5 * under the terms of the GNU General Public License version 3,
6 * as published by the Free Software Foundation.
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
16 * Authored by: Daniel van Vugt <daniel.van.vugt@canonical.com>
19 #include "anbox/graphics/program_family.h"
21 #include "anbox/graphics/emugl/DispatchTables.h"
28 void ProgramFamily::Shader::init(GLenum type, const GLchar* src) {
30 id = s_gles2.glCreateShader(type);
32 s_gles2.glShaderSource(id, 1, &src, NULL);
33 s_gles2.glCompileShader(id);
35 s_gles2.glGetShaderiv(id, GL_COMPILE_STATUS, &ok);
38 s_gles2.glGetShaderInfoLog(id, sizeof log - 1, NULL, log);
39 log[sizeof log - 1] = '\0';
40 s_gles2.glDeleteShader(id);
42 throw std::runtime_error(std::string("Compile failed: ") + log +
49 ProgramFamily::~ProgramFamily() noexcept {
50 // shader and program lifetimes are managed manually, so that we don't
51 // need any reference counting or to worry about how many copy constructions
52 // might have been followed by destructor calls during container resizes.
54 for (auto& p : program) {
55 if (p.second.id) s_gles2.glDeleteProgram(p.second.id);
58 for (auto& v : vshader) {
59 if (v.second.id) s_gles2.glDeleteShader(v.second.id);
62 for (auto& f : fshader) {
63 if (f.second.id) s_gles2.glDeleteShader(f.second.id);
67 GLuint ProgramFamily::add_program(const GLchar* const vshader_src,
68 const GLchar* const fshader_src) {
69 auto& v = vshader[vshader_src];
70 if (!v.id) v.init(GL_VERTEX_SHADER, vshader_src);
72 auto& f = fshader[fshader_src];
73 if (!f.id) f.init(GL_FRAGMENT_SHADER, fshader_src);
75 auto& p = program[{v.id, f.id}];
77 p.id = s_gles2.glCreateProgram();
78 s_gles2.glAttachShader(p.id, v.id);
79 s_gles2.glAttachShader(p.id, f.id);
80 s_gles2.glLinkProgram(p.id);
82 s_gles2.glGetProgramiv(p.id, GL_LINK_STATUS, &ok);
85 s_gles2.glGetProgramInfoLog(p.id, sizeof log - 1, NULL, log);
86 log[sizeof log - 1] = '\0';
87 s_gles2.glDeleteShader(p.id);
89 throw std::runtime_error(std::string("Link failed: ") + log);
95 } // namespace graphics