simplified EXI_DeviceMemoryCard.cpp,

warning fix for WII_IPC_HLE_Device_usb.cpp,
codecleanup and added the ability to create a formated
16Mb memcard in MemcardManager,
calibrate button is now easier to read in nJoy Testing

git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@1600 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
LPFaint99 2008-12-20 08:07:04 +00:00
parent a2a8be006a
commit c695ebd6f1
7 changed files with 294 additions and 344 deletions

View File

@ -30,6 +30,7 @@
#define MC_STATUS_ERASEERROR 0x10
#define MC_STATUS_PROGRAMEERROR 0x08
#define MC_STATUS_READY 0x01
#define SIZE_TO_Mb 1024 * 8 * 16
static CEXIMemoryCard *cards[2];
@ -76,34 +77,8 @@ CEXIMemoryCard::CEXIMemoryCard(const std::string& _rName, const std::string& _rF
u64 MemFileSize = ftell(pFile);
fseek(pFile, 0L, SEEK_SET);
switch ((MemFileSize / (8 * 1024)) - 5) // Convert the filesize in bytes to the "nintendo-size"
{
case 59:
nintendo_card_id = 0x00000004;
memory_card_size = 512 * 1024;
break;
case 123:
nintendo_card_id = 0x00000008;
memory_card_size = 1024 * 1024;
break;
case 251:
nintendo_card_id = 0x00000010;
memory_card_size = 2 * 1024 * 1024;
break;
case 507:
nintendo_card_id = 0x00000020;
memory_card_size = 4 * 1024 * 1024;
break;
case 1019:
nintendo_card_id = 0x00000040;
memory_card_size = 8 * 1024 * 1024;
break;
case 2043:
default:
nintendo_card_id = 0x00000080;
memory_card_size = 16 * 1024 * 1024;
break;
}
memory_card_size = (int)MemFileSize;
nintendo_card_id = memory_card_size / SIZE_TO_Mb;
memory_card_content = new u8[memory_card_size];
memset(memory_card_content, 0xFF, memory_card_size);
@ -116,7 +91,7 @@ CEXIMemoryCard::CEXIMemoryCard(const std::string& _rName, const std::string& _rF
{
// Create a new 128Mb memcard
nintendo_card_id = 0x00000080;
memory_card_size = 16 * 1024 * 1024;
memory_card_size = nintendo_card_id * SIZE_TO_Mb;
memory_card_content = new u8[memory_card_size];
memset(memory_card_content, 0xFF, memory_card_size);

View File

@ -394,7 +394,7 @@ u32 CWII_IPC_HLE_Device_usb_oh1_57e_305::Update()
// Why do we need this? 0 worked with the emulated wiimote in all games I tried
static int counter = 1000;
if (test && !stricmp(m_LocalName, "Wii") && (m_ScanEnable & 0x2))
if (test && !strcasecmp(m_LocalName, "Wii") && (m_ScanEnable & 0x2))
{
counter--;
if (counter < 0)

View File

@ -174,10 +174,10 @@ void CMemcardManager::CreateGUIControls()
{
// Create the controls for both memcards
// Loading invalid .raw files should no longer crash the app
m_MemcardPath_A = new wxFilePickerCtrl(this, ID_MEMCARDPATH_A, wxEmptyString, wxT("Choose a memory card:"),
wxT("Raw memcards (*.raw)|*.raw"), wxDefaultPosition, wxDefaultSize, wxFLP_USE_TEXTCTRL|wxFLP_FILE_MUST_EXIST|wxFLP_OPEN);
m_MemcardPath_B = new wxFilePickerCtrl(this, ID_MEMCARDPATH_B, wxEmptyString, wxT("Choose a memory card:"),
wxT("Raw memcards (*.raw)|*.raw"), wxDefaultPosition, wxDefaultSize, wxFLP_USE_TEXTCTRL|wxFLP_FILE_MUST_EXIST|wxFLP_OPEN);
m_MemcardPath[SLOT_A] = new wxFilePickerCtrl(this, ID_MEMCARDPATH_A, wxEmptyString, wxT("Choose a memory card:"),
wxT("Raw memcards (*.raw)|*.raw"), wxDefaultPosition, wxDefaultSize, wxFLP_USE_TEXTCTRL|wxFLP_OPEN);
m_MemcardPath[SLOT_B] = new wxFilePickerCtrl(this, ID_MEMCARDPATH_B, wxEmptyString, wxT("Choose a memory card:"),
wxT("Raw memcards (*.raw)|*.raw"), wxDefaultPosition, wxDefaultSize, wxFLP_USE_TEXTCTRL|wxFLP_OPEN);
m_MemcardList[SLOT_A] = new CMemcardListCtrl(this, ID_MEMCARDLIST_A, wxDefaultPosition, wxSize(350,400),
wxLC_REPORT | wxSUNKEN_BORDER | wxLC_ALIGN_LEFT | wxLC_SINGLE_SEL);
@ -187,32 +187,32 @@ void CMemcardManager::CreateGUIControls()
m_MemcardList[SLOT_A]->AssignImageList(new wxImageList(96,32),wxIMAGE_LIST_SMALL);
m_MemcardList[SLOT_B]->AssignImageList(new wxImageList(96,32),wxIMAGE_LIST_SMALL);
t_Status_A = new wxStaticText(this, 0, wxEmptyString, wxDefaultPosition,wxDefaultSize, 0, wxEmptyString);
t_Status_B = new wxStaticText(this, 0, wxEmptyString, wxDefaultPosition, wxDefaultSize, 0, wxEmptyString);
t_Status[SLOT_A] = new wxStaticText(this, 0, wxEmptyString, wxDefaultPosition,wxDefaultSize, 0, wxEmptyString);
t_Status[SLOT_B] = new wxStaticText(this, 0, wxEmptyString, wxDefaultPosition, wxDefaultSize, 0, wxEmptyString);
// buttons
m_CopyFrom_A = new wxButton(this, ID_COPYFROM_A, wxT("->Copy->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_CopyFrom_B = new wxButton(this, ID_COPYFROM_B, wxT("<-Copy<-"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_CopyFrom[SLOT_A] = new wxButton(this, ID_COPYFROM_A, wxT("->Copy->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_CopyFrom[SLOT_B] = new wxButton(this, ID_COPYFROM_B, wxT("<-Copy<-"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_FixChecksum_A = new wxButton(this, ID_FIXCHECKSUM_A, wxT("<-Fix Checksum"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_FixChecksum_B = new wxButton(this, ID_FIXCHECKSUM_B, wxT("Fix Checksum->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_FixChecksum[SLOT_A] = new wxButton(this, ID_FIXCHECKSUM_A, wxT("<-Fix Checksum"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_FixChecksum[SLOT_B] = new wxButton(this, ID_FIXCHECKSUM_B, wxT("Fix Checksum->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveImport_A = new wxButton(this, ID_SAVEIMPORT_A, wxT("<-Import GCI"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveImport_B = new wxButton(this, ID_SAVEIMPORT_B, wxT("Import GCI->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveImport[SLOT_A] = new wxButton(this, ID_SAVEIMPORT_A, wxT("<-Import GCI"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveImport[SLOT_B] = new wxButton(this, ID_SAVEIMPORT_B, wxT("Import GCI->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveExport_A = new wxButton(this, ID_SAVEEXPORT_A, wxT("<-Export GCI"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveExport_B = new wxButton(this, ID_SAVEEXPORT_B, wxT("Export GCI->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveExport[SLOT_A] = new wxButton(this, ID_SAVEEXPORT_A, wxT("<-Export GCI"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SaveExport[SLOT_B] = new wxButton(this, ID_SAVEEXPORT_B, wxT("Export GCI->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_ConvertToGci = new wxButton(this, ID_CONVERTTOGCI, wxT("Convert to GCI"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_Delete_A = new wxButton(this, ID_DELETE_A, wxT("<-Delete"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_Delete_B = new wxButton(this, ID_DELETE_B, wxT("Delete->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_Delete[SLOT_A] = new wxButton(this, ID_DELETE_A, wxT("<-Delete"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_Delete[SLOT_B] = new wxButton(this, ID_DELETE_B, wxT("Delete->"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_PrevPage_A = new wxButton(this, ID_PREVPAGE_A, wxT("Prev Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_PrevPage_B = new wxButton(this, ID_PREVPAGE_B, wxT("Prev Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_PrevPage[SLOT_A] = new wxButton(this, ID_PREVPAGE_A, wxT("Prev Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_PrevPage[SLOT_B] = new wxButton(this, ID_PREVPAGE_B, wxT("Prev Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_NextPage_A = new wxButton(this, ID_NEXTPAGE_A, wxT("Next Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_NextPage_B = new wxButton(this, ID_NEXTPAGE_B, wxT("Next Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_NextPage[SLOT_A] = new wxButton(this, ID_NEXTPAGE_A, wxT("Next Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_NextPage[SLOT_B] = new wxButton(this, ID_NEXTPAGE_B, wxT("Next Page"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
// Sizers that double as wxStaticBoxes
sMemcard_A = new wxStaticBoxSizer(wxVERTICAL, this, wxT("Memory Card A"));
@ -222,40 +222,40 @@ void CMemcardManager::CreateGUIControls()
wxBoxSizer* sButtons;
sButtons = new wxBoxSizer(wxVERTICAL);
sButtons->AddStretchSpacer(2);
sButtons->Add(m_CopyFrom_B, 0, wxEXPAND, 5);
sButtons->Add(m_CopyFrom_A, 0, wxEXPAND, 5);
sButtons->Add(m_CopyFrom[SLOT_B], 0, wxEXPAND, 5);
sButtons->Add(m_CopyFrom[SLOT_A], 0, wxEXPAND, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_FixChecksum_A, 0, wxEXPAND, 5);
sButtons->Add(m_FixChecksum_B, 0, wxEXPAND, 5);
sButtons->Add(m_FixChecksum[SLOT_A], 0, wxEXPAND, 5);
sButtons->Add(m_FixChecksum[SLOT_B], 0, wxEXPAND, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_SaveImport_A, 0, wxEXPAND, 5);
sButtons->Add(m_SaveExport_A, 0, wxEXPAND, 5);
sButtons->Add(m_SaveImport[SLOT_A], 0, wxEXPAND, 5);
sButtons->Add(m_SaveExport[SLOT_A], 0, wxEXPAND, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_ConvertToGci, 0, wxEXPAND, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_SaveImport_B, 0, wxEXPAND, 5);
sButtons->Add(m_SaveExport_B, 0, wxEXPAND, 5);
sButtons->Add(m_SaveImport[SLOT_B], 0, wxEXPAND, 5);
sButtons->Add(m_SaveExport[SLOT_B], 0, wxEXPAND, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_Delete_A, 0, wxEXPAND, 5);
sButtons->Add(m_Delete_B, 0, wxEXPAND, 5);
sButtons->Add(m_Delete[SLOT_A], 0, wxEXPAND, 5);
sButtons->Add(m_Delete[SLOT_B], 0, wxEXPAND, 5);
sButtons->AddStretchSpacer(1);
sPages_A = new wxBoxSizer(wxHORIZONTAL);
sPages_B = new wxBoxSizer(wxHORIZONTAL);
sPages_A->Add(m_PrevPage_A, 0, wxEXPAND|wxALL, 1);
sPages_A->Add(t_Status_A,0, wxEXPAND|wxALL, 5);
sPages_A->Add(m_PrevPage[SLOT_A], 0, wxEXPAND|wxALL, 1);
sPages_A->Add(t_Status[SLOT_A],0, wxEXPAND|wxALL, 5);
sPages_A->Add(0, 0, 1, wxEXPAND|wxALL, 0);
sPages_A->Add(m_NextPage_A, 0, wxEXPAND|wxALL, 1);
sPages_B->Add(m_PrevPage_B, 0, wxEXPAND|wxALL, 1);
sPages_B->Add(t_Status_B, 0, wxEXPAND|wxALL, 5);
sPages_A->Add(m_NextPage[SLOT_A], 0, wxEXPAND|wxALL, 1);
sPages_B->Add(m_PrevPage[SLOT_B], 0, wxEXPAND|wxALL, 1);
sPages_B->Add(t_Status[SLOT_B], 0, wxEXPAND|wxALL, 5);
sPages_B->Add(0, 0, 1, wxEXPAND|wxALL, 0);
sPages_B->Add(m_NextPage_B, 0, wxEXPAND|wxALL, 1);
sPages_B->Add(m_NextPage[SLOT_B], 0, wxEXPAND|wxALL, 1);
sMemcard_A->Add(m_MemcardPath_A, 0, wxEXPAND|wxALL, 5);
sMemcard_A->Add(m_MemcardPath[SLOT_A], 0, wxEXPAND|wxALL, 5);
sMemcard_A->Add(m_MemcardList[SLOT_A], 1, wxEXPAND|wxALL, 5);
sMemcard_A->Add(sPages_A, 0, wxEXPAND|wxALL, 1);
sMemcard_B->Add(m_MemcardPath_B, 0, wxEXPAND|wxALL, 5);
sMemcard_B->Add(m_MemcardPath[SLOT_B], 0, wxEXPAND|wxALL, 5);
sMemcard_B->Add(m_MemcardList[SLOT_B], 1, wxEXPAND|wxALL, 5);
sMemcard_B->Add(sPages_B, 0, wxEXPAND|wxALL, 1);
@ -268,20 +268,21 @@ void CMemcardManager::CreateGUIControls()
sMain->SetSizeHints(this);
Fit();
m_PrevPage_A->Disable();
m_NextPage_A->Disable();
m_PrevPage_B->Disable();
m_NextPage_B->Disable();
m_CopyFrom_A->Disable();
m_CopyFrom_B->Disable();
m_FixChecksum_A->Disable();
m_FixChecksum_B->Disable();
m_SaveImport_A->Disable();
m_SaveExport_A->Disable();
m_SaveImport_B->Disable();
m_SaveExport_B->Disable();
m_Delete_A->Disable();
m_Delete_B->Disable();
m_PrevPage[SLOT_A]->Disable();
m_NextPage[SLOT_A]->Disable();
m_PrevPage[SLOT_B]->Disable();
m_NextPage[SLOT_B]->Disable();
m_CopyFrom[SLOT_A]->Disable();
m_CopyFrom[SLOT_B]->Disable();
m_FixChecksum[SLOT_A]->Disable();
m_FixChecksum[SLOT_B]->Disable();
m_SaveImport[SLOT_A]->Disable();
m_SaveExport[SLOT_A]->Disable();
m_SaveImport[SLOT_B]->Disable();
m_SaveExport[SLOT_B]->Disable();
m_Delete[SLOT_A]->Disable();
m_Delete[SLOT_B]->Disable();
}
void CMemcardManager::OnClose(wxCloseEvent& WXUNUSED (event))
@ -291,158 +292,101 @@ void CMemcardManager::OnClose(wxCloseEvent& WXUNUSED (event))
void CMemcardManager::OnPathChange(wxFileDirPickerEvent& event)
{
int slot = SLOT_B;
int slot2 = SLOT_A;
switch (event.GetId())
{
case ID_MEMCARDPATH_A:
pageA = FIRSTPAGE;
if (m_MemcardList[SLOT_A]->usePages && m_PrevPage_A->IsEnabled())
{
m_PrevPage_A->Disable();
m_MemcardList[SLOT_A]->prevPage = false;
}
if (!strcasecmp(m_MemcardPath_A->GetPath().mb_str(), m_MemcardPath_B->GetPath().mb_str()))
{
PanicAlert(E_ALREADYOPENED);
}
else if (ReloadMemcard(event.GetPath().mb_str(), SLOT_A, pageA))
{
m_MemcardList[SLOT_B]->twoCardsLoaded = true;
m_FixChecksum_A->Enable();
m_SaveImport_A->Enable();
m_SaveExport_A->Enable();
m_Delete_A->Enable();
break;
}
if (memoryCard[SLOT_A])
{
delete memoryCard[SLOT_A];
memoryCard[SLOT_A] = NULL;
}
m_MemcardList[SLOT_B]->twoCardsLoaded = false;
m_MemcardPath_A->SetPath(wxEmptyString);
m_MemcardList[SLOT_A]->ClearAll();
t_Status_A->SetLabel(wxEmptyString);
m_FixChecksum_A->Disable();
m_SaveImport_A->Disable();
m_SaveExport_A->Disable();
m_Delete_A->Disable();
if (m_MemcardList[SLOT_A]->usePages)
{
m_PrevPage_A->Disable();
m_NextPage_A->Disable();
}
break;
slot = SLOT_A;
slot2 = SLOT_B;
case ID_MEMCARDPATH_B:
pageB = FIRSTPAGE;
if (m_MemcardList[SLOT_B]->usePages && m_PrevPage_B->IsEnabled())
page[slot] = FIRSTPAGE;
if (m_MemcardList[slot]->usePages && m_PrevPage[slot]->IsEnabled())
{
m_PrevPage_B->Disable();
m_MemcardList[SLOT_B]->prevPage = false;
m_PrevPage[slot]->Disable();
m_MemcardList[slot]->prevPage = false;
}
if (!strcasecmp(m_MemcardPath_A->GetPath().mb_str(), m_MemcardPath_B->GetPath().mb_str()))
if (!strcasecmp(m_MemcardPath[slot2]->GetPath().mb_str(), m_MemcardPath[slot]->GetPath().mb_str()))
{
PanicAlert(E_ALREADYOPENED);
}
else if (ReloadMemcard(event.GetPath().mb_str(), SLOT_B, pageB))
else if (ReloadMemcard(event.GetPath().mb_str(), slot))
{
m_MemcardList[SLOT_A]->twoCardsLoaded = true;
m_FixChecksum_B->Enable();
m_SaveImport_B->Enable();
m_SaveExport_B->Enable();
m_Delete_B->Enable();
m_MemcardList[slot2]->twoCardsLoaded = true;
m_FixChecksum[slot]->Enable();
m_SaveImport[slot]->Enable();
m_SaveExport[slot]->Enable();
m_Delete[slot]->Enable();
break;
}
if (memoryCard[SLOT_B])
if (memoryCard[slot])
{
delete memoryCard[SLOT_B];
memoryCard[SLOT_B] = NULL;
delete memoryCard[slot];
memoryCard[slot] = NULL;
}
m_MemcardList[SLOT_A]->twoCardsLoaded = false;
m_MemcardPath_B->SetPath(wxEmptyString);
m_MemcardList[SLOT_B]->ClearAll();
t_Status_B->SetLabel(wxEmptyString);
m_FixChecksum_B->Disable();
m_SaveImport_B->Disable();
m_SaveExport_B->Disable();
m_Delete_B->Disable();
if (m_MemcardList[SLOT_B]->usePages)
m_MemcardList[slot2]->twoCardsLoaded = false;
m_MemcardPath[slot]->SetPath(wxEmptyString);
m_MemcardList[slot]->ClearAll();
t_Status[slot]->SetLabel(wxEmptyString);
m_FixChecksum[slot]->Disable();
m_SaveImport[slot]->Disable();
m_SaveExport[slot]->Disable();
m_Delete[slot]->Disable();
if (m_MemcardList[slot]->usePages)
{
m_PrevPage_B->Disable();
m_NextPage_B->Disable();
m_PrevPage[slot]->Disable();
m_NextPage[slot]->Disable();
}
break;
}
if (m_Delete_B->IsEnabled() && m_Delete_A->IsEnabled())
if (m_Delete[slot]->IsEnabled() && m_Delete[slot2]->IsEnabled())
{
m_CopyFrom_A->Enable();
m_CopyFrom_B->Enable();
m_CopyFrom[SLOT_A]->Enable();
m_CopyFrom[SLOT_B]->Enable();
}
else
{
m_CopyFrom_A->Disable();
m_CopyFrom_B->Disable();
m_CopyFrom[SLOT_A]->Disable();
m_CopyFrom[SLOT_B]->Disable();
}
}
void CMemcardManager::OnPageChange(wxCommandEvent& event)
{
int slot = SLOT_B;
switch (event.GetId())
{
case ID_NEXTPAGE_A:
if (!m_PrevPage_A->IsEnabled())
{
m_PrevPage_A->Enable();
m_MemcardList[SLOT_A]->prevPage = true;
}
pageA++;
if (pageA == maxPages)
{
m_NextPage_A->Disable();
m_MemcardList[SLOT_A]->nextPage = false;
}
ReloadMemcard(m_MemcardPath_A->GetPath().mb_str(), SLOT_A, pageA);
break;
slot = SLOT_A;
case ID_NEXTPAGE_B:
if (!m_PrevPage_B->IsEnabled())
if (!m_PrevPage[slot]->IsEnabled())
{
m_PrevPage_B->Enable();
m_MemcardList[SLOT_B]->prevPage = true;
m_PrevPage[slot]->Enable();
m_MemcardList[slot]->prevPage = true;
}
pageB++;
if (pageB == maxPages)
page[slot]++;
if (page[slot] == maxPages)
{
m_NextPage_B->Disable();
m_MemcardList[SLOT_B]->nextPage = false;
m_NextPage[slot]->Disable();
m_MemcardList[slot]->nextPage = false;
}
ReloadMemcard(m_MemcardPath_B->GetPath().mb_str(), SLOT_B, pageB);
ReloadMemcard(m_MemcardPath[slot]->GetPath().mb_str(), slot);
break;
case ID_PREVPAGE_A:
if (!m_NextPage_A->IsEnabled())
{
m_NextPage_A->Enable();
m_MemcardList[SLOT_A]->nextPage = true;
}
pageA--;
if (!pageA)
{
m_PrevPage_A->Disable();
m_MemcardList[SLOT_A]->prevPage = false;
}
ReloadMemcard(m_MemcardPath_A->GetPath().mb_str(), SLOT_A, pageA);
break;
slot = SLOT_A;
case ID_PREVPAGE_B:
if (!m_NextPage_B->IsEnabled())
if (!m_NextPage[slot]->IsEnabled())
{
m_NextPage_B->Enable();
m_MemcardList[SLOT_B]->nextPage = true;
m_NextPage[slot]->Enable();
m_MemcardList[slot]->nextPage = true;
}
pageB--;
if (!pageB)
page[slot]--;
if (!page[slot])
{
m_PrevPage_B->Disable();
m_MemcardList[SLOT_B]->prevPage = false;
m_PrevPage[slot]->Disable();
m_MemcardList[slot]->prevPage = false;
}
ReloadMemcard(m_MemcardPath_B->GetPath().mb_str(), SLOT_B, pageB);
ReloadMemcard(m_MemcardPath[slot]->GetPath().mb_str(), slot);
break;
}
}
@ -455,11 +399,11 @@ void CMemcardManager::OnMenuChange(wxCommandEvent& event)
m_MemcardList[SLOT_B]->usePages = !m_MemcardList[SLOT_B]->usePages;
if (!m_MemcardList[SLOT_A]->usePages)
{
m_PrevPage_A->Disable();
m_PrevPage_B->Disable();
m_NextPage_A->Disable();
m_NextPage_B->Disable();
pageA = pageB = FIRSTPAGE;
m_PrevPage[SLOT_A]->Disable();
m_PrevPage[SLOT_B]->Disable();
m_NextPage[SLOT_A]->Disable();
m_NextPage[SLOT_B]->Disable();
page[SLOT_A] = page[SLOT_B] = FIRSTPAGE;
}
}
else
@ -467,13 +411,12 @@ void CMemcardManager::OnMenuChange(wxCommandEvent& event)
m_MemcardList[SLOT_A]->column[event.GetId()] = !m_MemcardList[SLOT_A]->column[event.GetId()];
m_MemcardList[SLOT_B]->column[event.GetId()] = !m_MemcardList[SLOT_B]->column[event.GetId()];
}
if (memoryCard[SLOT_A]) ReloadMemcard(m_MemcardPath_A->GetPath().mb_str(), SLOT_A, pageA);
if (memoryCard[SLOT_B]) ReloadMemcard(m_MemcardPath_B->GetPath().mb_str(), SLOT_B, pageB);
if (memoryCard[SLOT_A]) ReloadMemcard(m_MemcardPath[SLOT_A]->GetPath().mb_str(), SLOT_A);
if (memoryCard[SLOT_B]) ReloadMemcard(m_MemcardPath[SLOT_B]->GetPath().mb_str(), SLOT_B);
}
bool CMemcardManager::CopyDeleteSwitch(u32 error, int slot)
{
wxString blocksOpen;
switch (error)
{
case GCS:
@ -484,8 +427,8 @@ bool CMemcardManager::CopyDeleteSwitch(u32 error, int slot)
{
memoryCard[slot]->FixChecksums();
if (!memoryCard[slot]->Save()) PanicAlert(E_SAVEFAILED);
slot == SLOT_B ? ReloadMemcard(m_MemcardPath_B->GetPath().mb_str(), slot, FIRSTPAGE)
: ReloadMemcard(m_MemcardPath_A->GetPath().mb_str(), slot, FIRSTPAGE);
page[slot] = FIRSTPAGE;
ReloadMemcard(m_MemcardPath[slot]->GetPath().mb_str(), slot);
}
break;
case NOMEMCARD:
@ -500,8 +443,7 @@ bool CMemcardManager::CopyDeleteSwitch(u32 error, int slot)
PanicAlert(E_UNK);
break;
}
blocksOpen.Printf(wxT(E_OUTOFBLOCKS), memoryCard[slot]->GetFreeBlocks());
PanicAlert(blocksOpen.ToAscii());
PanicAlert(wxString::Format(wxT(E_OUTOFBLOCKS), memoryCard[slot]->GetFreeBlocks()));
break;
case OUTOFDIRENTRIES:
PanicAlert(E_OUTOFDIRENTRIES);
@ -545,8 +487,8 @@ void CMemcardManager::CopyDeleteClick(wxCommandEvent& event)
int index = index_B;
std::string fileName2("");
if (index_A != wxNOT_FOUND && pageA) index_A += itemsPerPage * pageA;
if (index_B != wxNOT_FOUND && pageB) index_B += itemsPerPage * pageB;
if (index_A != wxNOT_FOUND && page[SLOT_A]) index_A += itemsPerPage * page[SLOT_A];
if (index_B != wxNOT_FOUND && page[SLOT_B]) index_B += itemsPerPage * page[SLOT_B];
switch (event.GetId())
{
@ -640,7 +582,7 @@ void CMemcardManager::CopyDeleteClick(wxCommandEvent& event)
}
}
bool CMemcardManager::ReloadMemcard(const char *fileName, int card, int page)
bool CMemcardManager::ReloadMemcard(const char *fileName, int card)
{
wxString wxBlock;
wxString wxFirstBlock;
@ -652,7 +594,7 @@ bool CMemcardManager::ReloadMemcard(const char *fileName, int card, int page)
// TODO: add error checking and animate icons
memoryCard[card] = new GCMemcard(fileName);
if (ReadError(memoryCard[card])) return false;
if (memoryCard[card]->fail) return false;
m_MemcardList[card]->Hide();
m_MemcardList[card]->ClearAll();
@ -719,8 +661,8 @@ bool CMemcardManager::ReloadMemcard(const char *fileName, int card, int page)
}
}
int pagesMax = 128;
if (m_MemcardList[card]->usePages) pagesMax = (page + 1) * itemsPerPage;
for (j = page * itemsPerPage;(j < nFiles) && (j < pagesMax);j++)
if (m_MemcardList[card]->usePages) pagesMax = (page[card] + 1) * itemsPerPage;
for (j = page[card] * itemsPerPage;(j < nFiles) && (j < pagesMax);j++)
{
char title[32];
char comment[32];
@ -755,29 +697,13 @@ bool CMemcardManager::ReloadMemcard(const char *fileName, int card, int page)
{
if ((j == nFiles))
{
if (card)
{
m_NextPage_B->Disable();
m_MemcardList[SLOT_B]->nextPage = false;
}
else
{
m_NextPage_A->Disable();
m_MemcardList[SLOT_A]->nextPage = false;
}
m_NextPage[card]->Disable();
m_MemcardList[card]->nextPage = false;
}
else
{
if (card)
{
m_NextPage_B->Enable();
m_MemcardList[SLOT_B]->nextPage = true;
}
else
{
m_NextPage_A->Enable();
m_MemcardList[SLOT_A]->nextPage = true;
}
m_NextPage[card]->Enable();
m_MemcardList[card]->nextPage = true;
}
}
@ -794,29 +720,11 @@ bool CMemcardManager::ReloadMemcard(const char *fileName, int card, int page)
m_MemcardList[card]->Show();
wxLabel.Printf(wxT("%d Free Blocks; %d Free Dir Entries"),
memoryCard[card]->GetFreeBlocks(), 127 - nFiles);
card ? t_Status_B->SetLabel(wxLabel) : t_Status_A->SetLabel(wxLabel);
t_Status[card]->SetLabel(wxLabel);
return true;
}
bool CMemcardManager::ReadError(GCMemcard *memcard)
{
if (!memcard->fail[0]) return false;
wxString wxBlock;
if (memcard->fail[HDR_READ_ERROR]) PanicAlert("Failed to read header correctly\n(0x0000-0x1FFF)");
if (memcard->fail[DIR_READ_ERROR]) PanicAlert("Failed to read directory correctly\n(0x2000-0x3FFF)");
if (memcard->fail[DIR_BAK_READ_ERROR]) PanicAlert("Failed to read directory backup correctly\n(0x4000-0x5FFF)");
if (memcard->fail[BAT_READ_ERROR]) PanicAlert("Failed to read block allocation table correctly\n(0x6000-0x7FFF)");
if (memcard->fail[BAT_BAK_READ_ERROR]) PanicAlert("Failed to read block allocation table backup correctly\n(0x8000-0x9FFF)");
if (memcard->fail[HDR_CSUM_FAIL]) PanicAlert("Header checksum failed");
if (memcard->fail[DIR_CSUM_FAIL]) PanicAlert("Directory checksum failed\n and Directory backup checksum failed");
if (memcard->fail[BAT_CSUM_FAIL]) PanicAlert("Block Allocation Table checksum failed");
if (memcard->fail[DATA_READ_FAIL]) PanicAlert("Failed to read save data\n(0xA000-)\nMemcard may be truncated");
if (memcard->fail[HDR_SIZE_FFFF]) PanicAlert("Memcard failed to load\n Card size is invalid");
if (memcard->fail[NOTRAWORGCP]) PanicAlert("File does not have a valid extension (.raw/.gcp)");
return true;
}
void CMemcardManager::CMemcardListCtrl::OnRightClick(wxMouseEvent& event)
{

View File

@ -61,37 +61,28 @@ class CMemcardManager
private:
DECLARE_EVENT_TABLE();
int pageA,
pageB,
int page[2],
itemsPerPage,
maxPages;
wxBoxSizer *sMain;
wxBoxSizer *sPages_A;
wxBoxSizer *sPages_B;
wxStaticText *t_Status_A;
wxStaticText *t_Status_B;
wxButton *m_CopyFrom_A;
wxButton *m_CopyFrom_B;
wxButton *m_FixChecksum_A;
wxButton *m_FixChecksum_B;
wxButton *m_SaveImport_A;
wxButton *m_SaveImport_B;
wxButton *m_SaveExport_A;
wxButton *m_SaveExport_B;
wxButton *m_ConvertToGci;
wxButton *m_Delete_A;
wxButton *m_Delete_B;
wxButton *m_NextPage_A;
wxButton *m_NextPage_B;
wxButton *m_PrevPage_A;
wxButton *m_PrevPage_B;
wxStaticBoxSizer *sMemcard_A;
wxStaticBoxSizer *sMemcard_B;
wxFilePickerCtrl *m_MemcardPath_A;
wxFilePickerCtrl *m_MemcardPath_B;
std::string DefaultMemcard[2];
IniFile MemcardManagerIni;
wxBoxSizer *sMain,
*sPages_A,
*sPages_B;
wxButton *m_CopyFrom[2],
*m_FixChecksum[2],
*m_SaveImport[2],
*m_SaveExport[2],
*m_Delete[2],
*m_NextPage[2],
*m_PrevPage[2],
*m_ConvertToGci;
wxFilePickerCtrl *m_MemcardPath[2];
wxStaticBoxSizer *sMemcard_A,
*sMemcard_B;
wxStaticText *t_Status[2];
enum
{
ID_COPYFROM_A = 1000,
@ -133,11 +124,10 @@ class CMemcardManager
void CreateGUIControls();
void OnClose(wxCloseEvent& event);
void CopyDeleteClick(wxCommandEvent& event);
bool ReloadMemcard(const char *fileName, int card, int page);
bool ReloadMemcard(const char *fileName, int card);
void OnMenuChange(wxCommandEvent& event);
void OnPageChange(wxCommandEvent& event);
void OnPathChange(wxFileDirPickerEvent& event);
bool ReadError(GCMemcard *memcard);
bool CopyDeleteSwitch(u32 error, int slot);
class CMemcardListCtrl : public wxListCtrl

View File

@ -29,16 +29,6 @@ void ByteSwap(u8 *valueA, u8 *valueB)
*valueB = tmp;
}
u16 __inline bswap16(u16 s)
{
return (s>>8) | (s<<8);
}
u32 __inline bswap32(u32 s)
{
return (u32)bswap16((u16)(s>>16)) | ((u32)bswap16((u16)s)<<16);
}
u32 decode5A3(u16 val)
{
const int lut5to8[] = { 0x00,0x08,0x10,0x18,0x20,0x29,0x31,0x39,
@ -77,7 +67,7 @@ void decode5A3image(u32* dst, u16* src, int width, int height)
{
for (int ix = 0; ix < 4; ix++)
{
u32 RGBA = decode5A3(bswap16(src[ix]));
u32 RGBA = decode5A3(Common::swap16(src[ix]));
dst[(y + iy) * width + (x + ix)] = RGBA;
}
}
@ -96,7 +86,7 @@ void decodeCI8image(u32* dst, u8* src, u16* pal, int width, int height)
u32 *tdst = dst+(y+iy)*width+x;
for (int ix = 0; ix < 8; ix++)
{
tdst[ix] = decode5A3(bswap16(pal[src[ix]]));
tdst[ix] = decode5A3(Common::swap16(pal[src[ix]]));
}
}
}
@ -105,52 +95,69 @@ void decodeCI8image(u32* dst, u8* src, u16* pal, int width, int height)
GCMemcard::GCMemcard(const char *filename)
{
FILE *mcd = fopen(filename,"r+b");
FILE *mcd = fopen(filename, "r+b");
mcdFile = mcd;
fail[0] = true;
if (!mcd) return;
for(int i=0;i<FAILLAST;i++)fail[i]=false;
//This function can be removed once more about hdr is known and we can check for a valid header
std::string fileType;
SplitPath(filename, NULL, NULL, &fileType);
if (strcasecmp(fileType.c_str(), ".raw") && strcasecmp(fileType.c_str(), ".gcp"))
fail = false;
if (!mcd)
{
fail[0] = true;
fail[NOTRAWORGCP] = true;
return;
if (!PanicYesNo("File does not exist.\n Create a new 16MB Memcard?"))
{
fail = true;
return;
}
mcd = fopen(filename, "wb");
if (!mcd)
{
fail = true;
return;
}
mcdFile = mcd;
format(true);
fclose(mcd);
mcd = fopen(filename, "r+b");
}
else
{
//This function can be removed once more about hdr is known and we can check for a valid header
std::string fileType;
SplitPath(filename, NULL, NULL, &fileType);
if (strcasecmp(fileType.c_str(), ".raw") && strcasecmp(fileType.c_str(), ".gcp"))
{
fail = true;
PanicAlert("File does not have a valid extension (.raw/.gcp)");
return;
}
}
fseek(mcd, 0x0000, SEEK_SET);
if (fread(&hdr, 1, 0x2000, mcd) != 0x2000)
{
fail[0] = true;
fail[HDR_READ_ERROR] = true;
fail = true;
PanicAlert("Failed to read header correctly\n(0x0000-0x1FFF)");
return;
}
if (fread(&dir, 1, 0x2000, mcd) != 0x2000)
{
fail[0] = true;
fail[DIR_READ_ERROR] = true;
fail = true;
PanicAlert("Failed to read directory correctly\n(0x2000-0x3FFF)");
return;
}
if (fread(&dir_backup, 1, 0x2000, mcd) != 0x2000)
{
fail[0] = true;
fail[DIR_BAK_READ_ERROR] = true;
fail = true;
PanicAlert("Failed to read directory backup correctly\n(0x4000-0x5FFF)");
return;
}
if (fread(&bat, 1, 0x2000, mcd) != 0x2000)
{
fail[0] = true;
fail[BAT_READ_ERROR] = true;
fail = true;
PanicAlert("Failed to read block allocation table correctly\n(0x6000-0x7FFF)");
return;
}
if (fread(&bat_backup, 1, 0x2000, mcd) != 0x2000)
{
fail[0] = true;
fail[BAT_BAK_READ_ERROR] = true;
fail = true;
PanicAlert("Failed to read block allocation table backup correctly\n(0x8000-0x9FFF)");
return;
}
@ -160,8 +167,8 @@ GCMemcard::GCMemcard(const char *filename)
{
// header checksum error!
// invalid files do not always get here
fail[0] = true;
fail[HDR_CSUM_FAIL] = true;
fail = true;
PanicAlert("Header checksum failed");
return;
}
@ -170,8 +177,8 @@ GCMemcard::GCMemcard(const char *filename)
if (csums&4)
{
// backup is also wrong!
fail[0] = true;
fail[DIR_CSUM_FAIL] = true;
fail = true;
PanicAlert("Directory checksum failed\n and Directory backup checksum failed");
return;
}
else
@ -190,8 +197,8 @@ GCMemcard::GCMemcard(const char *filename)
if (csums&16)
{
// backup is also wrong!
fail[0] = true;
fail[BAT_CSUM_FAIL] = true;
fail = true;
PanicAlert("Block Allocation Table checksum failed");
return;
}
else
@ -227,14 +234,14 @@ GCMemcard::GCMemcard(const char *filename)
size_t read = fread(mc_data, 1, mc_data_size, mcd);
if (mc_data_size != read)
{
fail[0] = true;
fail[DATA_READ_FAIL] = true;
fail = true;
PanicAlert("Failed to read save data\n(0xA000-)\nMemcard may be truncated");
}
}
else
{
fail[0] = true;
fail[HDR_SIZE_FFFF] = true;
fail = true;
PanicAlert("Memcard failed to load\n Card size is invalid");
}
}
@ -269,8 +276,8 @@ void GCMemcard::calc_checksumsBE(u16 *buf, u32 num, u16 *c1, u16 *c2)
for (u32 i = 0; i < num; ++i)
{
//weird warnings here
*c1 += bswap16(buf[i]);
*c2 += bswap16((u16)(buf[i] ^ 0xffff));
*c1 += Common::swap16(buf[i]);
*c2 += Common::swap16((u16)(buf[i] ^ 0xffff));
}
if (*c1 == 0xffff)
{
@ -496,7 +503,7 @@ u32 GCMemcard::GetFileData(u32 index, u8* dest, bool old) //index in the directo
memcpy(dest,mc_data + 0x2000 * (block - 5), 0x2000);
dest+=0x2000;
u16 nextblock = bswap16(bat.Map[block - 5]);
u16 nextblock = Common::swap16(bat.Map[block - 5]);
if (block + saveLength != memcardSize && nextblock > 0)
{//Fixes for older memcards that were not initialized with FF
block = nextblock;
@ -570,7 +577,7 @@ u32 GCMemcard::ImportFile(DEntry& direntry, u8* contents, int remove)
int j = 2;
while(j < BE16(direntry.BlockCount) + 1)
{
bat_backup.Map[i] = bswap16(last + (u16)j);
bat_backup.Map[i] = Common::swap16(last + (u16)j);
i++;
j++;
}
@ -985,3 +992,84 @@ u32 GCMemcard::ReadAnimRGBA8(u32 index, u32* buffer, u8 *delays)
return frames;
}
bool GCMemcard::format(bool New)
{
u32 data_size = 0x2000 * (0x80 * 0x10 - 5);
if (New)
{
mc_data_size = data_size;
mc_data = new u8[mc_data_size];
}
// Only Format 16MB memcards for now
if (data_size != mc_data_size) return false;
// TODO:Once more is known about the header we can
// correct this function
memset(&hdr, 0xFF, 0x2000);
memset(&dir, 0xFF, 0x2000);
memset(&dir_backup, 0xFF, 0x2000);
memset(&bat, 0, 0x2000);
memset(&bat_backup, 0, 0x2000);
memset(mc_data, 0xFF, mc_data_size);
hdr.Unk1[0] = 0xE3;
hdr.Unk1[1] = 0x63;
hdr.Unk1[2] = 0x27;
hdr.Unk1[3] = 0xC1;
hdr.Unk1[4] = 0x6B;
hdr.Unk1[5] = 0x11;
hdr.Unk1[6] = 0xEC;
hdr.Unk1[7] = 0x47;
hdr.Unk1[8] = 0xF0;
hdr.Unk1[9] = 0x12;
hdr.Unk1[10] = 0x99;
hdr.Unk1[11] = 0x13;
hdr.fmtTime.low = 0x5CB62800;
hdr.fmtTime.high = 0xA665E7A3;
hdr.SramBias[3] = 0x40;
hdr.Unk2[0] = 0;
hdr.Unk2[1] = 0;
hdr.Unk2[2] = 0;
hdr.Unk2[3] = 0;
hdr.Unk2[4] = 0;
hdr.Unk2[5] = 0;
hdr.Unk2[6] = 0;
hdr.Unk2[7] = 0x01;
hdr.Pad1[0] = 0;
hdr.Pad1[1] = 0;
hdr.Size[0] = 0;
hdr.Size[1] = 0x80;
hdr.Encoding[0] = 0;
hdr.Encoding[1] = 0;
//hdr.CheckSum1[0] = 0xAA;
//hdr.CheckSum1[1] = 0x87;
//hdr.CheckSum2[0] = 0x54;
//hdr.CheckSum2[1] = 0x7B;
dir.UpdateCounter[0] = 0;
dir.UpdateCounter[1] = 0;
//dir.CheckSum1[0] = 0xF0;
//dir.CheckSum1[1] = 0x03;
//dir.CheckSum2[0] = 0;
//dir.CheckSum2[1] = 0;
dir_backup.UpdateCounter[0] = 0;
dir_backup.UpdateCounter[1] = 0x01;
//dir_backup.CheckSum1[0] = 0xF0;
//dir_backup.CheckSum1[1] = 0x04;
//dir_backup.CheckSum2[1] = 0xFE;
//bat.CheckSum1[0] = 0x07;
//bat.CheckSum1[1] = 0xFF;
//bat.CheckSum2[0] = 0xE8;
//bat.CheckSum2[1] = 0x03;
bat.FreeBlocks[0] = 0x07;
bat.FreeBlocks[1] = 0xFB;
bat.LastAllocated[1] = 0x04;
//bat_backup.CheckSum1[0] = 0x08;
//bat_backup.CheckSum2[0] = 0xE8;
//bat_backup.CheckSum2[1] = 0x02;
bat_backup.UpdateCounter[1] = 0x01;
bat_backup.FreeBlocks[0] = 0x07;
bat_backup.FreeBlocks[1] = 0xFB;
bat_backup.LastAllocated[1] = 0x04;
FixChecksums();
Save();
return true;
}

View File

@ -25,17 +25,6 @@ enum
GCI = 0,
SUCCESS,
NOMEMCARD,
HDR_READ_ERROR,
DIR_READ_ERROR,
DIR_BAK_READ_ERROR,
BAT_READ_ERROR,
BAT_BAK_READ_ERROR,
HDR_CSUM_FAIL,
DIR_CSUM_FAIL,
BAT_CSUM_FAIL,
DATA_READ_FAIL,
HDR_SIZE_FFFF,
NOTRAWORGCP,
OPENFAIL,
OUTOFBLOCKS,
OUTOFDIRENTRIES,
@ -48,7 +37,6 @@ enum
GCSFAIL,
FAIL,
WRITEFAIL,
FAILLAST,
};
class GCMemcard
@ -145,7 +133,7 @@ private:
#pragma pack(pop)
public:
bool fail[FAILLAST];
bool fail;
// constructor
GCMemcard(const char* fileName);
@ -155,6 +143,7 @@ public:
bool IsOpen();
bool Save();
bool format(bool New);
void calc_checksumsBE(u16 *buf, u32 num, u16 *c1, u16 *c2);
u32 TestChecksums();
@ -164,7 +153,7 @@ public:
u32 GetNumFiles();
// get the free blocks from bat
u16 GetFreeBlocks(void);
u16 GetFreeBlocks();
// Returns true if title already on memcard
bool TitlePresent(DEntry d);

View File

@ -240,7 +240,7 @@ void ConfigBox::CreateGUIControls()
// GUI center button
m_JoyButtonStart[i] = new wxTextCtrl(m_Controller[i], ID_BUTTONSTART, wxT("0"), wxPoint(278, 403), wxSize(59, 19), wxTE_READONLY | wxTE_CENTRE, wxDefaultValidator, wxT("0"));
m_JoyButtonStart[i]->Enable(false);
m_bJoyButtonCalibrate[i] = new wxButton(m_Controller[i], ID_BUTTONCALIBRATE, wxT("Calibrate"), wxPoint(297, 440), wxSize(21, 14), 0, wxDefaultValidator, wxT("Calibrate"));
m_bJoyButtonCalibrate[i] = new wxButton(m_Controller[i], ID_BUTTONCALIBRATE, wxT("Calibrate"), wxPoint(283, 430), wxSize(50, 20), 0, wxDefaultValidator, wxT("Calibrate"));
m_JoyButtonHalfpress[i] = new wxTextCtrl(m_Controller[i], ID_BUTTONHALFPRESS, wxT("0"), wxPoint(167, 424), wxSize(59, 19), wxTE_READONLY | wxTE_CENTRE, wxDefaultValidator, wxT("0"));
m_JoyButtonHalfpress[i]->Enable(false);
m_bJoyButtonStart[i] = new wxButton(m_Controller[i], IDB_BUTTONSTART, wxEmptyString, wxPoint(297, 385), wxSize(21, 14), 0, wxDefaultValidator, wxEmptyString);