Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 3 Aug 2017 14:14:13 +0000 (UTC)
From:      Hans Petter Selasky <hselasky@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-10@freebsd.org
Subject:   svn commit: r322007 - in stable/10/sys: conf dev/mlx5 dev/mlx5/mlx5_core dev/mlx5/mlx5_en modules/mlx5
Message-ID:  <201708031414.v73EEDSt058939@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: hselasky
Date: Thu Aug  3 14:14:13 2017
New Revision: 322007
URL: https://svnweb.freebsd.org/changeset/base/322007

Log:
  MFC r312872:
  Add support for reading advanced diagnostic counters.
  
  By default reading the diagnostic counters is disabled. The firmware
  decides which counters are supported and only those supported show up
  in the dev.mce.X.diagnostics sysctl tree.
  
  To enable reading of diagnostic counters set one or more of the
  following sysctls to one:
  
  dev.mce.X.conf.diag_general_enable=1
  dev.mce.X.conf.diag_pci_enable=1
  
  Sponsored by:		Mellanox Technologies

Added:
  stable/10/sys/dev/mlx5/diagnostics.h
     - copied unchanged from r312872, head/sys/dev/mlx5/diagnostics.h
  stable/10/sys/dev/mlx5/mlx5_core/mlx5_diagnostics.c
     - copied unchanged from r312872, head/sys/dev/mlx5/mlx5_core/mlx5_diagnostics.c
Modified:
  stable/10/sys/conf/files
  stable/10/sys/dev/mlx5/mlx5_en/en.h
  stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_ethtool.c
  stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_main.c
  stable/10/sys/modules/mlx5/Makefile
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/sys/conf/files
==============================================================================
--- stable/10/sys/conf/files	Thu Aug  3 14:12:23 2017	(r322006)
+++ stable/10/sys/conf/files	Thu Aug  3 14:14:13 2017	(r322007)
@@ -3939,6 +3939,8 @@ dev/mlx5/mlx5_core/mlx5_cmd.c			optional mlx5 pci	\
 	compile-with "${OFED_C}"
 dev/mlx5/mlx5_core/mlx5_cq.c			optional mlx5 pci	\
 	compile-with "${OFED_C}"
+dev/mlx5/mlx5_core/mlx5_diagnostics.c		optional mlx5 pci	\
+	compile-with "${OFED_C}"
 dev/mlx5/mlx5_core/mlx5_eq.c			optional mlx5 pci	\
 	compile-with "${OFED_C}"
 dev/mlx5/mlx5_core/mlx5_flow_table.c		optional mlx5 pci	\

