tcpdump를 실행해야 하는 스크립트에서 논리 오류를 찾을 수 없습니다.

tcpdump를 실행해야 하는 스크립트에서 논리 오류를 찾을 수 없습니다.

시간을 비교하고 시작 시간이 종료 시간이 아닌 현재 시간과 같을 경우 tcpdump를 시작하는 스크립트를 작성했습니다. 종료 시간이 현재 시간과 같으면 PID를 검색하여 종료합니다. 그런데 여기에는 아직 논리적 오류가 있는 것 같은데, 어떻게 해결해야 할지 정말 모르겠습니다.

Code:
#!/bin/sh
source /media/usbhd-sd[b-d]1/config.conf
pluggedin=true
echo $TIMESTART
echo $TIMEEND
echo $$
echo $Zeit
echo $$ >> /tmp/test.txt
while [ $pluggedin ];do
        Zeit=$(date +"%T")
        if [[ $TIMESTART == $Zeit ]];then
                if [[ $TIMEEND != $Zeit ]] && [ "$(pidof tcpdump)" == "" ];then
                        echo "tcpdump started"
                        sudo tcpdump -i eth0 -w /media/usbhd-sd[b-c]1/abfrage2.pcap &
                        #sudo umount /dev/sdb1
                else
                        pid1=$(ps -eo pid,args|awk '/abfrage2/ && ! /awk/{print $1}')
                        echo $pid1 >> /tmp/test.txt
                        sudo kill $pid1
                        echo "autodump stopped"
                fi

        else
        echo "tcpdump not yet started"
        fi
done

디버깅했는데 첫 번째 if가 정확하면 이 출력이 표시되지만 첫 번째 if가 올바르지 않으면 내부 if도 확인하지 않습니다. PID를 확인하고 외부 if에서 or를 수행하면 작동합니까?

Code:
+ [ true ]
+ date +%T
+ Zeit=08:51:00
+ [[ 08:51:00 == 08:51:00 ]]
+ [[ 08:51:02 != 08:51:00 ]]
+ pidof tcpdump
+ [ 9945 ==  ]
+ awk /abfrage2/ && ! /awk/{print $1}
+ ps -eo pid,args
+ pid1=
+ echo
+ sudo kill -9
kill: you need to specify whom to kill
+ echo autodump stopped
autodump stopped

고쳐 쓰다

제가 직접 몇 가지 오류를 발견했습니다.

최신 코드입니다. 이제 거의 작동하지만 tcpdump는 여전히 종료되지 않습니다. 하지만 이미 파일에 데이터를 쓰고 있습니다.

    #!/bin/sh
source /media/usbhd-sd[b-d]1/config.conf
pluggedin=true
echo $TIMESTART
echo $TIMEEND
echo $$
echo $Zeit
echo $$ >> /tmp/test.txt
while [ $pluggedin ];do
        Zeit=$(date +"%T")
        if [[ $TIMESTART == $Zeit ]] || [[ "$pid1" != "" ]];then
                if [[ $TIMEEND != $Zeit ]];then
                        if [ "$pid1" == "" ];then
                                echo "tcpdump started"
                                sudo tcpdump -i eth0 -w /media/usbhd-sd[b-c]1/abfrage2.pcap &
                                pid1=$(ps -eo pid,args|awk '/abfrage2/ && ! /awk/{print $1}')
                                #sudo umount /dev/sdb1
                        else
                        echo "Tcpdump already running"
                        fi
                else
                        if [ "$pid" != ""];then
                                echo $pid1 >> /tmp/test.txt
                                sudo kill -9 $pid1
                                echo "autodump stopped"
                        else
                                echo "autodump already stopped"
                        fi
                fi

        else
        echo "tcpdump noch yet started"
        fi
done

이제 디버깅을 통해 이 출력을 얻습니다. 시간이 40초이면 PID를 사용할 수 없습니다.

+ [ true ]
+ date +%T
+ Zeit=10:45:39
+ [[ 10:45:30 == 10:45:39 ]]
+ [[ 30285 !=  ]]
+ [[ 10:45:40 != 10:45:39 ]]
+ [ 30285 ==  ]
+ echo Tcpdump already running
Tcpdump already running
+ [ true ]
+ date +%T
+ Zeit=10:45:40
+ [[ 10:45:30 == 10:45:40 ]]
+ [[ 30285 !=  ]]
+ [[ 10:45:40 != 10:45:40 ]]
+ [  != ]
sh: !=: argument expected
+ echo autodump already stopped
autodump already stopped

답변1

좋은 질문, 좋은 예, 좋은 데이터, 좋은 노력, 감사합니다.

시간은 항상 변하기 때문에 비교하기 쉬운 시간값을 사용해야 합니다. 이 date명령을 사용하면 모든 시간 값을 "에포크"(1970-01-01 00:00:00 UTC) 이후의 초 수로 변경합니다.

timestart=$(date +%s -d "$TIMESTART")
timeend=$(date +%s -d "$TIMEEND")

에서 동일한 형식을 사용하여 Zeit이제 날짜를 정수로 비교할 수 있으며 가장 가까운 날짜가 더 큽니다.

        Zeit=$(date +"%s")
        if [ $timestart -le $Zeit ];then
                if [ $timeend -le $Zeit ] && [ "$(pidof tcpdump)" == "" ];then

나는 또한 당신이 배경을 죽이려고 하는 것처럼 보인다는 것을 알고 있습니다 tcpdump. 예를 들어, $!가장 최근에 시작된 백그라운드 작업의 PID가 포함된 내장 변수를 사용하는 것을 고려할 수 있습니다 (이 답변의 모든 코드는 테스트되지 않았습니다).

unset tcpdump_pid
while [ $pluggedin ];do
        Zeit=$(date +"%s")
        if [ $timestart -le $Zeit ] && [ "$tcpdump_pid" == "" ]; then
                echo "tcpdump started"
                sudo tcpdump -i eth0 -w /media/usbhd-sd[b-c]1/abfrage2.pcap &
                tcpdump_pid=$$
        fi                            
        if [ $timeend -le $Zeit ] && [ "$tcpdump_pid" != "" ];then
                sudo kill $tcpdump_pid
        fi
        # sleep ?
done

tcpdump매뉴얼 페이지 에 따르면 SIGINT 또는 SIGTERM은 종료 tcpdump되므로 -9필요하지 않으며 사용해서는 안 됩니다. 기본 killSIGTERM이면 충분합니다.

관련 정보