1P by GN⁺ | ★ favorite | 댓글 1개
  • 암호 없는 BitLocker가 별도 TPM(discrete TPM) 에 의존하면, 부팅 중 VMK가 TPM에서 CPU로 전달되는 순간 SPI 버스에서 평문 키를 캡처할 수 있음
  • Lenovo L13 실험은 100달러 미만의 DSLogic Plus로 진행됐지만, 33MHz SPI 버스를 안정적으로 읽기에는 샘플링 한계가 컸음
  • 캡처 데이터는 SPI → TIS → TPM 2.0 순서로 해석해야 하며, TPM2_Unseal 응답 버퍼에서 5761로 시작하는 32바이트 키를 찾아냄
  • 추출한 키로 dislocker-fuse를 이용해 BitLocker 파티션을 마운트하고, sethc.execmd.exe로 바꿔 Shift 5회 입력으로 SYSTEM 셸까지 얻음
  • 별도 TPM만으로는 충분한 보호가 어렵고, 실질적인 방어는 fTPM 사용 또는 BitLocker PIN·패스프레이즈 설정에 달려 있음

암호 없는 BitLocker와 별도 TPM의 약점

  • BitLocker 파티션은 FVEK(Full Volume Encryption Key) 로 암호화됨
  • FVEK는 다시 VMK(Volume Master Key) 로 암호화되어, 암호화된 데이터와 함께 디스크에 저장됨
    • 이 구조 덕분에 전체 디스크를 다시 암호화하지 않고도 키 회전이 가능함
  • VMK는 TPM에 저장됨
    • 따라서 디스크는 해당 컴퓨터에서 부팅될 때만 복호화될 수 있음
    • Active Directory에는 복구 메커니즘이 있음
  • 취약한 지점은 CPU가 디스크 복호화를 위해 TPM에 VMK 전송을 요청하는 순간임
    • VMK가 TPM과 CPU 사이의 SPI 버스를 평문으로 지나감
    • 이 값을 캡처하면 BitLocker 디스크 복호화에 사용할 수 있음

TPM 통신 캡처에 쓴 장비

  • 실험 장비는 DSLogic Plus 로직 분석기임
    • 2021년에 세금과 배송비 포함 100달러 미만에 구매함
  • 신호를 안정적으로 얻으려면 샘플링 주파수가 버스 주파수의 3~4배 정도 필요함
    • 대상 SPI 버스는 33MHz라 최소 100MHz 샘플링이 필요함
    • DSLogic Plus 사양은 최대 16채널에서 400MHz를 말하지만, 실제 사용 조건에는 제약이 있음
  • DSLogic Plus는 캡처 방식과 채널 수에 따라 한계가 뚜렷함
    • 동시에 캡처하는 채널 수가 늘어나면 샘플링 주파수가 낮아짐
    • 스트림 모드는 약 1분 동안 큰 데이터를 캡처할 수 있지만, 3채널에서 100MHz로 제한됨
    • 버퍼 모드는 400MHz 샘플링이 가능해도 몇 밀리초만 동작해 이 작업에는 실용적이지 않음
  • 더 전문적인 선택지는 약 10배 비싼 Saleae이며, 다른 장비는 sigrok 지원 하드웨어 목록에서 확인할 수 있음

보드 연결과 캡처 타이밍

  • SPI는 공유 버스라 작은 TPM 핀에 직접 연결할 필요가 없음
    • 같은 SPI 버스에 연결된 더 큰 부품이 있으면 그쪽에 훅을 걸 수 있음
    • 실험에서는 근처의 SPI flash를 식별해 사용함
    • 부품 표기가 있어 데이터시트를 찾아 용도를 확인하기 쉬웠음
  • DSLogic으로는 샘플링 주파수 하락 때문에 SPI 라인 중 3개만 캡처함
    • 중요한 라인은 CLK, MOSI, MISO임
  • 임계 전압은 신호 전압의 절반 정도로 잡아야 함
    • 측정된 신호 전압은 3.3V였고, 적절한 임계값은 약 1.6V였음
  • 찾는 VMK는 POST 단계 후반에 사용됨
    • Lenovo L13에서는 스플래시 화면 직후, 전체 약 25초 부팅 중 약 14초 지점이었음
    • 그 전에도 SPI 동작은 있지만 주로 초기 부팅 단계 읽기와 검증이며 TPM 통신은 아니었음
    • 부팅 직후 캡처를 시작하거나, 불필요한 데이터를 줄이려면 약 7초 뒤 시작할 수 있음

