Skip to content

Commit e9ca8d1

Browse files
ezbrcopybara-github
authored andcommitted
Distinguish the debug message for the case of self-move-assigned swiss tables.
PiperOrigin-RevId: 671484965 Change-Id: Ia1da7db0db1f776d48c74efaeab7252445208088
1 parent 043fe3c commit e9ca8d1

File tree

2 files changed

+16
-7
lines changed

2 files changed

+16
-7
lines changed

absl/container/internal/raw_hash_set.h

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -545,7 +545,10 @@ enum InvalidCapacity : size_t {
545545
kAboveMaxValidCapacity = ~size_t{} - 100,
546546
kReentrance,
547547
kDestroyed,
548+
549+
// These two must be last because we use `>= kMovedFrom` to mean moved-from.
548550
kMovedFrom,
551+
kSelfMovedFrom,
549552
};
550553

551554
// Returns a pointer to a control byte group that can be used by empty tables.
@@ -2911,7 +2914,7 @@ class raw_hash_set {
29112914

29122915
ABSL_ATTRIBUTE_REINITIALIZES void clear() {
29132916
if (SwisstableGenerationsEnabled() &&
2914-
capacity() == InvalidCapacity::kMovedFrom) {
2917+
capacity() >= InvalidCapacity::kMovedFrom) {
29152918
common().set_capacity(DefaultCapacity());
29162919
}
29172920
AssertNotDebugCapacity();
@@ -3596,7 +3599,7 @@ class raw_hash_set {
35963599

35973600
inline void destructor_impl() {
35983601
if (SwisstableGenerationsEnabled() &&
3599-
capacity() == InvalidCapacity::kMovedFrom) {
3602+
capacity() >= InvalidCapacity::kMovedFrom) {
36003603
return;
36013604
}
36023605
if (capacity() == 0) return;
@@ -3778,7 +3781,8 @@ class raw_hash_set {
37783781
// than using NDEBUG) to avoid issues in which NDEBUG is enabled in some
37793782
// translation units but not in others.
37803783
if (SwisstableGenerationsEnabled()) {
3781-
that.common().set_capacity(InvalidCapacity::kMovedFrom);
3784+
that.common().set_capacity(this == &that ? InvalidCapacity::kSelfMovedFrom
3785+
: InvalidCapacity::kMovedFrom);
37823786
}
37833787
if (!SwisstableGenerationsEnabled() || capacity() == DefaultCapacity() ||
37843788
capacity() > kAboveMaxValidCapacity) {
@@ -3908,7 +3912,12 @@ class raw_hash_set {
39083912
assert(capacity() != InvalidCapacity::kDestroyed &&
39093913
"Use of destroyed hash table.");
39103914
if (SwisstableGenerationsEnabled() &&
3911-
ABSL_PREDICT_FALSE(capacity() == InvalidCapacity::kMovedFrom)) {
3915+
ABSL_PREDICT_FALSE(capacity() >= InvalidCapacity::kMovedFrom)) {
3916+
if (capacity() == InvalidCapacity::kSelfMovedFrom) {
3917+
// If this log triggers, then a hash table was move-assigned to itself
3918+
// and then used again later without being reinitialized.
3919+
ABSL_RAW_LOG(FATAL, "Use of self-move-assigned hash table.");
3920+
}
39123921
ABSL_RAW_LOG(FATAL, "Use of moved-from hash table.");
39133922
}
39143923
}

absl/container/internal/raw_hash_set_test.cc

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2093,7 +2093,7 @@ TEST(Table, MoveSelfAssign) {
20932093
t = std::move(*&t);
20942094
if (SwisstableGenerationsEnabled()) {
20952095
// NOLINTNEXTLINE(bugprone-use-after-move)
2096-
EXPECT_DEATH_IF_SUPPORTED(t.contains("a"), "");
2096+
EXPECT_DEATH_IF_SUPPORTED(t.contains("a"), "self-move-assigned");
20972097
}
20982098
// As long as we don't crash, it's fine.
20992099
}
@@ -3689,14 +3689,14 @@ TEST(Table, MovedFromCallsFail) {
36893689
t1.insert(1);
36903690
t2 = std::move(t1);
36913691
// NOLINTNEXTLINE(bugprone-use-after-move)
3692-
EXPECT_DEATH_IF_SUPPORTED(t1.contains(1), "");
3692+
EXPECT_DEATH_IF_SUPPORTED(t1.contains(1), "moved-from");
36933693
}
36943694
{
36953695
ABSL_ATTRIBUTE_UNUSED IntTable t1;
36963696
t1.insert(1);
36973697
ABSL_ATTRIBUTE_UNUSED IntTable t2(std::move(t1));
36983698
// NOLINTNEXTLINE(bugprone-use-after-move)
3699-
EXPECT_DEATH_IF_SUPPORTED(t1.contains(1), "");
3699+
EXPECT_DEATH_IF_SUPPORTED(t1.contains(1), "moved-from");
37003700
t1.clear(); // Clearing a moved-from table is allowed.
37013701
}
37023702
}

0 commit comments

Comments
 (0)