mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-26 19:55:39 +00:00
e2240ec5a2
In XPConnect, native values are passed around within nsXPTCMiniVariant objects. an [nsXPTCMiniVariant] contains 64-bits of data in a union type. nsXPTCMiniVariant values are created by the platform-specific glue code and passed into XPConnect proper when calling from C++ into JS. When calling from JS into C++, we instead create nsXPTCVariant objects and pass them into the glue code. These objects have extra information in addition to the nsXPTCMiniVariant: namely they also have a `type` field with the type stored in the variant, space for flags, and a `ptr` field which is passed over IPC instead of the inner nsXPTCMiniVariant when a flag (`PTR_IS_DATA`) is set. The JSValue type in XPConnect is always passed as a pointer to a JSValue object, both for in parameters and out parameters. This is handled by making the JSValue type be unconditionally flagged as [`IsIndirect()`] This flag is also used for all types of outparameters. When the `IsIndirect()` flag is set, it means that the actual data is stored in the nsXPTCVariant's val field, and it sets the flag to tell the glue code to instead pass the `ptr` field (which is always pointing to the `val` field for [legacy reasons]) into the C++ code. In contrast "dipper" is a different and super weird flag. Currently only the string class types (nsACString & nsAString) are marked as "dipper". A "dipper" type is always passed as an "in" type (and thus always passed "directly"), even when it's actually an out parameter. XPConnect treats these types as though they are pointer types (nsAString*). This means that there is no space in the nsXPTCVariant to store the actual nsAString types when passing from JS into C++, so these values have to be allocated by a different mechanism (in the current code, there is a size 2 buffer for each string type in the context and once that buffer is exceeded, we heap allocate the nsString values). In effect, the current state looks something like this: +------------+---------------------+---------------------+ | type | out (xpt/native) | in (xpt/native) | +------------+---------------------+---------------------+ | TD_INT32 | indirect (int32_t*) | direct (int32_t) | +------------+---------------------+---------------------+ | TD_JSVAL | indirect (JSValue*) | indirect (JSValue*) | +------------+---------------------+---------------------+ | TD_ASTRING | direct (nsAString*) | direct (nsAString*) | +------------+---------------------+---------------------+ This patch ensures there is enough space in the nsXPTCVariant to fit the nsString value, and switches string class types to being unconditionally indirect instead of using the dipper system. This allows us to delete a ton of dipper-specific code, and unify the indirect and string class codepaths. This only affects the size of nsXPTCVariant objects, and does not affect nsXPTCMiniVariant objects. nsXPTCVariant objects are never allocated by the platform-specific binding code, rather, they are allocated in an AutoTArray on the stack as part of the CallMethodHelper object. The size increase is a total of 1 word, so 4 bytes in 32-bit builds, and 8 bytes in 64-bit builds, which is ignorable for stack allocated objects. [nsXPTCMiniVariant]: https://searchfox.org/mozilla-central/rev/eb6c5214a63e20a3fff455e92c876287a8d2e188/xpcom/reflect/xptcall/xptcall.h#20-47 [`IsIndirect()`]: https://searchfox.org/mozilla-central/rev/c0d81882c7941c4ff13a50603e37095cdab0d1ea/xpcom/reflect/xptinfo/xptinfo.h#371 [legacy reasons]: https://searchfox.org/mozilla-central/rev/eb6c5214a63e20a3fff455e92c876287a8d2e188/xpcom/reflect/xptcall/xptcall.h#66-79 |
||
---|---|---|
.. | ||
crashtests | ||
idl | ||
loader | ||
public | ||
shell | ||
src | ||
tests | ||
wrappers | ||
moz.build |