Browse Source

net/mlx5_core: Fix trimming down IRQ number

With several ConnectX-4 cards installed on a server, one may receive
irqn > 255 from the kernel API, which we mistakenly trim to 8bit.

This causes EQ creation failure with the following stack trace:
[<ffffffff812a11f4>] dump_stack+0x48/0x64
[<ffffffff810ace21>] __setup_irq+0x3a1/0x4f0
[<ffffffff810ad7e0>] request_threaded_irq+0x120/0x180
[<ffffffffa0923660>] ? mlx5_eq_int+0x450/0x450 [mlx5_core]
[<ffffffffa0922f64>] mlx5_create_map_eq+0x1e4/0x2b0 [mlx5_core]
[<ffffffffa091de01>] alloc_comp_eqs+0xb1/0x180 [mlx5_core]
[<ffffffffa091ea99>] mlx5_dev_init+0x5e9/0x6e0 [mlx5_core]
[<ffffffffa091ec29>] init_one+0x99/0x1c0 [mlx5_core]
[<ffffffff812e2afc>] local_pci_probe+0x4c/0xa0

Fixing it by changing of the irqn type from u8 to unsigned int to
support values > 255

Fixes: 61d0e73e0a5a ('net/mlx5_core: Use the the real irqn in eq->irqn')
Reported-by: Jiri Pirko <jiri@mellanox.com>
Signed-off-by: Doron Tsur <doront@mellanox.com>
Signed-off-by: Matan Barak <matanb@mellanox.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Doron Tsur 9 years ago
parent
commit
0b6e26ce89

+ 1 - 1
drivers/infiniband/hw/mlx5/cq.c

@@ -756,7 +756,7 @@ struct ib_cq *mlx5_ib_create_cq(struct ib_device *ibdev,
 	int uninitialized_var(index);
 	int uninitialized_var(index);
 	int uninitialized_var(inlen);
 	int uninitialized_var(inlen);
 	int cqe_size;
 	int cqe_size;
-	int irqn;
+	unsigned int irqn;
 	int eqn;
 	int eqn;
 	int err;
 	int err;
 
 

+ 3 - 3
drivers/net/ethernet/mellanox/mlx5/core/en_main.c

@@ -752,7 +752,7 @@ static int mlx5e_create_cq(struct mlx5e_channel *c,
 	struct mlx5_core_dev *mdev = priv->mdev;
 	struct mlx5_core_dev *mdev = priv->mdev;
 	struct mlx5_core_cq *mcq = &cq->mcq;
 	struct mlx5_core_cq *mcq = &cq->mcq;
 	int eqn_not_used;
 	int eqn_not_used;
-	int irqn;
+	unsigned int irqn;
 	int err;
 	int err;
 	u32 i;
 	u32 i;
 
 
@@ -806,7 +806,7 @@ static int mlx5e_enable_cq(struct mlx5e_cq *cq, struct mlx5e_cq_param *param)
 	void *in;
 	void *in;
 	void *cqc;
 	void *cqc;
 	int inlen;
 	int inlen;
-	int irqn_not_used;
+	unsigned int irqn_not_used;
 	int eqn;
 	int eqn;
 	int err;
 	int err;
 
 
@@ -1517,7 +1517,7 @@ static int mlx5e_create_drop_cq(struct mlx5e_priv *priv,
 	struct mlx5_core_dev *mdev = priv->mdev;
 	struct mlx5_core_dev *mdev = priv->mdev;
 	struct mlx5_core_cq *mcq = &cq->mcq;
 	struct mlx5_core_cq *mcq = &cq->mcq;
 	int eqn_not_used;
 	int eqn_not_used;
-	int irqn;
+	unsigned int irqn;
 	int err;
 	int err;
 
 
 	err = mlx5_cqwq_create(mdev, &param->wq, param->cqc, &cq->wq,
 	err = mlx5_cqwq_create(mdev, &param->wq, param->cqc, &cq->wq,

+ 2 - 1
drivers/net/ethernet/mellanox/mlx5/core/main.c

@@ -585,7 +585,8 @@ static void mlx5_irq_clear_affinity_hints(struct mlx5_core_dev *mdev)
 		mlx5_irq_clear_affinity_hint(mdev, i);
 		mlx5_irq_clear_affinity_hint(mdev, i);
 }
 }
 
 
-int mlx5_vector2eqn(struct mlx5_core_dev *dev, int vector, int *eqn, int *irqn)
+int mlx5_vector2eqn(struct mlx5_core_dev *dev, int vector, int *eqn,
+		    unsigned int *irqn)
 {
 {
 	struct mlx5_eq_table *table = &dev->priv.eq_table;
 	struct mlx5_eq_table *table = &dev->priv.eq_table;
 	struct mlx5_eq *eq, *n;
 	struct mlx5_eq *eq, *n;

+ 1 - 1
include/linux/mlx5/cq.h

@@ -45,7 +45,7 @@ struct mlx5_core_cq {
 	atomic_t		refcount;
 	atomic_t		refcount;
 	struct completion	free;
 	struct completion	free;
 	unsigned		vector;
 	unsigned		vector;
-	int			irqn;
+	unsigned int		irqn;
 	void (*comp)		(struct mlx5_core_cq *);
 	void (*comp)		(struct mlx5_core_cq *);
 	void (*event)		(struct mlx5_core_cq *, enum mlx5_event);
 	void (*event)		(struct mlx5_core_cq *, enum mlx5_event);
 	struct mlx5_uar	       *uar;
 	struct mlx5_uar	       *uar;

+ 3 - 2
include/linux/mlx5/driver.h

@@ -303,7 +303,7 @@ struct mlx5_eq {
 	u32			cons_index;
 	u32			cons_index;
 	struct mlx5_buf		buf;
 	struct mlx5_buf		buf;
 	int			size;
 	int			size;
-	u8			irqn;
+	unsigned int		irqn;
 	u8			eqn;
 	u8			eqn;
 	int			nent;
 	int			nent;
 	u64			mask;
 	u64			mask;
@@ -783,7 +783,8 @@ int mlx5_create_map_eq(struct mlx5_core_dev *dev, struct mlx5_eq *eq, u8 vecidx,
 int mlx5_destroy_unmap_eq(struct mlx5_core_dev *dev, struct mlx5_eq *eq);
 int mlx5_destroy_unmap_eq(struct mlx5_core_dev *dev, struct mlx5_eq *eq);
 int mlx5_start_eqs(struct mlx5_core_dev *dev);
 int mlx5_start_eqs(struct mlx5_core_dev *dev);
 int mlx5_stop_eqs(struct mlx5_core_dev *dev);
 int mlx5_stop_eqs(struct mlx5_core_dev *dev);
-int mlx5_vector2eqn(struct mlx5_core_dev *dev, int vector, int *eqn, int *irqn);
+int mlx5_vector2eqn(struct mlx5_core_dev *dev, int vector, int *eqn,
+		    unsigned int *irqn);
 int mlx5_core_attach_mcg(struct mlx5_core_dev *dev, union ib_gid *mgid, u32 qpn);
 int mlx5_core_attach_mcg(struct mlx5_core_dev *dev, union ib_gid *mgid, u32 qpn);
 int mlx5_core_detach_mcg(struct mlx5_core_dev *dev, union ib_gid *mgid, u32 qpn);
 int mlx5_core_detach_mcg(struct mlx5_core_dev *dev, union ib_gid *mgid, u32 qpn);