mirror of
				https://github.com/hedge-dev/XenonRecomp.git
				synced 2025-11-04 06:47:09 +00:00 
			
		
		
		
	PowerUtils: implemented XDBF wrapper
This commit is contained in:
		
							
								
								
									
										203
									
								
								PowerUtils/xdbf.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										203
									
								
								PowerUtils/xdbf.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,203 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include <xbox.h>
 | 
			
		||||
 | 
			
		||||
#define XDBF_SIGNATURE 0x58444246
 | 
			
		||||
#define XACH_SIGNATURE 0x58414348
 | 
			
		||||
 | 
			
		||||
struct XDBFHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> EntryTableLength;
 | 
			
		||||
    be<uint32_t> EntryCount;
 | 
			
		||||
    be<uint32_t> FreeSpaceTableLength;
 | 
			
		||||
    be<uint32_t> FreeSpaceTableEntryCount;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
enum EXDBFNamespace : uint16_t
 | 
			
		||||
{
 | 
			
		||||
    XDBF_SPA_NAMESPACE_METADATA = 1,
 | 
			
		||||
    XDBF_SPA_NAMESPACE_IMAGE = 2,
 | 
			
		||||
    XDBF_SPA_NAMESPACE_STRING_TABLE = 3,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_ACHIEVEMENT = 1,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_IMAGE = 2,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_SETTING = 3,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_TITLE = 4,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_STRING = 5,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_ACHIEVEMENT_SECURITY_GFWL = 6,
 | 
			
		||||
    XDBF_GPD_NAMESPACE_AVATAR_AWARD_360 = 6
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#pragma pack(1)
 | 
			
		||||
struct XDBFEntry
 | 
			
		||||
{
 | 
			
		||||
    be<EXDBFNamespace> NamespaceID;
 | 
			
		||||
    be<uint64_t> ResourceID;
 | 
			
		||||
    be<uint32_t> Offset;
 | 
			
		||||
    be<uint32_t> Length;
 | 
			
		||||
};
 | 
			
		||||
#pragma pack()
 | 
			
		||||
 | 
			
		||||
struct XDBFFreeSpaceEntry
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Offset;
 | 
			
		||||
    be<uint32_t> Length;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
enum EXDBFLanguage : uint32_t
 | 
			
		||||
{
 | 
			
		||||
    XDBF_LANGUAGE_UNKNOWN = 0,
 | 
			
		||||
    XDBF_LANGUAGE_ENGLISH = 1,
 | 
			
		||||
    XDBF_LANGUAGE_JAPANESE = 2,
 | 
			
		||||
    XDBF_LANGUAGE_GERMAN = 3,
 | 
			
		||||
    XDBF_LANGUAGE_FRENCH = 4,
 | 
			
		||||
    XDBF_LANGUAGE_SPANISH = 5,
 | 
			
		||||
    XDBF_LANGUAGE_ITALIAN = 6,
 | 
			
		||||
    XDBF_LANGUAGE_KOREAN = 7,
 | 
			
		||||
    XDBF_LANGUAGE_CHINESE_TRAD = 8,
 | 
			
		||||
    XDBF_LANGUAGE_PORTUGUESE = 9,
 | 
			
		||||
    XDBF_LANGUAGE_CHINESE_SIMP = 10,
 | 
			
		||||
    XDBF_LANGUAGE_POLISH = 11,
 | 
			
		||||
    XDBF_LANGUAGE_RUSSIAN = 12,
 | 
			
		||||
    XDBF_LANGUAGE_MAX
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XSTCHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> Size;
 | 
			
		||||
    be<EXDBFLanguage> Language;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#pragma pack(1)
 | 
			
		||||
struct XSTRHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> Size;
 | 
			
		||||
    be<uint16_t> StringCount;
 | 
			
		||||
};
 | 
			
		||||
#pragma pack()
 | 
			
		||||
 | 
			
		||||
struct XSTREntry
 | 
			
		||||
{
 | 
			
		||||
    be<uint16_t> ID;
 | 
			
		||||
    be<uint16_t> Length;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#pragma pack(1)
 | 
			
		||||
struct XACHHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> Size;
 | 
			
		||||
    be<uint16_t> AchievementCount;
 | 
			
		||||
};
 | 
			
		||||
#pragma pack()
 | 
			
		||||
 | 
			
		||||
enum EXACHFlags : uint32_t
 | 
			
		||||
{
 | 
			
		||||
    XACH_TYPE_COMPLETION = 1U,
 | 
			
		||||
    XACH_TYPE_LEVELING = 2U,
 | 
			
		||||
    XACH_TYPE_UNLOCK = 3U,
 | 
			
		||||
    XACH_TYPE_EVENT = 4U,
 | 
			
		||||
    XACH_TYPE_TOURNAMENT = 5U,
 | 
			
		||||
    XACH_TYPE_CHECKPOINT = 6U,
 | 
			
		||||
    XACH_TYPE_OTHER = 7U,
 | 
			
		||||
    XACH_TYPE_MASK = 7U,
 | 
			
		||||
    XACH_STATUS_UNACHIEVED = (1U << 4),
 | 
			
		||||
    XACH_STATUS_EARNED_ONLINE = (1U << 16),
 | 
			
		||||
    XACH_STATUS_EARNED = (1U << 17),
 | 
			
		||||
    XACH_STATUS_EDITED = (1U << 20)
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XACHEntry
 | 
			
		||||
{
 | 
			
		||||
    be<uint16_t> AchievementID;
 | 
			
		||||
    be<uint16_t> NameID;
 | 
			
		||||
    be<uint16_t> UnlockedDescID;
 | 
			
		||||
    be<uint16_t> LockedDescID;
 | 
			
		||||
    be<uint32_t> ImageID;
 | 
			
		||||
    be<uint16_t> Gamerscore;
 | 
			
		||||
    char pad0[0x02];
 | 
			
		||||
    be<EXACHFlags> Flags;
 | 
			
		||||
    char pad1[0x10];
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
union XDBFTitleID
 | 
			
		||||
{
 | 
			
		||||
    struct
 | 
			
		||||
    {
 | 
			
		||||
        be<uint16_t> u16;
 | 
			
		||||
        char u8[0x02];
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    be<uint32_t> u32;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XDBFTitleVersion
 | 
			
		||||
{
 | 
			
		||||
    be<uint16_t> Major;
 | 
			
		||||
    be<uint16_t> Minor;
 | 
			
		||||
    be<uint16_t> Build;
 | 
			
		||||
    be<uint16_t> Revision;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
enum EXDBFTitleType : uint32_t
 | 
			
		||||
{
 | 
			
		||||
    XDBF_TITLE_TYPE_SYSTEM = 0,
 | 
			
		||||
    XDBF_TITLE_TYPE_FULL = 1,
 | 
			
		||||
    XDBF_TITLE_TYPE_DEMO = 2,
 | 
			
		||||
    XDBF_TITLE_TYPE_DOWNLOAD = 3
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XTHDHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> Size;
 | 
			
		||||
    XDBFTitleID TitleID;
 | 
			
		||||
    be<EXDBFTitleType> Type;
 | 
			
		||||
    XDBFTitleVersion TitleVersion;
 | 
			
		||||
    char pad0[0x10];
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#pragma pack(1)
 | 
			
		||||
struct XGAAHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> Size;
 | 
			
		||||
    be<uint16_t> Count;
 | 
			
		||||
};
 | 
			
		||||
#pragma pack()
 | 
			
		||||
 | 
			
		||||
struct XGAAEntry
 | 
			
		||||
{
 | 
			
		||||
    char pad0[0x04];
 | 
			
		||||
    be<uint16_t> AvatarAwardID;
 | 
			
		||||
    char pad1[0x06];
 | 
			
		||||
    XDBFTitleID TitleID;
 | 
			
		||||
    be<uint16_t> NameID;
 | 
			
		||||
    be<uint16_t> UnlockedDescID;
 | 
			
		||||
    be<uint16_t> LockedDescID;
 | 
			
		||||
    char pad2[0x02];
 | 
			
		||||
    be<uint32_t> ImageID;
 | 
			
		||||
    char pad3[0x08];
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XSRCHeader
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> Signature;
 | 
			
		||||
    be<uint32_t> Version;
 | 
			
		||||
    be<uint32_t> Size;
 | 
			
		||||
    be<uint32_t> FileNameLength;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XSRCHeader2
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> UncompressedSize;
 | 
			
		||||
    be<uint32_t> CompressedSize;
 | 
			
		||||
};
 | 
			
		||||
							
								
								
									
										152
									
								
								PowerUtils/xdbf_wrapper.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										152
									
								
								PowerUtils/xdbf_wrapper.cpp
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,152 @@
 | 
			
		||||
#include "xdbf_wrapper.h"
 | 
			
		||||
 | 
			
		||||
XDBFWrapper::XDBFWrapper(const uint8_t* buffer, size_t bufferSize) : pBuffer(buffer), BufferSize(bufferSize)
 | 
			
		||||
{
 | 
			
		||||
    if (!buffer || bufferSize <= sizeof(XDBFHeader))
 | 
			
		||||
    {
 | 
			
		||||
        pBuffer = nullptr;
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    auto seek = pBuffer;
 | 
			
		||||
 | 
			
		||||
    pHeader = (XDBFHeader*)seek;
 | 
			
		||||
    seek += sizeof(XDBFHeader);
 | 
			
		||||
 | 
			
		||||
    if (pHeader->Signature != XDBF_SIGNATURE)
 | 
			
		||||
    {
 | 
			
		||||
        pBuffer = nullptr;
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pEntries = (XDBFEntry*)seek;
 | 
			
		||||
    seek += sizeof(XDBFEntry) * pHeader->EntryCount;
 | 
			
		||||
 | 
			
		||||
    pFiles = (XDBFFreeSpaceEntry*)seek;
 | 
			
		||||
    seek += sizeof(XDBFFreeSpaceEntry) * pHeader->FreeSpaceTableLength;
 | 
			
		||||
 | 
			
		||||
    pContent = seek;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
XDBFBlock XDBFWrapper::GetResource(EXDBFNamespace ns, uint64_t id) const
 | 
			
		||||
{
 | 
			
		||||
    for (int i = 0; i < pHeader->EntryCount; i++)
 | 
			
		||||
    {
 | 
			
		||||
        auto& entry = pEntries[i];
 | 
			
		||||
 | 
			
		||||
        if (entry.NamespaceID == ns && entry.ResourceID == id)
 | 
			
		||||
        {
 | 
			
		||||
            XDBFBlock block{};
 | 
			
		||||
            block.pBuffer = pContent + entry.Offset;
 | 
			
		||||
            block.BufferSize = entry.Length;
 | 
			
		||||
            return block;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return { nullptr };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string XDBFWrapper::GetString(EXDBFLanguage language, uint16_t id) const
 | 
			
		||||
{
 | 
			
		||||
    auto languageBlock = GetResource(XDBF_SPA_NAMESPACE_STRING_TABLE, (uint64_t)language);
 | 
			
		||||
 | 
			
		||||
    if (!languageBlock)
 | 
			
		||||
        return "";
 | 
			
		||||
 | 
			
		||||
    auto pHeader = (XSTRHeader*)languageBlock.pBuffer;
 | 
			
		||||
    auto seek = languageBlock.pBuffer + sizeof(XSTRHeader);
 | 
			
		||||
 | 
			
		||||
    for (int i = 0; i < pHeader->StringCount; i++)
 | 
			
		||||
    {
 | 
			
		||||
        auto entry = (XSTREntry*)seek;
 | 
			
		||||
 | 
			
		||||
        seek += sizeof(XSTREntry);
 | 
			
		||||
 | 
			
		||||
        if (entry->ID == id)
 | 
			
		||||
            return std::string((const char*)seek, entry->Length);
 | 
			
		||||
 | 
			
		||||
        seek += entry->Length;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return "";
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::vector<Achievement> XDBFWrapper::GetAchievements(EXDBFLanguage language) const
 | 
			
		||||
{
 | 
			
		||||
    std::vector<Achievement> result;
 | 
			
		||||
 | 
			
		||||
    auto achievementsBlock = GetResource(XDBF_SPA_NAMESPACE_METADATA, XACH_SIGNATURE);
 | 
			
		||||
 | 
			
		||||
    if (!achievementsBlock)
 | 
			
		||||
        return result;
 | 
			
		||||
 | 
			
		||||
    auto pHeader = (XACHHeader*)achievementsBlock.pBuffer;
 | 
			
		||||
    auto seek = achievementsBlock.pBuffer + sizeof(XACHHeader);
 | 
			
		||||
 | 
			
		||||
    for (int i = 0; i < pHeader->AchievementCount; i++)
 | 
			
		||||
    {
 | 
			
		||||
        auto entry = (XACHEntry*)seek;
 | 
			
		||||
 | 
			
		||||
        seek += sizeof(XACHEntry);
 | 
			
		||||
 | 
			
		||||
        Achievement achievement{};
 | 
			
		||||
        achievement.ID = entry->AchievementID;
 | 
			
		||||
        achievement.Name = GetString(language, entry->NameID);
 | 
			
		||||
        achievement.UnlockedDesc = GetString(language, entry->UnlockedDescID);
 | 
			
		||||
        achievement.LockedDesc = GetString(language, entry->LockedDescID);
 | 
			
		||||
        achievement.Score = entry->Gamerscore;
 | 
			
		||||
 | 
			
		||||
        auto imageBlock = GetResource(XDBF_SPA_NAMESPACE_IMAGE, entry->ImageID);
 | 
			
		||||
 | 
			
		||||
        if (imageBlock)
 | 
			
		||||
        {
 | 
			
		||||
            achievement.pImageBuffer = imageBlock.pBuffer;
 | 
			
		||||
            achievement.ImageBufferSize = imageBlock.BufferSize;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        result.push_back(achievement);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return result;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Achievement XDBFWrapper::GetAchievement(EXDBFLanguage language, uint16_t id) const
 | 
			
		||||
{
 | 
			
		||||
    Achievement result{};
 | 
			
		||||
 | 
			
		||||
    auto achievementsBlock = GetResource(XDBF_SPA_NAMESPACE_METADATA, 0x58414348);
 | 
			
		||||
 | 
			
		||||
    if (!achievementsBlock)
 | 
			
		||||
        return result;
 | 
			
		||||
 | 
			
		||||
    auto pHeader = (XACHHeader*)achievementsBlock.pBuffer;
 | 
			
		||||
    auto seek = achievementsBlock.pBuffer + sizeof(XACHHeader);
 | 
			
		||||
 | 
			
		||||
    for (int i = 0; i < pHeader->AchievementCount; i++)
 | 
			
		||||
    {
 | 
			
		||||
        auto entry = (XACHEntry*)seek;
 | 
			
		||||
 | 
			
		||||
        seek += sizeof(XACHEntry);
 | 
			
		||||
 | 
			
		||||
        if (entry->AchievementID == id)
 | 
			
		||||
        {
 | 
			
		||||
            result.ID = entry->AchievementID;
 | 
			
		||||
            result.Name = GetString(language, entry->NameID);
 | 
			
		||||
            result.UnlockedDesc = GetString(language, entry->UnlockedDescID);
 | 
			
		||||
            result.LockedDesc = GetString(language, entry->LockedDescID);
 | 
			
		||||
            result.Score = entry->Gamerscore;
 | 
			
		||||
 | 
			
		||||
            auto imageBlock = GetResource(XDBF_SPA_NAMESPACE_IMAGE, entry->ImageID);
 | 
			
		||||
 | 
			
		||||
            if (imageBlock)
 | 
			
		||||
            {
 | 
			
		||||
                result.pImageBuffer = imageBlock.pBuffer;
 | 
			
		||||
                result.ImageBufferSize = imageBlock.BufferSize;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            return result;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return result;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										47
									
								
								PowerUtils/xdbf_wrapper.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										47
									
								
								PowerUtils/xdbf_wrapper.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,47 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include "xdbf.h"
 | 
			
		||||
 | 
			
		||||
struct Achievement
 | 
			
		||||
{
 | 
			
		||||
    uint16_t ID;
 | 
			
		||||
    std::string Name;
 | 
			
		||||
    std::string UnlockedDesc;
 | 
			
		||||
    std::string LockedDesc;
 | 
			
		||||
    const uint8_t* pImageBuffer;
 | 
			
		||||
    size_t ImageBufferSize;
 | 
			
		||||
    uint16_t Score;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct XDBFBlock
 | 
			
		||||
{
 | 
			
		||||
    const uint8_t* pBuffer;
 | 
			
		||||
    size_t BufferSize;
 | 
			
		||||
 | 
			
		||||
    operator bool() const
 | 
			
		||||
    {
 | 
			
		||||
        return pBuffer;
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
class XDBFWrapper
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
    const uint8_t* pBuffer;
 | 
			
		||||
    size_t BufferSize;
 | 
			
		||||
 | 
			
		||||
    const uint8_t* pContent;
 | 
			
		||||
 | 
			
		||||
    const XDBFHeader* pHeader;
 | 
			
		||||
    const XDBFEntry* pEntries;
 | 
			
		||||
    const XDBFFreeSpaceEntry* pFiles;
 | 
			
		||||
 | 
			
		||||
    XDBFWrapper() {}
 | 
			
		||||
    XDBFWrapper(const uint8_t* pBuffer, size_t bufferSize);
 | 
			
		||||
    XDBFBlock GetResource(EXDBFNamespace ns, uint64_t id) const;
 | 
			
		||||
    std::string GetString(EXDBFLanguage language, uint16_t id) const;
 | 
			
		||||
    std::vector<Achievement> GetAchievements(EXDBFLanguage language) const;
 | 
			
		||||
    Achievement GetAchievement(EXDBFLanguage language, uint16_t id) const;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
extern XDBFWrapper g_xdbf;
 | 
			
		||||
@@ -54,6 +54,14 @@ typedef struct _XEX_FILE_FORMAT_INFO
 | 
			
		||||
    be<uint16_t> CompressionType;
 | 
			
		||||
} XEX_FILE_FORMAT_INFO;
 | 
			
		||||
 | 
			
		||||
typedef struct _XEX_RESOURCE_INFO
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> SizeOfHeader;
 | 
			
		||||
    uint8_t ResourceID[8];
 | 
			
		||||
    be<uint32_t> Offset;
 | 
			
		||||
    be<uint32_t> SizeOfData;
 | 
			
		||||
} XEX_RESOURCE_INFO;
 | 
			
		||||
 | 
			
		||||
typedef struct _XEX_BASIC_FILE_COMPRESSION_INFO
 | 
			
		||||
{
 | 
			
		||||
    be<uint32_t> SizeOfData;
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user