이 저장소에는 기계 코드에서 재현 된 Windows 시스템 용 밸브 방지 소스 코드의 일부가 포함되어 있습니다.
VAC (Valve Anti-Cheat)는 밸브에서 개발 한 사용자 모드 비 침습적 안티 cheat 시스템입니다. 원격 서버에서 스트리밍 된 모듈 (DLL) 형태로 제공됩니다. steamservice.dll 은 SteamService.exe (또는 admin으로 실행되면 Steam.exe )에로드됨에 따라 체트 방지 모듈을 준비하고 실행합니다. 클라이언트 VAC 인프라는 C++ 사용하여 구축되지만 (분해에 존재하는 많은 thiscall 컨벤션 기능으로 표시)이 리포지어에는 단순성을위한 C 코드가 포함되어 있습니다. 안티 cheat 바이너리는 현재 32-bit 입니다.
| ID | 목적 | . 텍스트 섹션 원시 크기 | 소스 폴더 |
|---|---|---|---|
| 1 | 시스템 구성에 대한 정보를 수집하십시오. 이 모듈은 진공 분석 게임이 시작되기 전에도 먼저로드됩니다. | 0x5C00 | 모듈/SystemInfo |
| 2 | 실행되는 프로세스 및 핸들을 열거하십시오. 이 모듈은 게임이 시작된 직후에로드되지만 나중에 반복적으로로드됩니다. | 0x4A00 | 모듈/ProcessHandlEList |
| 3 | steamservice.dll 에서 생성 한 파일 핑에서 VacProcessMonitor 데이터를 수집하십시오. virtual methods (polymorphism) 사용하는 것이 관찰 된 첫 번째 모듈입니다. | 0x6600 | 모듈/프로세스 모니터 |
VAC는 여러 암호화 / 해싱 방법을 사용합니다.
NtQuerySystemInformation . 문자열은 ^ 또는 > 또는 & char와 함께 xor-ed입니다.이 모듈은 진공 분석 게임이 시작되기 전에도 먼저로드됩니다.
첫 번째 모듈에서는 GetVersion 기능을 호출하여 메이저를 검색하고 시스템 버전을 빌드하여 0x47BB0A00 작성합니다.
18363 )10 ) 모듈은 GetNativeSystemInfo 함수를 호출하고 결과 SYSTEM_INFO struct에서 필드를 읽습니다.
그런 다음 SystemInformationClass 값 (코드에 표시된 순서대로)을 사용하여 NtQuerySystemInformation API 함수를 호출합니다.
SYSTEM_TIMEOFDAY_INFORMATION struct를 반환합니다. VAC는 두 필드를 사용합니다.SYSTEM_CODEINTEGRITY_INFORMATION , 모듈은 CodeIntegrityOptions 필드를 저장합니다SYSTEM_DEVICE_INFORMATION , 모듈은 NumberOfDisks 필드를 저장합니다SYSTEM_KERNEL_DEBUGGER_INFORMATION , VAC는 전체 구조물을 사용합니다SYSTEM_BOOT_ENVIRONMENT_INFORMATION , VAC Copies BootIdentifier GuidSYSTEM_RANGE_START_INFORMATION 은 단지 void* 입니다. 방지 방지 저장 반환 된 커널 공간 시작 주소 및 해당 주소의 부호 비트 (VAC가 실행중인 실행 파일이 LARGEADDRESSAWARE 옵션과 연결되어 있는지 확인하십시오). SYSTEM_INFORMATION_CLASS enum에 대한 자세한 내용은 Geoff Chappell의 페이지를 참조하십시오.
다음으로, 안티 셰이트 호출은 GetProcessImageFileNameA 함수 기능을 수행하여 현재 실행 파일의 경로를 검색하고 마지막 36 자 (예 : Program Files (x86)SteamSteam.exe )를 읽습니다.
나중에 VAC는 GetSystemDirectoryW 사용하여 시스템 디렉토리 경로 (예 C:WINDOWSsystem32 )를 검색하고이를 넓은 차에서 멀티 바이트 스트링으로 변환하여이를 저장합니다 (Multibyte String의 최대 길이 -200). 안티 체트 쿼리 폴더 fileId ( GetFileInformationByHandleEx 사용) 및 볼륨 일련 번호 ( GetVolumeInformationByHandleW ). 또한 GetWindowsDirectoryW API에서 얻은 Windows 디렉토리 와 동일합니다.
Module은 System Directory 에서 NtDll.dll 파일을 읽고 일부 처리를 수행합니다 (아직 반전되지 않음).
VAC는 수입 시스템 DLL (Max 16,이 진공 모듈로드)의 핸들 (기본 주소)을 저장하고 Winapi 함수에 대한 포인터 (Max 160, 모듈은 172 기능을 사용합니다). 이는 기능 주소가 해당 모듈베이스 보다 낮 으면 기능을 고정시켰다.
안티 셰이트는 비트와 리턴 주소를 수행하여 자체 모듈베이스를 받습니다 ( _ReturnAddress() & 0xFFFF0000 ). 그런 다음 수집합니다.
다음으로 FindFirstVolumeW / FindNextVolumeW API를 사용하여 볼륨을 열거합니다. VAC는 GetVolumeInformationW , GetDriveTypeW 및 GetVolumePathNamesForVolumeNameW 기능을 호출하여 볼륨 정보를 쿼리합니다.
struct VolumeData {
UINT volumeGuidHash;
DWORD getVolumeInformationError;
DWORD fileSystemFlags;
DWORD volumeSerialNumber;
UINT volumeNameHash;
UINT fileSystemNameHash;
WORD driveType;
WORD volumePathNameLength;
DWORD volumePathNameHash;
}; // sizeof(VolumeData) == 32Vac는 Max의 데이터를 수집합니다. 10 권.
이 모듈이 Vac-recured 게임이 시작된 후 스트리밍 된 경우, OpenProcess API 사용 ( OpenProcess API 사용)을 처리해야합니다.
결국, 모듈은 데이터 (2048 바이트), dword by dword xoring server에서 수신 된 키와 함께 dword (예 : 0x1d4855d3)
공개 ...
이 모듈은 비교적 new 것으로 보이거나 오랫동안 비활성화되었습니다. January 2020 모듈을 처음 보았습니다. 다양한 유형의 스캔을 수행 할 수 있습니다 (현재 3 ). 추가 스캔은 이전 스캔의 결과에 달려 있습니다.
각 스캔 유형은 기본 클래스의 four methods 구현합니다.
처음에 VAC 서버는 클라이언트에게 scan #1 수행하도록 지시합니다.
첫 번째 스캔 기능은 Steam_{E9FD3C51-9B58-4DA0-962C-734882B19273}_Pid:%000008X 파일핑을 열 수 있습니다. 매핑에는 다음 레이아웃이 있습니다.
struct VacProcessMonitorMapping {
DWORD magic; // when initialized - 0x30004
PVOID vacProcessMonitor;
}; // sizeof(VacProcessMonitorMapping) == 8 VacProcessMonitorMapping::vacProcessMonitor 는 VacProcessMonitor 객체 (크기 292 bytes )에 대한 포인터입니다.
그런 다음 VAC는 전체 VacProcessMonitor Object (292 바이트) 및 VMT (가상 메소드 테이블)를 6 방법 (24 바이트)으로 포함합니다. steamservice.dll 의 기본 주소도 수집됩니다.
이 데이터는 아마도 VacProcessMonitor 를 감지하기 위해 VAC 서버에서 사용될 수 있습니다. 절차는 다음과 같습니다.
if (method_ptr & 0xFFFF0000 != steamservice_base)
hook_detected ();