Same behavior, no heap allocation.
strings returned from glGetString() are guaranteed to be static strings,
so this is safe to do. They're also guaranteed to be null-terminated.
Some implementations can use the std::nullopt_t constructor of
std::optional to avoid needing to completely zero out the internal
buffer of the optional and instead only set the validity byte within it.
e.g. Consider the following function:
std::optional<std::vector<ShaderDiskCacheRaw>> fn() {
return {};
}
With libc++ this will result in the following code generation on x86-64:
Fn():
mov rax, rdi
vxorps xmm0, xmm0, xmm0
vmovups ymmword ptr [rdi], ymm0
vzeroupper
ret
With libstdc++, we also get the similar equivalent:
Fn():
vpxor xmm0, xmm0, xmm0
mov rax, rdi
vmovdqu XMMWORD PTR [rdi], xmm0
vmovdqu XMMWORD PTR [rdi+16], xmm0
ret
If we change this function to return std::nullopt instead, then this
simplifies both the code gen from libc++ and libstdc++ down to:
Fn():
mov BYTE PTR [rdi+24], 0
mov rax, rdi
ret
Given how little of a change is necessary to result in better code
generation, this is essentially a "free" very minor optimization.
Previously, we were returning a value that was way too big, causing an integer overflow in Fractured Souls.
According to wwylele, the biggest oberserved save size for 3DS is 1MB, so this new value should leave plenty of room, even if games use a bigger size.
Many of these functions are capable of being used within const contexts,
so we can apply the const qualifier in some cases and add const based
overloads for others, which makes the interface a little bit more
flexible and const-correct.
* core/memory: Amend unusual return value of operator=
operator= usually returns a reference to this. Given there's no comment
explaining why void was used, this can be assumed to be an oversight.
* core/memory: Make use of std::move in Entry::operator=
Same behavior, minus the need for an atomic reference count increment
and decrement (since MemoryRef contains a std::shared_ptr).
* ArmInterface: return ref instead of copy for GetTimer
* ArmInterface: add const ref GetTimer
* ArmInterface: return raw pointer instead of shared_ptr in GetTimer
* remove more unnecessary shared_ptr usage
* Fix save states
* fix unit tests
* video_core: reduce string allocations in shader decompiler
* use append for indentation instead of resize
Co-authored-by: Mat M. <mathew1800@gmail.com>
* am/am: Avoid redundant copy in GetProgramInfoFromCia()
We can just use a reference to the title metadata. Avoids copying
several data entries and std::vector instances that don't need to be
copied.
* hle/service: Avoid redundant copying of std::string
GetUserPath() returns the path as a reference, so we can make use of
said reference to avoid making copies.
By using a reference here, we avoid copying every single element in the
map, each of which contains a std::share_ptr and std::deque containing
std::vectors.
Same behavior, but doesn't result in an allocating copy of the passed in
string. Particularly given the string is only compared against other
existing strings.
Several standard constructors generally check if objects can be moved in
a non-throwing manner (usually via std::move_if_noexcept) to preserve
its exception guarantees. This means that if these were used with
certain containers any reallocations internally would cause resource
churn, as copies would be necessary instead of moves.
This way, if they're every used in that manner, the right behavior is
always performed.
Avoids copying the std::function when we don't need to. Particularly
given the std::function isn't actually stored anywhere, so there's no
need to move it.
Allows interfaces to move the vector into the calls, avoiding any
reallocations.
Many existing call sites already std::move into the parameter, expecting
a move to occur. Only a few remain where this wasn't already
being done, which we can convert over.
This one is similar to the ReceiveCaptureBufferInfo function except it doesn't clear the capture buffer, according to 3dbrew.
This function is used by the Home Menu
The Home Menu uses this to determine whether it is allowed to launch an app (call StartApplication)
This is a no-op for us, we allow any and all titles to be launched. The official APT module holds a list of some forbidden titles like some versions of IronFall and Flipnote Studio 3D.
On Windows, network shares use paths like \\server\share\file which were
being broken by FileUtil::SanitizePath() removing double slashes.
Changed the code in SanitizePath to permit a double-backslash if it
occurs at the start of a filepath (on Windows only).
They are called by the Home Menu during initialization.
These functions will not see much use until we actually implement application jumping and system rebooting. For now we just need them to prevent some unmapped reads in the Home Menu due to the static buffers not being properly set up.
Also rewritten how GetArchiveResource works so that they all use the same interface.
We should decide what to do with these at some point.
Related to #3131 and #3110
* Kernel/Process: Notify the CPUs that a new pagetable has been set every time the process they're executing changes.
Previously the page table would only be changed when the current CPU's page table was changed, this lead to stale JIT states and the PC going to 0 when context-switching a different core inside the ThreadManager::SwitchContext function because the JIT for a new pagetable is only constructed upon receiving the change notification.
* Kernel/Process: Use the relevant CPU's last process to determine when to switch its current process.
Previously it was checking the kernel's current_process variable, which gets overwritten every time a CPU runs its slice. The rescheduling happens after all CPUs have run their slice so the code was effectively only checking the last CPU's process.