-
Notifications
You must be signed in to change notification settings - Fork 8.1k
Description
-
On Windows, PowerShell terminates strings sent via the pipeline to native programs with an implicit trailing CRLF.
-
If WSL (
wsl.exe) happens to be targeted, the ultimately invoked Unix utility usually only expects LF newlines, retaining the CR instances as part of the data, causing problems, as shown in theawkexample below.
Note:
-
I'm not sure where the proper place to resolve this is. Arguably, it is
wsl.exe(andbash.exe) that should translate CRLF sequences to LF sequences before processing stdin input, but that should only be done for text input, and it is only the calling shell that knows whether data is textual or not (if PowerShell is the calling shell, the input is always text, but that's not necessarily always true). -
A simple way to solve the problem is to make PowerShell always send stdin input with LF-only newlines (
"`n"), under the assumption that even native Windows programs recognize such newline sequences; while technically a breaking change, it may be a Bucket 3: Unlikely Grey Area change, and therefore acceptable.
Steps to reproduce
On Windows, with WSL and an Ubuntu distro as the default:
The following should output two one - a single line.
'one two' | wsl -e awk '{ print $2, $1 }' | should -be 'two one'Expected behavior
The test should pass.
Actual behavior
Expected 'two one', but got @('two', ' one').
What the output doesn't directly show is the root cause of the problem: two is actually two`r (verbatim two followed by a CR in the raw output, which awk retained as part of field $2 due to not considering CRs part of newlines), due to the input line using CRLF as the trailing newline.
Since PowerShell recognizes a CR by itself as a newline too, the output is parsed as two lines.
Environment data
PowerShell Core 7.1.0-preview.6