code cleanup, focusing on dsp hle

git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@5143 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
Shawn Hoffman 2010-02-28 18:21:22 +00:00
parent cff39f5382
commit 80d303222b
32 changed files with 673 additions and 3590 deletions

View File

@ -120,7 +120,8 @@ void GBASockServer::Transfer(char* si_buffer)
memset(current_data, 0, sizeof(current_data));
size_t num_received = 0;
client.Receive(current_data, sizeof(current_data), num_received);
if (client.Receive(current_data, sizeof(current_data), num_received) == sf::Socket::Disconnected)
client.Close();
DEBUG_LOG(SERIALINTERFACE, "< %02x%02x%02x%02x%02x",
(u8)current_data[0], (u8)current_data[1], (u8)current_data[2],

View File

@ -1,7 +1,7 @@
<?xml version="1.0" encoding="Windows-1252"?>
<VisualStudioProject
ProjectType="Visual C++"
Version="9,00"
Version="9.00"
Name="Plugin_DSP_HLE"
ProjectGUID="{D6E56527-BBB9-4EAD-A6EC-49D4BF6AFCD8}"
RootNamespace="Plugin_DSP"
@ -594,7 +594,7 @@
>
</File>
<Filter
Name="UCode AX"
Name="AX"
>
<File
RelativePath=".\Src\UCodes\UCode_AX.cpp"
@ -658,7 +658,7 @@
</File>
</Filter>
<Filter
Name="UCode Zelda"
Name="Zelda"
>
<File
RelativePath="..\..\..\docs\DSP\DSP_UC_Luigi.txt"
@ -706,50 +706,6 @@
>
</File>
</Filter>
<Filter
Name="Debugger"
>
<File
RelativePath=".\Src\Debugger\Blocks.cpp"
>
</File>
<File
RelativePath=".\Src\Debugger\Debugger.cpp"
>
</File>
<File
RelativePath=".\Src\Debugger\Debugger.h"
>
</File>
<File
RelativePath=".\Src\Debugger\Logging.cpp"
>
</File>
<File
RelativePath=".\Src\Debugger\Mails.cpp"
>
</File>
<File
RelativePath=".\Src\Debugger\PBView.cpp"
>
</File>
<File
RelativePath=".\Src\Debugger\PBView.h"
>
</File>
</Filter>
<Filter
Name="Logging"
>
<File
RelativePath=".\Src\Debugger\File.cpp"
>
</File>
<File
RelativePath=".\Src\Debugger\File.h"
>
</File>
</Filter>
<File
RelativePath=".\Src\Config.cpp"
>
@ -766,10 +722,6 @@
RelativePath=".\Src\DSPHandler.h"
>
</File>
<File
RelativePath=".\Src\Globals.cpp"
>
</File>
<File
RelativePath=".\Src\Globals.h"
>

View File

@ -49,20 +49,3 @@ void CConfig::Save()
file.Save((std::string(File::GetUserPath(D_CONFIG_IDX)) + "DSP.ini").c_str());
}
void CConfig::GameIniLoad(const char *game_ini)
{
// This game config will affect global system config
// Need a better way to seperate system config from game config
//
/*
if (game_ini && strlen(game_ini))
{
IniFile iniFile;
iniFile.Load(game_ini);
//iniFile.Get("HLEaudio", "UseRE0Fix", &m_EnableRE0Fix, 0);
//iniFile.Get("HLEaudio", "UseLoopFix", &m_EnableLoopFix, 0);
}
*/
}

View File

@ -28,7 +28,6 @@ struct CConfig
CConfig();
void Load();
void GameIniLoad(const char *game_ini);
void Save();
};

View File

@ -54,7 +54,6 @@ unsigned short CDSPHandler::WriteControlRegister(unsigned short _Value)
// copy 128 byte from ARAM 0x000000 to IMEM
SetUCode(UCODE_INIT_AUDIO_SYSTEM);
Temp.DSPInitCode = 0;
// MessageBox(NULL, "UCODE_INIT_AUDIO_SYSTEM", "DSP-HLE", MB_OK);
}
m_DSPControl.Hex = Temp.Hex;

View File

@ -1,89 +0,0 @@
//
// Licensetype: GNU General Public License (GPL)
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
//
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
//
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
//
// Includes
// -------------
#include <iostream>
#include <fstream>
#include <sstream>
#ifndef _WIN32
#include <stdlib.h>
#endif
#include "Debugger.h"
#include "PBView.h"
#include "IniFile.h"
#include "FileUtil.h"
#include "StringUtil.h"
#include "FileSearch.h"
//#include "../Logging/File.h" // Write to file
// Make the wxTextCtrls scroll with each other
void DSPDebuggerHLE::DoScrollBlocks()
{
// ShowPosition = in letters
// GetScrollPos = number of lines from the top
// GetLineLength = letters in one line
// SetScrollPos = only set the scrollbar, doesn't update the text,
// Update() or Refresh() doesn't help
double pos = m_bl95->GetScrollPos(wxVERTICAL)*(m_bl95->GetLineLength(0)+12.95); // annoying :(
m_bl0->ShowPosition((int)pos);
/*
if(GetAsyncKeyState(VK_NUMPAD1))
A -= 0.1;
else if(GetAsyncKeyState(VK_NUMPAD2))
A += 0.11;
DEBUG_LOG(CONSOLE, "GetScrollPos:%i GetScrollRange:%i GetPosition:%i GetLastPosition:%i GetMaxWidth:%i \
GetLineLength:%i XYToPosition:%i\n \
GetScrollPos * GetLineLength + GetScrollRange:%i A:%f\n",
m_bl95->GetScrollPos(wxVERTICAL), m_bl95->GetScrollRange(wxVERTICAL),
m_bl95->GetPosition().y, m_bl95->GetLastPosition(), m_bl95->GetMaxWidth(),
m_bl95->GetLineLength(0), m_bl95->XYToPosition(0,25),
pos, A
);
for (int i = 0; i < 127; ++i)
{
m_bl0->AppendText(wxString::Format("%02i|68 : 01a70144\n", i));
m_bl95->AppendText(wxString::Format("%i Mouse\n", i));
}*/
}
void DSPDebuggerHLE::ScrollBlocksMouse(wxMouseEvent& event)
{
DoScrollBlocks();
event.Skip(); // otherwise we remove the regular behavior, for example scrolling
}
void DSPDebuggerHLE::ScrollBlocksCursor(wxScrollWinEvent& event)
{
DoScrollBlocks();
event.Skip(); // otherwise we remove the regular behavior, for example scrolling
}
// ==============

View File