Copied: stable/10/sys/dev/mlx5/diagnostics.h (from r312872, head/sys/dev/mlx5/diagnostics.h)
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ stable/10/sys/dev/mlx5/diagnostics.h	Thu Aug  3 14:14:13 2017	(r322007, copy of r312872, head/sys/dev/mlx5/diagnostics.h)
@@ -0,0 +1,138 @@
+/*-
+ * Copyright (c) 2013-2017, Mellanox Technologies, Ltd.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS `AS IS' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+#ifndef MLX5_CORE_DIAGNOSTICS_H
+#define	MLX5_CORE_DIAGNOSTICS_H
+
+#define	MLX5_CORE_DIAGNOSTICS_NUM(n, s, t) n
+#define	MLX5_CORE_DIAGNOSTICS_STRUCT(n, s, t) s,
+#define	MLX5_CORE_DIAGNOSTICS_ENTRY(n, s, t) { #s, (t) },
+
+struct mlx5_core_diagnostics_entry {
+	const char *const desc;
+	u16	counter_id;
+};
+
+#define	MLX5_CORE_PCI_DIAGNOSTICS(m) \
+m(+1, pxd_ready_bp, 0x0401) \
+m(+1, pci_write_bp, 0x0402) \
+m(+1, pci_read_bp, 0x0403) \
+m(+1, pci_read_stuck_no_completion_buffer, 0x0404) \
+m(+1, max_pci_bw, 0x0405) \
+m(+1, used_pci_bw, 0x0406) \
+m(+1, rx_pci_errors, 0) \
+m(+1, tx_pci_errors, 0) \
+m(+1, tx_pci_correctable_errors, 0) \
+m(+1, tx_pci_non_fatal_errors, 0) \
+m(+1, tx_pci_fatal_errors, 0)
+
+#define	MLX5_CORE_PCI_DIAGNOSTICS_NUM \
+	(0 MLX5_CORE_PCI_DIAGNOSTICS(MLX5_CORE_DIAGNOSTICS_NUM))
+
+union mlx5_core_pci_diagnostics {
+	u64	array[MLX5_CORE_PCI_DIAGNOSTICS_NUM];
+	struct {
+		u64	MLX5_CORE_PCI_DIAGNOSTICS(
+			MLX5_CORE_DIAGNOSTICS_STRUCT) dummy[0];
+	}	counter;
+};
+
+extern const struct mlx5_core_diagnostics_entry
+	mlx5_core_pci_diagnostics_table[MLX5_CORE_PCI_DIAGNOSTICS_NUM];
+
+#define	MLX5_CORE_GENERAL_DIAGNOSTICS(m) \
+m(+1, l0_mtt_miss, 0x0801) \
+m(+1, l0_mtt_hit, 0x0802) \
+m(+1, l1_mtt_miss, 0x0803) \
+m(+1, l1_mtt_hit, 0x0804) \
+m(+1, l0_mpt_miss, 0x0805) \
+m(+1, l0_mpt_hit, 0x0806) \
+m(+1, l1_mpt_miss, 0x0807) \
+m(+1, l1_mpt_hit, 0x0808) \
+m(+1, rxb_no_slow_path_credits, 0x0c01) \
+m(+1, rxb_no_fast_path_credits, 0x0c02) \
+m(+1, rxb_rxt_no_slow_path_cred_perf_count, 0x0c03) \
+m(+1, rxb_rxt_no_fast_path_cred_perf_count, 0x0c04) \
+m(+1, rxt_ctrl_perf_slice_load_slow, 0x1001) \
+m(+1, rxt_ctrl_perf_slice_load_fast, 0x1002) \
+m(+1, rxt_steering_perf_count_steering0_rse_work_rate, 0x1003) \
+m(+1, rxt_steering_perf_count_steering1_rse_work_rate, 0x1004) \
+m(+1, perf_count_tpt_credit, 0x1401) \
+m(+1, perf_wb_miss, 0x1402) \
+m(+1, perf_wb_hit, 0x1403) \
+m(+1, rxw_perf_rx_l1_slow_miss_ldb, 0x1404) \
+m(+1, rxw_perf_rx_l1_slow_hit_ldb, 0x1405) \
+m(+1, rxw_perf_rx_l1_fast_miss_ldb, 0x1406) \
+m(+1, rxw_perf_rx_l1_fast_hit_ldb, 0x1407) \
+m(+1, rxw_perf_l2_cache_read_miss_ldb, 0x1408) \
+m(+1, rxw_perf_l2_cache_read_hit_ldb, 0x1409) \
+m(+1, rxw_perf_rx_l1_slow_miss_reqsl, 0x140a) \
+m(+1, rxw_perf_rx_l1_slow_hit_reqsl, 0x140b) \
+m(+1, rxw_perf_rx_l1_fast_miss_reqsl, 0x140c) \
+m(+1, rxw_perf_rx_l1_fast_hit_reqsl, 0x140d) \
+m(+1, rxw_perf_l2_cache_read_miss_reqsl, 0x140e) \
+m(+1, rxw_perf_l2_cache_read_hit_reqsl, 0x140f) \
+m(+1, rxs_no_pxt_credits, 0x1801) \
+m(+1, rxc_eq_all_slices_busy, 0x1c01) \
+m(+1, rxc_cq_all_slices_busy, 0x1c02) \
+m(+1, rxc_msix_all_slices_busy, 0x1c03) \
+m(+1, sxw_qp_done_due_to_vl_limited, 0x2001) \
+m(+1, sxw_qp_done_due_to_desched, 0x2002) \
+m(+1, sxw_qp_done_due_to_work_done, 0x2003) \
+m(+1, sxw_qp_done_due_to_limited, 0x2004) \
+m(+1, sxw_qp_done_due_to_e2e_credits, 0x2005) \
+m(+1, sxw_packet_send_sxw2sxp_go_vld, 0x2006) \
+m(+1, sxw_perf_count_steering_hit, 0x2007) \
+m(+1, sxw_perf_count_steering_miss, 0x2008) \
+m(+1, sxw_perf_count_steering_rse_0, 0x2009) \
+m(+1, sxd_no_sched_credits, 0x2401) \
+m(+1, sxd_no_slow_path_sched_credits, 0x2402) \
+m(+1, tpt_indirect_mem_key, 0x2801)
+
+#define	MLX5_CORE_GENERAL_DIAGNOSTICS_NUM \
+	(0 MLX5_CORE_GENERAL_DIAGNOSTICS(MLX5_CORE_DIAGNOSTICS_NUM))
+
+union mlx5_core_general_diagnostics {
+	u64	array[MLX5_CORE_GENERAL_DIAGNOSTICS_NUM];
+	struct {
+		u64	MLX5_CORE_GENERAL_DIAGNOSTICS(
+			MLX5_CORE_DIAGNOSTICS_STRUCT) dummy[0];
+	}	counter;
+};
+
+extern const struct mlx5_core_diagnostics_entry
+	mlx5_core_general_diagnostics_table[MLX5_CORE_GENERAL_DIAGNOSTICS_NUM];
+
+/* function prototypes */
+int mlx5_core_set_diagnostics_full(struct mlx5_core_dev *mdev,
+				   u8 enable_pci, u8 enable_general);
+int mlx5_core_get_diagnostics_full(struct mlx5_core_dev *mdev,
+				   union mlx5_core_pci_diagnostics *ppci,
+				   union mlx5_core_general_diagnostics *pgen);
+int mlx5_core_supports_diagnostics(struct mlx5_core_dev *mdev, u16 counter_id);
+
+#endif					/* MLX5_CORE_DIAGNOSTICS_H */

Copied: stable/10/sys/dev/mlx5/mlx5_core/mlx5_diagnostics.c (from r312872, head/sys/dev/mlx5/mlx5_core/mlx5_diagnostics.c)
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ stable/10/sys/dev/mlx5/mlx5_core/mlx5_diagnostics.c	Thu Aug  3 14:14:13 2017	(r322007, copy of r312872, head/sys/dev/mlx5/mlx5_core/mlx5_diagnostics.c)
@@ -0,0 +1,286 @@
+/*-
+ * Copyright (c) 2013-2017, Mellanox Technologies, Ltd.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS `AS IS' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+#include <dev/mlx5/driver.h>
+#include <dev/mlx5/diagnostics.h>
+
+const struct mlx5_core_diagnostics_entry
+	mlx5_core_pci_diagnostics_table[
+		MLX5_CORE_PCI_DIAGNOSTICS_NUM] = {
+	MLX5_CORE_PCI_DIAGNOSTICS(MLX5_CORE_DIAGNOSTICS_ENTRY)
+};
+
+const struct mlx5_core_diagnostics_entry
+	mlx5_core_general_diagnostics_table[
+		MLX5_CORE_GENERAL_DIAGNOSTICS_NUM] = {
+	MLX5_CORE_GENERAL_DIAGNOSTICS(MLX5_CORE_DIAGNOSTICS_ENTRY)
+};
+
+static int mlx5_core_get_index_of_diag_counter(
+	const struct mlx5_core_diagnostics_entry *entry,
+	int size, u16 counter_id)
+{
+	int x;
+
+	/* check for invalid counter ID */
+	if (counter_id == 0)
+		return -1;
+
+	/* lookup counter ID in table */
+	for (x = 0; x != size; x++) {
+		if (entry[x].counter_id == counter_id)
+			return x;
+	}
+	return -1;
+}
+
+static void mlx5_core_put_diag_counter(
+	const struct mlx5_core_diagnostics_entry *entry,
+	u64 *array, int size, u16 counter_id, u64 value)
+{
+	int x;
+
+	/* check for invalid counter ID */
+	if (counter_id == 0)
+		return;
+
+	/* lookup counter ID in table */
+	for (x = 0; x != size; x++) {
+		if (entry[x].counter_id == counter_id) {
+			array[x] = value;
+			break;
+		}
+	}
+}
+
+int mlx5_core_set_diagnostics_full(struct mlx5_core_dev *dev,
+				   u8 enable_pci, u8 enable_general)
+{
+	void *diag_params_ctx;
+	void *in;
+	int numcounters;
+	int inlen;
+	int err;
+	int x;
+	int y;
+
+	if (MLX5_CAP_GEN(dev, debug) == 0)
+		return 0;
+
+	numcounters = MLX5_CAP_GEN(dev, num_of_diagnostic_counters);
+	if (numcounters == 0)
+		return 0;
+
+	inlen = MLX5_ST_SZ_BYTES(set_diagnostic_params_in) +
+	    MLX5_ST_SZ_BYTES(diagnostic_counter) * numcounters;
+	in = mlx5_vzalloc(inlen);
+	if (in == NULL)
+		return -ENOMEM;
+
+	diag_params_ctx = MLX5_ADDR_OF(set_diagnostic_params_in, in,
+				       diagnostic_params_ctx);
+
+	MLX5_SET(diagnostic_params_context, diag_params_ctx,
+		 enable, enable_pci || enable_general);
+	MLX5_SET(diagnostic_params_context, diag_params_ctx,
+		 single, 1);
+	MLX5_SET(diagnostic_params_context, diag_params_ctx,
+		 on_demand, 1);
+
+	/* collect the counters we want to enable */
+	for (x = y = 0; x != numcounters; x++) {
+		u16 counter_id =
+			MLX5_CAP_DEBUG(dev, diagnostic_counter[x].counter_id);
+		int index = -1;
+
+		if (index < 0 && enable_pci != 0) {
+			/* check if counter ID exists in local table */
+			index = mlx5_core_get_index_of_diag_counter(
+			    mlx5_core_pci_diagnostics_table,
+			    MLX5_CORE_PCI_DIAGNOSTICS_NUM,
+			    counter_id);
+		}
+		if (index < 0 && enable_general != 0) {
+			/* check if counter ID exists in local table */
+			index = mlx5_core_get_index_of_diag_counter(
+			    mlx5_core_general_diagnostics_table,
+			    MLX5_CORE_GENERAL_DIAGNOSTICS_NUM,
+			    counter_id);
+		}
+		if (index < 0)
+			continue;
+
+		MLX5_SET(diagnostic_params_context,
+			 diag_params_ctx,
+			 counter_id[y].counter_id,
+			 counter_id);
+		y++;
+	}
+
+	/* recompute input length */
+	inlen = MLX5_ST_SZ_BYTES(set_diagnostic_params_in) +
+	    MLX5_ST_SZ_BYTES(diagnostic_counter) * y;
+
+	/* set number of counters */
+	MLX5_SET(diagnostic_params_context, diag_params_ctx,
+		 num_of_counters, y);
+
+	/* execute firmware command */
+	err = mlx5_set_diagnostic_params(dev, in, inlen);
+
+	kvfree(in);
+
+	return err;
+}
+
+int mlx5_core_get_diagnostics_full(struct mlx5_core_dev *dev,
+				   union mlx5_core_pci_diagnostics *pdiag,
+				   union mlx5_core_general_diagnostics *pgen)
+{
+	void *out;
+	void *in;
+	int numcounters;
+	int outlen;
+	int inlen;
+	int err;
+	int x;
+
+	if (MLX5_CAP_GEN(dev, debug) == 0)
+		return 0;
+
+	numcounters = MLX5_CAP_GEN(dev, num_of_diagnostic_counters);
+	if (numcounters == 0)
+		return 0;
+
+	outlen = MLX5_ST_SZ_BYTES(query_diagnostic_counters_out) +
+	    MLX5_ST_SZ_BYTES(diagnostic_counter) * numcounters;
+
+	out = mlx5_vzalloc(outlen);
+	if (out == NULL)
+		return -ENOMEM;
+
+	err = mlx5_query_diagnostic_counters(dev, 1, 0, out, outlen);
+	if (err == 0) {
+		for (x = 0; x != numcounters; x++) {
+			u16 counter_id = MLX5_GET(
+			    query_diagnostic_counters_out,
+			    out, diag_counter[x].counter_id);
+			u64 counter_value = MLX5_GET64(
+			    query_diagnostic_counters_out,
+			    out, diag_counter[x].counter_value_h);
+
+			if (pdiag != NULL) {
+				mlx5_core_put_diag_counter(
+				    mlx5_core_pci_diagnostics_table,
+				    pdiag->array,
+				    MLX5_CORE_PCI_DIAGNOSTICS_NUM,
+				    counter_id, counter_value);
+			}
+			if (pgen != NULL) {
+				mlx5_core_put_diag_counter(
+				    mlx5_core_general_diagnostics_table,
+				    pgen->array,
+				    MLX5_CORE_GENERAL_DIAGNOSTICS_NUM,
+				    counter_id, counter_value);
+			}
+		}
+	}
+	kvfree(out);
+
+	if (pdiag != NULL) {
+		inlen = MLX5_ST_SZ_BYTES(mpcnt_reg);
+		outlen = MLX5_ST_SZ_BYTES(mpcnt_reg);
+
+		in = mlx5_vzalloc(inlen);
+		if (in == NULL)
+			return -ENOMEM;
+
+		out = mlx5_vzalloc(outlen);
+		if (out == NULL) {
+			kvfree(in);
+			return -ENOMEM;
+		}
+		MLX5_SET(mpcnt_reg, in, grp,
+			 MLX5_PCIE_PERFORMANCE_COUNTERS_GROUP);
+
+		err = mlx5_core_access_reg(dev, in, inlen, out, outlen,
+					   MLX5_REG_MPCNT, 0, 0);
+		if (err == 0) {
+			void *pcounters = MLX5_ADDR_OF(mpcnt_reg, out,
+			    counter_set.pcie_performance_counters_data_layout);
+
+			pdiag->counter.rx_pci_errors =
+			    MLX5_GET(pcie_performance_counters_data_layout,
+				     pcounters, rx_errors);
+			pdiag->counter.tx_pci_errors =
+			    MLX5_GET(pcie_performance_counters_data_layout,
+				     pcounters, tx_errors);
+		}
+		MLX5_SET(mpcnt_reg, in, grp,
+			 MLX5_PCIE_TIMERS_AND_STATES_COUNTERS_GROUP);
+
+		err = mlx5_core_access_reg(dev, in, inlen, out, outlen,
+		    MLX5_REG_MPCNT, 0, 0);
+		if (err == 0) {
+			void *pcounters = MLX5_ADDR_OF(mpcnt_reg, out,
+			    counter_set.pcie_timers_and_states_data_layout);
+
+			pdiag->counter.tx_pci_non_fatal_errors =
+			    MLX5_GET(pcie_timers_and_states_data_layout,
+				     pcounters, non_fatal_err_msg_sent);
+			pdiag->counter.tx_pci_fatal_errors =
+			    MLX5_GET(pcie_timers_and_states_data_layout,
+				     pcounters, fatal_err_msg_sent);
+		}
+		kvfree(in);
+		kvfree(out);
+	}
+	return 0;
+}
+
+int mlx5_core_supports_diagnostics(struct mlx5_core_dev *dev, u16 counter_id)
+{
+	int numcounters;
+	int x;
+
+	if (MLX5_CAP_GEN(dev, debug) == 0)
+		return 0;
+
+	/* check for any counter */
+	if (counter_id == 0)
+		return 1;
+
+	numcounters = MLX5_CAP_GEN(dev, num_of_diagnostic_counters);
+
+	/* check if counter ID exists in debug capability */
+	for (x = 0; x != numcounters; x++) {
+		if (MLX5_CAP_DEBUG(dev, diagnostic_counter[x].counter_id) ==
+		    counter_id)
+			return 1;
+	}
+	return 0;			/* not supported counter */
+}

