Make base::WeakPtr::Get() fast
It was previously calling WeakReference::is_valid() which was an out-of-line
method. That means code like
if (my_weak_ptr)
my_weak_ptr->foo();
would do two calls to is_valid(), plus tests and branching.
The is_valid() method showed up as one of the most frequently called non-inline
functions during browser start-up on Windows (about 1M calls).
is_valid() was also inefficient because it had to do a null-pointer check on
flag_, as well as checking if the flag was marked valid.
This patch removes the null-pointer check by using a sentinel object instead of
a nullptr. And instead of storing a bool in the flag, it stores a pointer-sized
bitmask 0 or ~0, so it can be AND'ed with the pointer value and conveniently
setting EFLAGS so that the code above just becomes a few loads, AND, branch,
and call. (The size of Flag is unchanged; it grows into the padding only.)
This is expected to reduce the binary size by ~48KB on Android, and increase it
by 79KB on x64 Linux -- something that's paid for by the split-out refactorings
to WeakPtr and WeakPtrFactory.
Exposing the SequenceChecker calls in inline functions caused the
MessageLoopTestType*.Nesting test to overflow on Win64 dcheck release builds,
which is why this patch also lowers the recursion depth there.
BUG=728324
Review-Url: https://codereview.chromium.org/2963623002
Cr-Commit-Position: refs/heads/master@{#483427}
CrOS-Libchrome-Original-Commit: 526f714c9ae172c3b16581b7e11eb035fd14274e
3 files changed