Release 2.27.5

- [BUGFIX] Assertion in send controller when path validation fails.
- [BUGFIX] Assertion in BBR when sending out-of-order packets is
  detected.
- [BUGFIX] Drop overflow receive history ranges when cloning.
- Log correct size of the incoming packet.
- Fix internal stream function.
This commit is contained in:
Dmitri Tikhonov 2021-01-18 13:26:33 -05:00
parent 347a040589
commit bbee242ac0
11 changed files with 62 additions and 26 deletions

View file

@ -1,3 +1,12 @@
2021-01-18
- 2.27.5
- [BUGFIX] Assertion in send controller when path validation fails.
- [BUGFIX] Assertion in BBR when sending out-of-order packets is
detected.
- [BUGFIX] Drop overflow receive history ranges when cloning.
- Log correct size of the incoming packet.
- Fix internal stream function.
2021-01-13
- 2.27.4
- [API] Add lsquic_conn_get_sni(), fixes issue #203.

View file

@ -26,7 +26,7 @@ author = u'LiteSpeed Technologies'
# The short X.Y version
version = u'2.27'
# The full version, including alpha/beta/rc tags
release = u'2.27.4'
release = u'2.27.5'
# -- General configuration ---------------------------------------------------

View file

@ -25,7 +25,7 @@ extern "C" {
#define LSQUIC_MAJOR_VERSION 2
#define LSQUIC_MINOR_VERSION 27
#define LSQUIC_PATCH_VERSION 4
#define LSQUIC_PATCH_VERSION 5
/**
* Engine flags:

View file

@ -344,9 +344,11 @@ lsquic_bbr_ack (void *cong_ctl, struct lsquic_packet_out *packet_out,
if (sample)
TAILQ_INSERT_TAIL(&bbr->bbr_ack_state.samples, sample, next);
if (is_valid_packno(bbr->bbr_ack_state.max_packno))
/* We assume packet numbers are ordered */
assert(packet_out->po_packno > bbr->bbr_ack_state.max_packno);
if (!is_valid_packno(bbr->bbr_ack_state.max_packno)
/* Packet ordering is checked for, and warned about, in
* lsquic_senhist_add().
*/
|| packet_out->po_packno > bbr->bbr_ack_state.max_packno)
bbr->bbr_ack_state.max_packno = packet_out->po_packno;
bbr->bbr_ack_state.acked_bytes += packet_sz;
}

View file

