TECH 으로 돌아가기
TECH HACKER NEWS 어제 8분 읽기 57 READS

IBM i의 QSYRUPWD는 어떻게 비밀번호 해시를 넘겨주는가

IBM i의 QSYRUPWD는 어떻게 비밀번호 해시를 넘겨주는가
SOURCE IMAGE · HACKER NEWS

IBM i는 과거 AS/400 계열에서 이어져 온 IBM의 통합 엔터프라이즈 플랫폼으로, 지금도 ERP·재무·물류·제조 같은 업무 핵심 시스템을 떠받치고 있다. 이 플랫폼에는 QSYRUPWD(Retrieve Encrypted User Password)라는 API가 존재한다. 권한을 가진 호출자에게 특정 사용자 프로파일의 비밀번호 관련 데이터를 암호화된 형태로 돌려주는 인터페이스로, 비밀번호를 평문으로 노출하지 않은 채 시스템 간에 옮겨야 하는 동기화·마이그레이션·복제 같은 관리 시나리오를 위해 마련된 것이다. 실렌트시그널(Silent Signal)의 연구자는 실제 IBM i 침투 테스트 과정에서 이 API의 동작이 시스템 설정에 따라 달라진다는 점을 발견하고, 그 내부 구조를 역공학으로 파고들었다.

QPWDLVL이 만들어내는 미묘한 차이

출발점은 클라이언트 서버가 QPWDLVL = 2로 설정돼 있었다는 관찰이다. IBM i에서 QPWDLVL 시스템 값은 운영체제가 허용하는 비밀번호 규칙과, 인증 호환성을 위해 유지하는 검증자(verifier) 형식을 함께 결정한다. IBM 문서에 따르면 레벨 0과 1은 오래된 DES 기반 방식, 레벨 2와 3은 SHA-1 기반 방식, 레벨 4는 PBKDF2 기반 검증자 모델을 사용한다. 특히 레벨 2에서는 이전 형식을 제거하는 대신 여러 검증자 형태를 함께 유지한다.

이 차이는 실무적으로 중요한 결과를 낳는다. 비밀번호 강도 점검에 널리 쓰이는 John the Ripper에는 as400_des와 as400_ssha1이라는 IBM i 전용 크래킹 포맷이 있는데, 이는 각각 DES 기반과 솔트가 적용된 SHA-1 기반 표현을 지원한다. 그런데 연구자의 테스트에서 QPWDLVL 0~1로 동작하는 시스템의 QSYRUPWD 출력은 이 포맷들과 호환됐지만, QPWDLVL 2~4에서 얻은 출력은 John the Ripper가 기대하는 형태와 맞지 않았다. 다시 말해 상위 레벨에서는 반환 데이터의 구조 자체가 달라져, ALLOBJ와 SECADM 권한(QSYRUPWD 호출에 필요한 권한)을 갖추고도 기존 도구로는 실질적인 비밀번호 검증이 불가능해진 것이다. 이는 IBM이 해당 레벨의 반환 구조를 공식 문서로 공개했다는 뜻이 아니라, 도구 분석에 근거한 경험적 관찰이다.

트레이스에서 CIPHER MI 함수까지

연구자는 UPWD0100 포맷으로 QSYRUPWD를 호출해 반환 버퍼를 그대로 뽑아내는 작은 CL 프로그램 PWDDUMP를 작성했다. 완전한 추출 도구를 만들기보다, 설정별로 API가 실제 무엇을 돌려주는지 확인하려는 목적이었다. 이어 IBM i가 제공하는 STRTRC 트레이스 도구로 QSYRUPWD 내부 호출을 기록하고, 읽기 어려운 스풀 파일을 스크레이퍼로 정리했다. 그 결과 이름부터 암호 처리를 시사하는 심볼들, 즉 일반 암호 연산과 AES·복호화 관련 루틴이 눈에 들어왔다.

