If the data is constant, such as a random number lattice for Perlin noise functions, it can be stored in a static array that is built in the init shader and deleted, if necessary, in the exit shader.
static struct mystruct *mydata; DLLEXPORT void myshader_init( /* init shader */ miState *state, struct myshader *paras, miBoolean *inst_req) { mydata = mi_mem_allocate(...) ...initialize *mydata... return(miTRUE); } DLLEXPORT void myshader_exit( /* exit shader */ miState *state, struct myshader *paras) { mi_mem_release(mydata); return(miTRUE); } DLLEXPORT void myshader( /* main shader */ miState *state, struct myshader *paras) { ...read-only access to *mydata... return(miTRUE); }
This form of data storage is very simple, but can be used only if the data is constant for the current frame, and does not in any way depend on shader parameters or the shader instance. This means that the shader body may not modify the data because it is unpredictable in which order shaders are called. Worse, the shader may be called in multiple threads simultaneously, so writing to the data could become interleaved in ways that are very hard to reproduce and debug. Locking is not a solution because that would mean that shaders would have to "wait in line" to gain access to the data, which seriously degrades parallel performance.
Copyright © 1986-2010 by mental images GmbH