aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/infiniband/hw/nes/nes_cm.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/infiniband/hw/nes/nes_cm.c')
-rw-r--r--drivers/infiniband/hw/nes/nes_cm.c279
1 files changed, 145 insertions, 134 deletions
diff --git a/drivers/infiniband/hw/nes/nes_cm.c b/drivers/infiniband/hw/nes/nes_cm.c
index 2854a6f7fdfe..a812db243477 100644
--- a/drivers/infiniband/hw/nes/nes_cm.c
+++ b/drivers/infiniband/hw/nes/nes_cm.c
@@ -86,15 +86,14 @@ static int mini_cm_accept(struct nes_cm_core *, struct ietf_mpa_frame *,
86 struct nes_cm_node *); 86 struct nes_cm_node *);
87static int mini_cm_reject(struct nes_cm_core *, struct ietf_mpa_frame *, 87static int mini_cm_reject(struct nes_cm_core *, struct ietf_mpa_frame *,
88 struct nes_cm_node *); 88 struct nes_cm_node *);
89static void mini_cm_recv_pkt(struct nes_cm_core *, struct nes_vnic *, 89static int mini_cm_recv_pkt(struct nes_cm_core *, struct nes_vnic *,
90 struct sk_buff *); 90 struct sk_buff *);
91static int mini_cm_dealloc_core(struct nes_cm_core *); 91static int mini_cm_dealloc_core(struct nes_cm_core *);
92static int mini_cm_get(struct nes_cm_core *); 92static int mini_cm_get(struct nes_cm_core *);
93static int mini_cm_set(struct nes_cm_core *, u32, u32); 93static int mini_cm_set(struct nes_cm_core *, u32, u32);
94 94
95static struct sk_buff *form_cm_frame(struct sk_buff *, struct nes_cm_node *, 95static void form_cm_frame(struct sk_buff *, struct nes_cm_node *,
96 void *, u32, void *, u32, u8); 96 void *, u32, void *, u32, u8);
97static struct sk_buff *get_free_pkt(struct nes_cm_node *cm_node);
98static int add_ref_cm_node(struct nes_cm_node *); 97static int add_ref_cm_node(struct nes_cm_node *);
99static int rem_ref_cm_node(struct nes_cm_core *, struct nes_cm_node *); 98static int rem_ref_cm_node(struct nes_cm_core *, struct nes_cm_node *);
100 99
@@ -251,7 +250,7 @@ static int parse_mpa(struct nes_cm_node *cm_node, u8 *buffer, u32 len)
251 * form_cm_frame - get a free packet and build empty frame Use 250 * form_cm_frame - get a free packet and build empty frame Use
252 * node info to build. 251 * node info to build.
253 */ 252 */
254static struct sk_buff *form_cm_frame(struct sk_buff *skb, 253static void form_cm_frame(struct sk_buff *skb,
255 struct nes_cm_node *cm_node, void *options, u32 optionsize, 254 struct nes_cm_node *cm_node, void *options, u32 optionsize,
256 void *data, u32 datasize, u8 flags) 255 void *data, u32 datasize, u8 flags)
257{ 256{
@@ -339,7 +338,6 @@ static struct sk_buff *form_cm_frame(struct sk_buff *skb,
339 skb_shinfo(skb)->nr_frags = 0; 338 skb_shinfo(skb)->nr_frags = 0;
340 cm_packets_created++; 339 cm_packets_created++;
341 340
342 return skb;
343} 341}
344 342
345 343
@@ -356,7 +354,6 @@ static void print_core(struct nes_cm_core *core)
356 354
357 nes_debug(NES_DBG_CM, "State : %u \n", core->state); 355 nes_debug(NES_DBG_CM, "State : %u \n", core->state);
358 356
359 nes_debug(NES_DBG_CM, "Tx Free cnt : %u \n", skb_queue_len(&core->tx_free_list));
360 nes_debug(NES_DBG_CM, "Listen Nodes : %u \n", atomic_read(&core->listen_node_cnt)); 357 nes_debug(NES_DBG_CM, "Listen Nodes : %u \n", atomic_read(&core->listen_node_cnt));
361 nes_debug(NES_DBG_CM, "Active Nodes : %u \n", atomic_read(&core->node_cnt)); 358 nes_debug(NES_DBG_CM, "Active Nodes : %u \n", atomic_read(&core->node_cnt));
362 359
@@ -381,8 +378,6 @@ int schedule_nes_timer(struct nes_cm_node *cm_node, struct sk_buff *skb,
381 int ret = 0; 378 int ret = 0;
382 u32 was_timer_set; 379 u32 was_timer_set;
383 380
384 if (!cm_node)
385 return -EINVAL;
386 new_send = kzalloc(sizeof(*new_send), GFP_ATOMIC); 381 new_send = kzalloc(sizeof(*new_send), GFP_ATOMIC);
387 if (!new_send) 382 if (!new_send)
388 return -1; 383 return -1;
@@ -459,13 +454,23 @@ static void nes_cm_timer_tick(unsigned long pass)
459 int ret = NETDEV_TX_OK; 454 int ret = NETDEV_TX_OK;
460 enum nes_cm_node_state last_state; 455 enum nes_cm_node_state last_state;
461 456
457 struct list_head timer_list;
458 INIT_LIST_HEAD(&timer_list);
462 spin_lock_irqsave(&cm_core->ht_lock, flags); 459 spin_lock_irqsave(&cm_core->ht_lock, flags);
463 460
464 list_for_each_safe(list_node, list_core_temp, 461 list_for_each_safe(list_node, list_core_temp,
465 &cm_core->connected_nodes) { 462 &cm_core->connected_nodes) {
466 cm_node = container_of(list_node, struct nes_cm_node, list); 463 cm_node = container_of(list_node, struct nes_cm_node, list);
467 add_ref_cm_node(cm_node); 464 if (!list_empty(&cm_node->recv_list) || (cm_node->send_entry)) {
468 spin_unlock_irqrestore(&cm_core->ht_lock, flags); 465 add_ref_cm_node(cm_node);
466 list_add(&cm_node->timer_entry, &timer_list);
467 }
468 }
469 spin_unlock_irqrestore(&cm_core->ht_lock, flags);
470
471 list_for_each_safe(list_node, list_core_temp, &timer_list) {
472 cm_node = container_of(list_node, struct nes_cm_node,
473 timer_entry);
469 spin_lock_irqsave(&cm_node->recv_list_lock, flags); 474 spin_lock_irqsave(&cm_node->recv_list_lock, flags);
470 list_for_each_safe(list_core, list_node_temp, 475 list_for_each_safe(list_core, list_node_temp,
471 &cm_node->recv_list) { 476 &cm_node->recv_list) {
@@ -519,7 +524,7 @@ static void nes_cm_timer_tick(unsigned long pass)
519 do { 524 do {
520 send_entry = cm_node->send_entry; 525 send_entry = cm_node->send_entry;
521 if (!send_entry) 526 if (!send_entry)
522 continue; 527 break;
523 if (time_after(send_entry->timetosend, jiffies)) { 528 if (time_after(send_entry->timetosend, jiffies)) {
524 if (cm_node->state != NES_CM_STATE_TSA) { 529 if (cm_node->state != NES_CM_STATE_TSA) {
525 if ((nexttimeout > 530 if ((nexttimeout >
@@ -528,18 +533,18 @@ static void nes_cm_timer_tick(unsigned long pass)
528 nexttimeout = 533 nexttimeout =
529 send_entry->timetosend; 534 send_entry->timetosend;
530 settimer = 1; 535 settimer = 1;
531 continue; 536 break;
532 } 537 }
533 } else { 538 } else {
534 free_retrans_entry(cm_node); 539 free_retrans_entry(cm_node);
535 continue; 540 break;
536 } 541 }
537 } 542 }
538 543
539 if ((cm_node->state == NES_CM_STATE_TSA) || 544 if ((cm_node->state == NES_CM_STATE_TSA) ||
540 (cm_node->state == NES_CM_STATE_CLOSED)) { 545 (cm_node->state == NES_CM_STATE_CLOSED)) {
541 free_retrans_entry(cm_node); 546 free_retrans_entry(cm_node);
542 continue; 547 break;
543 } 548 }
544 549
545 if (!send_entry->retranscount || 550 if (!send_entry->retranscount ||
@@ -557,7 +562,7 @@ static void nes_cm_timer_tick(unsigned long pass)
557 NES_CM_EVENT_ABORTED); 562 NES_CM_EVENT_ABORTED);
558 spin_lock_irqsave(&cm_node->retrans_list_lock, 563 spin_lock_irqsave(&cm_node->retrans_list_lock,
559 flags); 564 flags);
560 continue; 565 break;
561 } 566 }
562 atomic_inc(&send_entry->skb->users); 567 atomic_inc(&send_entry->skb->users);
563 cm_packets_retrans++; 568 cm_packets_retrans++;
@@ -583,7 +588,7 @@ static void nes_cm_timer_tick(unsigned long pass)
583 send_entry->retrycount--; 588 send_entry->retrycount--;
584 nexttimeout = jiffies + NES_SHORT_TIME; 589 nexttimeout = jiffies + NES_SHORT_TIME;
585 settimer = 1; 590 settimer = 1;
586 continue; 591 break;
587 } else { 592 } else {
588 cm_packets_sent++; 593 cm_packets_sent++;
589 } 594 }
@@ -615,14 +620,12 @@ static void nes_cm_timer_tick(unsigned long pass)
615 620
616 spin_unlock_irqrestore(&cm_node->retrans_list_lock, flags); 621 spin_unlock_irqrestore(&cm_node->retrans_list_lock, flags);
617 rem_ref_cm_node(cm_node->cm_core, cm_node); 622 rem_ref_cm_node(cm_node->cm_core, cm_node);
618 spin_lock_irqsave(&cm_core->ht_lock, flags);
619 if (ret != NETDEV_TX_OK) { 623 if (ret != NETDEV_TX_OK) {
620 nes_debug(NES_DBG_CM, "rexmit failed for cm_node=%p\n", 624 nes_debug(NES_DBG_CM, "rexmit failed for cm_node=%p\n",
621 cm_node); 625 cm_node);
622 break; 626 break;
623 } 627 }
624 } 628 }
625 spin_unlock_irqrestore(&cm_core->ht_lock, flags);
626 629
627 if (settimer) { 630 if (settimer) {
628 if (!timer_pending(&cm_core->tcp_timer)) { 631 if (!timer_pending(&cm_core->tcp_timer)) {
@@ -683,7 +686,7 @@ static int send_syn(struct nes_cm_node *cm_node, u32 sendack,
683 optionssize += 1; 686 optionssize += 1;
684 687
685 if (!skb) 688 if (!skb)
686 skb = get_free_pkt(cm_node); 689 skb = dev_alloc_skb(MAX_CM_BUFFER);
687 if (!skb) { 690 if (!skb) {
688 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n"); 691 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
689 return -1; 692 return -1;
@@ -708,7 +711,7 @@ static int send_reset(struct nes_cm_node *cm_node, struct sk_buff *skb)
708 int flags = SET_RST | SET_ACK; 711 int flags = SET_RST | SET_ACK;
709 712
710 if (!skb) 713 if (!skb)
711 skb = get_free_pkt(cm_node); 714 skb = dev_alloc_skb(MAX_CM_BUFFER);
712 if (!skb) { 715 if (!skb) {
713 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n"); 716 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
714 return -1; 717 return -1;
@@ -729,7 +732,7 @@ static int send_ack(struct nes_cm_node *cm_node, struct sk_buff *skb)
729 int ret; 732 int ret;
730 733
731 if (!skb) 734 if (!skb)
732 skb = get_free_pkt(cm_node); 735 skb = dev_alloc_skb(MAX_CM_BUFFER);
733 736
734 if (!skb) { 737 if (!skb) {
735 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n"); 738 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
@@ -752,7 +755,7 @@ static int send_fin(struct nes_cm_node *cm_node, struct sk_buff *skb)
752 755
753 /* if we didn't get a frame get one */ 756 /* if we didn't get a frame get one */
754 if (!skb) 757 if (!skb)
755 skb = get_free_pkt(cm_node); 758 skb = dev_alloc_skb(MAX_CM_BUFFER);
756 759
757 if (!skb) { 760 if (!skb) {
758 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n"); 761 nes_debug(NES_DBG_CM, "Failed to get a Free pkt\n");
@@ -767,59 +770,15 @@ static int send_fin(struct nes_cm_node *cm_node, struct sk_buff *skb)
767 770
768 771
769/** 772/**
770 * get_free_pkt
771 */
772static struct sk_buff *get_free_pkt(struct nes_cm_node *cm_node)
773{
774 struct sk_buff *skb, *new_skb;
775
776 /* check to see if we need to repopulate the free tx pkt queue */
777 if (skb_queue_len(&cm_node->cm_core->tx_free_list) < NES_CM_FREE_PKT_LO_WATERMARK) {
778 while (skb_queue_len(&cm_node->cm_core->tx_free_list) <
779 cm_node->cm_core->free_tx_pkt_max) {
780 /* replace the frame we took, we won't get it back */
781 new_skb = dev_alloc_skb(cm_node->cm_core->mtu);
782 BUG_ON(!new_skb);
783 /* add a replacement frame to the free tx list head */
784 skb_queue_head(&cm_node->cm_core->tx_free_list, new_skb);
785 }
786 }
787
788 skb = skb_dequeue(&cm_node->cm_core->tx_free_list);
789
790 return skb;
791}
792
793
794/**
795 * make_hashkey - generate hash key from node tuple
796 */
797static inline int make_hashkey(u16 loc_port, nes_addr_t loc_addr, u16 rem_port,
798 nes_addr_t rem_addr)
799{
800 u32 hashkey = 0;
801
802 hashkey = loc_addr + rem_addr + loc_port + rem_port;
803 hashkey = (hashkey % NES_CM_HASHTABLE_SIZE);
804
805 return hashkey;
806}
807
808
809/**
810 * find_node - find a cm node that matches the reference cm node 773 * find_node - find a cm node that matches the reference cm node
811 */ 774 */
812static struct nes_cm_node *find_node(struct nes_cm_core *cm_core, 775static struct nes_cm_node *find_node(struct nes_cm_core *cm_core,
813 u16 rem_port, nes_addr_t rem_addr, u16 loc_port, nes_addr_t loc_addr) 776 u16 rem_port, nes_addr_t rem_addr, u16 loc_port, nes_addr_t loc_addr)
814{ 777{
815 unsigned long flags; 778 unsigned long flags;
816 u32 hashkey;
817 struct list_head *hte; 779 struct list_head *hte;
818 struct nes_cm_node *cm_node; 780 struct nes_cm_node *cm_node;
819 781
820 /* make a hash index key for this packet */
821 hashkey = make_hashkey(loc_port, loc_addr, rem_port, rem_addr);
822
823 /* get a handle on the hte */ 782 /* get a handle on the hte */
824 hte = &cm_core->connected_nodes; 783 hte = &cm_core->connected_nodes;
825 784
@@ -887,7 +846,6 @@ static struct nes_cm_listener *find_listener(struct nes_cm_core *cm_core,
887static int add_hte_node(struct nes_cm_core *cm_core, struct nes_cm_node *cm_node) 846static int add_hte_node(struct nes_cm_core *cm_core, struct nes_cm_node *cm_node)
888{ 847{
889 unsigned long flags; 848 unsigned long flags;
890 u32 hashkey;
891 struct list_head *hte; 849 struct list_head *hte;
892 850
893 if (!cm_node || !cm_core) 851 if (!cm_node || !cm_core)
@@ -896,11 +854,6 @@ static int add_hte_node(struct nes_cm_core *cm_core, struct nes_cm_node *cm_node
896 nes_debug(NES_DBG_CM, "Adding Node %p to Active Connection HT\n", 854 nes_debug(NES_DBG_CM, "Adding Node %p to Active Connection HT\n",
897 cm_node); 855 cm_node);
898 856
899 /* first, make an index into our hash table */
900 hashkey = make_hashkey(cm_node->loc_port, cm_node->loc_addr,
901 cm_node->rem_port, cm_node->rem_addr);
902 cm_node->hashkey = hashkey;
903
904 spin_lock_irqsave(&cm_core->ht_lock, flags); 857 spin_lock_irqsave(&cm_core->ht_lock, flags);
905 858
906 /* get a handle on the hash table element (list head for this slot) */ 859 /* get a handle on the hash table element (list head for this slot) */
@@ -925,28 +878,36 @@ static int mini_cm_dec_refcnt_listen(struct nes_cm_core *cm_core,
925 struct list_head *list_pos = NULL; 878 struct list_head *list_pos = NULL;
926 struct list_head *list_temp = NULL; 879 struct list_head *list_temp = NULL;
927 struct nes_cm_node *cm_node = NULL; 880 struct nes_cm_node *cm_node = NULL;
881 struct list_head reset_list;
928 882
929 nes_debug(NES_DBG_CM, "attempting listener= %p free_nodes= %d, " 883 nes_debug(NES_DBG_CM, "attempting listener= %p free_nodes= %d, "
930 "refcnt=%d\n", listener, free_hanging_nodes, 884 "refcnt=%d\n", listener, free_hanging_nodes,
931 atomic_read(&listener->ref_count)); 885 atomic_read(&listener->ref_count));
932 /* free non-accelerated child nodes for this listener */ 886 /* free non-accelerated child nodes for this listener */
887 INIT_LIST_HEAD(&reset_list);
933 if (free_hanging_nodes) { 888 if (free_hanging_nodes) {
934 spin_lock_irqsave(&cm_core->ht_lock, flags); 889 spin_lock_irqsave(&cm_core->ht_lock, flags);
935 list_for_each_safe(list_pos, list_temp, 890 list_for_each_safe(list_pos, list_temp,
936 &g_cm_core->connected_nodes) { 891 &g_cm_core->connected_nodes) {
937 cm_node = container_of(list_pos, struct nes_cm_node, 892 cm_node = container_of(list_pos, struct nes_cm_node,
938 list); 893 list);
939 if ((cm_node->listener == listener) && 894 if ((cm_node->listener == listener) &&
940 (!cm_node->accelerated)) { 895 (!cm_node->accelerated)) {
941 cleanup_retrans_entry(cm_node); 896 add_ref_cm_node(cm_node);
942 spin_unlock_irqrestore(&cm_core->ht_lock, 897 list_add(&cm_node->reset_entry, &reset_list);
943 flags);
944 send_reset(cm_node, NULL);
945 spin_lock_irqsave(&cm_core->ht_lock, flags);
946 } 898 }
947 } 899 }
948 spin_unlock_irqrestore(&cm_core->ht_lock, flags); 900 spin_unlock_irqrestore(&cm_core->ht_lock, flags);
949 } 901 }
902
903 list_for_each_safe(list_pos, list_temp, &reset_list) {
904 cm_node = container_of(list_pos, struct nes_cm_node,
905 reset_entry);
906 cleanup_retrans_entry(cm_node);
907 send_reset(cm_node, NULL);
908 rem_ref_cm_node(cm_node->cm_core, cm_node);
909 }
910
950 spin_lock_irqsave(&cm_core->listen_list_lock, flags); 911 spin_lock_irqsave(&cm_core->listen_list_lock, flags);
951 if (!atomic_dec_return(&listener->ref_count)) { 912 if (!atomic_dec_return(&listener->ref_count)) {
952 list_del(&listener->list); 913 list_del(&listener->list);
@@ -1123,7 +1084,10 @@ static struct nes_cm_node *make_cm_node(struct nes_cm_core *cm_core,
1123 1084
1124 cm_node->loopbackpartner = NULL; 1085 cm_node->loopbackpartner = NULL;
1125 /* get the mac addr for the remote node */ 1086 /* get the mac addr for the remote node */
1126 arpindex = nes_arp_table(nesdev, cm_node->rem_addr, NULL, NES_ARP_RESOLVE); 1087 if (ipv4_is_loopback(htonl(cm_node->rem_addr)))
1088 arpindex = nes_arp_table(nesdev, ntohl(nesvnic->local_ipaddr), NULL, NES_ARP_RESOLVE);
1089 else
1090 arpindex = nes_arp_table(nesdev, cm_node->rem_addr, NULL, NES_ARP_RESOLVE);
1127 if (arpindex < 0) { 1091 if (arpindex < 0) {
1128 arpindex = nes_addr_resolve_neigh(nesvnic, cm_info->rem_addr); 1092 arpindex = nes_addr_resolve_neigh(nesvnic, cm_info->rem_addr);
1129 if (arpindex < 0) { 1093 if (arpindex < 0) {
@@ -1303,7 +1267,6 @@ static void drop_packet(struct sk_buff *skb)
1303static void handle_fin_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb, 1267static void handle_fin_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1304 struct tcphdr *tcph) 1268 struct tcphdr *tcph)
1305{ 1269{
1306 atomic_inc(&cm_resets_recvd);
1307 nes_debug(NES_DBG_CM, "Received FIN, cm_node = %p, state = %u. " 1270 nes_debug(NES_DBG_CM, "Received FIN, cm_node = %p, state = %u. "
1308 "refcnt=%d\n", cm_node, cm_node->state, 1271 "refcnt=%d\n", cm_node, cm_node->state,
1309 atomic_read(&cm_node->ref_count)); 1272 atomic_read(&cm_node->ref_count));
@@ -1341,6 +1304,7 @@ static void handle_rst_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1341{ 1304{
1342 1305
1343 int reset = 0; /* whether to send reset in case of err.. */ 1306 int reset = 0; /* whether to send reset in case of err.. */
1307 int passive_state;
1344 atomic_inc(&cm_resets_recvd); 1308 atomic_inc(&cm_resets_recvd);
1345 nes_debug(NES_DBG_CM, "Received Reset, cm_node = %p, state = %u." 1309 nes_debug(NES_DBG_CM, "Received Reset, cm_node = %p, state = %u."
1346 " refcnt=%d\n", cm_node, cm_node->state, 1310 " refcnt=%d\n", cm_node, cm_node->state,
@@ -1354,7 +1318,14 @@ static void handle_rst_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1354 cm_node->listener, cm_node->state); 1318 cm_node->listener, cm_node->state);
1355 active_open_err(cm_node, skb, reset); 1319 active_open_err(cm_node, skb, reset);
1356 break; 1320 break;
1357 /* For PASSIVE open states, remove the cm_node event */ 1321 case NES_CM_STATE_MPAREQ_RCVD:
1322 passive_state = atomic_add_return(1, &cm_node->passive_state);
1323 if (passive_state == NES_SEND_RESET_EVENT)
1324 create_event(cm_node, NES_CM_EVENT_RESET);
1325 cleanup_retrans_entry(cm_node);
1326 cm_node->state = NES_CM_STATE_CLOSED;
1327 dev_kfree_skb_any(skb);
1328 break;
1358 case NES_CM_STATE_ESTABLISHED: 1329 case NES_CM_STATE_ESTABLISHED:
1359 case NES_CM_STATE_SYN_RCVD: 1330 case NES_CM_STATE_SYN_RCVD:
1360 case NES_CM_STATE_LISTENING: 1331 case NES_CM_STATE_LISTENING:
@@ -1362,7 +1333,14 @@ static void handle_rst_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1362 passive_open_err(cm_node, skb, reset); 1333 passive_open_err(cm_node, skb, reset);
1363 break; 1334 break;
1364 case NES_CM_STATE_TSA: 1335 case NES_CM_STATE_TSA:
1336 active_open_err(cm_node, skb, reset);
1337 break;
1338 case NES_CM_STATE_CLOSED:
1339 cleanup_retrans_entry(cm_node);
1340 drop_packet(skb);
1341 break;
1365 default: 1342 default:
1343 drop_packet(skb);
1366 break; 1344 break;
1367 } 1345 }
1368} 1346}
@@ -1391,6 +1369,9 @@ static void handle_rcv_mpa(struct nes_cm_node *cm_node, struct sk_buff *skb,
1391 dev_kfree_skb_any(skb); 1369 dev_kfree_skb_any(skb);
1392 if (type == NES_CM_EVENT_CONNECTED) 1370 if (type == NES_CM_EVENT_CONNECTED)
1393 cm_node->state = NES_CM_STATE_TSA; 1371 cm_node->state = NES_CM_STATE_TSA;
1372 else
1373 atomic_set(&cm_node->passive_state,
1374 NES_PASSIVE_STATE_INDICATED);
1394 create_event(cm_node, type); 1375 create_event(cm_node, type);
1395 1376
1396 } 1377 }
@@ -1471,7 +1452,7 @@ static void handle_syn_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1471 int optionsize; 1452 int optionsize;
1472 1453
1473 optionsize = (tcph->doff << 2) - sizeof(struct tcphdr); 1454 optionsize = (tcph->doff << 2) - sizeof(struct tcphdr);
1474 skb_pull(skb, tcph->doff << 2); 1455 skb_trim(skb, 0);
1475 inc_sequence = ntohl(tcph->seq); 1456 inc_sequence = ntohl(tcph->seq);
1476 1457
1477 switch (cm_node->state) { 1458 switch (cm_node->state) {
@@ -1504,6 +1485,10 @@ static void handle_syn_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1504 cm_node->state = NES_CM_STATE_SYN_RCVD; 1485 cm_node->state = NES_CM_STATE_SYN_RCVD;
1505 send_syn(cm_node, 1, skb); 1486 send_syn(cm_node, 1, skb);
1506 break; 1487 break;
1488 case NES_CM_STATE_CLOSED:
1489 cleanup_retrans_entry(cm_node);
1490 send_reset(cm_node, skb);
1491 break;
1507 case NES_CM_STATE_TSA: 1492 case NES_CM_STATE_TSA:
1508 case NES_CM_STATE_ESTABLISHED: 1493 case NES_CM_STATE_ESTABLISHED:
1509 case NES_CM_STATE_FIN_WAIT1: 1494 case NES_CM_STATE_FIN_WAIT1:
@@ -1512,7 +1497,6 @@ static void handle_syn_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1512 case NES_CM_STATE_LAST_ACK: 1497 case NES_CM_STATE_LAST_ACK:
1513 case NES_CM_STATE_CLOSING: 1498 case NES_CM_STATE_CLOSING:
1514 case NES_CM_STATE_UNKNOWN: 1499 case NES_CM_STATE_UNKNOWN:
1515 case NES_CM_STATE_CLOSED:
1516 default: 1500 default:
1517 drop_packet(skb); 1501 drop_packet(skb);
1518 break; 1502 break;
@@ -1528,7 +1512,7 @@ static void handle_synack_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1528 int optionsize; 1512 int optionsize;
1529 1513
1530 optionsize = (tcph->doff << 2) - sizeof(struct tcphdr); 1514 optionsize = (tcph->doff << 2) - sizeof(struct tcphdr);
1531 skb_pull(skb, tcph->doff << 2); 1515 skb_trim(skb, 0);
1532 inc_sequence = ntohl(tcph->seq); 1516 inc_sequence = ntohl(tcph->seq);
1533 switch (cm_node->state) { 1517 switch (cm_node->state) {
1534 case NES_CM_STATE_SYN_SENT: 1518 case NES_CM_STATE_SYN_SENT:
@@ -1552,6 +1536,12 @@ static void handle_synack_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1552 /* passive open, so should not be here */ 1536 /* passive open, so should not be here */
1553 passive_open_err(cm_node, skb, 1); 1537 passive_open_err(cm_node, skb, 1);
1554 break; 1538 break;
1539 case NES_CM_STATE_LISTENING:
1540 case NES_CM_STATE_CLOSED:
1541 cm_node->tcp_cntxt.loc_seq_num = ntohl(tcph->ack_seq);
1542 cleanup_retrans_entry(cm_node);
1543 send_reset(cm_node, skb);
1544 break;
1555 case NES_CM_STATE_ESTABLISHED: 1545 case NES_CM_STATE_ESTABLISHED:
1556 case NES_CM_STATE_FIN_WAIT1: 1546 case NES_CM_STATE_FIN_WAIT1:
1557 case NES_CM_STATE_FIN_WAIT2: 1547 case NES_CM_STATE_FIN_WAIT2:
@@ -1559,7 +1549,6 @@ static void handle_synack_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1559 case NES_CM_STATE_TSA: 1549 case NES_CM_STATE_TSA:
1560 case NES_CM_STATE_CLOSING: 1550 case NES_CM_STATE_CLOSING:
1561 case NES_CM_STATE_UNKNOWN: 1551 case NES_CM_STATE_UNKNOWN:
1562 case NES_CM_STATE_CLOSED:
1563 case NES_CM_STATE_MPAREQ_SENT: 1552 case NES_CM_STATE_MPAREQ_SENT:
1564 default: 1553 default:
1565 drop_packet(skb); 1554 drop_packet(skb);
@@ -1574,6 +1563,13 @@ static void handle_ack_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1574 u32 inc_sequence; 1563 u32 inc_sequence;
1575 u32 rem_seq_ack; 1564 u32 rem_seq_ack;
1576 u32 rem_seq; 1565 u32 rem_seq;
1566 int ret;
1567 int optionsize;
1568 u32 temp_seq = cm_node->tcp_cntxt.loc_seq_num;
1569
1570 optionsize = (tcph->doff << 2) - sizeof(struct tcphdr);
1571 cm_node->tcp_cntxt.loc_seq_num = ntohl(tcph->ack_seq);
1572
1577 if (check_seq(cm_node, tcph, skb)) 1573 if (check_seq(cm_node, tcph, skb))
1578 return; 1574 return;
1579 1575
@@ -1586,7 +1582,18 @@ static void handle_ack_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1586 switch (cm_node->state) { 1582 switch (cm_node->state) {
1587 case NES_CM_STATE_SYN_RCVD: 1583 case NES_CM_STATE_SYN_RCVD:
1588 /* Passive OPEN */ 1584 /* Passive OPEN */
1585 ret = handle_tcp_options(cm_node, tcph, skb, optionsize, 1);
1586 if (ret)
1587 break;
1589 cm_node->tcp_cntxt.rem_ack_num = ntohl(tcph->ack_seq); 1588 cm_node->tcp_cntxt.rem_ack_num = ntohl(tcph->ack_seq);
1589 cm_node->tcp_cntxt.loc_seq_num = temp_seq;
1590 if (cm_node->tcp_cntxt.rem_ack_num !=
1591 cm_node->tcp_cntxt.loc_seq_num) {
1592 nes_debug(NES_DBG_CM, "rem_ack_num != loc_seq_num\n");
1593 cleanup_retrans_entry(cm_node);
1594 send_reset(cm_node, skb);
1595 return;
1596 }
1590 cm_node->state = NES_CM_STATE_ESTABLISHED; 1597 cm_node->state = NES_CM_STATE_ESTABLISHED;
1591 if (datasize) { 1598 if (datasize) {
1592 cm_node->tcp_cntxt.rcv_nxt = inc_sequence + datasize; 1599 cm_node->tcp_cntxt.rcv_nxt = inc_sequence + datasize;
@@ -1618,11 +1625,15 @@ static void handle_ack_pkt(struct nes_cm_node *cm_node, struct sk_buff *skb,
1618 dev_kfree_skb_any(skb); 1625 dev_kfree_skb_any(skb);
1619 } 1626 }
1620 break; 1627 break;
1628 case NES_CM_STATE_LISTENING:
1629 case NES_CM_STATE_CLOSED:
1630 cleanup_retrans_entry(cm_node);
1631 send_reset(cm_node, skb);
1632 break;
1621 case NES_CM_STATE_FIN_WAIT1: 1633 case NES_CM_STATE_FIN_WAIT1:
1622 case NES_CM_STATE_SYN_SENT: 1634 case NES_CM_STATE_SYN_SENT:
1623 case NES_CM_STATE_FIN_WAIT2: 1635 case NES_CM_STATE_FIN_WAIT2:
1624 case NES_CM_STATE_TSA: 1636 case NES_CM_STATE_TSA:
1625 case NES_CM_STATE_CLOSED:
1626 case NES_CM_STATE_MPAREQ_RCVD: 1637 case NES_CM_STATE_MPAREQ_RCVD:
1627 case NES_CM_STATE_LAST_ACK: 1638 case NES_CM_STATE_LAST_ACK:
1628 case NES_CM_STATE_CLOSING: 1639 case NES_CM_STATE_CLOSING:
@@ -1645,9 +1656,9 @@ static int handle_tcp_options(struct nes_cm_node *cm_node, struct tcphdr *tcph,
1645 nes_debug(NES_DBG_CM, "%s: Node %p, Sending RESET\n", 1656 nes_debug(NES_DBG_CM, "%s: Node %p, Sending RESET\n",
1646 __func__, cm_node); 1657 __func__, cm_node);
1647 if (passive) 1658 if (passive)
1648 passive_open_err(cm_node, skb, 0); 1659 passive_open_err(cm_node, skb, 1);
1649 else 1660 else
1650 active_open_err(cm_node, skb, 0); 1661 active_open_err(cm_node, skb, 1);
1651 return 1; 1662 return 1;
1652 } 1663 }
1653 } 1664 }
@@ -1967,6 +1978,7 @@ static int mini_cm_reject(struct nes_cm_core *cm_core,
1967 struct ietf_mpa_frame *mpa_frame, struct nes_cm_node *cm_node) 1978 struct ietf_mpa_frame *mpa_frame, struct nes_cm_node *cm_node)
1968{ 1979{
1969 int ret = 0; 1980 int ret = 0;
1981 int passive_state;
1970 1982
1971 nes_debug(NES_DBG_CM, "%s cm_node=%p type=%d state=%d\n", 1983 nes_debug(NES_DBG_CM, "%s cm_node=%p type=%d state=%d\n",
1972 __func__, cm_node, cm_node->tcp_cntxt.client, cm_node->state); 1984 __func__, cm_node, cm_node->tcp_cntxt.client, cm_node->state);
@@ -1974,9 +1986,13 @@ static int mini_cm_reject(struct nes_cm_core *cm_core,
1974 if (cm_node->tcp_cntxt.client) 1986 if (cm_node->tcp_cntxt.client)
1975 return ret; 1987 return ret;
1976 cleanup_retrans_entry(cm_node); 1988 cleanup_retrans_entry(cm_node);
1977 cm_node->state = NES_CM_STATE_CLOSED;
1978 1989
1979 ret = send_reset(cm_node, NULL); 1990 passive_state = atomic_add_return(1, &cm_node->passive_state);
1991 cm_node->state = NES_CM_STATE_CLOSED;
1992 if (passive_state == NES_SEND_RESET_EVENT)
1993 rem_ref_cm_node(cm_core, cm_node);
1994 else
1995 ret = send_reset(cm_node, NULL);
1980 return ret; 1996 return ret;
1981} 1997}
1982 1998
@@ -2034,7 +2050,7 @@ static int mini_cm_close(struct nes_cm_core *cm_core, struct nes_cm_node *cm_nod
2034 * recv_pkt - recv an ETHERNET packet, and process it through CM 2050 * recv_pkt - recv an ETHERNET packet, and process it through CM
2035 * node state machine 2051 * node state machine
2036 */ 2052 */
2037static void mini_cm_recv_pkt(struct nes_cm_core *cm_core, 2053static int mini_cm_recv_pkt(struct nes_cm_core *cm_core,
2038 struct nes_vnic *nesvnic, struct sk_buff *skb) 2054 struct nes_vnic *nesvnic, struct sk_buff *skb)
2039{ 2055{
2040 struct nes_cm_node *cm_node = NULL; 2056 struct nes_cm_node *cm_node = NULL;
@@ -2042,23 +2058,16 @@ static void mini_cm_recv_pkt(struct nes_cm_core *cm_core,
2042 struct iphdr *iph; 2058 struct iphdr *iph;
2043 struct tcphdr *tcph; 2059 struct tcphdr *tcph;
2044 struct nes_cm_info nfo; 2060 struct nes_cm_info nfo;
2061 int skb_handled = 1;
2045 2062
2046 if (!skb) 2063 if (!skb)
2047 return; 2064 return 0;
2048 if (skb->len < sizeof(struct iphdr) + sizeof(struct tcphdr)) { 2065 if (skb->len < sizeof(struct iphdr) + sizeof(struct tcphdr)) {
2049 dev_kfree_skb_any(skb); 2066 return 0;
2050 return;
2051 } 2067 }
2052 2068
2053 iph = (struct iphdr *)skb->data; 2069 iph = (struct iphdr *)skb->data;
2054 tcph = (struct tcphdr *)(skb->data + sizeof(struct iphdr)); 2070 tcph = (struct tcphdr *)(skb->data + sizeof(struct iphdr));
2055 skb_reset_network_header(skb);
2056 skb_set_transport_header(skb, sizeof(*tcph));
2057 if (!tcph) {
2058 dev_kfree_skb_any(skb);
2059 return;
2060 }
2061 skb->len = ntohs(iph->tot_len);
2062 2071
2063 nfo.loc_addr = ntohl(iph->daddr); 2072 nfo.loc_addr = ntohl(iph->daddr);
2064 nfo.loc_port = ntohs(tcph->dest); 2073 nfo.loc_port = ntohs(tcph->dest);
@@ -2077,23 +2086,21 @@ static void mini_cm_recv_pkt(struct nes_cm_core *cm_core,
2077 /* Only type of packet accepted are for */ 2086 /* Only type of packet accepted are for */
2078 /* the PASSIVE open (syn only) */ 2087 /* the PASSIVE open (syn only) */
2079 if ((!tcph->syn) || (tcph->ack)) { 2088 if ((!tcph->syn) || (tcph->ack)) {
2080 cm_packets_dropped++; 2089 skb_handled = 0;
2081 break; 2090 break;
2082 } 2091 }
2083 listener = find_listener(cm_core, nfo.loc_addr, 2092 listener = find_listener(cm_core, nfo.loc_addr,
2084 nfo.loc_port, 2093 nfo.loc_port,
2085 NES_CM_LISTENER_ACTIVE_STATE); 2094 NES_CM_LISTENER_ACTIVE_STATE);
2086 if (listener) { 2095 if (!listener) {
2087 nfo.cm_id = listener->cm_id; 2096 nfo.cm_id = NULL;
2088 nfo.conn_type = listener->conn_type; 2097 nfo.conn_type = 0;
2089 } else { 2098 nes_debug(NES_DBG_CM, "Unable to find listener for the pkt\n");
2090 nes_debug(NES_DBG_CM, "Unable to find listener " 2099 skb_handled = 0;
2091 "for the pkt\n");
2092 cm_packets_dropped++;
2093 dev_kfree_skb_any(skb);
2094 break; 2100 break;
2095 } 2101 }
2096 2102 nfo.cm_id = listener->cm_id;
2103 nfo.conn_type = listener->conn_type;
2097 cm_node = make_cm_node(cm_core, nesvnic, &nfo, 2104 cm_node = make_cm_node(cm_core, nesvnic, &nfo,
2098 listener); 2105 listener);
2099 if (!cm_node) { 2106 if (!cm_node) {
@@ -2119,9 +2126,13 @@ static void mini_cm_recv_pkt(struct nes_cm_core *cm_core,
2119 dev_kfree_skb_any(skb); 2126 dev_kfree_skb_any(skb);
2120 break; 2127 break;
2121 } 2128 }
2129 skb_reset_network_header(skb);
2130 skb_set_transport_header(skb, sizeof(*tcph));
2131 skb->len = ntohs(iph->tot_len);
2122 process_packet(cm_node, skb, cm_core); 2132 process_packet(cm_node, skb, cm_core);
2123 rem_ref_cm_node(cm_core, cm_node); 2133 rem_ref_cm_node(cm_core, cm_node);
2124 } while (0); 2134 } while (0);
2135 return skb_handled;
2125} 2136}
2126 2137
2127 2138
@@ -2130,10 +2141,7 @@ static void mini_cm_recv_pkt(struct nes_cm_core *cm_core,
2130 */ 2141 */
2131static struct nes_cm_core *nes_cm_alloc_core(void) 2142static struct nes_cm_core *nes_cm_alloc_core(void)
2132{ 2143{
2133 int i;
2134
2135 struct nes_cm_core *cm_core; 2144 struct nes_cm_core *cm_core;
2136 struct sk_buff *skb = NULL;
2137 2145
2138 /* setup the CM core */ 2146 /* setup the CM core */
2139 /* alloc top level core control structure */ 2147 /* alloc top level core control structure */
@@ -2151,19 +2159,6 @@ static struct nes_cm_core *nes_cm_alloc_core(void)
2151 2159
2152 atomic_set(&cm_core->events_posted, 0); 2160 atomic_set(&cm_core->events_posted, 0);
2153 2161
2154 /* init the packet lists */
2155 skb_queue_head_init(&cm_core->tx_free_list);
2156
2157 for (i = 0; i < NES_CM_DEFAULT_FRAME_CNT; i++) {
2158 skb = dev_alloc_skb(cm_core->mtu);
2159 if (!skb) {
2160 kfree(cm_core);
2161 return NULL;
2162 }
2163 /* add 'raw' skb to free frame list */
2164 skb_queue_head(&cm_core->tx_free_list, skb);
2165 }
2166
2167 cm_core->api = &nes_cm_api; 2162 cm_core->api = &nes_cm_api;
2168 2163
2169 spin_lock_init(&cm_core->ht_lock); 2164 spin_lock_init(&cm_core->ht_lock);
@@ -2392,7 +2387,6 @@ static int nes_cm_disconn_true(struct nes_qp *nesqp)
2392 atomic_inc(&cm_disconnects); 2387 atomic_inc(&cm_disconnects);
2393 cm_event.event = IW_CM_EVENT_DISCONNECT; 2388 cm_event.event = IW_CM_EVENT_DISCONNECT;
2394 if (last_ae == NES_AEQE_AEID_LLP_CONNECTION_RESET) { 2389 if (last_ae == NES_AEQE_AEID_LLP_CONNECTION_RESET) {
2395 issued_disconnect_reset = 1;
2396 cm_event.status = IW_CM_EVENT_STATUS_RESET; 2390 cm_event.status = IW_CM_EVENT_STATUS_RESET;
2397 nes_debug(NES_DBG_CM, "Generating a CM " 2391 nes_debug(NES_DBG_CM, "Generating a CM "
2398 "Disconnect Event (status reset) for " 2392 "Disconnect Event (status reset) for "
@@ -2542,6 +2536,7 @@ int nes_accept(struct iw_cm_id *cm_id, struct iw_cm_conn_param *conn_param)
2542 struct nes_v4_quad nes_quad; 2536 struct nes_v4_quad nes_quad;
2543 u32 crc_value; 2537 u32 crc_value;
2544 int ret; 2538 int ret;
2539 int passive_state;
2545 2540
2546 ibqp = nes_get_qp(cm_id->device, conn_param->qpn); 2541 ibqp = nes_get_qp(cm_id->device, conn_param->qpn);
2547 if (!ibqp) 2542 if (!ibqp)
@@ -2709,8 +2704,6 @@ int nes_accept(struct iw_cm_id *cm_id, struct iw_cm_conn_param *conn_param)
2709 conn_param->private_data_len + 2704 conn_param->private_data_len +
2710 sizeof(struct ietf_mpa_frame)); 2705 sizeof(struct ietf_mpa_frame));
2711 2706
2712 attr.qp_state = IB_QPS_RTS;
2713 nes_modify_qp(&nesqp->ibqp, &attr, IB_QP_STATE, NULL);
2714 2707
2715 /* notify OF layer that accept event was successfull */ 2708 /* notify OF layer that accept event was successfull */
2716 cm_id->add_ref(cm_id); 2709 cm_id->add_ref(cm_id);
@@ -2723,6 +2716,8 @@ int nes_accept(struct iw_cm_id *cm_id, struct iw_cm_conn_param *conn_param)
2723 cm_event.private_data = NULL; 2716 cm_event.private_data = NULL;
2724 cm_event.private_data_len = 0; 2717 cm_event.private_data_len = 0;
2725 ret = cm_id->event_handler(cm_id, &cm_event); 2718 ret = cm_id->event_handler(cm_id, &cm_event);
2719 attr.qp_state = IB_QPS_RTS;
2720 nes_modify_qp(&nesqp->ibqp, &attr, IB_QP_STATE, NULL);
2726 if (cm_node->loopbackpartner) { 2721 if (cm_node->loopbackpartner) {
2727 cm_node->loopbackpartner->mpa_frame_size = 2722 cm_node->loopbackpartner->mpa_frame_size =
2728 nesqp->private_data_len; 2723 nesqp->private_data_len;
@@ -2735,6 +2730,9 @@ int nes_accept(struct iw_cm_id *cm_id, struct iw_cm_conn_param *conn_param)
2735 printk(KERN_ERR "%s[%u] OFA CM event_handler returned, " 2730 printk(KERN_ERR "%s[%u] OFA CM event_handler returned, "
2736 "ret=%d\n", __func__, __LINE__, ret); 2731 "ret=%d\n", __func__, __LINE__, ret);
2737 2732
2733 passive_state = atomic_add_return(1, &cm_node->passive_state);
2734 if (passive_state == NES_SEND_RESET_EVENT)
2735 create_event(cm_node, NES_CM_EVENT_RESET);
2738 return 0; 2736 return 0;
2739} 2737}
2740 2738
@@ -2938,15 +2936,16 @@ int nes_destroy_listen(struct iw_cm_id *cm_id)
2938 */ 2936 */
2939int nes_cm_recv(struct sk_buff *skb, struct net_device *netdevice) 2937int nes_cm_recv(struct sk_buff *skb, struct net_device *netdevice)
2940{ 2938{
2939 int rc = 0;
2941 cm_packets_received++; 2940 cm_packets_received++;
2942 if ((g_cm_core) && (g_cm_core->api)) { 2941 if ((g_cm_core) && (g_cm_core->api)) {
2943 g_cm_core->api->recv_pkt(g_cm_core, netdev_priv(netdevice), skb); 2942 rc = g_cm_core->api->recv_pkt(g_cm_core, netdev_priv(netdevice), skb);
2944 } else { 2943 } else {
2945 nes_debug(NES_DBG_CM, "Unable to process packet for CM," 2944 nes_debug(NES_DBG_CM, "Unable to process packet for CM,"
2946 " cm is not setup properly.\n"); 2945 " cm is not setup properly.\n");
2947 } 2946 }
2948 2947
2949 return 0; 2948 return rc;
2950} 2949}
2951 2950
2952 2951
@@ -3217,6 +3216,18 @@ static void cm_event_reset(struct nes_cm_event *event)
3217 cm_event.private_data_len = 0; 3216 cm_event.private_data_len = 0;
3218 3217
3219 ret = cm_id->event_handler(cm_id, &cm_event); 3218 ret = cm_id->event_handler(cm_id, &cm_event);
3219 cm_id->add_ref(cm_id);
3220 atomic_inc(&cm_closes);
3221 cm_event.event = IW_CM_EVENT_CLOSE;
3222 cm_event.status = IW_CM_EVENT_STATUS_OK;
3223 cm_event.provider_data = cm_id->provider_data;
3224 cm_event.local_addr = cm_id->local_addr;
3225 cm_event.remote_addr = cm_id->remote_addr;
3226 cm_event.private_data = NULL;
3227 cm_event.private_data_len = 0;
3228 nes_debug(NES_DBG_CM, "NODE %p Generating CLOSE\n", event->cm_node);
3229 ret = cm_id->event_handler(cm_id, &cm_event);
3230
3220 nes_debug(NES_DBG_CM, "OFA CM event_handler returned, ret=%d\n", ret); 3231 nes_debug(NES_DBG_CM, "OFA CM event_handler returned, ret=%d\n", ret);
3221 3232
3222 3233