[ofa-general] [PATCH 03/10] RDMA/nes: Remove tx_free_list

Chien Tung chien.tin.tung at intel.com
Fri Nov 21 12:50:44 PST 2008


From: Faisal Latif <faisal.latif at intel.com>

RDMA/nes: Remove tx_free_list

There is no lock protecting tx_free_list thus causing a system crash
when skb_dequeue() is called and the list is empty.  Since it did not give
any performance boost under heavy load, removing it to simplfy the code.
Change get_free_pkt call to allocate MAX_CM_BUFFER skb for connection 
establishment/teardown as well as MPA request/response.

Signed-off-by: Faisal Latif <faisal.latif at intel.com>
Signed-off-by: Chien Tung <chien.tin.tung at intel.com>
--
diff --git a/drivers/infiniband/hw/nes/nes_cm.c b/drivers/infiniband/hw/nes/nes_cm.c
index 257d994..fe07797 100644
--- a/drivers/infiniband/hw/nes/nes_cm.c
+++ b/drivers/infiniband/hw/nes/nes_cm.c
@@ -94,7 +94,7 @@ static int mini_cm_set(struct nes_cm_core *, u32, u32);
 
 static struct sk_buff *form_cm_frame(struct sk_buff *, struct nes_cm_node *,
 	void *, u32, void *, u32, u8);
-static struct sk_buff *get_free_pkt(struct nes_cm_node *cm_node);
+static struct sk_buff *get_free_pkt(u32);
 static int add_ref_cm_node(struct nes_cm_node *);
 static int rem_ref_cm_node(struct nes_cm_core *, struct nes_cm_node *);
 
@@ -356,7 +356,6 @@ static void print_core(struct nes_cm_core *core)
 
 	nes_debug(NES_DBG_CM, "State         : %u \n",  core->state);
 
-	nes_debug(NES_DBG_CM, "Tx Free cnt   : %u \n", skb_queue_len(&core->tx_free_list));
 	nes_debug(NES_DBG_CM, "Listen Nodes  : %u \n", atomic_read(&core->listen_node_cnt));
 	nes_debug(NES_DBG_CM, "Active Nodes  : %u \n", atomic_read(&core->node_cnt));
 
