summaryrefslogtreecommitdiffstats
path: root/clang/lib/CodeGen/MicrosoftCXXABI.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/CodeGen/MicrosoftCXXABI.cpp')
-rw-r--r--clang/lib/CodeGen/MicrosoftCXXABI.cpp39
1 files changed, 28 insertions, 11 deletions
diff --git a/clang/lib/CodeGen/MicrosoftCXXABI.cpp b/clang/lib/CodeGen/MicrosoftCXXABI.cpp
index 869734ab4e4..f22b96a6a07 100644
--- a/clang/lib/CodeGen/MicrosoftCXXABI.cpp
+++ b/clang/lib/CodeGen/MicrosoftCXXABI.cpp
@@ -44,17 +44,7 @@ public:
return !RD->isPOD();
}
- RecordArgABI getRecordArgABI(const CXXRecordDecl *RD) const override {
- if (RD->hasNonTrivialCopyConstructor() || RD->hasNonTrivialDestructor()) {
- llvm::Triple::ArchType Arch = CGM.getTarget().getTriple().getArch();
- if (Arch == llvm::Triple::x86)
- return RAA_DirectInMemory;
- // On x64, pass non-trivial records indirectly.
- // FIXME: Test other Windows architectures.
- return RAA_Indirect;
- }
- return RAA_Default;
- }
+ RecordArgABI getRecordArgABI(const CXXRecordDecl *RD) const override;
StringRef GetPureVirtualCallName() override { return "_purecall"; }
// No known support for deleted functions in MSVC yet, so this choice is
@@ -407,6 +397,33 @@ private:
}
+CGCXXABI::RecordArgABI
+MicrosoftCXXABI::getRecordArgABI(const CXXRecordDecl *RD) const {
+ switch (CGM.getTarget().getTriple().getArch()) {
+ default:
+ // FIXME: Implement for other architectures.
+ return RAA_Default;
+
+ case llvm::Triple::x86:
+ // 32-bit x86 constructs non-trivial objects directly in outgoing argument
+ // slots. LLVM uses the inalloca attribute to implement this.
+ if (RD->hasNonTrivialCopyConstructor() || RD->hasNonTrivialDestructor())
+ return RAA_DirectInMemory;
+ return RAA_Default;
+
+ case llvm::Triple::x86_64:
+ // Win64 passes objects with non-trivial copy ctors indirectly.
+ if (RD->hasNonTrivialCopyConstructor())
+ return RAA_Indirect;
+ // Win64 passes objects larger than 8 bytes indirectly.
+ if (getContext().getTypeSize(RD->getTypeForDecl()) > 64)
+ return RAA_Indirect;
+ return RAA_Default;
+ }
+
+ llvm_unreachable("invalid enum");
+}
+
llvm::Value *MicrosoftCXXABI::adjustToCompleteObject(CodeGenFunction &CGF,
llvm::Value *ptr,
QualType type) {
OpenPOWER on IntegriCloud