mirror of
https://github.com/rustdesk/rustdesk.git
synced 2026-09-19 02:41:10 +03:00
feat: WebRTC transport racing, DTLS identity binding, and pc-leak fixes
- prefer-P2P racing (race_transports_prefer_webrtc) across punch and RelayResponse; ICE bridge with 400ms candidate resend - controlled-side answerer and ICE routing; sign local DTLS fingerprint into SignedId, controller verifies the binding fail-closed - fix pc leaks: close_webrtc() on insecure-decline paths (io_loop, port_forward); compute direct before disarming the offerer guard - point hbb_common to the WebRTC data-plane commit 9f5a296 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -155,6 +155,9 @@ async fn connect_and_login(
|
||||
if !stream.is_secured() && !crate::common::is_direct_ip_access(id) {
|
||||
if !confirm_insecure_connection(&interface, ui_receiver).await {
|
||||
*close_port_forward = true;
|
||||
// Close the WebRTC pc on this decline path too (no-op for TCP/WS), matching every
|
||||
// other exit in this function; a bare drop leaks it in the global session cache.
|
||||
stream.close_webrtc().await;
|
||||
return Ok(None);
|
||||
}
|
||||
}
|
||||
@@ -167,6 +170,7 @@ async fn connect_and_login(
|
||||
tokio::select! {
|
||||
res = timeout(READ_TIMEOUT, stream.next()) => match res {
|
||||
Err(_) => {
|
||||
stream.close_webrtc().await;
|
||||
bail!("Timeout");
|
||||
}
|
||||
Ok(Some(Ok(bytes))) => {
|
||||
@@ -174,7 +178,13 @@ async fn connect_and_login(
|
||||
received = true;
|
||||
interface.update_received(true);
|
||||
}
|
||||
let msg_in = Message::parse_from_bytes(&bytes)?;
|
||||
let msg_in = match Message::parse_from_bytes(&bytes) {
|
||||
Ok(msg) => msg,
|
||||
Err(err) => {
|
||||
stream.close_webrtc().await;
|
||||
return Err(err.into());
|
||||
}
|
||||
};
|
||||
match msg_in.union {
|
||||
Some(message::Union::Hash(hash)) => {
|
||||
if !interface.handle_hash(password, hash, &mut stream).await {
|
||||
@@ -184,6 +194,7 @@ async fn connect_and_login(
|
||||
Some(message::Union::LoginResponse(lr)) => match lr.union {
|
||||
Some(login_response::Union::Error(err)) => {
|
||||
if !interface.handle_login_error(&err) {
|
||||
stream.close_webrtc().await;
|
||||
return Ok(None);
|
||||
}
|
||||
}
|
||||
@@ -200,9 +211,11 @@ async fn connect_and_login(
|
||||
}
|
||||
}
|
||||
Ok(Some(Err(err))) => {
|
||||
stream.close_webrtc().await;
|
||||
bail!("Connection closed: {}", err);
|
||||
}
|
||||
_ => {
|
||||
stream.close_webrtc().await;
|
||||
bail!("Reset by the peer");
|
||||
}
|
||||
},
|
||||
@@ -221,6 +234,7 @@ async fn connect_and_login(
|
||||
if let Some(Ok(bytes)) = res {
|
||||
buffer.extend(bytes);
|
||||
} else {
|
||||
stream.close_webrtc().await;
|
||||
return Ok(None);
|
||||
}
|
||||
},
|
||||
@@ -255,5 +269,6 @@ async fn run_forward(forward: Framed<TcpStream, BytesCodec>, stream: Stream) ->
|
||||
},
|
||||
}
|
||||
}
|
||||
stream.close_webrtc().await;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user