Gitweb:     
http://git.kernel.org/git/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=123ed979eaa8de0dd2422862d247469eda0bd645
Commit:     123ed979eaa8de0dd2422862d247469eda0bd645
Parent:     027f6e1ad32de32f9fe1c61d0f744e329e8acfd9
Author:     Vlad Yasevich <[EMAIL PROTECTED]>
AuthorDate: Fri Nov 9 11:41:36 2007 -0500
Committer:  Vlad Yasevich <[EMAIL PROTECTED]>
CommitDate: Fri Nov 9 11:41:36 2007 -0500

    SCTP: Use hashed lookup when looking for an association.
    
    A SCTP endpoint may have a lot of associations on them and walking
    the list is fairly inefficient.  Instead, use a hashed lookup,
    and filter out the hash list based on the endopoing we already have.
    
    Signed-off-by: Vlad Yasevich <[EMAIL PROTECTED]>
---
 net/sctp/endpointola.c |   34 ++++++++++++++++++++++------------
 1 files changed, 22 insertions(+), 12 deletions(-)

diff --git a/net/sctp/endpointola.c b/net/sctp/endpointola.c
index 2d2d81e..68f0556 100644
--- a/net/sctp/endpointola.c
+++ b/net/sctp/endpointola.c
@@ -328,24 +328,34 @@ static struct sctp_association 
*__sctp_endpoint_lookup_assoc(
        const union sctp_addr *paddr,
        struct sctp_transport **transport)
 {
+       struct sctp_association *asoc = NULL;
+       struct sctp_transport *t = NULL;
+       struct sctp_hashbucket *head;
+       struct sctp_ep_common *epb;
+       int hash;
        int rport;
-       struct sctp_association *asoc;
-       struct list_head *pos;
 
+       *transport = NULL;
        rport = ntohs(paddr->v4.sin_port);
 
-       list_for_each(pos, &ep->asocs) {
-               asoc = list_entry(pos, struct sctp_association, asocs);
-               if (rport == asoc->peer.port) {
-                       *transport = sctp_assoc_lookup_paddr(asoc, paddr);
-
-                       if (*transport)
-                               return asoc;
+       hash = sctp_assoc_hashfn(ep->base.bind_addr.port, rport);
+       head = &sctp_assoc_hashtable[hash];
+       read_lock(&head->lock);
+       for (epb = head->chain; epb; epb = epb->next) {
+               asoc = sctp_assoc(epb);
+               if (asoc->ep != ep || rport != asoc->peer.port)
+                       goto next;
+
+               t = sctp_assoc_lookup_paddr(asoc, paddr);
+               if (t) {
+                       *transport = t;
+                       break;
                }
+next:
+               asoc = NULL;
        }
-
-       *transport = NULL;
-       return NULL;
+       read_unlock(&head->lock);
+       return asoc;
 }
 
 /* Lookup association on an endpoint based on a peer address.  BH-safe.  */
-
To unsubscribe from this list: send the line "unsubscribe git-commits-head" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to