TIOVX User Guide
vx_tutorial_graph_user_kernel.c File Reference
#include <stdio.h>
#include <VX/vx.h>
#include <TI/tivx.h>
#include <utility.h>
#include <ch03_graph/phase_rgb_user_kernel.h>

Go to the source code of this file.

Macros

#define IN_FILE_NAME   "${VX_TEST_DATA_PATH}/vx_tutorial_graph_image_gradients_phase_out.bmp"
 Input file name.
 
#define OUT_USER_KERNEL_FILE_NAME   "${VX_TEST_DATA_PATH}/vx_tutorial_graph_user_kernel_out.bmp"
 Output file name when tutorial is run with user kernel.
 
#define OUT_TARGET_KERNEL_FILE_NAME   "${VX_TEST_DATA_PATH}/vx_tutorial_graph_target_kernel_out.bmp"
 Output file name when tutorial is run with target kernel.
 

Functions

void vx_tutorial_graph_user_kernel (vx_bool add_as_target_kernel)
 Tutorial Entry Point. More...
 

Detailed Description

Show example usage of developing and invoking a user kernel

OpenVX allows users to define their own nodes called user kernels and provides an API to implement and invoke these user kernels. Once defined and implemented, user kernels can be added as any other node in an OpenVX graph

OpenVX user kernels need to run on the "HOST" CPU, i.e CPU where OpenVX APIs are invoked. This can be limiting for users who want to exploit performnance of specialized targets, like DSP, to execute their own functions. For this purpose, TIOVX specifies an API to define and implement "target kernels" . Like user kernels, once a target kernel is defined and implemented on a target (ex, DSP), it can be invoked as a normal node in an OpenVX graph using standard OpenVX APIs.

Most of the host side logic remains same for both user kernel and target kernel. For target kernel, additional target specific implementation is required on the required on target.

In this tutorial we learn below concepts,

  • Firstly, implement an OpenVX user kernel on HOST CPU
  • Invoke it as a single node OpenVX graph to test the user kernel in standalone mode
  • Next, implement target kernel on DSP for the same user kernel function
  • Modify the HOST side logic to use target kernel instead of user kernel
  • Invoke the same single node graph but this time with the target kernel

The custom kernel (user or target) we define in this tutorial does the below,

  • Take 16b signed phase image as input
  • Generate a 24b RGB image with different colors representing different phase values

NOTE: Make sure to run vx_tutorial_graph_image_gradients.c before running this tutorial, since output file from vx_tutorial_graph_image_gradients.c is used as input by this tutorial

Implementing a User Kernel
Implementing a Target Kernel on C66x DSP
  • For target kernel, there are two parts to the implementation, HOST side implementation and target side implementation
  • Target side implementation
  • HOST side implementation

    • Follow comments in file phase_rgb_user_kernel.c to understand how to implement the HOST side portion of target kernel
    • Follow comments in the function vx_tutorial_graph_user_kernel() to understand how to register the implemented target kernel and invoke it as a user graph.

    NOTE:
    The implementation on HOST side for user kernel and target kernel is largely the same. Any difference in implementation between user kernel and target kernel is shown by using using boolen variable 'add_as_target_kernel'.

    • When 'add_as_target_kernel' is 'vx_false_e', it is the implementation for user kernel.
    • When 'add_as_target_kernel' is 'vx_true_e', it is the implementation for target kernel.

Include below file to use the HOST callable interface for the user/target kernel

Definition in file vx_tutorial_graph_user_kernel.c.

Function Documentation

◆ vx_tutorial_graph_user_kernel()

void vx_tutorial_graph_user_kernel ( vx_bool  add_as_target_kernel)

Tutorial Entry Point.

Parameters
add_as_target_kernel[in] 'vx_false_e', run this tutorial with custom kernel running as user kernel
'vx_true_e', run this tutorial with custom kernel running as target kernel















- Define OpenVX object references required to invoke the user/target kernel

We need an OpenVX context, a graph to execute the node, a node to invoke the user target/kernel, and input/output image for the node.

/
vx_context context;
vx_image in_image = NULL;
vx_image out_image = NULL;
vx_node node = NULL;
vx_graph graph = NULL;



























- Specify the output file name

In order to compare and confirm that the user kernel and target kernel generate the same output we specify a different output file for user and target kernel

/
char *out_file = OUT_USER_KERNEL_FILE_NAME;
if(add_as_target_kernel)
{
}

























- Create OpenVX context

/
context = vxCreateContext();























- Register user or target kernel into the OpenVX context

This is required so that the user kernel or target can be invoked as any other node within an OpenVX graph. 'add_as_target_kernel' is used specify whether to register kernel as user kernel or target kernel.

This function is implemented in phase_rgb_user_kernel.c

Rest of the implementation post this is same for both user kernel and target kernel.

/
status = phase_rgb_user_kernel_add(context, add_as_target_kernel);
if(status!=(vx_status)VX_SUCCESS)
{
printf(" vx_tutorial_graph_user_kernel: ERROR: unable to add user kernel !!!\n");
}





















- Create input image and load input data into it

A name is given to the input image object via vxSetReferenceName. Image attributes are shown for informative purpose and width x height queried for later use.



















- Create output image

Output image dimensions as same as input image.

/
out_image = vxCreateImage(context, width, height, (vx_df_image)VX_DF_IMAGE_RGB);
vxSetReferenceName((vx_reference)out_image, "OUTPUT");

















- Create a graph object to execute the user/target kernel node

/
graph = vxCreateGraph(context);















- Create a node for the registered user/target kernel and insert into the graph

This function is implemented in phase_rgb_user_kernel.c

/
node = phase_rgb_user_kernel_node(graph, in_image, out_image);













- Verify the graph using standard OpenVX API


export graph to dot file, which can be coverted to jpg using dot tool
/
tivxExportGraphToDot(graph, ".", "vx_tutorial_graph_user_kernel");









- Excute the graph using standard OpenVX APIs

Ouptut image is saved to specified output file.

/
if(status==(vx_status)VX_SUCCESS)
{
printf(" Executing graph ...\n");
vxWaitGraph(graph);
printf(" Executing graph ... Done !!!\n");
printf(" Saving to file %s ...\n", out_file);
tivx_utils_save_vximage_to_bmpfile(out_file, out_image);
}







- Release image, node, graph objects

/
vxReleaseImage(&in_image);
vxReleaseImage(&out_image);





- Unregister user/kernel from the context

This function is implemented in phase_rgb_user_kernel.c



- Finally release the OpenVX context

/
vxReleaseContext(&context);

Definition at line 151 of file vx_tutorial_graph_user_kernel.c.