Skip to content

Commit a76448c

Browse files
authored
[Clang] Fix replaceability/relocatability computation (#145655)
for eligible classes with user provided constructor or `operator=` Fixes #144232
1 parent c92b580 commit a76448c

File tree

2 files changed

+38
-2
lines changed

2 files changed

+38
-2
lines changed

clang/lib/Sema/SemaTypeTraits.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -121,7 +121,7 @@ static bool hasSuitableConstructorForRelocation(Sema &SemaRef,
121121

122122
CXXMethodDecl *Decl =
123123
LookupSpecialMemberFromXValue(SemaRef, D, /*Assign=*/false);
124-
return Decl && Decl->isUserProvided() == AllowUserDefined &&
124+
return Decl && (AllowUserDefined || !Decl->isUserProvided()) &&
125125
!Decl->isDeleted();
126126
}
127127

@@ -137,7 +137,7 @@ static bool hasSuitableMoveAssignmentOperatorForRelocation(
137137
if (!Decl)
138138
return false;
139139

140-
return Decl && Decl->isUserProvided() == AllowUserDefined &&
140+
return Decl && (AllowUserDefined || !Decl->isUserProvided()) &&
141141
!Decl->isDeleted();
142142
}
143143

clang/test/SemaCXX/cxx2c-trivially-relocatable.cpp

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -410,3 +410,39 @@ C& C::operator=(const C&) = default;
410410
static_assert (!__builtin_is_cpp_trivially_relocatable(C));
411411
static_assert (!__builtin_is_replaceable(C));
412412
}
413+
414+
namespace GH144232 {
415+
416+
struct E trivially_relocatable_if_eligible replaceable_if_eligible {
417+
E (E &&);
418+
E &operator= (E &&) = default;
419+
};
420+
421+
struct F trivially_relocatable_if_eligible replaceable_if_eligible {
422+
F (F &&) = default;
423+
F &operator= (F &&);
424+
};
425+
426+
struct G trivially_relocatable_if_eligible replaceable_if_eligible { G (G const &) = default; };
427+
428+
struct I trivially_relocatable_if_eligible replaceable_if_eligible { I &operator= (const I &) = default; };
429+
430+
struct J trivially_relocatable_if_eligible replaceable_if_eligible { J (J const &); };
431+
struct K trivially_relocatable_if_eligible replaceable_if_eligible { K (K const &); };
432+
433+
434+
435+
static_assert (__builtin_is_replaceable (E));
436+
static_assert (__builtin_is_cpp_trivially_relocatable(E));
437+
static_assert (__builtin_is_replaceable (F));
438+
static_assert (__builtin_is_cpp_trivially_relocatable(F));
439+
static_assert (__builtin_is_replaceable (G));
440+
static_assert (__builtin_is_cpp_trivially_relocatable(G));
441+
static_assert (__builtin_is_replaceable (I));
442+
static_assert (__builtin_is_cpp_trivially_relocatable(I));
443+
static_assert (__builtin_is_replaceable (J));
444+
static_assert (__builtin_is_cpp_trivially_relocatable(J));
445+
static_assert (__builtin_is_replaceable (K));
446+
static_assert (__builtin_is_cpp_trivially_relocatable(K));
447+
448+
}

0 commit comments

Comments
 (0)