[RFC 11/29] nvkm/vgpu: introduce GSP RM client alloc and free for vGPU

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



To talk to the GSP firmware, the first step is allocating a GSP RM client.

NVDIA vGPU VFIO module requires a GSP RM client to obtain system information
and create and configure vGPUs.

Implement the GSP client allocation and free.

Signed-off-by: Zhi Wang <zhiw@xxxxxxxxxx>
---
 drivers/gpu/drm/nouveau/nvkm/vgpu_mgr/vfio.c | 58 ++++++++++++++++++++
 include/drm/nvkm_vgpu_mgr_vfio.h             | 10 ++++
 2 files changed, 68 insertions(+)

diff --git a/drivers/gpu/drm/nouveau/nvkm/vgpu_mgr/vfio.c b/drivers/gpu/drm/nouveau/nvkm/vgpu_mgr/vfio.c
index e98c9e83ee60..a0b4be2e1085 100644
--- a/drivers/gpu/drm/nouveau/nvkm/vgpu_mgr/vfio.c
+++ b/drivers/gpu/drm/nouveau/nvkm/vgpu_mgr/vfio.c
@@ -1,6 +1,7 @@
 /* SPDX-License-Identifier: MIT */
 
 #include <core/device.h>
+#include <subdev/gsp.h>
 
 #include <vgpu_mgr/vgpu_mgr.h>
 #include <drm/nvkm_vgpu_mgr_vfio.h>
@@ -43,11 +44,68 @@ static int attach_handle(void *handle,
 	return 0;
 }
 
+static int alloc_gsp_client(void *handle,
+			    struct nvidia_vgpu_gsp_client *client)
+{
+	struct nvkm_device *device = handle;
+	struct nvkm_gsp *gsp = device->gsp;
+	int ret = -ENOMEM;
+
+	client->gsp_device = kzalloc(sizeof(struct nvkm_gsp_device),
+				     GFP_KERNEL);
+	if (!client->gsp_device)
+		return ret;
+
+	client->gsp_client = kzalloc(sizeof(struct nvkm_gsp_client),
+				     GFP_KERNEL);
+	if (!client->gsp_client)
+		goto fail_alloc_client;
+
+	ret = nvkm_gsp_client_device_ctor(gsp, client->gsp_client,
+					  client->gsp_device);
+	if (ret)
+		goto fail_client_device_ctor;
+
+	return 0;
+
+fail_client_device_ctor:
+	kfree(client->gsp_client);
+	client->gsp_client = NULL;
+
+fail_alloc_client:
+	kfree(client->gsp_device);
+	client->gsp_device = NULL;
+
+	return ret;
+}
+
+static void free_gsp_client(struct nvidia_vgpu_gsp_client *client)
+{
+	nvkm_gsp_device_dtor(client->gsp_device);
+	nvkm_gsp_client_dtor(client->gsp_client);
+
+	kfree(client->gsp_device);
+	client->gsp_device = NULL;
+
+	kfree(client->gsp_client);
+	client->gsp_client = NULL;
+}
+
+static u32 get_gsp_client_handle(struct nvidia_vgpu_gsp_client *client)
+{
+	struct nvkm_gsp_client *c = client->gsp_client;
+
+	return c->object.handle;
+}
+
 struct nvkm_vgpu_mgr_vfio_ops nvkm_vgpu_mgr_vfio_ops = {
 	.vgpu_mgr_is_enabled = vgpu_mgr_is_enabled,
 	.get_handle = get_handle,
 	.attach_handle = attach_handle,
 	.detach_handle = detach_handle,
+	.alloc_gsp_client = alloc_gsp_client,
+	.free_gsp_client = free_gsp_client,
+	.get_gsp_client_handle = get_gsp_client_handle,
 };
 
 /**
diff --git a/include/drm/nvkm_vgpu_mgr_vfio.h b/include/drm/nvkm_vgpu_mgr_vfio.h
index 09ecc3dc454f..79920cc27055 100644
--- a/include/drm/nvkm_vgpu_mgr_vfio.h
+++ b/include/drm/nvkm_vgpu_mgr_vfio.h
@@ -10,6 +10,12 @@ struct nvidia_vgpu_vfio_handle_data {
 	void *priv;
 };
 
+/* A combo of handles of RmClient and RmDevice */
+struct nvidia_vgpu_gsp_client {
+	void *gsp_client;
+	void *gsp_device;
+};
+
 struct nvkm_vgpu_mgr_vfio_ops {
 	bool (*vgpu_mgr_is_enabled)(void *handle);
 	void (*get_handle)(void *handle,
@@ -17,6 +23,10 @@ struct nvkm_vgpu_mgr_vfio_ops {
 	int (*attach_handle)(void *handle,
 		             struct nvidia_vgpu_vfio_handle_data *data);
 	void (*detach_handle)(void *handle);
+	int (*alloc_gsp_client)(void *handle,
+				struct nvidia_vgpu_gsp_client *client);
+	void (*free_gsp_client)(struct nvidia_vgpu_gsp_client *client);
+	u32 (*get_gsp_client_handle)(struct nvidia_vgpu_gsp_client *client);
 };
 
 struct nvkm_vgpu_mgr_vfio_ops *nvkm_vgpu_mgr_get_vfio_ops(void *handle);
-- 
2.34.1





[Index of Archives]     [KVM ARM]     [KVM ia64]     [KVM ppc]     [Virtualization Tools]     [Spice Development]     [Libvirt]     [Libvirt Users]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite Questions]     [Linux Kernel]     [Linux SCSI]     [XFree86]

  Powered by Linux