]> www.infradead.org Git - users/jedix/linux-maple.git/commitdiff
RDS: message filtering based on UUID
authorBang Nguyen <bang.nguyen@oracle.com>
Wed, 3 Feb 2016 16:13:25 +0000 (08:13 -0800)
committerSantosh Shilimkar <santosh.shilimkar@oracle.com>
Tue, 31 May 2016 16:03:34 +0000 (09:03 -0700)
Egress message is filtered based on UUID and for ingress, the
unique UUID is CMS'ed to application to take further action.

SYSCTL 'uuid_tx_no_drop' to override UUID based packet filtering

Orabug: 23222944

Signed-off-by: Bang Nguyen <bang.nguyen@oracle.com>
Signed-off-by: Yuval Shaia <yuval.shaia@oracle.com>
Signed-off-by: Santosh Shilimkar <santosh.shilimkar@oracle.com>
net/rds/rds.h
net/rds/recv.c
net/rds/send.c
net/rds/sysctl.c

index 5499e15aaf3cacdc67b1daa98839c0f4a5e2678f..dfc1781d7457ad53a63022ce7a45265ae586d861 100644 (file)
@@ -1035,6 +1035,7 @@ extern unsigned long rds_sysctl_trace_flags;
 extern unsigned int  rds_sysctl_trace_level;
 extern unsigned int  rds_sysctl_shutdown_trace_start_time;
 extern unsigned int  rds_sysctl_shutdown_trace_end_time;
+extern unsigned int rds_sysctl_uuid_tx_no_drop;
 
 /* threads.c */
 int rds_threads_init(void);
index 90b665be6d4a188c837c765b8994f41bc684959d..0fc42f3119db73329ace4683c52ad593a9a256c3 100644 (file)
@@ -875,6 +875,11 @@ int rds_recvmsg(struct socket *sock, struct msghdr *msg, size_t size,
                        goto out;
                }
 
+               if (rds_cmsg_uuid(rs, inc, msg)) {
+                       ret = -EFAULT;
+                       goto out;
+               }
+
                rds_stats_inc(s_recv_delivered);
 
                sin = (struct sockaddr_in *)msg->msg_name;
index 5bc6400ae3687ef4d43384320405b95fb5612185..268dd727aa870c437052e35e22797cb23f6c13f6 100644 (file)
@@ -167,6 +167,27 @@ static void release_in_xmit(struct rds_connection *conn)
                wake_up_all(&conn->c_waitq);
 }
 
+static int rds_match_uuid(struct rds_connection *conn, struct rds_message *rm)
+{
+       int ret = 0;
+
+       if (!conn->c_acl_en || !rm->uuid.enable) {
+               rdsdebug("uuid is not enabled acl_en=%d uuid_en=%d val=%s\n",
+                        conn->c_acl_en, rm->uuid.enable, rm->uuid.value);
+               return 0;
+       }
+
+       ret = memcmp(conn->c_uuid, rm->uuid.value, sizeof(conn->c_uuid));
+
+       if (!ret && rm->m_rs)
+               rm->m_rs->rs_uuid_sent_cnt++;
+
+       if (ret && rds_sysctl_uuid_tx_no_drop)
+               return 0;
+
+       return ret;
+}
+
 /*
  * We're making the concious trade-off here to only send one message
  * down the connection at a time.
@@ -265,6 +286,12 @@ restart:
                        }
                        rm->data.op_active = 1;
 
+                       if (conn->c_acl_en) {
+                               memcpy(rm->uuid.value, conn->c_uuid,
+                                      RDS_UUID_MAXLEN);
+                               rm->uuid.enable = 1;
+                       }
+
                        conn->c_xmit_rm = rm;
                }
 
@@ -322,9 +349,11 @@ restart:
                                        &rm->m_flags))) {
                                spin_lock_irqsave(&conn->c_lock, flags);
                                if (test_and_clear_bit(RDS_MSG_ON_CONN,
-                                       &rm->m_flags))
+                                       &rm->m_flags)) {
+                                       rm->m_status = RDS_RDMA_SEND_DROPPED;
                                        list_move_tail(&rm->m_conn_item,
                                                &to_be_dropped);
+                               }
                                spin_unlock_irqrestore(&conn->c_lock, flags);
                                continue;
                        }
@@ -346,6 +375,20 @@ restart:
                        conn->c_xmit_rm = rm;
                }
 
+               /* If fail uuid match, drop the message */
+               if (rds_match_uuid(conn, rm)) {
+                       spin_lock_irqsave(&conn->c_lock, flags);
+                       if (test_and_clear_bit(RDS_MSG_ON_CONN, &rm->m_flags)) {
+                               rm->m_status = RDS_RDMA_SEND_ACCVIO;
+                               list_move_tail(&rm->m_conn_item,
+                                              &to_be_dropped);
+                       }
+                       spin_unlock_irqrestore(&conn->c_lock, flags);
+                       conn->c_xmit_rm = 0;
+                       rm->m_rs->rs_uuid_drop_cnt++;
+                       continue;
+               }
+
                /* The transport either sends the whole rdma or none of it */
                if (rm->rdma.op_active && !conn->c_xmit_rdma_sent) {
                        rm->m_final_op = &rm->rdma;
@@ -468,7 +511,7 @@ over_batch:
                        rds_message_unmapped(rm);
                        rds_message_put(rm);
                }
