[Beignet] [PATCH] re-enable userptr with fix: CPU access after GPU finishes the rendering

Zhigang Gong zhigang.gong at linux.intel.com
Tue Nov 18 20:56:02 PST 2014


This patch LGTM, just pushed, thanks.

On Tue, Nov 18, 2014 at 04:28:29PM +0800, Guo Yejun wrote:
> 1. the wait logic is integrated into function cl_mem_map/unmap_auto
> 2. use cl_mem_map/unmap_auto for userptr inside clEnqueueRead/WriteBuffer
> 3. do not use cl_buffer_subdata for userptr, use cl_mem_map/memcpy instead
> 
> Signed-off-by: Guo Yejun <yejun.guo at intel.com>
> ---
>  CMakeLists.txt   | 13 ++++++-------
>  src/cl_enqueue.c | 32 +++++++++++++++++++++++++++-----
>  src/cl_mem.c     | 11 ++++++++---
>  3 files changed, 41 insertions(+), 15 deletions(-)
> 
> diff --git a/CMakeLists.txt b/CMakeLists.txt
> index 3c68187..b14de96 100644
> --- a/CMakeLists.txt
> +++ b/CMakeLists.txt
> @@ -121,13 +121,12 @@ IF(DRM_INTEL_FOUND)
>    INCLUDE_DIRECTORIES(${DRM_INTEL_INCLUDE_DIRS})
>    MESSAGE(STATUS "Looking for DRM Intel - found at ${DRM_INTEL_PREFIX} ${DRM_INTEL_VERSION}")
>    #userptr support starts from 2.4.57, but 2.4.58 is the actual stable release
> -  #FIXME userptr has randome fail for some cases, need further investigating.
> -  #IF(DRM_INTEL_VERSION VERSION_GREATER 2.4.57)
> -  #  MESSAGE(STATUS "Enable userptr support")
> -  #  SET(DRM_INTEL_USERPTR "enable")
> -  #ELSE(DRM_INTEL_VERSION VERSION_GREATER 2.4.57)
> -  #  MESSAGE(STATUS "Disable userptr support")
> -  #ENDIF(DRM_INTEL_VERSION VERSION_GREATER 2.4.57)
> +  IF(DRM_INTEL_VERSION VERSION_GREATER 2.4.57)
> +    MESSAGE(STATUS "Enable userptr support")
> +    SET(DRM_INTEL_USERPTR "enable")
> +  ELSE(DRM_INTEL_VERSION VERSION_GREATER 2.4.57)
> +    MESSAGE(STATUS "Disable userptr support")
> +  ENDIF(DRM_INTEL_VERSION VERSION_GREATER 2.4.57)
>  ELSE(DRM_INTEL_FOUND)
>    MESSAGE(FATAL_ERROR "Looking for DRM Intel (>= 2.4.52) - not found")
>  ENDIF(DRM_INTEL_FOUND)
> diff --git a/src/cl_enqueue.c b/src/cl_enqueue.c
> index 5798e20..d51592c 100644
> --- a/src/cl_enqueue.c
> +++ b/src/cl_enqueue.c
> @@ -40,8 +40,15 @@ cl_int cl_enqueue_read_buffer(enqueue_data* data)
>      if (cl_buffer_get_subdata(mem->bo, data->offset + buffer->sub_offset,
>  			       data->size, data->ptr) != 0)
>        err = CL_MAP_FAILURE;
> -  } else
> -    memcpy(data->ptr, (char*)mem->host_ptr + data->offset + buffer->sub_offset, data->size);
> +  } else {
> +    void* src_ptr = cl_mem_map_auto(mem, 0);
> +    if (src_ptr == NULL)
> +      err = CL_MAP_FAILURE;
> +    else {
> +      memcpy(data->ptr, (char*)src_ptr + data->offset + buffer->sub_offset, data->size);
> +      cl_mem_unmap_auto(mem);
> +    }
> +  }
>    return err;
>  }
>  
> @@ -99,13 +106,28 @@ error:
>  
>  cl_int cl_enqueue_write_buffer(enqueue_data *data)
>  {
> +  cl_int err = CL_SUCCESS;
>    cl_mem mem = data->mem_obj;
>    assert(mem->type == CL_MEM_BUFFER_TYPE ||
>           mem->type == CL_MEM_SUBBUFFER_TYPE);
>    struct _cl_mem_buffer* buffer = (struct _cl_mem_buffer*)mem;
>  
> -  return cl_buffer_subdata(mem->bo, data->offset + buffer->sub_offset,
> -			   data->size, data->const_ptr);
> +  if (mem->is_userptr) {
> +    void* dst_ptr = cl_mem_map_auto(mem, 1);
> +    if (dst_ptr == NULL)
> +      err = CL_MAP_FAILURE;
> +    else {
> +      memcpy((char*)dst_ptr + data->offset + buffer->sub_offset, data->const_ptr, data->size);
> +      cl_mem_unmap_auto(mem);
> +    }
> +  }
> +  else {
> +    if (cl_buffer_subdata(mem->bo, data->offset + buffer->sub_offset,
> +			   data->size, data->const_ptr) != 0)
> +      err = CL_MAP_FAILURE;
> +  }
> +
> +  return err;
>  }
>  
>  cl_int cl_enqueue_write_buffer_rect(enqueue_data *data)
> @@ -240,7 +262,7 @@ cl_int cl_enqueue_map_buffer(enqueue_data *data)
>    struct _cl_mem_buffer* buffer = (struct _cl_mem_buffer*)mem;
>  
>    if (mem->is_userptr)
> -    ptr = mem->host_ptr;
> +    ptr = cl_mem_map_auto(mem, data->write_map ? 1 : 0);
>    else {
>      if(data->unsync_map == 1)
>        //because using unsync map in clEnqueueMapBuffer, so force use map_gtt here
> diff --git a/src/cl_mem.c b/src/cl_mem.c
> index 0fbd304..65f299f 100644
> --- a/src/cl_mem.c
> +++ b/src/cl_mem.c
> @@ -1818,8 +1818,13 @@ cl_mem_map_auto(cl_mem mem, int write)
>  {
>    if (IS_IMAGE(mem) && cl_mem_image(mem)->tiling != CL_NO_TILE)
>      return cl_mem_map_gtt(mem);
> -  else
> -    return cl_mem_map(mem, write);
> +  else {
> +    if (mem->is_userptr) {
> +      cl_buffer_wait_rendering(mem->bo);
> +      return mem->host_ptr;
> +    }else
> +      return cl_mem_map(mem, write);
> +  }
>  }
>  
>  LOCAL cl_int
> @@ -1829,7 +1834,7 @@ cl_mem_unmap_auto(cl_mem mem)
>      cl_buffer_unmap_gtt(mem->bo);
>      mem->mapped_gtt = 0;
>    }
> -  else
> +  else if (!mem->is_userptr)
>      cl_buffer_unmap(mem->bo);
>    return CL_SUCCESS;
>  }
> -- 
> 1.9.1
> 
> _______________________________________________
> Beignet mailing list
> Beignet at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/beignet


More information about the Beignet mailing list