Remove unused atomic utils
The removed building blocks have either been completely unused or have already been replaced. Bug: Change-Id: I68a4d5d42b7f1cc3c5f8d0e7ea7146c5a0f59048 Reviewed-on: https://chromium-review.googlesource.com/612163 Reviewed-by: Ulan Degenbaev <ulan@chromium.org> Commit-Queue: Michael Lippautz <mlippautz@chromium.org> Cr-Commit-Position: refs/heads/master@{#47304}
This commit is contained in:
parent
d9a036317c
commit
f3d48f56a8
@ -54,61 +54,6 @@ class AtomicNumber {
|
||||
base::AtomicWord value_;
|
||||
};
|
||||
|
||||
// This type uses no barrier accessors to change atomic word. Be careful with
|
||||
// data races.
|
||||
template <typename T>
|
||||
class NoBarrierAtomicValue {
|
||||
public:
|
||||
NoBarrierAtomicValue() : value_(0) {}
|
||||
|
||||
explicit NoBarrierAtomicValue(T initial)
|
||||
: value_(cast_helper<T>::to_storage_type(initial)) {}
|
||||
|
||||
static NoBarrierAtomicValue* FromAddress(void* address) {
|
||||
return reinterpret_cast<base::NoBarrierAtomicValue<T>*>(address);
|
||||
}
|
||||
|
||||
V8_INLINE bool TrySetValue(T old_value, T new_value) {
|
||||
return base::Relaxed_CompareAndSwap(
|
||||
&value_, cast_helper<T>::to_storage_type(old_value),
|
||||
cast_helper<T>::to_storage_type(new_value)) ==
|
||||
cast_helper<T>::to_storage_type(old_value);
|
||||
}
|
||||
|
||||
V8_INLINE T Value() const {
|
||||
return cast_helper<T>::to_return_type(base::Relaxed_Load(&value_));
|
||||
}
|
||||
|
||||
V8_INLINE void SetValue(T new_value) {
|
||||
base::Relaxed_Store(&value_, cast_helper<T>::to_storage_type(new_value));
|
||||
}
|
||||
|
||||
private:
|
||||
STATIC_ASSERT(sizeof(T) <= sizeof(base::AtomicWord));
|
||||
|
||||
template <typename S>
|
||||
struct cast_helper {
|
||||
static base::AtomicWord to_storage_type(S value) {
|
||||
return static_cast<base::AtomicWord>(value);
|
||||
}
|
||||
static S to_return_type(base::AtomicWord value) {
|
||||
return static_cast<S>(value);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename S>
|
||||
struct cast_helper<S*> {
|
||||
static base::AtomicWord to_storage_type(S* value) {
|
||||
return reinterpret_cast<base::AtomicWord>(value);
|
||||
}
|
||||
static S* to_return_type(base::AtomicWord value) {
|
||||
return reinterpret_cast<S*>(value);
|
||||
}
|
||||
};
|
||||
|
||||
base::AtomicWord value_;
|
||||
};
|
||||
|
||||
// Flag using T atomically. Also accepts void* as T.
|
||||
template <typename T>
|
||||
class AtomicValue {
|
||||
@ -175,82 +120,6 @@ class AtomicValue {
|
||||
base::AtomicWord value_;
|
||||
};
|
||||
|
||||
|
||||
// See utils.h for EnumSet. Storage is always base::AtomicWord.
|
||||
// Requirements on E:
|
||||
// - No explicit values.
|
||||
// - E::kLastValue defined to be the last actually used value.
|
||||
//
|
||||
// Example:
|
||||
// enum E { kA, kB, kC, kLastValue = kC };
|
||||
template <class E>
|
||||
class AtomicEnumSet {
|
||||
public:
|
||||
explicit AtomicEnumSet(base::AtomicWord bits = 0) : bits_(bits) {}
|
||||
|
||||
bool IsEmpty() const { return ToIntegral() == 0; }
|
||||
|
||||
bool Contains(E element) const { return (ToIntegral() & Mask(element)) != 0; }
|
||||
bool ContainsAnyOf(const AtomicEnumSet& set) const {
|
||||
return (ToIntegral() & set.ToIntegral()) != 0;
|
||||
}
|
||||
|
||||
void RemoveAll() { base::Release_Store(&bits_, 0); }
|
||||
|
||||
bool operator==(const AtomicEnumSet& set) const {
|
||||
return ToIntegral() == set.ToIntegral();
|
||||
}
|
||||
|
||||
bool operator!=(const AtomicEnumSet& set) const {
|
||||
return ToIntegral() != set.ToIntegral();
|
||||
}
|
||||
|
||||
AtomicEnumSet<E> operator|(const AtomicEnumSet& set) const {
|
||||
return AtomicEnumSet<E>(ToIntegral() | set.ToIntegral());
|
||||
}
|
||||
|
||||
// The following operations modify the underlying storage.
|
||||
|
||||
#define ATOMIC_SET_WRITE(OP, NEW_VAL) \
|
||||
do { \
|
||||
base::AtomicWord old; \
|
||||
do { \
|
||||
old = base::Acquire_Load(&bits_); \
|
||||
} while (base::Release_CompareAndSwap(&bits_, old, old OP NEW_VAL) != \
|
||||
old); \
|
||||
} while (false)
|
||||
|
||||
void Add(E element) { ATOMIC_SET_WRITE(|, Mask(element)); }
|
||||
|
||||
void Add(const AtomicEnumSet& set) { ATOMIC_SET_WRITE(|, set.ToIntegral()); }
|
||||
|
||||
void Remove(E element) { ATOMIC_SET_WRITE(&, ~Mask(element)); }
|
||||
|
||||
void Remove(const AtomicEnumSet& set) {
|
||||
ATOMIC_SET_WRITE(&, ~set.ToIntegral());
|
||||
}
|
||||
|
||||
void Intersect(const AtomicEnumSet& set) {
|
||||
ATOMIC_SET_WRITE(&, set.ToIntegral());
|
||||
}
|
||||
|
||||
#undef ATOMIC_SET_OP
|
||||
|
||||
private:
|
||||
// Check whether there's enough storage to hold E.
|
||||
STATIC_ASSERT(E::kLastValue < (sizeof(base::AtomicWord) * CHAR_BIT));
|
||||
|
||||
V8_INLINE base::AtomicWord ToIntegral() const {
|
||||
return base::Acquire_Load(&bits_);
|
||||
}
|
||||
|
||||
V8_INLINE base::AtomicWord Mask(E element) const {
|
||||
return static_cast<base::AtomicWord>(1) << element;
|
||||
}
|
||||
|
||||
base::AtomicWord bits_;
|
||||
};
|
||||
|
||||
class AsAtomic32 {
|
||||
public:
|
||||
template <typename T>
|
||||
|
@ -126,7 +126,8 @@ void LiveObjectRange<mode>::iterator::AdvanceToNextValidObject() {
|
||||
// make sure that we skip all set bits in the black area until the
|
||||
// object ends.
|
||||
HeapObject* black_object = HeapObject::FromAddress(addr);
|
||||
map = base::NoBarrierAtomicValue<Map*>::FromAddress(addr)->Value();
|
||||
map =
|
||||
base::AsAtomicPointer::Relaxed_Load(reinterpret_cast<Map**>(addr));
|
||||
size = black_object->SizeFromMap(map);
|
||||
Address end = addr + size - kPointerSize;
|
||||
// One word filler objects do not borrow the second mark bit. We have
|
||||
@ -153,7 +154,8 @@ void LiveObjectRange<mode>::iterator::AdvanceToNextValidObject() {
|
||||
object = black_object;
|
||||
}
|
||||
} else if ((mode == kGreyObjects || mode == kAllLiveObjects)) {
|
||||
map = base::NoBarrierAtomicValue<Map*>::FromAddress(addr)->Value();
|
||||
map =
|
||||
base::AsAtomicPointer::Relaxed_Load(reinterpret_cast<Map**>(addr));
|
||||
object = HeapObject::FromAddress(addr);
|
||||
size = object->SizeFromMap(map);
|
||||
}
|
||||
|
@ -597,21 +597,18 @@ class MemoryChunk {
|
||||
void set_prev_chunk(MemoryChunk* prev) { prev_chunk_.SetValue(prev); }
|
||||
|
||||
Space* owner() const {
|
||||
intptr_t owner_value = base::NoBarrierAtomicValue<intptr_t>::FromAddress(
|
||||
const_cast<Address*>(&owner_))
|
||||
->Value();
|
||||
if ((owner_value & kPageHeaderTagMask) == kPageHeaderTag) {
|
||||
return reinterpret_cast<Space*>(owner_value - kPageHeaderTag);
|
||||
} else {
|
||||
return nullptr;
|
||||
}
|
||||
uintptr_t owner_value = base::AsAtomicWord::Relaxed_Load(
|
||||
reinterpret_cast<const uintptr_t*>(&owner_));
|
||||
return ((owner_value & kPageHeaderTagMask) == kPageHeaderTag)
|
||||
? reinterpret_cast<Space*>(owner_value - kPageHeaderTag)
|
||||
: nullptr;
|
||||
}
|
||||
|
||||
void set_owner(Space* space) {
|
||||
DCHECK((reinterpret_cast<intptr_t>(space) & kPageHeaderTagMask) == 0);
|
||||
DCHECK_EQ(0, reinterpret_cast<intptr_t>(space) & kPageHeaderTagMask);
|
||||
owner_ = reinterpret_cast<Address>(space) + kPageHeaderTag;
|
||||
DCHECK((reinterpret_cast<intptr_t>(owner_) & kPageHeaderTagMask) ==
|
||||
kPageHeaderTag);
|
||||
DCHECK_EQ(kPageHeaderTag,
|
||||
reinterpret_cast<intptr_t>(owner_) & kPageHeaderTagMask);
|
||||
}
|
||||
|
||||
bool HasPageHeader() { return owner() != nullptr; }
|
||||
|
@ -125,150 +125,5 @@ TEST(AtomicValue, WithVoidStar) {
|
||||
EXPECT_EQ(&dummy, a.Value());
|
||||
}
|
||||
|
||||
TEST(NoBarrierAtomicValue, Initial) {
|
||||
NoBarrierAtomicValue<TestFlag> a(kA);
|
||||
EXPECT_EQ(TestFlag::kA, a.Value());
|
||||
}
|
||||
|
||||
TEST(NoBarrierAtomicValue, SetValue) {
|
||||
NoBarrierAtomicValue<TestFlag> a(kB);
|
||||
a.SetValue(kC);
|
||||
EXPECT_EQ(TestFlag::kC, a.Value());
|
||||
}
|
||||
|
||||
TEST(NoBarrierAtomicValue, WithVoidStar) {
|
||||
NoBarrierAtomicValue<void*> a(nullptr);
|
||||
NoBarrierAtomicValue<void*> dummy(nullptr);
|
||||
EXPECT_EQ(nullptr, a.Value());
|
||||
a.SetValue(&a);
|
||||
EXPECT_EQ(&a, a.Value());
|
||||
}
|
||||
|
||||
TEST(NoBarrierAtomicValue, Construction) {
|
||||
NoBarrierAtomicValue<TestFlag> a(kA);
|
||||
TestFlag b = kA;
|
||||
NoBarrierAtomicValue<TestFlag>* ptr =
|
||||
NoBarrierAtomicValue<TestFlag>::FromAddress(&b);
|
||||
EXPECT_EQ(ptr->Value(), a.Value());
|
||||
}
|
||||
|
||||
TEST(NoBarrierAtomicValue, ConstructionVoidStar) {
|
||||
NoBarrierAtomicValue<void*> a(nullptr);
|
||||
void* b = nullptr;
|
||||
NoBarrierAtomicValue<void*>* ptr =
|
||||
NoBarrierAtomicValue<void*>::FromAddress(&b);
|
||||
EXPECT_EQ(ptr->Value(), a.Value());
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
enum TestSetValue { kAA, kBB, kCC, kLastValue = kCC };
|
||||
|
||||
} // namespace
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, Constructor) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
EXPECT_TRUE(a.IsEmpty());
|
||||
EXPECT_FALSE(a.Contains(kAA));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, AddSingle) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
a.Add(kAA);
|
||||
EXPECT_FALSE(a.IsEmpty());
|
||||
EXPECT_TRUE(a.Contains(kAA));
|
||||
EXPECT_FALSE(a.Contains(kBB));
|
||||
EXPECT_FALSE(a.Contains(kCC));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, AddOtherSet) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
AtomicEnumSet<TestSetValue> b;
|
||||
a.Add(kAA);
|
||||
EXPECT_FALSE(a.IsEmpty());
|
||||
EXPECT_TRUE(b.IsEmpty());
|
||||
b.Add(a);
|
||||
EXPECT_FALSE(b.IsEmpty());
|
||||
EXPECT_TRUE(a.Contains(kAA));
|
||||
EXPECT_TRUE(b.Contains(kAA));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, RemoveSingle) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
a.Add(kAA);
|
||||
a.Add(kBB);
|
||||
EXPECT_TRUE(a.Contains(kAA));
|
||||
EXPECT_TRUE(a.Contains(kBB));
|
||||
a.Remove(kAA);
|
||||
EXPECT_FALSE(a.Contains(kAA));
|
||||
EXPECT_TRUE(a.Contains(kBB));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, RemoveOtherSet) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
AtomicEnumSet<TestSetValue> b;
|
||||
a.Add(kAA);
|
||||
a.Add(kBB);
|
||||
b.Add(kBB);
|
||||
a.Remove(b);
|
||||
EXPECT_TRUE(a.Contains(kAA));
|
||||
EXPECT_FALSE(a.Contains(kBB));
|
||||
EXPECT_FALSE(a.Contains(kCC));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, RemoveEmptySet) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
AtomicEnumSet<TestSetValue> b;
|
||||
a.Add(kAA);
|
||||
a.Add(kBB);
|
||||
EXPECT_TRUE(a.Contains(kAA));
|
||||
EXPECT_TRUE(a.Contains(kBB));
|
||||
EXPECT_FALSE(a.Contains(kCC));
|
||||
EXPECT_TRUE(b.IsEmpty());
|
||||
a.Remove(b);
|
||||
EXPECT_TRUE(a.Contains(kAA));
|
||||
EXPECT_TRUE(a.Contains(kBB));
|
||||
EXPECT_FALSE(a.Contains(kCC));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, Intersect) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
AtomicEnumSet<TestSetValue> b;
|
||||
a.Add(kAA);
|
||||
b.Add(kCC);
|
||||
a.Intersect(b);
|
||||
EXPECT_TRUE(a.IsEmpty());
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, ContainsAnyOf) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
AtomicEnumSet<TestSetValue> b;
|
||||
a.Add(kAA);
|
||||
b.Add(kCC);
|
||||
EXPECT_FALSE(a.ContainsAnyOf(b));
|
||||
b.Add(kAA);
|
||||
EXPECT_TRUE(a.ContainsAnyOf(b));
|
||||
}
|
||||
|
||||
|
||||
TEST(AtomicEnumSet, Equality) {
|
||||
AtomicEnumSet<TestSetValue> a;
|
||||
AtomicEnumSet<TestSetValue> b;
|
||||
a.Add(kAA);
|
||||
EXPECT_FALSE(a == b);
|
||||
EXPECT_TRUE(a != b);
|
||||
b.Add(kAA);
|
||||
EXPECT_TRUE(a == b);
|
||||
EXPECT_FALSE(a != b);
|
||||
}
|
||||
|
||||
} // namespace base
|
||||
} // namespace v8
|
||||
|
Loading…
Reference in New Issue
Block a user