Merge branch 'sii-m15w' into upstream
[pandora-kernel.git] / net / sctp / sm_make_chunk.c
index 556c495..4f11f58 100644 (file)
@@ -1275,7 +1275,12 @@ static sctp_cookie_param_t *sctp_pack_cookie(const struct sctp_endpoint *ep,
        unsigned int keylen;
        char *key;
 
-       headersize = sizeof(sctp_paramhdr_t) + SCTP_SECRET_SIZE;
+       /* Header size is static data prior to the actual cookie, including
+        * any padding.
+        */
+       headersize = sizeof(sctp_paramhdr_t) + 
+                    (sizeof(struct sctp_signed_cookie) - 
+                     sizeof(struct sctp_cookie));
        bodysize = sizeof(struct sctp_cookie)
                + ntohs(init_chunk->chunk_hdr->length) + addrs_len;
 
@@ -1354,7 +1359,7 @@ struct sctp_association *sctp_unpack_cookie(
        struct sctp_signed_cookie *cookie;
        struct sctp_cookie *bear_cookie;
        int headersize, bodysize, fixed_size;
-       __u8 digest[SCTP_SIGNATURE_SIZE];
+       __u8 *digest = ep->digest;
        struct scatterlist sg;
        unsigned int keylen, len;
        char *key;
@@ -1362,7 +1367,12 @@ struct sctp_association *sctp_unpack_cookie(
        struct sk_buff *skb = chunk->skb;
        struct timeval tv;
 
-       headersize = sizeof(sctp_chunkhdr_t) + SCTP_SECRET_SIZE;
+       /* Header size is static data prior to the actual cookie, including
+        * any padding.
+        */
+       headersize = sizeof(sctp_chunkhdr_t) +
+                    (sizeof(struct sctp_signed_cookie) - 
+                     sizeof(struct sctp_cookie));
        bodysize = ntohs(chunk->chunk_hdr->length) - headersize;
        fixed_size = headersize + sizeof(struct sctp_cookie);
 
@@ -1392,14 +1402,14 @@ struct sctp_association *sctp_unpack_cookie(
        sg.length = bodysize;
        key = (char *)ep->secret_key[ep->current_key];
 
-       memset(digest, 0x00, sizeof(digest));
+       memset(digest, 0x00, SCTP_SIGNATURE_SIZE);
        sctp_crypto_hmac(sctp_sk(ep->base.sk)->hmac, key, &keylen, &sg,
                         1, digest);
 
        if (memcmp(digest, cookie->signature, SCTP_SIGNATURE_SIZE)) {
                /* Try the previous key. */
                key = (char *)ep->secret_key[ep->last_key];
-               memset(digest, 0x00, sizeof(digest));
+               memset(digest, 0x00, SCTP_SIGNATURE_SIZE);
                sctp_crypto_hmac(sctp_sk(ep->base.sk)->hmac, key, &keylen,
                                 &sg, 1, digest);
 
@@ -1483,7 +1493,7 @@ no_hmac:
 
        /* Also, add the destination address. */
        if (list_empty(&retval->base.bind_addr.address_list)) {
-               sctp_add_bind_addr(&retval->base.bind_addr, &chunk->dest,
+               sctp_add_bind_addr(&retval->base.bind_addr, &chunk->dest, 1,
                                   GFP_ATOMIC);
        }
 
@@ -2007,7 +2017,7 @@ static int sctp_process_param(struct sctp_association *asoc,
                af->from_addr_param(&addr, param.addr, asoc->peer.port, 0);
                scope = sctp_scope(peer_addr);
                if (sctp_in_scope(&addr, scope))
-                       if (!sctp_assoc_add_peer(asoc, &addr, gfp, SCTP_ACTIVE))
+                       if (!sctp_assoc_add_peer(asoc, &addr, gfp, SCTP_UNCONFIRMED))
                                return 0;
                break;
 
@@ -2408,7 +2418,7 @@ static __u16 sctp_process_asconf_param(struct sctp_association *asoc,
                 * Due to Resource Shortage'.
                 */
 
-               peer = sctp_assoc_add_peer(asoc, &addr, GFP_ATOMIC, SCTP_ACTIVE);
+               peer = sctp_assoc_add_peer(asoc, &addr, GFP_ATOMIC, SCTP_UNCONFIRMED);
                if (!peer)
                        return SCTP_ERROR_RSRC_LOW;
 
@@ -2555,6 +2565,7 @@ static int sctp_asconf_param_success(struct sctp_association *asoc,
        union sctp_addr_param *addr_param;
        struct list_head *pos;
        struct sctp_transport *transport;
+       struct sctp_sockaddr_entry *saddr;
        int retval = 0;
 
        addr_param = (union sctp_addr_param *)
@@ -2568,7 +2579,11 @@ static int sctp_asconf_param_success(struct sctp_association *asoc,
        case SCTP_PARAM_ADD_IP:
                sctp_local_bh_disable();
                sctp_write_lock(&asoc->base.addr_lock);
-               retval = sctp_add_bind_addr(bp, &addr, GFP_ATOMIC);
+               list_for_each(pos, &bp->address_list) {
+                       saddr = list_entry(pos, struct sctp_sockaddr_entry, list);
+                       if (sctp_cmp_addr_exact(&saddr->a, &addr))
+                               saddr->use_as_src = 1;
+               }
                sctp_write_unlock(&asoc->base.addr_lock);
                sctp_local_bh_enable();
                break;
@@ -2581,6 +2596,7 @@ static int sctp_asconf_param_success(struct sctp_association *asoc,
                list_for_each(pos, &asoc->peer.transport_addr_list) {
                        transport = list_entry(pos, struct sctp_transport,
                                                 transports);
+                       dst_release(transport->dst);
                        sctp_transport_route(transport, NULL,
                                             sctp_sk(asoc->base.sk));
                }