@ -52,9 +52,9 @@ void
lsquic_ev_log_packet_in (const lsquic_cid_t *cid,
const lsquic_packet_in_t *packet_in)
{
switch (packet_in->pi_flags & (
PI_FROM_MINI|
PI_GQUIC))
unsigned packet_sz;
switch (packet_in->pi_flags & (PI_FROM_MINI|PI_GQUIC))
{
case PI_FROM_MINI|PI_GQUIC:
LCID("packet in: %"PRIu64" (from mini)", packet_in->pi_packno);
@ -65,15 +65,18 @@ lsquic_ev_log_packet_in (const lsquic_cid_t *cid,
lsquic_packet_in_ecn(packet_in));
break;
case PI_GQUIC:
LCID("packet in: %"PRIu64", size: %u", packet_in->pi_packno,
(unsigned) (packet_in->pi_data_sz + GQUIC_PACKET_HASH_SZ));
packet_sz = packet_in->pi_data_sz
+ (packet_in->pi_flags & PI_DECRYPTED ? GQUIC_PACKET_HASH_SZ : 0);
LCID("packet in: %"PRIu64", size: %u", packet_in->pi_packno, packet_sz);
break;
default:
packet_sz = packet_in->pi_data_sz
+ (packet_in->pi_flags & PI_DECRYPTED ? IQUIC_TAG_LEN : 0);
if (packet_in->pi_flags & PI_LOG_QL_BITS)
LCID("packet in: %"PRIu64", type: %s, size: %u; ecn: %u, spin: %d; "
"path: %hhu; Q: %d; L: %d",
packet_in->pi_packno, lsquic_hety2str[packet_in->pi_header_type],
(unsigned) (packet_in->pi_data_sz + IQUIC_TAG_LEN),
packet_sz,
lsquic_packet_in_ecn(packet_in),
/* spin bit value is only valid for short packet headers */
lsquic_packet_in_spin_bit(packet_in), packet_in->pi_path_id,
@ -83,7 +86,7 @@ lsquic_ev_log_packet_in (const lsquic_cid_t *cid,
LCID("packet in: %"PRIu64", type: %s, size: %u; ecn: %u, spin: %d; "
"path: %hhu",
packet_in->pi_packno, lsquic_hety2str[packet_in->pi_header_type],
(unsigned) (packet_in->pi_data_sz + IQUIC_TAG_LEN),
packet_sz,
lsquic_packet_in_ecn(packet_in),
/* spin bit value is only valid for short packet headers */
lsquic_packet_in_spin_bit(packet_in), packet_in->pi_path_id);

View file

@ -731,7 +731,8 @@ path_chal_alarm_expired (enum alarm_id al_id, void *ctx,
LSQ_INFO("migration to path #%u failed after none of %u path "
"challenges received responses", path_id, copath->cop_n_chals);
/* There may be a lingering challenge if its generation is delayed */
lsquic_send_ctl_cancel_chals(&conn->ifc_send_ctl, &copath->cop_path);
lsquic_send_ctl_cancel_path_verification(&conn->ifc_send_ctl,
&copath->cop_path);
wipe_path(conn, path_id);
}
else

View file

@ -503,7 +503,13 @@ lsquic_rechist_copy_ranges (struct lsquic_rechist *rechist, void *src_rechist,
assert(rechist->rh_n_used == 0);
prev_idx = UINT_MAX;
for (range = first(src_rechist); range; range = next(src_rechist))
for (range = first(src_rechist); range &&
/* Do not overwrite higher-numbered ranges. (Also, logic below
* does not work if rechist_reuse_last_elem() is used.)
*/
(rechist->rh_max_ranges == 0
|| rechist->rh_n_used < rechist->rh_max_ranges);
range = next(src_rechist))
{
idx = rechist_alloc_elem(rechist);
if (idx < 0)

View file

@ -3603,15 +3603,15 @@ lsquic_send_ctl_repath (struct lsquic_send_ctl *ctl,
}
/* Drop PATH_CHALLENGE packets for path `path'. */
/* Drop PATH_CHALLENGE and PATH_RESPONSE packets for path `path'. */
void
lsquic_send_ctl_cancel_chals (struct lsquic_send_ctl *ctl,
lsquic_send_ctl_cancel_path_verification (struct lsquic_send_ctl *ctl,
const struct network_path *path)
{
struct lsquic_packet_out *packet_out, *next;
/* We need only to examine the scheduled queue as lost challenges are
* not retransmitted.
/* We need only to examine the scheduled queue as lost challenges and
* responses are not retransmitted.
*/
for (packet_out = TAILQ_FIRST(&ctl->sc_scheduled_packets); packet_out;
packet_out = next)
@ -3619,7 +3619,8 @@ lsquic_send_ctl_cancel_chals (struct lsquic_send_ctl *ctl,
next = TAILQ_NEXT(packet_out, po_next);
if (packet_out->po_path == path)
{
assert(packet_out->po_frame_types & QUIC_FTBIT_PATH_CHALLENGE);
assert(packet_out->po_frame_types
& (QUIC_FTBIT_PATH_CHALLENGE|QUIC_FTBIT_PATH_RESPONSE));
assert(!(packet_out->po_frame_types & ctl->sc_retx_frames));
send_ctl_maybe_renumber_sched_to_right(ctl, packet_out);
send_ctl_sched_remove(ctl, packet_out);

View file

@ -387,7 +387,7 @@ lsquic_send_ctl_repath (struct lsquic_send_ctl *ctl,
int keep_path_properties);
void
lsquic_send_ctl_cancel_chals (struct lsquic_send_ctl *,
lsquic_send_ctl_cancel_path_verification (struct lsquic_send_ctl *,
const struct network_path *);
void

View file

@ -909,10 +909,10 @@ lsquic_stream_readable (struct lsquic_stream *stream)
int
lsquic_stream_is_write_reset (const struct lsquic_stream *stream)
{
if (stream->sm_bflags & SMBF_IETF)
return stream->stream_flags & STREAM_SS_RECVD;
else
return (stream->stream_flags & (STREAM_RST_RECVD|STREAM_RST_SENT))
/* The two protocols use different frames to effect write reset: */
const enum stream_flags cause_flag = stream->sm_bflags & SMBF_IETF
? STREAM_SS_RECVD : STREAM_RST_RECVD;
return (stream->stream_flags & (cause_flag|STREAM_RST_SENT))
|| (stream->sm_qflags & SMQF_SEND_RST);
}

View file

@ -121,6 +121,7 @@ test_range_copy (struct lsquic_rechist *orig, int ietf)
{
char orig_str[0x1000], new_str[0x1000];
struct lsquic_rechist new;
size_t len;
rechist2str(orig, orig_str, sizeof(orig_str));
@ -130,6 +131,19 @@ test_range_copy (struct lsquic_rechist *orig, int ietf)
(const struct lsquic_packno_range * (*) (void *)) lsquic_rechist_next);
rechist2str(&new, new_str, sizeof(new_str));
assert(0 == strcmp(orig_str, new_str));
lsquic_rechist_cleanup(&new);
/* This tests that lower-numbered ranges do not overwrite higher-numbered
* ranges.
*/
lsquic_rechist_init(&new, ietf, 10);
lsquic_rechist_copy_ranges(&new, orig,
(const struct lsquic_packno_range * (*) (void *)) lsquic_rechist_first,
(const struct lsquic_packno_range * (*) (void *)) lsquic_rechist_next);
rechist2str(&new, new_str, sizeof(new_str));
len = strlen(new_str);
assert(0 == strncmp(orig_str, new_str, len));
lsquic_rechist_cleanup(&new);
}