VPK (file format)/Vampire: The Masquerade – Bloodlines: Difference between revisions
m (Tweak footer section) |
m (Use syntaxhighlight tags over source tags) |
||
Line 17: | Line 17: | ||
VPK files have no header, but they do have a footer which acts in the same capacity as a header would, vaguely resembling a ZIP file in this regard. All VPKs should be at minimum 9 bytes long to contain the footer, and empty VPKs will be 9 null bytes. There are multiple empty VPKs shipped with {{Vtmb|1}} for unknown reasons. | VPK files have no header, but they do have a footer which acts in the same capacity as a header would, vaguely resembling a ZIP file in this regard. All VPKs should be at minimum 9 bytes long to contain the footer, and empty VPKs will be 9 null bytes. There are multiple empty VPKs shipped with {{Vtmb|1}} for unknown reasons. | ||
< | <syntaxhighlight lang=cpp>struct VPKFooter | ||
{ | { | ||
unsigned int FileCount; | unsigned int FileCount; | ||
unsigned int DirectoryOffset; // Absolute from the start of the VPK | unsigned int DirectoryOffset; // Absolute from the start of the VPK | ||
unsigned char Version; // Always 0 | unsigned char Version; // Always 0 | ||
};</ | };</syntaxhighlight> | ||
Since the version field is at the end of this struct, we can assume that the game is in fact reading each field sequentially in reverse. This would mean the version is being read before the other fields, which is sensible and follows the pattern of many other pack file formats. Your implementation may read the footer in any order however, because the version should always be zero. | Since the version field is at the end of this struct, we can assume that the game is in fact reading each field sequentially in reverse. This would mean the version is being read before the other fields, which is sensible and follows the pattern of many other pack file formats. Your implementation may read the footer in any order however, because the version should always be zero. | ||
Line 30: | Line 30: | ||
At the directory offset specified in the header, <code>FileCount</code> entries exist in a tightly packed array. The directory tree is usually written directly before the footer, but it can appear at any location in the file. Contrary to the footer's flow, the directory offset (and all offsets in the file entries) point to the beginning of the given data, and all reads from this point forward should add to the offset, not subtract from it. | At the directory offset specified in the header, <code>FileCount</code> entries exist in a tightly packed array. The directory tree is usually written directly before the footer, but it can appear at any location in the file. Contrary to the footer's flow, the directory offset (and all offsets in the file entries) point to the beginning of the given data, and all reads from this point forward should add to the offset, not subtract from it. | ||
< | <syntaxhighlight lang=cpp>struct VPKFileEntry | ||
{ | { | ||
unsigned int PathLength; | unsigned int PathLength; | ||
Line 36: | Line 36: | ||
unsigned int Offset; // Absolute from the start of the VPK | unsigned int Offset; // Absolute from the start of the VPK | ||
unsigned int Length; | unsigned int Length; | ||
};</ | };</syntaxhighlight> | ||
=== File Contents === | === File Contents === |
Revision as of 15:36, 16 February 2025
VPK ("Vampire PacK") is a package format used by Vampire: The Masquerade – Bloodlines. It is a completely separate format from Valve's .vpk file format, added in
Source (Left 4 Dead engine branch), now used in all modern
Source and
Source 2 games.
Vampire pack files can be opened with VPKEdit and PackFile Explorer (shipped with Unofficial Patch's Bloodlines SDK).
From this point on they will be referred to as VPKs for ease of communication.
Features
Self-contained
VPKs do not use any external archives like chunked Valve pack files. Instead, multiple standalone VPKs can be created, and the game will load them all as long as their filenames are formatted correctly. Their filenames must match packXYY.vpk
where X and Y are both integers starting at 0.
File Format
VPK files have no header, but they do have a footer which acts in the same capacity as a header would, vaguely resembling a ZIP file in this regard. All VPKs should be at minimum 9 bytes long to contain the footer, and empty VPKs will be 9 null bytes. There are multiple empty VPKs shipped with Vampire: The Masquerade – Bloodlines for unknown reasons.
struct VPKFooter
{
unsigned int FileCount;
unsigned int DirectoryOffset; // Absolute from the start of the VPK
unsigned char Version; // Always 0
};
Since the version field is at the end of this struct, we can assume that the game is in fact reading each field sequentially in reverse. This would mean the version is being read before the other fields, which is sensible and follows the pattern of many other pack file formats. Your implementation may read the footer in any order however, because the version should always be zero.
File Entries
At the directory offset specified in the header, FileCount
entries exist in a tightly packed array. The directory tree is usually written directly before the footer, but it can appear at any location in the file. Contrary to the footer's flow, the directory offset (and all offsets in the file entries) point to the beginning of the given data, and all reads from this point forward should add to the offset, not subtract from it.
struct VPKFileEntry
{
unsigned int PathLength;
char Path[PathLength]; // Is NOT null-terminated!
unsigned int Offset; // Absolute from the start of the VPK
unsigned int Length;
};
File Contents
Seeking to the given Offset
and reading Length
bytes will return the file data at the given Path
. Each file entry maps to one file.
File contents are usually stored from the very start of the file to the file entry list, but just like the entry list, there is no rule requiring this to be the case.
See also
- VPKEdit - Can browse, edit, and create Vampire PacK files
- Bloodlines SDK - Can browse and create Vampire PacK files
- VPK (file format) - Valve PacK file format, entirely separate from Vampire PacK file format