AIX 6.1에서 AIX 7.1로 마이그레이션하는 ksh93 스크립트가 있습니다.
7.1에서는 실패했지만 6.1에서는 잘 작동합니다. 다음은 중요한 부분의 일부입니다.
integer f_count=0
. . .
. . .
. . .
if [[ ($f_count*$sleep_interval%$alarm_interval -eq 0 ) && $f_count > 0 ]]
then
"if"에 도달하면
191행: *10%300: 산술 구문 오류
나는 이것을 명령 프롬프트에 입력하여 단순화하기로 결정했습니다.
AIX 7.1> integer x=1
AIX 7.1> [[ $x*10%300 -eq 0 ]]
AIX 7.1> print $?
1
AIX 7.1> integer x=0
AIX 7.1> [[ $x*10%300 -eq 0 ]]
-ksh93: *10%300: arithmetic syntax error
AIX 6.1> integer x=1
AIX 6.1> [[ $x*10%300 -eq 0 ]]
AIX 6.1> print $?
1
AIX 6.1> integer x=0
AIX 6.1> [[ $x*10%300 -eq 0 ]]
AIX 6.1> print $?
0
AIX 6.1에서 ksh93임을 보여주기 위해 이렇게 했습니다.
asdlkfjasd
-ksh93: asdlkfjasd: not found.
0 값을 이동하여 첫 번째 값이 아닌 경우 예상대로 작동합니다.
AIX 7.1> integer x=1
AIX 7.1> [[ 10*$x%300 -eq 0 ]]
AIX 7.1> print $?
1
AIX 7.1> integer x=0
AIX 7.1> [[ 10*$x%300 -eq 0 ]]
AIX 7.1> print $?
0
원래 방정식의 두 번째와 세 번째 변수는 결코 0이 될 수 없다는 것을 알고 있으므로 이렇게 하면 문제가 해결됩니다.
AIX 7.1 버그가 표시됩니까?
답변1
ksh93에서 버그를 발견한 것 같습니다.
다음 명령을 사용하여 이를 재현할 수 있습니다(ksh93u+).
$ x= ksh -c '[[ 0*1 -eq 5 ]]'
ksh: *1: arithmetic syntax error
그것은 중요하지 않습니다:
ksh -c '[[ " 0*1" -eq 5 ]]'
하지만. ksh93v-
(베타)에서는 재현할 수 없어서 수정 된 것 같습니다 .
어쨌든 나는 다음을 사용할 것이다:
if ((f_count * sleep_interval % alarm_interval == 0 && f_count > 0)); then
몇 가지 참고사항:
- inside
[[...]]
,>
문자열 비교용(10
2보다 작고 로케일에 따라-1
0보다 클 수 있음). 수치 비교 에 사용됩니다-gt
(사용하는 것이 더 좋지만((...))
). x
대신 을 사용하는 등 산술 표현식 내에서 변수를 확장하지 마세요$x
.$ x=-1 ksh -c '((-$x > 0))' ksh: --1 > 0: assignment requires lvalue
그리고
$ x=-1 ksh -c '((-x > 0))' $
또는:
$ x=1+1 ksh -c 'echo "$(($x * 2)) $((x * 2))"' 3 4
답변2
ksh는 산술 확장과 다르게 작동하는 것으로 보입니다. 이 문제를 해결하기 위해 AIX 6과 AIX 7 모두에서 예상대로 작동하는 산술 대체를 명시적으로 사용합니다.
...
if [[ ( $((f_count * sleep_interval % alarm_interval)) -eq 0 ) && $f_count -gt 0 ]]
...
답변3
아마도 대답은 간단할 것입니다. 산술 표현식의 시작 부분에 있는 변수가 0(영)으로 확장되면 문제가 발생합니다. 이는 KSH 조건식에서 -eq의 왼쪽 피연산자입니다. -eq는 숫자 비교이고 연산자는 왼쪽 피연산자로 숫자를 기대합니다.
피연산자를 확장/평가할 때 연산자는 세 단계를 수행해야 합니다. a) 변수 확장, b) 선행 0 제거, c) 이 순서로 표현식을 평가하면 관찰된 문제가 발생합니다.
이전 쉘 버전에서 a) 변수 확장, b) 표현식 평가, c) 선행 0 제거를 수행한 경우 문제가 발생하지 않습니다.