Enable Windows terminal VT output
ci / test (push) Canceled after 0s
ci / fuzz-smoke (push) Canceled after 0s
ci / macos-client (macos-aarch64, macos-14) (push) Canceled after 0s
ci / macos-client (macos-x86_64, macos-13) (push) Canceled after 0s
ci / windows-client (push) Canceled after 0s
ci / package-release (linux-x86_64, ubuntu-latest, , , ) (push) Canceled after 0s
ci / package-release (macos-aarch64, macos-14, , , ) (push) Canceled after 0s
ci / package-release (macos-x86_64, macos-13, , , ) (push) Canceled after 0s
ci / package-release (windows-aarch64, windows-latest, aarch64, windows, aarch64-pc-windows-msvc) (push) Canceled after 0s
ci / package-release (windows-x86_64, windows-latest, , , ) (push) Canceled after 0s
ci / remote-bench (push) Canceled after 0s
ci / publish-gitea-release (push) Canceled after 0s
ci / test (push) Canceled after 0s
ci / fuzz-smoke (push) Canceled after 0s
ci / macos-client (macos-aarch64, macos-14) (push) Canceled after 0s
ci / macos-client (macos-x86_64, macos-13) (push) Canceled after 0s
ci / windows-client (push) Canceled after 0s
ci / package-release (linux-x86_64, ubuntu-latest, , , ) (push) Canceled after 0s
ci / package-release (macos-aarch64, macos-14, , , ) (push) Canceled after 0s
ci / package-release (macos-x86_64, macos-13, , , ) (push) Canceled after 0s
ci / package-release (windows-aarch64, windows-latest, aarch64, windows, aarch64-pc-windows-msvc) (push) Canceled after 0s
ci / package-release (windows-x86_64, windows-latest, , , ) (push) Canceled after 0s
ci / remote-bench (push) Canceled after 0s
ci / publish-gitea-release (push) Canceled after 0s
This commit is contained in:
+68
-3
@@ -10232,15 +10232,71 @@ fn save_cache(path: &std::path::Path, cred: &CachedCredential) -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
struct RawMode;
|
||||
struct RawMode {
|
||||
#[cfg(windows)]
|
||||
console_modes: WindowsConsoleModeGuard,
|
||||
}
|
||||
|
||||
impl RawMode {
|
||||
fn enter() -> Result<Self> {
|
||||
flush_local_terminal_input();
|
||||
enable_raw_mode()?;
|
||||
let raw = Self {
|
||||
#[cfg(windows)]
|
||||
console_modes: WindowsConsoleModeGuard::enter(),
|
||||
};
|
||||
flush_local_terminal_input();
|
||||
drain_local_terminal_input();
|
||||
Ok(Self)
|
||||
Ok(raw)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg_attr(not(any(test, windows)), allow(dead_code))]
|
||||
fn windows_vt_output_mode(mode: u32) -> u32 {
|
||||
const ENABLE_VIRTUAL_TERMINAL_PROCESSING: u32 = 0x0004;
|
||||
mode | ENABLE_VIRTUAL_TERMINAL_PROCESSING
|
||||
}
|
||||
|
||||
#[cfg(windows)]
|
||||
struct WindowsConsoleModeGuard {
|
||||
output: Option<(windows_sys::Win32::Foundation::HANDLE, u32)>,
|
||||
}
|
||||
|
||||
#[cfg(windows)]
|
||||
impl WindowsConsoleModeGuard {
|
||||
fn enter() -> Self {
|
||||
unsafe {
|
||||
use windows_sys::Win32::Foundation::INVALID_HANDLE_VALUE;
|
||||
use windows_sys::Win32::System::Console::{
|
||||
GetConsoleMode, GetStdHandle, STD_OUTPUT_HANDLE, SetConsoleMode,
|
||||
};
|
||||
|
||||
let handle = GetStdHandle(STD_OUTPUT_HANDLE);
|
||||
if handle.is_null() || handle == INVALID_HANDLE_VALUE {
|
||||
return Self { output: None };
|
||||
}
|
||||
let mut original = 0u32;
|
||||
if GetConsoleMode(handle, &mut original) == 0 {
|
||||
return Self { output: None };
|
||||
}
|
||||
let desired = windows_vt_output_mode(original);
|
||||
if desired != original {
|
||||
let _ = SetConsoleMode(handle, desired);
|
||||
}
|
||||
Self {
|
||||
output: Some((handle, original)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn restore(&self) {
|
||||
if let Some((handle, mode)) = self.output {
|
||||
unsafe {
|
||||
use windows_sys::Win32::System::Console::SetConsoleMode;
|
||||
|
||||
let _ = SetConsoleMode(handle, mode);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -10304,6 +10360,8 @@ impl Drop for RawMode {
|
||||
let mut stdout = std::io::stdout();
|
||||
let _ = stdout.write_all(TERMINAL_CLEANUP);
|
||||
let _ = stdout.flush();
|
||||
#[cfg(windows)]
|
||||
self.console_modes.restore();
|
||||
let _ = disable_raw_mode();
|
||||
}
|
||||
}
|
||||
@@ -10369,7 +10427,7 @@ mod tests {
|
||||
vscode_command_candidates, vscode_safe_alias, wake_repaint_retry_deadline,
|
||||
windows_command_word, windows_deferred_update_script, windows_effective_url_script,
|
||||
windows_mode_from_readonly, windows_readonly_from_mode, windows_update_script,
|
||||
windows_url_reachable_script,
|
||||
windows_url_reachable_script, windows_vt_output_mode,
|
||||
};
|
||||
use dosh::config::{ClientConfig, CommandExtension, HostConfig};
|
||||
use dosh::native::EnvVar;
|
||||
@@ -10478,6 +10536,13 @@ mod tests {
|
||||
assert!(!windows_readonly_from_mode(0o755));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn windows_vt_output_mode_enables_ansi_sequences() {
|
||||
assert_eq!(windows_vt_output_mode(0), 0x0004);
|
||||
assert_eq!(windows_vt_output_mode(0x0001), 0x0005);
|
||||
assert_eq!(windows_vt_output_mode(0x0005), 0x0005);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn cleanup_stream_state_removes_all_per_stream_state_only_for_target() {
|
||||
let stream_id = 42;
|
||||
|
||||
Reference in New Issue
Block a user