ValvePak 5.0.2.177

dotnet add package ValvePak --version 5.0.2.177
                    
NuGet\Install-Package ValvePak -Version 5.0.2.177
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="ValvePak" Version="5.0.2.177" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="ValvePak" Version="5.0.2.177" />
                    
Directory.Packages.props
<PackageReference Include="ValvePak" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add ValvePak --version 5.0.2.177
                    
#r "nuget: ValvePak, 5.0.2.177"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package ValvePak@5.0.2.177
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=ValvePak&version=5.0.2.177
                    
Install as a Cake Addin
#tool nuget:?package=ValvePak&version=5.0.2.177
                    
Install as a Cake Tool

<h1 align="center"><img src="./Misc/logo.png" width="64" height="64" align="center"> Valve Pak for .NET</h1>

<p align="center"> <a href="https://github.com/ValveResourceFormat/ValvePak/actions" title="Build Status"><img alt="Build Status" src="https://img.shields.io/github/actions/workflow/status/ValveResourceFormat/ValvePak/ci.yml?logo=github&label=Build&logoColor=ffffff&style=for-the-badge&branch=master"></a> <a href="https://www.nuget.org/packages/ValvePak/" title="NuGet"><img alt="NuGet" src="https://img.shields.io/nuget/v/ValvePak.svg?logo=nuget&label=NuGet&logoColor=ffffff&color=004880&style=for-the-badge"></a> <a href="https://app.codecov.io/gh/ValveResourceFormat/ValvePak" title="Code Coverage"><img alt="Code Coverage" src="https://img.shields.io/codecov/c/github/ValveResourceFormat/ValvePak/master?logo=codecov&label=Coverage&logoColor=ffffff&color=F01F7A&style=for-the-badge"></a> </p>

A .NET library for reading and extracting VPK (Valve Pak) files, the uncompressed archive format used to package game content in Source and Source 2 engine games.

Usage

using var package = new Package();

// Open a vpk file
package.Read("pak01_dir.vpk");

// Can also pass in a stream
package.Read(File.OpenRead("pak01_dir.vpk"));

// Optionally verify hashes and signatures of the file if there are any
package.VerifyHashes();

// Find a file, this returns a PackageEntry
var file = package.FindEntry("path/to/file.txt");

if (file != null) {
	// Read a file to a byte array
	package.ReadEntry(file, out byte[] fileContents);

	// Inspect entry metadata
	Console.WriteLine(file.GetFullPath());  // "path/to/file.txt"
	Console.WriteLine(file.GetFileName());  // "file.txt"
	Console.WriteLine(file.TotalLength);    // file size in bytes
	Console.WriteLine(file.CRC32);          // CRC32 checksum
}

Do note that files such as pak01_001.vpk are just data files, you have to open pak01_dir.vpk.

Extract all files

using var package = new Package();
package.Read("pak01_dir.vpk");

foreach (var group in package.Entries)
{
	foreach (var entry in group.Value)
	{
		var filePath = entry.GetFullPath();

		package.ReadEntry(entry, out byte[] data);

		// Create the directory if needed, then write the file
		Directory.CreateDirectory(Path.GetDirectoryName(filePath));
		File.WriteAllBytes(filePath, data);
	}
}

Create a VPK

using var package = new Package();

// Add files to the package
package.AddFile("path/to/file.txt", File.ReadAllBytes("file.txt"));
package.AddFile("models/example.vmdl", File.ReadAllBytes("example.vmdl"));

// Remove a file from the package
package.RemoveFile(package.FindEntry("path/to/file.txt"));

// Write the package to disk
package.Write("pak01_dir.vpk");

Optimize for many lookups

By default, FindEntry performs a linear scan. If you need to look up many files, call OptimizeEntriesForBinarySearch() before Read() to sort entries and use binary search instead. You can also pass StringComparison.OrdinalIgnoreCase for case-insensitive lookups.

using var package = new Package();

// Call before Read() to enable binary search for FindEntry
package.OptimizeEntriesForBinarySearch();
package.Read("pak01_dir.vpk");

// FindEntry calls are now significantly faster
var file = package.FindEntry("path/to/file.txt");

Read into a user-provided buffer

var entry = package.FindEntry("path/to/file.txt");

// Allocate your own buffer (must be at least entry.TotalLength bytes)
var buffer = new byte[entry.TotalLength];
package.ReadEntry(entry, buffer, validateCrc: true);

Using ArrayPool to avoid allocations when reading many files:

var entry = package.FindEntry("path/to/file.txt");

var buffer = ArrayPool<byte>.Shared.Rent((int)entry.TotalLength);

try
{
	package.ReadEntry(entry, buffer, validateCrc: true);

	// Use buffer[..entry.TotalLength] here
}
finally
{
	ArrayPool<byte>.Shared.Return(buffer);
}

Stream-based access

GetMemoryMappedStreamIfPossible returns a memory-mapped stream for large files (over 4 KiB) and a MemoryStream for smaller ones. This avoids reading the entire file into a byte array.

var entry = package.FindEntry("path/to/file.txt");

using var stream = package.GetMemoryMappedStreamIfPossible(entry);

Verification

using var package = new Package();
package.Read("pak01_dir.vpk");

// Verify MD5 hashes of the directory tree and whole file
package.VerifyHashes();

// Verify MD5/Blake3 hashes of individual chunk files (pak01_000.vpk, pak01_001.vpk, ...)
package.VerifyChunkHashes();

// Verify CRC32 checksums of every file in the package
package.VerifyFileChecksums();

// Verify the RSA signature if the package is signed
bool valid = package.IsSignatureValid();
Product Compatible and additional computed target framework versions.
.NET net10.0 is compatible.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages (3)

Showing the top 3 NuGet packages that depend on ValvePak:

Package Downloads
ValveResourceFormat

Parser, decompiler, and exporter for Valve's Source 2 resource file formats. Supports models, textures, materials, maps, particles, and more.

VPKTools

Utilities to parse Valve's PAK files for metadata purposes.

CS2CalloutExtractor

A library for extracting callouts from Counter-Strike 2 `.vpk` files.

GitHub repositories (1)

Showing the top 1 popular GitHub repositories that depend on ValvePak:

Repository Stars
ValveResourceFormat/ValveResourceFormat
Source 2 Viewer is an all-in-one tool to browse VPK archives, view, extract, and decompile Source 2 assets, including maps, models, materials, textures, sounds, and more.
Version Downloads Last Updated
5.0.2.177 622 8/8/2026
4.0.0.142 20,198 11/11/2025
3.0.3.132 2,258 9/22/2025
2.0.1.107 12,921 5/9/2024
2.0.0.101 487 3/22/2024
1.8.0.93 1,061 2/13/2024
1.7.0.88 2,203 1/7/2024
1.6.2.76 7,592 11/23/2023
1.6.1.71 3,614 9/8/2023
1.6.0.67 375 9/5/2023
1.5.0.59 1,979 7/14/2023
1.4.0.53 2,287 3/22/2023
1.3.0.33 3,680 4/29/2022
1.2.0.24 1,025 1/15/2022
1.1.0.1 5,550 11/23/2021
1.0.2.35 3,032 6/23/2020
1.0.2.29 3,309 3/21/2019
1.0.0.24-AppVeyor 719 3/19/2019
0.4.0.11 3,366 9/18/2016
0.3.0.9 1,794 9/18/2016
Loading failed