SPI, TIS, TPM 2.0 해석

  • 캡처 신호는 SPI, TIS, TPM 2.0 세 계층으로 나눠 해석해야 함
  • SPI는 단순한 프로토콜이라 일반 로직 분석기로도 해석 가능함
    • 클럭이 0에서 1로 올라가는 순간 데이터 라인의 상태가 비트 값이 됨
    • 예시에서 MOSI는 8클럭 동안 0이라 0x00, MISO는 첫 비트만 켜져 0x80으로 해석됨
  • 가장 어려운 부분은 TIS(TPM Interface Specification) 였음
    • 동작하는 디코더를 찾지 못해 수동으로 처리함
    • libsigrok decoders는 정확한 데이터 해석에는 실패했지만, TPM 교환이 일어나는 대략적 구간을 찾는 데 도움이 됨
    • 실패 원인은 캡처에 Chip Select가 없거나, 클럭이 부정확하거나, 일부 바이트가 빠졌거나, 다른 이유일 수 있음
  • 마스터에서 슬레이브로 보내는 요청은 반복적인 패턴을 보임
    • 슬레이브가 준비 상태를 알리는 80을 보냄
    • 마스터가 D4 00 24 헤더와 TPM 바이트를 보냄
    • 슬레이브가 01 FF로 읽었음을 확인함
  • 슬레이브에서 마스터로 가는 응답은 레지스터 설정과 읽기에 의존함
    • 예시 프레임은 D4 00 24 주소에서 1바이트를 읽은 결과임
    • 슬레이브가 80으로 트랜잭션을 시작하고, 이후 관심 있는 값인 0x80이 나타남

TPM2_Unseal 응답에서 키 찾기

  • 키 반환을 요청하는 TPM 명령은 TPM2_Unseal
  • 요청 프레임보다 MISO 라인의 응답에 집중해 TPM 트랜잭션을 분리함
    • 원시 SPI 데이터에서 80 00 00 00 01 .. 마스크로 필터링하고 마지막 와일드카드 바이트만 유지함
    • TPM 트랜잭션 시작은 80 01 또는 80 02 헤더로 식별됨
    • 키가 든 응답은 더 긴 인증 응답이며 80 02로 시작함
  • Unseal 명령과 응답 사이에는 약 10ms 지연이 있었음
    • 80 02 헤더는 패스워드 세션을 나타내며, 대부분의 요청이 쓰는 평문 80 01 헤더와 다름
    • 요청 인증과 응답 HMAC 처리 때문에 지연이 생긴 것으로 보임
  • TPM 명령과 응답은 바이트를 하나씩 재조립해 얻음
    • 디코딩에는 tpmstream-web 도구를 사용함
    • 응답 버퍼 안의 키는 5761로 시작하며 길이는 32바이트임

디스크 마운트와 백도어

  • 추출한 키를 파일로 저장한 뒤 dislocker-fuse에 넘겨 BitLocker 파티션을 마운트함
  • 예시 명령은 키 파일을 만들고 /dev/sdd3./mnt/에 연결한 뒤, dislocker-file을 다시 ./mnt2/에 마운트함
  • 가장 단순한 백도어는 Windows의 sticky keys 프로그램을 cmd.exe로 덮어쓰는 방식임
    • Windows/System32/cmd.exeWindows/System32/sethc.exe로 복사함
    • 디스크를 노트북에 다시 넣고 부팅한 뒤 Shift 키를 5번 누르면 SYSTEM 셸을 얻음

장비 한계와 방어책

  • DSLogic은 이 작업에 추천하기 어려움
    • 많은 캡처가 실패해 버려야 했음
    • 버스 속도의 3배 샘플링은 일관된 클럭을 얻기에 겨우 충분했고 일부 바이트가 빠졌음
  • 장비 한계 때문에 프로토콜을 깊게 이해하고 캡처를 수동으로 해석하는 데 시간이 많이 들었음
    • 고용주가 장비를 구매하는 상황이라면 전문 로직 분석기를 사는 편이 낫다고 봄
  • 별도 TPM 사용은 기대와 달리 시스템 보안을 높이지 않으며 보안의 환상을 만들 수 있음
  • 방어책은 두 가지임
    • fTPM을 사용함
    • 별도 TPM을 써야 한다면 BitLocker에 PIN 또는 패스프레이즈를 설정함
  • Microsoft도 더 높은 수준의 데이터 보호가 필요한 조직 영역에는 BitLocker PIN 또는 패스프레이즈 설정을 권고

