Commit 92548ec2 authored by Xin Long's avatar Xin Long Committed by David S. Miller
Browse files

sctp: add the probe timer in transport for PLPMTUD



There are 3 timers described in rfc8899#section-5.1.1:

  PROBE_TIMER, PMTU_RAISE_TIMER, CONFIRMATION_TIMER

This patches adds a 'probe_timer' in transport, and it works as either
PROBE_TIMER or PMTU_RAISE_TIMER. At most time, it works as PROBE_TIMER
and expires every a 'probe_interval' time to send the HB probe packet.
When transport pl enters COMPLETE state, it works as PMTU_RAISE_TIMER
and expires in 'probe_interval * 30' time to go back to SEARCH state
and do searching again.

SCTP HB is an acknowledged packet, CONFIRMATION_TIMER is not needed.

The timer will start when transport pl enters BASE state and stop
when it enters DISABLED state.

Signed-off-by: default avatarXin Long <lucien.xin@gmail.com>
Acked-by: default avatarMarcelo Ricardo Leitner <marcelo.leitner@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent d9e2e410
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -59,6 +59,7 @@ enum sctp_verb {
	SCTP_CMD_HB_TIMERS_START,    /* Start the heartbeat timers. */
	SCTP_CMD_HB_TIMER_UPDATE,    /* Update a heartbeat timers.  */
	SCTP_CMD_HB_TIMERS_STOP,     /* Stop the heartbeat timers.  */
	SCTP_CMD_PROBE_TIMER_UPDATE, /* Update a probe timer.  */
	SCTP_CMD_TRANSPORT_HB_SENT,  /* Reset the status of a transport. */
	SCTP_CMD_TRANSPORT_IDLE,     /* Do manipulations on idle transport */
	SCTP_CMD_TRANSPORT_ON,       /* Mark the transport as active. */
+1 −0
Original line number Diff line number Diff line
@@ -77,6 +77,7 @@ enum sctp_event_timeout {
	SCTP_EVENT_TIMEOUT_T5_SHUTDOWN_GUARD,
	SCTP_EVENT_TIMEOUT_HEARTBEAT,
	SCTP_EVENT_TIMEOUT_RECONF,
	SCTP_EVENT_TIMEOUT_PROBE,
	SCTP_EVENT_TIMEOUT_SACK,
	SCTP_EVENT_TIMEOUT_AUTOCLOSE,
};
+8 −1
Original line number Diff line number Diff line
@@ -635,18 +635,25 @@ static inline void sctp_transport_pl_reset(struct sctp_transport *t)
			t->pl.state = SCTP_PL_BASE;
			t->pl.pmtu = SCTP_BASE_PLPMTU;
			t->pl.probe_size = SCTP_BASE_PLPMTU;
			sctp_transport_reset_probe_timer(t);
		}
	} else {
		if (t->pl.state != SCTP_PL_DISABLED)
		if (t->pl.state != SCTP_PL_DISABLED) {
			if (del_timer(&t->probe_timer))
				sctp_transport_put(t);
			t->pl.state = SCTP_PL_DISABLED;
		}
	}
}

static inline void sctp_transport_pl_update(struct sctp_transport *t)
{
	if (t->pl.state == SCTP_PL_DISABLED)
		return;

	if (del_timer(&t->probe_timer))
		sctp_transport_put(t);

	t->pl.state = SCTP_PL_BASE;
	t->pl.pmtu = SCTP_BASE_PLPMTU;
	t->pl.probe_size = SCTP_BASE_PLPMTU;
+2 −0
Original line number Diff line number Diff line
@@ -151,6 +151,7 @@ sctp_state_fn_t sctp_sf_cookie_wait_icmp_abort;
/* Prototypes for timeout event state functions.  */
sctp_state_fn_t sctp_sf_do_6_3_3_rtx;
sctp_state_fn_t sctp_sf_send_reconf;
sctp_state_fn_t sctp_sf_send_probe;
sctp_state_fn_t sctp_sf_do_6_2_sack;
sctp_state_fn_t sctp_sf_autoclose_timer_expire;

@@ -311,6 +312,7 @@ int sctp_do_sm(struct net *net, enum sctp_event_type event_type,
void sctp_generate_t3_rtx_event(struct timer_list *t);
void sctp_generate_heartbeat_event(struct timer_list *t);
void sctp_generate_reconf_event(struct timer_list *t);
void sctp_generate_probe_event(struct timer_list *t);
void sctp_generate_proto_unreach_event(struct timer_list *t);

void sctp_ootb_pkt_free(struct sctp_packet *packet);
+4 −0
Original line number Diff line number Diff line
@@ -936,6 +936,9 @@ struct sctp_transport {
	/* Timer to handler reconf chunk rtx */
	struct timer_list reconf_timer;

	/* Timer to send a probe HB packet for PLPMTUD */
	struct timer_list probe_timer;

	/* Since we're using per-destination retransmission timers
	 * (see above), we're also using per-destination "transmitted"
	 * queues.  This probably ought to be a private struct
@@ -1003,6 +1006,7 @@ void sctp_transport_free(struct sctp_transport *);
void sctp_transport_reset_t3_rtx(struct sctp_transport *);
void sctp_transport_reset_hb_timer(struct sctp_transport *);
void sctp_transport_reset_reconf_timer(struct sctp_transport *transport);
void sctp_transport_reset_probe_timer(struct sctp_transport *transport);
int sctp_transport_hold(struct sctp_transport *);
void sctp_transport_put(struct sctp_transport *);
void sctp_transport_update_rto(struct sctp_transport *, __u32);
Loading