저는 간단한 쉘 프로그램을 작성하고 있습니다. Mac osx 및 ubuntu의 쉘에서 /usr/bin/which를 사용하면 제대로 작동합니다. Red Hat Enterprise Linux 클라이언트 버전 6.3(San Diego)에서 똑같은 명령을 사용하면 "which: no ANYCOMMANDHERE in ((null))" 오류가 발생합니다.
이것 뒤에 어떤 직관이 있습니까? 오류가 무엇을 의미하는지조차 찾을 수 없습니다(내 소스를 표시하면 도움이 될지 알려주세요).
편집: 내 경로는 (셸 내부에서) 다음과 같습니다.
$ echo $PATH
/usr/lib64/qt-3.3/bin:/usr/local/bin:/bin:/usr/bin
고마워요, 존
답변1
문자열은 해당 인수가 NULL 포인터인 경우 printf의 (문자열) 변환 지정자 (null)
에 대한 인수로 일부 C 라이브러리로 대체됩니다.%s
char *path = 0; /* This would normally be = getenv("PATH"). */
printf ("which: no foobar in (%s)\n", path);
PATH 환경 변수가 설정되지 않았거나 내보내지지 않은 것 같습니다. 이러한 경우에는 getenv("PATH")
0을 반환합니다 . 마지막 가능성은 which
유틸리티에 심각한 버그가 있을 수 있다는 것입니다.
잘 작동한다고 말하면 export PATH
?
답변2
실제로 여기 있는 다른 모든 사람들이 답변한 질문인 PATH가 설정되지 않았습니다. 어떤 면에서는 맞지만 다른 면에서는 잘못되었습니다.
나는 같은 문제가있었습니다 (bash 사용). Bash "기능"이 누락된 기능인 것 같습니다. Bash는 쉘 변수(환경 변수가 아님!) PATH를 생성한 다음 조회에 사용합니다.
문제는 다음과 같습니다. PATH라는 쉘 변수가 있습니다. 그러나 이것은 환경 변수가 아닙니다. 이는 새로 생성된 하위 프로세스로 내보내지지 않음을 의미합니다. 여기서 우리가 배워야 할 한 가지는 echo $PATH를 사용하면환경변수 PATH가 설정되었습니다. set | grep "^PATH="와 동일한 문제가 있지만 한 가지 방법은 다음을 사용하는 것입니다.외부명령 환경: grep "^path="
셸 세션 예:
$ env -i bash
# A new shell is started with empty environment.
# What follows happens in this new shell:
$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
$ set | grep "^PATH="
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
$ env | grep "^PATH="
$ which ls
which: no ls in ((null))
$ export PATH
$ env | grep "^PATH="
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
$ which ls
/bin/ls
달성하려는 목표에 따라 쉘에 로그인 쉘 역할을 하도록 요청할 수 있습니다. bash의 경우 -l입니다. 이런 식으로 /etc/profile 및 기타 파일은 기본적으로 PATH를 올바르게 설정하는 소스입니다.
$ env -i bash -l
$ which ls
/bin/ls
또 다른 방법은 PATH를 내보내는 것입니다(위 참조).
답변3
tcsh에서 동일한 출력을 재현할 수 있습니다.
env -u PATH which ls
which: no ls in ((null))
csh와 tcsh에서는 환경 변수(모든 프로세스에 공통)와 쉘 변수(현재 쉘 호출에 로컬)가 구별됩니다. 두 가지를 모두 참조하기 위해 동일한 구문을 사용합니다(예: ) $PATH
. 동일한 이름의 쉘 변수와 환경 변수가 있는 경우 $PATH
쉘 변수가 인용됩니다.
[t]csh는 다른 구문을 사용하여놓다쉘 및 환경 변수:
set shell_var = foo
setenv env_var bar
(Bash와 같은 Bourne 기반 쉘은 구문과 용어가 다릅니다. 환경 변수는 "내보낸" 쉘 변수이거나 호출 프로세스에서 상속된 쉘 변수입니다.)
설명하는 증상에 따르면 쉘 변수 $PATH
(쓸모 없음)는 있지만 이름이 같은 환경 변수는 없습니다. 이런 일은 일반적으로 일어나서는 안 됩니다. .cshrc
및 .tcshrc
/또는 파일 .login
에 설정된 명령문을 확인하세요 $PATH
.
다음과 같이 당면한 문제를 해결할 수 있어야 합니다.
setenv PATH "$PATH" # set the environment variable
unset PATH # unset the shell variable, just to avoid confusion
unset PATH
(모든 것이 제대로 작동하는지 확인할 때까지 이 작업을 수행하지 마십시오.)
약간의 재미를 더하기 위해 [t]csh에는 특별한 기능이 있습니다.껍데기변수 $path
(소문자 참고). 해당 값은 환경 변수 :
의 구분된 구성 요소 배열 입니다 $PATH
. 하나를 설정하면 다른 하나가 자동으로 업데이트됩니다.
setenv PATH /usr/bin:/bin # sets $path to ( /usr/bin /bin )
set path = ( /usr/local/bin $path ) # sets $PATH to '/usr/local/bin:/usr/bin:/bin'
이는 편리할 수 있지만 원하는 경우 무시 $path
하고 처리 할 수 있습니다. 동일한 이름의 쓸모 없는 쉘 변수가 아닌 환경 변수 ( 를 사용하여 ) $PATH
를 설정했는지 확인하십시오 .$PATH
setenv
답변4
이 문제는 Redhat 및 포크 메커니즘에만 해당되는 것으로 나타났습니다. 하위 프로세스에는 ubuntu 및 mac osx와 마찬가지로 기본 환경 변수가 제공되지 않습니다. 이는 명시적으로 envp를 부모의 envp로 설정해야 함을 의미합니다(execve 호출에서).
내 질문에 오해의 소지가 있는 표현에 대해 사과드립니다(비록 이러한 유형의 것들을 정확히 찾아내기는 어렵지만).
당신의 도움을 주셔서 감사합니다! 존