-
Notifications
You must be signed in to change notification settings - Fork 24.8k
Description
Description
Opening the Performance Monitor causes a crash as of iOS 13.4
React Native version:
System:
OS: macOS 10.15.3
CPU: (8) x64 Intel(R) Core(TM) i7-8559U CPU @ 2.70GHz
Memory: 148.41 MB / 16.00 GB
Shell: 5.7.1 - /bin/zsh
Binaries:
Node: 10.16.0 - ~/.nvm/versions/node/v10.16.0/bin/node
Yarn: 1.21.1 - /usr/local/bin/yarn
npm: 6.9.0 - ~/.nvm/versions/node/v10.16.0/bin/npm
Watchman: 4.9.0 - /usr/local/bin/watchman
SDKs:
iOS SDK:
Platforms: iOS 13.4, DriverKit 19.0, macOS 10.15, tvOS 13.4, watchOS 6.2
Android SDK:
API Levels: 22, 23, 25, 26, 27, 28, 29
Build Tools: 25.0.3, 26.0.3, 27.0.3, 28.0.2, 28.0.3, 29.0.2
System Images: android-22 | Intel x86 Atom_64, android-23 | Google APIs Intel x86 Atom, android-25 | Android TV Intel x86 Atom, android-26 | Google APIs Intel x86 Atom_64, android-27 | Google Play Intel x86 Atom, android-28 | Google Play Intel x86 Atom, android-29 | Google APIs Intel x86 Atom, android-29 | Google Play Intel x86 Atom
Android NDK: 21.0.6113669
IDEs:
Android Studio: 3.6 AI-192.7142.36.36.6241897
Xcode: 11.4/11E146 - /usr/bin/xcodebuild
Languages:
Python: 2.7.15 - /usr/local/bin/python
npmPackages:
@react-native-community/cli: Not Found
react: 16.11.0 => 16.11.0
react-native: 0.62.0 => 0.62.0
npmGlobalPackages:
*react-native*: Not Found
Steps To Reproduce
- Start react-native on an iOS 13.4 simulator
npx react-native init PerfCrash
cd PerfCrash
yarn ios
- Open debug-menu
- Tap on "Show Perf Monitor"
Expected Results
Shows Performance Monitor; and doesn't crash.
Additional info
I've debugged the issue and seem to have found the problem. JavaScriptCore has been updated in iOS 13.4 and it seems it is no longer possible to set the JavaScript Core options after initializing the VM.
The RCTJSCSetOption
function now causes an EXC_BAD_ACCESS
exception. The setOption
function is resolved correctly but when calling it, it throws the exception. I've debugged the assembly and providing invalid values (logGC2=1
and logGC=3
) do not produce a crash. So it doesn't appear to be a parsing issue, and the crash seems to occur when actually updating the option to 1
.
static BOOL RCTJSCSetOption(const char *option)
{
static RCTJSCSetOptionType setOption;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
/**
* JSC private C++ static method to toggle options at runtime
*
* JSC::Options::setOptions - JavaScriptCore/runtime/Options.h
*/
setOption = dlsym(RTLD_DEFAULT, "_ZN3JSC7Options9setOptionEPKc");
if (RCT_DEBUG && setOption == NULL) {
RCTLogWarn(@"The symbol used to enable JSC runtime options is not available in this iOS version");
}
});
if (setOption) {
return setOption(option); // <-- This throws EXC_BAD_ACCESS exception
} else {
return NO;
}
}
After inspection on the JavaScriptCore code it was found that the JavaScriptCore options can no longer be changed after the VM was initialized.
https://github.com/WebKit/webkit/blob/master/Source/JavaScriptCore/runtime/OptionsList.h#L74
https://raw.githubusercontent.com/WebKit/webkit/master/Source/JavaScriptCore/ChangeLog
2019-09-12 Mark Lam <mark.lam@apple.com>
Harden JSC against the abuse of runtime options.
https://bugs.webkit.org/show_bug.cgi?id=201597
<rdar://problem/55167068>
Reviewed by Filip Pizlo.
Linux parts contributed by Carlos Garcia Campos <cgarcia@igalia.com>.
1. Introduce a JSC::Config struct that will be protected as ReadOnly once the
first VM instance is constructed. The end of the VM constructor calls
Config::permanentlyFreeze() which will make the Config ReadOnly.