Applied.
Committed revision 3211.

> Quoting Michael S. Tsirkin <[EMAIL PROTECTED]>:
> Subject: [PATCH] sdp: split sdp_inet_send to subroutines
> 
> The following is not yet applied. Opinions on othis?
> 
> ---
> 
> Split the sdp_inet_send to smaller subroutines.
> 
> Signed-off-by: Michael S. Tsirkin <[EMAIL PROTECTED]>

Index: linux-2.6.12.2/drivers/infiniband/ulp/sdp/sdp_send.c
===================================================================
--- linux-2.6.12.2.orig/drivers/infiniband/ulp/sdp/sdp_send.c
+++ linux-2.6.12.2/drivers/infiniband/ulp/sdp/sdp_send.c
@@ -1907,6 +1907,136 @@ done:
        return result;
 }
 
+static inline int sdp_send_while_space(struct sock *sk, struct sdp_sock *conn,
+                                      struct msghdr *msg, int oob,
+                                      size_t size, size_t *copied)
+{
+       struct sdpc_buff *buff;
+       int result = 0;
+       int copy;
+       /*
+        * send while there is room... (thresholds should be
+        * observed...) use a different threshold for urgent
+        * data to allow some space for sending.
+        */
+       while (sdp_inet_write_space(conn, oob) > 0) {
+               buff = sdp_send_data_buff_get(conn);
+               if (!buff) {
+                       result = -ENOMEM;
+                       goto done;
+               }
+
+               copy = min((size_t)(buff->end - buff->tail), size - *copied);
+               copy = min(copy, sdp_inet_write_space(conn, oob));
+
+#ifndef _SDP_DATA_PATH_NULL
+               result = memcpy_fromiovec(buff->tail, msg->msg_iov, copy);
+               if (result < 0) {
+                       sdp_buff_pool_put(buff);
+                       goto done;
+               }
+#endif
+               buff->tail += copy;
+               *copied += copy;
+
+               SDP_CONN_STAT_SEND_INC(conn, copy);
+
+               result = sdp_send_data_buff_put(conn, buff, copy,
+                                               (*copied == size ? oob : 0));
+               if (result < 0)
+                       goto done;
+
+               if (*copied == size)
+                       goto done;
+       }
+       /*
+        * set no space bits since this code path is taken
+        * when there is no write space.
+        */
+       set_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
+       set_bit(SOCK_NOSPACE, &sk->sk_socket->flags);
+
+done:
+       return result;
+}
+
+/* Returns new timeout value */
+static inline long sdp_wait_till_space(struct sock *sk, struct sdp_sock *conn,
+                                      int oob, long timeout)
+{
+       DECLARE_WAITQUEUE(wait, current);
+
+       add_wait_queue(sk->sk_sleep, &wait);
+       set_current_state(TASK_INTERRUPTIBLE);
+       /*
+        * ASYNC_NOSPACE is only set if we're not sleeping,
+        * while NOSPACE is set whenever there is no space,
+        * and is only cleared once space opens up, in
+        * DevConnAck()
+        */
+       clear_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
+
+       sdp_conn_unlock(conn);
+       if (sdp_inet_write_space(conn, oob) <= 0)
+               timeout = schedule_timeout(timeout);
+       sdp_conn_lock(conn);
+
+       remove_wait_queue(sk->sk_sleep, &wait);
+       set_current_state(TASK_RUNNING);
+       return timeout;
+}
+
+static inline int sdp_queue_iocb(struct kiocb *req, struct sdp_sock *conn,
+                                struct msghdr *msg, size_t size,
+                                size_t *copied)
+{
+       struct sdpc_iocb *iocb;
+       int result;
+       /*
+        * create IOCB with remaining space
+        */
+       iocb = sdp_iocb_create();
+       if (!iocb) {
+               sdp_dbg_warn(conn, "Failed to allocate IOCB <%Zu:%ld>",
+                            size, (long)*copied);
+               return -ENOMEM;
+       }
+
+       iocb->len  = size - *copied;
+       iocb->post = *copied;
+       iocb->size = size;
+       iocb->req  = req;
+       iocb->key  = req->ki_key;
+       iocb->addr = (unsigned long)msg->msg_iov->iov_base - *copied;
+
+       req->ki_cancel = sdp_inet_write_cancel;
+
+       result = sdp_iocb_lock(iocb);
+       if (result < 0) {
+               sdp_dbg_warn(conn, "Error <%d> locking IOCB <%Zu:%ld>",
+                            result, size, (long)copied);
+
+               sdp_iocb_destroy(iocb);
+               return result;
+       }
+
+       SDP_CONN_STAT_WQ_INC(conn, iocb->size);
+
+       conn->send_pipe += iocb->len;
+
+       result = sdp_send_data_queue(conn, (struct sdpc_desc *)iocb);
+       if (result < 0) {
+               sdp_dbg_warn(conn, "Error <%d> queueing write IOCB",
+                            result);
+
+               sdp_iocb_destroy(iocb);
+               return result;
+       }
+
+       *copied = 0; /* copied amount was saved in IOCB. */
+       return -EIOCBQUEUED;
+}
+
 /*
  * sdp_inet_send - send data from user space to the network
  */
