//////////////////////////////////////////////////////////////////////////////// // // Risen PAK file format specs. // (all values are little-endian) // Copyright (c) 2011 Nico Bendlin // // +---------------+ // | file header | // +---------------+ // | file data | // +---------------+ // | entry table | // +---------------+ // // All offsets are absolute (relative to the start of the header). // All timestamps represent the number of 100-nanosecond intervals // since January 1, 1601 (a Microsoft Windows FILETIME structure). // //////////////////////////////////////////////////////////////////////////////// enum RisenPakEncryption : uint32_t { RisenPakEncryption_None = 0x00000000 }; enum RisenPakCompression : uint32_t { RisenPakCompression_None = 0x00000000, RisenPakCompression_Auto = 0x00000001, RisenPakCompression_ZLib = 0x00000002 }; enum RisenPakAttributes : uint32_t { RisenPakAttribute_ReadOnly = 0x00000001, // FILE_ATTRIBUTE_READONLY RisenPakAttribute_Hidden = 0x00000002, // FILE_ATTRIBUTE_HIDDEN RisenPakAttribute_System = 0x00000004, // FILE_ATTRIBUTE_SYSTEM RisenPakAttribute_Directory = 0x00000010, // FILE_ATTRIBUTE_DIRECTORY RisenPakAttribute_Archive = 0x00000020, // FILE_ATTRIBUTE_ARCHIVE RisenPakAttribute_Normal = 0x00000080, // FILE_ATTRIBUTE_NORMAL RisenPakAttribute_Temporary = 0x00000100, // FILE_ATTRIBUTE_TEMPORARY RisenPakAttribute_Compressed = 0x00000800, // FILE_ATTRIBUTE_COMPRESSED RisenPakAttribute_NotIndexed = 0x00002000, // FILE_ATTRIBUTE_NOT_CONTENT_INDEXED RisenPakAttribute_Encrypted = 0x00004000, // FILE_ATTRIBUTE_ENCRYPTED RisenPakAttribute_Deleted = 0x00008000, // Not used in Risen PAKs RisenPakAttribute_Virtual = 0x00010000, // FILE_ATTRIBUTE_VIRTUAL RisenPakAttribute_Packed = 0x00020000, // Stored in a PAK volume RisenPakAttribute_Cached = 0x00040000 // Not used in Risen PAKs }; struct RisenPakHeader { uint32_t Version; // 0x00000001 uint32_t Product; // 0x30563347 ("G3V0") uint32_t Revision; // 0x00000000 enum RisenPakEncryption Encryption; enum RisenPakCompression Compression; uint32_t Reserved; // 0x00000000 uint64_t DataOffset; // sizeof(struct RisenPakHeader) uint64_t RootOffset; // class RisenPakDirectory uint64_t VolumeSize; }; class RisenPakFile { uint32_t NameLength; char8_t NameString[NameLength + (NameLength != 0)]; uint64_t DataOffset; uint64_t TimeCreated; // FILETIME uint64_t TimeLastAccessed; // FILETIME uint64_t TimeLastModified; // FILETIME uint32_t FileAttributes; // FILE_ATTRIBUTE_* | 0x00020000 enum RisenPakEncryption Encryption; enum RisenPakCompression Compression; uint32_t DataSize; uint32_t FileSize; } class RisenPakDirectory { uint32_t NameLength; char8_t NameString[NameLength + (NameLength != 0)]; uint64_t TimeCreated; // FILETIME uint64_t TimeLastAccessed; // FILETIME uint64_t TimeLastModified; // FILETIME uint32_t FileAttributes; // FILE_ATTRIBUTE_* | 0x00020000 uint32_t Count; for( Count ) { enum RisenPakAttributes Attributes; if( RisenPakAttribute_Directory & Attributes ) { class RisenPakDirectory Directory; } else { class RisenPakFile File; } } }