Skip to content

Commit 7837029

Browse files
elmarcoCBenoit
authored andcommitted
feat(session): make client_codecs_capabilities() configurable
Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
1 parent 0817d60 commit 7837029

File tree

5 files changed

+99
-16
lines changed

5 files changed

+99
-16
lines changed

crates/ironrdp-client/src/config.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -271,7 +271,7 @@ impl Config {
271271
Some(connector::BitmapConfig {
272272
color_depth,
273273
lossy_compression: true,
274-
codecs: client_codecs_capabilities(),
274+
codecs: client_codecs_capabilities(&[]).unwrap(),
275275
})
276276
} else {
277277
None

crates/ironrdp-connector/src/connection_activation.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -360,7 +360,7 @@ fn create_client_confirm_active(
360360
.bitmap
361361
.as_ref()
362362
.map(|b| b.codecs.clone())
363-
.unwrap_or_else(client_codecs_capabilities),
363+
.unwrap_or_else(|| client_codecs_capabilities(&[]).unwrap()),
364364
),
365365
CapabilitySet::FrameAcknowledge(FrameAcknowledge {
366366
// FIXME(#447): Revert this to 2 per FreeRDP.

crates/ironrdp-pdu/src/rdp/capability_sets/bitmap_codecs.rs

Lines changed: 73 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -641,17 +641,77 @@ impl CodecId {
641641
}
642642
}
643643

644-
pub fn client_codecs_capabilities() -> BitmapCodecs {
645-
let codecs = vec![Codec {
646-
id: CODEC_ID_REMOTEFX.0,
647-
property: CodecProperty::RemoteFx(RemoteFxContainer::ClientContainer(RfxClientCapsContainer {
648-
capture_flags: CaptureFlags::empty(),
649-
caps_data: RfxCaps(RfxCapset(vec![RfxICap {
650-
flags: RfxICapFlags::empty(),
651-
entropy_bits: EntropyBits::Rlgr3,
652-
}])),
653-
})),
654-
}];
655-
656-
BitmapCodecs(codecs)
644+
/// This function generates a list of client codec capabilities based on the
645+
/// provided configuration.
646+
///
647+
/// # Arguments
648+
///
649+
/// * `config` - A slice of string slices that specifies which codecs to include
650+
/// in the capabilities. Codecs can be explicitly turned on ("codec:on") or
651+
/// off ("codec:off").
652+
///
653+
/// # List of codecs
654+
///
655+
/// * `remotefx` (on by default)
656+
///
657+
/// # Returns
658+
///
659+
/// A vector of `Codec` structs representing the codec capabilities, or an error
660+
/// suitable for CLI.
661+
pub fn client_codecs_capabilities(config: &[&str]) -> Result<BitmapCodecs, String> {
662+
use std::collections::HashMap;
663+
664+
fn parse_codecs_config<'a>(codecs: &'a [&'a str]) -> Result<HashMap<&'a str, bool>, String> {
665+
let mut result = HashMap::new();
666+
667+
for &codec_str in codecs {
668+
if let Some(colon_index) = codec_str.find(':') {
669+
let codec_name = &codec_str[0..colon_index];
670+
let state_str = &codec_str[colon_index + 1..];
671+
672+
let state = match state_str {
673+
"on" => true,
674+
"off" => false,
675+
_ => return Err(format!("Unhandled configuration: {}", state_str)),
676+
};
677+
678+
result.insert(codec_name, state);
679+
} else {
680+
// No colon found, assume it's "on"
681+
result.insert(codec_str, true);
682+
}
683+
}
684+
685+
Ok(result)
686+
}
687+
688+
if config.contains(&"help") {
689+
return Err(r#"
690+
List of codecs:
691+
- `remotefx` (on by default)
692+
"#
693+
.to_owned());
694+
}
695+
let mut config = parse_codecs_config(config)?;
696+
let mut codecs = vec![];
697+
698+
if config.remove("remotefx").unwrap_or(true) {
699+
codecs.push(Codec {
700+
id: CODEC_ID_REMOTEFX.0,
701+
property: CodecProperty::RemoteFx(RemoteFxContainer::ClientContainer(RfxClientCapsContainer {
702+
capture_flags: CaptureFlags::empty(),
703+
caps_data: RfxCaps(RfxCapset(vec![RfxICap {
704+
flags: RfxICapFlags::empty(),
705+
entropy_bits: EntropyBits::Rlgr3,
706+
}])),
707+
})),
708+
});
709+
}
710+
711+
let codec_names = config.keys().copied().collect::<Vec<_>>().join(", ");
712+
if !codec_names.is_empty() {
713+
return Err(format!("Unknown codecs: {}", codec_names));
714+
}
715+
716+
Ok(BitmapCodecs(codecs))
657717
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,24 @@
11
mod rfx;
2+
3+
#[cfg(test)]
4+
mod tests {
5+
use ironrdp_pdu::rdp::capability_sets::{client_codecs_capabilities, CodecProperty};
6+
7+
#[test]
8+
fn test_codecs_capabilities() {
9+
let config = &[];
10+
let _capabilities = client_codecs_capabilities(config).unwrap();
11+
12+
let config = &["badcodec"];
13+
assert!(client_codecs_capabilities(config).is_err());
14+
15+
let config = &["remotefx:on"];
16+
let capabilities = client_codecs_capabilities(config).unwrap();
17+
assert_eq!(capabilities.0.len(), 1);
18+
assert!(matches!(capabilities.0[0].property, CodecProperty::RemoteFx(_)));
19+
20+
let config = &["remotefx:off"];
21+
let capabilities = client_codecs_capabilities(config).unwrap();
22+
assert_eq!(capabilities.0.len(), 0);
23+
}
24+
}

crates/ironrdp-web/src/session.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -839,7 +839,7 @@ fn build_config(
839839
bitmap: Some(connector::BitmapConfig {
840840
color_depth: 16,
841841
lossy_compression: true,
842-
codecs: client_codecs_capabilities(),
842+
codecs: client_codecs_capabilities(&[]).unwrap(),
843843
}),
844844
#[allow(clippy::arithmetic_side_effects)] // fine unless we end up with an insanely big version
845845
client_build: semver::Version::parse(env!("CARGO_PKG_VERSION"))

0 commit comments

Comments
 (0)