Summary:
Changelog:
[Internal][Added] - Introduce drainMicrotasks to JSI
This diff proposed a new JSI API `drainMicrotasks` to define
how hosts may integrate with the JSVMs' internal microtask
queue (a.k.a. job queue) and hence their native Promise.
The name `drainMicrotasks` is slightly preferred over `drainJobs`
to favor *host-friendliness* over *engine-friendliness*.
This diff auto implement the new API in JSC and Hermes as stubs
to make sure things compiled.
Please refer to the doc-comments in the `jsi.h` for a detailed
documentation on the semantics and the design of this API.
### Notes on the existing APIs from JSVMs
The presence of such queue and APIs to operate on them are
ubiquitous:
- Hermes: `Runtime::drainJobs`
- V8: `MicrotaskQueue::PerformCheckpoint`
- JSC: `VM::drainMicrotasks`
- QuickJS: `JS_ExecutePendingJob`
The only exception is ChakraCore, which requires hosts to provide
the queue and set up the `JsSetPromiseContinuationCallback`,
but a JSI implementation can provide that queue trivially.
### Extra note on ECMA-262
ECMA-262 changed the spec at Mar 2020 from "asking an ECMAScript
implementation to maintain a Job Queue" to "Ask the embedder to
define its event loop, including the job queue" so technically:
- the internal approach is closer to the old spec.
- the ChakraCore approach is closer to the current spec.
Reviewed By: mhorowitz
Differential Revision: D27727920
fbshipit-source-id: b839b959facbc009f7d14b781e9287c46ea64373
Summary:
A key difference in WeakRefs with the Hades GC is that they are mutable,
in the sense that reading the value of a WeakRef while a GC is active might
clear the WeakRef.
For this reason, attempting to lock the WeakObject might mutate the backing
reference.
I preferred to communicate this change in behavior via the API rather than
`const_cast` it away inside the implementation.
Changelog: [Internal] Change jsi::WeakObject to be mutable in lockWeakObject
Reviewed By: mhorowitz
Differential Revision: D21485758
fbshipit-source-id: 3618928be8f8791aed56cb20673896ff5b786ded
Summary:
We are moving towards 100%-prettified files. That's the first step when we apply Clang Format for `ReactCommon`.
Changelog: [Internal]
Reviewed By: mdvacca
Differential Revision: D20110895
fbshipit-source-id: 0a0ce4997cf1c3721b0b07ef78c1a57ce87d20f9
Summary:
[A recent change to JSStringToSTLString](https://github.com/facebook/react-native/pull/26955) causes a crash when the function is invoked with invalid UTF-16 data. The old behaviour, restored here, was to truncate the string before the first invalid character.
Here's how [the original code](https://github.com/facebook/react-native/blob/aee88b6843cea63d6aa0b5879ad6ef9da4701846/ReactCommon/jsi/JSCRuntime.cpp#L287) handled this case:
```
std::string JSStringToSTLString(JSStringRef str) {
size_t maxBytes = JSStringGetMaximumUTF8CStringSize(str);
// ^ maxBytes >= 1 regardless of str's contents
std::vector<char> buffer(maxBytes);
// ^ vector is zero initialised
JSStringGetUTF8CString(str, buffer.data(), maxBytes);
// ^ writes '\0' at the first invalid character and returns early (see JSC source code)
return std::string(buffer.data());
// ^ copies the string up to the first '\0'
}
```
See the JSC implementations of [`JSStringGetUTF8CString`](https://opensource.apple.com/source/JavaScriptCore/JavaScriptCore-7600.8.7/API/JSStringRef.cpp.auto.html) and [`convertUTF16ToUTF8`](https://opensource.apple.com/source/WTF/WTF-7600.7.2/wtf/unicode/UTF8.cpp.auto.html).
Based on the fact that `JSStringGetUTF8CString` *always* null-terminates the buffer - even when it bails out of converting an invalid string - here we're able to both
1. keep the fast path (not zero-initialising, not scanning for the null terminator) for the common case when the data is valid and JSStringGetUTF8CString returns a nonzero length; and
2. return the truncated string when JSStringGetUTF8CString returns an error code of 0, by scanning for the null terminator.
Changelog: [General] [Fixed] - Fix crash when passing invalid UTF-16 data from JSC into native code
Differential Revision: D19902751
fbshipit-source-id: 06bace2719800e921ec115ad6a29251eafd473f6
Summary:
In my app I have a case where I need to pass a very large string (45MB) between JS and native. This is obviously suboptimal, but… this is where I'm at.
The main bottleneck to doing this turned out to be `jsi`'s `JSStringToSTLString()`, which was extremely slow. In my case, 4.7s to execute. After this change, 204ms.
I don't really know C++, so I'm not sure this code is 100% correct and safe, and I bet it could be done even better by avoiding the extra memory allocation (would shave off another 70ms).
## Changelog
[General] [Changed] - Make JSStringToSTLString 23x faster
Pull Request resolved: https://github.com/facebook/react-native/pull/26955
Reviewed By: shergin
Differential Revision: D19578728
Pulled By: motiz88
fbshipit-source-id: 2fbce83166953ce928f0a6aa36eed710bfe05383
Summary:
PR https://github.com/facebook/react-native/pull/24633 introduced some inconsistency in crash messaging, this PR fix it. Asked by mhorowitz
[General] [Added] - Consistent reporting native module name on crash on native side
Pull Request resolved: https://github.com/facebook/react-native/pull/24704
Differential Revision: D15237424
Pulled By: cpojer
fbshipit-source-id: ded8db45b2a2ec9998ff33fdbecef3f12c19578f
Summary:
After upgrading RN from 0.57 to 0.59.4 we've received a lot of crash reports like `Exception in HostObject::get: <unknown>` with no clue what native module caused the crash. This commit adds native module name on crash in this situations. Related to https://github.com/facebook/react-native/issues/24607.
[General] [Added] - Report native module name on crash when native module has failed to load
Pull Request resolved: https://github.com/facebook/react-native/pull/24633
Differential Revision: D15120225
Pulled By: cpojer
fbshipit-source-id: cf8e3e5953548a58f1d010eb70343da5ee946ae8
Summary:
This is the couple of hacks I used after I finished #23802 in order to get fabric working on RNTester. This is inspired from prior work by kmagiera.
The goal of this PR is to show others what I’m struggling with, and to eventually merge it sans hacks.
- Yarn Install
- Uncomment the commented out pods in RNTester's pod file
- Open RNTesterPods workspace
- Run App
- this is only for pods, the non-pod RNTester will no longer work until updated with fabric too.
- `SurfaceHostingView` & `SurfaceHostingProxyRootView` both try to start the surface immediately, this leads to a race condition due to the javascript not having loaded yet, the hack here is:
1. Swizzle the `start` method on `RCTFabricSurface` to no-op when called.
2. Add observer for `RCTJavaScriptDidLoadNotification`
3. Call private method `_startAllSurfaces` on `_surfacePresenter` in AppDelegate when we receive `RCTJavaScriptDidLoadNotification`.
[General] [Added] - Use Fabric in RNTester
Pull Request resolved: https://github.com/facebook/react-native/pull/23803
Reviewed By: shergin, mdvacca
Differential Revision: D14450726
Pulled By: fkgozali
fbshipit-source-id: 8ae2d48634fecb60db539aaf0a2c89ba1f572c27
Summary:
Fixes#23459. It is not legal to write the character array of a std::string, and can result in undefined behavior.
[General] [Fixed] - Crash when substring intersects with emoji
Pull Request resolved: https://github.com/facebook/react-native/pull/23609
Differential Revision: D14198159
Pulled By: mdvacca
fbshipit-source-id: 71060b1b99ddab89793c98c09f99ec9974479e62
Summary:
This adds a new jsi API prepareJavaScript. This accepts the same
parameters as evaluateJavaScript() but does not evaluate anything; instead
it returns a new object PreparedJavaScript which can itself be evaluated,
via the new API evaluatePreparedJavaScript().
There is a new empty class PreparedJavaScript which may be subclassed by
each Runtime variant to store its particular prepared form.
Reviewed By: mhorowitz
Differential Revision: D10491585
fbshipit-source-id: 702b9e23f2ff03d71a8ab17efb7e154b16dd8e87
Summary:
This changes jsi::evaluateJavaScript() to accept a
const shared_ptr<Buffer> & instead of a unique_ptr<Buffer.
It is reasonable to want to pass the same buffer to evaluateJavaScript()
multiple times. This will also help unify the API with the upcoming
prepareJavaScript() API.
Because shared_ptr has a unique_ptr constructor, this is compatible with
all call sites.
Reviewed By: mhorowitz
Differential Revision: D14001664
fbshipit-source-id: b7a0b7ec578a3fd6a6272241d50067269d2b03e4
Summary:
His PR is related to #22609
There are still some warnings related to folly, but I plan to make the correction and send the PR to the repo of the folly.
Changelog:
[IOS][Changed] - Fix warning in JSCRuntime
Pull Request resolved: https://github.com/facebook/react-native/pull/23201
Differential Revision: D13859393
Pulled By: cpojer
fbshipit-source-id: 95df2b76b28b460f890d11e1395fddb6b1cc8fed
Summary:
This check is too aggressive. We will consider putting it back once we are
more certain nothing will trigger it.
Differential Revision: D13350907
fbshipit-source-id: 6033bdbfe7adb2a18bdf889c090cf271497605e5
Summary:
In the version of JSC on iOS 11, creating a JSContext on one
thread and using it on another can trigger subtle and nearly
impossible to debug reentrancy-related crashes in the VM (see
https://bugs.webkit.org/show_bug.cgi?id=186827). In !NDEBUG builds,
check for this case and throw an exception, so it can be detected
early.
Reviewed By: amnn
Differential Revision: D13313264
fbshipit-source-id: ee85435c20e23c8520495ce743d2f91f2eeada5c
Summary:
Older versions of JSC (ios 11 and before) have a bug which I
believe the ProtectionQueue mechanism tickles:
https://bugs.webkit.org/show_bug.cgi?id=186827
This removes the ProtectionQueue and replaces it with an atomic flag
to avoid calling unprotect after VM shutdown.
This also fixes a race condition in shutdown.
Reviewed By: danzimm
Differential Revision: D12969953
fbshipit-source-id: fa3a14f3207be67a987ac3cf0fc1c9ce88837b0b
Summary:
We were not accounting for shutdown properly when counting
jsi Objects at shutdown.
Reviewed By: danzimm
Differential Revision: D10451732
fbshipit-source-id: 7f0eb357aa3a011b7b2a97e44c22549e06e311c5
Summary:
This diff is an implementation of jsi::Runtime which uses JSC as the virtual machine. All of the JSC-specific details are encapsulated here.
@public
Reviewed By: RSNara
Differential Revision: D9328242
fbshipit-source-id: be3c7bed161916c1cb9a48182600b558f054eadc