Array program variables

In looking through the OptiX API reference documentation, I found that there is a function to set the value of a program variable to be an array of variables (e.g., for an array of floats - rtVariableSet1fv). So I am successfully able to set the variable on the host side using the following:

RTvariable dummy_RTvariable;
float dummy[5] = {0, 1, 2, 3, 4};

rtGeometryInstanceDeclareVariable( instance, "dummy", &dummy_RTvariable );
rtVariableSet1fv( dummy_RTvariable, dummy );

All of this compiles just fine. However, I am not able to find any documentation on how to use the variable on the device side. If I try to declare the variable as ‘float’ and then try to index it as an array, it obviously doesn’t compile:

rtDeclareVariable(float, dummy,,);

RT_PROGRAM void closest_hit(){
   rtPrintf("rho = %f\n",dummy[0]);

If I try to declare the variable as a float*, I get a runtime error when OptiX tries to compile the context:

rtDeclareVariable(float*, dummy,,);

RT_PROGRAM void closest_hit(){
   rtPrintf("rho = %f\n",dummy[0]);

OptiX Error: Invalid context (Details: Function “RTresult _rtContextCompile(RTcontext)” caught exception: Validation error: Variable “dummy” assigned type float. Should be user data.

Can somebody please point me to any documentation or examples for the corresponding code for rtVariableSet1fv on the device side?

That’s not how it works.

Both rtVariableSet1f() and rtVariableSet1fv() set exactly one float. Just the host side arguments are different. rtVariableSet1f() does it with a single float argument, rtVariableSet1fv() takes a pointer to float data, just that in this case the host side source “array” doesn’t need to be longer than one entry because only the first float is read.
The descriptions make more sense for the vector types (not arrays!) like float2, float3, and float4.

Please read on in the OptiX API Reference and look at the descriptions of RTresult RTAPI rtVariableSet1f ( RTvariable v, float f1 ) which explains this in more detail.

If you need arrays of any element type, including user defined structures, that’s always done with rtBuffer variables.

For example a 1D array of floats would be declared on device side as
rtBuffer myArray;
or more explicitly
rtBuffer<float, 1> myArray;

Note that the only legal way to index into any buffer is with operator which gives you access to exactly one element in that buffer, whatever element type. You must not use any pointer arithmetic on these buffers! (See #define rtBuffer device optix::buffer in the OptiX API Reference.)

Check out the OptiX examples for many other rtBuffer cases. There is no example without them, because they are the only way to get data back from OptiX.

If you’re new to OptiX, here’s my recommendation how to start learning the API: