Make CDolLoader a bit more c++ish, make wii dols be detected by the presence of a mfspr x, HID4.
git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@6909 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
parent
470ed118f5
commit
d3b8908a7c
|
@ -243,6 +243,7 @@ typedef unsigned int ppc_word;
|
|||
case 1008: return "HID0";
|
||||
case 1009: return "HID1";
|
||||
case 1010: return "IABR";
|
||||
case 1011: return "HID4";
|
||||
case 1013: return "DABR";
|
||||
case 1017: return "L2CR";
|
||||
case 1019: return "ICTC";
|
||||
|
|
|
@ -231,8 +231,9 @@ bool CBoot::BootUp()
|
|||
// DOL
|
||||
case SCoreStartupParameter::BOOT_DOL:
|
||||
{
|
||||
CDolLoader dolLoader(_StartupPara.m_strFilename.c_str());
|
||||
// Check if we have gotten a Wii file or not
|
||||
bool dolWii = CDolLoader::IsDolWii(_StartupPara.m_strFilename.c_str());
|
||||
bool dolWii = dolLoader.IsWii();
|
||||
if (dolWii != _StartupPara.bWii)
|
||||
{
|
||||
PanicAlertT("Warning - starting DOL in wrong console mode!");
|
||||
|
@ -261,7 +262,7 @@ bool CBoot::BootUp()
|
|||
|
||||
if (!BS2Success)
|
||||
{
|
||||
CDolLoader dolLoader(_StartupPara.m_strFilename.c_str());
|
||||
dolLoader.Load();
|
||||
PC = dolLoader.GetEntryPoint();
|
||||
}
|
||||
|
||||
|
|
|
@ -17,18 +17,17 @@
|
|||
|
||||
#include "Boot_DOL.h"
|
||||
#include "FileUtil.h"
|
||||
|
||||
#include "../HW/Memmap.h"
|
||||
|
||||
#include "CommonFuncs.h"
|
||||
|
||||
CDolLoader::CDolLoader(u8* _pBuffer, u32 _Size)
|
||||
: m_bInit(false)
|
||||
: m_isWii(false)
|
||||
{
|
||||
m_bInit = Initialize(_pBuffer, _Size);
|
||||
Initialize(_pBuffer, _Size);
|
||||
}
|
||||
|
||||
CDolLoader::CDolLoader(const char* _szFilename)
|
||||
: m_bInit(false)
|
||||
CDolLoader::CDolLoader(const char* _szFilename)
|
||||
: m_isWii(false)
|
||||
{
|
||||
u64 size = File::GetSize(_szFilename);
|
||||
u8* tmpBuffer = new u8[(size_t)size];
|
||||
|
@ -37,27 +36,79 @@ CDolLoader::CDolLoader(const char* _szFilename)
|
|||
fread(tmpBuffer, (size_t)size, 1, pStream);
|
||||
fclose(pStream);
|
||||
|
||||
m_bInit = Initialize(tmpBuffer, (u32)size);
|
||||
delete[] tmpBuffer;
|
||||
Initialize(tmpBuffer, (u32)size);
|
||||
delete [] tmpBuffer;
|
||||
}
|
||||
|
||||
bool CDolLoader::Initialize(u8* _pBuffer, u32 _Size)
|
||||
CDolLoader::~CDolLoader()
|
||||
{
|
||||
for (int i = 0; i < DOL_NUM_TEXT; i++)
|
||||
{
|
||||
delete [] text_section[i];
|
||||
text_section[i] = NULL;
|
||||
}
|
||||
|
||||
for (int i = 0; i < DOL_NUM_DATA; i++)
|
||||
{
|
||||
delete [] data_section[i];
|
||||
data_section[i] = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
void CDolLoader::Initialize(u8* _pBuffer, u32 _Size)
|
||||
{
|
||||
memcpy(&m_dolheader, _pBuffer, sizeof(SDolHeader));
|
||||
|
||||
// swap memory
|
||||
u32* p = (u32*)&m_dolheader;
|
||||
for (size_t i=0; i<(sizeof(SDolHeader)>>2); i++)
|
||||
for (size_t i = 0; i < (sizeof(SDolHeader)/sizeof(u32)); i++)
|
||||
p[i] = Common::swap32(p[i]);
|
||||
|
||||
for (int i = 0; i < DOL_NUM_TEXT; i++)
|
||||
text_section[i] = NULL;
|
||||
for (int i = 0; i < DOL_NUM_DATA; i++)
|
||||
data_section[i] = NULL;
|
||||
|
||||
u32 HID4_pattern = 0x7c13fba6;
|
||||
u32 HID4_mask = 0xfc1fffff;
|
||||
|
||||
for (int i = 0; i < DOL_NUM_TEXT; i++)
|
||||
{
|
||||
if (m_dolheader.textOffset[i] != 0)
|
||||
{
|
||||
text_section[i] = new u8[m_dolheader.textSize[i]];
|
||||
memcpy(text_section[i], _pBuffer + m_dolheader.textOffset[i], m_dolheader.textSize[i]);
|
||||
for (int j = 0; j < (m_dolheader.textSize[i]/sizeof(u32)); j++)
|
||||
{
|
||||
u32 word = Common::swap32(((u32*)text_section[i])[j]);
|
||||
if ((word & HID4_mask) == HID4_pattern)
|
||||
{
|
||||
m_isWii = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = 0; i < DOL_NUM_DATA; i++)
|
||||
{
|
||||
if (m_dolheader.dataOffset[i] != 0)
|
||||
{
|
||||
data_section[i] = new u8[m_dolheader.dataSize[i]];
|
||||
memcpy(data_section[i], _pBuffer + m_dolheader.dataOffset[i], m_dolheader.dataSize[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CDolLoader::Load()
|
||||
{
|
||||
// load all text (code) sections
|
||||
for (int i = 0; i < DOL_NUM_TEXT; i++)
|
||||
{
|
||||
if (m_dolheader.textOffset[i] != 0)
|
||||
{
|
||||
u8* pTemp = &_pBuffer[m_dolheader.textOffset[i]];
|
||||
for (u32 num = 0; num < m_dolheader.textSize[i]; num++)
|
||||
Memory::Write_U8(pTemp[num], m_dolheader.textAddress[i] + num);
|
||||
Memory::Write_U8(text_section[i][num], m_dolheader.textAddress[i] + num);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -66,32 +117,8 @@ bool CDolLoader::Initialize(u8* _pBuffer, u32 _Size)
|
|||
{
|
||||
if (m_dolheader.dataOffset[i] != 0)
|
||||
{
|
||||
u8* pTemp = &_pBuffer[m_dolheader.dataOffset[i]];
|
||||
for (u32 num = 0; num < m_dolheader.dataSize[i]; num++)
|
||||
Memory::Write_U8(pTemp[num], m_dolheader.dataAddress[i] + num);
|
||||
Memory::Write_U8(data_section[i][num], m_dolheader.dataAddress[i] + num);
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
u32 CDolLoader::GetEntryPoint()
|
||||
{
|
||||
return m_dolheader.entryPoint;
|
||||
}
|
||||
|
||||
bool CDolLoader::IsDolWii(const char* filename)
|
||||
{
|
||||
// try to open file
|
||||
FILE* pStream = fopen(filename, "rb");
|
||||
if (pStream)
|
||||
{
|
||||
fseeko(pStream, 0xe0, SEEK_SET);
|
||||
u32 entrypt = fgetc(pStream) << 24 | fgetc(pStream) << 16 |
|
||||
fgetc(pStream) << 8 | fgetc(pStream);
|
||||
|
||||
fclose(pStream);
|
||||
return entrypt >= 0x80004000;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
|
@ -25,10 +25,13 @@ class CDolLoader
|
|||
public:
|
||||
CDolLoader(const char* _szFilename);
|
||||
CDolLoader(u8* _pBuffer, u32 _Size);
|
||||
~CDolLoader();
|
||||
|
||||
u32 GetEntryPoint();
|
||||
|
||||
static bool IsDolWii(const char* filename);
|
||||
bool IsWii() { return m_isWii; }
|
||||
u32 GetEntryPoint() { return m_dolheader.entryPoint; }
|
||||
|
||||
// Load into emulated memory
|
||||
void Load();
|
||||
|
||||
private:
|
||||
enum
|
||||
|
@ -36,26 +39,32 @@ private:
|
|||
DOL_NUM_TEXT = 7,
|
||||
DOL_NUM_DATA = 11
|
||||
};
|
||||
|
||||
struct SDolHeader
|
||||
{
|
||||
u32 textOffset[DOL_NUM_TEXT];
|
||||
u32 dataOffset[DOL_NUM_DATA];
|
||||
u32 textOffset[DOL_NUM_TEXT];
|
||||
u32 dataOffset[DOL_NUM_DATA];
|
||||
|
||||
u32 textAddress[DOL_NUM_TEXT];
|
||||
u32 dataAddress[DOL_NUM_DATA];
|
||||
u32 textAddress[DOL_NUM_TEXT];
|
||||
u32 dataAddress[DOL_NUM_DATA];
|
||||
|
||||
u32 textSize[DOL_NUM_TEXT];
|
||||
u32 dataSize[DOL_NUM_DATA];
|
||||
u32 textSize[DOL_NUM_TEXT];
|
||||
u32 dataSize[DOL_NUM_DATA];
|
||||
|
||||
u32 bssAddress;
|
||||
u32 bssSize;
|
||||
u32 entryPoint;
|
||||
u32 padd[7];
|
||||
u32 bssAddress;
|
||||
u32 bssSize;
|
||||
u32 entryPoint;
|
||||
u32 padd[7];
|
||||
};
|
||||
SDolHeader m_dolheader;
|
||||
bool m_bInit;
|
||||
|
||||
bool Initialize(u8* _pBuffer, u32 _Size);
|
||||
u8 *data_section[DOL_NUM_DATA];
|
||||
u8 *text_section[DOL_NUM_TEXT];
|
||||
|
||||
bool m_isWii;
|
||||
|
||||
// Copy sections to internal buffers
|
||||
void Initialize(u8* _pBuffer, u32 _Size);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -189,7 +189,8 @@ bool SCoreStartupParameter::AutoSetup(EBootBS2 _BootBS2)
|
|||
}
|
||||
else if (!strcasecmp(Extension.c_str(), ".dol"))
|
||||
{
|
||||
bWii = CDolLoader::IsDolWii(m_strFilename.c_str());
|
||||
CDolLoader dolfile(m_strFilename.c_str());
|
||||
bWii = dolfile.IsWii();
|
||||
Region = USA_DIR;
|
||||
m_BootType = BOOT_DOL;
|
||||
bNTSC = true;
|
||||
|
|
Loading…
Reference in New Issue