]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
4.14-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 16 Aug 2021 08:11:14 +0000 (10:11 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 16 Aug 2021 08:11:14 +0000 (10:11 +0200)
added patches:
pci-msi-enable-and-mask-msi-x-early.patch
x86-resctrl-fix-default-monitoring-groups-reporting.patch

queue-4.14/pci-msi-enable-and-mask-msi-x-early.patch [new file with mode: 0644]
queue-4.14/series
queue-4.14/x86-resctrl-fix-default-monitoring-groups-reporting.patch [new file with mode: 0644]

diff --git a/queue-4.14/pci-msi-enable-and-mask-msi-x-early.patch b/queue-4.14/pci-msi-enable-and-mask-msi-x-early.patch
new file mode 100644 (file)
index 0000000..1c93cc3
--- /dev/null
@@ -0,0 +1,106 @@
+From 438553958ba19296663c6d6583d208dfb6792830 Mon Sep 17 00:00:00 2001
+From: Thomas Gleixner <tglx@linutronix.de>
+Date: Thu, 29 Jul 2021 23:51:40 +0200
+Subject: PCI/MSI: Enable and mask MSI-X early
+
+From: Thomas Gleixner <tglx@linutronix.de>
+
+commit 438553958ba19296663c6d6583d208dfb6792830 upstream.
+
+The ordering of MSI-X enable in hardware is dysfunctional:
+
+ 1) MSI-X is disabled in the control register
+ 2) Various setup functions
+ 3) pci_msi_setup_msi_irqs() is invoked which ends up accessing
+    the MSI-X table entries
+ 4) MSI-X is enabled and masked in the control register with the
+    comment that enabling is required for some hardware to access
+    the MSI-X table
+
+Step #4 obviously contradicts #3. The history of this is an issue with the
+NIU hardware. When #4 was introduced the table access actually happened in
+msix_program_entries() which was invoked after enabling and masking MSI-X.
+
+This was changed in commit d71d6432e105 ("PCI/MSI: Kill redundant call of
+irq_set_msi_desc() for MSI-X interrupts") which removed the table write
+from msix_program_entries().
+
+Interestingly enough nobody noticed and either NIU still works or it did
+not get any testing with a kernel 3.19 or later.
+
+Nevertheless this is inconsistent and there is no reason why MSI-X can't be
+enabled and masked in the control register early on, i.e. move step #4
+above to step #1. This preserves the NIU workaround and has no side effects
+on other hardware.
+
+Fixes: d71d6432e105 ("PCI/MSI: Kill redundant call of irq_set_msi_desc() for MSI-X interrupts")
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Tested-by: Marc Zyngier <maz@kernel.org>
+Reviewed-by: Ashok Raj <ashok.raj@intel.com>
+Reviewed-by: Marc Zyngier <maz@kernel.org>
+Acked-by: Bjorn Helgaas <bhelgaas@google.com>
+Cc: stable@vger.kernel.org
+Link: https://lore.kernel.org/r/20210729222542.344136412@linutronix.de
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/pci/msi.c |   28 +++++++++++++++-------------
+ 1 file changed, 15 insertions(+), 13 deletions(-)
+
+--- a/drivers/pci/msi.c
++++ b/drivers/pci/msi.c
+@@ -743,18 +743,25 @@ static int msix_capability_init(struct p
+       u16 control;
+       void __iomem *base;
+-      /* Ensure MSI-X is disabled while it is set up */
+-      pci_msix_clear_and_set_ctrl(dev, PCI_MSIX_FLAGS_ENABLE, 0);
++      /*
++       * Some devices require MSI-X to be enabled before the MSI-X
++       * registers can be accessed.  Mask all the vectors to prevent
++       * interrupts coming in before they're fully set up.
++       */
++      pci_msix_clear_and_set_ctrl(dev, 0, PCI_MSIX_FLAGS_MASKALL |
++                                  PCI_MSIX_FLAGS_ENABLE);
+       pci_read_config_word(dev, dev->msix_cap + PCI_MSIX_FLAGS, &control);
+       /* Request & Map MSI-X table region */
+       base = msix_map_region(dev, msix_table_size(control));
+-      if (!base)
+-              return -ENOMEM;
++      if (!base) {
++              ret = -ENOMEM;
++              goto out_disable;
++      }
+       ret = msix_setup_entries(dev, base, entries, nvec, affd);
+       if (ret)
+-              return ret;
++              goto out_disable;
+       ret = pci_msi_setup_msi_irqs(dev, nvec, PCI_CAP_ID_MSIX);
+       if (ret)
+@@ -765,14 +772,6 @@ static int msix_capability_init(struct p
+       if (ret)
+               goto out_free;
+-      /*
+-       * Some devices require MSI-X to be enabled before we can touch the
+-       * MSI-X registers.  We need to mask all the vectors to prevent
+-       * interrupts coming in before they're fully set up.
+-       */
+-      pci_msix_clear_and_set_ctrl(dev, 0,
+-                              PCI_MSIX_FLAGS_MASKALL | PCI_MSIX_FLAGS_ENABLE);
+-
+       msix_program_entries(dev, entries);
+       ret = populate_msi_sysfs(dev);
+@@ -807,6 +806,9 @@ out_avail:
+ out_free:
+       free_msi_irqs(dev);
++out_disable:
++      pci_msix_clear_and_set_ctrl(dev, PCI_MSIX_FLAGS_ENABLE, 0);
++
+       return ret;
+ }
index 07b30882368e1b4e5a27bd4ec968b41e7ac5a241..8c3603db036b83490af7e5b314ba1c56ba1afcf1 100644 (file)
@@ -17,3 +17,5 @@ xen-events-fix-race-in-set_evtchn_to_irq.patch
 vsock-virtio-avoid-potential-deadlock-when-vsock-dev.patch
 powerpc-kprobes-fix-kprobe-oops-happens-in-booke.patch
 x86-tools-fix-objdump-version-check-again.patch
+x86-resctrl-fix-default-monitoring-groups-reporting.patch
+pci-msi-enable-and-mask-msi-x-early.patch
diff --git a/queue-4.14/x86-resctrl-fix-default-monitoring-groups-reporting.patch b/queue-4.14/x86-resctrl-fix-default-monitoring-groups-reporting.patch
new file mode 100644 (file)
index 0000000..6834e25
--- /dev/null
@@ -0,0 +1,125 @@
+From 064855a69003c24bd6b473b367d364e418c57625 Mon Sep 17 00:00:00 2001
+From: Babu Moger <Babu.Moger@amd.com>
+Date: Mon, 2 Aug 2021 14:38:58 -0500
+Subject: x86/resctrl: Fix default monitoring groups reporting
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Babu Moger <Babu.Moger@amd.com>
+
+commit 064855a69003c24bd6b473b367d364e418c57625 upstream.
+
+Creating a new sub monitoring group in the root /sys/fs/resctrl leads to
+getting the "Unavailable" value for mbm_total_bytes and mbm_local_bytes
+on the entire filesystem.
+
+Steps to reproduce:
+
+  1. mount -t resctrl resctrl /sys/fs/resctrl/
+
+  2. cd /sys/fs/resctrl/
+
+  3. cat mon_data/mon_L3_00/mbm_total_bytes
+     23189832
+
+  4. Create sub monitor group:
+  mkdir mon_groups/test1
+
+  5. cat mon_data/mon_L3_00/mbm_total_bytes
+     Unavailable
+
+When a new monitoring group is created, a new RMID is assigned to the
+new group. But the RMID is not active yet. When the events are read on
+the new RMID, it is expected to report the status as "Unavailable".
+
+When the user reads the events on the default monitoring group with
+multiple subgroups, the events on all subgroups are consolidated
+together. Currently, if any of the RMID reads report as "Unavailable",
+then everything will be reported as "Unavailable".
+
+Fix the issue by discarding the "Unavailable" reads and reporting all
+the successful RMID reads. This is not a problem on Intel systems as
+Intel reports 0 on Inactive RMIDs.
+
+Fixes: d89b7379015f ("x86/intel_rdt/cqm: Add mon_data")
+Reported-by: PaweÅ‚ Szulik <pawel.szulik@intel.com>
+Signed-off-by: Babu Moger <Babu.Moger@amd.com>
+Signed-off-by: Borislav Petkov <bp@suse.de>
+Acked-by: Reinette Chatre <reinette.chatre@intel.com>
+Cc: stable@vger.kernel.org
+Link: https://bugzilla.kernel.org/show_bug.cgi?id=213311
+Link: https://lkml.kernel.org/r/162793309296.9224.15871659871696482080.stgit@bmoger-ubuntu
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ arch/x86/kernel/cpu/intel_rdt_monitor.c |   27 +++++++++++++--------------
+ 1 file changed, 13 insertions(+), 14 deletions(-)
+
+--- a/arch/x86/kernel/cpu/intel_rdt_monitor.c
++++ b/arch/x86/kernel/cpu/intel_rdt_monitor.c
+@@ -225,15 +225,14 @@ void free_rmid(u32 rmid)
+               list_add_tail(&entry->list, &rmid_free_lru);
+ }
+-static int __mon_event_count(u32 rmid, struct rmid_read *rr)
++static u64 __mon_event_count(u32 rmid, struct rmid_read *rr)
+ {
+       u64 chunks, shift, tval;
+       struct mbm_state *m;
+       tval = __rmid_read(rmid, rr->evtid);
+       if (tval & (RMID_VAL_ERROR | RMID_VAL_UNAVAIL)) {
+-              rr->val = tval;
+-              return -EINVAL;
++              return tval;
+       }
+       switch (rr->evtid) {
+       case QOS_L3_OCCUP_EVENT_ID:
+@@ -245,12 +244,6 @@ static int __mon_event_count(u32 rmid, s
+       case QOS_L3_MBM_LOCAL_EVENT_ID:
+               m = &rr->d->mbm_local[rmid];
+               break;
+-      default:
+-              /*
+-               * Code would never reach here because
+-               * an invalid event id would fail the __rmid_read.
+-               */
+-              return -EINVAL;
+       }
+       if (rr->first) {
+@@ -278,23 +271,29 @@ void mon_event_count(void *info)
+       struct rdtgroup *rdtgrp, *entry;
+       struct rmid_read *rr = info;
+       struct list_head *head;
++      u64 ret_val;
+       rdtgrp = rr->rgrp;
+-      if (__mon_event_count(rdtgrp->mon.rmid, rr))
+-              return;
++      ret_val = __mon_event_count(rdtgrp->mon.rmid, rr);
+       /*
+-       * For Ctrl groups read data from child monitor groups.
++       * For Ctrl groups read data from child monitor groups and
++       * add them together. Count events which are read successfully.
++       * Discard the rmid_read's reporting errors.
+        */
+       head = &rdtgrp->mon.crdtgrp_list;
+       if (rdtgrp->type == RDTCTRL_GROUP) {
+               list_for_each_entry(entry, head, mon.crdtgrp_list) {
+-                      if (__mon_event_count(entry->mon.rmid, rr))
+-                              return;
++                      if (__mon_event_count(entry->mon.rmid, rr) == 0)
++                              ret_val = 0;
+               }
+       }
++
++      /* Report error if none of rmid_reads are successful */
++      if (ret_val)
++              rr->val = ret_val;
+ }
+ static void mbm_update(struct rdt_domain *d, int rmid)