aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndy Grover <andy.grover@oracle.com>2010-01-13 18:50:09 -0500
committerAndy Grover <andy.grover@oracle.com>2010-09-08 21:11:48 -0400
commitf147dd9ecabf23fd63d2562ffe64252a0453ecde (patch)
tree1e3cdab2dc27b37ff2b820cd8081b33da95ab08c
parent9c030391e8741695ff6114703e4edccccb634479 (diff)
RDS/IB: Disallow connections less than RDS 3.1
RDS 3.0 connections (in OFED 1.3 and earlier) put the header at the end. 3.1 connections put it at the head. The code has significant added complexity in order to handle both configurations. In OFED 1.6 we can drop this and simplify the code by only supporting "header-first" configuration. This patch checks the protocol version, and if prior to 3.1, does not complete the connection. Signed-off-by: Andy Grover <andy.grover@oracle.com>
-rw-r--r--net/rds/ib_cm.c20
-rw-r--r--net/rds/ib_recv.c43
2 files changed, 16 insertions, 47 deletions
diff --git a/net/rds/ib_cm.c b/net/rds/ib_cm.c
index 3134336ca17d..8b0c743c0900 100644
--- a/net/rds/ib_cm.c
+++ b/net/rds/ib_cm.c
@@ -111,11 +111,21 @@ void rds_ib_cm_connect_complete(struct rds_connection *conn, struct rdma_cm_even
111 } 111 }
112 } 112 }
113 113
114 printk(KERN_NOTICE "RDS/IB: connected to %pI4 version %u.%u%s\n", 114 if (conn->c_version < RDS_PROTOCOL(3,1)) {
115 &conn->c_faddr, 115 printk(KERN_NOTICE "RDS/IB: Connection to %pI4 version %u.%u failed,"
116 RDS_PROTOCOL_MAJOR(conn->c_version), 116 " no longer supported\n",
117 RDS_PROTOCOL_MINOR(conn->c_version), 117 &conn->c_faddr,
118 ic->i_flowctl ? ", flow control" : ""); 118 RDS_PROTOCOL_MAJOR(conn->c_version),
119 RDS_PROTOCOL_MINOR(conn->c_version));
120 rds_conn_destroy(conn);
121 return;
122 } else {
123 printk(KERN_NOTICE "RDS/IB: connected to %pI4 version %u.%u%s\n",
124 &conn->c_faddr,
125 RDS_PROTOCOL_MAJOR(conn->c_version),
126 RDS_PROTOCOL_MINOR(conn->c_version),
127 ic->i_flowctl ? ", flow control" : "");
128 }
119 129
120 /* 130 /*
121 * Init rings and fill recv. this needs to wait until protocol negotiation 131 * Init rings and fill recv. this needs to wait until protocol negotiation
diff --git a/net/rds/ib_recv.c b/net/rds/ib_recv.c
index e294d00abc80..a68a3a721c6c 100644
--- a/net/rds/ib_recv.c
+++ b/net/rds/ib_recv.c
@@ -557,47 +557,6 @@ u64 rds_ib_piggyb_ack(struct rds_ib_connection *ic)
557 return rds_ib_get_ack(ic); 557 return rds_ib_get_ack(ic);
558} 558}
559 559
560static struct rds_header *rds_ib_get_header(struct rds_connection *conn,
561 struct rds_ib_recv_work *recv,
562 u32 data_len)
563{
564 struct rds_ib_connection *ic = conn->c_transport_data;
565 void *hdr_buff = &ic->i_recv_hdrs[recv - ic->i_recvs];
566 void *addr;
567 u32 misplaced_hdr_bytes;
568
569 /*
570 * Support header at the front (RDS 3.1+) as well as header-at-end.
571 *
572 * Cases:
573 * 1) header all in header buff (great!)
574 * 2) header all in data page (copy all to header buff)
575 * 3) header split across hdr buf + data page
576 * (move bit in hdr buff to end before copying other bit from data page)
577 */
578 if (conn->c_version > RDS_PROTOCOL_3_0 || data_len == RDS_FRAG_SIZE)
579 return hdr_buff;
580
581 if (data_len <= (RDS_FRAG_SIZE - sizeof(struct rds_header))) {
582 addr = kmap_atomic(recv->r_frag->f_page, KM_SOFTIRQ0);
583 memcpy(hdr_buff,
584 addr + recv->r_frag->f_offset + data_len,
585 sizeof(struct rds_header));
586 kunmap_atomic(addr, KM_SOFTIRQ0);
587 return hdr_buff;
588 }
589
590 misplaced_hdr_bytes = (sizeof(struct rds_header) - (RDS_FRAG_SIZE - data_len));
591
592 memmove(hdr_buff + misplaced_hdr_bytes, hdr_buff, misplaced_hdr_bytes);
593
594 addr = kmap_atomic(recv->r_frag->f_page, KM_SOFTIRQ0);
595 memcpy(hdr_buff, addr + recv->r_frag->f_offset + data_len,
596 sizeof(struct rds_header) - misplaced_hdr_bytes);
597 kunmap_atomic(addr, KM_SOFTIRQ0);
598 return hdr_buff;
599}
600
601/* 560/*
602 * It's kind of lame that we're copying from the posted receive pages into 561 * It's kind of lame that we're copying from the posted receive pages into
603 * long-lived bitmaps. We could have posted the bitmaps and rdma written into 562 * long-lived bitmaps. We could have posted the bitmaps and rdma written into
@@ -710,7 +669,7 @@ static void rds_ib_process_recv(struct rds_connection *conn,
710 } 669 }
711 data_len -= sizeof(struct rds_header); 670 data_len -= sizeof(struct rds_header);
712 671
713 ihdr = rds_ib_get_header(conn, recv, data_len); 672 ihdr = &ic->i_recv_hdrs[recv - ic->i_recvs];
714 673
715 /* Validate the checksum. */ 674 /* Validate the checksum. */
716 if (!rds_message_verify_checksum(ihdr)) { 675 if (!rds_message_verify_checksum(ihdr)) {