filename | src/drivers/gl_sl.c |
changeset | 561:533f6b478071 |
prev | 540:a3767018a96d |
author | nkeynes |
date | Fri Feb 08 00:06:56 2008 +0000 (16 years ago) |
permissions | -rw-r--r-- |
last change | Fix LDS/STS to FPUL/FPSCR to check the FPU disabled bit. Fixes the linux 2.4.0-test8 kernel boot (this wasn't exactly very well documented in the original manual) |
view | annotate | diff | log | raw |
1 /**
2 * $Id$
3 *
4 * GLSL shader loader/unloader. Current version assumes there's exactly
5 * 1 shader program that's used globally. This may turn out not to be the
6 * most efficient approach.
7 *
8 * Copyright (c) 2007 Nathan Keynes.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 */
21 #define GL_GLEXT_PROTOTYPES 1
23 #include "lxdream.h"
24 #include "display.h"
25 #include "drivers/gl_common.h"
27 #define MAX_ERROR_BUF 4096
29 gboolean glsl_is_supported()
30 {
31 return isGLExtensionSupported("GL_ARB_fragment_shader") &&
32 isGLExtensionSupported("GL_ARB_vertex_shader") &&
33 isGLExtensionSupported("GL_ARB_shading_language_100");
34 }
36 #ifdef GL_ARB_shader_objects
37 static GLhandleARB glsl_program, glsl_vert_shader, glsl_frag_shader;
39 void glsl_print_error( char *msg, GLhandleARB obj )
40 {
41 char buf[MAX_ERROR_BUF];
42 GLsizei length;
43 glGetInfoLogARB( obj, sizeof(buf), &length, buf );
44 ERROR( "%s: %s", msg, buf );
45 }
47 gboolean glsl_check_shader_error( char *msg, GLhandleARB obj )
48 {
49 GLint value;
51 glGetObjectParameterivARB(obj, GL_OBJECT_COMPILE_STATUS_ARB, &value);
52 if( value == 0 ) {
53 glsl_print_error(msg, obj);
54 return FALSE;
55 }
56 return TRUE;
57 }
59 gboolean glsl_check_program_error( char *msg, GLhandleARB obj )
60 {
61 if( glGetError() != GL_NO_ERROR ) {
62 glsl_print_error(msg, obj);
63 }
64 return TRUE;
65 }
68 gboolean glsl_load_shaders( const char *vertex_src, const char *fragment_src )
69 {
70 gboolean vsok, fsok, pok = FALSE;
71 glsl_program = glCreateProgramObjectARB();
73 glsl_vert_shader = glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB);
74 glsl_frag_shader = glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB);
75 glShaderSourceARB( glsl_vert_shader, 1, &vertex_src, NULL );
76 glCompileShaderARB(glsl_vert_shader);
77 vsok = glsl_check_shader_error("Failed to compile vertex shader", glsl_vert_shader);
78 glShaderSourceARB( glsl_frag_shader, 1, &fragment_src, NULL );
79 glCompileShaderARB(glsl_frag_shader);
80 fsok = glsl_check_shader_error("Failed to compile fragment shader", glsl_frag_shader);
82 if( vsok && fsok ) {
83 glAttachObjectARB(glsl_program, glsl_vert_shader);
84 glAttachObjectARB(glsl_program, glsl_frag_shader);
85 glLinkProgramARB(glsl_program);
86 pok = glsl_check_program_error( "Failed to link shader program", glsl_program );
87 }
88 if( pok ) {
89 glUseProgramObjectARB(glsl_program);
90 pok = glsl_check_program_error( "Failed to apply shader program", glsl_program );
91 } else {
92 glsl_unload_shaders();
93 }
94 return pok;
95 }
97 void glsl_unload_shaders(void)
98 {
99 glUseProgramObjectARB(0);
100 glDetachObjectARB(glsl_program, glsl_vert_shader);
101 glDetachObjectARB(glsl_program, glsl_frag_shader);
102 glDeleteObjectARB(glsl_program);
103 glDeleteObjectARB(glsl_vert_shader);
104 glDeleteObjectARB(glsl_frag_shader);
105 }
107 #else
108 static GLuint glsl_program, glsl_vert_shader, glsl_frag_shader;
110 gboolean glsl_check_shader_error( char *msg, GLuint shader )
111 {
112 GLint value;
114 glGetShaderiv( shader, GL_COMPILE_STATUS, &value );
115 if( value == 0 ) {
116 char buf[MAX_ERROR_BUF];
117 GLsizei length;
118 glGetShaderInfoLog( shader, sizeof(buf), &length, buf );
119 ERROR( "%s: %s", msg, buf );
120 return FALSE;
121 }
122 return TRUE;
123 }
124 gboolean glsl_check_program_error( char *msg, GLuint program )
125 {
126 if( glGetError() != GL_NO_ERROR ) {
127 char buf[MAX_ERROR_BUF];
128 GLsizei length;
129 glGetProgramInfoLog( program, sizeof(buf), &length, buf );
130 ERROR( "%s: %s", msg, buf );
131 return FALSE;
132 }
133 return TRUE;
134 }
136 gboolean glsl_load_shaders( const char *vertex_src, const char *fragment_src )
137 {
138 gboolean vsok, fsok, pok = FALSE;
139 glsl_program = glCreateProgram();
140 glsl_vert_shader = glCreateShader(GL_VERTEX_SHADER);
141 glsl_frag_shader = glCreateShader(GL_FRAGMENT_SHADER);
142 glShaderSource( glsl_vert_shader, 1, &vertex_src, NULL );
143 glCompileShader(glsl_vert_shader);
144 vsok = glsl_check_shader_error( "Failed to compile vertex shader", glsl_vert_shader );
145 glShaderSource( glsl_frag_shader, 1, &fragment_src, NULL );
146 glCompileShader(glsl_frag_shader);
147 fsok = glsl_check_shader_error( "Failed to compile fragment shader", glsl_frag_shader );
149 if( vsok && fsok ) {
150 glAttachShader(glsl_program, glsl_vert_shader);
151 glAttachShader(glsl_program, glsl_frag_shader);
152 glLinkProgram(glsl_program);
153 pok = glsl_check_program_error( "Failed to link shader program", glsl_program );
154 }
156 if( pok ) {
157 glUseProgram(glsl_program);
158 } else {
159 glsl_unload_shaders();
160 }
161 return pok;
162 }
164 void glsl_unload_shaders(void)
165 {
166 glUseProgram(0);
167 glDetachShader(glsl_program, glsl_vert_shader);
168 glDetachShader(glsl_program, glsl_frag_shader);
169 glDeleteProgram(glsl_program);
170 glDeleteShader(glsl_vert_shader);
171 glDeleteShader(glsl_frag_shader);
172 }
173 #endif
.