@@ -1915,12 +2045,9 @@ int sdp_inet_send(struct kiocb *req, str
 {
        struct sock      *sk;
        struct sdp_sock   *conn;
-       struct sdpc_buff *buff;
-       struct sdpc_iocb *iocb;
        int result = 0;
-       int copied = 0;
-       int copy;
-       int oob;
+       size_t copied = 0;
+       int oob, zcopy;
        long timeout = -1;
 
        /*
@@ -1954,75 +2081,35 @@ int sdp_inet_send(struct kiocb *req, str
         * they are smaller then the zopy threshold, but only if there is
         * no buffer write space.
         */
-       if (!(conn->src_zthresh > size) && !is_sync_kiocb(req))
-               goto skip;
+       zcopy = (size >= conn->src_zthresh && !is_sync_kiocb(req));
+
        /*
         * clear ASYN space bit, it'll be reset if there is no space.
         */
-       clear_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
+       if (!zcopy)
+               clear_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
        /*
         * process data first if window is open, next check conditions, then
         * wait if there is more work to be done. The absolute window size is
         * used to 'block' the caller if the connection is still connecting.
         */
        while (!result && copied < size) {
-               /*
-                * send while there is room... (thresholds should be
-                * observed...) use a different threshold for urgent
-                * data to allow some space for sending.
-                */
-               while (sdp_inet_write_space(conn, oob) > 0) {
-                       buff = sdp_send_data_buff_get(conn);
-                       if (!buff) {
-                               result = -ENOMEM;
-                               goto done;
-                       }
-
-                       copy = min((size_t)(buff->end - buff->tail),
-                                  (size_t)(size - copied));
-                       copy = min(copy, sdp_inet_write_space(conn, oob));
-
-#ifndef _SDP_DATA_PATH_NULL
-                       result = memcpy_fromiovec(buff->tail,
-                                                 msg->msg_iov,
-                                                 copy);
-                       if (result < 0) {
-                               sdp_buff_pool_put(buff);
-                               goto done;
-                       }
-#endif
-                       buff->tail += copy;
-                       copied += copy;
-
-                       SDP_CONN_STAT_SEND_INC(conn, copy);
-
-                       result = sdp_send_data_buff_put(conn, buff, copy,
-                                                       ((copied ==
-                                                       size) ? oob : 0));
-                       if (result < 0)
-                               goto done;
-
-                       if (copied == size)
-                               goto done;
+               if (!zcopy) {
+                       result = sdp_send_while_space(sk, conn, msg, oob, size,
+                                                     &copied);
+                       if (result < 0 || copied == size)
+                               break;
                }
-               /*
-                * set no space bits since this code path is taken
-                * when there is no write space.
-                */
-               set_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
-               set_bit(SOCK_NOSPACE, &sk->sk_socket->flags);
-               /*
-                * check status.
-                */
-skip: /* entry point for IOCB based transfers. Before processing IOCB,
-         check that the connection is OK, otherwise return error
-         synchronously. */
+
+               /* entry point for IOCB based transfers. Before processing IOCB,
+                  check that the connection is OK, otherwise return error
+                  synchronously. */
                /*
                 * onetime setup of timeout, but only if it's needed.
                 */
                if (timeout < 0)
                        timeout = sock_sndtimeo(sk,
-                                               MSG_DONTWAIT & msg->msg_flags);
+                                               msg->msg_flags & MSG_DONTWAIT);
 
                if (sk->sk_err) {
                        result = (copied > 0) ? 0 : sock_error(sk);
@@ -2051,77 +2138,14 @@ skip: /* entry point for IOCB based tran
                        break;
                }
                /*
-                * Either wait or create and queue an IOCB for defered
+                * Either wait or create and queue an IOCB for deferred
                 * completion. Wait on sync IO call create IOCB for async
                 * call.
                 */
-               if (is_sync_kiocb(req)) {
-                       DECLARE_WAITQUEUE(wait, current);
-
-                       add_wait_queue(sk->sk_sleep, &wait);
-                       set_current_state(TASK_INTERRUPTIBLE);
-                       /*
-                        * ASYNC_NOSPACE is only set if we're not sleeping,
-                        * while NOSPACE is set whenever there is no space,
-                        * and is only cleared once space opens up, in
-                        * DevConnAck()
-                        */
-                       clear_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
-
-                       sdp_conn_unlock(conn);
-                       if (sdp_inet_write_space(conn, oob) <= 0)
-                               timeout = schedule_timeout(timeout);
-                       sdp_conn_lock(conn);
-
-                       remove_wait_queue(sk->sk_sleep, &wait);
-                       set_current_state(TASK_RUNNING);
-
-                       continue;
-               }
-               /*
-                * create IOCB with remaining space
-                */
-               iocb = sdp_iocb_create();
-               if (!iocb) {
-                       sdp_dbg_warn(conn, "Failed to allocate IOCB <%Zu:%d>",
-                                    size, copied);
-                       result = -ENOMEM;
-                       break;
-               }
-
-               iocb->len  = size - copied;
-               iocb->post = copied;
-               iocb->size = size;
-               iocb->req  = req;
-               iocb->key  = req->ki_key;
-               iocb->addr = (unsigned long)msg->msg_iov->iov_base - copied;
-
-               req->ki_cancel = sdp_inet_write_cancel;
-
-               result = sdp_iocb_lock(iocb);
-               if (result < 0) {
-                       sdp_dbg_warn(conn, "Error <%d> locking IOCB <%Zu:%d>",
-                                    result, size, copied);
-
-                       sdp_iocb_destroy(iocb);
-                       break;
-               }
-
-               SDP_CONN_STAT_WQ_INC(conn, iocb->size);
-
-               conn->send_pipe += iocb->len;
-
-               result = sdp_send_data_queue(conn, (struct sdpc_desc *)iocb);
-               if (result < 0) {
-                       sdp_dbg_warn(conn, "Error <%d> queueing write IOCB",
-                                    result);
-
-                       sdp_iocb_destroy(iocb);
-                       break;
-               }
-
-               copied = 0; /* copied amount was saved in IOCB. */
-               result = -EIOCBQUEUED;
+               if (is_sync_kiocb(req))
+                       timeout = sdp_wait_till_space(sk, conn, oob, timeout);
+               else
+                       result = sdp_queue_iocb(req, conn, msg, size, &copied);
        }
 
 done:

-- 
MST
_______________________________________________
openib-general mailing list
[email protected]
http://openib.org/mailman/listinfo/openib-general

To unsubscribe, please visit http://openib.org/mailman/listinfo/openib-general

-- 
MST
_______________________________________________
openib-general mailing list
[email protected]
http://openib.org/mailman/listinfo/openib-general

To unsubscribe, please visit http://openib.org/mailman/listinfo/openib-general

Reply via email to