mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-05 07:28:11 +02:00
mesa/st: merge framebuffer objects from st to mesa
Reviewed-by: Kristian H. Kristensen <hoegsberg@google.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/14675>
This commit is contained in:
parent
21d4dd8c39
commit
7645e24045
7 changed files with 69 additions and 90 deletions
|
|
@ -60,6 +60,8 @@
|
|||
|
||||
#include "pipe/p_state.h"
|
||||
|
||||
#include "frontend/api.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
|
@ -2731,6 +2733,16 @@ struct gl_framebuffer
|
|||
|
||||
/** Delete this framebuffer */
|
||||
void (*Delete)(struct gl_framebuffer *fb);
|
||||
|
||||
struct st_framebuffer_iface *iface;
|
||||
enum st_attachment_type statts[ST_ATTACHMENT_COUNT];
|
||||
unsigned num_statts;
|
||||
int32_t stamp;
|
||||
int32_t iface_stamp;
|
||||
uint32_t iface_ID;
|
||||
|
||||
/* list of framebuffer objects */
|
||||
struct list_head head;
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -46,18 +46,18 @@ st_get_renderbuffer_resource(struct gl_renderbuffer *rb)
|
|||
}
|
||||
|
||||
/**
|
||||
* Cast wrapper to convert a struct gl_framebuffer to an st_framebuffer.
|
||||
* Cast wrapper to convert a struct gl_framebuffer to an gl_framebuffer.
|
||||
* Return NULL if the struct gl_framebuffer is a user-created framebuffer.
|
||||
* We'll only return non-null for window system framebuffers.
|
||||
* Note that this function may fail.
|
||||
*/
|
||||
static inline struct st_framebuffer *
|
||||
static inline struct gl_framebuffer *
|
||||
st_ws_framebuffer(struct gl_framebuffer *fb)
|
||||
{
|
||||
/* FBO cannot be casted. See st_new_framebuffer */
|
||||
if (fb && _mesa_is_winsys_fbo(fb) &&
|
||||
fb != _mesa_get_incomplete_framebuffer())
|
||||
return (struct st_framebuffer *) fb;
|
||||
return fb;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -37,8 +37,8 @@
|
|||
void st_viewport(struct gl_context *ctx)
|
||||
{
|
||||
struct st_context *st = ctx->st;
|
||||
struct st_framebuffer *stdraw;
|
||||
struct st_framebuffer *stread;
|
||||
struct gl_framebuffer *stdraw;
|
||||
struct gl_framebuffer *stread;
|
||||
|
||||
if (!st->invalidate_on_gl_viewport)
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -29,6 +29,7 @@
|
|||
#include "main/accum.h"
|
||||
#include "main/context.h"
|
||||
#include "main/debug_output.h"
|
||||
#include "main/framebuffer.h"
|
||||
#include "main/glthread.h"
|
||||
#include "main/shaderobj.h"
|
||||
#include "main/state.h"
|
||||
|
|
@ -932,7 +933,7 @@ void
|
|||
st_destroy_context(struct st_context *st)
|
||||
{
|
||||
struct gl_context *ctx = st->ctx;
|
||||
struct st_framebuffer *stfb, *next;
|
||||
struct gl_framebuffer *stfb, *next;
|
||||
struct gl_framebuffer *save_drawbuffer;
|
||||
struct gl_framebuffer *save_readbuffer;
|
||||
|
||||
|
|
@ -982,7 +983,7 @@ st_destroy_context(struct st_context *st)
|
|||
|
||||
/* release framebuffer in the winsys buffers list */
|
||||
LIST_FOR_EACH_ENTRY_SAFE_REV(stfb, next, &st->winsys_buffers, head) {
|
||||
st_framebuffer_reference(&stfb, NULL);
|
||||
_mesa_reference_framebuffer(&stfb, NULL);
|
||||
}
|
||||
|
||||
_mesa_HashWalk(ctx->Shared->FrameBuffers, destroy_framebuffer_attachment_sampler_cb, st);
|
||||
|
|
|
|||
|
|
@ -431,25 +431,6 @@ const struct nir_shader_compiler_options *
|
|||
st_get_nir_compiler_options(struct st_context *st, gl_shader_stage stage);
|
||||
|
||||
|
||||
/**
|
||||
* Wrapper for struct gl_framebuffer.
|
||||
* This is an opaque type to the outside world.
|
||||
*/
|
||||
struct st_framebuffer
|
||||
{
|
||||
struct gl_framebuffer Base;
|
||||
|
||||
struct st_framebuffer_iface *iface;
|
||||
enum st_attachment_type statts[ST_ATTACHMENT_COUNT];
|
||||
unsigned num_statts;
|
||||
int32_t stamp;
|
||||
int32_t iface_stamp;
|
||||
uint32_t iface_ID;
|
||||
|
||||
/* list of framebuffer objects */
|
||||
struct list_head head;
|
||||
};
|
||||
|
||||
void st_invalidate_state(struct gl_context *ctx);
|
||||
void st_set_background_context(struct gl_context *ctx,
|
||||
struct util_queue_monitoring *queue_info);
|
||||
|
|
|
|||
|
|
@ -29,6 +29,7 @@
|
|||
#include "main/extensions.h"
|
||||
#include "main/context.h"
|
||||
#include "main/debug_output.h"
|
||||
#include "main/framebuffer.h"
|
||||
#include "main/glthread.h"
|
||||
#include "main/texobj.h"
|
||||
#include "main/teximage.h"
|
||||
|
|
@ -150,23 +151,23 @@ buffer_index_to_attachment(gl_buffer_index index)
|
|||
*/
|
||||
static void
|
||||
st_context_validate(struct st_context *st,
|
||||
struct st_framebuffer *stdraw,
|
||||
struct st_framebuffer *stread)
|
||||
struct gl_framebuffer *stdraw,
|
||||
struct gl_framebuffer *stread)
|
||||
{
|
||||
if (stdraw && stdraw->stamp != st->draw_stamp) {
|
||||
st->dirty |= ST_NEW_FRAMEBUFFER;
|
||||
_mesa_resize_framebuffer(st->ctx, &stdraw->Base,
|
||||
stdraw->Base.Width,
|
||||
stdraw->Base.Height);
|
||||
_mesa_resize_framebuffer(st->ctx, stdraw,
|
||||
stdraw->Width,
|
||||
stdraw->Height);
|
||||
st->draw_stamp = stdraw->stamp;
|
||||
}
|
||||
|
||||
if (stread && stread->stamp != st->read_stamp) {
|
||||
if (stread != stdraw) {
|
||||
st->dirty |= ST_NEW_FRAMEBUFFER;
|
||||
_mesa_resize_framebuffer(st->ctx, &stread->Base,
|
||||
stread->Base.Width,
|
||||
stread->Base.Height);
|
||||
_mesa_resize_framebuffer(st->ctx, stread,
|
||||
stread->Width,
|
||||
stread->Height);
|
||||
}
|
||||
st->read_stamp = stread->stamp;
|
||||
}
|
||||
|
|
@ -202,7 +203,7 @@ st_set_ws_renderbuffer_surface(struct gl_renderbuffer *rb,
|
|||
* context).
|
||||
*/
|
||||
static void
|
||||
st_framebuffer_validate(struct st_framebuffer *stfb,
|
||||
st_framebuffer_validate(struct gl_framebuffer *stfb,
|
||||
struct st_context *st)
|
||||
{
|
||||
struct pipe_resource *textures[ST_ATTACHMENT_COUNT];
|
||||
|
|
@ -227,8 +228,8 @@ st_framebuffer_validate(struct st_framebuffer *stfb,
|
|||
new_stamp = p_atomic_read(&stfb->iface->stamp);
|
||||
} while(stfb->iface_stamp != new_stamp);
|
||||
|
||||
width = stfb->Base.Width;
|
||||
height = stfb->Base.Height;
|
||||
width = stfb->Width;
|
||||
height = stfb->Height;
|
||||
|
||||
for (i = 0; i < stfb->num_statts; i++) {
|
||||
struct gl_renderbuffer *rb;
|
||||
|
|
@ -244,7 +245,7 @@ st_framebuffer_validate(struct st_framebuffer *stfb,
|
|||
continue;
|
||||
}
|
||||
|
||||
rb = stfb->Base.Attachment[idx].Renderbuffer;
|
||||
rb = stfb->Attachment[idx].Renderbuffer;
|
||||
assert(rb);
|
||||
if (rb->texture == textures[i]) {
|
||||
pipe_resource_reference(&textures[i], NULL);
|
||||
|
|
@ -268,7 +269,7 @@ st_framebuffer_validate(struct st_framebuffer *stfb,
|
|||
|
||||
if (changed) {
|
||||
++stfb->stamp;
|
||||
_mesa_resize_framebuffer(st->ctx, &stfb->Base, width, height);
|
||||
_mesa_resize_framebuffer(st->ctx, stfb, width, height);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -277,7 +278,7 @@ st_framebuffer_validate(struct st_framebuffer *stfb,
|
|||
* Update the attachments to validate by looping the existing renderbuffers.
|
||||
*/
|
||||
static void
|
||||
st_framebuffer_update_attachments(struct st_framebuffer *stfb)
|
||||
st_framebuffer_update_attachments(struct gl_framebuffer *stfb)
|
||||
{
|
||||
gl_buffer_index idx;
|
||||
|
||||
|
|
@ -290,7 +291,7 @@ st_framebuffer_update_attachments(struct st_framebuffer *stfb)
|
|||
struct gl_renderbuffer *rb;
|
||||
enum st_attachment_type statt;
|
||||
|
||||
rb = stfb->Base.Attachment[idx].Renderbuffer;
|
||||
rb = stfb->Attachment[idx].Renderbuffer;
|
||||
if (!rb || rb->software)
|
||||
continue;
|
||||
|
||||
|
|
@ -308,14 +309,14 @@ st_framebuffer_update_attachments(struct st_framebuffer *stfb)
|
|||
* corresponds to a window and is not a user-created FBO.
|
||||
*/
|
||||
static bool
|
||||
st_framebuffer_add_renderbuffer(struct st_framebuffer *stfb,
|
||||
st_framebuffer_add_renderbuffer(struct gl_framebuffer *stfb,
|
||||
gl_buffer_index idx, bool prefer_srgb)
|
||||
{
|
||||
struct gl_renderbuffer *rb;
|
||||
enum pipe_format format;
|
||||
bool sw;
|
||||
|
||||
assert(_mesa_is_winsys_fbo(&stfb->Base));
|
||||
assert(_mesa_is_winsys_fbo(stfb));
|
||||
|
||||
/* do not distinguish depth/stencil buffers */
|
||||
if (idx == BUFFER_STENCIL)
|
||||
|
|
@ -346,21 +347,21 @@ st_framebuffer_add_renderbuffer(struct st_framebuffer *stfb,
|
|||
return false;
|
||||
|
||||
if (idx != BUFFER_DEPTH) {
|
||||
_mesa_attach_and_own_rb(&stfb->Base, idx, rb);
|
||||
_mesa_attach_and_own_rb(stfb, idx, rb);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool rb_ownership_taken = false;
|
||||
if (util_format_get_component_bits(format, UTIL_FORMAT_COLORSPACE_ZS, 0)) {
|
||||
_mesa_attach_and_own_rb(&stfb->Base, BUFFER_DEPTH, rb);
|
||||
_mesa_attach_and_own_rb(stfb, BUFFER_DEPTH, rb);
|
||||
rb_ownership_taken = true;
|
||||
}
|
||||
|
||||
if (util_format_get_component_bits(format, UTIL_FORMAT_COLORSPACE_ZS, 1)) {
|
||||
if (rb_ownership_taken)
|
||||
_mesa_attach_and_reference_rb(&stfb->Base, BUFFER_STENCIL, rb);
|
||||
_mesa_attach_and_reference_rb(stfb, BUFFER_STENCIL, rb);
|
||||
else
|
||||
_mesa_attach_and_own_rb(&stfb->Base, BUFFER_STENCIL, rb);
|
||||
_mesa_attach_and_own_rb(stfb, BUFFER_STENCIL, rb);
|
||||
}
|
||||
|
||||
return true;
|
||||
|
|
@ -435,11 +436,11 @@ st_visual_to_context_mode(const struct st_visual *visual,
|
|||
/**
|
||||
* Create a framebuffer from a manager interface.
|
||||
*/
|
||||
static struct st_framebuffer *
|
||||
static struct gl_framebuffer *
|
||||
st_framebuffer_create(struct st_context *st,
|
||||
struct st_framebuffer_iface *stfbi)
|
||||
{
|
||||
struct st_framebuffer *stfb;
|
||||
struct gl_framebuffer *stfb;
|
||||
struct gl_config mode;
|
||||
gl_buffer_index idx;
|
||||
bool prefer_srgb = false;
|
||||
|
|
@ -447,7 +448,7 @@ st_framebuffer_create(struct st_context *st,
|
|||
if (!stfbi)
|
||||
return NULL;
|
||||
|
||||
stfb = CALLOC_STRUCT(st_framebuffer);
|
||||
stfb = CALLOC_STRUCT(gl_framebuffer);
|
||||
if (!stfb)
|
||||
return NULL;
|
||||
|
||||
|
|
@ -493,14 +494,14 @@ st_framebuffer_create(struct st_context *st,
|
|||
}
|
||||
}
|
||||
|
||||
_mesa_initialize_window_framebuffer(&stfb->Base, &mode);
|
||||
_mesa_initialize_window_framebuffer(stfb, &mode);
|
||||
|
||||
stfb->iface = stfbi;
|
||||
stfb->iface_ID = stfbi->ID;
|
||||
stfb->iface_stamp = p_atomic_read(&stfbi->stamp) - 1;
|
||||
|
||||
/* add the color buffer */
|
||||
idx = stfb->Base._ColorDrawBufferIndexes[0];
|
||||
idx = stfb->_ColorDrawBufferIndexes[0];
|
||||
if (!st_framebuffer_add_renderbuffer(stfb, idx, prefer_srgb)) {
|
||||
FREE(stfb);
|
||||
return NULL;
|
||||
|
|
@ -516,18 +517,6 @@ st_framebuffer_create(struct st_context *st,
|
|||
}
|
||||
|
||||
|
||||
/**
|
||||
* Reference a framebuffer.
|
||||
*/
|
||||
void
|
||||
st_framebuffer_reference(struct st_framebuffer **ptr,
|
||||
struct st_framebuffer *stfb)
|
||||
{
|
||||
struct gl_framebuffer *fb = stfb ? &stfb->Base : NULL;
|
||||
_mesa_reference_framebuffer((struct gl_framebuffer **) ptr, fb);
|
||||
}
|
||||
|
||||
|
||||
static uint32_t
|
||||
st_framebuffer_iface_hash(const void *key)
|
||||
{
|
||||
|
|
@ -627,7 +616,7 @@ st_framebuffers_purge(struct st_context *st)
|
|||
{
|
||||
struct st_context_iface *st_iface = &st->iface;
|
||||
struct st_manager *smapi = st_iface->state_manager;
|
||||
struct st_framebuffer *stfb, *next;
|
||||
struct gl_framebuffer *stfb, *next;
|
||||
|
||||
assert(smapi);
|
||||
|
||||
|
|
@ -644,7 +633,7 @@ st_framebuffers_purge(struct st_context *st)
|
|||
*/
|
||||
if (!st_framebuffer_iface_lookup(smapi, stfbi)) {
|
||||
list_del(&stfb->head);
|
||||
st_framebuffer_reference(&stfb, NULL);
|
||||
_mesa_reference_framebuffer(&stfb, NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1023,12 +1012,12 @@ st_api_get_current(struct st_api *stapi)
|
|||
}
|
||||
|
||||
|
||||
static struct st_framebuffer *
|
||||
static struct gl_framebuffer *
|
||||
st_framebuffer_reuse_or_create(struct st_context *st,
|
||||
struct gl_framebuffer *fb,
|
||||
struct st_framebuffer_iface *stfbi)
|
||||
{
|
||||
struct st_framebuffer *cur = NULL, *stfb = NULL;
|
||||
struct gl_framebuffer *cur = NULL, *stfb = NULL;
|
||||
|
||||
if (!stfbi)
|
||||
return NULL;
|
||||
|
|
@ -1038,7 +1027,7 @@ st_framebuffer_reuse_or_create(struct st_context *st,
|
|||
*/
|
||||
LIST_FOR_EACH_ENTRY(cur, &st->winsys_buffers, head) {
|
||||
if (cur->iface_ID == stfbi->ID) {
|
||||
st_framebuffer_reference(&stfb, cur);
|
||||
_mesa_reference_framebuffer(&stfb, cur);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
@ -1052,14 +1041,14 @@ st_framebuffer_reuse_or_create(struct st_context *st,
|
|||
* the framebuffer interface object hash table.
|
||||
*/
|
||||
if (!st_framebuffer_iface_insert(stfbi->state_manager, stfbi)) {
|
||||
st_framebuffer_reference(&cur, NULL);
|
||||
_mesa_reference_framebuffer(&cur, NULL);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* add to the context's winsys buffers list */
|
||||
list_add(&cur->head, &st->winsys_buffers);
|
||||
|
||||
st_framebuffer_reference(&stfb, cur);
|
||||
_mesa_reference_framebuffer(&stfb, cur);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1073,7 +1062,7 @@ st_api_make_current(struct st_api *stapi, struct st_context_iface *stctxi,
|
|||
struct st_framebuffer_iface *streadi)
|
||||
{
|
||||
struct st_context *st = (struct st_context *) stctxi;
|
||||
struct st_framebuffer *stdraw, *stread;
|
||||
struct gl_framebuffer *stdraw, *stread;
|
||||
bool ret;
|
||||
|
||||
if (st) {
|
||||
|
|
@ -1089,7 +1078,7 @@ st_api_make_current(struct st_api *stapi, struct st_context_iface *stctxi,
|
|||
stread = NULL;
|
||||
/* reuse the draw fb for the read fb */
|
||||
if (stdraw)
|
||||
st_framebuffer_reference(&stread, stdraw);
|
||||
_mesa_reference_framebuffer(&stread, stdraw);
|
||||
}
|
||||
|
||||
/* If framebuffers were asked for, we'd better have allocated them */
|
||||
|
|
@ -1101,7 +1090,7 @@ st_api_make_current(struct st_api *stapi, struct st_context_iface *stctxi,
|
|||
if (stread != stdraw)
|
||||
st_framebuffer_validate(stread, st);
|
||||
|
||||
ret = _mesa_make_current(st->ctx, &stdraw->Base, &stread->Base);
|
||||
ret = _mesa_make_current(st->ctx, stdraw, stread);
|
||||
|
||||
st->draw_stamp = stdraw->stamp - 1;
|
||||
st->read_stamp = stread->stamp - 1;
|
||||
|
|
@ -1112,8 +1101,8 @@ st_api_make_current(struct st_api *stapi, struct st_context_iface *stctxi,
|
|||
ret = _mesa_make_current(st->ctx, incomplete, incomplete);
|
||||
}
|
||||
|
||||
st_framebuffer_reference(&stdraw, NULL);
|
||||
st_framebuffer_reference(&stread, NULL);
|
||||
_mesa_reference_framebuffer(&stdraw, NULL);
|
||||
_mesa_reference_framebuffer(&stread, NULL);
|
||||
|
||||
/* Purge the context's winsys_buffers list in case any
|
||||
* of the referenced drawables no longer exist.
|
||||
|
|
@ -1152,7 +1141,7 @@ st_api_destroy(struct st_api *stapi)
|
|||
void
|
||||
st_manager_flush_frontbuffer(struct st_context *st)
|
||||
{
|
||||
struct st_framebuffer *stfb = st_ws_framebuffer(st->ctx->DrawBuffer);
|
||||
struct gl_framebuffer *stfb = st_ws_framebuffer(st->ctx->DrawBuffer);
|
||||
struct gl_renderbuffer *rb = NULL;
|
||||
|
||||
if (!stfb)
|
||||
|
|
@ -1163,16 +1152,16 @@ st_manager_flush_frontbuffer(struct st_context *st)
|
|||
* flushing.
|
||||
*/
|
||||
if (st->ctx->Visual.doubleBufferMode &&
|
||||
!stfb->Base.Visual.doubleBufferMode)
|
||||
!stfb->Visual.doubleBufferMode)
|
||||
return;
|
||||
|
||||
/* Check front buffer used at the GL API level. */
|
||||
enum st_attachment_type statt = ST_ATTACHMENT_FRONT_LEFT;
|
||||
rb = stfb->Base.Attachment[BUFFER_FRONT_LEFT].Renderbuffer;
|
||||
rb = stfb->Attachment[BUFFER_FRONT_LEFT].Renderbuffer;
|
||||
if (!rb) {
|
||||
/* Check back buffer redirected by EGL_KHR_mutable_render_buffer. */
|
||||
statt = ST_ATTACHMENT_BACK_LEFT;
|
||||
rb = stfb->Base.Attachment[BUFFER_BACK_LEFT].Renderbuffer;
|
||||
rb = stfb->Attachment[BUFFER_BACK_LEFT].Renderbuffer;
|
||||
}
|
||||
|
||||
/* Do we have a front color buffer and has it been drawn to since last
|
||||
|
|
@ -1194,8 +1183,8 @@ st_manager_flush_frontbuffer(struct st_context *st)
|
|||
void
|
||||
st_manager_validate_framebuffers(struct st_context *st)
|
||||
{
|
||||
struct st_framebuffer *stdraw = st_ws_framebuffer(st->ctx->DrawBuffer);
|
||||
struct st_framebuffer *stread = st_ws_framebuffer(st->ctx->ReadBuffer);
|
||||
struct gl_framebuffer *stdraw = st_ws_framebuffer(st->ctx->DrawBuffer);
|
||||
struct gl_framebuffer *stread = st_ws_framebuffer(st->ctx->ReadBuffer);
|
||||
|
||||
if (stdraw)
|
||||
st_framebuffer_validate(stdraw, st);
|
||||
|
|
@ -1214,7 +1203,7 @@ st_manager_flush_swapbuffers(void)
|
|||
{
|
||||
GET_CURRENT_CONTEXT(ctx);
|
||||
struct st_context *st = (ctx) ? ctx->st : NULL;
|
||||
struct st_framebuffer *stfb;
|
||||
struct gl_framebuffer *stfb;
|
||||
|
||||
if (!st)
|
||||
return;
|
||||
|
|
@ -1236,7 +1225,7 @@ st_manager_add_color_renderbuffer(struct st_context *st,
|
|||
struct gl_framebuffer *fb,
|
||||
gl_buffer_index idx)
|
||||
{
|
||||
struct st_framebuffer *stfb = st_ws_framebuffer(fb);
|
||||
struct gl_framebuffer *stfb = st_ws_framebuffer(fb);
|
||||
|
||||
/* FBO */
|
||||
if (!stfb)
|
||||
|
|
@ -1244,7 +1233,7 @@ st_manager_add_color_renderbuffer(struct st_context *st,
|
|||
|
||||
assert(_mesa_is_winsys_fbo(fb));
|
||||
|
||||
if (stfb->Base.Attachment[idx].Renderbuffer)
|
||||
if (stfb->Attachment[idx].Renderbuffer)
|
||||
return true;
|
||||
|
||||
switch (idx) {
|
||||
|
|
@ -1258,7 +1247,7 @@ st_manager_add_color_renderbuffer(struct st_context *st,
|
|||
}
|
||||
|
||||
if (!st_framebuffer_add_renderbuffer(stfb, idx,
|
||||
stfb->Base.Visual.sRGBCapable))
|
||||
stfb->Visual.sRGBCapable))
|
||||
return false;
|
||||
|
||||
st_framebuffer_update_attachments(stfb);
|
||||
|
|
|
|||
|
|
@ -48,10 +48,6 @@ bool
|
|||
st_manager_add_color_renderbuffer(struct st_context *st, struct gl_framebuffer *fb,
|
||||
gl_buffer_index idx);
|
||||
|
||||
void
|
||||
st_framebuffer_reference(struct st_framebuffer **ptr,
|
||||
struct st_framebuffer *stfb);
|
||||
|
||||
void
|
||||
st_framebuffer_interface_destroy(struct st_framebuffer_interface *stfbi);
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue