![여러 사용자 입력을 반복하려고 할 때 예기치 않은 출력이 나타나는 이유는 무엇입니까? [복사]](https://linux55.com/image/197430/%EC%97%AC%EB%9F%AC%20%EC%82%AC%EC%9A%A9%EC%9E%90%20%EC%9E%85%EB%A0%A5%EC%9D%84%20%EB%B0%98%EB%B3%B5%ED%95%98%EB%A0%A4%EA%B3%A0%20%ED%95%A0%20%EB%95%8C%20%EC%98%88%EA%B8%B0%EC%B9%98%20%EC%95%8A%EC%9D%80%20%EC%B6%9C%EB%A0%A5%EC%9D%B4%20%EB%82%98%ED%83%80%EB%82%98%EB%8A%94%20%EC%9D%B4%EC%9C%A0%EB%8A%94%20%EB%AC%B4%EC%97%87%EC%9E%85%EB%8B%88%EA%B9%8C%3F%20%5B%EB%B3%B5%EC%82%AC%5D.png)
저는 다음 bash 쉘 스크립트를 작성하고 있습니다.
#!/bin/bash
declare -i N
read N
for i in {1..$N}
do
echo "Number: $i"
done
declare -i N
(나는 정수를 만든다고 믿는다 N
)
그러나 이 명령을 실행하면 다음과 같은 출력이 나타납니다.
>vim new.sh
>chmod +x passgen.sh
>./passgen.sh
15
Number: {1..15}
여기서는 사용자로부터 한계를 얻은 다음 루프를 실행하고 싶습니다.
답변1
에서 man bash
:
확장 순서는 중괄호 확장, 매개변수 및 변수 확장, 산술 확장, 명령 대체(왼쪽에서 오른쪽으로 수행됨)입니다.
보시다시피 중괄호 확장이 먼저 나오므로 분명히 귀하의 질문에서 건너 뛰었습니다. 나는 다른 루프를 사용할 것입니다.
답변2
버팀대 확장의 문제점이 지적되었지만 나는 단지 다음과 같이 언급하고 싶습니다.
(나는 -i N 진술이 N을 정수로 만든다고 믿습니다)
나는 대답할 것입니다. 그렇습니다. 명령 주입 취약점이 되기 때문에 문제가 됩니다. 이 정수 속성을 설정하면 변수에 값이 할당될 때마다 해당 값이 산술 표현식으로 해석됩니다.
사용자가 a[$(reboot)]
이 read
프롬프트를 입력하면 다시 시작이 시도됩니다.
bash
이는 산술 표현식을 평가할 zsh
때 흔히 발생하는 문제입니다 ksh
. for (( i = 1; i <= N; i++ ))
ksh93 스타일 형식( 포함 여부에 관계없이 )을 사용하더라도 declare -i N
의 내용이 N
여전히 해당 산술적 맥락에서 평가되기 때문에 문제가 발생할 수 있습니다.
for i in {1..$N}
declare -i N
ksh, zsh 또는 yash -o braceexpand
(횡설수설을 반복하지만 명령 주입 취약점을 유발하지 않는)에서는 괜찮을 것입니다(없음). 또는 sh
구현 sh
이 ksh
.
#! /bin/sh -
IFS= read -r N
i=1; while [ "$i" -lt "$N" ]; do
printf '%s\n' "Number: $n"
done
ksh
[
피연산자는 여전히 -lt
산술 표현식으로 처리되므로 명령 주입 취약점이 여전히 발생합니다. // [[ $i -lt $N ]]
or도 사용하지 마세요 .(( i < N ))
bash
zsh
ksh
또는 루프를 수행하기 위해 적절한 프로그래밍 언어를 사용하거나 입력을 먼저 정리할 수 awk
있습니다 .perl