Compare commits
10 commits
0bb6e12cc4
...
245906e147
Author | SHA1 | Date | |
---|---|---|---|
245906e147 | |||
20663c774d | |||
324ace3cd6 | |||
33f93ad003 | |||
9f423a24b8 | |||
50ceb9a43a | |||
ecb811ad04 | |||
bf302d7917 | |||
d19a7c3782 | |||
c725641f13 |
25 changed files with 265 additions and 245 deletions
|
@ -10,7 +10,7 @@ if (-not ([bool](net session 2>$null))) {
|
|||
}
|
||||
|
||||
$VSVer = "17"
|
||||
$ExeFile = "vs_BuildTools.exe"
|
||||
$ExeFile = "vs_community.exe"
|
||||
$Uri = "https://aka.ms/vs/$VSVer/release/$ExeFile"
|
||||
$Destination = "./$ExeFile"
|
||||
|
||||
|
@ -19,21 +19,39 @@ $WebClient = New-Object System.Net.WebClient
|
|||
$WebClient.DownloadFile($Uri, $Destination)
|
||||
Write-Host "Finished downloading $ExeFile"
|
||||
|
||||
$VSROOT = "C:/VSBuildTools/$VSVer"
|
||||
$Arguments = @(
|
||||
"--installPath `"$VSROOT`"", # set custom installation path
|
||||
"--quiet", # suppress UI
|
||||
"--wait", # wait for installation to complete
|
||||
"--norestart", # prevent automatic restart
|
||||
"--add Microsoft.VisualStudio.Workload.VCTools", # add C++ build tools workload
|
||||
"--add Microsoft.VisualStudio.Component.VC.Tools.x86.x64", # add core x86/x64 C++ tools
|
||||
"--add Microsoft.VisualStudio.Component.Windows10SDK.19041" # add specific Windows SDK
|
||||
"--quiet", # Suppress installer UI
|
||||
"--wait", # Wait for installation to complete
|
||||
"--norestart", # Prevent automatic restart
|
||||
"--force", # Force installation even if components are already installed
|
||||
"--add Microsoft.VisualStudio.Workload.NativeDesktop", # Desktop development with C++
|
||||
"--add Microsoft.VisualStudio.Component.VC.Tools.x86.x64", # Core C++ compiler/tools for x86/x64
|
||||
"--add Microsoft.VisualStudio.Component.Windows11SDK.26100",# Windows 11 SDK (26100)
|
||||
"--add Microsoft.VisualStudio.Component.Windows10SDK.19041",# Windows 10 SDK (19041)
|
||||
"--add Microsoft.VisualStudio.Component.VC.Llvm.Clang", # LLVM Clang compiler
|
||||
"--add Microsoft.VisualStudio.Component.VC.Llvm.ClangToolset", # LLVM Clang integration toolset
|
||||
"--add Microsoft.VisualStudio.Component.Windows11SDK.22621",# Windows 11 SDK (22621)
|
||||
"--add Microsoft.VisualStudio.Component.VC.CMake.Project", # CMake project support
|
||||
"--add Microsoft.VisualStudio.ComponentGroup.VC.Tools.142.x86.x64", # VC++ 14.2 toolset
|
||||
"--add Microsoft.VisualStudio.ComponentGroup.NativeDesktop.Llvm.Clang" # LLVM Clang for native desktop
|
||||
)
|
||||
|
||||
Write-Host "Installing Visual Studio Build Tools"
|
||||
$InstallProcess = Start-Process -FilePath $Destination -NoNewWindow -PassThru -Wait -ArgumentList $Arguments
|
||||
$ExitCode = $InstallProcess.ExitCode
|
||||
$InstallProcess = Start-Process -FilePath $Destination -NoNewWindow -PassThru -ArgumentList $Arguments
|
||||
|
||||
# Spinner while installing
|
||||
$Spinner = "|/-\"
|
||||
$i = 0
|
||||
while (-not $InstallProcess.HasExited) {
|
||||
Write-Host -NoNewline ("`rInstalling... " + $Spinner[$i % $Spinner.Length])
|
||||
Start-Sleep -Milliseconds 250
|
||||
$i++
|
||||
}
|
||||
|
||||
# Clear spinner line
|
||||
Write-Host "`rSetup completed! "
|
||||
|
||||
$ExitCode = $InstallProcess.ExitCode
|
||||
if ($ExitCode -ne 0) {
|
||||
Write-Host "Error installing Visual Studio Build Tools (Error: $ExitCode)"
|
||||
Exit $ExitCode
|
||||
|
|
|
@ -895,13 +895,13 @@ if (MSVC AND CXX_CLANG)
|
|||
endif()
|
||||
|
||||
if (YUZU_USE_FASTER_LD)
|
||||
# fallback if everything fails (bfd)
|
||||
set(LINKER bfd)
|
||||
# clang should always use lld
|
||||
find_program(LLD lld)
|
||||
|
||||
if (LLD)
|
||||
set(LINKER lld)
|
||||
endif()
|
||||
|
||||
# GNU appears to work better with mold
|
||||
# TODO: mold has been slow lately, see if better options exist (search for gold?)
|
||||
if (CXX_GCC)
|
||||
|
@ -910,7 +910,6 @@ if (YUZU_USE_FASTER_LD)
|
|||
set(LINKER mold)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
message(NOTICE "Selecting ${LINKER} as linker")
|
||||
add_link_options("-fuse-ld=${LINKER}")
|
||||
endif()
|
||||
|
|
|
@ -4,8 +4,8 @@ To build Eden, you MUST have a C++ compiler.
|
|||
* On Linux, this is usually [GCC](https://gcc.gnu.org/) 11+ or [Clang](https://clang.llvm.org/) v14+
|
||||
- GCC 12 also requires Clang 14+
|
||||
* On Windows, this is either:
|
||||
- **[MSVC](https://visualstudio.microsoft.com/downloads/)**,
|
||||
* *A convenience script to install the **minimal** version (Visual Build Tools) is provided in `.ci/windows/install-msvc.ps1`*
|
||||
- **[MSVC](https://visualstudio.microsoft.com/downloads/)** (you should select *Community* option),
|
||||
* *A convenience script to install the Visual Community Studio 2022 with necessary tools is provided in `.ci/windows/install-msvc.ps1`*
|
||||
- clang-cl - can be downloaded from the MSVC installer,
|
||||
- or **[MSYS2](https://www.msys2.org)**
|
||||
* On macOS, this is Apple Clang
|
||||
|
@ -211,4 +211,4 @@ Then install the libraries: `sudo pkg install qt6 boost glslang libzip library/l
|
|||
|
||||
## All Done
|
||||
|
||||
You may now return to the **[root build guide](Build.md)**.
|
||||
You may now return to the **[root build guide](Build.md)**.
|
||||
|
|
|
@ -178,7 +178,7 @@ struct Values {
|
|||
SwitchableSetting<std::string> audio_input_device_id{
|
||||
linkage, "auto", "input_device", Category::Audio, Specialization::RuntimeList};
|
||||
SwitchableSetting<AudioMode, true> sound_index{
|
||||
linkage, AudioMode::Stereo, AudioMode::Mono, AudioMode::Surround,
|
||||
linkage, AudioMode::Stereo,
|
||||
"sound_index", Category::SystemAudio, Specialization::Default, true,
|
||||
true};
|
||||
SwitchableSetting<u8, true> volume{linkage,
|
||||
|
@ -199,8 +199,6 @@ struct Values {
|
|||
SwitchableSetting<bool> use_multi_core{linkage, true, "use_multi_core", Category::Core};
|
||||
SwitchableSetting<MemoryLayout, true> memory_layout_mode{linkage,
|
||||
MemoryLayout::Memory_4Gb,
|
||||
MemoryLayout::Memory_4Gb,
|
||||
MemoryLayout::Memory_12Gb,
|
||||
"memory_layout_mode",
|
||||
Category::Core,
|
||||
Specialization::Default,
|
||||
|
@ -240,9 +238,8 @@ struct Values {
|
|||
#endif
|
||||
"cpu_backend",
|
||||
Category::Cpu};
|
||||
SwitchableSetting<CpuAccuracy, true> cpu_accuracy{linkage, CpuAccuracy::Auto,
|
||||
CpuAccuracy::Auto, CpuAccuracy::Paranoid,
|
||||
"cpu_accuracy", Category::Cpu};
|
||||
SwitchableSetting<CpuAccuracy, true> cpu_accuracy{linkage, CpuAccuracy::Auto,
|
||||
"cpu_accuracy", Category::Cpu};
|
||||
|
||||
SwitchableSetting<bool> use_fast_cpu_time{linkage,
|
||||
false,
|
||||
|
@ -324,10 +321,10 @@ struct Values {
|
|||
|
||||
// Renderer
|
||||
SwitchableSetting<RendererBackend, true> renderer_backend{
|
||||
linkage, RendererBackend::Vulkan, RendererBackend::OpenGL, RendererBackend::Null,
|
||||
linkage, RendererBackend::Vulkan,
|
||||
"backend", Category::Renderer};
|
||||
SwitchableSetting<ShaderBackend, true> shader_backend{
|
||||
linkage, ShaderBackend::SpirV, ShaderBackend::Glsl, ShaderBackend::SpirV,
|
||||
linkage, ShaderBackend::SpirV,
|
||||
"shader_backend", Category::Renderer, Specialization::RuntimeList};
|
||||
SwitchableSetting<int> vulkan_device{linkage, 0, "vulkan_device", Category::Renderer,
|
||||
Specialization::RuntimeList};
|
||||
|
@ -342,8 +339,6 @@ struct Values {
|
|||
Category::Renderer};
|
||||
SwitchableSetting<SpirvOptimizeMode, true> optimize_spirv_output{linkage,
|
||||
SpirvOptimizeMode::Never,
|
||||
SpirvOptimizeMode::Never,
|
||||
SpirvOptimizeMode::Always,
|
||||
"optimize_spirv_output",
|
||||
Category::Renderer};
|
||||
SwitchableSetting<bool> use_asynchronous_gpu_emulation{
|
||||
|
@ -354,12 +349,10 @@ struct Values {
|
|||
#else
|
||||
AstcDecodeMode::Gpu,
|
||||
#endif
|
||||
AstcDecodeMode::Cpu,
|
||||
AstcDecodeMode::CpuAsynchronous,
|
||||
"accelerate_astc",
|
||||
Category::Renderer};
|
||||
SwitchableSetting<VSyncMode, true> vsync_mode{
|
||||
linkage, VSyncMode::Fifo, VSyncMode::Immediate, VSyncMode::FifoRelaxed,
|
||||
linkage, VSyncMode::Fifo,
|
||||
"use_vsync", Category::Renderer, Specialization::RuntimeList, true,
|
||||
true};
|
||||
SwitchableSetting<NvdecEmulation> nvdec_emulation{linkage, NvdecEmulation::Gpu,
|
||||
|
@ -372,8 +365,6 @@ struct Values {
|
|||
#else
|
||||
FullscreenMode::Exclusive,
|
||||
#endif
|
||||
FullscreenMode::Borderless,
|
||||
FullscreenMode::Exclusive,
|
||||
"fullscreen_mode",
|
||||
Category::Renderer,
|
||||
Specialization::Default,
|
||||
|
@ -381,8 +372,6 @@ struct Values {
|
|||
true};
|
||||
SwitchableSetting<AspectRatio, true> aspect_ratio{linkage,
|
||||
AspectRatio::R16_9,
|
||||
AspectRatio::R16_9,
|
||||
AspectRatio::Stretch,
|
||||
"aspect_ratio",
|
||||
Category::Renderer,
|
||||
Specialization::Default,
|
||||
|
@ -430,8 +419,6 @@ struct Values {
|
|||
#else
|
||||
GpuAccuracy::High,
|
||||
#endif
|
||||
GpuAccuracy::Normal,
|
||||
GpuAccuracy::Extreme,
|
||||
"gpu_accuracy",
|
||||
Category::RendererAdvanced,
|
||||
Specialization::Default,
|
||||
|
@ -442,8 +429,6 @@ struct Values {
|
|||
|
||||
SwitchableSetting<DmaAccuracy, true> dma_accuracy{linkage,
|
||||
DmaAccuracy::Default,
|
||||
DmaAccuracy::Default,
|
||||
DmaAccuracy::Safe,
|
||||
"dma_accuracy",
|
||||
Category::RendererAdvanced,
|
||||
Specialization::Default,
|
||||
|
@ -456,20 +441,14 @@ struct Values {
|
|||
#else
|
||||
AnisotropyMode::Automatic,
|
||||
#endif
|
||||
AnisotropyMode::Automatic,
|
||||
AnisotropyMode::X16,
|
||||
"max_anisotropy",
|
||||
Category::RendererAdvanced};
|
||||
SwitchableSetting<AstcRecompression, true> astc_recompression{linkage,
|
||||
AstcRecompression::Uncompressed,
|
||||
AstcRecompression::Uncompressed,
|
||||
AstcRecompression::Bc3,
|
||||
"astc_recompression",
|
||||
Category::RendererAdvanced};
|
||||
SwitchableSetting<VramUsageMode, true> vram_usage_mode{linkage,
|
||||
VramUsageMode::Conservative,
|
||||
VramUsageMode::Conservative,
|
||||
VramUsageMode::Aggressive,
|
||||
"vram_usage_mode",
|
||||
Category::RendererAdvanced};
|
||||
SwitchableSetting<bool> skip_cpu_inner_invalidation{linkage,
|
||||
|
@ -595,14 +574,10 @@ struct Values {
|
|||
// System
|
||||
SwitchableSetting<Language, true> language_index{linkage,
|
||||
Language::EnglishAmerican,
|
||||
Language::Japanese,
|
||||
Language::Serbian,
|
||||
"language_index",
|
||||
Category::System};
|
||||
SwitchableSetting<Region, true> region_index{linkage, Region::Usa, Region::Japan,
|
||||
Region::Taiwan, "region_index", Category::System};
|
||||
SwitchableSetting<TimeZone, true> time_zone_index{linkage, TimeZone::Auto,
|
||||
TimeZone::Auto, TimeZone::Zulu,
|
||||
SwitchableSetting<Region, true> region_index{linkage, Region::Usa, "region_index", Category::System};
|
||||
SwitchableSetting<TimeZone, true> time_zone_index{linkage, TimeZone::Auto,
|
||||
"time_zone_index", Category::System};
|
||||
// Measured in seconds since epoch
|
||||
SwitchableSetting<bool> custom_rtc_enabled{
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <string_view>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
#include "common/common_types.h"
|
||||
|
@ -18,8 +19,10 @@ namespace Settings {
|
|||
|
||||
template <typename T>
|
||||
struct EnumMetadata {
|
||||
static std::vector<std::pair<std::string, T>> Canonicalizations();
|
||||
static std::vector<std::pair<std::string_view, T>> Canonicalizations();
|
||||
static u32 Index();
|
||||
static constexpr T GetFirst();
|
||||
static constexpr T GetLast();
|
||||
};
|
||||
|
||||
#define PAIR_45(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_46(N, __VA_ARGS__))
|
||||
|
@ -69,138 +72,101 @@ struct EnumMetadata {
|
|||
#define PAIR_1(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_2(N, __VA_ARGS__))
|
||||
#define PAIR(N, X, ...) {#X, N::X} __VA_OPT__(, PAIR_1(N, __VA_ARGS__))
|
||||
|
||||
#define ENUM(NAME, ...) \
|
||||
enum class NAME : u32 { __VA_ARGS__ }; \
|
||||
template <> \
|
||||
inline std::vector<std::pair<std::string, NAME>> EnumMetadata<NAME>::Canonicalizations() { \
|
||||
return {PAIR(NAME, __VA_ARGS__)}; \
|
||||
} \
|
||||
template <> \
|
||||
inline u32 EnumMetadata<NAME>::Index() { \
|
||||
return __COUNTER__; \
|
||||
#define PP_HEAD(A, ...) A
|
||||
|
||||
#define ENUM(NAME, ...) \
|
||||
enum class NAME : u32 { __VA_ARGS__ }; \
|
||||
template<> inline std::vector<std::pair<std::string_view, NAME>> EnumMetadata<NAME>::Canonicalizations() { \
|
||||
return {PAIR(NAME, __VA_ARGS__)}; \
|
||||
} \
|
||||
template<> inline u32 EnumMetadata<NAME>::Index() { \
|
||||
return __COUNTER__; \
|
||||
} \
|
||||
template<> inline constexpr NAME EnumMetadata<NAME>::GetFirst() { \
|
||||
return NAME::PP_HEAD(__VA_ARGS__); \
|
||||
} \
|
||||
template<> inline constexpr NAME EnumMetadata<NAME>::GetLast() { \
|
||||
return (std::vector<std::pair<std::string_view, NAME>>{PAIR(NAME, __VA_ARGS__)}).back().second; \
|
||||
}
|
||||
|
||||
// AudioEngine must be specified discretely due to having existing but slightly different
|
||||
// canonicalizations
|
||||
// TODO (lat9nq): Remove explicit definition of AudioEngine/sink_id
|
||||
enum class AudioEngine : u32 {
|
||||
Auto,
|
||||
Cubeb,
|
||||
Sdl2,
|
||||
Null,
|
||||
Oboe,
|
||||
};
|
||||
|
||||
template <>
|
||||
inline std::vector<std::pair<std::string, AudioEngine>>
|
||||
EnumMetadata<AudioEngine>::Canonicalizations() {
|
||||
enum class AudioEngine : u32 { Auto, Cubeb, Sdl2, Null, Oboe, };
|
||||
template<>
|
||||
inline std::vector<std::pair<std::string_view, AudioEngine>> EnumMetadata<AudioEngine>::Canonicalizations() {
|
||||
return {
|
||||
{"auto", AudioEngine::Auto}, {"cubeb", AudioEngine::Cubeb}, {"sdl2", AudioEngine::Sdl2},
|
||||
{"null", AudioEngine::Null}, {"oboe", AudioEngine::Oboe},
|
||||
};
|
||||
}
|
||||
|
||||
template <>
|
||||
/// @brief This is just a sufficiently large number that is more than the number of other enums declared here
|
||||
template<>
|
||||
inline u32 EnumMetadata<AudioEngine>::Index() {
|
||||
// This is just a sufficiently large number that is more than the number of other enums declared
|
||||
// here
|
||||
return 100;
|
||||
}
|
||||
template<>
|
||||
inline constexpr AudioEngine EnumMetadata<AudioEngine>::GetFirst() {
|
||||
return AudioEngine::Auto;
|
||||
}
|
||||
template<>
|
||||
inline constexpr AudioEngine EnumMetadata<AudioEngine>::GetLast() {
|
||||
return AudioEngine::Oboe;
|
||||
}
|
||||
|
||||
ENUM(AudioMode, Mono, Stereo, Surround);
|
||||
static_assert(EnumMetadata<AudioMode>::GetFirst() == AudioMode::Mono);
|
||||
static_assert(EnumMetadata<AudioMode>::GetLast() == AudioMode::Surround);
|
||||
|
||||
ENUM(Language, Japanese, EnglishAmerican, French, German, Italian, Spanish, Chinese, Korean, Dutch,
|
||||
Portuguese, Russian, Taiwanese, EnglishBritish, FrenchCanadian, SpanishLatin,
|
||||
ChineseSimplified, ChineseTraditional, PortugueseBrazilian, Serbian);
|
||||
|
||||
ENUM(Region, Japan, Usa, Europe, Australia, China, Korea, Taiwan);
|
||||
|
||||
ENUM(TimeZone, Auto, Default, Cet, Cst6Cdt, Cuba, Eet, Egypt, Eire, Est, Est5Edt, Gb, GbEire, Gmt,
|
||||
GmtPlusZero, GmtMinusZero, GmtZero, Greenwich, Hongkong, Hst, Iceland, Iran, Israel, Jamaica,
|
||||
Japan, Kwajalein, Libya, Met, Mst, Mst7Mdt, Navajo, Nz, NzChat, Poland, Portugal, Prc, Pst8Pdt,
|
||||
Roc, Rok, Singapore, Turkey, Uct, Universal, Utc, WSu, Wet, Zulu);
|
||||
|
||||
GmtPlusZero, GmtMinusZero, GmtZero, Greenwich, Hongkong, Hst, Iceland, Iran, Israel, Jamaica,
|
||||
Japan, Kwajalein, Libya, Met, Mst, Mst7Mdt, Navajo, Nz, NzChat, Poland, Portugal, Prc, Pst8Pdt,
|
||||
Roc, Rok, Singapore, Turkey, Uct, Universal, Utc, WSu, Wet, Zulu);
|
||||
ENUM(AnisotropyMode, Automatic, Default, X2, X4, X8, X16);
|
||||
|
||||
ENUM(AstcDecodeMode, Cpu, Gpu, CpuAsynchronous);
|
||||
|
||||
ENUM(AstcRecompression, Uncompressed, Bc1, Bc3);
|
||||
|
||||
ENUM(VSyncMode, Immediate, Mailbox, Fifo, FifoRelaxed);
|
||||
|
||||
ENUM(VramUsageMode, Conservative, Aggressive);
|
||||
|
||||
ENUM(RendererBackend, OpenGL, Vulkan, Null);
|
||||
|
||||
ENUM(ShaderBackend, Glsl, Glasm, SpirV);
|
||||
|
||||
ENUM(GpuAccuracy, Normal, High, Extreme);
|
||||
|
||||
ENUM(DmaAccuracy, Default, Unsafe, Safe);
|
||||
|
||||
ENUM(CpuBackend, Dynarmic, Nce);
|
||||
|
||||
ENUM(CpuAccuracy, Auto, Accurate, Unsafe, Paranoid);
|
||||
|
||||
ENUM(CpuClock, Boost, Fast)
|
||||
|
||||
ENUM(MemoryLayout, Memory_4Gb, Memory_6Gb, Memory_8Gb, Memory_10Gb, Memory_12Gb);
|
||||
|
||||
ENUM(ConfirmStop, Ask_Always, Ask_Based_On_Game, Ask_Never);
|
||||
|
||||
ENUM(FullscreenMode, Borderless, Exclusive);
|
||||
|
||||
ENUM(NvdecEmulation, Off, Cpu, Gpu);
|
||||
|
||||
ENUM(ResolutionSetup,
|
||||
Res1_4X,
|
||||
Res1_2X,
|
||||
Res3_4X,
|
||||
Res1X,
|
||||
Res3_2X,
|
||||
Res2X,
|
||||
Res3X,
|
||||
Res4X,
|
||||
Res5X,
|
||||
Res6X,
|
||||
Res7X,
|
||||
Res8X);
|
||||
|
||||
ENUM(ResolutionSetup, Res1_4X, Res1_2X, Res3_4X, Res1X, Res3_2X, Res2X, Res3X, Res4X, Res5X, Res6X, Res7X, Res8X);
|
||||
ENUM(ScalingFilter, NearestNeighbor, Bilinear, Bicubic, Spline1, Gaussian, Lanczos, ScaleForce, Fsr, Area, MaxEnum);
|
||||
|
||||
ENUM(AntiAliasing, None, Fxaa, Smaa, MaxEnum);
|
||||
|
||||
ENUM(AspectRatio, R16_9, R4_3, R21_9, R16_10, Stretch);
|
||||
|
||||
ENUM(ConsoleMode, Handheld, Docked);
|
||||
|
||||
ENUM(AppletMode, HLE, LLE);
|
||||
|
||||
ENUM(SpirvOptimizeMode, Never, OnLoad, Always);
|
||||
|
||||
ENUM(GpuOverclock, Low, Medium, High)
|
||||
|
||||
ENUM(TemperatureUnits, Celsius, Fahrenheit)
|
||||
|
||||
template <typename Type>
|
||||
inline std::string CanonicalizeEnum(Type id) {
|
||||
inline std::string_view CanonicalizeEnum(Type id) {
|
||||
const auto group = EnumMetadata<Type>::Canonicalizations();
|
||||
for (auto& [name, value] : group) {
|
||||
if (value == id) {
|
||||
for (auto& [name, value] : group)
|
||||
if (value == id)
|
||||
return name;
|
||||
}
|
||||
}
|
||||
return "unknown";
|
||||
}
|
||||
|
||||
template <typename Type>
|
||||
inline Type ToEnum(const std::string& canonicalization) {
|
||||
const auto group = EnumMetadata<Type>::Canonicalizations();
|
||||
for (auto& [name, value] : group) {
|
||||
if (name == canonicalization) {
|
||||
for (auto& [name, value] : group)
|
||||
if (name == canonicalization)
|
||||
return value;
|
||||
}
|
||||
}
|
||||
return {};
|
||||
}
|
||||
} // namespace Settings
|
||||
|
|
|
@ -72,10 +72,17 @@ public:
|
|||
u32 specialization_ = Specialization::Default, bool save_ = true,
|
||||
bool runtime_modifiable_ = false, BasicSetting* other_setting_ = nullptr)
|
||||
requires(ranged)
|
||||
: BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization_,
|
||||
other_setting_),
|
||||
: BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization_, other_setting_),
|
||||
value{default_val}, default_value{default_val}, maximum{max_val}, minimum{min_val} {}
|
||||
|
||||
explicit Setting(Linkage& linkage, const Type& default_val,
|
||||
const std::string& name, Category category_,
|
||||
u32 specialization_ = Specialization::Default, bool save_ = true,
|
||||
bool runtime_modifiable_ = false, BasicSetting* other_setting_ = nullptr)
|
||||
requires(ranged && std::is_enum_v<Type>)
|
||||
: BasicSetting(linkage, name, category_, save_, runtime_modifiable_, specialization_, other_setting_),
|
||||
value{default_val}, default_value{default_val}, maximum{EnumMetadata<Type>::GetLast()}, minimum{EnumMetadata<Type>::GetFirst()} {}
|
||||
|
||||
/**
|
||||
* Returns a reference to the setting's value.
|
||||
*
|
||||
|
@ -119,9 +126,6 @@ protected:
|
|||
return value_.has_value() ? std::to_string(*value_) : "none";
|
||||
} else if constexpr (std::is_same_v<Type, bool>) {
|
||||
return value_ ? "true" : "false";
|
||||
} else if constexpr (std::is_same_v<Type, AudioEngine>) {
|
||||
// Compatibility with old AudioEngine setting being a string
|
||||
return CanonicalizeEnum(value_);
|
||||
} else if constexpr (std::is_floating_point_v<Type>) {
|
||||
return fmt::format("{:f}", value_);
|
||||
} else if constexpr (std::is_enum_v<Type>) {
|
||||
|
@ -207,7 +211,7 @@ public:
|
|||
|
||||
[[nodiscard]] std::string Canonicalize() const override final {
|
||||
if constexpr (std::is_enum_v<Type>) {
|
||||
return CanonicalizeEnum(this->GetValue());
|
||||
return std::string{CanonicalizeEnum(this->GetValue())};
|
||||
} else {
|
||||
return ToString(this->GetValue());
|
||||
}
|
||||
|
@ -288,41 +292,32 @@ public:
|
|||
* @param other_setting_ A second Setting to associate to this one in metadata
|
||||
*/
|
||||
template <typename T = BasicSetting>
|
||||
explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name,
|
||||
Category category_, u32 specialization_ = Specialization::Default,
|
||||
bool save_ = true, bool runtime_modifiable_ = false,
|
||||
typename std::enable_if<!ranged, T*>::type other_setting_ = nullptr)
|
||||
: Setting<Type, false>{
|
||||
linkage, default_val, name, category_, specialization_,
|
||||
save_, runtime_modifiable_, other_setting_} {
|
||||
explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, T* other_setting_ = nullptr) requires(!ranged)
|
||||
: Setting<Type, false>{ linkage, default_val, name, category_, specialization_, save_, runtime_modifiable_, other_setting_} {
|
||||
linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); });
|
||||
}
|
||||
virtual ~SwitchableSetting() = default;
|
||||
|
||||
/**
|
||||
* Sets a default value, minimum value, maximum value, and label.
|
||||
*
|
||||
* @param linkage Setting registry
|
||||
* @param default_val Initial value of the setting, and default value of the setting
|
||||
* @param min_val Sets the minimum allowed value of the setting
|
||||
* @param max_val Sets the maximum allowed value of the setting
|
||||
* @param name Label for the setting
|
||||
* @param category_ Category of the setting AKA INI group
|
||||
* @param specialization_ Suggestion for how frontend implementations represent this in a config
|
||||
* @param save_ Suggests that this should or should not be saved to a frontend config file
|
||||
* @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded
|
||||
* @param other_setting_ A second Setting to associate to this one in metadata
|
||||
*/
|
||||
/// @brief Sets a default value, minimum value, maximum value, and label.
|
||||
/// @param linkage Setting registry
|
||||
/// @param default_val Initial value of the setting, and default value of the setting
|
||||
/// @param min_val Sets the minimum allowed value of the setting
|
||||
/// @param max_val Sets the maximum allowed value of the setting
|
||||
/// @param name Label for the setting
|
||||
/// @param category_ Category of the setting AKA INI group
|
||||
/// @param specialization_ Suggestion for how frontend implementations represent this in a config
|
||||
/// @param save_ Suggests that this should or should not be saved to a frontend config file
|
||||
/// @param runtime_modifiable_ Suggests whether this is modifiable while a guest is loaded
|
||||
/// @param other_setting_ A second Setting to associate to this one in metadata
|
||||
template <typename T = BasicSetting>
|
||||
explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val,
|
||||
const Type& max_val, const std::string& name, Category category_,
|
||||
u32 specialization_ = Specialization::Default, bool save_ = true,
|
||||
bool runtime_modifiable_ = false,
|
||||
typename std::enable_if<ranged, T*>::type other_setting_ = nullptr)
|
||||
: Setting<Type, true>{linkage, default_val, min_val,
|
||||
max_val, name, category_,
|
||||
specialization_, save_, runtime_modifiable_,
|
||||
other_setting_} {
|
||||
explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const Type& min_val, const Type& max_val, const std::string& name, Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, T* other_setting_ = nullptr) requires(ranged)
|
||||
: Setting<Type, true>{linkage, default_val, min_val, max_val, name, category_, specialization_, save_, runtime_modifiable_, other_setting_} {
|
||||
linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); });
|
||||
}
|
||||
|
||||
template <typename T = BasicSetting>
|
||||
explicit SwitchableSetting(Linkage& linkage, const Type& default_val, const std::string& name, Category category_, u32 specialization_ = Specialization::Default, bool save_ = true, bool runtime_modifiable_ = false, T* other_setting_ = nullptr) requires(ranged)
|
||||
: Setting<Type, true>{linkage, default_val, EnumMetadata<Type>::GetFirst(), EnumMetadata<Type>::GetLast(), name, category_, specialization_, save_, runtime_modifiable_, other_setting_} {
|
||||
linkage.restore_functions.emplace_back([this]() { this->SetGlobal(true); });
|
||||
}
|
||||
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
|
||||
#include <deque>
|
||||
#include <mutex>
|
||||
#include <stack>
|
||||
|
||||
#include "common/math_util.h"
|
||||
#include "core/hle/service/apm/apm_controller.h"
|
||||
|
@ -23,6 +24,7 @@
|
|||
#include "core/hle/service/am/hid_registration.h"
|
||||
#include "core/hle/service/am/lifecycle_manager.h"
|
||||
#include "core/hle/service/am/process_holder.h"
|
||||
#include "core/hle/service/am/service/storage.h"
|
||||
|
||||
namespace Service::AM {
|
||||
|
||||
|
@ -97,6 +99,9 @@ struct Applet {
|
|||
std::deque<std::vector<u8>> preselected_user_launch_parameter{};
|
||||
std::deque<std::vector<u8>> friend_invitation_storage_channel{};
|
||||
|
||||
// Context Stack
|
||||
std::stack<SharedPointer<IStorage>> context_stack{};
|
||||
|
||||
// Caller applet
|
||||
std::weak_ptr<Applet> caller_applet{};
|
||||
std::shared_ptr<AppletDataBroker> caller_applet_broker{};
|
||||
|
|
|
@ -1,3 +1,6 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
|
@ -15,12 +18,12 @@ IProcessWindingController::IProcessWindingController(Core::System& system_,
|
|||
static const FunctionInfo functions[] = {
|
||||
{0, D<&IProcessWindingController::GetLaunchReason>, "GetLaunchReason"},
|
||||
{11, D<&IProcessWindingController::OpenCallingLibraryApplet>, "OpenCallingLibraryApplet"},
|
||||
{21, nullptr, "PushContext"},
|
||||
{22, nullptr, "PopContext"},
|
||||
{23, nullptr, "CancelWindingReservation"},
|
||||
{30, nullptr, "WindAndDoReserved"},
|
||||
{40, nullptr, "ReserveToStartAndWaitAndUnwindThis"},
|
||||
{41, nullptr, "ReserveToStartAndWait"},
|
||||
{21, D<&IProcessWindingController::PushContext>, "PushContext"},
|
||||
{22, D<&IProcessWindingController::PopContext>, "PopContext"},
|
||||
{23, D<&IProcessWindingController::CancelWindingReservation>, "CancelWindingReservation"},
|
||||
{30, D<&IProcessWindingController::WindAndDoReserved>, "WindAndDoReserved"},
|
||||
{40, D<&IProcessWindingController::ReserveToStartAndWaitAndUnwindThis>, "ReserveToStartAndWaitAndUnwindThis"},
|
||||
{41, D<&IProcessWindingController::ReserveToStartAndWait>, "ReserveToStartAndWait"},
|
||||
};
|
||||
// clang-format on
|
||||
|
||||
|
@ -51,4 +54,43 @@ Result IProcessWindingController::OpenCallingLibraryApplet(
|
|||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result IProcessWindingController::PushContext(SharedPointer<IStorage> context) {
|
||||
LOG_INFO(Service_AM, "called");
|
||||
m_applet->context_stack.push(context);
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result IProcessWindingController::PopContext(Out<SharedPointer<IStorage>> out_context) {
|
||||
LOG_INFO(Service_AM, "called");
|
||||
|
||||
if (m_applet->context_stack.empty()) {
|
||||
LOG_ERROR(Service_AM, "Context stack is empty");
|
||||
R_THROW(ResultUnknown);
|
||||
}
|
||||
|
||||
*out_context = m_applet->context_stack.top();
|
||||
m_applet->context_stack.pop();
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result IProcessWindingController::CancelWindingReservation() {
|
||||
LOG_WARNING(Service_AM, "STUBBED");
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result IProcessWindingController::WindAndDoReserved() {
|
||||
LOG_WARNING(Service_AM, "STUBBED");
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result IProcessWindingController::ReserveToStartAndWaitAndUnwindThis() {
|
||||
LOG_WARNING(Service_AM, "STUBBED");
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result IProcessWindingController::ReserveToStartAndWait() {
|
||||
LOG_WARNING(Service_AM, "STUBBED");
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
} // namespace Service::AM
|
||||
|
|
|
@ -1,8 +1,12 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "core/hle/service/am/service/storage.h"
|
||||
#include "core/hle/service/am/am_types.h"
|
||||
#include "core/hle/service/cmif_types.h"
|
||||
#include "core/hle/service/service.h"
|
||||
|
@ -21,6 +25,12 @@ private:
|
|||
Result GetLaunchReason(Out<AppletProcessLaunchReason> out_launch_reason);
|
||||
Result OpenCallingLibraryApplet(
|
||||
Out<SharedPointer<ILibraryAppletAccessor>> out_calling_library_applet);
|
||||
Result PushContext(SharedPointer<IStorage> in_context);
|
||||
Result PopContext(Out<SharedPointer<IStorage>> out_context);
|
||||
Result CancelWindingReservation();
|
||||
Result WindAndDoReserved();
|
||||
Result ReserveToStartAndWaitAndUnwindThis();
|
||||
Result ReserveToStartAndWait();
|
||||
|
||||
const std::shared_ptr<Applet> m_applet;
|
||||
};
|
||||
|
|
|
@ -1,3 +1,6 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
|
@ -67,6 +70,7 @@ ISelfController::ISelfController(Core::System& system_, std::shared_ptr<Applet>
|
|||
{110, nullptr, "SetApplicationAlbumUserData"},
|
||||
{120, D<&ISelfController::SaveCurrentScreenshot>, "SaveCurrentScreenshot"},
|
||||
{130, D<&ISelfController::SetRecordVolumeMuted>, "SetRecordVolumeMuted"},
|
||||
{230, D<&ISelfController::Unknown230>, "Unknown230"},
|
||||
{1000, nullptr, "GetDebugStorageChannel"},
|
||||
};
|
||||
// clang-format on
|
||||
|
@ -404,4 +408,12 @@ Result ISelfController::SetRecordVolumeMuted(bool muted) {
|
|||
R_SUCCEED();
|
||||
}
|
||||
|
||||
Result ISelfController::Unknown230(u32 in_val, Out<u16> out_val) {
|
||||
LOG_WARNING(Service_AM, "(STUBBED) called, in_val={}", in_val);
|
||||
|
||||
*out_val = 0;
|
||||
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
} // namespace Service::AM
|
||||
|
|
|
@ -1,3 +1,6 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
|
@ -63,6 +66,7 @@ private:
|
|||
Result SetAlbumImageTakenNotificationEnabled(bool enabled);
|
||||
Result SaveCurrentScreenshot(Capture::AlbumReportOption album_report_option);
|
||||
Result SetRecordVolumeMuted(bool muted);
|
||||
Result Unknown230(u32 in_val, Out<u16> out_val);
|
||||
|
||||
Kernel::KProcess* const m_process;
|
||||
const std::shared_ptr<Applet> m_applet;
|
||||
|
|
|
@ -38,11 +38,6 @@ EmitContext::EmitContext(RegAlloc& reg_alloc, IR::Block& block)
|
|||
|
||||
EmitContext::~EmitContext() = default;
|
||||
|
||||
void EmitContext::EraseInstruction(IR::Inst* inst) {
|
||||
block.Instructions().erase(inst);
|
||||
inst->ClearArgs();
|
||||
}
|
||||
|
||||
EmitX64::EmitX64(BlockOfCode& code)
|
||||
: code(code) {
|
||||
exception_handler.Register(code);
|
||||
|
|
|
@ -1,3 +1,6 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
/* This file is part of the dynarmic project.
|
||||
* Copyright (c) 2016 MerryMage
|
||||
* SPDX-License-Identifier: 0BSD
|
||||
|
@ -54,8 +57,6 @@ struct EmitContext {
|
|||
EmitContext(RegAlloc& reg_alloc, IR::Block& block);
|
||||
virtual ~EmitContext();
|
||||
|
||||
void EraseInstruction(IR::Inst* inst);
|
||||
|
||||
virtual FP::FPCR FPCR(bool fpcr_controlled = true) const = 0;
|
||||
|
||||
virtual bool HasOptimization(OptimizationFlag flag) const = 0;
|
||||
|
|
|
@ -46,7 +46,7 @@ Block::iterator Block::PrependNewInst(iterator insertion_point, Opcode opcode, s
|
|||
inst->SetArg(index, arg);
|
||||
index++;
|
||||
});
|
||||
return instructions.insert_before(insertion_point, inst);
|
||||
return instructions.insert(insertion_point, *inst);
|
||||
}
|
||||
|
||||
static std::string TerminalToString(const Terminal& terminal_variant) noexcept {
|
||||
|
|
|
@ -12,10 +12,9 @@
|
|||
#include <memory>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <boost/intrusive/list.hpp>
|
||||
|
||||
#include <mcl/container/intrusive_list.hpp>
|
||||
#include "dynarmic/common/common_types.h"
|
||||
|
||||
#include "dynarmic/ir/location_descriptor.h"
|
||||
#include "dynarmic/ir/microinstruction.h"
|
||||
#include "dynarmic/ir/terminal.h"
|
||||
|
@ -35,7 +34,7 @@ enum class Opcode;
|
|||
class Block final {
|
||||
public:
|
||||
//using instruction_list_type = dense_list<Inst>;
|
||||
using instruction_list_type = mcl::intrusive_list<Inst>;
|
||||
using instruction_list_type = boost::intrusive::list<Inst>;
|
||||
using size_type = instruction_list_type::size_type;
|
||||
using iterator = instruction_list_type::iterator;
|
||||
using const_iterator = instruction_list_type::const_iterator;
|
||||
|
|
|
@ -10,10 +10,10 @@
|
|||
|
||||
#include <vector>
|
||||
|
||||
#include "dynarmic/common/common_types.h"
|
||||
#include "dynarmic/common/assert.h"
|
||||
#include <mcl/bit_cast.hpp>
|
||||
|
||||
#include "dynarmic/common/common_types.h"
|
||||
#include "dynarmic/common/assert.h"
|
||||
#include "dynarmic/ir/opcodes.h"
|
||||
#include "dynarmic/ir/acc_type.h"
|
||||
#include "dynarmic/ir/basic_block.h"
|
||||
|
@ -124,7 +124,7 @@ public:
|
|||
ASSERT(value.GetType() == Type::U64);
|
||||
return value;
|
||||
}
|
||||
ASSERT_FALSE("Invalid bitsize");
|
||||
ASSERT_MSG(false, "Invalid bitsize");
|
||||
}
|
||||
|
||||
U32 LeastSignificantWord(const U64& value) {
|
||||
|
@ -2950,19 +2950,10 @@ public:
|
|||
block.SetTerminal(terminal);
|
||||
}
|
||||
|
||||
void SetInsertionPointBefore(IR::Inst* new_insertion_point) {
|
||||
insertion_point = IR::Block::iterator{*new_insertion_point};
|
||||
}
|
||||
|
||||
void SetInsertionPointBefore(IR::Block::iterator new_insertion_point) {
|
||||
insertion_point = new_insertion_point;
|
||||
}
|
||||
|
||||
void SetInsertionPointAfter(IR::Inst* new_insertion_point) {
|
||||
insertion_point = IR::Block::iterator{*new_insertion_point};
|
||||
++insertion_point;
|
||||
}
|
||||
|
||||
void SetInsertionPointAfter(IR::Block::iterator new_insertion_point) {
|
||||
insertion_point = new_insertion_point;
|
||||
++insertion_point;
|
||||
|
|
|
@ -9,10 +9,9 @@
|
|||
#pragma once
|
||||
|
||||
#include <array>
|
||||
#include <boost/intrusive/list.hpp>
|
||||
|
||||
#include <mcl/container/intrusive_list.hpp>
|
||||
#include "dynarmic/common/common_types.h"
|
||||
|
||||
#include "dynarmic/ir/value.h"
|
||||
#include "dynarmic/ir/opcodes.h"
|
||||
|
||||
|
@ -26,7 +25,7 @@ constexpr size_t max_arg_count = 4;
|
|||
/// A representation of a microinstruction. A single ARM/Thumb instruction may be
|
||||
/// converted into zero or more microinstructions.
|
||||
//class Inst final {
|
||||
class Inst final : public mcl::intrusive_list_node<Inst> {
|
||||
class Inst final : public boost::intrusive::list_base_hook<> {
|
||||
public:
|
||||
explicit Inst(Opcode op) : op(op) {}
|
||||
|
||||
|
|
|
@ -85,12 +85,10 @@ static void ConstantMemoryReads(IR::Block& block, A32::UserCallbacks* cb) {
|
|||
}
|
||||
|
||||
static void FlagsPass(IR::Block& block) {
|
||||
using Iterator = std::reverse_iterator<IR::Block::iterator>;
|
||||
|
||||
struct FlagInfo {
|
||||
bool set_not_required = false;
|
||||
bool has_value_request = false;
|
||||
Iterator value_request = {};
|
||||
IR::Block::reverse_iterator value_request = {};
|
||||
};
|
||||
struct ValuelessFlagInfo {
|
||||
bool set_not_required = false;
|
||||
|
@ -101,7 +99,7 @@ static void FlagsPass(IR::Block& block) {
|
|||
FlagInfo c_flag;
|
||||
FlagInfo ge;
|
||||
|
||||
auto do_set = [&](FlagInfo& info, IR::Value value, Iterator inst) {
|
||||
auto do_set = [&](FlagInfo& info, IR::Value value, IR::Block::reverse_iterator const inst) {
|
||||
if (info.has_value_request) {
|
||||
info.value_request->ReplaceUsesWith(value);
|
||||
}
|
||||
|
@ -113,14 +111,14 @@ static void FlagsPass(IR::Block& block) {
|
|||
info.set_not_required = true;
|
||||
};
|
||||
|
||||
auto do_set_valueless = [&](ValuelessFlagInfo& info, Iterator inst) {
|
||||
auto do_set_valueless = [&](ValuelessFlagInfo& info, IR::Block::reverse_iterator const inst) {
|
||||
if (info.set_not_required) {
|
||||
inst->Invalidate();
|
||||
}
|
||||
info.set_not_required = true;
|
||||
};
|
||||
|
||||
auto do_get = [](FlagInfo& info, Iterator inst) {
|
||||
auto do_get = [](FlagInfo& info, IR::Block::reverse_iterator const inst) {
|
||||
if (info.has_value_request) {
|
||||
info.value_request->ReplaceUsesWith(IR::Value{&*inst});
|
||||
}
|
||||
|
@ -447,7 +445,8 @@ static void A64CallbackConfigPass(IR::Block& block, const A64::UserConfig& conf)
|
|||
return;
|
||||
}
|
||||
|
||||
for (auto& inst : block) {
|
||||
for (auto it = block.begin(); it != block.end(); it++) {
|
||||
auto& inst = *it;
|
||||
if (inst.GetOpcode() != IR::Opcode::A64DataCacheOperationRaised) {
|
||||
continue;
|
||||
}
|
||||
|
@ -456,7 +455,7 @@ static void A64CallbackConfigPass(IR::Block& block, const A64::UserConfig& conf)
|
|||
if (op == A64::DataCacheOperation::ZeroByVA) {
|
||||
A64::IREmitter ir{block};
|
||||
ir.current_location = A64::LocationDescriptor{IR::LocationDescriptor{inst.GetArg(0).GetU64()}};
|
||||
ir.SetInsertionPointBefore(&inst);
|
||||
ir.SetInsertionPointBefore(it);
|
||||
|
||||
size_t bytes = 4 << static_cast<size_t>(conf.dczid_el0 & 0b1111);
|
||||
IR::U64 addr{inst.GetArg(2)};
|
||||
|
@ -1243,7 +1242,7 @@ static void IdentityRemovalPass(IR::Block& block) {
|
|||
}
|
||||
|
||||
if (inst.GetOpcode() == IR::Opcode::Identity || inst.GetOpcode() == IR::Opcode::Void) {
|
||||
iter = block.Instructions().erase(inst);
|
||||
iter = block.Instructions().erase(iter);
|
||||
to_invalidate.push_back(&inst);
|
||||
} else {
|
||||
++iter;
|
||||
|
@ -1405,8 +1404,9 @@ static void PolyfillPass(IR::Block& block, const PolyfillOptions& polyfill) {
|
|||
|
||||
IR::IREmitter ir{block};
|
||||
|
||||
for (auto& inst : block) {
|
||||
ir.SetInsertionPointBefore(&inst);
|
||||
for (auto it = block.begin(); it != block.end(); it++) {
|
||||
auto& inst = *it;
|
||||
ir.SetInsertionPointBefore(it);
|
||||
|
||||
switch (inst.GetOpcode()) {
|
||||
case IR::Opcode::SHA256MessageSchedule0:
|
||||
|
|
|
@ -135,6 +135,8 @@ target_include_directories(dynarmic_tests PRIVATE . ../src)
|
|||
target_compile_options(dynarmic_tests PRIVATE ${DYNARMIC_CXX_FLAGS})
|
||||
target_compile_definitions(dynarmic_tests PRIVATE FMT_USE_USER_DEFINED_LITERALS=1)
|
||||
|
||||
target_compile_options(dynarmic_tests PRIVATE -mavx2)
|
||||
if ("x86_64" IN_LIST ARCHITECTURE)
|
||||
target_compile_options(dynarmic_tests PRIVATE -mavx2)
|
||||
endif()
|
||||
|
||||
add_test(dynarmic_tests dynarmic_tests --durations yes)
|
||||
|
|
|
@ -785,18 +785,13 @@ void BufferCache<P>::BindHostGraphicsUniformBuffers(size_t stage) {
|
|||
}
|
||||
|
||||
template <class P>
|
||||
void BufferCache<P>::BindHostGraphicsUniformBuffer(size_t stage, u32 index, u32 binding_index,
|
||||
bool needs_bind) {
|
||||
void BufferCache<P>::BindHostGraphicsUniformBuffer(size_t stage, u32 index, u32 binding_index, bool needs_bind) {
|
||||
++channel_state->uniform_cache_shots[0];
|
||||
const Binding& binding = channel_state->uniform_buffers[stage][index];
|
||||
const DAddr device_addr = binding.device_addr;
|
||||
const u32 size = (std::min)(binding.size, (*channel_state->uniform_buffer_sizes)[stage][index]);
|
||||
Buffer& buffer = slot_buffers[binding.buffer_id];
|
||||
TouchBuffer(buffer, binding.buffer_id);
|
||||
const bool sync_buffer = SynchronizeBuffer(buffer, device_addr, size);
|
||||
if (sync_buffer) {
|
||||
++channel_state->uniform_cache_hits[0];
|
||||
}
|
||||
++channel_state->uniform_cache_shots[0];
|
||||
const bool use_fast_buffer = binding.buffer_id != NULL_BUFFER_ID &&
|
||||
size <= channel_state->uniform_buffer_skip_cache_size &&
|
||||
!memory_tracker.IsRegionGpuModified(device_addr, size);
|
||||
|
@ -827,7 +822,10 @@ void BufferCache<P>::BindHostGraphicsUniformBuffer(size_t stage, u32 index, u32
|
|||
device_memory.ReadBlockUnsafe(device_addr, span.data(), size);
|
||||
return;
|
||||
}
|
||||
|
||||
// Classic cached path
|
||||
if (SynchronizeBuffer(buffer, device_addr, size)) {
|
||||
++channel_state->uniform_cache_hits[0];
|
||||
}
|
||||
// Skip binding if it's not needed and if the bound buffer is not the fast version
|
||||
// This exists to avoid instances where the fast buffer is bound and a GPU write happens
|
||||
needs_bind |= HasFastUniformBufferBound(stage, binding_index);
|
||||
|
|
|
@ -45,9 +45,31 @@ SPDX-License-Identifier: GPL-2.0-or-later
|
|||
<true/>
|
||||
<key>NSHumanReadableCopyright</key>
|
||||
<string></string>
|
||||
<!-- Fixed -->
|
||||
<key>LSApplicationCategoryType</key>
|
||||
<string>public.app-category.games</string>
|
||||
<key>CFBundleDocumentTypes</key>
|
||||
<array>
|
||||
<dict>
|
||||
<key>CFBundleTypeExtensions</key>
|
||||
<array>
|
||||
<string>nsp</string>
|
||||
<string>xci</string>
|
||||
<string>nro</string>
|
||||
</array>
|
||||
<key>CFBundleTypeName</key>
|
||||
<string>Switch File</string>
|
||||
<key>CFBundleTypeRole</key>
|
||||
<string>Viewer</string>
|
||||
<key>LSHandlerRank</key>
|
||||
<string>Default</string>
|
||||
</dict>
|
||||
</array>
|
||||
<key>NSPrincipalClass</key>
|
||||
<string>NSApplication</string>
|
||||
<key>NSHighResolutionCapable</key>
|
||||
<string>True</string>
|
||||
<key>UIDesignRequiresCompatibility</key>
|
||||
<true/> <!-- https://bugreports.qt.io/browse/QTBUG-138942 -->
|
||||
</dict>
|
||||
</plist>
|
||||
|
|
|
@ -270,10 +270,8 @@ void ConfigureAudio::UpdateAudioDevices(int sink_index) {
|
|||
void ConfigureAudio::InitializeAudioSinkComboBox() {
|
||||
sink_combo_box->clear();
|
||||
sink_combo_box->addItem(QString::fromUtf8(AudioCore::Sink::auto_device_name));
|
||||
|
||||
for (const auto& id : AudioCore::Sink::GetSinkIDs()) {
|
||||
sink_combo_box->addItem(QString::fromStdString(Settings::CanonicalizeEnum(id)));
|
||||
}
|
||||
for (const auto& id : AudioCore::Sink::GetSinkIDs())
|
||||
sink_combo_box->addItem(QString::fromStdString(std::string{Settings::CanonicalizeEnum(id)}));
|
||||
}
|
||||
|
||||
void ConfigureAudio::RetranslateUI() {
|
||||
|
|
|
@ -13,6 +13,7 @@
|
|||
#include <QString>
|
||||
#include <QStringLiteral>
|
||||
#include <QWidget>
|
||||
#include <QObject>
|
||||
#include <qobjectdefs.h>
|
||||
#include "qt_common/shared_translation.h"
|
||||
|
||||
|
|
|
@ -58,11 +58,11 @@ class GameList : public QWidget {
|
|||
public:
|
||||
enum {
|
||||
COLUMN_NAME,
|
||||
COLUMN_COMPATIBILITY,
|
||||
COLUMN_ADD_ONS,
|
||||
COLUMN_FILE_TYPE,
|
||||
COLUMN_SIZE,
|
||||
COLUMN_PLAY_TIME,
|
||||
COLUMN_ADD_ONS,
|
||||
COLUMN_COMPATIBILITY,
|
||||
COLUMN_COUNT, // Number of columns
|
||||
};
|
||||
|
||||
|
|
|
@ -204,36 +204,24 @@ QList<QStandardItem*> MakeGameListEntry(const std::string& path,
|
|||
const PlayTime::PlayTimeManager& play_time_manager,
|
||||
const FileSys::PatchManager& patch)
|
||||
{
|
||||
const auto it = FindMatchingCompatibilityEntry(compatibility_list, program_id);
|
||||
auto const it = FindMatchingCompatibilityEntry(compatibility_list, program_id);
|
||||
// The game list uses 99 as compatibility number for untested games
|
||||
QString compatibility = it != compatibility_list.end() ? it->second.first : QStringLiteral("99");
|
||||
|
||||
// The game list uses this as compatibility number for untested games
|
||||
QString compatibility{QStringLiteral("99")};
|
||||
if (it != compatibility_list.end()) {
|
||||
compatibility = it->second.first;
|
||||
}
|
||||
auto const file_type = loader.GetFileType();
|
||||
auto const file_type_string = QString::fromStdString(Loader::GetFileTypeString(file_type));
|
||||
|
||||
const auto file_type = loader.GetFileType();
|
||||
const auto file_type_string = QString::fromStdString(Loader::GetFileTypeString(file_type));
|
||||
|
||||
QList<QStandardItem*> list{
|
||||
new GameListItemPath(FormatGameName(path), icon, QString::fromStdString(name),
|
||||
file_type_string, program_id),
|
||||
new GameListItemCompat(compatibility),
|
||||
QString patch_versions = GetGameListCachedObject(fmt::format("{:016X}", patch.GetTitleID()), "pv.txt", [&patch, &loader] {
|
||||
return FormatPatchNameVersions(patch, loader, loader.IsRomFSUpdatable());
|
||||
});
|
||||
return QList<QStandardItem*>{
|
||||
new GameListItemPath(FormatGameName(path), icon, QString::fromStdString(name), file_type_string, program_id),
|
||||
new GameListItem(file_type_string),
|
||||
new GameListItemSize(size),
|
||||
new GameListItemPlayTime(play_time_manager.GetPlayTime(program_id)),
|
||||
new GameListItem(patch_versions),
|
||||
new GameListItemCompat(compatibility),
|
||||
};
|
||||
|
||||
QString patch_versions;
|
||||
|
||||
patch_versions = GetGameListCachedObject(
|
||||
fmt::format("{:016X}", patch.GetTitleID()), "pv.txt", [&patch, &loader] {
|
||||
return FormatPatchNameVersions(patch, loader, loader.IsRomFSUpdatable());
|
||||
});
|
||||
|
||||
list.insert(2, new GameListItem(patch_versions));
|
||||
|
||||
return list;
|
||||
}
|
||||
} // Anonymous namespace
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue