git: 253a1fa16b98 - main - mlx5: Fix handling of port_module_event

From: Konstantin Belousov <kib_at_FreeBSD.org>
Date: Sat, 23 Nov 2024 11:00:57 UTC
The branch main has been updated by kib:

URL: https://cgit.FreeBSD.org/src/commit/?id=253a1fa16b98ac5f73f0820cfdd4f5ad7378757a

commit 253a1fa16b98ac5f73f0820cfdd4f5ad7378757a
Author:     Ariel Ehrenberg <aehrenberg@nvidia.com>
AuthorDate: 2024-10-31 09:18:26 +0000
Commit:     Konstantin Belousov <kib@FreeBSD.org>
CommitDate: 2024-11-23 10:59:26 +0000

    mlx5: Fix handling of port_module_event
    
    Remove the array of port module status and instead save module status
    and module number.
    
    At boot, for each PCI function driver get event from fw about module
    status. The event contains module number and module status. Driver
    stores module number and module status..  When user (ifconfig) ask for
    modules information, for each pci function driver first queries fw to
    get module number of current pci function, then driver compares the
    module number to the module number it stored before and if it matches
    and module status is "plugged and enabled" then driver queries fw for
    the eprom information of that module number and return it to the
    caller.
    
    In fact fw could have concluded that required module number of the
    current pci function, but fw is not implemented this way. current
    design of PRM/FW is that MCIA register handling is only aware of
    modules, not the pci function->module connections.  FW is designed to
    take the module number written to MCIA and write/read the content
    to/from the associated module's EPROM.
    
    So, based on current FW design, we must supply the module num so fw
    can find the corresponding I2C interface of the module to write/read.
    
    Sponsored by:   NVidia networking
    MFC after:      1 week
---
 sys/dev/mlx5/driver.h            |  3 ++-
 sys/dev/mlx5/mlx5_core/mlx5_eq.c | 10 +++++-----
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/sys/dev/mlx5/driver.h b/sys/dev/mlx5/driver.h
index db1c9f0bb46c..cdefe7e013f6 100644
--- a/sys/dev/mlx5/driver.h
+++ b/sys/dev/mlx5/driver.h
@@ -723,7 +723,8 @@ struct mlx5_core_dev {
 	u32			vsc_addr;
 	u32			issi;
 	struct mlx5_special_contexts special_contexts;
-	unsigned int module_status[MLX5_MAX_PORTS];
+	unsigned int module_status;
+	unsigned int module_num;
 	struct mlx5_flow_root_namespace *root_ns;
 	struct mlx5_flow_root_namespace *fdb_root_ns;
 	struct mlx5_flow_root_namespace *esw_egress_root_ns;
diff --git a/sys/dev/mlx5/mlx5_core/mlx5_eq.c b/sys/dev/mlx5/mlx5_core/mlx5_eq.c
index 29c12e41650e..1090f8638171 100644
--- a/sys/dev/mlx5/mlx5_core/mlx5_eq.c
+++ b/sys/dev/mlx5/mlx5_core/mlx5_eq.c
@@ -690,9 +690,9 @@ static const char *mlx5_port_module_event_error_type_to_string(u8 error_type)
 
 unsigned int mlx5_query_module_status(struct mlx5_core_dev *dev, int module_num)
 {
-	if (module_num < 0 || module_num >= MLX5_MAX_PORTS)
-		return 0;		/* undefined */
-	return dev->module_status[module_num];
+	if (module_num != dev->module_num)
+		return 0;		/* module num doesn't equal to what FW reported */
+	return dev->module_status;
 }
 
 static void mlx5_port_module_event(struct mlx5_core_dev *dev,
@@ -740,8 +740,8 @@ static void mlx5_port_module_event(struct mlx5_core_dev *dev,
 		    "Module %u, unknown status %d\n", module_num, module_status);
 	}
 	/* store module status */
-	if (module_num < MLX5_MAX_PORTS)
-		dev->module_status[module_num] = module_status;
+	dev->module_status = module_status;
+	dev->module_num = module_num;
 }
 
 static void mlx5_port_general_notification_event(struct mlx5_core_dev *dev,