From 06daa03c5cd2d8aea6ee797923d2bbfdf500caef Mon Sep 17 00:00:00 2001 From: Antonio Gomes Date: Fri, 6 Jan 2023 23:54:04 -0300 Subject: [PATCH] rusticl: Implement spec for cl_khr_image2d_from_buffer Part-of: --- src/gallium/frontends/rusticl/api/device.rs | 2 +- src/gallium/frontends/rusticl/api/memory.rs | 28 ++++++++++++++++++++++++---- src/gallium/frontends/rusticl/core/device.rs | 16 +++++++++++++++- 3 files changed, 40 insertions(+), 6 deletions(-) diff --git a/src/gallium/frontends/rusticl/api/device.rs b/src/gallium/frontends/rusticl/api/device.rs index 3cc72a9..61a7a6d 100644 --- a/src/gallium/frontends/rusticl/api/device.rs +++ b/src/gallium/frontends/rusticl/api/device.rs @@ -80,7 +80,7 @@ impl CLInfo for cl_device_id { } CL_DEVICE_IMAGE_MAX_ARRAY_SIZE => cl_prop::(dev.image_array_size()), CL_DEVICE_IMAGE_MAX_BUFFER_SIZE => cl_prop::(dev.image_buffer_size()), - CL_DEVICE_IMAGE_PITCH_ALIGNMENT => cl_prop::(0), + CL_DEVICE_IMAGE_PITCH_ALIGNMENT => cl_prop::(dev.image_pitch_alignment()), CL_DEVICE_IMAGE_SUPPORT => cl_prop::(dev.image_supported()), CL_DEVICE_IMAGE2D_MAX_HEIGHT => cl_prop::(dev.image_2d_size()), CL_DEVICE_IMAGE2D_MAX_WIDTH => cl_prop::(dev.image_2d_size()), diff --git a/src/gallium/frontends/rusticl/api/memory.rs b/src/gallium/frontends/rusticl/api/memory.rs index f165942..e23012e 100644 --- a/src/gallium/frontends/rusticl/api/memory.rs +++ b/src/gallium/frontends/rusticl/api/memory.rs @@ -452,7 +452,10 @@ fn validate_image_desc( let p = p.get_arc()?; if !match desc.image_type { CL_MEM_OBJECT_IMAGE1D_BUFFER => p.is_buffer(), - CL_MEM_OBJECT_IMAGE2D => true, + CL_MEM_OBJECT_IMAGE2D => { + (p.is_buffer() && devs.iter().any(|d| d.image2d_from_buffer_supported())) + || p.mem_type == CL_MEM_OBJECT_IMAGE2D + } _ => false, } { return Err(CL_INVALID_OPERATION); @@ -478,12 +481,29 @@ fn validate_image_desc( // host_ptr is not NULL and image_slice_pitch = 0, image_slice_pitch is calculated as // image_row_pitch × image_height for a 2D image array or 3D image and image_row_pitch for a 1D // image array. If image_slice_pitch is not 0, it must be a multiple of the image_row_pitch. + let has_buf_parent = parent.as_ref().map_or(false, |p| p.is_buffer()); if host_ptr.is_null() { - if desc.image_row_pitch != 0 || desc.image_slice_pitch != 0 { + if (desc.image_row_pitch != 0 || desc.image_slice_pitch != 0) && !has_buf_parent { return Err(err); } - desc.image_row_pitch = desc.image_width * elem_size; - desc.image_slice_pitch = desc.image_row_pitch * desc.image_height; + + if desc.image_row_pitch == 0 { + desc.image_row_pitch = desc.image_width * elem_size; + } + if desc.image_slice_pitch == 0 { + desc.image_slice_pitch = desc.image_row_pitch * desc.image_height; + } + + if has_buf_parent { + let pitch_alignment = devs + .iter() + .map(|d| d.image_pitch_alignment()) + .max() + .unwrap() as usize; + if desc.image_row_pitch % (pitch_alignment * elem_size) != 0 { + return Err(err); + } + } } else { if desc.image_row_pitch == 0 { desc.image_row_pitch = desc.image_width * elem_size; diff --git a/src/gallium/frontends/rusticl/core/device.rs b/src/gallium/frontends/rusticl/core/device.rs index dfd6fc2..77c51b0 100644 --- a/src/gallium/frontends/rusticl/core/device.rs +++ b/src/gallium/frontends/rusticl/core/device.rs @@ -500,6 +500,10 @@ impl Device { if self.image_supported() { add_ext(1, 0, 0, "", "__opencl_c_images"); + if self.image2d_from_buffer_supported() { + add_ext(1, 0, 0, "cl_khr_image2d_from_buffer", ""); + } + if self.image_read_write_supported() { add_ext(1, 0, 0, "", "__opencl_c_read_write_images"); } @@ -610,8 +614,14 @@ impl Device { .param(pipe_cap::PIPE_CAP_MAX_TEXTURE_ARRAY_LAYERS) as usize } + pub fn image_pitch_alignment(&self) -> cl_uint { + self.screen + .param(pipe_cap::PIPE_CAP_LINEAR_IMAGE_PITCH_ALIGNMENT) as u32 + } + pub fn image_base_address_alignment(&self) -> cl_uint { - 0 + self.screen + .param(pipe_cap::PIPE_CAP_LINEAR_IMAGE_BASE_ADDRESS_ALIGNMENT) as u32 } pub fn image_buffer_size(&self) -> usize { @@ -623,6 +633,10 @@ impl Device { self.shader_param(pipe_shader_cap::PIPE_SHADER_CAP_MAX_SAMPLER_VIEWS) as cl_uint } + pub fn image2d_from_buffer_supported(&self) -> bool { + self.image_pitch_alignment() != 0 && self.image_base_address_alignment() != 0 + } + pub fn image_supported(&self) -> bool { // TODO check CL_DEVICE_IMAGE_SUPPORT reqs self.shader_param(pipe_shader_cap::PIPE_SHADER_CAP_MAX_SHADER_IMAGES) != 0 && -- 2.7.4