NVIDIA IndeX API nvidia_logo_transpbg.gif Up
nv::index::IRendering_kernel_program_parameters Class Referenceabstract

The interface class representing user-defined parameter buffers for user-programmable rendering kernel components. More...

#include <irendering_kernel_programs.h>

Inherits mi::base::Interface_declare< 0x82ad1cdf, ... >.

Public Member Functions

virtual mi::Uint32 get_nb_buffer_slots () const =0
 Returns the number of valid buffer slots available to assign user-defined data to. More...
 
virtual mi::Size get_max_buffer_size () const =0
 Returns the maximum size of an individual buffer assignable to an individual buffer slot. More...
 
virtual mi::Size get_array_offset_alignment () const =0
 Returns the alignment in bytes of array components in a single buffer assigned to a buffer slot. More...
 
virtual bool set_buffer_data (mi::Uint32 slot_idx, const void *data, mi::Size data_size)=0
 Assigns the buffer contents to a particular buffer slot. More...
 

Detailed Description

The interface class representing user-defined parameter buffers for user-programmable rendering kernel components.

User-defined parameter buffers allow the application to define custom input to IRendering_kernel_program instances. Such input can be utilized to implement custom rendering kernel programs independent of the input made available through the NVIDIA IndeX rendering kernel interfaces. For instance, an application is enabled to implement a specialized material shading method that is not pre-defined by any existing NVIDIA IndeX rendering properties. The required material parameters, unknown to the actual rendering system, are passed through this interface class to NVIDIA IndeX, which handles the distribution of such data to each rendering node and rendering device. The interface class acts as a scene attribute to scene elements enabled to utilize rendering kernel components (IRendering_kernel_program).

Each instance of this interface allows for a certain number of data buffers to be added. The buffer data is assigned to so called buffer slots. These buffer slots are a way to identify the actual buffers and access them in the rendering kernel programs, as shown in the following example code snippet of a volume sample program.

This example illustrates the input of clip-plane parameters on the application side:

struct Plane_data_struct
{
mi::math::Vector<mi::Float32, 4> plane_equation;
};
// Define two clip planes
Plane_data_struct planes[2];
// First clip plane
mi::math::Vector<mi::Float32, 3> clip_plane_0_normal = mi::math::Vector<mi::Float32, 3>(1.0f, 1.0f, -1.0f);
clip_plane_0_normal.normalize();
planes[0].plane_equation = mi::math::Vector<mi::Float32, 4>(clip_plane_0_normal, -11.0f);
// Second clip plane
mi::math::Vector<mi::Float32, 3> clip_plane_1_normal = mi::math::Vector<mi::Float32, 3>(-1.0f, 1.0f, 1.0f);
clip_plane_1_normal.normalize();
planes[1].plane_equation = mi::math::Vector<mi::Float32, 4>(clip_plane_1_normal, 10.0f);
// Add the two defined planes to the rendering kernel parameter buffers
kernel_param_buffers->set_buffer_data(CLIP_PLANE_PARAM_BUFFER_SLOT, planes, sizeof(Plane_data_struct) * 2);

This example illustrates how to access clip-plane information defined by the application in a rendering kernel program:

