struct _tpl_gbm_display
{
tbm_bufmgr bufmgr;
- tpl_list_t cached_buffers;
tpl_bool_t bound_client_display;
};
struct _tpl_gbm_surface
{
- tpl_buffer_t *current_rendering_buffer;
- tpl_list_t done_rendering_queue;
tbm_surface_queue_h tbm_queue;
};
struct _tpl_gbm_buffer
{
tpl_display_t *display;
- tpl_buffer_t *tpl_buffer;
- tbm_surface_h tbm_surface;
+ tpl_gbm_buffer_t* *tpl_gbm_surface;
tbm_bo bo;
struct gbm_bo *gbm_bo;
#define TPL_BUFFER_CACHE_MAX_ENTRIES 40
-static TPL_INLINE tpl_bool_t
-__tpl_gbm_surface_buffer_cache_add(tpl_list_t *buffer_cache, tpl_buffer_t *buffer)
-{
- tpl_buffer_t *evict = NULL;
-
- TPL_ASSERT(buffer_cache);
- TPL_ASSERT(buffer);
-
- if (__tpl_list_get_count(buffer_cache) >= TPL_BUFFER_CACHE_MAX_ENTRIES)
- {
- evict = __tpl_list_pop_front(buffer_cache, NULL);
-
- TPL_ASSERT(evict);
- tpl_object_unreference(&evict->base);
- }
-
- TPL_LOG(3, "buf:%10p buf->base:%10p evict:%10p", buffer, &buffer->base, evict);
-
- if (-1 == tpl_object_reference(&buffer->base))
- return TPL_FALSE;
+static int tpl_gbm_buffer_key;
+#define KEY_TPL_GBM_BUFFER (unsigned long)(&tpl_gbm_buffer_key)
- return __tpl_list_push_back(buffer_cache, (void *)buffer);
-}
-
-static TPL_INLINE void
-__tpl_gbm_surface_buffer_cache_remove(tpl_list_t *buffer_cache, size_t name)
+static void __tpl_gbm_buffer_free(tpl_gbm_buffer_t *gbm_buffer);
+static inline tpl_gbm_buffer_t *
+__tpl_gbm_get_gbm_buffer_from_tbm_surface(tbm_surface_h surface)
{
- tpl_list_node_t *node;
-
- TPL_ASSERT(buffer_cache);
-
- node = __tpl_list_get_front_node(buffer_cache);
-
- while (node)
- {
- tpl_buffer_t *buffer = (tpl_buffer_t *)__tpl_list_node_get_data(node);
-
- TPL_ASSERT(buffer);
-
- if (buffer->key == name)
- {
- tpl_object_unreference(&buffer->base);
- __tpl_list_remove(node, NULL);
- TPL_LOG(3, "name:%zu buf:%10p buf->base:%10p", name, buffer, &buffer->base);
- return;
- }
+ tbm_bo bo;
+ tpl_gbm_buffer_t *buf=NULL;
- node = __tpl_list_node_next(node);
- }
+ bo = tbm_surface_internal_get_bo(surface, 0);
+ tbm_bo_get_user_data(bo, KEY_TPL_GBM_BUFFER, (void **)&buf);
- TPL_LOG(3, "Buffer named %zu not found in cache", name);
+ return buf;
}
-static TPL_INLINE tpl_buffer_t *
-__tpl_gbm_surface_buffer_cache_find(tpl_list_t *buffer_cache, size_t name)
+static inline void
+__tpl_gbm_set_gbm_buffer_to_tbm_surface(tbm_surface_h surface, tpl_gbm_buffer_t *buf)
{
- tpl_list_node_t *node;
-
- TPL_ASSERT(buffer_cache);
-
- node = __tpl_list_get_front_node(buffer_cache);
-
- while (node)
- {
- tpl_buffer_t *buffer = (tpl_buffer_t *)__tpl_list_node_get_data(node);
-
- TPL_ASSERT(buffer);
-
- if (buffer->key == name)
- {
- TPL_LOG(3, "name:%zu buf:%10p buf->base:%10p", name, buffer, &buffer->base);
- return buffer;
- }
-
- node = __tpl_list_node_next(node);
- }
-
- TPL_LOG(3, "Buffer named %zu not found in cache", name);
+ tbm_bo bo;
- return NULL;
+ bo = tbm_surface_internal_get_bo(surface, 0);
+ tbm_bo_add_user_data(bo, KEY_TPL_GBM_BUFFER, (tbm_data_free)__tpl_gbm_buffer_free);
+ tbm_bo_set_user_data(bo, KEY_TPL_GBM_BUFFER, buf);
}
-
static TPL_INLINE tpl_bool_t
__tpl_gbm_display_is_gbm_device(tpl_handle_t native_dpy)
{
display->backend.data = gbm_display;
display->bufmgr_fd = -1;
- if (__tpl_gbm_display_is_gbm_device(display->native_handle))
- {
- __tpl_list_init(&gbm_display->cached_buffers);
- }
- else
- goto free_gbm_display;
-
return TPL_TRUE;
free_gbm_display:
if (gbm_display != NULL)
if (gbm_display->bound_client_display)
__tpl_gbm_display_unbind_client_wayland_display(display, NULL);
- __tpl_list_fini(&gbm_display->cached_buffers, (tpl_free_func_t) tpl_object_unreference);
-
free(gbm_display);
}
display->backend.data = NULL;
surface->backend.data = (void *)tpl_gbm_surface;
tpl_gbm_surface->tbm_queue = NULL;
- __tpl_list_init(&tpl_gbm_surface->done_rendering_queue);
-
if (surface->type == TPL_SURFACE_TYPE_WINDOW)
{
struct gbm_surface *gbm_surface = (struct gbm_surface*)surface->native_handle;
}
static void
-__tpl_gbm_surface_buffer_free(tpl_buffer_t *buffer)
-{
- TPL_LOG(3, "buffer(%p) key:%zu", buffer, buffer?buffer->key:-1);
- if (buffer != NULL)
- {
- __tpl_buffer_set_surface(buffer, NULL);
- tpl_object_unreference((tpl_object_t *) buffer);
- }
-}
-
-static tpl_bool_t
-__tpl_gbm_surface_destroy_cached_buffers(tpl_surface_t *surface)
-{
- tpl_gbm_surface_t *gbm_surface = NULL;
- tpl_gbm_display_t *gbm_display = NULL;
-
- if (surface == NULL)
- {
- TPL_ERR("tpl surface is invalid!!\n");
- return TPL_FALSE;
- }
-
- gbm_surface = (tpl_gbm_surface_t*)surface->backend.data;
- gbm_display = (tpl_gbm_display_t*)surface->display->backend.data;
-
- if (gbm_surface == NULL || gbm_display == NULL)
- {
- TPL_ERR("tpl surface has invalid members!!\n");
- return TPL_FALSE;
- }
-
- return TPL_TRUE;
-}
-
-static tpl_bool_t
-__tpl_gbm_surface_update_cached_buffers(tpl_surface_t *surface)
-{
- tpl_gbm_surface_t *gbm_surface = NULL;
- tpl_gbm_display_t *gbm_display = NULL;
-
- if (surface == NULL)
- {
- TPL_ERR("tpl surface is invalid!!\n");
- return TPL_FALSE;
- }
-
- gbm_surface = (tpl_gbm_surface_t*)surface->backend.data;
- gbm_display = (tpl_gbm_display_t*)surface->display->backend.data;
-
- if (gbm_surface == NULL || gbm_display == NULL)
- {
- TPL_ERR("tpl surface has invalid members!!\n");
- return TPL_FALSE;
- }
-
- return TPL_TRUE;
-}
-
-static void
__tpl_gbm_surface_fini(tpl_surface_t *surface)
{
tpl_gbm_surface_t *gbm_surface = NULL;
- tpl_gbm_display_t *gbm_display = NULL;
TPL_ASSERT(surface);
TPL_ASSERT(surface->display);
if (NULL == gbm_surface)
return;
- gbm_display = (tpl_gbm_display_t *) surface->display->backend.data;
- if (NULL == gbm_display)
- return;
-
TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
free(gbm_surface);
TPL_ASSERT(surface->display);
TPL_ASSERT(surface->display->native_handle);
TPL_ASSERT(frame);
- TPL_ASSERT(frame->buffer);
-
- tpl_gbm_buffer_t *gbm_buffer = NULL;
+ TPL_ASSERT(frame->tbm_surface);
TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
tpl_gbm_surface_t *gbm_surface = (tpl_gbm_surface_t*)surface->backend.data;
- tpl_buffer_t *buffer = NULL;
+ tbm_surface_h tbm_surface = frame->tbm_surface;
- if (!__tpl_list_is_empty(&gbm_surface->done_rendering_queue))
- {
- buffer = __tpl_list_pop_front(&gbm_surface->done_rendering_queue, NULL);
+ tbm_surface_internal_unref(tbm_surface);
- TPL_ASSERT(buffer);
-
- gbm_buffer = (tpl_gbm_buffer_t *) buffer->backend.data;
- }
-
- tbm_surface_internal_unref(gbm_buffer->tbm_surface);
-
- if (gbm_surface->tbm_queue && gbm_buffer->tbm_surface)
+ if (gbm_surface->tbm_queue)
{
- tbm_surface_queue_enqueue(gbm_surface->tbm_queue, gbm_buffer->tbm_surface);
+ tbm_surface_queue_enqueue(gbm_surface->tbm_queue, tbm_surface);
TPL_LOG(6, "tbm_surface ENQUEUED!!");
}
}
gbm_surface = (tpl_gbm_surface_t *) surface->backend.data;
- TPL_ASSERT(gbm_surface->current_rendering_buffer == NULL);
-
TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
return TPL_TRUE;
static tpl_bool_t
__tpl_gbm_surface_end_frame(tpl_surface_t *surface)
{
- tpl_gbm_surface_t *gbm_surface = NULL;
- tpl_gbm_buffer_t *gbm_buffer = NULL;
-
TPL_ASSERT(surface);
TPL_ASSERT(surface->display);
- gbm_surface = (tpl_gbm_surface_t *) surface->backend.data;
-
- TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
-
- if (gbm_surface->current_rendering_buffer != NULL)
- {
- gbm_buffer = (tpl_gbm_buffer_t *) gbm_surface->current_rendering_buffer->backend.data;
-
- TPL_LOG(6, "current_rendering_buffer BO:%d", tbm_bo_export(gbm_buffer->bo));
- }
-
- /* MOVE BUFFER : (current buffer) --> [done queue] */
- if (TPL_TRUE != __tpl_list_push_back(&gbm_surface->done_rendering_queue, gbm_surface->current_rendering_buffer))
- return TPL_FALSE;
-
- gbm_surface->current_rendering_buffer = NULL;
-
return TPL_TRUE;
}
return depth;
}
-static int tpl_buffer_key;
-#define KEY_TPL_BUFFER (unsigned long)(&tpl_buffer_key)
-
-static inline tpl_buffer_t *
-__tpl_gbm_surface_get_buffer_from_tbm_surface(tbm_surface_h surface)
-{
- tbm_bo bo;
- tpl_buffer_t* buf=NULL;
-
- bo = tbm_surface_internal_get_bo(surface, 0);
- tbm_bo_get_user_data(bo, KEY_TPL_BUFFER, (void **)&buf);
-
- return buf;
-}
-
-static inline void
-__tpl_gbm_buffer_set_tbm_surface(tbm_surface_h surface, tpl_buffer_t *buf)
-{
- tbm_bo bo;
-
- bo = tbm_surface_internal_get_bo(surface, 0);
- tbm_bo_add_user_data(bo, KEY_TPL_BUFFER, NULL);
- tbm_bo_set_user_data(bo, KEY_TPL_BUFFER, buf);
-}
-
-static tpl_buffer_t *
+static tbm_surface_h
__tpl_gbm_surface_create_buffer_from_gbm_surface(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
{
- tpl_buffer_t *buffer = NULL;
- tpl_gbm_buffer_t *gbm_buffer = NULL;
tbm_bo bo;
tbm_surface_h tbm_surface = NULL;
tbm_surface_queue_error_e tsq_err = 0;
+ tpl_gbm_buffer_t *gbm_buffer = NULL;
- tbm_bo_handle bo_handle;
- int width, height, depth;
- uint32_t size, offset, stride, key;
- tpl_format_t format;
tpl_gbm_surface_t *gbm_surface = NULL;
tpl_gbm_display_t *gbm_display = NULL;
/* It will be dec when before tbm_surface_queue_enqueue called */
tbm_surface_internal_ref(tbm_surface);
- if ((bo = tbm_surface_internal_get_bo(tbm_surface, 0)) == NULL)
- {
- TPL_ERR("Failed to get tbm_bo from tbm_surface");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- key = tbm_bo_export(bo);
-
- buffer = __tpl_gbm_surface_buffer_cache_find(&gbm_display->cached_buffers, key);
- if (buffer != NULL)
+ if ((gbm_buffer = __tpl_gbm_get_gbm_buffer_from_tbm_surface(tbm_surface)) != NULL)
{
- return buffer;
+ return tbm_surface;
}
- width = tbm_surface_get_width(tbm_surface);
- height = tbm_surface_get_height(tbm_surface);
-
- switch(tbm_surface_get_format(tbm_surface))
- {
- case TBM_FORMAT_ARGB8888: format = TPL_FORMAT_ARGB8888; break;
- case TBM_FORMAT_XRGB8888: format = TPL_FORMAT_XRGB8888; break;
- case TBM_FORMAT_RGB565: format = TPL_FORMAT_RGB565; break;
- default:
- format = TPL_FORMAT_INVALID;
- TPL_ERR("No matched format!!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- depth = __tpl_gbm_get_depth_from_format(format);
-
- /* Get pitch stride from tbm_surface */
- tbm_surface_internal_get_plane_data(tbm_surface, 0, &size, &offset, &stride);
-
- /* Create tpl buffer. */
- bo_handle = tbm_bo_get_handle(bo, TBM_DEVICE_3D);
-
- buffer = __tpl_buffer_alloc(surface, (size_t) key,
- (int)bo_handle.u32, width, height, depth, stride);
-
- if (buffer == NULL)
+ if ((bo = tbm_surface_internal_get_bo(tbm_surface, 0)) == NULL)
{
- TPL_ERR("Failed to allocate tpl buffer | surf:%p bo_hnd:%d WxHxD:%dx%dx%d",
- surface, (int) bo_handle.u32, width, height, depth);
+ TPL_ERR("Failed to get tbm_bo from tbm_surface");
tbm_surface_internal_unref(tbm_surface);
return NULL;
}
if (gbm_buffer == NULL)
{
TPL_ERR("Mem alloc for gbm_buffer failed!");
- tpl_object_unreference((tpl_object_t *) buffer);
tbm_surface_internal_unref(tbm_surface);
return NULL;
}
- buffer->backend.data = (void *)gbm_buffer;
-
- /* Post process */
gbm_buffer->display = surface->display;
gbm_buffer->bo = bo;
- gbm_buffer->tbm_surface = tbm_surface;
-
- if (TPL_TRUE != __tpl_gbm_surface_buffer_cache_add(&gbm_display->cached_buffers, buffer))
- {
- TPL_ERR("Adding surface to buffer cache failed!");
- tpl_object_unreference((tpl_object_t *) buffer);
- tbm_surface_internal_unref(tbm_surface);
- free(gbm_buffer);
- return NULL;
- }
if (reset_buffers != NULL)
*reset_buffers = TPL_FALSE;
- TPL_LOG(3, "buffer:%p bo_hnd:%d, %dx%d", buffer, (int) bo_handle.u32, width, height);
- __tpl_gbm_buffer_set_tbm_surface(tbm_surface, buffer);
-
- return buffer;
-}
+ __tpl_gbm_set_gbm_buffer_to_tbm_surface(tbm_surface, gbm_buffer);
-static void
-__tpl_gbm_buffer_destroy_notify(struct wl_listener *listener, void *data)
-{
- tpl_display_t *display;
- tpl_gbm_display_t *gbm_display;
- tpl_gbm_buffer_t *gbm_buffer = NULL;
- size_t key = 0;
-
- gbm_buffer = wl_container_of(listener, gbm_buffer, destroy_listener);
- display = gbm_buffer->display;
- key = tbm_bo_export(gbm_buffer->bo);
- gbm_display = (tpl_gbm_display_t *)display->backend.data;
- tpl_object_unreference((tpl_object_t *)gbm_buffer->tpl_buffer);
- __tpl_gbm_surface_buffer_cache_remove(&gbm_display->cached_buffers, key);
+ return tbm_surface;
}
-static tpl_buffer_t *
+static tbm_surface_h
__tpl_gbm_surface_create_buffer_from_wl_tbm(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
{
- tpl_buffer_t *buffer = NULL;
tpl_gbm_buffer_t *gbm_buffer = NULL;
tbm_surface_h tbm_surface = NULL;
/* TODO: If HW support getting of gem memory size,
#if 0
tbm_surface_info_s tbm_surf_info;
#endif
- tbm_bo bo;
- tbm_bo_handle bo_handle;
-
- int width = 0, height = 0, depth;
- uint32_t size, offset, stride;
- tpl_format_t format = TPL_FORMAT_INVALID;
- size_t key = 0;
-
- tpl_gbm_display_t *gbm_display;
-
TPL_ASSERT(surface);
TPL_ASSERT(surface->display);
TPL_ASSERT(surface->native_handle);
- gbm_display = (tpl_gbm_display_t *) surface->display->backend.data;
-
tbm_surface = wayland_tbm_server_get_surface(NULL, (struct wl_resource*)surface->native_handle);
if (tbm_surface == NULL)
{
return NULL;
}
- bo = tbm_surface_internal_get_bo(tbm_surface, 0);
- key = tbm_bo_export(bo);
-
- buffer = __tpl_gbm_surface_buffer_cache_find(&gbm_display->cached_buffers, key);
- if (buffer != NULL)
- {
- __tpl_buffer_set_surface(buffer, surface);
- }
- else
- {
- /* Inc ref count about tbm_surface */
- /* It will be dec when gbm_buffer_fini called*/
- tbm_surface_internal_ref(tbm_surface);
-
- if (TPL_TRUE != __tpl_gbm_display_get_pixmap_info(
- surface->display,
- surface->native_handle,
- &width, &height, &format))
- {
- TPL_ERR("Failed to get pixmap info!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
- /* TODO: If HW support getting of gem memory size,
- then replace tbm_surface_internal_get_plane_data() to tbm_surface_get_info() */
-#if 0
- if (tbm_surface_get_info(tbm_surface, &tbm_surf_info) != 0)
- {
- TPL_ERR("Failed to get stride info!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
- stride = tbm_surf_info.planes[0].stride;
-#else
- if (!tbm_surface_internal_get_plane_data(tbm_surface, 0, &size, &offset, &stride))
- {
- TPL_ERR("Failed to get tbm_surface stride info!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-#endif
- depth = __tpl_gbm_get_depth_from_format(format);
-
- /* Create tpl buffer. */
- bo_handle = tbm_bo_get_handle(bo, TBM_DEVICE_3D);
- if (NULL == bo_handle.ptr)
- {
- TPL_ERR("Failed to get bo handle!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- buffer = __tpl_buffer_alloc(surface, key,
- (int) bo_handle.u32, width, height, depth, stride);
- if (buffer == NULL)
- {
- TPL_ERR("Failed to alloc TPL buffer!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- gbm_buffer = (tpl_gbm_buffer_t *) calloc(1, sizeof(tpl_gbm_buffer_t));
- if (gbm_buffer == NULL)
- {
- TPL_ERR("Mem alloc failed for gbm buffer!");
- tpl_object_unreference((tpl_object_t *) buffer);
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- gbm_buffer->display = surface->display;
- gbm_buffer->bo = bo;
- gbm_buffer->tbm_surface = tbm_surface;
- gbm_buffer->tpl_buffer = buffer;
-
- buffer->backend.data = (void *)gbm_buffer;
- buffer->key = key;
-
- if (TPL_TRUE != __tpl_gbm_surface_buffer_cache_add(&gbm_display->cached_buffers, buffer))
- {
- TPL_ERR("Adding surface to buffer cache failed!");
- tpl_object_unreference((tpl_object_t *) buffer);
- tbm_surface_internal_unref(tbm_surface);
- free(gbm_buffer);
- return NULL;
- }
-
- gbm_buffer->destroy_listener.notify = __tpl_gbm_buffer_destroy_notify;
- wl_resource_add_destroy_listener((struct wl_resource*)surface->native_handle, &gbm_buffer->destroy_listener);
- }
-
- if (reset_buffers != NULL)
- *reset_buffers = TPL_FALSE;
-
- return buffer;
+ return tbm_surface;
}
-static tpl_buffer_t *
+static tbm_surface_h
__tpl_gbm_surface_get_buffer(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
{
- int width, height;
- tpl_gbm_surface_t *gbm_surface;
+ tbm_surface_h tbm_surface = NULL;
TPL_ASSERT(surface);
TPL_ASSERT(surface->backend.data);
- gbm_surface = (tpl_gbm_surface_t *)surface->backend.data;
-
if (reset_buffers != NULL)
*reset_buffers = TPL_FALSE;
- TPL_LOG(3, "window(%p, %p), current(%p)", surface, surface->native_handle,
- gbm_surface->current_rendering_buffer);
-
- if (surface->type != TPL_SURFACE_TYPE_PIXMAP &&
- TPL_TRUE != __tpl_gbm_display_get_window_info(surface->display,
- surface->native_handle, &width, &height, NULL, 0, 0))
- {
- TPL_ERR("Failed to get window info!");
- return NULL;
- }
-
- /* Check whether the surface was resized by wayland_egl */
- if (surface->type != TPL_SURFACE_TYPE_PIXMAP &&
- gbm_surface->current_rendering_buffer != NULL &&
- (width != gbm_surface->current_rendering_buffer->width ||
- height != gbm_surface->current_rendering_buffer->height))
- {
- __tpl_gbm_surface_buffer_free(gbm_surface->current_rendering_buffer);
- gbm_surface->current_rendering_buffer = NULL;
-
- if (reset_buffers != NULL)
- *reset_buffers = TPL_TRUE;
- }
-
- if (gbm_surface->current_rendering_buffer == NULL)
- {
- if (surface->type == TPL_SURFACE_TYPE_WINDOW)
- {
- gbm_surface->current_rendering_buffer =
- __tpl_gbm_surface_create_buffer_from_gbm_surface(surface, reset_buffers);
- }
- if (surface->type == TPL_SURFACE_TYPE_PIXMAP)
- {
- gbm_surface->current_rendering_buffer =
- __tpl_gbm_surface_create_buffer_from_wl_tbm(surface, reset_buffers);
- }
- TPL_LOG(3, "window(%p, %p), current(%p)", surface, surface->native_handle,
- gbm_surface->current_rendering_buffer);
- }
-
- TPL_ASSERT(gbm_surface->current_rendering_buffer);
-
- return gbm_surface->current_rendering_buffer;
-}
-
-static tpl_bool_t
-__tpl_gbm_buffer_init(tpl_buffer_t *buffer)
-{
- TPL_IGNORE(buffer);
-
- return TPL_TRUE;
-}
-
-static void
-__tpl_gbm_buffer_fini(tpl_buffer_t *buffer)
-{
- TPL_ASSERT(buffer);
-
- TPL_LOG(3, "tpl_buffer(%p) key:%zu fd:%d %dx%d", buffer, buffer->key, buffer->fd, buffer->width, buffer->height);
-
- if (buffer->backend.data)
+ if (surface->type == TPL_SURFACE_TYPE_WINDOW)
{
- tpl_gbm_buffer_t *gbm_buffer = (tpl_gbm_buffer_t *)buffer->backend.data;
-
- if (gbm_buffer->bo != NULL && gbm_buffer->tbm_surface != NULL)
- {
- tbm_surface_internal_unref(gbm_buffer->tbm_surface);
- tbm_surface_destroy(gbm_buffer->tbm_surface);
- gbm_buffer->bo = NULL;
- gbm_buffer->tbm_surface = NULL;
- }
-
- buffer->backend.data = NULL;
- free(gbm_buffer);
+ tbm_surface = __tpl_gbm_surface_create_buffer_from_gbm_surface(surface, reset_buffers);
}
-}
-
-static void *
-__tpl_gbm_buffer_map(tpl_buffer_t *buffer, int size)
-{
- tpl_gbm_buffer_t *gbm_buffer;
- tbm_bo_handle handle;
-
- TPL_ASSERT(buffer);
- TPL_ASSERT(buffer->backend.data);
-
- gbm_buffer = (tpl_gbm_buffer_t *) buffer->backend.data;
-
- TPL_ASSERT(gbm_buffer->bo);
-
- handle = tbm_bo_get_handle(gbm_buffer->bo, TBM_DEVICE_CPU);
- return handle.ptr;
-}
-
-static void
-__tpl_gbm_buffer_unmap(tpl_buffer_t *buffer, void *ptr, int size)
-{
- TPL_IGNORE(buffer);
- TPL_IGNORE(ptr);
- TPL_IGNORE(size);
-
- /* Do nothing. */
-}
-
-static tpl_bool_t
-__tpl_gbm_buffer_lock(tpl_buffer_t *buffer, tpl_lock_usage_t usage)
-{
- tpl_gbm_buffer_t *gbm_buffer;
- tbm_bo_handle handle;
-
- TPL_ASSERT(buffer);
- TPL_ASSERT(buffer->backend.data);
-
- gbm_buffer = (tpl_gbm_buffer_t *) buffer->backend.data;
-
- TPL_ASSERT(gbm_buffer->bo);
-
- TPL_OBJECT_UNLOCK(buffer);
-
- switch (usage)
+ if (surface->type == TPL_SURFACE_TYPE_PIXMAP)
{
- case TPL_LOCK_USAGE_GPU_READ:
- handle = tbm_bo_map(gbm_buffer->bo, TBM_DEVICE_3D, TBM_OPTION_READ);
- break;
- case TPL_LOCK_USAGE_GPU_WRITE:
- handle = tbm_bo_map(gbm_buffer->bo, TBM_DEVICE_3D, TBM_OPTION_WRITE);
- break;
- case TPL_LOCK_USAGE_CPU_READ:
- handle = tbm_bo_map(gbm_buffer->bo, TBM_DEVICE_CPU, TBM_OPTION_READ);
- break;
- case TPL_LOCK_USAGE_CPU_WRITE:
- handle = tbm_bo_map(gbm_buffer->bo, TBM_DEVICE_CPU, TBM_OPTION_WRITE);
- break;
- default:
- TPL_ERR("Unsupported buffer usage!");
- TPL_OBJECT_LOCK(buffer);
- return TPL_FALSE;
+ tbm_surface = __tpl_gbm_surface_create_buffer_from_wl_tbm(surface, reset_buffers);
}
- TPL_OBJECT_LOCK(buffer);
-
- if (handle.u32 != 0 || handle.ptr != NULL)
- return TPL_FALSE;
+ TPL_ASSERT(tbm_surface);
- return TPL_TRUE;
+ return tbm_surface;
}
-
static void
-__tpl_gbm_buffer_unlock(tpl_buffer_t *buffer)
+__tpl_gbm_buffer_free(tpl_gbm_buffer_t *gbm_buffer)
{
- tpl_gbm_buffer_t *gbm_buffer;
-
- TPL_ASSERT(buffer);
- TPL_ASSERT(buffer->backend.data);
-
- gbm_buffer = (tpl_gbm_buffer_t *) buffer->backend.data;
-
- TPL_ASSERT(gbm_buffer->bo);
-
- TPL_OBJECT_UNLOCK(buffer);
- tbm_bo_unmap(gbm_buffer->bo);
- TPL_OBJECT_LOCK(buffer);
+ TPL_ASSERT(gbm_buffer);
+ free(gbm_buffer);
}
tpl_bool_t
backend->validate_frame = __tpl_gbm_surface_validate_frame;
backend->get_buffer = __tpl_gbm_surface_get_buffer;
backend->post = __tpl_gbm_surface_post;
- backend->destroy_cached_buffers = __tpl_gbm_surface_destroy_cached_buffers;
- backend->update_cached_buffers = __tpl_gbm_surface_update_cached_buffers;
-}
-
-void
-__tpl_buffer_init_backend_gbm(tpl_buffer_backend_t *backend)
-{
- TPL_ASSERT(backend);
-
- backend->type = TPL_BACKEND_GBM;
- backend->data = NULL;
-
- backend->init = __tpl_gbm_buffer_init;
- backend->fini = __tpl_gbm_buffer_fini;
- backend->map = __tpl_gbm_buffer_map;
- backend->unmap = __tpl_gbm_buffer_unmap;
- backend->lock = __tpl_gbm_buffer_lock;
- backend->unlock = __tpl_gbm_buffer_unlock;
- backend->create_native_buffer = NULL;
}
#ifdef EGL_BIND_WL_DISPLAY
struct _tpl_wayland_display
{
tbm_bufmgr bufmgr;
- tpl_list_t cached_buffers;
struct wayland_tbm_client *wl_tbm_client;
struct wl_event_queue *wl_queue;
struct wl_registry *wl_registry;
struct _tpl_wayland_surface
{
- tpl_buffer_t *current_rendering_buffer;
- tpl_list_t done_rendering_queue;
tbm_surface_queue_h tbm_queue;
tpl_bool_t resized;
};
struct _tpl_wayland_buffer
{
tpl_display_t *display;
- tbm_surface_h tbm_surface;
tbm_bo bo;
-
- tpl_buffer_t *tpl_buffer;
+ tpl_wayland_surface_t *wayland_surface;
struct wl_proxy *wl_proxy;
};
#define TPL_BUFFER_CACHE_MAX_ENTRIES 40
-static TPL_INLINE tpl_bool_t
-__tpl_wayland_surface_buffer_cache_add(tpl_list_t *buffer_cache, tpl_buffer_t *buffer)
-{
- tpl_buffer_t *evict = NULL;
-
- TPL_ASSERT(buffer_cache);
- TPL_ASSERT(buffer);
-
- if (__tpl_list_get_count(buffer_cache) >= TPL_BUFFER_CACHE_MAX_ENTRIES)
- {
- evict = __tpl_list_pop_front(buffer_cache, NULL);
-
- TPL_ASSERT(evict);
- tpl_object_unreference(&evict->base);
- }
-
- TPL_LOG(3, "buf:%10p buf->base:%10p evict:%10p", buffer, &buffer->base, evict);
+static int tpl_wayland_buffer_key;
+#define KEY_TPL_WAYLAND_BUFFER (unsigned long)(&tpl_wayland_buffer_key)
- if (-1 == tpl_object_reference(&buffer->base))
- return TPL_FALSE;
-
- return __tpl_list_push_back(buffer_cache, (void *)buffer);
-}
-
-static TPL_INLINE void
-__tpl_wayland_surface_buffer_cache_remove(tpl_list_t *buffer_cache, size_t name)
+static void __tpl_wayland_buffer_free(tpl_wayland_buffer_t *wayland_buffer);
+static inline tpl_wayland_buffer_t *
+__tpl_wayland_get_wayland_buffer_from_tbm_surface(tbm_surface_h surface)
{
- tpl_list_node_t *node;
-
- TPL_ASSERT(buffer_cache);
-
- node = __tpl_list_get_front_node(buffer_cache);
+ tbm_bo bo;
+ tpl_wayland_buffer_t *buf=NULL;
- while (node)
- {
- tpl_buffer_t *buffer = (tpl_buffer_t *)__tpl_list_node_get_data(node);
-
- TPL_ASSERT(buffer);
+ bo = tbm_surface_internal_get_bo(surface, 0);
+ tbm_bo_get_user_data(bo, KEY_TPL_WAYLAND_BUFFER, (void **)&buf);
- if (buffer->key == name)
- {
- tpl_object_unreference(&buffer->base);
- __tpl_list_remove(node, NULL);
- TPL_LOG(3, "name:%zu buf:%10p buf->base:%10p", name, buffer, &buffer->base);
- return;
- }
-
- node = __tpl_list_node_next(node);
- }
-
- TPL_LOG(3, "Buffer named %zu not found in cache", name);
+ return buf;
}
-static void
-__tpl_wayland_surface_buffer_free(tpl_buffer_t *buffer);
-
-static TPL_INLINE void
-__tpl_wayland_surface_buffer_cache_remove_all(tpl_list_t *buffer_cache)
-{
- tpl_list_node_t *node;
-
- TPL_ASSERT(buffer_cache);
-
- node = __tpl_list_get_front_node(buffer_cache);
-
- while (node)
- {
- tpl_buffer_t *buffer = (tpl_buffer_t *)__tpl_list_node_get_data(node);
-
- TPL_ASSERT(buffer);
-
- tpl_object_unreference(&buffer->base);
-
- __tpl_list_remove(node, (tpl_free_func_t)__tpl_wayland_surface_buffer_free);
- node = __tpl_list_node_next(node);
- }
-}
-
-static TPL_INLINE tpl_buffer_t *
-__tpl_wayland_surface_buffer_cache_find(tpl_list_t *buffer_cache, size_t name)
+static inline void
+__tpl_wayland_set_wayland_buffer_to_tbm_surface(tbm_surface_h surface, tpl_wayland_buffer_t *buf)
{
- tpl_list_node_t *node;
-
- TPL_ASSERT(buffer_cache);
-
- node = __tpl_list_get_front_node(buffer_cache);
-
- while (node)
- {
- tpl_buffer_t *buffer = (tpl_buffer_t *)__tpl_list_node_get_data(node);
-
- TPL_ASSERT(buffer);
-
- if (buffer->key == name)
- {
- TPL_LOG(3, "name:%zu buf:%10p buf->base:%10p", name, buffer, &buffer->base);
- return buffer;
- }
-
- node = __tpl_list_node_next(node);
- }
-
- TPL_LOG(3, "Buffer named %zu not found in cache", name);
+ tbm_bo bo;
- return NULL;
+ bo = tbm_surface_internal_get_bo(surface, 0);
+ tbm_bo_add_user_data(bo, KEY_TPL_WAYLAND_BUFFER, __tpl_wayland_buffer_free);
+ tbm_bo_set_user_data(bo, KEY_TPL_WAYLAND_BUFFER, buf);
}
-
static TPL_INLINE tpl_bool_t
__tpl_wayland_display_is_wl_display(tpl_handle_t native_dpy)
{
goto destroy_queue;
wl_proxy_set_queue((struct wl_proxy *)wayland_display->wl_registry, wayland_display->wl_queue);
-
- __tpl_list_init(&wayland_display->cached_buffers);
}
else
goto free_wl_display;
if (wayland_display != NULL)
{
wayland_tbm_client_deinit(wayland_display->wl_tbm_client);
- __tpl_list_fini(&wayland_display->cached_buffers, (tpl_free_func_t)tpl_object_unreference);
free(wayland_display);
}
display->backend.data = NULL;
return TPL_TRUE;
}
-static tpl_bool_t
-__tpl_wayland_display_get_pixmap_info(tpl_display_t *display, tpl_handle_t pixmap,
- int *width, int *height, tpl_format_t *format)
-{
- tbm_surface_h tbm_surface = NULL;
- int tbm_format = -1;
-
- tbm_surface = wayland_tbm_server_get_surface(NULL, (struct wl_resource*)pixmap);
- if (tbm_surface == NULL)
- return TPL_FALSE;
-
- if (width) *width = tbm_surface_get_width(tbm_surface);
- if (height) *height = tbm_surface_get_height(tbm_surface);
- if (format)
- {
- tbm_format = tbm_surface_get_format(tbm_surface);
- switch(tbm_format)
- {
- case TBM_FORMAT_ARGB8888: *format = TPL_FORMAT_ARGB8888; break;
- case TBM_FORMAT_XRGB8888: *format = TPL_FORMAT_XRGB8888; break;
- case TBM_FORMAT_RGB565: *format = TPL_FORMAT_RGB565; break;
- default:
- *format = TPL_FORMAT_INVALID;
- return TPL_FALSE;
- }
- }
-
- return TPL_TRUE;
-}
-
static void
__tpl_wayland_display_flush(tpl_display_t *display)
{
__tpl_wayland_surface_init(tpl_surface_t *surface)
{
tpl_wayland_surface_t *wayland_surface = NULL;
+ int tbm_format;
+ struct wl_egl_window *wl_egl_window = (struct wl_egl_window *)surface->native_handle;
+
TPL_ASSERT(surface);
+ TPL_ASSERT(surface->type == TPL_SURFACE_TYPE_WINDOW);
+ TPL_ASSERT(surface->native_handle);
wayland_surface = (tpl_wayland_surface_t *) calloc(1, sizeof(tpl_wayland_surface_t));
if (NULL == wayland_surface)
wayland_surface->tbm_queue = NULL;
wayland_surface->resized = TPL_FALSE;
- __tpl_list_init(&wayland_surface->done_rendering_queue);
-
- if (surface->type == TPL_SURFACE_TYPE_WINDOW)
+ switch (surface->format)
{
- int tbm_format;
- struct wl_egl_window *wl_egl_window = (struct wl_egl_window *)surface->native_handle;
- wl_egl_window->private = surface;
- wl_egl_window->resize_callback = (void*)__cb_client_window_resize_callback;
-
- switch (surface->format)
- {
- case TPL_FORMAT_ARGB8888: tbm_format = TBM_FORMAT_ARGB8888;
- break;
- case TPL_FORMAT_XRGB8888: tbm_format = TBM_FORMAT_XRGB8888;
- break;
- case TPL_FORMAT_RGB565: tbm_format = TBM_FORMAT_RGB565;
- break;
- default:
- TPL_ERR("Unsupported format found in surface!");
- return TPL_FALSE;
- }
-
- wayland_surface->tbm_queue = tbm_surface_queue_create(
- CLIENT_QUEUE_SIZE,
- wl_egl_window->width,
- wl_egl_window->height,
- tbm_format,
- 0);
-
- if (wayland_surface->tbm_queue == NULL)
- {
- TPL_ERR("TBM surface queue creation failed!");
- goto error;
- }
-
- if (TPL_TRUE != __tpl_wayland_display_get_window_info(surface->display, surface->native_handle,
- &surface->width, &surface->height, NULL, 0, 0))
- goto error;
-
- TPL_LOG(3, "window(%p, %p) %dx%d", surface, surface->native_handle, surface->width, surface->height);
- return TPL_TRUE;
- }
- else if (surface->type == TPL_SURFACE_TYPE_PIXMAP)
- {
- if (TPL_TRUE != __tpl_wayland_display_get_pixmap_info(surface->display, surface->native_handle,
- &surface->width, &surface->height, NULL))
- goto error;
-
- return TPL_TRUE;
- }
-
-error:
- free(wayland_surface);
-
- return TPL_FALSE;
-}
-
-static void
-__tpl_wayland_surface_buffer_free(tpl_buffer_t *buffer)
-{
- TPL_LOG(3, "buffer(%p) key:%zu", buffer, buffer?buffer->key:-1);
- if (buffer != NULL)
- {
- tpl_object_unreference((tpl_object_t *) buffer);
- }
-}
-
-static tpl_bool_t
-__tpl_wayland_surface_destroy_cached_buffers(tpl_surface_t *surface)
-{
- tpl_wayland_surface_t *wayland_surface = NULL;
- tpl_wayland_display_t *wayland_display = NULL;
-
- if (surface == NULL)
- {
- TPL_ERR("tpl surface is invalid!!\n");
+ case TPL_FORMAT_ARGB8888: tbm_format = TBM_FORMAT_ARGB8888;
+ break;
+ case TPL_FORMAT_XRGB8888: tbm_format = TBM_FORMAT_XRGB8888;
+ break;
+ case TPL_FORMAT_RGB565: tbm_format = TBM_FORMAT_RGB565;
+ break;
+ default:
+ TPL_ERR("Unsupported format found in surface!");
return TPL_FALSE;
}
- wayland_surface = (tpl_wayland_surface_t*)surface->backend.data;
- wayland_display = (tpl_wayland_display_t*)surface->display->backend.data;
+ wayland_surface->tbm_queue = tbm_surface_queue_create(
+ CLIENT_QUEUE_SIZE,
+ wl_egl_window->width,
+ wl_egl_window->height,
+ tbm_format,
+ 0);
- if (wayland_surface == NULL || wayland_display == NULL)
+ if (wayland_surface->tbm_queue == NULL)
{
- TPL_ERR("tpl surface has invalid members!!\n");
- return TPL_FALSE;
+ TPL_ERR("TBM surface queue creation failed!");
+ goto error;
}
- __tpl_wayland_surface_buffer_cache_remove_all(&wayland_display->cached_buffers);
+ surface->width = wl_egl_window->width;
+ surface->height = wl_egl_window->height;
- return TPL_TRUE;
-}
-
-static tpl_bool_t
-__tpl_wayland_surface_update_cached_buffers(tpl_surface_t *surface)
-{
- tpl_wayland_surface_t *wayland_surface = NULL;
- tpl_wayland_display_t *wayland_display = NULL;
-
- if (surface == NULL)
- {
- TPL_ERR("tpl surface is invalid!!\n");
- return TPL_FALSE;
- }
+ wl_egl_window->private = surface;
+ wl_egl_window->resize_callback = (void*)__cb_client_window_resize_callback;
- wayland_surface = (tpl_wayland_surface_t*)surface->backend.data;
- wayland_display = (tpl_wayland_display_t*)surface->display->backend.data;
+ TPL_LOG(3, "window(%p, %p) %dx%d", surface, surface->native_handle, surface->width, surface->height);
+ return TPL_TRUE;
- if (wayland_surface == NULL || wayland_display == NULL)
- {
- TPL_ERR("tpl surface has invalid members!!\n");
- return TPL_FALSE;
- }
+error:
+ free(wayland_surface);
- return TPL_TRUE;
+ return TPL_FALSE;
}
static void
TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
- __tpl_wayland_surface_buffer_cache_remove_all(&wayland_display->cached_buffers);
-
if (surface->type == TPL_SURFACE_TYPE_WINDOW)
{
struct wl_egl_window *wl_egl_window = (struct wl_egl_window *)surface->native_handle;
TPL_ASSERT(surface->display);
TPL_ASSERT(surface->display->native_handle);
TPL_ASSERT(frame);
- TPL_ASSERT(frame->buffer);
+ TPL_ASSERT(frame->tbm_surface);
+ struct wl_egl_window *wl_egl_window = NULL;
tpl_wayland_display_t *wayland_display = (tpl_wayland_display_t*) surface->display->backend.data;
+ tpl_wayland_surface_t *wayland_surface = (tpl_wayland_surface_t*) surface->backend.data;
tpl_wayland_buffer_t *wayland_buffer = NULL;
+ tbm_surface_h tbm_surface = NULL;
+ tbm_surface_queue_error_e tsqe;
+ int i;
TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
- wayland_buffer = (tpl_wayland_buffer_t *)frame->buffer->backend.data;
- struct wl_egl_window *wl_egl_window = NULL;
- int i;
+ tbm_surface = frame->tbm_surface;
+ wayland_buffer = __tpl_wayland_get_wayland_buffer_from_tbm_surface(tbm_surface);
+ TPL_ASSERT(wayland_buffer);
+
tbm_bo_handle bo_handle = tbm_bo_get_handle(wayland_buffer->bo , TBM_DEVICE_CPU);
if (bo_handle.ptr != NULL)
TPL_IMAGE_DUMP(bo_handle.ptr, surface->width, surface->height, surface->dump_count++);
- TPL_LOG(3, "\t buffer(%p, %p) key:%zu", frame->buffer, wayland_buffer->wl_proxy, frame->buffer->key);
wl_egl_window = (struct wl_egl_window *)surface->native_handle;
- tpl_object_reference((tpl_object_t *)frame->buffer);
+ tbm_surface_internal_unref(tbm_surface);
+ tsqe = tbm_surface_queue_enqueue(wayland_surface->tbm_queue, tbm_surface);
+
+ /* deprecated */
+ tsqe = tbm_surface_queue_acquire(wayland_surface->tbm_queue, &tbm_surface);
+ tbm_surface_internal_ref(tbm_surface);
+
wl_surface_attach(wl_egl_window->surface,
(void *)wayland_buffer->wl_proxy,
wl_egl_window->dx,
Because the buffer_release callback only be triggered if this callback is registered. */
struct wl_callback *frame_callback = NULL;
frame_callback = wl_surface_frame(wl_egl_window->surface);
- wl_callback_add_listener(frame_callback, &frame_listener, frame->buffer);
+ wl_callback_add_listener(frame_callback, &frame_listener, tbm_surface);
wl_proxy_set_queue((struct wl_proxy *)frame_callback, wayland_display->wl_queue);
}
wl_surface_commit(wl_egl_window->surface);
wl_display_flush(surface->display->native_handle);
-
- TPL_LOG(7, "BO:%d", tbm_bo_export(wayland_buffer->bo));
}
static tpl_bool_t
__tpl_wayland_surface_begin_frame(tpl_surface_t *surface)
{
- tpl_wayland_surface_t *wayland_surface;
-
TPL_ASSERT(surface);
TPL_ASSERT(surface->display);
- wayland_surface = (tpl_wayland_surface_t *) surface->backend.data;
-
- TPL_ASSERT(wayland_surface->current_rendering_buffer == NULL);
-
- TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
-
TPL_OBJECT_UNLOCK(surface);
__tpl_wayland_display_roundtrip(surface->display);
-
TPL_OBJECT_LOCK(surface);
- wayland_surface->current_rendering_buffer = NULL;
-
return TPL_TRUE;
}
static tpl_bool_t
__tpl_wayland_surface_end_frame(tpl_surface_t *surface)
{
- tpl_wayland_surface_t *wayland_surface = NULL;
- tpl_wayland_buffer_t *wayland_buffer = NULL;
-
TPL_ASSERT(surface);
TPL_ASSERT(surface->display);
-
- wayland_surface = (tpl_wayland_surface_t *) surface->backend.data;
-
- TPL_LOG(3, "window(%p, %p)", surface, surface->native_handle);
-
- if (wayland_surface->current_rendering_buffer != NULL)
- {
- wayland_buffer = (tpl_wayland_buffer_t *) wayland_surface->current_rendering_buffer->backend.data;
-
- TPL_LOG(6, "current_rendering_buffer BO:%d", tbm_bo_export(wayland_buffer->bo));
- }
-
- wayland_surface->current_rendering_buffer = NULL;
-
return TPL_TRUE;
}
return depth;
}
-static tpl_buffer_t *
-__tpl_wayland_surface_create_buffer_from_wl_egl(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
+static tbm_surface_h
+__tpl_wayland_surface_get_buffer(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
{
- tpl_buffer_t *buffer = NULL;
- tpl_wayland_buffer_t *wayland_buffer = NULL;
- tpl_wayland_surface_t *wayland_surface = NULL;
- tpl_wayland_display_t *wayland_display = NULL;
- tbm_bo bo;
- tbm_bo_handle bo_handle;
- int width, height, depth, format;
- uint32_t stride, size, offset;
- uint32_t key;
- tpl_format_t tpl_format;
-
- tbm_surface_h tbm_surface = NULL;
- tbm_surface_queue_error_e tsq_err = 0;
-
- /* TODO: If HW support getting of gem memory size,
- use tbm_surface_get_info() with tbm_surface_info_s */
-#if 0
- tbm_surface_info_s tbm_surf_info;
-#endif
- struct wl_proxy *wl_proxy = NULL;
-
TPL_ASSERT(surface);
- TPL_ASSERT(surface->display);
TPL_ASSERT(surface->native_handle);
- TPL_ASSERT(surface->display->backend.data);
+ TPL_ASSERT(surface->backend.data);
+ TPL_ASSERT(surface->display);
- wayland_display = (tpl_wayland_display_t *) surface->display->backend.data;
- wayland_surface = (tpl_wayland_surface_t *) surface->backend.data;
+ int width, height, format;
+ tbm_surface_h tbm_surface = NULL;
+ tpl_wayland_buffer_t *wayland_buffer = NULL;
+ tpl_wayland_surface_t *wayland_surface = (tpl_wayland_surface_t*)surface->backend.data;
+ tpl_wayland_display_t *wayland_display = (tpl_wayland_display_t*)surface->display->backend.data;
+ struct wl_egl_window *wl_egl_window = (struct wl_egl_window *)surface->native_handle;
+ struct wl_proxy *wl_proxy = NULL;
+ tbm_surface_queue_error_e tsq_err = 0;
- struct wl_egl_window *wl_egl_window = (struct wl_egl_window *)surface->native_handle;
- width = wl_egl_window->width;
- height = wl_egl_window->height;
- format = tbm_surface_queue_get_format(wayland_surface->tbm_queue);
+ if (reset_buffers != NULL) *reset_buffers = TPL_FALSE;
+
+ width = wl_egl_window->width;
+ height = wl_egl_window->height;
+ format = tbm_surface_queue_get_format(wayland_surface->tbm_queue);
/* Check whether the surface was resized by wayland_egl */
if (wayland_surface->resized == TPL_TRUE ||
{
tbm_surface_queue_reset(wayland_surface->tbm_queue, width, height, format);
- /* Remove all cached buffers (This code will be deleted.)*/
- __tpl_wayland_surface_buffer_cache_remove_all(&wayland_display->cached_buffers);
if (reset_buffers != NULL)
*reset_buffers = TPL_TRUE;
}
TPL_OBJECT_UNLOCK(surface);
- TPL_LOG(6, "Wait until dequeable | tsq_err = %d", tsq_err);
while(tbm_surface_queue_can_dequeue(wayland_surface->tbm_queue, 0) == 0)
{
/* Application sent all buffers to the server. Wait for server response. */
tbm_surface_internal_ref(tbm_surface);
- /* Get tbm_bo from tbm_surface_h */
- bo = tbm_surface_internal_get_bo(tbm_surface, 0);
- if (NULL == bo)
- {
- TPL_ERR("TBM get bo failed!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- key = tbm_bo_export(bo);
-
- buffer = __tpl_wayland_surface_buffer_cache_find(&wayland_display->cached_buffers, key);
- if (buffer != NULL)
- {
- return buffer;
- }
-
- width = tbm_surface_get_width(tbm_surface);
- height = tbm_surface_get_height(tbm_surface);
-
- switch(tbm_surface_get_format(tbm_surface))
- {
- case TBM_FORMAT_ARGB8888: tpl_format = TPL_FORMAT_ARGB8888; break;
- case TBM_FORMAT_XRGB8888: tpl_format = TPL_FORMAT_XRGB8888; break;
- case TBM_FORMAT_RGB565: tpl_format = TPL_FORMAT_RGB565; break;
- default:
- tpl_format = TPL_FORMAT_INVALID;
- TPL_ERR("No matched format!!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- depth = __tpl_wayland_get_depth_from_format(tpl_format);
-
- /* Get pitch stride from tbm_surface */
- tbm_surface_internal_get_plane_data(tbm_surface, 0, &size, &offset, &stride);
-
- /* Create tpl buffer. */
- bo_handle = tbm_bo_get_handle(bo, TBM_DEVICE_3D);
- if (bo_handle.ptr == NULL)
+ if ((wayland_buffer = __tpl_wayland_get_wayland_buffer_from_tbm_surface(tbm_surface)) != NULL)
{
- TPL_ERR("TBM bo get handle failed!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- buffer = __tpl_buffer_alloc(surface, (size_t) key,
- (int)bo_handle.u32, width, height, depth, stride);
-
- if (buffer == NULL)
- {
- TPL_ERR("Failed to allocate tpl buffer | surf:%p bo_hnd:%d WxHxD:%dx%dx%d",
- surface, (int) bo_handle.u32, width, height, depth);
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
+ return tbm_surface;
}
wayland_buffer = (tpl_wayland_buffer_t *) calloc(1, sizeof(tpl_wayland_buffer_t));
if (wayland_buffer == NULL)
{
TPL_ERR("Mem alloc for wayland_buffer failed!");
- tpl_object_unreference((tpl_object_t *) buffer);
tbm_surface_internal_unref(tbm_surface);
return NULL;
}
- buffer->backend.data = (void *)wayland_buffer;
-
- if (TPL_TRUE != __tpl_wayland_surface_buffer_cache_add(&wayland_display->cached_buffers, buffer))
- {
- TPL_ERR("Adding surface to buffer cache failed!");
- tpl_object_unreference((tpl_object_t *) buffer);
- tbm_surface_internal_unref(tbm_surface);
- free(wayland_buffer);
- return NULL;
- }
-
- wl_proxy = (struct wl_proxy *)wayland_tbm_client_create_buffer(wayland_display->wl_tbm_client,
- tbm_surface);
+ wl_proxy = (struct wl_proxy *)wayland_tbm_client_create_buffer(
+ wayland_display->wl_tbm_client,
+ tbm_surface);
if (wl_proxy == NULL)
{
TPL_ERR("Failed to create TBM client buffer!");
tbm_surface_internal_unref(tbm_surface);
- tpl_object_unreference((tpl_object_t *)buffer);
free(wayland_buffer);
return NULL;
}
wl_proxy_set_queue(wl_proxy, wayland_display->wl_queue);
- wl_buffer_add_listener((void *)wl_proxy, &buffer_release_listener, buffer);
+ wl_buffer_add_listener((void *)wl_proxy, &buffer_release_listener, tbm_surface);
wl_display_flush((struct wl_display *)surface->display->native_handle);
wayland_buffer->display = surface->display;
- wayland_buffer->tbm_surface = tbm_surface;
wayland_buffer->wl_proxy = wl_proxy;
- wayland_buffer->bo = bo;
-
- wayland_surface = (tpl_wayland_surface_t*) surface->backend.data;
-
- if (reset_buffers != NULL)
- *reset_buffers = TPL_FALSE;
-
- TPL_LOG(3, "buffer:%p bo_hnd:%d, %dx%d", buffer, (int) bo_handle.u32, width, height);
-
- return buffer;
-}
-
-static int tpl_buffer_key;
-#define KEY_TPL_BUFFER (unsigned long)(&tpl_buffer_key)
-
-static inline tpl_buffer_t *
-__tpl_wayland_surface_get_buffer_from_tbm_surface(tbm_surface_h surface)
-{
- tbm_bo bo;
- tpl_buffer_t* buf=NULL;
-
- bo = tbm_surface_internal_get_bo(surface, 0);
- tbm_bo_get_user_data(bo, KEY_TPL_BUFFER, (void **)&buf);
-
- return buf;
-}
-#if 0
-static inline void
-__tpl_wayland_buffer_set_tbm_surface(tbm_surface_h surface, tpl_buffer_t *buf)
-{
- tbm_bo bo;
-
- bo = tbm_surface_internal_get_bo(surface, 0);
- tbm_bo_add_user_data(bo, KEY_TPL_BUFFER, NULL);
- tbm_bo_set_user_data(bo, KEY_TPL_BUFFER, buf);
-}
-#endif
-
-static tpl_buffer_t *
-__tpl_wayland_surface_create_buffer_from_wl_tbm(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
-{
- tpl_buffer_t *buffer = NULL;
- tpl_wayland_buffer_t *wayland_buffer = NULL;
- tbm_surface_h tbm_surface = NULL;
- /* TODO: If HW support getting of gem memory size,
- use tbm_surface_get_info() with tbm_surface_info_s */
-#if 0
- tbm_surface_info_s tbm_surf_info;
-#endif
- tbm_bo bo;
- tbm_bo_handle bo_handle;
-
- int width = 0, height = 0, depth;
- uint32_t size, offset, stride;
- tpl_format_t format = TPL_FORMAT_INVALID;
- size_t key = 0;
-
- TPL_ASSERT(surface);
- TPL_ASSERT(surface->display);
- TPL_ASSERT(surface->native_handle);
-
- tbm_surface = wayland_tbm_server_get_surface(NULL, (struct wl_resource*)surface->native_handle);
- if (tbm_surface == NULL)
- {
- TPL_ERR("Failed to get tbm surface!");
- return NULL;
- }
-
- bo = tbm_surface_internal_get_bo(tbm_surface, 0);
- key = tbm_bo_export(bo);
+ wayland_buffer->bo = tbm_surface_internal_get_bo(tbm_surface, 0);
+ wayland_buffer->wayland_surface = wayland_surface;
- /* Inc ref count about tbm_surface */
- /* It will be dec when wayland_buffer_fini called*/
- tbm_surface_internal_ref(tbm_surface);
+ __tpl_wayland_set_wayland_buffer_to_tbm_surface(tbm_surface, wayland_buffer);
- if (TPL_TRUE != __tpl_wayland_display_get_pixmap_info(
- surface->display,
- surface->native_handle,
- &width, &height, &format))
- {
- TPL_ERR("Failed to get pixmap info!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
- /* TODO: If HW support getting of gem memory size,
- then replace tbm_surface_internal_get_plane_data() to tbm_surface_get_info() */
-#if 0
- if (tbm_surface_get_info(tbm_surface, &tbm_surf_info) != 0)
- {
- TPL_ERR("Failed to get stride info!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
- stride = tbm_surf_info.planes[0].stride;
-#else
- if (!tbm_surface_internal_get_plane_data(tbm_surface, 0, &size, &offset, &stride))
- {
- TPL_ERR("Failed to get tbm_surface stride info!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-#endif
- depth = __tpl_wayland_get_depth_from_format(format);
-
- /* Create tpl buffer. */
- bo_handle = tbm_bo_get_handle(bo, TBM_DEVICE_3D);
- if (NULL == bo_handle.ptr)
- {
- TPL_ERR("Failed to get bo handle!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- buffer = __tpl_buffer_alloc(surface, key,
- (int) bo_handle.u32, width, height, depth, stride);
- if (buffer == NULL)
- {
- TPL_ERR("Failed to alloc TPL buffer!");
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- wayland_buffer = (tpl_wayland_buffer_t *) calloc(1, sizeof(tpl_wayland_buffer_t));
- if (wayland_buffer == NULL)
- {
- TPL_ERR("Mem alloc failed for wayland buffer!");
- tpl_object_unreference((tpl_object_t *) buffer);
- tbm_surface_internal_unref(tbm_surface);
- return NULL;
- }
-
- wayland_buffer->display = surface->display;
- wayland_buffer->bo = bo;
- wayland_buffer->tbm_surface = tbm_surface;
- wayland_buffer->tpl_buffer = buffer;
-
- buffer->backend.data = (void *)wayland_buffer;
- buffer->key = key;
-
- if (reset_buffers != NULL)
- *reset_buffers = TPL_FALSE;
-
- return buffer;
-}
-
-static tpl_buffer_t *
-__tpl_wayland_surface_get_buffer(tpl_surface_t *surface, tpl_bool_t *reset_buffers)
-{
- int width, height;
- tpl_wayland_surface_t *wayland_surface;
-
- TPL_ASSERT(surface);
- TPL_ASSERT(surface->backend.data);
-
- wayland_surface = (tpl_wayland_surface_t *)surface->backend.data;
-
- if (reset_buffers != NULL)
- *reset_buffers = TPL_FALSE;
-
- TPL_LOG(3, "window(%p, %p), current(%p)", surface, surface->native_handle,
- wayland_surface->current_rendering_buffer);
-
- if (surface->type != TPL_SURFACE_TYPE_PIXMAP &&
- TPL_TRUE != __tpl_wayland_display_get_window_info(surface->display,
- surface->native_handle, &width, &height, NULL, 0, 0))
- {
- TPL_ERR("Failed to get window info!");
- return NULL;
- }
-
- if (wayland_surface->resized || wayland_surface->current_rendering_buffer == NULL)
- {
- if (surface->type == TPL_SURFACE_TYPE_WINDOW)
- {
- wayland_surface->current_rendering_buffer =
- __tpl_wayland_surface_create_buffer_from_wl_egl(surface, reset_buffers);
- }
- if (surface->type == TPL_SURFACE_TYPE_PIXMAP)
- {
- wayland_surface->current_rendering_buffer =
- __tpl_wayland_surface_create_buffer_from_wl_tbm(surface, reset_buffers);
- }
- TPL_LOG(3, "window(%p, %p), current(%p)", surface, surface->native_handle,
- wayland_surface->current_rendering_buffer);
- }
-
- TPL_ASSERT(wayland_surface->current_rendering_buffer);
-
- return wayland_surface->current_rendering_buffer;
-}
-
-static tpl_bool_t
-__tpl_wayland_buffer_init(tpl_buffer_t *buffer)
-{
- TPL_IGNORE(buffer);
-
- return TPL_TRUE;
+ return tbm_surface;
}
static void
-__tpl_wayland_buffer_fini(tpl_buffer_t *buffer)
-{
- TPL_ASSERT(buffer);
-
- TPL_LOG(3, "tpl_buffer(%p) key:%zu fd:%d %dx%d", buffer, buffer->key, buffer->fd, buffer->width, buffer->height);
-
- if (buffer->backend.data)
- {
- tpl_wayland_buffer_t *wayland_buffer = (tpl_wayland_buffer_t *)buffer->backend.data;
-
- tpl_wayland_display_t *wayland_display =
- (tpl_wayland_display_t *)wayland_buffer->display->backend.data;
-
- if (wayland_buffer->bo != NULL && wayland_buffer->tbm_surface != NULL)
- {
- tbm_surface_internal_unref(wayland_buffer->tbm_surface);
- tbm_surface_destroy(wayland_buffer->tbm_surface);
- wayland_buffer->bo = NULL;
- wayland_buffer->tbm_surface = NULL;
- }
-
- wl_display_flush((struct wl_display *)wayland_buffer->display->native_handle);
-
- if (wayland_buffer->wl_proxy != NULL)
- wayland_tbm_client_destroy_buffer(wayland_display->wl_tbm_client, (void *)wayland_buffer->wl_proxy);
-
- buffer->backend.data = NULL;
- free(wayland_buffer);
- }
-}
-
-static void *
-__tpl_wayland_buffer_map(tpl_buffer_t *buffer, int size)
+__tpl_wayland_buffer_free(tpl_wayland_buffer_t *wayland_buffer)
{
- tpl_wayland_buffer_t *wayland_buffer;
- tbm_bo_handle handle;
+ TPL_ASSERT(wayland_buffer);
+ TPL_ASSERT(wayland_buffer->display);
- TPL_ASSERT(buffer);
- TPL_ASSERT(buffer->backend.data);
+ tpl_wayland_display_t *wayland_display =
+ (tpl_wayland_display_t *)wayland_buffer->display->backend.data;
- wayland_buffer = (tpl_wayland_buffer_t *) buffer->backend.data;
+ wl_display_flush((struct wl_display *)wayland_buffer->display->native_handle);
- TPL_ASSERT(wayland_buffer->bo);
+ if (wayland_buffer->wl_proxy != NULL)
+ wayland_tbm_client_destroy_buffer(wayland_display->wl_tbm_client, (void *)wayland_buffer->wl_proxy);
- handle = tbm_bo_get_handle(wayland_buffer->bo, TBM_DEVICE_CPU);
- return handle.ptr;
-}
-
-static void
-__tpl_wayland_buffer_unmap(tpl_buffer_t *buffer, void *ptr, int size)
-{
- TPL_IGNORE(buffer);
- TPL_IGNORE(ptr);
- TPL_IGNORE(size);
-
- /* Do nothing. */
-}
-
-static tpl_bool_t
-__tpl_wayland_buffer_lock(tpl_buffer_t *buffer, tpl_lock_usage_t usage)
-{
- tpl_wayland_buffer_t *wayland_buffer;
- tbm_bo_handle handle;
-
- TPL_ASSERT(buffer);
- TPL_ASSERT(buffer->backend.data);
-
- wayland_buffer = (tpl_wayland_buffer_t *) buffer->backend.data;
-
- TPL_ASSERT(wayland_buffer->bo);
-
- TPL_OBJECT_UNLOCK(buffer);
-
- switch (usage)
- {
- case TPL_LOCK_USAGE_GPU_READ:
- handle = tbm_bo_map(wayland_buffer->bo, TBM_DEVICE_3D, TBM_OPTION_READ);
- break;
- case TPL_LOCK_USAGE_GPU_WRITE:
- handle = tbm_bo_map(wayland_buffer->bo, TBM_DEVICE_3D, TBM_OPTION_WRITE);
- break;
- case TPL_LOCK_USAGE_CPU_READ:
- handle = tbm_bo_map(wayland_buffer->bo, TBM_DEVICE_CPU, TBM_OPTION_READ);
- break;
- case TPL_LOCK_USAGE_CPU_WRITE:
- handle = tbm_bo_map(wayland_buffer->bo, TBM_DEVICE_CPU, TBM_OPTION_WRITE);
- break;
- default:
- TPL_ERR("Unsupported buffer usage!");
- TPL_OBJECT_LOCK(buffer);
- return TPL_FALSE;
- }
-
- TPL_OBJECT_LOCK(buffer);
-
- if (handle.u32 != 0 || handle.ptr != NULL)
- return TPL_FALSE;
-
- return TPL_TRUE;
-}
-
-static void
-__tpl_wayland_buffer_unlock(tpl_buffer_t *buffer)
-{
- tpl_wayland_buffer_t *wayland_buffer;
-
- TPL_ASSERT(buffer);
- TPL_ASSERT(buffer->backend.data);
-
- wayland_buffer = (tpl_wayland_buffer_t *) buffer->backend.data;
-
- TPL_ASSERT(wayland_buffer->bo);
-
- TPL_OBJECT_UNLOCK(buffer);
- tbm_bo_unmap(wayland_buffer->bo);
- TPL_OBJECT_LOCK(buffer);
+ free(wayland_buffer);
}
tpl_bool_t
backend->fini = __tpl_wayland_display_fini;
backend->query_config = __tpl_wayland_display_query_config;
backend->filter_config = __tpl_wayland_display_filter_config;
- backend->get_window_info = __tpl_wayland_display_get_window_info;
- backend->get_pixmap_info = __tpl_wayland_display_get_pixmap_info;
+ backend->get_window_info = __tpl_wayland_display_get_window_info;
+ backend->get_pixmap_info = NULL;
backend->flush = __tpl_wayland_display_flush;
backend->bind_client_display_handle = NULL;
backend->unbind_client_display_handle = NULL;
backend->validate_frame = __tpl_wayland_surface_validate_frame;
backend->get_buffer = __tpl_wayland_surface_get_buffer;
backend->post = __tpl_wayland_surface_post;
- backend->destroy_cached_buffers = __tpl_wayland_surface_destroy_cached_buffers;
- backend->update_cached_buffers = __tpl_wayland_surface_update_cached_buffers;
-}
-
-void
-__tpl_buffer_init_backend_wayland(tpl_buffer_backend_t *backend)
-{
- TPL_ASSERT(backend);
-
- backend->type = TPL_BACKEND_WAYLAND;
- backend->data = NULL;
-
- backend->init = __tpl_wayland_buffer_init;
- backend->fini = __tpl_wayland_buffer_fini;
- backend->map = __tpl_wayland_buffer_map;
- backend->unmap = __tpl_wayland_buffer_unmap;
- backend->lock = __tpl_wayland_buffer_lock;
- backend->unlock = __tpl_wayland_buffer_unlock;
- backend->create_native_buffer = NULL;
+ backend->destroy_cached_buffers = NULL;
+ backend->update_cached_buffers = NULL;
}
static void
static void
__cb_client_buffer_release_callback(void *data, struct wl_proxy *proxy)
{
- tpl_buffer_t *tpl_buffer;
- tpl_surface_t *surface;
- tpl_wayland_surface_t *wayland_surface;
+ tpl_wayland_surface_t *wayland_surface = NULL;
+ tpl_wayland_buffer_t *wayland_buffer = NULL;
+ tbm_surface_h tbm_surface = NULL;
TPL_ASSERT(data);
- tpl_buffer = (tpl_buffer_t *) data;
- surface = tpl_buffer->surface;
- wayland_surface = (tpl_wayland_surface_t *)surface->backend.data;
+ tbm_surface = (tbm_surface_h) data;
- TPL_LOG(3, "release window(%p, %p), buffer(%p), key:%zu",
- surface, surface?surface->native_handle:NULL,
- tpl_buffer, tpl_buffer->key);
+ wayland_buffer = __tpl_wayland_get_wayland_buffer_from_tbm_surface(tbm_surface);
- if (surface != NULL)
+ if (wayland_buffer != NULL)
{
- TPL_OBJECT_LOCK(surface);
-
- tpl_wayland_buffer_t *wayland_buffer = (tpl_wayland_buffer_t*) tpl_buffer->backend.data;
- tbm_surface_internal_unref(wayland_buffer->tbm_surface);
- tbm_surface_queue_release(wayland_surface->tbm_queue, wayland_buffer->tbm_surface);
- TPL_LOG(7, "BO:%d", tbm_bo_export(wayland_buffer->bo));
+ wayland_surface = wayland_buffer->wayland_surface;
- TPL_OBJECT_UNLOCK(surface);
+ tbm_surface_internal_unref(tbm_surface);
+ tbm_surface_queue_release(wayland_surface->tbm_queue, tbm_surface);
}
-
- tpl_object_unreference((tpl_object_t *)tpl_buffer);
}
static const struct wl_buffer_listener buffer_release_listener = {