static void drm_destroy( struct d3dadapter9_context *ctx ) { struct d3dadapter9drm_context *drm = (struct d3dadapter9drm_context *)ctx; /* pipe_loader_sw destroys the context */ if (drm->swdev) { pipe_loader_release(&drm->swdev, 1); } pipe_loader_release(&drm->dev, 1); FREE(ctx); }
static void vl_dri3_screen_destroy(struct vl_screen *vscreen) { struct vl_dri3_screen *scrn = (struct vl_dri3_screen *)vscreen; int i; assert(vscreen); dri3_flush_present_events(scrn); if (scrn->front_buffer) { dri3_free_front_buffer(scrn, scrn->front_buffer); scrn->front_buffer = NULL; return; } for (i = 0; i < BACK_BUFFER_NUM; ++i) { if (scrn->back_buffers[i]) { dri3_free_back_buffer(scrn, scrn->back_buffers[i]); scrn->back_buffers[i] = NULL; } } if (scrn->special_event) xcb_unregister_for_special_event(scrn->conn, scrn->special_event); scrn->base.pscreen->destroy(scrn->base.pscreen); pipe_loader_release(&scrn->base.dev, 1); FREE(scrn); return; }
void gallium_screen_destroy(struct gbm_gallium_drm_device *gdrm) { FREE(gdrm->base.driver_name); gdrm->screen->destroy(gdrm->screen); pipe_loader_release((struct pipe_loader_device **)&gdrm->driver, 1); }
static void vl_drm_screen_destroy(struct vl_screen *vscreen) { assert(vscreen); vscreen->pscreen->destroy(vscreen->pscreen); pipe_loader_release(&vscreen->dev, 1); FREE(vscreen); }
XA_EXPORT void xa_tracker_destroy(struct xa_tracker *xa) { free(xa->supported_formats); xa_context_destroy(xa->default_ctx); xa->screen->destroy(xa->screen); pipe_loader_release(&xa->dev, 1); free(xa); }
static void drm_destroy( struct d3dadapter9_context *ctx ) { struct d3dadapter9drm_context *drm = (struct d3dadapter9drm_context *)ctx; if (ctx->ref) ctx->ref->destroy(ctx->ref); /* because ref is a wrapper around hal, freeing ref frees hal too. */ else if (ctx->hal) ctx->hal->destroy(ctx->hal); if (drm->swdev) pipe_loader_release(&drm->swdev, 1); if (drm->dev) pipe_loader_release(&drm->dev, 1); close(drm->fd); FREE(ctx); }
XA_EXPORT void xa_tracker_destroy(struct xa_tracker *xa) { free(xa->supported_formats); xa_context_destroy(xa->default_ctx); xa->screen->destroy(xa->screen); #if !GALLIUM_STATIC_TARGETS pipe_loader_release(&xa->dev, 1); #endif free(xa); }
void dri_destroy_screen(__DRIscreen * sPriv) { struct dri_screen *screen = dri_screen(sPriv); dri_destroy_screen_helper(screen); pipe_loader_release(&screen->dev, 1); free(screen); sPriv->driverPrivate = NULL; sPriv->extensions = NULL; }
void dri_destroy_screen(__DRIscreen * sPriv) { struct dri_screen *screen = dri_screen(sPriv); dri_destroy_screen_helper(screen); #if !GALLIUM_STATIC_TARGETS pipe_loader_release(&screen->dev, 1); #endif // !GALLIUM_STATIC_TARGETS free(screen); sPriv->driverPrivate = NULL; sPriv->extensions = NULL; }
static void vl_dri2_screen_destroy(struct vl_screen *vscreen) { struct vl_dri_screen *scrn = (struct vl_dri_screen *)vscreen; assert(vscreen); if (scrn->flushed) { free(xcb_dri2_swap_buffers_reply(scrn->conn, scrn->swap_cookie, NULL)); free(xcb_dri2_wait_sbc_reply(scrn->conn, scrn->wait_cookie, NULL)); free(xcb_dri2_get_buffers_reply(scrn->conn, scrn->buffers_cookie, NULL)); } vl_dri2_destroy_drawable(scrn); scrn->base.pscreen->destroy(scrn->base.pscreen); pipe_loader_release(&scrn->base.dev, 1); /* There is no user provided fd */ FREE(scrn); }
static void close_prog(struct program *p) { /* unset all state */ cso_release_all(p->cso); p->pipe->delete_vs_state(p->pipe, p->vs); p->pipe->delete_fs_state(p->pipe, p->fs); pipe_surface_reference(&p->framebuffer.cbufs[0], NULL); pipe_resource_reference(&p->target, NULL); pipe_resource_reference(&p->vbuf, NULL); cso_destroy_context(p->cso); p->pipe->destroy(p->pipe); p->screen->destroy(p->screen); pipe_loader_release(&p->dev, 1); FREE(p); }
static void vl_dri3_screen_destroy(struct vl_screen *vscreen) { struct vl_dri3_screen *scrn = (struct vl_dri3_screen *)vscreen; int i; assert(vscreen); dri3_flush_present_events(scrn); if (scrn->front_buffer) { dri3_free_front_buffer(scrn, scrn->front_buffer); scrn->front_buffer = NULL; } for (i = 0; i < BACK_BUFFER_NUM; ++i) { if (scrn->back_buffers[i]) { dri3_free_back_buffer(scrn, scrn->back_buffers[i]); scrn->back_buffers[i] = NULL; } } if (scrn->special_event) { xcb_void_cookie_t cookie = xcb_present_select_input_checked(scrn->conn, scrn->eid, scrn->drawable, XCB_PRESENT_EVENT_MASK_NO_EVENT); xcb_discard_reply(scrn->conn, cookie.sequence); xcb_unregister_for_special_event(scrn->conn, scrn->special_event); } scrn->pipe->destroy(scrn->pipe); scrn->base.pscreen->destroy(scrn->base.pscreen); pipe_loader_release(&scrn->base.dev, 1); FREE(scrn); return; }
int gallium_screen_create(struct gbm_gallium_drm_device *gdrm) { struct pipe_loader_device *dev; #ifdef HAVE_PIPE_LOADER_DRM int ret; ret = pipe_loader_drm_probe_fd(&dev, gdrm->base.base.fd); if (!ret) return -1; #endif /* HAVE_PIPE_LOADER_DRM */ gdrm->screen = pipe_loader_create_screen(dev, get_library_search_path()); if (gdrm->screen == NULL) { debug_printf("failed to load driver: %s\n", gdrm->base.driver_name); pipe_loader_release(&dev, 1); return -1; }; gdrm->driver = dev; gdrm->base.driver_name = strdup(dev->driver_name); return 0; }
struct vl_screen * vl_drm_screen_create(int fd) { struct vl_screen *vscreen; int new_fd; vscreen = CALLOC_STRUCT(vl_screen); if (!vscreen) return NULL; if (fd < 0 || (new_fd = dup(fd)) < 0) goto free_screen; if (pipe_loader_drm_probe_fd(&vscreen->dev, new_fd)) vscreen->pscreen = pipe_loader_create_screen(vscreen->dev); if (!vscreen->pscreen) goto release_pipe; vscreen->destroy = vl_drm_screen_destroy; vscreen->texture_from_drawable = NULL; vscreen->get_dirty_area = NULL; vscreen->get_timestamp = NULL; vscreen->set_next_timestamp = NULL; vscreen->get_private = NULL; return vscreen; release_pipe: if (vscreen->dev) pipe_loader_release(&vscreen->dev, 1); else close(new_fd); free_screen: FREE(vscreen); return NULL; }
struct vl_screen * vl_dri3_screen_create(Display *display, int screen) { struct vl_dri3_screen *scrn; const xcb_query_extension_reply_t *extension; xcb_dri3_open_cookie_t open_cookie; xcb_dri3_open_reply_t *open_reply; xcb_get_geometry_cookie_t geom_cookie; xcb_get_geometry_reply_t *geom_reply; int is_different_gpu; int fd; assert(display); scrn = CALLOC_STRUCT(vl_dri3_screen); if (!scrn) return NULL; scrn->conn = XGetXCBConnection(display); if (!scrn->conn) goto free_screen; xcb_prefetch_extension_data(scrn->conn , &xcb_dri3_id); xcb_prefetch_extension_data(scrn->conn, &xcb_present_id); extension = xcb_get_extension_data(scrn->conn, &xcb_dri3_id); if (!(extension && extension->present)) goto free_screen; extension = xcb_get_extension_data(scrn->conn, &xcb_present_id); if (!(extension && extension->present)) goto free_screen; open_cookie = xcb_dri3_open(scrn->conn, RootWindow(display, screen), None); open_reply = xcb_dri3_open_reply(scrn->conn, open_cookie, NULL); if (!open_reply) goto free_screen; if (open_reply->nfd != 1) { free(open_reply); goto free_screen; } fd = xcb_dri3_open_reply_fds(scrn->conn, open_reply)[0]; if (fd < 0) { free(open_reply); goto free_screen; } fcntl(fd, F_SETFD, FD_CLOEXEC); free(open_reply); fd = loader_get_user_preferred_fd(fd, &is_different_gpu); /* TODO support different GPU */ if (is_different_gpu) goto close_fd; geom_cookie = xcb_get_geometry(scrn->conn, RootWindow(display, screen)); geom_reply = xcb_get_geometry_reply(scrn->conn, geom_cookie, NULL); if (!geom_reply) goto close_fd; /* TODO support depth other than 24 */ if (geom_reply->depth != 24) { free(geom_reply); goto close_fd; } free(geom_reply); if (pipe_loader_drm_probe_fd(&scrn->base.dev, fd)) scrn->base.pscreen = pipe_loader_create_screen(scrn->base.dev); if (!scrn->base.pscreen) goto release_pipe; scrn->base.destroy = vl_dri3_screen_destroy; scrn->base.texture_from_drawable = vl_dri3_screen_texture_from_drawable; scrn->base.get_dirty_area = vl_dri3_screen_get_dirty_area; scrn->base.get_timestamp = vl_dri3_screen_get_timestamp; scrn->base.set_next_timestamp = vl_dri3_screen_set_next_timestamp; scrn->base.get_private = vl_dri3_screen_get_private; scrn->base.pscreen->flush_frontbuffer = vl_dri3_flush_frontbuffer; return &scrn->base; release_pipe: if (scrn->base.dev) { pipe_loader_release(&scrn->base.dev, 1); fd = -1; } close_fd: if (fd != -1) close(fd); free_screen: FREE(scrn); return NULL; }
struct vl_screen * vl_dri2_screen_create(Display *display, int screen) { struct vl_dri_screen *scrn; const xcb_query_extension_reply_t *extension; xcb_dri2_query_version_cookie_t dri2_query_cookie; xcb_dri2_query_version_reply_t *dri2_query = NULL; xcb_dri2_connect_cookie_t connect_cookie; xcb_dri2_connect_reply_t *connect = NULL; xcb_dri2_authenticate_cookie_t authenticate_cookie; xcb_dri2_authenticate_reply_t *authenticate = NULL; xcb_screen_iterator_t s; xcb_generic_error_t *error = NULL; char *device_name; int fd, device_name_length; unsigned driverType; drm_magic_t magic; assert(display); scrn = CALLOC_STRUCT(vl_dri_screen); if (!scrn) return NULL; scrn->conn = XGetXCBConnection(display); if (!scrn->conn) goto free_screen; xcb_prefetch_extension_data(scrn->conn, &xcb_dri2_id); extension = xcb_get_extension_data(scrn->conn, &xcb_dri2_id); if (!(extension && extension->present)) goto free_screen; dri2_query_cookie = xcb_dri2_query_version (scrn->conn, XCB_DRI2_MAJOR_VERSION, XCB_DRI2_MINOR_VERSION); dri2_query = xcb_dri2_query_version_reply (scrn->conn, dri2_query_cookie, &error); if (dri2_query == NULL || error != NULL || dri2_query->minor_version < 2) goto free_query; s = xcb_setup_roots_iterator(xcb_get_setup(scrn->conn)); scrn->base.xcb_screen = get_xcb_screen(s, screen); if (!scrn->base.xcb_screen) goto free_query; driverType = XCB_DRI2_DRIVER_TYPE_DRI; { char *prime = getenv("DRI_PRIME"); if (prime) { unsigned primeid; errno = 0; primeid = strtoul(prime, NULL, 0); if (errno == 0) driverType |= ((primeid & DRI2DriverPrimeMask) << DRI2DriverPrimeShift); } } connect_cookie = xcb_dri2_connect_unchecked( scrn->conn, ((xcb_screen_t *)(scrn->base.xcb_screen))->root, driverType); connect = xcb_dri2_connect_reply(scrn->conn, connect_cookie, NULL); if (connect == NULL || connect->driver_name_length + connect->device_name_length == 0) goto free_connect; device_name_length = xcb_dri2_connect_device_name_length(connect); device_name = CALLOC(1, device_name_length + 1); if (!device_name) goto free_connect; memcpy(device_name, xcb_dri2_connect_device_name(connect), device_name_length); fd = loader_open_device(device_name); free(device_name); if (fd < 0) goto free_connect; if (drmGetMagic(fd, &magic)) goto close_fd; authenticate_cookie = xcb_dri2_authenticate_unchecked( scrn->conn, ((xcb_screen_t *)(scrn->base.xcb_screen))->root, magic); authenticate = xcb_dri2_authenticate_reply(scrn->conn, authenticate_cookie, NULL); if (authenticate == NULL || !authenticate->authenticated) goto free_authenticate; if (pipe_loader_drm_probe_fd(&scrn->base.dev, fd)) scrn->base.pscreen = pipe_loader_create_screen(scrn->base.dev); if (!scrn->base.pscreen) goto release_pipe; scrn->base.destroy = vl_dri2_screen_destroy; scrn->base.texture_from_drawable = vl_dri2_screen_texture_from_drawable; scrn->base.get_dirty_area = vl_dri2_screen_get_dirty_area; scrn->base.get_timestamp = vl_dri2_screen_get_timestamp; scrn->base.set_next_timestamp = vl_dri2_screen_set_next_timestamp; scrn->base.get_private = vl_dri2_screen_get_private; scrn->base.pscreen->flush_frontbuffer = vl_dri2_flush_frontbuffer; vl_compositor_reset_dirty_area(&scrn->dirty_areas[0]); vl_compositor_reset_dirty_area(&scrn->dirty_areas[1]); /* The pipe loader duplicates the fd */ close(fd); free(authenticate); free(connect); free(dri2_query); free(error); return &scrn->base; release_pipe: if (scrn->base.dev) pipe_loader_release(&scrn->base.dev, 1); free_authenticate: free(authenticate); close_fd: close(fd); free_connect: free(connect); free_query: free(dri2_query); free(error); free_screen: FREE(scrn); return NULL; }
XA_EXPORT struct xa_tracker * xa_tracker_create(int drm_fd) { struct xa_tracker *xa = calloc(1, sizeof(struct xa_tracker)); enum xa_surface_type stype; unsigned int num_formats; int loader_fd; if (!xa) return NULL; loader_fd = dup(drm_fd); if (loader_fd == -1) return NULL; if (pipe_loader_drm_probe_fd(&xa->dev, loader_fd, false)) xa->screen = pipe_loader_create_screen(xa->dev, PIPE_SEARCH_DIR); if (!xa->screen) goto out_no_screen; xa->default_ctx = xa_context_create(xa); if (!xa->default_ctx) goto out_no_pipe; num_formats = 0; for (stype = 0; stype < XA_LAST_SURFACE_TYPE; ++stype) num_formats += num_preferred[stype]; num_formats += 1; xa->supported_formats = calloc(num_formats, sizeof(*xa->supported_formats)); if (!xa->supported_formats) goto out_sf_alloc_fail; xa->supported_formats[0] = xa_format_unknown; num_formats = 1; memset(xa->format_map, 0, sizeof(xa->format_map)); for (stype = 0; stype < XA_LAST_SURFACE_TYPE; ++stype) { unsigned int bind = stype_bind[stype]; enum xa_formats xa_format; int i; for (i = 0; i < num_preferred[stype]; ++i) { xa_format = preferred[stype][i]; struct xa_format_descriptor fdesc = xa_get_pipe_format(xa_format); if (xa->screen->is_format_supported(xa->screen, fdesc.format, PIPE_TEXTURE_2D, 0, bind)) { if (xa->format_map[stype][0] == 0) xa->format_map[stype][0] = num_formats; xa->format_map[stype][1] = num_formats; xa->supported_formats[num_formats++] = xa_format; } } } return xa; out_sf_alloc_fail: xa_context_destroy(xa->default_ctx); out_no_pipe: xa->screen->destroy(xa->screen); out_no_screen: if (xa->dev) pipe_loader_release(&xa->dev, 1); free(xa); return NULL; }
static HRESULT WINAPI drm_create_adapter( int fd, ID3DAdapter9 **ppAdapter ) { struct d3dadapter9drm_context *ctx = CALLOC_STRUCT(d3dadapter9drm_context); HRESULT hr; int i; const char *paths[] = { getenv("D3D9_DRIVERS_PATH"), getenv("D3D9_DRIVERS_DIR"), PIPE_SEARCH_DIR }; if (!ctx) { return E_OUTOFMEMORY; } ctx->base.resource_from_present = drm_resource_from_present; ctx->base.destroy = drm_destroy; /* use pipe-loader to dlopen appropriate drm driver */ if (!pipe_loader_drm_probe_fd(&ctx->dev, fd, FALSE)) { DBG("Failed to probe drm fd %d.\n", fd); FREE(ctx); close(fd); return D3DERR_DRIVERINTERNALERROR; } /* use pipe-loader to create a drm screen (hal) */ ctx->base.hal = NULL; for (i = 0; !ctx->base.hal && i < Elements(paths); ++i) { if (!paths[i]) { continue; } ctx->base.hal = pipe_loader_create_screen(ctx->dev, paths[i]); } if (!ctx->base.hal) { DBG("Unable to load requested driver.\n"); pipe_loader_release(&ctx->dev, 1); FREE(ctx); return D3DERR_DRIVERINTERNALERROR; } /* wrap it to create a software screen that can share resources */ if (pipe_loader_sw_probe_wrapped(&ctx->swdev, ctx->base.hal)) { ctx->base.ref = NULL; for (i = 0; !ctx->base.ref && i < Elements(paths); ++i) { if (!paths[i]) { continue; } ctx->base.ref = pipe_loader_create_screen(ctx->swdev, paths[i]); } } if (!ctx->base.ref) { DBG("Couldn't wrap drm screen to swrast screen. Software devices " "will be unavailable.\n"); } /* read out PCI info */ read_descriptor(&ctx->base, fd); /* create and return new ID3DAdapter9 */ hr = NineAdapter9_new(&ctx->base, (struct NineAdapter9 **)ppAdapter); if (FAILED(hr)) { if (ctx->swdev) { pipe_loader_release(&ctx->swdev, 1); } pipe_loader_release(&ctx->dev, 1); FREE(ctx); return hr; } return D3D_OK; }
struct vl_screen * vl_dri3_screen_create(Display *display, int screen) { struct vl_dri3_screen *scrn; const xcb_query_extension_reply_t *extension; xcb_dri3_open_cookie_t open_cookie; xcb_dri3_open_reply_t *open_reply; xcb_get_geometry_cookie_t geom_cookie; xcb_get_geometry_reply_t *geom_reply; xcb_xfixes_query_version_cookie_t xfixes_cookie; xcb_xfixes_query_version_reply_t *xfixes_reply; xcb_generic_error_t *error; int fd; assert(display); scrn = CALLOC_STRUCT(vl_dri3_screen); if (!scrn) return NULL; scrn->conn = XGetXCBConnection(display); if (!scrn->conn) goto free_screen; xcb_prefetch_extension_data(scrn->conn , &xcb_dri3_id); xcb_prefetch_extension_data(scrn->conn, &xcb_present_id); xcb_prefetch_extension_data (scrn->conn, &xcb_xfixes_id); extension = xcb_get_extension_data(scrn->conn, &xcb_dri3_id); if (!(extension && extension->present)) goto free_screen; extension = xcb_get_extension_data(scrn->conn, &xcb_present_id); if (!(extension && extension->present)) goto free_screen; extension = xcb_get_extension_data(scrn->conn, &xcb_xfixes_id); if (!(extension && extension->present)) goto free_screen; xfixes_cookie = xcb_xfixes_query_version(scrn->conn, XCB_XFIXES_MAJOR_VERSION, XCB_XFIXES_MINOR_VERSION); xfixes_reply = xcb_xfixes_query_version_reply(scrn->conn, xfixes_cookie, &error); if (!xfixes_reply || error || xfixes_reply->major_version < 2) { free(error); free(xfixes_reply); goto free_screen; } free(xfixes_reply); open_cookie = xcb_dri3_open(scrn->conn, RootWindow(display, screen), None); open_reply = xcb_dri3_open_reply(scrn->conn, open_cookie, NULL); if (!open_reply) goto free_screen; if (open_reply->nfd != 1) { free(open_reply); goto free_screen; } fd = xcb_dri3_open_reply_fds(scrn->conn, open_reply)[0]; if (fd < 0) { free(open_reply); goto free_screen; } fcntl(fd, F_SETFD, FD_CLOEXEC); free(open_reply); fd = loader_get_user_preferred_fd(fd, &scrn->is_different_gpu); geom_cookie = xcb_get_geometry(scrn->conn, RootWindow(display, screen)); geom_reply = xcb_get_geometry_reply(scrn->conn, geom_cookie, NULL); if (!geom_reply) goto close_fd; scrn->base.xcb_screen = dri3_get_screen_for_root(scrn->conn, geom_reply->root); if (!scrn->base.xcb_screen) { free(geom_reply); goto close_fd; } /* TODO support depth other than 24 or 30 */ if (geom_reply->depth != 24 && geom_reply->depth != 30) { free(geom_reply); goto close_fd; } scrn->base.color_depth = geom_reply->depth; free(geom_reply); if (pipe_loader_drm_probe_fd(&scrn->base.dev, fd)) scrn->base.pscreen = pipe_loader_create_screen(scrn->base.dev); if (!scrn->base.pscreen) goto release_pipe; scrn->pipe = scrn->base.pscreen->context_create(scrn->base.pscreen, NULL, 0); if (!scrn->pipe) goto no_context; scrn->base.destroy = vl_dri3_screen_destroy; scrn->base.texture_from_drawable = vl_dri3_screen_texture_from_drawable; scrn->base.get_dirty_area = vl_dri3_screen_get_dirty_area; scrn->base.get_timestamp = vl_dri3_screen_get_timestamp; scrn->base.set_next_timestamp = vl_dri3_screen_set_next_timestamp; scrn->base.get_private = vl_dri3_screen_get_private; scrn->base.pscreen->flush_frontbuffer = vl_dri3_flush_frontbuffer; scrn->base.set_back_texture_from_output = vl_dri3_screen_set_back_texture_from_output; scrn->next_back = 1; return &scrn->base; no_context: scrn->base.pscreen->destroy(scrn->base.pscreen); release_pipe: if (scrn->base.dev) { pipe_loader_release(&scrn->base.dev, 1); fd = -1; } close_fd: if (fd != -1) close(fd); free_screen: FREE(scrn); return NULL; }