--- /dev/null
+From 62eed66e98b4c2286fef2ce5911d8d75b7515f7b Mon Sep 17 00:00:00 2001
+From: Tadeusz Struk <tadeusz.struk@intel.com>
+Date: Mon, 20 Mar 2017 17:25:35 -0700
+Subject: IB/hfi1: Protect the global dev_cntr_names and port_cntr_names
+
+From: Tadeusz Struk <tadeusz.struk@intel.com>
+
+commit 62eed66e98b4c2286fef2ce5911d8d75b7515f7b upstream.
+
+Protect the global dev_cntr_names and port_cntr_names with the global
+mutex as they are allocated and freed in a function called per device.
+Otherwise there is a danger of double free and memory leaks.
+
+Fixes: Commit b7481944b06e ("IB/hfi1: Show statistics counters under IB stats interface")
+Reviewed-by: Dennis Dalessandro <dennis.dalessandro@intel.com>
+Reviewed-by: Easwar Hariharan <easwar.hariharan@intel.com>
+Signed-off-by: Tadeusz Struk <tadeusz.struk@intel.com>
+Signed-off-by: Dennis Dalessandro <dennis.dalessandro@intel.com>
+Signed-off-by: Mike Marciniszyn <mike.marciniszyn@intel.com>
+Signed-off-by: Doug Ledford <dledford@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/infiniband/hw/hfi1/verbs.c | 12 +++++++++++-
+ 1 file changed, 11 insertions(+), 1 deletion(-)
+
+--- a/drivers/infiniband/hw/hfi1/verbs.c
++++ b/drivers/infiniband/hw/hfi1/verbs.c
+@@ -1524,6 +1524,7 @@ static const char * const driver_cntr_na
+ "DRIVER_EgrHdrFull"
+ };
+
++static DEFINE_MUTEX(cntr_names_lock); /* protects the *_cntr_names bufers */
+ static const char **dev_cntr_names;
+ static const char **port_cntr_names;
+ static int num_driver_cntrs = ARRAY_SIZE(driver_cntr_names);
+@@ -1578,6 +1579,7 @@ static struct rdma_hw_stats *alloc_hw_st
+ {
+ int i, err;
+
++ mutex_lock(&cntr_names_lock);
+ if (!cntr_names_initialized) {
+ struct hfi1_devdata *dd = dd_from_ibdev(ibdev);
+
+@@ -1586,8 +1588,10 @@ static struct rdma_hw_stats *alloc_hw_st
+ num_driver_cntrs,
+ &num_dev_cntrs,
+ &dev_cntr_names);
+- if (err)
++ if (err) {
++ mutex_unlock(&cntr_names_lock);
+ return NULL;
++ }
+
+ for (i = 0; i < num_driver_cntrs; i++)
+ dev_cntr_names[num_dev_cntrs + i] =
+@@ -1601,10 +1605,12 @@ static struct rdma_hw_stats *alloc_hw_st
+ if (err) {
+ kfree(dev_cntr_names);
+ dev_cntr_names = NULL;
++ mutex_unlock(&cntr_names_lock);
+ return NULL;
+ }
+ cntr_names_initialized = 1;
+ }
++ mutex_unlock(&cntr_names_lock);
+
+ if (!port_num)
+ return rdma_alloc_hw_stats_struct(
+@@ -1823,9 +1829,13 @@ void hfi1_unregister_ib_device(struct hf
+ del_timer_sync(&dev->mem_timer);
+ verbs_txreq_exit(dev);
+
++ mutex_lock(&cntr_names_lock);
+ kfree(dev_cntr_names);
+ kfree(port_cntr_names);
++ dev_cntr_names = NULL;
++ port_cntr_names = NULL;
+ cntr_names_initialized = 0;
++ mutex_unlock(&cntr_names_lock);
+ }
+
+ void hfi1_cnp_rcv(struct hfi1_packet *packet)