Adds show_desktop_wallpaper flag, disables Windows wallpaper by default (#19541)

This commit is contained in:
Isaiah Becker-Mayer 2023-01-06 09:26:15 -08:00 committed by GitHub
parent 54b8fce42b
commit f30e5c970c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
11 changed files with 119 additions and 93 deletions

92
Cargo.lock generated
View file

@ -202,9 +202,9 @@ dependencies = [
[[package]]
name = "cc"
version = "1.0.77"
version = "1.0.78"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e9f73505338f7d905b19d18738976aae232eb46b8efc15554ffc56deb5d9ebe4"
checksum = "a20104e2335ce8a659d6dd92a51a767a0c062599c73b343fd152cb401e828c3d"
[[package]]
name = "cexpr"
@ -325,9 +325,9 @@ dependencies = [
[[package]]
name = "data-encoding"
version = "2.3.2"
version = "2.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3ee2393c4a91429dffb4bedf19f4d6abf27d8a732c8ce4980305d782e5426d57"
checksum = "23d8666cb01533c39dde32bcbab8e227b4ed6679b2c925eba05feabea39508fb"
[[package]]
name = "delog"
@ -351,9 +351,9 @@ dependencies = [
[[package]]
name = "der"
version = "0.6.0"
version = "0.6.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "13dd2ae565c0a381dde7fade45fce95984c568bdcb4700a4fdbe3175e0380b2f"
checksum = "f1a467a65c5e759bce6e65eaf91cc29f466cdc57cb65777bd646872a8a1fd4de"
dependencies = [
"const-oid 0.9.1",
"pem-rfc7468 0.6.0",
@ -656,9 +656,9 @@ dependencies = [
[[package]]
name = "is-terminal"
version = "0.4.1"
version = "0.4.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "927609f78c2913a6f6ac3c27a4fe87f43e2a35367c0c4b0f8265e8f49a104330"
checksum = "28dfb6c8100ccc63462345b67d1bbc3679177c75ee4bf59bf29c8b1d110b8189"
dependencies = [
"hermit-abi 0.2.6",
"io-lifetimes",
@ -687,9 +687,9 @@ dependencies = [
[[package]]
name = "itoa"
version = "1.0.4"
version = "1.0.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4217ad341ebadf8d8e724e264f13e593e0648f5b3e94b3896a5df283be015ecc"
checksum = "fad582f4b9e86b6caa621cabeb0963332d92eea04729ab12892c2533951e6440"
[[package]]
name = "js-sys"
@ -739,9 +739,9 @@ checksum = "348108ab3fba42ec82ff6e9564fc4ca0247bdccdc68dd8af9764bbc79c3c8ffb"
[[package]]
name = "linux-raw-sys"
version = "0.1.3"
version = "0.1.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f9f08d8963a6c613f4b1a78f4f4a4dbfadf8e6545b2d72861731e4858b8b47f"
checksum = "f051f77a7c8e6957c0696eac88f26b0117e54f52d3fc682ab19397a8812846a4"
[[package]]
name = "lock_api"
@ -912,9 +912,9 @@ dependencies = [
[[package]]
name = "oid-registry"
version = "0.6.0"
version = "0.6.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7d4bda43fd1b844cbc6e6e54b5444e2b1bc7838bce59ad205902cccbb26d6761"
checksum = "9bedf36ffb6ba96c2eb7144ef6270557b52e54b20c0a8e1eb2ff99a6c6959bff"
dependencies = [
"asn1-rs",
]
@ -978,7 +978,7 @@ version = "0.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "eff33bdbdfc54cc98a2eca766ebdec3e1b8fb7387523d5c9c9a2891da856f719"
dependencies = [
"der 0.6.0",
"der 0.6.1",
"pkcs8 0.9.0",
"spki 0.6.0",
"zeroize",
@ -1001,7 +1001,7 @@ version = "0.9.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9eca2c590a5f85da82668fa685c09ce2888b9430e83299debf1f34b65fd4a4ba"
dependencies = [
"der 0.6.0",
"der 0.6.1",
"spki 0.6.0",
]
@ -1022,18 +1022,18 @@ dependencies = [
[[package]]
name = "proc-macro2"
version = "1.0.47"
version = "1.0.49"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5ea3d908b0e36316caf9e9e2c4625cdde190a7e6f440d794667ed17a1855e725"
checksum = "57a8eca9f9c4ffde41714334dee777596264c7825420f521abc92b5b5deb63a5"
dependencies = [
"unicode-ident",
]
[[package]]
name = "quote"
version = "1.0.21"
version = "1.0.23"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bbe448f377a7d6961e30f5955f9b8d106c3f5e449d493ee1b125c1d43c2b5179"
checksum = "8856d8364d252a14d474036ea1358d63c9e6965c8e5c1885c18f73d70bff9c7b"
dependencies = [
"proc-macro2",
]
@ -1144,7 +1144,7 @@ dependencies = [
[[package]]
name = "rdp-rs"
version = "0.1.0"
source = "git+https://github.com/gravitational/rdp-rs?rev=8f9f2ab4835f3e52cc9d1771114cc745f3c02759#8f9f2ab4835f3e52cc9d1771114cc745f3c02759"
source = "git+https://github.com/gravitational/rdp-rs?rev=75eb6a30b83e7152ee6213964b5ac6e783304840#75eb6a30b83e7152ee6213964b5ac6e783304840"
dependencies = [
"boring",
"bufstream",
@ -1283,9 +1283,9 @@ dependencies = [
[[package]]
name = "rustix"
version = "0.36.4"
version = "0.36.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cb93e85278e08bb5788653183213d3a60fc242b10cb9be96586f5a73dcb67c23"
checksum = "a3807b5d10909833d3e9acd1eb5fb988f79376ff10fce42937de71a449c4c588"
dependencies = [
"bitflags",
"errno",
@ -1309,9 +1309,9 @@ dependencies = [
[[package]]
name = "ryu"
version = "1.0.11"
version = "1.0.12"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4501abdff3ae82a1c1b477a17252eb69cee9e66eb915c1abaa4f44d873df9f09"
checksum = "7b4b9743ed687d4b4bcedf9ff5eaa7398495ae14e61cba0a295704edbc7decde"
[[package]]
name = "scopeguard"
@ -1331,24 +1331,24 @@ dependencies = [
[[package]]
name = "semver"
version = "1.0.14"
version = "1.0.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e25dfac463d778e353db5be2449d1cce89bd6fd23c9f1ea21310ce6e5a1b29c4"
checksum = "58bc9567378fc7690d6b2addae4e60ac2eeea07becb2c64b9f218b53865cba2a"
[[package]]
name = "serde"
version = "1.0.148"
version = "1.0.151"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e53f64bb4ba0191d6d0676e1b141ca55047d83b74f5607e6d8eb88126c52c2dc"
checksum = "97fed41fc1a24994d044e6db6935e69511a1153b52c15eb42493b26fa87feba0"
dependencies = [
"serde_derive",
]
[[package]]
name = "serde_derive"
version = "1.0.148"
version = "1.0.151"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a55492425aa53521babf6137309e7d34c20bbfbbfcfe2c7f3a047fd1f6b92c0c"
checksum = "255abe9a125a985c05190d687b320c12f9b1f0b99445e608c21ba0782c719ad8"
dependencies = [
"proc-macro2",
"quote",
@ -1357,9 +1357,9 @@ dependencies = [
[[package]]
name = "serde_json"
version = "1.0.89"
version = "1.0.91"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "020ff22c755c2ed3f8cf162dbb41a7268d934702f3ed3631656ea597e08fc3db"
checksum = "877c235533714907a8c2464236f5c4b2a17262ef1bd71f38f35ea592c8da6883"
dependencies = [
"itoa",
"ryu",
@ -1420,7 +1420,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "67cf02bbac7a337dc36e4f5a693db6c21e7863f45070f7064577eb4367a3212b"
dependencies = [
"base64ct",
"der 0.6.0",
"der 0.6.1",
]
[[package]]
@ -1449,9 +1449,9 @@ checksum = "6bdef32e8150c2a081110b42772ffe7d7c9032b606bc226c8260fd97e0976601"
[[package]]
name = "syn"
version = "1.0.104"
version = "1.0.107"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4ae548ec36cf198c0ef7710d3c230987c2d6d7bd98ad6edc0274462724c585ce"
checksum = "1f4064b5b16e03ae50984a5a8ed5d4f8803e6bc1fd170a3cda91a1be4b18e3f5"
dependencies = [
"proc-macro2",
"quote",
@ -1501,18 +1501,18 @@ checksum = "222a222a5bfe1bba4a77b45ec488a741b3cb8872e5e499451fd7d0129c9c7c3d"
[[package]]
name = "thiserror"
version = "1.0.37"
version = "1.0.38"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "10deb33631e3c9018b9baf9dcbbc4f737320d2b576bac10f6aefa048fa407e3e"
checksum = "6a9cd18aa97d5c45c6603caea1da6628790b37f7a34b6ca89522331c5180fed0"
dependencies = [
"thiserror-impl",
]
[[package]]
name = "thiserror-impl"
version = "1.0.37"
version = "1.0.38"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "982d17546b47146b28f7c22e3d08465f6b8903d0ea13c1660d9d84a6e7adcdbb"
checksum = "1fb327af4685e4d03fa8cbcf1716380da910eeb2bb8be417e7f9fd3fb164f36f"
dependencies = [
"proc-macro2",
"quote",
@ -1548,24 +1548,24 @@ dependencies = [
[[package]]
name = "toml"
version = "0.5.9"
version = "0.5.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8d82e1a7758622a465f8cee077614c73484dac5b836c02ff6a40d5d1010324d7"
checksum = "1333c76748e868a4d9d1017b5ab53171dfd095f70c712fdb4653a406547f598f"
dependencies = [
"serde",
]
[[package]]
name = "typenum"
version = "1.15.0"
version = "1.16.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dcf81ac59edc17cc8697ff311e8f5ef2d99fcbd9817b34cec66f90b6c3dfd987"
checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba"
[[package]]
name = "unicode-ident"
version = "1.0.5"
version = "1.0.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6ceab39d59e4c9499d4e5a8ee0e2735b891bb7308ac83dfb4e80cad195c9f6f3"
checksum = "84a22b9f218b40614adcb3f4ff08b703773ad44fa9423e4e0d346d5db86e4ebc"
[[package]]
name = "unicode-xid"

View file

@ -7,6 +7,10 @@ windows_desktop_service:
# connect to windows_desktop_service, users connect to the proxy's web UI
# instead.
public_addr: "desktop-access.example.com:3028"
# (optional) Determines whether desktop sessions will show a user-selected wallpaper
# vs a system-default, single-color wallpaper. For improved visual performance,
# set this to false (its default value).
show_desktop_wallpaper: false
ldap:
# Address of the LDAP server for secure LDAP connections.
# Usually, this address will use port 636, like: ldap.example.com:636.

View file

@ -1574,6 +1574,7 @@ func applyWindowsDesktopConfig(fc *FileConfig, cfg *service.Config) error {
if err != nil {
return trace.Wrap(err)
}
cfg.WindowsDesktop.ShowDesktopWallpaper = fc.WindowsDesktop.ShowDesktopWallpaper
cfg.WindowsDesktop.Hosts, err = utils.AddrsFromStrings(fc.WindowsDesktop.Hosts, defaults.RDPListenPort)
if err != nil {
return trace.Wrap(err)

View file

@ -1928,6 +1928,9 @@ type WindowsDesktopService struct {
Labels map[string]string `yaml:"labels,omitempty"`
// PublicAddr is a list of advertised public addresses of this service.
PublicAddr apiutils.Strings `yaml:"public_addr,omitempty"`
// ShowDesktopWallpaper determines whether desktop sessions will show a
// user-selected wallpaper vs a system-default, single-color wallpaper.
ShowDesktopWallpaper bool `yaml:"show_desktop_wallpaper,omitempty"`
// LDAP is the LDAP connection parameters.
LDAP LDAPConfig `yaml:"ldap"`
// Discovery configures desktop discovery via LDAP.

View file

@ -1283,6 +1283,9 @@ type WindowsDesktopConfig struct {
ListenAddr utils.NetAddr
// PublicAddrs is a list of advertised public addresses of the service.
PublicAddrs []utils.NetAddr
// ShowDesktopWallpaper determines whether desktop sessions will show a
// user-selected wallpaper vs a system-default, single-color wallpaper.
ShowDesktopWallpaper bool
// LDAP is the LDAP connection parameters.
LDAP LDAPConfig

View file

@ -221,6 +221,7 @@ func (process *TeleportProcess) initWindowsDesktopServiceRegistered(log *logrus.
StaticHosts: cfg.WindowsDesktop.Hosts,
OnHeartbeat: process.onHeartbeat(teleport.ComponentWindowsDesktop),
},
ShowDesktopWallpaper: cfg.WindowsDesktop.ShowDesktopWallpaper,
LDAPConfig: windows.LDAPConfig(cfg.WindowsDesktop.LDAP),
DiscoveryBaseDN: cfg.WindowsDesktop.Discovery.BaseDN,
DiscoveryLDAPFilters: cfg.WindowsDesktop.Discovery.Filters,

View file

@ -20,7 +20,7 @@ num-traits = "0.2.15"
rand = { version = "0.8.5", features = ["getrandom"] }
rand_chacha = "0.3.1"
rsa = "0.7.2"
rdp-rs = { git = "https://github.com/gravitational/rdp-rs", rev = "8f9f2ab4835f3e52cc9d1771114cc745f3c02759" }
rdp-rs = { git = "https://github.com/gravitational/rdp-rs", rev = "75eb6a30b83e7152ee6213964b5ac6e783304840" }
uuid = { version = "1.2.2", features = ["v4"] }
utf16string = "0.2.0"

View file

@ -241,19 +241,21 @@ func (c *Client) connect(ctx context.Context) error {
res := C.connect_rdp(
C.uintptr_t(c.handle),
addr,
username,
// cert length and bytes.
C.uint32_t(len(userCertDER)),
(*C.uint8_t)(unsafe.Pointer(&userCertDER[0])),
// key length and bytes.
C.uint32_t(len(userKeyDER)),
(*C.uint8_t)(unsafe.Pointer(&userKeyDER[0])),
// screen size.
C.uint16_t(c.clientWidth),
C.uint16_t(c.clientHeight),
C.bool(c.cfg.AllowClipboard),
C.bool(c.cfg.AllowDirectorySharing),
C.CGOConnectParams{
go_addr: addr,
go_username: username,
// cert length and bytes.
cert_der_len: C.uint32_t(len(userCertDER)),
cert_der: (*C.uint8_t)(unsafe.Pointer(&userCertDER[0])),
// key length and bytes.
key_der_len: C.uint32_t(len(userKeyDER)),
key_der: (*C.uint8_t)(unsafe.Pointer(&userKeyDER[0])),
screen_width: C.uint16_t(c.clientWidth),
screen_height: C.uint16_t(c.clientHeight),
allow_clipboard: C.bool(c.cfg.AllowClipboard),
allow_directory_sharing: C.bool(c.cfg.AllowDirectorySharing),
show_desktop_wallpaper: C.bool(c.cfg.ShowDesktopWallpaper),
},
)
if res.err != C.ErrCodeSuccess {
return trace.ConnectionProblem(nil, "RDP connection failed")

View file

@ -54,6 +54,10 @@ type Config struct {
// directory sharing.
AllowDirectorySharing bool
// ShowDesktopWallpaper determines whether desktop sessions will show a
// user-selected wallpaper vs a system-default, single-color wallpaper.
ShowDesktopWallpaper bool
// Log is the logger for status messages.
Log logrus.FieldLogger
}

View file

@ -176,36 +176,25 @@ impl From<Result<Client, ConnectError>> for ClientOrError {
/// The caller mmust ensure that go_addr, go_username, cert_der, key_der point to valid buffers in respect
/// to their corresponding parameters.
#[no_mangle]
pub unsafe extern "C" fn connect_rdp(
go_ref: usize,
go_addr: *const c_char,
go_username: *const c_char,
cert_der_len: u32,
cert_der: *mut u8,
key_der_len: u32,
key_der: *mut u8,
screen_width: u16,
screen_height: u16,
allow_clipboard: bool,
allow_directory_sharing: bool,
) -> ClientOrError {
pub unsafe extern "C" fn connect_rdp(go_ref: usize, params: CGOConnectParams) -> ClientOrError {
// Convert from C to Rust types.
let addr = from_c_string(go_addr);
let username = from_c_string(go_username);
let cert_der = from_go_array(cert_der, cert_der_len);
let key_der = from_go_array(key_der, key_der_len);
let addr = from_c_string(params.go_addr);
let username = from_c_string(params.go_username);
let cert_der = from_go_array(params.cert_der, params.cert_der_len);
let key_der = from_go_array(params.key_der, params.key_der_len);
connect_rdp_inner(
go_ref,
&addr,
ConnectParams {
addr,
username,
cert_der,
key_der,
screen_width,
screen_height,
allow_clipboard,
allow_directory_sharing,
screen_width: params.screen_width,
screen_height: params.screen_height,
allow_clipboard: params.allow_clipboard,
allow_directory_sharing: params.allow_directory_sharing,
show_desktop_wallpaper: params.show_desktop_wallpaper,
},
)
.into()
@ -234,7 +223,23 @@ const RDP_CONNECT_TIMEOUT: time::Duration = time::Duration::from_secs(5);
const RDP_HANDSHAKE_TIMEOUT: time::Duration = time::Duration::from_secs(10);
const RDPSND_CHANNEL_NAME: &str = "rdpsnd";
#[repr(C)]
pub struct CGOConnectParams {
go_addr: *const c_char,
go_username: *const c_char,
cert_der_len: u32,
cert_der: *mut u8,
key_der_len: u32,
key_der: *mut u8,
screen_width: u16,
screen_height: u16,
allow_clipboard: bool,
allow_directory_sharing: bool,
show_desktop_wallpaper: bool,
}
struct ConnectParams {
addr: String,
username: String,
cert_der: Vec<u8>,
key_der: Vec<u8>,
@ -242,15 +247,13 @@ struct ConnectParams {
screen_height: u16,
allow_clipboard: bool,
allow_directory_sharing: bool,
show_desktop_wallpaper: bool,
}
fn connect_rdp_inner(
go_ref: usize,
addr: &str,
params: ConnectParams,
) -> Result<Client, ConnectError> {
fn connect_rdp_inner(go_ref: usize, params: ConnectParams) -> Result<Client, ConnectError> {
// Connect and authenticate.
let addr = addr
let addr = params
.addr
.to_socket_addrs()?
.next()
.ok_or(ConnectError::InvalidAddr())?;
@ -291,6 +294,11 @@ fn connect_rdp_inner(
// Generate a random 8-digit PIN for our smartcard.
let mut rng = rand_chacha::ChaCha20Rng::from_entropy();
let pin = format!("{:08}", rng.gen_range(0i32..=99999999i32));
let mut performance_flags = sec::ExtendedInfoFlag::PerfDisableFullWindowDrag as u32
| sec::ExtendedInfoFlag::PerfDisableMenuAnimations as u32;
if !params.show_desktop_wallpaper {
performance_flags |= sec::ExtendedInfoFlag::PerfDisableWallpaper as u32;
}
sec::connect(
&mut mcs,
&domain.to_string(),
@ -300,11 +308,7 @@ fn connect_rdp_inner(
// InfoPasswordIsScPin means that the user will not be prompted for the smartcard PIN code,
// which is known only to Teleport and unique for each RDP session.
Some(sec::InfoFlag::InfoPasswordIsScPin as u32 | sec::InfoFlag::InfoMouseHasWheel as u32),
Some(
sec::ExtendedInfoFlag::PerfDisableCursorBlink as u32
| sec::ExtendedInfoFlag::PerfDisableFullWindowDrag as u32
| sec::ExtendedInfoFlag::PerfDisableMenuAnimations as u32,
),
Some(performance_flags),
)?;
// Client for the "global" channel - video output and user input.
let global = global::Client::new(

View file

@ -161,6 +161,9 @@ type WindowsServiceConfig struct {
Heartbeat HeartbeatConfig
// HostLabelsFn gets labels that should be applied to a Windows host.
HostLabelsFn func(host string) map[string]string
// ShowDesktopWallpaper determines whether desktop sessions will show a
// user-selected wallpaper vs a system-default, single-color wallpaper.
ShowDesktopWallpaper bool
// LDAPConfig contains parameters for connecting to an LDAP server.
windows.LDAPConfig
// DiscoveryBaseDN is the base DN for searching for Windows Desktops.
@ -809,6 +812,7 @@ func (s *WindowsService) connectRDP(ctx context.Context, log logrus.FieldLogger,
AuthorizeFn: authorize,
AllowClipboard: authCtx.Checker.DesktopClipboard(),
AllowDirectorySharing: authCtx.Checker.DesktopDirectorySharing(),
ShowDesktopWallpaper: s.cfg.ShowDesktopWallpaper,
})
if err != nil {
s.onSessionStart(ctx, sw, &identity, sessionStartTime, windowsUser, string(sessionID), desktop, err)