diff mbox

x86/MSI: handle both MSI-X and MSI in cfg space write intercept

Message ID 571911AD02000078000E46C9@prv-mh.provo.novell.com (mailing list archive)
State New, archived
Headers show

Commit Message

Jan Beulich April 21, 2016, 3:45 p.m. UTC
In commit aa7c1fdf9d ("x86/MSI: properly track guest masking requests")
I neglected to consider devices allowing for both MSI and MSI-X to be
used (not at the same time of course): The MSI-X part of the intercept
logic needs to fall through to the MSI one when the access is outside
the MSI-X capability bounds.

Signed-off-by: Jan Beulich <jbeulich@suse.com>
x86/MSI: handle both MSI-X and MSI in cfg space write intercept

In commit aa7c1fdf9d ("x86/MSI: properly track guest masking requests")
I neglected to consider devices allowing for both MSI and MSI-X to be
used (not at the same time of course): The MSI-X part of the intercept
logic needs to fall through to the MSI one when the access is outside
the MSI-X capability bounds.

Signed-off-by: Jan Beulich <jbeulich@suse.com>

--- a/xen/arch/x86/msi.c
+++ b/xen/arch/x86/msi.c
@@ -1292,17 +1292,17 @@ int pci_msi_conf_write_intercept(struct
                                           PCI_CAP_ID_MSIX);
         ASSERT(pos);
 
-        if ( reg < pos || reg >= msix_pba_offset_reg(pos) + 4 )
-            return 0;
+        if ( reg >= pos && reg < msix_pba_offset_reg(pos) + 4 )
+        {
+            if ( reg != msix_control_reg(pos) || size != 2 )
+                return -EACCES;
 
-        if ( reg != msix_control_reg(pos) || size != 2 )
-            return -EACCES;
+            pdev->msix->guest_maskall = !!(*data & PCI_MSIX_FLAGS_MASKALL);
+            if ( pdev->msix->host_maskall )
+                *data |= PCI_MSIX_FLAGS_MASKALL;
 
-        pdev->msix->guest_maskall = !!(*data & PCI_MSIX_FLAGS_MASKALL);
-        if ( pdev->msix->host_maskall )
-            *data |= PCI_MSIX_FLAGS_MASKALL;
-
-        return 1;
+            return 1;
+        }
     }
 
     entry = find_msi_entry(pdev, -1, PCI_CAP_ID_MSI);

Comments

Andrew Cooper April 22, 2016, 5:20 p.m. UTC | #1
On 21/04/16 16:45, Jan Beulich wrote:
> In commit aa7c1fdf9d ("x86/MSI: properly track guest masking requests")
> I neglected to consider devices allowing for both MSI and MSI-X to be
> used (not at the same time of course): The MSI-X part of the intercept
> logic needs to fall through to the MSI one when the access is outside
> the MSI-X capability bounds.
>
> Signed-off-by: Jan Beulich <jbeulich@suse.com>

Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
Wei Liu April 25, 2016, 11:29 a.m. UTC | #2
On Thu, Apr 21, 2016 at 09:45:17AM -0600, Jan Beulich wrote:
> In commit aa7c1fdf9d ("x86/MSI: properly track guest masking requests")
> I neglected to consider devices allowing for both MSI and MSI-X to be
> used (not at the same time of course): The MSI-X part of the intercept
> logic needs to fall through to the MSI one when the access is outside
> the MSI-X capability bounds.
> 
> Signed-off-by: Jan Beulich <jbeulich@suse.com>
> 

Release-acked-by: Wei Liu <wei.liu2@citrix.com>
diff mbox

Patch

--- a/xen/arch/x86/msi.c
+++ b/xen/arch/x86/msi.c
@@ -1292,17 +1292,17 @@  int pci_msi_conf_write_intercept(struct
                                           PCI_CAP_ID_MSIX);
         ASSERT(pos);
 
-        if ( reg < pos || reg >= msix_pba_offset_reg(pos) + 4 )
-            return 0;
+        if ( reg >= pos && reg < msix_pba_offset_reg(pos) + 4 )
+        {
+            if ( reg != msix_control_reg(pos) || size != 2 )
+                return -EACCES;
 
-        if ( reg != msix_control_reg(pos) || size != 2 )
-            return -EACCES;
+            pdev->msix->guest_maskall = !!(*data & PCI_MSIX_FLAGS_MASKALL);
+            if ( pdev->msix->host_maskall )
+                *data |= PCI_MSIX_FLAGS_MASKALL;
 
-        pdev->msix->guest_maskall = !!(*data & PCI_MSIX_FLAGS_MASKALL);
-        if ( pdev->msix->host_maskall )
-            *data |= PCI_MSIX_FLAGS_MASKALL;
-
-        return 1;
+            return 1;
+        }
     }
 
     entry = find_msi_entry(pdev, -1, PCI_CAP_ID_MSI);