diff options
author | Roy Ivy III <rivy.dev@gmail.com> | 2020-05-27 21:58:28 -0500 |
---|---|---|
committer | David Peter <sharkdp@users.noreply.github.com> | 2020-06-03 09:13:47 +0200 |
commit | a2c09b41bc2e6a586310fd72d76ca1d14f95fbeb (patch) | |
tree | 894c2cb6213546475270a32e2bae86efa250a90a /src | |
parent | 0ef792ac1e127dcf919e77908035faf63616352b (diff) |
Fix pager process execution under 'windows'
## [why]
For 'windows' platforms, directly spawning a process (eg, called PATHNAME) bypasses the
usual windows shell machinery for determining which process to execute. Specifically,
the extensions in PATHEXT will not be used to determine the final executable. So,
`PATHNAME.bat`, `PATHNAME.cmd`, ... will *not* be executed even if on they exist on the
PATH; and this is counter to the usual expectation of a Windows user. Additionally,
built-in commands, such as `echo` and `dir`, will never be accessible as they do not
have a PATH to execute and, so, will never be found.
To use the usual machinery, giving access to PATHNAME.bat and `echo`, execute the PATHNAME
using the windows shell, eg `cmd /d/c PATHNAME`. Note this may expose the constructed
command line to the windows shell quoting vagaries (sadly, that may be part of the price).
Following Windows standards, the ComSpec environment variable is used to determine which
shell to use, with a fallback to the "modern", built-in `cmd` shell.
Diffstat (limited to 'src')
-rw-r--r-- | src/output.rs | 13 |
1 files changed, 11 insertions, 2 deletions
diff --git a/src/output.rs b/src/output.rs index e7d59d67..31b2994a 100644 --- a/src/output.rs +++ b/src/output.rs @@ -74,8 +74,18 @@ impl OutputType { let is_less = pager_path.file_stem() == Some(&OsString::from("less")); + #[cfg(windows)] + let (pager_path, args) = { + let p = std::env::var("ComSpec").unwrap_or_else(|_| "cmd".to_string()); + let mut a = args.to_vec(); + a.insert(0, pager_path.to_str().unwrap().to_string()); + a.insert(0, "/d/c".to_string()); + (p, a) + }; + + let mut p = Command::new(&pager_path); + let mut process = if is_less { - let mut p = Command::new(&pager_path); if args.is_empty() || replace_arguments_to_less { p.arg("--RAW-CONTROL-CHARS"); if quit_if_one_screen { @@ -106,7 +116,6 @@ impl OutputType { p.env("LESSCHARSET", "UTF-8"); p } else { - let mut p = Command::new(&pager_path); p.args(args); p }; |