123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153 |
- /* StarPU --- Runtime system for heterogeneous multicore architectures.
- *
- * Copyright (C) 2011-2013 Inria
- * Copyright (C) 2012,2017 CNRS
- * Copyright (C) 2010-2011,2013, 2018 Université de Bordeaux
- *
- * StarPU is free software; you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License as published by
- * the Free Software Foundation; either version 2.1 of the License, or (at
- * your option) any later version.
- *
- * StarPU is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- *
- * See the GNU Lesser General Public License in COPYING.LGPL for more details.
- */
- #include "socl.h"
- static void release_callback_memobject(void * e)
- {
- cl_mem mem = (cl_mem)e;
- /* Release references */
- gc_entity_unstore(&mem->context);
- //Delete this mem_object from the mem_object list
- mem_object_release(mem);
- /* Destruct object */
- starpu_data_unregister_submit(mem->handle);
- if (!(mem->flags & CL_MEM_USE_HOST_PTR))
- free(mem->ptr);
- }
- /**
- * \brief Create a buffer
- *
- * A buffer has always an allocated region in host memory. If CL_MEM_USE_HOST_PTR
- * is set, we use memory pointed by host_ptr, otherwise some host memory is
- * allocated.
- *
- * If CL_MEM_USE_HOST_PTR or CL_MEM_ALLOC_HOST_PTR are set, memory pointed by host_ptr
- * is not coherent. To enforce coherency, you have to map the buffer (clEnqueueMapBuffer).
- *
- * If CL_MEM_COPY_HOST_PTR is set, the buffer will be duplicated in host memory. You
- * should avoid it.
- *
- */
- CL_API_SUFFIX__VERSION_1_0
- CL_API_ENTRY cl_mem CL_API_CALL
- soclCreateBuffer(cl_context context,
- cl_mem_flags flags,
- size_t size,
- void * host_ptr,
- cl_int * errcode_ret)
- {
- cl_mem mem;
- if (errcode_ret != NULL)
- *errcode_ret = CL_SUCCESS;
- //Check flags
- if (((flags & CL_MEM_READ_ONLY) && (flags & CL_MEM_WRITE_ONLY))
- || ((flags & CL_MEM_READ_WRITE) && (flags & CL_MEM_READ_ONLY))
- || ((flags & CL_MEM_READ_WRITE) && (flags & CL_MEM_WRITE_ONLY))
- || ((flags & CL_MEM_USE_HOST_PTR) && (flags & CL_MEM_ALLOC_HOST_PTR))
- || ((flags & CL_MEM_USE_HOST_PTR) && (flags & CL_MEM_COPY_HOST_PTR)))
- {
- if (errcode_ret != NULL)
- *errcode_ret = CL_INVALID_VALUE;
- return NULL;
- }
- if (size == 0)
- {
- if (errcode_ret != NULL)
- *errcode_ret = CL_INVALID_BUFFER_SIZE;
- return NULL;
- }
- if ((host_ptr == NULL && (flags & (CL_MEM_USE_HOST_PTR | CL_MEM_COPY_HOST_PTR)))
- || (host_ptr != NULL && !(flags & (CL_MEM_USE_HOST_PTR | CL_MEM_COPY_HOST_PTR))))
- {
- if (errcode_ret != NULL)
- *errcode_ret = CL_INVALID_HOST_PTR;
- return NULL;
- }
- //Alloc cl_mem structure
- mem = (cl_mem)gc_entity_alloc(sizeof(struct _cl_mem), release_callback_memobject, "buffer");
- if (mem == NULL)
- {
- if (errcode_ret != NULL)
- *errcode_ret = CL_OUT_OF_HOST_MEMORY;
- return NULL;
- }
- mem->ptr = NULL;
- mem->map_count = 0;
- gc_entity_store(&mem->context, context);
- mem->flags = flags;
- mem->size = size;
- mem->host_ptr = host_ptr;
- #ifdef DEBUG
- static int id = 0;
- mem->id = id++;
- #endif
- mem_object_store(mem);
- //TODO: we shouldn't allocate the buffer ourselves. StarPU allocates it if a NULL pointer is given
- // If not MEM_USE_HOST_PTR, we need to alloc the buffer ourselves
- if (!(flags & CL_MEM_USE_HOST_PTR))
- {
- mem->ptr = valloc(size);
- if (mem->ptr == NULL)
- {
- if (errcode_ret != NULL)
- *errcode_ret = CL_MEM_OBJECT_ALLOCATION_FAILURE;
- free(mem);
- return NULL;
- }
- //The buffer doesn't contain meaningful data
- mem->scratch = 1;
- }
- else
- {
- //The buffer may contain meaningful data
- mem->scratch = 0;
- mem->ptr = host_ptr;
- }
- // Access mode
- mem->mode = (flags & CL_MEM_READ_ONLY) ? CL_MEM_READ_ONLY :
- (flags & CL_MEM_WRITE_ONLY) ? CL_MEM_WRITE_ONLY : CL_MEM_READ_WRITE;
- // Perform data copy if necessary
- if (flags & CL_MEM_COPY_HOST_PTR)
- memcpy(mem->ptr, host_ptr, size);
- // Create StarPU buffer (on home node? what's this?)
- starpu_variable_data_register(&mem->handle, STARPU_MAIN_RAM, (uintptr_t)mem->ptr, size);
- DEBUG_MSG("[Buffer %d] Initialized (cl_mem %p handle %p)\n", mem->id, mem, mem->handle);
- return mem;
- }
|