Modified: stable/10/sys/dev/mlx5/mlx5_en/en.h
==============================================================================
--- stable/10/sys/dev/mlx5/mlx5_en/en.h	Thu Aug  3 14:12:23 2017	(r322006)
+++ stable/10/sys/dev/mlx5/mlx5_en/en.h	Thu Aug  3 14:14:13 2017	(r322007)
@@ -69,6 +69,7 @@
 #include <dev/mlx5/qp.h>
 #include <dev/mlx5/cq.h>
 #include <dev/mlx5/vport.h>
+#include <dev/mlx5/diagnostics.h>
 
 #include <dev/mlx5/mlx5_core/wq.h>
 #include <dev/mlx5/mlx5_core/transobj.h>
@@ -412,7 +413,9 @@ struct mlx5e_params {
   m(+1, u64 tx_completion_fact, "tx_completion_fact", "1..MAX: Completion event ratio") \
   m(+1, u64 tx_completion_fact_max, "tx_completion_fact_max", "Maximum completion event ratio") \
   m(+1, u64 hw_lro, "hw_lro", "set to enable hw_lro") \
-  m(+1, u64 cqe_zipping, "cqe_zipping", "0 : CQE zipping disabled")
+  m(+1, u64 cqe_zipping, "cqe_zipping", "0 : CQE zipping disabled") \
+  m(+1, u64 diag_pci_enable, "diag_pci_enable", "0: Disabled 1: Enabled") \
+  m(+1, u64 diag_general_enable, "diag_general_enable", "0: Disabled 1: Enabled")
 
 #define	MLX5E_PARAMS_NUM (0 MLX5E_PARAMS(MLX5E_STATS_COUNT))
 
@@ -670,6 +673,8 @@ struct mlx5e_priv {
 
 	struct mlx5e_params params;
 	struct mlx5e_params_ethtool params_ethtool;
+	union mlx5_core_pci_diagnostics params_pci;
+	union mlx5_core_general_diagnostics params_general;
 	struct mtx async_events_mtx;	/* sync hw events */
 	struct work_struct update_stats_work;
 	struct work_struct update_carrier_work;

Modified: stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_ethtool.c
==============================================================================
--- stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_ethtool.c	Thu Aug  3 14:12:23 2017	(r322006)
+++ stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_ethtool.c	Thu Aug  3 14:14:13 2017	(r322007)
@@ -377,6 +377,24 @@ mlx5e_ethtool_handler(SYSCTL_HANDLER_ARGS)
 			mlx5e_open_locked(priv->ifp);
 		break;
 
+	case MLX5_PARAM_OFFSET(diag_pci_enable):
+		priv->params_ethtool.diag_pci_enable =
+		    priv->params_ethtool.diag_pci_enable ? 1 : 0;
+
+		error = -mlx5_core_set_diagnostics_full(priv->mdev,
+		    priv->params_ethtool.diag_pci_enable,
+		    priv->params_ethtool.diag_general_enable);
+		break;
+
+	case MLX5_PARAM_OFFSET(diag_general_enable):
+		priv->params_ethtool.diag_general_enable =
+		    priv->params_ethtool.diag_general_enable ? 1 : 0;
+
+		error = -mlx5_core_set_diagnostics_full(priv->mdev,
+		    priv->params_ethtool.diag_pci_enable,
+		    priv->params_ethtool.diag_general_enable);
+		break;
+
 	default:
 		break;
 	}
@@ -624,6 +642,45 @@ mlx5e_ethtool_debug_stats(SYSCTL_HANDLER_ARGS)
 	return (error);
 }
 
