2 * Copyright © 2008, 2009 Intel Corporation
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
27 * This file is the main() routine and scaffolding for producing
28 * builtin_compiler (which doesn't include builtins itself and is used
29 * to generate the profile information for builtin_function.cpp), and
30 * for glsl_compiler (which does include builtins and can be used to
31 * offline compile GLSL code and examine the resulting GLSL IR.
35 #include "glsl_parser_extras.h"
36 #include "ir_optimization.h"
38 #include "loop_analysis.h"
39 #include "standalone_scaffolding.h"
42 initialize_context(struct gl_context
*ctx
, gl_api api
)
44 initialize_context_to_defaults(ctx
, api
);
46 /* The standalone compiler needs to claim support for almost
47 * everything in order to compile the built-in functions.
49 ctx
->Const
.GLSLVersion
= 330;
50 ctx
->Extensions
.ARB_ES3_compatibility
= true;
52 ctx
->Const
.MaxClipPlanes
= 8;
53 ctx
->Const
.MaxDrawBuffers
= 2;
55 /* More than the 1.10 minimum to appease parser tests taken from
56 * apps that (hopefully) already checked the number of coords.
58 ctx
->Const
.MaxTextureCoordUnits
= 4;
60 ctx
->Driver
.NewShader
= _mesa_new_shader
;
63 /* Returned string will have 'ctx' as its ralloc owner. */
65 load_text_file(void *ctx
, const char *file_name
)
69 size_t total_read
= 0;
70 FILE *fp
= fopen(file_name
, "rb");
76 fseek(fp
, 0L, SEEK_END
);
78 fseek(fp
, 0L, SEEK_SET
);
80 text
= (char *) ralloc_size(ctx
, size
+ 1);
83 size_t bytes
= fread(text
+ total_read
,
84 1, size
- total_read
, fp
);
85 if (bytes
< size
- total_read
) {
96 } while (total_read
< size
);
98 text
[total_read
] = '\0';
112 const struct option compiler_opts
[] = {
113 { "glsl-es", 0, &glsl_es
, 1 },
114 { "dump-ast", 0, &dump_ast
, 1 },
115 { "dump-hir", 0, &dump_hir
, 1 },
116 { "dump-lir", 0, &dump_lir
, 1 },
117 { "link", 0, &do_link
, 1 },
122 * \brief Print proper usage and exit with failure.
125 usage_fail(const char *name
)
129 "usage: %s [options] <file.vert | file.geom | file.frag>\n"
131 "Possible options are:\n";
132 printf(header
, name
, name
);
133 for (const struct option
*o
= compiler_opts
; o
->name
!= 0; ++o
) {
134 printf(" --%s\n", o
->name
);
141 compile_shader(struct gl_context
*ctx
, struct gl_shader
*shader
)
143 struct _mesa_glsl_parse_state
*state
=
144 new(shader
) _mesa_glsl_parse_state(ctx
, shader
->Type
, shader
);
146 _mesa_glsl_compile_shader(ctx
, shader
, dump_ast
, dump_hir
);
148 /* Print out the resulting IR */
149 if (!state
->error
&& dump_lir
) {
150 _mesa_print_ir(shader
->ir
, state
);
157 main(int argc
, char **argv
)
159 int status
= EXIT_SUCCESS
;
160 struct gl_context local_ctx
;
161 struct gl_context
*ctx
= &local_ctx
;
165 while ((c
= getopt_long(argc
, argv
, "", compiler_opts
, &idx
)) != -1)
172 initialize_context(ctx
, (glsl_es
) ? API_OPENGLES2
: API_OPENGL_COMPAT
);
174 struct gl_shader_program
*whole_program
;
176 whole_program
= rzalloc (NULL
, struct gl_shader_program
);
177 assert(whole_program
!= NULL
);
178 whole_program
->InfoLog
= ralloc_strdup(whole_program
, "");
180 for (/* empty */; argc
> optind
; optind
++) {
181 whole_program
->Shaders
=
182 reralloc(whole_program
, whole_program
->Shaders
,
183 struct gl_shader
*, whole_program
->NumShaders
+ 1);
184 assert(whole_program
->Shaders
!= NULL
);
186 struct gl_shader
*shader
= rzalloc(whole_program
, gl_shader
);
188 whole_program
->Shaders
[whole_program
->NumShaders
] = shader
;
189 whole_program
->NumShaders
++;
191 const unsigned len
= strlen(argv
[optind
]);
195 const char *const ext
= & argv
[optind
][len
- 5];
196 if (strncmp(".vert", ext
, 5) == 0 || strncmp(".glsl", ext
, 5) == 0)
197 shader
->Type
= GL_VERTEX_SHADER
;
198 else if (strncmp(".geom", ext
, 5) == 0)
199 shader
->Type
= GL_GEOMETRY_SHADER
;
200 else if (strncmp(".frag", ext
, 5) == 0)
201 shader
->Type
= GL_FRAGMENT_SHADER
;
205 shader
->Source
= load_text_file(whole_program
, argv
[optind
]);
206 if (shader
->Source
== NULL
) {
207 printf("File \"%s\" does not exist.\n", argv
[optind
]);
211 compile_shader(ctx
, shader
);
213 if (!shader
->CompileStatus
) {
214 printf("Info log for %s:\n%s\n", argv
[optind
], shader
->InfoLog
);
215 status
= EXIT_FAILURE
;
220 if ((status
== EXIT_SUCCESS
) && do_link
) {
221 link_shaders(ctx
, whole_program
);
222 status
= (whole_program
->LinkStatus
) ? EXIT_SUCCESS
: EXIT_FAILURE
;
224 if (strlen(whole_program
->InfoLog
) > 0)
225 printf("Info log for linking:\n%s\n", whole_program
->InfoLog
);
228 for (unsigned i
= 0; i
< MESA_SHADER_TYPES
; i
++)
229 ralloc_free(whole_program
->_LinkedShaders
[i
]);
231 ralloc_free(whole_program
);
232 _mesa_glsl_release_types();
233 _mesa_glsl_release_builtin_functions();