@@ -691,7 +690,7 @@ static int send_syn(struct nes_cm_node *cm_node, u32 sendack,
 	optionssize += 1;
 
 	if (!skb)
-		skb = get_free_pkt(cm_node);
+		skb = get_free_pkt(MAX_CM_BUFFER);
 	if (!skb) {
 		nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
 		return -1;
@@ -716,7 +715,7 @@ static int send_reset(struct nes_cm_node *cm_node, struct sk_buff *skb)
 	int flags = SET_RST | SET_ACK;
 
 	if (!skb)
-		skb = get_free_pkt(cm_node);
+		skb = get_free_pkt(MAX_CM_BUFFER);
 	if (!skb) {
 		nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
 		return -1;
@@ -737,7 +736,7 @@ static int send_ack(struct nes_cm_node *cm_node, struct sk_buff *skb)
 	int ret;
 
 	if (!skb)
-		skb = get_free_pkt(cm_node);
+		skb = get_free_pkt(MAX_CM_BUFFER);
 
 	if (!skb) {
 		nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
@@ -760,7 +759,7 @@ static int send_fin(struct nes_cm_node *cm_node, struct sk_buff *skb)
 
 	/* if we didn't get a frame get one */
 	if (!skb)
-		skb = get_free_pkt(cm_node);
+		skb = get_free_pkt(MAX_CM_BUFFER);
 
 	if (!skb) {
 		nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
@@ -777,40 +776,9 @@ static int send_fin(struct nes_cm_node *cm_node, struct sk_buff *skb)
 /**
  * get_free_pkt
  */
-static struct sk_buff *get_free_pkt(struct nes_cm_node *cm_node)
-{
-	struct sk_buff *skb, *new_skb;
-
-	/* check to see if we need to repopulate the free tx pkt queue */
-	if (skb_queue_len(&cm_node->cm_core->tx_free_list) < NES_CM_FREE_PKT_LO_WATERMARK) {
-		while (skb_queue_len(&cm_node->cm_core->tx_free_list) <
-				cm_node->cm_core->free_tx_pkt_max) {
-			/* replace the frame we took, we won't get it back */
-			new_skb = dev_alloc_skb(cm_node->cm_core->mtu);
-			BUG_ON(!new_skb);
-			/* add a replacement frame to the free tx list head */
-			skb_queue_head(&cm_node->cm_core->tx_free_list, new_skb);
-		}
-	}
-
-	skb = skb_dequeue(&cm_node->cm_core->tx_free_list);
-
-	return skb;
-}
-
-
-/**
- * make_hashkey - generate hash key from node tuple
- */
-static inline int make_hashkey(u16 loc_port, nes_addr_t loc_addr, u16 rem_port,
-		nes_addr_t rem_addr)
+static struct sk_buff *get_free_pkt(u32 pktsize)
 {
-	u32 hashkey = 0;
-
-	hashkey = loc_addr + rem_addr + loc_port + rem_port;
-	hashkey = (hashkey % NES_CM_HASHTABLE_SIZE);
-
-	return hashkey;
+		return dev_alloc_skb(pktsize);
 }
 
 
@@ -821,13 +789,9 @@ static struct nes_cm_node *find_node(struct nes_cm_core *cm_core,
 		u16 rem_port, nes_addr_t rem_addr, u16 loc_port, nes_addr_t loc_addr)
 {
 	unsigned long flags;
-	u32 hashkey;
 	struct list_head *hte;
 	struct nes_cm_node *cm_node;
 
-	/* make a hash index key for this packet */
-	hashkey = make_hashkey(loc_port, loc_addr, rem_port, rem_addr);
-
 	/* get a handle on the hte */
 	hte = &cm_core->connected_nodes;
 
@@ -895,7 +859,6 @@ static struct nes_cm_listener *find_listener(struct nes_cm_core *cm_core,
 static int add_hte_node(struct nes_cm_core *cm_core, struct nes_cm_node *cm_node)
 {
 	unsigned long flags;
-	u32 hashkey;
 	struct list_head *hte;
 
 	if (!cm_node || !cm_core)
@@ -904,11 +867,6 @@ static int add_hte_node(struct nes_cm_core *cm_core, struct nes_cm_node *cm_node
 	nes_debug(NES_DBG_CM, "Adding Node %p to Active Connection HT\n",
 		cm_node);
 
-	/* first, make an index into our hash table */
-	hashkey = make_hashkey(cm_node->loc_port, cm_node->loc_addr,
-			cm_node->rem_port, cm_node->rem_addr);
-	cm_node->hashkey = hashkey;
-
 	spin_lock_irqsave(&cm_core->ht_lock, flags);
 
 	/* get a handle on the hash table element (list head for this slot) */
@@ -2151,10 +2109,7 @@ static void mini_cm_recv_pkt(struct nes_cm_core *cm_core,
  */
 static struct nes_cm_core *nes_cm_alloc_core(void)
 {
-	int i;
-
 	struct nes_cm_core *cm_core;
-	struct sk_buff *skb = NULL;
 
 	/* setup the CM core */
 	/* alloc top level core control structure */
@@ -2172,19 +2127,6 @@ static struct nes_cm_core *nes_cm_alloc_core(void)
 
 	atomic_set(&cm_core->events_posted, 0);
 
-	/* init the packet lists */
-	skb_queue_head_init(&cm_core->tx_free_list);
-
-	for (i = 0; i < NES_CM_DEFAULT_FRAME_CNT; i++) {
-		skb = dev_alloc_skb(cm_core->mtu);
-		if (!skb) {
-			kfree(cm_core);
-			return NULL;
-		}
-		/* add 'raw' skb to free frame list */
-		skb_queue_head(&cm_core->tx_free_list, skb);
-	}
-
 	cm_core->api = &nes_cm_api;
 
 	spin_lock_init(&cm_core->ht_lock);
diff --git a/drivers/infiniband/hw/nes/nes_cm.h b/drivers/infiniband/hw/nes/nes_cm.h
index 282a9cb..89d80fc 100644
--- a/drivers/infiniband/hw/nes/nes_cm.h
+++ b/drivers/infiniband/hw/nes/nes_cm.h
@@ -161,6 +161,8 @@ struct nes_timer_entry {
 
 #define NES_CM_DEF_SEQ2      0x18ed5740
 #define NES_CM_DEF_LOCAL_ID2 0xb807
+#define	MAX_CM_BUFFER	512
+
 
 typedef u32 nes_addr_t;
 
@@ -254,8 +256,6 @@ struct nes_cm_listener {
 
 /* per connection node and node state information */
 struct nes_cm_node {
-	u32                       hashkey;
-
 	nes_addr_t                loc_addr, rem_addr;
 	u16                       loc_port, rem_port;
 
@@ -352,7 +352,6 @@ struct nes_cm_core {
 	u32                     mtu;
 	u32                     free_tx_pkt_max;
 	u32                     rx_pkt_posted;
-	struct sk_buff_head     tx_free_list;
 	atomic_t                ht_node_cnt;
 	struct list_head        connected_nodes;
 	/* struct list_head hashtable[NES_CM_HASHTABLE_SIZE]; */



More information about the general mailing list