@@ -40,13 +40,19 @@ enum vmd_features {
40
40
* membars, in order to allow proper address translation during
41
41
* resource assignment to enable guest virtualization
42
42
*/
43
- VMD_FEAT_HAS_MEMBAR_SHADOW = (1 << 0 ),
43
+ VMD_FEAT_HAS_MEMBAR_SHADOW = (1 << 0 ),
44
44
45
45
/*
46
46
* Device may provide root port configuration information which limits
47
47
* bus numbering
48
48
*/
49
- VMD_FEAT_HAS_BUS_RESTRICTIONS = (1 << 1 ),
49
+ VMD_FEAT_HAS_BUS_RESTRICTIONS = (1 << 1 ),
50
+
51
+ /*
52
+ * Device contains physical location shadow registers in
53
+ * vendor-specific capability space
54
+ */
55
+ VMD_FEAT_HAS_MEMBAR_SHADOW_VSCAP = (1 << 2 ),
50
56
};
51
57
52
58
/*
@@ -454,6 +460,28 @@ static int vmd_enable_domain(struct vmd_dev *vmd, unsigned long features)
454
460
}
455
461
}
456
462
463
+ if (features & VMD_FEAT_HAS_MEMBAR_SHADOW_VSCAP ) {
464
+ int pos = pci_find_capability (vmd -> dev , PCI_CAP_ID_VNDR );
465
+ u32 reg , regu ;
466
+
467
+ pci_read_config_dword (vmd -> dev , pos + 4 , & reg );
468
+
469
+ /* "SHDW" */
470
+ if (pos && reg == 0x53484457 ) {
471
+ pci_read_config_dword (vmd -> dev , pos + 8 , & reg );
472
+ pci_read_config_dword (vmd -> dev , pos + 12 , & regu );
473
+ offset [0 ] = vmd -> dev -> resource [VMD_MEMBAR1 ].start -
474
+ (((u64 ) regu << 32 | reg ) &
475
+ PCI_BASE_ADDRESS_MEM_MASK );
476
+
477
+ pci_read_config_dword (vmd -> dev , pos + 16 , & reg );
478
+ pci_read_config_dword (vmd -> dev , pos + 20 , & regu );
479
+ offset [1 ] = vmd -> dev -> resource [VMD_MEMBAR2 ].start -
480
+ (((u64 ) regu << 32 | reg ) &
481
+ PCI_BASE_ADDRESS_MEM_MASK );
482
+ }
483
+ }
484
+
457
485
/*
458
486
* Certain VMD devices may have a root port configuration option which
459
487
* limits the bus range to between 0-127, 128-255, or 224-255
@@ -716,16 +744,20 @@ static int vmd_resume(struct device *dev)
716
744
static SIMPLE_DEV_PM_OPS (vmd_dev_pm_ops , vmd_suspend , vmd_resume ) ;
717
745
718
746
static const struct pci_device_id vmd_ids [] = {
719
- {PCI_DEVICE (PCI_VENDOR_ID_INTEL , PCI_DEVICE_ID_INTEL_VMD_201D ),},
747
+ {PCI_DEVICE (PCI_VENDOR_ID_INTEL , PCI_DEVICE_ID_INTEL_VMD_201D ),
748
+ .driver_data = VMD_FEAT_HAS_MEMBAR_SHADOW_VSCAP ,},
720
749
{PCI_DEVICE (PCI_VENDOR_ID_INTEL , PCI_DEVICE_ID_INTEL_VMD_28C0 ),
721
750
.driver_data = VMD_FEAT_HAS_MEMBAR_SHADOW |
722
751
VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
723
752
{PCI_DEVICE (PCI_VENDOR_ID_INTEL , 0x467f ),
724
- .driver_data = VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
753
+ .driver_data = VMD_FEAT_HAS_MEMBAR_SHADOW_VSCAP |
754
+ VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
725
755
{PCI_DEVICE (PCI_VENDOR_ID_INTEL , 0x4c3d ),
726
- .driver_data = VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
756
+ .driver_data = VMD_FEAT_HAS_MEMBAR_SHADOW_VSCAP |
757
+ VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
727
758
{PCI_DEVICE (PCI_VENDOR_ID_INTEL , PCI_DEVICE_ID_INTEL_VMD_9A0B ),
728
- .driver_data = VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
759
+ .driver_data = VMD_FEAT_HAS_MEMBAR_SHADOW_VSCAP |
760
+ VMD_FEAT_HAS_BUS_RESTRICTIONS ,},
729
761
{0 ,}
730
762
};
731
763
MODULE_DEVICE_TABLE (pci , vmd_ids );
0 commit comments