PageRenderTime 40ms CodeModel.GetById 11ms RepoModel.GetById 0ms app.codeStats 1ms

/brlcad/tags/rel-7-4-2/src/liboptical/sh_stack.c

https://bitbucket.org/vrrm/brl-cad-copy-for-fast-history-browsing-in-git
C | 378 lines | 219 code | 65 blank | 94 comment | 51 complexity | 0a6ea9b22a80cc63fe9edbae0628f63d MD5 | raw file
Possible License(s): GPL-2.0, LGPL-2.0, LGPL-2.1, Apache-2.0, AGPL-3.0, LGPL-3.0, GPL-3.0, MPL-2.0-no-copyleft-exception, CC-BY-SA-3.0, 0BSD, BSD-3-Clause
  1. /* S H _ S T A C K . C
  2. * BRL-CAD
  3. *
  4. * Copyright (C) 1986-2005 United States Government as represented by
  5. * the U.S. Army Research Laboratory.
  6. *
  7. * This library is free software; you can redistribute it and/or
  8. * modify it under the terms of the GNU Lesser General Public License
  9. * as published by the Free Software Foundation; either version 2 of
  10. * the License, or (at your option) any later version.
  11. *
  12. * This library is distributed in the hope that it will be useful, but
  13. * WITHOUT ANY WARRANTY; without even the implied warranty of
  14. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  15. * Library General Public License for more details.
  16. *
  17. * You should have received a copy of the GNU Lesser General Public
  18. * License along with this file; see the file named COPYING for more
  19. * information.
  20. */
  21. /** @file sh_stack.c
  22. * S T A C K . C
  23. *
  24. * Stack multiple material modules together
  25. *
  26. * Author -
  27. * Phillip Dykstra
  28. * Lee A. Butler
  29. *
  30. * Source -
  31. * SECAD/VLD Computing Consortium, Bldg 394
  32. * The U. S. Army Ballistic Research Laboratory
  33. * Aberdeen Proving Ground, Maryland 21005-5066
  34. *
  35. */
  36. #ifndef lint
  37. static const char RCSid[] = "@(#)$Header$ (BRL)";
  38. #endif
  39. #include "common.h"
  40. #include <stdio.h>
  41. #include <string.h>
  42. #include "machine.h"
  43. #include "vmath.h"
  44. #include "raytrace.h"
  45. #include "rtprivate.h"
  46. HIDDEN int stk_setup(register struct region *rp, struct bu_vls *matparm, char **dpp, struct mfuncs *mf_p, struct rt_i *rtip, struct mfuncs **headp), stk_render(struct application *ap, struct partition *pp, struct shadework *swp, char *dp);
  47. HIDDEN void stk_print(register struct region *rp, char *dp), stk_free(char *cp);
  48. HIDDEN int ext_setup(register struct region *rp, struct bu_vls *matparm, char **dpp, struct mfuncs *mf_p, struct rt_i *rtip, struct mfuncs **headp);
  49. struct mfuncs stk_mfuncs[] = {
  50. {MF_MAGIC, "stack", 0, 0, 0,
  51. stk_setup, stk_render, stk_print, stk_free},
  52. {MF_MAGIC, "extern", 0, 0, 0,
  53. ext_setup, stk_render, stk_print, stk_free},
  54. {0, (char *)0, 0, 0, 0,
  55. 0, 0, 0, 0}
  56. };
  57. struct stk_specific {
  58. struct mfuncs *mfuncs[16];
  59. char *udata[16];
  60. };
  61. #define STK_NULL ((struct stk_specific *)0)
  62. #define STK_O(m) offsetof(struct stk_specific, m)
  63. struct bu_structparse stk_parse[] = {
  64. {"", 0, (char *)0, 0, BU_STRUCTPARSE_FUNC_NULL }
  65. };
  66. /*
  67. * E X T _ S E T U P
  68. *
  69. * Returns 0 on failure, 1 on success.
  70. */
  71. HIDDEN int
  72. ext_setup(register struct region *rp, struct bu_vls *matparm, char **dpp, struct mfuncs *mf_p, struct rt_i *rtip, struct mfuncs **headp)
  73. /* parameter string */
  74. /* pointer to user data pointer */
  75. {
  76. struct bu_mapped_file *parameter_file;
  77. struct bu_vls parameter_data;
  78. char *filename;
  79. int status;
  80. RT_CHECK_RTI(rtip);
  81. BU_CK_VLS( matparm );
  82. RT_CK_REGION(rp);
  83. filename = bu_vls_addr(matparm);
  84. parameter_file = bu_open_mapped_file( filename, (char *)NULL );
  85. if (!parameter_file) {
  86. bu_log("cannot open external shader file \"%s\"\n", filename);
  87. bu_bomb("ext_setup()\n");
  88. }
  89. bu_vls_init(&parameter_data);
  90. bu_vls_strncpy( &parameter_data, (char *)parameter_file->buf,
  91. parameter_file->buflen );
  92. if (rdebug&RDEBUG_SHADE ) {
  93. bu_log("ext_setup(%s): {%s}\n",
  94. filename, bu_vls_addr(&parameter_data));
  95. }
  96. bu_close_mapped_file( parameter_file );
  97. status = stk_setup(rp, &parameter_data, dpp, mf_p, rtip, headp);
  98. bu_vls_free( &parameter_data );
  99. return status;
  100. }
  101. /*
  102. * S T K _ D O S E T U P
  103. */
  104. static int stk_dosetup(char *cp, struct region *rp, char **dpp, char **mpp, struct rt_i *rtip, struct mfuncs **headp)
  105. /* udata pointer address */
  106. /* mfuncs pointer address */
  107. {
  108. register struct mfuncs *mfp;
  109. #ifdef HAVE_DLOPEN
  110. register struct mfuncs *mfp_new;
  111. #endif
  112. struct bu_vls arg;
  113. char matname[32];
  114. int ret;
  115. int i;
  116. RT_CK_RTI(rtip);
  117. if(rdebug&RDEBUG_MATERIAL)
  118. bu_log( "...starting \"%s\"\n", cp );
  119. /* skip leading white space */
  120. while( *cp == ' ' || *cp == '\t' )
  121. cp++;
  122. for( i = 0; i < 31 && *cp != '\0'; i++, cp++ ) {
  123. if (*cp == ' ' || *cp == '\t' ) {
  124. matname[i++] = '\0';
  125. break;
  126. } else
  127. matname[i] = *cp;
  128. }
  129. matname[i] = '\0'; /* ensure null termination */
  130. #ifdef HAVE_DLOPEN
  131. retry:
  132. #endif
  133. for( mfp = *headp; mfp != MF_NULL; mfp = mfp->mf_forw ) {
  134. if (matname[0] != mfp->mf_name[0] ||
  135. strcmp( matname, mfp->mf_name ) != 0 )
  136. continue;
  137. goto found;
  138. }
  139. #ifdef HAVE_DLOPEN
  140. /* If we get here, then the shader wasn't found in the list of
  141. * compiled-in (or previously loaded) shaders. See if we can
  142. * dynamically load it.
  143. */
  144. bu_log("Shader \"%s\"... ", matname);
  145. if ((mfp_new = load_dynamic_shader(matname, strlen(matname)))) {
  146. mlib_add_shader(headp, mfp_new);
  147. goto retry;
  148. }
  149. #else
  150. bu_log("****** dynamic shader loading not available ******\n");
  151. #endif
  152. bu_log("stack_setup(%s): material not known\n",
  153. matname );
  154. ret = -1;
  155. goto out;
  156. found:
  157. *mpp = (char *)mfp;
  158. *dpp = (char *)0;
  159. bu_vls_init( &arg );
  160. if (*cp != '\0' )
  161. bu_vls_strcat( &arg, ++cp );
  162. if (rdebug&RDEBUG_MATERIAL)
  163. bu_log("calling %s with %s\n", mfp->mf_name, bu_vls_addr(&arg));
  164. if (mfp->mf_setup( rp, &arg, dpp, mfp, rtip, headp ) < 0 ) {
  165. /* Setup has failed */
  166. bu_vls_free( &arg );
  167. ret = -1; /* BAD */
  168. goto out;
  169. }
  170. bu_vls_free( &arg );
  171. ret = 0; /* OK */
  172. out:
  173. if (rdebug&RDEBUG_MATERIAL)
  174. bu_log( "...finished \"%s\", ret=%d\n", matname, ret );
  175. return ret;
  176. }
  177. /*
  178. * S T K _ S E T U P
  179. *
  180. * Returns 0 on failure, 1 on success.
  181. */
  182. HIDDEN int
  183. stk_setup(register struct region *rp, struct bu_vls *matparm, char **dpp, struct mfuncs *mf_p, struct rt_i *rtip, struct mfuncs **headp)
  184. /* parameter string */
  185. /* pointer to user data pointer */
  186. {
  187. register struct stk_specific *sp;
  188. char *cp, *start;
  189. int i;
  190. int inputs = 0;
  191. struct mfuncs *mfp;
  192. BU_CK_VLS( matparm );
  193. RT_CK_RTI(rtip);
  194. BU_GETSTRUCT( sp, stk_specific );
  195. *dpp = (char *)sp;
  196. /*bu_struct_parse( matparm, stk_parse, (char *)sp );*/
  197. if(rdebug&RDEBUG_MATERIAL || rdebug&RDEBUG_SHADE)
  198. bu_log( "stk_setup called with \"%s\"\n", bu_vls_addr(matparm) );
  199. i = 0;
  200. start = cp = bu_vls_addr(matparm);
  201. while( *cp != '\0' ) {
  202. if (*cp == ';' ) {
  203. *cp = '\0';
  204. if (i >= 16 ) {
  205. bu_log( "stk_setup: max levels exceeded\n" );
  206. return( 0 );
  207. }
  208. /* add one */
  209. if (stk_dosetup(start, rp, &sp->udata[i],
  210. (char **)&sp->mfuncs[i], rtip, headp) == 0 ) {
  211. inputs |= sp->mfuncs[i]->mf_inputs;
  212. i++;
  213. } else {
  214. /* XXX else clear entry? */
  215. bu_log("Problem in stack shader setup\n");
  216. }
  217. start = ++cp;
  218. } else {
  219. cp++;
  220. }
  221. }
  222. if (start != cp ) {
  223. if (i >= 16 ) {
  224. bu_log( "stk_setup: max levels exceeded\n" );
  225. return( 0 );
  226. }
  227. /* add one */
  228. if (stk_dosetup(start, rp, &sp->udata[i], (char **)&sp->mfuncs[i],
  229. rtip, headp ) == 0 ) {
  230. inputs |= sp->mfuncs[i]->mf_inputs;
  231. i++;
  232. } else {
  233. /* XXX else clear entry? */
  234. }
  235. }
  236. /* Request only those input bits needed by subordinate shaders */
  237. BU_GETSTRUCT( mfp, mfuncs );
  238. bcopy( (char *)rp->reg_mfuncs, (char *)mfp, sizeof(*mfp) );
  239. mfp->mf_inputs = inputs;
  240. rp->reg_mfuncs = (genptr_t)mfp;
  241. return( 1 );
  242. }
  243. /*
  244. * S T K _ R E N D E R
  245. *
  246. * Evaluate all of the rendering functions in the stack.
  247. *
  248. * Returns:
  249. * 0 stack processing aborted
  250. * 1 stack processed to completion
  251. */
  252. HIDDEN int
  253. stk_render(struct application *ap, struct partition *pp, struct shadework *swp, char *dp)
  254. {
  255. register struct stk_specific *sp =
  256. (struct stk_specific *)dp;
  257. int i;
  258. int ret_status;
  259. char tmp[128];
  260. for( i = 0; i < 16 && sp->mfuncs[i] != NULL; i++ ) {
  261. if (rdebug&RDEBUG_SHADE) {
  262. sprintf(tmp, "before stacked \"%s\" shader", sp->mfuncs[i]->mf_name);
  263. pr_shadework( tmp, swp );
  264. }
  265. /*
  266. * Every shader takes the shadework structure as its
  267. * input and updates it as the "output".
  268. */
  269. ret_status = sp->mfuncs[i]->mf_render( ap, pp, swp,
  270. sp->udata[i] );
  271. if ( ! ret_status ) return ret_status;
  272. }
  273. return(1);
  274. }
  275. /*
  276. * S T K _ P R I N T
  277. */
  278. HIDDEN void
  279. stk_print(register struct region *rp, char *dp)
  280. {
  281. register struct stk_specific *sp =
  282. (struct stk_specific *)dp;
  283. int i;
  284. bu_log("~~~~starting stack print\n");
  285. for( i = 0; i < 16 && sp->mfuncs[i] != NULL; i++ ) {
  286. bu_log("~~~~stack entry %d:\n", i);
  287. sp->mfuncs[i]->mf_print( rp, sp->udata[i] );
  288. }
  289. bu_log("~~~~ending stack print\n");
  290. }
  291. /*
  292. * S T K _ F R E E
  293. */
  294. HIDDEN void
  295. stk_free(char *cp)
  296. {
  297. register struct stk_specific *sp =
  298. (struct stk_specific *)cp;
  299. int i;
  300. for( i = 0; i < 16 && sp->mfuncs[i] != NULL; i++ ) {
  301. sp->mfuncs[i]->mf_free( sp->udata[i] );
  302. }
  303. bu_free( cp, "stk_specific" );
  304. }
  305. /*
  306. * Local Variables:
  307. * mode: C
  308. * tab-width: 8
  309. * c-basic-offset: 4
  310. * indent-tabs-mode: t
  311. * End:
  312. * ex: shiftwidth=4 tabstop=8
  313. */