@ -1,650 +0,0 @@
//
// Licensetype: GNU General Public License (GPL)
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
//
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
//
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
//
// Includes
// -------------
// includes
#include <iostream> // System
#include <fstream>
#include <sstream>
#ifndef _WIN32
#include <stdlib.h>
#endif
#include "IniFile.h" // Common
#include "FileUtil.h"
#include "StringUtil.h"
#include "FileSearch.h"
#include "LogManager.h"
#include "Debugger.h"
#include "PBView.h"
#include "../Debugger/File.h" // Write to file
// =======================================================================================
// Event table and class
BEGIN_EVENT_TABLE(DSPDebuggerHLE,wxDialog)
EVT_CLOSE(DSPDebuggerHLE::OnClose) // on close event
EVT_BUTTON(ID_UPD,DSPDebuggerHLE::OnUpdate) // buttons
// left cotrols
EVT_CHECKLISTBOX(IDC_CHECKLIST5, DSPDebuggerHLE::OnOptions) // options
EVT_CHECKLISTBOX(IDC_CHECKLIST6, DSPDebuggerHLE::OnShowAll)
EVT_RADIOBOX(IDC_RADIO0,DSPDebuggerHLE::ShowBase) // update frequency
// right cotrols
EVT_RADIOBOX(IDC_RADIO0,DSPDebuggerHLE::ShowBase)
EVT_RADIOBOX(IDC_RADIO1,DSPDebuggerHLE::ChangeFrequency) // update frequency
EVT_RADIOBOX(IDC_RADIO2,DSPDebuggerHLE::ChangePreset) // presets
EVT_CHECKLISTBOX(IDC_CHECKLIST1, DSPDebuggerHLE::OnSettingsCheck) // settings
EVT_NOTEBOOK_PAGE_CHANGED(ID_NOTEBOOK, DSPDebuggerHLE::UpdateMail) // mails
EVT_RADIOBOX(IDC_RADIO3,DSPDebuggerHLE::ChangeMail)
EVT_CHECKLISTBOX(IDC_CHECKLIST2, DSPDebuggerHLE::OnGameChange) // gc
EVT_CHECKLISTBOX(IDC_CHECKLIST3, DSPDebuggerHLE::OnGameChange) // wii
EVT_CHECKLISTBOX(IDC_CHECKLIST4, DSPDebuggerHLE::MailSettings) // settings
//EVT_RIGHT_DOWN(DSPDebuggerHLE::ScrollBlocks)
//EVT_LEFT_DOWN(DSPDebuggerHLE::ScrollBlocks)
//EVT_MOUSE_EVENTS(DSPDebuggerHLE::ScrollBlocks)
//EVT_MOTION(DSPDebuggerHLE::ScrollBlocks)
//EVT_SCROLL(DSPDebuggerHLE::ScrollBlocks)
//EVT_SCROLLWIN(DSPDebuggerHLE::ScrollBlocks)
END_EVENT_TABLE()
DSPDebuggerHLE::DSPDebuggerHLE(wxWindow *parent, wxWindowID id, const wxString &title,
const wxPoint &position, const wxSize& size, long style)
: wxDialog(parent, id, title, position, size, style)
, m_GPRListView(NULL)
//, gUpdFreq(5) // loaded from file
, giShowAll(-1)
, gPreset(0)
, upd95(false) // block view settings
, upd94(false)
, upd93(false)
, upd92(false)
{
// Confirm parenting
//this->Reparent(parent);
CreateGUIControls();
// load ini...
IniFile file;
file.Load(File::GetUserPath(F_DEBUGGERCONFIG_IDX));
this->Load(file);
// append block names
PBn.resize(266/2);
PBn[10] = "mixer";
PBn[34] = "initial_time_delay";
PBn[41] = "updates";
PBn[46] = "dpop";
PBn[58] = "vol_env";
PBn[60] = "audio_addr";
PBn[68] = "adpcm";
PBn[88] = "src";
PBn[95] = "adpcm_loop_info";
PBn[98] = "lpf";
PBn[102] = "hpf";
PBn[106] = "pad";
PBp.resize(266/2);
PBp[10] = "volume_left, unknown";
PBp[58] = "cur_volume, cur_volume_delta"; // PBVolumeEnvelope
PBp[60] = "looping, sample_format"; // PBAudioAddr
PBp[62] = "loop_addr_hi, loop_addr_lo";
PBp[64] = "end_addr_hi, end_addr_lo";
PBp[66] = "cur_addr_hi, cur_addr_lo";
PBp[68] = "coef[0], coef[1]"; // PBADPCMInfo
PBp[94] = "cur_addr_frac, last_samples[0]";
PBp[94] = "last_samples[3], pred_scale";
PBp[96] = "yn1, yn2";
//wxEVT_RIGHT_DOWN, wxEVT_MOUSEWHEEL, wxEVT_LEFT_UP,
//m_bl95, m_PageBlock, sBlock
m_bl95->Connect(wxID_ANY, wxEVT_SCROLLWIN_THUMBTRACK,
wxScrollWinEventHandler(DSPDebuggerHLE::ScrollBlocksCursor), (wxObject*)NULL, this);
m_bl95->Connect(wxID_ANY, wxEVT_SCROLLWIN_THUMBRELEASE,
wxScrollWinEventHandler(DSPDebuggerHLE::ScrollBlocksCursor), (wxObject*)NULL, this);
m_bl95->Connect(wxID_ANY, wxEVT_MOTION,
wxMouseEventHandler(DSPDebuggerHLE::ScrollBlocksMouse), (wxObject*)NULL, this);
m_bl95->Connect(wxID_ANY, wxEVT_MOUSEWHEEL,
wxMouseEventHandler(DSPDebuggerHLE::ScrollBlocksMouse), (wxObject*)NULL, this);
}
DSPDebuggerHLE::~DSPDebuggerHLE()
{
/*
// empty
IniFile file;
file.Load(File::GetUserPath(F_DEBUGGERCONFIG_IDX));
this->Save(file);
file.Save(File::GetUserPath(F_DEBUGGERCONFIG_IDX));
*/
// Reset
m_DebuggerFrame = NULL;
// Talk
NOTICE_LOG(CONSOLE, "Stop [Sound]\t\tDSPDebuggerHLE destroyed");
}
// ====================
// ========================================================================
// System functions
// --------------
void DSPDebuggerHLE::OnClose(wxCloseEvent& event)
{
//PanicAlert("OnClose");
//event.Skip();
// Save the window position
IniFile file;
file.Load(File::GetUserPath(F_DEBUGGERCONFIG_IDX));
this->Save(file);
file.Save(File::GetUserPath(F_DEBUGGERCONFIG_IDX));
//EndModal(0);
//Close(true);
//Destroy();
delete this;
}
void DSPDebuggerHLE::OnUpdate(wxCommandEvent& /*event*/)
{
this->NotifyUpdate();
}
// ===============
// ==========================================================================
// Save and load settings
// --------------
void DSPDebuggerHLE::Save(IniFile& _IniFile) const
{
// TODO2: get the screen resolution and make limits from that
if(GetPosition().x < 1000 && GetPosition().y < 1000
&& GetSize().GetWidth() < 1000 && GetSize().GetHeight() < 1000)
{
_IniFile.Set("SoundWindow", "x", GetPosition().x);
_IniFile.Set("SoundWindow", "y", GetPosition().y);
_IniFile.Set("SoundWindow", "w", GetSize().GetWidth());
_IniFile.Set("SoundWindow", "h", GetSize().GetHeight());
}
// save settings
_IniFile.Set("SoundWindow", "UpdateFrequency", m_RadioBox[1]->GetSelection());
_IniFile.Set("SoundWindow", "ScanMails", m_gcwiiset->IsChecked(0));
_IniFile.Set("SoundWindow", "StoreMails", m_gcwiiset->IsChecked(1));
_IniFile.Set("SoundWindow", "ShowBase", m_RadioBox[0]->GetSelection() ? false : true);
}
void DSPDebuggerHLE::Load(IniFile& _IniFile)
{
int x,y,w,h;
_IniFile.Get("SoundWindow", "x", &x, GetPosition().x);
_IniFile.Get("SoundWindow", "y", &y, GetPosition().y);
_IniFile.Get("SoundWindow", "w", &w, GetSize().GetWidth());
_IniFile.Get("SoundWindow", "h", &h, GetSize().GetHeight());
SetSize(x, y, w, h);
// Show number base
_IniFile.Get("SoundWindow", "ShowBase", &bShowBase, !m_RadioBox[0]->GetSelection());
m_RadioBox[0]->SetSelection(!bShowBase);
_IniFile.Get("SoundWindow", "UpdateFrequency", &gUpdFreq, m_RadioBox[1]->GetSelection());
m_RadioBox[1]->SetSelection(gUpdFreq);
DoChangeFrequency();
// Read and store mails on/off
_IniFile.Get("SoundWindow", "ScanMails", &ScanMails, m_gcwiiset->IsChecked(0));
m_gcwiiset->Check(0, ScanMails);
_IniFile.Get("SoundWindow", "StoreMails", &StoreMails, m_gcwiiset->IsChecked(1));
m_gcwiiset->Check(1, StoreMails);
}
// ===================
// Create GUI controls
// -------------
void DSPDebuggerHLE::CreateGUIControls()
{
//SetTitle(wxT("Sound"));
// Basic settings
//SetIcon(wxNullIcon);
//SetSize(8, 8, 200, 100); // These will become the minimin sizes allowed by resizing
//Center();
// Declarations
wxBoxSizer * m_MainSizer, * sMain, *_sMail, * sBlock;
wxButton* m_Upd;
wxButton* m_SelC;
wxButton* m_Presets;
wxStaticBoxSizer* sLeft;
int m_radioBoxNChoices[4];
// Notebook -----------------------------------------------------
m_Notebook = new wxNotebook(this, ID_NOTEBOOK, wxDefaultPosition, wxDefaultSize);
m_PageMain = new wxPanel(m_Notebook, ID_PAGEMAIN, wxDefaultPosition, wxDefaultSize);
m_Notebook->AddPage(m_PageMain, wxT("Main"));
m_PageMail = new wxPanel(m_Notebook, ID_PAGEMAIL, wxDefaultPosition, wxDefaultSize);
m_Notebook->AddPage(m_PageMail, wxT("Mail"));
m_PageBlock = new wxPanel(m_Notebook, ID_PAGEBLOCK, wxDefaultPosition, wxDefaultSize);
m_Notebook->AddPage(m_PageBlock, wxT("Blocks"));
// ===================================================================
// Blocks Page
wxStaticBoxSizer * m_bl0Sizer = new wxStaticBoxSizer (wxVERTICAL, m_PageBlock, wxT("Block"));
m_bl0 = new wxTextCtrl(m_PageBlock, ID_BL0, _T(""), wxDefaultPosition, wxSize(250, 120),
wxTE_RICH | wxTE_MULTILINE | wxTE_READONLY | wxTE_DONTWRAP | wxNO_BORDER);
m_bl0Sizer->Add(m_bl0, 1, wxEXPAND | wxALL, 0);
wxStaticBoxSizer * m_bl1Sizer = new wxStaticBoxSizer (wxVERTICAL, m_PageBlock, wxT("Block 95"));
m_bl95 = new wxTextCtrl(m_PageBlock, ID_BL95, _T(""), wxDefaultPosition, wxSize(300, 120),
wxTE_RICH | wxTE_MULTILINE | wxTE_READONLY | wxTE_DONTWRAP | wxNO_BORDER);
m_bl1Sizer->Add(m_bl95, 1, wxEXPAND | wxALL, 0);
wxStaticBoxSizer * m_bl2Sizer = new wxStaticBoxSizer (wxVERTICAL, m_PageBlock, wxT("Block 94"));
m_bl94 = new wxTextCtrl(m_PageBlock, ID_BL94, _T(""), wxDefaultPosition, wxSize(300, 120),
wxTE_RICH | wxTE_MULTILINE | wxTE_DONTWRAP | wxNO_BORDER );
m_bl2Sizer->Add(m_bl94, 1, wxEXPAND | wxALL, 0);
// ===================================================================
// Mail Page
wxStaticBoxSizer * m_m1Sizer = new wxStaticBoxSizer (wxVERTICAL, m_PageMail, wxT("Entire mail"));
m_log = new wxTextCtrl(m_PageMail, ID_LOG, _T(""), wxDefaultPosition, wxSize(175, 120),
wxTE_RICH | wxTE_MULTILINE | wxTE_READONLY | wxTE_DONTWRAP | wxNO_BORDER);
m_m1Sizer->Add(m_log, 1, wxEXPAND | wxALL, 0);
wxStaticBoxSizer * m_m2Sizer = new wxStaticBoxSizer (wxVERTICAL, m_PageMail, wxT("Logged mail"));
m_log1 = new wxTextCtrl(m_PageMail, ID_LOG1, _T(""), wxDefaultPosition, wxSize(300, 120),
wxTE_RICH | wxTE_MULTILINE | wxTE_READONLY | wxTE_DONTWRAP | wxNO_BORDER );
m_m2Sizer->Add(m_log1, 1, wxEXPAND | wxALL, 0);
// Show different mails, make room for five mails, in usual circumstances it's two or three
wxString m_radioBoxChoices3[] = { wxT("0"), wxT("1"), wxT("2"), wxT("3"), wxT("4") };
m_radioBoxNChoices[3] = sizeof( m_radioBoxChoices3 ) / sizeof( wxString );
m_RadioBox[3] = new wxRadioBox( m_PageMail, IDC_RADIO3, wxT("Show mail"),
wxDefaultPosition, wxDefaultSize, m_radioBoxNChoices[3], m_radioBoxChoices3, 1, wxRA_SPECIFY_COLS);
m_RadioBox[3]->Enable(false);
// Games checkboxes (m_PageMail) -----------------------------
wxStaticBoxSizer * m_gameSizer1 = new wxStaticBoxSizer(wxVERTICAL, m_PageMail, wxT("GC"));
m_gc = new wxCheckListBox(m_PageMail, IDC_CHECKLIST2, wxDefaultPosition, wxDefaultSize,
0, NULL, wxNO_BORDER | wxLB_SINGLE);
m_gameSizer1->Add(m_gc, 1, wxEXPAND | wxALL, 0);
wxStaticBoxSizer * m_gameSizer2 = new wxStaticBoxSizer(wxVERTICAL, m_PageMail, wxT("Wii"));
m_wii = new wxCheckListBox(m_PageMail, IDC_CHECKLIST3, wxDefaultPosition, wxDefaultSize,
0, NULL, wxNO_BORDER | wxLB_SINGLE);
m_gameSizer2->Add(m_wii, 1, wxEXPAND | wxALL, 0);
// Settings
wxStaticBoxSizer * m_gameSizer3 = new wxStaticBoxSizer(wxVERTICAL, m_PageMail, wxT("Settings"));
m_gcwiiset = new wxCheckListBox(m_PageMail, IDC_CHECKLIST4, wxDefaultPosition, wxDefaultSize,
0, NULL, wxNO_BORDER | wxLB_SINGLE);
m_gameSizer3->Add(m_gcwiiset, 0, 0, 0);
m_gcwiiset->Append(wxT("Scan mails"));
m_gcwiiset->Append(wxT("Store mails"));
// ===================================================================
// Main Page
// Options checkboxlist (m_PageMain) -----------------------------------
wxStaticBoxSizer * m_checkSizer = new wxStaticBoxSizer (wxVERTICAL, m_PageMain, wxT("Options"));
m_options = new wxCheckListBox(m_PageMain, IDC_CHECKLIST5, wxDefaultPosition, wxDefaultSize,
0, NULL, wxNO_BORDER);
// checkboxes
m_options->Append(wxT("Save to file"));
m_options->Append(wxT("Only looping"));
m_options->Append(wxT("Show all"));
m_options->Check(0, gSaveFile);
m_options->Check(1, gOnlyLooping);
m_options->Check(2, gShowAll);
m_options->SetMinSize(wxSize(m_options->GetSize().GetWidth() - 40,
m_options->GetCount() * 15));
m_checkSizer->Add(m_options, 0, 0, 0);
// ------------------------
// Options checkboxlist (m_PageMain) -----------------------------------
wxStaticBoxSizer * m_showallSizer = new wxStaticBoxSizer (wxVERTICAL, m_PageMain, wxT("Show all"));
m_opt_showall = new wxCheckListBox(m_PageMain, IDC_CHECKLIST6, wxDefaultPosition, wxDefaultSize,
0, NULL, wxNO_BORDER);
// checkboxes
m_opt_showall->Append(wxT("Part 1"));
m_opt_showall->Append(wxT("Part 2"));
m_opt_showall->Append(wxT("Part 3"));
m_opt_showall->Append(wxT("Part 4"));
m_opt_showall->SetMinSize(wxSize(m_opt_showall->GetSize().GetWidth() - 40,
m_opt_showall->GetCount() * 15));
m_showallSizer->Add(m_opt_showall, 0, 0, 0);
// Update frequency, numeric base, presets radio boxes --------------------
wxString m_radioBoxChoices0[] = { wxT("Show base 10"), wxT("Show base 16") };
m_radioBoxNChoices[0] = sizeof( m_radioBoxChoices0 ) / sizeof( wxString );
m_RadioBox[0] = new wxRadioBox( m_PageMain, IDC_RADIO0, wxT("Show base"),
wxDefaultPosition, wxDefaultSize, m_radioBoxNChoices[0], m_radioBoxChoices0, 1, wxRA_SPECIFY_COLS);
wxString m_radioBoxChoices1[] = { wxT("Never"), wxT("5 times/s"), wxT("15 times/s"), wxT("30 times/s") };
m_radioBoxNChoices[1] = sizeof( m_radioBoxChoices1 ) / sizeof( wxString );
m_RadioBox[1] = new wxRadioBox( m_PageMain, IDC_RADIO1, wxT("Update freq."),
wxDefaultPosition, wxDefaultSize, m_radioBoxNChoices[1], m_radioBoxChoices1, 1, wxRA_SPECIFY_COLS);
wxString m_radioBoxChoices2[] = { wxT("Preset 1"), wxT("Updates"), wxT("Looping"), wxT("Mixer") };
m_radioBoxNChoices[2] = sizeof( m_radioBoxChoices2 ) / sizeof( wxString );
m_RadioBox[2] = new wxRadioBox( m_PageMain, IDC_RADIO2, wxT("Presets"),
wxDefaultPosition, wxDefaultSize, m_radioBoxNChoices[2], m_radioBoxChoices2, 1, wxRA_SPECIFY_COLS);
// ------------------------
// --------------------------------------------------------------------
// Settings checkboxes (m_PageMain)
// -------------------------
wxStaticBoxSizer * m_checkSizer2 = new wxStaticBoxSizer(wxVERTICAL, m_PageMain, wxT("Settings"));
m_settings = new wxCheckListBox(m_PageMain, IDC_CHECKLIST1, wxDefaultPosition, wxDefaultSize,
0, NULL, wxNO_BORDER);
m_settings->Append(wxT("SSBM fix"));
m_settings->Append(wxT("SSBM remedy 1"));
m_settings->Append(wxT("SSBM remedy 2"));
m_settings->Append(wxT("Sequenced"));
m_settings->Append(wxT("Volume delta"));
m_settings->Append(wxT("Reset all"));
m_settings->Check(0, gSSBM);
m_settings->Check(1, gSSBMremedy1);
m_settings->Check(2, gSSBMremedy2);
m_settings->Check(3, gSequenced);
m_settings->Check(4, gVolume);
m_settings->Check(5, gReset);
// because the wxCheckListBox is a little underdeveloped we have to help it with this
// to bad there's no windows xp styles for the checkboxes
m_settings->SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE));
m_settings->SetMinSize(wxSize(m_settings->GetSize().GetWidth() - 40,
m_settings->GetCount() * 15));
#ifdef _WIN32
//for (int i = 0; i < m_settings->GetCount(); ++i)
// m_settings->GetItem(i)->SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE));
#endif
m_checkSizer2->Add(m_settings, 0, 0, 0);
// ------------------------
// --------------------------------------------------------------------
// Buttons
// ------------------------
m_Upd = new wxButton(m_PageMain, ID_UPD, wxT("Update"),
wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SelC = new wxButton(m_PageMain, ID_SELC, wxT("Select Columns"),
wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_SelC->Enable(false);
m_Presets = new wxButton(m_PageMain, ID_PRESETS, wxT("Presets"),
wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator);
m_Presets->Enable(false);
// --------------------------------------------------------------------
// --------------------------------------------------------------------
// Left buttons and checkboxes (MAIN
// ------------------------
wxBoxSizer* sButtons;
sButtons = new wxBoxSizer(wxVERTICAL);
sButtons->AddSpacer(5); // to set a minimum margin
sButtons->Add(m_Upd, 0, 0, 5);
sButtons->Add(m_SelC, 0, 0, 5);
sButtons->Add(m_Presets, 0, 0, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_checkSizer, 0, 0, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_showallSizer, 0, 0, 5);
sButtons->AddStretchSpacer(1);
sButtons->Add(m_RadioBox[0], 0, 0, 5);
sButtons->AddSpacer(5);
// ------------------------
// --------------------------------------------------------------------
// Right buttons and checkboxes (MAIN)
// ------------------------
wxBoxSizer* sButtons2;
sButtons2 = new wxBoxSizer(wxVERTICAL);
sButtons2->AddStretchSpacer(1);
sButtons2->Add(m_RadioBox[1], 0, 0, 5); // Update freq.
sButtons2->AddStretchSpacer(1);
sButtons2->Add(m_RadioBox[2], 0, 0, 5);
sButtons2->AddStretchSpacer(1);
sButtons2->Add(m_checkSizer2, 0, 0, 5);
sButtons2->AddStretchSpacer(1);
// ------------------------
// --------------------------------------------------------------------
// Parameter tables view (MAIN)
sLeft = new wxStaticBoxSizer(wxVERTICAL, m_PageMain, wxT("Current Status"));
// The big window that holds the parameter tables
m_GPRListView = new CPBView(m_PageMain, ID_GPR, wxDefaultPosition, GetSize(),
wxLC_REPORT | wxSUNKEN_BORDER | wxLC_ALIGN_LEFT | wxLC_SINGLE_SEL | wxLC_SORT_ASCENDING);
sLeft->Add(m_GPRListView, 1, wxEXPAND|wxALL, 5);
sMain = new wxBoxSizer(wxHORIZONTAL);
sMain->Add(sLeft, 1, wxEXPAND | wxALL, 5); // margin = 5
sMain->Add(sButtons, 0, wxALL, 0);
sMain->Add(sButtons2, 0, wxALL, 5); // margin = 5
// --------------------------------------------------------------------
// --------------------------------------------------------------------
// Add all stuff to the mail container (MAIL)
// -----------------------------
// For the buttons on the right
wxBoxSizer * sMailRight = new wxBoxSizer(wxVERTICAL);
//wxStaticBoxSizer * sMailRight = new wxStaticBoxSizer(wxVERTICAL, m_PageMail, wxT("Current"));
_sMail = new wxBoxSizer(wxHORIZONTAL);
_sMail->Add(m_m1Sizer, 0, wxEXPAND | (wxUP | wxDOWN), 5); // margin = 5
_sMail->Add(m_m2Sizer, 1, wxEXPAND | (wxUP | wxDOWN | wxLEFT), 5); // margin = 5
_sMail->Add(sMailRight, 0, wxEXPAND | wxALL, 0); // margin = 0
sMailRight->Add(m_RadioBox[3], 0, wxALL, 5); // margin = 5
sMailRight->Add(m_gameSizer1, 1, wxEXPAND | wxALL, 5); // margin = 5
sMailRight->Add(m_gameSizer2, 1, wxEXPAND | wxALL, 5); // margin = 5
sMailRight->Add(m_gameSizer3, 0, wxALL, 5); // margin = 5
// --------------------------------------------------------------------
// --------------------------------------------------------------------
// The blocks view container (BLOCKS)
// -----------------------------
// For the buttons on the right
//wxBoxSizer * sMailRight = new wxBoxSizer(wxVERTICAL);
//wxStaticBoxSizer * sMailRight = new wxStaticBoxSizer(wxVERTICAL, m_PageMail, wxT("Current"));
sBlock = new wxBoxSizer(wxHORIZONTAL);
sBlock->Add(m_bl0Sizer, 0, wxEXPAND | (wxUP | wxDOWN), 5); // margin = 5
sBlock->Add(m_bl1Sizer, 1, wxEXPAND | (wxUP | wxDOWN | wxLEFT), 5); // margin = 5
sBlock->Add(m_bl2Sizer, 1, wxEXPAND | (wxUP | wxDOWN | wxRIGHT), 5); // margin = 5
//sBlock->Add(sMailRight, 0, wxEXPAND | wxALL, 0); // margin = 0
/*sMailRight->Add(m_RadioBox[3], 0, wxALL, 5); // margin = 5
sMailRight->Add(m_gameSizer1, 1, wxEXPAND | wxALL, 5); // margin = 5
sMailRight->Add(m_gameSizer2, 1, wxEXPAND | wxALL, 5); // margin = 5
sMailRight->Add(m_gameSizer3, 0, wxALL, 5); // margin = 5*/
// --------------------------------------------------------------------
// --------------------------------------------------------------------
// Main containers
// -----------------------------
m_MainSizer = new wxBoxSizer(wxVERTICAL);
m_MainSizer->Add(m_Notebook, 1, wxEXPAND | wxALL, 5);
//m_MainSizer->SetSizeHints(this);
m_PageMain->SetSizer(sMain);
m_PageMail->SetSizer(_sMail);
m_PageBlock->SetSizer(sBlock);
//sMain->Layout();
this->SetSizer(m_MainSizer);
//this->Layout();
NotifyUpdate();
// --------------------------------------------------------------------
}
// =======================================================================================
// Settings
void DSPDebuggerHLE::OnSettingsCheck(wxCommandEvent& event)
{
gSSBM = m_settings->IsChecked(0);
gSSBMremedy1 = m_settings->IsChecked(1);
gSSBMremedy2 = m_settings->IsChecked(2);
gSequenced = m_settings->IsChecked(3);
gVolume = m_settings->IsChecked(4);
gReset = m_settings->IsChecked(5);
}
// =======================================================================================
// Change preset
void DSPDebuggerHLE::ChangePreset(wxCommandEvent& event)
{
DoChangePreset();
}
void DSPDebuggerHLE::DoChangePreset()
{
if(m_RadioBox[2]->GetSelection() == 0)
gPreset = 0;
else if(m_RadioBox[2]->GetSelection() == 1)
gPreset = 1;
else if(m_RadioBox[2]->GetSelection() == 2)
gPreset = 2;
else if(m_RadioBox[2]->GetSelection() == 3)
gPreset = 3;
}
// =======================================================================================
// Show base
void DSPDebuggerHLE::ShowBase(wxCommandEvent& event)
{
if(m_RadioBox[0]->GetSelection() == 0)
bShowBase = true;
else if(m_RadioBox[0]->GetSelection() == 1)
bShowBase = false;
}
// =======================================================================================
// Change update frequency
void DSPDebuggerHLE::ChangeFrequency(wxCommandEvent& event)
{
DoChangeFrequency();
}
void DSPDebuggerHLE::DoChangeFrequency()
{
if(m_RadioBox[1]->GetSelection() == 0)
gUpdFreq = 0;
else if(m_RadioBox[1]->GetSelection() == 1)
gUpdFreq = 5;
else if(m_RadioBox[1]->GetSelection() == 2)
gUpdFreq = 15;
else if(m_RadioBox[1]->GetSelection() == 3)
gUpdFreq = 30;
}
// =======================================================================================
// Options
void DSPDebuggerHLE::OnOptions(wxCommandEvent& event)
{
gSaveFile = m_options->IsChecked(0);
gOnlyLooping = m_options->IsChecked(1);
gShowAll = m_options->IsChecked(2);
}
void DSPDebuggerHLE::OnShowAll(wxCommandEvent& event)
{
/// Only allow one selection at a time
for (u32 i = 0; i < m_opt_showall->GetCount(); ++i)
if(i != (u32)event.GetInt()) m_opt_showall->Check(i, false);
if(m_opt_showall->IsChecked(0)) giShowAll = 0;
else if(m_opt_showall->IsChecked(1)) giShowAll = 1;
else if(m_opt_showall->IsChecked(2)) giShowAll = 2;
else if(m_opt_showall->IsChecked(3)) giShowAll = 3;
else giShowAll = -1;
}
void DSPDebuggerHLE::NotifyUpdate()
{
if (m_GPRListView != NULL)
{
m_GPRListView->Update();
}
}

View File

@ -1,173 +0,0 @@
//
// Licensetype: GNU General Public License (GPL)
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
//
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
//
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
//
#ifndef __DSPDebuggerHLE_h__
#define __DSPDebuggerHLE_h__
// general things
#include <iostream>
#include <vector>
// wx stuff, I'm not sure if we use all these
#ifndef WX_PRECOMP
#include <wx/wx.h>
#include <wx/dialog.h>
#else
#include <wx/wxprec.h>
#endif
#include <wx/button.h>
#include <wx/stattext.h>
#include <wx/statbox.h>
#include <wx/statbmp.h>
#include <wx/datetime.h> // for the timestamps
#include <wx/sizer.h>
#include <wx/notebook.h>
#include <wx/filepicker.h>
#include <wx/listctrl.h>
#include <wx/imaglist.h>
#include "../Globals.h"
class CPBView;
class IniFile;
class DSPDebuggerHLE : public wxDialog
{
private:
DECLARE_EVENT_TABLE();
public:
DSPDebuggerHLE(wxWindow *parent,
wxWindowID id = 1,
const wxString &title = wxT("Sound"),
const wxPoint& pos = wxDefaultPosition,
const wxSize& size = wxDefaultSize,
#ifdef _WIN32
long style = wxNO_BORDER);
#else
long style = wxDEFAULT_FRAME_STYLE | wxCLIP_CHILDREN | wxNO_FULL_REPAINT_ON_RESIZE);
#endif
virtual ~DSPDebuggerHLE();
void Save(IniFile& _IniFile) const;
void Load(IniFile& _IniFile);
void NotifyUpdate();
void OnUpdate(wxCommandEvent& event);
// options
void ShowBase(wxCommandEvent& event);
void OnOptions(wxCommandEvent& event);
void OnShowAll(wxCommandEvent& event);
// update frequency
void ChangeFrequency(wxCommandEvent& event);
void DoChangeFrequency();
void ChangePreset(wxCommandEvent& event);
void DoChangePreset();
// settings
void OnSettingsCheck(wxCommandEvent& event);
// ============== Mail
void DoUpdateMail();
void UpdateMail(wxNotebookEvent& event);
void ChangeMail(wxCommandEvent& event);
void ReadDir();
bool NoDuplicate(std::string FileName);
void OnGameChange(wxCommandEvent& event);
void MailSettings(wxCommandEvent& event);
void Readfile(std::string FileName, bool GC);
std::string Readfile_(std::string FileName);
u32 CountFiles(std::string FileName);
// ============== Blocks
void DoScrollBlocks();
void ScrollBlocksMouse(wxMouseEvent& event);
void ScrollBlocksCursor(wxScrollWinEvent& event);
CPBView* m_GPRListView;
std::vector<std::string> sMail, sMailEnd, sFullMail;
wxRadioBox * m_RadioBox[4], * m_RadioBoxShowAll;
bool gSaveFile; // main options
bool gOnlyLooping;
bool gShowAll;
int giShowAll;
int gUpdFreq;// main update freq.
int gPreset; // main presets
bool bShowBase; // main presets
u32 gLastBlock;
bool ScanMails; // mail settings
bool StoreMails;
bool upd95; bool upd94; bool upd93; bool upd92; // block view settings
std::string str0; std::string str95; std::string str94; std::string str93; std::string str92;
std::vector<std::string> PBn; std::vector<std::string> PBp;
// members
wxTextCtrl * m_log, * m_log1, // mail
* m_bl0, * m_bl95, * m_bl94; // blocks
private:
// declarations
wxNotebook *m_Notebook; // notebook
wxPanel *m_PageMain, *m_PageMail, *m_PageBlock;
wxCheckBox *m_Check[9];
wxRadioButton *m_Radio[5];
wxCheckListBox * m_options, * m_opt_showall, * m_settings, * m_gc, * m_wii, * m_gcwiiset;
wxPanel *m_Controller;
std::vector<std::string> all_all_files, all_files, gc_files, wii_files;
// WARNING: Make sure these are not also elsewhere
enum
{
IDC_CHECK0 = 2000,
IDC_CHECK1,
IDC_CHECK2,
IDC_CHECK3,
IDC_CHECK4,
IDC_CHECKLIST1, IDC_CHECKLIST2, IDC_CHECKLIST3, IDC_CHECKLIST4, IDC_CHECKLIST5, IDC_CHECKLIST6,
IDC_RADIO0, IDC_RADIO1, IDC_RADIO2, IDC_RADIO3, IDC_RADIO4,
IDG_LABEL1, IDG_LABEL2,
ID_UPD,
ID_SELC,
ID_PRESETS,
ID_GPR,
ID_NOTEBOOK, ID_PAGEMAIN, ID_PAGEMAIL, ID_PAGEBLOCK, // notebook
ID_LOG, ID_LOG1, // mails
ID_BL0, ID_BL95, ID_BL94, ID_BL93, ID_BL92,
};
void OnClose(wxCloseEvent& event);
void CreateGUIControls();
};
#endif

View File

@ -1,117 +0,0 @@
// Copyright (C) 2003 Dolphin Project.
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
// --------------------
// Includes
#include <string>
#include <stdio.h>
#include "Common.h"
#ifdef _WIN32
#include <windows.h>
#endif
#if defined(HAVE_WX) && HAVE_WX
#include "../Debugger/Debugger.h"
extern DSPDebuggerHLE* m_DebuggerFrame;
#endif
#include "../Debugger/File.h"
// --------------------
// On and off
bool g_consoleEnable = true;
//int gSaveFile = 0;
#define DEBUG_HLE
// --------------------
// Create file handles
#ifdef DEBUG_HLE
FILE* __fStdOut[nFiles];
#endif
// =======================================================================================
/* Open file handles */
// -------------
void StartFile(int width, int height, char* fname)
{
#if defined(DEBUG_HLE) && defined(_WIN32)
if(fname)
{
for(int i = 0; i < nFiles; i++)
{
// Edit the log file name
std::string FileEnding = ".log";
std::string FileName = fname;
char buffer[33]; _itoa(i, buffer, 10); // convert number to string
std::string FullFilename = (FileName + buffer + FileEnding);
__fStdOut[i] = fopen(FullFilename.c_str(), "w");
}
}
#endif
}
// ======================
/* Close the file handles */
// -------------
void CloseFile()
{
// Close the file handles
for(int i = 0; i < nFiles; i++)
{
if(__fStdOut[i]) fclose(__fStdOut[i]);
}
}
// ---------------------------------------------------------------------------------------
// File printf function
// -------------
int PrintFile(int a, char *fmt, ...)
{
#if defined(DEBUG_HLE) && defined(_WIN32)
if(m_DebuggerFrame->gSaveFile)
{
char s[StringSize];
va_list argptr;
int cnt;
va_start(argptr, fmt);
cnt = vsnprintf(s, StringSize, fmt, argptr);
va_end(argptr);
// ---------------------------------------------------------------------------------------
if(__fStdOut[a]) // TODO: make this work, we have to set all default values to NULL
// to make it work
fprintf(__fStdOut[a], s);
// -------------
return(cnt);
}
else
{
return 0;
}
#else
return 0;
#endif
}

View File

