Hack/DreamHack

[DreamHack] command-injection-1

swc0317 2025. 3. 12. 22:12
728x90
반응형
문제 링크

 

 

https://dreamhack.io/wargame/challenges/44

 

command-injection-1

특정 Host에 ping 패킷을 보내는 서비스입니다. Command Injection을 통해 플래그를 획득하세요. 플래그는 flag.py에 있습니다. Reference Exercise: Command Injection

dreamhack.io

 

문제 해법

 

커맨드 인젝션을 이용한 exploit을 통해, 

 

서버 내부 명령어를 실행토록 하는 공격입니다.

 

ping 루트

 

@APP.route('/ping', methods=['GET', 'POST'])
def ping():
    if request.method == 'POST':
        host = request.form.get('host')
        cmd = f'ping -c 3 "{host}"'
        try:
            output = subprocess.check_output(['/bin/sh', '-c', cmd], timeout=5)
            return render_template('ping_result.html', data=output.decode('utf-8'))
        except subprocess.TimeoutExpired:
            return render_template('ping_result.html', data='Timeout !')
        except subprocess.CalledProcessError:
            return render_template('ping_result.html', data=f'an error occurred while executing the command. -> {cmd}')

    return render_template('ping.html')

 

Flask를 통해 만들어진 웹서버 내 ping route 입니다.

 

 

ping route에 접근하면

 

 

와 같은 방식으로 호스트를 입력하는 칸이 있습니다.

 

    if request.method == 'POST':
        host = request.form.get('host')
        cmd = f'ping -c 3 "{host}"'
        try:
            output = subprocess.check_output(['/bin/sh', '-c', cmd], timeout=5)
            return render_template('ping_result.html', data=output.decode('utf-8'))

 

ping 경로 처리 동작을 보면, host에 입력받은 

 

문자열을 저장,

 

 /bin/sh -c 'ping -c 3 "host"'가 됩니다.

 

이 명령어는 셸을 통해 ping -c 3 "host" 라는 명령어를 실행합니다.

 

그래서, 이 "host" 자리를 공격할 겁니다.

 

리눅스 다중 명령어

 

리눅스엔 한 구문으로 다중 명령어를 실행할 수 있는 방법이 있습니다.

 

세미콜론, |, && 등을 이용하는 방법입니다.

 

이중 세미 콜론을 통해 명령어를 실행하겠습니다.

 

먼저 8.8.8.8" 라는 구문을 입력해주면

 

ping -c 3 "8.8.8.8" 까지 실행 됩니다.

 

이제 우리가 알아야하는 flag.py의 내용물을 출력할 구문을 추가해줍니다.

 

;cat flag.py

 

여기서 문제는, host 마지막에 오는 따옴표를 처리하지 않았습니다.

 

저는 깔끔하게 처리하기 위해 또 다른 명령어 echo "" 를 실행하기 위해

 

echo "까지 추가했습니다. 완성된 명령어는 다음과 같습니다.

 

8.8.8.8";cat flag.py;echo "

 

 

문제가 있습니다. 입력받을 수 있는 형식과 맞지 않습니다.

 

이는 html 내부 패턴 매칭에 의해 지정된 문자만 받을 수 있기 때문입니다.

 

html을 수정합니다.

 

저는 크롬 환경이라 f12를 통해 개발자 도구에 접근합니다.

 

각 환경에 맞게 개발자 도구에 접근하셔야 합니다.

 

 

이렇게 pattern 이라된 변수를 확인하실 수 있는데,

 

[A-Za-z0-9.]{5,20} 이 부분의 뜻이 다음과 같습니다.

 

[] : A 부터 Z 즉 대문자, a 부터 z 즉 소문자, 0 부터 9, 즉 모든 정수 및 마침표 . 를 사용할 수 있습니다.

 

이때 글의 수는 5 ~ 20 입니다.

 

이때 리눅스의 다중 명령어를 실행하기 위해, 공백, 세미콜론, 그리고 

 

임의로 따옴표를 넣어 host를 마무리해야 하므로 따옴표를 추가해줍니다.

 

 

사실 아예 패턴 변수를 지워, 패턴 제한을 없애도 괜찮을 것 같습니다.

 

 

위 처럼 성공적으로 결과가 나온 모습입니다.

728x90
반응형

'Hack > DreamHack' 카테고리의 다른 글

[DreamHack] file-download-1  (0) 2025.03.12
[DreamHack] cookie  (0) 2025.03.11