// Define the user-defined data structure
struct Plane_data_buffer
{
float4 plane_equation;
};
class Volume_sample_program
{
public:
// Define variables to bind the contents of the user-defined buffer to
const Plane_data_buffer* m_plane_array_buffer;
const Plane_data_buffer* m_plane_buffer_0;
const Plane_data_buffer* m_plane_buffer_1;
public:
void initialize()
{
// Bind the contents of the buffer slot 0 to the variable
m_plane_array_buffer = state.bind_parameter_buffer<Plane_data_buffer>(0);
// Bind the contents of the buffer slot 0 to the variable pointing to the first entry
m_plane_buffer_0 = state.bind_parameter_buffer<Plane_data_buffer>(0, 0 /*array offset*/);
// Bind the contents of the buffer slot 0 to the variable pointing to the second entry
m_plane_buffer_1 = state.bind_parameter_buffer<Plane_data_buffer>(0, 1 /*array offset*/);
}
...
int execute(
const Sample_info_self& sample_info,
Sample_output& sample_output)
{
const float dist_p_00 = dot(m_plane_array_buffer[0].plane_equation, make_float4(sample_info.sample_position, 1.0f));
const float dist_p_01 = dot(m_plane_array_buffer[1].plane_equation, make_float4(sample_info.sample_position, 1.0f));
#define NV_IDX_DEVICE_INLINE_MEMBER
A member method's qualifier macro.
Definition: xac_interface_standard_lib_doc.h:15
#define NV_IDX_VOLUME_SAMPLE_PROGRAM
An initializing macro of a volume sample program.
Definition: xac_interface_standard_lib_doc.h:23

or to access the same data through the separate entries:

const float dist_p_00 = dot(m_plane_buffer_0->plane_equation, make_float4(sample_info.sample_position, 1.0f));
const float dist_p_01 = dot(m_plane_buffer_1->plane_equation, make_float4(sample_info.sample_position, 1.0f));
...
};

As shown in the above example the association of data input through this interface class and the actual data at runtime happens through the buffer slot identifiers. Further, the example illustrates that a buffer slot can actually hold an array of structures (in this example an array of Plane_data_buffer instances). It is possible to access such arrays in a straightforward way through the array index operator or by binding the contents of the array to individual variables. The function to perform the binding (state.bind_parameter_buffer()) allows both use cases:

const T* bind_parameter_buffer(
unsigned buffer_slot,
unsigned buffer_slot_offset = 0u);

The buffer_slot_offset parameter allows to select a particular array element. The offset unit is the actual number of array elements to offset the binding.

It is important to note that the contents of the buffer data input through this interface must conform to certain rules to ensure data consistency between the host and device data. Especially, data alignment of buffer contents must be regarded. For example, certain vector data types require alignment to special boundaries inside structures: https://docs.nvidia.com/cuda/cuda-c-programming-guide/index.html#device-memory-accesses

Example for misaligned data between host and device:

struct wrong_alignment
{
float3 normal;
float4 color; // misaligned
};

In this example the 'color' entry of the structure is not correctly aligned to the struct. A float4 variable requires a 16 byte alignment. Such cases can be corrected by manually adding padding data:

struct correct_alignment
{
float3 normal;
char padding_data[4]; // align the next entry to a 16 byte boundary
float4 color;
};

Similarly, when storing multiple elements in an array of structures, the individual structures require alignment to a certain boundary. This required array offset alignment can be queried through this interface using the get_array_offset_alignment() method. In order to achieve correct structure alignment, padding data can be used:

struct array_element
{
float material_property_0;
float material_property_1;
float material_property_2;
char padding[4]; // pad structure to multiple of 16 bytes
};

Member Function Documentation

 get_array_offset_alignment()

virtual mi::Size nv::index::IRendering_kernel_program_parameters::get_array_offset_alignment ( ) const
pure virtual

Returns the alignment in bytes of array components in a single buffer assigned to a buffer slot.

Returns
Alignment in bytes of array components in a single buffer.

 get_max_buffer_size()

virtual mi::Size nv::index::IRendering_kernel_program_parameters::get_max_buffer_size ( ) const
pure virtual

Returns the maximum size of an individual buffer assignable to an individual buffer slot.

Returns
Maximum size of an individual buffer assignable to a buffer slot.

 get_nb_buffer_slots()

virtual mi::Uint32 nv::index::IRendering_kernel_program_parameters::get_nb_buffer_slots ( ) const
pure virtual

Returns the number of valid buffer slots available to assign user-defined data to.

Returns
Returns the number of valid buffer slots available.

 set_buffer_data()

virtual bool nv::index::IRendering_kernel_program_parameters::set_buffer_data ( mi::Uint32  slot_idx,
const void *  data,
mi::Size  data_size 
)
pure virtual

Assigns the buffer contents to a particular buffer slot.

Note
An instance of the IRendering_kernel_program_parameters class does not take ownership of the user data passed through the set_buffer_data() method. The buffer data is copied for internal use.
Parameters
[in]slot_idxThe buffer slot index to assign the buffer data to.
[in]dataA raw pointer to the buffer data to assign to the buffer slot.
[in]data_sizeThe size in bytes of the buffer data to assign to the buffer slot.
Returns
True on successful input of the user buffer data to the specified buffer slot, false otherwise.

The documentation for this class was generated from the following file: