Commit 16845c5d authored by Gerd Hoffmann's avatar Gerd Hoffmann
Browse files

drm/virtio: implement blob resources: implement vram object



A virtio-gpu vram object is based on range-based allocation.
No guest shmemfs backing, so we call drm_gem_private_object_init.

This is for host memory without any guest backing (atleast initially).

Signed-off-by: default avatarGerd Hoffmann <kraxel@redhat.com>
Acked-by: default avatarTomeu Vizoso <tomeu.vizoso@collabora.com>
Link: http://patchwork.freedesktop.org/patch/msgid/20200924003214.662-12-gurchetansingh@chromium.org


Co-developed-by: default avatarGurchetan Singh <gurchetansingh@chromium.org>
Signed-off-by: default avatarGurchetan Singh <gurchetansingh@chromium.org>
parent 5c824604
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -3,7 +3,7 @@
# Makefile for the drm device driver.  This driver provides support for the
# Direct Rendering Infrastructure (DRI) in XFree86 4.1.0 and higher.

virtio-gpu-y := virtgpu_drv.o virtgpu_kms.o virtgpu_gem.o \
virtio-gpu-y := virtgpu_drv.o virtgpu_kms.o virtgpu_gem.o virtgpu_vram.o \
	virtgpu_display.o virtgpu_vq.o \
	virtgpu_fence.o virtgpu_object.o virtgpu_debugfs.o virtgpu_plane.o \
	virtgpu_ioctl.o virtgpu_prime.o virtgpu_trace_points.o
+19 −1
Original line number Diff line number Diff line
@@ -72,9 +72,27 @@ virtio_gpu_debugfs_irq_info(struct seq_file *m, void *data)
	return 0;
}

static int
virtio_gpu_debugfs_host_visible_mm(struct seq_file *m, void *data)
{
	struct drm_info_node *node = (struct drm_info_node *)m->private;
	struct virtio_gpu_device *vgdev = node->minor->dev->dev_private;
	struct drm_printer p;

	if (!vgdev->has_host_visible) {
		seq_puts(m, "Host allocations not visible to guest\n");
		return 0;
	}

	p = drm_seq_file_printer(m);
	drm_mm_print(&vgdev->host_visible_mm, &p);
	return 0;
}

static struct drm_info_list virtio_gpu_debugfs_list[] = {
	{ "virtio-gpu-features", virtio_gpu_features },
	{ "virtio-gpu-irq-fence", virtio_gpu_debugfs_irq_info, 0, NULL },
	{ "virtio-gpu-host-visible-mm", virtio_gpu_debugfs_host_visible_mm },
};

#define VIRTIO_GPU_DEBUGFS_ENTRIES ARRAY_SIZE(virtio_gpu_debugfs_list)
+25 −1
Original line number Diff line number Diff line
@@ -99,9 +99,19 @@ struct virtio_gpu_object_shmem {
	uint32_t mapped;
};

struct virtio_gpu_object_vram {
	struct virtio_gpu_object base;
	uint32_t map_state;
	uint32_t map_info;
	struct drm_mm_node vram_node;
};

#define to_virtio_gpu_shmem(virtio_gpu_object) \
	container_of((virtio_gpu_object), struct virtio_gpu_object_shmem, base)

#define to_virtio_gpu_vram(virtio_gpu_object) \
	container_of((virtio_gpu_object), struct virtio_gpu_object_vram, base)

struct virtio_gpu_object_array {
	struct ww_acquire_ctx ticket;
	struct list_head next;
@@ -222,6 +232,7 @@ struct virtio_gpu_device {
	bool has_resource_blob;
	bool has_host_visible;
	struct virtio_shm_region host_visible_region;
	struct drm_mm host_visible_mm;

	struct work_struct config_changed_work;

@@ -233,8 +244,10 @@ struct virtio_gpu_device {
	uint32_t num_capsets;
	struct list_head cap_cache;

	/* protects resource state when exporting */
	/* protects uuid state when exporting */
	spinlock_t resource_export_lock;
	/* protects map state and host_visible_mm */
	spinlock_t host_visible_lock;
};

struct virtio_gpu_fpriv {
@@ -365,6 +378,12 @@ int
virtio_gpu_cmd_resource_assign_uuid(struct virtio_gpu_device *vgdev,
				    struct virtio_gpu_object_array *objs);

int virtio_gpu_cmd_map(struct virtio_gpu_device *vgdev,
		       struct virtio_gpu_object_array *objs, uint64_t offset);

void virtio_gpu_cmd_unmap(struct virtio_gpu_device *vgdev,
			  struct virtio_gpu_object *bo);

/* virtgpu_display.c */
int virtio_gpu_modeset_init(struct virtio_gpu_device *vgdev);
void virtio_gpu_modeset_fini(struct virtio_gpu_device *vgdev);
@@ -411,4 +430,9 @@ struct drm_gem_object *virtgpu_gem_prime_import_sg_table(
/* virtgpu_debugfs.c */
void virtio_gpu_debugfs_init(struct drm_minor *minor);

/* virtgpu_vram.c */
bool virtio_gpu_is_vram(struct virtio_gpu_object *bo);
int virtio_gpu_vram_create(struct virtio_gpu_device *vgdev,
			   struct virtio_gpu_object_params *params,
			   struct virtio_gpu_object **bo_ptr);
#endif
+8 −0
Original line number Diff line number Diff line
@@ -121,6 +121,7 @@ int virtio_gpu_init(struct drm_device *dev)

	spin_lock_init(&vgdev->display_info_lock);
	spin_lock_init(&vgdev->resource_export_lock);
	spin_lock_init(&vgdev->host_visible_lock);
	ida_init(&vgdev->ctx_id_ida);
	ida_init(&vgdev->resource_ida);
	init_waitqueue_head(&vgdev->resp_wq);
@@ -169,6 +170,9 @@ int virtio_gpu_init(struct drm_device *dev)
			 (unsigned long)vgdev->host_visible_region.addr,
			 (unsigned long)vgdev->host_visible_region.len);
		vgdev->has_host_visible = true;
		drm_mm_init(&vgdev->host_visible_mm,
			    (unsigned long)vgdev->host_visible_region.addr,
			    (unsigned long)vgdev->host_visible_region.len);
	}

	DRM_INFO("features: %cvirgl %cedid %cresource_blob %chost_visible\n",
@@ -262,6 +266,10 @@ void virtio_gpu_release(struct drm_device *dev)
	virtio_gpu_modeset_fini(vgdev);
	virtio_gpu_free_vbufs(vgdev);
	virtio_gpu_cleanup_cap_cache(vgdev);

	if (vgdev->has_host_visible)
		drm_mm_takedown(&vgdev->host_visible_mm);

	kfree(vgdev->capsets);
	kfree(vgdev);
}
+12 −0
Original line number Diff line number Diff line
@@ -84,6 +84,18 @@ void virtio_gpu_cleanup_object(struct virtio_gpu_object *bo)
		}

		drm_gem_shmem_free_object(&bo->base.base);
	} else if (virtio_gpu_is_vram(bo)) {
		struct virtio_gpu_object_vram *vram = to_virtio_gpu_vram(bo);

		spin_lock(&vgdev->host_visible_lock);
		if (drm_mm_node_allocated(&vram->vram_node))
			drm_mm_remove_node(&vram->vram_node);

		spin_unlock(&vgdev->host_visible_lock);

		drm_gem_free_mmap_offset(&vram->base.base.base);
		drm_gem_object_release(&vram->base.base.base);
		kfree(vram);
	}
}

Loading