다음 단계는 시스템 서비스 도구(SST)를 이용한 내부 분석이었다. SST는 로그·메모리 덤프·런타임 상태 같은 저수준 진단 정보를 수집하는 IBM i의 서비스 인터페이스로, 접근하려면 *SERVICE 권한과 운영체제 프로파일과는 별개인 SST 전용 자격 증명이 필요하다. 연구자는 SST로 QSYMIUTLS·QSYCODEUTL·QZLSRTPW·QSYRUPWD 등 서비스 프로그램의 어셈블리를 덤프했다. 그런데 qsy_aes_decrypt나 qsy_cipher 함수 안에는 블록 암호 라운드나 키 스케줄 같은 명시적 암호 구현이 없었다. 실제 민감한 연산은 더 낮은 계층으로 위임되고 있었던 것이다.

그 경로가 바로 SCV(Supervisor Call Vectored)다. scv 명령으로 특권 LIC 코드로 전환하는 이 메커니즘에서 R10은 함수 선택자 역할을 하고 인자는 R3부터 전달된다. 코드에는 선택자 346이 등장했는데, 레이프 스발가르드(Leif Svalgaard)의 MI 프로그래밍 자료를 근거로 SCV 10 핸들러가 담긴 LIC 모듈 .#cfmir를 추적한 끝에, 346이 CIPHER MI 함수에 해당한다는 사실을 확인했다. 함수 테이블의 기준 포인터에 선택자×8 오프셋을 더해 실제 함수 포인터 #crciphr를 찾아낸 것으로, TOC 포인터 설정과 PPC64의 부호 확장 규칙까지 손으로 계산하는 과정이 뒤따랐다.

디버거 없이 브레이크포인트를 만드는 법

SST는 GDB 같은 완전한 디버거가 아니어서, 태스크에 붙어 범용 레지스터를 볼 수는 있지만 명령 단위 스텝 실행이나 편한 브레이크포인트 처리는 지원하지 않는다. 연구자는 이를 우회하기 위해 CIPHER 호출 직전의 SCV 명령을 직접 패치했다. NOP에 해당하는 ori r0, r0, 0과 4바이트 뒤로 점프하는 무조건 분기(0x4BFFFFFC)를 심어, CPU가 알려진 주소에서 무한 루프를 돌게 만든 것이다. 실제로는 원래 명령 쌍 44000141 E8410020을 60000000 4BFFFFFC로 바꾸고 F11을 두 번 눌러 적용했으며, 주소의 상위부는 시스템마다 달라도 하위 오프셋은 이 코드 위치에서 동일했다. 이후 한 터미널에서 PWDDUMP를 호출하면 프로그램이 멈추고, 다른 터미널에서 SST를 그 프로세스에 붙여 루프 지점의 레지스터와 값을 관찰할 수 있게 된다.

실무자 입장에서 이 분석이 주는 함의는 분명하다. 최신 QPWDLVL 설정은 그 자체로 오래된 크래킹 도구를 무력화해 방어 효과를 높이지만, 동시에 조직이 자체적으로 수행하던 비밀번호 강도 점검도 어렵게 만든다. 또한 QSYRUPWD 호출과 SST 접근에는 ALLOBJ·SECADM·*SERVICE 같은 최고 수준의 권한이 요구되므로, 이런 계정과 SST 전용 자격 증명(운영체제 QSECOFR와 별개일 수 있는)의 관리가 곧 보안의 핵심임을 다시 확인시켜 준다. 다만 여기서 공개된 내용은 IBM이 문서화한 구조가 아닌 한 시스템에 대한 역공학 결과이며, 원문 자체가 CIPHER 파라미터 해석 직전에서 끊겨 완전한 해시 재구성 절차까지는 담고 있지 않다는 한계도 함께 기억할 필요가 있다.

SOURCE · HACKER NEWS
원문 전체 보기 → https://blog.silentsignal.eu/2026/07/28/the-cipher-behind-qs...
SHARE
처리 중...