Closed
Bug 1169391
Opened 9 years ago
Closed 9 years ago
Clear out "reserved" Rooted contents between JSOP_* cases
Categories
(Core :: JavaScript Engine, defect)
Core
JavaScript Engine
Tracking
()
RESOLVED
FIXED
mozilla41
Tracking | Status | |
---|---|---|
firefox41 | --- | fixed |
People
(Reporter: sfink, Assigned: sfink)
References
Details
Attachments
(2 files)
44.74 KB,
patch
|
terrence
:
review+
|
Details | Diff | Splinter Review |
4.57 KB,
patch
|
sfink
:
review+
|
Details | Diff | Splinter Review |
Right now, Interpret() pushes a small pile of Rooted<T> variables onto the runtime lists on entry, then the JSOPs change their values instead of instantiating their own. But they don't clear their values when they're done, which means that you can end up with stale values keeping things alive that do not need to be kept alive.
Assignee | ||
Comment 1•9 years ago
|
||
Lots of bikeshedding opportunity here. I wasn't very happy to do all the cut & paste implementation of operator blahblah() stuff, and I *really* wasn't happy about defining an operator&. Especially since it's barely used. But anyway, this doesn't seem completely unreasonable.
Attachment #8612478 -
Flags: review?(terrence)
Comment 2•9 years ago
|
||
Comment on attachment 8612478 [details] [diff] [review] Use a ReservedRooted class for optimized Rooted use in vm/Interpreter.cpp Review of attachment 8612478 [details] [diff] [review]: ----------------------------------------------------------------- This is brilliant. I think you may even have saved a few lines, ultimately. At the very least it makes the actual implementation code cleaner. ::: js/public/RootingAPI.h @@ +75,5 @@ > * > * - MutableHandle<T> is a non-const reference to Rooted<T>. It is used in the > * same way as Handle<T> and includes a |set(const T& v)| method to allow > * updating the value of the referenced Rooted<T>. A MutableHandle<T> can be > + * created with an implicit cast from a Rooted<T>*. \o/ ::: js/src/vm/Interpreter.cpp @@ +1660,5 @@ > + * variables at the beginning, thus inserting them into the Rooted list once > + * upon entry. ReservedRooted "borrows" a reserved Rooted variable and uses it > + * within a local scope, resetting the value to nullptr (or the appropriate > + * equivalent for T) at scope end. This still avoids inserting/removing the > + * Rooted from the rooter list, but still prevents stale values from being kept |This still clause, but still clause| reads a bit awkwardly. @@ +1669,5 @@ > +class ReservedRootedBase { > +}; > + > +template<typename T> > +class ReservedRooted : public ReservedRootedBase<T> { { on newline since the body is non-trivial. @@ +1688,5 @@ > + > + T& get() { return savedRoot->get(); } > + const T& get() const { return savedRoot->get(); } > + T* address() { return savedRoot->address(); } > + const T* address() const { return savedRoot->address(); } Please use the existing shared decls for these where possible. I think something like: DECLARE_NONPOINTER_ACCESSOR_METHODS(*savedRoot->address()); DECLARE_NONPOINTER_MUTABLE_ACCESSOR_METHODS(*savedRoot->address()); @@ +1691,5 @@ > + T* address() { return savedRoot->address(); } > + const T* address() const { return savedRoot->address(); } > + > + operator const T&() const { return get(); } > + operator T&() { return get(); } And here you can probably get away with: DECLARE_NONPOINTER_MUTABLE_ACCESSOR_METHODS(T); @@ +1695,5 @@ > + operator T&() { return get(); } > + const T& operator->() const { return get(); } > + operator Handle<T>() { return *savedRoot; } > + operator Rooted<T>&() { return *savedRoot; } > + ReservedRooted<T>& operator=(const T& p) { *savedRoot = p; return *this; } DECLARE_NONPOINTER_MUTABLE_ACCESSOR_METHODS(ReservedRooted, T) You will need to add a set() method for that, though, so it's less win. Not sure how the others fit in. Most of the other wrapper classes needed a few one-offs too, so not a big deal. @@ +1706,5 @@ > + friend class ValueOperations<ReservedRooted<Value>>; > + const Value* extract() const { > + return static_cast<const ReservedRooted<Value>*>(this)->address(); > + } > +}; This seems like a ton of boilerplate until you remember how much you get with it automatically. Still might be worth opening a bug to add a MACRO to wrap all of these nearly-identical CRTP definitions.
Attachment #8612478 -
Flags: review?(terrence) → review+
Comment 3•9 years ago
|
||
Clang is a bit less flexible with indirect goto -- it needs ReservedRooted to be destructed before we hit any indirect goto (although normal goto is fine). This patch adds the requisite {} to make that happen. I generated this patch with -w, since that's a ton of spurious indentation change. You can safely assume that I did actually fix up the indentation.
Attachment #8613130 -
Flags: review?(sphink)
Assignee | ||
Updated•9 years ago
|
Attachment #8613130 -
Flags: review?(sphink) → review+
Assignee | ||
Comment 4•9 years ago
|
||
https://treeherder.mozilla.org/#/jobs?repo=try&revision=350c38d51b18
Assignee | ||
Comment 5•9 years ago
|
||
Without the unified breakage: https://treeherder.mozilla.org/#/jobs?repo=try&revision=6b715231bb68
Comment 7•9 years ago
|
||
https://hg.mozilla.org/mozilla-central/rev/c9c7ec25b894
Status: ASSIGNED → RESOLVED
Closed: 9 years ago
status-firefox41:
--- → fixed
Resolution: --- → FIXED
Target Milestone: --- → mozilla41
You need to log in
before you can comment on or make changes to this bug.
Description
•