restrict switch sides to remote desktop sessions (#15610)

* fix: restrict switch sides to remote desktop sessions

 Reject switch sides requests outside authenticated remote desktop sessions, and reject switch sides responses that try to carry non-remote login types.

 Add scope coverage so file transfer, terminal, view camera, and port forward sessions cannot use switch sides.

Signed-off-by: 21pages <sunboeasy@gmail.com>

* fix review: consume switch sides UUID before rejecting response

Signed-off-by: 21pages <sunboeasy@gmail.com>

---------

Signed-off-by: 21pages <sunboeasy@gmail.com>
This commit is contained in:
21pages
2026-07-17 15:52:49 +08:00
committed by GitHub
parent 5abf4e9724
commit 96e2a330b8

View File

@@ -2807,7 +2807,6 @@ impl Connection {
#[cfg(feature = "flutter")] #[cfg(feature = "flutter")]
#[cfg(not(any(target_os = "android", target_os = "ios")))] #[cfg(not(any(target_os = "android", target_os = "ios")))]
if let Some(lr) = _s.lr.clone().take() { if let Some(lr) = _s.lr.clone().take() {
self.handle_login_request_without_validation(&lr).await;
SWITCH_SIDES_UUID SWITCH_SIDES_UUID
.lock() .lock()
.unwrap() .unwrap()
@@ -2816,6 +2815,15 @@ impl Connection {
if let Ok(uuid) = uuid::Uuid::from_slice(_s.uuid.to_vec().as_ref()) { if let Ok(uuid) = uuid::Uuid::from_slice(_s.uuid.to_vec().as_ref()) {
if let Some((_instant, uuid_old)) = uuid_old { if let Some((_instant, uuid_old)) = uuid_old {
if uuid == uuid_old { if uuid == uuid_old {
if lr.union.is_some() {
log::warn!(
"Rejected switch sides response for non-remote-desktop session; closing connection"
);
self.send_login_error("Connection not allowed").await;
return false;
}
self.reset_session_scope_for_login();
self.handle_login_request_without_validation(&lr).await;
self.from_switch = true; self.from_switch = true;
self.set_conn_audit_primary_auth(ConnAuditPrimaryAuth::SwitchSides); self.set_conn_audit_primary_auth(ConnAuditPrimaryAuth::SwitchSides);
if !self.send_logon_response_and_keep_alive().await { if !self.send_logon_response_and_keep_alive().await {
@@ -5656,6 +5664,7 @@ impl Connection {
Some(misc::Union::ChangeDisplayResolution(_)) => "misc.change_display_resolution", Some(misc::Union::ChangeDisplayResolution(_)) => "misc.change_display_resolution",
Some(misc::Union::MessageQuery(_)) => "misc.message_query", Some(misc::Union::MessageQuery(_)) => "misc.message_query",
Some(misc::Union::FollowCurrentDisplay(_)) => "misc.follow_current_display", Some(misc::Union::FollowCurrentDisplay(_)) => "misc.follow_current_display",
Some(misc::Union::SwitchSidesRequest(_)) => "misc.switch_sides_request",
Some(_) => "misc.other", Some(_) => "misc.other",
None => "misc.empty", None => "misc.empty",
} }
@@ -6773,6 +6782,10 @@ mod test {
misc_msg(|m| m.set_capture_displays(CaptureDisplays::new())), misc_msg(|m| m.set_capture_displays(CaptureDisplays::new())),
Some("misc.capture_displays"), Some("misc.capture_displays"),
), ),
(
misc_msg(|m| m.set_switch_sides_request(SwitchSidesRequest::new())),
Some("misc.switch_sides_request"),
),
(msg(|m| m.set_clipboard(Clipboard::new())), None), (msg(|m| m.set_clipboard(Clipboard::new())), None),
( (
msg(|m| m.set_multi_clipboards(MultiClipboards::new())), msg(|m| m.set_multi_clipboards(MultiClipboards::new())),
@@ -6817,6 +6830,10 @@ mod test {
misc_msg(|m| m.set_toggle_privacy_mode(TogglePrivacyMode::new())), misc_msg(|m| m.set_toggle_privacy_mode(TogglePrivacyMode::new())),
Some("misc.toggle_privacy_mode"), Some("misc.toggle_privacy_mode"),
), ),
(
misc_msg(|m| m.set_switch_sides_request(SwitchSidesRequest::new())),
Some("misc.switch_sides_request"),
),
(misc_msg(|m| m.set_chat_message(ChatMessage::new())), None), (misc_msg(|m| m.set_chat_message(ChatMessage::new())), None),
(msg(|m| m.set_clipboard(Clipboard::new())), None), (msg(|m| m.set_clipboard(Clipboard::new())), None),
( (
@@ -6902,6 +6919,10 @@ mod test {
msg(|m| m.set_terminal_action(TerminalAction::new())), msg(|m| m.set_terminal_action(TerminalAction::new())),
Some("terminal_action"), Some("terminal_action"),
), ),
(
misc_msg(|m| m.set_switch_sides_request(SwitchSidesRequest::new())),
Some("misc.switch_sides_request"),
),
], ],
), ),
( (
@@ -6912,6 +6933,10 @@ mod test {
None, None,
), ),
(msg(|m| m.set_terminal_action(TerminalAction::new())), None), (msg(|m| m.set_terminal_action(TerminalAction::new())), None),
(
misc_msg(|m| m.set_switch_sides_request(SwitchSidesRequest::new())),
None,
),
], ],
), ),
( (
@@ -6931,6 +6956,10 @@ mod test {
msg(|m| m.set_screenshot_request(ScreenshotRequest::new())), msg(|m| m.set_screenshot_request(ScreenshotRequest::new())),
Some("screenshot_request"), Some("screenshot_request"),
), ),
(
misc_msg(|m| m.set_switch_sides_request(SwitchSidesRequest::new())),
Some("misc.switch_sides_request"),
),
(misc_msg(|m| m.set_refresh_video(true)), None), (misc_msg(|m| m.set_refresh_video(true)), None),
(misc_msg(|m| m.set_refresh_video_display(0)), None), (misc_msg(|m| m.set_refresh_video_display(0)), None),
( (