@ -1,41 +0,0 @@
// Copyright (C) 2003 Dolphin Project.
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
// Declarations and definitions
// -------------
// --------------------
// Settings
// -------------
const int nFiles = 4;
const int StringSize = 5000; // Warning, mind this value, if exceeded a crash may occur
// --------------------
// Functions
// -------------
void StartFile(int width, int height, char* fname);
void StopFile();
int PrintFile(int a, char *fmt, ...);
void OpenConsole();
void CloseConsole();
#ifdef _WIN32
HWND GetConsoleHwnd(void);
#endif

View File

@ -1,952 +0,0 @@
//
// Licensetype: GNU General Public License (GPL)
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
//
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
//
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
//
// Includes
// -------------
#include <iostream> // System
#include <vector>
#include <string> // so that we can test std::string == abc
#include <math.h> // for the pow() function
#ifdef _WIN32
#include <windows.h>
#endif
#include "StringUtil.h" // Common
#include "../Debugger/Debugger.h" // Local
#include "../Debugger/PBView.h"
#include "../Debugger/File.h" // Print file
#include "../Globals.h"
#include "../UCodes/UCodes.h"
#include "../UCodes/UCode_AXStructs.h"
#include "../UCodes/UCode_AX.h"
#include "../UCodes/UCode_AXWii.h"
#include "../UCodes/UCode_AX_Voice.h"
// Declarations and definitions
// -------------
// Externals
extern DSPDebuggerHLE* m_DebuggerFrame;
//int PBSize = 128;
// Parameter blocks
std::vector<int> mem(NUMBER_OF_PBS); // mem1 or mem2
std::vector<u32> gloopPos(NUMBER_OF_PBS);
std::vector<u32> gsampleEnd(NUMBER_OF_PBS);
std::vector<u32> gsamplePos(NUMBER_OF_PBS);
// main
std::vector<u16> running(NUMBER_OF_PBS, 0);
std::vector<u16> gsrc_type(NUMBER_OF_PBS);
std::vector<u16> gis_stream(NUMBER_OF_PBS);
// PBSampleRateConverter src
std::vector<u32> gratio(NUMBER_OF_PBS);
std::vector<u32> gratiohi(NUMBER_OF_PBS);
std::vector<u32> gratiolo(NUMBER_OF_PBS);
std::vector<u32> gfrac(NUMBER_OF_PBS);
std::vector<u32> gcoef(NUMBER_OF_PBS);
// PBSampleRateConverter mixer
std::vector<u16> gvolume_left(NUMBER_OF_PBS);
std::vector<u16> gmix_unknown(NUMBER_OF_PBS);
std::vector<u16> gvolume_right(NUMBER_OF_PBS);
std::vector<u16> gmix_unknown2(NUMBER_OF_PBS);
std::vector<u16> gmixer_control(NUMBER_OF_PBS);
std::vector<u32> gmixer_control_wii(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol1(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol2(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol3(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol4(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol5(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol6(NUMBER_OF_PBS);
std::vector<u16> gmixer_vol7(NUMBER_OF_PBS);
std::vector<u16> gmixer_d1(NUMBER_OF_PBS);
std::vector<u16> gmixer_d2(NUMBER_OF_PBS);
std::vector<u16> gmixer_d3(NUMBER_OF_PBS);
std::vector<u16> gmixer_d4(NUMBER_OF_PBS);
std::vector<u16> gmixer_d5(NUMBER_OF_PBS);
std::vector<u16> gmixer_d6(NUMBER_OF_PBS);
std::vector<u16> gmixer_d7(NUMBER_OF_PBS);
// PBVolumeEnvelope vol_env
std::vector<u16> gcur_volume(NUMBER_OF_PBS);
std::vector<u16> gcur_volume_delta(NUMBER_OF_PBS);
// PBAudioAddr audio_addr (incl looping)
std::vector<u16> gaudioFormat(NUMBER_OF_PBS);
std::vector<u16> glooping(NUMBER_OF_PBS);
std::vector<u16> gloop1(NUMBER_OF_PBS);
std::vector<u16> gloop2(NUMBER_OF_PBS);
std::vector<u16> gloop3(NUMBER_OF_PBS);
// PBADPCMInfo adpcm
std::vector<u16> gadloop1(NUMBER_OF_PBS);
std::vector<u16> gadloop2(NUMBER_OF_PBS);
std::vector<u16> gadloop3(NUMBER_OF_PBS);
// updates
std::vector<u16> gupdates1(NUMBER_OF_PBS);
std::vector<u16> gupdates2(NUMBER_OF_PBS);
std::vector<u16> gupdates3(NUMBER_OF_PBS);
std::vector<u16> gupdates4(NUMBER_OF_PBS);
std::vector<u16> gupdates5(NUMBER_OF_PBS);
std::vector<u32> gupdates_addr(NUMBER_OF_PBS);
std::vector<u32> gupdates_data(NUMBER_OF_PBS);
std::vector<u32> gupdates_data1(NUMBER_OF_PBS);
std::vector<u32> gupdates_data2(NUMBER_OF_PBS);
std::vector<u32> gupdates_data3(NUMBER_OF_PBS);
std::vector<u32> gupdates_data4(NUMBER_OF_PBS);
// Counters
int count1 = 0;
int count2 = 0;
int iupd = 0;
bool iupdonce = false;
std::vector<u16> viupd(15); // the length of the update frequency bar
int vectorLengthGUI = 8; // length of playback history bar for the GUI version
int vectorLength = 15; // for console version
int vectorLength2 = 100; // for console version, how long to show
// More stuff
// Should we worry about the additonal memory these lists require? Bool will allocate
// very little memory
std::vector< std::vector<bool> > vector1(NUMBER_OF_PBS, std::vector<bool>(vectorLength, false));
std::vector< std::vector<bool> > vector2(NUMBER_OF_PBS, std::vector<bool>(vectorLength2, false));
std::vector<int> numberRunning(NUMBER_OF_PBS);
// Classes
extern DSPDebuggerHLE* m_DebuggerFrame;
// =======================================================================================
// Write title
// --------------
std::string writeTitle(int a, bool Wii)
{
std::string b;
if(a == 0)
{
if(m_DebuggerFrame->bShowBase) // show base 10
{
b = " adpcm adpcm_loop\n";
b = b + " Nr m pos / end lpos | voll volr | isl iss | pre yn1 yn2 pre yn1 yn2 | frac ratio[hi lo]\n";
}
else
{
b = " adpcm adpcm_loop\n";
b = b + " Nr pos / end lpos | voll volr | isl iss | pre yn1 yn2 pre yn1 yn2 | frac rati[hi lo ]\n";
}
}
else if(a == 1)
{
if(m_DebuggerFrame->bShowBase) // show base 10
{
b = " Nr pos / end lpos | voll volr | src form coef | 1 2 3 4 5 addr value\n";
}
else
{
b = " Nr pos / end lpos | voll volr | src form coef | 1 2 3 4 5 addr value\n";
}
}
else if(a == 2)
{
if(m_DebuggerFrame->bShowBase) // show base 10
{
b = " Nr pos / end lpos | voll volr | isl iss | e-l e-s\n";
}
else
{
b = " Nr pos / end lpos | voll volr | isl iss | e-l e-s\n";
}
}
else if(a == 3)
{
if(m_DebuggerFrame->bShowBase) // show base 10
{
if(Wii)
b = " Nr voll volr dl dr curv delt mixc r | v1 v2 v3 v4 v5 v6 v7 | d1 d2 d3 d4 d5 d6 d7\n";
else
b = " Nr voll volr dl dr curv delt mixc r | v1 v2 v3 v4 v5 v6 v7 | d1 d2 d3 d4 d5 d6 d7\n";
}
else
{
if(Wii)
b = " Nr voll volr dl dr curv delt mixc r | v1 v2 v3 v4 v5 v6 v7 | d1 d2 d3 d4 d5 d6 d7\n";
else
b = " Nr voll volr dl dr curv delt mixc r | v1 v2 v3 v4 v5 v6 v7 | d1 d2 d3 d4 d5 d6 d7\n";
}
}
return b;
}
// =======================================================================================
// =======================================================================================
// Write main message (presets)
// --------------
std::string writeMessage(int a, int i, bool Wii)
{
char buf [1000] = "";
std::string sbuf;
// =======================================================================================
// PRESETS
// ---------------------------------------------------------------------------------------
/*
PRESET 0
" Nr m pos / end lpos | voll volr | isl iss | pre yn1 yn2 pre yn1 yn2 | frac ratio[hi lo]\n";
"---------------|00 1 12,341,234/134,123,412 12341234 | 00,000 00,000 | 0 0 | 000 00000 00000 000 00000 00000 | 00000 00000[0 00000]
" Nr pos / end lpos | voll volr | isl iss | pre yn1 yn2 pre yn1 yn2 | frac rati[hi lo ]\n";
"---------------|00 12,341,234/134,123,412 12341234 | 00,000 00,000 | 0 0 | 000 0000 0000 000 0000 0000 | 0000 0000[0 00000]
PRESET 1 (updates)
" Nr pos / end lpos | voll volr | src form coef | 1 2 3 4 5 addr value\n";
"---------------|00 12,341,234/12,341,234 12341234 | 00,000 00,000 | 0 0 0 | 0 0 0 0 0 80808080 80808080
PRESET 2
" Nr pos / end lpos | voll volr | isl iss | e-l e-s\n";
"---------------|00 12,341,234/12341234 12,341,234 | 00000 00000 | 0 0 | 00,000,000 00,000,000
*/
if(a == 0)
{
if(m_DebuggerFrame->bShowBase) // base 10 (decimal)
{
if(Wii) // Wii
{
sprintf(buf,"%c%02i %i %10s/%10s %10s | %6s %6s | %i %i | %03i %05i %05i %03i %05i %05i | %05i %05i[%i %05i]",
223, i, mem[i], ThS(gsamplePos[i],true).c_str(), ThS(gsampleEnd[i],true).c_str(), ThS(gloopPos[i],true).c_str(),
ThS(gvolume_left[i]).c_str(), ThS(gvolume_right[i]).c_str(),
glooping[i], gis_stream[i],
gadloop1[i], gadloop2[i], gadloop3[i], gloop1[i], gloop2[i], gloop3[i],
gfrac[i], gratio[i], gratiohi[i], gratiolo[i]
);
}
else // GC
{
sprintf(buf,"%c%02i %10s/%10s %10s | %6s %6s | %i %i | %03i %05i %05i %03i %05i %05i | %05i %05i[%i %05i]",
223, i, ThS(gsamplePos[i],true).c_str(), ThS(gsampleEnd[i],true).c_str(), ThS(gloopPos[i],true).c_str(),
ThS(gvolume_left[i]).c_str(), ThS(gvolume_right[i]).c_str(),
glooping[i], gis_stream[i],
gadloop1[i], gadloop2[i], gadloop3[i], gloop1[i], gloop2[i], gloop3[i],
gfrac[i], gratio[i], gratiohi[i], gratiolo[i]
);
}
}
else
{
sprintf(buf,"%c%02i %08x/%08x %08x | %04x %04x | %i %i | %02x %04x %04x %02x %04x %04x | %04x %04x[%i %04x]",
223, i, gsamplePos[i], gsampleEnd[i], gloopPos[i],
gvolume_left[i], gvolume_right[i],
glooping[i], gis_stream[i],
gadloop1[i], gadloop2[i], gadloop3[i], gloop1[i], gloop2[i], gloop3[i],
gfrac[i], gratio[i], gratiohi[i], gratiolo[i]
);
}
}
else if(a == 1)
{
if(m_DebuggerFrame->bShowBase) // base 10 (decimal)
{
sprintf(buf,"%c%02i %10s/%10s %10s | %6s %6s | %u %u %u | %u %u %u %u %u %08x %08x %08x %08x %08x %08x",
223, i, ThS(gsamplePos[i]).c_str(), ThS(gsampleEnd[i]).c_str(), ThS(gloopPos[i]).c_str(),
ThS(gvolume_left[i]).c_str(), ThS(gvolume_right[i]).c_str(),
gsrc_type[i], gaudioFormat[i], gcoef[i],
gupdates1[i], gupdates2[i], gupdates3[i], gupdates4[i], gupdates5[i], gupdates_addr[i],
gupdates_data[i], gupdates_data1[i], gupdates_data2[i], gupdates_data3[i], gupdates_data4[i]
);
}
else // base 16 (hexadecimal)
{
if(Wii) // Wii
{
sprintf(buf,"%c%02i %08x/%08x %08x | %04x %04x | %u %u %u | %u %u %u %08x %08x %08x %08x %08x %08x",
223, i, gsamplePos[i], gsampleEnd[i], gloopPos[i],
gvolume_left[i], gvolume_right[i],
gsrc_type[i], gaudioFormat[i], gcoef[i],
gupdates1[i], gupdates2[i], gupdates3[i], gupdates_addr[i],
gupdates_data[i], gupdates_data1[i], gupdates_data2[i], gupdates_data3[i], gupdates_data4[i]
);
}
else // GC
{
sprintf(buf,"%c%02i %08x/%08x %08x | %04x %04x | %u %u %u | %u %u %u %u %u %08x %08x %08x %08x %08x %08x",
223, i, gsamplePos[i], gsampleEnd[i], gloopPos[i],
gvolume_left[i], gvolume_right[i],
gsrc_type[i], gaudioFormat[i], gcoef[i],
gupdates1[i], gupdates2[i], gupdates3[i], gupdates4[i], gupdates5[i], gupdates_addr[i],
gupdates_data[i], gupdates_data1[i], gupdates_data2[i], gupdates_data3[i], gupdates_data4[i]
);
}
}
}
else if(a == 2)
{
if(m_DebuggerFrame->bShowBase)
{
sprintf(buf,"%c%02i %10s/%10s %10s | %05i %05i | %i %i | %10s %10s",
223, i, ThS(gsamplePos[i]).c_str(), ThS(gsampleEnd[i]).c_str(), ThS(gloopPos[i]).c_str(),
gvolume_left[i], gvolume_right[i],
glooping[i], gis_stream[i],
ThS(gsampleEnd[i] - gloopPos[i], false).c_str(), ThS(gsampleEnd[i] - gsamplePos[i], false).c_str()
);
}
else
{
sprintf(buf,"%c%02i %08x/%08x %08x | %04x %04x | %i %i | %08x %08x",
223, i, gsamplePos[i], gsampleEnd[i], gloopPos[i],
gvolume_left[i], gvolume_right[i],
glooping[i], gis_stream[i],
gsampleEnd[i] - gloopPos[i], gsampleEnd[i] - gsamplePos[i]
);
}
}
/*
PRESET 3
" Nr voll volr dl dr curv delt mixc r | v1 v2 v3 v4 v5 v6 v7 | d1 d2 d3 d4 d5 d6 d7\n";
"---------------|00 00000 00000 00000 00000 00000 00000 00000 0 | 00000 00000 00000 00000 00000 00000 00000 | 00000 00000 00000 00000 00000 00000 00000
*/
else if(a == 3)
{
if(m_DebuggerFrame->bShowBase)
{
if(Wii) // Wii
{
sprintf(buf,"%c%02i %05i %05i %05i %05i %05i %05i %05i %i | %05i %05i %05i %05i %05i %05i %05i | %05i %05i %05i %05i %05i %05i %05i",
223, i,
gvolume_left[i], gvolume_right[i], gmix_unknown[i], gmix_unknown2[i], gcur_volume[i], gcur_volume_delta[i],
gmixer_control_wii[i], (gmixer_control_wii[i] & MIXCONTROL_RAMPING),
gmixer_vol1[i], gmixer_vol2[i], gmixer_vol3[i], gmixer_vol4[i], gmixer_vol5[i],
gmixer_vol6[i], gmixer_vol7[i],
gmixer_d1[i], gmixer_d2[i], gmixer_d3[i], gmixer_d4[i], gmixer_d5[i],
gmixer_d6[i], gmixer_d7[i]
);
}
else // GC
{
sprintf(buf,"%c%02i %05i %05i %05i %05i %05i %05i %08i %i | %05i %05i %05i %05i %05i %05i %05i | %05i %05i %05i %05i %05i %05i %05i",
223, i,
gvolume_left[i], gvolume_right[i], gmix_unknown[i], gmix_unknown2[i], gcur_volume[i], gcur_volume_delta[i],
gmixer_control[i], (gmixer_control[i] & MIXCONTROL_RAMPING),
gmixer_vol1[i], gmixer_vol2[i], gmixer_vol3[i], gmixer_vol4[i], gmixer_vol5[i],
gmixer_vol6[i], gmixer_vol7[i],
gmixer_d1[i], gmixer_d2[i], gmixer_d3[i], gmixer_d4[i], gmixer_d5[i],
gmixer_d6[i], gmixer_d7[i]
);
}
}
else
{
if(Wii)
{
sprintf(buf,"%c%02i %04x %04x %04x %04x %04x %04x %08x %i | %04x %04x %04x %04x %04x %04x %04x | %04x %04x %04x %04x %04x %04x %04x",
223, i,
gvolume_left[i], gvolume_right[i], gmix_unknown[i], gmix_unknown2[i], gcur_volume[i], gcur_volume_delta[i],
gmixer_control_wii[i], (gmixer_control_wii[i] & MIXCONTROL_RAMPING),
gmixer_vol1[i], gmixer_vol2[i], gmixer_vol3[i], gmixer_vol4[i], gmixer_vol5[i],
gmixer_vol6[i], gmixer_vol7[i],
gmixer_d1[i], gmixer_d2[i], gmixer_d3[i], gmixer_d4[i], gmixer_d5[i],
gmixer_d6[i], gmixer_d7[i]
);
}
else
{
sprintf(buf,"%c%02i %04x %04x %04x %04x %04x %04x %04x %i | %04x %04x %04x %04x %04x %04x %04x | %04x %04x %04x %04x %04x %04x %04x",
223, i,
gvolume_left[i], gvolume_right[i], gmix_unknown[i], gmix_unknown2[i], gcur_volume[i], gcur_volume_delta[i],
gmixer_control[i], (gmixer_control[i] & MIXCONTROL_RAMPING),
gmixer_vol1[i], gmixer_vol2[i], gmixer_vol3[i], gmixer_vol4[i], gmixer_vol5[i],
gmixer_vol6[i], gmixer_vol7[i],
gmixer_d1[i], gmixer_d2[i], gmixer_d3[i], gmixer_d4[i], gmixer_d5[i],
gmixer_d6[i], gmixer_d7[i]
);
}
}
}
sbuf = buf;
return sbuf;
}
// ================
// =======================================================================================
// Collect parameters from Wii or GC
// --------------
/*
std::string ShowAllPB(int a, int i)
{
if(a == 0)
{
}
else if(a == 1)
{
}
else if(a == 1)
{
}
else if(a == 1)
}
*/
// ================
// =======================================================================================
// Collect parameters from Wii or GC
// --------------
//inline void MixAddVoice(ParamBlockType &pb
//void CollectPB(bool Wii, int i, AXParamBlockWii * PBw, ParamBlockType &pb)
template<class ParamBlockType> void CollectPB(bool Wii, int i, ParamBlockType &PBs)
//void CollectPB(bool Wii, int i, AXParamBlockWii * PBw, AXParamBlock * PBs)
{
// AXPB base
gsrc_type[i] = PBs[i].src_type;
gcoef[i] = PBs[i].coef_select;
if(Wii) gmixer_control_wii[i] = PBs[i].mixer_control;
else gmixer_control[i] = PBs[i].mixer_control;
//running[i] = PBs[i].running;
gis_stream[i] = PBs[i].is_stream;
// mixer (some differences)
gvolume_left[i] = PBs[i].mixer.volume_left;
gvolume_right[i] = PBs[i].mixer.volume_right;
gmix_unknown[i] = PBs[i].mixer.unknown;
gmix_unknown2[i] = PBs[i].mixer.unknown2;
gcur_volume[i] = PBs[i].vol_env.cur_volume;
gcur_volume_delta[i] = PBs[i].vol_env.cur_volume_delta;
gmixer_vol1[i] = PBs[i].mixer.unknown3[0];
gmixer_vol2[i] = PBs[i].mixer.unknown3[2];
gmixer_vol3[i] = PBs[i].mixer.unknown3[4];
gmixer_vol4[i] = PBs[i].mixer.unknown3[6];
gmixer_vol5[i] = PBs[i].mixer.unknown3[0];
gmixer_vol6[i] = PBs[i].mixer.unknown3[2];
gmixer_vol7[i] = PBs[i].mixer.unknown3[4];
gmixer_d1[i] = PBs[i].mixer.unknown4[1];
gmixer_d2[i] = PBs[i].mixer.unknown4[3];
gmixer_d3[i] = PBs[i].mixer.unknown4[5];
gmixer_d4[i] = PBs[i].mixer.unknown4[7];
gmixer_d5[i] = PBs[i].mixer.unknown4[1];
gmixer_d6[i] = PBs[i].mixer.unknown4[3];
gmixer_d7[i] = PBs[i].mixer.unknown4[5];
// PBAudioAddr audio_addr
glooping[i] = PBs[i].audio_addr.looping;
gaudioFormat[i] = PBs[i].audio_addr.sample_format;
gloopPos[i] = (PBs[i].audio_addr.loop_addr_hi << 16) | PBs[i].audio_addr.loop_addr_lo;
gsampleEnd[i] = (PBs[i].audio_addr.end_addr_hi << 16) | PBs[i].audio_addr.end_addr_lo;
gsamplePos[i] = (PBs[i].audio_addr.cur_addr_hi << 16) | PBs[i].audio_addr.cur_addr_lo;
if(gloopPos[i] > 0x20000000) gloopPos[i] -= 0x20000000;
if(gsampleEnd[i] > 0x20000000) gsampleEnd[i] -= 0x20000000;
if(gsamplePos[i] > 0x20000000) { gsamplePos[i] -= 0x20000000;
mem[i] = 2;} else { mem[i] = 1; }
// PBADPCMLoopInfo adpcm_loop_info (same in GC and Wii)
gadloop1[i] = PBs[i].adpcm.pred_scale;
gadloop2[i] = PBs[i].adpcm.yn1;
gadloop3[i] = PBs[i].adpcm.yn2;
gloop1[i] = PBs[i].adpcm_loop_info.pred_scale;
gloop2[i] = PBs[i].adpcm_loop_info.yn1;
gloop3[i] = PBs[i].adpcm_loop_info.yn2;
// updates (differences)
gupdates1[i] = PBs[i].updates.num_updates[0];
gupdates2[i] = PBs[i].updates.num_updates[1];
gupdates3[i] = PBs[i].updates.num_updates[2];
gupdates4[i] = PBs[i].updates.num_updates[3];
gupdates5[i] = PBs[i].updates.num_updates[4];
gupdates_addr[i] = (PBs[i].updates.data_hi << 16) | PBs[i].updates.data_lo;
if(gupdates_addr[i] > 0x80000000 && gupdates_addr[i] < 0x93ffffff)
{
gupdates_data[i] = Memory_Read_U32(gupdates_addr[i]);
gupdates_data1[i] = Memory_Read_U32(gupdates_addr[i] + 4);
gupdates_data2[i] = Memory_Read_U32(gupdates_addr[i] + 8);
gupdates_data3[i] = Memory_Read_U32(gupdates_addr[i] + 12);
gupdates_data3[i] = Memory_Read_U32(gupdates_addr[i] + 16);
}
// PBSampleRateConverter src
gratio[i] = (u32)(((PBs[i].src.ratio_hi << 16) + PBs[i].src.ratio_lo) * ratioFactor);
gratiohi[i] = PBs[i].src.ratio_hi;
gratiolo[i] = PBs[i].src.ratio_lo;
gfrac[i] = PBs[i].src.cur_addr_frac;
}
// ===============
// =======================================================================================
// Prepare the condition that makes us show a certain block
// --------------
template<class ParamBlockType>
bool PrepareConditions(bool Wii, int i, ParamBlockType &PBs)
{
bool Conditions;
if (m_DebuggerFrame->gOnlyLooping) // show only looping blocks
{
Conditions = PBs[i].audio_addr.looping ? true : false;
}
else if (m_DebuggerFrame->gShowAll) // show all blocks
{
Conditions = true;
}
else if (m_DebuggerFrame->giShowAll > -1) // show all blocks
{
if (m_DebuggerFrame->giShowAll == 0)
Conditions = (i < 31);
else if(m_DebuggerFrame->giShowAll == 1)
Conditions = (i > 30 && i < 61);
else if(m_DebuggerFrame->giShowAll == 2)
Conditions = (i > 60 && i < 91);
else if(m_DebuggerFrame->giShowAll == 3)
Conditions = (i > 90 && i < 121);
}
else // show only the ones that have recently been running
{
Conditions = (numberRunning.at(i) > 0 || PBs[i].audio_addr.looping);
}
return Conditions;
}
// ===============
template<class ParamBlockType>
void Logging_(short* _pBuffer, int _iSize, int a, bool Wii, ParamBlockType &PBs,
int numberOfPBs, u32 m_addressPBs)
//void Logging__(short* _pBuffer, int _iSize, int a, bool Wii)
{
bool Conditions; // Select blocks to show
// =======================================================================================
// Update parameter values
// --------------
// We could chose to update these only if a block is currently running. Later I'll add options
// to see both the current and the latest active value.
int irun = 0;
for (int i = 0; i < numberOfPBs; i++)
{
// --------------------------------------------------------------------
// Write a line for the text log if nothing is playing
// --------------
if (PBs[i].running)
{
irun++;
}
if (i == numberOfPBs - 1 && irun == 0)
{
for (int j = 0; j < nFiles; j++)
{
std::string sfbuff;
sfbuff = "-----\n";
PrintFile(j, (char *)sfbuff.c_str());
}
}
// --------------
// --------------------------------------
// Now go through only a subset of the blocks depending on Conditions
// ------------------
/* Prepare conditions. We may for example get Conditions = true for blocks
that currently have numberRunning.at(i) > 0 */
Conditions = PrepareConditions(Wii, i, PBs);
if (Conditions)
{
// Collect parameters
CollectPB(Wii, i, PBs);
// ---------------------------------------------------------------------------------------
// Write to file
// --------------
for (int ii = 0; ii < nFiles; ii++)
{
std::string sfbuff;
if(a == 0) sfbuff = "***"; // note if it's before or after an update (*** = before)
else sfbuff = " ";
// write running
char cbuf[10];
sprintf(cbuf, "%i", PBs[i].running);
sfbuff = sfbuff + cbuf;
sfbuff = sfbuff + writeMessage(ii, i, Wii);
// write _iSize
strcpy(cbuf, ""); sprintf(cbuf, "%i", _iSize);
sfbuff = sfbuff + " | _iSize: " + cbuf + "\n";
PrintFile(ii, (char *)sfbuff.c_str());
}
// --------------
}
}
// ==============
// =======================================================================================
// Control how often the screen is updated, and then update the screen
// --------------
if(a == 0) count1++; // a == 0 when Logging is called before the blocks are updated
if (m_DebuggerFrame->gUpdFreq > 0 && count1 > (200/m_DebuggerFrame->gUpdFreq))
{
// =======================================================================================
/* Save the displayed running history for each block. Vector1 is a vector1[NUMBER_OF_PBS]
[100] vector. */
// --------------
/*
Move all items back like this:
1 to 0
2 1
3 ...
5 to 4
*/
for (int i = 0; i < numberOfPBs; i++)
{
for (int j = 1; j < vectorLength; j++)
{
vector1.at(i).at(j-1) = vector1.at(i).at(j);
}
// save the latest value
vector1.at(i).at(vectorLength-1) = PBs[i].running ? true : false;
}
// ==============
// =======================================================================================
/* Have a separate set for which ones to show. Currently show blocks that have been
running at least once the last 100 updates.
// --------------
Move all items back like this:
1 to 0
2 1
3 ...
*/
for (int i = 0; i < numberOfPBs; i++)
{
for (int j = 1; j < vectorLength2; j++)
{
vector2.at(i).at(j-1) = vector2.at(i).at(j);
}
// save the latest value
vector2.at(i).at(vectorLength2-1) = PBs[i].running ? true : false;
}
// ==============
// =======================================================================================
// Count how many we have running now in a certain block
// --------------
int jj = 0;
for (int i = 0; i < numberOfPBs; i++)
{
jj = 0;
for (int j = 0; j < vectorLength2-1; j++) // the hundred last updates
{
if (vector2.at(i).at(j)) // if it was on then
{
jj++;
}
numberRunning.at(i) = jj;
}
}
// ==============
// =======================================================================================
// Write header
// --------------
char buffer [1000] = "";
std::string sbuff;
sbuff = writeTitle(m_DebuggerFrame->gPreset, Wii);
// ==============
// =======================================================================================
// Now go through all blocks
// --------------
for (int i = 0; i < numberOfPBs; i++)
{
// --------------------------------------
// Now go through only a subset of the blocks depending on Conditions
// ------------------
// Prepare conditions
Conditions = PrepareConditions(Wii, i, PBs);
if (Conditions)
{
// --------------------------------------
// Save playback history text string for the console and GUI debugger
// ------------------
if(m_DebuggerFrame)
{
std::string guipr; // gui progress
for (int j = 0; j < vectorLengthGUI; j++)
{
if(vector1.at(i).at(j) == false)
{
guipr = guipr + "0";
}
else
{
guipr = guipr + "1";
}
}
u32 run = atoi( guipr.c_str());
m_DebuggerFrame->m_GPRListView->m_CachedRegs[1][i] = run;
guipr.clear();
}
// and for the console debugger
for (int j = 0; j < vectorLength; j++)
{
if(vector1.at(i).at(j) == false)
{
sbuff = sbuff + " ";
}
else
{
sprintf(buffer, "%c", 177);
sbuff = sbuff + buffer; strcpy(buffer, "");
}
}
// ---------
// Hopefully this is false if we don't have a debugging window and so it doesn't cause a crash
if(m_DebuggerFrame)
{
m_DebuggerFrame->m_GPRListView->m_CachedRegs[2][i] = gsamplePos[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[3][i] = gsampleEnd[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[4][i] = gloopPos[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[5][i] = gvolume_left[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[6][i] = gvolume_right[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[7][i] = glooping[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[8][i] = gloop1[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[9][i] = gloop2[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[10][i] = gloop3[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[11][i] = gis_stream[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[12][i] = gaudioFormat[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[13][i] = gsrc_type[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[14][i] = gcoef[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[15][i] = gfrac[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[16][i] = gratio[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[17][i] = gratiohi[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[18][i] = gratiolo[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[19][i] = gupdates1[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[20][i] = gupdates2[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[21][i] = gupdates3[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[22][i] = gupdates4[i];
m_DebuggerFrame->m_GPRListView->m_CachedRegs[23][i] = gupdates5[i];
}
// add new line
sbuff = sbuff + writeMessage(m_DebuggerFrame->gPreset, i, Wii); strcpy(buffer, "");
sbuff = sbuff + "\n";
} // end of if(Conditions)
// ==============
} // end of for (int i = 0; i < numberOfPBs; i++)
// =======================================================================================
// Write global values
// ---------------
int nOfBlocks;
int span = m_DebuggerFrame->gLastBlock - m_addressPBs;
if(Wii)
nOfBlocks = (m_DebuggerFrame->gLastBlock-m_addressPBs) / 256;
else
nOfBlocks = (m_DebuggerFrame->gLastBlock-m_addressPBs) / 192;
sprintf(buffer, "\nThe parameter blocks span from %08x to %08x (%s bytes) impl. %i blocks | numberOfPBs %i | _iSize %i\n",
m_addressPBs, m_DebuggerFrame->gLastBlock, ThS(span).c_str(), nOfBlocks, numberOfPBs, _iSize);
sbuff = sbuff + buffer; strcpy(buffer, "");
// ===============
// =======================================================================================
// Write settings
// ---------------
sprintf(buffer, "\nSettings: SSBM fix %i | SSBM rem1 %i | SSBM rem2 %i\nSequenced %i | Volume %i | Reset %i | Only looping %i | Save file %i\n",
gSSBM, gSSBMremedy1, gSSBMremedy2, gSequenced,
gVolume, gReset, m_DebuggerFrame->gOnlyLooping, m_DebuggerFrame->gSaveFile);
sbuff = sbuff + buffer; strcpy(buffer, "");
// ===============
// =======================================================================================
// Show update frequency
// ---------------
sbuff = sbuff + "\n";
if(!iupdonce)
{
viupd.at(0) = 1;
viupd.at(1) = 1;
viupd.at(2) = 1;
iupdonce = true;
}
for (u32 i = 0; i < viupd.size(); i++) // 0, 1,..., 9
{
if (i < viupd.size()-1)
{
viupd.at(viupd.size()-i-1) = viupd.at(viupd.size()-i-2); // move all forward
}
else
{
viupd.at(0) = viupd.at(viupd.size()-1);
}
// Correction
if (viupd.at(viupd.size()-3) == 1 && viupd.at(viupd.size()-2) == 1 && viupd.at(viupd.size()-1) == 1)
{
viupd.at(0) = 0;
}
if(viupd.at(0) == 0 && viupd.at(1) == 1 && viupd.at(2) == 1 && viupd.at(3) == 0)
{
viupd.at(0) = 1;
}
}
for (u32 i = 0; i < viupd.size(); i++)
{
if(viupd.at(i) == 0)
sbuff = sbuff + " ";
else
sbuff = sbuff + ".";
}
// ================
// =======================================================================================
// Print
// ----------------
// FIXME: Console::ClearScreen();
INFO_LOG(CONSOLE, "%s", sbuff.c_str());
sbuff.clear(); strcpy(buffer, "");
// ================
// New values are written so update - DISABLED - It flickered a lot, even worse than a
// console window. So for now only the console windows is updated.
/*
if(m_DebuggerFrame)
{
m_DebuggerFrame->NotifyUpdate();
}
*/
count2=0;
count1=0;
} // end of if (j>20)
} // end of function
// I placed this in CUCode_AX so it can share member values with that class
void CUCode_AX::Logging(short* _pBuffer, int _iSize, int a, bool Wii)
{
/* Doing all this may have a noticable CPU effect, so we can disable it completely
this way. But remember that "Save to file" will not write anything then either. */
/*
This is all broken right now since ReadOutPBs is gone.
*/
/*
if (m_DebuggerFrame->gUpdFreq > 0)
{
int version; // AX version
int numberOfPBs;
// Declare structures
AXParamBlock PBs[NUMBER_OF_PBS];
AXParamBlockWii PBw[NUMBER_OF_PBS];
AXParamBlockWii_ PBw_[NUMBER_OF_PBS];
if (_CRC == 0xfa450138) version = 0; else version = 1;
// Read out structs and number of PBs that have data
if (Wii)
{
if(version == 0)
{
// numberOfPBs = ReadOutPBsWii(m_addressPBs, PBw, NUMBER_OF_PBS);
// Logging_(_pBuffer, _iSize, a, Wii, PBw, numberOfPBs, m_addressPBs);
}
else
{
// numberOfPBs = ReadOutPBsWii(m_addressPBs, PBw_, NUMBER_OF_PBS);
// Logging_(_pBuffer, _iSize, a, Wii, PBw_, numberOfPBs, m_addressPBs);
}
}
else
{
// numberOfPBs = ReadOutPBs(m_addressPBs, PBs, NUMBER_OF_PBS);
// Logging_(_pBuffer, _iSize, a, Wii, PBs, numberOfPBs, m_addressPBs);
}
} */
}

View File

@ -1,297 +0,0 @@
//
// Licensetype: GNU General Public License (GPL)
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
//
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
//
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
//
// Includes
// -------------
#include <iostream>
#include <fstream>
#include <sstream>
#ifndef _WIN32
#include <stdlib.h>
#endif
//#include "ConsoleWindow.h" // Open and close console
#include "Debugger.h"
#include "PBView.h"
#include "IniFile.h"
#include "FileUtil.h"
#include "StringUtil.h"
#include "FileSearch.h"
// Declarations and definitions
// -------------
extern std::vector<std::string> sMailLog, sMailTime;
extern DSPDebuggerHLE* m_DebuggerFrame;
// =======================================================================================
// Update mail window
// --------------
void DSPDebuggerHLE::DoUpdateMail()
{
//Console::Print("i %i %i\n", sFullMail.size(), sMailLog.size());
if(sFullMail.size() > 0 && sMailLog.size() > 0)
{
m_log->SetValue(wxString::FromAscii(sFullMail.at(m_RadioBox[3]->GetSelection()).c_str()));
m_log->SetDefaultStyle(wxTextAttr(*wxBLUE)); // doesn't work because of the current wx
m_log1->SetValue(wxString::FromAscii(sMailLog.at(m_RadioBox[3]->GetSelection()).c_str()));
m_log1->AppendText(wxT("\n\n"));
}
}
void DSPDebuggerHLE::UpdateMail(wxNotebookEvent& event)
{
DoUpdateMail();
/* This may be called before m_DebuggerFrame is fully created through the
EVT_NOTEBOOK_PAGE_CHANGED, in that case it will crash because this
is accessing members of it */
if(StoreMails && m_DebuggerFrame) ReadDir();
}
// Change mail from radio button change
void DSPDebuggerHLE::ChangeMail(wxCommandEvent& event)
{
//Console::Print("abc");
DoUpdateMail();
//if(StoreMails) ReadDir();
}
// ==============
// =======================================================================================
// Read out mails from dir
// --------------
void DSPDebuggerHLE::ReadDir()
{
CFileSearch::XStringVector Directories;
//Directories.push_back("Logs/Mail");
Directories.push_back(File::GetUserPath(D_MAILLOGS_IDX));
CFileSearch::XStringVector Extensions;
Extensions.push_back("*.log");
CFileSearch FileSearch(Extensions, Directories);
const CFileSearch::XStringVector& rFilenames = FileSearch.GetFileNames();
//m_gc->Show(false);
//m_gc->Append(wxT("SSBM ffffix"));
//m_gc->Show(true);
// Clear in case we already did this earlier
all_all_files.clear();
if (rFilenames.size() > 0 && m_gc && m_wii)
{
for (u32 i = 0; i < rFilenames.size(); i++)
{
std::string FileName;
SplitPath(rFilenames[i], NULL, &FileName, NULL); // place the filename in FileName
//std::string FileName = StripSpaces(*FileName);
std::vector<std::string> pieces;
SplitString(FileName, "_sep", pieces); // split string
// Save all filenames heres
if(pieces[2] == "0") all_all_files.push_back(pieces[0]);
// Cut to size
std::string cut;
if(pieces[0].length() > 18)
cut = pieces[0].substr(0, 18) + "...";
else
cut = pieces[0];
//Console::Print("%s %s %s\n", pieces[0].c_str(), pieces[1].c_str(),
// pieces[2].c_str(), pieces[3].c_str());
if (NoDuplicate(pieces[0]) && pieces.size() >= 3)
{
all_files.push_back(pieces[0]);
if (pieces[3] == "GC")
{
gc_files.push_back(pieces[0]);
m_gc->Append(wxString::FromAscii(cut.c_str()));
}
else
{
wii_files.push_back(pieces[0]);
m_wii->Append(wxString::FromAscii(cut.c_str()));
}
}
}
}
}
// =======================================================================================
// Check for duplicates and count files from all_all_files
// --------------
bool DSPDebuggerHLE::NoDuplicate(std::string FileName)
{
for (u32 i = 0; i < all_files.size(); i++)
{
if(all_files.at(i) == FileName)
return false;
}
return true;
}
// Count the number of files for each game
u32 DSPDebuggerHLE::CountFiles(std::string FileName)
{
int match = 0;
for (u32 i = 0; i < all_all_files.size(); i++)
{
//Console::Print("CountFiles %i %s\n", i, all_all_files[i].c_str());
if(all_all_files[i] == FileName)
match++;
}
//Console::Print("We found %i files for this game\n", match);
return match;
}
// ==============
// =======================================================================================
// Read file from harddrive
// --------------
std::string DSPDebuggerHLE::Readfile_(std::string FileName)
{
char c; // declare a char variable
FILE *file; // declare a FILE pointer
std::string sz = "";
if(File::Exists(FileName.c_str()))
file = fopen(FileName.c_str(), "r"); // open a text file for reading
else
return "";
if(file == NULL)
{
// file could not be opened
}
else
{
while(1) // looping through file
{
c = fgetc(file);
if(c != EOF)
sz += c; // print the file one character at a time
else
break; // break when EOF is reached
}
fclose(file);
}
return sz;
}
// Read file
void DSPDebuggerHLE::Readfile(std::string FileName, bool GC)
{
u32 n = CountFiles(FileName); // count how many mails we have
u32 curr_n = 0;
std::ifstream file;
for (u32 i = 0; i < m_RadioBox[3]->GetCount(); i++)
{
if(m_RadioBox[3]->IsItemEnabled(i)) curr_n++;
m_RadioBox[3]->Enable(i, false); // disable all
}
//Console::Print("Disabled all: n %i\n", n);
for (u32 i = 0; i < n; i++)
{
m_RadioBox[3]->Enable(i, true); // then anble the right ones
//Console::Print("m_RadioBox[3] enabled: %i\n", i);
std::string sz = "";
std::ostringstream ci;
ci << i;
std::string f0 = std::string(File::GetUserPath(D_MAILLOGS_IDX)) + FileName + "_sep" + ci.str() + "_sep" + "0_sep" + (GC ? "GC" : "Wii") + "_sep.log";
std::string f1 = std::string(File::GetUserPath(D_MAILLOGS_IDX)) + FileName + "_sep" + ci.str() + "_sep" + "1_sep" + (GC ? "GC" : "Wii") + "_sep.log";
//Console::Print("ifstream %s %s\n", f0.c_str(), f1.c_str());
if(sFullMail.size() <= i) sFullMail.resize(sFullMail.size() + 1);
if(sMailLog.size() <= i) sMailLog.resize(sMailLog.size() + 1);
if(Readfile_(f0).length() > 0) sFullMail.at(i) = Readfile_(f0);
else sFullMail.at(i) = "";
if(Readfile_(f1).length() > 0) sMailLog.at(i) = Readfile_(f1);
else sMailLog.at(i) = "";
}
if(n < curr_n) m_RadioBox[3]->Select(n - 1);
//Console::Print("Select: %i | n %i curr_n %i\n", n - 1, n, curr_n);
DoUpdateMail();
}
// ==============
// =======================================================================================
// Read the file to the text window
// ---------------
void DSPDebuggerHLE::OnGameChange(wxCommandEvent& event)
{
if(event.GetId() == 2006)
{
// Only allow one selected game at a time
for (u32 i = 0; i < m_gc->GetCount(); ++i)
if(i != (u32)event.GetInt()) m_gc->Check(i, false);
for (u32 i = 0; i < m_wii->GetCount(); ++i)
m_wii->Check(i, false);
Readfile(gc_files[event.GetInt()], true);
}
else
{
for (u32 i = 0; i < m_gc->GetCount(); ++i)
m_gc->Check(i, false);
for (u32 i = 0; i < m_wii->GetCount(); ++i)
if(i != (u32)event.GetInt()) m_wii->Check(i, false);
Readfile(wii_files[event.GetInt()], false);
}
}
// Settings
void DSPDebuggerHLE::MailSettings(wxCommandEvent& event)
{
//for (int i = 0; i < all_all_files.size(); ++i)
//Console::Print("s: %s \n", all_all_files.at(i).c_str());
ScanMails = m_gcwiiset->IsChecked(0);
StoreMails = m_gcwiiset->IsChecked(1);
}

View File

@ -1,103 +0,0 @@
// Copyright (C) 2003 Dolphin Project.
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
#include "PBView.h"
#include <iostream>
#include <string>
#include <stdio.h>
#include <stdlib.h>
// external declarations
extern const char* GetGRPName(unsigned int index);
CPBView::CPBView(wxWindow* parent, const wxWindowID id, const wxPoint& pos, const wxSize& size, long style)
: wxListCtrl(parent, id, pos, size, style)
{
}
void CPBView::Update()
{
ClearAll();
InsertColumn(1, wxT("upd4"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("upd3"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("upd2"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("upd1"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("upd0"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("r_lo"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("r_hi"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("ratio"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("frac"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("coef"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("src_t"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("form"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("isstr"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("yn2"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("yn1"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("pred_s"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("isloop"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("volr"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("voll"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("loopto"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(1, wxT("end"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(0, wxT("pos"), wxLIST_FORMAT_LEFT, 90);
InsertColumn(0, wxT("run"), wxLIST_FORMAT_RIGHT, 50);
InsertColumn(0, wxT("Block"), wxLIST_FORMAT_CENTER, 40);
for (int i = 0; i < 64; i++)
{
InsertItemInReportView(i);
}
}
void CPBView::InsertItemInReportView(int _Row)
{
long tmp = InsertItem(_Row, wxString::Format(wxT("%02i"), _Row), 0);
SetItemData(tmp, _Row);
wxString text;
// A somewhat primitive attempt to show the playing history for a certain block.
char cbuff [33];
sprintf(cbuff, "%08i", m_CachedRegs[_Row][0]); //TODO?
std::string c = cbuff;
int n[8];
for (int j = 0; j < 8; j++)
{
n[j] = atoi( c.substr(j, 1).c_str() );
// 149 = dot, 160 = space
if (n[j] == 1)
n[j] = 149;
else
n[j] = 160;
}
// pretty neat huh?
SetItem(tmp, 1, wxString::Format(wxT("%c%c%c%c%c%c%c%c"), n[0],n[1],n[2],n[3],n[4],n[5],n[6],n[7]));
for (int column = 2; column < GetColumnCount(); column++)
SetItem(tmp, column, wxString::Format(wxT("0x%08x"), m_CachedRegs[_Row][column]));
}

View File

@ -1,45 +0,0 @@
// Copyright (C) 2003 Dolphin Project.
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, version 2.0.
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License 2.0 for more details.
// A copy of the GPL 2.0 should have been included with the program.
// If not, see http://www.gnu.org/licenses/
// Official SVN repository and contact information can be found at
// http://code.google.com/p/dolphin-emu/
#ifndef __PBView_h__
#define __PBView_h__
#include <wx/listctrl.h>
#include <wx/dcclient.h>
#include "Common.h"
class CPBView : public wxListCtrl
{
public:
CPBView(wxWindow* parent,
const wxWindowID id,
const wxPoint& pos,
const wxSize& size,
long style);
void Update();
u32 m_CachedRegs[64][92];
private:
bool m_CachedRegHasChanged[64];
void InsertItemInReportView(int _Index);
};
#endif

View File

@ -22,29 +22,42 @@
#include "pluginspecs_dsp.h"
#include "StringUtil.h"
#include "../../../Core/Core/Src/ConfigManager.h" // FIXME
extern DSPInitialize g_dspInitialize;
#if defined(HAVE_WX) && HAVE_WX
#include "Debugger/Debugger.h"
class DSPDebuggerHLE;
extern DSPDebuggerHLE* m_DebuggerFrame;
#endif
extern bool gSSBM;
extern bool gSSBMremedy1;
extern bool gSSBMremedy2;
extern bool gSequenced;
extern bool gVolume;
extern bool gReset;
extern float ratioFactor; // a global to get the ratio factor from MixAdd
u8 Memory_Read_U8(u32 _uAddress);
u16 Memory_Read_U16(u32 _uAddress);
u32 Memory_Read_U32(u32 _uAddress);
float Memory_Read_Float(u32 _uAddress);
void* Memory_Get_Pointer(u32 _uAddress);
extern PLUGIN_GLOBALS* globals;
extern u8* g_pMemory;
// TODO: Wii support? Most likely audio data still must be in the old 24MB TRAM.
#define RAM_MASK 0x1FFFFFF
inline u8 Memory_Read_U8(u32 _uAddress)
{
_uAddress &= RAM_MASK;
return g_pMemory[_uAddress];
}
inline u16 Memory_Read_U16(u32 _uAddress)
{
_uAddress &= RAM_MASK;
return Common::swap16(*(u16*)&g_pMemory[_uAddress]);
}
inline u32 Memory_Read_U32(u32 _uAddress)
{
_uAddress &= RAM_MASK;
return Common::swap32(*(u32*)&g_pMemory[_uAddress]);
}
inline float Memory_Read_Float(u32 _uAddress)
{
u32 uTemp = Memory_Read_U32(_uAddress);
return *(float*)&uTemp;
}
inline void* Memory_Get_Pointer(u32 _uAddress)
{
_uAddress &= RAM_MASK;
return &g_pMemory[_uAddress];
}
#endif

View File

@ -11,8 +11,6 @@ files = [
'HLEMixer.cpp',
'main.cpp',
'Config.cpp',
'Globals.cpp',
'Debugger/File.cpp',
'UCodes/UCode_AX.cpp',
'UCodes/UCode_AXWii.cpp',
'UCodes/UCode_CARD.cpp',
@ -30,12 +28,6 @@ dspenv = env.Clone()
if dspenv['HAVE_WX']:
files += [
'ConfigDlg.cpp',
'Debugger/Debugger.cpp',
'Debugger/PBView.cpp',
'Debugger/Mails.cpp',
'Debugger/Blocks.cpp',
'Debugger/Logging.cpp',
]
dspenv.Append(

View File

@ -17,11 +17,6 @@
#include "FileUtil.h" // For IsDirectory()
#include "StringUtil.h" // For StringFromFormat()
#if defined(HAVE_WX) && HAVE_WX
#include "../Debugger/Debugger.h"
//#include "../Logging/File.h" // For PrintFile()
extern DSPDebuggerHLE* m_DebuggerFrame;
#endif
#include <sstream>
#include "../Config.h"
@ -34,26 +29,12 @@ extern DSPDebuggerHLE* m_DebuggerFrame;
#include "UCode_AX.h"
#include "UCode_AX_Voice.h"
// ------------------------------------------------------------------
// Externals
// -----------
extern bool gSSBM;
extern bool gSSBMremedy1;
extern bool gSSBMremedy2;
extern bool gSequenced;
extern bool gVolume;
extern bool gReset;
std::vector<std::string> sMailLog, sMailTime;
// -----------
CUCode_AX::CUCode_AX(CMailHandler& _rMailHandler)
: IUCode(_rMailHandler)
, m_addressPBs(0xFFFFFFFF)
: IUCode(_rMailHandler)
, m_addressPBs(0xFFFFFFFF)
{
// we got loaded
m_rMailHandler.PushMail(0xDCD10000);
m_rMailHandler.PushMail(DSP_INIT);
templbuffer = new int[1024 * 1024];
temprbuffer = new int[1024 * 1024];
@ -66,233 +47,22 @@ CUCode_AX::~CUCode_AX()
delete [] temprbuffer;
}
// Save file to harddrive
void CUCode_AX::SaveLogFile(std::string f, int resizeTo, bool type, bool Wii)
// Needs A LOT of love!
static void ProcessUpdates(AXPB &PB)
{
//#ifdef DEBUG_LEVEL
std::ostringstream ci;
std::ostringstream cType;
ci << (resizeTo - 1); // write ci
cType << type; // write cType
std::string FileName = std::string(File::GetUserPath(D_MAILLOGS_IDX)) + std::string(globals->unique_id);
FileName += "_sep"; FileName += ci.str(); FileName += "_sep"; FileName += cType.str();
FileName += Wii ? "_sepWii_sep" : "_sepGC_sep"; FileName += ".log";
FILE* fhandle = fopen(FileName.c_str(), "w");
fprintf(fhandle, "%s", f.c_str());
fflush(fhandle); fhandle = NULL;
//#endif
}
// ============================================
// Save the logged AX mail
// ----------------
void CUCode_AX::SaveLog_(bool Wii, const char* _fmt, va_list ap)
{
char Msg[512];
vsprintf(Msg, _fmt, ap);
#if defined(HAVE_WX) && HAVE_WX
if (m_DebuggerFrame->ScanMails)
{
if (strcmp(Msg, "Begin") == 0)
{
TmpMailLog = "";
}
else if (strcmp(Msg, "End") == 0)
{
if (saveNext && saveNext < 100) // limit because saveNext is not initialized
{
// Save the timestamps and comment
std::ostringstream ci;
ci << (saveNext - 1);
TmpMailLog += "\n\n";
TmpMailLog += "-----------------------------------------------------------------------\n";
// TmpMailLog += "Current mail: " + std::string(globals->unique_id) + " mail " + ci + "\n";
if (Wii)
TmpMailLog += "Current CRC: " + StringFromFormat("0x%08x \n\n", _CRC);
for (u32 i = 0; i < sMailTime.size(); i++)
{
char tmpbuf[128]; sprintf(tmpbuf, "Mail %i received: %s\n", i, sMailTime.at(i).c_str());
TmpMailLog += tmpbuf;
}
TmpMailLog += "-----------------------------------------------------------------------";
sMailLog.push_back(TmpMailLog);
// Save file to disc
if (m_DebuggerFrame->StoreMails)
{
SaveLogFile(TmpMailLog, saveNext, 1, Wii);
}
m_DebuggerFrame->DoUpdateMail(); // update the view
saveNext = 0;
}
}
else
{
#endif
TmpMailLog += Msg;
TmpMailLog += "\n";
DEBUG_LOG(DSPHLE, "%s", Msg); // also write it to the log
#if defined(HAVE_WX) && HAVE_WX
}
}
#endif
}
// ----------------
// ============================================
// Save the whole AX mail
// ----------------
void CUCode_AX::SaveMail(bool Wii, u32 _uMail)
{
#if defined(HAVE_WX) && HAVE_WX
if (!m_DebuggerFrame) return;
if (m_DebuggerFrame->ScanMails)
{
int i = 0;
std::string sTemp;
std::string sTempEnd;
std::string * sAct = &sTemp;
bool doOnce = true; // for the while loop, to avoid getting stuck
// Go through the mail
while (i < 250)
{
// Make a new row for each AX-Command
u16 axcomm = Memory_Read_U16(_uMail + i);
if (axcomm < 15 && axcomm != 0) // we can at most write 8 messages per log
{
*sAct += "\n";
}
char szTemp2[128] = "";
sprintf(szTemp2, "%08x : 0x%04x\n", _uMail + i, axcomm);
*sAct += szTemp2;
// set i to 160 so that we show some things after the end to
if ((axcomm == AXLIST_END || axcomm == 0x000e) && doOnce)
{
i = 160;
sAct = &sTempEnd;
doOnce = false;
}
i += 2;
}
// Compare this mail to old mails
u32 addnew = 0;
for (u32 j = 0; j < m_DebuggerFrame->sMail.size(); j++)
{
if (m_DebuggerFrame->sMail.at(j).length() != sTemp.length())
{
//wxMessageBox( wxString::Format("%s \n\n%s", m_DebuggerFrame->sMail.at(i).c_str(),
// sTemp.c_str()) );
addnew++;
}
}
// In case the mail didn't match any saved mail, save it
if (addnew == m_DebuggerFrame->sMail.size())
{
//Console::Print("%i | %i\n", addnew, m_DebuggerFrame->sMail.size());
u32 resizeTo = (u32)(m_DebuggerFrame->sMail.size() + 1);
// ------------------------------------
// get timestamp
wxDateTime datetime = wxDateTime::UNow();
char Msg[128];
sprintf(Msg, "%04i-%02i-%02i %02i:%02i:%02i:%03i",
datetime.GetYear(), datetime.GetMonth() + 1, datetime.GetDay(),
datetime.GetHour(), datetime.GetMinute(), datetime.GetSecond(), datetime.GetMillisecond());
sMailTime.push_back(Msg);
// ------------------------------------
m_DebuggerFrame->sMail.push_back(sTemp); // save the main comparison mail
std::string lMail = sTemp + "------------------\n" + sTempEnd;
m_DebuggerFrame->sFullMail.push_back(lMail);
// enable the radio button and update view
if (resizeTo <= m_DebuggerFrame->m_RadioBox[3]->GetCount())
{
m_DebuggerFrame->m_RadioBox[3]->Enable(resizeTo - 1, true);
m_DebuggerFrame->m_RadioBox[3]->Select(resizeTo - 1);
}
addnew = 0;
saveNext = resizeTo; // save the log to
// ------------------------------------
// Save as file
if (m_DebuggerFrame->StoreMails)
{
//Console::Print("m_DebuggerFrame->sMail.size(): %i | resizeTo:%i\n", m_DebuggerFrame->sMail.size(), resizeTo);
SaveLogFile(lMail, resizeTo, 0, Wii);
}
}
sTemp = "";
sTempEnd = "";
}
#endif
}
// ----------------
static bool ReadOutPB(u32 pb_address, AXParamBlock &PB)
{
const u16 *pSrc = (const u16 *)g_dspInitialize.pGetMemoryPointer(pb_address);
if (!pSrc)
return false;
u16 *pDest = (u16 *)&PB;
// TODO: SSE. Although it won't help much.
for (int p = 0; p < (int)sizeof(AXParamBlock) / 2; p++)
{
pDest[p] = Common::swap16(pSrc[p]);
}
return true;
}
static bool WriteBackPB(u32 pb_address, AXParamBlock &PB)
{
const u16 *pSrc = (const u16*)&PB;
u16 *pDest = (u16 *)g_dspInitialize.pGetMemoryPointer(pb_address);
if (!pDest)
return false;
// TODO: SSE. Although it won't help much.
for (size_t p = 0; p < sizeof(AXParamBlock) / 2; p++)
{
pDest[p] = Common::swap16(pSrc[p]);
}
return true;
}
static void ProcessUpdates(AXParamBlock &PB)
{
// ---------------------------------------------------------------------------------------
/* Make the updates we are told to do. When there are multiple updates for a block they
are placed in memory directly following updaddr. They are mostly for initial time
delays, sometimes for the FIR filter or channel volumes. We do all of them at once here.
If we get both an on and an off update we chose on. Perhaps that makes the RE1 music
work better. */
u16 *pDest = (u16 *)&PB;
u16 upd0 = pDest[34]; u16 upd1 = pDest[35]; u16 upd2 = pDest[36]; // num_updates
u16 upd3 = pDest[37]; u16 upd4 = pDest[38];
u16 upd_hi = pDest[39]; // update addr
u16 upd_lo = pDest[40];
int numupd = upd0 + upd1 + upd2 + upd3 + upd4;
if (numupd > 64) numupd = 64; // prevent crazy values
const u32 updaddr = (u32)(upd_hi << 16) | upd_lo;
int on = false, off = false;
// Make the updates we are told to do. When there are multiple updates for a block they
// are placed in memory directly following updaddr. They are mostly for initial time
// delays, sometimes for the FIR filter or channel volumes. We do all of them at once here.
// If we get both an on and an off update we chose on. Perhaps that makes the RE1 music
// work better.
int numupd = PB.updates.num_updates[0]
+ PB.updates.num_updates[1]
+ PB.updates.num_updates[2]
+ PB.updates.num_updates[3]
+ PB.updates.num_updates[4];
if (numupd > 64) numupd = 64; // prevent crazy values TODO: LOL WHAT
const u32 updaddr = (u32)(PB.updates.data_hi << 16) | PB.updates.data_lo;
int on = 0, off = 0;
for (int j = 0; j < numupd; j++)
{
int k = g_Config.m_EnableRE0Fix ? 0 : j;
@ -305,18 +75,86 @@ static void ProcessUpdates(AXParamBlock &PB)
// 0-3, those are important
//&& (upd0 || upd1 || upd2 || upd3 || upd4) // We should use these in some way to I think
// but I don't know how or when
&& gSequenced) // on and off option
)
{
pDest[updpar] = upddata;
((u16*)&PB)[updpar] = upddata; // WTF ABOUNDS!
}
if (updpar == 7 && upddata == 1) on++;
if (updpar == 7 && upddata == 1) off++;
// hack: if we get both an on and an off select on rather than off
if (on > 0 && off > 0) pDest[7] = 1;
if (on > 0 && off > 0) PB.running = 1;
}
}
static void VoiceHacks(AXPB &pb)
{
// get necessary values
const u32 sampleEnd = (pb.audio_addr.end_addr_hi << 16) | pb.audio_addr.end_addr_lo;
const u32 loopPos = (pb.audio_addr.loop_addr_hi << 16) | pb.audio_addr.loop_addr_lo;
// const u32 updaddr = (u32)(pb.updates.data_hi << 16) | pb.updates.data_lo;
// const u16 updpar = Memory_Read_U16(updaddr);
// const u16 upddata = Memory_Read_U16(updaddr + 2);
// =======================================================================================
/* Fix problems introduced with the SSBM fix. Sometimes when a music stream ended sampleEnd
would end up outside of bounds while the block was still playing resulting in noise
a strange noise. This should take care of that.
*/
if (
(sampleEnd > (0x017fffff * 2) || loopPos > (0x017fffff * 2)) // ARAM bounds in nibbles
)
{
pb.running = 0;
// also reset all values if it makes any difference
pb.audio_addr.cur_addr_hi = 0; pb.audio_addr.cur_addr_lo = 0;
pb.audio_addr.end_addr_hi = 0; pb.audio_addr.end_addr_lo = 0;
pb.audio_addr.loop_addr_hi = 0; pb.audio_addr.loop_addr_lo = 0;
pb.src.cur_addr_frac = 0; pb.src.ratio_hi = 0; pb.src.ratio_lo = 0;
pb.adpcm.pred_scale = 0; pb.adpcm.yn1 = 0; pb.adpcm.yn2 = 0;
pb.audio_addr.looping = 0;
pb.adpcm_loop_info.pred_scale = 0;
pb.adpcm_loop_info.yn1 = 0; pb.adpcm_loop_info.yn2 = 0;
}
/*
// the fact that no settings are reset (except running) after a SSBM type music stream or another
looping block (for example in Battle Stadium DON) has ended could cause loud garbled sound to be
played from one or more blocks. Perhaps it was in conjunction with the old sequenced music fix below,
I'm not sure. This was an attempt to prevent that anyway by resetting all. But I'm not sure if this
is needed anymore. Please try to play SSBM without it and see if it works anyway.
*/
if (
// detect blocks that have recently been running that we should reset
pb.running == 0 && pb.audio_addr.looping == 1
//pb.running == 0 && pb.adpcm_loop_info.pred_scale
// this prevents us from ruining sequenced music blocks, may not be needed
/*
&& !(pb.updates.num_updates[0] || pb.updates.num_updates[1] || pb.updates.num_updates[2]
|| pb.updates.num_updates[3] || pb.updates.num_updates[4])
*/
//&& !(updpar || upddata)
&& pb.mixer_control == 0 // only use this in SSBM
)
{
// reset the detection values
pb.audio_addr.looping = 0;
pb.adpcm_loop_info.pred_scale = 0;
pb.adpcm_loop_info.yn1 = 0; pb.adpcm_loop_info.yn2 = 0;
//pb.audio_addr.cur_addr_hi = 0; pb.audio_addr.cur_addr_lo = 0;
//pb.audio_addr.end_addr_hi = 0; pb.audio_addr.end_addr_lo = 0;
//pb.audio_addr.loop_addr_hi = 0; pb.audio_addr.loop_addr_lo = 0;
//pb.src.cur_addr_frac = 0; PBs[i].src.ratio_hi = 0; PBs[i].src.ratio_lo = 0;
//pb.adpcm.pred_scale = 0; pb.adpcm.yn1 = 0; pb.adpcm.yn2 = 0;
}
}
void CUCode_AX::MixAdd(short* _pBuffer, int _iSize)
{
@ -326,16 +164,7 @@ void CUCode_AX::MixAdd(short* _pBuffer, int _iSize)
memset(templbuffer, 0, _iSize * sizeof(int));
memset(temprbuffer, 0, _iSize * sizeof(int));
#if defined(HAVE_WX) && HAVE_WX
// write logging data to debugger
if (m_DebuggerFrame && _pBuffer)
{
CUCode_AX::Logging(_pBuffer, _iSize, 0, false);
}
#endif
AXParamBlock PB;
AXPB PB;
for (int x = 0; x < numPBaddr; x++)
{
@ -345,21 +174,20 @@ void CUCode_AX::MixAdd(short* _pBuffer, int _iSize)
if (!blockAddr)
return;
// ------------
for (int i = 0; i < NUMBER_OF_PBS; i++)
{
if (!ReadOutPB(blockAddr, PB))
if (!ReadPB(blockAddr, PB))
break;
ProcessUpdates(PB);
MixAddVoice(PB, templbuffer, temprbuffer, _iSize, false);
VoiceHacks(PB);
MixAddVoice(PB, templbuffer, temprbuffer, _iSize);
if (!WriteBackPB(blockAddr, PB))
if (!WritePB(blockAddr, PB))
break;
// next PB, or done
blockAddr = (PB.next_pb_hi << 16) | PB.next_pb_lo;
// Guess we're out of blocks
if (!blockAddr)
break;
}
@ -380,29 +208,21 @@ void CUCode_AX::MixAdd(short* _pBuffer, int _iSize)
*_pBuffer++ = right;
}
}
#if defined(HAVE_WX) && HAVE_WX
// write logging data to debugger again after the update
if (m_DebuggerFrame && _pBuffer)
{
CUCode_AX::Logging(_pBuffer, _iSize, 1, false);
}
#endif
}
// ------------------------------------------------------------------------------
// Handle incoming mail
// -----------
void CUCode_AX::HandleMail(u32 _uMail)
{
if ((_uMail & 0xFFFF0000) == MAIL_AX_ALIST)
{
// a new List
DEBUG_LOG(DSPHLE, " >>>> u32 MAIL : General Mail (%08x)", _uMail);
// We are expected to get a new CmdBlock
DEBUG_LOG(DSPHLE, "GetNextCmdBlock (%ibytes)", (u16)_uMail);
}
else if (_uMail == 0xCDD10000) // Action 0 - restart
{
m_rMailHandler.PushMail(0xDCD10001);
m_rMailHandler.PushMail(DSP_RESUME);
}
else if (_uMail == 0xCDD10001) // Action 1 - new ucode upload
{
@ -421,28 +241,14 @@ void CUCode_AX::HandleMail(u32 _uMail)
// ------------------------------------------------------------------------------
// Update with DSP Interrupt
// -----------
void CUCode_AX::Update(int cycles)
{
// check if we have to sent something
// check if we have to send something
if (!m_rMailHandler.IsEmpty())
{
g_dspInitialize.pGenerateDSPInterrupt();
}
}
// -----------
// Shortcut to avoid having to write SaveLog(false, ...) every time
void CUCode_AX::SaveLog(const char* _fmt, ...)
{
#if defined(HAVE_WX) && HAVE_WX
va_list ap; va_start(ap, _fmt);
if (m_DebuggerFrame) SaveLog_(false, _fmt, ap);
va_end(ap);
#endif
}
// ============================================
// AX seems to bootup one task only and waits for resume-callbacks
@ -451,9 +257,9 @@ void CUCode_AX::SaveLog(const char* _fmt, ...)
bool CUCode_AX::AXTask(u32& _uMail)
{
u32 uAddress = _uMail;
SaveLog("Begin");
SaveLog("=====================================================================");
SaveLog("%08x : AXTask - AXCommandList-Addr:", uAddress);
DEBUG_LOG(DSPHLE, "Begin");
DEBUG_LOG(DSPHLE, "=====================================================================");
DEBUG_LOG(DSPHLE, "%08x : AXTask - AXCommandList-Addr:", uAddress);
u32 Addr__AXStudio;
u32 Addr__AXOutSBuffer;
@ -463,8 +269,8 @@ bool CUCode_AX::AXTask(u32& _uMail)
u32 Addr__12;
u32 Addr__4_1;
u32 Addr__4_2;
// u32 Addr__4_3;
// u32 Addr__4_4;
//u32 Addr__4_3;
//u32 Addr__4_4;
u32 Addr__5_1;
u32 Addr__5_2;
u32 Addr__6;
@ -474,9 +280,6 @@ bool CUCode_AX::AXTask(u32& _uMail)
numPBaddr = 0;
#if defined(HAVE_WX) && HAVE_WX
if (m_DebuggerFrame) SaveMail(false, _uMail); // Save mail for debugging
#endif
while (bExecuteList)
{
static int last_valid_command = 0;
@ -488,7 +291,7 @@ bool CUCode_AX::AXTask(u32& _uMail)
case AXLIST_STUDIOADDR: //00
Addr__AXStudio = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST studio address: %08x", uAddress, Addr__AXStudio);
DEBUG_LOG(DSPHLE, "%08x : AXLIST studio address: %08x", uAddress, Addr__AXStudio);
break;
case 0x001: // 2byte x 10
@ -501,7 +304,7 @@ bool CUCode_AX::AXTask(u32& _uMail)
uAddress += 2;
u16 param3 = Memory_Read_U16(uAddress);
uAddress += 2;
SaveLog("%08x : AXLIST 1: %08x, %04x, %04x, %04x", uAddress, address, param1, param2, param3);
DEBUG_LOG(DSPHLE, "%08x : AXLIST 1: %08x, %04x, %04x, %04x", uAddress, address, param1, param2, param3);
}
break;
@ -518,14 +321,12 @@ bool CUCode_AX::AXTask(u32& _uMail)
m_addressPBs = Memory_Read_U32(uAddress); // left in for now
uAddress += 4;
soundStream->GetMixer()->SetHLEReady(true);
SaveLog("%08x : AXLIST PB address: %08x", uAddress, m_addressPBs);
SaveLog("Update the SoundThread to be in sync");
// soundStream->Update(); //do it in this thread to avoid sync problems
DEBUG_LOG(DSPHLE, "%08x : AXLIST PB address: %08x", uAddress, m_addressPBs);
}
break;
case 0x0003:
SaveLog("%08x : AXLIST command 0x0003 ????");
DEBUG_LOG(DSPHLE, "%08x : AXLIST command 0x0003 ????");
break;
case 0x0004: // AUX?
@ -533,7 +334,7 @@ bool CUCode_AX::AXTask(u32& _uMail)
uAddress += 4;
Addr__4_2 = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST 4_1 4_2 addresses: %08x %08x", uAddress, Addr__4_1, Addr__4_2);
DEBUG_LOG(DSPHLE, "%08x : AXLIST 4_1 4_2 addresses: %08x %08x", uAddress, Addr__4_1, Addr__4_2);
break;
case 0x0005:
@ -541,31 +342,31 @@ bool CUCode_AX::AXTask(u32& _uMail)
uAddress += 4;
Addr__5_2 = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST 5_1 5_2 addresses: %08x %08x", uAddress, Addr__5_1, Addr__5_2);
DEBUG_LOG(DSPHLE, "%08x : AXLIST 5_1 5_2 addresses: %08x %08x", uAddress, Addr__5_1, Addr__5_2);
break;
case 0x0006:
Addr__6 = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST 6 address: %08x", uAddress, Addr__6);
DEBUG_LOG(DSPHLE, "%08x : AXLIST 6 address: %08x", uAddress, Addr__6);
break;
case AXLIST_SBUFFER:
Addr__AXOutSBuffer = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST OutSBuffer address: %08x", uAddress, Addr__AXOutSBuffer);
DEBUG_LOG(DSPHLE, "%08x : AXLIST OutSBuffer address: %08x", uAddress, Addr__AXOutSBuffer);
break;
case 0x0009:
Addr__9 = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST 6 address: %08x", Addr__9);
DEBUG_LOG(DSPHLE, "%08x : AXLIST 6 address: %08x", Addr__9);
break;
case AXLIST_COMPRESSORTABLE: // 0xa
Addr__A = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST CompressorTable address: %08x", uAddress, Addr__A);
DEBUG_LOG(DSPHLE, "%08x : AXLIST CompressorTable address: %08x", uAddress, Addr__A);
break;
case 0x000e:
@ -576,16 +377,16 @@ bool CUCode_AX::AXTask(u32& _uMail)
// Although we don't, currently.
Addr__AXOutSBuffer_2 = Memory_Read_U32(uAddress);
uAddress += 4;
SaveLog("%08x : AXLIST sbuf2 addresses: %08x %08x", uAddress, Addr__AXOutSBuffer_1, Addr__AXOutSBuffer_2);
DEBUG_LOG(DSPHLE, "%08x : AXLIST sbuf2 addresses: %08x %08x", uAddress, Addr__AXOutSBuffer_1, Addr__AXOutSBuffer_2);
break;
case AXLIST_END:
bExecuteList = false;
SaveLog("%08x : AXLIST end", uAddress);
DEBUG_LOG(DSPHLE, "%08x : AXLIST end", uAddress);
break;
case 0x0010: //Super Monkey Ball 2
SaveLog("%08x : AXLIST 0x0010", uAddress);
DEBUG_LOG(DSPHLE, "%08x : AXLIST 0x0010", uAddress);
//should probably read/skip stuff here
uAddress += 8;
break;
@ -620,7 +421,6 @@ bool CUCode_AX::AXTask(u32& _uMail)
num += 2;
}
// Wii AX will always show this
PanicAlert(szTemp);
// bFirst = false;
}
@ -633,11 +433,10 @@ bool CUCode_AX::AXTask(u32& _uMail)
if (bExecuteList)
last_valid_command = iCommand;
}
SaveLog("AXTask - done, send resume");
SaveLog("=====================================================================");
SaveLog("End");
DEBUG_LOG(DSPHLE, "AXTask - done, send resume");
DEBUG_LOG(DSPHLE, "=====================================================================");
DEBUG_LOG(DSPHLE, "End");
// i hope resume is okay AX
m_rMailHandler.PushMail(0xDCD10002);
m_rMailHandler.PushMail(DSP_YIELD);
return true;
}

View File

@ -37,16 +37,6 @@ public:
void MixAdd(short* _pBuffer, int _iSize);
void Update(int cycles);
// Logging
//template<class ParamBlockType>
//void Logging(short* _pBuffer, int _iSize, int a, bool Wii, ParamBlockType &PBs, int numberOfPBs);
void Logging(short* _pBuffer, int _iSize, int a, bool Wii);
void SaveLog_(bool Wii, const char* _fmt, va_list ap);
void SaveMail(bool Wii, u32 _uMail);
void SaveLogFile(std::string f, int resizeTo, bool type, bool Wii);
std::string TmpMailLog;
int saveNext;
// PBs
u8 numPBaddr;
u32 PBaddr[8]; //2 needed for MP2
@ -69,8 +59,6 @@ private:
// ax task message handler
bool AXTask(u32& _uMail);
void SaveLog(const char* _fmt, ...);
void SendMail(u32 _uMail);
};
#endif // _UCODE_AX

View File

@ -20,10 +20,10 @@
struct PBMixer
{
u16 volume_left;
u16 unknown;
u16 volume_right;
u16 unknown2;
u16 left;
u16 left_delta;
u16 right;
u16 right_delta;
u16 unknown3[8];
u16 unknown4[6];
@ -31,13 +31,60 @@ struct PBMixer
struct PBMixerWii
{
u16 volume_left;
u16 unknown;
u16 volume_right;
u16 unknown2;
// volume mixing values in .15, 0x8000 = ca. 1.0
u16 left;
u16 left_delta;
u16 right;
u16 right_delta;
u16 unknown3[12];
u16 unknown4[8];
u16 auxA_left;
u16 auxA_left_delta;
u16 auxA_right;
u16 auxA_right_delta;
u16 auxB_left;
u16 auxB_left_delta;
u16 auxB_right;
u16 auxB_right_delta;
// Note: the following elements usage changes a little in DPL2 mode
// TODO: implement and comment it in the mixer
u16 auxC_left;
u16 auxC_left_delta;
u16 auxC_right;
u16 auxC_right_delta;
u16 surround;
u16 surround_delta;
u16 auxA_surround;
u16 auxA_surround_delta;
u16 auxB_surround;
u16 auxB_surround_delta;
u16 auxC_surround;
u16 auxC_surround_delta;
};
struct PBMixerWM
{
u16 main0;
u16 main0_delta;
u16 aux0;
u16 aux0_delta;
u16 main1;
u16 main1_delta;
u16 aux1;
u16 aux1_delta;
u16 main2;
u16 main2_delta;
u16 aux2;
u16 aux2_delta;
u16 main3;
u16 main3_delta;
u16 aux3;
u16 aux3_delta;
};
struct PBInitialTimeDelay
@ -62,32 +109,49 @@ struct PBUpdates
u16 data_lo;
};
struct PBUpdatesWii
{
u16 num_updates[3];
u16 data_hi; // These point to main RAM. Not sure about the structure of the data.
u16 data_lo;
};
// The DSP stores the final sample values for each voice after every frame of processing.
// The values are then accumulated for all dropped voices, added to the next frame of audio,
// and ramped down on a per-sample basis to provide a gentle "roll off."
struct PBDpop
{
s16 unknown[9];
};
struct PBDpopWii
{
s16 unknown[12];
};
struct PBDpopWii
{
s16 left;
s16 auxA_left;
s16 auxB_left;
s16 auxC_left;
struct PBDpopWii_ // new CRC version
{
s16 unknown[7];
};
s16 right;
s16 auxA_right;
s16 auxB_right;
s16 auxC_right;
s16 surround;
s16 auxA_surround;
s16 auxB_surround;
s16 auxC_surround;
};
struct PBDpopWM
{
s16 aMain0;
s16 aMain1;
s16 aMain2;
s16 aMain3;
s16 aAux0;
s16 aAux1;
s16 aAux2;
s16 aAux3;
};
struct PBVolumeEnvelope
{
u16 cur_volume;
s16 cur_volume_delta;
u16 cur_volume; // volume at start of frame
s16 cur_volume_delta; // signed per sample delta (96 samples per frame)
};
struct PBUnknown2
@ -118,12 +182,20 @@ struct PBADPCMInfo
struct PBSampleRateConverter
{
u16 ratio_hi;
u16 ratio_lo;
// ratio = (f32)ratio * 0x10000;
// valid range is 1/512 to 4.0000
u16 ratio_hi; // integer part of sampling ratio
u16 ratio_lo; // fraction part of sampling ratio
u16 cur_addr_frac;
u16 last_samples[4];
};
struct PBSampleRateConverterWM
{
u16 currentAddressFrac;
u16 last_samples[4];
};
struct PBADPCMLoopInfo
{
u16 pred_scale;
@ -131,35 +203,34 @@ struct PBADPCMLoopInfo
u16 yn2;
};
struct AXParamBlock
struct AXPB
{
u16 next_pb_hi;
u16 next_pb_lo;
u16 this_pb_hi;
u16 this_pb_lo;
u16 src_type; // Type of sample rate converter (none, ?, linear)
u16 coef_select;
u16 mixer_control;
u16 running; // 1=RUN 0=STOP
u16 is_stream; // 1 = stream, 0 = one shot
/* 9 */ PBMixer mixer;
/* 27 */ PBInitialTimeDelay initial_time_delay;
/* 34 */ PBUpdates updates;
/* 41 */ PBDpop dpop;
/* 50 */ PBVolumeEnvelope vol_env;
/* 52 */ PBUnknown2 unknown3;
/* 55 */ PBAudioAddr audio_addr;
/* 63 */ PBADPCMInfo adpcm;
/* 83 */ PBSampleRateConverter src;
/* 90 */ PBADPCMLoopInfo adpcm_loop_info;
/* 93 */ //u16 unknown_maybe_padding[3]; // Comment this out to get some speedup
PBMixer mixer;
PBInitialTimeDelay initial_time_delay;
PBUpdates updates;
PBDpop dpop;
PBVolumeEnvelope vol_env;
PBUnknown2 unknown3;
PBAudioAddr audio_addr;
PBADPCMInfo adpcm;
PBSampleRateConverter src;
PBADPCMLoopInfo adpcm_loop_info;
u16 unknown_maybe_padding[3];
};
struct PBLpf
struct PBLowPassFilter
{
u16 enabled;
u16 yn1;
@ -167,69 +238,112 @@ struct PBLpf
u16 b0;
};
struct PBHpf
struct PBBiquadFilter
{
u16 enabled;
u16 on; // on = 2, off = 0
u16 xn1; // History data
u16 xn2;
u16 yn1;
u16 a0;
u16 b0;
u16 yn2;
u16 b0; // Filter coefficients
u16 b1;
u16 b2;
u16 a1;
u16 a2;
};
struct AXParamBlockWii
union PBInfImpulseResponseWM
{
PBLowPassFilter lpf;
PBBiquadFilter biquad;
};
struct AXPBWii
{
u16 next_pb_hi;
u16 next_pb_lo;
u16 this_pb_hi;
u16 this_pb_lo;
u16 src_type; // Type of sample rate converter (none, ?, linear)
u16 coef_select;
u16 src_type; // Type of sample rate converter (none, 4-tap, linear)
u16 coef_select; // coef for the 4-tap src
u32 mixer_control;
u16 running; // 1=RUN 0=STOP
u16 is_stream; // 1 = stream, 0 = one shot
/* 10 */ PBMixerWii mixer;
/* 34 */ PBInitialTimeDelay initial_time_delay;
/* 41 */ PBUpdatesWii updates;
/* 46 */ PBDpopWii dpop;
/* 58 */ PBVolumeEnvelope vol_env;
/* 60 */ PBAudioAddr audio_addr;
/* 68 */ PBADPCMInfo adpcm;
/* 88 */ PBSampleRateConverter src;
/* 95 */ PBADPCMLoopInfo adpcm_loop_info;
/* 98 */ PBLpf lpf;
/* 102 */ PBHpf hpf;
/* 106 */ //u16 pad[22]; // Comment this out to get some speedup
PBMixerWii mixer;
PBInitialTimeDelay initial_time_delay;
PBDpopWii dpop;
PBVolumeEnvelope vol_env;
PBAudioAddr audio_addr;
PBADPCMInfo adpcm;
PBSampleRateConverter src;
PBADPCMLoopInfo adpcm_loop_info;
PBLowPassFilter lpf;
PBBiquadFilter biquad;
// WIIMOTE :D
u16 remote;
u16 remote_mixer_control;
PBMixerWM remote_mixer;
PBDpopWM remote_dpop;
PBSampleRateConverterWM remote_src;
PBInfImpulseResponseWM remote_iir;
u16 pad[12]; // align us, captain! (32B)
};
struct AXParamBlockWii_ // new CRC version
// Seems like nintendo used an early version of AXWii and forgot to remove the update functionality ;p
struct PBUpdatesWiiSports
{
/* 0x000 */ u16 next_pb_hi;
/* 0x002 */ u16 next_pb_lo;
/* 0x004 */ u16 this_pb_hi;
/* 0x006 */ u16 this_pb_lo;
/* 0x008 */ u16 src_type; // Type of sample rate converter (none, ?, linear)
/* 0x00A */ u16 coef_select;
/* 0x00C */ u32 mixer_control;
/* 0x010 */ u16 running; // 1=RUN 0=STOP
/* 0x012 */ u16 is_stream; // 1 = stream, 0 = one shot
/* 0x014 */ PBMixerWii mixer;
/* 0x044 */ PBInitialTimeDelay initial_time_delay;
/* 0x052 */ PBUpdatesWii updates;
/* 0x05C */ PBDpopWii_ dpop;
/* 0x06A */ PBVolumeEnvelope vol_env;
/* 0x06E */ PBAudioAddr audio_addr;
/* 0x07E */ PBADPCMInfo adpcm;
/* 0x0A6 */ PBSampleRateConverter src;
/* 0x0B4 */ PBADPCMLoopInfo adpcm_loop_info;
/* 0x0BA */ PBLpf lpf;
/* 0x0C2 */ PBHpf hpf;
/* 0x0CA */ //u16 pad[27]; // Comment this out to get some speedup
/* 0x100 */
u16 num_updates[3];
u16 data_hi;
u16 data_lo;
};
struct AXPBWiiSports
{
u16 next_pb_hi;
u16 next_pb_lo;
u16 this_pb_hi;
u16 this_pb_lo;
u16 src_type; // Type of sample rate converter (none, 4-tap, linear)
u16 coef_select; // coef for the 4-tap src
u32 mixer_control;
u16 running; // 1=RUN 0=STOP
u16 is_stream; // 1 = stream, 0 = one shot
PBMixerWii mixer;
PBInitialTimeDelay initial_time_delay;
PBUpdatesWiiSports updates;
PBDpopWii dpop;
PBVolumeEnvelope vol_env;
PBAudioAddr audio_addr;
PBADPCMInfo adpcm;
PBSampleRateConverter src;
PBADPCMLoopInfo adpcm_loop_info;
PBLowPassFilter lpf;
PBBiquadFilter biquad;
// WIIMOTE :D
u16 remote;
u16 remote_mixer_control;
PBMixerWM remote_mixer;
PBDpopWM remote_dpop;
PBSampleRateConverterWM remote_src;
PBInfImpulseResponseWM remote_iir;
u16 pad[7]; // align us, captain! (32B)
};
// TODO: All these enums have changed a lot for wii
enum {
AUDIOFORMAT_ADPCM = 0,
AUDIOFORMAT_PCM8 = 0x19,
@ -242,4 +356,10 @@ enum {
MIXCONTROL_RAMPING = 8,
};
// Both may be used at once
enum {
FILTER_LOWPASS = 1,
FILTER_BIQUAD = 2,
};
#endif // _UCODE_AX_STRUCTS_H

View File

@ -17,12 +17,6 @@
#include "StringUtil.h"
#if defined(HAVE_WX) && HAVE_WX
#include "../Debugger/Debugger.h"
//#include "../Logging/File.h" // For PrintFile
extern DSPDebuggerHLE * m_DebuggerFrame;
#endif
#include "../MailHandler.h"
#include "Mixer.h"
@ -33,33 +27,23 @@ extern DSPDebuggerHLE * m_DebuggerFrame;
#include "UCode_AX_Voice.h"
// ------------------------------------------------------------------
// Declarations
// -----------
extern bool gSequenced;
// -----------
CUCode_AXWii::CUCode_AXWii(CMailHandler& _rMailHandler, u32 l_CRC)
: IUCode(_rMailHandler)
, m_addressPBs(0xFFFFFFFF)
, _CRC(l_CRC)
{
// we got loaded
m_rMailHandler.PushMail(0xDCD10000);
m_rMailHandler.PushMail(DSP_INIT);
templbuffer = new int[1024 * 1024];
temprbuffer = new int[1024 * 1024];
lCUCode_AX = new CUCode_AX(_rMailHandler);
lCUCode_AX->_CRC = l_CRC;
wiisportsHack = _CRC == 0xfa450138;
}
CUCode_AXWii::~CUCode_AXWii()
{
m_rMailHandler.Clear();
delete lCUCode_AX;
delete [] templbuffer;
delete [] temprbuffer;
}
@ -72,7 +56,7 @@ void CUCode_AXWii::HandleMail(u32 _uMail)
}
else if (_uMail == 0xCDD10000) // Action 0 - restart
{
m_rMailHandler.PushMail(0xDCD10001);
m_rMailHandler.PushMail(DSP_RESUME);
}
else if (_uMail == 0xCDD10001) // Action 1 - new ucode upload
{
@ -87,115 +71,37 @@ void CUCode_AXWii::HandleMail(u32 _uMail)
}
}
template<class ParamBlockType> void ProcessUpdates(ParamBlockType &PB)
void CUCode_AXWii::MixAdd(short* _pBuffer, int _iSize)
{
// ---------------------------------------------------------------------------------------
/* Make the updates we are told to do. See comments to the GC version in UCode_AX.cpp */
// ------------
u16 *pDest = (u16 *)&PB;
u16 upd0 = pDest[41]; u16 upd1 = pDest[42]; u16 upd2 = pDest[43]; // num_updates
u16 upd_hi = pDest[44]; // update addr
u16 upd_lo = pDest[45];
int numupd = upd0 + upd1 + upd2;
if(numupd > 64) numupd = 64; // prevent to high values
const u32 updaddr = (u32)(upd_hi << 16) | upd_lo;
int on = false, off = false;
for (int j = 0; j < numupd; j++) // make alll updates
{
const u16 updpar = Memory_Read_U16(updaddr);
const u16 upddata = Memory_Read_U16(updaddr + 2);
// some safety checks, I hope it's enough
if( ( (updaddr > 0x80000000 && updaddr < 0x817fffff)
|| (updaddr > 0x90000000 && updaddr < 0x93ffffff) )
&& updpar < 127 && updpar > 3 && upddata >= 0 // updpar > 3 because we don't want to change
// 0-3, those are important
//&& (upd0 || upd1 || upd2) // We should use these in some way to I think
// but I don't know how or when
&& gSequenced) // on and off option
{
//PanicAlert("Update %i: %i = %04x", i, updpar, upddata);
//DEBUG_LOG(DSPHLE, "Update: %i = %04x", updpar, upddata);
pDest[updpar] = upddata;
}
if (updpar == 7 && upddata == 1) on++;
if (updpar == 7 && upddata == 1) off++;
}
// hack: if we get both an on and an off select on rather than off
if (on > 0 && off > 0) pDest[7] = 1;
}
AXPBWii PB;
template<class ParamBlockType>
void CUCode_AXWii::MixAdd_(short* _pBuffer, int _iSize, ParamBlockType &PB)
{
if (_iSize > 1024 * 1024)
_iSize = 1024 * 1024;
// write zeroes to the beginning of templbuffer
memset(templbuffer, 0, _iSize * sizeof(int));
memset(temprbuffer, 0, _iSize * sizeof(int));
// -------------------------------------------
// write logging data to debugger
#if defined(HAVE_WX) && HAVE_WX
/*
If this is to be resurrected, it has to be moved into the main PB loop below.
if (m_DebuggerFrame && _pBuffer)
{
lCUCode_AX->Logging(_pBuffer, _iSize, 0, true);
// -------------------------------------------
// Write the first block values
int p = numberOfPBs - 1;
if(numberOfPBs > p)
{
if(PBs[p].running && !m_DebuggerFrame->upd95)
{
const u32 blockAddr = (u32)(PBs[p].this_pb_hi<< 16) | PBs[p].this_pb_lo;
const short *pSrc = (const short *)g_dspInitialize.pGetMemoryPointer(blockAddr);
for (u32 i = 0; i < sizeof(AXParamBlockWii) / 2; i+=2)
{
if(i == 10 || i == 34 || i == 41 || i == 46 || i == 46 || i == 58 || i == 60
|| i == 68 || i == 88 || i == 95)
{m_DebuggerFrame->str0 += "\n"; m_DebuggerFrame->str95 += "\n";}
std::string line = StringFromFormat("%02i|%02i : %s : %s",
i/2, i,
m_DebuggerFrame->PBn[i].c_str(), m_DebuggerFrame->PBp[i].c_str()
);
for (u32 j = 0; j < 50 - line.length(); ++j)
line += " ";
m_DebuggerFrame->str0 += line;
m_DebuggerFrame->str0 += "\n";
m_DebuggerFrame->str95 += StringFromFormat(" : %02i|%02i : %04x%04x\n",
i/2, i,
Common::swap16(pSrc[i]), Common::swap16(pSrc[i+1]));
}
m_DebuggerFrame->m_bl95->AppendText(wxString::FromAscii(m_DebuggerFrame->str95.c_str()));
m_DebuggerFrame->m_bl0->AppendText(wxString::FromAscii(m_DebuggerFrame->str0.c_str()));
m_DebuggerFrame->upd95 = true;
}
}
}*/
// -----------------
#endif
u32 blockAddr = m_addressPBs;
if (!blockAddr)
return;
for (int i = 0; i < NUMBER_OF_PBS; i++)
{
// read out pbs
if (!ReadOutPBWii(blockAddr, PB))
break;
ProcessUpdates(PB);
MixAddVoice(PB, templbuffer, temprbuffer, _iSize, true, UCODE_AXWII);
if (!WriteBackPBWii(blockAddr, PB))
if (!ReadPB(blockAddr, PB))
break;
// next block
if (wiisportsHack)
MixAddVoice(*(AXPBWiiSports*)&PB, templbuffer, temprbuffer, _iSize);
else
MixAddVoice(PB, templbuffer, temprbuffer, _iSize);
if (!WritePB(blockAddr, PB))
break;
// next PB, or done
blockAddr = (PB.next_pb_hi << 16) | PB.next_pb_lo;
if (blockAddr == 0) break;
if (!blockAddr)
break;
}
// We write the sound to _pBuffer
@ -214,14 +120,6 @@ void CUCode_AXWii::MixAdd_(short* _pBuffer, int _iSize, ParamBlockType &PB)
*_pBuffer++ = right;
}
}
#if defined(HAVE_WX) && HAVE_WX
// write logging data to debugger again after the update
if (m_DebuggerFrame && _pBuffer)
{
lCUCode_AX->Logging(_pBuffer, _iSize, 1, true);
}
#endif
}
@ -234,20 +132,6 @@ void CUCode_AXWii::Update(int cycles)
}
}
// Shortcut
void CUCode_AXWii::SaveLog(const char* _fmt, ...)
{
#if defined(HAVE_WX) && HAVE_WX
va_list ap;
va_start(ap, _fmt);
if(m_DebuggerFrame)
lCUCode_AX->SaveLog_(true, _fmt, ap);
va_end(ap);
#endif
}
// AX seems to bootup one task only and waits for resume-callbacks
// everytime the DSP has "spare time" it sends a resume-mail to the CPU
// and the __DSPHandler calls a AX-Callback which generates a new AXFrame
@ -258,10 +142,6 @@ bool CUCode_AXWii::AXTask(u32& _uMail)
u32 Addr__AXOutSBuffer;
bool bExecuteList = true;
#if defined(HAVE_WX) && HAVE_WX
if(m_DebuggerFrame) lCUCode_AX->SaveMail(true, uAddress); // Save mail for debugging
#endif
/*
for (int i=0;i<64;i++) {
NOTICE_LOG(DSPHLE,"%x - %08x",uAddress+(i*4),Memory_Read_U32(uAddress+(i*4)));
@ -292,20 +172,14 @@ bool CUCode_AXWii::AXTask(u32& _uMail)
case 0x0004:
// PBs are here now
m_addressPBs = Memory_Read_U32(uAddress);
lCUCode_AX->m_addressPBs = m_addressPBs; // for the sake of logging
soundStream->GetMixer()->SetHLEReady(true);
// soundStream->Update();
uAddress += 4;
break;
case 0x0005:
if (_CRC != 0xfa450138)
{
if (!wiisportsHack)
uAddress += 10;
}
else // Wii Sports uCode
{
}
break;
case 0x0006:
@ -322,71 +196,39 @@ bool CUCode_AXWii::AXTask(u32& _uMail)
break;
case 0x000a:
if (_CRC != 0xfa450138) // AXLIST_COMPRESSORTABLE
{
uAddress += 8;
}
else // Wii Sports uCode
{
if (wiisportsHack) // AXLIST_COMPRESSORTABLE
uAddress += 4;
}
else
uAddress += 8;
break;
case 0x000b:
if (_CRC != 0xfa450138)
{
uAddress += 10;
//0xDCD10004 <-- causing problems for some games under HLE (TOS2/NTSC,...)
//m_rMailHandler.PushMail(0xDCD10004);
}
else // Wii Sports uCode
{
if (wiisportsHack)
uAddress += 2;
}
else
uAddress += 10;
break;
case 0x000c:
if (_CRC != 0xfa450138)
{
uAddress += 10;
//m_rMailHandler.PushMail(0xDCD10004);
}
else // Wii Sports uCode
{
if (wiisportsHack)
uAddress += 8;
//m_rMailHandler.PushMail(0xDCD10004);
}
else
uAddress += 10;
break;
case 0x000d:
if (_CRC != 0xfa450138)
{
uAddress += 16;
}
else // Wii Sports uCode
{
uAddress += 16; //??
//m_rMailHandler.PushMail(0xDCD10004);
}
break;
case 0x000e:
if (_CRC != 0xfa450138)
{
// This is the end.
bExecuteList = false;
//m_rMailHandler.PushMail(0xDCD10002);
}
else // Wii Sports uCode
{
if (wiisportsHack)
uAddress += 16;
}
else
bExecuteList = false;
break;
case 0x000f: // only for Wii Sports uCode
// This is the end.
bExecuteList = false;
//m_rMailHandler.PushMail(0xDCD10002);
break;
default:
@ -397,21 +239,6 @@ bool CUCode_AXWii::AXTask(u32& _uMail)
}
}
m_rMailHandler.PushMail(0xDCD10002); //its here in case there is a CMD fuckup
m_rMailHandler.PushMail(DSP_YIELD); //its here in case there is a CMD fuckup
return true;
}
void CUCode_AXWii::MixAdd(short* _pBuffer, int _iSize)
{
if(_CRC == 0xfa450138)
{
AXParamBlockWii PB;
MixAdd_( _pBuffer, _iSize, PB);
}
else
{
AXParamBlockWii_ PB;
MixAdd_(_pBuffer, _iSize, PB);
}
}

View File

@ -30,15 +30,8 @@ public:
void HandleMail(u32 _uMail);
void MixAdd(short* _pBuffer, int _iSize);
template<class ParamBlockType>
//void Logging(short* _pBuffer, int _iSize, int a, bool Wii, ParamBlockType &PBs, int numberOfPBs);
void MixAdd_(short* _pBuffer, int _iSize, ParamBlockType &PBs);
void Update(int cycles);
// The logging function for the debugger
void Logging(short* _pBuffer, int _iSize, int a);
CUCode_AX * lCUCode_AX; // we need the logging functions in there
private:
enum
{
@ -49,12 +42,13 @@ private:
u32 m_addressPBs;
u32 _CRC;
bool wiisportsHack;
int *templbuffer;
int *temprbuffer;
// ax task message handler
bool AXTask(u32& _uMail);
void SaveLog(const char* _fmt, ...);
void SendMail(u32 _uMail);
};

View File

@ -60,9 +60,8 @@ inline s16 ADPCM_Step(PBADPCMInfo &adpcm, u32& samplePos, u32 newSamplePos, u16
return adpcm.yn1;
}
// =======================================================================================
// TODO: WTF is going on here?!?
// Volume control (ramping)
// --------------
inline u16 ADPCM_Vol(u16 vol, u16 delta)
{
int x = vol;
@ -87,6 +86,5 @@ inline u16 ADPCM_Vol(u16 vol, u16 delta)
if (x >= 0x4e20) x = 0x4e20; // add a definitive limit at 20 000
return x; // update volume
}
// ==============
#endif // _UCODE_AX_ADPCM_H

View File

@ -25,85 +25,93 @@
#include "../main.h"
#include "../Config.h"
// ----------------------------------------------------
// Externals
// -----------
extern bool gSSBM;
extern bool gSSBMremedy1;
extern bool gSSBMremedy2;
extern bool gSequenced;
extern bool gVolume;
extern bool gReset;
extern bool gSequenced;
extern float ratioFactor;
template<class ParamBlockType>
inline bool ReadOutPBWii(u32 pbs_address, ParamBlockType& PB)
// MRAM -> ARAM for GC
inline bool ReadPB(u32 addr, AXPB &PB)
{
u32 blockAddr = pbs_address;
u32 pAddr = 0;
const short *pSrc = (const short *)g_dspInitialize.pGetMemoryPointer(blockAddr);
if (!pSrc)
const u16* PB_in_mram = (const u16*)g_dspInitialize.pGetMemoryPointer(addr);
if (PB_in_mram == NULL)
return false;
pAddr = blockAddr;
short *pDest = (short *)&PB;
for (u32 p = 0; p < sizeof(ParamBlockType) / 2; p++)
{
if (p == 6 || p == 7) pDest[p] = pSrc[p]; // control for the u32
else pDest[p] = Common::swap16(pSrc[p]);
u16* PB_in_aram = (u16*)&PB;
#if defined(HAVE_WX) && HAVE_WX
#if defined(_DEBUG) || defined(DEBUGFAST)
if(m_DebuggerFrame) m_DebuggerFrame->gLastBlock = blockAddr + p*2 + 2; // save last block location
#endif
#endif
for (size_t p = 0; p < (sizeof(AXPB) >> 1); p++)
{
PB_in_aram[p] = Common::swap16(PB_in_mram[p]);
}
PB.mixer_control = Common::swap32(PB.mixer_control);
return true;
}
template<class ParamBlockType>
inline bool WriteBackPBWii(u32 pb_address, ParamBlockType& PB)
//void WriteBackPBsWii(u32 pbs_address, AXParamBlockWii* _pPBs, int _num)
// MRAM -> ARAM for Wii
inline bool ReadPB(u32 addr, AXPBWii &PB)
{
// write back and 'halfword'swap
short* pSrc = (short*)&PB;
short* pDest = (short*)g_dspInitialize.pGetMemoryPointer(pb_address);
if (!pDest)
const u16* PB_in_mram = (const u16*)g_dspInitialize.pGetMemoryPointer(addr);
if (PB_in_mram == NULL)
return false;
PB.mixer_control = Common::swap32(PB.mixer_control);
for (size_t p = 0; p < sizeof(ParamBlockType) / 2; p++)
u16* PB_in_aram = (u16*)&PB;
// preswap the mixer_control
PB.mixer_control = ((u32)PB_in_mram[7] << 16) | ((u32)PB_in_mram[6] >> 16);
for (size_t p = 0; p < (sizeof(AXPBWii) >> 1); p++)
{
if (p == 6 || p == 7) pDest[p] = pSrc[p]; // control for the u32
else pDest[p] = Common::swap16(pSrc[p]);
PB_in_aram[p] = Common::swap16(PB_in_mram[p]);
}
return true;
}
template<class ParamBlockType>
inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer, int _iSize, bool Wii, u32 _uCode = UCODE_ROM)
// ARAM -> MRAM for GC
inline bool WritePB(u32 addr, AXPB &PB)
{
ratioFactor = 32000.0f / (float)soundStream->GetMixer()->GetSampleRate();
const u16* PB_in_aram = (const u16*)&PB;
u16* PB_in_mram = (u16*)g_dspInitialize.pGetMemoryPointer(addr);
if (PB_in_mram == NULL)
return false;
DoVoiceHacks(pb, Wii);
for (size_t p = 0; p < (sizeof(AXPB) >> 1); p++)
{
PB_in_mram[p] = Common::swap16(PB_in_aram[p]);
}
// =============
return true;
}
// ARAM -> MRAM for Wii
inline bool WritePB(u32 addr, AXPBWii &PB)
{
const u16* PB_in_aram = (const u16*)&PB;
u16* PB_in_mram = (u16*)g_dspInitialize.pGetMemoryPointer(addr);
if (PB_in_mram == NULL)
return false;
// preswap the mixer_control
*(u32*)&PB_in_mram[6] = (PB.mixer_control << 16) | (PB.mixer_control >> 16);
for (size_t p = 0; p < (sizeof(AXPBWii) >> 1); p++)
{
PB_in_mram[p] = Common::swap16(PB_in_aram[p]);
}
return true;
}
//////////////////////////////////////////////////////////////////////////
// TODO: fix handling of gc/wii PB differences
// TODO: generally fix up the mess - looks crazy and kinda wrong
template<class ParamBlockType>
inline void MixAddVoice(ParamBlockType &pb,
int *templbuffer, int *temprbuffer,
int _iSize)
{
if (pb.running)
{
// Read initial parameters
// ------------
//constants
const u32 ratio = (u32)(((pb.src.ratio_hi << 16) + pb.src.ratio_lo) * ratioFactor);
const u32 ratio = (u32)(((pb.src.ratio_hi << 16) + pb.src.ratio_lo)
* /*ratioFactor:*/(32000.0f / (float)soundStream->GetMixer()->GetSampleRate()));
u32 sampleEnd = (pb.audio_addr.end_addr_hi << 16) | pb.audio_addr.end_addr_lo;
u32 loopPos = (pb.audio_addr.loop_addr_hi << 16) | pb.audio_addr.loop_addr_lo;
//variables
u32 samplePos = (pb.audio_addr.cur_addr_hi << 16) | pb.audio_addr.cur_addr_lo;
u32 frac = pb.src.cur_addr_frac;
// =============
// =======================================================================================
// Handle No-SRC streams - No src streams have pb.src_type == 2 and have pb.src.ratio_hi = 0
@ -113,20 +121,16 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
// ---------------------------------------------------------------------------------------
// Stream settings
// src_type = 2 (most other games have src_type = 0)
// ------------
// Affected games:
// Baten Kaitos - Eternal Wings (2003)
// Baten Kaitos - Origins (2006)?
// Soul Calibur 2: The movie music use src_type 2 but it needs no adjustment, perhaps
// the sound format plays in to, Baten use ADPCM, SC2 use PCM16
// ------------
//if (pb.src_type == 2 && (pb.src.ratio_hi == 0 && pb.src.ratio_lo == 0))
if (pb.running && (pb.src.ratio_hi == 0 && pb.src.ratio_lo == 0))
{
pb.src.ratio_hi = 1;
}
// =============
// =======================================================================================
// Games that use looping to play non-looping music streams - SSBM has info in all
@ -134,7 +138,6 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
// like any other looping streams the music works. I'm unsure how we are actually supposed to
// detect that these kinds of blocks should be looping. It seems like pb.mixer_control == 0 may
// identify these types of blocks. Updates did not write any looping values.
// --------------
if (
(pb.adpcm_loop_info.pred_scale || pb.adpcm_loop_info.yn1 || pb.adpcm_loop_info.yn2)
&& pb.mixer_control == 0
@ -142,10 +145,10 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
{
pb.audio_addr.looping = 1;
}
// =============
// Top Spin 3 Wii
if(pb.audio_addr.sample_format > 25) pb.audio_addr.sample_format = 0;
if (pb.audio_addr.sample_format > 25)
pb.audio_addr.sample_format = 0;
// =======================================================================================
// Walk through _iSize. _iSize = numSamples. If the game goes slow _iSize will be higher to
@ -158,7 +161,6 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
// =======================================================================================
// Process sample format
// --------------
switch (pb.audio_addr.sample_format)
{
case AUDIOFORMAT_PCM8:
@ -170,7 +172,7 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
{
sample = pb.adpcm.yn1;
}
else //linear interpolation
else // linear interpolation
{
sample = (pb.adpcm.yn1 * (u16)frac + pb.adpcm.yn2 * (u16)(0xFFFF - frac)) >> 16;
}
@ -184,7 +186,7 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
pb.adpcm.yn1 = (s16)(u16)((g_dspInitialize.pARAM_Read_U8(samplePos * 2) << 8) | (g_dspInitialize.pARAM_Read_U8((samplePos * 2 + 1))));
if (pb.src_type == SRCTYPE_NEAREST)
sample = pb.adpcm.yn1;
else //linear interpolation
else // linear interpolation
sample = (pb.adpcm.yn1 * (u16)frac + pb.adpcm.yn2 * (u16)(0xFFFF - frac)) >> 16;
samplePos = newSamplePos;
@ -197,7 +199,6 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
default:
break;
}
// ================
// ===================================================================
// Overall volume control. In addition to this there is also separate volume settings to
@ -212,58 +213,49 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
int x = pb.vol_env.cur_volume;
x += pb.vol_env.cur_volume_delta; // I'm not sure about this, can anybody find a game
// that use this? Or how does it work?
if (x < 0) x = 0;
if (x >= 0x7fff) x = 0x7fff;
if (x < 0)
x = 0;
if (x >= 0x7fff)
x = 0x7fff;
pb.vol_env.cur_volume = x; // maybe not per sample?? :P
}
int leftmix = pb.mixer.volume_left >> 5;
int rightmix = pb.mixer.volume_right >> 5;
int leftmix = pb.mixer.left >> 5;
int rightmix = pb.mixer.right >> 5;
int left = sample * leftmix >> 8;
int right = sample * rightmix >> 8;
//adpcm has to walk from oldSamplePos to samplePos here
// adpcm has to walk from oldSamplePos to samplePos here
templbuffer[s] += left;
temprbuffer[s] += right;
// ===============
// ===================================================================
// Control the behavior when we reach the end of the sample
if (samplePos >= sampleEnd)
{
if (pb.audio_addr.looping == 1)
{
samplePos = loopPos;
if (pb.audio_addr.sample_format == AUDIOFORMAT_ADPCM)
{
if (!pb.is_stream)
if ((!pb.is_stream) && (pb.audio_addr.sample_format == AUDIOFORMAT_ADPCM))
{
pb.adpcm.yn1 = pb.adpcm_loop_info.yn1;
pb.adpcm.yn2 = pb.adpcm_loop_info.yn2;
pb.adpcm.pred_scale = pb.adpcm_loop_info.pred_scale;
}
}
}
else
{
pb.running = 0;
samplePos = loopPos;
//samplePos = samplePos - sampleEnd + loopPos;
memset(&pb.updates, 0, sizeof(pb.updates));
memset(&pb.dpop, 0, sizeof(pb.dpop));
memset(pb.src.last_samples, 0, 8);
break;
}
}
// ===============
} // end of the _iSize loop
// Update volume
//if (sizeof(ParamBlockType) == sizeof(AXParamBlock)) // this is not needed anymore I think
if (gVolume) // allow us to turn this off in the debugger
{
pb.mixer.volume_left = ADPCM_Vol(pb.mixer.volume_left, pb.mixer.unknown);
pb.mixer.volume_right = ADPCM_Vol(pb.mixer.volume_right, pb.mixer.unknown2);
}
pb.mixer.left = ADPCM_Vol(pb.mixer.left, pb.mixer.left_delta);
pb.mixer.right = ADPCM_Vol(pb.mixer.right, pb.mixer.right_delta);
pb.src.cur_addr_frac = (u16)frac;
pb.audio_addr.cur_addr_hi = samplePos >> 16;
@ -272,110 +264,4 @@ inline void MixAddVoice(ParamBlockType &pb, int *templbuffer, int *temprbuffer,
} // if (pb.running)
}
// ================================================
// Voice hacks
// --------------
template<class ParamBlockType>
inline void DoVoiceHacks(ParamBlockType &pb, bool Wii)
{
// get necessary values
const u32 sampleEnd = (pb.audio_addr.end_addr_hi << 16) | pb.audio_addr.end_addr_lo;
const u32 loopPos = (pb.audio_addr.loop_addr_hi << 16) | pb.audio_addr.loop_addr_lo;
const u32 updaddr = (u32)(pb.updates.data_hi << 16) | pb.updates.data_lo;
const u16 updpar = Memory_Read_U16(updaddr);
const u16 upddata = Memory_Read_U16(updaddr + 2);
// =======================================================================================
/* Fix problems introduced with the SSBM fix. Sometimes when a music stream ended sampleEnd
would end up outside of bounds while the block was still playing resulting in noise
a strange noise. This should take care of that.
*/
// ------------
if (
(sampleEnd > (0x017fffff * 2) || loopPos > (0x017fffff * 2)) // ARAM bounds in nibbles
&& gSSBMremedy1
&& !Wii
)
{
pb.running = 0;
// also reset all values if it makes any difference
pb.audio_addr.cur_addr_hi = 0; pb.audio_addr.cur_addr_lo = 0;
pb.audio_addr.end_addr_hi = 0; pb.audio_addr.end_addr_lo = 0;
pb.audio_addr.loop_addr_hi = 0; pb.audio_addr.loop_addr_lo = 0;
pb.src.cur_addr_frac = 0; pb.src.ratio_hi = 0; pb.src.ratio_lo = 0;
pb.adpcm.pred_scale = 0; pb.adpcm.yn1 = 0; pb.adpcm.yn2 = 0;
pb.audio_addr.looping = 0;
pb.adpcm_loop_info.pred_scale = 0;
pb.adpcm_loop_info.yn1 = 0; pb.adpcm_loop_info.yn2 = 0;
}
/*
// the fact that no settings are reset (except running) after a SSBM type music stream or another
looping block (for example in Battle Stadium DON) has ended could cause loud garbled sound to be
played from one or more blocks. Perhaps it was in conjunction with the old sequenced music fix below,
I'm not sure. This was an attempt to prevent that anyway by resetting all. But I'm not sure if this
is needed anymore. Please try to play SSBM without it and see if it works anyway.
*/
if (
// detect blocks that have recently been running that we should reset
pb.running == 0 && pb.audio_addr.looping == 1
//pb.running == 0 && pb.adpcm_loop_info.pred_scale
// this prevents us from ruining sequenced music blocks, may not be needed
/*
&& !(pb.updates.num_updates[0] || pb.updates.num_updates[1] || pb.updates.num_updates[2]
|| pb.updates.num_updates[3] || pb.updates.num_updates[4])
*/
&& !(updpar || upddata)
&& pb.mixer_control == 0 // only use this in SSBM
&& gSSBMremedy2 // let us turn this fix on and off
&& !Wii
)
{
// reset the detection values
pb.audio_addr.looping = 0;
pb.adpcm_loop_info.pred_scale = 0;
pb.adpcm_loop_info.yn1 = 0; pb.adpcm_loop_info.yn2 = 0;
//pb.audio_addr.cur_addr_hi = 0; pb.audio_addr.cur_addr_lo = 0;
//pb.audio_addr.end_addr_hi = 0; pb.audio_addr.end_addr_lo = 0;
//pb.audio_addr.loop_addr_hi = 0; pb.audio_addr.loop_addr_lo = 0;
//pb.src.cur_addr_frac = 0; PBs[i].src.ratio_hi = 0; PBs[i].src.ratio_lo = 0;
//pb.adpcm.pred_scale = 0; pb.adpcm.yn1 = 0; pb.adpcm.yn2 = 0;
}
// =============
// =======================================================================================
// Reset all values
// ------------
if (gReset
&& (pb.running || pb.audio_addr.looping || pb.adpcm_loop_info.pred_scale)
)
{
pb.running = 0;
pb.audio_addr.cur_addr_hi = 0; pb.audio_addr.cur_addr_lo = 0;
pb.audio_addr.end_addr_hi = 0; pb.audio_addr.end_addr_lo = 0;
pb.audio_addr.loop_addr_hi = 0; pb.audio_addr.loop_addr_lo = 0;
pb.src.cur_addr_frac = 0; pb.src.ratio_hi = 0; pb.src.ratio_lo = 0;
pb.adpcm.pred_scale = 0; pb.adpcm.yn1 = 0; pb.adpcm.yn2 = 0;
pb.audio_addr.looping = 0;
pb.adpcm_loop_info.pred_scale = 0;
pb.adpcm_loop_info.yn1 = 0; pb.adpcm_loop_info.yn2 = 0;
}
}
#endif // _UCODE_AX_VOICE_H
#endif

View File

@ -22,17 +22,6 @@
class CUCode_CARD : public IUCode
{
private:
enum EDSP_Codes
{
DSP_INIT = 0xDCD10000,
DSP_RESUME = 0xDCD10001,
DSP_YIELD = 0xDCD10002,
DSP_DONE = 0xDCD10003,
DSP_SYNC = 0xDCD10004,
DSP_UNKN = 0xDCD10005,
};
public:
CUCode_CARD(CMailHandler& _rMailHandler);
virtual ~CUCode_CARD();

View File

@ -166,16 +166,6 @@ public:
}
private:
enum EDSP_Codes
{
DSP_INIT = 0xDCD10000,
DSP_RESUME = 0xDCD10001,
DSP_YIELD = 0xDCD10002,
DSP_DONE = 0xDCD10003,
DSP_SYNC = 0xDCD10004,
DSP_FRAME_END = 0xDCD10005,
};
// These map CRC to behaviour.
// DMA version

View File

@ -24,7 +24,6 @@
#define UCODE_ROM 0x0000000
#define UCODE_INIT_AUDIO_SYSTEM 0x0000001
#define UCODE_AXWII 0x1000000
class CMailHandler;
@ -49,6 +48,16 @@ public:
protected:
CMailHandler& m_rMailHandler;
Common::CriticalSection m_csMix;
enum EDSP_Codes
{
DSP_INIT = 0xDCD10000,
DSP_RESUME = 0xDCD10001,
DSP_YIELD = 0xDCD10002,
DSP_DONE = 0xDCD10003,
DSP_SYNC = 0xDCD10004,
DSP_FRAME_END = 0xDCD10005,
};
};
extern IUCode* UCodeFactory(u32 _CRC, CMailHandler& _rMailHandler);

View File

@ -22,9 +22,6 @@
#if defined(HAVE_WX) && HAVE_WX
#include "ConfigDlg.h"
DSPConfigDialogHLE* m_ConfigFrame = NULL;
#include "Debugger/File.h" // For file logging
#include "Debugger/Debugger.h"
DSPDebuggerHLE* m_DebuggerFrame = NULL;
#endif
#include "ChunkFile.h"
@ -124,19 +121,6 @@ wxWindow* GetParentedWxWindow(HWND Parent)
void DllDebugger(HWND _hParent, bool Show)
{
#if defined(HAVE_WX) && HAVE_WX
if (Show)
{
if (!m_DebuggerFrame)
m_DebuggerFrame = new DSPDebuggerHLE(NULL);
//m_DebuggerFrame = new DSPDebuggerHLE(GetParentedWxWindow(_hParent));
m_DebuggerFrame->Show();
}
else
{
if (m_DebuggerFrame) m_DebuggerFrame->Close();
}
#endif
}
@ -167,7 +151,6 @@ void DllConfig(HWND _hParent)
#if defined(HAVE_WX) && HAVE_WX
// Load config settings
g_Config.Load();
g_Config.GameIniLoad(globals->game_ini);
wxWindow *frame = GetParentedWxWindow(_hParent);
m_ConfigFrame = new DSPConfigDialogHLE(frame);
@ -221,19 +204,6 @@ void Shutdown()
// Delete the UCodes
CDSPHandler::Destroy();
#if defined(HAVE_WX) && HAVE_WX
// Reset mails
/*
if (m_DebuggerFrame)
{
sMailLog.clear();
sMailTime.clear();
m_DebuggerFrame->sMail.clear();
m_DebuggerFrame->sMailEnd.clear();
}
*/
#endif
}
void DoState(unsigned char **ptr, int mode)
@ -331,11 +301,9 @@ void DSP_Update(int cycles)
CDSPHandler::GetInstance().Update(cycles);
}
/* Other Audio will pass through here. The kind of audio that sometimes are
used together with pre-drawn movies. This audio can be disabled further
inside Mixer_PushSamples(), the reason that we don't disable this entire
function when Other Audio is disabled is that then we can't turn it back on
again once the game has started. */
// The reason that we don't disable this entire
// function when Other Audio is disabled is that then we can't turn it back on
// again once the game has started.
void DSP_SendAIBuffer(unsigned int address, unsigned int num_samples)
{
if (!soundStream)

View File

@ -21,11 +21,6 @@
#include "SoundStream.h"
#include "Globals.h" // Local
#if defined(HAVE_WX) && HAVE_WX
#include "Debugger/Debugger.h"
extern DSPDebuggerHLE* m_DebuggerFrame;
#endif
extern SoundStream *soundStream;
#endif

View File

@ -586,6 +586,10 @@
<Filter
Name="RE"
>
<File
RelativePath="..\..\..\docs\DSP\DSP_UC_3B3B30CA.txt"
>
</File>
<File
RelativePath="..\..\..\docs\DSP\DSP_UC_ROM.txt"
>

View File

@ -281,7 +281,7 @@
ProgramDataBaseFileName="$(IntDir)\"
WarningLevel="3"
SuppressStartupBanner="true"
DebugInformationFormat="4"
DebugInformationFormat="3"
CompileAs="0"
ForcedIncludeFiles="stdafx.h"
/>
@ -379,7 +379,7 @@
ProgramDataBaseFileName="$(IntDir)\"
WarningLevel="3"
SuppressStartupBanner="true"
DebugInformationFormat="4"
DebugInformationFormat="3"
CompileAs="0"
ForcedIncludeFiles="stdafx.h"
/>

View File

@ -18,7 +18,6 @@
#include "Common.h"
#include "IniFile.h"
#include "VideoConfig.h"
#include "../../../Core/Core/Src/ConfigManager.h" // FIXME
Config g_Config;

View File

@ -164,6 +164,11 @@ void 008c_BigCrazyFunction()
00a1 0340 00ff andi $AC1.M, #0x00ff
00a3 1f5f mrr $AX0.H, $AC1.M
00a4 02bf 88e5 call 0x88e5
88e5 387a orr'l $AC0.M, $AX0.H : $AC1.M, @$AR2
88e6 18dd lrrd $AC1.L, @$AR2
88e7 4c05 add'dr $ACC0, $ACC1 : $AR1
88e8 1b5e srri @$AR2, $AC0.M
88e9 1a5c srr @$AR2, $AC0.L
00a6 1f1c mrr $AX0.L, $AC0.L
00a7 811e clr'mv $ACC0 : $AX1.H, $AC0.M
00a8 191e lrri $AC0.M, @$AR0
@ -171,7 +176,11 @@ void 008c_BigCrazyFunction()
00aa 1ffc mrr $AC1.M, $AC0.L
00ab 1f5e mrr $AX0.H, $AC0.M
00ac 02bf 8809 call 0x8809
8809 392e orr'sn $AC1.M, $AX0.H : @$AR2, $AC1.L
880a 1b5f srri @$AR2, $AC1.M
00ae 02bf 8723 call 0x8723
8723 3300 xorr $AC1.M, $AX1.H
8724 1adf srrd @$AR2, $AC1.M
00b0 0006 dar $AR2
00b1 8106 clr'dr $ACC0 : $AR2
00b2 00de 166c lr $AC0.M, @0x166c
@ -182,6 +191,11 @@ void 008c_BigCrazyFunction()
00ba 0340 00ff andi $AC1.M, #0x00ff
00bc 1f5f mrr $AX0.H, $AC1.M
00bd 02bf 88e5 call 0x88e5
88e5 387a orr'l $AC0.M, $AX0.H : $AC1.M, @$AR2
88e6 18dd lrrd $AC1.L, @$AR2
88e7 4c05 add'dr $ACC0, $ACC1 : $AR1
88e8 1b5e srri @$AR2, $AC0.M
88e9 1a5c srr @$AR2, $AC0.L
00bf 1f1c mrr $AX0.L, $AC0.L
00c0 811e clr'mv $ACC0 : $AX1.H, $AC0.M
00c1 191e lrri $AC0.M, @$AR0
@ -189,7 +203,11 @@ void 008c_BigCrazyFunction()
00c3 1ffc mrr $AC1.M, $AC0.L
00c4 1f5e mrr $AX0.H, $AC0.M
00c5 02bf 8809 call 0x8809
8809 392e orr'sn $AC1.M, $AX0.H : @$AR2, $AC1.L
880a 1b5f srri @$AR2, $AC1.M
00c7 02bf 8723 call 0x8723
8723 3300 xorr $AC1.M, $AX1.H
8724 1adf srrd @$AR2, $AC1.M
00c9 8100 clr $ACC0
00ca 8900 clr $ACC1
00cb 00d1 0005 lr $AC1.H, @0x0005
@ -210,6 +228,8 @@ void 008c_BigCrazyFunction()
00de 00df 0003 lr $AC1.M, @0x0003
00e0 1504 lsl $ACC1, #4
00e1 02bf 8809 call 0x8809
8809 392e orr'sn $AC1.M, $AX0.H : @$AR2, $AC1.L
880a 1b5f srri @$AR2, $AC1.M
00e3 029f 0102 jmp 0x0102
:
@ -220,6 +240,11 @@ void 008c_BigCrazyFunction()
00eb 00de 1043 lr $AC0.M, @0x1043
00ed 0240 fff0 andi $AC0.M, #0xfff0
00ef 02bf 88e5 call 0x88e5
88e5 387a orr'l $AC0.M, $AX0.H : $AC1.M, @$AR2
88e6 18dd lrrd $AC1.L, @$AR2
88e7 4c05 add'dr $ACC0, $ACC1 : $AR1
88e8 1b5e srri @$AR2, $AC0.M
88e9 1a5c srr @$AR2, $AC0.L
00f1 029f 0102 jmp 0x0102
:
@ -233,6 +258,8 @@ void 008c_BigCrazyFunction()
00fe 1404 lsl $ACC0, #4
00ff 1f5e mrr $AX0.H, $AC0.M
0100 02bf 8809 call 0x8809
8809 392e orr'sn $AC1.M, $AX0.H : @$AR2, $AC1.L
880a 1b5f srri @$AR2, $AC1.M
:
0102 0083 0013 lri $AR3, #0x0013
@ -244,13 +271,26 @@ void 008c_BigCrazyFunction()
010c 0240 fff0 andi $AC0.M, #0xfff0
010e 1f5e mrr $AX0.H, $AC0.M
010f 02bf 81f4 call 0x81f4
81f4 b51e mulxac'mv $AX0.H, $AX1.L, $ACC1 : $AX1.H, $AC0.M
81f5 9909 asr16'ir $ACC1 : $AR1
81f6 1b7f srri @$AR3, $AC1.M
81f7 812b clr's $ACC0 : @$AR3, $AC1.L
0111 f100 lsl16 $ACC1
0112 02bf 8458 call 0x8458
8458 b51e mulxac'mv $AX0.H, $AX1.L, $ACC1 : $AX1.H, $AC0.M
8459 9900 asr16 $ACC1
845a 1b7f srri @$AR3, $AC1.M
845b 812b clr's $ACC0 : @$AR3, $AC1.L
0114 8f00 set40
0115 0082 0015 lri $AR2, #0x0015
0117 00de 0006 lr $AC0.M, @0x0006
0119 00da 165b lr $AX0.H, @0x165b
011b 02bf 88e5 call 0x88e5
88e5 387a orr'l $AC0.M, $AX0.H : $AC1.M, @$AR2
88e6 18dd lrrd $AC1.L, @$AR2
88e7 4c05 add'dr $ACC0, $ACC1 : $AR1
88e8 1b5e srri @$AR2, $AC0.M
88e9 1a5c srr @$AR2, $AC0.L
011d 14fd asr $ACC0, #-3
011e 1403 lsl $ACC0, #3
011f 1b5e srri @$AR2, $AC0.M
@ -260,6 +300,11 @@ void 008c_BigCrazyFunction()
0125 14f4 asr $ACC0, #-12
0126 00da 166b lr $AX0.H, @0x166b
0128 02bf 88e5 call 0x88e5
88e5 387a orr'l $AC0.M, $AX0.H : $AC1.M, @$AR2
88e6 18dd lrrd $AC1.L, @$AR2
88e7 4c05 add'dr $ACC0, $ACC1 : $AR1
88e8 1b5e srri @$AR2, $AC0.M
88e9 1a5c srr @$AR2, $AC0.L
012a b100 tst $ACC0
012b 0290 012e jge 0x012e