diff --git a/.github/workflows/tquic-integration.yml b/.github/workflows/tquic-integration.yml index aba03618..0b2d9687 100644 --- a/.github/workflows/tquic-integration.yml +++ b/.github/workflows/tquic-integration.yml @@ -23,3 +23,7 @@ jobs: run: | cd tools/tests/ bash ./tquic_tools_test.sh -b ../../target/release/ -t multipath_redundant,multipath_minrtt,multipath_roundrobin -f 1000M -p 5 + - name: Run integration tests for disable_1rtt_encryption + run: | + cd tools/tests/ + bash ./tquic_tools_test.sh -b ../../target/release/ -t multipath_minrtt -c '~~disable-encryption' -s '~~disable-encryption' diff --git a/src/connection/connection.rs b/src/connection/connection.rs index ebf84f08..2af19cee 100644 --- a/src/connection/connection.rs +++ b/src/connection/connection.rs @@ -1680,7 +1680,11 @@ impl Connection { .tls_session .get_overhead(level) .ok_or(Error::InternalError)?; - let total_overhead = pkt_num_offset + pkt_num_len + crypto_overhead; + let total_overhead = if !self.is_encryption_disabled(hdr.pkt_type) { + pkt_num_offset + pkt_num_len + crypto_overhead + } else { + pkt_num_offset + pkt_num_len + }; match left.checked_sub(total_overhead) { Some(val) => left = val, @@ -1727,6 +1731,8 @@ impl Connection { // fields) in bytes let payload_len = write_status.written; if pkt_type != PacketType::OneRTT { + // Note: This type of packet is always encrypted, even if the disable_1rtt_encryption + // transport parameter is successfully negotiated. let len = pkt_num_len + payload_len + crypto_overhead; let mut out = &mut out[hdr_offset..]; out.write_varint_with_len(len as u64, crate::LENGTH_FIELD_LEN)?; diff --git a/src/packet.rs b/src/packet.rs index d346adee..f2d9f998 100644 --- a/src/packet.rs +++ b/src/packet.rs @@ -541,33 +541,43 @@ pub(crate) fn decrypt_header( aead: &Open, plaintext_mode: bool, ) -> Result<()> { - if pkt_buf.len() < pkt_num_offset + MAX_PKT_NUM_LEN + SAMPLE_LEN { + let pkt_buf_min = if !plaintext_mode { + pkt_num_offset + MAX_PKT_NUM_LEN + SAMPLE_LEN + } else { + // All aspects of encryption on 1-RTT packets are removed and it is no + // longer including an AEAD tag. + pkt_num_offset + MAX_PKT_NUM_LEN + }; + if pkt_buf.len() < pkt_buf_min { return Err(Error::BufferTooShort); } + // Decrypt packet haader if needed let mut first = pkt_buf[0]; - let sample_start = pkt_num_offset + MAX_PKT_NUM_LEN; - let sample = &pkt_buf[sample_start..sample_start + SAMPLE_LEN]; - let mask = aead.new_mask(sample)?; - - // Remove protection of bits in the first byte - if !plaintext_mode { + let (pkt_num_len, pkt_num_buf) = if !plaintext_mode { + // Remove protection of bits in the first byte + let sample_start = pkt_num_offset + MAX_PKT_NUM_LEN; + let sample = &pkt_buf[sample_start..sample_start + SAMPLE_LEN]; + let mask = aead.new_mask(sample)?; if PacketHeader::long_header(first) { first ^= mask[0] & 0x0f; } else { first ^= mask[0] & 0x1f; } - } - let pkt_num_len = usize::from((first & PKT_NUM_LEN_MASK) + 1); - let pkt_num_buf = &mut pkt_buf[pkt_num_offset..pkt_num_offset + pkt_num_len]; + let pkt_num_len = usize::from((first & PKT_NUM_LEN_MASK) + 1); + let pkt_num_buf = &mut pkt_buf[pkt_num_offset..pkt_num_offset + pkt_num_len]; - // Remove protection of packet number field - if !plaintext_mode { + // Remove protection of packet number field for i in 0..pkt_num_len { pkt_num_buf[i] ^= mask[i + 1]; } - } + (pkt_num_len, pkt_num_buf) + } else { + let pkt_num_len = usize::from((first & PKT_NUM_LEN_MASK) + 1); + let pkt_num_buf = &mut pkt_buf[pkt_num_offset..pkt_num_offset + pkt_num_len]; + (pkt_num_len, pkt_num_buf) + }; // Extract packet number corresponding to the length. let pkt_num = {