Enable quic tests in bogo

- bogo_shim needs quic feature
- provide/check quic transport params in bogo_shim
- reject servers that handshake at TLS1.2, but include a quic transport
  params extension.
- don't expose quic transport params extension for TLS1.2 clients.

These last two match BoringSSL.
This commit is contained in:
Joseph Birr-Pixton 2018-05-14 20:29:47 +01:00 committed by ctz
parent 9808983de7
commit 87ab639360
6 changed files with 51 additions and 11 deletions

View File

@ -37,7 +37,7 @@ regex = "0.2"
[[example]]
name = "bogo_shim"
path = "examples/internal/bogo_shim.rs"
required-features = ["dangerous_configuration"]
required-features = ["dangerous_configuration", "quic"]
[[example]]
name = "trytls_shim"

View File

@ -15,7 +15,6 @@
"TLS13-WrongOuterRecord": "we're lax on this",
"*DTLS*": "not supported",
"TokenBinding-*": "not supported",
"QUICTransportParams-*": "not supported",
"DummyPQPadding-*": "not supported",
"MTU*": "dtls only",
"DisableEverything": "not useful",
@ -272,6 +271,8 @@
"CurveTest-Server-Compressed-P-384-TLS12": ":PEER_MISBEHAVIOUR:",
"CurveTest-Client-Compressed-P-384-TLS13Draft23": ":PEER_MISBEHAVIOUR:",
"CurveTest-Server-Compressed-P-384-TLS13Draft23": ":PEER_MISBEHAVIOUR:",
"QUICTransportParams-Client-Rejected-TLS12": ":PEER_MISBEHAVIOUR:",
"QUICTransportParams-Server-Rejected-TLS12": "missing peer quic transport params",
"ExtendedMasterSecret-NoToYes-Client": ":PEER_MISBEHAVIOUR:",
"ExtendedMasterSecret-YesToNo-Server": ":PEER_MISBEHAVIOUR:",
"ExtendedMasterSecret-YesToNo-Client": ":PEER_MISBEHAVIOUR:"

View File

@ -6,7 +6,7 @@
set -xe
if [ ! -e ../target/debug/examples/bogo_shim ] ; then
cargo test --no-run --features dangerous_configuration
cargo test --no-run --features dangerous_configuration,quic
fi
if [ ! -e bogo/ ] ; then

View File

@ -19,6 +19,8 @@ use std::io::BufReader;
use std::io::{Write, Read};
use std::sync::Arc;
use rustls::internal::msgs::enums::ProtocolVersion;
use rustls::quic::ClientQuicExt;
use rustls::quic::ServerQuicExt;
static BOGO_NACK: i32 = 89;
@ -59,6 +61,8 @@ struct Options {
export_keying_material_context: String,
export_keying_material_context_used: bool,
read_size: usize,
quic_transport_params: Vec<u8>,
expect_quic_transport_params: Vec<u8>,
}
impl Options {
@ -93,6 +97,8 @@ impl Options {
export_keying_material_context: "".to_string(),
export_keying_material_context_used: false,
read_size: 512,
quic_transport_params: vec![],
expect_quic_transport_params: vec![],
}
}
@ -407,6 +413,14 @@ fn exec(opts: &Options, sess: &mut Box<rustls::Session>) {
sent_exporter = true;
}
if !sess.is_handshaking() &&
!opts.expect_quic_transport_params.is_empty() {
let their_transport_params = sess.get_quic_transport_parameters()
.expect("missing peer quic transport params");
assert_eq!(opts.expect_quic_transport_params,
their_transport_params);
}
let mut buf = [0u8; 1024];
let len = match sess.read(&mut buf[..opts.read_size]) {
Ok(len) => len,
@ -524,6 +538,14 @@ fn main() {
"-use-export-context" => {
opts.export_keying_material_context_used = true;
}
"-quic-transport-params" => {
opts.quic_transport_params = base64::decode(args.remove(0).as_bytes())
.expect("invalid base64");
}
"-expected-quic-transport-params" => {
opts.expect_quic_transport_params = base64::decode(args.remove(0).as_bytes())
.expect("invalid base64");
}
"-ocsp-response" => {
opts.server_ocsp_response = base64::decode(args.remove(0).as_bytes())
@ -664,16 +686,26 @@ fn main() {
let make_session = || {
if opts.server {
let s: Box<rustls::Session> =
Box::new(rustls::ServerSession::new(server_cfg.as_ref().unwrap()));
s
let s = if opts.quic_transport_params.is_empty() {
rustls::ServerSession::new(server_cfg.as_ref().unwrap())
} else {
rustls::ServerSession::new_quic(server_cfg.as_ref().unwrap(),
opts.quic_transport_params.clone())
};
Box::new(s) as Box<rustls::Session>
} else {
let dns_name =
webpki::DNSNameRef::try_from_ascii_str(&opts.host_name).unwrap();
let s: Box<rustls::Session> =
Box::new(rustls::ClientSession::new(client_cfg.as_ref().unwrap(),
dns_name));
s
let s = if opts.quic_transport_params.is_empty() {
rustls::ClientSession::new(client_cfg.as_ref().unwrap(),
dns_name)
} else {
rustls::ClientSession::new_quic(client_cfg.as_ref().unwrap(),
dns_name,
opts.quic_transport_params.clone())
};
Box::new(s) as Box<rustls::Session>
}
};

View File

@ -644,6 +644,13 @@ impl State for ExpectServerHello {
process_alpn_protocol(sess, server_hello.get_alpn_protocol())?;
}
// Reject QUIC if TLS1.2 is in use.
if !sess.common.is_tls13() &&
server_hello.find_extension(ExtensionType::TransportParameters).is_some() {
sess.common.send_fatal_alert(AlertDescription::UnsupportedExtension);
return Err(TLSError::PeerMisbehavedError("server wants to do quic+tls1.2".to_string()));
}
// If ECPointFormats extension is supplied by the server, it must contain
// Uncompressed. But it's allowed to be omitted.
if let Some(point_fmts) = server_hello.get_ecpoints_extension() {

View File

@ -225,7 +225,7 @@ impl ExpectClientHello {
}
// QUIC transport parameters
if let Some(params) = hello.get_quic_params_extension() {
if let (Some(params), true) = (hello.get_quic_params_extension(), sess.common.is_tls13()) {
sess.quic_params = Some(params);
}