Merge latest master changes

This commit is contained in:
Rodolfo Bogado
2016-07-15 12:06:22 -03:00
parent 1aad4159e2
commit dda45ee317
420 changed files with 9403 additions and 9430 deletions

View File

@@ -13,7 +13,7 @@ foreach(LLVM_CONFIG_NAME ${LLVM_CONFIG_EXECUTABLES})
if (LLVM_CONFIG_EXE)
execute_process(COMMAND ${LLVM_CONFIG_EXE} --version OUTPUT_VARIABLE LLVM_PACKAGE_VERSION
OUTPUT_STRIP_TRAILING_WHITESPACE )
if (${LLVM_PACKAGE_VERSION} VERSION_GREATER "3.3")
if (LLVM_PACKAGE_VERSION VERSION_GREATER "3.3")
execute_process(COMMAND ${LLVM_CONFIG_EXE} --includedir OUTPUT_VARIABLE LLVM_INCLUDE_DIRS
OUTPUT_STRIP_TRAILING_WHITESPACE )
execute_process(COMMAND ${LLVM_CONFIG_EXE} --ldflags OUTPUT_VARIABLE LLVM_LDFLAGS

View File

@@ -33,6 +33,7 @@
#include "Core/PowerPC/Profiler.h"
#include "Core/State.h"
#include "DiscIO/Enums.h"
#include "DiscIO/Volume.h"
#include "DiscIO/VolumeCreator.h"
@@ -226,15 +227,14 @@ static int GetCountry(std::string filename)
if (pVolume != nullptr)
{
DiscIO::IVolume::ECountry country = pVolume->GetCountry();
int country = static_cast<int>(pVolume->GetCountry());
__android_log_print(ANDROID_LOG_INFO, DOLPHIN_TAG, "Country Code: %i", country);
return country;
}
// Return UNKNOWN
return 13;
return static_cast<int>(DiscIO::Country::COUNTRY_UNKNOWN);
}
static int GetPlatform(std::string filename)
@@ -245,13 +245,13 @@ static int GetPlatform(std::string filename)
{
switch (pVolume->GetVolumeType())
{
case DiscIO::IVolume::GAMECUBE_DISC:
case DiscIO::Platform::GAMECUBE_DISC:
__android_log_print(ANDROID_LOG_INFO, DOLPHIN_TAG, "Volume is a GameCube disc.");
return 0;
case DiscIO::IVolume::WII_DISC:
case DiscIO::Platform::WII_DISC:
__android_log_print(ANDROID_LOG_INFO, DOLPHIN_TAG, "Volume is a Wii disc.");
return 1;
case DiscIO::IVolume::WII_WAD:
case DiscIO::Platform::WII_WAD:
__android_log_print(ANDROID_LOG_INFO, DOLPHIN_TAG, "Volume is a Wii WAD.");
return 2;
}
@@ -269,13 +269,13 @@ static std::string GetTitle(std::string filename)
if (pVolume != nullptr)
{
std::map<DiscIO::IVolume::ELanguage, std::string> titles = pVolume->GetLongNames();
std::map<DiscIO::Language, std::string> titles = pVolume->GetLongNames();
if (titles.empty())
titles = pVolume->GetShortNames();
/*
bool is_wii_title = pVolume->GetVolumeType() != DiscIO::IVolume::GAMECUBE_DISC;
DiscIO::IVolume::ELanguage language = SConfig::GetInstance().GetCurrentLanguage(is_wii_title);
bool is_wii_title = pVolume->GetVolumeType() != DiscIO::Platform::GAMECUBE_DISC;
DiscIO::Language language = SConfig::GetInstance().GetCurrentLanguage(is_wii_title);
auto it = titles.find(language);
if (it != end)
@@ -284,8 +284,8 @@ static std::string GetTitle(std::string filename)
auto end = titles.end();
// English tends to be a good fallback when the requested language isn't available
// if (language != DiscIO::IVolume::ELanguage::LANGUAGE_ENGLISH) {
auto it = titles.find(DiscIO::IVolume::ELanguage::LANGUAGE_ENGLISH);
// if (language != DiscIO::Language::LANGUAGE_ENGLISH) {
auto it = titles.find(DiscIO::Language::LANGUAGE_ENGLISH);
if (it != end)
return it->second;
//}
@@ -312,11 +312,11 @@ static std::string GetDescription(std::string filename)
if (volume != nullptr)
{
std::map<DiscIO::IVolume::ELanguage, std::string> descriptions = volume->GetDescriptions();
std::map<DiscIO::Language, std::string> descriptions = volume->GetDescriptions();
/*
bool is_wii_title = pVolume->GetVolumeType() != DiscIO::IVolume::GAMECUBE_DISC;
DiscIO::IVolume::ELanguage language = SConfig::GetInstance().GetCurrentLanguage(is_wii_title);
bool is_wii_title = pVolume->GetVolumeType() != DiscIO::Platform::GAMECUBE_DISC;
DiscIO::Language language = SConfig::GetInstance().GetCurrentLanguage(is_wii_title);
auto it = descriptions.find(language);
if (it != end)
@@ -325,8 +325,8 @@ static std::string GetDescription(std::string filename)
auto end = descriptions.end();
// English tends to be a good fallback when the requested language isn't available
// if (language != DiscIO::IVolume::ELanguage::LANGUAGE_ENGLISH) {
auto it = descriptions.find(DiscIO::IVolume::ELanguage::LANGUAGE_ENGLISH);
// if (language != DiscIO::Language::LANGUAGE_ENGLISH) {
auto it = descriptions.find(DiscIO::Language::LANGUAGE_ENGLISH);
if (it != end)
return it->second;
//}

View File

@@ -26,7 +26,10 @@
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
<Import Project="..\..\VSProps\Base.props" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup Label="UserMacros">
<CScript Condition="'$(ProgramFiles(x86))' != ''">%windir%\System32\cscript</CScript>
<CScript Condition="'$(ProgramFiles(x86))' == ''">%windir%\Sysnative\cscript</CScript>
</PropertyGroup>
<!--
OutDir is always created, which is annoying for SCMRevGen as it doesn't really have an outdir.
Here it's redirected to some other place to hide the annoyance.
@@ -36,7 +39,7 @@
</PropertyGroup>
<ItemDefinitionGroup>
<PreBuildEvent>
<Command>"%windir%\Sysnative\cscript" /nologo /E:JScript "make_scmrev.h.js"</Command>
<Command>"$(CScript)" /nologo /E:JScript "make_scmrev.h.js"</Command>
</PreBuildEvent>
</ItemDefinitionGroup>
<ItemGroup>

View File

@@ -17,15 +17,15 @@
#include "Common/CommonFuncs.h"
#include "Common/CommonPaths.h"
#include "Common/CommonTypes.h"
#include "Common/StringUtil.h"
#include "Common/Logging/Log.h"
#include "Common/StringUtil.h"
#ifdef _WIN32
#include <Windows.h>
#else
#include <errno.h>
#include <iconv.h>
#include <locale.h>
#include <errno.h>
#endif
#if !defined(_WIN32) && !defined(ANDROID)
@@ -237,8 +237,7 @@ bool TryParse(const std::string& str, u32* const output)
return false;
#if ULONG_MAX > UINT_MAX
if (value >= 0x100000000ull &&
value <= 0xFFFFFFFF00000000ull)
if (value >= 0x100000000ull && value <= 0xFFFFFFFF00000000ull)
return false;
#endif
@@ -248,9 +247,11 @@ bool TryParse(const std::string& str, u32* const output)
bool TryParse(const std::string& str, bool* const output)
{
if ("1" == str || !strcasecmp("true", str.c_str()))
float value;
const bool is_valid_float = TryParse(str, &value);
if ((is_valid_float && value == 1) || !strcasecmp("true", str.c_str()))
*output = true;
else if ("0" == str || !strcasecmp("false", str.c_str()))
else if ((is_valid_float && value == 0) || !strcasecmp("false", str.c_str()))
*output = false;
else
return false;
@@ -270,7 +271,8 @@ std::string StringFromBool(bool value)
return value ? "True" : "False";
}
bool SplitPath(const std::string& full_path, std::string* _pPath, std::string* _pFilename, std::string* _pExtension)
bool SplitPath(const std::string& full_path, std::string* _pPath, std::string* _pFilename,
std::string* _pExtension)
{
if (full_path.empty())
return false;
@@ -302,7 +304,8 @@ bool SplitPath(const std::string& full_path, std::string* _pPath, std::string* _
return true;
}
void BuildCompleteFilename(std::string& _CompleteFilename, const std::string& _Path, const std::string& _Filename)
void BuildCompleteFilename(std::string& _CompleteFilename, const std::string& _Path,
const std::string& _Filename)
{
_CompleteFilename = _Path;
@@ -357,12 +360,15 @@ std::string ReplaceAll(std::string result, const std::string& src, const std::st
std::string UTF16ToUTF8(const std::wstring& input)
{
auto const size = WideCharToMultiByte(CP_UTF8, 0, input.data(), (int)input.size(), nullptr, 0, nullptr, nullptr);
auto const size = WideCharToMultiByte(CP_UTF8, 0, input.data(), (int)input.size(), nullptr, 0,
nullptr, nullptr);
std::string output;
output.resize(size);
if (size == 0 || size != WideCharToMultiByte(CP_UTF8, 0, input.data(), (int)input.size(), &output[0], (int)output.size(), nullptr, nullptr))
if (size == 0 ||
size != WideCharToMultiByte(CP_UTF8, 0, input.data(), (int)input.size(), &output[0],
(int)output.size(), nullptr, nullptr))
{
output.clear();
}
@@ -377,7 +383,9 @@ std::wstring CPToUTF16(u32 code_page, const std::string& input)
std::wstring output;
output.resize(size);
if (size == 0 || size != MultiByteToWideChar(code_page, 0, input.data(), (int)input.size(), &output[0], (int)output.size()))
if (size == 0 ||
size != MultiByteToWideChar(code_page, 0, input.data(), (int)input.size(), &output[0],
(int)output.size()))
{
output.clear();
}
@@ -427,8 +435,8 @@ std::string CodeToUTF8(const char* fromcode, const std::basic_string<T>& input)
while (src_bytes != 0)
{
size_t const iconv_result = iconv(conv_desc, (char**)(&src_buffer), &src_bytes,
&dst_buffer, &dst_bytes);
size_t const iconv_result =
iconv(conv_desc, (char**)(&src_buffer), &src_bytes, &dst_buffer, &dst_bytes);
if ((size_t)-1 == iconv_result)
{
@@ -460,14 +468,14 @@ std::string CodeToUTF8(const char* fromcode, const std::basic_string<T>& input)
std::string CP1252ToUTF8(const std::string& input)
{
//return CodeToUTF8("CP1252//TRANSLIT", input);
//return CodeToUTF8("CP1252//IGNORE", input);
// return CodeToUTF8("CP1252//TRANSLIT", input);
// return CodeToUTF8("CP1252//IGNORE", input);
return CodeToUTF8("CP1252", input);
}
std::string SHIFTJISToUTF8(const std::string& input)
{
//return CodeToUTF8("CP932", input);
// return CodeToUTF8("CP932", input);
return CodeToUTF8("SJIS", input);
}

View File

@@ -355,7 +355,7 @@ static bool getbitstring(u32 *ctrl, u32 *out, u8 len)
static bool batchdecrypt(u32 *codes, u16 size)
{
u32 tmp, *ptr = codes;
u32 tmparray[4] = {0}, tmparray2[8] = {0};
u32 tmparray[4] = { 0 }, tmparray2[8] = { 0 };
// Not required
//if (size & 1) return 0;

View File

@@ -82,7 +82,7 @@ enum
static std::mutex s_lock;
static std::vector<ARCode> s_active_codes;
static std::vector<std::string> s_internal_log;
static std::atomic<bool> s_use_internal_log{false};
static std::atomic<bool> s_use_internal_log{ false };
// pointer to the code currently being run, (used by log messages that include the code name)
static const ARCode* s_current_code = nullptr;
static bool s_disable_logging = false;
@@ -101,7 +101,7 @@ struct ARAddr
};
};
ARAddr(const u32 addr): address(addr)
ARAddr(const u32 addr) : address(addr)
{}
u32 GCAddress() const
{
@@ -167,7 +167,7 @@ std::vector<ARCode> LoadCodes(const IniFile& global_ini, const IniFile& local_in
}
}
const IniFile* inis[2] = {&global_ini, &local_ini};
const IniFile* inis[2] = { &global_ini, &local_ini };
for (const IniFile* ini : inis)
{
std::vector<std::string> lines;

View File

@@ -17,7 +17,7 @@ struct AREntry
{
AREntry()
{}
AREntry(u32 _addr, u32 _value): cmd_addr(_addr), value(_value)
AREntry(u32 _addr, u32 _value) : cmd_addr(_addr), value(_value)
{}
u32 cmd_addr;
u32 value;

View File

@@ -12,12 +12,10 @@
#include "Common/MathUtil.h"
#include "Common/StringUtil.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h"
#include "Core/Host.h"
#include "Core/PatchEngine.h"
#include "Core/Boot/Boot.h"
#include "Core/Boot/Boot_DOL.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h"
#include "Core/Debugger/Debugger_SymbolMap.h"
#include "Core/HLE/HLE.h"
#include "Core/HW/DVDInterface.h"
@@ -25,13 +23,17 @@
#include "Core/HW/Memmap.h"
#include "Core/HW/ProcessorInterface.h"
#include "Core/HW/VideoInterface.h"
#include "Core/Host.h"
#include "Core/IPC_HLE/WII_IPC_HLE.h"
#include "Core/PowerPC/PowerPC.h"
#include "Core/PatchEngine.h"
#include "Core/PowerPC/PPCAnalyst.h"
#include "Core/PowerPC/PPCSymbolDB.h"
#include "Core/PowerPC/PowerPC.h"
#include "Core/PowerPC/SignatureDB.h"
#include "DiscIO/Enums.h"
#include "DiscIO/NANDContentLoader.h"
#include "DiscIO/Volume.h"
#include "DiscIO/VolumeCreator.h"
bool CBoot::DVDRead(u64 dvd_offset, u32 output_address, u32 length, bool decrypt)
@@ -51,7 +53,7 @@ void CBoot::Load_FST(bool _bIsWii)
const DiscIO::IVolume& volume = DVDInterface::GetVolume();
// copy first 20 bytes of disc to start of Mem 1
DVDRead(/*offset*/0, /*address*/0, /*length*/0x20, false);
DVDRead(/*offset*/ 0, /*address*/ 0, /*length*/ 0x20, false);
// copy of game id
Memory::Write_U32(Memory::Read_U32(0x0000), 0x3180);
@@ -82,8 +84,7 @@ void CBoot::UpdateDebugger_MapLoaded()
Host_NotifyMapLoaded();
}
bool CBoot::FindMapFile(std::string* existing_map_file,
std::string* writable_map_file,
bool CBoot::FindMapFile(std::string* existing_map_file, std::string* writable_map_file,
std::string* title_id)
{
std::string title_id_str;
@@ -99,8 +100,7 @@ bool CBoot::FindMapFile(std::string* existing_map_file,
if (Loader.IsValid())
{
u64 TitleID = Loader.GetTitleID();
title_id_str = StringFromFormat("%08X_%08X",
(u32)(TitleID >> 32) & 0xFFFFFFFF,
title_id_str = StringFromFormat("%08X_%08X", (u32)(TitleID >> 32) & 0xFFFFFFFF,
(u32)TitleID & 0xFFFFFFFF);
}
break;
@@ -130,7 +130,8 @@ bool CBoot::FindMapFile(std::string* existing_map_file,
*title_id = title_id_str;
bool found = false;
static const std::string maps_directories[] = {
static const std::string maps_directories[] =
{
File::GetUserPath(D_MAPS_IDX),
File::GetSysDirectory() + MAPS_DIR DIR_SEP
};
@@ -167,14 +168,18 @@ bool CBoot::LoadMapFromFilename()
bool CBoot::Load_BS2(const std::string& _rBootROMFilename)
{
// CRC32
const u32 USA_v1_0 = 0x6D740AE7; // https://forums.dolphin-emu.org/Thread-unknown-hash-on-ipl-bin?pid=385344#pid385344
const u32 USA_v1_1 = 0xD5E6FEEA; // https://forums.dolphin-emu.org/Thread-unknown-hash-on-ipl-bin?pid=385334#pid385334
const u32 USA_v1_2 = 0x86573808; // https://forums.dolphin-emu.org/Thread-unknown-hash-on-ipl-bin?pid=385399#pid385399
const u32 BRA_v1_0 = 0x667D0B64; // GameCubes sold in Brazil have this IPL. Same as USA v1.2 but localized
const u32 JAP_v1_0 = 0x6DAC1F2A; // Redump
const u32 JAP_v1_1 = 0xD235E3F9; // https://bugs.dolphin-emu.org/issues/8936
const u32 PAL_v1_0 = 0x4F319F43; // Redump
const u32 PAL_v1_2 = 0xAD1B7F16; // Redump
const u32 USA_v1_0 =
0x6D740AE7; // https://forums.dolphin-emu.org/Thread-unknown-hash-on-ipl-bin?pid=385344#pid385344
const u32 USA_v1_1 =
0xD5E6FEEA; // https://forums.dolphin-emu.org/Thread-unknown-hash-on-ipl-bin?pid=385334#pid385334
const u32 USA_v1_2 =
0x86573808; // https://forums.dolphin-emu.org/Thread-unknown-hash-on-ipl-bin?pid=385399#pid385399
const u32 BRA_v1_0 =
0x667D0B64; // GameCubes sold in Brazil have this IPL. Same as USA v1.2 but localized
const u32 JAP_v1_0 = 0x6DAC1F2A; // Redump
const u32 JAP_v1_1 = 0xD235E3F9; // https://bugs.dolphin-emu.org/issues/8936
const u32 PAL_v1_0 = 0x4F319F43; // Redump
const u32 PAL_v1_2 = 0xAD1B7F16; // Redump
// Load the whole ROM dump
std::string data;
@@ -239,7 +244,6 @@ bool CBoot::Load_BS2(const std::string& _rBootROMFilename)
return true;
}
// Third boot step after BootManager and Core. See Call schedule in BootManager.cpp
bool CBoot::BootUp()
{
@@ -264,7 +268,7 @@ bool CBoot::BootUp()
const DiscIO::IVolume& pVolume = DVDInterface::GetVolume();
if ((pVolume.GetVolumeType() == DiscIO::IVolume::WII_DISC) != _StartupPara.bWii)
if ((pVolume.GetVolumeType() == DiscIO::Platform::WII_DISC) != _StartupPara.bWii)
{
PanicAlertT("Warning - starting ISO in wrong console mode!");
}
@@ -279,7 +283,7 @@ bool CBoot::BootUp()
WII_IPC_HLE_Interface::ES_DIVerify(tmd_buffer);
}
_StartupPara.bWii = pVolume.GetVolumeType() == DiscIO::IVolume::WII_DISC;
_StartupPara.bWii = pVolume.GetVolumeType() == DiscIO::Platform::WII_DISC;
// HLE BS2 or not
if (_StartupPara.bHLE_BS2)
@@ -338,7 +342,8 @@ bool CBoot::BootUp()
{
BS2Success = EmulatedBS2(dolWii);
}
else if ((!DVDInterface::VolumeIsValid() || DVDInterface::GetVolume().GetVolumeType() != DiscIO::IVolume::WII_DISC) &&
else if ((!DVDInterface::VolumeIsValid() ||
DVDInterface::GetVolume().GetVolumeType() != DiscIO::Platform::WII_DISC) &&
!_StartupPara.m_strDefaultISO.empty())
{
DVDInterface::SetVolumeName(_StartupPara.m_strDefaultISO);
@@ -348,7 +353,8 @@ bool CBoot::BootUp()
if (!_StartupPara.m_strDVDRoot.empty())
{
NOTICE_LOG(BOOT, "Setting DVDRoot %s", _StartupPara.m_strDVDRoot.c_str());
DVDInterface::SetVolumeDirectory(_StartupPara.m_strDVDRoot, dolWii, _StartupPara.m_strApploader, _StartupPara.m_strFilename);
DVDInterface::SetVolumeDirectory(_StartupPara.m_strDVDRoot, dolWii,
_StartupPara.m_strApploader, _StartupPara.m_strFilename);
BS2Success = EmulatedBS2(dolWii);
}
@@ -408,7 +414,7 @@ bool CBoot::BootUp()
// Poor man's bootup
if (_StartupPara.bWii)
SetupWiiMemory(DiscIO::IVolume::COUNTRY_UNKNOWN);
SetupWiiMemory(DiscIO::Country::COUNTRY_UNKNOWN);
else
EmulatedBS2_GC(true);
@@ -437,7 +443,6 @@ bool CBoot::BootUp()
DVDInterface::SetDiscInside(DVDInterface::VolumeIsValid());
break;
// Bootstrap 2 (AKA: Initial Program Loader, "BIOS")
case SConfig::BOOT_BS2:
{
@@ -465,7 +470,8 @@ bool CBoot::BootUp()
}
}
// HLE jump to loader (homebrew). Disabled when Gecko is active as it interferes with the code handler
// HLE jump to loader (homebrew). Disabled when Gecko is active as it interferes with the code
// handler
if (!SConfig::GetInstance().bEnableCheats)
{
HLE::Patch(0x80001800, "HBReload");

View File

@@ -7,7 +7,10 @@
#include <cstdlib>
#include <string>
#include "DiscIO/Volume.h"
namespace DiscIO
{
enum class Country;
}
struct CountrySetting
{
@@ -20,7 +23,6 @@ struct CountrySetting
class CBoot
{
public:
static bool BootUp();
static bool IsElfWii(const std::string& filename);
@@ -36,8 +38,7 @@ public:
// If title_id is not nullptr, it is set to the title id
//
// Returns true if a map file exists, false if none could be found.
static bool FindMapFile(std::string* existing_map_file,
std::string* writable_map_file,
static bool FindMapFile(std::string* existing_map_file, std::string* writable_map_file,
std::string* title_id = nullptr);
private:
@@ -56,5 +57,5 @@ private:
static bool Load_BS2(const std::string& _rBootROMFilename);
static void Load_FST(bool _bIsWii);
static bool SetupWiiMemory(DiscIO::IVolume::ECountry country);
static bool SetupWiiMemory(DiscIO::Country country);
};

View File

@@ -8,18 +8,21 @@
#include "Common/NandPaths.h"
#include "Common/SettingsHandler.h"
#include "Core/Boot/Boot.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h"
#include "Core/MemTools.h"
#include "Core/PatchEngine.h"
#include "Core/Boot/Boot.h"
#include "Core/HLE/HLE.h"
#include "Core/HW/CPU.h"
#include "Core/HW/DVDInterface.h"
#include "Core/HW/EXI_DeviceIPL.h"
#include "Core/HW/Memmap.h"
#include "Core/MemTools.h"
#include "Core/PatchEngine.h"
#include "Core/PowerPC/PowerPC.h"
#include "DiscIO/Enums.h"
#include "DiscIO/Volume.h"
void CBoot::RunFunction(u32 _iAddr)
{
PC = _iAddr;
@@ -56,30 +59,37 @@ bool CBoot::EmulatedBS2_GC(bool skipAppLoader)
// It's possible to boot DOL and ELF files without a disc inserted
if (DVDInterface::VolumeIsValid())
DVDRead(/*offset*/0x00000000, /*address*/0x00000000, 0x20, false); // write disc info
DVDRead(/*offset*/ 0x00000000, /*address*/ 0x00000000, 0x20, false); // write disc info
PowerPC::HostWrite_U32(0x0D15EA5E, 0x80000020); // Booted from bootrom. 0xE5207C22 = booted from jtag
PowerPC::HostWrite_U32(Memory::REALRAM_SIZE, 0x80000028); // Physical Memory Size (24MB on retail)
// TODO determine why some games fail when using a retail ID. (Seem to take different EXI paths, see Ikaruga for example)
PowerPC::HostWrite_U32(0x10000006, 0x8000002C); // Console type - DevKit (retail ID == 0x00000003) see YAGCD 4.2.1.1.2
PowerPC::HostWrite_U32(0x0D15EA5E,
0x80000020); // Booted from bootrom. 0xE5207C22 = booted from jtag
PowerPC::HostWrite_U32(Memory::REALRAM_SIZE,
0x80000028); // Physical Memory Size (24MB on retail)
// TODO determine why some games fail when using a retail ID. (Seem to take different EXI paths,
// see Ikaruga for example)
PowerPC::HostWrite_U32(
0x10000006,
0x8000002C); // Console type - DevKit (retail ID == 0x00000003) see YAGCD 4.2.1.1.2
PowerPC::HostWrite_U32(SConfig::GetInstance().bNTSC
? 0 : 1, 0x800000CC); // Fake the VI Init of the IPL (YAGCD 4.2.1.4)
PowerPC::HostWrite_U32(SConfig::GetInstance().bNTSC ? 0 : 1,
0x800000CC); // Fake the VI Init of the IPL (YAGCD 4.2.1.4)
PowerPC::HostWrite_U32(0x01000000, 0x800000d0); // ARAM Size. 16MB main + 4/16/32MB external (retail consoles have no external ARAM)
PowerPC::HostWrite_U32(0x01000000, 0x800000d0); // ARAM Size. 16MB main + 4/16/32MB external
// (retail consoles have no external ARAM)
PowerPC::HostWrite_U32(0x09a7ec80, 0x800000F8); // Bus Clock Speed
PowerPC::HostWrite_U32(0x1cf7c580, 0x800000FC); // CPU Clock Speed
PowerPC::HostWrite_U32(0x09a7ec80, 0x800000F8); // Bus Clock Speed
PowerPC::HostWrite_U32(0x1cf7c580, 0x800000FC); // CPU Clock Speed
PowerPC::HostWrite_U32(0x4c000064, 0x80000300); // Write default DFI Handler: rfi
PowerPC::HostWrite_U32(0x4c000064, 0x80000800); // Write default FPU Handler: rfi
PowerPC::HostWrite_U32(0x4c000064, 0x80000C00); // Write default Syscall Handler: rfi
PowerPC::HostWrite_U32(0x4c000064, 0x80000300); // Write default DFI Handler: rfi
PowerPC::HostWrite_U32(0x4c000064, 0x80000800); // Write default FPU Handler: rfi
PowerPC::HostWrite_U32(0x4c000064, 0x80000C00); // Write default Syscall Handler: rfi
PowerPC::HostWrite_U64((u64)CEXIIPL::GetGCTime() * (u64)40500000, 0x800030D8); // Preset time base ticks
// HIO checks this
//PowerPC::HostWrite_U16(0x8200, 0x000030e6); // Console type
PowerPC::HostWrite_U64((u64)CEXIIPL::GetGCTime() * (u64)40500000,
0x800030D8); // Preset time base ticks
// HIO checks this
// PowerPC::HostWrite_U16(0x8200, 0x000030e6); // Console type
HLE::Patch(0x81300000, "OSReport"); // HLE OSReport for Apploader
HLE::Patch(0x81300000, "OSReport"); // HLE OSReport for Apploader
if (!DVDInterface::VolumeIsValid())
return false;
@@ -89,8 +99,7 @@ bool CBoot::EmulatedBS2_GC(bool skipAppLoader)
const DiscIO::IVolume& volume = DVDInterface::GetVolume();
const u32 apploader_offset = 0x2440;
u32 apploader_entry, apploader_size, apploader_trailer;
if (skipAppLoader ||
!volume.ReadSwapped(apploader_offset + 0x10, &apploader_entry, false) ||
if (skipAppLoader || !volume.ReadSwapped(apploader_offset + 0x10, &apploader_entry, false) ||
!volume.ReadSwapped(apploader_offset + 0x14, &apploader_size, false) ||
!volume.ReadSwapped(apploader_offset + 0x18, &apploader_trailer, false) ||
apploader_entry == (u32)-1 || apploader_size + apploader_trailer == (u32)-1)
@@ -104,8 +113,10 @@ bool CBoot::EmulatedBS2_GC(bool skipAppLoader)
if (SConfig::GetInstance().bNTSC)
{
PowerPC::ppcState.gpr[1] = 0x81566550; // StackPointer, used to be set to 0x816ffff0
PowerPC::ppcState.gpr[2] = 0x81465cc0; // Global pointer to Small Data Area 2 Base (haven't seen anything use it...meh)
PowerPC::ppcState.gpr[13] = 0x81465320; // Global pointer to Small Data Area Base (Luigi's Mansion's apploader uses it)
PowerPC::ppcState.gpr[2] = 0x81465cc0; // Global pointer to Small Data Area 2 Base (haven't
// seen anything use it...meh)
PowerPC::ppcState.gpr[13] =
0x81465320; // Global pointer to Small Data Area Base (Luigi's Mansion's apploader uses it)
}
else
{
@@ -148,11 +159,11 @@ bool CBoot::EmulatedBS2_GC(bool skipAppLoader)
u32 iLength = PowerPC::Read_U32(0x81300008);
u32 iDVDOffset = PowerPC::Read_U32(0x8130000c);
INFO_LOG(MASTER_LOG, "DVDRead: offset: %08x memOffset: %08x length: %i", iDVDOffset, iRamAddress, iLength);
INFO_LOG(MASTER_LOG, "DVDRead: offset: %08x memOffset: %08x length: %i", iDVDOffset,
iRamAddress, iLength);
DVDRead(iDVDOffset, iRamAddress, iLength, false);
}
while (PowerPC::ppcState.gpr[3] != 0x00);
} while (PowerPC::ppcState.gpr[3] != 0x00);
// iAppLoaderClose
DEBUG_LOG(MASTER_LOG, "call iAppLoaderClose");
@@ -170,31 +181,33 @@ bool CBoot::EmulatedBS2_GC(bool skipAppLoader)
return true;
}
bool CBoot::SetupWiiMemory(DiscIO::IVolume::ECountry country)
bool CBoot::SetupWiiMemory(DiscIO::Country country)
{
static const CountrySetting SETTING_EUROPE = {"EUR", "PAL", "EU", "LE"};
static const CountrySetting SETTING_USA = {"USA", "NTSC", "US", "LU"};
static const CountrySetting SETTING_JAPAN = {"JPN", "NTSC", "JP", "LJ"};
static const CountrySetting SETTING_KOREA = {"KOR", "NTSC", "KR", "LKH"};
static const std::map<DiscIO::IVolume::ECountry, const CountrySetting> country_settings = {
{DiscIO::IVolume::COUNTRY_EUROPE, SETTING_EUROPE},
{DiscIO::IVolume::COUNTRY_USA, SETTING_USA},
{DiscIO::IVolume::COUNTRY_JAPAN, SETTING_JAPAN},
{DiscIO::IVolume::COUNTRY_KOREA, SETTING_KOREA},
//TODO: Determine if Taiwan have their own specific settings.
// Also determine if there are other specific settings
// for other countries.
{DiscIO::IVolume::COUNTRY_TAIWAN, SETTING_JAPAN}
};
static const CountrySetting SETTING_EUROPE = { "EUR", "PAL", "EU", "LE" };
static const CountrySetting SETTING_USA = { "USA", "NTSC", "US", "LU" };
static const CountrySetting SETTING_JAPAN = { "JPN", "NTSC", "JP", "LJ" };
static const CountrySetting SETTING_KOREA = { "KOR", "NTSC", "KR", "LKH" };
static const std::map<DiscIO::Country, const CountrySetting> country_settings = {
{DiscIO::Country::COUNTRY_EUROPE, SETTING_EUROPE},
{DiscIO::Country::COUNTRY_USA, SETTING_USA},
{DiscIO::Country::COUNTRY_JAPAN, SETTING_JAPAN},
{DiscIO::Country::COUNTRY_KOREA, SETTING_KOREA},
// TODO: Determine if Taiwan have their own specific settings.
// Also determine if there are other specific settings
// for other countries.
{DiscIO::Country::COUNTRY_TAIWAN, SETTING_JAPAN} };
auto entryPos = country_settings.find(country);
const CountrySetting& country_setting =
(entryPos != country_settings.end()) ?
entryPos->second :
(SConfig::GetInstance().bNTSC ? SETTING_USA : SETTING_EUROPE); // default to USA or EUR depending on game's video mode
(SConfig::GetInstance().bNTSC ?
SETTING_USA :
SETTING_EUROPE); // default to USA or EUR depending on game's video mode
SettingsHandler gen;
std::string serno;
std::string settings_Filename(Common::GetTitleDataPath(TITLEID_SYSMENU, Common::FROM_SESSION_ROOT) + WII_SETTING);
std::string settings_Filename(
Common::GetTitleDataPath(TITLEID_SYSMENU, Common::FROM_SESSION_ROOT) + WII_SETTING);
if (File::Exists(settings_Filename))
{
File::IOFile settingsFileHandle(settings_Filename, "rb");
@@ -257,51 +270,51 @@ bool CBoot::SetupWiiMemory(DiscIO::IVolume::ECountry country)
// When booting a WAD or the system menu, there will probably not be a disc inserted
if (DVDInterface::VolumeIsValid())
DVDRead(0x00000000, 0x00000000, 0x20, false); // Game Code
DVDRead(0x00000000, 0x00000000, 0x20, false); // Game Code
Memory::Write_U32(0x0D15EA5E, 0x00000020); // Another magic word
Memory::Write_U32(0x00000001, 0x00000024); // Unknown
Memory::Write_U32(Memory::REALRAM_SIZE, 0x00000028); // MEM1 size 24MB
Memory::Write_U32(0x00000023, 0x0000002c); // Production Board Model
Memory::Write_U32(0x00000000, 0x00000030); // Init
Memory::Write_U32(0x817FEC60, 0x00000034); // Init
Memory::Write_U32(0x0D15EA5E, 0x00000020); // Another magic word
Memory::Write_U32(0x00000001, 0x00000024); // Unknown
Memory::Write_U32(Memory::REALRAM_SIZE, 0x00000028); // MEM1 size 24MB
Memory::Write_U32(0x00000023, 0x0000002c); // Production Board Model
Memory::Write_U32(0x00000000, 0x00000030); // Init
Memory::Write_U32(0x817FEC60, 0x00000034); // Init
// 38, 3C should get start, size of FST through apploader
Memory::Write_U32(0x38a00040, 0x00000060); // Exception init
Memory::Write_U32(0x8008f7b8, 0x000000e4); // Thread Init
Memory::Write_U32(Memory::REALRAM_SIZE, 0x000000f0); // "Simulated memory size" (debug mode?)
Memory::Write_U32(0x8179b500, 0x000000f4); // __start
Memory::Write_U32(0x0e7be2c0, 0x000000f8); // Bus speed
Memory::Write_U32(0x2B73A840, 0x000000fc); // CPU speed
Memory::Write_U16(0x0000, 0x000030e6); // Console type
Memory::Write_U32(0x00000000, 0x000030c0); // EXI
Memory::Write_U32(0x00000000, 0x000030c4); // EXI
Memory::Write_U32(0x00000000, 0x000030dc); // Time
Memory::Write_U32(0x00000000, 0x000030d8); // Time
Memory::Write_U16(0x8201, 0x000030e6); // Dev console / debug capable
Memory::Write_U32(0x00000000, 0x000030f0); // Apploader
Memory::Write_U32(0x01800000, 0x00003100); // BAT
Memory::Write_U32(0x01800000, 0x00003104); // BAT
Memory::Write_U32(0x00000000, 0x0000310c); // Init
Memory::Write_U32(0x8179d500, 0x00003110); // Init
Memory::Write_U32(0x04000000, 0x00003118); // Unknown
Memory::Write_U32(0x04000000, 0x0000311c); // BAT
Memory::Write_U32(0x93400000, 0x00003120); // BAT
Memory::Write_U32(0x90000800, 0x00003124); // Init - MEM2 low
Memory::Write_U32(0x93ae0000, 0x00003128); // Init - MEM2 high
Memory::Write_U32(0x93ae0000, 0x00003130); // IOS MEM2 low
Memory::Write_U32(0x93b00000, 0x00003134); // IOS MEM2 high
Memory::Write_U32(0x00000012, 0x00003138); // Console type
Memory::Write_U32(0x38a00040, 0x00000060); // Exception init
Memory::Write_U32(0x8008f7b8, 0x000000e4); // Thread Init
Memory::Write_U32(Memory::REALRAM_SIZE, 0x000000f0); // "Simulated memory size" (debug mode?)
Memory::Write_U32(0x8179b500, 0x000000f4); // __start
Memory::Write_U32(0x0e7be2c0, 0x000000f8); // Bus speed
Memory::Write_U32(0x2B73A840, 0x000000fc); // CPU speed
Memory::Write_U16(0x0000, 0x000030e6); // Console type
Memory::Write_U32(0x00000000, 0x000030c0); // EXI
Memory::Write_U32(0x00000000, 0x000030c4); // EXI
Memory::Write_U32(0x00000000, 0x000030dc); // Time
Memory::Write_U32(0x00000000, 0x000030d8); // Time
Memory::Write_U16(0x8201, 0x000030e6); // Dev console / debug capable
Memory::Write_U32(0x00000000, 0x000030f0); // Apploader
Memory::Write_U32(0x01800000, 0x00003100); // BAT
Memory::Write_U32(0x01800000, 0x00003104); // BAT
Memory::Write_U32(0x00000000, 0x0000310c); // Init
Memory::Write_U32(0x8179d500, 0x00003110); // Init
Memory::Write_U32(0x04000000, 0x00003118); // Unknown
Memory::Write_U32(0x04000000, 0x0000311c); // BAT
Memory::Write_U32(0x93400000, 0x00003120); // BAT
Memory::Write_U32(0x90000800, 0x00003124); // Init - MEM2 low
Memory::Write_U32(0x93ae0000, 0x00003128); // Init - MEM2 high
Memory::Write_U32(0x93ae0000, 0x00003130); // IOS MEM2 low
Memory::Write_U32(0x93b00000, 0x00003134); // IOS MEM2 high
Memory::Write_U32(0x00000012, 0x00003138); // Console type
// 40 is copied from 88 after running apploader
Memory::Write_U32(0x00090204, 0x00003140); // IOS revision (IOS9, v2.4)
Memory::Write_U32(0x00062507, 0x00003144); // IOS date in USA format (June 25, 2007)
Memory::Write_U16(0x0113, 0x0000315e); // Apploader
Memory::Write_U32(0x0000FF16, 0x00003158); // DDR ram vendor code
Memory::Write_U32(0x00000000, 0x00003160); // Init semaphore (sysmenu waits for this to clear)
Memory::Write_U32(0x00090204, 0x00003188); // Expected IOS revision
Memory::Write_U32(0x00090204, 0x00003140); // IOS revision (IOS9, v2.4)
Memory::Write_U32(0x00062507, 0x00003144); // IOS date in USA format (June 25, 2007)
Memory::Write_U16(0x0113, 0x0000315e); // Apploader
Memory::Write_U32(0x0000FF16, 0x00003158); // DDR ram vendor code
Memory::Write_U32(0x00000000, 0x00003160); // Init semaphore (sysmenu waits for this to clear)
Memory::Write_U32(0x00090204, 0x00003188); // Expected IOS revision
Memory::Write_U8(0x80, 0x0000315c); // OSInit
Memory::Write_U16(0x0000, 0x000030e0); // PADInit
Memory::Write_U32(0x80000000, 0x00003184); // GameID Address
Memory::Write_U8(0x80, 0x0000315c); // OSInit
Memory::Write_U16(0x0000, 0x000030e0); // PADInit
Memory::Write_U32(0x80000000, 0x00003184); // GameID Address
// Fake the VI Init of the IPL
Memory::Write_U32(SConfig::GetInstance().bNTSC ? 0 : 1, 0x000000CC);
@@ -323,7 +336,7 @@ bool CBoot::EmulatedBS2_Wii()
INFO_LOG(BOOT, "Faking Wii BS2...");
// Setup Wii memory
DiscIO::IVolume::ECountry country_code = DiscIO::IVolume::COUNTRY_UNKNOWN;
DiscIO::Country country_code = DiscIO::Country::COUNTRY_UNKNOWN;
if (DVDInterface::VolumeIsValid())
country_code = DVDInterface::GetVolume().GetCountry();
if (SetupWiiMemory(country_code) == false)
@@ -331,7 +344,8 @@ bool CBoot::EmulatedBS2_Wii()
// Execute the apploader
bool apploaderRan = false;
if (DVDInterface::VolumeIsValid() && DVDInterface::GetVolume().GetVolumeType() == DiscIO::IVolume::WII_DISC)
if (DVDInterface::VolumeIsValid() &&
DVDInterface::GetVolume().GetVolumeType() == DiscIO::Platform::WII_DISC)
{
// This is some kind of consistency check that is compared to the 0x00
// values as the game boots. This location keeps the 4 byte ID for as long
@@ -358,15 +372,15 @@ bool CBoot::EmulatedBS2_Wii()
PowerPC::ppcState.spr[SPR_DBAT5U] = 0xd0001fff;
PowerPC::ppcState.spr[SPR_DBAT5L] = 0x1000002a;
Memory::Write_U32(0x4c000064, 0x00000300); // Write default DSI Handler: rfi
Memory::Write_U32(0x4c000064, 0x00000800); // Write default FPU Handler: rfi
Memory::Write_U32(0x4c000064, 0x00000C00); // Write default Syscall Handler: rfi
Memory::Write_U32(0x4c000064, 0x00000300); // Write default DSI Handler: rfi
Memory::Write_U32(0x4c000064, 0x00000800); // Write default FPU Handler: rfi
Memory::Write_U32(0x4c000064, 0x00000C00); // Write default Syscall Handler: rfi
HLE::Patch(0x81300000, "OSReport"); // HLE OSReport for Apploader
HLE::Patch(0x81300000, "OSReport"); // HLE OSReport for Apploader
PowerPC::ppcState.gpr[1] = 0x816ffff0; // StackPointer
PowerPC::ppcState.gpr[1] = 0x816ffff0; // StackPointer
const u32 apploader_offset = 0x2440; // 0x1c40;
const u32 apploader_offset = 0x2440; // 0x1c40;
// Load Apploader to Memory
const DiscIO::IVolume& volume = DVDInterface::GetVolume();
@@ -380,7 +394,7 @@ bool CBoot::EmulatedBS2_Wii()
}
DVDRead(apploader_offset + 0x20, 0x01200000, apploader_size, true);
//call iAppLoaderEntry
// call iAppLoaderEntry
DEBUG_LOG(BOOT, "Call iAppLoaderEntry");
u32 iAppLoaderFuncAddr = 0x80004000;
@@ -415,10 +429,10 @@ bool CBoot::EmulatedBS2_Wii()
u32 iLength = PowerPC::Read_U32(0x81300008);
u32 iDVDOffset = PowerPC::Read_U32(0x8130000c) << 2;
INFO_LOG(BOOT, "DVDRead: offset: %08x memOffset: %08x length: %i", iDVDOffset, iRamAddress, iLength);
INFO_LOG(BOOT, "DVDRead: offset: %08x memOffset: %08x length: %i", iDVDOffset,
iRamAddress, iLength);
DVDRead(iDVDOffset, iRamAddress, iLength, true);
}
while (PowerPC::ppcState.gpr[3] != 0x00);
} while (PowerPC::ppcState.gpr[3] != 0x00);
// iAppLoaderClose
DEBUG_LOG(BOOT, "Run iAppLoaderClose");

View File

@@ -31,7 +31,8 @@ CDolLoader::CDolLoader(const std::string& filename)
}
CDolLoader::~CDolLoader()
{}
{
}
bool CDolLoader::Initialize(const std::vector<u8>& buffer)
{
@@ -101,10 +102,12 @@ void CDolLoader::Load() const
// load all text (code) sections
for (size_t i = 0; i < m_text_sections.size(); ++i)
if (!m_text_sections[i].empty())
Memory::CopyToEmu(m_dolheader.textAddress[i], m_text_sections[i].data(), m_text_sections[i].size());
Memory::CopyToEmu(m_dolheader.textAddress[i], m_text_sections[i].data(),
m_text_sections[i].size());
// load all data sections
for (size_t i = 0; i < m_data_sections.size(); ++i)
if (!m_data_sections[i].empty())
Memory::CopyToEmu(m_dolheader.dataAddress[i], m_data_sections[i].data(), m_data_sections[i].size());
Memory::CopyToEmu(m_dolheader.dataAddress[i], m_data_sections[i].data(),
m_data_sections[i].size());
}

View File

@@ -16,19 +16,9 @@ public:
CDolLoader(const std::vector<u8>& buffer);
~CDolLoader();
bool IsValid() const
{
return m_is_valid;
}
bool IsWii() const
{
return m_is_wii;
}
u32 GetEntryPoint() const
{
return m_dolheader.entryPoint;
}
bool IsValid() const { return m_is_valid; }
bool IsWii() const { return m_is_wii; }
u32 GetEntryPoint() const { return m_dolheader.entryPoint; }
// Load into emulated memory
void Load() const;

View File

@@ -4,6 +4,7 @@
#include <memory>
#include "Common/CommonFuncs.h"
#include "Common/FileUtil.h"
#include "Core/Boot/Boot.h"
#include "Core/Boot/ElfReader.h"
@@ -13,7 +14,7 @@
bool CBoot::IsElfWii(const std::string& filename)
{
/* We already check if filename existed before we called this function, so
there is no need for another check, just read the file right away */
there is no need for another check, just read the file right away */
size_t filesize = File::GetSize(filename);
auto elf = std::make_unique<u8[]>(filesize);
@@ -50,7 +51,6 @@ bool CBoot::IsElfWii(const std::string& filename)
return false;
}
bool CBoot::Boot_ELF(const std::string& filename)
{
// Read ELF from file

View File

@@ -9,23 +9,24 @@
#include "Common/FileUtil.h"
#include "Common/NandPaths.h"
#include "Core/ConfigManager.h"
#include "Core/PatchEngine.h"
#include "Core/Boot/Boot.h"
#include "Core/Boot/Boot_DOL.h"
#include "Core/ConfigManager.h"
#include "Core/HLE/HLE.h"
#include "Core/HW/Memmap.h"
#include "Core/HW/VideoInterface.h"
#include "Core/IPC_HLE/WII_IPC_HLE.h"
#include "Core/IPC_HLE/WII_IPC_HLE_Device_FileIO.h"
#include "Core/PatchEngine.h"
#include "Core/PowerPC/PowerPC.h"
#include "DiscIO/Enums.h"
#include "DiscIO/NANDContentLoader.h"
#include "DiscIO/Volume.h"
#include "DiscIO/VolumeCreator.h"
#include "DiscIO/WiiWad.h"
static u32 state_checksum(u32 *buf, int len)
static u32 state_checksum(u32* buf, int len)
{
u32 checksum = 0;
len = len >> 2;
@@ -50,7 +51,8 @@ struct StateFlags
bool CBoot::Boot_WiiWAD(const std::string& _pFilename)
{
std::string state_filename(Common::GetTitleDataPath(TITLEID_SYSMENU, Common::FROM_SESSION_ROOT) + WII_STATE);
std::string state_filename(Common::GetTitleDataPath(TITLEID_SYSMENU, Common::FROM_SESSION_ROOT) +
WII_STATE);
if (File::Exists(state_filename))
{
@@ -58,7 +60,7 @@ bool CBoot::Boot_WiiWAD(const std::string& _pFilename)
StateFlags state;
state_file.ReadBytes(&state, sizeof(StateFlags));
state.type = 0x03; // TYPE_RETURN
state.type = 0x03; // TYPE_RETURN
state.checksum = state_checksum((u32*)&state.flags, sizeof(StateFlags) - 4);
state_file.Seek(0, SEEK_SET);
@@ -70,13 +72,14 @@ bool CBoot::Boot_WiiWAD(const std::string& _pFilename)
File::IOFile state_file(state_filename, "a+b");
StateFlags state;
memset(&state, 0, sizeof(StateFlags));
state.type = 0x03; // TYPE_RETURN
state.discstate = 0x01; // DISCSTATE_WII
state.type = 0x03; // TYPE_RETURN
state.discstate = 0x01; // DISCSTATE_WII
state.checksum = state_checksum((u32*)&state.flags, sizeof(StateFlags) - 4);
state_file.WriteBytes(&state, sizeof(StateFlags));
}
const DiscIO::CNANDContentLoader& ContentLoader = DiscIO::CNANDContentManager::Access().GetNANDLoader(_pFilename);
const DiscIO::CNANDContentLoader& ContentLoader =
DiscIO::CNANDContentManager::Access().GetNANDLoader(_pFilename);
if (!ContentLoader.IsValid())
return false;
@@ -90,12 +93,13 @@ bool CBoot::Boot_WiiWAD(const std::string& _pFilename)
if (!SetupWiiMemory(ContentLoader.GetCountry()))
return false;
// this sets a bit that is used to detect NTSC-J
if (ContentLoader.GetCountry() == DiscIO::IVolume::COUNTRY_JAPAN)
if (ContentLoader.GetCountry() == DiscIO::Country::COUNTRY_JAPAN)
{
VideoInterface::SetRegionReg('J');
}
// DOL
const DiscIO::SNANDContent* pContent = ContentLoader.GetContentByIndex(ContentLoader.GetBootIndex());
const DiscIO::SNANDContent* pContent =
ContentLoader.GetContentByIndex(ContentLoader.GetBootIndex());
if (pContent == nullptr)
return false;
@@ -125,4 +129,3 @@ bool CBoot::Boot_WiiWAD(const std::string& _pFilename)
return true;
}

View File

@@ -13,16 +13,16 @@
#include "Core/HW/Memmap.h"
#include "Core/PowerPC/PPCSymbolDB.h"
static void bswap(u32 &w)
static void bswap(u32& w)
{
w = Common::swap32(w);
}
static void bswap(u16 &w)
static void bswap(u16& w)
{
w = Common::swap16(w);
}
static void byteswapHeader(Elf32_Ehdr &ELF_H)
static void byteswapHeader(Elf32_Ehdr& ELF_H)
{
bswap(ELF_H.e_type);
bswap(ELF_H.e_machine);
@@ -39,7 +39,7 @@ static void byteswapHeader(Elf32_Ehdr &ELF_H)
bswap(ELF_H.e_flags);
}
static void byteswapSegment(Elf32_Phdr &sec)
static void byteswapSegment(Elf32_Phdr& sec)
{
bswap(sec.p_align);
bswap(sec.p_filesz);
@@ -51,7 +51,7 @@ static void byteswapSegment(Elf32_Phdr &sec)
bswap(sec.p_type);
}
static void byteswapSection(Elf32_Shdr &sec)
static void byteswapSection(Elf32_Shdr& sec)
{
bswap(sec.sh_addr);
bswap(sec.sh_addralign);
@@ -65,15 +65,15 @@ static void byteswapSection(Elf32_Shdr &sec)
bswap(sec.sh_type);
}
ElfReader::ElfReader(void *ptr)
ElfReader::ElfReader(void* ptr)
{
base = (char*)ptr;
base32 = (u32*)ptr;
header = (Elf32_Ehdr*)ptr;
byteswapHeader(*header);
segments = (Elf32_Phdr *)(base + header->e_phoff);
sections = (Elf32_Shdr *)(base + header->e_shoff);
segments = (Elf32_Phdr*)(base + header->e_phoff);
sections = (Elf32_Shdr*)(base + header->e_shoff);
for (int i = 0; i < GetNumSegments(); i++)
{
@@ -122,8 +122,8 @@ bool ElfReader::LoadIntoMemory()
{
Elf32_Phdr* p = segments + i;
INFO_LOG(MASTER_LOG, "Type: %i Vaddr: %08x Filesz: %i Memsz: %i ",
p->p_type, p->p_vaddr, p->p_filesz, p->p_memsz);
INFO_LOG(MASTER_LOG, "Type: %i Vaddr: %08x Filesz: %i Memsz: %i ", p->p_type, p->p_vaddr,
p->p_filesz, p->p_memsz);
if (p->p_type == PT_LOAD)
{
@@ -134,7 +134,7 @@ bool ElfReader::LoadIntoMemory()
Memory::CopyToEmu(writeAddr, src, srcSize);
if (srcSize < dstSize)
Memory::Memset(writeAddr + srcSize, 0, dstSize - srcSize); //zero out bss
Memory::Memset(writeAddr + srcSize, 0, dstSize - srcSize); // zero out bss
INFO_LOG(MASTER_LOG, "Loadable Segment Copied to %08x, size %08x", writeAddr, p->p_memsz);
}
@@ -144,7 +144,7 @@ bool ElfReader::LoadIntoMemory()
return true;
}
SectionID ElfReader::GetSectionByName(const char *name, int firstSection) const
SectionID ElfReader::GetSectionByName(const char* name, int firstSection) const
{
for (int i = firstSection; i < header->e_shnum; i++)
{
@@ -163,10 +163,10 @@ bool ElfReader::LoadSymbols()
if (sec != -1)
{
int stringSection = sections[sec].sh_link;
const char* stringBase = (const char *)GetSectionDataPtr(stringSection);
const char* stringBase = (const char*)GetSectionDataPtr(stringSection);
//We have a symbol table!
Elf32_Sym* symtab = (Elf32_Sym *)(GetSectionDataPtr(sec));
// We have a symbol table!
Elf32_Sym* symtab = (Elf32_Sym*)(GetSectionDataPtr(sec));
int numSymbols = sections[sec].sh_size / sizeof(Elf32_Sym);
for (int sym = 0; sym < numSymbols; sym++)
{
@@ -186,9 +186,11 @@ bool ElfReader::LoadSymbols()
switch (type)
{
case STT_OBJECT:
symtype = Symbol::SYMBOL_DATA; break;
symtype = Symbol::SYMBOL_DATA;
break;
case STT_FUNC:
symtype = Symbol::SYMBOL_FUNCTION; break;
symtype = Symbol::SYMBOL_FUNCTION;
break;
default:
continue;
}

View File

@@ -26,54 +26,27 @@ private:
Elf32_Phdr* segments;
Elf32_Shdr* sections;
u32 *sectionAddrs;
u32* sectionAddrs;
bool bRelocate;
u32 entryPoint;
public:
ElfReader(void* ptr);
~ElfReader()
{}
u32 Read32(int off) const
{
return base32[off >> 2];
}
~ElfReader() {}
u32 Read32(int off) const { return base32[off >> 2]; }
// Quick accessors
ElfType GetType() const
{
return (ElfType)(header->e_type);
}
ElfMachine GetMachine() const
{
return (ElfMachine)(header->e_machine);
}
u32 GetEntryPoint() const
{
return entryPoint;
}
u32 GetFlags() const
{
return (u32)(header->e_flags);
}
ElfType GetType() const { return (ElfType)(header->e_type); }
ElfMachine GetMachine() const { return (ElfMachine)(header->e_machine); }
u32 GetEntryPoint() const { return entryPoint; }
u32 GetFlags() const { return (u32)(header->e_flags); }
bool LoadIntoMemory();
bool LoadSymbols();
int GetNumSegments() const
{
return (int)(header->e_phnum);
}
int GetNumSections() const
{
return (int)(header->e_shnum);
}
const u8* GetPtr(int offset) const
{
return (u8*)base + offset;
}
int GetNumSegments() const { return (int)(header->e_phnum); }
int GetNumSections() const { return (int)(header->e_shnum); }
const u8* GetPtr(int offset) const { return (u8*)base + offset; }
const char* GetSectionName(int section) const;
const u8 *GetSectionDataPtr(int section) const
const u8* GetSectionDataPtr(int section) const
{
if (section < 0 || section >= header->e_shnum)
return nullptr;
@@ -82,26 +55,11 @@ public:
else
return nullptr;
}
bool IsCodeSection(int section) const
{
return sections[section].sh_type == SHT_PROGBITS;
}
const u8* GetSegmentPtr(int segment)
{
return GetPtr(segments[segment].p_offset);
}
u32 GetSectionAddr(SectionID section) const
{
return sectionAddrs[section];
}
int GetSectionSize(SectionID section) const
{
return sections[section].sh_size;
}
SectionID GetSectionByName(const char* name, int firstSection = 0) const; //-1 for not found
bool IsCodeSection(int section) const { return sections[section].sh_type == SHT_PROGBITS; }
const u8* GetSegmentPtr(int segment) { return GetPtr(segments[segment].p_offset); }
u32 GetSectionAddr(SectionID section) const { return sectionAddrs[section]; }
int GetSectionSize(SectionID section) const { return sections[section].sh_size; }
SectionID GetSectionByName(const char* name, int firstSection = 0) const; //-1 for not found
bool DidRelocate() const
{
return bRelocate;
}
bool DidRelocate() const { return bRelocate; }
};

View File

@@ -34,62 +34,60 @@ enum ElfMachine
};
// File version
#define EV_NONE 0
#define EV_NONE 0
#define EV_CURRENT 1
// Identification index
#define EI_MAG0 0
#define EI_MAG1 1
#define EI_MAG2 2
#define EI_MAG3 3
#define EI_CLASS 4
#define EI_DATA 5
#define EI_MAG0 0
#define EI_MAG1 1
#define EI_MAG2 2
#define EI_MAG3 3
#define EI_CLASS 4
#define EI_DATA 5
#define EI_VERSION 6
#define EI_PAD 7
#define EI_PAD 7
#define EI_NIDENT 16
// Magic number
#define ELFMAG0 0x7F
#define ELFMAG1 'E'
#define ELFMAG2 'L'
#define ELFMAG3 'F'
#define ELFMAG1 'E'
#define ELFMAG2 'L'
#define ELFMAG3 'F'
// File class
#define ELFCLASSNONE 0
#define ELFCLASS32 1
#define ELFCLASS64 2
#define ELFCLASS32 1
#define ELFCLASS64 2
// Encoding
#define ELFDATANONE 0
#define ELFDATA2LSB 1
#define ELFDATA2MSB 2
// Sections constants
// Section indexes
#define SHN_UNDEF 0
#define SHN_UNDEF 0
#define SHN_LORESERVE 0xFF00
#define SHN_LOPROC 0xFF00
#define SHN_HIPROC 0xFF1F
#define SHN_ABS 0xFFF1
#define SHN_COMMON 0xFFF2
#define SHN_LOPROC 0xFF00
#define SHN_HIPROC 0xFF1F
#define SHN_ABS 0xFFF1
#define SHN_COMMON 0xFFF2
#define SHN_HIRESERVE 0xFFFF
// Section types
#define SHT_NULL 0
#define SHT_PROGBITS 1
#define SHT_SYMTAB 2
#define SHT_STRTAB 3
#define SHT_RELA 4
#define SHT_HASH 5
#define SHT_DYNAMIC 6
#define SHT_NOTE 7
#define SHT_NOBITS 8
#define SHT_REL 9
#define SHT_SHLIB 10
#define SHT_DYNSYM 11
#define SHT_NULL 0
#define SHT_PROGBITS 1
#define SHT_SYMTAB 2
#define SHT_STRTAB 3
#define SHT_RELA 4
#define SHT_HASH 5
#define SHT_DYNAMIC 6
#define SHT_NOTE 7
#define SHT_NOBITS 8
#define SHT_REL 9
#define SHT_SHLIB 10
#define SHT_DYNSYM 11
#define SHT_LOPROC 0x70000000
#define SHT_HIPROC 0x7FFFFFFF
#define SHT_LOUSER 0x80000000
@@ -98,7 +96,6 @@ enum ElfMachine
// Custom section types
#define SHT_PSPREL 0x700000a0
// Section flags
enum ElfSectionFlags
{
@@ -109,47 +106,47 @@ enum ElfSectionFlags
};
// Symbol binding
#define STB_LOCAL 0
#define STB_GLOBAL 1
#define STB_WEAK 2
#define STB_LOCAL 0
#define STB_GLOBAL 1
#define STB_WEAK 2
#define STB_LOPROC 13
#define STB_HIPROC 15
// Symbol types
#define STT_NOTYPE 0
#define STT_OBJECT 1
#define STT_FUNC 2
#define STT_SECTION 3
#define STT_FILE 4
#define STT_LOPROC 13
#define STT_HIPROC 15
#define STT_NOTYPE 0
#define STT_OBJECT 1
#define STT_FUNC 2
#define STT_SECTION 3
#define STT_FILE 4
#define STT_LOPROC 13
#define STT_HIPROC 15
// Undefined name
#define STN_UNDEF 0
// Relocation types
#define R_386_NONE 0
#define R_386_32 1
#define R_386_PC32 2
#define R_386_GOT32 3
#define R_386_PLT32 4
#define R_386_COPY 5
#define R_386_GLOB_DAT 6
#define R_386_JMP_SLOT 7
#define R_386_RELATIVE 8
#define R_386_GOTOFF 9
#define R_386_GOTPC 10
#define R_386_NONE 0
#define R_386_32 1
#define R_386_PC32 2
#define R_386_GOT32 3
#define R_386_PLT32 4
#define R_386_COPY 5
#define R_386_GLOB_DAT 6
#define R_386_JMP_SLOT 7
#define R_386_RELATIVE 8
#define R_386_GOTOFF 9
#define R_386_GOTPC 10
// Segment types
#define PT_NULL 0
#define PT_LOAD 1
#define PT_DYNAMIC 2
#define PT_INTERP 3
#define PT_NOTE 4
#define PT_SHLIB 5
#define PT_PHDR 6
#define PT_LOPROC 0x70000000
#define PT_HIPROC 0x7FFFFFFF
#define PT_NULL 0
#define PT_LOAD 1
#define PT_DYNAMIC 2
#define PT_INTERP 3
#define PT_NOTE 4
#define PT_SHLIB 5
#define PT_PHDR 6
#define PT_LOPROC 0x70000000
#define PT_HIPROC 0x7FFFFFFF
// Segment flags
#define PF_X 1
@@ -157,50 +154,50 @@ enum ElfSectionFlags
#define PF_R 4
// Dynamic Array Tags
#define DT_NULL 0
#define DT_NEEDED 1
#define DT_PLTRELSZ 2
#define DT_PLTGOT 3
#define DT_HASH 4
#define DT_STRTAB 5
#define DT_SYMTAB 6
#define DT_RELA 7
#define DT_RELASZ 8
#define DT_RELAENT 9
#define DT_STRSZ 10
#define DT_SYMENT 11
#define DT_INIT 12
#define DT_FINI 13
#define DT_SONAME 14
#define DT_RPATH 15
#define DT_SYMBOLIC 16
#define DT_REL 17
#define DT_RELSZ 18
#define DT_RELENT 19
#define DT_PLTREL 20
#define DT_DEBUG 21
#define DT_TEXTREL 22
#define DT_JMPREL 23
#define DT_LOPROC 0x70000000
#define DT_HIPROC 0x7FFFFFFF
#define DT_NULL 0
#define DT_NEEDED 1
#define DT_PLTRELSZ 2
#define DT_PLTGOT 3
#define DT_HASH 4
#define DT_STRTAB 5
#define DT_SYMTAB 6
#define DT_RELA 7
#define DT_RELASZ 8
#define DT_RELAENT 9
#define DT_STRSZ 10
#define DT_SYMENT 11
#define DT_INIT 12
#define DT_FINI 13
#define DT_SONAME 14
#define DT_RPATH 15
#define DT_SYMBOLIC 16
#define DT_REL 17
#define DT_RELSZ 18
#define DT_RELENT 19
#define DT_PLTREL 20
#define DT_DEBUG 21
#define DT_TEXTREL 22
#define DT_JMPREL 23
#define DT_LOPROC 0x70000000
#define DT_HIPROC 0x7FFFFFFF
// ELF file header
struct Elf32_Ehdr
{
u8 e_ident[EI_NIDENT];
u16 e_type;
u16 e_machine;
u32 e_version;
u32 e_entry;
u32 e_phoff;
u32 e_shoff;
u32 e_flags;
u16 e_ehsize;
u16 e_phentsize;
u16 e_phnum;
u16 e_shentsize;
u16 e_shnum;
u16 e_shstrndx;
u8 e_ident[EI_NIDENT];
u16 e_type;
u16 e_machine;
u32 e_version;
u32 e_entry;
u32 e_phoff;
u32 e_shoff;
u32 e_flags;
u16 e_ehsize;
u16 e_phentsize;
u16 e_phnum;
u16 e_shentsize;
u16 e_shnum;
u16 e_shstrndx;
};
// Section header
@@ -237,14 +234,14 @@ struct Elf32_Sym
u32 st_name;
u32 st_value;
u32 st_size;
u8 st_info;
u8 st_other;
u8 st_info;
u8 st_other;
u16 st_shndx;
};
#define ELF32_ST_BIND(i) ((i)>>4)
#define ELF32_ST_TYPE(i) ((i)&0xf)
#define ELF32_ST_INFO(b,t) (((b)<<4)+((t)&0xf))
#define ELF32_ST_BIND(i) ((i) >> 4)
#define ELF32_ST_TYPE(i) ((i)&0xf)
#define ELF32_ST_INFO(b, t) (((b) << 4) + ((t)&0xf))
// Relocation entries
struct Elf32_Rel
@@ -260,16 +257,14 @@ struct Elf32_Rela
s32 r_addend;
};
#define ELF32_R_SYM(i) ((i)>>8)
#define ELF32_R_SYM(i) ((i) >> 8)
#define ELF32_R_TYPE(i) ((u8)(i))
#define ELF32_R_INFO(s,t) (((s)<<8 )+(u8)(t))
#define ELF32_R_INFO(s, t) (((s) << 8) + (u8)(t))
struct Elf32_Dyn
{
s32 d_tag;
union
{
union {
u32 d_val;
u32 d_ptr;
} d_un;

View File

@@ -11,52 +11,41 @@
#include "Common/FileUtil.h"
#include "Common/StringUtil.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h" // for bWii
#include "Core/Boot/Boot.h"
#include "Core/Boot/Boot_DOL.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h" // for bWii
#include "Core/FifoPlayer/FifoDataFile.h"
#include "Core/HW/SI.h"
#include "Core/PowerPC/PowerPC.h"
#include "DiscIO/Enums.h"
#include "DiscIO/NANDContentLoader.h"
#include "DiscIO/Volume.h"
#include "DiscIO/VolumeCreator.h"
SConfig* SConfig::m_Instance;
SConfig::SConfig()
: bEnableDebugging(false), bAutomaticStart(false), bBootToPause(false),
bJITNoBlockCache(false), bJITNoBlockLinking(false),
bJITOff(false),
bJITLoadStoreOff(false), bJITLoadStorelXzOff(false),
bJITLoadStorelwzOff(false), bJITLoadStorelbzxOff(false),
bJITLoadStoreFloatingOff(false), bJITLoadStorePairedOff(false),
bJITFloatingPointOff(false), bJITIntegerOff(false),
bJITPairedOff(false), bJITSystemRegistersOff(false),
bJITBranchOff(false),
bJITILTimeProfiling(false), bJITILOutputIR(false),
bFPRF(false), bAccurateNaNs(false), iTimingVariance(40),
bCPUThread(true), bDSPThread(false), bDSPHLE(true),
: bEnableDebugging(false), bAutomaticStart(false), bBootToPause(false), bJITNoBlockCache(false),
bJITNoBlockLinking(false), bJITOff(false), bJITLoadStoreOff(false),
bJITLoadStorelXzOff(false), bJITLoadStorelwzOff(false), bJITLoadStorelbzxOff(false),
bJITLoadStoreFloatingOff(false), bJITLoadStorePairedOff(false), bJITFloatingPointOff(false),
bJITIntegerOff(false), bJITPairedOff(false), bJITSystemRegistersOff(false),
bJITBranchOff(false), bJITILTimeProfiling(false), bJITILOutputIR(false), bFPRF(false),
bAccurateNaNs(false), iTimingVariance(40), bCPUThread(true), bDSPThread(false), bDSPHLE(true),
bSkipIdle(true), bSyncGPUOnSkipIdleHack(true), bNTSC(false), bForceNTSCJ(false),
bHLE_BS2(true), bEnableCheats(false),
bEnableMemcardSdWriting(true),
bDPL2Decoder(false), bTimeStretching(false), bRSHACK(false), bWiiSpeakSupport(false), iLatency(14),
bRunCompareServer(false), bRunCompareClient(false),
bMMU(false), bDCBZOFF(false),
iBBDumpPort(0), bDoubleVideoRate(false),
bFastDiscSpeed(false), bSyncGPU(false),
SelectedLanguage(0), bOverrideGCLanguage(false), bWii(false),
bConfirmStop(false), bHideCursor(false),
bHLE_BS2(true), bEnableCheats(false), bEnableMemcardSdWriting(true), bDPL2Decoder(false),
iLatency(14), bRunCompareServer(false), bRunCompareClient(false), bMMU(false),
bDCBZOFF(false), iBBDumpPort(0), bFastDiscSpeed(false), bSyncGPU(false), SelectedLanguage(0),
bOverrideGCLanguage(false), bWii(false), bConfirmStop(false), bHideCursor(false),
bTimeStretching(false), bRSHACK(false), bWiiSpeakSupport(false),
bAutoHideCursor(false), bUsePanicHandlers(true), bOnScreenDisplayMessages(true),
iRenderWindowXPos(-1), iRenderWindowYPos(-1),
iRenderWindowWidth(640), iRenderWindowHeight(480),
bRenderWindowAutoSize(false), bKeepWindowOnTop(false),
bFullscreen(false), bRenderToMain(false),
bProgressive(false), bPAL60(false),
bDisableScreenSaver(false),
iPosX(100), iPosY(100), iWidth(800), iHeight(600),
m_analytics_enabled(false), m_analytics_permission_asked(false),
bLoopFifoReplay(true)
iRenderWindowXPos(-1), iRenderWindowYPos(-1), iRenderWindowWidth(640),
iRenderWindowHeight(480), bRenderWindowAutoSize(false), bKeepWindowOnTop(false),
bFullscreen(false), bRenderToMain(false), bProgressive(false), bPAL60(false),
bDisableScreenSaver(false), iPosX(100), iPosY(100), iWidth(800), iHeight(600),
m_analytics_enabled(false), m_analytics_permission_asked(false), bLoopFifoReplay(true)
{
LoadDefaults();
// Make sure we have log manager
@@ -80,12 +69,11 @@ SConfig::~SConfig()
delete m_SYSCONF;
}
void SConfig::SaveSettings()
{
NOTICE_LOG(BOOT, "Saving settings to %s", File::GetUserPath(F_DOLPHINCONFIG_IDX).c_str());
IniFile ini;
ini.Load(File::GetUserPath(F_DOLPHINCONFIG_IDX)); // load first to not kill unknown stuff
ini.Load(File::GetUserPath(F_DOLPHINCONFIG_IDX)); // load first to not kill unknown stuff
SaveGeneralSettings(ini);
SaveInterfaceSettings(ini);
@@ -164,8 +152,8 @@ void SConfig::SaveInterfaceSettings(IniFile& ini)
interface->Set("OnScreenDisplayMessages", bOnScreenDisplayMessages);
interface->Set("HideCursor", bHideCursor);
interface->Set("AutoHideCursor", bAutoHideCursor);
interface->Set("MainWindowPosX", (iPosX == -32000) ? 0 : iPosX); // TODO - HAX
interface->Set("MainWindowPosY", (iPosY == -32000) ? 0 : iPosY); // TODO - HAX
interface->Set("MainWindowPosX", (iPosX == -32000) ? 0 : iPosX); // TODO - HAX
interface->Set("MainWindowPosY", (iPosY == -32000) ? 0 : iPosY); // TODO - HAX
interface->Set("MainWindowWidth", iWidth);
interface->Set("MainWindowHeight", iHeight);
interface->Set("Language", m_InterfaceLanguage);
@@ -415,6 +403,8 @@ void SConfig::LoadGeneralSettings(IniFile& ini)
general->Get("NANDRootPath", &m_NANDPath);
File::SetUserPath(D_WIIROOT_IDX, m_NANDPath);
general->Get("DumpPath", &m_DumpPath);
CreateDumpPath(m_DumpPath);
general->Get("WirelessMac", &m_WirelessMac);
}
@@ -542,7 +532,8 @@ void SConfig::LoadCoreSettings(IniFile& ini)
core->Get("OutputIR", &bJITILOutputIR, false);
for (int i = 0; i < MAX_SI_CHANNELS; ++i)
{
core->Get(StringFromFormat("SIDevice%i", i), (u32*)&m_SIDevice[i], (i == 0) ? SIDEVICE_GC_CONTROLLER : SIDEVICE_NONE);
core->Get(StringFromFormat("SIDevice%i", i), (u32*)&m_SIDevice[i],
(i == 0) ? SIDEVICE_GC_CONTROLLER : SIDEVICE_NONE);
core->Get(StringFromFormat("AdapterRumble%i", i), &m_AdapterRumble[i], true);
core->Get(StringFromFormat("SimulateKonga%i", i), &m_AdapterKonga[i], false);
}
@@ -679,7 +670,7 @@ void SConfig::LoadDefaults()
bLoopFifoReplay = true;
bJITOff = false; // debugger only settings
bJITOff = false; // debugger only settings
bJITLoadStoreOff = false;
bJITLoadStoreFloatingOff = false;
bJITLoadStorePairedOff = false;
@@ -693,31 +684,32 @@ void SConfig::LoadDefaults()
m_strUniqueID = "00000000";
m_revision = 0;
}
static const char* GetRegionOfCountry(DiscIO::IVolume::ECountry country)
static const char* GetRegionOfCountry(DiscIO::Country country)
{
switch (country)
{
case DiscIO::IVolume::COUNTRY_USA:
case DiscIO::Country::COUNTRY_USA:
return USA_DIR;
case DiscIO::IVolume::COUNTRY_TAIWAN:
case DiscIO::IVolume::COUNTRY_KOREA:
case DiscIO::Country::COUNTRY_TAIWAN:
case DiscIO::Country::COUNTRY_KOREA:
// TODO: Should these have their own Region Dir?
case DiscIO::IVolume::COUNTRY_JAPAN:
case DiscIO::Country::COUNTRY_JAPAN:
return JAP_DIR;
case DiscIO::IVolume::COUNTRY_AUSTRALIA:
case DiscIO::IVolume::COUNTRY_EUROPE:
case DiscIO::IVolume::COUNTRY_FRANCE:
case DiscIO::IVolume::COUNTRY_GERMANY:
case DiscIO::IVolume::COUNTRY_ITALY:
case DiscIO::IVolume::COUNTRY_NETHERLANDS:
case DiscIO::IVolume::COUNTRY_RUSSIA:
case DiscIO::IVolume::COUNTRY_SPAIN:
case DiscIO::IVolume::COUNTRY_WORLD:
case DiscIO::Country::COUNTRY_AUSTRALIA:
case DiscIO::Country::COUNTRY_EUROPE:
case DiscIO::Country::COUNTRY_FRANCE:
case DiscIO::Country::COUNTRY_GERMANY:
case DiscIO::Country::COUNTRY_ITALY:
case DiscIO::Country::COUNTRY_NETHERLANDS:
case DiscIO::Country::COUNTRY_RUSSIA:
case DiscIO::Country::COUNTRY_SPAIN:
case DiscIO::Country::COUNTRY_WORLD:
return EUR_DIR;
case DiscIO::IVolume::COUNTRY_UNKNOWN:
case DiscIO::Country::COUNTRY_UNKNOWN:
default:
return nullptr;
}
@@ -742,12 +734,9 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
std::string Extension;
SplitPath(m_strFilename, nullptr, nullptr, &Extension);
if (!strcasecmp(Extension.c_str(), ".gcm") ||
!strcasecmp(Extension.c_str(), ".iso") ||
!strcasecmp(Extension.c_str(), ".wbfs") ||
!strcasecmp(Extension.c_str(), ".ciso") ||
!strcasecmp(Extension.c_str(), ".gcz") ||
bootDrive)
if (!strcasecmp(Extension.c_str(), ".gcm") || !strcasecmp(Extension.c_str(), ".iso") ||
!strcasecmp(Extension.c_str(), ".wbfs") || !strcasecmp(Extension.c_str(), ".ciso") ||
!strcasecmp(Extension.c_str(), ".gcz") || bootDrive)
{
m_BootType = BOOT_ISO;
std::unique_ptr<DiscIO::IVolume> pVolume(DiscIO::CreateVolumeFromFilename(m_strFilename));
@@ -757,7 +746,8 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
PanicAlertT("Could not read \"%s\". "
"There is no disc in the drive, or it is not a GC/Wii backup. "
"Please note that original GameCube and Wii discs cannot be read "
"by most PC DVD drives.", m_strFilename.c_str());
"by most PC DVD drives.",
m_strFilename.c_str());
else
PanicAlertT("\"%s\" is an invalid GCM/ISO file, or is not a GC/Wii ISO.",
m_strFilename.c_str());
@@ -768,7 +758,7 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
m_revision = pVolume->GetRevision();
// Check if we have a Wii disc
bWii = pVolume->GetVolumeType() == DiscIO::IVolume::WII_DISC;
bWii = pVolume->GetVolumeType() == DiscIO::Platform::WII_DISC;
const char* retrieved_region_dir = GetRegionOfCountry(pVolume->GetCountry());
if (!retrieved_region_dir)
@@ -786,8 +776,10 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
{
bWii = CBoot::IsElfWii(m_strFilename);
// TODO: Right now GC homebrew boots in NTSC and Wii homebrew in PAL.
// This is intentional so that Wii homebrew can boot in both 50Hz and 60Hz, without forcing all GC homebrew to 50Hz.
// In the future, it probably makes sense to add a Region setting for homebrew somewhere in the emulator config.
// This is intentional so that Wii homebrew can boot in both 50Hz and 60Hz, without forcing
// all GC homebrew to 50Hz.
// In the future, it probably makes sense to add a Region setting for homebrew somewhere in
// the emulator config.
bNTSC = bWii ? false : true;
set_region_dir = bNTSC ? USA_DIR : EUR_DIR;
m_BootType = BOOT_ELF;
@@ -818,15 +810,16 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
else if (DiscIO::CNANDContentManager::Access().GetNANDLoader(m_strFilename).IsValid())
{
std::unique_ptr<DiscIO::IVolume> pVolume(DiscIO::CreateVolumeFromFilename(m_strFilename));
const DiscIO::CNANDContentLoader& ContentLoader = DiscIO::CNANDContentManager::Access().GetNANDLoader(m_strFilename);
const DiscIO::CNANDContentLoader& ContentLoader =
DiscIO::CNANDContentManager::Access().GetNANDLoader(m_strFilename);
if (ContentLoader.GetContentByIndex(ContentLoader.GetBootIndex()) == nullptr)
{
//WAD is valid yet cannot be booted. Install instead.
// WAD is valid yet cannot be booted. Install instead.
u64 installed = DiscIO::CNANDContentManager::Access().Install_WiiWAD(m_strFilename);
if (installed)
SuccessAlertT("The WAD has been installed successfully");
return false; //do not boot
return false; // do not boot
}
const char* retrieved_region_dir = GetRegionOfCountry(ContentLoader.GetCountry());
@@ -850,7 +843,8 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
}
// Use the TitleIDhex for name and/or unique ID if launching from nand folder
// or if it is not ascii characters (specifically sysmenu could potentially apply to other things)
// or if it is not ascii characters (specifically sysmenu could potentially apply to other
// things)
std::string titleidstr = StringFromFormat("%016" PRIx64, ContentLoader.GetTitleID());
if (m_strName.empty())
@@ -899,7 +893,8 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
{
m_strBootROM = File::GetUserPath(D_GCUSER_IDX) + DIR_SEP + set_region_dir + DIR_SEP GC_IPL;
if (!File::Exists(m_strBootROM))
m_strBootROM = File::GetSysDirectory() + GC_SYS_DIR + DIR_SEP + set_region_dir + DIR_SEP GC_IPL;
m_strBootROM =
File::GetSysDirectory() + GC_SYS_DIR + DIR_SEP + set_region_dir + DIR_SEP GC_IPL;
if (!File::Exists(m_strBootROM))
{
@@ -917,7 +912,8 @@ bool SConfig::AutoSetup(EBootBS2 _BootBS2)
return true;
}
void SConfig::CheckMemcardPath(std::string& memcardPath, const std::string& gameRegion, bool isSlotA)
void SConfig::CheckMemcardPath(std::string& memcardPath, const std::string& gameRegion,
bool isSlotA)
{
std::string ext("." + gameRegion + ".raw");
if (memcardPath.empty())
@@ -953,7 +949,7 @@ void SConfig::CheckMemcardPath(std::string& memcardPath, const std::string& game
PanicAlertT("Copy failed");
}
}
memcardPath = filename; // Always correct the path!
memcardPath = filename; // Always correct the path!
}
else if (region.compare(gameRegion) != 0)
{
@@ -964,17 +960,19 @@ void SConfig::CheckMemcardPath(std::string& memcardPath, const std::string& game
}
}
DiscIO::IVolume::ELanguage SConfig::GetCurrentLanguage(bool wii) const
DiscIO::Language SConfig::GetCurrentLanguage(bool wii) const
{
DiscIO::IVolume::ELanguage language;
int language_value;
if (wii)
language = (DiscIO::IVolume::ELanguage)SConfig::GetInstance().m_SYSCONF->GetData<u8>("IPL.LNG");
language_value = SConfig::GetInstance().m_SYSCONF->GetData<u8>("IPL.LNG");
else
language = (DiscIO::IVolume::ELanguage)(SConfig::GetInstance().SelectedLanguage + 1);
language_value = SConfig::GetInstance().SelectedLanguage + 1;
DiscIO::Language language = static_cast<DiscIO::Language>(language_value);
// Get rid of invalid values (probably doesn't matter, but might as well do it)
if (language > DiscIO::IVolume::ELanguage::LANGUAGE_UNKNOWN || language < 0)
language = DiscIO::IVolume::ELanguage::LANGUAGE_UNKNOWN;
if (language > DiscIO::Language::LANGUAGE_UNKNOWN ||
language < DiscIO::Language::LANGUAGE_JAPANESE)
language = DiscIO::Language::LANGUAGE_UNKNOWN;
return language;
}

View File

@@ -12,7 +12,11 @@
#include "Common/SysConf.h"
#include "Core/HW/EXI_Device.h"
#include "Core/HW/SI_Device.h"
#include "DiscIO/Volume.h"
namespace DiscIO
{
enum class Language;
}
// DSP Backend Types
#define BACKEND_NULLSOUND _trans("No audio output")
@@ -34,7 +38,7 @@ enum GPUDeterminismMode
GPU_DETERMINISM_FAKE_COMPLETION,
};
struct SConfig: NonCopyable
struct SConfig : NonCopyable
{
// Wii Devices
bool m_WiiSDCard;
@@ -80,7 +84,7 @@ struct SConfig: NonCopyable
bool bFPRF;
bool bAccurateNaNs;
int iTimingVariance; // in milli secounds
int iTimingVariance; // in milli secounds
bool bCPUThread;
bool bDSPThread;
bool bDSPHLE;
@@ -180,12 +184,9 @@ struct SConfig: NonCopyable
void LoadDefaults();
bool AutoSetup(EBootBS2 _BootBS2);
const std::string &GetUniqueID() const
{
return m_strUniqueID;
}
const std::string& GetUniqueID() const { return m_strUniqueID; }
void CheckMemcardPath(std::string& memcardPath, const std::string& gameRegion, bool isSlotA);
DiscIO::IVolume::ELanguage GetCurrentLanguage(bool wii) const;
DiscIO::Language GetCurrentLanguage(bool wii) const;
IniFile LoadDefaultGameIni() const;
IniFile LoadLocalGameIni() const;
@@ -290,11 +291,7 @@ struct SConfig: NonCopyable
void LoadSettings();
// Return the permanent and somewhat globally used instance of this struct
static SConfig& GetInstance()
{
return(*m_Instance);
}
static SConfig& GetInstance() { return (*m_Instance); }
static void Init();
static void Shutdown();

View File

@@ -15,15 +15,15 @@
#include "AudioCommon/AudioCommon.h"
#include "Common/CPUDetect.h"
#include "Common/CommonPaths.h"
#include "Common/CommonTypes.h"
#include "Common/CPUDetect.h"
#include "Common/Logging/LogManager.h"
#include "Common/MathUtil.h"
#include "Common/MemoryUtil.h"
#include "Common/StringUtil.h"
#include "Common/Thread.h"
#include "Common/Timer.h"
#include "Common/Logging/LogManager.h"
#include "Core/Analytics.h"
#include "Core/ConfigManager.h"
@@ -35,11 +35,6 @@
#ifdef USE_MEMORYWATCHER
#include "Core/MemoryWatcher.h"
#endif
#include "Core/Movie.h"
#include "Core/NetPlayClient.h"
#include "Core/NetPlayProto.h"
#include "Core/PatchEngine.h"
#include "Core/State.h"
#include "Core/Boot/Boot.h"
#include "Core/FifoPlayer/FifoPlayer.h"
#include "Core/HW/AudioInterface.h"
@@ -58,35 +53,35 @@
#include "Core/IPC_HLE/WII_IPC_HLE_Device_usb.h"
#include "Core/IPC_HLE/WII_IPC_HLE_WiiMote.h"
#include "Core/IPC_HLE/WII_Socket.h"
#include "Core/Movie.h"
#include "Core/NetPlayClient.h"
#include "Core/NetPlayProto.h"
#include "Core/PatchEngine.h"
#include "Core/PowerPC/JitInterface.h"
#include "Core/PowerPC/PowerPC.h"
#include "Core/State.h"
#ifdef USE_GDBSTUB
#include "Core/PowerPC/GDBStub.h"
#endif
#include "DiscIO/FileMonitor.h"
#include "InputCommon/GCAdapter.h"
#include "InputCommon/ControllerInterface/ControllerInterface.h"
#include "InputCommon/GCAdapter.h"
#include "VideoCommon/Fifo.h"
#include "VideoCommon/OnScreenDisplay.h"
#include "VideoCommon/RenderBase.h"
#include "VideoCommon/VideoBackendBase.h"
// This can mostly be removed when we move to VS2015
// to use the thread_local keyword
#ifdef _MSC_VER
#define ThreadLocalStorage __declspec(thread)
#elif defined __ANDROID__ || defined __APPLE__
// This will most likely have to stay, to support android
// Android and OSX haven't implemented the keyword yet.
#if defined __ANDROID__ || defined __APPLE__
#include <pthread.h>
#else // Everything besides VS and Android
#define ThreadLocalStorage __thread
#else // Everything besides OSX and Android
#define ThreadLocalStorage thread_local
#endif
namespace Core
{
// TODO: ugly, remove
bool g_aspect_wide;
@@ -106,7 +101,7 @@ void EmuThread();
static bool s_is_stopping = false;
static bool s_hardware_initialized = false;
static bool s_is_started = false;
static std::atomic<bool> s_is_booting{false};
static std::atomic<bool> s_is_booting{ false };
static void* s_window_handle = nullptr;
static std::string s_state_filename;
static std::thread s_emu_thread;
@@ -122,7 +117,7 @@ struct HostJob
std::function<void()> job;
bool run_after_stop;
};
static std::mutex s_host_jobs_lock;
static std::mutex s_host_jobs_lock;
static std::queue<HostJob> s_host_jobs_queue;
#ifdef ThreadLocalStorage
@@ -166,8 +161,8 @@ void FrameUpdateOnCPUThread()
// Formatted stop message
std::string StopMessage(bool main_thread, const std::string& message)
{
return StringFromFormat("Stop [%s %i]\t%s\t%s",
main_thread ? "Main Thread" : "Video Thread", Common::CurrentThreadId(), MemUsage().c_str(), message.c_str());
return StringFromFormat("Stop [%s %i]\t%s\t%s", main_thread ? "Main Thread" : "Video Thread",
Common::CurrentThreadId(), MemUsage().c_str(), message.c_str());
}
void DisplayMessage(const std::string& message, int time_in_ms)
@@ -249,19 +244,17 @@ bool Init()
Core::UpdateWantDeterminism(/*initial*/ true);
INFO_LOG(OSREPORT, "Starting core = %s mode",
_CoreParameter.bWii ? "Wii" : "GameCube");
INFO_LOG(OSREPORT, "CPU Thread separate = %s",
_CoreParameter.bCPUThread ? "Yes" : "No");
INFO_LOG(OSREPORT, "Starting core = %s mode", _CoreParameter.bWii ? "Wii" : "GameCube");
INFO_LOG(OSREPORT, "CPU Thread separate = %s", _CoreParameter.bCPUThread ? "Yes" : "No");
Host_UpdateMainFrame(); // Disable any menus or buttons at boot
Host_UpdateMainFrame(); // Disable any menus or buttons at boot
g_aspect_wide = _CoreParameter.bWii;
if (g_aspect_wide)
{
IniFile gameIni = _CoreParameter.LoadGameIni();
gameIni.GetOrCreateSection("Wii")->Get("Widescreen", &g_aspect_wide,
!!SConfig::GetInstance().m_SYSCONF->GetData<u8>("IPL.AR"));
gameIni.GetOrCreateSection("Wii")->Get(
"Widescreen", &g_aspect_wide, !!SConfig::GetInstance().m_SYSCONF->GetData<u8>("IPL.AR"));
}
s_window_handle = Host_GetRenderHandle();
@@ -338,8 +331,7 @@ void UndeclareAsCPUThread()
// For the CPU Thread only.
static void CPUSetInitialExecutionState()
{
QueueHostJob([]
{
QueueHostJob([] {
SetState(SConfig::GetInstance().bBootToPause ? CORE_PAUSE : CORE_RUN);
Host_UpdateMainFrame();
});
@@ -367,15 +359,14 @@ static void CpuThread()
DolphinAnalytics::Instance()->ReportGameStart();
if (_CoreParameter.bFastmem)
EMM::InstallExceptionHandler(); // Let's run under memory watch
EMM::InstallExceptionHandler(); // Let's run under memory watch
if (!s_state_filename.empty())
{
// Needs to PauseAndLock the Core
// NOTE: EmuThread should have left us in CPU_STEPPING so nothing will happen
// until after the job is serviced.
QueueHostJob([]
{
QueueHostJob([] {
// Recheck in case Movie cleared it since.
if (!s_state_filename.empty())
State::LoadAs(s_state_filename);
@@ -496,7 +487,7 @@ void EmuThread()
HW::Init();
if (!g_video_backend->Initialize(s_window_handle))
if (!video_backend->Initialize(s_window_handle))
{
s_is_booting.store(false);
PanicAlert("Failed to initialize video backend!");
@@ -539,7 +530,9 @@ void EmuThread()
if (core_parameter.bWii)
{
if (init_controllers)
Wiimote::Initialize(s_window_handle, !s_state_filename.empty());
Wiimote::Initialize(s_window_handle, !s_state_filename.empty() ?
Wiimote::InitializeMode::DO_WAIT_FOR_WIIMOTES :
Wiimote::InitializeMode::DO_NOT_WAIT_FOR_WIIMOTES);
else
Wiimote::LoadConfig();
@@ -547,7 +540,6 @@ void EmuThread()
for (unsigned int i = 0; i != MAX_BBMOTES; ++i)
if (g_wiimote_sources[i])
GetUsbPointer()->AccessWiiMote(i | 0x100)->Activate(true);
}
AudioCommon::InitSoundStream(s_window_handle);
@@ -571,8 +563,8 @@ void EmuThread()
UndeclareAsCPUThread();
// Setup our core, but can't use dynarec if we are compare server
if (core_parameter.iCPUCore != PowerPC::CORE_INTERPRETER
&& (!core_parameter.bRunCompareServer || core_parameter.bRunCompareClient))
if (core_parameter.iCPUCore != PowerPC::CORE_INTERPRETER &&
(!core_parameter.bRunCompareServer || core_parameter.bRunCompareClient))
{
PowerPC::SetMode(PowerPC::MODE_JIT);
}
@@ -610,7 +602,7 @@ void EmuThread()
// We have now exited the Video Loop
INFO_LOG(CONSOLE, "%s", StopMessage(false, "Video Loop Ended").c_str());
}
else // SingleCore mode
else // SingleCore mode
{
// The spawned CPU Thread also does the graphics.
// The EmuThread is thus an idle thread, which sleeps while
@@ -752,7 +744,7 @@ static std::string GenerateScreenshotName()
{
std::string path = GenerateScreenshotFolderPath();
//append gameId, path only contains the folder here.
// append gameId, path only contains the folder here.
path += SConfig::GetInstance().GetUniqueID();
std::string name;
@@ -820,7 +812,8 @@ bool PauseAndLock(bool do_lock, bool unpause_on_unlock)
// audio has to come after CPU, because CPU thread can wait for audio thread (m_throttle).
DSP::GetDSPEmulator()->PauseAndLock(do_lock, false);
// video has to come after CPU, because CPU thread can wait for video thread (s_efbAccessRequested).
// video has to come after CPU, because CPU thread can wait for video thread
// (s_efbAccessRequested).
Fifo::PauseAndLock(do_lock, false);
#if defined(__LIBUSB__) || defined(_WIN32)
@@ -907,25 +900,32 @@ void UpdateTitle()
float FPS = (float)(s_drawn_frame.load() * 1000.0 / ElapseTime);
float VPS = (float)(s_drawn_video.load() * 1000.0 / ElapseTime);
float Speed = (float)(s_drawn_video.load() * (100 * 1000.0) / (VideoInterface::GetTargetRefreshRate() * ElapseTime));
float Speed = (float)(s_drawn_video.load() * (100 * 1000.0) /
(VideoInterface::GetTargetRefreshRate() * ElapseTime));
// Settings are shown the same for both extended and summary info
std::string SSettings = StringFromFormat("%s %s | %s | %s", PowerPC::GetCPUName(), _CoreParameter.bCPUThread ? "DC" : "SC",
std::string SSettings = StringFromFormat(
"%s %s | %s | %s", PowerPC::GetCPUName(), _CoreParameter.bCPUThread ? "DC" : "SC",
g_video_backend->GetDisplayName().c_str(), _CoreParameter.bDSPHLE ? "HLE" : "LLE");
std::string SFPS;
if (Movie::IsPlayingInput())
SFPS = StringFromFormat("VI: %u/%u - Input: %u/%u - FPS: %.0f - VPS: %.0f - %.0f%%", (u32)Movie::g_currentFrame, (u32)Movie::g_totalFrames, (u32)Movie::g_currentInputCount, (u32)Movie::g_totalInputCount, FPS, VPS, Speed);
SFPS = StringFromFormat("Input: %u/%u - VI: %u - FPS: %.0f - VPS: %.0f - %.0f%%",
(u32)Movie::g_currentInputCount, (u32)Movie::g_totalInputCount,
(u32)Movie::g_currentFrame, FPS, VPS, Speed);
else if (Movie::IsRecordingInput())
SFPS = StringFromFormat("VI: %u - Input: %u - FPS: %.0f - VPS: %.0f - %.0f%%", (u32)Movie::g_currentFrame, (u32)Movie::g_currentInputCount, FPS, VPS, Speed);
SFPS = StringFromFormat("Input: %u - VI: %u - FPS: %.0f - VPS: %.0f - %.0f%%",
(u32)Movie::g_currentInputCount, (u32)Movie::g_currentFrame, FPS, VPS,
Speed);
else
{
SFPS = StringFromFormat("FPS: %.0f - VPS: %.0f - %.0f%%", FPS, VPS, Speed);
if (SConfig::GetInstance().m_InterfaceExtendedFPSInfo)
{
// Use extended or summary information. The summary information does not print the ticks data,
// that's more of a debugging interest, it can always be optional of course if someone is interested.
// that's more of a debugging interest, it can always be optional of course if someone is
// interested.
static u64 ticks = 0;
static u64 idleTicks = 0;
u64 newTicks = CoreTiming::GetTicks();
@@ -937,16 +937,14 @@ void UpdateTitle()
ticks = newTicks;
idleTicks = newIdleTicks;
float TicksPercentage = (float)diff / (float)(SystemTimers::GetTicksPerSecond() / 1000000) * 100;
float TicksPercentage =
(float)diff / (float)(SystemTimers::GetTicksPerSecond() / 1000000) * 100;
SFPS += StringFromFormat(" | CPU: %s%i MHz [Real: %i + IdleSkip: %i] / %i MHz (%s%3.0f%%)",
_CoreParameter.bSkipIdle ? "~" : "",
(int)(diff),
(int)(diff - idleDiff),
(int)(idleDiff),
SystemTimers::GetTicksPerSecond() / 1000000,
_CoreParameter.bSkipIdle ? "~" : "",
TicksPercentage);
SFPS +=
StringFromFormat(" | CPU: %s%i MHz [Real: %i + IdleSkip: %i] / %i MHz (%s%3.0f%%)",
_CoreParameter.bSkipIdle ? "~" : "", (int)(diff), (int)(diff - idleDiff),
(int)(idleDiff), SystemTimers::GetTicksPerSecond() / 1000000,
_CoreParameter.bSkipIdle ? "~" : "", TicksPercentage);
}
}
// This is our final "frame counter" string
@@ -979,10 +977,7 @@ void UpdateWantDeterminism(bool initial)
// For now, this value is not itself configurable. Instead, individual
// settings that depend on it, such as GPU determinism mode. should have
// override options for testing,
bool new_want_determinism =
Movie::IsPlayingInput() ||
Movie::IsRecordingInput() ||
NetPlay::IsNetPlayRunning();
bool new_want_determinism = Movie::IsMovieActive() || NetPlay::IsNetPlayRunning();
if (new_want_determinism != g_want_determinism || initial)
{
WARN_LOG(COMMON, "Want determinism <- %s", new_want_determinism ? "true" : "false");
@@ -992,7 +987,8 @@ void UpdateWantDeterminism(bool initial)
g_want_determinism = new_want_determinism;
WiiSockMan::GetInstance().UpdateWantDeterminism(new_want_determinism);
Fifo::UpdateWantDeterminism(new_want_determinism);
// We need to clear the cache because some parts of the JIT depend on want_determinism, e.g. use of FMA.
// We need to clear the cache because some parts of the JIT depend on want_determinism, e.g. use
// of FMA.
JitInterface::ClearCache();
Common::InitializeWiiRoot(g_want_determinism);
@@ -1009,7 +1005,7 @@ void QueueHostJob(std::function<void()> job, bool run_during_stop)
{
std::lock_guard<std::mutex> guard(s_host_jobs_lock);
send_message = s_host_jobs_queue.empty();
s_host_jobs_queue.emplace(HostJob{std::move(job), run_during_stop});
s_host_jobs_queue.emplace(HostJob{ std::move(job), run_during_stop });
}
// If the the queue was empty then kick the Host to come and get this job.
if (send_message)
@@ -1041,4 +1037,4 @@ void HostDispatchJobs()
}
}
} // Core
} // Core

View File

@@ -27,31 +27,31 @@ const u16 idle_skip_sigs[NUM_IDLE_SIGS][MAX_IDLE_SIG_SIZE + 1] =
{
// From AX:
{ 0x26fc, // LRS $30, @DMBH
0x02c0, 0x8000, // ANDCF $30, #0x8000
0x029d, 0xFFFF, // JLZ 0x027a
0, 0 }, // RET
0x02c0, 0x8000, // ANDCF $30, #0x8000
0x029d, 0xFFFF, // JLZ 0x027a
0, 0 }, // RET
{ 0x27fc, // LRS $31, @DMBH
0x03c0, 0x8000, // ANDCF $31, #0x8000
0x029d, 0xFFFF, // JLZ 0x027a
0, 0 }, // RET
0x03c0, 0x8000, // ANDCF $31, #0x8000
0x029d, 0xFFFF, // JLZ 0x027a
0, 0 }, // RET
{ 0x26fe, // LRS $30, @CMBH
0x02c0, 0x8000, // ANDCF $30, #0x8000
0x029c, 0xFFFF, // JLNZ 0x0280
0, 0 }, // RET
0x02c0, 0x8000, // ANDCF $30, #0x8000
0x029c, 0xFFFF, // JLNZ 0x0280
0, 0 }, // RET
{ 0x27fe, // LRS $31, @CMBH
0x03c0, 0x8000, // ANDCF $31, #0x8000
0x029c, 0xFFFF, // JLNZ 0x0280
0, 0 }, // RET
0x03c0, 0x8000, // ANDCF $31, #0x8000
0x029c, 0xFFFF, // JLNZ 0x0280
0, 0 }, // RET
{ 0x26fc, // LRS $AC0.M, @DMBH
0x02a0, 0x8000, // ANDF $AC0.M, #0x8000
0x029c, 0xFFFF, // JLNZ 0x????
0, 0 },
0x02a0, 0x8000, // ANDF $AC0.M, #0x8000
0x029c, 0xFFFF, // JLNZ 0x????
0, 0 },
{ 0x27fc, // LRS $AC1.M, @DMBH
0x03a0, 0x8000, // ANDF $AC1.M, #0x8000
0x029c, 0xFFFF, // JLNZ 0x????
0, 0 },
// From Zelda:
{ 0x00de, 0xFFFE, // LR $AC0.M, @CMBH
0x03a0, 0x8000, // ANDF $AC1.M, #0x8000
0x029c, 0xFFFF, // JLNZ 0x????
0, 0 },
// From Zelda:
{ 0x00de, 0xFFFE, // LR $AC0.M, @CMBH
0x02c0, 0x8000, // ANDCF $AC0.M, #0x8000
0x029c, 0xFFFF, // JLNZ 0x05cf
0 },

View File

@@ -45,7 +45,7 @@ static const char *err_string[] =
"Number out of range"
};
DSPAssembler::DSPAssembler(const AssemblerSettings &settings):
DSPAssembler::DSPAssembler(const AssemblerSettings &settings) :
gdg_buffer(nullptr),
m_cur_addr(0),
m_cur_pass(0),
@@ -763,7 +763,7 @@ bool DSPAssembler::AssembleFile(const char *fname, int pass)
m_cur_pass = pass;
#define LINEBUF_SIZE 1024
char line[LINEBUF_SIZE] = {0};
char line[LINEBUF_SIZE] = { 0 };
while (!failed && !fsrc.fail() && !fsrc.eof())
{
int opcode_size = 0;
@@ -775,8 +775,8 @@ bool DSPAssembler::AssembleFile(const char *fname, int pass)
//printf("A: %s\n", line);
code_line++;
param_t params[10] = {{0, P_NONE, nullptr}};
param_t params_ext[10] = {{0, P_NONE, nullptr}};
param_t params[10] = { {0, P_NONE, nullptr} };
param_t params_ext[10] = { {0, P_NONE, nullptr} };
bool upper = true;
for (int i = 0; i < LINEBUF_SIZE; i++)

View File

@@ -42,7 +42,7 @@ public:
// default implementation used by the DSP emulator.
//
// Can also be inherited from if you want to only override part of the methods.
class DefaultDSPCaptureLogger: public DSPCaptureLogger
class DefaultDSPCaptureLogger : public DSPCaptureLogger
{
public:
void LogIFXRead(u16 address, u16 read_value) override
@@ -56,7 +56,7 @@ public:
// A capture logger implementation that logs to PCAP files in a custom
// packet-based format.
class PCAPDSPCaptureLogger final: public DSPCaptureLogger, NonCopyable
class PCAPDSPCaptureLogger final : public DSPCaptureLogger, NonCopyable
{
public:
// Automatically creates a writeable file (truncate existing file).

View File

@@ -40,7 +40,7 @@ static bool VerifyRoms()
u32 hash_drom; // dsp_coef.bin
};
static const std::array<DspRomHashes, 4> known_roms = {{
static const std::array<DspRomHashes, 4> known_roms = { {
// Official Nintendo ROM
{ 0x66f334fe, 0xf3b93527 },
@@ -53,7 +53,7 @@ static bool VerifyRoms()
// above with improved resampling coefficients
{ 0xd9907f71, 0xdb6880c1 }
}};
} };
u32 hash_irom = HashAdler32((u8*)g_dsp.irom, DSP_IROM_BYTE_SIZE);
u32 hash_drom = HashAdler32((u8*)g_dsp.coef, DSP_COEF_BYTE_SIZE);

View File

@@ -14,46 +14,46 @@
#include "Core/DSP/DSPCaptureLogger.h"
#include "Core/DSP/DSPEmitter.h"
enum: u32
enum : u32
{
DSP_IRAM_BYTE_SIZE = 0x2000,
DSP_IRAM_SIZE = 0x1000,
DSP_IRAM_MASK = 0x0fff
};
enum: u32
enum : u32
{
DSP_IROM_BYTE_SIZE = 0x2000,
DSP_IROM_SIZE = 0x1000,
DSP_IROM_MASK = 0x0fff
};
enum: u32
enum : u32
{
DSP_DRAM_BYTE_SIZE = 0x2000,
DSP_DRAM_SIZE = 0x1000,
DSP_DRAM_MASK = 0x0fff
};
enum: u32
enum : u32
{
DSP_COEF_BYTE_SIZE = 0x1000,
DSP_COEF_SIZE = 0x800,
DSP_COEF_MASK = 0x7ff
};
enum: u16
enum : u16
{
DSP_RESET_VECTOR = 0x8000
};
enum: u8
enum : u8
{
DSP_STACK_DEPTH = 0x20,
DSP_STACK_MASK = 0x1f
};
enum: u32
enum : u32
{
DSP_CR_IMEM = 2,
DSP_CR_DMEM = 0,
@@ -62,7 +62,7 @@ enum: u32
};
// Register table taken from libasnd
enum: int
enum : int
{
// Address registers
DSP_REG_AR0 = 0x00,
@@ -116,7 +116,7 @@ enum: int
};
// Hardware registers address
enum: u32
enum : u32
{
DSP_COEF_A1_0 = 0xa0,
@@ -152,7 +152,7 @@ enum: u32
};
// Stacks
enum: int
enum : int
{
DSP_STACK_C,
DSP_STACK_D
@@ -160,7 +160,7 @@ enum: int
// cr (Not g_dsp.r[CR]) bits
// See HW/DSP.cpp.
enum: u32
enum : u32
{
CR_EXTERNAL_INT = 0x0002,
CR_HALT = 0x0004,
@@ -168,7 +168,7 @@ enum: u32
};
// SR bits
enum: u16
enum : u16
{
SR_CARRY = 0x0001,
SR_OVERFLOW = 0x0002,
@@ -192,7 +192,7 @@ enum: u16
};
// Exception vectors
enum: int
enum : int
{
EXP_STOVF = 1, // 0x0002 stack under/over flow
EXP_2 = 2, // 0x0004

View File

@@ -189,7 +189,7 @@ bool DSPDisassembler::DisassembleOpcode(const u16 *binbuf, int base_addr, int pa
break;
}
}
const DSPOPCTemplate fake_op = {"CW", 0x0000, 0x0000, nop, nullptr, 1, 1, {{P_VAL, 2, 0, 0, 0xffff}}, false, false, false, false, false};
const DSPOPCTemplate fake_op = { "CW", 0x0000, 0x0000, nop, nullptr, 1, 1, {{P_VAL, 2, 0, 0, 0xffff}}, false, false, false, false, false };
if (!opc)
opc = &fake_op;

View File

@@ -16,7 +16,7 @@
using namespace Gen;
DSPEmitter::DSPEmitter(): gpr(*this), storeIndex(-1), storeIndex2(-1)
DSPEmitter::DSPEmitter() : gpr(*this), storeIndex(-1), storeIndex2(-1)
{
m_compiledCode = nullptr;

View File

@@ -18,7 +18,7 @@
typedef u32(*DSPCompiledCode)();
typedef const u8 *Block;
class DSPEmitter: public Gen::X64CodeBlock
class DSPEmitter : public Gen::X64CodeBlock
{
public:
DSPEmitter();

View File

@@ -292,7 +292,7 @@ const DSPOPCTemplate opcodes[] =
};
const DSPOPCTemplate cw =
{"CW", 0x0000, 0x0000, nop, nullptr, 1, 1, {{P_VAL, 2, 0, 0, 0xffff}}, false, false, false, false, false};
{ "CW", 0x0000, 0x0000, nop, nullptr, 1, 1, {{P_VAL, 2, 0, 0, 0xffff}}, false, false, false, false, false };
// extended opcodes

View File

@@ -12,9 +12,9 @@ using namespace Gen;
// Ordered in order of prefered use.
// Not all of these are actually available
const std::array<X64Reg, 15> DSPJitRegCache::m_allocation_order = {{
const std::array<X64Reg, 15> DSPJitRegCache::m_allocation_order = { {
R8, R9, R10, R11, R12, R13, R14, R15, RSI, RDI, RBX, RCX, RDX, RAX, RBP
}};
} };
static void* GetRegisterPointer(size_t reg)
{
@@ -233,8 +233,7 @@ void DSPJitRegCache::FlushRegs(DSPJitRegCache &cache, bool emit)
movcnt++;
}
}
}
while (movcnt != 0);
} while (movcnt != 0);
// free all host regs that are not used for the same guest reg
for (size_t i = 0; i < regs.size(); i++)

View File

@@ -49,9 +49,9 @@ public:
//this does not modify the final state of gpr
<code using gpr>
FixupBranch b = JCC();
DSPJitRegCache c = gpr;
<code using c>
gpr.FlushRegs(c);
DSPJitRegCache c = gpr;
<code using c>
gpr.FlushRegs(c);
SetBranchTarget(b);
<code using gpr>
@@ -59,12 +59,12 @@ public:
<code using gpr>
DSPJitRegCache c = gpr;
FixupBranch b1 = JCC();
<code using gpr>
gpr.FlushRegs(c);
FixupBranch b2 = JMP();
<code using gpr>
gpr.FlushRegs(c);
FixupBranch b2 = JMP();
SetBranchTarget(b1);
<code using gpr>
gpr.FlushRegs(c);
<code using gpr>
gpr.FlushRegs(c);
SetBranchTarget(b2);
<code using gpr>
@@ -73,21 +73,21 @@ public:
<code using gpr>
DSPJitRegCache c = gpr;
FixupBranch b1 = JCC();
<code using c>
FixupBranch b2 = JMP();
<code using c>
FixupBranch b2 = JMP();
SetBranchTarget(b1);
<code using gpr>
gpr.FlushRegs(c);
<code using gpr>
gpr.FlushRegs(c);
SetBranchTarget(b2);
<code using gpr>
//this does not modify the final state of gpr
<code using gpr>
u8* b = GetCodePtr();
DSPJitRegCache c = gpr;
<code using gpr>
gpr.FlushRegs(c);
JCC(b);
DSPJitRegCache c = gpr;
<code using gpr>
gpr.FlushRegs(c);
JCC(b);
<code using gpr>
this all is not needed when gpr would not be used at all in the
@@ -144,7 +144,7 @@ private:
int last_use_ctr;
int parentReg;
int shift; // Current shift if parentReg == DSP_REG_NONE
// otherwise the shift this part can be found at
// otherwise the shift this part can be found at
Gen::X64Reg host_reg;
// TODO:

View File

@@ -21,7 +21,7 @@ class LabelMap
{
struct label_t
{
label_t(const std::string &lbl, s32 address, LabelType ltype): name(lbl), addr(address), type(ltype)
label_t(const std::string &lbl, s32 address, LabelType ltype) : name(lbl), addr(address), type(ltype)
{}
std::string name;
s32 addr;

View File

@@ -10,7 +10,7 @@
#include "Core/Debugger/Dump.h"
CDump::CDump(const std::string& filename):
CDump::CDump(const std::string& filename) :
m_pData(nullptr)
{
File::IOFile pStream(filename, "rb");

View File

@@ -109,4 +109,4 @@ struct Rela_Header
signed int addend;
};
const char ELFID[4] = {0x7F, 'E', 'L', 'F'};
const char ELFID[4] = { 0x7F, 'E', 'L', 'F' };

View File

@@ -10,7 +10,7 @@
//wrapper between disasm control and Dolphin debugger
class PPCDebugInterface final: public DebugInterface
class PPCDebugInterface final : public DebugInterface
{
public:
PPCDebugInterface()

View File

@@ -199,18 +199,24 @@ void CalculateVertexElementSizes(int sizes[], int vatIndex, const CPMemory& cpMe
const VAT& vtxAttr = cpMem.vtxAttr[vatIndex];
// Colors
const u64 colDesc[2] = {vtxDesc.Color0, vtxDesc.Color1};
const u32 colComp[2] = {vtxAttr.g0.Color0Comp, vtxAttr.g0.Color1Comp};
const u64 colDesc[2] = { vtxDesc.Color0, vtxDesc.Color1 };
const u32 colComp[2] = { vtxAttr.g0.Color0Comp, vtxAttr.g0.Color1Comp };
const u32 tcElements[8] = {vtxAttr.g0.Tex0CoordElements, vtxAttr.g1.Tex1CoordElements,
vtxAttr.g1.Tex2CoordElements, vtxAttr.g1.Tex3CoordElements,
vtxAttr.g1.Tex4CoordElements, vtxAttr.g2.Tex5CoordElements,
vtxAttr.g2.Tex6CoordElements, vtxAttr.g2.Tex7CoordElements};
const u32 tcElements[8] =
{
vtxAttr.g0.Tex0CoordElements, vtxAttr.g1.Tex1CoordElements,
vtxAttr.g1.Tex2CoordElements, vtxAttr.g1.Tex3CoordElements,
vtxAttr.g1.Tex4CoordElements, vtxAttr.g2.Tex5CoordElements,
vtxAttr.g2.Tex6CoordElements, vtxAttr.g2.Tex7CoordElements
};
const u32 tcFormat[8] = {vtxAttr.g0.Tex0CoordFormat, vtxAttr.g1.Tex1CoordFormat,
vtxAttr.g1.Tex2CoordFormat, vtxAttr.g1.Tex3CoordFormat,
vtxAttr.g1.Tex4CoordFormat, vtxAttr.g2.Tex5CoordFormat,
vtxAttr.g2.Tex6CoordFormat, vtxAttr.g2.Tex7CoordFormat};
const u32 tcFormat[8] =
{
vtxAttr.g0.Tex0CoordFormat, vtxAttr.g1.Tex1CoordFormat,
vtxAttr.g1.Tex2CoordFormat, vtxAttr.g1.Tex3CoordFormat,
vtxAttr.g1.Tex4CoordFormat, vtxAttr.g2.Tex5CoordFormat,
vtxAttr.g2.Tex6CoordFormat, vtxAttr.g2.Tex7CoordFormat
};
// Add position and texture matrix indices
u64 vtxDescHex = cpMem.vtxDesc.Hex;

View File

@@ -12,11 +12,13 @@
using namespace FifoFileStruct;
FifoDataFile::FifoDataFile(): m_Flags(0)
{}
FifoDataFile::FifoDataFile() : m_Flags(0)
{
}
FifoDataFile::~FifoDataFile()
{}
{
}
bool FifoDataFile::HasBrokenEFBCopies() const
{

View File

@@ -60,31 +60,13 @@ public:
bool GetIsWii() const;
bool HasBrokenEFBCopies() const;
u32* GetBPMem()
{
return m_BPMem;
}
u32* GetCPMem()
{
return m_CPMem;
}
u32* GetXFMem()
{
return m_XFMem;
}
u32* GetXFRegs()
{
return m_XFRegs;
}
u32* GetBPMem() { return m_BPMem; }
u32* GetCPMem() { return m_CPMem; }
u32* GetXFMem() { return m_XFMem; }
u32* GetXFRegs() { return m_XFRegs; }
void AddFrame(const FifoFrameInfo& frameInfo);
const FifoFrameInfo& GetFrame(u32 frame) const
{
return m_Frames[frame];
}
u32 GetFrameCount() const
{
return static_cast<u32>(m_Frames.size());
}
const FifoFrameInfo& GetFrame(u32 frame) const { return m_Frames[frame]; }
u32 GetFrameCount() const { return static_cast<u32>(m_Frames.size()); }
bool Save(const std::string& filename);
static std::unique_ptr<FifoDataFile> Load(const std::string& filename, bool flagsOnly);

View File

@@ -17,8 +17,7 @@ enum
#pragma pack(push, 4)
union FileHeader
{
union FileHeader {
struct
{
u32 fileId;
@@ -39,8 +38,7 @@ union FileHeader
u32 rawData[32];
};
union FileFrameInfo
{
union FileFrameInfo {
struct
{
u64 fifoDataOffset;

View File

@@ -28,7 +28,8 @@
bool IsPlayingBackFifologWithBrokenEFBCopies = false;
FifoPlayer::~FifoPlayer()
{}
{
}
bool FifoPlayer::Open(const std::string& filename)
{
@@ -61,62 +62,54 @@ void FifoPlayer::Close()
class FifoPlayer::CPUCore final : public CPUCoreBase
{
public:
explicit CPUCore(FifoPlayer* parent): m_parent(parent)
{}
CPUCore(const CPUCore&) = delete;
~CPUCore()
{}
CPUCore& operator=(const CPUCore&) = delete;
explicit CPUCore(FifoPlayer* parent) : m_parent(parent) {}
CPUCore(const CPUCore&) = delete;
~CPUCore() {}
CPUCore& operator=(const CPUCore&) = delete;
void Init() override
{
IsPlayingBackFifologWithBrokenEFBCopies = m_parent->m_File->HasBrokenEFBCopies();
void Init() override
{
IsPlayingBackFifologWithBrokenEFBCopies = m_parent->m_File->HasBrokenEFBCopies();
m_parent->m_CurrentFrame = m_parent->m_FrameRangeStart;
m_parent->LoadMemory();
}
m_parent->m_CurrentFrame = m_parent->m_FrameRangeStart;
m_parent->LoadMemory();
}
void Shutdown() override
{
IsPlayingBackFifologWithBrokenEFBCopies = false;
}
void ClearCache() override
{
// Nothing to clear.
}
void Shutdown() override { IsPlayingBackFifologWithBrokenEFBCopies = false; }
void ClearCache() override
{
// Nothing to clear.
}
void SingleStep() override
{
// NOTE: AdvanceFrame() will get stuck forever in Dual Core because the FIFO
// is disabled by CPU::EnableStepping(true) so the frame never gets displayed.
PanicAlertT("Cannot SingleStep the FIFO. Use Frame Advance instead.");
}
void SingleStep() override
{
// NOTE: AdvanceFrame() will get stuck forever in Dual Core because the FIFO
// is disabled by CPU::EnableStepping(true) so the frame never gets displayed.
PanicAlertT("Cannot SingleStep the FIFO. Use Frame Advance instead.");
}
const char* GetName() override
{
return "FifoPlayer";
}
void Run() override
{
while (CPU::GetState() == CPU::CPU_RUNNING)
{
switch (m_parent->AdvanceFrame())
{
case CPU::CPU_POWERDOWN:
CPU::Break();
Host_Message(WM_USER_STOP);
break;
const char* GetName() override { return "FifoPlayer"; }
void Run() override
{
while (CPU::GetState() == CPU::CPU_RUNNING)
{
switch (m_parent->AdvanceFrame())
{
case CPU::CPU_POWERDOWN:
CPU::Break();
Host_Message(WM_USER_STOP);
break;
case CPU::CPU_STEPPING:
CPU::Break();
Host_UpdateMainFrame();
break;
}
}
}
case CPU::CPU_STEPPING:
CPU::Break();
Host_UpdateMainFrame();
break;
}
}
}
private:
FifoPlayer* m_parent;
FifoPlayer* m_parent;
};
int FifoPlayer::AdvanceFrame()

View File

@@ -65,64 +65,28 @@ public:
// PowerPC state.
std::unique_ptr<CPUCoreBase> GetCPUCore();
FifoDataFile* GetFile()
{
return m_File.get();
}
FifoDataFile* GetFile() { return m_File.get(); }
u32 GetFrameObjectCount();
u32 GetCurrentFrameNum() const
{
return m_CurrentFrame;
}
const AnalyzedFrameInfo& GetAnalyzedFrameInfo(u32 frame) const
{
return m_FrameInfo[frame];
}
u32 GetCurrentFrameNum() const { return m_CurrentFrame; }
const AnalyzedFrameInfo& GetAnalyzedFrameInfo(u32 frame) const { return m_FrameInfo[frame]; }
// Frame range
u32 GetFrameRangeStart() const
{
return m_FrameRangeStart;
}
u32 GetFrameRangeStart() const { return m_FrameRangeStart; }
void SetFrameRangeStart(u32 start);
u32 GetFrameRangeEnd() const
{
return m_FrameRangeEnd;
}
u32 GetFrameRangeEnd() const { return m_FrameRangeEnd; }
void SetFrameRangeEnd(u32 end);
// Object range
u32 GetObjectRangeStart() const
{
return m_ObjectRangeStart;
}
void SetObjectRangeStart(u32 start)
{
m_ObjectRangeStart = start;
}
u32 GetObjectRangeEnd() const
{
return m_ObjectRangeEnd;
}
void SetObjectRangeEnd(u32 end)
{
m_ObjectRangeEnd = end;
}
u32 GetObjectRangeStart() const { return m_ObjectRangeStart; }
void SetObjectRangeStart(u32 start) { m_ObjectRangeStart = start; }
u32 GetObjectRangeEnd() const { return m_ObjectRangeEnd; }
void SetObjectRangeEnd(u32 end) { m_ObjectRangeEnd = end; }
// If enabled then all memory updates happen at once before the first frame
// Default is disabled
void SetEarlyMemoryUpdates(bool enabled)
{
m_EarlyMemoryUpdates = enabled;
}
void SetEarlyMemoryUpdates(bool enabled) { m_EarlyMemoryUpdates = enabled; }
// Callbacks
void SetFileLoadedCallback(CallbackFunc callback)
{
m_FileLoadedCb = callback;
}
void SetFrameWrittenCallback(CallbackFunc callback)
{
m_FrameWrittenCb = callback;
}
void SetFileLoadedCallback(CallbackFunc callback) { m_FileLoadedCb = callback; }
void SetFrameWrittenCallback(CallbackFunc callback) { m_FrameWrittenCb = callback; }
static FifoPlayer& GetInstance();
private:

View File

@@ -3,6 +3,7 @@
// Refer to the license.txt file included.
#include <algorithm>
#include <cstring>
#include "Core/FifoPlayer/FifoRecordAnalyzer.h"

View File

@@ -21,7 +21,8 @@ FifoRecorder::FifoRecorder()
m_RecordFramesRemaining(0), m_FinishedCb(nullptr), m_File(nullptr), m_SkipNextData(true),
m_SkipFutureData(true), m_FrameEnded(false), m_Ram(Memory::RAM_SIZE),
m_ExRam(Memory::EXRAM_SIZE)
{}
{
}
FifoRecorder::~FifoRecorder()
{

View File

@@ -19,10 +19,7 @@ public:
void StartRecording(s32 numFrames, CallbackFunc finishedCb);
void StopRecording();
FifoDataFile* GetRecordedFile()
{
return m_File;
}
FifoDataFile* GetRecordedFile() { return m_File; }
// Called from video thread
// Must write one full GP command at a time
@@ -42,10 +39,7 @@ public:
void SetVideoMemory(u32* bpMem, u32* cpMem, u32* xfMem, u32* xfRegs, u32 xfRegsSize);
// Checked once per frame prior to callng EndFrame()
bool IsRecording() const
{
return m_IsRecording;
}
bool IsRecording() const { return m_IsRecording; }
static FifoRecorder& GetInstance();
private:

View File

@@ -16,7 +16,7 @@ class GeckoCode
{
public:
GeckoCode(): enabled(false)
GeckoCode() : enabled(false)
{}
struct Code

View File

@@ -15,7 +15,7 @@ namespace Gecko
void LoadCodes(const IniFile& globalIni, const IniFile& localIni, std::vector<GeckoCode>& gcodes)
{
const IniFile* inis[2] = {&globalIni, &localIni};
const IniFile* inis[2] = { &globalIni, &localIni };
for (const IniFile* ini : inis)
{

View File

@@ -17,24 +17,24 @@ Output at "48KHz" is actually 48043Hz.
Sample counter counts streaming stereo samples after upsampling.
[DAC] causes [AI I/F] to read from RAM at rate selected by AIDFR.
Each [SRC] will upsample a 32KHz source, or pass through the 48KHz
source. The [Mixer]/[DAC] only operate at 48KHz.
source. The [Mixer]/[DAC] only operate at 48KHz.
AIS == disc streaming == DTK(Disk Track Player) == streaming audio, etc.
Supposedly, the retail hardware only supports 48KHz streaming from
[Drive I/F]. However it's more likely that the hardware supports
32KHz streaming, and the upsampling is transparent to the user.
TODO check if anything tries to stream at 32KHz.
[Drive I/F]. However it's more likely that the hardware supports
32KHz streaming, and the upsampling is transparent to the user.
TODO check if anything tries to stream at 32KHz.
The [Drive I/F] actually supports simultaneous requests for audio and
normal data. For this reason, we can't really get rid of the crit section.
normal data. For this reason, we can't really get rid of the crit section.
IMPORTANT:
This file mainly deals with the [Drive I/F], however [AIDFR] controls
the rate at which the audio data is DMA'd from RAM into the [AI FIFO]
(and the speed at which the FIFO is read by its SRC). Everything else
relating to AID happens in DSP.cpp. It's kinda just bad hardware design.
TODO maybe the files should be merged?
the rate at which the audio data is DMA'd from RAM into the [AI FIFO]
(and the speed at which the FIFO is read by its SRC). Everything else
relating to AID happens in DSP.cpp. It's kinda just bad hardware design.
TODO maybe the files should be merged?
*/
#include <algorithm>
@@ -70,16 +70,9 @@ enum
};
// AI Control Register
union AICR
{
AICR()
{
hex = 0;
}
AICR(u32 _hex)
{
hex = _hex;
}
union AICR {
AICR() { hex = 0; }
AICR(u32 _hex) { hex = _hex; }
struct
{
u32 PSTAT : 1; // sample counter/playback enable
@@ -87,8 +80,8 @@ union AICR
u32 AIINTMSK : 1; // 0=interrupt masked 1=interrupt enabled
u32 AIINT : 1; // audio interrupt status
u32 AIINTVLD : 1; // This bit controls whether AIINT is affected by the Interrupt Timing
// register
// matching the sample counter. Once set, AIINT will hold its last value
// register
// matching the sample counter. Once set, AIINT will hold its last value
u32 SCRESET : 1; // write to reset counter
u32 AIDFR : 1; // AID Frequency (0=48khz 1=32khz)
u32 : 25;
@@ -97,12 +90,8 @@ union AICR
};
// AI Volume Register
union AIVR
{
AIVR()
{
hex = 0;
}
union AIVR {
AIVR() { hex = 0; }
struct
{
u32 left : 8;
@@ -162,14 +151,14 @@ void Init()
}
void Shutdown()
{}
{
}
void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
{
mmio->Register(
base | AI_CONTROL_REGISTER, MMIO::DirectRead<u32>(&m_Control.hex),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
AICR tmpAICtrl(val);
if (m_Control.AIINTMSK != tmpAICtrl.AIINTMSK)
@@ -234,20 +223,17 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
}));
mmio->Register(base | AI_VOLUME_REGISTER, MMIO::DirectRead<u32>(&m_Volume.hex),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
m_Volume.hex = val;
g_sound_stream->GetMixer()->SetStreamingVolume(m_Volume.left, m_Volume.right);
}));
mmio->Register(base | AI_SAMPLE_COUNTER, MMIO::ComplexRead<u32>([](u32)
{
mmio->Register(base | AI_SAMPLE_COUNTER, MMIO::ComplexRead<u32>([](u32) {
return m_SampleCounter +
static_cast<u32>((CoreTiming::GetTicks() - g_LastCPUTime) /
g_CPUCyclesPerSample);
}),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
m_SampleCounter = val;
g_LastCPUTime = CoreTiming::GetTicks();
CoreTiming::RemoveEvent(et_AI);
@@ -255,8 +241,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
}));
mmio->Register(base | AI_INTERRUPT_TIMING, MMIO::DirectRead<u32>(&m_InterruptTiming),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
DEBUG_LOG(AUDIO_INTERFACE, "AI_INTERRUPT_TIMING=%08x@%08x", val,
PowerPC::ppcState.pc);
m_InterruptTiming = val;

View File

@@ -74,10 +74,7 @@ void Run()
std::unique_lock<std::mutex> state_lock(s_state_change_lock);
while (s_state != CPU_POWERDOWN)
{
s_state_cpu_cvar.wait(state_lock, []
{
return !s_state_paused_and_locked;
});
s_state_cpu_cvar.wait(state_lock, [] { return !s_state_paused_and_locked; });
switch (s_state)
{
@@ -113,10 +110,7 @@ void Run()
case CPU_STEPPING:
// Wait for step command.
s_state_cpu_cvar.wait(state_lock,
[]
{
return s_state_cpu_step_instruction || s_state != CPU_STEPPING;
});
[] { return s_state_cpu_step_instruction || s_state != CPU_STEPPING; });
if (s_state != CPU_STEPPING)
{
// Signal event if the mode changes.
@@ -167,10 +161,7 @@ void Stop()
s_state_cpu_cvar.notify_one();
// FIXME: MsgHandler can cause this to deadlock the GUI Thread. Remove the timeout.
bool success = s_state_cpu_idle_cvar.wait_for(state_lock, std::chrono::seconds(5),
[]
{
return !s_state_cpu_thread_active;
});
[] { return !s_state_cpu_thread_active; });
if (!success)
ERROR_LOG(POWERPC, "CPU Thread failed to acknowledge CPU_POWERDOWN. It may be deadlocked.");
RunAdjacentSystems(false);
@@ -193,7 +184,8 @@ const volatile State* GetStatePtr()
}
void Reset()
{}
{
}
void StepOpcode(Common::Event* event)
{
@@ -236,10 +228,7 @@ void EnableStepping(bool stepping)
// Wait for the CPU Thread to leave the run loop
// FIXME: MsgHandler can cause this to deadlock the GUI Thread. Remove the timeout.
bool success = s_state_cpu_idle_cvar.wait_for(state_lock, std::chrono::seconds(5),
[]
{
return !s_state_cpu_thread_active;
});
[] { return !s_state_cpu_thread_active; });
if (!success)
ERROR_LOG(POWERPC, "Abandoned waiting for CPU Thread! The Core may be deadlocked.");
@@ -288,10 +277,7 @@ bool PauseAndLock(bool do_lock, bool unpause_on_unlock, bool control_adjacent)
// FIXME: MsgHandler can cause this to deadlock the GUI Thread. Remove the timeout.
bool success = s_state_cpu_idle_cvar.wait_for(state_lock, std::chrono::seconds(10),
[]
{
return !s_state_cpu_thread_active;
});
[] { return !s_state_cpu_thread_active; });
if (!success)
NOTICE_LOG(
POWERPC,

View File

@@ -65,8 +65,7 @@ enum
};
// UARAMCount
union UARAMCount
{
union UARAMCount {
u32 Hex;
struct
{
@@ -76,8 +75,7 @@ union UARAMCount
};
// Blocks are 32 bytes.
union UAudioDMAControl
{
union UAudioDMAControl {
u16 Hex;
struct
{
@@ -85,8 +83,7 @@ union UAudioDMAControl
u16 Enable : 1;
};
UAudioDMAControl(u16 _Hex = 0): Hex(_Hex)
{}
UAudioDMAControl(u16 _Hex = 0) : Hex(_Hex) {}
};
// AudioDMA
@@ -99,7 +96,8 @@ struct AudioDMA
AudioDMA()
: current_source_address(0), remaining_blocks_count(0), SourceAddress(0), AudioDMAControl(0)
{}
{
}
};
// ARAM_DMA
@@ -144,8 +142,7 @@ static u32 last_aram_dma_count;
static bool instant_dma;
UDSPControl g_dspState;
union ARAM_Info
{
union ARAM_Info {
u16 Hex;
struct
{
@@ -290,17 +287,17 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
u16* ptr;
bool align_writes_on_32_bytes;
} directly_mapped_vars[] = {
{AR_INFO, &g_ARAM_Info.Hex},
{AR_MODE, &g_AR_MODE},
{AR_REFRESH, &g_AR_REFRESH},
{AR_DMA_MMADDR_H, MMIO::Utils::HighPart(&g_arDMA.MMAddr)},
{AR_DMA_MMADDR_L, MMIO::Utils::LowPart(&g_arDMA.MMAddr), true},
{AR_DMA_ARADDR_H, MMIO::Utils::HighPart(&g_arDMA.ARAddr)},
{AR_DMA_ARADDR_L, MMIO::Utils::LowPart(&g_arDMA.ARAddr), true},
{AR_DMA_CNT_H, MMIO::Utils::HighPart(&g_arDMA.Cnt.Hex)},
// AR_DMA_CNT_L triggers DMA
{AUDIO_DMA_START_HI, MMIO::Utils::HighPart(&g_audioDMA.SourceAddress)},
{AUDIO_DMA_START_LO, MMIO::Utils::LowPart(&g_audioDMA.SourceAddress)},
{AR_INFO, &g_ARAM_Info.Hex},
{AR_MODE, &g_AR_MODE},
{AR_REFRESH, &g_AR_REFRESH},
{AR_DMA_MMADDR_H, MMIO::Utils::HighPart(&g_arDMA.MMAddr)},
{AR_DMA_MMADDR_L, MMIO::Utils::LowPart(&g_arDMA.MMAddr), true},
{AR_DMA_ARADDR_H, MMIO::Utils::HighPart(&g_arDMA.ARAddr)},
{AR_DMA_ARADDR_L, MMIO::Utils::LowPart(&g_arDMA.ARAddr), true},
{AR_DMA_CNT_H, MMIO::Utils::HighPart(&g_arDMA.Cnt.Hex)},
// AR_DMA_CNT_L triggers DMA
{AUDIO_DMA_START_HI, MMIO::Utils::HighPart(&g_audioDMA.SourceAddress)},
{AUDIO_DMA_START_LO, MMIO::Utils::LowPart(&g_audioDMA.SourceAddress)},
};
for (auto& mapped_var : directly_mapped_vars)
{
@@ -311,8 +308,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
// DSP mail MMIOs call DSP emulator functions to get results or write data.
mmio->Register(
base | DSP_MAIL_TO_DSP_HI, MMIO::ComplexRead<u16>([](u32)
{
base | DSP_MAIL_TO_DSP_HI, MMIO::ComplexRead<u16>([](u32) {
if (dsp_slice > DSP_MAIL_SLICE && dsp_is_lle)
{
dsp_emulator->DSP_Update(DSP_MAIL_SLICE);
@@ -320,22 +316,12 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
}
return dsp_emulator->DSP_ReadMailBoxHigh(true);
}),
MMIO::ComplexWrite<u16>([](u32, u16 val)
{
dsp_emulator->DSP_WriteMailBoxHigh(true, val);
}));
MMIO::ComplexWrite<u16>([](u32, u16 val) { dsp_emulator->DSP_WriteMailBoxHigh(true, val); }));
mmio->Register(
base | DSP_MAIL_TO_DSP_LO,
MMIO::ComplexRead<u16>([](u32)
{
return dsp_emulator->DSP_ReadMailBoxLow(true);
}),
MMIO::ComplexWrite<u16>([](u32, u16 val)
{
dsp_emulator->DSP_WriteMailBoxLow(true, val);
}));
mmio->Register(base | DSP_MAIL_FROM_DSP_HI, MMIO::ComplexRead<u16>([](u32)
{
MMIO::ComplexRead<u16>([](u32) { return dsp_emulator->DSP_ReadMailBoxLow(true); }),
MMIO::ComplexWrite<u16>([](u32, u16 val) { dsp_emulator->DSP_WriteMailBoxLow(true, val); }));
mmio->Register(base | DSP_MAIL_FROM_DSP_HI, MMIO::ComplexRead<u16>([](u32) {
if (dsp_slice > DSP_MAIL_SLICE && dsp_is_lle)
{
dsp_emulator->DSP_Update(DSP_MAIL_SLICE);
@@ -344,20 +330,17 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
return dsp_emulator->DSP_ReadMailBoxHigh(false);
}),
MMIO::InvalidWrite<u16>());
mmio->Register(base | DSP_MAIL_FROM_DSP_LO, MMIO::ComplexRead<u16>([](u32)
{
mmio->Register(base | DSP_MAIL_FROM_DSP_LO, MMIO::ComplexRead<u16>([](u32) {
return dsp_emulator->DSP_ReadMailBoxLow(false);
}),
MMIO::InvalidWrite<u16>());
mmio->Register(
base | DSP_CONTROL, MMIO::ComplexRead<u16>([](u32)
{
base | DSP_CONTROL, MMIO::ComplexRead<u16>([](u32) {
return (g_dspState.Hex & ~DSP_CONTROL_MASK) |
(dsp_emulator->DSP_ReadControlRegister() & DSP_CONTROL_MASK);
}),
MMIO::ComplexWrite<u16>([](u32, u16 val)
{
MMIO::ComplexWrite<u16>([](u32, u16 val) {
UDSPControl tmpControl;
tmpControl.Hex = (val & ~DSP_CONTROL_MASK) |
(dsp_emulator->DSP_WriteControlRegister(val) & DSP_CONTROL_MASK);
@@ -404,8 +387,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
// ARAM MMIO controlling the DMA start.
mmio->Register(base | AR_DMA_CNT_L, MMIO::DirectRead<u16>(MMIO::Utils::LowPart(&g_arDMA.Cnt.Hex)),
MMIO::ComplexWrite<u16>([](u32, u16 val)
{
MMIO::ComplexWrite<u16>([](u32, u16 val) {
g_arDMA.Cnt.Hex = (g_arDMA.Cnt.Hex & 0xFFFF0000) | (val & ~31);
Do_ARAM_DMA();
}));
@@ -413,8 +395,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
// Audio DMA MMIO controlling the DMA start.
mmio->Register(
base | AUDIO_DMA_CONTROL_LEN, MMIO::DirectRead<u16>(&g_audioDMA.AudioDMAControl.Hex),
MMIO::ComplexWrite<u16>([](u32, u16 val)
{
MMIO::ComplexWrite<u16>([](u32, u16 val) {
bool already_enabled = g_audioDMA.AudioDMAControl.Enable;
g_audioDMA.AudioDMAControl.Hex = val;
@@ -443,8 +424,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
// Audio DMA blocks remaining is invalid to write to, and requires logic on
// the read side.
mmio->Register(
base | AUDIO_DMA_BLOCKS_LEFT, MMIO::ComplexRead<u16>([](u32)
{
base | AUDIO_DMA_BLOCKS_LEFT, MMIO::ComplexRead<u16>([](u32) {
// remaining_blocks_count is zero-based. DreamMix World Fighters will hang if it never
// reaches zero.
return (g_audioDMA.remaining_blocks_count > 0 ? g_audioDMA.remaining_blocks_count - 1 : 0);
@@ -508,7 +488,7 @@ void UpdateDSPSlice(int cycles)
// This happens at 4 khz, since 32 bytes at 4khz = 4 bytes at 32 khz (16bit stereo pcm)
void UpdateAudioDMA()
{
static short zero_samples[8 * 2] = {0};
static short zero_samples[8 * 2] = { 0 };
if (g_audioDMA.AudioDMAControl.Enable)
{
// Read audio at g_audioDMA.current_source_address in RAM and push onto an

View File

@@ -31,8 +31,7 @@ enum
// UDSPControl
#define DSP_CONTROL_MASK 0x0C07
union UDSPControl
{
union UDSPControl {
u16 Hex;
struct
{
@@ -51,13 +50,12 @@ union UDSPControl
u16 DSP_mask : 1;
// Other ???
u16 DMAState : 1; // DSPGetDMAStatus() uses this flag. __ARWaitForDMA() uses it too...maybe
// it's just general DMA flag
// it's just general DMA flag
u16 DSPInitCode : 1; // Indicator that the DSP was initialized?
u16 DSPInit : 1; // DSPInit() writes to this flag
u16 pad : 4;
};
UDSPControl(u16 _Hex = 0): Hex(_Hex)
{}
UDSPControl(u16 _Hex = 0) : Hex(_Hex) {}
};
extern UDSPControl g_dspState;

View File

@@ -13,7 +13,8 @@
#include "Core/HW/SystemTimers.h"
DSPHLE::DSPHLE()
{}
{
}
bool DSPHLE::Initialize(bool bWii, bool bDSPThread)
{
@@ -33,7 +34,8 @@ bool DSPHLE::Initialize(bool bWii, bool bDSPThread)
}
void DSPHLE::DSP_StopSoundStream()
{}
{
}
void DSPHLE::Shutdown()
{
@@ -242,4 +244,5 @@ u16 DSPHLE::DSP_ReadControlRegister()
}
void DSPHLE::PauseAndLock(bool doLock, bool unpauseOnUnlock)
{}
{
}

View File

@@ -12,17 +12,14 @@
class PointerWrap;
class UCodeInterface;
class DSPHLE: public DSPEmulator
class DSPHLE : public DSPEmulator
{
public:
DSPHLE();
bool Initialize(bool bWii, bool bDSPThread) override;
void Shutdown() override;
bool IsLLE() override
{
return false;
}
bool IsLLE() override { return false; }
void DoState(PointerWrap& p) override;
void PauseAndLock(bool doLock, bool unpauseOnUnlock = true) override;
@@ -36,10 +33,7 @@ public:
void DSP_StopSoundStream() override;
u32 DSP_UpdateRate() override;
CMailHandler& AccessMailHandler()
{
return m_MailHandler;
}
CMailHandler& AccessMailHandler() { return m_MailHandler; }
// Formerly DSPHandler
UCodeInterface* GetUCode();
void SetUCode(u32 _crc);
@@ -63,10 +57,7 @@ private:
DSPMailbox = 0x00000000;
}
DSPState()
{
Reset();
}
DSPState() { Reset(); }
};
DSPState m_dspState;

View File

@@ -10,7 +10,8 @@
#include "Core/HW/DSP.h"
CMailHandler::CMailHandler()
{}
{
}
CMailHandler::~CMailHandler()
{

View File

@@ -16,7 +16,7 @@
#define AX_GC
#include "Core/HW/DSPHLE/UCodes/AXVoice.h"
AXUCode::AXUCode(DSPHLE* dsphle, u32 crc): UCodeInterface(dsphle, crc), m_cmdlist_size(0)
AXUCode::AXUCode(DSPHLE* dsphle, u32 crc) : UCodeInterface(dsphle, crc), m_cmdlist_size(0)
{
WARN_LOG(DSPHLE, "Instantiating AXUCode: crc=%08x", crc);
m_mail_handler.PushMail(DSP_INIT);
@@ -34,8 +34,8 @@ void AXUCode::LoadResamplingCoefficients()
{
m_coeffs_available = false;
std::string filenames[] = {File::GetUserPath(D_GCUSER_IDX) + "dsp_coef.bin",
File::GetSysDirectory() + "/GC/dsp_coef.bin"};
std::string filenames[] = { File::GetUserPath(D_GCUSER_IDX) + "dsp_coef.bin",
File::GetSysDirectory() + "/GC/dsp_coef.bin" };
size_t fidx;
std::string filename;
@@ -348,9 +348,12 @@ void AXUCode::SetupProcessing(u32 init_addr)
init_data[i] = HLEMemory_Read_U16(init_addr + 2 * i);
// List of all buffers we have to initialize
int* buffers[] = {m_samples_left, m_samples_right, m_samples_surround,
m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround,
m_samples_auxB_left, m_samples_auxB_right, m_samples_auxB_surround};
int* buffers[] =
{
m_samples_left, m_samples_right, m_samples_surround,
m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround,
m_samples_auxB_left, m_samples_auxB_right, m_samples_auxB_surround
};
u32 init_idx = 0;
for (auto& buffer : buffers)
@@ -377,11 +380,11 @@ void AXUCode::SetupProcessing(u32 init_addr)
void AXUCode::DownloadAndMixWithVolume(u32 addr, u16 vol_main, u16 vol_auxa, u16 vol_auxb)
{
int* buffers_main[3] = {m_samples_left, m_samples_right, m_samples_surround};
int* buffers_auxa[3] = {m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround};
int* buffers_auxb[3] = {m_samples_auxB_left, m_samples_auxB_right, m_samples_auxB_surround};
int** buffers[3] = {buffers_main, buffers_auxa, buffers_auxb};
u16 volumes[3] = {vol_main, vol_auxa, vol_auxb};
int* buffers_main[3] = { m_samples_left, m_samples_right, m_samples_surround };
int* buffers_auxa[3] = { m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround };
int* buffers_auxb[3] = { m_samples_auxB_left, m_samples_auxB_right, m_samples_auxB_surround };
int** buffers[3] = { buffers_main, buffers_auxa, buffers_auxb };
u16 volumes[3] = { vol_main, vol_auxa, vol_auxb };
for (u32 i = 0; i < 3; ++i)
{
@@ -410,9 +413,12 @@ void AXUCode::ProcessPBList(u32 pb_addr)
while (pb_addr)
{
AXBuffers buffers = {{m_samples_left, m_samples_right, m_samples_surround, m_samples_auxA_left,
m_samples_auxA_right, m_samples_auxA_surround, m_samples_auxB_left,
m_samples_auxB_right, m_samples_auxB_surround}};
AXBuffers buffers = {
{
m_samples_left, m_samples_right, m_samples_surround, m_samples_auxA_left,
m_samples_auxA_right, m_samples_auxA_surround, m_samples_auxB_left,
m_samples_auxB_right, m_samples_auxB_surround}
};
ReadPB(pb_addr, pb);
@@ -438,7 +444,7 @@ void AXUCode::ProcessPBList(u32 pb_addr)
void AXUCode::MixAUXSamples(int aux_id, u32 write_addr, u32 read_addr)
{
int* buffers[3] = {nullptr};
int* buffers[3] = { nullptr };
switch (aux_id)
{
@@ -565,7 +571,7 @@ void AXUCode::SendAUXAndMix(u32 main_auxa_up, u32 auxb_s_up, u32 main_l_dl, u32
u32 auxb_l_dl, u32 auxb_r_dl)
{
// Buffers to upload first
int* up_buffers[] = {m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround};
int* up_buffers[] = { m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround };
// Upload AUXA LRS
int* ptr = (int*)HLEMemory_Get_Pointer(main_auxa_up);
@@ -579,8 +585,8 @@ void AXUCode::SendAUXAndMix(u32 main_auxa_up, u32 auxb_s_up, u32 main_l_dl, u32
*ptr++ = Common::swap32(sample);
// Download buffers and addresses
int* dl_buffers[] = {m_samples_left, m_samples_right, m_samples_auxB_left, m_samples_auxB_right};
u32 dl_addrs[] = {main_l_dl, main_r_dl, auxb_l_dl, auxb_r_dl};
int* dl_buffers[] = { m_samples_left, m_samples_right, m_samples_auxB_left, m_samples_auxB_right };
u32 dl_addrs[] = { main_l_dl, main_r_dl, auxb_l_dl, auxb_r_dl };
// Download and mix
for (size_t i = 0; i < ArraySize(dl_buffers); ++i)

View File

@@ -49,7 +49,7 @@ enum AXMixControl
MIX_AUXC_S_RAMP = 0x800000
};
class AXUCode: public UCodeInterface
class AXUCode : public UCodeInterface
{
public:
AXUCode(DSPHLE* dsphle, u32 crc);

View File

@@ -176,7 +176,7 @@ struct PBAudioAddr
u16 looping;
u16 sample_format;
u16 loop_addr_hi; // Start of loop (this will point to a shared "zero" buffer if one-shot mode is
// active)
// active)
u16 loop_addr_lo;
u16 end_addr_hi; // End of sample (and loop), inclusive
u16 end_addr_lo;
@@ -267,8 +267,7 @@ struct PBBiquadFilter
u16 a2;
};
union PBInfImpulseResponseWM
{
union PBInfImpulseResponseWM {
PBLowPassFilter lpf;
PBBiquadFilter biquad;
};
@@ -308,7 +307,7 @@ struct AXPBWii
PBSampleRateConverterWM remote_src;
PBInfImpulseResponseWM remote_iir;
u16 pad[12]; // align us, captain! (32B)
u16 padding[12]; // align us, captain! (32B)
};
// TODO: All these enums have changed a lot for Wii

View File

@@ -16,6 +16,7 @@
#include "Common/CommonTypes.h"
#include "Common/MathUtil.h"
#include "Core/ConfigManager.h"
#include "Core/HW/DSP.h"
#include "Core/HW/DSPHLE/UCodes/AX.h"
#include "Core/HW/DSPHLE/UCodes/AXStructs.h"
@@ -37,8 +38,7 @@ namespace
#define HILO_TO_32(name) ((name##_hi << 16) | name##_lo)
// Used to pass a large amount of buffers to the mixing function.
union AXBuffers
{
union AXBuffers {
struct
{
int* left;
@@ -225,10 +225,28 @@ u16 AcceleratorGetSample()
// stream type. This is what the AX UCode does and I don't really
// know why.
acc_pb->adpcm.pred_scale = acc_pb->adpcm_loop_info.pred_scale;
if (!acc_pb->is_stream)
if (SConfig::GetInstance().bRSHACK)
{
acc_pb->adpcm.yn1 = acc_pb->adpcm_loop_info.yn1;
acc_pb->adpcm.yn2 = acc_pb->adpcm_loop_info.yn2;
if (acc_pb->is_stream)
{
// HORRIBLE HACK: this behavior changed between versions at some point; needs some sort
// of branch. delroth says anyone who submits this code as a serious PR will be banned
// from Dolphin.
// needed for RS2
acc_pb->lpf.enabled += 1;
// needed for RS3
acc_pb->padding[0] += 1;
}
}
else
{
if (!acc_pb->is_stream)
{
acc_pb->adpcm.yn1 = acc_pb->adpcm_loop_info.yn1;
acc_pb->adpcm.yn2 = acc_pb->adpcm_loop_info.yn2;
}
}
}
else
@@ -395,10 +413,7 @@ void GetInputSamples(PB_TYPE& pb, s16* samples, u16 count, const s16* coeffs)
if (coeffs)
coeffs += pb.coef_select * 0x200;
u32 curr_pos =
ResampleAudio([](u32)
{
return AcceleratorGetSample();
}, samples, count, pb.src.last_samples,
ResampleAudio([](u32) { return AcceleratorGetSample(); }, samples, count, pb.src.last_samples,
pb.src.cur_addr_frac, HILO_TO_32(pb.src.ratio), pb.src_type, coeffs);
pb.src.cur_addr_frac = (curr_pos & 0xFFFF);
@@ -537,10 +552,7 @@ void ProcessVoice(PB_TYPE& pb, const AXBuffers& buffers, u16 count, AXMixControl
// We use ratio 0x55555 == (5 * 65536 + 21845) / 65536 == 5.3333 which
// is the nearest we can get to 96/18
u32 curr_pos = ResampleAudio([&samples](u32 i)
{
return samples[i];
}, wm_samples, wm_count,
u32 curr_pos = ResampleAudio([&samples](u32 i) { return samples[i]; }, wm_samples, wm_count,
pb.remote_src.last_samples, pb.remote_src.cur_addr_frac, 0x55555,
SRCTYPE_POLYPHASE, coeffs);
pb.remote_src.cur_addr_frac = curr_pos & 0xFFFF;

View File

@@ -15,7 +15,7 @@
#include "Core/HW/DSPHLE/UCodes/AXVoice.h"
#include "Core/HW/DSPHLE/UCodes/UCodes.h"
AXWiiUCode::AXWiiUCode(DSPHLE* dsphle, u32 crc): AXUCode(dsphle, crc), m_last_main_volume(0x8000)
AXWiiUCode::AXWiiUCode(DSPHLE* dsphle, u32 crc) : AXUCode(dsphle, crc), m_last_main_volume(0x8000)
{
for (u16& volume : m_last_aux_volumes)
volume = 0x8000;
@@ -26,7 +26,8 @@ AXWiiUCode::AXWiiUCode(DSPHLE* dsphle, u32 crc): AXUCode(dsphle, crc), m_last_ma
}
AXWiiUCode::~AXWiiUCode()
{}
{
}
void AXWiiUCode::HandleCommandList()
{
@@ -100,12 +101,12 @@ void AXWiiUCode::HandleCommandList()
{
volume = m_cmdlist[curr_idx++];
u32 addresses[6] = {
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
(u32)(m_cmdlist[curr_idx + 8] << 16) | m_cmdlist[curr_idx + 9],
(u32)(m_cmdlist[curr_idx + 10] << 16) | m_cmdlist[curr_idx + 11],
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
(u32)(m_cmdlist[curr_idx + 8] << 16) | m_cmdlist[curr_idx + 9],
(u32)(m_cmdlist[curr_idx + 10] << 16) | m_cmdlist[curr_idx + 11],
};
curr_idx += 12;
UploadAUXMixLRSC(cmd == CMD_UPL_AUXB_MIX_LRSC_OLD, addresses, volume);
@@ -130,10 +131,10 @@ void AXWiiUCode::HandleCommandList()
case CMD_WM_OUTPUT_OLD:
{
u32 addresses[4] = {
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
};
curr_idx += 8;
OutputWMSamples(addresses);
@@ -193,12 +194,12 @@ void AXWiiUCode::HandleCommandList()
{
volume = m_cmdlist[curr_idx++];
u32 addresses[6] = {
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
(u32)(m_cmdlist[curr_idx + 8] << 16) | m_cmdlist[curr_idx + 9],
(u32)(m_cmdlist[curr_idx + 10] << 16) | m_cmdlist[curr_idx + 11],
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
(u32)(m_cmdlist[curr_idx + 8] << 16) | m_cmdlist[curr_idx + 9],
(u32)(m_cmdlist[curr_idx + 10] << 16) | m_cmdlist[curr_idx + 11],
};
curr_idx += 12;
UploadAUXMixLRSC(cmd == CMD_UPL_AUXB_MIX_LRSC, addresses, volume);
@@ -224,10 +225,10 @@ void AXWiiUCode::HandleCommandList()
case CMD_WM_OUTPUT:
{
u32 addresses[4] = {
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
(u32)(m_cmdlist[curr_idx + 0] << 16) | m_cmdlist[curr_idx + 1],
(u32)(m_cmdlist[curr_idx + 2] << 16) | m_cmdlist[curr_idx + 3],
(u32)(m_cmdlist[curr_idx + 4] << 16) | m_cmdlist[curr_idx + 5],
(u32)(m_cmdlist[curr_idx + 6] << 16) | m_cmdlist[curr_idx + 7],
};
curr_idx += 8;
OutputWMSamples(addresses);
@@ -256,14 +257,14 @@ void AXWiiUCode::SetupProcessing(u32 init_addr)
int* ptr;
u32 samples;
} buffers[] = {
{m_samples_left, 32}, {m_samples_right, 32}, {m_samples_surround, 32},
{m_samples_auxA_left, 32}, {m_samples_auxA_right, 32}, {m_samples_auxA_surround, 32},
{m_samples_auxB_left, 32}, {m_samples_auxB_right, 32}, {m_samples_auxB_surround, 32},
{m_samples_auxC_left, 32}, {m_samples_auxC_right, 32}, {m_samples_auxC_surround, 32},
{m_samples_left, 32}, {m_samples_right, 32}, {m_samples_surround, 32},
{m_samples_auxA_left, 32}, {m_samples_auxA_right, 32}, {m_samples_auxA_surround, 32},
{m_samples_auxB_left, 32}, {m_samples_auxB_right, 32}, {m_samples_auxB_surround, 32},
{m_samples_auxC_left, 32}, {m_samples_auxC_right, 32}, {m_samples_auxC_surround, 32},
{m_samples_wm0, 6}, {m_samples_aux0, 6}, {m_samples_wm1, 6},
{m_samples_aux1, 6}, {m_samples_wm2, 6}, {m_samples_aux2, 6},
{m_samples_wm3, 6}, {m_samples_aux3, 6}};
{m_samples_wm0, 6}, {m_samples_aux0, 6}, {m_samples_wm1, 6},
{m_samples_aux1, 6}, {m_samples_wm2, 6}, {m_samples_aux2, 6},
{m_samples_wm3, 6}, {m_samples_aux3, 6} };
u32 init_idx = 0;
for (auto& buffer : buffers)
@@ -436,13 +437,18 @@ void AXWiiUCode::ProcessPBList(u32 pb_addr)
while (pb_addr)
{
AXBuffers buffers = {{m_samples_left, m_samples_right, m_samples_surround,
m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround,
m_samples_auxB_left, m_samples_auxB_right, m_samples_auxB_surround,
m_samples_auxC_left, m_samples_auxC_right, m_samples_auxC_surround,
m_samples_wm0, m_samples_aux0, m_samples_wm1,
m_samples_aux1, m_samples_wm2, m_samples_aux2,
m_samples_wm3, m_samples_aux3}};
AXBuffers buffers =
{
{
m_samples_left, m_samples_right, m_samples_surround,
m_samples_auxA_left, m_samples_auxA_right, m_samples_auxA_surround,
m_samples_auxB_left, m_samples_auxB_right, m_samples_auxB_surround,
m_samples_auxC_left, m_samples_auxC_right, m_samples_auxC_surround,
m_samples_wm0, m_samples_aux0, m_samples_wm1,
m_samples_aux1, m_samples_wm2, m_samples_aux2,
m_samples_wm3, m_samples_aux3
}
};
ReadPB(pb_addr, pb);
@@ -480,8 +486,8 @@ void AXWiiUCode::MixAUXSamples(int aux_id, u32 write_addr, u32 read_addr, u16 vo
GenerateVolumeRamp(volume_ramp, m_last_aux_volumes[aux_id], volume, ArraySize(volume_ramp));
m_last_aux_volumes[aux_id] = volume;
int* buffers[3] = {nullptr};
int* main_buffers[3] = {m_samples_left, m_samples_right, m_samples_surround};
int* buffers[3] = { nullptr };
int* main_buffers[3] = { m_samples_left, m_samples_right, m_samples_surround };
switch (aux_id)
{
@@ -547,7 +553,7 @@ void AXWiiUCode::UploadAUXMixLRSC(int aux_id, u32* addresses, u16 volume)
GenerateVolumeRamp(volume_ramp, m_last_aux_volumes[aux_id], volume, 96);
m_last_aux_volumes[aux_id] = volume;
int* mix_dest[4] = {m_samples_left, m_samples_right, m_samples_surround, m_samples_auxC_left};
int* mix_dest[4] = { m_samples_left, m_samples_right, m_samples_surround, m_samples_auxC_left };
for (u32 mix_i = 0; mix_i < 4; ++mix_i)
{
int* dl_ptr = (int*)HLEMemory_Get_Pointer(addresses[2 + mix_i]);
@@ -569,7 +575,7 @@ void AXWiiUCode::OutputSamples(u32 lr_addr, u32 surround_addr, u16 volume, bool
GenerateVolumeRamp(volume_ramp, m_last_main_volume, volume, ArraySize(volume_ramp));
m_last_main_volume = volume;
int upload_buffer[3 * 32] = {0};
int upload_buffer[3 * 32] = { 0 };
for (u32 i = 0; i < 3 * 32; ++i)
upload_buffer[i] = Common::swap32(m_samples_surround[i]);
@@ -614,7 +620,7 @@ void AXWiiUCode::OutputSamples(u32 lr_addr, u32 surround_addr, u16 volume, bool
void AXWiiUCode::OutputWMSamples(u32* addresses)
{
int* buffers[] = {m_samples_wm0, m_samples_wm1, m_samples_wm2, m_samples_wm3};
int* buffers[] = { m_samples_wm0, m_samples_wm1, m_samples_wm2, m_samples_wm3 };
for (u32 i = 0; i < 4; ++i)
{

View File

@@ -8,7 +8,7 @@
struct AXPBWii;
class AXWiiUCode: public AXUCode
class AXWiiUCode : public AXUCode
{
public:
AXWiiUCode(DSPHLE* dsphle, u32 crc);

View File

@@ -9,7 +9,7 @@
#include "Core/HW/DSPHLE/DSPHLE.h"
#include "Core/HW/DSPHLE/UCodes/UCodes.h"
CARDUCode::CARDUCode(DSPHLE* dsphle, u32 crc): UCodeInterface(dsphle, crc)
CARDUCode::CARDUCode(DSPHLE* dsphle, u32 crc) : UCodeInterface(dsphle, crc)
{
DEBUG_LOG(DSPHLE, "CARDUCode - initialized");
m_mail_handler.PushMail(DSP_INIT);

View File

@@ -6,7 +6,7 @@
#include "Core/HW/DSPHLE/UCodes/UCodes.h"
class CARDUCode: public UCodeInterface
class CARDUCode : public UCodeInterface
{
public:
CARDUCode(DSPHLE* dsphle, u32 crc);

View File

@@ -82,7 +82,7 @@ void ProcessGBACrypto(u32 address)
*(u32*)sec_params.unk1, *(u32*)sec_params.unk2, x22, x23);
}
GBAUCode::GBAUCode(DSPHLE* dsphle, u32 crc): UCodeInterface(dsphle, crc)
GBAUCode::GBAUCode(DSPHLE* dsphle, u32 crc) : UCodeInterface(dsphle, crc)
{
m_mail_handler.PushMail(DSP_INIT);
}

View File

@@ -11,7 +11,7 @@
// written back to RAM at the dest address provided in the crypto parameters.
void ProcessGBACrypto(u32 address);
struct GBAUCode: public UCodeInterface
struct GBAUCode : public UCodeInterface
{
GBAUCode(DSPHLE* dsphle, u32 crc);
virtual ~GBAUCode();

View File

@@ -7,20 +7,24 @@
#include "Common/Logging/Log.h"
#include "Core/HW/DSPHLE/UCodes/UCodes.h"
INITUCode::INITUCode(DSPHLE* dsphle, u32 crc): UCodeInterface(dsphle, crc)
INITUCode::INITUCode(DSPHLE* dsphle, u32 crc) : UCodeInterface(dsphle, crc)
{
DEBUG_LOG(DSPHLE, "INITUCode - initialized");
m_mail_handler.PushMail(0x80544348);
}
INITUCode::~INITUCode()
{}
{
}
void INITUCode::Init()
{}
{
}
void INITUCode::Update()
{}
{
}
void INITUCode::HandleMail(u32 mail)
{}
{
}

View File

@@ -6,7 +6,7 @@
#include "Core/HW/DSPHLE/UCodes/UCodes.h"
class INITUCode: public UCodeInterface
class INITUCode : public UCodeInterface
{
public:
INITUCode(DSPHLE* dsphle, u32 crc);

View File

@@ -27,10 +27,12 @@ ROMUCode::ROMUCode(DSPHLE* dsphle, u32 crc)
}
ROMUCode::~ROMUCode()
{}
{
}
void ROMUCode::Update()
{}
{
}
void ROMUCode::HandleMail(u32 mail)
{

View File

@@ -6,7 +6,7 @@
#include "Core/HW/DSPHLE/UCodes/UCodes.h"
class ROMUCode: public UCodeInterface
class ROMUCode : public UCodeInterface
{
public:
ROMUCode(DSPHLE* dsphle, u32 crc);

View File

@@ -47,13 +47,13 @@ UCodeInterface* UCodeFactory(u32 crc, DSPHLE* dsphle, bool wii)
case 0x3ad3b7ac: // Naruto 3, Paper Mario - The Thousand Year Door
case 0x3daf59b9: // Alien Hominid
case 0x4e8a8b21: // spdemo, Crazy Taxi, 18 Wheeler, Disney, Monkeyball 1/2, Cubivore, Nintendo
// Puzzle Collection, Wario,
// Puzzle Collection, Wario,
// Capcom vs. SNK 2, Naruto 2, Lost Kingdoms, Star Fox, Mario Party 4, Mortal Kombat,
// Smugglers Run Warzone, Smash Brothers, Sonic Mega Collection, ZooCube
// nddemo, Star Fox
case 0x07f88145: // bustamove, Ikaruga, F-Zero GX, Robotech Battle Cry, Star Soldier, Soul
// Calibur 2,
// Zelda:OOT, Tony Hawk, Viewtiful Joe
// Calibur 2,
// Zelda:OOT, Tony Hawk, Viewtiful Joe
case 0xe2136399: // Billy Hatcher, Dragon Ball Z, Mario Party 5, TMNT, 1080° Avalanche
case 0x3389a79e: // MP1/MP2 Wii (Metroid Prime Trilogy)
INFO_LOG(DSPHLE, "CRC %08x: AX ucode chosen", crc);

View File

@@ -69,21 +69,15 @@ public:
: m_mail_handler(dsphle->AccessMailHandler()), m_upload_setup_in_progress(false),
m_dsphle(dsphle), m_crc(crc), m_next_ucode(), m_next_ucode_steps(0),
m_needs_resume_mail(false)
{}
{
}
virtual ~UCodeInterface()
{}
virtual ~UCodeInterface() {}
virtual void HandleMail(u32 mail) = 0;
virtual void Update() = 0;
virtual void DoState(PointerWrap& p)
{
DoStateShared(p);
}
static u32 GetCRC(UCodeInterface* ucode)
{
return ucode ? ucode->m_crc : UCODE_NULL;
}
virtual void DoState(PointerWrap& p) { DoStateShared(p); }
static u32 GetCRC(UCodeInterface* ucode) { return ucode ? ucode->m_crc : UCODE_NULL; }
protected:
void PrepareBootUCode(u32 mail);

View File

@@ -69,7 +69,7 @@ enum ZeldaUCodeFlag
static const std::map<u32, u32> UCODE_FLAGS = {
// GameCube IPL/BIOS, NTSC.
{0x24B22038, LIGHT_PROTOCOL | FOUR_MIXING_DESTS | TINY_VPB | VOLUME_EXPLICIT_STEP | NO_CMD_0D |
WEIRD_CMD_0C},
WEIRD_CMD_0C},
// GameCube IPL/BIOS, PAL.
{0x6BA3B3EA, LIGHT_PROTOCOL | FOUR_MIXING_DESTS | NO_CMD_0D | WEIRD_CMD_0C},
// Pikmin 1 GC NTSC.
@@ -109,7 +109,7 @@ static const std::map<u32, u32> UCODE_FLAGS = {
// * The Legend of Zelda: Twilight Princess / Wii (type ????, CRC ????)
};
ZeldaUCode::ZeldaUCode(DSPHLE* dsphle, u32 crc): UCodeInterface(dsphle, crc)
ZeldaUCode::ZeldaUCode(DSPHLE* dsphle, u32 crc) : UCodeInterface(dsphle, crc)
{
auto it = UCODE_FLAGS.find(crc);
if (it == UCODE_FLAGS.end())
@@ -694,14 +694,8 @@ struct ZeldaAudioRenderer::VPB
// (left/right) and Y (front/back) coordinates of the sound. 0x00 is all
// right/back, 0x7F is all left/front. Format is 0XXXXXXX0YYYYYYY.
u16 dolby_voice_position;
u8 GetDolbyVoiceX() const
{
return (dolby_voice_position >> 8) & 0x7F;
}
u8 GetDolbyVoiceY() const
{
return dolby_voice_position & 0x7F;
}
u8 GetDolbyVoiceX() const { return (dolby_voice_position >> 8) & 0x7F; }
u8 GetDolbyVoiceY() const { return dolby_voice_position & 0x7F; }
// How much reverbation to apply to the Dolby mixed voice. 0 is none,
// 0x7FFF is the maximum value.
s16 dolby_reverb_factor;
@@ -774,14 +768,8 @@ struct ZeldaAudioRenderer::VPB
// requires the two latest sample values to be able to decode future
// samples.
s16 afc_remaining_samples[0x10];
s16* AFCYN2()
{
return &afc_remaining_samples[0xE];
}
s16* AFCYN1()
{
return &afc_remaining_samples[0xF];
}
s16* AFCYN2() { return &afc_remaining_samples[0xE]; }
s16* AFCYN1() { return &afc_remaining_samples[0xF]; }
u16 unk_68_80[0x80 - 0x68];
enum SamplesSourceType
@@ -1003,11 +991,11 @@ void ZeldaAudioRenderer::ApplyReverb(bool post_rendering)
// Each of the 4 RPBs maps to one of these buffers.
MixingBuffer* reverb_buffers[4] = {
&m_buf_unk0_reverb, &m_buf_unk1_reverb, &m_buf_front_left_reverb, &m_buf_front_right_reverb,
&m_buf_unk0_reverb, &m_buf_unk1_reverb, &m_buf_front_left_reverb, &m_buf_front_right_reverb,
};
std::array<s16, 8>* last8_samples_buffers[4] = {
&m_buf_unk0_reverb_last8, &m_buf_unk1_reverb_last8, &m_buf_front_left_reverb_last8,
&m_buf_front_right_reverb_last8,
&m_buf_unk0_reverb_last8, &m_buf_unk1_reverb_last8, &m_buf_front_left_reverb_last8,
&m_buf_front_right_reverb_last8,
};
u16* rpb_base_ptr = (u16*)HLEMemory_Get_Pointer(m_reverb_pb_base_addr);
@@ -1041,8 +1029,7 @@ void ZeldaAudioRenderer::ApplyReverb(bool post_rendering)
for (u16 i = 0; i < 8; ++i)
(*last8_samples_buffers[rpb_idx])[i] = buffer[0x50 + i];
auto ApplyFilter = [&]()
{
auto ApplyFilter = [&]() {
// Filter the buffer using provided coefficients.
for (u16 i = 0; i < 0x50; ++i)
{
@@ -1163,10 +1150,10 @@ void ZeldaAudioRenderer::AddVoice(u16 voice_id)
// Compute volume for each quadrant.
u16 shift_factor = (m_flags & MAKE_DOLBY_LOUDER) ? 15 : 16;
s16 quadrant_volumes[4] = {
(s16)((left_volume * front_volume) >> shift_factor),
(s16)((left_volume * back_volume) >> shift_factor),
(s16)((right_volume * front_volume) >> shift_factor),
(s16)((right_volume * back_volume) >> shift_factor),
(s16)((left_volume * front_volume) >> shift_factor),
(s16)((left_volume * back_volume) >> shift_factor),
(s16)((right_volume * front_volume) >> shift_factor),
(s16)((right_volume * back_volume) >> shift_factor),
};
// Compute the volume delta for each sample to match the difference
@@ -1196,15 +1183,15 @@ void ZeldaAudioRenderer::AddVoice(u16 voice_id)
s16 volume;
s16 volume_delta;
} buffers[8] = {
{&m_buf_front_left, quadrant_volumes[0], volume_deltas[0]},
{&m_buf_back_left, quadrant_volumes[1], volume_deltas[1]},
{&m_buf_front_right, quadrant_volumes[2], volume_deltas[2]},
{&m_buf_back_right, quadrant_volumes[3], volume_deltas[3]},
{&m_buf_front_left, quadrant_volumes[0], volume_deltas[0]},
{&m_buf_back_left, quadrant_volumes[1], volume_deltas[1]},
{&m_buf_front_right, quadrant_volumes[2], volume_deltas[2]},
{&m_buf_back_right, quadrant_volumes[3], volume_deltas[3]},
{&m_buf_front_left_reverb, reverb_volumes[0], reverb_volume_deltas[0]},
{&m_buf_back_left_reverb, reverb_volumes[1], reverb_volume_deltas[1]},
{&m_buf_front_right_reverb, reverb_volumes[2], reverb_volume_deltas[2]},
{&m_buf_back_right_reverb, reverb_volumes[3], reverb_volume_deltas[3]},
{&m_buf_front_left_reverb, reverb_volumes[0], reverb_volume_deltas[0]},
{&m_buf_back_left_reverb, reverb_volumes[1], reverb_volume_deltas[1]},
{&m_buf_front_right_reverb, reverb_volumes[2], reverb_volume_deltas[2]},
{&m_buf_back_right_reverb, reverb_volumes[3], reverb_volume_deltas[3]},
};
for (const auto& buffer : buffers)
{
@@ -1400,9 +1387,9 @@ void ZeldaAudioRenderer::LoadInputSamples(MixingBuffer* buffer, VPB* vpb)
bool variable_step;
};
std::map<u16, PatternInfo> samples_source_to_pattern = {
{VPB::SRC_CONST_PATTERN_0, {0, false}}, {VPB::SRC_CONST_PATTERN_0_VARIABLE_STEP, {0, true}},
{VPB::SRC_CONST_PATTERN_1, {1, false}}, {VPB::SRC_CONST_PATTERN_2, {2, false}},
{VPB::SRC_CONST_PATTERN_3, {3, false}},
{VPB::SRC_CONST_PATTERN_0, {0, false}}, {VPB::SRC_CONST_PATTERN_0_VARIABLE_STEP, {0, true}},
{VPB::SRC_CONST_PATTERN_1, {1, false}}, {VPB::SRC_CONST_PATTERN_2, {2, false}},
{VPB::SRC_CONST_PATTERN_3, {3, false}},
};
auto& pattern_info = samples_source_to_pattern[vpb->samples_source_type];
u16 pattern_offset = pattern_info.idx * PATTERN_SIZE;

View File

@@ -15,50 +15,17 @@ public:
void AddVoice(u16 voice_id);
void FinalizeFrame();
void SetFlags(u32 flags)
{
m_flags = flags;
}
void SetSineTable(std::array<s16, 0x80>&& sine_table)
{
m_sine_table = sine_table;
}
void SetConstPatterns(std::array<s16, 0x100>&& patterns)
{
m_const_patterns = patterns;
}
void SetResamplingCoeffs(std::array<s16, 0x100>&& coeffs)
{
m_resampling_coeffs = coeffs;
}
void SetAfcCoeffs(std::array<s16, 0x20>&& coeffs)
{
m_afc_coeffs = coeffs;
}
void SetVPBBaseAddress(u32 addr)
{
m_vpb_base_addr = addr;
}
void SetReverbPBBaseAddress(u32 addr)
{
m_reverb_pb_base_addr = addr;
}
void SetOutputVolume(u16 volume)
{
m_output_volume = volume;
}
void SetOutputLeftBufferAddr(u32 addr)
{
m_output_lbuf_addr = addr;
}
void SetOutputRightBufferAddr(u32 addr)
{
m_output_rbuf_addr = addr;
}
void SetARAMBaseAddr(u32 addr)
{
m_aram_base_addr = addr;
}
void SetFlags(u32 flags) { m_flags = flags; }
void SetSineTable(std::array<s16, 0x80>&& sine_table) { m_sine_table = sine_table; }
void SetConstPatterns(std::array<s16, 0x100>&& patterns) { m_const_patterns = patterns; }
void SetResamplingCoeffs(std::array<s16, 0x100>&& coeffs) { m_resampling_coeffs = coeffs; }
void SetAfcCoeffs(std::array<s16, 0x20>&& coeffs) { m_afc_coeffs = coeffs; }
void SetVPBBaseAddress(u32 addr) { m_vpb_base_addr = addr; }
void SetReverbPBBaseAddress(u32 addr) { m_reverb_pb_base_addr = addr; }
void SetOutputVolume(u16 volume) { m_output_volume = volume; }
void SetOutputLeftBufferAddr(u32 addr) { m_output_lbuf_addr = addr; }
void SetOutputRightBufferAddr(u32 addr) { m_output_rbuf_addr = addr; }
void SetARAMBaseAddr(u32 addr) { m_aram_base_addr = addr; }
void DoState(PointerWrap& p);
private:
@@ -215,7 +182,7 @@ private:
u32 m_reverb_pb_base_addr = 0;
};
class ZeldaUCode: public UCodeInterface
class ZeldaUCode : public UCodeInterface
{
public:
ZeldaUCode(DSPHLE* dsphle, u32 crc);
@@ -242,7 +209,7 @@ private:
// of the original DSP implementation is rewritten in an asynchronous/coro
// + state machine style. It is less readable, but the best we can do given
// our constraints.
enum class MailState: u32
enum class MailState : u32
{
WAITING,
RENDERING,
@@ -307,7 +274,7 @@ private:
void RunPendingCommands();
// Sends the two mails from DSP to CPU to ack the command execution.
enum class CommandAck: u32
enum class CommandAck : u32
{
STANDARD,
DONE_RENDERING,

View File

@@ -148,12 +148,12 @@ void DSPDebugInterface::InsertBLR(unsigned int address, unsigned int value)
int DSPDebugInterface::GetColor(unsigned int address)
{
static const int colors[6] = {
0xd0FFFF, // light cyan
0xFFd0d0, // light red
0xd8d8FF, // light blue
0xFFd0FF, // light purple
0xd0FFd0, // light green
0xFFFFd0, // light yellow
0xd0FFFF, // light cyan
0xFFd0d0, // light red
0xd8d8FF, // light blue
0xFFd0FF, // light purple
0xd0FFd0, // light green
0xFFFFd0, // light yellow
};
// Scan backwards so we don't miss it. Hm, actually, let's not - it looks pretty good.
@@ -194,4 +194,5 @@ void DSPDebugInterface::SetPC(unsigned int address)
}
void DSPDebugInterface::RunToBreakpoint()
{}
{
}

View File

@@ -9,17 +9,13 @@
#include "Common/CommonTypes.h"
#include "Common/DebugInterface.h"
class DSPDebugInterface final: public DebugInterface
class DSPDebugInterface final : public DebugInterface
{
public:
DSPDebugInterface()
{}
DSPDebugInterface() {}
std::string Disassemble(unsigned int address) override;
void GetRawMemoryString(int memory, unsigned int address, char* dest, int max_size) override;
int GetInstructionSize(int instruction) override
{
return 1;
}
int GetInstructionSize(int instruction) override { return 1; }
bool IsAlive() override;
bool IsBreakpoint(unsigned int address) override;
void SetBreakpoint(unsigned int address) override;
@@ -33,8 +29,7 @@ public:
unsigned int ReadInstruction(unsigned int address) override;
unsigned int GetPC() override;
void SetPC(unsigned int address) override;
void Step() override
{}
void Step() override {}
void RunToBreakpoint() override;
void InsertBLR(unsigned int address, unsigned int value) override;
int GetColor(unsigned int address) override;

View File

@@ -31,7 +31,8 @@
DSPLLE::DSPLLE()
: m_hDSPThread(), m_csDSPThreadActive(), m_bWii(false), m_bDSPThread(false),
m_bIsRunning(false), m_cycle_count(0)
{}
{
}
static Common::Event dspEvent;
static Common::Event ppcEvent;
@@ -165,11 +166,9 @@ bool DSPLLE::Initialize(bool bWii, bool bDSPThread)
return false;
// needs to be after DSPCore_Init for the dspjit ptr
if (NetPlay::IsNetPlayRunning() || Movie::IsMovieActive() || Core::g_want_determinism ||
!g_dsp_jit)
{
if (Core::g_want_determinism || !g_dsp_jit)
bDSPThread = false;
}
m_bWii = bWii;
m_bDSPThread = bDSPThread;
@@ -290,27 +289,26 @@ void DSPLLE::DSP_Update(int cycles)
return;
// Sound stream update job has been handled by AudioDMA routine, which is more efficient
/*
// This gets called VERY OFTEN. The soundstream update might be expensive so only do it 200
times per second or something.
int cycles_between_ss_update;
// This gets called VERY OFTEN. The soundstream update might be expensive so only do it 200
times per second or something.
int cycles_between_ss_update;
if (g_dspInitialize.bWii)
cycles_between_ss_update = 121500000 / 200;
else
cycles_between_ss_update = 81000000 / 200;
if (g_dspInitialize.bWii)
cycles_between_ss_update = 121500000 / 200;
else
cycles_between_ss_update = 81000000 / 200;
m_cycle_count += cycles;
if (m_cycle_count > cycles_between_ss_update)
{
while (m_cycle_count > cycles_between_ss_update)
m_cycle_count -= cycles_between_ss_update;
soundStream->Update();
}
m_cycle_count += cycles;
if (m_cycle_count > cycles_between_ss_update)
{
while (m_cycle_count > cycles_between_ss_update)
m_cycle_count -= cycles_between_ss_update;
soundStream->Update();
}
*/
if (m_bDSPThread)
{
if (requestDisableThread || NetPlay::IsNetPlayRunning() || Movie::IsMovieActive() ||
Core::g_want_determinism)
if (requestDisableThread || Core::g_want_determinism)
{
DSP_StopSoundStream();
m_bDSPThread = false;

View File

@@ -13,17 +13,14 @@
class PointerWrap;
class DSPLLE: public DSPEmulator
class DSPLLE : public DSPEmulator
{
public:
DSPLLE();
bool Initialize(bool bWii, bool bDSPThread) override;
void Shutdown() override;
bool IsLLE() override
{
return true;
}
bool IsLLE() override { return true; }
void DoState(PointerWrap& p) override;
void PauseAndLock(bool doLock, bool unpauseOnUnlock = true) override;

View File

@@ -11,13 +11,11 @@
namespace DSPSymbols
{
class DSPSymbolDB: public SymbolDB
class DSPSymbolDB : public SymbolDB
{
public:
DSPSymbolDB()
{}
~DSPSymbolDB()
{}
DSPSymbolDB() {}
~DSPSymbolDB() {}
Symbol* GetSymbolFromAddr(u32 addr) override;
};

View File

@@ -28,6 +28,7 @@
#include "Core/IPC_HLE/WII_IPC_HLE_Device_DI.h"
#include "Core/Movie.h"
#include "DiscIO/Enums.h"
#include "DiscIO/Volume.h"
#include "DiscIO/VolumeCreator.h"
@@ -107,8 +108,7 @@ enum
};
// DI Status Register
union UDISR
{
union UDISR {
u32 Hex;
struct
{
@@ -121,19 +121,12 @@ union UDISR
u32 BRKINT : 1; // w 1: clear brkint
u32 : 25;
};
UDISR()
{
Hex = 0;
}
UDISR(u32 _hex)
{
Hex = _hex;
}
UDISR() { Hex = 0; }
UDISR(u32 _hex) { Hex = _hex; }
};
// DI Cover Register
union UDICVR
{
union UDICVR {
u32 Hex;
struct
{
@@ -142,18 +135,11 @@ union UDICVR
u32 CVRINT : 1; // r 1: Interrupt requested w 1: Interrupt clear
u32 : 29;
};
UDICVR()
{
Hex = 0;
}
UDICVR(u32 _hex)
{
Hex = _hex;
}
UDICVR() { Hex = 0; }
UDICVR(u32 _hex) { Hex = _hex; }
};
union UDICMDBUF
{
union UDICMDBUF {
u32 Hex;
struct
{
@@ -165,8 +151,7 @@ union UDICMDBUF
};
// DI DMA Address Register
union UDIMAR
{
union UDIMAR {
u32 Hex;
struct
{
@@ -181,8 +166,7 @@ union UDIMAR
};
// DI DMA Address Length Register
union UDILENGTH
{
union UDILENGTH {
u32 Hex;
struct
{
@@ -197,8 +181,7 @@ union UDILENGTH
};
// DI DMA Control Register
union UDICR
{
union UDICR {
u32 Hex;
struct
{
@@ -209,8 +192,7 @@ union UDICR
};
};
union UDIIMMBUF
{
union UDIIMMBUF {
u32 Hex;
struct
{
@@ -222,22 +204,15 @@ union UDIIMMBUF
};
// DI Config Register
union UDICFG
{
union UDICFG {
u32 Hex;
struct
{
u32 CONFIG : 8;
u32 : 24;
};
UDICFG()
{
Hex = 0;
}
UDICFG(u32 _hex)
{
Hex = _hex;
}
UDICFG() { Hex = 0; }
UDICFG(u32 _hex) { Hex = _hex; }
};
static std::unique_ptr<DiscIO::IVolume> s_inserted_volume;
@@ -357,8 +332,7 @@ static u32 ProcessDTKSamples(short* tempPCM, u32 num_samples)
s_audio_position += sizeof(tempADPCM);
StreamADPCM::DecodeBlock(tempPCM + samples_processed * 2, tempADPCM);
samples_processed += StreamADPCM::SAMPLES_PER_BLOCK;
}
while (samples_processed < num_samples);
} while (samples_processed < num_samples);
for (unsigned i = 0; i < samples_processed * 2; ++i)
{
// TODO: Fix the mixer so it can accept non-byte-swapped samples.
@@ -502,10 +476,20 @@ static void InsertDiscCallback(u64 userdata, s64 cyclesLate)
delete _FileName;
}
void ChangeDisc(const std::string& newFileName)
// Can only be called by the host thread
void ChangeDiscAsHost(const std::string& newFileName)
{
// WARNING: Can only run on Host Thread
bool was_unpaused = Core::PauseAndLock(true);
// The host thread is now temporarily the CPU thread
ChangeDiscAsCPU(newFileName);
Core::PauseAndLock(false, was_unpaused);
}
// Can only be called by the CPU thread
void ChangeDiscAsCPU(const std::string& newFileName)
{
std::string* _FileName = new std::string(newFileName);
CoreTiming::ScheduleEvent(0, s_eject_disc);
CoreTiming::ScheduleEvent(500000000, s_insert_disc, (u64)_FileName);
@@ -522,7 +506,6 @@ void ChangeDisc(const std::string& newFileName)
}
Movie::g_discChange = fileName.substr(sizeofpath);
}
Core::PauseAndLock(false, was_unpaused);
}
void SetLidOpen(bool open)
@@ -541,8 +524,7 @@ bool ChangePartition(u64 offset)
void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
{
mmio->Register(base | DI_STATUS_REGISTER, MMIO::DirectRead<u32>(&s_DISR.Hex),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
UDISR tmpStatusReg(val);
s_DISR.DEINITMASK = tmpStatusReg.DEINITMASK;
@@ -568,8 +550,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
}));
mmio->Register(base | DI_COVER_REGISTER, MMIO::DirectRead<u32>(&s_DICVR.Hex),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
UDICVR tmpCoverReg(val);
s_DICVR.CVRINTMASK = tmpCoverReg.CVRINTMASK;
@@ -594,8 +575,7 @@ void RegisterMMIO(MMIO::Mapping* mmio, u32 base)
mmio->Register(base | DI_DMA_LENGTH_REGISTER, MMIO::DirectRead<u32>(&s_DILENGTH.Hex),
MMIO::DirectWrite<u32>(&s_DILENGTH.Hex, ~0x1F));
mmio->Register(base | DI_DMA_CONTROL_REGISTER, MMIO::DirectRead<u32>(&s_DICR.Hex),
MMIO::ComplexWrite<u32>([](u32, u32 val)
{
MMIO::ComplexWrite<u32>([](u32, u32 val) {
s_DICR.Hex = val & 7;
if (s_DICR.TSTART)
{
@@ -970,7 +950,7 @@ void ExecuteCommand(u32 command_0, u32 command_1, u32 command_2, u32 output_addr
/*
if (iDVDOffset == 0x84800000)
{
ERROR_LOG(DVDINTERFACE, "Firmware upload");
ERROR_LOG(DVDINTERFACE, "Firmware upload");
}
else*/
if ((offset < 0) || ((offset + len) > 0x40) || len > 0x40)
@@ -1441,7 +1421,7 @@ s64 CalculateRawDiscReadTime(u64 offset, s64 length)
// Note that the speed at a track (in bytes per second) is the same as
// the radius of that track because of the length unit used.
double speed;
if (s_inserted_volume->GetVolumeType() == DiscIO::IVolume::WII_DISC)
if (s_inserted_volume->GetVolumeType() == DiscIO::Platform::WII_DISC)
{
speed = std::sqrt(((average_offset - WII_DISC_LOCATION_1_OFFSET) / WII_BYTES_PER_AREA_UNIT +
WII_DISC_AREA_UP_TO_LOCATION_1) /

View File

@@ -84,7 +84,7 @@ enum DICommand
DVDLowAudioBufferConfig = 0xe4
};
enum DIInterruptType: int
enum DIInterruptType : int
{
INT_DEINT = 0,
INT_TCINT = 1,
@@ -108,7 +108,8 @@ bool VolumeIsValid();
// Disc detection and swapping
void SetDiscInside(bool _DiscInside);
bool IsDiscInside();
void ChangeDisc(const std::string& fileName); // [NOT THREADSAFE] Host only
void ChangeDiscAsHost(const std::string& path); // Can only be called by the host thread
void ChangeDiscAsCPU(const std::string& path); // Can only be called by the CPU thread
// DVD Access Functions
bool ChangePartition(u64 offset);

View File

@@ -9,7 +9,7 @@
class CEXIChannel;
class IEXIDevice;
class PointerWrap;
enum TEXIDevices: int;
enum TEXIDevices : int;
namespace MMIO
{
class Mapping;

View File

@@ -44,8 +44,7 @@ void CEXIChannel::RegisterMMIO(MMIO::Mapping* mmio, u32 base)
// Warning: the base is not aligned on a page boundary here. We can't use |
// to select a register address, instead we need to use +.
mmio->Register(base + EXI_STATUS, MMIO::ComplexRead<u32>([this](u32)
{
mmio->Register(base + EXI_STATUS, MMIO::ComplexRead<u32>([this](u32) {
// check if external device is present
// pretty sure it is memcard only, not entirely sure
if (m_ChannelId == 2)
@@ -59,8 +58,7 @@ void CEXIChannel::RegisterMMIO(MMIO::Mapping* mmio, u32 base)
return m_Status.Hex;
}),
MMIO::ComplexWrite<u32>([this](u32, u32 val)
{
MMIO::ComplexWrite<u32>([this](u32, u32 val) {
UEXI_STATUS newStatus(val);
m_Status.EXIINTMASK = newStatus.EXIINTMASK;
@@ -97,8 +95,7 @@ void CEXIChannel::RegisterMMIO(MMIO::Mapping* mmio, u32 base)
mmio->Register(base + EXI_DMALENGTH, MMIO::DirectRead<u32>(&m_DMALength),
MMIO::DirectWrite<u32>(&m_DMALength));
mmio->Register(base + EXI_DMACONTROL, MMIO::DirectRead<u32>(&m_Control.Hex),
MMIO::ComplexWrite<u32>([this](u32, u32 val)
{
MMIO::ComplexWrite<u32>([this](u32, u32 val) {
m_Control.Hex = val;
if (m_Control.TSTART)

View File

@@ -9,7 +9,7 @@
class IEXIDevice;
class PointerWrap;
enum TEXIDevices: int;
enum TEXIDevices : int;
namespace MMIO
{
class Mapping;
@@ -28,8 +28,7 @@ private:
};
// EXI Status Register - "Channel Parameter Register"
union UEXI_STATUS
{
union UEXI_STATUS {
u32 Hex;
// DO NOT obey the warning and give this struct a name. Things will fail.
struct
@@ -50,19 +49,12 @@ private:
u32 ROMDIS : 1; // ROM Disable
u32 : 18;
};
UEXI_STATUS()
{
Hex = 0;
}
UEXI_STATUS(u32 _hex)
{
Hex = _hex;
}
UEXI_STATUS() { Hex = 0; }
UEXI_STATUS(u32 _hex) { Hex = _hex; }
};
// EXI Control Register
union UEXI_CONTROL
{
union UEXI_CONTROL {
u32 Hex;
struct
{
@@ -116,8 +108,5 @@ public:
void PauseAndLock(bool doLock, bool unpauseOnUnlock);
// This should only be used to transition interrupts from SP1 to Channel 2
void SetEXIINT(bool exiint)
{
m_Status.EXIINT = !!exiint;
}
void SetEXIINT(bool exiint) { m_Status.EXIINT = !!exiint; }
};

View File

@@ -67,17 +67,14 @@ void IEXIDevice::DMARead(u32 _uAddr, u32 _uSize)
// Just a dummy that logs reads and writes
// to be used for EXI devices we haven't emulated
// DOES NOT FUNCTION AS "NO DEVICE INSERTED" -> Appears as unknown device
class CEXIDummy: public IEXIDevice
class CEXIDummy : public IEXIDevice
{
std::string m_strName;
void TransferByte(u8& _byte) override
{}
void TransferByte(u8& _byte) override {}
public:
CEXIDummy(const std::string& _strName): m_strName(_strName)
{}
virtual ~CEXIDummy()
{}
CEXIDummy(const std::string& _strName) : m_strName(_strName) {}
virtual ~CEXIDummy() {}
void ImmWrite(u32 data, u32 size) override
{
INFO_LOG(EXPANSIONINTERFACE, "EXI DUMMY %s ImmWrite: %08x", m_strName.c_str(), data);
@@ -97,10 +94,7 @@ public:
INFO_LOG(EXPANSIONINTERFACE, "EXI DUMMY %s DMARead: %08x bytes, from device to %08x",
m_strName.c_str(), size, addr);
}
bool IsPresent() const override
{
return true;
}
bool IsPresent() const override { return true; }
};
// F A C T O R Y

View File

@@ -9,7 +9,7 @@
class PointerWrap;
enum TEXIDevices: int
enum TEXIDevices : int
{
EXIDEVICE_DUMMY,
EXIDEVICE_MEMORYCARD,
@@ -20,53 +20,38 @@ enum TEXIDevices: int
EXIDEVICE_AM_BASEBOARD,
EXIDEVICE_GECKO,
EXIDEVICE_MEMORYCARDFOLDER, // Only used when creating a device by EXIDevice_Create
// Converted to EXIDEVICE_MEMORYCARD internally
EXIDEVICE_AGP,
EXIDEVICE_NONE = (u8)-1
// Converted to EXIDEVICE_MEMORYCARD internally
EXIDEVICE_AGP,
EXIDEVICE_NONE = (u8)-1
};
class IEXIDevice
{
private:
// Byte transfer function for this device
virtual void TransferByte(u8&)
{}
virtual void TransferByte(u8&) {}
public:
// Immediate copy functions
virtual void ImmWrite(u32 _uData, u32 _uSize);
virtual u32 ImmRead(u32 _uSize);
virtual void ImmReadWrite(u32& /*_uData*/, u32 /*_uSize*/)
{}
virtual void ImmReadWrite(u32& /*_uData*/, u32 /*_uSize*/) {}
// DMA copy functions
virtual void DMAWrite(u32 _uAddr, u32 _uSize);
virtual void DMARead(u32 _uAddr, u32 _uSize);
virtual bool UseDelayedTransferCompletion() const
{
return false;
}
virtual bool IsPresent() const
{
return false;
}
virtual void SetCS(int)
{}
virtual void DoState(PointerWrap&)
{}
virtual void PauseAndLock(bool doLock, bool unpauseOnUnlock = true)
{}
virtual bool UseDelayedTransferCompletion() const { return false; }
virtual bool IsPresent() const { return false; }
virtual void SetCS(int) {}
virtual void DoState(PointerWrap&) {}
virtual void PauseAndLock(bool doLock, bool unpauseOnUnlock = true) {}
virtual IEXIDevice* FindDevice(TEXIDevices device_type, int customIndex = -1)
{
return (device_type == m_deviceType) ? this : nullptr;
}
// Is generating interrupt ?
virtual bool IsInterruptSet()
{
return false;
}
virtual ~IEXIDevice()
{}
virtual bool IsInterruptSet() { return false; }
virtual ~IEXIDevice() {}
// for savestates. storing it here seemed cleaner than requiring each implementation to report its
// type.
// I know this class is set up like an interface, but no code requires it to be strictly such.

View File

@@ -7,7 +7,7 @@
#include "Common/ChunkFile.h"
#include "Common/CommonTypes.h"
CEXIAD16::CEXIAD16(): m_uPosition(0), m_uCommand(0)
CEXIAD16::CEXIAD16() : m_uPosition(0), m_uCommand(0)
{
m_uAD16Register.U32 = 0x00;
}

View File

@@ -8,7 +8,7 @@
class PointerWrap;
class CEXIAD16: public IEXIDevice
class CEXIAD16 : public IEXIDevice
{
public:
CEXIAD16();
@@ -24,8 +24,7 @@ private:
read = 0xa2
};
union UAD16Reg
{
union UAD16Reg {
u32 U32;
u32 U8[4];
};

View File

@@ -218,7 +218,7 @@ u32 CEXIAgp::ImmRead(u32 _uSize)
}
break;
case 0xAE040000: // read 1 byte from 16 bit address
// ToDo: Flash special handling
// ToDo: Flash special handling
if (m_eeprom_size == 0)
RomVal1 = 0xFF;
else
@@ -228,7 +228,7 @@ u32 CEXIAgp::ImmRead(u32 _uSize)
m_current_cmd = 0;
break;
case 0xAE0B0000: // read 1 bit from DMA with 6 or 14 bit address
// Change to byte access instead of endian file access?
// Change to byte access instead of endian file access?
RomVal1 = EE_READ_FALSE;
if ((m_eeprom_size != 0) && (m_eeprom_pos >= EE_IGNORE_BITS) &&
((((u64*)m_eeprom.data())[(m_eeprom_cmd >> 1) & m_eeprom_add_mask]) >>
@@ -271,7 +271,7 @@ void CEXIAgp::ImmWrite(u32 _uData, u32 _uSize)
{
case 0xAE020000: // set up 24 bit address for read 2 bytes
case 0xAE030000: // set up 24 bit address for read (0x10000 byte group)
// 25 bit address shifted one bit right = 24 bits
// 25 bit address shifted one bit right = 24 bits
m_rw_offset = ((_uData & 0xFFFFFF00) >> (8 - 1));
m_return_pos = 0;
HashCmd = (_uData & 0xFF000000) >> 24;
@@ -282,7 +282,7 @@ void CEXIAgp::ImmWrite(u32 _uData, u32 _uSize)
CRC8(&HashCmd, 1);
break;
case 0xAE040000: // set up 16 bit address for read 1 byte
// ToDo: Flash special handling
// ToDo: Flash special handling
m_eeprom_pos = ((_uData & 0xFFFF0000) >> 0x10) & m_eeprom_mask;
HashCmd = (_uData & 0xFF000000) >> 24;
CRC8(&HashCmd, 1);
@@ -290,7 +290,7 @@ void CEXIAgp::ImmWrite(u32 _uData, u32 _uSize)
CRC8(&HashCmd, 1);
break;
case 0xAE070000: // write 1 byte from 16 bit address
// ToDo: Flash special handling
// ToDo: Flash special handling
m_eeprom_pos = ((_uData & 0xFFFF0000) >> 0x10) & m_eeprom_mask;
if (m_eeprom_size != 0)
((m_eeprom.data()))[(m_eeprom_pos)] = (_uData & 0x0000FF00) >> 0x8;
@@ -341,7 +341,7 @@ void CEXIAgp::ImmWrite(u32 _uData, u32 _uSize)
case 0xAE010000:
case 0xAE090000: // start DMA
m_eeprom_write_status = false; // ToDo: Verify with hardware which commands disable EEPROM CS
// Fall-through intentional
// Fall-through intentional
case 0xAE0A0000: // end DMA
m_eeprom_pos = 0;
// Fall-through intentional

View File

@@ -11,15 +11,12 @@
class PointerWrap;
class CEXIAgp: public IEXIDevice
class CEXIAgp : public IEXIDevice
{
public:
CEXIAgp(const int index);
virtual ~CEXIAgp() override;
bool IsPresent() const override
{
return true;
}
bool IsPresent() const override { return true; }
void ImmWrite(u32 _uData, u32 _uSize) override;
u32 ImmRead(u32 _uSize) override;
void DoState(PointerWrap& p) override;

View File

@@ -8,8 +8,9 @@
#include "Common/Logging/Log.h"
#include "Core/HW/EXI_DeviceAMBaseboard.h"
CEXIAMBaseboard::CEXIAMBaseboard(): m_position(0), m_have_irq(false)
{}
CEXIAMBaseboard::CEXIAMBaseboard() : m_position(0), m_have_irq(false)
{
}
void CEXIAMBaseboard::SetCS(int cs)
{
@@ -27,25 +28,25 @@ void CEXIAMBaseboard::TransferByte(u8& _byte)
{
/*
ID:
00 00 xx xx xx xx
xx xx 06 04 10 00
00 00 xx xx xx xx
xx xx 06 04 10 00
CMD:
01 00 00 b3 xx
xx xx xx xx 04
01 00 00 b3 xx
xx xx xx xx 04
exi_lanctl_write:
ff 02 01 63 xx
xx xx xx xx 04
ff 02 01 63 xx
xx xx xx xx 04
exi_imr_read:
86 00 00 f5 xx xx xx
xx xx xx xx 04 rr rr
86 00 00 f5 xx xx xx
xx xx xx xx 04 rr rr
exi_imr_write:
87 80 5c 17 xx
xx xx xx xx 04
87 80 5c 17 xx
xx xx xx xx 04
exi_isr_read:
82 .. .. .. xx xx xx
xx xx xx xx 04 rr rr
3 byte command, 1 byte checksum
82 .. .. .. xx xx xx
xx xx xx xx 04 rr rr
3 byte command, 1 byte checksum
*/
DEBUG_LOG(SP1, "AM-BB > %02x", _byte);
if (m_position < 4)

View File

@@ -8,7 +8,7 @@
class PointerWrap;
class CEXIAMBaseboard: public IEXIDevice
class CEXIAMBaseboard : public IEXIDevice
{
public:
CEXIAMBaseboard();

View File

@@ -30,7 +30,7 @@ CEXIETHERNET::CEXIETHERNET()
// Parse MAC address from config, and generate a new one if it doesn't
// exist or can't be parsed.
std::string& mac_addr_setting = SConfig::GetInstance().m_bba_mac;
u8 mac_addr[MAC_ADDRESS_SIZE] = {0};
u8 mac_addr[MAC_ADDRESS_SIZE] = { 0 };
if (!StringToMacAddress(mac_addr_setting, mac_addr))
{
@@ -436,7 +436,7 @@ inline u8 CEXIETHERNET::HashIndex(u8* dest_eth_addr)
inline bool CEXIETHERNET::RecvMACFilter()
{
static u8 const broadcast[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
static u8 const broadcast[] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
// Accept all destination addrs?
if (mBbaMem[BBA_NCRB] & NCRB_PR)
@@ -522,13 +522,13 @@ bool CEXIETHERNET::RecvHandlePacket()
/*
halt copy
if (cur_packet_size >= PAGE_SIZE)
desc.status |= FO | BF
desc.status |= FO | BF
if (RBFIM)
raise RBFI
raise RBFI
if (AUTORCVR)
discard bad packet
discard bad packet
else
inc MPC instead of receiving packets
inc MPC instead of receiving packets
*/
status |= DESC_FO | DESC_BF;
mBbaMem[BBA_IR] |= mBbaMem[BBA_IMR] & INT_RBF;

View File

@@ -194,7 +194,7 @@ enum RecvStatus
#define BBA_RECV_SIZE 0x800
class CEXIETHERNET: public IEXIDevice
class CEXIETHERNET : public IEXIDevice
{
public:
CEXIETHERNET();
@@ -291,10 +291,7 @@ public:
return ((u16)mBbaMem[index + 1] << 8) | mBbaMem[index];
}
inline u8* ptr_from_page_ptr(int const index) const
{
return &mBbaMem[page_ptr(index) << 8];
}
inline u8* ptr_from_page_ptr(int const index) const { return &mBbaMem[page_ptr(index) << 8]; }
bool IsMXCommand(u32 const data);
bool IsWriteCommand(u32 const data);
const char* GetRegisterName() const;

View File

@@ -25,7 +25,7 @@ std::atomic<bool> GeckoSockServer::server_running;
std::mutex GeckoSockServer::connection_lock;
std::queue<std::unique_ptr<sf::TcpSocket>> GeckoSockServer::waiting_socks;
GeckoSockServer::GeckoSockServer(): client_running(false)
GeckoSockServer::GeckoSockServer() : client_running(false)
{
if (!connectionThread.joinable())
connectionThread = std::thread(GeckoConnectionWaiter);

View File

@@ -45,15 +45,11 @@ private:
static std::queue<std::unique_ptr<sf::TcpSocket>> waiting_socks;
};
class CEXIGecko: public IEXIDevice, private GeckoSockServer
class CEXIGecko : public IEXIDevice, private GeckoSockServer
{
public:
CEXIGecko()
{}
bool IsPresent() const override
{
return true;
}
CEXIGecko() {}
bool IsPresent() const override { return true; }
void ImmReadWrite(u32& _uData, u32 _uSize) override;
private:

View File

@@ -4,6 +4,7 @@
#include <cstring>
#include "Common/Assert.h"
#include "Common/ChunkFile.h"
#include "Common/CommonPaths.h"
#include "Common/CommonTypes.h"
@@ -12,6 +13,7 @@
#include "Common/MemoryUtil.h"
#include "Common/Timer.h"
#include "Core/ConfigManager.h"
#include "Core/Core.h"
#include "Core/CoreTiming.h"
#include "Core/HW/EXI_DeviceIPL.h"
#include "Core/HW/Sram.h"
@@ -83,7 +85,7 @@ void CEXIIPL::Descrambler(u8* data, u32 size)
}
}
CEXIIPL::CEXIIPL(): m_uPosition(0), m_uAddress(0), m_uRWOffset(0), m_FontsLoaded(false)
CEXIIPL::CEXIIPL() : m_uPosition(0), m_uAddress(0), m_uRWOffset(0), m_FontsLoaded(false)
{
// Determine region
m_bNTSC = SConfig::GetInstance().bNTSC;
@@ -421,6 +423,7 @@ u32 CEXIIPL::GetGCTime()
}
else
{
_assert_(!Core::g_want_determinism);
ltime = Common::Timer::GetLocalTimeSinceJan1970();
}

View File

@@ -10,7 +10,7 @@
class PointerWrap;
class CEXIIPL: public IEXIDevice
class CEXIIPL : public IEXIDevice
{
public:
CEXIIPL();
@@ -67,14 +67,8 @@ private:
void UpdateRTC();
void TransferByte(u8& _uByte) override;
bool IsWriteCommand() const
{
return !!(m_uAddress & (1 << 31));
}
u32 CommandRegion() const
{
return (m_uAddress & ~(1 << 31)) >> 8;
}
bool IsWriteCommand() const { return !!(m_uAddress & (1 << 31)); }
u32 CommandRegion() const { return (m_uAddress & ~(1 << 31)) >> 8; }
void LoadFileToIPL(const std::string& filename, u32 offset);
void LoadFontFile(const std::string& filename, u32 offset);
std::string FindIPLDump(const std::string& path_prefix);

View File

@@ -27,6 +27,7 @@
#include "Core/HW/Sram.h"
#include "Core/HW/SystemTimers.h"
#include "Core/Movie.h"
#include "DiscIO/Enums.h"
#include "DiscIO/NANDContentLoader.h"
#define MC_STATUS_BUSY 0x80
@@ -60,29 +61,23 @@ void CEXIMemoryCard::EventCompleteFindInstance(u64 userdata,
void CEXIMemoryCard::CmdDoneCallback(u64 userdata, s64 cyclesLate)
{
EventCompleteFindInstance(userdata, [](CEXIMemoryCard* instance)
{
instance->CmdDone();
});
EventCompleteFindInstance(userdata, [](CEXIMemoryCard* instance) { instance->CmdDone(); });
}
void CEXIMemoryCard::TransferCompleteCallback(u64 userdata, s64 cyclesLate)
{
EventCompleteFindInstance(userdata,
[](CEXIMemoryCard* instance)
{
instance->TransferComplete();
});
[](CEXIMemoryCard* instance) { instance->TransferComplete(); });
}
CEXIMemoryCard::CEXIMemoryCard(const int index, bool gciFolder): card_index(index)
CEXIMemoryCard::CEXIMemoryCard(const int index, bool gciFolder) : card_index(index)
{
struct
{
const char* done;
const char* transfer_complete;
} const event_names[] = {
{"memcardDoneA", "memcardTransferCompleteA"}, {"memcardDoneB", "memcardTransferCompleteB"},
{"memcardDoneA", "memcardTransferCompleteA"}, {"memcardDoneB", "memcardTransferCompleteB"},
};
if ((size_t)index >= ArraySize(event_names))
@@ -134,14 +129,14 @@ CEXIMemoryCard::CEXIMemoryCard(const int index, bool gciFolder): card_index(inde
}
memory_card_size = memorycard->GetCardId() * SIZE_TO_Mb;
u8 header[20] = {0};
u8 header[20] = { 0 };
memorycard->Read(0, static_cast<s32>(ArraySize(header)), header);
SetCardFlashID(header, card_index);
}
void CEXIMemoryCard::SetupGciFolder(u16 sizeMb)
{
DiscIO::IVolume::ECountry country_code = DiscIO::IVolume::COUNTRY_UNKNOWN;
DiscIO::Country country_code = DiscIO::Country::COUNTRY_UNKNOWN;
auto strUniqueID = SConfig::GetInstance().m_strUniqueID;
u32 CurrentGameId = 0;
@@ -164,14 +159,14 @@ void CEXIMemoryCard::SetupGciFolder(u16 sizeMb)
std::string strDirectoryName = File::GetUserPath(D_GCUSER_IDX);
switch (country_code)
{
case DiscIO::IVolume::COUNTRY_JAPAN:
case DiscIO::Country::COUNTRY_JAPAN:
ascii = false;
strDirectoryName += JAP_DIR DIR_SEP;
break;
case DiscIO::IVolume::COUNTRY_USA:
case DiscIO::Country::COUNTRY_USA:
strDirectoryName += USA_DIR DIR_SEP;
break;
case DiscIO::IVolume::COUNTRY_UNKNOWN:
case DiscIO::Country::COUNTRY_UNKNOWN:
{
// The current game's region is not passed down to the EXI device level.
// Usually, we can retrieve the region from SConfig::GetInstance().m_strUniqueId.
@@ -191,20 +186,20 @@ void CEXIMemoryCard::SetupGciFolder(u16 sizeMb)
std::string region = memcardFilename.substr(memcardFilename.size() - 7, 3);
if (region == JAP_DIR)
{
country_code = DiscIO::IVolume::COUNTRY_JAPAN;
country_code = DiscIO::Country::COUNTRY_JAPAN;
ascii = false;
strDirectoryName += JAP_DIR DIR_SEP;
break;
}
else if (region == USA_DIR)
{
country_code = DiscIO::IVolume::COUNTRY_USA;
country_code = DiscIO::Country::COUNTRY_USA;
strDirectoryName += USA_DIR DIR_SEP;
break;
}
}
default:
country_code = DiscIO::IVolume::COUNTRY_EUROPE;
country_code = DiscIO::Country::COUNTRY_EUROPE;
strDirectoryName += EUR_DIR DIR_SEP;
}
strDirectoryName += StringFromFormat("Card %c", 'A' + card_index);

View File

@@ -12,7 +12,7 @@
class MemoryCardBase;
class PointerWrap;
class CEXIMemoryCard: public IEXIDevice
class CEXIMemoryCard : public IEXIDevice
{
public:
CEXIMemoryCard(const int index, bool gciFolder);

View File

@@ -137,9 +137,9 @@ void CEXIMic::StreamReadOne()
// cmdGetBuffer, which is when we actually read data from a buffer filled
// in the background by Pa_Callback.
u8 const CEXIMic::exi_id[] = {0, 0x0a, 0, 0, 0};
u8 const CEXIMic::exi_id[] = { 0, 0x0a, 0, 0, 0 };
CEXIMic::CEXIMic(int index): slot(index)
CEXIMic::CEXIMic(int index) : slot(index)
{
m_position = 0;
command = 0;

View File

@@ -10,7 +10,7 @@
#if HAVE_PORTAUDIO
class CEXIMic: public IEXIDevice
class CEXIMic : public IEXIDevice
{
public:
CEXIMic(const int index);
@@ -38,8 +38,7 @@ private:
u32 m_position;
int command;
union UStatus
{
union UStatus {
u16 U16;
u8 U8[2];
struct
@@ -100,11 +99,10 @@ protected:
#else // HAVE_PORTAUDIO
class CEXIMic: public IEXIDevice
class CEXIMic : public IEXIDevice
{
public:
CEXIMic(const int)
{}
CEXIMic(const int) {}
};
#endif

View File

@@ -6,45 +6,45 @@
#include "Common/Common.h"
#include "InputCommon/KeyboardStatus.h"
static const u16 keys0_bitmasks[] = {KEYMASK_HOME, KEYMASK_END, KEYMASK_PGUP, KEYMASK_PGDN,
KEYMASK_SCROLLLOCK, KEYMASK_A, KEYMASK_B, KEYMASK_C,
KEYMASK_D, KEYMASK_E, KEYMASK_F, KEYMASK_G,
KEYMASK_H, KEYMASK_I, KEYMASK_J, KEYMASK_K};
static const u16 keys0_bitmasks[] = { KEYMASK_HOME, KEYMASK_END, KEYMASK_PGUP, KEYMASK_PGDN,
KEYMASK_SCROLLLOCK, KEYMASK_A, KEYMASK_B, KEYMASK_C,
KEYMASK_D, KEYMASK_E, KEYMASK_F, KEYMASK_G,
KEYMASK_H, KEYMASK_I, KEYMASK_J, KEYMASK_K };
static const u16 keys1_bitmasks[] = {
KEYMASK_L, KEYMASK_M, KEYMASK_N, KEYMASK_O, KEYMASK_P, KEYMASK_Q, KEYMASK_R, KEYMASK_S,
KEYMASK_T, KEYMASK_U, KEYMASK_V, KEYMASK_W, KEYMASK_X, KEYMASK_Y, KEYMASK_Z, KEYMASK_1};
KEYMASK_L, KEYMASK_M, KEYMASK_N, KEYMASK_O, KEYMASK_P, KEYMASK_Q, KEYMASK_R, KEYMASK_S,
KEYMASK_T, KEYMASK_U, KEYMASK_V, KEYMASK_W, KEYMASK_X, KEYMASK_Y, KEYMASK_Z, KEYMASK_1 };
static const u16 keys2_bitmasks[] = {
KEYMASK_2, KEYMASK_3, KEYMASK_4, KEYMASK_5,
KEYMASK_6, KEYMASK_7, KEYMASK_8, KEYMASK_9,
KEYMASK_0, KEYMASK_MINUS, KEYMASK_PLUS, KEYMASK_PRINTSCR,
KEYMASK_BRACE_OPEN, KEYMASK_BRACE_CLOSE, KEYMASK_COLON, KEYMASK_QUOTE};
KEYMASK_2, KEYMASK_3, KEYMASK_4, KEYMASK_5,
KEYMASK_6, KEYMASK_7, KEYMASK_8, KEYMASK_9,
KEYMASK_0, KEYMASK_MINUS, KEYMASK_PLUS, KEYMASK_PRINTSCR,
KEYMASK_BRACE_OPEN, KEYMASK_BRACE_CLOSE, KEYMASK_COLON, KEYMASK_QUOTE };
static const u16 keys3_bitmasks[] = {
KEYMASK_HASH, KEYMASK_COMMA, KEYMASK_PERIOD, KEYMASK_QUESTIONMARK, KEYMASK_INTERNATIONAL1,
KEYMASK_F1, KEYMASK_F2, KEYMASK_F3, KEYMASK_F4, KEYMASK_F5,
KEYMASK_F6, KEYMASK_F7, KEYMASK_F8, KEYMASK_F9, KEYMASK_F10,
KEYMASK_F11};
KEYMASK_HASH, KEYMASK_COMMA, KEYMASK_PERIOD, KEYMASK_QUESTIONMARK, KEYMASK_INTERNATIONAL1,
KEYMASK_F1, KEYMASK_F2, KEYMASK_F3, KEYMASK_F4, KEYMASK_F5,
KEYMASK_F6, KEYMASK_F7, KEYMASK_F8, KEYMASK_F9, KEYMASK_F10,
KEYMASK_F11 };
static const u16 keys4_bitmasks[] = {
KEYMASK_F12, KEYMASK_ESC, KEYMASK_INSERT, KEYMASK_DELETE,
KEYMASK_TILDE, KEYMASK_BACKSPACE, KEYMASK_TAB, KEYMASK_CAPSLOCK,
KEYMASK_LEFTSHIFT, KEYMASK_RIGHTSHIFT, KEYMASK_LEFTCONTROL, KEYMASK_RIGHTALT,
KEYMASK_LEFTWINDOWS, KEYMASK_SPACE, KEYMASK_RIGHTWINDOWS, KEYMASK_MENU};
static const u16 keys5_bitmasks[] = {KEYMASK_LEFTARROW, KEYMASK_DOWNARROW, KEYMASK_UPARROW,
KEYMASK_RIGHTARROW, KEYMASK_ENTER};
KEYMASK_F12, KEYMASK_ESC, KEYMASK_INSERT, KEYMASK_DELETE,
KEYMASK_TILDE, KEYMASK_BACKSPACE, KEYMASK_TAB, KEYMASK_CAPSLOCK,
KEYMASK_LEFTSHIFT, KEYMASK_RIGHTSHIFT, KEYMASK_LEFTCONTROL, KEYMASK_RIGHTALT,
KEYMASK_LEFTWINDOWS, KEYMASK_SPACE, KEYMASK_RIGHTWINDOWS, KEYMASK_MENU };
static const u16 keys5_bitmasks[] = { KEYMASK_LEFTARROW, KEYMASK_DOWNARROW, KEYMASK_UPARROW,
KEYMASK_RIGHTARROW, KEYMASK_ENTER };
static const char* const named_keys0[] = {"HOME", "END", "PGUP", "PGDN", "SCR LK", "A", "B", "C",
"D", "E", "F", "G", "H", "I", "J", "K"};
static const char* const named_keys1[] = {"L", "M", "N", "O", "P", "Q", "R", "S",
"T", "U", "V", "W", "X", "Y", "Z", "1"};
static const char* const named_keys2[] = {"2", "3", "4", "5", "6", "7", "8", "9",
"0", "-", "`", "PRT SC", "'", "[", "EQUALS", "*"};
static const char* const named_keys3[] = {"]", ",", ".", "/", "\\", "F1", "F2", "F3",
"F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11"};
static const char* const named_keys0[] = { "HOME", "END", "PGUP", "PGDN", "SCR LK", "A", "B", "C",
"D", "E", "F", "G", "H", "I", "J", "K" };
static const char* const named_keys1[] = { "L", "M", "N", "O", "P", "Q", "R", "S",
"T", "U", "V", "W", "X", "Y", "Z", "1" };
static const char* const named_keys2[] = { "2", "3", "4", "5", "6", "7", "8", "9",
"0", "-", "`", "PRT SC", "'", "[", "EQUALS", "*" };
static const char* const named_keys3[] = { "]", ",", ".", "/", "\\", "F1", "F2", "F3",
"F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11" };
static const char* const named_keys4[] = {
"F12", "ESC", "INSERT", "DELETE", ";", "BACKSPACE", "TAB", "CAPS LOCK",
"L SHIFT", "R SHIFT", "L CTRL", "R ALT", "L WIN", "SPACE", "R WIN", "MENU"};
static const char* const named_keys5[] = {"LEFT", "DOWN", "UP", "RIGHT", "ENTER"};
"F12", "ESC", "INSERT", "DELETE", ";", "BACKSPACE", "TAB", "CAPS LOCK",
"L SHIFT", "R SHIFT", "L CTRL", "R ALT", "L WIN", "SPACE", "R WIN", "MENU" };
static const char* const named_keys5[] = { "LEFT", "DOWN", "UP", "RIGHT", "ENTER" };
GCKeyboard::GCKeyboard(const unsigned int index): m_index(index)
GCKeyboard::GCKeyboard(const unsigned int index) : m_index(index)
{
// buttons
groups.emplace_back(m_keys0x = new Buttons(_trans("Keys")));
@@ -73,9 +73,10 @@ GCKeyboard::GCKeyboard(const unsigned int index): m_index(index)
// options
groups.emplace_back(m_options = new ControlGroup(_trans("Options")));
m_options->settings.emplace_back(
new ControlGroup::BackgroundInputSetting(_trans("Background Input")));
m_options->settings.emplace_back(new ControlGroup::IterateUI(_trans("Iterative Input")));
m_options->boolean_settings.emplace_back(
std::make_unique<ControlGroup::BackgroundInputSetting>(_trans("Background Input")));
m_options->boolean_settings.emplace_back(std::make_unique<ControlGroup::BooleanSetting>(
_trans("Iterative Input"), false, ControlGroup::SettingType::VIRTUAL));
}
std::string GCKeyboard::GetName() const

Some files were not shown because too many files have changed in this diff Show More