Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 311634
b: refs/heads/master
c: 4244854
h: refs/heads/master
v: v3
  • Loading branch information
Neil Horman authored and David S. Miller committed Jul 1, 2012
1 parent 5933e6f commit 025c94d
Show file tree
Hide file tree
Showing 11 changed files with 40 additions and 6 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 0e90b49ca4b891f085b57559a3071a4feefb496c
refs/heads/master: 4244854d22bf8f782698c5224b9191c8d2d42610
4 changes: 4 additions & 0 deletions trunk/include/net/sctp/structs.h
Original file line number Diff line number Diff line change
Expand Up @@ -912,6 +912,9 @@ struct sctp_transport {
/* Is this structure kfree()able? */
malloced:1;

/* Has this transport moved the ctsn since we last sacked */
__u32 sack_generation;

struct flowi fl;

/* This is the peer's IP address and port. */
Expand Down Expand Up @@ -1584,6 +1587,7 @@ struct sctp_association {
*/
__u8 sack_needed; /* Do we need to sack the peer? */
__u32 sack_cnt;
__u32 sack_generation;

/* These are capabilities which our peer advertised. */
__u8 ecn_capable:1, /* Can peer do ECN? */
Expand Down
3 changes: 2 additions & 1 deletion trunk/include/net/sctp/tsnmap.h
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,8 @@ void sctp_tsnmap_free(struct sctp_tsnmap *map);
int sctp_tsnmap_check(const struct sctp_tsnmap *, __u32 tsn);

/* Mark this TSN as seen. */
int sctp_tsnmap_mark(struct sctp_tsnmap *, __u32 tsn);
int sctp_tsnmap_mark(struct sctp_tsnmap *, __u32 tsn,
struct sctp_transport *trans);

/* Mark this TSN and all lower as seen. */
void sctp_tsnmap_skip(struct sctp_tsnmap *map, __u32 tsn);
Expand Down
1 change: 1 addition & 0 deletions trunk/net/sctp/associola.c
Original file line number Diff line number Diff line change
Expand Up @@ -271,6 +271,7 @@ static struct sctp_association *sctp_association_init(struct sctp_association *a
*/
asoc->peer.sack_needed = 1;
asoc->peer.sack_cnt = 0;
asoc->peer.sack_generation = 1;

/* Assume that the peer will tell us if he recognizes ASCONF
* as part of INIT exchange.
Expand Down
5 changes: 5 additions & 0 deletions trunk/net/sctp/output.c
Original file line number Diff line number Diff line change
Expand Up @@ -248,6 +248,11 @@ static sctp_xmit_t sctp_packet_bundle_sack(struct sctp_packet *pkt,
/* If the SACK timer is running, we have a pending SACK */
if (timer_pending(timer)) {
struct sctp_chunk *sack;

if (pkt->transport->sack_generation !=
pkt->transport->asoc->peer.sack_generation)
return retval;

asoc->a_rwnd = asoc->rwnd;
sack = sctp_make_sack(asoc);
if (sack) {
Expand Down
16 changes: 16 additions & 0 deletions trunk/net/sctp/sm_make_chunk.c
Original file line number Diff line number Diff line change
Expand Up @@ -734,8 +734,10 @@ struct sctp_chunk *sctp_make_sack(const struct sctp_association *asoc)
int len;
__u32 ctsn;
__u16 num_gabs, num_dup_tsns;
struct sctp_association *aptr = (struct sctp_association *)asoc;
struct sctp_tsnmap *map = (struct sctp_tsnmap *)&asoc->peer.tsn_map;
struct sctp_gap_ack_block gabs[SCTP_MAX_GABS];
struct sctp_transport *trans;

memset(gabs, 0, sizeof(gabs));
ctsn = sctp_tsnmap_get_ctsn(map);
Expand Down Expand Up @@ -805,6 +807,20 @@ struct sctp_chunk *sctp_make_sack(const struct sctp_association *asoc)
sctp_addto_chunk(retval, sizeof(__u32) * num_dup_tsns,
sctp_tsnmap_get_dups(map));

/* Once we have a sack generated, check to see what our sack
* generation is, if its 0, reset the transports to 0, and reset
* the association generation to 1
*
* The idea is that zero is never used as a valid generation for the
* association so no transport will match after a wrap event like this,
* Until the next sack
*/
if (++aptr->peer.sack_generation == 0) {
list_for_each_entry(trans, &asoc->peer.transport_addr_list,
transports)
trans->sack_generation = 0;
aptr->peer.sack_generation = 1;
}
nodata:
return retval;
}
Expand Down
2 changes: 1 addition & 1 deletion trunk/net/sctp/sm_sideeffect.c
Original file line number Diff line number Diff line change
Expand Up @@ -1268,7 +1268,7 @@ static int sctp_cmd_interpreter(sctp_event_t event_type,
case SCTP_CMD_REPORT_TSN:
/* Record the arrival of a TSN. */
error = sctp_tsnmap_mark(&asoc->peer.tsn_map,
cmd->obj.u32);
cmd->obj.u32, NULL);
break;

case SCTP_CMD_REPORT_FWDTSN:
Expand Down
2 changes: 2 additions & 0 deletions trunk/net/sctp/transport.c
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,8 @@ static struct sctp_transport *sctp_transport_init(struct sctp_transport *peer,
peer->af_specific = sctp_get_af_specific(addr->sa.sa_family);
memset(&peer->saddr, 0, sizeof(union sctp_addr));

peer->sack_generation = 0;

/* From 6.3.1 RTO Calculation:
*
* C1) Until an RTT measurement has been made for a packet sent to the
Expand Down
6 changes: 5 additions & 1 deletion trunk/net/sctp/tsnmap.c
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,8 @@ int sctp_tsnmap_check(const struct sctp_tsnmap *map, __u32 tsn)


/* Mark this TSN as seen. */
int sctp_tsnmap_mark(struct sctp_tsnmap *map, __u32 tsn)
int sctp_tsnmap_mark(struct sctp_tsnmap *map, __u32 tsn,
struct sctp_transport *trans)
{
u16 gap;

Expand All @@ -133,6 +134,9 @@ int sctp_tsnmap_mark(struct sctp_tsnmap *map, __u32 tsn)
*/
map->max_tsn_seen++;
map->cumulative_tsn_ack_point++;
if (trans)
trans->sack_generation =
trans->asoc->peer.sack_generation;
map->base_tsn++;
} else {
/* Either we already have a gap, or about to record a gap, so
Expand Down
3 changes: 2 additions & 1 deletion trunk/net/sctp/ulpevent.c
Original file line number Diff line number Diff line change
Expand Up @@ -715,7 +715,8 @@ struct sctp_ulpevent *sctp_ulpevent_make_rcvmsg(struct sctp_association *asoc,
* can mark it as received so the tsn_map is updated correctly.
*/
if (sctp_tsnmap_mark(&asoc->peer.tsn_map,
ntohl(chunk->subh.data_hdr->tsn)))
ntohl(chunk->subh.data_hdr->tsn),
chunk->transport))
goto fail_mark;

/* First calculate the padding, so we don't inadvertently
Expand Down
2 changes: 1 addition & 1 deletion trunk/net/sctp/ulpqueue.c
Original file line number Diff line number Diff line change
Expand Up @@ -1051,7 +1051,7 @@ void sctp_ulpq_renege(struct sctp_ulpq *ulpq, struct sctp_chunk *chunk,
if (chunk && (freed >= needed)) {
__u32 tsn;
tsn = ntohl(chunk->subh.data_hdr->tsn);
sctp_tsnmap_mark(&asoc->peer.tsn_map, tsn);
sctp_tsnmap_mark(&asoc->peer.tsn_map, tsn, chunk->transport);
sctp_ulpq_tail_data(ulpq, chunk, gfp);

sctp_ulpq_partial_delivery(ulpq, chunk, gfp);
Expand Down

0 comments on commit 025c94d

Please sign in to comment.