[PATCH i-g-t 1/1] lib/intel_compute: Allow the user to override input and output addresses

Zbigniew Kempczyński zbigniew.kempczynski at intel.com
Fri Apr 18 08:56:47 UTC 2025


On Thu, Apr 17, 2025 at 05:40:23PM +0200, Francois Dugast wrote:
> The user can specify custom GPU addresses to be used for the input and
> output arrays, otherwise default values will be used. If a compatible
> VM is also provided in user_execenv, the user can even create its own
> arrays and pass their addresses in user_execenv, for example with SVM.
> 
> Signed-off-by: Francois Dugast <francois.dugast at intel.com>

LGTM. I wondered how custom input/output data are not asserting but
I've recall that you've introduced skip_results_check in user_execenv.

Let's wait for CI.

But from me:

Reviewed-by: Zbigniew Kempczyński <zbigniew.kempczynski at intel.com>

--
Zbigniew

> ---
>  lib/intel_compute.c | 128 +++++++++++++++++++++++++++++++-------------
>  lib/intel_compute.h |   4 ++
>  2 files changed, 95 insertions(+), 37 deletions(-)
> 
> diff --git a/lib/intel_compute.c b/lib/intel_compute.c
> index 2d21e9799..070bc0d2d 100644
> --- a/lib/intel_compute.c
> +++ b/lib/intel_compute.c
> @@ -743,6 +743,8 @@ static void compute_exec(int fd, const unsigned char *kernel,
>  	};
>  	struct bo_execenv execenv;
>  	float *input_data, *output_data;
> +	uint64_t bind_input_addr = (user && user->input_addr) ? user->input_addr : ADDR_INPUT;
> +	uint64_t bind_output_addr = (user && user->output_addr) ? user->output_addr : ADDR_OUTPUT;
>  	uint16_t devid = intel_get_drm_devid(fd);
>  
>  	bo_execenv_create(fd, &execenv, eci, user);
> @@ -756,16 +758,24 @@ static void compute_exec(int fd, const unsigned char *kernel,
>  
>  	memcpy(bo_dict[0].data, kernel, size);
>  	create_dynamic_state(bo_dict[1].data, OFFSET_KERNEL);
> -	create_surface_state(bo_dict[2].data, ADDR_INPUT, ADDR_OUTPUT);
> -	create_indirect_data(bo_dict[3].data, ADDR_INPUT, ADDR_OUTPUT,
> +	create_surface_state(bo_dict[2].data, bind_input_addr, bind_output_addr);
> +	create_indirect_data(bo_dict[3].data, bind_input_addr, bind_output_addr,
>  			     IS_DG1(devid) ? 0x200 : 0x40, execenv.array_size);
>  
> -	input_data = (float *) bo_dict[4].data;
> -	output_data = (float *) bo_dict[5].data;
> -	srand(time(NULL));
> +	if (user && user->input_addr) {
> +		input_data = from_user_pointer(user->input_addr);
> +	} else {
> +		input_data = (float *) bo_dict[4].data;
> +		srand(time(NULL));
>  
> -	for (int i = 0; i < execenv.array_size; i++)
> -		input_data[i] = rand() / (float)RAND_MAX;
> +		for (int i = 0; i < execenv.array_size; i++)
> +			input_data[i] = rand() / (float)RAND_MAX;
> +	}
> +
> +	if (user && user->output_addr)
> +		output_data = from_user_pointer(user->output_addr);
> +	else
> +		output_data = (float *) bo_dict[5].data;
>  
>  	if (IS_DG1(devid))
>  		dg1_compute_exec_compute(bo_dict[6].data,
> @@ -1033,6 +1043,8 @@ static void xehp_compute_exec(int fd, const unsigned char *kernel,
>  	};
>  	struct bo_execenv execenv;
>  	float *input_data, *output_data;
> +	uint64_t bind_input_addr = (user && user->input_addr) ? user->input_addr : ADDR_INPUT;
> +	uint64_t bind_output_addr = (user && user->output_addr) ? user->output_addr : ADDR_OUTPUT;
>  
>  	bo_execenv_create(fd, &execenv, eci, user);
>  
> @@ -1045,16 +1057,25 @@ static void xehp_compute_exec(int fd, const unsigned char *kernel,
>  
>  	memcpy(bo_dict[0].data, kernel, size);
>  	create_dynamic_state(bo_dict[1].data, OFFSET_KERNEL);
> -	xehp_create_surface_state(bo_dict[2].data, ADDR_INPUT, ADDR_OUTPUT);
> -	xehp_create_indirect_data(bo_dict[3].data, ADDR_INPUT, ADDR_OUTPUT, execenv.array_size);
> -	xehp_create_surface_state(bo_dict[7].data, ADDR_INPUT, ADDR_OUTPUT);
> +	xehp_create_surface_state(bo_dict[2].data, bind_input_addr, bind_output_addr);
> +	xehp_create_indirect_data(bo_dict[3].data, bind_input_addr, bind_output_addr,
> +				  execenv.array_size);
> +	xehp_create_surface_state(bo_dict[7].data, bind_input_addr, bind_output_addr);
>  
> -	input_data = (float *) bo_dict[4].data;
> -	output_data = (float *) bo_dict[5].data;
> -	srand(time(NULL));
> +	if (user && user->input_addr) {
> +		input_data = from_user_pointer(user->input_addr);
> +	} else {
> +		input_data = (float *) bo_dict[4].data;
> +		srand(time(NULL));
>  
> -	for (int i = 0; i < execenv.array_size; i++)
> -		input_data[i] = rand() / (float)RAND_MAX;
> +		for (int i = 0; i < execenv.array_size; i++)
> +			input_data[i] = rand() / (float)RAND_MAX;
> +	}
> +
> +	if (user && user->output_addr)
> +		output_data = from_user_pointer(user->output_addr);
> +	else
> +		output_data = (float *) bo_dict[5].data;
>  
>  	xehp_compute_exec_compute(bo_dict[8].data,
>  				  ADDR_GENERAL_STATE_BASE,
> @@ -1250,6 +1271,8 @@ static void xehpc_compute_exec(int fd, const unsigned char *kernel,
>  	};
>  	struct bo_execenv execenv;
>  	float *input_data, *output_data;
> +	uint64_t bind_input_addr = (user && user->input_addr) ? user->input_addr : ADDR_INPUT;
> +	uint64_t bind_output_addr = (user && user->output_addr) ? user->output_addr : ADDR_OUTPUT;
>  
>  	bo_execenv_create(fd, &execenv, eci, user);
>  
> @@ -1261,14 +1284,23 @@ static void xehpc_compute_exec(int fd, const unsigned char *kernel,
>  	bo_execenv_bind(&execenv, bo_dict, XEHPC_BO_DICT_ENTRIES);
>  
>  	memcpy(bo_dict[0].data, kernel, size);
> -	xehpc_create_indirect_data(bo_dict[1].data, ADDR_INPUT, ADDR_OUTPUT, execenv.array_size);
> +	xehpc_create_indirect_data(bo_dict[1].data, bind_input_addr, bind_output_addr,
> +				   execenv.array_size);
>  
> -	input_data = (float *) bo_dict[2].data;
> -	output_data = (float *) bo_dict[3].data;
> -	srand(time(NULL));
> +	if (user && user->input_addr) {
> +		input_data = from_user_pointer(user->input_addr);
> +	} else {
> +		input_data = (float *) bo_dict[2].data;
> +		srand(time(NULL));
>  
> -	for (int i = 0; i < execenv.array_size; i++)
> -		input_data[i] = rand() / (float)RAND_MAX;
> +		for (int i = 0; i < execenv.array_size; i++)
> +			input_data[i] = rand() / (float)RAND_MAX;
> +	}
> +
> +	if (user && user->output_addr)
> +		output_data = from_user_pointer(user->output_addr);
> +	else
> +		output_data = (float *) bo_dict[3].data;
>  
>  	xehpc_compute_exec_compute(bo_dict[5].data,
>  				   ADDR_GENERAL_STATE_BASE,
> @@ -1643,6 +1675,8 @@ static void xelpg_compute_exec(int fd, const unsigned char *kernel,
>  
>  	struct bo_execenv execenv;
>  	float *input_data, *output_data;
> +	uint64_t bind_input_addr = (user && user->input_addr) ? user->input_addr : ADDR_INPUT;
> +	uint64_t bind_output_addr = (user && user->output_addr) ? user->output_addr : ADDR_OUTPUT;
>  
>  	bo_execenv_create(fd, &execenv, eci, user);
>  
> @@ -1656,16 +1690,25 @@ static void xelpg_compute_exec(int fd, const unsigned char *kernel,
>  	memcpy(bo_dict[0].data, kernel, size);
>  
>  	create_dynamic_state(bo_dict[1].data, OFFSET_KERNEL);
> -	xehp_create_surface_state(bo_dict[2].data, ADDR_INPUT, ADDR_OUTPUT);
> -	xelpg_create_indirect_data(bo_dict[3].data, ADDR_INPUT, ADDR_OUTPUT, execenv.array_size);
> -	xehp_create_surface_state(bo_dict[7].data, ADDR_INPUT, ADDR_OUTPUT);
> +	xehp_create_surface_state(bo_dict[2].data, bind_input_addr, bind_output_addr);
> +	xelpg_create_indirect_data(bo_dict[3].data, bind_input_addr, bind_output_addr,
> +				   execenv.array_size);
> +	xehp_create_surface_state(bo_dict[7].data, bind_input_addr, bind_output_addr);
>  
> -	input_data = (float *) bo_dict[4].data;
> -	output_data = (float *) bo_dict[5].data;
> -	srand(time(NULL));
> +	if (user && user->input_addr) {
> +		input_data = from_user_pointer(user->input_addr);
> +	} else {
> +		input_data = (float *) bo_dict[4].data;
> +		srand(time(NULL));
>  
> -	for (int i = 0; i < execenv.array_size; i++)
> -		input_data[i] = rand() / (float)RAND_MAX;
> +		for (int i = 0; i < execenv.array_size; i++)
> +			input_data[i] = rand() / (float)RAND_MAX;
> +	}
> +
> +	if (user && user->output_addr)
> +		output_data = from_user_pointer(user->output_addr);
> +	else
> +		output_data = (float *) bo_dict[5].data;
>  
>  	xelpg_compute_exec_compute(bo_dict[8].data,
>  				   ADDR_GENERAL_STATE_BASE,
> @@ -1740,6 +1783,8 @@ static void xe2lpg_compute_exec(int fd, const unsigned char *kernel,
>  
>  	struct bo_execenv execenv;
>  	float *input_data, *output_data;
> +	uint64_t bind_input_addr = (user && user->input_addr) ? user->input_addr : ADDR_INPUT;
> +	uint64_t bind_output_addr = (user && user->output_addr) ? user->output_addr : ADDR_OUTPUT;
>  
>  	bo_execenv_create(fd, &execenv, eci, user);
>  
> @@ -1752,16 +1797,25 @@ static void xe2lpg_compute_exec(int fd, const unsigned char *kernel,
>  
>  	memcpy(bo_dict[0].data, kernel, size);
>  	create_dynamic_state(bo_dict[1].data, OFFSET_KERNEL);
> -	xehp_create_surface_state(bo_dict[2].data, ADDR_INPUT, ADDR_OUTPUT);
> -	xelpg_create_indirect_data(bo_dict[3].data, ADDR_INPUT, ADDR_OUTPUT, execenv.array_size);
> -	xehp_create_surface_state(bo_dict[7].data, ADDR_INPUT, ADDR_OUTPUT);
> +	xehp_create_surface_state(bo_dict[2].data, bind_input_addr, bind_output_addr);
> +	xelpg_create_indirect_data(bo_dict[3].data, bind_input_addr, bind_output_addr,
> +				   execenv.array_size);
> +	xehp_create_surface_state(bo_dict[7].data, bind_input_addr, bind_output_addr);
>  
> -	input_data = (float *) bo_dict[4].data;
> -	output_data = (float *) bo_dict[5].data;
> -	srand(time(NULL));
> +	if (user && user->input_addr) {
> +		input_data = from_user_pointer(user->input_addr);
> +	} else {
> +		input_data = (float *) bo_dict[4].data;
> +		srand(time(NULL));
>  
> -	for (int i = 0; i < execenv.array_size; i++)
> -		input_data[i] = rand() / (float)RAND_MAX;
> +		for (int i = 0; i < execenv.array_size; i++)
> +			input_data[i] = rand() / (float)RAND_MAX;
> +	}
> +
> +	if (user && user->output_addr)
> +		output_data = from_user_pointer(user->output_addr);
> +	else
> +		output_data = (float *) bo_dict[5].data;
>  
>  	xe2lpg_compute_exec_compute(bo_dict[8].data,
>  				    ADDR_GENERAL_STATE_BASE,
> diff --git a/lib/intel_compute.h b/lib/intel_compute.h
> index a79c3172c..f0d1750cc 100644
> --- a/lib/intel_compute.h
> +++ b/lib/intel_compute.h
> @@ -59,6 +59,10 @@ struct user_execenv {
>  	bool skip_results_check;
>  	/** @array_size: size of input and output arrays */
>  	uint32_t array_size;
> +	/** @input_addr: override default address of the input array if provided */
> +	uint64_t input_addr;
> +	/** @output_addr: override default address of the output array if provided */
> +	uint64_t output_addr;
>  };
>  
>  extern const struct intel_compute_kernels intel_compute_square_kernels[];
> -- 
> 2.43.0
> 


More information about the igt-dev mailing list