effect-parser.h 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286
  1. /******************************************************************************
  2. Copyright (C) 2013 by Hugh Bailey <[email protected]>
  3. This program is free software: you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation, either version 3 of the License, or
  6. (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program. If not, see <http://www.gnu.org/licenses/>.
  13. ******************************************************************************/
  14. #ifndef EFFECT_PARSER_H
  15. #define EFFECT_PARSER_H
  16. #include "../util/darray.h"
  17. #include "../util/cf-parser.h"
  18. #include "graphics.h"
  19. #ifdef __cplusplus
  20. extern "C" {
  21. #endif
  22. struct dstr;
  23. /*
  24. * The effect parser takes an effect file and converts it into individual
  25. * shaders for each technique's pass. It automatically writes all dependent
  26. * structures/functions/parameters to the shader and builds shader text for
  27. * each shader component of each pass.
  28. */
  29. /* ------------------------------------------------------------------------- */
  30. /* effect parser var data */
  31. struct ep_var {
  32. char *type, *name, *mapping;
  33. bool uniform;
  34. };
  35. static inline void ep_var_init(struct ep_var *epv)
  36. {
  37. memset(epv, 0, sizeof(struct ep_var));
  38. }
  39. static inline void ep_var_free(struct ep_var *epv)
  40. {
  41. bfree(epv->type);
  42. bfree(epv->name);
  43. bfree(epv->mapping);
  44. }
  45. /* ------------------------------------------------------------------------- */
  46. /* effect parser param data */
  47. struct ep_param {
  48. char *type, *name;
  49. DARRAY(uint8_t) default_val;
  50. DARRAY(char*) properties;
  51. struct effect_param *param;
  52. bool is_const, is_property, is_uniform, is_texture, written;
  53. int writeorder, array_count;
  54. };
  55. extern void ep_param_writevar(struct dstr *dst, struct darray *use_params);
  56. static inline void ep_param_init(struct ep_param *epp,
  57. char *type, char *name,
  58. bool is_property, bool is_const, bool is_uniform)
  59. {
  60. epp->type = type;
  61. epp->name = name;
  62. epp->is_property = is_property;
  63. epp->is_const = is_const;
  64. epp->is_uniform = is_uniform;
  65. epp->is_texture = (astrcmp_n(epp->type, "texture", 7) == 0);
  66. epp->written = false;
  67. epp->writeorder = false;
  68. epp->array_count = 0;
  69. da_init(epp->default_val);
  70. da_init(epp->properties);
  71. }
  72. static inline void ep_param_free(struct ep_param *epp)
  73. {
  74. bfree(epp->type);
  75. bfree(epp->name);
  76. da_free(epp->default_val);
  77. da_free(epp->properties);
  78. }
  79. /* ------------------------------------------------------------------------- */
  80. /* effect parser struct data */
  81. struct ep_struct {
  82. char *name;
  83. DARRAY(struct ep_var) vars; /* struct ep_var */
  84. bool written;
  85. };
  86. static inline bool ep_struct_mapped(struct ep_struct *eps)
  87. {
  88. if (eps->vars.num > 0)
  89. return eps->vars.array[0].mapping != NULL;
  90. return false;
  91. }
  92. static inline void ep_struct_init(struct ep_struct *eps)
  93. {
  94. memset(eps, 0, sizeof(struct ep_struct));
  95. }
  96. static inline void ep_struct_free(struct ep_struct *eps)
  97. {
  98. size_t i;
  99. bfree(eps->name);
  100. for (i = 0; i < eps->vars.num; i++)
  101. ep_var_free(eps->vars.array+i);
  102. da_free(eps->vars);
  103. }
  104. /* ------------------------------------------------------------------------- */
  105. /* effect parser sampler data */
  106. struct ep_sampler {
  107. char *name;
  108. DARRAY(char*) states;
  109. DARRAY(char*) values;
  110. bool written;
  111. };
  112. static inline void ep_sampler_init(struct ep_sampler *eps)
  113. {
  114. memset(eps, 0, sizeof(struct ep_sampler));
  115. }
  116. static inline void ep_sampler_free(struct ep_sampler *eps)
  117. {
  118. size_t i;
  119. for (i = 0; i < eps->states.num; i++)
  120. bfree(eps->states.array[i]);
  121. for (i = 0; i < eps->values.num; i++)
  122. bfree(eps->values.array[i]);
  123. bfree(eps->name);
  124. da_free(eps->states);
  125. da_free(eps->values);
  126. }
  127. /* ------------------------------------------------------------------------- */
  128. /* effect parser pass data */
  129. struct ep_pass {
  130. char *name;
  131. DARRAY(struct cf_token) vertex_program;
  132. DARRAY(struct cf_token) fragment_program;
  133. struct effect_pass *pass;
  134. };
  135. static inline void ep_pass_init(struct ep_pass *epp)
  136. {
  137. memset(epp, 0, sizeof(struct ep_pass));
  138. }
  139. static inline void ep_pass_free(struct ep_pass *epp)
  140. {
  141. bfree(epp->name);
  142. da_free(epp->vertex_program);
  143. da_free(epp->fragment_program);
  144. }
  145. /* ------------------------------------------------------------------------- */
  146. /* effect parser technique data */
  147. struct ep_technique {
  148. char *name;
  149. DARRAY(struct ep_pass) passes; /* struct ep_pass */
  150. };
  151. static inline void ep_technique_init(struct ep_technique *ept)
  152. {
  153. memset(ept, 0, sizeof(struct ep_technique));
  154. }
  155. static inline void ep_technique_free(struct ep_technique *ept)
  156. {
  157. size_t i;
  158. for (i = 0; i < ept->passes.num; i++)
  159. ep_pass_free(ept->passes.array+i);
  160. bfree(ept->name);
  161. da_free(ept->passes);
  162. }
  163. /* ------------------------------------------------------------------------- */
  164. /* effect parser function data */
  165. struct ep_func {
  166. char *name, *ret_type, *mapping;
  167. struct dstr contents;
  168. DARRAY(struct ep_var) param_vars;
  169. DARRAY(const char*) func_deps;
  170. DARRAY(const char*) struct_deps;
  171. DARRAY(const char*) param_deps;
  172. DARRAY(const char*) sampler_deps;
  173. bool written;
  174. };
  175. static inline void ep_func_init(struct ep_func *epf, char *ret_type,
  176. char *name)
  177. {
  178. memset(epf, 0, sizeof(struct ep_func));
  179. epf->name = name;
  180. epf->ret_type = ret_type;
  181. }
  182. static inline void ep_func_free(struct ep_func *epf)
  183. {
  184. size_t i;
  185. for (i = 0; i < epf->param_vars.num; i++)
  186. ep_var_free(epf->param_vars.array+i);
  187. bfree(epf->name);
  188. bfree(epf->ret_type);
  189. bfree(epf->mapping);
  190. dstr_free(&epf->contents);
  191. da_free(epf->param_vars);
  192. da_free(epf->func_deps);
  193. da_free(epf->struct_deps);
  194. da_free(epf->param_deps);
  195. da_free(epf->sampler_deps);
  196. }
  197. /* ------------------------------------------------------------------------- */
  198. struct effect_parser {
  199. effect_t effect;
  200. DARRAY(struct ep_param) params;
  201. DARRAY(struct ep_struct) structs;
  202. DARRAY(struct ep_func) funcs;
  203. DARRAY(struct ep_sampler) samplers;
  204. DARRAY(struct ep_technique) techniques;
  205. /* internal vars */
  206. DARRAY(struct cf_lexer) files;
  207. DARRAY(struct cf_token) tokens;
  208. struct effect_pass *cur_pass;
  209. struct cf_parser cfp;
  210. };
  211. static inline void ep_init(struct effect_parser *ep)
  212. {
  213. da_init(ep->params);
  214. da_init(ep->structs);
  215. da_init(ep->funcs);
  216. da_init(ep->samplers);
  217. da_init(ep->techniques);
  218. da_init(ep->files);
  219. da_init(ep->tokens);
  220. ep->cur_pass = NULL;
  221. cf_parser_init(&ep->cfp);
  222. }
  223. extern void ep_free(struct effect_parser *ep);
  224. extern bool ep_parse(struct effect_parser *ep, effect_t effect,
  225. const char *effect_string, const char *file);
  226. #ifdef __cplusplus
  227. }
  228. #endif
  229. #endif