+static void
+mlx5e_create_diagnostics(struct mlx5e_priv *priv)
+{
+	struct mlx5_core_diagnostics_entry entry;
+	struct sysctl_ctx_list *ctx;
+	struct sysctl_oid *node;
+	int x;
+
+	/* sysctl context we are using */
+	ctx = &priv->sysctl_ctx;
+
+	/* create root node */
+	node = SYSCTL_ADD_NODE(ctx,
+	    SYSCTL_CHILDREN(priv->sysctl_ifnet), OID_AUTO,
+	    "diagnostics", CTLFLAG_RD, NULL, "Diagnostics");
+	if (node == NULL)
+		return;
+
+	/* create PCI diagnostics */
+	for (x = 0; x != MLX5_CORE_PCI_DIAGNOSTICS_NUM; x++) {
+		entry = mlx5_core_pci_diagnostics_table[x];
+		if (mlx5_core_supports_diagnostics(priv->mdev, entry.counter_id) == 0)
+			continue;
+		SYSCTL_ADD_UQUAD(ctx, SYSCTL_CHILDREN(node), OID_AUTO,
+		    entry.desc, CTLFLAG_RD, priv->params_pci.array + x,
+		    "PCI diagnostics counter");
+	}
+
+	/* create general diagnostics */
+	for (x = 0; x != MLX5_CORE_GENERAL_DIAGNOSTICS_NUM; x++) {
+		entry = mlx5_core_general_diagnostics_table[x];
+		if (mlx5_core_supports_diagnostics(priv->mdev, entry.counter_id) == 0)
+			continue;
+		SYSCTL_ADD_UQUAD(ctx, SYSCTL_CHILDREN(node), OID_AUTO,
+		    entry.desc, CTLFLAG_RD, priv->params_general.array + x,
+		    "General diagnostics counter");
+	}
+}
+
 void
 mlx5e_create_ethtool(struct mlx5e_priv *priv)
 {
@@ -705,4 +762,7 @@ mlx5e_create_ethtool(struct mlx5e_priv *priv)
 	SYSCTL_ADD_PROC(&priv->sysctl_ctx, SYSCTL_CHILDREN(node), OID_AUTO, "eeprom_info",
 	    CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_MPSAFE, priv, 0,
 	    mlx5e_read_eeprom, "I", "EEPROM information");
+
+	/* Diagnostics support */
+	mlx5e_create_diagnostics(priv);
 }

