There's no guarantee that directory initialization has completed by this
point, so we can't safely use NativeLibrary.
I'm making this change because of a crash being reported in Google Play
Console. The exact way it's crashing is mysterious to me, so I'm not
sure if this commit fixes the crash, but I think this commit is
a reasonable change to make even if it doesn't fix the crash. Backtrace
from Google Play Console:
#00 pc 0x0000000000469074 /data/app/~~m0kqybFNfeqnDenQFc53XQ==/org.dolphinemu.dolphinemu-Mtaw0lU8DVUQbte2ZjBp3w==/lib/arm64/libmain.so (std::__ndk1::pair<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>> const, std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>::pair[abi:nn180000]<char const* const&, char const* const&, 0>(char const* const&, char const* const&)) (BuildId: 64cfebf5b574b6729ebc51799aa94ccc3238cbcc)
#01 pc 0x0000000000468e9c /data/app/~~m0kqybFNfeqnDenQFc53XQ==/org.dolphinemu.dolphinemu-Mtaw0lU8DVUQbte2ZjBp3w==/lib/arm64/libmain.so (std::__ndk1::pair<std::__ndk1::__tree_iterator<std::__ndk1::__value_type<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>, std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>, std::__ndk1::__tree_node<std::__ndk1::__value_type<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>, std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>, void*>*, long>, bool> std::__ndk1::__tree<std::__ndk1::__value_type<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>, std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>, std::__ndk1::__map_value_compare<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>, std::__ndk1::__value_type<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>, std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>, std::__ndk1::less<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>, true>, std::__ndk1::allocator<std::__ndk1::__value_type<std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>, std::__ndk1::basic_string<char, std::__ndk1::char_traits<char>, std::__ndk1::allocator<char>>>>>::__emplace_unique_impl<char const* const&, char const* const&>(char const* const&, char const* const&)) (BuildId: 64cfebf5b574b6729ebc51799aa94ccc3238cbcc)
#02 pc 0x0000000000462f08 /data/app/~~m0kqybFNfeqnDenQFc53XQ==/org.dolphinemu.dolphinemu-Mtaw0lU8DVUQbte2ZjBp3w==/lib/arm64/libmain.so (Common::Log::LogManager::GetLogTypes()) (BuildId: 64cfebf5b574b6729ebc51799aa94ccc3238cbcc)
#03 pc 0x000000000044339c /data/app/~~m0kqybFNfeqnDenQFc53XQ==/org.dolphinemu.dolphinemu-Mtaw0lU8DVUQbte2ZjBp3w==/lib/arm64/libmain.so (Java_org_dolphinemu_dolphinemu_NativeLibrary_GetLogTypeNames+56) (BuildId: 64cfebf5b574b6729ebc51799aa94ccc3238cbcc)
#04 pc 0x000000000031456c /data/misc/apexdata/com.android.art/dalvik-cache/arm64/boot.oat (art_jni_trampoline+108)
#05 pc 0x0000000000781508 /apex/com.android.art/lib64/libart.so (nterp_helper+152)
#06 pc 0x00000000002d94d4 /data/app/~~m0kqybFNfeqnDenQFc53XQ==/org.dolphinemu.dolphinemu-Mtaw0lU8DVUQbte2ZjBp3w==/base.apk (org.dolphinemu.dolphinemu.features.settings.ui.SettingsFragmentPresenter.<clinit>+16)
[...]
Previously, PerformanceTracker registered a callback to be updated on
emulation state changes. PerformanceTrackers live in a global variable
(g_perf_metrics) within libvideocommon. The callback was stored in a
global variable in libcore. This created a race condition at shutdown
between these libraries, when the PerfTracker's destructor tried to
unregister the callback.
Notify the PerfTracker directly from libcore, without callbacks, since
Core.cpp already references g_perf_metrics explicitly. Also rename
Core::CallOnStateChangedCallbacks to NotifyStateChanged to better
reflect what it's doing.
Extracted games contain a boot.bin file that contains the disc header.
These boot.bin files are considered valid volumes by Dolphin, since
Dolphin only checks the disc header to determine if something is a valid
GC/Wii disc. Running them doesn't make any sense, though.
boot.bin files used to not be scanned by Dolphin due to their file
extension, but .bin was added to the list of file extensions to scan for
in 494e2c0. To stop them from showing up in the game list, let's update
the ShouldHideFromGameList mechanism.
Different threads are adding and calling callbacks, so this should have
some locking. This is both to ensure thread safety when accessing
`s_callbacks` and to ensure that there won't be situations where a
callback gets called after it's removed.
`s_callback_guards` is also accessed from multiple threads and has
therefore been made atomic.
a1691a4 made it so analytics start events can only be generated when
starting the main activity. However, some users launch Dolphin's
emulation activity from a separate frontend application, bypassing
Dolphin's main activity. This change adjusts the logic so that start
events can be generated if any activity is started after 6 hours of
inactivity. This more closely matches the behavior we had before
a1691a4, while still ensuring duplicate start events aren't generated.
I've also fixed the inconsistent indentation in ActivityTracker.kt.
Require callers of Config::AddConfigChangedCallback and
CPUThreadConfigCallback::AddConfigChangedCallback to handle the returned
ConfigChangedCallbackIDs to hopefully prevent future issues with
callbacks getting called after their associated objects have been
destroyed.
Use a single lambda as a callback which calls InitCustomPaths and
RefreshConfig instead of having separate callbacks for each of them.
This fixes the callback for InitCustomPaths not being removed on
shutdown; the callback for the lambda (previously for RefreshConfig) is
already removed in Shutdown().
Prevent SetHardcoreMode from being called after m_client is set to
nullptr. rc_client_set_hardcore_enabled() checks for nullptr so this
didn't cause any problems, but better not to rely on that.
Also prevents multiple SetHardcoreMode callbacks from piling up when
repeatedly toggling Config::RA_ENABLED.
Remove ConfigChangedCallback in MainWindow's destructor to prevent the
callback from accessing the destroyed MainWindow afterward.
After MainWindow is destroyed UICommon::Shutdown calls
LogManager::Shutdown which ultimately triggers any remaining callbacks.
This resulted in calling MainWindow::OnHardcoreChanged, which crashed in
debug builds and didn't have any obvious effect in release builds.
Fixing an oversight: this was causing the debugger to be disabled if achievements were disabled but hardcore mode was still enabled in the .ini. This fix properly checks for hardcore state via AchievementManager which takes both settings into account.
I've been playing Rock Band 3 recently and have experienced a bug where
sometimes if you disconnect and reconnect a USB microphone, the game
won't pick up on it connecting, not even it you disconnect and reconnect
it again. An investigation into what's going on inside Dolphin shows
that when the game triggers a call to OH0::DeviceOpen after the device
has been reinserted, Dolphin doesn't open the device because it's
already present in m_opened_devices.
Removing the device from m_opened_devices after calling OH0::TriggerHook
in OH0::OnDeviceChange resolves this specific issue in my testing. Doing
this matches us removing the device from m_opened_devices after calling
OH0::TriggerHook in OH0::DeviceClose, but I haven't looked at exactly
what real IOS does.
I have been able to reproduce a much rarer issue that has the same
symptoms on the surface but where OH0::DeviceOpen gets past its
m_opened_devices check. I'm currently not sure what the cause of this
remaining issue is.
71f654c added a new platform in the middle of the C++ platform enum
without updating the corresponding Android code, making the Android code
incorrectly treat Wii discs as WAD files, WAD files as DOL/ELF files,
and so on. This commit fixes the problem.
To be able to add the new Triforce entry into the Platform enum without
it leading to the UI getting an additional tab, I'm splitting the enum
into Platform and PlatformTab. Platform now exactly matches the C++
enum (previously it excluded ELFOrDOL), and PlatformTab has the same
content as the old Platform.
RetroAchievements disables pausing too frequently when running but there's no sense of doing this if RetroAchievements does not currently have a game running.
Some games open two USB interfaces, e.g. /dev/usb/oh0 and /dev/usb/hid.
This was causing us to run two scanning threads at once, using up more
CPU time for scanning than we need to.
We have identified that a failed RetroAchievements game load (most easily done when closing a game before the server can finish responding) can leave data behind that causes problems. As such, refactored CloseGame to always delete data even if there wasn't a game loaded when it was called, and call it on the failure paths of LoadGameCallback.
Instead of having USBScanner create "hooks" as it scans for devices,
let's have USBScanner present a list of devices to USBHost and have
USBHost diff the new device list with its old device list to create the
hook calls instead. This gets rid of some complex edge cases that the
next commit otherwise would have to deal with, in particular regarding
toggling determinism and adding new USBHosts to a USBScanner.
Note: After adding the missing locking of m_devices_mutex, I had to move
the locking of m_hooks_mutex to avoid a random deadlock between the CPU
thread and USB scanning thread. (Either that or I would have to lock
m_devices_mutex before m_hooks_mutex.)
This gets rid of the ugly direct access to USBScanner::m_devices that
was introduced by the previous commit.
This also fixes a potential thread safety issue.
USB_HIDv4::TriggerDeviceChangeReply loops through m_devices and calls
GetDeviceEntry for each device. If USB_HIDv4::TriggerDeviceChangeReply
is called after a new device is added to m_devices but before hooks are
dispatched, GetDeviceEntry crashes, because the hook that's supposed to
update m_device_ids hasn't run yet. With this commit, this issue can no
longer happen, because USBHost::m_devices_mutex doesn't get unlocked in
between updating m_devices and dispatching the hooks.
dolphin-start event was being generated twice for the normal
end-user case, as can be seen in analytics data for some years.
The problem occured when:
* Android reaped the process hosting the dolphin activity
(e.g. for power/memory saving).
and
* Dolphin activity was in "stopped" state for > 6 hours before
being switched back to.
Under above conditions, both calls to ReportStartToAnalytics
would be performed, as dolphin thought it was being launched anew,
and also thought it had been asleep for > 6 hours.
fixes https://bugs.dolphin-emu.org/issues/13675
Due to requests from RA Devs, updating the AchievementManager LoadGameCallback to still set MemoryPeeker (and set m_system) if the load game response is NO_GAME_LOADED, so that the memory inspector et al continue function properly on unidentified hashes. Without this, no memory is loaded and the memory inspector will show all zeroes.
If the development system is started for a game with an unrecognized hash, RA_Integration opens a dialog for connecting the hash with a title. That dialog is prepopulated by the results of GameTitleEstimateHandler.
Displays an additional message when an achievement unlocks that isn't on the site yet (either hasn't yet been uploaded or modified from remote) i.e. achievements the "player" is actively developing.
When you use TimePlayed, you have to provide a game ID either when
creating the object or when calling GetTimePlayed on it. If you don't
provide a game ID when creating the object, function calls that don't
take a game ID will silently fail, except for Reload. This isn't very
obvious, and there's no strong benefit to storing the game ID inside
TimePlayed anyway (it just lets TimePlayed skip calling EscapeFileName),
so this commit removes the TimePlayed constructor that takes a game ID
and instead makes the functions that need game IDs always take a game ID
argument.
It was being done manually, which a TODO comment advised against.
Using generic_string() from std::filesystem::path solves this.
Fix encoding issue using generic_wstring instead.
Fix overlays stacking on top of each other or not moving to the edge of
the screen when enabling or disabling overlays while emulation is
active.
This change only applies when Config::GFX_MOVABLE_PERFORMANCE_METRICS is
False.
This lets you use PS3 Rock Band controllers with Wii Rock Band and
Guitar Hero games.
A normal user will probably never have any reason to disable this
behavior, but I figured maybe there's some person out there who would
like to disable it. (For instance, I know there's a mod for RB3 that's
trying to implement the same kind of cross-console controller
compatibility, and that can only be tested if the behavior I'm adding is
disabled.) So the behavior is controlled by an INI-only setting.