Cygwin bash 명령줄의 ASCII가 아닌 경우 오류 발생

Cygwin bash 명령줄의 ASCII가 아닌 경우 오류 발생

cmd.exe에서 bash를 이렇게 호출합니다.

c:\cygwin\bin\bash --login -c "echo ф"

Cygwin 2.8.0을 얻으십시오

/usr/bin/bash: echo ф: command not found

인수를 명령 이름의 일부로 처리합니다. Cygwin 2.5.2에서 동일한 작업을 수행하면 출력이 표시됩니다 ф.

답변1

이것은 예전에는 작동했고 Unices에서 bash를 실행하는 사람들에게는 잘 작동했기 때문에(여기서 Debian에서 테스트했습니다) Cygwin 버그를 발견한 것 같습니다. Cygwin 프로젝트에는 다음과 같은 프로젝트가 있습니다.Cygwin 버그 신고. 여기에는 유용한 정보와 단계가 많이 있으며 여기에 요약하기에는 너무 깁니다.

그동안 캐릭터를 탈출하면 이 문제를 해결할 수 있을 것 같습니다. Bash는 플래그가 echo주어지면 -e다양한 이스케이프 시퀀스를 해석합니다.

c:\cygwin\bin\bash --login -c "echo -e '\xd1\x84'"

작동해야합니다. 16진수 D1 84는 ф의 UTF-8 인코딩입니다. 도구 가 있는 경우 unicode이를 알려 주지만 다음과 같은 문자만 표시 od됩니다 xxd.

$ echo -n 'ф' | od -t x1
0000000 d1 84
0000002

$ echo -n 'ф' | xxd -p
d184

Cygwin FAQ에서는 기본적으로 UTF-8을 사용하므로 제대로 작동한다고 나와 있습니다. 하지만 물론 다른 인코딩을 사용할 수도 있습니다.Windows에서는 주로 UTF16le을 사용합니다.):

$ echo -n 'ф' | iconv -t utf16le | xxd -p
4404

답변2

cmd.exe이는 ASCII가 아닌 문자가 있는 매개변수 주위에 추가 따옴표 쌍이 추가되기 때문에 발생합니다 . 따라서 실제로 cygwin 애플리케이션에 도달하는 내용은 다음과 같습니다.

C:\cygwin\bin\bash --login -c "echo blo"
arg0: /usr/bin/bash
arg1: --login
arg2: -c
arg3: echo blo

따라서 bash는 ' echo blo'를 해석할 수 있지만 다음과 같습니다.

C:\cygwin\bin\bash --login -c "echo blöd"
arg0: /usr/bin/bash
arg1: --login
arg2: -c
arg3: "echo blöd"

이제 bash는 ''을 인식하지 못합니다 "echo blöd".

답변3

사용자 1274247의 분석이 정확합니다.

따라서 cmd.exe가 우리가 모르는 사이에 앞뒤 따옴표를 두 배로 늘릴 때 선행 및 후행 따옴표를 제거하는 방법을 찾아야 합니다.

공백, 작은따옴표 및 ASCII가 아닌 문자가 포함된 경로를 처리할 때도 똑같은 문제가 발생했습니다. 나는 실행할 bash 명령(일명 -c)과 문제의 문자열 인수를 분리하여 이 문제를 해결했습니다.

bash 사람들에 따르면 :

-c string
If the -c option is present, then commands are read from string. If there are arguments after the string, they are assigned to the positional parameters, starting with $0. 

따라서 우리의 명령은 다음과 같습니다:

C:\cygwin\bin\bash.exe -lc 'a="${0%\"}"; a="${a#\"}";echo "$a"; sleep 10' "C:\spa ces\quo'tes\nonàscîï"

또는 mintty 터미널을 사용하려는 경우:

C:\cygwin\bin\mintty.exe /bin/bash -lc 'a="${0%\"}"; a="${a#\"}";echo "$a"; sleep 10' "C:\spa ces\quo'tes\nonàscîï"

regedit(파일을 마우스 오른쪽 버튼으로 클릭하면 실행되는 bash 명령)에서 사용하려는 경우 올바른 이스케이프(따옴표 및 %)는 다음과 같습니다.

Windows Registry Editor Version 5.00

[HKEY_CURRENT_USER\Software\Classes\*\shell\Test]
@="echo filename in bash"

[HKEY_CURRENT_USER\Software\Classes\*\shell\Test\command]
@="C:\\cygwin\\bin\\mintty.exe /bin/bash -lc ' a=\"${0%%\\\"}\"; a=\"${a#\\\"}\";echo \"$a\"; sleep 10 ' \"%1\""

예를 들어, 나는 이것을 사용하여 (더 큰 도구 상자에서 가져온) 파일을 복사합니다.

Windows Registry Editor Version 5.00

[HKEY_CURRENT_USER\Software\Classes\*\shell\Duplicate]
@="Duplicate file"

[HKEY_CURRENT_USER\Software\Classes\*\shell\Duplicate\command]
@="C:\\cygwin\\bin\\mintty.exe /bin/bash -lc ' a=\"${0%%\\\"}\"; a=\"${a#\\\"}\" ; cd \"$(dirname \"$(cygpath \"$a\")\")\"; f=\"$(basename \"$a\")\" ; n=\"$(basename \"$a\" \".${f##*.}\")\" ; cp \"${f}\" \"${n}-copy.${f##*.}\"   ' \"%1\" "

관련 정보