Modified: stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_main.c
==============================================================================
--- stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_main.c	Thu Aug  3 14:12:23 2017	(r322006)
+++ stable/10/sys/dev/mlx5/mlx5_en/mlx5_en_main.c	Thu Aug  3 14:14:13 2017	(r322007)
@@ -573,6 +573,16 @@ mlx5e_update_stats_work(struct work_struct *work)
 
 free_out:
 	kvfree(out);
+
+	/* Update diagnostics, if any */
+	if (priv->params_ethtool.diag_pci_enable ||
+	    priv->params_ethtool.diag_general_enable) {
+		int error = mlx5_core_get_diagnostics_full(mdev,
+		    priv->params_ethtool.diag_pci_enable ? &priv->params_pci : NULL,
+		    priv->params_ethtool.diag_general_enable ? &priv->params_general : NULL);
+		if (error != 0)
+			if_printf(priv->ifp, "Failed reading diagnostics: %d\n", error);
+	}
 	PRIV_UNLOCK(priv);
 }
 

Modified: stable/10/sys/modules/mlx5/Makefile
==============================================================================
--- stable/10/sys/modules/mlx5/Makefile	Thu Aug  3 14:12:23 2017	(r322006)
+++ stable/10/sys/modules/mlx5/Makefile	Thu Aug  3 14:14:13 2017	(r322007)
@@ -6,6 +6,7 @@ SRCS= \
 mlx5_alloc.c \
 mlx5_cmd.c \
 mlx5_cq.c \
+mlx5_diagnostics.c \
 mlx5_eq.c \
 mlx5_eswitch_vacl.c \
 mlx5_flow_table.c \



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201708031414.v73EEDSt058939>