diff options
Diffstat (limited to 'net/sctp')
| -rw-r--r-- | net/sctp/Kconfig | 2 | ||||
| -rw-r--r-- | net/sctp/auth.c | 10 | ||||
| -rw-r--r-- | net/sctp/sm_make_chunk.c | 23 | ||||
| -rw-r--r-- | net/sctp/sm_sideeffect.c | 14 | ||||
| -rw-r--r-- | net/sctp/sm_statefuns.c | 9 | ||||
| -rw-r--r-- | net/sctp/ulpevent.c | 3 |
6 files changed, 30 insertions, 31 deletions
diff --git a/net/sctp/Kconfig b/net/sctp/Kconfig index 6e2eb1dd64ed..68934438ee19 100644 --- a/net/sctp/Kconfig +++ b/net/sctp/Kconfig @@ -31,7 +31,7 @@ menuconfig IP_SCTP homing at either or both ends of an association." To compile this protocol support as a module, choose M here: the - module will be called sctp. Debug messages are handeled by the + module will be called sctp. Debug messages are handled by the kernel's dynamic debugging framework. If in doubt, say N. diff --git a/net/sctp/auth.c b/net/sctp/auth.c index 4278764d82b8..83e97e8892e0 100644 --- a/net/sctp/auth.c +++ b/net/sctp/auth.c @@ -741,14 +741,8 @@ void sctp_auth_calculate_hmac(const struct sctp_association *asoc, if (crypto_shash_setkey(tfm, &asoc_key->data[0], asoc_key->len)) goto free; - { - SHASH_DESC_ON_STACK(desc, tfm); - - desc->tfm = tfm; - crypto_shash_digest(desc, (u8 *)auth, - end - (unsigned char *)auth, digest); - shash_desc_zero(desc); - } + crypto_shash_tfm_digest(tfm, (u8 *)auth, end - (unsigned char *)auth, + digest); free: if (free_key) diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c index f7cb0b7faec2..47910470e532 100644 --- a/net/sctp/sm_make_chunk.c +++ b/net/sctp/sm_make_chunk.c @@ -1670,17 +1670,14 @@ static struct sctp_cookie_param *sctp_pack_cookie( ntohs(init_chunk->chunk_hdr->length), raw_addrs, addrs_len); if (sctp_sk(ep->base.sk)->hmac) { - SHASH_DESC_ON_STACK(desc, sctp_sk(ep->base.sk)->hmac); + struct crypto_shash *tfm = sctp_sk(ep->base.sk)->hmac; int err; /* Sign the message. */ - desc->tfm = sctp_sk(ep->base.sk)->hmac; - - err = crypto_shash_setkey(desc->tfm, ep->secret_key, + err = crypto_shash_setkey(tfm, ep->secret_key, sizeof(ep->secret_key)) ?: - crypto_shash_digest(desc, (u8 *)&cookie->c, bodysize, - cookie->signature); - shash_desc_zero(desc); + crypto_shash_tfm_digest(tfm, (u8 *)&cookie->c, bodysize, + cookie->signature); if (err) goto free_cookie; } @@ -1741,17 +1738,13 @@ struct sctp_association *sctp_unpack_cookie( /* Check the signature. */ { - SHASH_DESC_ON_STACK(desc, sctp_sk(ep->base.sk)->hmac); + struct crypto_shash *tfm = sctp_sk(ep->base.sk)->hmac; int err; - desc->tfm = sctp_sk(ep->base.sk)->hmac; - - err = crypto_shash_setkey(desc->tfm, ep->secret_key, + err = crypto_shash_setkey(tfm, ep->secret_key, sizeof(ep->secret_key)) ?: - crypto_shash_digest(desc, (u8 *)bear_cookie, bodysize, - digest); - shash_desc_zero(desc); - + crypto_shash_tfm_digest(tfm, (u8 *)bear_cookie, bodysize, + digest); if (err) { *error = -SCTP_IERROR_NOMEM; goto fail; diff --git a/net/sctp/sm_sideeffect.c b/net/sctp/sm_sideeffect.c index 2bc29463e1dc..9f36fe911d08 100644 --- a/net/sctp/sm_sideeffect.c +++ b/net/sctp/sm_sideeffect.c @@ -1523,9 +1523,17 @@ static int sctp_cmd_interpreter(enum sctp_event_type event_type, timeout = asoc->timeouts[cmd->obj.to]; BUG_ON(!timeout); - timer->expires = jiffies + timeout; - sctp_association_hold(asoc); - add_timer(timer); + /* + * SCTP has a hard time with timer starts. Because we process + * timer starts as side effects, it can be hard to tell if we + * have already started a timer or not, which leads to BUG + * halts when we call add_timer. So here, instead of just starting + * a timer, if the timer is already started, and just mod + * the timer with the shorter of the two expiration times + */ + if (!timer_pending(timer)) + sctp_association_hold(asoc); + timer_reduce(timer, jiffies + timeout); break; case SCTP_CMD_TIMER_RESTART: diff --git a/net/sctp/sm_statefuns.c b/net/sctp/sm_statefuns.c index 26788f4a3b9e..e86620fbd90f 100644 --- a/net/sctp/sm_statefuns.c +++ b/net/sctp/sm_statefuns.c @@ -1856,12 +1856,13 @@ static enum sctp_disposition sctp_sf_do_dupcook_a( /* Update the content of current association. */ sctp_add_cmd_sf(commands, SCTP_CMD_UPDATE_ASSOC, SCTP_ASOC(new_asoc)); sctp_add_cmd_sf(commands, SCTP_CMD_EVENT_ULP, SCTP_ULPEVENT(ev)); - if (sctp_state(asoc, SHUTDOWN_PENDING) && + if ((sctp_state(asoc, SHUTDOWN_PENDING) || + sctp_state(asoc, SHUTDOWN_SENT)) && (sctp_sstate(asoc->base.sk, CLOSING) || sock_flag(asoc->base.sk, SOCK_DEAD))) { - /* if were currently in SHUTDOWN_PENDING, but the socket - * has been closed by user, don't transition to ESTABLISHED. - * Instead trigger SHUTDOWN bundled with COOKIE_ACK. + /* If the socket has been closed by user, don't + * transition to ESTABLISHED. Instead trigger SHUTDOWN + * bundled with COOKIE_ACK. */ sctp_add_cmd_sf(commands, SCTP_CMD_REPLY, SCTP_CHUNK(repl)); return sctp_sf_do_9_2_start_shutdown(net, ep, asoc, diff --git a/net/sctp/ulpevent.c b/net/sctp/ulpevent.c index c82dbdcf13f2..77d5c36a8991 100644 --- a/net/sctp/ulpevent.c +++ b/net/sctp/ulpevent.c @@ -343,6 +343,9 @@ void sctp_ulpevent_nofity_peer_addr_change(struct sctp_transport *transport, struct sockaddr_storage addr; struct sctp_ulpevent *event; + if (asoc->state < SCTP_STATE_ESTABLISHED) + return; + memset(&addr, 0, sizeof(struct sockaddr_storage)); memcpy(&addr, &transport->ipaddr, transport->af_specific->sockaddr_len); |