[DreamHack] [Reversing] Labyrinth

image.png

image.png

어쩌다보니 첫 퍼블이 이 문제가 되었다..

image.png

난이도는 엄청 쉬운 편이였는데, 왜 4시간동안 사람들이 못풀었는지 잘 모르겠다…(난 뒤늦게 아침에 문제 업로드를 발견했다.)

flag 확인에 필요한 입력값은 다음 디스어셈블리 지점에서 확인가능하다.

(주소 기준은 /mnt/data/probobjdump -d -Mintel 한 결과)

  1. 입력 받는 곳(“submission: %s”)
116e: lea rbx, [rsp+0xb0]           ; 입력 버퍼(rbX)
1176: lea rdi, [rip+0xe94]  # 2011  ; "submission: %s" 포맷
117f: mov rsi, rbx
1182: call 1100 <__isoc99_scanf@plt>
  1. .rodata0x2090, 0x20a0에서 32바이트를 스택으로 복사
11d0: movdqa xmm0, XMMWORD PTR [rip+0xeb8]  # 2090
11e4: movaps XMMWORD PTR [rsp+0x10], xmm0   ; [rsp+0x10..0x1f]
11e9: movdqa xmm0, XMMWORD PTR [rip+0xeaf]  # 20a0
11f1: movaps XMMWORD PTR [rsp+0x20], xmm0   ; [rsp+0x20..0x2f]
11da: lea rsi, [rsp+0x10]                   ; rsi = 테이블 시작
11df: lea rbp, [rsp+0x30]                   ; rbp = 디코딩 결과 저장할 버퍼
  1. 각 바이트에 ^ 0x30 적용해 디코딩(32바이트 루프)
1200: movzx eax, BYTE PTR [rsi+rdx]   ; 테이블에서 1바이트 로드
120b: mov    BYTE PTR [rsp+0x3], al
120f: movzx  eax, BYTE PTR [rsp+0x3]
1214: xor    eax, 0x30                ; 여기서 ^ 0x30
1217: mov    BYTE PTR [rbp+rdx], al   ; 디코딩 바이트를 rbp+rdx에 저장
1239: cmp    rdx, 0x20                ; 총 32바이트(0x20) 반복
123d: jne    1200
  1. 길이/일치 검증 후 정답 출력 포맷 사용
1247: call 10c0 <strlen@plt>
124c: cmp  rax, 0x20                  ; 길이 32 확인
...
130f: lea  rsi, [rip+0xcfe] # 2014    ; "DH{%s}" 포맷 문자열
1316: call 10f0 <__printf_chk@plt>    ; 정답 출력

요약하면,