hc
2024-01-03 2f7c68cb55ecb7331f2381deb497c27155f32faf
kernel/drivers/gpu/drm/i915/gvt/gvt.c
....@@ -31,10 +31,10 @@
3131 */
3232
3333 #include <linux/types.h>
34
-#include <xen/xen.h>
3534 #include <linux/kthread.h>
3635
3736 #include "i915_drv.h"
37
+#include "intel_gvt.h"
3838 #include "gvt.h"
3939 #include <linux/vfio.h>
4040 #include <linux/mdev.h>
....@@ -49,15 +49,15 @@
4949 static struct intel_vgpu_type *intel_gvt_find_vgpu_type(struct intel_gvt *gvt,
5050 const char *name)
5151 {
52
+ const char *driver_name =
53
+ dev_driver_string(&gvt->gt->i915->drm.pdev->dev);
5254 int i;
53
- struct intel_vgpu_type *t;
54
- const char *driver_name = dev_driver_string(
55
- &gvt->dev_priv->drm.pdev->dev);
5655
56
+ name += strlen(driver_name) + 1;
5757 for (i = 0; i < gvt->num_types; i++) {
58
- t = &gvt->types[i];
59
- if (!strncmp(t->name, name + strlen(driver_name) + 1,
60
- sizeof(t->name)))
58
+ struct intel_vgpu_type *t = &gvt->types[i];
59
+
60
+ if (!strncmp(t->name, name, sizeof(t->name)))
6161 return t;
6262 }
6363
....@@ -120,10 +120,8 @@
120120 [0 ... NR_MAX_INTEL_VGPU_TYPES - 1] = NULL,
121121 };
122122
123
-static bool intel_get_gvt_attrs(struct attribute ***type_attrs,
124
- struct attribute_group ***intel_vgpu_type_groups)
123
+static bool intel_get_gvt_attrs(struct attribute_group ***intel_vgpu_type_groups)
125124 {
126
- *type_attrs = gvt_type_attrs;
127125 *intel_vgpu_type_groups = gvt_vgpu_type_groups;
128126 return true;
129127 }
....@@ -185,59 +183,13 @@
185183 .vgpu_query_plane = intel_vgpu_query_plane,
186184 .vgpu_get_dmabuf = intel_vgpu_get_dmabuf,
187185 .write_protect_handler = intel_vgpu_page_track_handler,
186
+ .emulate_hotplug = intel_vgpu_emulate_hotplug,
188187 };
189
-
190
-/**
191
- * intel_gvt_init_host - Load MPT modules and detect if we're running in host
192
- * @gvt: intel gvt device
193
- *
194
- * This function is called at the driver loading stage. If failed to find a
195
- * loadable MPT module or detect currently we're running in a VM, then GVT-g
196
- * will be disabled
197
- *
198
- * Returns:
199
- * Zero on success, negative error code if failed.
200
- *
201
- */
202
-int intel_gvt_init_host(void)
203
-{
204
- if (intel_gvt_host.initialized)
205
- return 0;
206
-
207
- /* Xen DOM U */
208
- if (xen_domain() && !xen_initial_domain())
209
- return -ENODEV;
210
-
211
- /* Try to load MPT modules for hypervisors */
212
- if (xen_initial_domain()) {
213
- /* In Xen dom0 */
214
- intel_gvt_host.mpt = try_then_request_module(
215
- symbol_get(xengt_mpt), "xengt");
216
- intel_gvt_host.hypervisor_type = INTEL_GVT_HYPERVISOR_XEN;
217
- } else {
218
-#if IS_ENABLED(CONFIG_DRM_I915_GVT_KVMGT)
219
- /* not in Xen. Try KVMGT */
220
- intel_gvt_host.mpt = try_then_request_module(
221
- symbol_get(kvmgt_mpt), "kvmgt");
222
- intel_gvt_host.hypervisor_type = INTEL_GVT_HYPERVISOR_KVM;
223
-#endif
224
- }
225
-
226
- /* Fail to load MPT modules - bail out */
227
- if (!intel_gvt_host.mpt)
228
- return -EINVAL;
229
-
230
- gvt_dbg_core("Running with hypervisor %s in host mode\n",
231
- supported_hypervisors[intel_gvt_host.hypervisor_type]);
232
-
233
- intel_gvt_host.initialized = true;
234
- return 0;
235
-}
236188
237189 static void init_device_info(struct intel_gvt *gvt)
238190 {
239191 struct intel_gvt_device_info *info = &gvt->device_info;
240
- struct pci_dev *pdev = gvt->dev_priv->drm.pdev;
192
+ struct pci_dev *pdev = gvt->gt->i915->drm.pdev;
241193
242194 info->max_support_vgpus = 8;
243195 info->cfg_space_size = PCI_CFG_SPACE_EXP_SIZE;
....@@ -303,21 +255,20 @@
303255
304256 /**
305257 * intel_gvt_clean_device - clean a GVT device
306
- * @gvt: intel gvt device
258
+ * @i915: i915 private
307259 *
308260 * This function is called at the driver unloading stage, to free the
309261 * resources owned by a GVT device.
310262 *
311263 */
312
-void intel_gvt_clean_device(struct drm_i915_private *dev_priv)
264
+void intel_gvt_clean_device(struct drm_i915_private *i915)
313265 {
314
- struct intel_gvt *gvt = to_gvt(dev_priv);
266
+ struct intel_gvt *gvt = fetch_and_zero(&i915->gvt);
315267
316
- if (WARN_ON(!gvt))
268
+ if (drm_WARN_ON(&i915->drm, !gvt))
317269 return;
318270
319271 intel_gvt_destroy_idle_vgpu(gvt->idle_vgpu);
320
- intel_gvt_hypervisor_host_exit(&dev_priv->drm.pdev->dev, gvt);
321272 intel_gvt_cleanup_vgpu_type_groups(gvt);
322273 intel_gvt_clean_vgpu_types(gvt);
323274
....@@ -332,13 +283,12 @@
332283 intel_gvt_clean_mmio_info(gvt);
333284 idr_destroy(&gvt->vgpu_idr);
334285
335
- kfree(dev_priv->gvt);
336
- dev_priv->gvt = NULL;
286
+ kfree(i915->gvt);
337287 }
338288
339289 /**
340290 * intel_gvt_init_device - initialize a GVT device
341
- * @dev_priv: drm i915 private data
291
+ * @i915: drm i915 private data
342292 *
343293 * This function is called at the initialization stage, to initialize
344294 * necessary GVT components.
....@@ -347,20 +297,13 @@
347297 * Zero on success, negative error code if failed.
348298 *
349299 */
350
-int intel_gvt_init_device(struct drm_i915_private *dev_priv)
300
+int intel_gvt_init_device(struct drm_i915_private *i915)
351301 {
352302 struct intel_gvt *gvt;
353303 struct intel_vgpu *vgpu;
354304 int ret;
355305
356
- /*
357
- * Cannot initialize GVT device without intel_gvt_host gets
358
- * initialized first.
359
- */
360
- if (WARN_ON(!intel_gvt_host.initialized))
361
- return -EINVAL;
362
-
363
- if (WARN_ON(dev_priv->gvt))
306
+ if (drm_WARN_ON(&i915->drm, i915->gvt))
364307 return -EEXIST;
365308
366309 gvt = kzalloc(sizeof(struct intel_gvt), GFP_KERNEL);
....@@ -373,7 +316,8 @@
373316 spin_lock_init(&gvt->scheduler.mmio_context_lock);
374317 mutex_init(&gvt->lock);
375318 mutex_init(&gvt->sched_lock);
376
- gvt->dev_priv = dev_priv;
319
+ gvt->gt = &i915->gt;
320
+ i915->gvt = gvt;
377321
378322 init_device_info(gvt);
379323
....@@ -421,13 +365,6 @@
421365 goto out_clean_types;
422366 }
423367
424
- ret = intel_gvt_hypervisor_host_init(&dev_priv->drm.pdev->dev, gvt,
425
- &intel_gvt_ops);
426
- if (ret) {
427
- gvt_err("failed to register gvt-g host device: %d\n", ret);
428
- goto out_clean_types;
429
- }
430
-
431368 vgpu = intel_gvt_create_idle_vgpu(gvt);
432369 if (IS_ERR(vgpu)) {
433370 ret = PTR_ERR(vgpu);
....@@ -436,12 +373,11 @@
436373 }
437374 gvt->idle_vgpu = vgpu;
438375
439
- ret = intel_gvt_debugfs_init(gvt);
440
- if (ret)
441
- gvt_err("debugfs registeration failed, go on.\n");
376
+ intel_gvt_debugfs_init(gvt);
442377
443378 gvt_dbg_core("gvt device initialization is done\n");
444
- dev_priv->gvt = gvt;
379
+ intel_gvt_host.dev = &i915->drm.pdev->dev;
380
+ intel_gvt_host.initialized = true;
445381 return 0;
446382
447383 out_clean_types:
....@@ -465,9 +401,58 @@
465401 out_clean_idr:
466402 idr_destroy(&gvt->vgpu_idr);
467403 kfree(gvt);
404
+ i915->gvt = NULL;
468405 return ret;
469406 }
470407
471
-#if IS_ENABLED(CONFIG_DRM_I915_GVT_KVMGT)
472
-MODULE_SOFTDEP("pre: kvmgt");
473
-#endif
408
+int
409
+intel_gvt_pm_resume(struct intel_gvt *gvt)
410
+{
411
+ intel_gvt_restore_fence(gvt);
412
+ intel_gvt_restore_mmio(gvt);
413
+ intel_gvt_restore_ggtt(gvt);
414
+ return 0;
415
+}
416
+
417
+int
418
+intel_gvt_register_hypervisor(struct intel_gvt_mpt *m)
419
+{
420
+ int ret;
421
+ void *gvt;
422
+
423
+ if (!intel_gvt_host.initialized)
424
+ return -ENODEV;
425
+
426
+ if (m->type != INTEL_GVT_HYPERVISOR_KVM &&
427
+ m->type != INTEL_GVT_HYPERVISOR_XEN)
428
+ return -EINVAL;
429
+
430
+ /* Get a reference for device model module */
431
+ if (!try_module_get(THIS_MODULE))
432
+ return -ENODEV;
433
+
434
+ intel_gvt_host.mpt = m;
435
+ intel_gvt_host.hypervisor_type = m->type;
436
+ gvt = (void *)kdev_to_i915(intel_gvt_host.dev)->gvt;
437
+
438
+ ret = intel_gvt_hypervisor_host_init(intel_gvt_host.dev, gvt,
439
+ &intel_gvt_ops);
440
+ if (ret < 0) {
441
+ gvt_err("Failed to init %s hypervisor module\n",
442
+ supported_hypervisors[intel_gvt_host.hypervisor_type]);
443
+ module_put(THIS_MODULE);
444
+ return -ENODEV;
445
+ }
446
+ gvt_dbg_core("Running with hypervisor %s in host mode\n",
447
+ supported_hypervisors[intel_gvt_host.hypervisor_type]);
448
+ return 0;
449
+}
450
+EXPORT_SYMBOL_GPL(intel_gvt_register_hypervisor);
451
+
452
+void
453
+intel_gvt_unregister_hypervisor(void)
454
+{
455
+ intel_gvt_hypervisor_host_exit(intel_gvt_host.dev);
456
+ module_put(THIS_MODULE);
457
+}
458
+EXPORT_SYMBOL_GPL(intel_gvt_unregister_hypervisor);