diff options
author | Peter Collingbourne <peter@pcc.me.uk> | 2016-11-22 00:21:43 +0000 |
---|---|---|
committer | Peter Collingbourne <peter@pcc.me.uk> | 2016-11-22 00:21:43 +0000 |
commit | aea11161bc7db9f21babdf095ae757b78dafba11 (patch) | |
tree | fdb70544e1be12f5cef549be77171c4e339a4de0 /test/CodeGenCXX/uncopyable-args.cpp | |
parent | 0e90760c2c0f65118c85c16025838600b3fb11b5 (diff) |
Sema, CodeGen: Ensure that an implicit copy ctor is available more often under the Microsoft C++ ABI.
This is needed because whether the constructor is deleted can control whether
we pass structs by value directly.
To fix this properly we probably want a more direct way for CodeGen to ask
whether the constructor was deleted.
Fixes PR31049.
Differential Revision: https://reviews.llvm.org/D26822
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@287600 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'test/CodeGenCXX/uncopyable-args.cpp')
-rw-r--r-- | test/CodeGenCXX/uncopyable-args.cpp | 61 |
1 files changed, 61 insertions, 0 deletions
diff --git a/test/CodeGenCXX/uncopyable-args.cpp b/test/CodeGenCXX/uncopyable-args.cpp index c1d284a741..9cd57dd01c 100644 --- a/test/CodeGenCXX/uncopyable-args.cpp +++ b/test/CodeGenCXX/uncopyable-args.cpp @@ -204,3 +204,64 @@ void bar() { // WIN64-LABEL: declare void @"\01?foo@two_copy_ctors@@YAXUB@1@@Z"(%"struct.two_copy_ctors::B"*) } + +namespace definition_only { +struct A { + A(); + A(A &&o); + void *p; +}; +void *foo(A a) { return a.p; } +// WIN64-LABEL: define i8* @"\01?foo@definition_only@@YAPEAXUA@1@@Z"{{.*}} +// WIN64-NEXT: : +// WIN64-NEXT: getelementptr +// WIN64-NEXT: load +} + +namespace deleted_by_member { +struct B { + B(); + B(B &&o); + void *p; +}; +struct A { + A(); + B b; +}; +void *foo(A a) { return a.b.p; } +// WIN64-LABEL: define i8* @"\01?foo@deleted_by_member@@YAPEAXUA@1@@Z"{{.*}} +// WIN64-NEXT: : +// WIN64-NEXT: getelementptr +// WIN64-NEXT: getelementptr +// WIN64-NEXT: load +} + +namespace deleted_by_base { +struct B { + B(); + B(B &&o); + void *p; +}; +struct A : B { + A(); +}; +void *foo(A a) { return a.p; } +// WIN64-LABEL: define i8* @"\01?foo@deleted_by_base@@YAPEAXUA@1@@Z"{{.*}} +// WIN64-NEXT: : +// WIN64-NEXT: bitcast +// WIN64-NEXT: getelementptr +// WIN64-NEXT: load +} + +namespace explicit_delete { +struct A { + A(); + A(const A &o) = delete; + void *p; +}; +// WIN64-LABEL: define i8* @"\01?foo@explicit_delete@@YAPEAXUA@1@@Z"{{.*}} +// WIN64-NEXT: : +// WIN64-NEXT: getelementptr +// WIN64-NEXT: load +void *foo(A a) { return a.p; } +} |