if (vswc->command.used || pfence != NULL)
vmw_ioctl_command(vws,
- vswc->base.cid,
- 0,
+ vswc->base.cid,
+ 0,
vswc->command.buffer,
vswc->command.used,
- &fence);
+ &fence,
+ vswc->base.imported_fence_fd,
+ vswc->base.hints);
pb_validate_fence(vswc->validate, fence);
mtx_lock(&vws->cs_mutex);
debug_flush_flush(vswc->fctx);
#endif
swc->hints &= ~SVGA_HINT_FLAG_CAN_PRE_FLUSH;
+ swc->hints &= ~SVGA_HINT_FLAG_EXPORT_FENCE_FD;
vswc->preemptive_flush = FALSE;
vswc->seen_surfaces = 0;
vswc->seen_regions = 0;
vswc->seen_mobs = 0;
+ if (vswc->base.imported_fence_fd != -1) {
+ close(vswc->base.imported_fence_fd);
+ vswc->base.imported_fence_fd = -1;
+ }
+
if(pfence)
vmw_fence_reference(vswc->vws, pfence, fence);
if (vswc->base.cid == -1)
goto out_no_context;
+ vswc->base.imported_fence_fd = -1;
+
vswc->base.have_gb_objects = sws->have_gb_objects;
vswc->vws = vws;
void
vmw_ioctl_command(struct vmw_winsys_screen *vws, int32_t cid,
- uint32_t throttle_us, void *commands, uint32_t size,
- struct pipe_fence_handle **pfence)
+ uint32_t throttle_us, void *commands, uint32_t size,
+ struct pipe_fence_handle **pfence, int32_t imported_fence_fd,
+ uint32_t flags)
{
struct drm_vmw_execbuf_arg arg;
struct drm_vmw_fence_rep rep;
memset(&arg, 0, sizeof(arg));
memset(&rep, 0, sizeof(rep));
+ if (flags & SVGA_HINT_FLAG_EXPORT_FENCE_FD) {
+ arg.flags |= DRM_VMW_EXECBUF_FLAG_EXPORT_FENCE_FD;
+ }
+
+ if (imported_fence_fd != -1) {
+ arg.flags |= DRM_VMW_EXECBUF_FLAG_IMPORT_FENCE_FD;
+ }
+
rep.error = -EFAULT;
if (pfence)
arg.fence_rep = (unsigned long)&rep;
arg.version = vws->ioctl.drm_execbuf_version;
arg.context_handle = (vws->base.have_vgpu10 ? cid : SVGA3D_INVALID_ID);
+ /* Older DRM module requires this to be zero */
+ if (vws->base.have_fence_fd)
+ arg.imported_fence_fd = imported_fence_fd;
+
/* In DRM_VMW_EXECBUF_VERSION 1, the drm_vmw_execbuf_arg structure ends with
* the flags field. The structure size sent to drmCommandWrite must match
* the drm_execbuf_version. Otherwise, an invalid value will be returned.
vmw_fences_signal(vws->fence_ops, rep.passed_seqno, rep.seqno,
TRUE);
- *pfence = vmw_fence_create(vws->fence_ops, rep.handle,
- rep.seqno, rep.mask, -1);
- if (*pfence == NULL) {
- /*
- * Fence creation failed. Need to sync.
- */
- (void) vmw_ioctl_fence_finish(vws, rep.handle, rep.mask);
- vmw_ioctl_fence_unref(vws, rep.handle);
- }
+ /* Older DRM module will set this to zero, but -1 is the proper FD
+ * to use for no Fence FD support */
+ if (!vws->base.have_fence_fd)
+ rep.fd = -1;
+
+ *pfence = vmw_fence_create(vws->fence_ops, rep.handle,
+ rep.seqno, rep.mask, rep.fd);
+ if (*pfence == NULL) {
+ /*
+ * Fence creation failed. Need to sync.
+ */
+ (void) vmw_ioctl_fence_finish(vws, rep.handle, rep.mask);
+ vmw_ioctl_fence_unref(vws, rep.handle);
+ }
}
}
}
vws->base.have_set_predication_cmd = TRUE;
}
+ if (version->version_major == 2 && version->version_minor >= 14) {
+ vws->base.have_fence_fd = TRUE;
+ }
+
free(cap_buffer);
drmFreeVersion(version);
vmw_printf("%s OK\n", __FUNCTION__);