Пример #1
0
static void
vmw_dri1_present_locked(struct pipe_context *locked_pipe,
			struct pipe_surface *surf,
			const struct drm_clip_rect *rect,
			unsigned int num_clip,
			int x_draw, int y_draw,
			const struct drm_clip_rect *bbox,
			struct pipe_fence_handle **p_fence)
{
   struct svga_winsys_surface *srf =
      svga_screen_texture_get_winsys_surface(surf->texture);
   struct vmw_svga_winsys_surface *vsrf = vmw_svga_winsys_surface(srf);
   struct vmw_winsys_screen *vws =
      vmw_winsys_screen(svga_winsys_screen(locked_pipe->screen));
   struct drm_clip_rect clip;
   int i;
   struct
   {
      SVGA3dCmdHeader header;
      SVGA3dCmdPresent body;
      SVGA3dCopyRect rect;
   } cmd;
   boolean visible = FALSE;
   uint32_t fence_seq = 0;

   VMW_FUNC;
   cmd.header.id = SVGA_3D_CMD_PRESENT;
   cmd.header.size = sizeof cmd.body + sizeof cmd.rect;
   cmd.body.sid = vsrf->sid;

   for (i = 0; i < num_clip; ++i) {
      if (!vmw_dri1_intersect_src_bbox(&clip, x_draw, y_draw, rect++, bbox))
	 continue;

      cmd.rect.x = clip.x1;
      cmd.rect.y = clip.y1;
      cmd.rect.w = clip.x2 - clip.x1;
      cmd.rect.h = clip.y2 - clip.y1;
      cmd.rect.srcx = (int)clip.x1 - x_draw;
      cmd.rect.srcy = (int)clip.y1 - y_draw;

      vmw_printf("%s: Clip %d x %d y %d w %d h %d srcx %d srcy %d\n",
		   __FUNCTION__,
		   i,
		   cmd.rect.x,
		   cmd.rect.y,
		   cmd.rect.w, cmd.rect.h, cmd.rect.srcx, cmd.rect.srcy);

      vmw_ioctl_command(vws, &cmd, sizeof cmd.header + cmd.header.size,
                        &fence_seq);
      visible = TRUE;
   }

   *p_fence = (visible) ? vmw_pipe_fence(fence_seq) : NULL;
   vmw_svga_winsys_surface_reference(&vsrf, NULL);
}
Пример #2
0
static enum pipe_error
vmw_swc_flush(struct svga_winsys_context *swc,
              struct pipe_fence_handle **pfence)
{
   struct vmw_svga_winsys_context *vswc = vmw_svga_winsys_context(swc);
   struct pipe_fence_handle *fence = NULL;
   unsigned i;
   enum pipe_error ret;

   ret = pb_validate_validate(vswc->validate);
   assert(ret == PIPE_OK);
   if(ret == PIPE_OK) {
   
      /* Apply relocations */
      for(i = 0; i < vswc->region.used; ++i) {
         struct vmw_buffer_relocation *reloc = &vswc->region.relocs[i];
         struct SVGAGuestPtr ptr;

         if(!vmw_gmr_bufmgr_region_ptr(reloc->buffer, &ptr))
            assert(0);

         ptr.offset += reloc->offset;

	 if (reloc->is_mob) {
	    if (reloc->mob.id)
	       *reloc->mob.id = ptr.gmrId;
	    if (reloc->mob.offset_into_mob)
	       *reloc->mob.offset_into_mob = ptr.offset;
	    else {
	       assert(ptr.offset == 0);
	    }
	 } else
	    *reloc->region.where = ptr;
      }

      if (vswc->command.used || pfence != NULL)
         vmw_ioctl_command(vswc->vws,
			   vswc->base.cid,
			   0,
                           vswc->command.buffer,
                           vswc->command.used,
                           &fence);

      pb_validate_fence(vswc->validate, fence);
   }

   vswc->command.used = 0;
   vswc->command.reserved = 0;

   for(i = 0; i < vswc->surface.used + vswc->surface.staged; ++i) {
      struct vmw_ctx_validate_item *isurf = &vswc->surface.items[i];
      if (isurf->referenced)
         p_atomic_dec(&isurf->vsurf->validated);
      vmw_svga_winsys_surface_reference(&isurf->vsurf, NULL);
   }

   util_hash_table_clear(vswc->hash);
   vswc->surface.used = 0;
   vswc->surface.reserved = 0;

   for(i = 0; i < vswc->shader.used + vswc->shader.staged; ++i) {
      struct vmw_ctx_validate_item *ishader = &vswc->shader.items[i];
      if (ishader->referenced)
         p_atomic_dec(&ishader->vshader->validated);
      vmw_svga_winsys_shader_reference(&ishader->vshader, NULL);
   }

   vswc->shader.used = 0;
   vswc->shader.reserved = 0;

   vswc->region.used = 0;
   vswc->region.reserved = 0;

#ifdef DEBUG
   vswc->must_flush = FALSE;
   debug_flush_flush(vswc->fctx);
#endif
   vswc->preemptive_flush = FALSE;
   vswc->seen_surfaces = 0;
   vswc->seen_regions = 0;
   vswc->seen_mobs = 0;

   if(pfence)
      vmw_fence_reference(vswc->vws, pfence, fence);

   vmw_fence_reference(vswc->vws, &fence, NULL);

   return ret;
}