댓글과 토론

Hacker News 의견들
  • 모든 TPM은 이런 중간자 공격을 막기 위해 암호화된 세션을 지원함. TPM2_StartAuthSession을 쓰고 각 세션 명령에 암호화를 지정하면 되는데, BitLocker는 이걸 쓰지 않으니 심각한 실패임. Microsoft가 고쳐야 함
    비교하자면 systemd는 TPM과 함께 LUKS 디스크 암호화를 쓸 때 암호화된 세션을 사용함: https://github.com/systemd/systemd/commit/acbb504eaf1be51572...

    • 이건 제대로 된 중간자 공격도 아니고 그냥 수동 스니핑에 가까움
      TPM을 잘 몰라서 묻자면, 인증된 세션은 어떻게 동작하는지 궁금함. 운영체제가 공격자가 진짜 중간자 공격에서 위조할 수 없는 방식으로 TPM에 자기 신원을 어떻게 증명하는가? 운영체제 쪽에 저장된 비밀이나 키는 아직 암호화 키가 없으니 디스크에 평문으로 있어야 할 것 같음
      설령 운영체제가 어떤 식으로 TPM의 신원을 검증하고, 디스크의 파일 몇 개를 수정하는 방식으로 우회할 수 없게 만들었다 해도, 공격자가 에뮬레이터에서 같은 루틴을 돌리는 건 무엇이 막는지 모르겠음. Intel ME나 SGX 같은 CPU 쪽 보안 실행 환경과 통합하지 않는 한 이 접근으로 진짜 보안을 얻기 어려워 보이고, 그러면 애초에 TPM이 필요 없을 듯함
    • 그 누락이 의도적인지, 그렇다면 이유가 뭔지 궁금함
    • 인증된 세션은 완전히 통합된 장치가 아니면 실질적으로 거의 쓸모가 없음. SRK 신원을 보장할 방법이 없어서 중간자 공격은 여전히 가능함
  • 2021년에 나온 다른 글도 있음
    https://arstechnica.com/gadgets/2021/08/how-to-go-from-stole...
    일부 노트북 제조사는 노트북을 열면 TPM을 지우는 설정을 제공함. RAM을 추가할 수 있는지 보려고 노트북을 열었다면, BitLocker 복구 키에 접근할 수 있거나 백업이 있기를 바라야 함

    • 복구 키 사본을 어딘가에 보관하는 건 좋은 습관임
    • 아마 단순한 탬퍼 스위치 버튼에 의존할 가능성이 높고, 뒷면 플라스틱을 잘라내면 쉽게 우회될 수 있음. 케이스 전체에 배선을 깔아두는 식의 정교한 장치를 넣었을 것 같지는 않음
    • 소비자용 장치에서 섀시 침입 감지가 기본으로 켜진 건 본 적이 없음. 기업 계정의 대량 주문 제품이었을 수도 있음. 그런 제품은 IT 부서가 원하는 설정으로 출고될 수 있음
    • 노트북 나사를 풀고 내부에 접근하는 경우를 말하는 건가?
      플라스틱을 잘라내는 식으로 접근할 수도 있지 않을까 싶음. Matrix의 기생충 추출 장면 같은 방식으로
    • 요즘은 업그레이드 가능한 RAM이 있는 노트북을 찾기 어렵다는 게 농담거리임. 일부 ThinkPad 라인도 그렇고, 게이밍 노트북은 종종 가능함
  • 새로울 건 없음. 기본 설정은 PIN을 요구하지 않지만, Microsoft 문서는 여러 공격을 설명하고 이를 완전히 막는 BitLocker PIN 설정을 권장함. TPM이 무차별 대입을 막기 때문에 PIN은 꽤 약해도 됨
    예: https://learn.microsoft.com/en-us/windows/security/operating...

    • 흥미롭게도 내가 알기로 Windows Defender는 이제 기본적으로 접근성 기반 권한 상승 공격을 막음. Behavior:Win32/AccessibilityEscalation
    • TPM은 실패 시도가 X번 발생하면 키 자료를 지울 거라고 기대했는데, 그렇지 않은가?
  • BitLocker와 이런 종류의 암호화에서, 복호화 키를 시스템이 자동으로 제공하는 구조가 늘 이해가 안 됐음. 노트북 전체를 도난당하면 BitLocker가 어떤 보안을 제공하는가? 공격자 입장에서는 시스템이 부팅되고 사용자 계정 암호를 요구할 뿐임
    내가 이해한 바로는, 하드디스크를 노트북에서 빼서 다른 시스템에서 실행하려 할 때 내 데이터를 보호하는 것 같음. 이 어쩌면 어리석은 오해 때문에 나는 항상 BitLocker에 수동으로 입력해야 하는 암호를 설정해 왔고, LUKS에서도 늘 그렇게 했음. 완전히 틀린 생각인가?

    • 공격자는 로그인을 우회하거나, 시스템 메모리에서 키를 추출하거나, 물리 TPM이 있는 경우 이 글 같은 방식의 공격을 해야 함. 이건 비싼 컴퓨터를 훔쳐 빨리 돈을 벌려는 일반 절도범보다는 훨씬 정교한 공격일 가능성이 큼
      보통은 드라이브를 지우고 팔려고 할 가능성이 높고, 실제로 콜드 부트 공격을 시도하진 않을 듯함. 다만 전부 위협 모델에 달려 있음. 개인적으로 개인 장비에서 전체 디스크 암호화를 쓰는 주된 이유는 저장장치를 폐기할 때 물리적으로 파괴할 필요를 줄이기 위해서임
      하드디스크가 고장 나도 내 데이터가 사라졌는지 확인하려고 실제로 뜯어낼 필요가 없음. 내 장치는 보통 밖에 있을 때 절전 모드라서, 누군가 콜드 부트 공격을 하려면 어차피 할 수 있음
    • 완전히 틀리진 않았지만, 이제 키를 내보낼 수 있게 되는 위험을 놓치고 있을 수 있음
      말한 대로 복호화 키가 시스템에 자동으로 제공된다면, 그 키는 RAM에 있고 공격자가 내보낸 뒤 암호화된 디스크에 재사용할 준비가 된 상태임. 콜드 부트 공격[1]은 위협 모델에 맞는지 판단하려면 더 읽어볼 만한 공격 벡터임
      [1] https://en.wikipedia.org/wiki/Cold_boot_attack
    • Windows는 올바른 계정 암호를 입력하기 전까지 누구도 파일에 접근하지 못하게 해야 함. 그래서 이 컴퓨터에서는 디스크가 복호화되지만, 그 다음에는 Windows가 접근을 막음
    • 추측하자면 디스크 암호화에 암호를 설정하지 않았다면, 그 시나리오에서는 보호가 없을 듯함
  • 키가 공유 버스를 지나간다면, 시스템의 모든 구성요소가 이 논리 분석기처럼 쉽게 키를 가로챌 수 있다는 뜻인가? 공급망 보안 악몽처럼 들림

    • 이런 암호화의 목적은 분리된 하드드라이브를 데이터 위험 없이 팔거나 재사용할 수 있게 하는 것임
      누구든 노트북을 부팅해서 복호화된 하드드라이브에 접근할 수 있다면, 먼저 키를 스니핑하는 게 무슨 차이가 있나? 노트북을 부팅할 수 있다면 어차피 최종 결과물에는 접근할 수 있었음
    • 몇몇 구성요소 사이에서 공유되긴 하지만, 전부는 전혀 아님. 요즘은 보통 SPI 버스에 부트 플래시와 TPM, 그리고 버스 마스터인 CPU 자체 정도만 붙어 있음
  • 누군가 노트북을 훔치는 상황에서 BitLocker가 보호해 주길 원한다면, 어차피 암호를 써야 하고 최대 절전이 아닌 절전 모드는 꺼야 함

    • 첫 번째는 이 글 전까지 완전히 명확하진 않았음. 노트북 도난은 전체 디스크 암호화가 의미 있는 위협 중 사실상 가장 약한[1] 부류이고, Windows는 일반 계정 암호 외에는 아무것도 요구하지 않는다는 점을 크게 내세워 왔음
      그렇다면 TPM의 “신뢰된” 하드웨어가 지금 실제로 뭘 하고 있는 건가? 부트 측정도 위조 가능한가? 게다가 이건 황당할 정도로 멍청함. 왜 키 자료가 버스 위를 평문으로 돌아다니는가? 키 교환 프로토콜 같은 것도 전혀 없음
      [1] 여기서 보안 삭제 얘기도 나오는데, 그건 더 약한 사례이긴 함. 하지만 전체 디스크 암호화에 소켓에서 뽑아 물리적으로 파괴할 수 있는 EEPROM이 있으면 그 부분은 똑같이 효과적으로 해결됨
  • 원시 신호를 0과 1로 바꾸는 데 어떤 소프트웨어를 썼는지 궁금함. 예전부터 비슷한 프로젝트가 있었는데, 80년대 카세트테이프에서 디지털 데이터를 읽는 작업임. 테이프의 .wav 파일은 꽤 괜찮게 확보했지만, 이를 0과 1로 바꿀 적절한 도구나 라이브러리를 아직 못 찾았음
    물론 진짜 재미는 0과 1을 디코딩하기 시작한 뒤부터일 것임. 비트가 어떻게 인코딩됐는지는 알고 있고, 주파수 편이 변조[0]임. 모르겠는 건 이걸 내가 추가 처리할 수 있는 비트 스트림으로 디코딩하는 데 무엇을 쓰면 되는가임
    [0] https://en.wikipedia.org/wiki/Frequency-shift_keying

    • 오래된 FSK 테이프 디코딩에는 슬라이딩 Goertzel 필터를 살펴보면 좋음. 구현하기 쉬운 필터이고, 슬라이딩 윈도 안에서 특정 주파수 빈의 진폭을 추출하며 DTMF 디코딩 문헌에서 자주 언급됨
      이런 필터 한 쌍의 출력을 비교해 디지털 출력을 만들 수 있음. 희소 슬라이딩 이산 푸리에 변환도 쓸 수 있지만, 주파수 빈 사이 보간이 더 번거로운 반면 Goertzel 필터는 그걸 대신 처리해 줌
    • 이건 디지털 신호 처리라는 큰 분야이고, 본질적으로 모뎀이나 사운드 카드의 아날로그-디지털 변환기가 하는 일임
      어떤 원시 신호든 바이트로 바꿔 주는 단일 알고리즘이나 소프트웨어는 알지 못함. 신호가 어떤 변조 방식을 쓰는지 파악하고, 해당 디코더를 찾거나 직접 작성해야 함. 일반적으로 필터링과 여러 수학 알고리즘이 들어가지만, 기본 디코딩용 프로그램은 꽤 짧고 단순한 편임
      배워두면 꽤 멋진 기술인데, 같은 기법을 온갖 곳에 쓸 수 있기 때문임. 예를 들어 DSP를 조금 배우고 나니 무선 통신, 음악과 사운드 디자인, 이미지, 영상 처리에서 할 수 있는 일이 많이 열렸음
    • 글만 보면 쉬워 보임. 클록이 낮음에서 높음으로 바뀔 때 데이터 라인의 현재 레벨이 비트값이고, 시작점을 찾으려면 1 하나와 0 일곱 개를 찾으면 됨
    • Pulseview https://github.com/sigrokproject/pulseview와 Sigrok 프로젝트의 다른 부분들 https://github.com/sigrokproject을 보면 될 듯함
      또는 글쓴이가 DSlogic을 언급했으니, 해당 논리 분석기 제조사가 만든 그 프로그램들의 포크가 있을 수도 있음
    • 그 시대의 로딩 루틴은 DC 영점 교차 횟수를 세어서 X번 교차하면 0, Y번 교차하면 1로 바꿀 뿐이고, 주파수나 진폭은 신경 쓰지 않음
      원시 신호는 보통 안정적인 에지를 위한 히스테리시스를 구현하려고 슈미트 트리거에 들어감. 그렇게 하면 테이프 신호의 극성과 모터 편차가 보정됨
  • “별도 물리 TPM을 쓰면 실제로 보안이 감소한다”는 부분이 아이러니함
    2015년 내 노트북에는 물리 TPM이 없었고, 켜려고 하니 “호환 TPM 없이 BitLocker 허용(USB 플래시 드라이브의 암호 또는 시작 키 필요)”이라고 나와서 덜 안전하다고 생각했음. 어차피 BitLocker를 안 써서 다행임

  • Windows Vista 시절처럼 명령 프롬프트 이름을 접근성 처리기로 바꾸는 초등학교식 트릭이 아직도 그대로 통한다는 사실이 너무 웃김
    로그인 없이 관리자 권한으로 실행되는 것이라면 Windows가 인증을 할 거라고 상상하게 되는데, Windows는 75%가 보안 연극이고 나머지 25%도 다른 종류의 연극처럼 보임

  • 2021년에 같은 기법이 설명됐음:
    https://dolosgroup.io/blog/2021/7/9/from-stolen-laptop-to-in...