-               rds_send_remove_from_sock(&to_be_dropped, RDS_RDMA_SEND_DROPPED);
+               rds_send_remove_from_sock(&to_be_dropped, rm->m_status);
        }
 
        /*
@@ -1065,6 +1108,11 @@ static int rds_rm_size(struct msghdr *msg, int data_len)
                        size += sizeof(struct scatterlist);
                        break;
 
+               case RDS_CMSG_UUID:
+                       cmsg_groups |= 1;
+                       size += sizeof(struct scatterlist);
+                       break;
+
                default:
                        return -EINVAL;
                }
@@ -1104,6 +1152,17 @@ static int rds_cmsg_asend(struct rds_sock *rs, struct rds_message *rm,
        return 0;
 }
 
+static int rds_cmsg_uuid(struct rds_sock *rs, struct rds_message *rm,
+                        struct cmsghdr *cmsg)
+{
+       struct rds_uuid_args *args = CMSG_DATA(cmsg);
+
+       /* Copy uuid to rm */
+       memcpy(rm->uuid.value, args->uuid, RDS_UUID_MAXLEN);
+
+       return 0;
+}
+
 static int rds_cmsg_send(struct rds_sock *rs, struct rds_message *rm,
                         struct msghdr *msg, int *allocated_mr)
 {
@@ -1148,6 +1207,10 @@ static int rds_cmsg_send(struct rds_sock *rs, struct rds_message *rm,
                        ret = rds_cmsg_asend(rs, rm, cmsg);
                        break;
 
+               case RDS_CMSG_UUID:
+                       ret = rds_cmsg_uuid(rs, rm, cmsg);
+                       break;
+
                default:
                        return -EINVAL;
                }
@@ -1248,6 +1311,7 @@ int rds_sendmsg(struct socket *sock, struct msghdr *msg, size_t payload_len)
        rm->data.op_active = 1;
 
        rm->m_daddr = daddr;
+       rm->uuid.enable = rs->rs_uuid_en;
 
        /* For RDMA operation(s), add up rmda bytes to payload to make
         * sure its within system QoS threshold limits.
@@ -1317,6 +1381,11 @@ int rds_sendmsg(struct socket *sock, struct msghdr *msg, size_t payload_len)
                goto out;
        }
 
+       if (conn->c_acl_init && rds_match_uuid(conn, rm)) {
+               ret = -EFAULT;
+               goto out;
+       }
+
        /* Not accepting new sends until all the failed ops have been reaped */
        if (rds_async_send_enabled && conn->c_pending_flush) {
                ret = -EAGAIN;
@@ -1584,6 +1653,11 @@ rds_send_pong(struct rds_connection *conn, __be16 dport)
        conn->c_next_tx_seq++;
        spin_unlock_irqrestore(&conn->c_lock, flags);
 
+       if (conn->c_acl_en) {
+               memcpy(rm->uuid.value, conn->c_uuid, RDS_UUID_MAXLEN);
+               rm->uuid.enable = 1;
+       }
+
        rds_stats_inc(s_send_queued);
        rds_stats_inc(s_send_pong);
 
@@ -1635,6 +1709,11 @@ rds_send_hb(struct rds_connection *conn, int response)
        conn->c_next_tx_seq++;
        spin_unlock_irqrestore(&conn->c_lock, flags);
 
+       if (conn->c_acl_en) {
+               memcpy(rm->uuid.value, conn->c_uuid, RDS_UUID_MAXLEN);
+               rm->uuid.enable = 1;
+       }
+
        ret = rds_send_xmit(conn);
        if (ret == -ENOMEM || ret == -EAGAIN)
                queue_delayed_work(rds_wq, &conn->c_send_w, 1);
index b22e8b8b6b89dd48ba5674b4acd5113b64292998..e26122c706a67b76a0c9d051ee47eb21a2326286 100644 (file)
@@ -52,6 +52,9 @@ unsigned int rds_sysctl_ping_enable = 1;
 unsigned int rds_sysctl_shutdown_trace_start_time;
 unsigned int rds_sysctl_shutdown_trace_end_time;
 
+/*  Do not drop packets on transmit */
+unsigned int rds_sysctl_uuid_tx_no_drop = 1;
+
 /*
  * We have official values, but must maintain the sysctl interface for existing
  * software that expects to find these values here.
@@ -127,6 +130,13 @@ static struct ctl_table rds_sysctl_rds_table[] = {
                .mode           = 0644,
                .proc_handler   = &proc_dointvec,
        },
+       {
+               .procname       = "uuid_tx_no_drop",
+               .data           = &rds_sysctl_uuid_tx_no_drop,
+               .maxlen         = sizeof(int),
+               .mode           = 0644,
+               .proc_handler   = &proc_dointvec,
+       },
        { }
 };