OSDN Git Service

intel: Add a new function to check if a BO's reloc tree references some BO.
authorEric Anholt <eric@anholt.net>
Fri, 2 Oct 2009 02:09:26 +0000 (19:09 -0700)
committerEric Anholt <eric@anholt.net>
Fri, 2 Oct 2009 02:09:26 +0000 (19:09 -0700)
There are a bunch of places in GL where if we can't do this we have to
flush the batchbuffer, and the cost of lookups here is outweighed by flush
savings.

libdrm/intel/intel_bufmgr.c
libdrm/intel/intel_bufmgr.h
libdrm/intel/intel_bufmgr_gem.c
libdrm/intel/intel_bufmgr_priv.h

index 219c761..20e59b8 100644 (file)
@@ -228,6 +228,12 @@ int drm_intel_bo_busy(drm_intel_bo *bo)
 }
 
 int
+drm_intel_bo_references(drm_intel_bo *bo, drm_intel_bo *target_bo)
+{
+       return bo->bufmgr->bo_references(bo, target_bo);
+}
+
+int
 drm_intel_get_pipe_from_crtc_id (drm_intel_bufmgr *bufmgr, int crtc_id)
 {
        if (bufmgr->get_pipe_from_crtc_id)
index 218b759..cb7196c 100644 (file)
@@ -110,6 +110,7 @@ int drm_intel_bo_flink(drm_intel_bo *bo, uint32_t *name);
 int drm_intel_bo_busy(drm_intel_bo *bo);
 
 int drm_intel_bo_disable_reuse(drm_intel_bo *bo);
+int drm_intel_bo_references(drm_intel_bo *bo, drm_intel_bo *target_bo);
 
 /* drm_intel_bufmgr_gem.c */
 drm_intel_bufmgr *drm_intel_bufmgr_gem_init(int fd, int batch_size);
index 78297e0..d4fa159 100644 (file)
@@ -681,7 +681,7 @@ drm_intel_gem_bo_map_gtt(drm_intel_bo *bo)
     if (bo_gem->gtt_virtual == NULL) {
        struct drm_i915_gem_mmap_gtt mmap_arg;
 
-       DBG("bo_map_gtt: %d (%s)\n", bo_gem->gem_handle, bo_gem->name);
+       DBG("bo_map_gtt: mmap %d (%s)\n", bo_gem->gem_handle, bo_gem->name);
 
        memset(&mmap_arg, 0, sizeof(mmap_arg));
        mmap_arg.handle = bo_gem->gem_handle;
@@ -715,7 +715,7 @@ drm_intel_gem_bo_map_gtt(drm_intel_bo *bo)
 
     bo->virtual = bo_gem->gtt_virtual;
 
-    DBG("bo_map: %d (%s) -> %p\n", bo_gem->gem_handle, bo_gem->name,
+    DBG("bo_map_gtt: %d (%s) -> %p\n", bo_gem->gem_handle, bo_gem->name,
        bo_gem->gtt_virtual);
 
     /* Now move it to the GTT domain so that the CPU caches are flushed */
@@ -1390,6 +1390,29 @@ drm_intel_gem_bo_disable_reuse(drm_intel_bo *bo)
 }
 
 /**
+ * Clear the flag set by drm_intel_gem_bo_get_aperture_space() so we're ready
+ * for the next drm_intel_bufmgr_check_aperture_space() call.
+ */
+static int
+drm_intel_gem_bo_references(drm_intel_bo *bo, drm_intel_bo *target_bo)
+{
+    drm_intel_bo_gem *bo_gem = (drm_intel_bo_gem *)bo;
+    int i;
+
+    if (bo == NULL || target_bo == NULL)
+       return 0;
+
+    for (i = 0; i < bo_gem->reloc_count; i++) {
+       if (bo_gem->reloc_target_bo[i] == target_bo)
+           return 1;
+       if (drm_intel_gem_bo_references(bo_gem->reloc_target_bo[i], target_bo))
+           return 1;
+    }
+
+    return 0;
+}
+
+/**
  * Initializes the GEM buffer manager, which uses the kernel to allocate, map,
  * and manage map buffer objections.
  *
@@ -1474,6 +1497,8 @@ drm_intel_bufmgr_gem_init(int fd, int batch_size)
     bufmgr_gem->bufmgr.check_aperture_space = drm_intel_gem_check_aperture_space;
     bufmgr_gem->bufmgr.bo_disable_reuse = drm_intel_gem_bo_disable_reuse;
     bufmgr_gem->bufmgr.get_pipe_from_crtc_id = drm_intel_gem_get_pipe_from_crtc_id;
+    bufmgr_gem->bufmgr.bo_references = drm_intel_gem_bo_references;
+
     /* Initialize the linked lists for BO reuse cache. */
     for (i = 0, size = 4096; i < DRM_INTEL_GEM_BO_BUCKETS; i++, size *= 2) {
        DRMINITLISTHEAD(&bufmgr_gem->cache_bucket[i].head);
index af17c12..454d457 100644 (file)
@@ -207,6 +207,9 @@ struct _drm_intel_bufmgr {
      */
     int (*get_pipe_from_crtc_id)(drm_intel_bufmgr *bufmgr, int crtc_id);
 
+   /** Returns true if target_bo is in the relocation tree rooted at bo. */
+    int (*bo_references)(drm_intel_bo *bo, drm_intel_bo *target_bo);
+
     int debug; /**< Enables verbose debugging printouts */
 };